mirror of
https://github.com/Tonejs/Tone.js
synced 2024-11-16 00:27:58 +00:00
converting FeedbackDelay to ts
This commit is contained in:
parent
3e6484eef6
commit
40727ee650
4 changed files with 208 additions and 1 deletions
|
@ -53,7 +53,7 @@ extends ToneAudioNode<Options> {
|
|||
*/
|
||||
output = this._dryWet;
|
||||
|
||||
protected _internalChannels = [this.input, this.output, this.effectReturn, this.effectSend];
|
||||
protected _internalChannels: ToneAudioNode[] = [this.input, this.output, this.effectReturn, this.effectSend];
|
||||
|
||||
constructor(options: EffectOptions) {
|
||||
super(options);
|
||||
|
|
64
Tone/effect/FeedbackDelay.test.ts
Normal file
64
Tone/effect/FeedbackDelay.test.ts
Normal file
|
@ -0,0 +1,64 @@
|
|||
import { expect } from "chai";
|
||||
import { BasicTests } from "test/helper/Basic";
|
||||
import { FeedbackDelay } from "./FeedbackDelay";
|
||||
// import {EffectTests} from "test/helper/EffectTests";
|
||||
import { FeedbackEffect } from "./FeedbackEffect";
|
||||
|
||||
describe("FeedbackDelay", () => {
|
||||
|
||||
BasicTests(FeedbackDelay);
|
||||
// EffectTests(FeedbackDelay, 0.01);
|
||||
|
||||
context("API", () => {
|
||||
|
||||
it("extends FeedbackEffect", () => {
|
||||
const feedbackDelay = new FeedbackDelay(0.2, 0.3);
|
||||
expect(feedbackDelay).to.be.instanceOf(FeedbackEffect);
|
||||
feedbackDelay.dispose();
|
||||
});
|
||||
|
||||
it("parses constructor arguments correctly", () => {
|
||||
const feedbackDelay = new FeedbackDelay(0.1, 0.4);
|
||||
expect(feedbackDelay.delayTime.value).to.be.closeTo(0.1, 0.01);
|
||||
expect(feedbackDelay.feedback.value).to.be.closeTo(0.4, 0.01);
|
||||
feedbackDelay.dispose();
|
||||
});
|
||||
|
||||
it("can pass in options in the constructor", () => {
|
||||
const feedbackDelay = new FeedbackDelay({
|
||||
delayTime : 0.2,
|
||||
feedback : 0.3,
|
||||
});
|
||||
expect(feedbackDelay.delayTime.value).to.be.closeTo(0.2, 0.01);
|
||||
expect(feedbackDelay.feedback.value).to.be.closeTo(0.3, 0.01);
|
||||
feedbackDelay.dispose();
|
||||
});
|
||||
|
||||
it("can get/set the options", () => {
|
||||
const feedbackDelay = new FeedbackDelay();
|
||||
feedbackDelay.set({
|
||||
feedback : 0.4,
|
||||
});
|
||||
expect(feedbackDelay.get().feedback).to.be.closeTo(0.4, 0.01);
|
||||
feedbackDelay.dispose();
|
||||
});
|
||||
|
||||
it("can set the delayTime", () => {
|
||||
const feedbackDelay = new FeedbackDelay();
|
||||
feedbackDelay.delayTime.value = "4n";
|
||||
expect(feedbackDelay.delayTime.value).to.be.closeTo(0.5, 0.001);
|
||||
feedbackDelay.delayTime.value = 0.22;
|
||||
expect(feedbackDelay.delayTime.value).to.be.closeTo(0.22, 0.001);
|
||||
feedbackDelay.dispose();
|
||||
});
|
||||
|
||||
it("can set the feedback amount", () => {
|
||||
const feedbackDelay = new FeedbackDelay();
|
||||
feedbackDelay.feedback.value = 1;
|
||||
expect(feedbackDelay.feedback.value).to.be.closeTo(1, 0.001);
|
||||
feedbackDelay.feedback.value = 0.22;
|
||||
expect(feedbackDelay.feedback.value).to.be.closeTo(0.22, 0.001);
|
||||
feedbackDelay.dispose();
|
||||
});
|
||||
});
|
||||
});
|
76
Tone/effect/FeedbackDelay.ts
Normal file
76
Tone/effect/FeedbackDelay.ts
Normal file
|
@ -0,0 +1,76 @@
|
|||
import { Delay } from "Tone/core";
|
||||
import { Param } from "Tone/core/context/Param";
|
||||
import { optionsFromArguments } from "Tone/core/util/Defaults";
|
||||
import { readOnly } from "Tone/core/util/Interface";
|
||||
import { FeedbackEffect, FeedbackEffectOptions } from "./FeedbackEffect";
|
||||
|
||||
interface FeedbackDelayOptions extends FeedbackEffectOptions {
|
||||
delayTime: Time;
|
||||
maxDelay: Time;
|
||||
}
|
||||
|
||||
/**
|
||||
* FeedbackDelay is a DelayNode in which part of output signal is fed back into the delay.
|
||||
*
|
||||
* @param delayTime The delay applied to the incoming signal.
|
||||
* @param feedback The amount of the effected signal which is fed back through the delay.
|
||||
* @example
|
||||
* var feedbackDelay = new FeedbackDelay("8n", 0.5).toMaster();
|
||||
* var tom = new Tone.MembraneSynth({
|
||||
* "octaves" : 4,
|
||||
* "pitchDecay" : 0.1
|
||||
* }).connect(feedbackDelay);
|
||||
* tom.triggerAttackRelease("A2","32n");
|
||||
*/
|
||||
export class FeedbackDelay extends FeedbackEffect<FeedbackDelayOptions> {
|
||||
|
||||
/**
|
||||
* the delay node
|
||||
*/
|
||||
private _delayNode: Delay;
|
||||
|
||||
/**
|
||||
* The delayTime of the DelayNode.
|
||||
*/
|
||||
delayTime: Param<Time>;
|
||||
|
||||
constructor(delayTime?: Time, feedback?: NormalRange);
|
||||
constructor(options?: Partial<FeedbackDelayOptions>);
|
||||
constructor() {
|
||||
|
||||
super(optionsFromArguments(FeedbackDelay.getDefaults(), arguments, ["delayTime", "feedback"]));
|
||||
const options = optionsFromArguments(FeedbackDelay.getDefaults(), arguments, ["delayTime", "feedback"]);
|
||||
|
||||
this._delayNode = new Delay({
|
||||
context: this.context,
|
||||
delayTime: options.delayTime,
|
||||
maxDelay: options.maxDelay,
|
||||
});
|
||||
this._internalChannels.push(this._delayNode);
|
||||
|
||||
/**
|
||||
* The delayTime of the DelayNode.
|
||||
* @type {Time}
|
||||
* @signal
|
||||
*/
|
||||
this.delayTime = this._delayNode.delayTime;
|
||||
|
||||
// connect it up
|
||||
this.connectEffect(this._delayNode);
|
||||
readOnly(this, "delayTime");
|
||||
}
|
||||
|
||||
static getDefaults(): FeedbackDelayOptions {
|
||||
return Object.assign(FeedbackEffect.getDefaults(), {
|
||||
delayTime: 0.25,
|
||||
maxDelay: 1,
|
||||
});
|
||||
}
|
||||
|
||||
dispose(): this {
|
||||
super.dispose();
|
||||
this._delayNode.dispose();
|
||||
this.delayTime.dispose();
|
||||
return this;
|
||||
}
|
||||
}
|
67
Tone/effect/FeedbackEffect.ts
Normal file
67
Tone/effect/FeedbackEffect.ts
Normal file
|
@ -0,0 +1,67 @@
|
|||
import { Gain } from "../core/context/Gain";
|
||||
import { Param } from "../core/context/Param";
|
||||
import { readOnly } from "../core/util/Interface";
|
||||
import { Effect, EffectOptions } from "./Effect";
|
||||
|
||||
export interface FeedbackEffectOptions extends EffectOptions {
|
||||
/**
|
||||
* The feedback from the output back to the input
|
||||
* ```
|
||||
* +---<--------<---+
|
||||
* | |
|
||||
* | +----------+ |
|
||||
* +--> feedback +>-+
|
||||
* +----------+
|
||||
* ```
|
||||
*/
|
||||
feedback: NormalRange;
|
||||
}
|
||||
|
||||
/**
|
||||
* FeedbackEffect provides a loop between an audio source and its own output.
|
||||
* This is a base-class for feedback effects.
|
||||
*/
|
||||
export abstract class FeedbackEffect<Options extends FeedbackEffectOptions> extends Effect<Options> {
|
||||
|
||||
name = "FeedbackEffect";
|
||||
|
||||
/**
|
||||
* the gain which controls the feedback
|
||||
*/
|
||||
private _feedbackGain: Gain<NormalRange>;
|
||||
|
||||
/**
|
||||
* The amount of signal which is fed back into the effect input.
|
||||
*/
|
||||
feedback: Param<NormalRange>;
|
||||
|
||||
constructor(options: FeedbackEffectOptions) {
|
||||
|
||||
super(options);
|
||||
|
||||
this._feedbackGain = new Gain({
|
||||
context: this.context,
|
||||
gain: options.feedback,
|
||||
units: "normalRange",
|
||||
});
|
||||
|
||||
this.feedback = this._feedbackGain.gain;
|
||||
readOnly(this, "feedback");
|
||||
|
||||
// the feedback loop
|
||||
this.effectReturn.chain(this._feedbackGain, this.effectSend);
|
||||
}
|
||||
|
||||
static getDefaults(): FeedbackEffectOptions {
|
||||
return Object.assign(Effect.getDefaults(), {
|
||||
feedback: 0.125,
|
||||
});
|
||||
}
|
||||
|
||||
dispose(): this {
|
||||
super.dispose();
|
||||
this._feedbackGain.dispose();
|
||||
this.feedback.dispose();
|
||||
return this;
|
||||
}
|
||||
}
|
Loading…
Reference in a new issue