From 6c834b1d252078511a934db775ccb6d0a5d7f8e5 Mon Sep 17 00:00:00 2001 From: wolfbiter Date: Sat, 22 Oct 2016 10:02:29 -0700 Subject: [PATCH 1/2] put delay node after filters --- app/mixins/playable-arrangement/track-clip.js | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/app/mixins/playable-arrangement/track-clip.js b/app/mixins/playable-arrangement/track-clip.js index e8f89a52..3b4f7502 100644 --- a/app/mixins/playable-arrangement/track-clip.js +++ b/app/mixins/playable-arrangement/track-clip.js @@ -213,7 +213,7 @@ export default Ember.Mixin.create( trackVolumeNode: computedObject(GainNode, { 'audioContext': 'audioContext', - 'outputNode': 'tunaDelayNode.content', + 'outputNode': 'tunaHighpassFilterNode.content', }), quarterNoteDelayTime: Ember.computed('syncBpm', function() { @@ -221,13 +221,6 @@ export default Ember.Mixin.create( return bpmToSpb(this.get('syncBpm')) * 1000; }), - tunaDelayNode: computedObject(TunaDelayNode, { - 'bypass': 'delayBypass', - 'delayTime': 'quarterNoteDelayTime', - 'audioContext': 'audioContext', - 'outputNode': 'tunaHighpassFilterNode.content', - }), - highpassFilterType: 'highpass', tunaHighpassFilterNode: computedObject(TunaFilterNode, { 'filterType': 'highpassFilterType', @@ -241,6 +234,13 @@ export default Ember.Mixin.create( 'filterType': 'lowpassFilterType', 'frequency': 22050, 'audioContext': 'audioContext', + 'outputNode': 'tunaDelayNode.content', + }), + + tunaDelayNode: computedObject(TunaDelayNode, { + 'bypass': 'delayBypass', + 'delayTime': 'quarterNoteDelayTime', + 'audioContext': 'audioContext', 'outputNode': 'outputNode.content', }), From 7b8fe8800c2265de7ff7b9180a7847e9dc23d52a Mon Sep 17 00:00:00 2001 From: wolfbiter Date: Sat, 22 Oct 2016 10:50:30 -0700 Subject: [PATCH 2/2] add 3 band DJ eq to track clip --- .../precision-controls/transition.js | 6 ++ .../automatable-clip/control.js | 12 ++- app/mixins/playable-arrangement/track-clip.js | 76 ++++++++++++++++--- app/models/mix/transition.js | 72 ++++++++++++++++++ 4 files changed, 154 insertions(+), 12 deletions(-) diff --git a/app/components/mix-builder/precision-controls/transition.js b/app/components/mix-builder/precision-controls/transition.js index 135ebde8..7a779e0c 100644 --- a/app/components/mix-builder/precision-controls/transition.js +++ b/app/components/mix-builder/precision-controls/transition.js @@ -11,6 +11,9 @@ import { import { CONTROL_TYPE_VOLUME, + CONTROL_TYPE_LOW_BAND, + CONTROL_TYPE_MID_BAND, + CONTROL_TYPE_HIGH_BAND, CONTROL_TYPE_FILTER_HIGHPASS_CUTOFF, CONTROL_TYPE_FILTER_LOWPASS_CUTOFF, CONTROL_TYPE_DELAY_WET, @@ -19,6 +22,9 @@ import { const AUTOMATION_OPTIONS = { [CONTROL_TYPE_VOLUME]: 'Volume', + [CONTROL_TYPE_LOW_BAND]: 'Low EQ', + [CONTROL_TYPE_MID_BAND]: 'Mid EQ', + [CONTROL_TYPE_HIGH_BAND]: 'High EQ', [CONTROL_TYPE_FILTER_HIGHPASS_CUTOFF]: 'Highpass', [CONTROL_TYPE_FILTER_LOWPASS_CUTOFF]: 'Lowpass', [CONTROL_TYPE_DELAY_WET]: 'Delay Wet', diff --git a/app/mixins/playable-arrangement/automatable-clip/control.js b/app/mixins/playable-arrangement/automatable-clip/control.js index 5e36b920..83914ed5 100644 --- a/app/mixins/playable-arrangement/automatable-clip/control.js +++ b/app/mixins/playable-arrangement/automatable-clip/control.js @@ -7,6 +7,9 @@ import RequireAttributes from 'linx/lib/require-attributes'; import { isValidNumber } from 'linx/lib/utils'; export const CONTROL_TYPE_VOLUME = 'gain'; +export const CONTROL_TYPE_LOW_BAND = 'low-band'; +export const CONTROL_TYPE_MID_BAND = 'mid-band'; +export const CONTROL_TYPE_HIGH_BAND = 'high-band'; export const CONTROL_TYPE_BPM = 'bpm'; export const CONTROL_TYPE_PITCH = 'pitch'; export const CONTROL_TYPE_DELAY_WET = 'delay-wet'; @@ -21,7 +24,10 @@ export const CONTROL_TYPES = [ CONTROL_TYPE_DELAY_WET, CONTROL_TYPE_DELAY_CUTOFF, CONTROL_TYPE_FILTER_HIGHPASS_CUTOFF, - CONTROL_TYPE_FILTER_LOWPASS_CUTOFF + CONTROL_TYPE_FILTER_LOWPASS_CUTOFF, + CONTROL_TYPE_LOW_BAND, + CONTROL_TYPE_MID_BAND, + CONTROL_TYPE_HIGH_BAND ]; // Interface for Automatable Controls @@ -49,6 +55,10 @@ export default function(audioParamPath) { case CONTROL_TYPE_FILTER_HIGHPASS_CUTOFF: case CONTROL_TYPE_FILTER_LOWPASS_CUTOFF: return d3.scale.log().domain([20, 22050]).range([0, 1]); + case CONTROL_TYPE_LOW_BAND: + case CONTROL_TYPE_MID_BAND: + case CONTROL_TYPE_HIGH_BAND: + return d3.scale.linear().domain([-40, 40]).range([0, 1]); default: return d3.scale.identity(); } diff --git a/app/mixins/playable-arrangement/track-clip.js b/app/mixins/playable-arrangement/track-clip.js index 3b4f7502..6c4e57ef 100644 --- a/app/mixins/playable-arrangement/track-clip.js +++ b/app/mixins/playable-arrangement/track-clip.js @@ -23,6 +23,9 @@ import { import { default as AutomatableClipControlMixin, CONTROL_TYPE_VOLUME, + CONTROL_TYPE_LOW_BAND, + CONTROL_TYPE_MID_BAND, + CONTROL_TYPE_HIGH_BAND, CONTROL_TYPE_PITCH, CONTROL_TYPE_DELAY_WET, CONTROL_TYPE_DELAY_CUTOFF, @@ -32,42 +35,63 @@ import { // TODO(CLEANUP): nest under track-clip/controls/gain? const TrackVolumeControl = Ember.Object.extend( - AutomatableClipControlMixin('trackVolumeNode.gain'), { + new AutomatableClipControlMixin('trackVolumeNode.gain'), { type: CONTROL_TYPE_VOLUME, defaultValue: 1, }); +const TrackLowBandControl = Ember.Object.extend( + new AutomatableClipControlMixin('lowBandEqNode.filter.gain'), { + + type: CONTROL_TYPE_LOW_BAND, + defaultValue: 6, +}); + +const TrackMidBandControl = Ember.Object.extend( + new AutomatableClipControlMixin('midBandEqNode.filter.gain'), { + + type: CONTROL_TYPE_MID_BAND, + defaultValue: 6, +}); + +const TrackHighBandControl = Ember.Object.extend( + new AutomatableClipControlMixin('highBandEqNode.filter.gain'), { + + type: CONTROL_TYPE_HIGH_BAND, + defaultValue: 6, +}); + const TrackPitchControl = Ember.Object.extend( - AutomatableClipControlMixin('soundtouchNode.pitch'), { + new AutomatableClipControlMixin('soundtouchNode.pitch'), { type: CONTROL_TYPE_PITCH, defaultValue: 0, }); const TrackDelayWetControl = Ember.Object.extend( - AutomatableClipControlMixin('tunaDelayNode.wet.gain'), { + new AutomatableClipControlMixin('tunaDelayNode.wet.gain'), { type: CONTROL_TYPE_DELAY_WET, defaultValue: 0, }); const TrackDelayCutoffControl = Ember.Object.extend( - AutomatableClipControlMixin('tunaDelayNode.filter.frequency'), { + new AutomatableClipControlMixin('tunaDelayNode.filter.frequency'), { type: CONTROL_TYPE_DELAY_CUTOFF, defaultValue: 2000, }); const TrackHighpassFilterCutoffControl = Ember.Object.extend( - AutomatableClipControlMixin('tunaHighpassFilterNode.filter.frequency'), { + new AutomatableClipControlMixin('tunaHighpassFilterNode.filter.frequency'), { type: CONTROL_TYPE_FILTER_HIGHPASS_CUTOFF, defaultValue: 20, }); const TrackLowpassFilterCutoffControl = Ember.Object.extend( - AutomatableClipControlMixin('tunaLowpassFilterNode.filter.frequency'), { + new AutomatableClipControlMixin('tunaLowpassFilterNode.filter.frequency'), { type: CONTROL_TYPE_FILTER_LOWPASS_CUTOFF, defaultValue: 22050, @@ -78,7 +102,7 @@ const TrackLowpassFilterCutoffControl = Ember.Object.extend( export default Ember.Mixin.create( AutomatableClipMixin, PlayableClipMixin, - ReadinessMixin('isTrackClipReady'), { + new ReadinessMixin('isTrackClipReady'), { // required params track: null, @@ -95,6 +119,9 @@ export default Ember.Mixin.create( controls: Ember.computed(function() { return [ TrackVolumeControl.create({ clip: this }), + TrackLowBandControl.create({ clip: this }), + TrackMidBandControl.create({ clip: this }), + TrackHighBandControl.create({ clip: this }), TrackPitchControl.create({ clip: this }), TrackDelayWetControl.create({ clip: this }), TrackDelayCutoffControl.create({ clip: this }), @@ -213,12 +240,34 @@ export default Ember.Mixin.create( trackVolumeNode: computedObject(GainNode, { 'audioContext': 'audioContext', - 'outputNode': 'tunaHighpassFilterNode.content', + 'outputNode': 'lowBandEqNode.content', }), - quarterNoteDelayTime: Ember.computed('syncBpm', function() { - // return bpmToSpb(this.get('syncBpm')) * 1000 * 3 / 4; - return bpmToSpb(this.get('syncBpm')) * 1000; + lowBandFilterType: 'lowshelf', + lowBandEqNode: computedObject(TunaFilterNode, { + 'filterType': 'lowBandFilterType', + 'frequency': 70, + 'gain': 6, + 'audioContext': 'audioContext', + 'outputNode': 'midBandEqNode.content', + }), + + midBandFilterType: 'peaking', + midBandEqNode: computedObject(TunaFilterNode, { + 'filterType': 'midBandFilterType', + 'frequency': 1000, + 'gain': 6, + 'audioContext': 'audioContext', + 'outputNode': 'highBandEqNode.content', + }), + + highBandFilterType: 'highshelf', + highBandEqNode: computedObject(TunaFilterNode, { + 'filterType': 'highBandFilterType', + 'frequency': 13000, + 'gain': 6, + 'audioContext': 'audioContext', + 'outputNode': 'tunaHighpassFilterNode.content', }), highpassFilterType: 'highpass', @@ -237,6 +286,11 @@ export default Ember.Mixin.create( 'outputNode': 'tunaDelayNode.content', }), + quarterNoteDelayTime: Ember.computed('syncBpm', function() { + // return bpmToSpb(this.get('syncBpm')) * 1000 * 3 / 4; + return bpmToSpb(this.get('syncBpm')) * 1000; + }), + tunaDelayNode: computedObject(TunaDelayNode, { 'bypass': 'delayBypass', 'delayTime': 'quarterNoteDelayTime', diff --git a/app/models/mix/transition.js b/app/models/mix/transition.js index a64576a9..241f172a 100644 --- a/app/models/mix/transition.js +++ b/app/models/mix/transition.js @@ -9,6 +9,9 @@ import DependentRelationshipMixin from 'linx/mixins/models/dependent-relationshi import { CONTROL_TYPE_VOLUME, + CONTROL_TYPE_LOW_BAND, + CONTROL_TYPE_MID_BAND, + CONTROL_TYPE_HIGH_BAND, CONTROL_TYPE_DELAY_WET, CONTROL_TYPE_DELAY_CUTOFF, CONTROL_TYPE_FILTER_HIGHPASS_CUTOFF, @@ -69,6 +72,18 @@ export default DS.Model.extend( controlType: CONTROL_TYPE_VOLUME, transition: this, }); + const fromTrackLowBandClip = store.createRecord('mix/transition/from-track-automation-clip', { + controlType: CONTROL_TYPE_LOW_BAND, + transition: this, + }); + const fromTrackMidBandClip = store.createRecord('mix/transition/from-track-automation-clip', { + controlType: CONTROL_TYPE_MID_BAND, + transition: this, + }); + const fromTrackHighBandClip = store.createRecord('mix/transition/from-track-automation-clip', { + controlType: CONTROL_TYPE_HIGH_BAND, + transition: this, + }); const fromTrackDelayWetClip = store.createRecord('mix/transition/from-track-automation-clip', { controlType: CONTROL_TYPE_DELAY_WET, transition: this, @@ -85,10 +100,23 @@ export default DS.Model.extend( controlType: CONTROL_TYPE_FILTER_LOWPASS_CUTOFF, transition: this, }); + const toTrackVolumeClip = store.createRecord('mix/transition/to-track-automation-clip', { controlType: CONTROL_TYPE_VOLUME, transition: this, }); + const toTrackLowBandClip = store.createRecord('mix/transition/to-track-automation-clip', { + controlType: CONTROL_TYPE_LOW_BAND, + transition: this, + }); + const toTrackMidBandClip = store.createRecord('mix/transition/to-track-automation-clip', { + controlType: CONTROL_TYPE_MID_BAND, + transition: this, + }); + const toTrackHighBandClip = store.createRecord('mix/transition/to-track-automation-clip', { + controlType: CONTROL_TYPE_HIGH_BAND, + transition: this, + }); const toTrackHighpassCutoffClip = store.createRecord('mix/transition/to-track-automation-clip', { controlType: CONTROL_TYPE_FILTER_HIGHPASS_CUTOFF, transition: this, @@ -100,6 +128,9 @@ export default DS.Model.extend( const fromTrackAutomationClips = [ fromTrackVolumeClip, + fromTrackLowBandClip, + fromTrackMidBandClip, + fromTrackHighBandClip, fromTrackDelayWetClip, fromTrackDelayCutoffClip, fromTrackHighpassCutoffClip, @@ -108,6 +139,9 @@ export default DS.Model.extend( const toTrackAutomationClips = [ toTrackVolumeClip, + toTrackLowBandClip, + toTrackMidBandClip, + toTrackHighBandClip, toTrackHighpassCutoffClip, toTrackLowpassCutoffClip ]; @@ -125,6 +159,25 @@ export default DS.Model.extend( direction: -1 })); + fromTrackLowBandClip.addControlPoints(generateControlPointParams({ + startValue: 6, + endValue: 6, + n: volumeControlPointCount, + beatCount, + })); + fromTrackMidBandClip.addControlPoints(generateControlPointParams({ + startValue: 6, + endValue: 6, + n: volumeControlPointCount, + beatCount, + })); + fromTrackHighBandClip.addControlPoints(generateControlPointParams({ + startValue: 6, + endValue: 6, + n: volumeControlPointCount, + beatCount, + })); + fromTrackHighpassCutoffClip.addControlPoints(generateControlPointParams({ startValue: 20, endValue: 20, @@ -176,6 +229,25 @@ export default DS.Model.extend( direction: 1 })); + toTrackLowBandClip.addControlPoints(generateControlPointParams({ + startValue: 6, + endValue: 6, + n: volumeControlPointCount, + beatCount, + })); + toTrackMidBandClip.addControlPoints(generateControlPointParams({ + startValue: 6, + endValue: 6, + n: volumeControlPointCount, + beatCount, + })); + toTrackHighBandClip.addControlPoints(generateControlPointParams({ + startValue: 6, + endValue: 6, + n: volumeControlPointCount, + beatCount, + })); + toTrackHighpassCutoffClip.addControlPoints(generateControlPointParams({ startValue: 20, endValue: 20,