mirror of
https://github.com/tildearrow/furnace.git
synced 2024-11-16 01:35:07 +00:00
ADSFGGGGGJKSDGHASLJKFHL
This commit is contained in:
parent
2c7abb4635
commit
a0dc9de262
4 changed files with 72 additions and 38 deletions
|
@ -94,12 +94,15 @@ void DivPlatformSNES::tick(bool sysTick) {
|
||||||
unsigned char kon=0;
|
unsigned char kon=0;
|
||||||
unsigned char koff=0;
|
unsigned char koff=0;
|
||||||
for (int i=0; i<8; i++) {
|
for (int i=0; i<8; i++) {
|
||||||
DivInstrument* ins=parent->getIns(chan[i].ins,DIV_INS_AMIGA);
|
//bool hadGain=chan[i].std.vol.had || chan[i].std.ex1.had || chan[i].std.ex2.had;
|
||||||
bool hadGain=chan[i].std.vol.had || chan[i].std.ex1.had || chan[i].std.ex2.had;
|
|
||||||
chan[i].std.next();
|
chan[i].std.next();
|
||||||
if (ins->type==DIV_INS_AMIGA && chan[i].std.vol.had) {
|
if (chan[i].std.vol.had) {
|
||||||
|
chan[i].outVol=VOL_SCALE_LOG(chan[i].vol&127,MIN(127,chan[i].std.vol.val),127);
|
||||||
|
}
|
||||||
|
/*
|
||||||
|
if (chan[i].std.vol.had) {
|
||||||
chWrite(i,7,MIN(127,chan[i].std.vol.val*2));
|
chWrite(i,7,MIN(127,chan[i].std.vol.val*2));
|
||||||
} else if (!chan[i].useEnv && hadGain) {
|
} else if (!chan[i].state.useEnv && hadGain) {
|
||||||
if (chan[i].std.ex1.val==0) {
|
if (chan[i].std.ex1.val==0) {
|
||||||
// direct gain
|
// direct gain
|
||||||
chWrite(i,7,chan[i].std.vol.val);
|
chWrite(i,7,chan[i].std.vol.val);
|
||||||
|
@ -107,7 +110,7 @@ void DivPlatformSNES::tick(bool sysTick) {
|
||||||
// inc/dec
|
// inc/dec
|
||||||
chWrite(i,7,chan[i].std.ex2.val|((chan[i].std.ex1.val-1)<<5)|0x80);
|
chWrite(i,7,chan[i].std.ex2.val|((chan[i].std.ex1.val-1)<<5)|0x80);
|
||||||
}
|
}
|
||||||
}
|
}*/
|
||||||
if (chan[i].std.arp.had) {
|
if (chan[i].std.arp.had) {
|
||||||
if (!chan[i].inPorta) {
|
if (!chan[i].inPorta) {
|
||||||
if (chan[i].std.arp.mode) {
|
if (chan[i].std.arp.mode) {
|
||||||
|
@ -146,7 +149,7 @@ void DivPlatformSNES::tick(bool sysTick) {
|
||||||
int val=chan[i].std.panR.val&0x7f;
|
int val=chan[i].std.panR.val&0x7f;
|
||||||
chan[i].panR=(val<<1)|(val>>6);
|
chan[i].panR=(val<<1)|(val>>6);
|
||||||
}
|
}
|
||||||
if (chan[i].std.panL.had || chan[i].std.panR.had) {
|
if (chan[i].std.vol.had || chan[i].std.panL.had || chan[i].std.panR.had) {
|
||||||
writeOutVol(i);
|
writeOutVol(i);
|
||||||
}
|
}
|
||||||
if (chan[i].setPos) {
|
if (chan[i].setPos) {
|
||||||
|
@ -168,12 +171,29 @@ void DivPlatformSNES::tick(bool sysTick) {
|
||||||
if (chan[i].freq>16383) chan[i].freq=16383;
|
if (chan[i].freq>16383) chan[i].freq=16383;
|
||||||
if (chan[i].keyOn) {
|
if (chan[i].keyOn) {
|
||||||
unsigned int start, end, loop;
|
unsigned int start, end, loop;
|
||||||
size_t tabAddr=sampleTableAddr(i);
|
unsigned short tabAddr=sampleTableAddr(i);
|
||||||
if (chan[i].useEnv) {
|
if (chan[i].state.useEnv) {
|
||||||
chWrite(i,5,ins->snes.a|(ins->snes.d<<4)|0x80);
|
chWrite(i,5,chan[i].state.a|(chan[i].state.d<<4)|0x80);
|
||||||
chWrite(i,6,ins->snes.r|(ins->snes.s<<5));
|
chWrite(i,6,chan[i].state.r|(chan[i].state.s<<5));
|
||||||
} else {
|
} else {
|
||||||
chWrite(i,5,0);
|
chWrite(i,5,0);
|
||||||
|
switch (chan[i].state.gainMode) {
|
||||||
|
case DivInstrumentSNES::GAIN_MODE_DIRECT:
|
||||||
|
chWrite(i,7,chan[i].state.gain&127);
|
||||||
|
break;
|
||||||
|
case DivInstrumentSNES::GAIN_MODE_DEC_LINEAR:
|
||||||
|
chWrite(i,7,0x80|(chan[i].state.gain&31));
|
||||||
|
break;
|
||||||
|
case DivInstrumentSNES::GAIN_MODE_INC_LINEAR:
|
||||||
|
chWrite(i,7,0xc0|(chan[i].state.gain&31));
|
||||||
|
break;
|
||||||
|
case DivInstrumentSNES::GAIN_MODE_DEC_LOG:
|
||||||
|
chWrite(i,7,0xa0|(chan[i].state.gain&31));
|
||||||
|
break;
|
||||||
|
case DivInstrumentSNES::GAIN_MODE_INC_INVLOG:
|
||||||
|
chWrite(i,7,0xe0|(chan[i].state.gain&31));
|
||||||
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
if (chan[i].useWave) {
|
if (chan[i].useWave) {
|
||||||
start=waveTableAddr(i);
|
start=waveTableAddr(i);
|
||||||
|
@ -193,9 +213,6 @@ void DivPlatformSNES::tick(bool sysTick) {
|
||||||
sampleMem[tabAddr+1]=start>>8;
|
sampleMem[tabAddr+1]=start>>8;
|
||||||
sampleMem[tabAddr+2]=loop&0xff;
|
sampleMem[tabAddr+2]=loop&0xff;
|
||||||
sampleMem[tabAddr+3]=loop>>8;
|
sampleMem[tabAddr+3]=loop>>8;
|
||||||
if (!hadGain) {
|
|
||||||
chWrite(i,7,0x7f);
|
|
||||||
}
|
|
||||||
kon|=(1<<i);
|
kon|=(1<<i);
|
||||||
chan[i].keyOn=false;
|
chan[i].keyOn=false;
|
||||||
}
|
}
|
||||||
|
@ -220,7 +237,7 @@ void DivPlatformSNES::tick(bool sysTick) {
|
||||||
int DivPlatformSNES::dispatch(DivCommand c) {
|
int DivPlatformSNES::dispatch(DivCommand c) {
|
||||||
switch (c.cmd) {
|
switch (c.cmd) {
|
||||||
case DIV_CMD_NOTE_ON: {
|
case DIV_CMD_NOTE_ON: {
|
||||||
DivInstrument* ins=parent->getIns(chan[c.chan].ins,DIV_INS_AMIGA);
|
DivInstrument* ins=parent->getIns(chan[c.chan].ins,DIV_INS_SNES);
|
||||||
if (ins->amiga.useWave) {
|
if (ins->amiga.useWave) {
|
||||||
chan[c.chan].useWave=true;
|
chan[c.chan].useWave=true;
|
||||||
chan[c.chan].wtLen=ins->amiga.waveLen+1;
|
chan[c.chan].wtLen=ins->amiga.waveLen+1;
|
||||||
|
@ -239,6 +256,9 @@ int DivPlatformSNES::dispatch(DivCommand c) {
|
||||||
if (chan[c.chan].useWave || chan[c.chan].sample<0 || chan[c.chan].sample>=parent->song.sampleLen) {
|
if (chan[c.chan].useWave || chan[c.chan].sample<0 || chan[c.chan].sample>=parent->song.sampleLen) {
|
||||||
chan[c.chan].sample=-1;
|
chan[c.chan].sample=-1;
|
||||||
}
|
}
|
||||||
|
if (chan[c.chan].insChanged) {
|
||||||
|
chan[c.chan].state=ins->snes;
|
||||||
|
}
|
||||||
if (c.value!=DIV_NOTE_NULL) {
|
if (c.value!=DIV_NOTE_NULL) {
|
||||||
chan[c.chan].baseFreq=round(NOTE_FREQUENCY(c.value));
|
chan[c.chan].baseFreq=round(NOTE_FREQUENCY(c.value));
|
||||||
chan[c.chan].freqChanged=true;
|
chan[c.chan].freqChanged=true;
|
||||||
|
@ -247,11 +267,6 @@ int DivPlatformSNES::dispatch(DivCommand c) {
|
||||||
chan[c.chan].active=true;
|
chan[c.chan].active=true;
|
||||||
chan[c.chan].keyOn=true;
|
chan[c.chan].keyOn=true;
|
||||||
chan[c.chan].macroInit(ins);
|
chan[c.chan].macroInit(ins);
|
||||||
if (ins->type==DIV_INS_SNES) {
|
|
||||||
// initialize to max gain in case of direct gain mode macro without gain level macro
|
|
||||||
chan[c.chan].std.vol.val=0x7f;
|
|
||||||
chan[c.chan].useEnv=ins->snes.useEnv;
|
|
||||||
}
|
|
||||||
chan[c.chan].insChanged=false;
|
chan[c.chan].insChanged=false;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
@ -277,12 +292,6 @@ int DivPlatformSNES::dispatch(DivCommand c) {
|
||||||
writeOutVol(c.chan);
|
writeOutVol(c.chan);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
// case DIV_CMD_GLOBAL_VOLUME:
|
|
||||||
// gblVolL=MIN(c.value,127);
|
|
||||||
// gblVolR=MIN(c.value,127);
|
|
||||||
// rWrite(0x0c,gblVolL);
|
|
||||||
// rWrite(0x1c,gblVolR);
|
|
||||||
// break;
|
|
||||||
case DIV_CMD_GET_VOLUME:
|
case DIV_CMD_GET_VOLUME:
|
||||||
return chan[c.chan].vol;
|
return chan[c.chan].vol;
|
||||||
break;
|
break;
|
||||||
|
@ -326,7 +335,7 @@ int DivPlatformSNES::dispatch(DivCommand c) {
|
||||||
}
|
}
|
||||||
case DIV_CMD_PRE_PORTA:
|
case DIV_CMD_PRE_PORTA:
|
||||||
if (chan[c.chan].active && c.value2) {
|
if (chan[c.chan].active && c.value2) {
|
||||||
if (parent->song.resetMacroOnPorta) chan[c.chan].macroInit(parent->getIns(chan[c.chan].ins,DIV_INS_AMIGA));
|
if (parent->song.resetMacroOnPorta) chan[c.chan].macroInit(parent->getIns(chan[c.chan].ins,DIV_INS_SNES));
|
||||||
}
|
}
|
||||||
chan[c.chan].inPorta=c.value;
|
chan[c.chan].inPorta=c.value;
|
||||||
break;
|
break;
|
||||||
|
@ -346,7 +355,7 @@ int DivPlatformSNES::dispatch(DivCommand c) {
|
||||||
|
|
||||||
void DivPlatformSNES::updateWave(int ch) {
|
void DivPlatformSNES::updateWave(int ch) {
|
||||||
// Due to the overflow bug in hardware's resampler, the written amplitude here is half of maximum
|
// Due to the overflow bug in hardware's resampler, the written amplitude here is half of maximum
|
||||||
size_t pos=waveTableAddr(ch);
|
unsigned short pos=waveTableAddr(ch);
|
||||||
for (int i=0; i<chan[ch].wtLen/16; i++) {
|
for (int i=0; i<chan[ch].wtLen/16; i++) {
|
||||||
sampleMem[pos++]=0xb0;
|
sampleMem[pos++]=0xb0;
|
||||||
for (int j=0; j<8; j++) {
|
for (int j=0; j<8; j++) {
|
||||||
|
@ -363,8 +372,8 @@ void DivPlatformSNES::writeOutVol(int ch) {
|
||||||
int outL=0;
|
int outL=0;
|
||||||
int outR=0;
|
int outR=0;
|
||||||
if (!isMuted[ch]) {
|
if (!isMuted[ch]) {
|
||||||
outL=chan[ch].vol*chan[ch].panL/255;
|
outL=(globalVolL*((chan[ch].outVol*chan[ch].panL)/127))/127;
|
||||||
outR=chan[ch].vol*chan[ch].panR/255;
|
outR=(globalVolR*((chan[ch].outVol*chan[ch].panR)/127))/127;
|
||||||
}
|
}
|
||||||
chWrite(ch,0,outL);
|
chWrite(ch,0,outL);
|
||||||
chWrite(ch,1,outR);
|
chWrite(ch,1,outR);
|
||||||
|
@ -417,6 +426,7 @@ void DivPlatformSNES::reset() {
|
||||||
// TODO more initial values
|
// TODO more initial values
|
||||||
// this can't be 0 or channel 1 won't play
|
// this can't be 0 or channel 1 won't play
|
||||||
// this can't be 0x100 either as that's used by SPC700 page 1 and the stack
|
// this can't be 0x100 either as that's used by SPC700 page 1 and the stack
|
||||||
|
// this may not even be 0x200 as some space will be taken by the playback routine and variables
|
||||||
sampleTableBase=0x200;
|
sampleTableBase=0x200;
|
||||||
rWrite(0x5d,sampleTableBase>>8);
|
rWrite(0x5d,sampleTableBase>>8);
|
||||||
rWrite(0x0c,127); // global volume left
|
rWrite(0x0c,127); // global volume left
|
||||||
|
@ -506,6 +516,11 @@ void DivPlatformSNES::renderSamples() {
|
||||||
sampleMemLen=memPos;
|
sampleMemLen=memPos;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void DivPlatformSNES::setFlags(unsigned int flags) {
|
||||||
|
globalVolL=127-(flags&127);
|
||||||
|
globalVolR=127-((flags>>8)&127);
|
||||||
|
}
|
||||||
|
|
||||||
int DivPlatformSNES::init(DivEngine* p, int channels, int sugRate, unsigned int flags) {
|
int DivPlatformSNES::init(DivEngine* p, int channels, int sugRate, unsigned int flags) {
|
||||||
parent=p;
|
parent=p;
|
||||||
dumpWrites=false;
|
dumpWrites=false;
|
||||||
|
@ -517,6 +532,7 @@ int DivPlatformSNES::init(DivEngine* p, int channels, int sugRate, unsigned int
|
||||||
sampleMemLen=0;
|
sampleMemLen=0;
|
||||||
chipClock=1024000;
|
chipClock=1024000;
|
||||||
rate=chipClock/32;
|
rate=chipClock/32;
|
||||||
|
setFlags(flags);
|
||||||
reset();
|
reset();
|
||||||
return 8;
|
return 8;
|
||||||
}
|
}
|
||||||
|
|
|
@ -34,9 +34,9 @@ class DivPlatformSNES: public DivDispatch {
|
||||||
int note;
|
int note;
|
||||||
int panL, panR;
|
int panL, panR;
|
||||||
bool active, insChanged, freqChanged, keyOn, keyOff, inPorta, useWave, setPos;
|
bool active, insChanged, freqChanged, keyOn, keyOff, inPorta, useWave, setPos;
|
||||||
signed char vol;
|
int vol, outVol;
|
||||||
int wtLen;
|
int wtLen;
|
||||||
bool useEnv;
|
DivInstrumentSNES state;
|
||||||
DivMacroInt std;
|
DivMacroInt std;
|
||||||
DivWaveSynth ws;
|
DivWaveSynth ws;
|
||||||
void macroInit(DivInstrument* which) {
|
void macroInit(DivInstrument* which) {
|
||||||
|
@ -53,8 +53,8 @@ class DivPlatformSNES: public DivDispatch {
|
||||||
wave(-1),
|
wave(-1),
|
||||||
ins(-1),
|
ins(-1),
|
||||||
note(0),
|
note(0),
|
||||||
panL(255),
|
panL(127),
|
||||||
panR(255),
|
panR(127),
|
||||||
active(false),
|
active(false),
|
||||||
insChanged(true),
|
insChanged(true),
|
||||||
freqChanged(false),
|
freqChanged(false),
|
||||||
|
@ -64,13 +64,13 @@ class DivPlatformSNES: public DivDispatch {
|
||||||
useWave(false),
|
useWave(false),
|
||||||
setPos(false),
|
setPos(false),
|
||||||
vol(127),
|
vol(127),
|
||||||
wtLen(16),
|
outVol(127),
|
||||||
useEnv(false) {}
|
wtLen(16) {}
|
||||||
};
|
};
|
||||||
Channel chan[8];
|
Channel chan[8];
|
||||||
DivDispatchOscBuffer* oscBuf[8];
|
DivDispatchOscBuffer* oscBuf[8];
|
||||||
bool isMuted[8];
|
bool isMuted[8];
|
||||||
signed char gblVolL, gblVolR;
|
signed char globalVolL, globalVolR;
|
||||||
size_t sampleTableBase;
|
size_t sampleTableBase;
|
||||||
|
|
||||||
struct QueuedWrite {
|
struct QueuedWrite {
|
||||||
|
@ -101,6 +101,7 @@ class DivPlatformSNES: public DivDispatch {
|
||||||
bool isStereo();
|
bool isStereo();
|
||||||
void notifyInsChange(int ins);
|
void notifyInsChange(int ins);
|
||||||
void notifyWaveChange(int wave);
|
void notifyWaveChange(int wave);
|
||||||
|
void setFlags(unsigned int flags);
|
||||||
void notifyInsDeletion(void* ins);
|
void notifyInsDeletion(void* ins);
|
||||||
void poke(unsigned int addr, unsigned short val);
|
void poke(unsigned int addr, unsigned short val);
|
||||||
void poke(std::vector<DivRegWrite>& wlist);
|
void poke(std::vector<DivRegWrite>& wlist);
|
||||||
|
|
|
@ -4295,7 +4295,9 @@ void FurnaceGUI::drawInsEdit() {
|
||||||
if (ins->type==DIV_INS_AMIGA) {
|
if (ins->type==DIV_INS_AMIGA) {
|
||||||
volMax=64;
|
volMax=64;
|
||||||
}
|
}
|
||||||
if (ins->type==DIV_INS_FM || ins->type==DIV_INS_SEGAPCM || ins->type==DIV_INS_MIKEY || ins->type==DIV_INS_MULTIPCM || ins->type==DIV_INS_SU || ins->type==DIV_INS_OPZ || ins->type==DIV_INS_OPM) {
|
if (ins->type==DIV_INS_FM || ins->type==DIV_INS_SEGAPCM || ins->type==DIV_INS_MIKEY ||
|
||||||
|
ins->type==DIV_INS_MULTIPCM || ins->type==DIV_INS_SU || ins->type==DIV_INS_OPZ ||
|
||||||
|
ins->type==DIV_INS_OPM || ins->type==DIV_INS_SNES) {
|
||||||
volMax=127;
|
volMax=127;
|
||||||
}
|
}
|
||||||
if (ins->type==DIV_INS_GB) {
|
if (ins->type==DIV_INS_GB) {
|
||||||
|
|
|
@ -755,12 +755,27 @@ void FurnaceGUI::drawSysConf(int chan, DivSystem type, unsigned int& flags, bool
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
case DIV_SYSTEM_SNES: {
|
||||||
|
ImGui::Text("Volume scale:");
|
||||||
|
int vsL=127-(flags&127);
|
||||||
|
int vsR=127-((flags>>8)&127);
|
||||||
|
if (CWSliderInt("Left##VolScaleL",&vsL,0,127)) {
|
||||||
|
if (vsL<0) vsL=0;
|
||||||
|
if (vsL>127) vsL=127;
|
||||||
|
copyOfFlags=(flags&(~0x7f))|(127-vsL);
|
||||||
|
} rightClickable
|
||||||
|
if (CWSliderInt("Right##VolScaleL",&vsR,0,127)) {
|
||||||
|
if (vsR<0) vsR=0;
|
||||||
|
if (vsR>127) vsR=127;
|
||||||
|
copyOfFlags=(flags&(~0x7f00))|((127-vsR)<<8);
|
||||||
|
} rightClickable
|
||||||
|
break;
|
||||||
|
}
|
||||||
case DIV_SYSTEM_SWAN:
|
case DIV_SYSTEM_SWAN:
|
||||||
case DIV_SYSTEM_VERA:
|
case DIV_SYSTEM_VERA:
|
||||||
case DIV_SYSTEM_BUBSYS_WSG:
|
case DIV_SYSTEM_BUBSYS_WSG:
|
||||||
case DIV_SYSTEM_YMU759:
|
case DIV_SYSTEM_YMU759:
|
||||||
case DIV_SYSTEM_PET:
|
case DIV_SYSTEM_PET:
|
||||||
case DIV_SYSTEM_SNES:
|
|
||||||
case DIV_SYSTEM_T6W28:
|
case DIV_SYSTEM_T6W28:
|
||||||
ImGui::Text("nothing to configure");
|
ImGui::Text("nothing to configure");
|
||||||
break;
|
break;
|
||||||
|
|
Loading…
Reference in a new issue