OpenShot Audio Library | OpenShotAudio  0.3.3
juce_MPESynthesiserBase.cpp
1 /*
2  ==============================================================================
3 
4  This file is part of the JUCE library.
5  Copyright (c) 2017 - ROLI Ltd.
6 
7  JUCE is an open source library subject to commercial or open-source
8  licensing.
9 
10  The code included in this file is provided under the terms of the ISC license
11  http://www.isc.org/downloads/software-support-policy/isc-license. Permission
12  To use, copy, modify, and/or distribute this software for any purpose with or
13  without fee is hereby granted provided that the above copyright notice and
14  this permission notice appear in all copies.
15 
16  JUCE IS PROVIDED "AS IS" WITHOUT ANY WARRANTY, AND ALL WARRANTIES, WHETHER
17  EXPRESSED OR IMPLIED, INCLUDING MERCHANTABILITY AND FITNESS FOR PURPOSE, ARE
18  DISCLAIMED.
19 
20  ==============================================================================
21 */
22 
23 namespace juce
24 {
25 
27  : instrument (new MPEInstrument)
28 {
29  instrument->addListener (this);
30 }
31 
33  : instrument (inst)
34 {
35  jassert (instrument != nullptr);
36  instrument->addListener (this);
37 }
38 
39 //==============================================================================
41 {
42  return instrument->getZoneLayout();
43 }
44 
46 {
47  instrument->setZoneLayout (newLayout);
48 }
49 
50 //==============================================================================
51 void MPESynthesiserBase::enableLegacyMode (int pitchbendRange, Range<int> channelRange)
52 {
53  instrument->enableLegacyMode (pitchbendRange, channelRange);
54 }
55 
57 {
58  return instrument->isLegacyModeEnabled();
59 }
60 
62 {
63  return instrument->getLegacyModeChannelRange();
64 }
65 
67 {
68  instrument->setLegacyModeChannelRange (channelRange);
69 }
70 
72 {
73  return instrument->getLegacyModePitchbendRange();
74 }
75 
77 {
78  instrument->setLegacyModePitchbendRange (pitchbendRange);
79 }
80 
81 //==============================================================================
83 {
84  instrument->setPressureTrackingMode (modeToUse);
85 }
86 
88 {
89  instrument->setPitchbendTrackingMode (modeToUse);
90 }
91 
93 {
94  instrument->setTimbreTrackingMode (modeToUse);
95 }
96 
97 //==============================================================================
99 {
100  instrument->processNextMidiEvent (m);
101 }
102 
103 //==============================================================================
104 template <typename floatType>
106  const MidiBuffer& inputMidi,
107  int startSample,
108  int numSamples)
109 {
110  // you must set the sample rate before using this!
111  jassert (sampleRate != 0);
112 
113  MidiBuffer::Iterator midiIterator (inputMidi);
114  midiIterator.setNextSamplePosition (startSample);
115 
116  bool firstEvent = true;
117  int midiEventPos;
118  MidiMessage m;
119 
120  const ScopedLock sl (noteStateLock);
121 
122  while (numSamples > 0)
123  {
124  if (! midiIterator.getNextEvent (m, midiEventPos))
125  {
126  renderNextSubBlock (outputAudio, startSample, numSamples);
127  return;
128  }
129 
130  auto samplesToNextMidiMessage = midiEventPos - startSample;
131 
132  if (samplesToNextMidiMessage >= numSamples)
133  {
134  renderNextSubBlock (outputAudio, startSample, numSamples);
135  handleMidiEvent (m);
136  break;
137  }
138 
139  if (samplesToNextMidiMessage < ((firstEvent && ! subBlockSubdivisionIsStrict) ? 1 : minimumSubBlockSize))
140  {
141  handleMidiEvent (m);
142  continue;
143  }
144 
145  firstEvent = false;
146 
147  renderNextSubBlock (outputAudio, startSample, samplesToNextMidiMessage);
148  handleMidiEvent (m);
149  startSample += samplesToNextMidiMessage;
150  numSamples -= samplesToNextMidiMessage;
151  }
152 
153  while (midiIterator.getNextEvent (m, midiEventPos))
154  handleMidiEvent (m);
155 }
156 
157 // explicit instantiation for supported float types:
158 template void MPESynthesiserBase::renderNextBlock<float> (AudioBuffer<float>&, const MidiBuffer&, int, int);
159 template void MPESynthesiserBase::renderNextBlock<double> (AudioBuffer<double>&, const MidiBuffer&, int, int);
160 
161 //==============================================================================
163 {
164  if (sampleRate != newRate)
165  {
166  const ScopedLock sl (noteStateLock);
167  instrument->releaseAllNotes();
168  sampleRate = newRate;
169  }
170 }
171 
172 //==============================================================================
173 void MPESynthesiserBase::setMinimumRenderingSubdivisionSize (int numSamples, bool shouldBeStrict) noexcept
174 {
175  jassert (numSamples > 0); // it wouldn't make much sense for this to be less than 1
176  minimumSubBlockSize = numSamples;
177  subBlockSubdivisionIsStrict = shouldBeStrict;
178 }
179 
180 } // namespace juce
void setNextSamplePosition(int samplePosition) noexcept
bool getNextEvent(MidiMessage &result, int &samplePosition) noexcept
void setPitchbendTrackingMode(TrackingMode modeToUse)
virtual void handleMidiEvent(const MidiMessage &)
bool isLegacyModeEnabled() const noexcept
MPEZoneLayout getZoneLayout() const noexcept
void setZoneLayout(MPEZoneLayout newLayout)
int getLegacyModePitchbendRange() const noexcept
void setLegacyModeChannelRange(Range< int > channelRange)
void setLegacyModePitchbendRange(int pitchbendRange)
void enableLegacyMode(int pitchbendRange=2, Range< int > channelRange=Range< int >(1, 17))
void setTimbreTrackingMode(TrackingMode modeToUse)
std::unique_ptr< MPEInstrument > instrument
void setPressureTrackingMode(TrackingMode modeToUse)
Range< int > getLegacyModeChannelRange() const noexcept
virtual void setCurrentPlaybackSampleRate(double sampleRate)
void renderNextBlock(AudioBuffer< floatType > &outputAudio, const MidiBuffer &inputMidi, int startSample, int numSamples)
void setMinimumRenderingSubdivisionSize(int numSamples, bool shouldBeStrict=false) noexcept
virtual void renderNextSubBlock(AudioBuffer< float > &outputAudio, int startSample, int numSamples)=0