removed aliasing in rect and saw oscilators

This commit is contained in:
2022-03-19 14:53:21 +01:00
parent 0ade24ebf6
commit 0f82e6e711
5 changed files with 59 additions and 12 deletions

View File

@@ -1,3 +1,5 @@
import "env.memory" memory(4);
fn melody(ch: i32, t: i32, T: i32) {
let lazy riff_pos = abs(((T&31) - 16) as f32) as i32;
let lazy shift = ((1-((T>>5)&3))%2-1) * 2;
@@ -7,7 +9,7 @@ fn melody(ch: i32, t: i32, T: i32) {
let inline riff_note = 5514 >> (riff_pos % note_count * 4) & 15;
let inline melody_note = shift + octave - riff_note;
ch?1 = riff_pos * 10 + 4;
ch?1 = riff_pos * 10 + 63;
ch?3 = melody_note + 64;
let inline arp_note = shift + ((0x85>>((t/2)%3*4)) & 15) - 1;
@@ -36,12 +38,12 @@ export fn upd() {
data 80 {
i8(
0, 64, 0, 128, 0, 0x90,
0, 64, 0, 128, 0, 0x4c,
0, 80, 0, 128, 0, 0x90,
0, 80, 0, 128, 0, 0x4c,
5, 128, 0, 128, 0, 0x4c,
5, 128, 0, 128, 0, 0x4c,
0xf8, 0x85,
0x81, 0x81, 0, 105, 0, 80
0x81, 0x81, 0, 110, 0, 80
)
}

Binary file not shown.

View File

@@ -34,8 +34,9 @@ export fn gesSnd(t: i32) -> f32 {
channelState?GesChannelState.Trigger = ctrl;
if envState {
envVol = envVol + 8 * pow(1.5625, (15 - channelReg?4 & 15) as f32) as i32;
if envVol >= 65535 {
let lazy attack = channelReg?4 & 15;
envVol = envVol + 12 * pow(1.5625, (15 - attack) as f32) as i32;
if envVol >= 65535 | !attack {
envVol = 65535;
envState = 0;
}
@@ -61,25 +62,33 @@ export fn gesSnd(t: i32) -> f32 {
let inline pulseWidth = channelReg?1;
let phaseShift = (pulseWidth - 128) * 255;
let invPhaseInc = 1 as f32 / phaseInc as f32;
i = 0;
let wave = ctrl >> 6;
if wave < 2 {
if wave {
let pulsePhase1 = pulseWidth << 23;
let pulsePhase2 = (511 - pulseWidth) << 23;
loop sawLoop {
let p = (phase ^ 32768) << 16;
p = ((p ^ (p >> 31)) >> 15) + phaseShift;
p = (p < 0 | p > 65535) * 65535;
i!(GesBufferOffset + 128*4) = (phase ^ p & 65535) - 32768;
let saw = (p >> 16) - polyBlep(phase, invPhaseInc, -32767);
let saw2 = select(p #>= pulsePhase1 & p #< pulsePhase2, -saw, saw);
let saw2 = saw2 -
polyBlep((p - pulsePhase1) >> 16, invPhaseInc, -saw) -
polyBlep((p - pulsePhase2) >> 16, invPhaseInc, saw);
i!(GesBufferOffset + 128*4) = saw2;
phase = phase + phaseInc;
branch_if (i := i + 4) < 64*4: sawLoop;
}
}
else
{
let pulsePhase = 32768 + pulseWidth * 128;
loop rectLoop {
let p = (phase & 65535) + phaseShift;
i!(GesBufferOffset + 128*4) = select(p >= 32768, -32768, 32767);
i!(GesBufferOffset + 128*4) = select((phase & 65535) < pulsePhase, -32768, 32767) -
polyBlep(phase, invPhaseInc, -32767) -
polyBlep(phase - pulsePhase, invPhaseInc, 32767);
phase = phase + phaseInc;
branch_if (i := i + 4) < 64*4: rectLoop;
}
@@ -163,3 +172,9 @@ export fn gesSnd(t: i32) -> f32 {
}
(((t & 127) * 4)!GesBufferOffset) as f32 / 32768 as f32
}
fn polyBlep(transientPhase: i32, invPhaseInc: f32, magnitude: i32) -> i32 {
let lazy t = ((transientPhase << 16) >> 16) as f32 * invPhaseInc;
let lazy x = max(0 as f32, 1 as f32 - abs(t));
(f32.copysign(x * x, t) * magnitude as f32) as i32
}

File diff suppressed because one or more lines are too long

30
test/ges_test.cwa Normal file
View File

@@ -0,0 +1,30 @@
import "env.memory" memory(4);
import "env.pow" fn pow(f32, f32) -> f32;
import "env.sin" fn sin(f32) -> f32;
import "env.cls" fn cls(i32);
import "env.rectangle" fn rectangle(f32, f32, f32, f32, i32);
include "../platform/src/ges.cwa"
export fn snd(t: i32) -> f32 {
gesSnd(t)
}
export fn upd() {
80?0 = 32!32 / 200 & 2 | 0x41;
80?3 = (32!32 / 400)%7*12/7 + 40;
let pulse = (32!32 * 256 / 2000) & 511;
if pulse >= 256 {
pulse = 511 - pulse;
}
80?1 = pulse;
cls(0);
rectangle(0.0, 100.0, (pulse * 320 / 256) as f32, 16.0, 15);
}
data 80 {
i8(
0x41, 0, 0, 80, 0x70, 0
)
}