uint OPL_CALC_SLOT(OPL_SLOT SLOT)
{
/* calcrate envelope generator */
if ((SLOT.evc += SLOT.evs) >= SLOT.eve)
{
switch (SLOT.evm)
{
case ENV_MOD_AR: /* ATTACK . DECAY1 */
/* next DR */
SLOT.evm = ENV_MOD_DR;
SLOT.evc = EG_DST;
SLOT.eve = SLOT.SL;
SLOT.evs = SLOT.evsd;
break;
case ENV_MOD_DR: /* DECAY . SL or RR */
SLOT.evc = SLOT.SL;
SLOT.eve = EG_DED;
if (SLOT.eg_typ)
{
SLOT.evs = 0;
}
else
{
SLOT.evm = ENV_MOD_RR;
SLOT.evs = SLOT.evsr;
}
break;
case ENV_MOD_RR: /* RR . OFF */
SLOT.evc = EG_OFF;
SLOT.eve = EG_OFF + 1;
SLOT.evs = 0;
break;
}
}
/* calcrate envelope */
return SLOT.TLL + ENV_CURVE[SLOT.evc >> ENV_BITS] + (SLOT.ams ? ams : 0);
}