mirror of
https://github.com/TomHarte/CLK.git
synced 2024-12-25 18:30:21 +00:00
Adds vibrato.
This would complete melodic output, subject to bug fixes.
This commit is contained in:
parent
9e3614066a
commit
983c32bf75
@ -7,3 +7,22 @@
|
||||
//
|
||||
|
||||
#include "LowFrequencyOscillator.hpp"
|
||||
|
||||
using namespace Yamaha::OPL;
|
||||
|
||||
void LowFrequencyOscillator::update() {
|
||||
++counter;
|
||||
|
||||
// This produces output of:
|
||||
//
|
||||
// four instances of 0, four instances of 1... _three_ instances of 26,
|
||||
// four instances of 25, four instances of 24... _three_ instances of 0.
|
||||
//
|
||||
// ... advancing once every 64th update.
|
||||
const int tremolo_index = (counter >> 6) % 210;
|
||||
const int tremolo_levels[2] = {tremolo_index >> 2, 52 - ((tremolo_index+1) >> 2)};
|
||||
tremolo = tremolo_levels[tremolo_index / 107];
|
||||
|
||||
// Vibrato is relatively simple: it's just three bits from the counter.
|
||||
vibrato = (counter >> 10) & 7;
|
||||
}
|
||||
|
@ -21,31 +21,14 @@ class LowFrequencyOscillator {
|
||||
public:
|
||||
/// Current attenuation due to tremolo / amplitude modulation, between 0 and 26.
|
||||
int tremolo = 0;
|
||||
/// TODO
|
||||
/// A number between 0 and 7 indicating the current vibrato offset; this should be combined by operators
|
||||
/// with their frequency number to get the actual vibrato.
|
||||
int vibrato = 0;
|
||||
/// A counter of the number of operator update cycles (i.e. input clock / 72) since an arbitrary time.
|
||||
int counter = 0;
|
||||
|
||||
/// Updates the oscillator outputs
|
||||
void update() {
|
||||
++counter;
|
||||
|
||||
// Update tremolo.
|
||||
++tremolo_phase_;
|
||||
|
||||
// This produces output of:
|
||||
//
|
||||
// four instances of 0, four instances of 1... _three_ instances of 26,
|
||||
// four instances of 25, four instances of 24... _three_ instances of 0.
|
||||
//
|
||||
// ... advancing once every 64th update.
|
||||
const int tremolo_index = (tremolo_phase_ >> 6) % 210;
|
||||
const int tremolo_levels[2] = {tremolo_index >> 2, 52 - ((tremolo_index+1) >> 2)};
|
||||
tremolo = tremolo_levels[tremolo_index / 107];
|
||||
}
|
||||
|
||||
private:
|
||||
int tremolo_phase_ = 0;
|
||||
void update();
|
||||
};
|
||||
|
||||
}
|
||||
|
@ -81,11 +81,16 @@ void Operator::update(
|
||||
constexpr int multipliers[] = {
|
||||
1, 2, 4, 6, 8, 10, 12, 14, 16, 18, 20, 20, 24, 24, 30, 30
|
||||
};
|
||||
const int top_freq = channel_period >> 7;
|
||||
assert(top_freq < 8);
|
||||
constexpr int vibrato_shifts[8] = {3, 1, 0, 1, 3, 1, 0, 1};
|
||||
constexpr int vibrato_signs[2] = {1, -1};
|
||||
const int vibrato = (top_freq >> vibrato_shifts[oscillator.vibrato]) * vibrato_signs[oscillator.vibrato >> 2] * int(apply_vibrato_);
|
||||
|
||||
// Update the raw phase.
|
||||
state.raw_phase_ += multipliers[frequency_multiple_] * channel_period << channel_octave;
|
||||
state.raw_phase_ += multipliers[frequency_multiple_] * (channel_period + vibrato) << channel_octave;
|
||||
|
||||
// Hence calculate phase (TODO: by also taking account of vibrato).
|
||||
// Hence calculate phase.
|
||||
constexpr int waveforms[4][4] = {
|
||||
{1023, 1023, 1023, 1023}, // Sine: don't mask in any quadrant.
|
||||
{511, 511, 0, 0}, // Half sine: keep the first half intact, lock to 0 in the second half.
|
||||
|
Loading…
Reference in New Issue
Block a user