fix portamentos, pitch bends
- period slides were off by a factor of 4 - we need to reset a note's envelope if it was released, and then portamento'd into - instruments shouldn't trigger notes in the presence of 3xx/5xx
This commit is contained in:
parent
4a0efd648d
commit
50c5513aeb
1 changed files with 12 additions and 6 deletions
18
xm.js
18
xm.js
|
|
@ -78,13 +78,13 @@ popfilter = FilterCoeffs(200.0 / 44100.0);
|
||||||
popfilter_alpha = 0.9837;
|
popfilter_alpha = 0.9837;
|
||||||
|
|
||||||
function UpdateChannelPeriod(ch, period, f_smp) {
|
function UpdateChannelPeriod(ch, period, f_smp) {
|
||||||
var freq = 8363 * Math.pow(2, (4608 - period) / 768);
|
var freq = 8363 * Math.pow(2, (1152.0 - period) / 192.0);
|
||||||
ch.doff = freq / f_smp;
|
ch.doff = freq / f_smp;
|
||||||
ch.filter = FilterCoeffs(ch.doff / 2);
|
ch.filter = FilterCoeffs(ch.doff / 2);
|
||||||
}
|
}
|
||||||
|
|
||||||
function PeriodForNote(ch, note) {
|
function PeriodForNote(ch, note) {
|
||||||
return 7680 - note*64 - ch.inst.fine*0.5;
|
return 1920 - note*16 - ch.inst.fine / 8.0;
|
||||||
}
|
}
|
||||||
|
|
||||||
function UpdateChannelNote(ch, note, f_smp) {
|
function UpdateChannelNote(ch, note, f_smp) {
|
||||||
|
|
@ -116,10 +116,8 @@ function next_row(f_smp) {
|
||||||
var inst = instruments[r[i][1] - 1];
|
var inst = instruments[r[i][1] - 1];
|
||||||
if (inst !== undefined) {
|
if (inst !== undefined) {
|
||||||
ch.inst = inst;
|
ch.inst = inst;
|
||||||
// retrigger?
|
// retrigger unless overridden below
|
||||||
ch.off = 0;
|
triggernote = true;
|
||||||
ch.release = 0;
|
|
||||||
ch.envtick = 0;
|
|
||||||
// new instrument doesn ot reset volume!
|
// new instrument doesn ot reset volume!
|
||||||
} else {
|
} else {
|
||||||
// console.log("invalid inst", r[i][1], instruments.length);
|
// console.log("invalid inst", r[i][1], instruments.length);
|
||||||
|
|
@ -172,6 +170,12 @@ function next_row(f_smp) {
|
||||||
ch.portaspeed = ch.effectdata;
|
ch.portaspeed = ch.effectdata;
|
||||||
}
|
}
|
||||||
triggernote = false;
|
triggernote = false;
|
||||||
|
if (ch.release) {
|
||||||
|
// reset envelopes if note was released but leave offset/pitch/etc
|
||||||
|
// alone
|
||||||
|
ch.envtick = 0;
|
||||||
|
ch.release = 0;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
if (triggernote) {
|
if (triggernote) {
|
||||||
ch.off = 0;
|
ch.off = 0;
|
||||||
|
|
@ -285,6 +289,7 @@ function audio_cb(e) {
|
||||||
var dk = ch.doff;
|
var dk = ch.doff;
|
||||||
// console.log(j, offset, ch);
|
// console.log(j, offset, ch);
|
||||||
for (var i = offset; i < offset+tickduration; i++) {
|
for (var i = offset; i < offset+tickduration; i++) {
|
||||||
|
if (ch.mute) break;
|
||||||
var s = samp[k|0];
|
var s = samp[k|0];
|
||||||
var si = ch.filter[0] * (s + ch.filterstate[0]) + ch.filter[1]*ch.filterstate[1] + ch.filter[2]*ch.filterstate[2];
|
var si = ch.filter[0] * (s + ch.filterstate[0]) + ch.filter[1]*ch.filterstate[1] + ch.filter[2]*ch.filterstate[2];
|
||||||
ch.filterstate[2] = ch.filterstate[1]; ch.filterstate[1] = si; ch.filterstate[0] = s;
|
ch.filterstate[2] = ch.filterstate[1]; ch.filterstate[1] = si; ch.filterstate[0] = s;
|
||||||
|
|
@ -371,6 +376,7 @@ function playXM(arrayBuf) {
|
||||||
pan: 128,
|
pan: 128,
|
||||||
vL: 0, vR: 0, // left right volume envelope followers (changes per sample)
|
vL: 0, vR: 0, // left right volume envelope followers (changes per sample)
|
||||||
vLprev: 0, vRprev: 0,
|
vLprev: 0, vRprev: 0,
|
||||||
|
mute: 0,
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
console.log("header len " + hlen);
|
console.log("header len " + hlen);
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue