summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--source/saw/main.c83
1 files changed, 25 insertions, 58 deletions
diff --git a/source/saw/main.c b/source/saw/main.c
index 63e8a4c..1a51aeb 100644
--- a/source/saw/main.c
+++ b/source/saw/main.c
@@ -205,7 +205,6 @@ typedef struct {
saw_da_f32_t outline;
f64 begin;
f64 end;
- f64 tail;
f64 crossfade;
f64 base_frequency;
f64 volume;
@@ -660,9 +659,6 @@ static void saw_audio_render(void) {
case INSTRUMENT_SAMPLER: {
saw_sampler_t *sam = &track->sampler;
- if (sam->begin + sam->crossfade + TIME_EPS >= sam->end)
- break;
-
f64 frequency = saw_voices[n].frequency;
f64 amplitude = saw_voices[n].amplitude;
@@ -677,32 +673,33 @@ static void saw_audio_render(void) {
sustain, duration,
release);
- f64 crossfade = sam->crossfade;
- f64 sample_begin = sam->begin;
- f64 sample_end = sam->end;
+ if (frequency < TIME_EPS)
+ break;
+
+ f64 crossfade = (sam->crossfade * sam->base_frequency) /
+ frequency;
+ f64 sample_begin = (sam->begin * sam->base_frequency) /
+ frequency;
+ f64 sample_end = (sam->end * sam->base_frequency) /
+ frequency;
f64 sample_duration = sample_end - sample_begin -
crossfade;
- f64 sample_tail = sam->tail;
- f64 body_end = duration + crossfade;
- f64 tail_begin = duration;
- f64 tail_end = tail_begin + sample_tail;
+ f64 body_end = duration + release;
if (t <= body_end) {
// Play the body
//
f64 q = t;
- assert(sample_duration > TIME_EPS);
- while (q >= sample_duration)
- q -= sample_duration;
+ if (sample_duration > TIME_EPS)
+ q -= sample_duration * floor(q / sample_duration);
q += sample_begin;
f64 u0 = 1.;
- if (t > tail_begin && crossfade > TIME_EPS)
- u0 = 1. - (t - tail_begin) / crossfade;
- if (t >= sample_duration && q < crossfade &&
- crossfade > TIME_EPS) {
+ if (sample_duration > TIME_EPS &&
+ crossfade > TIME_EPS && t >= sample_duration &&
+ q < crossfade) {
// Play the body crossfade
//
@@ -739,30 +736,9 @@ static void saw_audio_render(void) {
}
}
- if (t >= tail_begin && t <= tail_end) {
- // Play the tail
- //
-
- f64 q = t - tail_begin;
-
- f64 u = 1.;
- if (q < crossfade && crossfade > TIME_EPS)
- u = q / crossfade;
-
- f64 r = sample_end + q;
- i64 k = (i64) floor(r * SAMPLE_RATE + .5);
-
- saw_playback_temp[i * CHANNEL_COUNT] +=
- (f32) (saw_sampler(sam, 0, frequency, k) * a * u *
- GLOBAL_VOLUME);
- saw_playback_temp[i * CHANNEL_COUNT + 1] +=
- (f32) (saw_sampler(sam, 1, frequency, k) * a * u *
- GLOBAL_VOLUME);
- }
-
saw_voices[n].time++;
- if (t > duration + release) {
+ if (t >= duration + release) {
saw_voices[n].enabled = 0;
regroup_voices = 1;
}
@@ -1728,7 +1704,6 @@ static void saw_ui_choose_instrument(saw_track_t *track, i64 x0,
track->sampler.begin = 0.;
track->sampler.end = 1.;
- track->sampler.tail = .2;
track->sampler.crossfade = .01;
track->sampler.base_frequency = 440.;
track->sampler.volume = .5;
@@ -1888,15 +1863,12 @@ static void saw_ui_sampler(saw_sampler_t *sampler, i64 x0, i64 y0,
w, text_height, TINT_WHITE, SZ("End"), 100000,
0., 60., &sampler->end);
saw_ui_value_float(x, y0 + height - sample_height - text_height * 3,
- w, text_height, TINT_WHITE, SZ("Tail"), 100000,
- 0., 60., &sampler->tail);
- saw_ui_value_float(x, y0 + height - sample_height - text_height * 4,
w, text_height, TINT_WHITE, SZ("Crossfade"),
100000, 0., 60., &sampler->crossfade);
- saw_ui_value_float(x, y0 + height - sample_height - text_height * 5,
+ saw_ui_value_float(x, y0 + height - sample_height - text_height * 4,
w, text_height, TINT_WHITE, SZ("Base freq."),
500, 1., 44100., &sampler->base_frequency);
- saw_ui_value_float(x, y0 + height - sample_height - text_height * 6,
+ saw_ui_value_float(x, y0 + height - sample_height - text_height * 5,
w, text_height, TINT_WHITE, SZ("Volume."), 10000,
0., 2., &sampler->volume);
@@ -1906,22 +1878,21 @@ static void saw_ui_sampler(saw_sampler_t *sampler, i64 x0, i64 y0,
nvgTextAlign(saw_nvg, NVG_ALIGN_LEFT | NVG_ALIGN_BASELINE);
nvgText(saw_nvg, x,
frame_height - y0 - height + sample_height +
- (text_height * 15) / 2,
+ (text_height * 13) / 2,
"Envelope", NULL);
- saw_ui_value_float(x, y0 + height - sample_height - text_height * 9,
+ saw_ui_value_float(x, y0 + height - sample_height - text_height * 8,
w, text_height, TINT_WHITE, SZ("Sustain"), 10000,
0., 1., &sampler->envelope.sustain);
- saw_ui_value_float(x,
- y0 + height - sample_height - text_height * 10,
+ saw_ui_value_float(x, y0 + height - sample_height - text_height * 9,
w, text_height, TINT_WHITE, SZ("Attack"), 100000,
0., 6., &sampler->envelope.attack);
saw_ui_value_float(x,
- y0 + height - sample_height - text_height * 11,
+ y0 + height - sample_height - text_height * 10,
w, text_height, TINT_WHITE, SZ("Decay"), 100000,
0., 6., &sampler->envelope.decay);
saw_ui_value_float(x,
- y0 + height - sample_height - text_height * 12,
+ y0 + height - sample_height - text_height * 11,
w, text_height, TINT_WHITE, SZ("Release"),
100000, 0., 6., &sampler->envelope.release);
}
@@ -2848,12 +2819,11 @@ static void saw_init(void) {
sam->outline.values[i] = fabs(v[k] + v[k + 1]) * .5;
}
- i64 begin, end, tail, crossfade, bfreq, volume, sustain,
- attack, decay, release;
+ i64 begin, end, crossfade, bfreq, volume, sustain, attack,
+ decay, release;
SCAN_(" begin %lld", 1, &begin);
SCAN_(" end %lld", 1, &end);
- SCAN_(" tail %lld", 1, &tail);
SCAN_(" crossfade %lld", 1, &crossfade);
SCAN_(" base_frequency %lld", 1, &bfreq);
SCAN_(" volume %lld", 1, &volume);
@@ -2864,7 +2834,6 @@ static void saw_init(void) {
sam->begin = begin * .0001;
sam->end = end * .0001;
- sam->tail = tail * .0001;
sam->crossfade = crossfade * .0001;
sam->base_frequency = bfreq * .0001;
sam->volume = volume * .0001;
@@ -3152,8 +3121,6 @@ static void saw_cleanup(void) {
(i64) floor(sam->begin * 10000 + .5));
fprintf(f, "end %lld\n",
(i64) floor(sam->end * 10000 + .5));
- fprintf(f, "tail %lld\n",
- (i64) floor(sam->tail * 10000 + .5));
fprintf(f, "crossfade %lld\n",
(i64) floor(sam->crossfade * 10000 + .5));
fprintf(f, "base_frequency %lld\n",