📄 maphrcnv.c
字号:
dBlkFnum = (UINT32)(((pCi->dRegH & ~0x20L) << 8)
| (pCi->dRegL | 0x80000000));
if((pCi->dRegH & 0x20L) == 0x20L) {
MaSndDrv_SetCommand(gPhrInfo.sdSeqId, -1L,
MASNDDRV_CMD_NOTE_ON_MA2EX, dCh, dBlkFnum, 0x7FL);
}
else {
MaSndDrv_SetCommand(gPhrInfo.sdSeqId, -1L,
MASNDDRV_CMD_NOTE_OFF_MA2EX, dCh, dBlkFnum, 0L);
}
sdRet++;
}
}
else if((pbExMsg[0] == 0x43) &&
(pbExMsg[1] == 0x04) &&
(pbExMsg[2] == 0x02) &&
(pbExMsg[5] == 0xF7)) { /* Pitch Bend Range */
dCh = (UINT32)((pbExMsg[3] & 0x03) + (dPhrCh << 2));
PitchBendRange(dCh, pbExMsg[4]);
}
return (sdRet);
}
/****************************************************************************
* CnvAllSoundOff
*
* Function:
* Put AllSoundOff to sound driver.
* Argument:
* dCh #Channel(0..15)
* Return:
* Number of put command.
*
****************************************************************************/
static SINT32 CnvAllSoundOff(UINT32 dCh)
{
MaSndDrv_SetCommand(gPhrInfo.sdSeqId, -1L,
MASNDDRV_CMD_ALL_SOUND_OFF, dCh, 0L, 0L);
gPhrInfo.sChInfo[dCh].dNoteOffTime = 0xFFFFFFFF;
return (1L);
}
/****************************************************************************
* CnvAllNoteOff
*
* Function:
* Put AllNoteOff to sound driver.
* Argument:
* dCh #Channel(0..15)
* Return:
* Number of put command.
*
****************************************************************************/
static SINT32 CnvAllNoteOff(UINT32 dCh)
{
MaSndDrv_SetCommand(gPhrInfo.sdSeqId, -1L,
MASNDDRV_CMD_ALL_NOTE_OFF, dCh, 0L, 0L);
gPhrInfo.sChInfo[dCh].dNoteOffTime = 0xFFFFFFFF;
return (1L);
}
/****************************************************************************
* PutInitPhraseMessage
*
* Function:
* Put initialize command to sound driver.
* Argument:
* bPhrCh Sequence Number(0..3)
* Return:
* Number of put command.
*
****************************************************************************/
static SINT32 PutInitPhraseMessage(UINT32 dPhrCh)
{
UINT32 i;
UINT32 dCh;
SINT32 sdRet;
PMAPHRCHINFO pCi;
MAPHRCNV_DBGMSG(("PutInitPhraseMessage[%ld] \n", dPhrCh));
sdRet = 0L;
for(i = 0; i < MAPHR_MAX_SLOT; i++) {
dCh = (UINT32)(i + (dPhrCh << 2));
pCi = &(gPhrInfo.sChInfo[dCh]);
/* Direct ON */
MaSndDrv_SetCommand(gPhrInfo.sdSeqId, -1L,
MASNDDRV_CMD_VOL_DIRECT, dCh, 0L, 0L);
/* All Sound Off */
MaSndDrv_SetCommand(gPhrInfo.sdSeqId, -1L,
MASNDDRV_CMD_ALL_SOUND_OFF, dCh, 0L, 0L);
/* Program Change */
if(gPhrInfo.sApiInfo[dPhrCh].sDataInfo.dVersion == (UINT32)MAPHR_VERSION_LV2)
sdRet += CnvProgramChange2(dCh, pCi->dProgNo);
else
sdRet += CnvProgramChange(dCh, pCi->dProgNo);
/* Channel Volume */
MaSndDrv_SetCommand(gPhrInfo.sdSeqId, -1L,
MASNDDRV_CMD_CHANNEL_VOLUME, dCh, pCi->dVolume, 0L);
/* Expression */
MaSndDrv_SetCommand(gPhrInfo.sdSeqId, -1L,
MASNDDRV_CMD_EXPRESSION, dCh, pCi->dExp, 0L);
/* Panpot */
MaSndDrv_SetCommand(gPhrInfo.sdSeqId, -1L,
MASNDDRV_CMD_PANPOT, dCh, pCi->dPan, 0L);
/* Modulation */
MaSndDrv_SetCommand(gPhrInfo.sdSeqId, -1L,
MASNDDRV_CMD_MODULATION_DEPTH, dCh, pCi->dMod, 0L);
/* BendRange */
MaSndDrv_SetCommand(gPhrInfo.sdSeqId, -1L,
MASNDDRV_CMD_BEND_RANGE, dCh, pCi->dRange, 0L);
/* PitchBend */
MaSndDrv_SetCommand(gPhrInfo.sdSeqId, -1L,
MASNDDRV_CMD_PITCH_BEND, dCh, (UINT32)(pCi->dPitch << 7), 0L);
/* Direct OFF */
MaSndDrv_SetCommand(gPhrInfo.sdSeqId, -1L,
MASNDDRV_CMD_VOL_DIRECT, dCh, 1L, 0L);
sdRet += 9L;
}
return (sdRet);
}
/****************************************************************************
* InitPhraseInfo
*
* Function:
* Initialize MAPHRDATAINFO structure.
* Argument:
* pPi pointer to MALIBPHRINFO
* Return:
*
*
****************************************************************************/
static void InitPhraseInfo(PMALIBPHRINFO pPi)
{
UINT32 i;
PMALIBVOCINFO pVi;
pPi->dErrChk = 0L;
pPi->dVersion = 0L;
pPi->pbVoice = NULL;
pPi->pbSeq = NULL;
pPi->dVoiceSize = 0L;
pPi->dSeqSize = 0L;
pPi->dPlayTime = 0L;
pPi->dTimer = 0L;
pPi->dCurrentTime = 0L;
pPi->dDataPosition = 0L;
for(i = 0; i < 16; i++) {
pVi = &(pPi->sVocInfo[i]);
pVi->dBankNo = 0xFFFFFFFF;
pVi->dProgNo = 0xFFFFFFFF;
}
}
/****************************************************************************
* InitApiInfo
*
* Function:
* Initialize MAPHRAPIINFO structure.
* Argument:
* bPhrCh Sequence Number(0..3)
* Return:
*
*
****************************************************************************/
static void InitApiInfo(UINT32 dPhrCh)
{
PMAPHRAPIINFO pAi;
if(MAPHR_MAX_CHANNEL <= dPhrCh) return;
pAi = &(gPhrInfo.sApiInfo[dPhrCh]);
pAi->Status = MAPHR_STATUS_NODATA;
pAi->dVolume = 100L;
pAi->dPan = 64L;
pAi->sdMasterChannel = -1L;
pAi->dSlave = 0L;
pAi->dLoopCount = 0L;
pAi->dLength = 0L;
pAi->dRamAdr = 0L;
pAi->dRamEndAdr = 0L;
InitPhraseInfo(&(pAi->sDataInfo));
}
/****************************************************************************
* InitChInfo
*
* Function:
* Initialize MAPHRCHINFO structure.
* Argument:
* dCh #Channel(0..15)
* Return:
*
*
****************************************************************************/
static void InitChInfo(UINT32 dCh)
{
PMAPHRCHINFO pCi = &(gPhrInfo.sChInfo[dCh]);
pCi->dKey = 0L;
pCi->dVelocity = 127L;
pCi->dProgNo = 0L;
pCi->dBankNo = 1L;
pCi->dNewBank = 1L;
pCi->dVolume = 100L;
pCi->dMod = 0L;
pCi->dRange = 2L;
pCi->dNewRange = 2L;
pCi->dPitch = 64L;
pCi->dExNoteFlag = 0x00L;
pCi->dRegH = 0x00L;
pCi->dRegL = 0x00L;
pCi->sdOctShift = 0L;
pCi->dNoteOffTime = 0xFFFFFFFF;
pCi->dPan = gPhrInfo.sApiInfo[dCh >> 2].dPan;
pCi->dExp = gPhrInfo.sApiInfo[dCh >> 2].dVolume;
}
/****************************************************************************
* Callback
*
* Function:
* Callback.
* Argument:
* dCh Sequence Number(0..3)
* dEvent Event Number
* Return:
* 0 success.
*
****************************************************************************/
static SINT32 Callback(UINT32 dCh, UINT32 dEvent)
{
struct event eve;
if(gPhrInfo.pfnEvHandler != NULL) {
eve.ch = (int)dCh;
eve.mode = (int)dEvent;
gPhrInfo.pfnEvHandler(&eve);
}
return (MASMW_SUCCESS);
}
/****************************************************************************
* Seek1
*
* Function:
* Seek(for LV1).
* Argument:
* dPhrCh Sequence Number(0..3)
* dPos Seek Position[ms]
* Return:
* 0 success.
* < 0 error code.
*
****************************************************************************/
static SINT32 Seek1(UINT32 dPhrCh, UINT32 dPos)
{
UINT8* pbExMsg;
UINT32 i;
UINT32 dCh;
UINT32 dTmp;
UINT32 dData;
UINT32 dSeekTime;
UINT32 dCurrent;
UINT32 dDuration;
PMAPHRCHINFO pCi;
PMALIBPHRINFO pDi;
MAPHRCNV_DBGMSG(("Seek1[%08lX %08lX %08lX] \n", dPhrCh, dPos, gPhrInfo.dPlayStatus));
dSeekTime = (UINT32)(dPos / MASMW_DIRECT_BASETIME);
pDi = &(gPhrInfo.sApiInfo[dPhrCh].sDataInfo);
if(dSeekTime >= pDi->dPlayTime) {
return (MASMW_ERROR);
}
/* Seek to head position */
pDi->dTimer = 0L;
pDi->dCurrentTime = 0L;
pDi->dDataPosition = 0L;
/* Initialize each channel info */
for(i = 0; i < MAPHR_MAX_SLOT; i++) {
dCh = (UINT32)(i + (dPhrCh << 2));
InitChInfo(dCh);
}
/* Seek the position */
while(pDi->dSeqSize > pDi->dDataPosition) {
/* Get Current Time */
dCurrent = pDi->dDataPosition;
dDuration = (UINT32)pDi->pbSeq[dCurrent++];
if(dDuration & 0x80) {
dDuration = (UINT32)(((dDuration & 0x7FL) << 7) +
(UINT32)pDi->pbSeq[dCurrent++] + 128L);
}
if((pDi->dCurrentTime + dDuration) >= dSeekTime) {
pDi->dTimer = dSeekTime;
break;
}
/* Update position & time */
pDi->dDataPosition = dCurrent;
pDi->dCurrentTime += dDuration;
dData = (UINT32)pDi->pbSeq[pDi->dDataPosition++];
switch(dData) {
case 0x00L :
dData = pDi->pbSeq[pDi->dDataPosition++];
dCh = (UINT32)(((dData & 0xC0) >> 6) + (dPhrCh << 2));
pCi = &(gPhrInfo.sChInfo[dCh]);
dTmp = (UINT32)(dData & 0x0FL);
switch(dData & 0x30L) {
case 0x00L : /* Short type Volume */
pCi->dVolume = gdShortVolTable[dTmp];
break;
case 0x10L : /* Short type PitchBend */
break;
case 0x20L : /* Short type Modulation */
pCi->dMod = gdShortModTable[dTmp];
break;
case 0x30 :
dData = (UINT32)pDi->pbSeq[pDi->dDataPosition++];
switch(dTmp) {
case 0x00L : /* Program Change */
pCi->dProgNo = (UINT32)(dData & 0x03L);
break;
case 0x02L : /* Octave Shift */
OctaveShift(dCh, dData);
break;
case 0x04L : /* Pitch Bend */
pCi->dRange = pCi->dNewRange;
pCi->dPitch = (UINT32)(dData & 0x7FL);
break;
case 0x0AL : /* Panpot */
pCi->dPan = (UINT32)(dData & 0x7FL);
break;
case 0x0BL : /* Normal type Volume */
pCi->dVolume = (UINT32)(dData & 0x7FL);
break;
default :
break;
}
break;
default :
break;
}
break;
case 0xFF :
dData = (UINT32)pDi->pbSeq[pDi->dDataPosition++];
if(dData == 0xF0L) { /* Exclusive Message */
dTmp = (UINT32)pDi->pbSeq[pDi->dDataPosition++];
pbExMsg = &(pDi->pbSeq[pDi->dDataPosition]);
if( (dTmp == 6L) &&
(pbExMsg[0] == 0x43) &&
(pbExMsg[1] == 0x03) &&
(pbExMsg[2] == 0x90) &&
(pbExMsg[5] == 0xF7)) { /* Extend NoteOn/Off */
dCh = (UINT32)((pbExMsg[3] & 0x03) + (dPhrCh << 2));
pCi = &(gPhrInfo.sChInfo[dCh]);
if((pbExMsg[3] & 0xF0) == 0xC0) {
pCi->dExNoteFlag |= 0x02L;
pCi->dRegH = (UINT32)pbExMsg[4];
}
else if((pbExMsg[3] & 0xF0) == 0xB0) {
pCi->dExNoteFlag |= 0x01L;
pCi->dRegL = (UINT32)pbExMsg[4];
}
}
else if((dTmp == 6L) &&
(pbExMsg[0] == 0x43) &&
(pbExMsg[1] == 0x04) &&
(pbExMsg[2] == 0x02) &&
(pbExMsg[4] <= 24) &&
(pbExMsg[5] == 0xF7)) { /* Pitch Bend Range */
dCh = (UINT32)((pbExMsg[3] & 0x03) + (dPhrCh << 2));
pCi = &(gPhrInfo.sChInfo[dCh]);
pCi->dNewRange = (UINT32)pbExMsg[4];
}
/* skip exclusive message */
pDi->dDataPosition += dTmp;
}
break;
default :
dDuration = (UINT32)pDi->pbSeq[pDi->dDataPosition++];
if(dDuration & 0x80L) {
pDi->dDataPosition++;
}
break;
}
}
return (MASMW_SUCCESS);
}
/****************************************************************************
* Seek2
*
* Function:
* Seek(for LV2)
* Argument:
* dPhrCh Sequence Number(0..3)
* dPos Seek Position[ms]
* Return:
* 0 success.
* < 0 error code.
*
****************************************************************************/
static SINT32 Seek2(UINT32 dPhrCh, UINT32 dPos)
{
UINT32 i;
UINT32 dCh;
UINT32 dTmp;
UINT32 dData;
UINT32 dSeekTime;
UINT32 dCurrent;
UINT32 dDuration;
PMAPHRCHINFO pCi;
PMALIBPHRINFO pDi;
MAPHRCNV_DBGMSG(("Seek2[%08lX %08lX %08lX] \n", dPhrCh, dPos, gPhrInfo.dPlayStatus));
dSeekTime = (UINT32)(dPos / MASMW_DIRECT_BASETIME);
pDi = &(gPhrInfo.sApiInfo[dPhrCh].sDataInfo);
if(dSeekTime >= pDi->dPlayTime) {
return (MASMW_ERROR);
}
/* Seek to head position */
pDi->dTimer = 0L;
pDi->dCurrentTime = 0L;
pDi->dDataPosition = 0L;
/* Initialize each channel info */
for(i = 0; i < MAPHR_MAX_SLOT; i++) {
dCh = (UINT32)(i + (dPhrCh << 2));
InitChInfo(dCh);
}
/* Seek the position */
while(pDi->dSeqSize > pDi->dDataPosition) {
/* Get Current Time */
dCurrent = pDi->dDataPosition;
dDuration = (UINT32)pDi->pbSeq[dCurrent++];
if(dDuration & 0x80L) {
dDuration = (UINT32)(((dDuration & 0x7FL) << 7) +
(UINT32)pDi->pbSeq[dCurrent++] + 128L);
}
if((pDi->dCurrentTime + dDuration) >= dSeekTime) {
pDi->dTimer = dSeekTime;
break;
}
/* Update position & time */
pDi->dDataPosition = dCurrent;
pDi->dCurrentTime += dDuration;
dData = (UINT32)pDi->pbSeq[pDi->dDataPosition++];
switch(dData) {
case 0x00L :
dData = pDi->pbSeq[pDi->dDataPosition++];
dCh = (UINT32)(((dData & 0xC0) >> 6) + (dPhrCh << 2));
pCi = &(gPhrInfo.sChInfo[dCh]);
dTmp = (UINT32)(dData & 0x0FL);
switch(dData & 0x30) {
case 0x00L : /* Short type Volume */
if((0L < dTmp) && (dTmp < 15L)) {
pCi->dVolume = gdShortVolTable[dTmp];
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -