📄 resample.c
字号:
newt_coeffs[i][0] = newt_coeffs[i-1][0] / i; newt_coeffs[i][i] = newt_coeffs[i-1][0] / i; } for (j = 1; j < i; j++) { newt_coeffs[i][j] = newt_coeffs[i-1][j-1] + newt_coeffs[i-1][j]; if (i > 1) newt_coeffs[i][j] /= i; } } for (i = 0; i <= n; i++) for (j = 0, sign = pow(-1, i); j <= i; j++, sign *= -1) newt_coeffs[i][j] *= sign;}#endif /* NOT USED *//* initialize the coefficients of the current resampling algorithm */void initialize_resampler_coeffs(void){ /* initialize_newton_coeffs(); */ initialize_gauss_table(gauss_n); /* we don't have to initialize newton table any more */ /* bounds checking values for the appropriate sample types */ /* this is as good a place as any to initialize them */ if (play_mode->encoding & PE_24BIT) { sample_bounds_min = -8388608; sample_bounds_max = 8388607; } else /* 16-bit */ { sample_bounds_min = -32768; sample_bounds_max = 32767; }}/* change the parameter for the current resampling algorithm */int set_resampler_parm(int val){ if (cur_resample == resample_gauss) { if (val < 1 || val > 34) return -1; else gauss_n = val; } else if (cur_resample == resample_newton) { if (val < 1 || val > 57) return -1; else if (val % 2 == 0) return -1; else { newt_n = val; /* set optimal value for newt_max */ newt_max = newt_n * 1.57730263158 - 1.875328947; if (newt_max < newt_n) newt_max = newt_n; if (newt_max > 57) newt_max = 57; } } return 0;}/*************** resampling with fixed increment *****************/static resample_t *rs_plain_c(int v, int32 *countptr){ Voice *vp = &voice[v]; resample_t *dest = resample_buffer + resample_buffer_offset; sample_t *src = vp->sample->data; int32 ofs, count = *countptr, i, le; le = (int32)(vp->sample->loop_end >> FRACTION_BITS); ofs = (int32)(vp->sample_offset >> FRACTION_BITS); i = ofs + count; if(i > le) i = le; count = i - ofs; for (i = 0; i < count; i++) { dest[i] = src[i + ofs]; } ofs += count; if(ofs == le) { vp->timeout = 1; *countptr = count; } vp->sample_offset = ((splen_t)ofs << FRACTION_BITS); return resample_buffer + resample_buffer_offset;}static resample_t *rs_plain(int v, int32 *countptr){ /* Play sample until end, then free the voice. */ Voice *vp = &voice[v]; resample_t *dest = resample_buffer + resample_buffer_offset; sample_t *src = vp->sample->data; splen_t ofs = vp->sample_offset, ls = 0, le = vp->sample->data_length; resample_rec_t resrc; int32 count = *countptr, incr = vp->sample_increment;#ifdef PRECALC_LOOPS int32 i, j;#endif if(vp->cache && incr == (1 << FRACTION_BITS)) return rs_plain_c(v, countptr); resrc.loop_start = ls; resrc.loop_end = le; resrc.data_length = vp->sample->data_length;#ifdef PRECALC_LOOPS if (incr < 0) incr = -incr; /* In case we're coming out of a bidir loop */ /* Precalc how many times we should go through the loop. NOTE: Assumes that incr > 0 and that ofs <= le */ i = PRECALC_LOOP_COUNT(ofs, le, incr); if (i > count) { i = count; count = 0; } else count -= i; for(j = 0; j < i; j++) { RESAMPLATION; ofs += incr; } if (ofs >= le) { FINALINTERP; vp->timeout = 1; *countptr -= count; }#else /* PRECALC_LOOPS */ while (count--) { RESAMPLATION; ofs += incr; if (ofs >= le) { FINALINTERP; vp->timeout = 1; *countptr -= count; break; } }#endif /* PRECALC_LOOPS */ vp->sample_offset = ofs; /* Update offset */ return resample_buffer + resample_buffer_offset;}static resample_t *rs_loop_c(Voice *vp, int32 count){ int32 ofs = (int32)(vp->sample_offset >> FRACTION_BITS), le = (int32)(vp->sample->loop_end >> FRACTION_BITS), ll = le - (int32)(vp->sample->loop_start >> FRACTION_BITS); resample_t *dest = resample_buffer + resample_buffer_offset; sample_t *src = vp->sample->data; int32 i, j; while(count) { while(ofs >= le) ofs -= ll; /* Precalc how many times we should go through the loop */ i = le - ofs; if(i > count) i = count; count -= i; for (j = 0; j < i; j++) { dest[j] = src[j + ofs]; } dest += i; ofs += i; } vp->sample_offset = ((splen_t)ofs << FRACTION_BITS); return resample_buffer + resample_buffer_offset;}static resample_t *rs_loop(Voice *vp, int32 count){ /* Play sample until end-of-loop, skip back and continue. */ splen_t ofs = vp->sample_offset, ls, le, ll; resample_rec_t resrc; resample_t *dest = resample_buffer + resample_buffer_offset; sample_t *src = vp->sample->data;#ifdef PRECALC_LOOPS int32 i, j;#endif int32 incr = vp->sample_increment; if(vp->cache && incr == (1 << FRACTION_BITS)) return rs_loop_c(vp, count); resrc.loop_start = ls = vp->sample->loop_start; resrc.loop_end = le = vp->sample->loop_end; ll = le - ls; resrc.data_length = vp->sample->data_length;#ifdef PRECALC_LOOPS while (count) { while (ofs >= le) {ofs -= ll;} /* Precalc how many times we should go through the loop */ i = PRECALC_LOOP_COUNT(ofs, le, incr); if (i > count) { i = count; count = 0; } else {count -= i;} for(j = 0; j < i; j++) { RESAMPLATION; ofs += incr; } }#else while (count--) { RESAMPLATION; ofs += incr; if (ofs >= le) ofs -= ll; /* Hopefully the loop is longer than an increment. */ }#endif vp->sample_offset = ofs; /* Update offset */ return resample_buffer + resample_buffer_offset;}static resample_t *rs_bidir(Voice *vp, int32 count){#if SAMPLE_LENGTH_BITS == 32 int32#else splen_t#endif ofs = vp->sample_offset, le = vp->sample->loop_end, ls = vp->sample->loop_start; resample_t *dest = resample_buffer + resample_buffer_offset; sample_t *src = vp->sample->data; int32 incr = vp->sample_increment; resample_rec_t resrc;#ifdef PRECALC_LOOPS#if SAMPLE_LENGTH_BITS == 32 int32#else splen_t#endif le2 = le << 1, ls2 = ls << 1; int32 i, j; /* Play normally until inside the loop region */ resrc.loop_start = ls; resrc.loop_end = le; resrc.data_length = vp->sample->data_length; if (incr > 0 && ofs < ls) { /* NOTE: Assumes that incr > 0, which is NOT always the case when doing bidirectional looping. I have yet to see a case where both ofs <= ls AND incr < 0, however. */ i = PRECALC_LOOP_COUNT(ofs, ls, incr); if (i > count) { i = count; count = 0; } else count -= i; for(j = 0; j < i; j++) { RESAMPLATION; ofs += incr; } } /* Then do the bidirectional looping */ while(count) { /* Precalc how many times we should go through the loop */ i = PRECALC_LOOP_COUNT(ofs, incr > 0 ? le : ls, incr); if (i > count) { i = count; count = 0; } else count -= i; for(j = 0; j < i; j++) { RESAMPLATION; ofs += incr; } if(ofs >= 0 && ofs >= le) { /* fold the overshoot back in */ ofs = le2 - ofs; incr *= -1; } else if (ofs <= 0 || ofs <= ls) { ofs = ls2 - ofs; incr *= -1; } }#else /* PRECALC_LOOPS */ /* Play normally until inside the loop region */ if (ofs < ls) { while (count--) { RESAMPLATION; ofs += incr; if (ofs >= ls) break; } } /* Then do the bidirectional looping */ if (count > 0) while (count--) { RESAMPLATION; ofs += incr; if (ofs >= le) { /* fold the overshoot back in */ ofs = le - (ofs - le); incr = -incr; } else if (ofs <= ls) { ofs = ls + (ls - ofs); incr = -incr; } }#endif /* PRECALC_LOOPS */ vp->sample_increment = incr; vp->sample_offset = ofs; /* Update offset */ return resample_buffer + resample_buffer_offset;}/*********************** vibrato versions ***************************//* We only need to compute one half of the vibrato sine cycle */static int vib_phase_to_inc_ptr(int phase){ if (phase < VIBRATO_SAMPLE_INCREMENTS / 2) return VIBRATO_SAMPLE_INCREMENTS / 2 - 1 - phase; else if (phase >= 3 * VIBRATO_SAMPLE_INCREMENTS / 2) return 5 * VIBRATO_SAMPLE_INCREMENTS / 2 - 1 - phase; else return phase - VIBRATO_SAMPLE_INCREMENTS / 2;}static int32 update_vibrato(Voice *vp, int sign){ int32 depth; int phase, pb; double a; int ch = vp->channel; if(vp->vibrato_delay > 0) { vp->vibrato_delay -= vp->vibrato_control_ratio; if(vp->vibrato_delay > 0) return vp->sample_increment; } if (vp->vibrato_phase++ >= 2 * VIBRATO_SAMPLE_INCREMENTS - 1) vp->vibrato_phase = 0; phase = vib_phase_to_inc_ptr(vp->vibrato_phase); if (vp->vibrato_sample_increment[phase]) { if (sign) return -vp->vibrato_sample_increment[phase]; else return vp->vibrato_sample_increment[phase]; } /* Need to compute this sample increment. */ depth = vp->vibrato_depth; depth <<= 7; if (vp->vibrato_sweep && !channel[ch].mod.val) { /* Need to update sweep */ vp->vibrato_sweep_position += vp->vibrato_sweep; if (vp->vibrato_sweep_position >= (1 << SWEEP_SHIFT)) vp->vibrato_sweep=0; else { /* Adjust depth */ depth *= vp->vibrato_sweep_position; depth >>= SWEEP_SHIFT; } } if(vp->sample->inst_type == INST_SF2) { pb = (int)((lookup_triangular(vp->vibrato_phase * (SINE_CYCLE_LENGTH / (2 * VIBRATO_SAMPLE_INCREMENTS))) * (double)(depth) * VIBRATO_AMPLITUDE_TUNING)); } else { pb = (int)((lookup_sine(vp->vibrato_phase * (SINE_CYCLE_LENGTH / (2 * VIBRATO_SAMPLE_INCREMENTS))) * (double)(depth) * VIBRATO_AMPLITUDE_TUNING)); } a = TIM_FSCALE(((double)(vp->sample->sample_rate) * (double)(vp->frequency)) / ((double)(vp->sample->root_freq) * (double)(play_mode->rate)), FRACTION_BITS); if(pb < 0) { pb = -pb; a /= bend_fine[(pb >> 5) & 0xFF] * bend_coarse[pb >> 13]; pb = -pb; } else { a *= bend_fine[(pb >> 5) & 0xFF] * bend_coarse[pb >> 13]; } a += 0.5; /* If the sweep's over, we can store the newly computed sample_increment */ if (!vp->vibrato_sweep || channel[ch].mod.val) vp->vibrato_sample_increment[phase] = (int32) a; if (sign) a = -a; /* need to preserve the loop direction */ return (int32) a;}static resample_t *rs_vib_plain(int v, int32 *countptr){ /* Play sample until end, then free the voice. */ Voice *vp = &voice[v]; resample_t *dest = resample_buffer + resample_buffer_offset; sample_t *src = vp->sample->data; splen_t ls = 0, le = vp->sample->data_length, ofs = vp->sample_offset; resample_rec_t resrc; int32 count = *countptr, incr = vp->sample_increment; int cc = vp->vibrato_control_counter; resrc.loop_start = ls; resrc.loop_end = le; resrc.data_length = vp->sample->data_length; /* This has never been tested */ if (incr < 0) incr = -incr; /* In case we're coming out of a bidir loop */ while (count--) {
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -