Browse Source

Update to JUCE 6.0.4, all patches rebased

tags/2020-12-27
falkTX 3 years ago
parent
commit
776e0314ce
Signed by: falkTX <falktx@falktx.com> GPG Key ID: CDBAA37ABC74FBA0
100 changed files with 64751 additions and 63142 deletions
  1. +29
    -4
      libs/juce-current/source/modules/juce_audio_basics/audio_play_head/juce_AudioPlayHead.h
  2. +24
    -24
      libs/juce-current/source/modules/juce_audio_basics/buffers/juce_AudioDataConverters.cpp
  3. +8
    -8
      libs/juce-current/source/modules/juce_audio_basics/buffers/juce_AudioSampleBuffer.h
  4. +1
    -1
      libs/juce-current/source/modules/juce_audio_basics/juce_audio_basics.h
  5. +1
    -1
      libs/juce-current/source/modules/juce_audio_basics/midi/juce_MidiKeyboardState.h
  6. +1
    -1
      libs/juce-current/source/modules/juce_audio_basics/midi/juce_MidiMessage.h
  7. +5
    -4
      libs/juce-current/source/modules/juce_audio_devices/audio_io/juce_AudioDeviceManager.cpp
  8. +79
    -22
      libs/juce-current/source/modules/juce_audio_devices/audio_io/juce_AudioIODeviceType.cpp
  9. +5
    -2
      libs/juce-current/source/modules/juce_audio_devices/audio_io/juce_AudioIODeviceType.h
  10. +45
    -75
      libs/juce-current/source/modules/juce_audio_devices/juce_audio_devices.cpp
  11. +18
    -11
      libs/juce-current/source/modules/juce_audio_devices/juce_audio_devices.h
  12. +11
    -2
      libs/juce-current/source/modules/juce_audio_devices/midi_io/juce_MidiDevices.h
  13. +0
    -5
      libs/juce-current/source/modules/juce_audio_devices/native/juce_linux_ALSA.cpp
  14. +26
    -29
      libs/juce-current/source/modules/juce_audio_devices/native/juce_linux_Bela.cpp
  15. +205
    -163
      libs/juce-current/source/modules/juce_audio_devices/native/juce_linux_JackAudio.cpp
  16. +32
    -14
      libs/juce-current/source/modules/juce_audio_devices/native/juce_linux_Midi.cpp
  17. +0
    -6
      libs/juce-current/source/modules/juce_audio_devices/native/juce_mac_CoreAudio.cpp
  18. +26
    -17
      libs/juce-current/source/modules/juce_audio_devices/native/juce_mac_CoreMidi.cpp
  19. +8
    -13
      libs/juce-current/source/modules/juce_audio_devices/native/juce_win32_ASIO.cpp
  20. +0
    -6
      libs/juce-current/source/modules/juce_audio_devices/native/juce_win32_DirectSound.cpp
  21. +38
    -40
      libs/juce-current/source/modules/juce_audio_devices/native/juce_win32_Midi.cpp
  22. +324
    -125
      libs/juce-current/source/modules/juce_audio_devices/native/juce_win32_WASAPI.cpp
  23. +24
    -22
      libs/juce-current/source/modules/juce_audio_formats/codecs/juce_OggVorbisAudioFormat.cpp
  24. +6
    -15
      libs/juce-current/source/modules/juce_audio_formats/codecs/juce_WindowsMediaAudioFormat.cpp
  25. +11
    -9
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/Ogg Vorbis Licence.txt
  26. +1091
    -788
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/bitwise.c
  27. +241
    -242
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/codec.h
  28. +4
    -0
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/config_types.h
  29. +278
    -0
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/crctable.h
  30. +2109
    -1796
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/framing.c
  31. +0
    -134
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.2/README
  32. +0
    -0
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/AUTHORS
  33. +58
    -0
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/CHANGES
  34. +1
    -1
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/COPYING
  35. +147
    -0
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/README.md
  36. +108
    -109
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/analysis.c
  37. +143
    -144
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/backends.h
  38. +252
    -253
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/bitrate.c
  39. +58
    -59
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/bitrate.h
  40. +1043
    -1033
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/block.c
  41. +12273
    -12256
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/books/coupled/res_books_51.h
  42. +15782
    -15782
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/books/coupled/res_books_stereo.h
  43. +1546
    -1546
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/books/floor/floor_books.h
  44. +7757
    -7757
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/books/uncoupled/res_books_uncoupled.h
  45. +461
    -451
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/codebook.c
  46. +117
    -119
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/codebook.h
  47. +166
    -187
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/codec_internal.h
  48. +374
    -375
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/envelope.c
  49. +79
    -80
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/envelope.h
  50. +220
    -223
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/floor0.c
  51. +1088
    -1084
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/floor1.c
  52. +57
    -58
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/highlevel.h
  53. +688
    -660
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/info.c
  54. +93
    -94
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/lookup.c
  55. +31
    -32
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/lookup.h
  56. +191
    -192
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/lookup_data.h
  57. +159
    -160
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/lpc.c
  58. +28
    -29
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/lpc.h
  59. +454
    -454
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/lsp.c
  60. +27
    -28
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/lsp.h
  61. +808
    -816
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/mapping0.c
  62. +784
    -785
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/masking.h
  63. +562
    -563
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/mdct.c
  64. +70
    -71
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/mdct.h
  65. +216
    -0
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/misc.c
  66. +53
    -53
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/misc.h
  67. +259
    -260
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/modes/floor_all.h
  68. +50
    -50
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/modes/psych_11.h
  69. +132
    -133
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/modes/psych_16.h
  70. +641
    -642
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/modes/psych_44.h
  71. +100
    -101
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/modes/psych_8.h
  72. +162
    -163
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/modes/residue_16.h
  73. +291
    -292
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/modes/residue_44.h
  74. +450
    -451
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/modes/residue_44p51.h
  75. +317
    -318
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/modes/residue_44u.h
  76. +108
    -109
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/modes/residue_8.h
  77. +142
    -143
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/modes/setup_11.h
  78. +152
    -153
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/modes/setup_16.h
  79. +127
    -128
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/modes/setup_22.h
  80. +131
    -132
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/modes/setup_32.h
  81. +116
    -117
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/modes/setup_44.h
  82. +73
    -74
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/modes/setup_44p51.h
  83. +73
    -74
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/modes/setup_44u.h
  84. +148
    -149
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/modes/setup_8.h
  85. +224
    -225
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/modes/setup_X.h
  86. +189
    -186
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/os.h
  87. +1211
    -1205
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/psy.c
  88. +153
    -154
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/psy.h
  89. +44
    -45
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/registry.c
  90. +31
    -32
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/registry.h
  91. +886
    -891
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/res0.c
  92. +89
    -90
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/scales.h
  93. +610
    -585
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/sharedbook.c
  94. +1254
    -1255
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/smallft.c
  95. +33
    -34
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/smallft.h
  96. +179
    -184
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/synthesis.c
  97. +1224
    -1215
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/vorbisenc.c
  98. +2448
    -2358
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/vorbisfile.c
  99. +2135
    -2135
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/window.c
  100. +25
    -26
      libs/juce-current/source/modules/juce_audio_formats/codecs/oggvorbis/libvorbis-1.3.7/lib/window.h

+ 29
- 4
libs/juce-current/source/modules/juce_audio_basics/audio_play_head/juce_AudioPlayHead.h View File

@@ -122,10 +122,35 @@ public:
bool isLooping;
//==============================================================================
bool operator== (const CurrentPositionInfo& other) const noexcept;
bool operator!= (const CurrentPositionInfo& other) const noexcept;
void resetToDefault();
bool operator== (const CurrentPositionInfo& other) const noexcept
{
return timeInSamples == other.timeInSamples
&& ppqPosition == other.ppqPosition
&& editOriginTime == other.editOriginTime
&& ppqPositionOfLastBarStart == other.ppqPositionOfLastBarStart
&& frameRate == other.frameRate
&& isPlaying == other.isPlaying
&& isRecording == other.isRecording
&& bpm == other.bpm
&& timeSigNumerator == other.timeSigNumerator
&& timeSigDenominator == other.timeSigDenominator
&& ppqLoopStart == other.ppqLoopStart
&& ppqLoopEnd == other.ppqLoopEnd
&& isLooping == other.isLooping;
}
bool operator!= (const CurrentPositionInfo& other) const noexcept
{
return ! operator== (other);
}
void resetToDefault()
{
zerostruct (*this);
timeSigNumerator = 4;
timeSigDenominator = 4;
bpm = 120;
}
};
//==============================================================================


+ 24
- 24
libs/juce-current/source/modules/juce_audio_basics/buffers/juce_AudioDataConverters.cpp View File

@@ -32,7 +32,7 @@ void AudioDataConverters::convertFloatToInt16LE (const float* source, void* dest
{
for (int i = 0; i < numSamples; ++i)
{
*reinterpret_cast<uint16*> (intData) = ByteOrder::swapIfBigEndian ((uint16) (short) roundToInt (jlimit (-maxVal, maxVal, maxVal * source[i])));
*unalignedPointerCast<uint16*> (intData) = ByteOrder::swapIfBigEndian ((uint16) (short) roundToInt (jlimit (-maxVal, maxVal, maxVal * source[i])));
intData += destBytesPerSample;
}
}
@@ -43,7 +43,7 @@ void AudioDataConverters::convertFloatToInt16LE (const float* source, void* dest
for (int i = numSamples; --i >= 0;)
{
intData -= destBytesPerSample;
*reinterpret_cast<uint16*> (intData) = ByteOrder::swapIfBigEndian ((uint16) (short) roundToInt (jlimit (-maxVal, maxVal, maxVal * source[i])));
*unalignedPointerCast<uint16*> (intData) = ByteOrder::swapIfBigEndian ((uint16) (short) roundToInt (jlimit (-maxVal, maxVal, maxVal * source[i])));
}
}
}
@@ -57,7 +57,7 @@ void AudioDataConverters::convertFloatToInt16BE (const float* source, void* dest
{
for (int i = 0; i < numSamples; ++i)
{
*reinterpret_cast<uint16*> (intData) = ByteOrder::swapIfLittleEndian ((uint16) (short) roundToInt (jlimit (-maxVal, maxVal, maxVal * source[i])));
*unalignedPointerCast<uint16*> (intData) = ByteOrder::swapIfLittleEndian ((uint16) (short) roundToInt (jlimit (-maxVal, maxVal, maxVal * source[i])));
intData += destBytesPerSample;
}
}
@@ -68,7 +68,7 @@ void AudioDataConverters::convertFloatToInt16BE (const float* source, void* dest
for (int i = numSamples; --i >= 0;)
{
intData -= destBytesPerSample;
*reinterpret_cast<uint16*> (intData) = ByteOrder::swapIfLittleEndian ((uint16) (short) roundToInt (jlimit (-maxVal, maxVal, maxVal * source[i])));
*unalignedPointerCast<uint16*> (intData) = ByteOrder::swapIfLittleEndian ((uint16) (short) roundToInt (jlimit (-maxVal, maxVal, maxVal * source[i])));
}
}
}
@@ -132,7 +132,7 @@ void AudioDataConverters::convertFloatToInt32LE (const float* source, void* dest
{
for (int i = 0; i < numSamples; ++i)
{
*reinterpret_cast<uint32*> (intData) = ByteOrder::swapIfBigEndian ((uint32) roundToInt (jlimit (-maxVal, maxVal, maxVal * source[i])));
*unalignedPointerCast<uint32*> (intData) = ByteOrder::swapIfBigEndian ((uint32) roundToInt (jlimit (-maxVal, maxVal, maxVal * source[i])));
intData += destBytesPerSample;
}
}
@@ -143,7 +143,7 @@ void AudioDataConverters::convertFloatToInt32LE (const float* source, void* dest
for (int i = numSamples; --i >= 0;)
{
intData -= destBytesPerSample;
*reinterpret_cast<uint32*> (intData) = ByteOrder::swapIfBigEndian ((uint32) roundToInt (jlimit (-maxVal, maxVal, maxVal * source[i])));
*unalignedPointerCast<uint32*> (intData) = ByteOrder::swapIfBigEndian ((uint32) roundToInt (jlimit (-maxVal, maxVal, maxVal * source[i])));
}
}
}
@@ -157,7 +157,7 @@ void AudioDataConverters::convertFloatToInt32BE (const float* source, void* dest
{
for (int i = 0; i < numSamples; ++i)
{
*reinterpret_cast<uint32*> (intData) = ByteOrder::swapIfLittleEndian ((uint32) roundToInt (jlimit (-maxVal, maxVal, maxVal * source[i])));
*unalignedPointerCast<uint32*> (intData) = ByteOrder::swapIfLittleEndian ((uint32) roundToInt (jlimit (-maxVal, maxVal, maxVal * source[i])));
intData += destBytesPerSample;
}
}
@@ -168,7 +168,7 @@ void AudioDataConverters::convertFloatToInt32BE (const float* source, void* dest
for (int i = numSamples; --i >= 0;)
{
intData -= destBytesPerSample;
*reinterpret_cast<uint32*> (intData) = ByteOrder::swapIfLittleEndian ((uint32) roundToInt (jlimit (-maxVal, maxVal, maxVal * source[i])));
*unalignedPointerCast<uint32*> (intData) = ByteOrder::swapIfLittleEndian ((uint32) roundToInt (jlimit (-maxVal, maxVal, maxVal * source[i])));
}
}
}
@@ -181,10 +181,10 @@ void AudioDataConverters::convertFloatToFloat32LE (const float* source, void* de
for (int i = 0; i < numSamples; ++i)
{
*reinterpret_cast<float*> (d) = source[i];
*unalignedPointerCast<float*> (d) = source[i];
#if JUCE_BIG_ENDIAN
*reinterpret_cast<uint32*> (d) = ByteOrder::swap (*reinterpret_cast<uint32*> (d));
*unalignedPointerCast<uint32*> (d) = ByteOrder::swap (*unalignedPointerCast<uint32*> (d));
#endif
d += destBytesPerSample;
@@ -199,10 +199,10 @@ void AudioDataConverters::convertFloatToFloat32BE (const float* source, void* de
for (int i = 0; i < numSamples; ++i)
{
*reinterpret_cast<float*> (d) = source[i];
*unalignedPointerCast<float*> (d) = source[i];
#if JUCE_LITTLE_ENDIAN
*reinterpret_cast<uint32*> (d) = ByteOrder::swap (*reinterpret_cast<uint32*> (d));
*unalignedPointerCast<uint32*> (d) = ByteOrder::swap (*unalignedPointerCast<uint32*> (d));
#endif
d += destBytesPerSample;
@@ -219,7 +219,7 @@ void AudioDataConverters::convertInt16LEToFloat (const void* source, float* dest
{
for (int i = 0; i < numSamples; ++i)
{
dest[i] = scale * (short) ByteOrder::swapIfBigEndian (*reinterpret_cast<const uint16*> (intData));
dest[i] = scale * (short) ByteOrder::swapIfBigEndian (*unalignedPointerCast<const uint16*> (intData));
intData += srcBytesPerSample;
}
}
@@ -230,7 +230,7 @@ void AudioDataConverters::convertInt16LEToFloat (const void* source, float* dest
for (int i = numSamples; --i >= 0;)
{
intData -= srcBytesPerSample;
dest[i] = scale * (short) ByteOrder::swapIfBigEndian (*reinterpret_cast<const uint16*> (intData));
dest[i] = scale * (short) ByteOrder::swapIfBigEndian (*unalignedPointerCast<const uint16*> (intData));
}
}
}
@@ -244,7 +244,7 @@ void AudioDataConverters::convertInt16BEToFloat (const void* source, float* dest
{
for (int i = 0; i < numSamples; ++i)
{
dest[i] = scale * (short) ByteOrder::swapIfLittleEndian (*reinterpret_cast<const uint16*> (intData));
dest[i] = scale * (short) ByteOrder::swapIfLittleEndian (*unalignedPointerCast<const uint16*> (intData));
intData += srcBytesPerSample;
}
}
@@ -255,7 +255,7 @@ void AudioDataConverters::convertInt16BEToFloat (const void* source, float* dest
for (int i = numSamples; --i >= 0;)
{
intData -= srcBytesPerSample;
dest[i] = scale * (short) ByteOrder::swapIfLittleEndian (*reinterpret_cast<const uint16*> (intData));
dest[i] = scale * (short) ByteOrder::swapIfLittleEndian (*unalignedPointerCast<const uint16*> (intData));
}
}
}
@@ -319,7 +319,7 @@ void AudioDataConverters::convertInt32LEToFloat (const void* source, float* dest
{
for (int i = 0; i < numSamples; ++i)
{
dest[i] = scale * (float) ByteOrder::swapIfBigEndian (*reinterpret_cast<const uint32*> (intData));
dest[i] = scale * (float) ByteOrder::swapIfBigEndian (*unalignedPointerCast<const uint32*> (intData));
intData += srcBytesPerSample;
}
}
@@ -330,7 +330,7 @@ void AudioDataConverters::convertInt32LEToFloat (const void* source, float* dest
for (int i = numSamples; --i >= 0;)
{
intData -= srcBytesPerSample;
dest[i] = scale * (float) ByteOrder::swapIfBigEndian (*reinterpret_cast<const uint32*> (intData));
dest[i] = scale * (float) ByteOrder::swapIfBigEndian (*unalignedPointerCast<const uint32*> (intData));
}
}
}
@@ -344,7 +344,7 @@ void AudioDataConverters::convertInt32BEToFloat (const void* source, float* dest
{
for (int i = 0; i < numSamples; ++i)
{
dest[i] = scale * (float) ByteOrder::swapIfLittleEndian (*reinterpret_cast<const uint32*> (intData));
dest[i] = scale * (float) ByteOrder::swapIfLittleEndian (*unalignedPointerCast<const uint32*> (intData));
intData += srcBytesPerSample;
}
}
@@ -355,7 +355,7 @@ void AudioDataConverters::convertInt32BEToFloat (const void* source, float* dest
for (int i = numSamples; --i >= 0;)
{
intData -= srcBytesPerSample;
dest[i] = scale * (float) ByteOrder::swapIfLittleEndian (*reinterpret_cast<const uint32*> (intData));
dest[i] = scale * (float) ByteOrder::swapIfLittleEndian (*unalignedPointerCast<const uint32*> (intData));
}
}
}
@@ -366,10 +366,10 @@ void AudioDataConverters::convertFloat32LEToFloat (const void* source, float* de
for (int i = 0; i < numSamples; ++i)
{
dest[i] = *reinterpret_cast<const float*> (s);
dest[i] = *unalignedPointerCast<const float*> (s);
#if JUCE_BIG_ENDIAN
auto d = reinterpret_cast<uint32*> (dest + i);
auto d = unalignedPointerCast<uint32*> (dest + i);
*d = ByteOrder::swap (*d);
#endif
@@ -383,10 +383,10 @@ void AudioDataConverters::convertFloat32BEToFloat (const void* source, float* de
for (int i = 0; i < numSamples; ++i)
{
dest[i] = *reinterpret_cast<const float*> (s);
dest[i] = *unalignedPointerCast<const float*> (s);
#if JUCE_LITTLE_ENDIAN
auto d = reinterpret_cast<uint32*> (dest + i);
auto d = unalignedPointerCast<uint32*> (dest + i);
*d = ByteOrder::swap (*d);
#endif


+ 8
- 8
libs/juce-current/source/modules/juce_audio_basics/buffers/juce_AudioSampleBuffer.h View File

@@ -409,8 +409,8 @@ public:
auto numSamplesToCopy = (size_t) jmin (newNumSamples, size);
auto newChannels = reinterpret_cast<Type**> (newData.get());
auto newChan = reinterpret_cast<Type*> (newData + channelListSize);
auto newChannels = unalignedPointerCast<Type**> (newData.get());
auto newChan = unalignedPointerCast<Type*> (newData + channelListSize);
for (int j = 0; j < newNumChannels; ++j)
{
@@ -442,10 +442,10 @@ public:
{
allocatedBytes = newTotalBytes;
allocatedData.allocate (newTotalBytes, clearExtraSpace || isClear);
channels = reinterpret_cast<Type**> (allocatedData.get());
channels = unalignedPointerCast<Type**> (allocatedData.get());
}
auto* chan = reinterpret_cast<Type*> (allocatedData + channelListSize);
auto* chan = unalignedPointerCast<Type*> (allocatedData + channelListSize);
for (int i = 0; i < newNumChannels; ++i)
{
@@ -1127,7 +1127,7 @@ private:
void allocateData()
{
#if (! JUCE_GCC) || (__GNUC__ * 100 + __GNUC_MINOR__) >= 409
#if ! JUCE_PROJUCER_LIVE_BUILD && (! JUCE_GCC || (__GNUC__ * 100 + __GNUC_MINOR__) >= 409)
static_assert (alignof (Type) <= detail::maxAlignment,
"AudioBuffer cannot hold types with alignment requirements larger than that guaranteed by malloc");
#endif
@@ -1142,8 +1142,8 @@ private:
allocatedBytes = (size_t) numChannels * (size_t) size * sizeof (Type) + channelListSize + 32;
allocatedData.malloc (allocatedBytes);
channels = reinterpret_cast<Type**> (allocatedData.get());
auto chan = reinterpret_cast<Type*> (allocatedData + channelListSize);
channels = unalignedPointerCast<Type**> (allocatedData.get());
auto chan = unalignedPointerCast<Type*> (allocatedData + channelListSize);
for (int i = 0; i < numChannels; ++i)
{
@@ -1167,7 +1167,7 @@ private:
else
{
allocatedData.malloc (numChannels + 1, sizeof (Type*));
channels = reinterpret_cast<Type**> (allocatedData.get());
channels = unalignedPointerCast<Type**> (allocatedData.get());
}
for (int i = 0; i < numChannels; ++i)


+ 1
- 1
libs/juce-current/source/modules/juce_audio_basics/juce_audio_basics.h View File

@@ -32,7 +32,7 @@
ID: juce_audio_basics
vendor: juce
version: 6.0.0
version: 6.0.4
name: JUCE audio and MIDI data classes
description: Classes for audio buffer manipulation, midi message handling, synthesis, etc.
website: http://www.juce.com/juce


+ 1
- 1
libs/juce-current/source/modules/juce_audio_basics/midi/juce_MidiKeyboardState.h View File

@@ -136,7 +136,7 @@ public:
//==============================================================================
/** Receives events from a MidiKeyboardState object. */
class Listener
class JUCE_API Listener
{
public:
//==============================================================================


+ 1
- 1
libs/juce-current/source/modules/juce_audio_basics/midi/juce_MidiMessage.h View File

@@ -401,7 +401,7 @@ public:
/** Returns true if the message is an aftertouch event.
For aftertouch events, use the getNoteNumber() method to find out the key
that it applies to, and getAftertouchValue() to find out the amount. Use
that it applies to, and getAfterTouchValue() to find out the amount. Use
getChannel() to find out the channel.
@see getAftertouchValue, getNoteNumber


+ 5
- 4
libs/juce-current/source/modules/juce_audio_devices/audio_io/juce_AudioDeviceManager.cpp View File

@@ -177,8 +177,9 @@ static void addIfNotNull (OwnedArray<AudioIODeviceType>& list, AudioIODeviceType
void AudioDeviceManager::createAudioDeviceTypes (OwnedArray<AudioIODeviceType>& list)
{
addIfNotNull (list, AudioIODeviceType::createAudioIODeviceType_WASAPI (false));
addIfNotNull (list, AudioIODeviceType::createAudioIODeviceType_WASAPI (true));
addIfNotNull (list, AudioIODeviceType::createAudioIODeviceType_WASAPI (WASAPIDeviceMode::shared));
addIfNotNull (list, AudioIODeviceType::createAudioIODeviceType_WASAPI (WASAPIDeviceMode::exclusive));
addIfNotNull (list, AudioIODeviceType::createAudioIODeviceType_WASAPI (WASAPIDeviceMode::sharedLowLatency));
addIfNotNull (list, AudioIODeviceType::createAudioIODeviceType_DirectSound());
addIfNotNull (list, AudioIODeviceType::createAudioIODeviceType_ASIO());
addIfNotNull (list, AudioIODeviceType::createAudioIODeviceType_CoreAudio());
@@ -544,6 +545,8 @@ String AudioDeviceManager::setAudioDeviceSetup (const AudioDeviceSetup& newSetup
else if (currentAudioDevice != nullptr)
return {};
stopDevice();
if (getCurrentDeviceTypeObject() == nullptr
|| (newSetup.inputDeviceName.isEmpty() && newSetup.outputDeviceName.isEmpty()))
{
@@ -555,8 +558,6 @@ String AudioDeviceManager::setAudioDeviceSetup (const AudioDeviceSetup& newSetup
return {};
}
stopDevice();
String error;
if (currentSetup.inputDeviceName != newSetup.inputDeviceName


+ 79
- 22
libs/juce-current/source/modules/juce_audio_devices/audio_io/juce_AudioIODeviceType.cpp View File

@@ -42,48 +42,105 @@ void AudioIODeviceType::callDeviceChangeListeners()
}
//==============================================================================
#if ! JUCE_MAC
AudioIODeviceType* AudioIODeviceType::createAudioIODeviceType_CoreAudio() { return nullptr; }
#if JUCE_MAC
AudioIODeviceType* AudioIODeviceType::createAudioIODeviceType_CoreAudio() { return new CoreAudioClasses::CoreAudioIODeviceType(); }
#else
AudioIODeviceType* AudioIODeviceType::createAudioIODeviceType_CoreAudio() { return nullptr; }
#endif
#if ! JUCE_IOS
AudioIODeviceType* AudioIODeviceType::createAudioIODeviceType_iOSAudio() { return nullptr; }
#if JUCE_IOS
AudioIODeviceType* AudioIODeviceType::createAudioIODeviceType_iOSAudio() { return new iOSAudioIODeviceType(); }
#else
AudioIODeviceType* AudioIODeviceType::createAudioIODeviceType_iOSAudio() { return nullptr; }
#endif
#if ! (JUCE_WINDOWS && JUCE_WASAPI)
AudioIODeviceType* AudioIODeviceType::createAudioIODeviceType_WASAPI (bool) { return nullptr; }
#if JUCE_WINDOWS && JUCE_WASAPI
AudioIODeviceType* AudioIODeviceType::createAudioIODeviceType_WASAPI (WASAPIDeviceMode deviceMode)
{
auto windowsVersion = SystemStats::getOperatingSystemType();
if (windowsVersion < SystemStats::WinVista
|| (WasapiClasses::isLowLatencyMode (deviceMode) && windowsVersion < SystemStats::Windows10))
return nullptr;
return new WasapiClasses::WASAPIAudioIODeviceType (deviceMode);
}
AudioIODeviceType* AudioIODeviceType::createAudioIODeviceType_WASAPI (bool exclusiveMode)
{
return createAudioIODeviceType_WASAPI (exclusiveMode ? WASAPIDeviceMode::exclusive
: WASAPIDeviceMode::shared);
}
#else
AudioIODeviceType* AudioIODeviceType::createAudioIODeviceType_WASAPI (WASAPIDeviceMode) { return nullptr; }
AudioIODeviceType* AudioIODeviceType::createAudioIODeviceType_WASAPI (bool) { return nullptr; }
#endif
#if ! (JUCE_WINDOWS && JUCE_DIRECTSOUND)
AudioIODeviceType* AudioIODeviceType::createAudioIODeviceType_DirectSound() { return nullptr; }
#if JUCE_WINDOWS && JUCE_DIRECTSOUND
AudioIODeviceType* AudioIODeviceType::createAudioIODeviceType_DirectSound() { return new DSoundAudioIODeviceType(); }
#else
AudioIODeviceType* AudioIODeviceType::createAudioIODeviceType_DirectSound() { return nullptr; }
#endif
#if ! (JUCE_WINDOWS && JUCE_ASIO)
AudioIODeviceType* AudioIODeviceType::createAudioIODeviceType_ASIO() { return nullptr; }
#if JUCE_WINDOWS && JUCE_ASIO
AudioIODeviceType* AudioIODeviceType::createAudioIODeviceType_ASIO() { return new ASIOAudioIODeviceType(); }
#else
AudioIODeviceType* AudioIODeviceType::createAudioIODeviceType_ASIO() { return nullptr; }
#endif
#if ! (JUCE_LINUX && JUCE_ALSA)
AudioIODeviceType* AudioIODeviceType::createAudioIODeviceType_ALSA() { return nullptr; }
#if JUCE_LINUX && JUCE_ALSA
AudioIODeviceType* AudioIODeviceType::createAudioIODeviceType_ALSA() { return createAudioIODeviceType_ALSA_PCMDevices(); }
#else
AudioIODeviceType* AudioIODeviceType::createAudioIODeviceType_ALSA() { return nullptr; }
#endif
#if ! (JUCE_LINUX && JUCE_JACK)
AudioIODeviceType* AudioIODeviceType::createAudioIODeviceType_JACK() { return nullptr; }
#if JUCE_LINUX && JUCE_JACK
AudioIODeviceType* AudioIODeviceType::createAudioIODeviceType_JACK() { return new JackAudioIODeviceType(); }
#else
AudioIODeviceType* AudioIODeviceType::createAudioIODeviceType_JACK() { return nullptr; }
#endif
#if ! (JUCE_LINUX && JUCE_BELA)
AudioIODeviceType* AudioIODeviceType::createAudioIODeviceType_Bela() { return nullptr; }
#if JUCE_LINUX && JUCE_BELA
AudioIODeviceType* AudioIODeviceType::createAudioIODeviceType_Bela() { return new BelaAudioIODeviceType(); }
#else
AudioIODeviceType* AudioIODeviceType::createAudioIODeviceType_Bela() { return nullptr; }
#endif
#if ! JUCE_ANDROID
AudioIODeviceType* AudioIODeviceType::createAudioIODeviceType_Android() { return nullptr; }
#if JUCE_ANDROID
AudioIODeviceType* AudioIODeviceType::createAudioIODeviceType_Android()
{
#if JUCE_USE_ANDROID_OBOE
if (isOboeAvailable())
return nullptr;
#endif
#if JUCE_USE_ANDROID_OPENSLES
if (isOpenSLAvailable())
return nullptr;
#endif
return new AndroidAudioIODeviceType();
}
#else
AudioIODeviceType* AudioIODeviceType::createAudioIODeviceType_Android() { return nullptr; }
#endif
#if ! (JUCE_ANDROID && JUCE_USE_ANDROID_OPENSLES)
AudioIODeviceType* AudioIODeviceType::createAudioIODeviceType_OpenSLES() { return nullptr; }
#if JUCE_ANDROID && JUCE_USE_ANDROID_OPENSLES
AudioIODeviceType* AudioIODeviceType::createAudioIODeviceType_OpenSLES()
{
return isOpenSLAvailable() ? new OpenSLAudioDeviceType() : nullptr;
}
#else
AudioIODeviceType* AudioIODeviceType::createAudioIODeviceType_OpenSLES() { return nullptr; }
#endif
#if ! (JUCE_ANDROID && JUCE_USE_ANDROID_OBOE)
AudioIODeviceType* AudioIODeviceType::createAudioIODeviceType_Oboe() { return nullptr; }
#if JUCE_ANDROID && JUCE_USE_ANDROID_OBOE
AudioIODeviceType* AudioIODeviceType::createAudioIODeviceType_Oboe()
{
return isOboeAvailable() ? new OboeAudioIODeviceType() : nullptr;
}
#else
AudioIODeviceType* AudioIODeviceType::createAudioIODeviceType_Oboe() { return nullptr; }
#endif
} // namespace juce

+ 5
- 2
libs/juce-current/source/modules/juce_audio_devices/audio_io/juce_AudioIODeviceType.h View File

@@ -149,8 +149,8 @@ public:
static AudioIODeviceType* createAudioIODeviceType_CoreAudio();
/** Creates an iOS device type if it's available on this platform, or returns null. */
static AudioIODeviceType* createAudioIODeviceType_iOSAudio();
/** Creates a WASAPI device type if it's available on this platform, or returns null. */
static AudioIODeviceType* createAudioIODeviceType_WASAPI (bool exclusiveMode);
/** Creates a WASAPI device type in the specified mode if it's available on this platform, or returns null. */
static AudioIODeviceType* createAudioIODeviceType_WASAPI (WASAPIDeviceMode deviceMode);
/** Creates a DirectSound device type if it's available on this platform, or returns null. */
static AudioIODeviceType* createAudioIODeviceType_DirectSound();
/** Creates an ASIO device type if it's available on this platform, or returns null. */
@@ -168,6 +168,9 @@ public:
/** Creates a Bela device type if it's available on this platform, or returns null. */
static AudioIODeviceType* createAudioIODeviceType_Bela();
/** This method has been deprecated. You should call the method which takes a WASAPIDeviceMode instead. */
JUCE_DEPRECATED (static AudioIODeviceType* createAudioIODeviceType_WASAPI (bool exclusiveMode));
protected:
explicit AudioIODeviceType (const String& typeName);


+ 45
- 75
libs/juce-current/source/modules/juce_audio_devices/juce_audio_devices.cpp View File

@@ -45,6 +45,8 @@
#include "juce_audio_devices.h"
#include "native/juce_MidiDataConcatenator.h"
//==============================================================================
#if JUCE_MAC
#define Point CarbonDummyPointName
@@ -55,6 +57,9 @@
#undef Point
#undef Component
#include "native/juce_mac_CoreAudio.cpp"
#include "native/juce_mac_CoreMidi.cpp"
#elif JUCE_IOS
#import <AudioToolbox/AudioToolbox.h>
#import <AVFoundation/AVFoundation.h>
@@ -64,13 +69,21 @@
#import <CoreMIDI/MIDINetworkSession.h>
#endif
#include "native/juce_ios_Audio.cpp"
#include "native/juce_mac_CoreMidi.cpp"
//==============================================================================
#elif JUCE_WINDOWS
#if JUCE_WASAPI
#include <mmreg.h>
#include "native/juce_win32_WASAPI.cpp"
#endif
#if JUCE_USE_WINRT_MIDI && JUCE_MSVC
#if JUCE_DIRECTSOUND
#include "native/juce_win32_DirectSound.cpp"
#endif
#if JUCE_USE_WINRT_MIDI && (JUCE_MSVC || JUCE_CLANG)
/* If you cannot find any of the header files below then you are probably
attempting to use the Windows 10 Bluetooth Low Energy API. For this to work you
need to install version 10.0.14393.0 of the Windows Standalone SDK and you may
@@ -93,6 +106,8 @@
JUCE_END_IGNORE_WARNINGS_MSVC
#endif
#include "native/juce_win32_Midi.cpp"
#if JUCE_ASIO
/* This is very frustrating - we only need to use a handful of definitions from
a couple of the header files in Steinberg's ASIO SDK, and it'd be easy to copy
@@ -114,6 +129,7 @@
needed - so to simplify things, you could just copy these into your JUCE directory).
*/
#include <iasiodrv.h>
#include "native/juce_win32_ASIO.cpp"
#endif
//==============================================================================
@@ -128,6 +144,7 @@
just set the JUCE_ALSA flag to 0.
*/
#include <alsa/asoundlib.h>
#include "native/juce_linux_ALSA.cpp"
#endif
#if JUCE_JACK
@@ -140,6 +157,7 @@
JUCE with low latency audio support, just set the JUCE_JACK flag to 0.
*/
#include <jack/jack.h>
#include "native/juce_linux_JackAudio.cpp"
#endif
#if JUCE_BELA
@@ -149,89 +167,18 @@
*/
#include <Bela.h>
#include <Midi.h>
#include "native/juce_linux_Bela.cpp"
#endif
#undef SIZEOF
//==============================================================================
#elif JUCE_ANDROID
#if JUCE_USE_ANDROID_OPENSLES
#include <SLES/OpenSLES.h>
#include <SLES/OpenSLES_Android.h>
#include <SLES/OpenSLES_AndroidConfiguration.h>
#endif
#if JUCE_USE_ANDROID_OBOE
#if JUCE_USE_ANDROID_OPENSLES
#error "Oboe cannot be enabled at the same time as openSL! Please disable JUCE_USE_ANDROID_OPENSLES"
#endif
JUCE_BEGIN_IGNORE_WARNINGS_GCC_LIKE ("-Wunused-parameter",
"-Wzero-as-null-pointer-constant",
"-Winconsistent-missing-destructor-override",
"-Wshadow-field-in-constructor",
"-Wshadow-field")
#include <oboe/Oboe.h>
JUCE_END_IGNORE_WARNINGS_GCC_LIKE
#endif
#endif
#include "audio_io/juce_AudioDeviceManager.cpp"
#include "audio_io/juce_AudioIODevice.cpp"
#include "audio_io/juce_AudioIODeviceType.cpp"
#include "midi_io/juce_MidiMessageCollector.cpp"
#include "midi_io/juce_MidiDevices.cpp"
#include "sources/juce_AudioSourcePlayer.cpp"
#include "sources/juce_AudioTransportSource.cpp"
#include "native/juce_MidiDataConcatenator.h"
//==============================================================================
#if JUCE_MAC
#include "native/juce_mac_CoreAudio.cpp"
#include "native/juce_mac_CoreMidi.cpp"
//==============================================================================
#elif JUCE_IOS
#include "native/juce_ios_Audio.cpp"
#include "native/juce_mac_CoreMidi.cpp"
//==============================================================================
#elif JUCE_WINDOWS
#if JUCE_WASAPI
#include "native/juce_win32_WASAPI.cpp"
#endif
#if JUCE_DIRECTSOUND
#include "native/juce_win32_DirectSound.cpp"
#endif
#include "native/juce_win32_Midi.cpp"
#if JUCE_ASIO
#include "native/juce_win32_ASIO.cpp"
#endif
//==============================================================================
#elif JUCE_LINUX
#if JUCE_ALSA
#include "native/juce_linux_ALSA.cpp"
#endif
#if JUCE_JACK
#include "native/juce_linux_JackAudio.cpp"
#endif
#if JUCE_BELA
#include "native/juce_linux_Bela.cpp"
#else
#if ! JUCE_BELA
#include "native/juce_linux_Midi.cpp"
#endif
//==============================================================================
#elif JUCE_ANDROID
#include "native/juce_android_Audio.cpp"
#include "native/juce_android_Midi.cpp"
@@ -239,10 +186,25 @@
#include "native/juce_android_HighPerformanceAudioHelpers.h"
#if JUCE_USE_ANDROID_OPENSLES
#include <SLES/OpenSLES.h>
#include <SLES/OpenSLES_Android.h>
#include <SLES/OpenSLES_AndroidConfiguration.h>
#include "native/juce_android_OpenSL.cpp"
#endif
#if JUCE_USE_ANDROID_OBOE
#if JUCE_USE_ANDROID_OPENSLES
#error "Oboe cannot be enabled at the same time as openSL! Please disable JUCE_USE_ANDROID_OPENSLES"
#endif
JUCE_BEGIN_IGNORE_WARNINGS_GCC_LIKE ("-Wunused-parameter",
"-Wzero-as-null-pointer-constant",
"-Winconsistent-missing-destructor-override",
"-Wshadow-field-in-constructor",
"-Wshadow-field")
#include <oboe/Oboe.h>
JUCE_END_IGNORE_WARNINGS_GCC_LIKE
#include "native/juce_android_Oboe.cpp"
#endif
#endif
@@ -259,3 +221,11 @@ namespace juce
bool JUCE_CALLTYPE SystemAudioVolume::setMuted (bool) { jassertfalse; return false; }
}
#endif
#include "audio_io/juce_AudioDeviceManager.cpp"
#include "audio_io/juce_AudioIODevice.cpp"
#include "audio_io/juce_AudioIODeviceType.cpp"
#include "midi_io/juce_MidiMessageCollector.cpp"
#include "midi_io/juce_MidiDevices.cpp"
#include "sources/juce_AudioSourcePlayer.cpp"
#include "sources/juce_AudioTransportSource.cpp"

+ 18
- 11
libs/juce-current/source/modules/juce_audio_devices/juce_audio_devices.h View File

@@ -32,7 +32,7 @@
ID: juce_audio_devices
vendor: juce
version: 6.0.0
version: 6.0.4
name: JUCE audio and MIDI I/O device classes
description: Classes to play and record from audio and MIDI I/O devices
website: http://www.juce.com/juce
@@ -88,21 +88,12 @@
#endif
/** Config: JUCE_WASAPI
Enables WASAPI audio devices (Windows Vista and above). See also the
JUCE_WASAPI_EXCLUSIVE flag.
Enables WASAPI audio devices (Windows Vista and above).
*/
#ifndef JUCE_WASAPI
#define JUCE_WASAPI 1
#endif
/** Config: JUCE_WASAPI_EXCLUSIVE
Enables WASAPI audio devices in exclusive mode (Windows Vista and above).
*/
#ifndef JUCE_WASAPI_EXCLUSIVE
#define JUCE_WASAPI_EXCLUSIVE 0
#endif
/** Config: JUCE_DIRECTSOUND
Enables DirectSound audio (MS Windows only).
*/
@@ -174,6 +165,22 @@
//==============================================================================
#include "midi_io/juce_MidiDevices.h"
#include "midi_io/juce_MidiMessageCollector.h"
namespace juce
{
/** Available modes for the WASAPI audio device.
Pass one of these to the AudioIODeviceType::createAudioIODeviceType_WASAPI()
method to create a WASAPI AudioIODeviceType object in this mode.
*/
enum class WASAPIDeviceMode
{
shared,
exclusive,
sharedLowLatency
};
}
#include "audio_io/juce_AudioIODevice.h"
#include "audio_io/juce_AudioIODeviceType.h"
#include "audio_io/juce_SystemAudioVolume.h"


+ 11
- 2
libs/juce-current/source/modules/juce_audio_devices/midi_io/juce_MidiDevices.h View File

@@ -164,12 +164,16 @@ public:
/** Deprecated. */
static std::unique_ptr<MidiInput> openDevice (int, MidiInputCallback*);
/** @internal */
class Pimpl;
private:
//==============================================================================
explicit MidiInput (const String&, const String&);
MidiDeviceInfo deviceInfo;
void* internal = nullptr;
std::unique_ptr<Pimpl> internal;
JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR (MidiInput)
};
@@ -350,6 +354,9 @@ public:
/** Deprecated. */
static std::unique_ptr<MidiOutput> openDevice (int);
/** @internal */
class Pimpl;
private:
//==============================================================================
struct PendingMessage
@@ -368,7 +375,9 @@ private:
void run() override;
MidiDeviceInfo deviceInfo;
void* internal = nullptr;
std::unique_ptr<Pimpl> internal;
CriticalSection lock;
PendingMessage* firstMessage = nullptr;


+ 0
- 5
libs/juce-current/source/modules/juce_audio_devices/native/juce_linux_ALSA.cpp View File

@@ -1299,9 +1299,4 @@ AudioIODeviceType* createAudioIODeviceType_ALSA_PCMDevices()
return new ALSAAudioIODeviceType (false, "ALSA");
}
AudioIODeviceType* AudioIODeviceType::createAudioIODeviceType_ALSA()
{
return createAudioIODeviceType_ALSA_PCMDevices();
}
} // namespace juce

+ 26
- 29
libs/juce-current/source/modules/juce_audio_devices/native/juce_linux_Bela.cpp View File

@@ -24,12 +24,12 @@ namespace juce
{
//==============================================================================
class BelaMidiInput
class MidiInput::Pimpl
{
public:
static Array<BelaMidiInput*> midiInputs;
static Array<Pimpl*> midiInputs;
BelaMidiInput (const String& port, MidiInput* input, MidiInputCallback* callback)
Pimpl (const String& port, MidiInput* input, MidiInputCallback* callback)
: midiInput (input), midiPort (port), midiCallback (callback)
{
jassert (midiCallback != nullptr);
@@ -38,7 +38,7 @@ public:
buffer.resize (32);
}
~BelaMidiInput()
~Pimpl()
{
stop();
midiInputs.removeAllInstancesOf (this);
@@ -76,7 +76,7 @@ public:
}
if (receivedBytes > 0)
pushMidiData (receivedBytes);
pushMidiData ((int) receivedBytes);
}
static Array<MidiDeviceInfo> getDevices (bool input)
@@ -141,7 +141,7 @@ private:
snd_rawmidi_info_t* info;
snd_rawmidi_info_alloca (&info);
snd_rawmidi_info_set_device (info, device);
snd_rawmidi_info_set_device (info, (unsigned int) device);
snd_rawmidi_info_set_stream (info, input ? SND_RAWMIDI_STREAM_INPUT
: SND_RAWMIDI_STREAM_OUTPUT);
@@ -173,10 +173,10 @@ private:
Midi midi;
MidiDataConcatenator concatenator { 512 };
JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR (BelaMidiInput)
JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR (Pimpl)
};
Array<BelaMidiInput*> BelaMidiInput::midiInputs;
Array<MidiInput::Pimpl*> MidiInput::Pimpl::midiInputs;
//==============================================================================
@@ -366,7 +366,7 @@ public:
String getLastError() override { return lastError; }
//==============================================================================
int getCurrentBufferSizeSamples() override { return actualBufferSize; }
int getCurrentBufferSizeSamples() override { return (int) actualBufferSize; }
double getCurrentSampleRate() override { return 44100.0; }
int getCurrentBitDepth() override { return 16; }
BigInteger getActiveOutputChannels() const override { BigInteger b; b.setRange (0, actualNumberOfOutputs, true); return b; }
@@ -384,8 +384,8 @@ private:
bool setup (BelaContext& context)
{
actualBufferSize = context.audioFrames;
actualNumberOfInputs = context.audioInChannels + context.analogInChannels;
actualNumberOfOutputs = context.audioOutChannels + context.analogOutChannels;
actualNumberOfInputs = (int) (context.audioInChannels + context.analogInChannels);
actualNumberOfOutputs = (int) (context.audioOutChannels + context.analogOutChannels);
isBelaOpen = true;
firstCallback = true;
@@ -405,7 +405,7 @@ private:
ScopedLock lock (callbackLock);
// Check for and process and midi
for (auto midiInput : BelaMidiInput::midiInputs)
for (auto midiInput : MidiInput::Pimpl::midiInputs)
midiInput->poll();
if (callback != nullptr)
@@ -413,27 +413,29 @@ private:
jassert (context.audioFrames <= actualBufferSize);
jassert ((context.flags & BELA_FLAG_INTERLEAVED) == 0);
using Frames = decltype (context.audioFrames);
// Setup channelInBuffers
for (int ch = 0; ch < actualNumberOfInputs; ++ch)
{
if (ch < analogChannelStart)
channelInBuffer[ch] = &context.audioIn[ch * context.audioFrames];
channelInBuffer[ch] = &context.audioIn[(Frames) ch * context.audioFrames];
else
channelInBuffer[ch] = &context.analogIn[(ch - analogChannelStart) * context.analogFrames];
channelInBuffer[ch] = &context.analogIn[(Frames) (ch - analogChannelStart) * context.analogFrames];
}
// Setup channelOutBuffers
for (int ch = 0; ch < actualNumberOfOutputs; ++ch)
{
if (ch < analogChannelStart)
channelOutBuffer[ch] = &context.audioOut[ch * context.audioFrames];
channelOutBuffer[ch] = &context.audioOut[(Frames) ch * context.audioFrames];
else
channelOutBuffer[ch] = &context.analogOut[(ch - analogChannelStart) * context.audioFrames];
channelOutBuffer[ch] = &context.analogOut[(Frames) (ch - analogChannelStart) * context.audioFrames];
}
callback->audioDeviceIOCallback (channelInBuffer.getData(), actualNumberOfInputs,
channelOutBuffer.getData(), actualNumberOfOutputs,
context.audioFrames);
(int) context.audioFrames);
}
}
@@ -521,25 +523,19 @@ struct BelaAudioIODeviceType : public AudioIODeviceType
JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR (BelaAudioIODeviceType)
};
//==============================================================================
AudioIODeviceType* AudioIODeviceType::createAudioIODeviceType_Bela()
{
return new BelaAudioIODeviceType();
}
//==============================================================================
MidiInput::MidiInput (const String& deviceName, const String& deviceID)
: deviceInfo (deviceName, deviceID)
{
}
MidiInput::~MidiInput() { delete static_cast<BelaMidiInput*> (internal); }
void MidiInput::start() { static_cast<BelaMidiInput*> (internal)->start(); }
void MidiInput::stop() { static_cast<BelaMidiInput*> (internal)->stop(); }
MidiInput::~MidiInput() = default;
void MidiInput::start() { internal->start(); }
void MidiInput::stop() { internal->stop(); }
Array<MidiDeviceInfo> MidiInput::getAvailableDevices()
{
return BelaMidiInput::getDevices (true);
return Pimpl::getDevices (true);
}
MidiDeviceInfo MidiInput::getDefaultDevice()
@@ -553,7 +549,7 @@ std::unique_ptr<MidiInput> MidiInput::openDevice (const String& deviceIdentifier
return {};
std::unique_ptr<MidiInput> midiInput (new MidiInput (deviceIdentifier, deviceIdentifier));
midiInput->internal = new BelaMidiInput (deviceIdentifier, midiInput.get(), callback);
midiInput->internal = std::make_unique<Pimpl> (deviceIdentifier, midiInput.get(), callback);
return midiInput;
}
@@ -587,7 +583,8 @@ std::unique_ptr<MidiInput> MidiInput::openDevice (int index, MidiInputCallback*
//==============================================================================
// TODO: Add Bela MidiOutput support
MidiOutput::~MidiOutput() {}
class MidiOutput::Pimpl {};
MidiOutput::~MidiOutput() = default;
void MidiOutput::sendMessageNow (const MidiMessage&) {}
Array<MidiDeviceInfo> MidiOutput::getAvailableDevices() { return {}; }
MidiDeviceInfo MidiOutput::getDefaultDevice() { return {}; }


+ 205
- 163
libs/juce-current/source/modules/juce_audio_devices/native/juce_linux_JackAudio.cpp View File

@@ -36,9 +36,11 @@ static void* juce_loadJackFunction (const char* const name)
#define JUCE_DECL_JACK_FUNCTION(return_type, fn_name, argument_types, arguments) \
return_type fn_name argument_types \
{ \
using ReturnType = return_type; \
typedef return_type (*fn_type) argument_types; \
static fn_type fn = (fn_type) juce_loadJackFunction (#fn_name); \
return (fn != nullptr) ? ((*fn) arguments) : (return_type) 0; \
jassert (fn != nullptr); \
return (fn != nullptr) ? ((*fn) arguments) : ReturnType(); \
}
#define JUCE_DECL_VOID_JACK_FUNCTION(fn_name, argument_types, arguments) \
@@ -46,30 +48,35 @@ static void* juce_loadJackFunction (const char* const name)
{ \
typedef void (*fn_type) argument_types; \
static fn_type fn = (fn_type) juce_loadJackFunction (#fn_name); \
jassert (fn != nullptr); \
if (fn != nullptr) (*fn) arguments; \
}
//==============================================================================
JUCE_DECL_JACK_FUNCTION (jack_client_t*, jack_client_open, (const char* client_name, jack_options_t options, jack_status_t* status, ...), (client_name, options, status));
JUCE_DECL_JACK_FUNCTION (int, jack_client_close, (jack_client_t *client), (client));
JUCE_DECL_JACK_FUNCTION (int, jack_activate, (jack_client_t* client), (client));
JUCE_DECL_JACK_FUNCTION (int, jack_deactivate, (jack_client_t* client), (client));
JUCE_DECL_JACK_FUNCTION (jack_nframes_t, jack_get_buffer_size, (jack_client_t* client), (client));
JUCE_DECL_JACK_FUNCTION (jack_nframes_t, jack_get_sample_rate, (jack_client_t* client), (client));
JUCE_DECL_VOID_JACK_FUNCTION (jack_on_shutdown, (jack_client_t* client, void (*function)(void* arg), void* arg), (client, function, arg));
JUCE_DECL_JACK_FUNCTION (void* , jack_port_get_buffer, (jack_port_t* port, jack_nframes_t nframes), (port, nframes));
JUCE_DECL_JACK_FUNCTION (jack_nframes_t, jack_port_get_total_latency, (jack_client_t* client, jack_port_t* port), (client, port));
JUCE_DECL_JACK_FUNCTION (jack_port_t* , jack_port_register, (jack_client_t* client, const char* port_name, const char* port_type, unsigned long flags, unsigned long buffer_size), (client, port_name, port_type, flags, buffer_size));
JUCE_DECL_VOID_JACK_FUNCTION (jack_set_error_function, (void (*func)(const char*)), (func));
JUCE_DECL_JACK_FUNCTION (int, jack_set_process_callback, (jack_client_t* client, JackProcessCallback process_callback, void* arg), (client, process_callback, arg));
JUCE_DECL_JACK_FUNCTION (const char**, jack_get_ports, (jack_client_t* client, const char* port_name_pattern, const char* type_name_pattern, unsigned long flags), (client, port_name_pattern, type_name_pattern, flags));
JUCE_DECL_JACK_FUNCTION (int, jack_connect, (jack_client_t* client, const char* source_port, const char* destination_port), (client, source_port, destination_port));
JUCE_DECL_JACK_FUNCTION (const char*, jack_port_name, (const jack_port_t* port), (port));
JUCE_DECL_JACK_FUNCTION (void*, jack_set_port_connect_callback, (jack_client_t* client, JackPortConnectCallback connect_callback, void* arg), (client, connect_callback, arg));
JUCE_DECL_JACK_FUNCTION (jack_port_t* , jack_port_by_id, (jack_client_t* client, jack_port_id_t port_id), (client, port_id));
JUCE_DECL_JACK_FUNCTION (int, jack_port_connected, (const jack_port_t* port), (port));
JUCE_DECL_JACK_FUNCTION (int, jack_port_connected_to, (const jack_port_t* port, const char* port_name), (port, port_name));
JUCE_DECL_JACK_FUNCTION (int, jack_set_xrun_callback, (jack_client_t* client, JackXRunCallback xrun_callback, void* arg), (client, xrun_callback, arg));
JUCE_DECL_JACK_FUNCTION (jack_client_t*, jack_client_open, (const char* client_name, jack_options_t options, jack_status_t* status, ...), (client_name, options, status))
JUCE_DECL_JACK_FUNCTION (int, jack_client_close, (jack_client_t *client), (client))
JUCE_DECL_JACK_FUNCTION (int, jack_activate, (jack_client_t* client), (client))
JUCE_DECL_JACK_FUNCTION (int, jack_deactivate, (jack_client_t* client), (client))
JUCE_DECL_JACK_FUNCTION (jack_nframes_t, jack_get_buffer_size, (jack_client_t* client), (client))
JUCE_DECL_JACK_FUNCTION (jack_nframes_t, jack_get_sample_rate, (jack_client_t* client), (client))
JUCE_DECL_VOID_JACK_FUNCTION (jack_on_shutdown, (jack_client_t* client, void (*function)(void* arg), void* arg), (client, function, arg))
JUCE_DECL_VOID_JACK_FUNCTION (jack_on_info_shutdown, (jack_client_t* client, JackInfoShutdownCallback function, void* arg), (client, function, arg))
JUCE_DECL_JACK_FUNCTION (void* , jack_port_get_buffer, (jack_port_t* port, jack_nframes_t nframes), (port, nframes))
JUCE_DECL_JACK_FUNCTION (jack_nframes_t, jack_port_get_total_latency, (jack_client_t* client, jack_port_t* port), (client, port))
JUCE_DECL_JACK_FUNCTION (jack_port_t* , jack_port_register, (jack_client_t* client, const char* port_name, const char* port_type, unsigned long flags, unsigned long buffer_size), (client, port_name, port_type, flags, buffer_size))
JUCE_DECL_VOID_JACK_FUNCTION (jack_set_error_function, (void (*func)(const char*)), (func))
JUCE_DECL_JACK_FUNCTION (int, jack_set_process_callback, (jack_client_t* client, JackProcessCallback process_callback, void* arg), (client, process_callback, arg))
JUCE_DECL_JACK_FUNCTION (const char**, jack_get_ports, (jack_client_t* client, const char* port_name_pattern, const char* type_name_pattern, unsigned long flags), (client, port_name_pattern, type_name_pattern, flags))
JUCE_DECL_JACK_FUNCTION (int, jack_connect, (jack_client_t* client, const char* source_port, const char* destination_port), (client, source_port, destination_port))
JUCE_DECL_JACK_FUNCTION (const char*, jack_port_name, (const jack_port_t* port), (port))
JUCE_DECL_JACK_FUNCTION (void*, jack_set_port_connect_callback, (jack_client_t* client, JackPortConnectCallback connect_callback, void* arg), (client, connect_callback, arg))
JUCE_DECL_JACK_FUNCTION (jack_port_t* , jack_port_by_id, (jack_client_t* client, jack_port_id_t port_id), (client, port_id))
JUCE_DECL_JACK_FUNCTION (int, jack_port_connected, (const jack_port_t* port), (port))
JUCE_DECL_JACK_FUNCTION (int, jack_port_connected_to, (const jack_port_t* port, const char* port_name), (port, port_name))
JUCE_DECL_JACK_FUNCTION (int, jack_set_xrun_callback, (jack_client_t* client, JackXRunCallback xrun_callback, void* arg), (client, xrun_callback, arg))
JUCE_DECL_JACK_FUNCTION (int, jack_port_flags, (const jack_port_t* port), (port))
JUCE_DECL_JACK_FUNCTION (jack_port_t*, jack_port_by_name, (jack_client_t* client, const char* name), (client, name))
JUCE_DECL_VOID_JACK_FUNCTION (jack_free, (void* ptr), (ptr))
#if JUCE_DEBUG
#define JACK_LOGGING_ENABLED 1
@@ -115,56 +122,56 @@ namespace
struct JackPortIterator
{
JackPortIterator (jack_client_t* const client, const bool forInput)
: ports (nullptr), index (-1)
{
if (client != nullptr)
ports = juce::jack_get_ports (client, nullptr, nullptr,
forInput ? JackPortIsOutput : JackPortIsInput);
// (NB: This looks like it's the wrong way round, but it is correct!)
}
~JackPortIterator()
{
::free (ports);
ports.reset (juce::jack_get_ports (client, nullptr, nullptr,
forInput ? JackPortIsInput : JackPortIsOutput));
}
bool next()
{
if (ports == nullptr || ports [index + 1] == nullptr)
if (ports == nullptr || ports.get()[index + 1] == nullptr)
return false;
name = CharPointer_UTF8 (ports[++index]);
clientName = name.upToFirstOccurrenceOf (":", false, false);
name = CharPointer_UTF8 (ports.get()[++index]);
return true;
}
const char** ports;
int index;
String getClientName() const
{
return name.upToFirstOccurrenceOf (":", false, false);
}
String getChannelName() const
{
return name.fromFirstOccurrenceOf (":", false, false);
}
struct Free
{
void operator() (const char** ptr) const noexcept { juce::jack_free (ptr); }
};
std::unique_ptr<const char*, Free> ports;
int index = -1;
String name;
String clientName;
};
class JackAudioIODeviceType;
static Array<JackAudioIODeviceType*> activeDeviceTypes;
//==============================================================================
class JackAudioIODevice : public AudioIODevice
{
public:
JackAudioIODevice (const String& deviceName,
const String& inId,
const String& outId)
: AudioIODevice (deviceName, "JACK"),
inputId (inId),
outputId (outId),
deviceIsOpen (false),
callback (nullptr),
totalNumberOfInputChannels (0),
totalNumberOfOutputChannels (0)
{
jassert (deviceName.isNotEmpty());
jack_status_t status;
JackAudioIODevice (const String& inName,
const String& outName,
std::function<void()> notifyIn)
: AudioIODevice (outName.isEmpty() ? inName : outName, "JACK"),
inputName (inName),
outputName (outName),
notifyChannelsChanged (std::move (notifyIn))
{
jassert (outName.isNotEmpty() || inName.isNotEmpty());
jack_status_t status = {};
client = juce::jack_client_open (JUCE_JACK_CLIENT_NAME, JackNoStartServer, &status);
if (client == nullptr)
@@ -179,10 +186,10 @@ public:
const StringArray inputChannels (getInputChannelNames());
for (int i = 0; i < inputChannels.size(); ++i)
{
String inputName;
inputName << "in_" << ++totalNumberOfInputChannels;
String inputChannelName;
inputChannelName << "in_" << ++totalNumberOfInputChannels;
inputPorts.add (juce::jack_port_register (client, inputName.toUTF8(),
inputPorts.add (juce::jack_port_register (client, inputChannelName.toUTF8(),
JACK_DEFAULT_AUDIO_TYPE, JackPortIsInput, 0));
}
@@ -190,10 +197,10 @@ public:
const StringArray outputChannels (getOutputChannelNames());
for (int i = 0; i < outputChannels.size(); ++i)
{
String outputName;
outputName << "out_" << ++totalNumberOfOutputChannels;
String outputChannelName;
outputChannelName << "out_" << ++totalNumberOfOutputChannels;
outputPorts.add (juce::jack_port_register (client, outputName.toUTF8(),
outputPorts.add (juce::jack_port_register (client, outputChannelName.toUTF8(),
JACK_DEFAULT_AUDIO_TYPE, JackPortIsOutput, 0));
}
@@ -202,7 +209,7 @@ public:
}
}
~JackAudioIODevice()
~JackAudioIODevice() override
{
close();
if (client != nullptr)
@@ -212,19 +219,19 @@ public:
}
}
StringArray getChannelNames (bool forInput) const
StringArray getChannelNames (const String& clientName, bool forInput) const
{
StringArray names;
for (JackPortIterator i (client, forInput); i.next();)
if (i.clientName == getName())
names.add (i.name.fromFirstOccurrenceOf (":", false, false));
if (i.getClientName() == clientName)
names.add (i.getChannelName());
return names;
}
StringArray getOutputChannelNames() override { return getChannelNames (false); }
StringArray getInputChannelNames() override { return getChannelNames (true); }
StringArray getOutputChannelNames() override { return getChannelNames (outputName, true); }
StringArray getInputChannelNames() override { return getChannelNames (inputName, false); }
Array<double> getAvailableSampleRates() override
{
@@ -241,15 +248,29 @@ public:
Array<int> sizes;
if (client != nullptr)
sizes.add (juce::jack_get_buffer_size (client));
sizes.add (static_cast<int> (juce::jack_get_buffer_size (client)));
return sizes;
}
int getDefaultBufferSize() override { return getCurrentBufferSizeSamples(); }
int getCurrentBufferSizeSamples() override { return client != nullptr ? juce::jack_get_buffer_size (client) : 0; }
double getCurrentSampleRate() override { return client != nullptr ? juce::jack_get_sample_rate (client) : 0; }
int getCurrentBufferSizeSamples() override { return client != nullptr ? static_cast<int> (juce::jack_get_buffer_size (client)) : 0; }
double getCurrentSampleRate() override { return client != nullptr ? static_cast<int> (juce::jack_get_sample_rate (client)) : 0; }
template <typename Fn>
void forEachClientChannel (const String& clientName, bool isInput, Fn&& fn)
{
auto index = 0;
for (JackPortIterator i (client, isInput); i.next();)
{
if (i.getClientName() != clientName)
continue;
fn (i.ports.get()[i.index], index);
index += 1;
}
}
String open (const BigInteger& inputChannels, const BigInteger& outputChannels,
double /* sampleRate */, int /* bufferSizeSamples */) override
@@ -263,38 +284,55 @@ public:
lastError.clear();
close();
xruns = 0;
xruns.store (0, std::memory_order_relaxed);
juce::jack_set_process_callback (client, processCallback, this);
juce::jack_set_port_connect_callback (client, portConnectCallback, this);
juce::jack_on_shutdown (client, shutdownCallback, this);
juce::jack_on_info_shutdown (client, infoShutdownCallback, this);
juce::jack_set_xrun_callback (client, xrunCallback, this);
juce::jack_activate (client);
deviceIsOpen = true;
if (! inputChannels.isZero())
{
for (JackPortIterator i (client, true); i.next();)
forEachClientChannel (inputName, false, [&] (const char* portName, int index)
{
if (inputChannels [i.index] && i.clientName == getName())
{
int error = juce::jack_connect (client, i.ports[i.index], juce::jack_port_name ((jack_port_t*) inputPorts[i.index]));
if (error != 0)
JUCE_JACK_LOG ("Cannot connect input port " + String (i.index) + " (" + i.name + "), error " + String (error));
}
}
if (! inputChannels[index])
return;
jassert (index < inputPorts.size());
const auto* source = portName;
const auto* inputPort = inputPorts[index];
jassert (juce::jack_port_flags (juce::jack_port_by_name (client, source)) & JackPortIsOutput);
jassert (juce::jack_port_flags (inputPort) & JackPortIsInput);
auto error = juce::jack_connect (client, source, juce::jack_port_name (inputPort));
if (error != 0)
JUCE_JACK_LOG ("Cannot connect input port " + String (index) + " (" + portName + "), error " + String (error));
});
}
if (! outputChannels.isZero())
{
for (JackPortIterator i (client, false); i.next();)
forEachClientChannel (outputName, true, [&] (const char* portName, int index)
{
if (outputChannels [i.index] && i.clientName == getName())
{
int error = juce::jack_connect (client, juce::jack_port_name ((jack_port_t*) outputPorts[i.index]), i.ports[i.index]);
if (error != 0)
JUCE_JACK_LOG ("Cannot connect output port " + String (i.index) + " (" + i.name + "), error " + String (error));
}
}
if (! outputChannels[index])
return;
jassert (index < outputPorts.size());
const auto* outputPort = outputPorts[index];
const auto* destination = portName;
jassert (juce::jack_port_flags (outputPort) & JackPortIsOutput);
jassert (juce::jack_port_flags (juce::jack_port_by_name (client, destination)) & JackPortIsInput);
auto error = juce::jack_connect (client, juce::jack_port_name (outputPort), destination);
if (error != 0)
JUCE_JACK_LOG ("Cannot connect output port " + String (index) + " (" + portName + "), error " + String (error));
});
}
updateActivePorts();
@@ -308,12 +346,15 @@ public:
if (client != nullptr)
{
juce::jack_deactivate (client);
const auto result = juce::jack_deactivate (client);
jassert (result == 0);
ignoreUnused (result);
juce::jack_set_xrun_callback (client, xrunCallback, nullptr);
juce::jack_set_process_callback (client, processCallback, nullptr);
juce::jack_set_port_connect_callback (client, portConnectCallback, nullptr);
juce::jack_on_shutdown (client, shutdownCallback, nullptr);
juce::jack_on_info_shutdown (client, infoShutdownCallback, nullptr);
}
deviceIsOpen = false;
@@ -347,7 +388,7 @@ public:
bool isPlaying() override { return callback != nullptr; }
int getCurrentBitDepth() override { return 32; }
String getLastError() override { return lastError; }
int getXRunCount() const noexcept override { return xruns; }
int getXRunCount() const noexcept override { return xruns.load (std::memory_order_relaxed); }
BigInteger getActiveOutputChannels() const override { return activeOutputChannels; }
BigInteger getActiveInputChannels() const override { return activeInputChannels; }
@@ -357,7 +398,7 @@ public:
int latency = 0;
for (int i = 0; i < outputPorts.size(); i++)
latency = jmax (latency, (int) juce::jack_port_get_total_latency (client, (jack_port_t*) outputPorts [i]));
latency = jmax (latency, (int) juce::jack_port_get_total_latency (client, outputPorts[i]));
return latency;
}
@@ -367,14 +408,36 @@ public:
int latency = 0;
for (int i = 0; i < inputPorts.size(); i++)
latency = jmax (latency, (int) juce::jack_port_get_total_latency (client, (jack_port_t*) inputPorts [i]));
latency = jmax (latency, (int) juce::jack_port_get_total_latency (client, inputPorts[i]));
return latency;
}
String inputId, outputId;
String inputName, outputName;
private:
//==============================================================================
class MainThreadDispatcher : private AsyncUpdater
{
public:
explicit MainThreadDispatcher (JackAudioIODevice& device) : ref (device) {}
~MainThreadDispatcher() override { cancelPendingUpdate(); }
void updateActivePorts()
{
if (MessageManager::getInstance()->isThisTheMessageThread())
handleAsyncUpdate();
else
triggerAsyncUpdate();
}
private:
void handleAsyncUpdate() override { ref.updateActivePorts(); }
JackAudioIODevice& ref;
};
//==============================================================================
void process (const int numSamples)
{
int numActiveInChans = 0, numActiveOutChans = 0;
@@ -382,17 +445,17 @@ private:
for (int i = 0; i < totalNumberOfInputChannels; ++i)
{
if (activeInputChannels[i])
if (jack_default_audio_sample_t* in
= (jack_default_audio_sample_t*) juce::jack_port_get_buffer ((jack_port_t*) inputPorts.getUnchecked(i), numSamples))
inChans [numActiveInChans++] = (float*) in;
if (auto* in = (jack_default_audio_sample_t*) juce::jack_port_get_buffer (inputPorts.getUnchecked (i),
static_cast<jack_nframes_t> (numSamples)))
inChans[numActiveInChans++] = (float*) in;
}
for (int i = 0; i < totalNumberOfOutputChannels; ++i)
{
if (activeOutputChannels[i])
if (jack_default_audio_sample_t* out
= (jack_default_audio_sample_t*) juce::jack_port_get_buffer ((jack_port_t*) outputPorts.getUnchecked(i), numSamples))
outChans [numActiveOutChans++] = (float*) out;
if (auto* out = (jack_default_audio_sample_t*) juce::jack_port_get_buffer (outputPorts.getUnchecked (i),
static_cast<jack_nframes_t> (numSamples)))
outChans[numActiveOutChans++] = (float*) out;
}
const ScopedLock sl (callbackLock);
@@ -406,14 +469,14 @@ private:
else
{
for (int i = 0; i < numActiveOutChans; ++i)
zeromem (outChans[i], sizeof (float) * numSamples);
zeromem (outChans[i], static_cast<size_t> (numSamples) * sizeof (float));
}
}
static int processCallback (jack_nframes_t nframes, void* callbackArgument)
{
if (callbackArgument != nullptr)
((JackAudioIODevice*) callbackArgument)->process (nframes);
((JackAudioIODevice*) callbackArgument)->process (static_cast<int> (nframes));
return 0;
}
@@ -431,11 +494,11 @@ private:
BigInteger newOutputChannels, newInputChannels;
for (int i = 0; i < outputPorts.size(); ++i)
if (juce::jack_port_connected ((jack_port_t*) outputPorts.getUnchecked(i)))
if (juce::jack_port_connected (outputPorts.getUnchecked (i)))
newOutputChannels.setBit (i);
for (int i = 0; i < inputPorts.size(); ++i)
if (juce::jack_port_connected ((jack_port_t*) inputPorts.getUnchecked(i)))
if (juce::jack_port_connected (inputPorts.getUnchecked (i)))
newInputChannels.setBit (i);
if (newOutputChannels != activeOutputChannels
@@ -451,14 +514,15 @@ private:
if (oldCallback != nullptr)
start (oldCallback);
sendDeviceChangedCallback();
if (notifyChannelsChanged != nullptr)
notifyChannelsChanged();
}
}
static void portConnectCallback (jack_port_id_t, jack_port_id_t, int, void* arg)
{
if (JackAudioIODevice* device = static_cast<JackAudioIODevice*> (arg))
device->updateActivePorts();
device->mainThreadDispatcher.updateActivePorts();
}
static void threadInitCallback (void* /* callbackArgument */)
@@ -477,81 +541,76 @@ private:
}
}
static void infoShutdownCallback (jack_status_t code, const char* reason, void* arg)
{
jassert (code == 0);
ignoreUnused (code);
JUCE_JACK_LOG ("Shutting down with message:");
JUCE_JACK_LOG (reason);
ignoreUnused (reason);
shutdownCallback (arg);
}
static void errorCallback (const char* msg)
{
JUCE_JACK_LOG ("JackAudioIODevice::errorCallback " + String (msg));
ignoreUnused (msg);
}
static void sendDeviceChangedCallback();
bool deviceIsOpen;
jack_client_t* client;
bool deviceIsOpen = false;
jack_client_t* client = nullptr;
String lastError;
AudioIODeviceCallback* callback;
AudioIODeviceCallback* callback = nullptr;
CriticalSection callbackLock;
HeapBlock<float*> inChans, outChans;
int totalNumberOfInputChannels;
int totalNumberOfOutputChannels;
Array<void*> inputPorts, outputPorts;
int totalNumberOfInputChannels = 0;
int totalNumberOfOutputChannels = 0;
Array<jack_port_t*> inputPorts, outputPorts;
BigInteger activeInputChannels, activeOutputChannels;
int xruns;
};
std::atomic<int> xruns { 0 };
std::function<void()> notifyChannelsChanged;
MainThreadDispatcher mainThreadDispatcher { *this };
};
//==============================================================================
class JackAudioIODeviceType;
class JackAudioIODeviceType : public AudioIODeviceType
{
public:
JackAudioIODeviceType()
: AudioIODeviceType ("JACK"),
hasScanned (false)
{
activeDeviceTypes.add (this);
}
~JackAudioIODeviceType()
{
activeDeviceTypes.removeFirstMatchingValue (this);
}
: AudioIODeviceType ("JACK")
{}
void scanForDevices()
{
hasScanned = true;
inputNames.clear();
inputIds.clear();
outputNames.clear();
outputIds.clear();
if (juce_libjackHandle == nullptr) juce_libjackHandle = dlopen ("libjack.so.0", RTLD_LAZY);
if (juce_libjackHandle == nullptr) juce_libjackHandle = dlopen ("libjack.so", RTLD_LAZY);
if (juce_libjackHandle == nullptr) return;
jack_status_t status;
jack_status_t status = {};
// open a dummy client
if (jack_client_t* const client = juce::jack_client_open ("JuceJackDummy", JackNoStartServer, &status))
if (auto* const client = juce::jack_client_open ("JuceJackDummy", JackNoStartServer, &status))
{
// scan for output devices
for (JackPortIterator i (client, false); i.next();)
{
if (i.clientName != (JUCE_JACK_CLIENT_NAME) && ! inputNames.contains (i.clientName))
{
inputNames.add (i.clientName);
inputIds.add (i.ports [i.index]);
}
}
if (i.getClientName() != (JUCE_JACK_CLIENT_NAME) && ! inputNames.contains (i.getClientName()))
inputNames.add (i.getClientName());
// scan for input devices
for (JackPortIterator i (client, true); i.next();)
{
if (i.clientName != (JUCE_JACK_CLIENT_NAME) && ! outputNames.contains (i.clientName))
{
outputNames.add (i.clientName);
outputIds.add (i.ports [i.index]);
}
}
if (i.getClientName() != (JUCE_JACK_CLIENT_NAME) && ! outputNames.contains (i.getClientName()))
outputNames.add (i.getClientName());
juce::jack_client_close (client);
}
@@ -580,8 +639,8 @@ public:
jassert (hasScanned); // need to call scanForDevices() before doing this
if (JackAudioIODevice* d = dynamic_cast<JackAudioIODevice*> (device))
return asInput ? inputIds.indexOf (d->inputId)
: outputIds.indexOf (d->outputId);
return asInput ? inputNames.indexOf (d->inputName)
: outputNames.indexOf (d->outputName);
return -1;
}
@@ -595,34 +654,17 @@ public:
const int outputIndex = outputNames.indexOf (outputDeviceName);
if (inputIndex >= 0 || outputIndex >= 0)
return new JackAudioIODevice (outputIndex >= 0 ? outputDeviceName
: inputDeviceName,
inputIds [inputIndex],
outputIds [outputIndex]);
return new JackAudioIODevice (inputDeviceName, outputDeviceName,
[this] { callDeviceChangeListeners(); });
return nullptr;
}
void portConnectionChange() { callDeviceChangeListeners(); }
private:
StringArray inputNames, outputNames, inputIds, outputIds;
bool hasScanned;
StringArray inputNames, outputNames;
bool hasScanned = false;
JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR (JackAudioIODeviceType)
};
void JackAudioIODevice::sendDeviceChangedCallback()
{
for (int i = activeDeviceTypes.size(); --i >= 0;)
if (JackAudioIODeviceType* d = activeDeviceTypes[i])
d->portConnectionChange();
}
//==============================================================================
AudioIODeviceType* AudioIODeviceType::createAudioIODeviceType_JACK()
{
return new JackAudioIODeviceType();
}
} // namespace juce

+ 32
- 14
libs/juce-current/source/modules/juce_audio_devices/native/juce_linux_Midi.cpp View File

@@ -25,10 +25,6 @@ namespace juce
#if JUCE_ALSA
//==============================================================================
namespace
{
//==============================================================================
class AlsaClient : public ReferenceCountedObject
{
@@ -453,9 +449,23 @@ static AlsaClient::Port* iterateMidiDevices (bool forInput,
return port;
}
} // namespace
struct AlsaPortPtr
{
explicit AlsaPortPtr (AlsaClient::Port* p)
: ptr (p) {}
~AlsaPortPtr() noexcept { AlsaClient::getInstance()->deletePort (ptr); }
AlsaClient::Port* ptr = nullptr;
};
//==============================================================================
class MidiInput::Pimpl : public AlsaPortPtr
{
public:
using AlsaPortPtr::AlsaPortPtr;
};
Array<MidiDeviceInfo> MidiInput::getAvailableDevices()
{
Array<MidiDeviceInfo> devices;
@@ -485,7 +495,7 @@ std::unique_ptr<MidiInput> MidiInput::openDevice (const String& deviceIdentifier
std::unique_ptr<MidiInput> midiInput (new MidiInput (port->portName, deviceIdentifier));
port->setupInput (midiInput.get(), callback);
midiInput->internal = port;
midiInput->internal = std::make_unique<Pimpl> (port);
return midiInput;
}
@@ -501,7 +511,7 @@ std::unique_ptr<MidiInput> MidiInput::createNewDevice (const String& deviceName,
std::unique_ptr<MidiInput> midiInput (new MidiInput (deviceName, getFormattedPortIdentifier (client->getId(), port->portId)));
port->setupInput (midiInput.get(), callback);
midiInput->internal = port;
midiInput->internal = std::make_unique<Pimpl> (port);
return midiInput;
}
@@ -536,20 +546,25 @@ MidiInput::MidiInput (const String& deviceName, const String& deviceIdentifier)
MidiInput::~MidiInput()
{
stop();
AlsaClient::getInstance()->deletePort (static_cast<AlsaClient::Port*> (internal));
}
void MidiInput::start()
{
static_cast<AlsaClient::Port*> (internal)->enableCallback (true);
internal->ptr->enableCallback (true);
}
void MidiInput::stop()
{
static_cast<AlsaClient::Port*> (internal)->enableCallback (false);
internal->ptr->enableCallback (false);
}
//==============================================================================
class MidiOutput::Pimpl : public AlsaPortPtr
{
public:
using AlsaPortPtr::AlsaPortPtr;
};
Array<MidiDeviceInfo> MidiOutput::getAvailableDevices()
{
Array<MidiDeviceInfo> devices;
@@ -577,7 +592,7 @@ std::unique_ptr<MidiOutput> MidiOutput::openDevice (const String& deviceIdentifi
std::unique_ptr<MidiOutput> midiOutput (new MidiOutput (port->portName, deviceIdentifier));
port->setupOutput();
midiOutput->internal = port;
midiOutput->internal = std::make_unique<Pimpl> (port);
return midiOutput;
}
@@ -593,7 +608,7 @@ std::unique_ptr<MidiOutput> MidiOutput::createNewDevice (const String& deviceNam
std::unique_ptr<MidiOutput> midiOutput (new MidiOutput (deviceName, getFormattedPortIdentifier (client->getId(), port->portId)));
port->setupOutput();
midiOutput->internal = port;
midiOutput->internal = std::make_unique<Pimpl> (port);
return midiOutput;
}
@@ -623,17 +638,18 @@ std::unique_ptr<MidiOutput> MidiOutput::openDevice (int index)
MidiOutput::~MidiOutput()
{
stopBackgroundThread();
AlsaClient::getInstance()->deletePort (static_cast<AlsaClient::Port*> (internal));
}
void MidiOutput::sendMessageNow (const MidiMessage& message)
{
static_cast<AlsaClient::Port*> (internal)->sendMessageNow (message);
internal->ptr->sendMessageNow (message);
}
//==============================================================================
#else
class MidiInput::Pimpl {};
// (These are just stub functions if ALSA is unavailable...)
MidiInput::MidiInput (const String& deviceName, const String& deviceID)
: deviceInfo (deviceName, deviceID)
@@ -651,6 +667,8 @@ StringArray MidiInput::getDevices()
int MidiInput::getDefaultDeviceIndex() { return 0;}
std::unique_ptr<MidiInput> MidiInput::openDevice (int, MidiInputCallback*) { return {}; }
class MidiOutput::Pimpl {};
MidiOutput::~MidiOutput() {}
void MidiOutput::sendMessageNow (const MidiMessage&) {}
Array<MidiDeviceInfo> MidiOutput::getAvailableDevices() { return {}; }


+ 0
- 6
libs/juce-current/source/modules/juce_audio_devices/native/juce_mac_CoreAudio.cpp View File

@@ -2234,12 +2234,6 @@ private:
};
//==============================================================================
AudioIODeviceType* AudioIODeviceType::createAudioIODeviceType_CoreAudio()
{
return new CoreAudioClasses::CoreAudioIODeviceType();
}
#undef JUCE_COREAUDIOLOG
} // namespace juce

+ 26
- 17
libs/juce-current/source/modules/juce_audio_devices/native/juce_mac_CoreMidi.cpp View File

@@ -393,6 +393,12 @@ namespace CoreMidiHelpers
}
}
class MidiInput::Pimpl : public CoreMidiHelpers::MidiPortAndCallback
{
public:
using MidiPortAndCallback::MidiPortAndCallback;
};
//==============================================================================
Array<MidiDeviceInfo> MidiInput::getAvailableDevices()
{
@@ -424,7 +430,7 @@ std::unique_ptr<MidiInput> MidiInput::openDevice (const String& deviceIdentifier
if (CHECK_ERROR (MIDIObjectGetStringProperty (endpoint, kMIDIPropertyName, &cfName.cfString)))
{
MIDIPortRef port;
auto mpc = std::make_unique<MidiPortAndCallback> (*callback);
auto mpc = std::make_unique<Pimpl> (*callback);