The JUCE cross-platform C++ framework, with DISTRHO/KXStudio specific changes
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

159 lines
4.5KB

  1. /*
  2. ==============================================================================
  3. This file is part of the JUCE library - "Jules' Utility Class Extensions"
  4. Copyright 2004-11 by Raw Material Software Ltd.
  5. ------------------------------------------------------------------------------
  6. JUCE can be redistributed and/or modified under the terms of the GNU General
  7. Public License (Version 2), as published by the Free Software Foundation.
  8. A copy of the license is included in the JUCE distribution, or can be found
  9. online at www.gnu.org/licenses.
  10. JUCE is distributed in the hope that it will be useful, but WITHOUT ANY
  11. WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR
  12. A PARTICULAR PURPOSE. See the GNU General Public License for more details.
  13. ------------------------------------------------------------------------------
  14. To release a closed-source product which uses JUCE, commercial licenses are
  15. available: visit www.rawmaterialsoftware.com/juce for more information.
  16. ==============================================================================
  17. */
  18. MixerAudioSource::MixerAudioSource()
  19. : tempBuffer (2, 0),
  20. currentSampleRate (0.0),
  21. bufferSizeExpected (0)
  22. {
  23. }
  24. MixerAudioSource::~MixerAudioSource()
  25. {
  26. removeAllInputs();
  27. }
  28. //==============================================================================
  29. void MixerAudioSource::addInputSource (AudioSource* input, const bool deleteWhenRemoved)
  30. {
  31. if (input != nullptr && ! inputs.contains (input))
  32. {
  33. double localRate;
  34. int localBufferSize;
  35. {
  36. const ScopedLock sl (lock);
  37. localRate = currentSampleRate;
  38. localBufferSize = bufferSizeExpected;
  39. }
  40. if (localRate > 0.0)
  41. input->prepareToPlay (localBufferSize, localRate);
  42. const ScopedLock sl (lock);
  43. inputsToDelete.setBit (inputs.size(), deleteWhenRemoved);
  44. inputs.add (input);
  45. }
  46. }
  47. void MixerAudioSource::removeInputSource (AudioSource* const input)
  48. {
  49. if (input != nullptr)
  50. {
  51. ScopedPointer<AudioSource> toDelete;
  52. {
  53. const ScopedLock sl (lock);
  54. const int index = inputs.indexOf (input);
  55. if (index < 0)
  56. return;
  57. if (inputsToDelete [index])
  58. toDelete = input;
  59. inputsToDelete.shiftBits (-1, index);
  60. inputs.remove (index);
  61. }
  62. input->releaseResources();
  63. }
  64. }
  65. void MixerAudioSource::removeAllInputs()
  66. {
  67. OwnedArray<AudioSource> toDelete;
  68. {
  69. const ScopedLock sl (lock);
  70. for (int i = inputs.size(); --i >= 0;)
  71. if (inputsToDelete[i])
  72. toDelete.add (inputs.getUnchecked(i));
  73. inputs.clear();
  74. }
  75. for (int i = toDelete.size(); --i >= 0;)
  76. toDelete.getUnchecked(i)->releaseResources();
  77. }
  78. void MixerAudioSource::prepareToPlay (int samplesPerBlockExpected, double sampleRate)
  79. {
  80. tempBuffer.setSize (2, samplesPerBlockExpected);
  81. const ScopedLock sl (lock);
  82. currentSampleRate = sampleRate;
  83. bufferSizeExpected = samplesPerBlockExpected;
  84. for (int i = inputs.size(); --i >= 0;)
  85. inputs.getUnchecked(i)->prepareToPlay (samplesPerBlockExpected, sampleRate);
  86. }
  87. void MixerAudioSource::releaseResources()
  88. {
  89. const ScopedLock sl (lock);
  90. for (int i = inputs.size(); --i >= 0;)
  91. inputs.getUnchecked(i)->releaseResources();
  92. tempBuffer.setSize (2, 0);
  93. currentSampleRate = 0;
  94. bufferSizeExpected = 0;
  95. }
  96. void MixerAudioSource::getNextAudioBlock (const AudioSourceChannelInfo& info)
  97. {
  98. const ScopedLock sl (lock);
  99. if (inputs.size() > 0)
  100. {
  101. inputs.getUnchecked(0)->getNextAudioBlock (info);
  102. if (inputs.size() > 1)
  103. {
  104. tempBuffer.setSize (jmax (1, info.buffer->getNumChannels()),
  105. info.buffer->getNumSamples());
  106. AudioSourceChannelInfo info2 (&tempBuffer, 0, info.numSamples);
  107. for (int i = 1; i < inputs.size(); ++i)
  108. {
  109. inputs.getUnchecked(i)->getNextAudioBlock (info2);
  110. for (int chan = 0; chan < info.buffer->getNumChannels(); ++chan)
  111. info.buffer->addFrom (chan, info.startSample, tempBuffer, chan, 0, info.numSamples);
  112. }
  113. }
  114. }
  115. else
  116. {
  117. info.clearActiveBufferRegion();
  118. }
  119. }