Skip to content

Slewing a Square LFO #1378

@kdulcet

Description

@kdulcet

Funny that this is the first issue on the tracker but I'm really stuck here and I'm wondering if there is any other approach.

I want to use follower to output a control signal to slew the volume of a square LFO.

Why I can't use RampTo: I'm not using the timeline conventionally - I'm modulating LFOs to create the tempo. The "tempo" is a hz figure that I need the LFOs to follow sample accruately.

What I'd like to do

sinewave -> 4hz Amp LFO - follower -> MUTE

Then I want to take the controller data from the follower and apply it to a fresh sine wave.

Sinewave -> follower processed LFO to gain -> Out

However, every time I try to extract JUST the control signal from the follower and have it muted, the follower signal gets mixed in the main.

The following is my tempo code. I'm hoping this is something obvious about tone.js controllers that I'm simply not understanding.

`

<title>Follower Amplitude Modulation Test</title> <script src="https://unpkg.com/[email protected]/build/Tone.js"></script>

Follower Amplitude Modulation Test

Test: Sine wave (240.1 Hz) → Square LFO (4 Hz) → Follower (7ms) → Direct Output

Start Test Stop Test
<script src="https://unpkg.com/[email protected]/build/Tone.js"></script>
<script>
    let sourceSine, squareLFO, follower, ampMod, masterGain, scaler, offset;
    let isPlaying = false;

    document.getElementById('startBtn').addEventListener('click', async () => {
        if (isPlaying) return;
        
        await Tone.start();
        
        // Your approach: Source for analysis → Follower → Controls different oscillator gain
        
        // Source chain (220Hz modulated by 4Hz, for follower analysis - MUTED)
        const sourceOsc = new Tone.Oscillator(440, "sine");
        const lfo = new Tone.Oscillator(4, "square");
        const scaler = new Tone.Multiply(0.5);
        const offset = new Tone.Add(0.5);
        const ampMod = new Tone.Gain(1.0);
        const follower = new Tone.Follower(0.005);  // 5ms
        const muteGain = new Tone.Gain(0);  // MUTE the source
        
        // Target chain (440Hz controlled by follower via Multiply)
        const targetOsc = new Tone.Oscillator(140, "sine");
        const multiply = new Tone.Multiply(1);  // Multiply by follower value
        const masterGain = new Tone.Gain(0.5);

        // Source routing: 220Hz → 4Hz LFO modulation → Follower → TERMINATE
        lfo.connect(scaler);
        scaler.connect(offset);
        offset.connect(ampMod.gain);
        sourceOsc.connect(ampMod);
        ampMod.connect(follower);
        follower.connect(muteGain);  // TERMINATE follower audio completely
        
        // Target routing: 440Hz → Multiply (controlled by follower) → Master → Output
        targetOsc.connect(multiply);
        multiply.connect(masterGain);
        masterGain.toDestination();
        
        // CONTROL: Follower controls multiply factor (pure parameter control)
        follower.connect(multiply.factor);  // Control the multiplication factor
        
        // Start oscillators
        sourceOsc.start();
        lfo.start();
        targetOsc.start();
        
        isPlaying = true;
        console.log('Test started: LFO → Follower → Controls 440Hz sine gain');
    });
    
    document.getElementById('stopBtn').addEventListener('click', () => {
        if (!isPlaying) return;
        
        // Stop oscillators
        if (sourceOsc) sourceOsc.stop();
        if (lfo) lfo.stop();
        if (targetOsc) targetOsc.stop();
        
        // Dispose nodes
        [sourceOsc, lfo, targetOsc, scaler, offset, ampMod, follower, muteGain, multiply, masterGain].forEach(node => {
            if (node) node.dispose();
        });

        isPlaying = false;
        console.log('Test stopped');
    });
</script>
`

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions