New upstream version 5.4.5~ds0
authorIOhannes m zmölnig (Debian/GNU) <umlaeute@debian.org>
Tue, 22 Oct 2019 09:44:38 +0000 (11:44 +0200)
committerIOhannes m zmölnig (Debian/GNU) <umlaeute@debian.org>
Tue, 22 Oct 2019 09:44:38 +0000 (11:44 +0200)
221 files changed:
.github/ISSUE_TEMPLATE.txt [deleted file]
.gitlab-ci.yml [deleted file]
BREAKING-CHANGES.txt
ChangeList.txt
doxygen/process_source_files.py
examples/DSP/OscillatorDemo.h
examples/DemoRunner/Builds/Android/app/CMakeLists.txt
examples/DemoRunner/Builds/Android/app/src/main/AndroidManifest.xml
examples/DemoRunner/Builds/LinuxMakefile/Makefile
examples/DemoRunner/Builds/MacOSX/DemoRunner.entitlements [new file with mode: 0644]
examples/DemoRunner/Builds/MacOSX/DemoRunner.xcodeproj/project.pbxproj
examples/DemoRunner/Builds/MacOSX/Info-App.plist
examples/DemoRunner/Builds/VisualStudio2015/DemoRunner_App.vcxproj
examples/DemoRunner/Builds/VisualStudio2015/DemoRunner_App.vcxproj.filters
examples/DemoRunner/Builds/VisualStudio2015/resources.rc
examples/DemoRunner/Builds/VisualStudio2017/DemoRunner_App.vcxproj
examples/DemoRunner/Builds/VisualStudio2017/DemoRunner_App.vcxproj.filters
examples/DemoRunner/Builds/VisualStudio2017/resources.rc
examples/DemoRunner/Builds/VisualStudio2019/DemoRunner_App.vcxproj
examples/DemoRunner/Builds/VisualStudio2019/DemoRunner_App.vcxproj.filters
examples/DemoRunner/Builds/VisualStudio2019/resources.rc
examples/DemoRunner/Builds/iOS/DemoRunner.xcodeproj/project.pbxproj
examples/DemoRunner/Builds/iOS/Info-App.plist
examples/DemoRunner/DemoRunner.jucer
examples/DemoRunner/JuceLibraryCode/AppConfig.h
examples/DemoRunner/JuceLibraryCode/JuceHeader.h
examples/DemoRunner/Source/Main.cpp
examples/DemoRunner/Source/UI/DemoContentComponent.cpp
examples/Plugins/DSPModulePluginDemo.h
extras/AudioPerformanceTest/AudioPerformanceTest.jucer
extras/AudioPerformanceTest/Builds/MacOSX/AudioPerformanceTest.entitlements [new file with mode: 0644]
extras/AudioPerformanceTest/Builds/MacOSX/AudioPerformanceTest.xcodeproj/project.pbxproj
extras/AudioPerformanceTest/Builds/iOS/AudioPerformanceTest.entitlements [new file with mode: 0644]
extras/AudioPerformanceTest/Builds/iOS/AudioPerformanceTest.xcodeproj/project.pbxproj
extras/AudioPerformanceTest/JuceLibraryCode/AppConfig.h
extras/AudioPerformanceTest/JuceLibraryCode/JuceHeader.h
extras/AudioPluginHost/AudioPluginHost.jucer
extras/AudioPluginHost/Builds/MacOSX/AudioPluginHost.entitlements [new file with mode: 0644]
extras/AudioPluginHost/Builds/MacOSX/AudioPluginHost.xcodeproj/project.pbxproj
extras/AudioPluginHost/Builds/iOS/AudioPluginHost.entitlements [new file with mode: 0644]
extras/AudioPluginHost/Builds/iOS/AudioPluginHost.xcodeproj/project.pbxproj
extras/AudioPluginHost/JuceLibraryCode/AppConfig.h
extras/AudioPluginHost/JuceLibraryCode/JuceHeader.h
extras/AudioPluginHost/Source/HostStartup.cpp
extras/AudioPluginHost/Source/Plugins/PluginGraph.cpp
extras/AudioPluginHost/Source/UI/GraphEditorPanel.cpp
extras/BinaryBuilder/BinaryBuilder.jucer
extras/BinaryBuilder/Builds/MacOSX/BinaryBuilder.entitlements [new file with mode: 0644]
extras/BinaryBuilder/Builds/MacOSX/BinaryBuilder.xcodeproj/project.pbxproj
extras/BinaryBuilder/JuceLibraryCode/AppConfig.h
extras/BinaryBuilder/JuceLibraryCode/JuceHeader.h
extras/NetworkGraphicsDemo/Builds/MacOSX/NetworkGraphicsDemo.entitlements [new file with mode: 0644]
extras/NetworkGraphicsDemo/Builds/MacOSX/NetworkGraphicsDemo.xcodeproj/project.pbxproj
extras/NetworkGraphicsDemo/Builds/iOS/NetworkGraphicsDemo.entitlements [new file with mode: 0644]
extras/NetworkGraphicsDemo/Builds/iOS/NetworkGraphicsDemo.xcodeproj/project.pbxproj
extras/NetworkGraphicsDemo/JuceLibraryCode/AppConfig.h
extras/NetworkGraphicsDemo/JuceLibraryCode/JuceHeader.h
extras/NetworkGraphicsDemo/NetworkGraphicsDemo.jucer
extras/Projucer/Builds/LinuxMakefile/Makefile
extras/Projucer/Builds/MacOSX/Info-App.plist
extras/Projucer/Builds/MacOSX/Projucer.entitlements [new file with mode: 0644]
extras/Projucer/Builds/MacOSX/Projucer.xcodeproj/project.pbxproj
extras/Projucer/Builds/VisualStudio2015/Projucer_App.vcxproj
extras/Projucer/Builds/VisualStudio2015/resources.rc
extras/Projucer/Builds/VisualStudio2017/Projucer_App.vcxproj
extras/Projucer/Builds/VisualStudio2017/resources.rc
extras/Projucer/Builds/VisualStudio2019/Projucer_App.vcxproj
extras/Projucer/Builds/VisualStudio2019/resources.rc
extras/Projucer/JuceLibraryCode/AppConfig.h
extras/Projucer/JuceLibraryCode/JuceHeader.h
extras/Projucer/Projucer.jucer
extras/Projucer/Source/Application/Windows/jucer_AboutWindowComponent.h
extras/Projucer/Source/Application/jucer_Application.cpp
extras/Projucer/Source/ComponentEditor/PaintElements/jucer_PaintElementImage.cpp
extras/Projucer/Source/Project/UI/Sidebar/jucer_ExporterTreeItems.h
extras/Projucer/Source/Project/UI/Sidebar/jucer_LiveBuildTab.h
extras/Projucer/Source/Project/UI/Sidebar/jucer_ProjectTab.h
extras/Projucer/Source/Project/UI/jucer_HeaderComponent.cpp
extras/Projucer/Source/Project/UI/jucer_HeaderComponent.h
extras/Projucer/Source/Project/UI/jucer_ModulesInformationComponent.h
extras/Projucer/Source/Project/UI/jucer_ProjectContentComponent.cpp
extras/Projucer/Source/Project/jucer_Project.cpp
extras/Projucer/Source/ProjectSaving/jucer_ProjectExport_MSVC.h
extras/Projucer/Source/ProjectSaving/jucer_ProjectExport_Xcode.h
extras/Projucer/Source/ProjectSaving/jucer_ProjectSaver.h
extras/Projucer/Source/Utility/Helpers/jucer_PresetIDs.h
extras/UnitTestRunner/Builds/MacOSX/UnitTestRunner.entitlements [new file with mode: 0644]
extras/UnitTestRunner/Builds/MacOSX/UnitTestRunner.xcodeproj/project.pbxproj
extras/UnitTestRunner/Builds/VisualStudio2017/UnitTestRunner_ConsoleApp.vcxproj
extras/UnitTestRunner/Builds/VisualStudio2017/UnitTestRunner_ConsoleApp.vcxproj.filters
extras/UnitTestRunner/Builds/VisualStudio2019/UnitTestRunner_ConsoleApp.vcxproj
extras/UnitTestRunner/Builds/VisualStudio2019/UnitTestRunner_ConsoleApp.vcxproj.filters
extras/UnitTestRunner/JuceLibraryCode/AppConfig.h
extras/UnitTestRunner/JuceLibraryCode/JuceHeader.h
extras/UnitTestRunner/UnitTestRunner.jucer
extras/WindowsDLL/JuceLibraryCode/AppConfig.h
extras/WindowsDLL/JuceLibraryCode/JuceHeader.h
extras/WindowsDLL/WindowsDLL.jucer
modules/JUCE Module Format.txt
modules/juce_analytics/juce_analytics.h
modules/juce_audio_basics/juce_audio_basics.h
modules/juce_audio_basics/utilities/juce_CatmullRomInterpolator.h
modules/juce_audio_basics/utilities/juce_LagrangeInterpolator.h
modules/juce_audio_devices/audio_io/juce_AudioDeviceManager.cpp
modules/juce_audio_devices/juce_audio_devices.cpp
modules/juce_audio_devices/juce_audio_devices.h
modules/juce_audio_devices/native/juce_android_Oboe.cpp
modules/juce_audio_devices/native/juce_android_OpenSL.cpp
modules/juce_audio_devices/native/juce_linux_Bela.cpp
modules/juce_audio_devices/native/juce_mac_CoreMidi.cpp
modules/juce_audio_formats/codecs/juce_CoreAudioFormat.cpp
modules/juce_audio_formats/juce_audio_formats.h
modules/juce_audio_plugin_client/AAX/juce_AAX_Wrapper.cpp
modules/juce_audio_plugin_client/Standalone/juce_StandaloneFilterWindow.h
modules/juce_audio_plugin_client/VST/juce_VST_Wrapper.cpp
modules/juce_audio_plugin_client/VST3/juce_VST3_Wrapper.cpp
modules/juce_audio_plugin_client/juce_audio_plugin_client.h
modules/juce_audio_processors/format_types/juce_AudioUnitPluginFormat.mm
modules/juce_audio_processors/format_types/juce_VST3PluginFormat.cpp
modules/juce_audio_processors/format_types/juce_VSTPluginFormat.cpp
modules/juce_audio_processors/juce_audio_processors.h
modules/juce_audio_processors/processors/juce_AudioProcessor.h
modules/juce_audio_processors/processors/juce_AudioProcessorGraph.h
modules/juce_audio_processors/utilities/juce_AudioProcessorParameterWithID.h
modules/juce_audio_processors/utilities/juce_AudioProcessorValueTreeState.cpp
modules/juce_audio_processors/utilities/juce_AudioProcessorValueTreeState.h
modules/juce_audio_utils/gui/juce_AudioAppComponent.h
modules/juce_audio_utils/juce_audio_utils.h
modules/juce_audio_utils/native/juce_ios_BluetoothMidiDevicePairingDialogue.mm
modules/juce_blocks_basics/blocks/juce_Block.h
modules/juce_blocks_basics/blocks/juce_BlockConfigManager.h
modules/juce_blocks_basics/blocks/juce_TouchList.h
modules/juce_blocks_basics/juce_blocks_basics.h
modules/juce_blocks_basics/littlefoot/juce_LittleFootRemoteHeap.h
modules/juce_blocks_basics/protocol/juce_BlocksProtocolDefinitions.h
modules/juce_blocks_basics/topology/internal/juce_BlockImplementation.cpp
modules/juce_blocks_basics/topology/internal/juce_BlockSerialReader.cpp [new file with mode: 0644]
modules/juce_blocks_basics/topology/internal/juce_ConnectedDeviceGroup.cpp
modules/juce_blocks_basics/topology/internal/juce_Detector.cpp
modules/juce_blocks_basics/topology/internal/juce_DetectorHolder.cpp
modules/juce_blocks_basics/topology/internal/juce_MidiDeviceConnection.cpp
modules/juce_blocks_basics/topology/juce_PhysicalTopologySource.cpp
modules/juce_blocks_basics/topology/juce_PhysicalTopologySource.h
modules/juce_blocks_basics/topology/juce_RuleBasedTopologySource.h
modules/juce_blocks_basics/topology/juce_TopologySource.h
modules/juce_box2d/juce_box2d.h
modules/juce_core/containers/juce_NamedValueSet.h
modules/juce_core/containers/juce_OwnedArray.h
modules/juce_core/files/juce_File.cpp
modules/juce_core/juce_core.cpp
modules/juce_core/juce_core.h
modules/juce_core/memory/juce_OptionalScopedPointer.h
modules/juce_core/misc/juce_WindowsRegistry.h
modules/juce_core/native/juce_BasicNativeHeaders.h
modules/juce_core/native/juce_android_JNIHelpers.cpp
modules/juce_core/native/juce_android_JNIHelpers.h
modules/juce_core/native/juce_linux_Network.cpp
modules/juce_core/native/juce_posix_NamedPipe.cpp
modules/juce_core/native/juce_posix_SharedCode.h
modules/juce_core/native/juce_win32_Registry.cpp
modules/juce_core/network/juce_Socket.cpp
modules/juce_core/network/juce_URL.cpp
modules/juce_core/network/juce_URL.h
modules/juce_core/system/juce_CompilerSupport.h
modules/juce_core/system/juce_StandardHeader.h
modules/juce_core/time/juce_PerformanceCounter.cpp
modules/juce_cryptography/juce_cryptography.h
modules/juce_data_structures/juce_data_structures.h
modules/juce_dsp/containers/juce_AudioBlock.h
modules/juce_dsp/containers/juce_AudioBlock_test.cpp [new file with mode: 0644]
modules/juce_dsp/frequency/juce_Convolution.cpp
modules/juce_dsp/juce_dsp.cpp
modules/juce_dsp/juce_dsp.h
modules/juce_dsp/processors/juce_Bias.h
modules/juce_dsp/processors/juce_Gain.h
modules/juce_dsp/processors/juce_LadderFilter.h
modules/juce_dsp/processors/juce_Oversampling.cpp
modules/juce_dsp/processors/juce_Oversampling.h
modules/juce_dsp/processors/juce_Reverb.h
modules/juce_dsp/processors/juce_WaveShaper.h
modules/juce_events/juce_events.h
modules/juce_events/messages/juce_ApplicationBase.h
modules/juce_events/messages/juce_MessageManager.cpp
modules/juce_events/messages/juce_MessageManager.h
modules/juce_events/native/juce_linux_EventLoop.h
modules/juce_events/native/juce_linux_Messaging.cpp
modules/juce_graphics/contexts/juce_GraphicsContext.h
modules/juce_graphics/fonts/juce_GlyphArrangement.h
modules/juce_graphics/fonts/juce_TextLayout.cpp
modules/juce_graphics/geometry/juce_RectangleList.h
modules/juce_graphics/images/juce_Image.h
modules/juce_graphics/juce_graphics.h
modules/juce_graphics/native/juce_mac_CoreGraphicsContext.mm
modules/juce_graphics/native/juce_mac_Fonts.mm
modules/juce_gui_basics/juce_gui_basics.h
modules/juce_gui_basics/layout/juce_Grid.cpp
modules/juce_gui_basics/layout/juce_Grid.h
modules/juce_gui_basics/layout/juce_GridItem.cpp
modules/juce_gui_basics/layout/juce_GridItem.h
modules/juce_gui_basics/layout/juce_SidePanel.cpp
modules/juce_gui_basics/layout/juce_SidePanel.h
modules/juce_gui_basics/menus/juce_PopupMenu.cpp
modules/juce_gui_basics/menus/juce_PopupMenu.h
modules/juce_gui_basics/native/juce_android_ContentSharer.cpp
modules/juce_gui_basics/native/juce_android_Windowing.cpp
modules/juce_gui_basics/native/juce_linux_X11_Windowing.cpp
modules/juce_gui_extra/code_editor/juce_CodeEditorComponent.cpp
modules/juce_gui_extra/juce_gui_extra.h
modules/juce_gui_extra/misc/juce_PushNotifications.h
modules/juce_gui_extra/native/juce_android_PushNotifications.cpp
modules/juce_gui_extra/native/juce_linux_X11_WebBrowserComponent.cpp
modules/juce_opengl/juce_opengl.h
modules/juce_opengl/opengl/juce_OpenGLContext.cpp
modules/juce_opengl/opengl/juce_OpenGLImage.cpp
modules/juce_osc/juce_osc.h
modules/juce_product_unlocking/juce_product_unlocking.h
modules/juce_video/juce_video.h
modules/juce_video/native/juce_android_Video.h
modules/juce_video/native/juce_win32_Video.h
modules/juce_video/playback/juce_VideoComponent.cpp
modules/juce_video/playback/juce_VideoComponent.h

diff --git a/.github/ISSUE_TEMPLATE.txt b/.github/ISSUE_TEMPLATE.txt
deleted file mode 100644 (file)
index 2404c33..0000000
+++ /dev/null
@@ -1,17 +0,0 @@
-Please include:
-
-  1) detailed steps on how to reproduce the bug, preferably with already
-     existing JUCE code such as the demo plugin or the demo code
-  2) the expected behaviour
-  3) the operating system
-  4) the architecture (32-bit or 64-bit)
-  5) a stack trace - if the bug causes a crash
-  6) the plugin format (VST2, VST3, AU, AAX, RTAS) - if applicable
-  7) which DAW you observed the bug in - if applicable
-
-Make sure you have pulled the latest commits from the `develop` branch of the
-JUCE repo and have re-compiled the Projucer before you submit your bug. Often
-we have already fixed the issue but it hasn't yet been released on the `master`
-branch. If it's a major bug, which must be hot-fixed immediately, then we will
-also accept bug reports for tagged release versions.
-
diff --git a/.gitlab-ci.yml b/.gitlab-ci.yml
deleted file mode 100644 (file)
index e91a6b1..0000000
+++ /dev/null
@@ -1,4 +0,0 @@
-include:
-  - project: 'juce-repos/JUCE-utils'
-    file: '/CI/gitlab-ci.yml'
-
index ef40f8a0eda2c991ccfc02ac4b768db29f6622bc..61d162fcc17cce9748ce6cbc61515e84f3a8afcf 100644 (file)
@@ -1,6 +1,58 @@
 JUCE breaking changes
 =====================
 
+Version 5.4.5
+=============
+
+Change
+------
+The JUCEApplicationBase::backButtonPressed() method now returns a bool to
+indicate whether the back event was handled or not.
+
+Possible Issues
+---------------
+Applications which override this method will fail to compile.
+
+Workaround
+----------
+You will need to update your code to return a bool indicating whether the back
+event was handled or not.
+
+Rationale
+---------
+The back button behaviour on Android was previously broken as it would not do
+anything. The new code will correctly call finish() on the Activity when the
+back button is pressed but this method now allows the user to override this to
+implement their own custom navigation behaviour by returning true to indicate
+that it has been handled.
+
+
+Change
+------
+The AudioBlock class has been refactored and some of the method names have
+changed. Additionally the `const` behaviour now mirrors that of `std::span`,
+with the `const`-ness of the contained data decoupled from the `const`-ness of
+the container.
+
+Possible Issues
+---------------
+Code using the old method names or violating `const`-correctness will fail to
+compile.
+
+Workaround
+----------
+You will need to update your code to use the new method names and select an
+appropriate `const`-ness for the AudioBlock and the data it references.
+
+Rationale
+---------
+The names of some of the methods in the AudioBlock class were ambiguous,
+particularly when chaining methods involving references to other blocks. The
+interaction between the `const`-ness of the AudioBlock and the `const`-ness of
+the referenced data was also ambiguous and has now been standardised to the
+same behaviour as other non-owning data views like `std::span`.
+
+
 Version 5.4.4
 =============
 
index a1a755f561fec537aacd96b43a7791e49b300db6..bf40c1c39ec9b1d15868bb4300507694fa4b9183 100644 (file)
@@ -3,13 +3,25 @@
 This file just lists the more notable headline features. For more detailed info\r
 about minor changes and bugfixes, please see the git log!\r
 \r
+Version 5.4.5\r
+  - Improved message queue performance on Linux\r
+  - Added missing lifecycle callbacks on Android Q\r
+  - Refactored the AudioBlock class\r
+  - Fixed APVTS parameter update recursion\r
+  - Updated Bela code to support latest release\r
+  - Fixed issues drawing italicised text on macOS\r
+  - Fixed broken back button behaviour on Android\r
+  - Added Bluetooth permissions settings needed for iOS 13.0+ to the Projucer\r
+  - Replaced select() calls with poll()\r
+  - Various bug-fixes, improvements and documentation updates\r
+\r
 Version 5.4.4\r
   - Improvements to floating point number printing\r
   - Faster plug-in parameter indexing\r
   - Added support for persisting attachements to MIDI devices\r
   - Refactored Linux event loop handling\r
   - Multiple C++ modernisation improvements to the API\r
-  - Added support for macOS 10.55 and iOS 13\r
+  - Added support for macOS 10.15 and iOS 13\r
   - Added support for Visual Studio 2019\r
   - Removed support for Visual Studio 2013\r
 \r
index 376c97db2ba3dfa705ddb2d5b5c201344e769aa3..d9862ff708e69b381f0d5a2ef7a61305ec1ea74e 100644 (file)
@@ -75,8 +75,10 @@ if __name__ == "__main__":
                              "subdirectories")
     args = parser.parse_args()
 
-    try: 
+    try:
         shutil.rmtree(args.dest_dir)
+    except OSError:
+        pass
     except FileNotFoundError:
         pass
 
index 6eadf8b4c7e5c6ad5cafdd3a8940bd208dd3d6f3..a564337e1aa5cd6c83f493289d5d0e493a2ea125 100644 (file)
@@ -73,11 +73,11 @@ struct OscillatorDemoDSP
 \r
     void process (const ProcessContextReplacing<float>& context)\r
     {\r
-        tempBuffer.copy (context.getInputBlock());\r
-        tempBuffer.multiply (static_cast<float> (fileMix));\r
+        tempBuffer.copyFrom (context.getInputBlock());\r
+        tempBuffer.multiplyBy (static_cast<float> (fileMix));\r
 \r
         oscillators[currentOscillatorIdx].process (context);\r
-        context.getOutputBlock().multiply (static_cast<float> (1.0 - fileMix));\r
+        context.getOutputBlock().multiplyBy (static_cast<float> (1.0 - fileMix));\r
 \r
         context.getOutputBlock().add (tempBuffer);\r
 \r
index caa7c4a00dc33e6e6733453459d9616e951d4585..a6fa1d43bd62cb984e8ca8ff6025993553a131ab 100644 (file)
@@ -8,7 +8,7 @@ SET(BINARY_NAME "juce_jni")
 add_library("cpufeatures" STATIC "${ANDROID_NDK}/sources/android/cpufeatures/cpu-features.c")
 set_source_files_properties("${ANDROID_NDK}/sources/android/cpufeatures/cpu-features.c" PROPERTIES COMPILE_FLAGS "-Wno-sign-conversion -Wno-gnu-statement-expression")
 
-add_definitions("-DJUCE_ANDROID=1" "-DJUCE_ANDROID_API_VERSION=23" "-DJUCE_PUSH_NOTIFICATIONS=1" "-DJUCE_PUSH_NOTIFICATIONS_ACTIVITY=\"com/roli/juce/JuceActivity\"" "-DJUCE_ANDROID_GL_ES_VERSION_3_0=1" "-DJUCE_DEMO_RUNNER=1" "-DJUCE_UNIT_TESTS=1" "-DJUCER_ANDROIDSTUDIO_7F0E4A25=1" "-DJUCE_APP_VERSION=5.4.4" "-DJUCE_APP_VERSION_HEX=0x50404")
+add_definitions("-DJUCE_ANDROID=1" "-DJUCE_ANDROID_API_VERSION=23" "-DJUCE_PUSH_NOTIFICATIONS=1" "-DJUCE_PUSH_NOTIFICATIONS_ACTIVITY=\"com/roli/juce/JuceActivity\"" "-DJUCE_ANDROID_GL_ES_VERSION_3_0=1" "-DJUCE_DEMO_RUNNER=1" "-DJUCE_UNIT_TESTS=1" "-DJUCER_ANDROIDSTUDIO_7F0E4A25=1" "-DJUCE_APP_VERSION=5.4.5" "-DJUCE_APP_VERSION_HEX=0x50405")
 
 include_directories( AFTER
     "../../../JuceLibraryCode"
@@ -527,6 +527,7 @@ add_library( ${BINARY_NAME}
     "../../../../../modules/juce_blocks_basics/protocol/Protocol Format.txt"
     "../../../../../modules/juce_blocks_basics/topology/internal/juce_BandwidthStatsLogger.cpp"
     "../../../../../modules/juce_blocks_basics/topology/internal/juce_BlockImplementation.cpp"
+    "../../../../../modules/juce_blocks_basics/topology/internal/juce_BlockSerialReader.cpp"
     "../../../../../modules/juce_blocks_basics/topology/internal/juce_ConnectedDeviceGroup.cpp"
     "../../../../../modules/juce_blocks_basics/topology/internal/juce_DepreciatedVersionReader.cpp"
     "../../../../../modules/juce_blocks_basics/topology/internal/juce_Detector.cpp"
@@ -926,6 +927,7 @@ add_library( ${BINARY_NAME}
     "../../../../../modules/juce_data_structures/juce_data_structures.mm"
     "../../../../../modules/juce_data_structures/juce_data_structures.h"
     "../../../../../modules/juce_dsp/containers/juce_AudioBlock.h"
+    "../../../../../modules/juce_dsp/containers/juce_AudioBlock_test.cpp"
     "../../../../../modules/juce_dsp/containers/juce_SIMDRegister.h"
     "../../../../../modules/juce_dsp/containers/juce_SIMDRegister_Impl.h"
     "../../../../../modules/juce_dsp/containers/juce_SIMDRegister_test.cpp"
@@ -2130,6 +2132,7 @@ set_source_files_properties("../../../../../modules/juce_blocks_basics/protocol/
 set_source_files_properties("../../../../../modules/juce_blocks_basics/protocol/Protocol Format.txt" PROPERTIES HEADER_FILE_ONLY TRUE)
 set_source_files_properties("../../../../../modules/juce_blocks_basics/topology/internal/juce_BandwidthStatsLogger.cpp" PROPERTIES HEADER_FILE_ONLY TRUE)
 set_source_files_properties("../../../../../modules/juce_blocks_basics/topology/internal/juce_BlockImplementation.cpp" PROPERTIES HEADER_FILE_ONLY TRUE)
+set_source_files_properties("../../../../../modules/juce_blocks_basics/topology/internal/juce_BlockSerialReader.cpp" PROPERTIES HEADER_FILE_ONLY TRUE)
 set_source_files_properties("../../../../../modules/juce_blocks_basics/topology/internal/juce_ConnectedDeviceGroup.cpp" PROPERTIES HEADER_FILE_ONLY TRUE)
 set_source_files_properties("../../../../../modules/juce_blocks_basics/topology/internal/juce_DepreciatedVersionReader.cpp" PROPERTIES HEADER_FILE_ONLY TRUE)
 set_source_files_properties("../../../../../modules/juce_blocks_basics/topology/internal/juce_Detector.cpp" PROPERTIES HEADER_FILE_ONLY TRUE)
@@ -2529,6 +2532,7 @@ set_source_files_properties("../../../../../modules/juce_data_structures/juce_da
 set_source_files_properties("../../../../../modules/juce_data_structures/juce_data_structures.mm" PROPERTIES HEADER_FILE_ONLY TRUE)
 set_source_files_properties("../../../../../modules/juce_data_structures/juce_data_structures.h" PROPERTIES HEADER_FILE_ONLY TRUE)
 set_source_files_properties("../../../../../modules/juce_dsp/containers/juce_AudioBlock.h" PROPERTIES HEADER_FILE_ONLY TRUE)
+set_source_files_properties("../../../../../modules/juce_dsp/containers/juce_AudioBlock_test.cpp" PROPERTIES HEADER_FILE_ONLY TRUE)
 set_source_files_properties("../../../../../modules/juce_dsp/containers/juce_SIMDRegister.h" PROPERTIES HEADER_FILE_ONLY TRUE)
 set_source_files_properties("../../../../../modules/juce_dsp/containers/juce_SIMDRegister_Impl.h" PROPERTIES HEADER_FILE_ONLY TRUE)
 set_source_files_properties("../../../../../modules/juce_dsp/containers/juce_SIMDRegister_test.cpp" PROPERTIES HEADER_FILE_ONLY TRUE)
index 5ea204f5d877e5d2c7daf629c8978bbead6e988a..80922f549eddf28920fff6ed24591a5d7c2831be 100644 (file)
@@ -1,6 +1,6 @@
 <?xml version="1.0" encoding="utf-8"?>
 
-<manifest xmlns:android="http://schemas.android.com/apk/res/android" android:versionCode="1" android:versionName="5.4.4"
+<manifest xmlns:android="http://schemas.android.com/apk/res/android" android:versionCode="1" android:versionName="5.4.5"
           package="com.juce.demorunner">
   <supports-screens android:smallScreens="true" android:normalScreens="true" android:largeScreens="true" android:anyDensity="true"/>
   <uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>
index ae6f7824a920bda394b2ac422272f6ee9ab20300..a63eabe4e271695c876eea748a0fc00096a95a7b 100644 (file)
@@ -35,7 +35,7 @@ ifeq ($(CONFIG),Debug)
     TARGET_ARCH := -march=native
   endif
 
-  JUCE_CPPFLAGS := $(DEPFLAGS) -DLINUX=1 -DDEBUG=1 -D_DEBUG=1 -DJUCE_DEMO_RUNNER=1 -DJUCE_UNIT_TESTS=1 -DJUCER_LINUX_MAKE_6D53C8B4=1 -DJUCE_APP_VERSION=5.4.4 -DJUCE_APP_VERSION_HEX=0x50404 $(shell pkg-config --cflags alsa x11 xinerama xext freetype2 webkit2gtk-4.0 gtk+-x11-3.0 libcurl) -pthread -I../../JuceLibraryCode -I../../../../modules $(CPPFLAGS)
+  JUCE_CPPFLAGS := $(DEPFLAGS) -DLINUX=1 -DDEBUG=1 -D_DEBUG=1 -DJUCE_DEMO_RUNNER=1 -DJUCE_UNIT_TESTS=1 -DJUCER_LINUX_MAKE_6D53C8B4=1 -DJUCE_APP_VERSION=5.4.5 -DJUCE_APP_VERSION_HEX=0x50405 $(shell pkg-config --cflags alsa x11 xinerama xext freetype2 webkit2gtk-4.0 gtk+-x11-3.0 libcurl) -pthread -I../../JuceLibraryCode -I../../../../modules $(CPPFLAGS)
   JUCE_CPPFLAGS_APP := -DJucePlugin_Build_VST=0 -DJucePlugin_Build_VST3=0 -DJucePlugin_Build_AU=0 -DJucePlugin_Build_AUv3=0 -DJucePlugin_Build_RTAS=0 -DJucePlugin_Build_AAX=0 -DJucePlugin_Build_Standalone=0 -DJucePlugin_Build_Unity=0
   JUCE_TARGET_APP := DemoRunner
 
@@ -56,7 +56,7 @@ ifeq ($(CONFIG),Release)
     TARGET_ARCH := -march=native
   endif
 
-  JUCE_CPPFLAGS := $(DEPFLAGS) -DLINUX=1 -DNDEBUG=1 -DJUCE_DEMO_RUNNER=1 -DJUCE_UNIT_TESTS=1 -DJUCER_LINUX_MAKE_6D53C8B4=1 -DJUCE_APP_VERSION=5.4.4 -DJUCE_APP_VERSION_HEX=0x50404 $(shell pkg-config --cflags alsa x11 xinerama xext freetype2 webkit2gtk-4.0 gtk+-x11-3.0 libcurl) -pthread -I../../JuceLibraryCode -I../../../../modules $(CPPFLAGS)
+  JUCE_CPPFLAGS := $(DEPFLAGS) -DLINUX=1 -DNDEBUG=1 -DJUCE_DEMO_RUNNER=1 -DJUCE_UNIT_TESTS=1 -DJUCER_LINUX_MAKE_6D53C8B4=1 -DJUCE_APP_VERSION=5.4.5 -DJUCE_APP_VERSION_HEX=0x50405 $(shell pkg-config --cflags alsa x11 xinerama xext freetype2 webkit2gtk-4.0 gtk+-x11-3.0 libcurl) -pthread -I../../JuceLibraryCode -I../../../../modules $(CPPFLAGS)
   JUCE_CPPFLAGS_APP := -DJucePlugin_Build_VST=0 -DJucePlugin_Build_VST3=0 -DJucePlugin_Build_AU=0 -DJucePlugin_Build_AUv3=0 -DJucePlugin_Build_RTAS=0 -DJucePlugin_Build_AAX=0 -DJucePlugin_Build_Standalone=0 -DJucePlugin_Build_Unity=0
   JUCE_TARGET_APP := DemoRunner
 
diff --git a/examples/DemoRunner/Builds/MacOSX/DemoRunner.entitlements b/examples/DemoRunner/Builds/MacOSX/DemoRunner.entitlements
new file mode 100644 (file)
index 0000000..6631ffa
--- /dev/null
@@ -0,0 +1,6 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
+<plist version="1.0">
+<dict>
+</dict>
+</plist>
index df5bf5cec99868382aec48159becb2cc26f45e0f..0aee90e6137106e01165ba1a53cc35f9e7607f28 100644 (file)
                        path = "../../../../modules/juce_audio_utils";
                        sourceTree = "SOURCE_ROOT";
                };
+               0CCFDC1D1C7B8A12BF4822F1 = {
+                       isa = PBXFileReference;
+                       lastKnownFileType = text.plist.xml;
+                       name = DemoRunner.entitlements;
+                       path = DemoRunner.entitlements;
+                       sourceTree = "SOURCE_ROOT";
+               };
                0ECB4FCD24794CE516792552 = {
                        isa = PBXFileReference;
                        lastKnownFileType = folder;
                                CLANG_CXX_LANGUAGE_STANDARD = "c++14";
                                CLANG_CXX_LIBRARY = "libc++";
                                CLANG_LINK_OBJC_RUNTIME = NO;
+                               CODE_SIGN_IDENTITY = "";
                                COMBINE_HIDPI_IMAGES = YES;
                                CONFIGURATION_BUILD_DIR = "$(PROJECT_DIR)/build/$(CONFIGURATION)";
                                COPY_PHASE_STRIP = NO;
                                        "JUCE_DEMO_RUNNER=1",
                                        "JUCE_UNIT_TESTS=1",
                                        "JUCER_XCODE_MAC_F6D2F4CF=1",
-                                       "JUCE_APP_VERSION=5.4.4",
-                                       "JUCE_APP_VERSION_HEX=0x50404",
+                                       "JUCE_APP_VERSION=5.4.5",
+                                       "JUCE_APP_VERSION_HEX=0x50405",
                                        "JucePlugin_Build_VST=0",
                                        "JucePlugin_Build_VST3=0",
                                        "JucePlugin_Build_AU=0",
                                CLANG_CXX_LANGUAGE_STANDARD = "c++14";
                                CLANG_CXX_LIBRARY = "libc++";
                                CLANG_LINK_OBJC_RUNTIME = NO;
+                               CODE_SIGN_IDENTITY = "";
                                COMBINE_HIDPI_IMAGES = YES;
                                CONFIGURATION_BUILD_DIR = "$(PROJECT_DIR)/build/$(CONFIGURATION)";
                                DEAD_CODE_STRIPPING = YES;
                                        "JUCE_DEMO_RUNNER=1",
                                        "JUCE_UNIT_TESTS=1",
                                        "JUCER_XCODE_MAC_F6D2F4CF=1",
-                                       "JUCE_APP_VERSION=5.4.4",
-                                       "JUCE_APP_VERSION_HEX=0x50404",
+                                       "JUCE_APP_VERSION=5.4.5",
+                                       "JUCE_APP_VERSION_HEX=0x50405",
                                        "JucePlugin_Build_VST=0",
                                        "JucePlugin_Build_VST3=0",
                                        "JucePlugin_Build_AU=0",
                                CLANG_WARN_SUSPICIOUS_MOVE = YES;
                                CLANG_WARN_UNREACHABLE_CODE = YES;
                                CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
+                               CODE_SIGN_IDENTITY = "";
                                DEBUG_INFORMATION_FORMAT = dwarf;
                                ENABLE_STRICT_OBJC_MSGSEND = YES;
                                ENABLE_TESTABILITY = YES;
                                CLANG_WARN_SUSPICIOUS_MOVE = YES;
                                CLANG_WARN_UNREACHABLE_CODE = YES;
                                CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
+                               CODE_SIGN_IDENTITY = "";
                                DEBUG_INFORMATION_FORMAT = dwarf;
                                ENABLE_STRICT_OBJC_MSGSEND = YES;
                                GCC_C_LANGUAGE_STANDARD = c11;
index 3a0f53914eee92318f681d977321efa2aadb9f09..9aee797cfb36bdbaf0a0ad1a7cb70c326d8245af 100644 (file)
@@ -22,9 +22,9 @@
     <key>CFBundleSignature</key>\r
     <string>????</string>\r
     <key>CFBundleShortVersionString</key>\r
-    <string>5.4.4</string>\r
+    <string>5.4.5</string>\r
     <key>CFBundleVersion</key>\r
-    <string>5.4.4</string>\r
+    <string>5.4.5</string>\r
     <key>NSHumanReadableCopyright</key>\r
     <string>Copyright (c) 2018 - ROLI Ltd.</string>\r
     <key>NSHighResolutionCapable</key>\r
index e324a45ec2d8198a78538a0863537a79a7b96c0d..05447de16eb397ac9c2e26442ad205bff46cf0ca 100644 (file)
@@ -64,7 +64,7 @@
       <Optimization>Disabled</Optimization>\r
       <DebugInformationFormat>ProgramDatabase</DebugInformationFormat>\r
       <AdditionalIncludeDirectories>..\..\JuceLibraryCode;..\..\..\..\modules;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>\r
-      <PreprocessorDefinitions>_CRT_SECURE_NO_WARNINGS;WIN32;_WINDOWS;DEBUG;_DEBUG;JUCE_DEMO_RUNNER=1;JUCE_UNIT_TESTS=1;JUCER_VS2015_78A5022=1;JUCE_APP_VERSION=5.4.4;JUCE_APP_VERSION_HEX=0x50404;JucePlugin_Build_VST=0;JucePlugin_Build_VST3=0;JucePlugin_Build_AU=0;JucePlugin_Build_AUv3=0;JucePlugin_Build_RTAS=0;JucePlugin_Build_AAX=0;JucePlugin_Build_Standalone=0;JucePlugin_Build_Unity=0;%(PreprocessorDefinitions)</PreprocessorDefinitions>\r
+      <PreprocessorDefinitions>_CRT_SECURE_NO_WARNINGS;WIN32;_WINDOWS;DEBUG;_DEBUG;JUCE_DEMO_RUNNER=1;JUCE_UNIT_TESTS=1;JUCER_VS2015_78A5022=1;JUCE_APP_VERSION=5.4.5;JUCE_APP_VERSION_HEX=0x50405;JucePlugin_Build_VST=0;JucePlugin_Build_VST3=0;JucePlugin_Build_AU=0;JucePlugin_Build_AUv3=0;JucePlugin_Build_RTAS=0;JucePlugin_Build_AAX=0;JucePlugin_Build_Standalone=0;JucePlugin_Build_Unity=0;%(PreprocessorDefinitions)</PreprocessorDefinitions>\r
       <RuntimeLibrary>MultiThreadedDebugDLL</RuntimeLibrary>\r
       <RuntimeTypeInfo>true</RuntimeTypeInfo>\r
       <PrecompiledHeader/>\r
     <ClCompile>\r
       <Optimization>Full</Optimization>\r
       <AdditionalIncludeDirectories>..\..\JuceLibraryCode;..\..\..\..\modules;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>\r
-      <PreprocessorDefinitions>_CRT_SECURE_NO_WARNINGS;WIN32;_WINDOWS;NDEBUG;JUCE_DEMO_RUNNER=1;JUCE_UNIT_TESTS=1;JUCER_VS2015_78A5022=1;JUCE_APP_VERSION=5.4.4;JUCE_APP_VERSION_HEX=0x50404;JucePlugin_Build_VST=0;JucePlugin_Build_VST3=0;JucePlugin_Build_AU=0;JucePlugin_Build_AUv3=0;JucePlugin_Build_RTAS=0;JucePlugin_Build_AAX=0;JucePlugin_Build_Standalone=0;JucePlugin_Build_Unity=0;%(PreprocessorDefinitions)</PreprocessorDefinitions>\r
+      <PreprocessorDefinitions>_CRT_SECURE_NO_WARNINGS;WIN32;_WINDOWS;NDEBUG;JUCE_DEMO_RUNNER=1;JUCE_UNIT_TESTS=1;JUCER_VS2015_78A5022=1;JUCE_APP_VERSION=5.4.5;JUCE_APP_VERSION_HEX=0x50405;JucePlugin_Build_VST=0;JucePlugin_Build_VST3=0;JucePlugin_Build_AU=0;JucePlugin_Build_AUv3=0;JucePlugin_Build_RTAS=0;JucePlugin_Build_AAX=0;JucePlugin_Build_Standalone=0;JucePlugin_Build_Unity=0;%(PreprocessorDefinitions)</PreprocessorDefinitions>\r
       <RuntimeLibrary>MultiThreaded</RuntimeLibrary>\r
       <RuntimeTypeInfo>true</RuntimeTypeInfo>\r
       <PrecompiledHeader/>\r
     <ClCompile Include="..\..\..\..\modules\juce_blocks_basics\topology\internal\juce_BlockImplementation.cpp">\r
       <ExcludedFromBuild>true</ExcludedFromBuild>\r
     </ClCompile>\r
+    <ClCompile Include="..\..\..\..\modules\juce_blocks_basics\topology\internal\juce_BlockSerialReader.cpp">\r
+      <ExcludedFromBuild>true</ExcludedFromBuild>\r
+    </ClCompile>\r
     <ClCompile Include="..\..\..\..\modules\juce_blocks_basics\topology\internal\juce_ConnectedDeviceGroup.cpp">\r
       <ExcludedFromBuild>true</ExcludedFromBuild>\r
     </ClCompile>\r
     <ClCompile Include="..\..\..\..\modules\juce_data_structures\juce_data_structures.cpp">\r
       <ExcludedFromBuild>true</ExcludedFromBuild>\r
     </ClCompile>\r
+    <ClCompile Include="..\..\..\..\modules\juce_dsp\containers\juce_AudioBlock_test.cpp">\r
+      <ExcludedFromBuild>true</ExcludedFromBuild>\r
+    </ClCompile>\r
     <ClCompile Include="..\..\..\..\modules\juce_dsp\containers\juce_SIMDRegister_test.cpp">\r
       <ExcludedFromBuild>true</ExcludedFromBuild>\r
     </ClCompile>\r
index 9a2e0bc092ef7cf6a662074d7ea1c2d3e78acd54..d669b59020bf02febba3cc0271b5e3cd0570d3d5 100644 (file)
     <ClCompile Include="..\..\..\..\modules\juce_blocks_basics\topology\internal\juce_BlockImplementation.cpp">\r
       <Filter>JUCE Modules\juce_blocks_basics\topology\internal</Filter>\r
     </ClCompile>\r
+    <ClCompile Include="..\..\..\..\modules\juce_blocks_basics\topology\internal\juce_BlockSerialReader.cpp">\r
+      <Filter>JUCE Modules\juce_blocks_basics\topology\internal</Filter>\r
+    </ClCompile>\r
     <ClCompile Include="..\..\..\..\modules\juce_blocks_basics\topology\internal\juce_ConnectedDeviceGroup.cpp">\r
       <Filter>JUCE Modules\juce_blocks_basics\topology\internal</Filter>\r
     </ClCompile>\r
     <ClCompile Include="..\..\..\..\modules\juce_data_structures\juce_data_structures.mm">\r
       <Filter>JUCE Modules\juce_data_structures</Filter>\r
     </ClCompile>\r
+    <ClCompile Include="..\..\..\..\modules\juce_dsp\containers\juce_AudioBlock_test.cpp">\r
+      <Filter>JUCE Modules\juce_dsp\containers</Filter>\r
+    </ClCompile>\r
     <ClCompile Include="..\..\..\..\modules\juce_dsp\containers\juce_SIMDRegister_test.cpp">\r
       <Filter>JUCE Modules\juce_dsp\containers</Filter>\r
     </ClCompile>\r
index eaf889030da2bca4bc0f047311e910660402789a..b9e17aa798ca8c02a2343347b8cf8c0a004f5604 100644 (file)
@@ -7,7 +7,7 @@
 #include <windows.h>\r
 \r
 VS_VERSION_INFO VERSIONINFO\r
-FILEVERSION  5,4,4,0\r
+FILEVERSION  5,4,5,0\r
 BEGIN\r
   BLOCK "StringFileInfo"\r
   BEGIN\r
@@ -16,9 +16,9 @@ BEGIN
       VALUE "CompanyName",  "ROLI Ltd.\0"\r
       VALUE "LegalCopyright",  "Copyright (c) 2018 - ROLI Ltd.\0"\r
       VALUE "FileDescription",  "DemoRunner\0"\r
-      VALUE "FileVersion",  "5.4.4\0"\r
+      VALUE "FileVersion",  "5.4.5\0"\r
       VALUE "ProductName",  "DemoRunner\0"\r
-      VALUE "ProductVersion",  "5.4.4\0"\r
+      VALUE "ProductVersion",  "5.4.5\0"\r
     END\r
   END\r
 \r
index 040005b86bda613fe0cf91bb5e457223faa2f8f7..cd93c15b80fdec998935e00df8b63649db79cf11 100644 (file)
@@ -64,7 +64,7 @@
       <Optimization>Disabled</Optimization>\r
       <DebugInformationFormat>ProgramDatabase</DebugInformationFormat>\r
       <AdditionalIncludeDirectories>..\..\JuceLibraryCode;..\..\..\..\modules;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>\r
-      <PreprocessorDefinitions>_CRT_SECURE_NO_WARNINGS;WIN32;_WINDOWS;DEBUG;_DEBUG;JUCE_DEMO_RUNNER=1;JUCE_UNIT_TESTS=1;JUCER_VS2017_78A5024=1;JUCE_APP_VERSION=5.4.4;JUCE_APP_VERSION_HEX=0x50404;JucePlugin_Build_VST=0;JucePlugin_Build_VST3=0;JucePlugin_Build_AU=0;JucePlugin_Build_AUv3=0;JucePlugin_Build_RTAS=0;JucePlugin_Build_AAX=0;JucePlugin_Build_Standalone=0;JucePlugin_Build_Unity=0;%(PreprocessorDefinitions)</PreprocessorDefinitions>\r
+      <PreprocessorDefinitions>_CRT_SECURE_NO_WARNINGS;WIN32;_WINDOWS;DEBUG;_DEBUG;JUCE_DEMO_RUNNER=1;JUCE_UNIT_TESTS=1;JUCER_VS2017_78A5024=1;JUCE_APP_VERSION=5.4.5;JUCE_APP_VERSION_HEX=0x50405;JucePlugin_Build_VST=0;JucePlugin_Build_VST3=0;JucePlugin_Build_AU=0;JucePlugin_Build_AUv3=0;JucePlugin_Build_RTAS=0;JucePlugin_Build_AAX=0;JucePlugin_Build_Standalone=0;JucePlugin_Build_Unity=0;%(PreprocessorDefinitions)</PreprocessorDefinitions>\r
       <RuntimeLibrary>MultiThreadedDebugDLL</RuntimeLibrary>\r
       <RuntimeTypeInfo>true</RuntimeTypeInfo>\r
       <PrecompiledHeader/>\r
     <ClCompile>\r
       <Optimization>Full</Optimization>\r
       <AdditionalIncludeDirectories>..\..\JuceLibraryCode;..\..\..\..\modules;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>\r
-      <PreprocessorDefinitions>_CRT_SECURE_NO_WARNINGS;WIN32;_WINDOWS;NDEBUG;JUCE_DEMO_RUNNER=1;JUCE_UNIT_TESTS=1;JUCER_VS2017_78A5024=1;JUCE_APP_VERSION=5.4.4;JUCE_APP_VERSION_HEX=0x50404;JucePlugin_Build_VST=0;JucePlugin_Build_VST3=0;JucePlugin_Build_AU=0;JucePlugin_Build_AUv3=0;JucePlugin_Build_RTAS=0;JucePlugin_Build_AAX=0;JucePlugin_Build_Standalone=0;JucePlugin_Build_Unity=0;%(PreprocessorDefinitions)</PreprocessorDefinitions>\r
+      <PreprocessorDefinitions>_CRT_SECURE_NO_WARNINGS;WIN32;_WINDOWS;NDEBUG;JUCE_DEMO_RUNNER=1;JUCE_UNIT_TESTS=1;JUCER_VS2017_78A5024=1;JUCE_APP_VERSION=5.4.5;JUCE_APP_VERSION_HEX=0x50405;JucePlugin_Build_VST=0;JucePlugin_Build_VST3=0;JucePlugin_Build_AU=0;JucePlugin_Build_AUv3=0;JucePlugin_Build_RTAS=0;JucePlugin_Build_AAX=0;JucePlugin_Build_Standalone=0;JucePlugin_Build_Unity=0;%(PreprocessorDefinitions)</PreprocessorDefinitions>\r
       <RuntimeLibrary>MultiThreaded</RuntimeLibrary>\r
       <RuntimeTypeInfo>true</RuntimeTypeInfo>\r
       <PrecompiledHeader/>\r
     <ClCompile Include="..\..\..\..\modules\juce_blocks_basics\topology\internal\juce_BlockImplementation.cpp">\r
       <ExcludedFromBuild>true</ExcludedFromBuild>\r
     </ClCompile>\r
+    <ClCompile Include="..\..\..\..\modules\juce_blocks_basics\topology\internal\juce_BlockSerialReader.cpp">\r
+      <ExcludedFromBuild>true</ExcludedFromBuild>\r
+    </ClCompile>\r
     <ClCompile Include="..\..\..\..\modules\juce_blocks_basics\topology\internal\juce_ConnectedDeviceGroup.cpp">\r
       <ExcludedFromBuild>true</ExcludedFromBuild>\r
     </ClCompile>\r
     <ClCompile Include="..\..\..\..\modules\juce_data_structures\juce_data_structures.cpp">\r
       <ExcludedFromBuild>true</ExcludedFromBuild>\r
     </ClCompile>\r
+    <ClCompile Include="..\..\..\..\modules\juce_dsp\containers\juce_AudioBlock_test.cpp">\r
+      <ExcludedFromBuild>true</ExcludedFromBuild>\r
+    </ClCompile>\r
     <ClCompile Include="..\..\..\..\modules\juce_dsp\containers\juce_SIMDRegister_test.cpp">\r
       <ExcludedFromBuild>true</ExcludedFromBuild>\r
     </ClCompile>\r
index 2ffed545fe93bb0c8e3b034693d69cd29f09df95..1c01ce48da0abc4190cf18957c8d9e7d30237778 100644 (file)
     <ClCompile Include="..\..\..\..\modules\juce_blocks_basics\topology\internal\juce_BlockImplementation.cpp">\r
       <Filter>JUCE Modules\juce_blocks_basics\topology\internal</Filter>\r
     </ClCompile>\r
+    <ClCompile Include="..\..\..\..\modules\juce_blocks_basics\topology\internal\juce_BlockSerialReader.cpp">\r
+      <Filter>JUCE Modules\juce_blocks_basics\topology\internal</Filter>\r
+    </ClCompile>\r
     <ClCompile Include="..\..\..\..\modules\juce_blocks_basics\topology\internal\juce_ConnectedDeviceGroup.cpp">\r
       <Filter>JUCE Modules\juce_blocks_basics\topology\internal</Filter>\r
     </ClCompile>\r
     <ClCompile Include="..\..\..\..\modules\juce_data_structures\juce_data_structures.mm">\r
       <Filter>JUCE Modules\juce_data_structures</Filter>\r
     </ClCompile>\r
+    <ClCompile Include="..\..\..\..\modules\juce_dsp\containers\juce_AudioBlock_test.cpp">\r
+      <Filter>JUCE Modules\juce_dsp\containers</Filter>\r
+    </ClCompile>\r
     <ClCompile Include="..\..\..\..\modules\juce_dsp\containers\juce_SIMDRegister_test.cpp">\r
       <Filter>JUCE Modules\juce_dsp\containers</Filter>\r
     </ClCompile>\r
index eaf889030da2bca4bc0f047311e910660402789a..b9e17aa798ca8c02a2343347b8cf8c0a004f5604 100644 (file)
@@ -7,7 +7,7 @@
 #include <windows.h>\r
 \r
 VS_VERSION_INFO VERSIONINFO\r
-FILEVERSION  5,4,4,0\r
+FILEVERSION  5,4,5,0\r
 BEGIN\r
   BLOCK "StringFileInfo"\r
   BEGIN\r
@@ -16,9 +16,9 @@ BEGIN
       VALUE "CompanyName",  "ROLI Ltd.\0"\r
       VALUE "LegalCopyright",  "Copyright (c) 2018 - ROLI Ltd.\0"\r
       VALUE "FileDescription",  "DemoRunner\0"\r
-      VALUE "FileVersion",  "5.4.4\0"\r
+      VALUE "FileVersion",  "5.4.5\0"\r
       VALUE "ProductName",  "DemoRunner\0"\r
-      VALUE "ProductVersion",  "5.4.4\0"\r
+      VALUE "ProductVersion",  "5.4.5\0"\r
     END\r
   END\r
 \r
index abf67e40dcd0a8c99b825085cf7951c2637280a6..8ce8e59268ca3f08afb3beab14d0908ff11beda5 100644 (file)
@@ -64,7 +64,7 @@
       <Optimization>Disabled</Optimization>\r
       <DebugInformationFormat>ProgramDatabase</DebugInformationFormat>\r
       <AdditionalIncludeDirectories>..\..\JuceLibraryCode;..\..\..\..\modules;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>\r
-      <PreprocessorDefinitions>_CRT_SECURE_NO_WARNINGS;WIN32;_WINDOWS;DEBUG;_DEBUG;JUCE_DEMO_RUNNER=1;JUCE_UNIT_TESTS=1;JUCER_VS2019_78A5026=1;JUCE_APP_VERSION=5.4.4;JUCE_APP_VERSION_HEX=0x50404;JucePlugin_Build_VST=0;JucePlugin_Build_VST3=0;JucePlugin_Build_AU=0;JucePlugin_Build_AUv3=0;JucePlugin_Build_RTAS=0;JucePlugin_Build_AAX=0;JucePlugin_Build_Standalone=0;JucePlugin_Build_Unity=0;%(PreprocessorDefinitions)</PreprocessorDefinitions>\r
+      <PreprocessorDefinitions>_CRT_SECURE_NO_WARNINGS;WIN32;_WINDOWS;DEBUG;_DEBUG;JUCE_DEMO_RUNNER=1;JUCE_UNIT_TESTS=1;JUCER_VS2019_78A5026=1;JUCE_APP_VERSION=5.4.5;JUCE_APP_VERSION_HEX=0x50405;JucePlugin_Build_VST=0;JucePlugin_Build_VST3=0;JucePlugin_Build_AU=0;JucePlugin_Build_AUv3=0;JucePlugin_Build_RTAS=0;JucePlugin_Build_AAX=0;JucePlugin_Build_Standalone=0;JucePlugin_Build_Unity=0;%(PreprocessorDefinitions)</PreprocessorDefinitions>\r
       <RuntimeLibrary>MultiThreadedDebugDLL</RuntimeLibrary>\r
       <RuntimeTypeInfo>true</RuntimeTypeInfo>\r
       <PrecompiledHeader/>\r
     <ClCompile>\r
       <Optimization>Full</Optimization>\r
       <AdditionalIncludeDirectories>..\..\JuceLibraryCode;..\..\..\..\modules;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>\r
-      <PreprocessorDefinitions>_CRT_SECURE_NO_WARNINGS;WIN32;_WINDOWS;NDEBUG;JUCE_DEMO_RUNNER=1;JUCE_UNIT_TESTS=1;JUCER_VS2019_78A5026=1;JUCE_APP_VERSION=5.4.4;JUCE_APP_VERSION_HEX=0x50404;JucePlugin_Build_VST=0;JucePlugin_Build_VST3=0;JucePlugin_Build_AU=0;JucePlugin_Build_AUv3=0;JucePlugin_Build_RTAS=0;JucePlugin_Build_AAX=0;JucePlugin_Build_Standalone=0;JucePlugin_Build_Unity=0;%(PreprocessorDefinitions)</PreprocessorDefinitions>\r
+      <PreprocessorDefinitions>_CRT_SECURE_NO_WARNINGS;WIN32;_WINDOWS;NDEBUG;JUCE_DEMO_RUNNER=1;JUCE_UNIT_TESTS=1;JUCER_VS2019_78A5026=1;JUCE_APP_VERSION=5.4.5;JUCE_APP_VERSION_HEX=0x50405;JucePlugin_Build_VST=0;JucePlugin_Build_VST3=0;JucePlugin_Build_AU=0;JucePlugin_Build_AUv3=0;JucePlugin_Build_RTAS=0;JucePlugin_Build_AAX=0;JucePlugin_Build_Standalone=0;JucePlugin_Build_Unity=0;%(PreprocessorDefinitions)</PreprocessorDefinitions>\r
       <RuntimeLibrary>MultiThreaded</RuntimeLibrary>\r
       <RuntimeTypeInfo>true</RuntimeTypeInfo>\r
       <PrecompiledHeader/>\r
     <ClCompile Include="..\..\..\..\modules\juce_blocks_basics\topology\internal\juce_BlockImplementation.cpp">\r
       <ExcludedFromBuild>true</ExcludedFromBuild>\r
     </ClCompile>\r
+    <ClCompile Include="..\..\..\..\modules\juce_blocks_basics\topology\internal\juce_BlockSerialReader.cpp">\r
+      <ExcludedFromBuild>true</ExcludedFromBuild>\r
+    </ClCompile>\r
     <ClCompile Include="..\..\..\..\modules\juce_blocks_basics\topology\internal\juce_ConnectedDeviceGroup.cpp">\r
       <ExcludedFromBuild>true</ExcludedFromBuild>\r
     </ClCompile>\r
     <ClCompile Include="..\..\..\..\modules\juce_data_structures\juce_data_structures.cpp">\r
       <ExcludedFromBuild>true</ExcludedFromBuild>\r
     </ClCompile>\r
+    <ClCompile Include="..\..\..\..\modules\juce_dsp\containers\juce_AudioBlock_test.cpp">\r
+      <ExcludedFromBuild>true</ExcludedFromBuild>\r
+    </ClCompile>\r
     <ClCompile Include="..\..\..\..\modules\juce_dsp\containers\juce_SIMDRegister_test.cpp">\r
       <ExcludedFromBuild>true</ExcludedFromBuild>\r
     </ClCompile>\r
index 2bcd62786c835f5850d0da35a858ef479a8159f7..71680ce40424f4f53cd83d0dc2277bef06adc64d 100644 (file)
     <ClCompile Include="..\..\..\..\modules\juce_blocks_basics\topology\internal\juce_BlockImplementation.cpp">\r
       <Filter>JUCE Modules\juce_blocks_basics\topology\internal</Filter>\r
     </ClCompile>\r
+    <ClCompile Include="..\..\..\..\modules\juce_blocks_basics\topology\internal\juce_BlockSerialReader.cpp">\r
+      <Filter>JUCE Modules\juce_blocks_basics\topology\internal</Filter>\r
+    </ClCompile>\r
     <ClCompile Include="..\..\..\..\modules\juce_blocks_basics\topology\internal\juce_ConnectedDeviceGroup.cpp">\r
       <Filter>JUCE Modules\juce_blocks_basics\topology\internal</Filter>\r
     </ClCompile>\r
     <ClCompile Include="..\..\..\..\modules\juce_data_structures\juce_data_structures.mm">\r
       <Filter>JUCE Modules\juce_data_structures</Filter>\r
     </ClCompile>\r
+    <ClCompile Include="..\..\..\..\modules\juce_dsp\containers\juce_AudioBlock_test.cpp">\r
+      <Filter>JUCE Modules\juce_dsp\containers</Filter>\r
+    </ClCompile>\r
     <ClCompile Include="..\..\..\..\modules\juce_dsp\containers\juce_SIMDRegister_test.cpp">\r
       <Filter>JUCE Modules\juce_dsp\containers</Filter>\r
     </ClCompile>\r
index eaf889030da2bca4bc0f047311e910660402789a..b9e17aa798ca8c02a2343347b8cf8c0a004f5604 100644 (file)
@@ -7,7 +7,7 @@
 #include <windows.h>\r
 \r
 VS_VERSION_INFO VERSIONINFO\r
-FILEVERSION  5,4,4,0\r
+FILEVERSION  5,4,5,0\r
 BEGIN\r
   BLOCK "StringFileInfo"\r
   BEGIN\r
@@ -16,9 +16,9 @@ BEGIN
       VALUE "CompanyName",  "ROLI Ltd.\0"\r
       VALUE "LegalCopyright",  "Copyright (c) 2018 - ROLI Ltd.\0"\r
       VALUE "FileDescription",  "DemoRunner\0"\r
-      VALUE "FileVersion",  "5.4.4\0"\r
+      VALUE "FileVersion",  "5.4.5\0"\r
       VALUE "ProductName",  "DemoRunner\0"\r
-      VALUE "ProductVersion",  "5.4.4\0"\r
+      VALUE "ProductVersion",  "5.4.5\0"\r
     END\r
   END\r
 \r
index 0f01890ca82ea16966ca020ecc633368b8cde98d..5751f07482d9c0c6aee80d40bccdd9c64bdd3e70 100644 (file)
                91A9A0FE9DF4F4E10009EEC7 = {
                        isa = PBXGroup;
                        children = (
-                               0CCFDC1D1C7B8A12BF4822F1,
                                9683F931FA1B8B85FA8C4BD8,
                                5A0B2CEF393A25C6D4B1B76C,
                                61F3057D838D7DABB0FA3D34,
                B18D059E5616FA729F764229 = {
                        isa = XCBuildConfiguration;
                        buildSettings = {
+                               "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "";
                                ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
-                               ASSETCATALOG_COMPILER_LAUNCHIMAGE_NAME = LaunchImage;
                                CLANG_CXX_LANGUAGE_STANDARD = "c++14";
                                CLANG_CXX_LIBRARY = "libc++";
                                CLANG_LINK_OBJC_RUNTIME = NO;
                                        "JUCE_DEMO_RUNNER=1",
                                        "JUCE_UNIT_TESTS=1",
                                        "JUCER_XCODE_IPHONE_5BC26AE3=1",
-                                       "JUCE_APP_VERSION=5.4.4",
-                                       "JUCE_APP_VERSION_HEX=0x50404",
+                                       "JUCE_APP_VERSION=5.4.5",
+                                       "JUCE_APP_VERSION_HEX=0x50405",
                                        "JucePlugin_Build_VST=0",
                                        "JucePlugin_Build_VST3=0",
                                        "JucePlugin_Build_AU=0",
                69330F27DD2C71609336C7D2 = {
                        isa = XCBuildConfiguration;
                        buildSettings = {
+                               "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "";
                                ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
-                               ASSETCATALOG_COMPILER_LAUNCHIMAGE_NAME = LaunchImage;
                                CLANG_CXX_LANGUAGE_STANDARD = "c++14";
                                CLANG_CXX_LIBRARY = "libc++";
                                CLANG_LINK_OBJC_RUNTIME = NO;
                                        "JUCE_DEMO_RUNNER=1",
                                        "JUCE_UNIT_TESTS=1",
                                        "JUCER_XCODE_IPHONE_5BC26AE3=1",
-                                       "JUCE_APP_VERSION=5.4.4",
-                                       "JUCE_APP_VERSION_HEX=0x50404",
+                                       "JUCE_APP_VERSION=5.4.5",
+                                       "JUCE_APP_VERSION_HEX=0x50405",
                                        "JucePlugin_Build_VST=0",
                                        "JucePlugin_Build_VST3=0",
                                        "JucePlugin_Build_AU=0",
                C01EC82F42B640CA1E54AD53 = {
                        isa = XCBuildConfiguration;
                        buildSettings = {
-                               "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "iPhone Developer";
+                               "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "";
                                ALWAYS_SEARCH_USER_PATHS = NO;
                                CLANG_ENABLE_OBJC_WEAK = YES;
                                CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
                07EA85D22270E8EA13CA0BBE = {
                        isa = XCBuildConfiguration;
                        buildSettings = {
-                               "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "iPhone Developer";
+                               "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "";
                                ALWAYS_SEARCH_USER_PATHS = NO;
                                CLANG_ENABLE_OBJC_WEAK = YES;
                                CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
index 483c3852b7439f6dbfea01f523ea278ad045f6da..39de13f091897e8f4800b39f867e08c1218abebd 100644 (file)
@@ -7,6 +7,10 @@
     <string>This app requires audio input. If you do not have an audio interface connected it will use the built-in microphone.</string>\r
     <key>NSCameraUsageDescription</key>\r
     <string>This app requires access to the camera to function correctly.</string>\r
+    <key>NSBluetoothAlwaysUsageDescription</key>\r
+    <string>This app requires access to Bluetooth to function correctly.</string>\r
+    <key>NSBluetoothPeripheralUsageDescription</key>\r
+    <string>This app requires access to Bluetooth to function correctly.</string>\r
     <key>LSRequiresIPhoneOS</key>\r
     <true/>\r
     <key>UIViewControllerBasedStatusBarAppearance</key>\r
@@ -26,9 +30,9 @@
     <key>CFBundleSignature</key>\r
     <string>????</string>\r
     <key>CFBundleShortVersionString</key>\r
-    <string>5.4.4</string>\r
+    <string>5.4.5</string>\r
     <key>CFBundleVersion</key>\r
-    <string>5.4.4</string>\r
+    <string>5.4.5</string>\r
     <key>NSHumanReadableCopyright</key>\r
     <string>Copyright (c) 2018 - ROLI Ltd.</string>\r
     <key>NSHighResolutionCapable</key>\r
index f661d0ed91bfa8730236c74a6f92b6f48658b926..4a28f30c59937764ca5dc47a8a832a534ddf04d3 100644 (file)
@@ -1,7 +1,7 @@
 <?xml version="1.0" encoding="UTF-8"?>\r
 \r
-<JUCERPROJECT name="DemoRunner" projectType="guiapp" jucerVersion="5.4.4" defines="JUCE_DEMO_RUNNER=1&#10;JUCE_UNIT_TESTS=1"\r
-              bundleIdentifier="com.juce.demorunner" version="5.4.4" companyName="ROLI Ltd."\r
+<JUCERPROJECT name="DemoRunner" projectType="guiapp" jucerVersion="5.4.5" defines="JUCE_DEMO_RUNNER=1&#10;JUCE_UNIT_TESTS=1"\r
+              bundleIdentifier="com.juce.demorunner" version="5.4.5" companyName="ROLI Ltd."\r
               companyCopyright="Copyright (c) 2018 - ROLI Ltd." companyWebsite="https://www.juce.com/"\r
               companyEmail="info@juce.com" id="yj7xMM" reportAppUsage="1">\r
   <MAINGROUP id="G8kbr7" name="DemoRunner">\r
     </ANDROIDSTUDIO>\r
     <XCODE_IPHONE targetFolder="Builds/iOS" UISupportsDocumentBrowser="1" microphonePermissionNeeded="1"\r
                   cameraPermissionNeeded="1" iCloudPermissions="1" UIFileSharingEnabled="1"\r
-                  customXcodeResourceFolders="../Assets" smallIcon="YyqWd2" bigIcon="YyqWd2">\r
+                  customXcodeResourceFolders="../Assets" smallIcon="YyqWd2" bigIcon="YyqWd2"\r
+                  iosBluetoothPermissionNeeded="1">\r
       <CONFIGURATIONS>\r
         <CONFIGURATION isDebug="1" name="Debug" recommendedWarnings="LLVM"/>\r
         <CONFIGURATION isDebug="0" name="Release" recommendedWarnings="LLVM"/>\r
index 7c6bfaa70f57cc41ad2456c3a61aa4443a34420f..fd7cbb98922c7143dc59bd407eeba7a9237578b3 100644 (file)
@@ -47,6 +47,8 @@
 \r
 #define JUCE_USE_DARK_SPLASH_SCREEN 1\r
 \r
+#define JUCE_PROJUCER_VERSION 0x50405\r
+\r
 //==============================================================================\r
 #define JUCE_MODULE_AVAILABLE_juce_analytics              1\r
 #define JUCE_MODULE_AVAILABLE_juce_audio_basics           1\r
index 06f7f814015cdb01e5d6335b4900724b39a09fff..c1d016dd9018df98980d0c65aec5740c822ad514 100644 (file)
 #include <juce_video/juce_video.h>\r
 \r
 \r
+#if defined (JUCE_PROJUCER_VERSION) && JUCE_PROJUCER_VERSION < JUCE_VERSION\r
+ /** If you've hit this error then the version of the Projucer that was used to generate this project is\r
+     older than the version of the JUCE modules being included. To fix this error, re-save your project\r
+     using the latest version of the Projucer or, if you aren't using the Projucer to manage your project,\r
+     remove the JUCE_PROJUCER_VERSION define from the AppConfig.h file.\r
+ */\r
+ #error "This project was last saved using an outdated version of the Projucer! Re-save this project with the latest version to fix this error."\r
+#endif\r
+\r
 #if ! DONT_SET_USING_JUCE_NAMESPACE\r
  // If your code uses a lot of JUCE classes, then this will obviously save you\r
  // a lot of typing, but can be disabled by setting DONT_SET_USING_JUCE_NAMESPACE.\r
@@ -47,7 +56,7 @@ namespace ProjectInfo
 {\r
     const char* const  projectName    = "DemoRunner";\r
     const char* const  companyName    = "ROLI Ltd.";\r
-    const char* const  versionString  = "5.4.4";\r
-    const int          versionNumber  = 0x50404;\r
+    const char* const  versionString  = "5.4.5";\r
+    const int          versionNumber  = 0x50405;\r
 }\r
 #endif\r
index 3f58c792b9b421af69fcc581cff519cdb5476a01..edbd8f8e616b223fbcdc90712e2c95ee14c78747 100644 (file)
@@ -108,7 +108,7 @@ public:
         mainWindow.reset (new MainAppWindow (getApplicationName()));\r
     }\r
 \r
-    void backButtonPressed() override    { mainWindow->getMainComponent().getSidePanel().showOrHide (false); }\r
+    bool backButtonPressed() override    { mainWindow->getMainComponent().getSidePanel().showOrHide (false); return true; }\r
     void shutdown() override             { mainWindow = nullptr; }\r
 \r
     //==============================================================================\r
index 19e61be7974816cc07419e3adf61c4b5ac418f2b..1c6d9a3562282ba1a8aac29d927dd51d35149f95 100644 (file)
@@ -156,7 +156,7 @@ void DemoContentComponent::setDemo (const String& category, int selectedDemoInde
 \r
 bool DemoContentComponent::isShowingHomeScreen() const noexcept\r
 {\r
-    return isComponentIntroDemo (demoContent->getComponent());\r
+    return isComponentIntroDemo (demoContent->getComponent()) && getCurrentTabIndex() == 0;\r
 }\r
 \r
 void DemoContentComponent::showHomeScreen()\r
index a814a91a3c40b14f4e1faa3b2edbcc202aa72495..43d4f2ef1c56c87df460f637ceea321ac9154207 100644 (file)
@@ -196,7 +196,7 @@ public:
             process (dsp::ProcessContextReplacing<float> (firstChan));\r
 \r
             for (size_t chan = 1; chan < block.getNumChannels(); ++chan)\r
-                block.getSingleChannelBlock (chan).copy (firstChan);\r
+                block.getSingleChannelBlock (chan).copyFrom (firstChan);\r
         }\r
     }\r
 \r
index 895863e8d0c26f34204efaadef540e8032def939..f030db71421d907e9e5ed5c9eba64b4cec184b5f 100644 (file)
@@ -1,7 +1,7 @@
 <?xml version="1.0" encoding="UTF-8"?>\r
 \r
 <JUCERPROJECT id="AKfc5m" name="AudioPerformanceTest" projectType="guiapp"\r
-              bundleIdentifier="com.juce.AudioPerformanceTest" jucerVersion="5.4.4"\r
+              bundleIdentifier="com.juce.AudioPerformanceTest" jucerVersion="5.4.5"\r
               displaySplashScreen="0" reportAppUsage="0" companyName="ROLI Ltd."\r
               companyCopyright="ROLI Ltd.">\r
   <MAINGROUP id="b1eVTe" name="AudioPerformanceTest">\r
diff --git a/extras/AudioPerformanceTest/Builds/MacOSX/AudioPerformanceTest.entitlements b/extras/AudioPerformanceTest/Builds/MacOSX/AudioPerformanceTest.entitlements
new file mode 100644 (file)
index 0000000..6631ffa
--- /dev/null
@@ -0,0 +1,6 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
+<plist version="1.0">
+<dict>
+</dict>
+</plist>
index 282962a3f8178d7413776554d1a5dad14cf03700..0772d9b1b02ace95f9515c936c05e1e34fadd3f7 100644 (file)
                        path = "../../JuceLibraryCode/include_juce_audio_utils.mm";
                        sourceTree = "SOURCE_ROOT";
                };
+               C3BE13F50343166A30728D8A = {
+                       isa = PBXFileReference;
+                       lastKnownFileType = text.plist.xml;
+                       name = AudioPerformanceTest.entitlements;
+                       path = AudioPerformanceTest.entitlements;
+                       sourceTree = "SOURCE_ROOT";
+               };
                C8EE61FDD1F06817A014B881 = {
                        isa = PBXFileReference;
                        lastKnownFileType = file;
                                CLANG_CXX_LANGUAGE_STANDARD = "c++14";
                                CLANG_CXX_LIBRARY = "libc++";
                                CLANG_LINK_OBJC_RUNTIME = NO;
+                               CODE_SIGN_IDENTITY = "";
                                COMBINE_HIDPI_IMAGES = YES;
                                CONFIGURATION_BUILD_DIR = "$(PROJECT_DIR)/build/$(CONFIGURATION)";
                                COPY_PHASE_STRIP = NO;
                                CLANG_CXX_LANGUAGE_STANDARD = "c++14";
                                CLANG_CXX_LIBRARY = "libc++";
                                CLANG_LINK_OBJC_RUNTIME = NO;
+                               CODE_SIGN_IDENTITY = "";
                                COMBINE_HIDPI_IMAGES = YES;
                                CONFIGURATION_BUILD_DIR = "$(PROJECT_DIR)/build/$(CONFIGURATION)";
                                DEAD_CODE_STRIPPING = YES;
                                CLANG_WARN_SUSPICIOUS_MOVE = YES;
                                CLANG_WARN_UNREACHABLE_CODE = YES;
                                CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
+                               CODE_SIGN_IDENTITY = "";
                                DEBUG_INFORMATION_FORMAT = dwarf;
                                ENABLE_STRICT_OBJC_MSGSEND = YES;
                                ENABLE_TESTABILITY = YES;
                                CLANG_WARN_SUSPICIOUS_MOVE = YES;
                                CLANG_WARN_UNREACHABLE_CODE = YES;
                                CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
+                               CODE_SIGN_IDENTITY = "";
                                DEBUG_INFORMATION_FORMAT = dwarf;
                                ENABLE_STRICT_OBJC_MSGSEND = YES;
                                GCC_C_LANGUAGE_STANDARD = c11;
diff --git a/extras/AudioPerformanceTest/Builds/iOS/AudioPerformanceTest.entitlements b/extras/AudioPerformanceTest/Builds/iOS/AudioPerformanceTest.entitlements
new file mode 100644 (file)
index 0000000..6631ffa
--- /dev/null
@@ -0,0 +1,6 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
+<plist version="1.0">
+<dict>
+</dict>
+</plist>
index 81affeea843143151a535c69558a76f83d767164..979f35672b86945dcccc01671f7263278afd2028 100644 (file)
                        path = "../../JuceLibraryCode/include_juce_audio_utils.mm";
                        sourceTree = "SOURCE_ROOT";
                };
+               C3BE13F50343166A30728D8A = {
+                       isa = PBXFileReference;
+                       lastKnownFileType = text.plist.xml;
+                       name = AudioPerformanceTest.entitlements;
+                       path = AudioPerformanceTest.entitlements;
+                       sourceTree = "SOURCE_ROOT";
+               };
                C6030BFC7A19A5075AB0EC28 = {
                        isa = PBXFileReference;
                        lastKnownFileType = wrapper.framework;
                19B7C16D592FB25D09022191 = {
                        isa = XCBuildConfiguration;
                        buildSettings = {
+                               "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "";
                                ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
-                               ASSETCATALOG_COMPILER_LAUNCHIMAGE_NAME = LaunchImage;
                                CLANG_CXX_LANGUAGE_STANDARD = "c++14";
                                CLANG_CXX_LIBRARY = "libc++";
                                CLANG_LINK_OBJC_RUNTIME = NO;
                B7A6988E30C0A68B01EDC53B = {
                        isa = XCBuildConfiguration;
                        buildSettings = {
+                               "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "";
                                ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
-                               ASSETCATALOG_COMPILER_LAUNCHIMAGE_NAME = LaunchImage;
                                CLANG_CXX_LANGUAGE_STANDARD = "c++14";
                                CLANG_CXX_LIBRARY = "libc++";
                                CLANG_LINK_OBJC_RUNTIME = NO;
                B907CDF95622107F20CD7617 = {
                        isa = XCBuildConfiguration;
                        buildSettings = {
-                               "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "iPhone Developer";
+                               "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "";
                                ALWAYS_SEARCH_USER_PATHS = NO;
                                CLANG_ENABLE_OBJC_WEAK = YES;
                                CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
                BF82CBDF63CC37CADC61A511 = {
                        isa = XCBuildConfiguration;
                        buildSettings = {
-                               "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "iPhone Developer";
+                               "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "";
                                ALWAYS_SEARCH_USER_PATHS = NO;
                                CLANG_ENABLE_OBJC_WEAK = YES;
                                CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
index 954761b210077aaddd8b9c407f22d8c02be2fe84..9032f6ee16486679d489dc4648b42dee51f40909 100644 (file)
@@ -47,6 +47,8 @@
 \r
 #define JUCE_USE_DARK_SPLASH_SCREEN 1\r
 \r
+#define JUCE_PROJUCER_VERSION 0x50405\r
+\r
 //==============================================================================\r
 #define JUCE_MODULE_AVAILABLE_juce_audio_basics          1\r
 #define JUCE_MODULE_AVAILABLE_juce_audio_devices         1\r
index 82feea7ca6fd5d592fa262f4b732576d61909f5c..1368bac8befe377660eeeb0414044bf0c151d170 100644 (file)
 #include <juce_gui_extra/juce_gui_extra.h>\r
 \r
 \r
+#if defined (JUCE_PROJUCER_VERSION) && JUCE_PROJUCER_VERSION < JUCE_VERSION\r
+ /** If you've hit this error then the version of the Projucer that was used to generate this project is\r
+     older than the version of the JUCE modules being included. To fix this error, re-save your project\r
+     using the latest version of the Projucer or, if you aren't using the Projucer to manage your project,\r
+     remove the JUCE_PROJUCER_VERSION define from the AppConfig.h file.\r
+ */\r
+ #error "This project was last saved using an outdated version of the Projucer! Re-save this project with the latest version to fix this error."\r
+#endif\r
+\r
 #if ! DONT_SET_USING_JUCE_NAMESPACE\r
  // If your code uses a lot of JUCE classes, then this will obviously save you\r
  // a lot of typing, but can be disabled by setting DONT_SET_USING_JUCE_NAMESPACE.\r
index 5aff91d484db4c6fb02dce5c17b04d5ae92f86a6..8ace7ccf009a4d58bfae55e7f633e39e176f960e 100644 (file)
@@ -2,7 +2,7 @@
 \r
 <JUCERPROJECT id="NTe0XB0ij" name="AudioPluginHost" projectType="guiapp" version="1.0.0"\r
               juceFolder="../../../juce" bundleIdentifier="com.roli.juce.pluginhost"\r
-              jucerVersion="5.4.4" companyName="ROLI Ltd." displaySplashScreen="0"\r
+              jucerVersion="5.4.5" companyName="ROLI Ltd." displaySplashScreen="0"\r
               reportAppUsage="0" companyCopyright="ROLI Ltd.">\r
   <EXPORTFORMATS>\r
     <XCODE_MAC targetFolder="Builds/MacOSX" rtasFolder="~/SDKs/PT_80_SDK" objCExtraSuffix="M73TRi"\r
diff --git a/extras/AudioPluginHost/Builds/MacOSX/AudioPluginHost.entitlements b/extras/AudioPluginHost/Builds/MacOSX/AudioPluginHost.entitlements
new file mode 100644 (file)
index 0000000..6631ffa
--- /dev/null
@@ -0,0 +1,6 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
+<plist version="1.0">
+<dict>
+</dict>
+</plist>
index c99c747cb5b0bb14079bfecd6075a2812209c6bb..8ba981feaaa74ffed6590df940f007facc5d628a 100644 (file)
                        path = System/Library/Frameworks/CoreAudioKit.framework;
                        sourceTree = SDKROOT;
                };
+               EC252E34CF52A70B4A836BDC = {
+                       isa = PBXFileReference;
+                       lastKnownFileType = text.plist.xml;
+                       name = AudioPluginHost.entitlements;
+                       path = AudioPluginHost.entitlements;
+                       sourceTree = "SOURCE_ROOT";
+               };
                F14CDB17EFE157DA3C3A5A91 = {
                        isa = PBXFileReference;
                        lastKnownFileType = sourcecode.c.h;
                                CLANG_CXX_LANGUAGE_STANDARD = "c++14";
                                CLANG_CXX_LIBRARY = "libc++";
                                CLANG_LINK_OBJC_RUNTIME = NO;
+                               CODE_SIGN_IDENTITY = "";
                                COMBINE_HIDPI_IMAGES = YES;
                                CONFIGURATION_BUILD_DIR = "$(PROJECT_DIR)/build/$(CONFIGURATION)";
                                COPY_PHASE_STRIP = NO;
                                CLANG_CXX_LANGUAGE_STANDARD = "c++14";
                                CLANG_CXX_LIBRARY = "libc++";
                                CLANG_LINK_OBJC_RUNTIME = NO;
+                               CODE_SIGN_IDENTITY = "";
                                COMBINE_HIDPI_IMAGES = YES;
                                CONFIGURATION_BUILD_DIR = "$(PROJECT_DIR)/build/$(CONFIGURATION)";
                                DEAD_CODE_STRIPPING = YES;
                                CLANG_WARN_SUSPICIOUS_MOVE = YES;
                                CLANG_WARN_UNREACHABLE_CODE = YES;
                                CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
+                               CODE_SIGN_IDENTITY = "";
                                DEBUG_INFORMATION_FORMAT = dwarf;
                                ENABLE_STRICT_OBJC_MSGSEND = YES;
                                ENABLE_TESTABILITY = YES;
                                CLANG_WARN_SUSPICIOUS_MOVE = YES;
                                CLANG_WARN_UNREACHABLE_CODE = YES;
                                CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
+                               CODE_SIGN_IDENTITY = "";
                                DEBUG_INFORMATION_FORMAT = dwarf;
                                ENABLE_STRICT_OBJC_MSGSEND = YES;
                                GCC_C_LANGUAGE_STANDARD = c11;
diff --git a/extras/AudioPluginHost/Builds/iOS/AudioPluginHost.entitlements b/extras/AudioPluginHost/Builds/iOS/AudioPluginHost.entitlements
new file mode 100644 (file)
index 0000000..6631ffa
--- /dev/null
@@ -0,0 +1,6 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
+<plist version="1.0">
+<dict>
+</dict>
+</plist>
index b754683976d785b39a7090246296412803be7c72..56ef09ea9d5c918391d1ae3e3539125337cab8ee 100644 (file)
                        path = System/Library/Frameworks/CoreAudioKit.framework;
                        sourceTree = SDKROOT;
                };
+               EC252E34CF52A70B4A836BDC = {
+                       isa = PBXFileReference;
+                       lastKnownFileType = text.plist.xml;
+                       name = AudioPluginHost.entitlements;
+                       path = AudioPluginHost.entitlements;
+                       sourceTree = "SOURCE_ROOT";
+               };
                F14CDB17EFE157DA3C3A5A91 = {
                        isa = PBXFileReference;
                        lastKnownFileType = sourcecode.c.h;
                C8B793AC1BEFBE7A99BE8352 = {
                        isa = XCBuildConfiguration;
                        buildSettings = {
+                               "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "";
                                ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
-                               ASSETCATALOG_COMPILER_LAUNCHIMAGE_NAME = LaunchImage;
                                CLANG_CXX_LANGUAGE_STANDARD = "c++14";
                                CLANG_CXX_LIBRARY = "libc++";
                                CLANG_LINK_OBJC_RUNTIME = NO;
                49453CC5AD9F08D2738464AC = {
                        isa = XCBuildConfiguration;
                        buildSettings = {
+                               "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "";
                                ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
-                               ASSETCATALOG_COMPILER_LAUNCHIMAGE_NAME = LaunchImage;
                                CLANG_CXX_LANGUAGE_STANDARD = "c++14";
                                CLANG_CXX_LIBRARY = "libc++";
                                CLANG_LINK_OBJC_RUNTIME = NO;
                8D1CA827F1EFD443BDCF198A = {
                        isa = XCBuildConfiguration;
                        buildSettings = {
-                               "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "iPhone Developer";
+                               "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "";
                                ALWAYS_SEARCH_USER_PATHS = NO;
                                CLANG_ENABLE_OBJC_WEAK = YES;
                                CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
                C9295196717FABE454A210B7 = {
                        isa = XCBuildConfiguration;
                        buildSettings = {
-                               "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "iPhone Developer";
+                               "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "";
                                ALWAYS_SEARCH_USER_PATHS = NO;
                                CLANG_ENABLE_OBJC_WEAK = YES;
                                CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
index f2c41a734b53834af0d42fba2ba45c6fd6299eed..0a43cec5aa57c4880f00a21352c1458bf0c8e0f4 100644 (file)
@@ -49,6 +49,8 @@
 \r
 #define JUCE_USE_DARK_SPLASH_SCREEN 1\r
 \r
+#define JUCE_PROJUCER_VERSION 0x50405\r
+\r
 //==============================================================================\r
 #define JUCE_MODULE_AVAILABLE_juce_audio_basics          1\r
 #define JUCE_MODULE_AVAILABLE_juce_audio_devices         1\r
index 01d36b3b84f771af08c6dc108333c9d28c34c0e4..5b63c7a0c80c449edeadff1b9047c974ac46f2b5 100644 (file)
 \r
 #include "BinaryData.h"\r
 \r
+#if defined (JUCE_PROJUCER_VERSION) && JUCE_PROJUCER_VERSION < JUCE_VERSION\r
+ /** If you've hit this error then the version of the Projucer that was used to generate this project is\r
+     older than the version of the JUCE modules being included. To fix this error, re-save your project\r
+     using the latest version of the Projucer or, if you aren't using the Projucer to manage your project,\r
+     remove the JUCE_PROJUCER_VERSION define from the AppConfig.h file.\r
+ */\r
+ #error "This project was last saved using an outdated version of the Projucer! Re-save this project with the latest version to fix this error."\r
+#endif\r
+\r
 #if ! DONT_SET_USING_JUCE_NAMESPACE\r
  // If your code uses a lot of JUCE classes, then this will obviously save you\r
  // a lot of typing, but can be disabled by setting DONT_SET_USING_JUCE_NAMESPACE.\r
index 49d8e52e6854931bf6bc44566f6660e02378b337..e45009acaac099cd22f3737afe2afdd7bd247cbe 100644 (file)
@@ -126,10 +126,12 @@ public:
             JUCEApplicationBase::quit();\r
     }\r
 \r
-    void backButtonPressed() override\r
+    bool backButtonPressed() override\r
     {\r
         if (mainWindow->graphHolder != nullptr)\r
             mainWindow->graphHolder->hideLastSidePanel();\r
+\r
+        return true;\r
     }\r
 \r
     const String getApplicationName() override       { return "Juce Plug-In Host"; }\r
index 0eeb43cdd5d117f11ed4821c158adfa09d167d16..082911e504b0d4edd3a47a1b307ce8e4b41a7e96 100644 (file)
@@ -325,9 +325,13 @@ static XmlElement* createNodeXml (AudioProcessorGraph::Node* const node) noexcep
     if (auto* plugin = dynamic_cast<AudioPluginInstance*> (node->getProcessor()))\r
     {\r
         auto e = new XmlElement ("FILTER");\r
-        e->setAttribute ("uid", (int) node->nodeID.uid);\r
-        e->setAttribute ("x", node->properties ["x"].toString());\r
-        e->setAttribute ("y", node->properties ["y"].toString());\r
+\r
+        e->setAttribute ("uid",      (int) node->nodeID.uid);\r
+        e->setAttribute ("x",        node->properties ["x"].toString());\r
+        e->setAttribute ("y",        node->properties ["y"].toString());\r
+       #if JUCE_WINDOWS && JUCE_WIN_PER_MONITOR_DPI_AWARE\r
+        e->setAttribute ("DPIAware", node->properties["DPIAware"].toString());\r
+       #endif\r
 \r
         for (int i = 0; i < (int) PluginWindow::Type::numTypes; ++i)\r
         {\r
@@ -401,8 +405,11 @@ void PluginGraph::createNodeFromXml (const XmlElement& xml)
                 node->getProcessor()->setStateInformation (m.getData(), (int) m.getSize());\r
             }\r
 \r
-            node->properties.set ("x", xml.getDoubleAttribute ("x"));\r
-            node->properties.set ("y", xml.getDoubleAttribute ("y"));\r
+            node->properties.set ("x",        xml.getDoubleAttribute ("x"));\r
+            node->properties.set ("y",        xml.getDoubleAttribute ("y"));\r
+           #if JUCE_WINDOWS && JUCE_WIN_PER_MONITOR_DPI_AWARE\r
+            node->properties.set ("DPIAware", xml.getDoubleAttribute ("DPIAware"));\r
+           #endif\r
 \r
             for (int i = 0; i < (int) PluginWindow::Type::numTypes; ++i)\r
             {\r
index bea2b67bb62e25b57e056c313d53cd9e0eb1f369..a74497f6d9fb3c11f53a398b7ac0547b50be1d03 100644 (file)
@@ -442,12 +442,14 @@ struct GraphEditorPanel::PluginComponent   : public Component,
             case 10:  showWindow (PluginWindow::Type::normal); break;\r
             case 11:  showWindow (PluginWindow::Type::programs); break;\r
             case 12:  showWindow (PluginWindow::Type::generic)  ; break;\r
+           #if JUCE_WINDOWS && JUCE_WIN_PER_MONITOR_DPI_AWARE\r
             case 13:\r
             {\r
                 if (auto* node = graph.graph.getNodeForId (pluginID))\r
                     node->properties.set ("DPIAware", ! node->properties ["DPIAware"]);\r
                 break;\r
             }\r
+           #endif\r
             case 14:  showWindow (PluginWindow::Type::debug); break;\r
             case 20:  showWindow (PluginWindow::Type::audioIO); break;\r
             case 21:  testStateSaveLoad(); break;\r
index 5efa1e0475000494e3695fed8d68c191b49acdb3..8c13340bb789e06d89e38a84281ff9e6e0d10046 100644 (file)
@@ -1,7 +1,7 @@
 <?xml version="1.0" encoding="UTF-8"?>\r
 \r
 <JUCERPROJECT id="3t6YqETY1" name="BinaryBuilder" projectType="consoleapp"\r
-              juceFolder="../../../juce" jucerVersion="5.4.4" bundleIdentifier="com.roli.binarybuilder"\r
+              juceFolder="../../../juce" jucerVersion="5.4.5" bundleIdentifier="com.roli.binarybuilder"\r
               displaySplashScreen="0" reportAppUsage="0" companyName="ROLI Ltd."\r
               companyCopyright="ROLI Ltd.">\r
   <EXPORTFORMATS>\r
diff --git a/extras/BinaryBuilder/Builds/MacOSX/BinaryBuilder.entitlements b/extras/BinaryBuilder/Builds/MacOSX/BinaryBuilder.entitlements
new file mode 100644 (file)
index 0000000..6631ffa
--- /dev/null
@@ -0,0 +1,6 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
+<plist version="1.0">
+<dict>
+</dict>
+</plist>
index a6b08ca81ad480aefe1892dd7ecfa2ca49411e18..479760bf0db531b27ca53e9cf503c60e8b0eff95 100644 (file)
                        path = RecentFilesMenuTemplate.nib;
                        sourceTree = "SOURCE_ROOT";
                };
+               25C3A81567A43C28D8A9C143 = {
+                       isa = PBXFileReference;
+                       lastKnownFileType = text.plist.xml;
+                       name = BinaryBuilder.entitlements;
+                       path = BinaryBuilder.entitlements;
+                       sourceTree = "SOURCE_ROOT";
+               };
                50B7C64414A3E778021F5EC4 = {
                        isa = PBXFileReference;
                        lastKnownFileType = sourcecode.cpp.cpp;
                                CLANG_CXX_LANGUAGE_STANDARD = "c++14";
                                CLANG_CXX_LIBRARY = "libc++";
                                CLANG_LINK_OBJC_RUNTIME = NO;
+                               CODE_SIGN_IDENTITY = "";
                                COMBINE_HIDPI_IMAGES = YES;
                                CONFIGURATION_BUILD_DIR = "$(PROJECT_DIR)/build/$(CONFIGURATION)";
                                COPY_PHASE_STRIP = NO;
                                CLANG_CXX_LANGUAGE_STANDARD = "c++14";
                                CLANG_CXX_LIBRARY = "libc++";
                                CLANG_LINK_OBJC_RUNTIME = NO;
+                               CODE_SIGN_IDENTITY = "";
                                COMBINE_HIDPI_IMAGES = YES;
                                CONFIGURATION_BUILD_DIR = "$(PROJECT_DIR)/build/$(CONFIGURATION)";
                                DEAD_CODE_STRIPPING = YES;
                                CLANG_WARN_SUSPICIOUS_MOVE = YES;
                                CLANG_WARN_UNREACHABLE_CODE = YES;
                                CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
+                               CODE_SIGN_IDENTITY = "";
                                DEBUG_INFORMATION_FORMAT = dwarf;
                                ENABLE_STRICT_OBJC_MSGSEND = YES;
                                ENABLE_TESTABILITY = YES;
                                CLANG_WARN_SUSPICIOUS_MOVE = YES;
                                CLANG_WARN_UNREACHABLE_CODE = YES;
                                CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
+                               CODE_SIGN_IDENTITY = "";
                                DEBUG_INFORMATION_FORMAT = dwarf;
                                ENABLE_STRICT_OBJC_MSGSEND = YES;
                                GCC_C_LANGUAGE_STANDARD = c11;
index 163583165ca95042571ca3bdc42366736627965e..ee326c0319db59d9d2a0a109d0ab02c58206f2d8 100644 (file)
@@ -47,6 +47,8 @@
 \r
 #define JUCE_USE_DARK_SPLASH_SCREEN 1\r
 \r
+#define JUCE_PROJUCER_VERSION 0x50405\r
+\r
 //==============================================================================\r
 #define JUCE_MODULE_AVAILABLE_juce_core      1\r
 \r
index ce4d6d90ccf293bc08bfaefd6d7a9b2c2e496489..990925e65a7e7a8f9d665a653a033b42e63293e3 100644 (file)
 #include <juce_core/juce_core.h>\r
 \r
 \r
+#if defined (JUCE_PROJUCER_VERSION) && JUCE_PROJUCER_VERSION < JUCE_VERSION\r
+ /** If you've hit this error then the version of the Projucer that was used to generate this project is\r
+     older than the version of the JUCE modules being included. To fix this error, re-save your project\r
+     using the latest version of the Projucer or, if you aren't using the Projucer to manage your project,\r
+     remove the JUCE_PROJUCER_VERSION define from the AppConfig.h file.\r
+ */\r
+ #error "This project was last saved using an outdated version of the Projucer! Re-save this project with the latest version to fix this error."\r
+#endif\r
+\r
 #if ! DONT_SET_USING_JUCE_NAMESPACE\r
  // If your code uses a lot of JUCE classes, then this will obviously save you\r
  // a lot of typing, but can be disabled by setting DONT_SET_USING_JUCE_NAMESPACE.\r
diff --git a/extras/NetworkGraphicsDemo/Builds/MacOSX/NetworkGraphicsDemo.entitlements b/extras/NetworkGraphicsDemo/Builds/MacOSX/NetworkGraphicsDemo.entitlements
new file mode 100644 (file)
index 0000000..6631ffa
--- /dev/null
@@ -0,0 +1,6 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
+<plist version="1.0">
+<dict>
+</dict>
+</plist>
index bf306b31c1e6e93243511ac69aa400ac3c7e34f9..8d4427ba549d50c43952b4ba974e0aa09fb565e6 100644 (file)
                        path = ../../Source/SharedCanvas.h;
                        sourceTree = "SOURCE_ROOT";
                };
+               280A781618BDE3AF9BE15495 = {
+                       isa = PBXFileReference;
+                       lastKnownFileType = text.plist.xml;
+                       name = NetworkGraphicsDemo.entitlements;
+                       path = NetworkGraphicsDemo.entitlements;
+                       sourceTree = "SOURCE_ROOT";
+               };
                2E13A899F4E3C99054A3656F = {
                        isa = PBXFileReference;
                        lastKnownFileType = wrapper.framework;
                                CLANG_CXX_LANGUAGE_STANDARD = "c++14";
                                CLANG_CXX_LIBRARY = "libc++";
                                CLANG_LINK_OBJC_RUNTIME = NO;
+                               CODE_SIGN_IDENTITY = "";
                                COMBINE_HIDPI_IMAGES = YES;
                                CONFIGURATION_BUILD_DIR = "$(PROJECT_DIR)/build/$(CONFIGURATION)";
                                COPY_PHASE_STRIP = NO;
                                CLANG_CXX_LANGUAGE_STANDARD = "c++14";
                                CLANG_CXX_LIBRARY = "libc++";
                                CLANG_LINK_OBJC_RUNTIME = NO;
+                               CODE_SIGN_IDENTITY = "";
                                COMBINE_HIDPI_IMAGES = YES;
                                CONFIGURATION_BUILD_DIR = "$(PROJECT_DIR)/build/$(CONFIGURATION)";
                                DEAD_CODE_STRIPPING = YES;
                                CLANG_WARN_SUSPICIOUS_MOVE = YES;
                                CLANG_WARN_UNREACHABLE_CODE = YES;
                                CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
+                               CODE_SIGN_IDENTITY = "";
                                DEBUG_INFORMATION_FORMAT = dwarf;
                                ENABLE_STRICT_OBJC_MSGSEND = YES;
                                ENABLE_TESTABILITY = YES;
                                CLANG_WARN_SUSPICIOUS_MOVE = YES;
                                CLANG_WARN_UNREACHABLE_CODE = YES;
                                CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
+                               CODE_SIGN_IDENTITY = "";
                                DEBUG_INFORMATION_FORMAT = dwarf;
                                ENABLE_STRICT_OBJC_MSGSEND = YES;
                                GCC_C_LANGUAGE_STANDARD = c11;
diff --git a/extras/NetworkGraphicsDemo/Builds/iOS/NetworkGraphicsDemo.entitlements b/extras/NetworkGraphicsDemo/Builds/iOS/NetworkGraphicsDemo.entitlements
new file mode 100644 (file)
index 0000000..6631ffa
--- /dev/null
@@ -0,0 +1,6 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
+<plist version="1.0">
+<dict>
+</dict>
+</plist>
index e1c662c3d3df723eb31ba07689e5d2dadb2d92fa..00987e47fdcfd1947535c926f41d8871d7a62ffc 100644 (file)
                        path = ../../Source/SharedCanvas.h;
                        sourceTree = "SOURCE_ROOT";
                };
+               280A781618BDE3AF9BE15495 = {
+                       isa = PBXFileReference;
+                       lastKnownFileType = text.plist.xml;
+                       name = NetworkGraphicsDemo.entitlements;
+                       path = NetworkGraphicsDemo.entitlements;
+                       sourceTree = "SOURCE_ROOT";
+               };
                2E13A899F4E3C99054A3656F = {
                        isa = PBXFileReference;
                        lastKnownFileType = wrapper.framework;
                EE7498599191DDC73ECB55B0 = {
                        isa = XCBuildConfiguration;
                        buildSettings = {
+                               "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "";
                                ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
-                               ASSETCATALOG_COMPILER_LAUNCHIMAGE_NAME = LaunchImage;
                                CLANG_CXX_LANGUAGE_STANDARD = "c++14";
                                CLANG_CXX_LIBRARY = "libc++";
                                CLANG_LINK_OBJC_RUNTIME = NO;
                2E06386CE7CCA5FF76819BFF = {
                        isa = XCBuildConfiguration;
                        buildSettings = {
+                               "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "";
                                ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
-                               ASSETCATALOG_COMPILER_LAUNCHIMAGE_NAME = LaunchImage;
                                CLANG_CXX_LANGUAGE_STANDARD = "c++14";
                                CLANG_CXX_LIBRARY = "libc++";
                                CLANG_LINK_OBJC_RUNTIME = NO;
                3BF0365A560ACD4FD24D40CE = {
                        isa = XCBuildConfiguration;
                        buildSettings = {
-                               "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "iPhone Developer";
+                               "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "";
                                ALWAYS_SEARCH_USER_PATHS = NO;
                                CLANG_ENABLE_OBJC_WEAK = YES;
                                CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
                9C6D2FD441D79104734762A5 = {
                        isa = XCBuildConfiguration;
                        buildSettings = {
-                               "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "iPhone Developer";
+                               "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "";
                                ALWAYS_SEARCH_USER_PATHS = NO;
                                CLANG_ENABLE_OBJC_WEAK = YES;
                                CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
index 22f64728ca45abbee431c7d6605470db46c42983..f0cdeab24baee0aec1a147fb049f3ad81e44374d 100644 (file)
@@ -47,6 +47,8 @@
 \r
 #define JUCE_USE_DARK_SPLASH_SCREEN 1\r
 \r
+#define JUCE_PROJUCER_VERSION 0x50405\r
+\r
 //==============================================================================\r
 #define JUCE_MODULE_AVAILABLE_juce_audio_basics          1\r
 #define JUCE_MODULE_AVAILABLE_juce_audio_devices         1\r
index b72437d24d6e0ffc439102f846cc411130d5cda8..e7443e5872db29d97772614c7e51c1d446c0b802 100644 (file)
 \r
 #include "BinaryData.h"\r
 \r
+#if defined (JUCE_PROJUCER_VERSION) && JUCE_PROJUCER_VERSION < JUCE_VERSION\r
+ /** If you've hit this error then the version of the Projucer that was used to generate this project is\r
+     older than the version of the JUCE modules being included. To fix this error, re-save your project\r
+     using the latest version of the Projucer or, if you aren't using the Projucer to manage your project,\r
+     remove the JUCE_PROJUCER_VERSION define from the AppConfig.h file.\r
+ */\r
+ #error "This project was last saved using an outdated version of the Projucer! Re-save this project with the latest version to fix this error."\r
+#endif\r
+\r
 #if ! DONT_SET_USING_JUCE_NAMESPACE\r
  // If your code uses a lot of JUCE classes, then this will obviously save you\r
  // a lot of typing, but can be disabled by setting DONT_SET_USING_JUCE_NAMESPACE.\r
index f8843645e1a52f2c1dcf9e61b3d928a34c15de6e..79a87de7c5b2368e85f477cbade1636b54dbdfe1 100644 (file)
@@ -1,7 +1,7 @@
 <?xml version="1.0" encoding="UTF-8"?>\r
 \r
 <JUCERPROJECT id="gWI5Ir" name="NetworkGraphicsDemo" projectType="guiapp" bundleIdentifier="com.juce.NetworkGraphicsDemo"\r
-              jucerVersion="5.4.4" displaySplashScreen="0" reportAppUsage="0"\r
+              jucerVersion="5.4.5" displaySplashScreen="0" reportAppUsage="0"\r
               companyName="ROLI Ltd." companyCopyright="ROLI Ltd.">\r
   <MAINGROUP id="OT9rJ2" name="NetworkGraphicsDemo">\r
     <GROUP id="{48D54E6E-37F4-B20A-E038-C63E4EDFD4D9}" name="Source">\r
index ccf330cba686e4a3eae18152811f8ec23e0610a1..25b490460d4b136f97d80a308f910690fd354ba9 100644 (file)
@@ -35,7 +35,7 @@ ifeq ($(CONFIG),Debug)
     TARGET_ARCH := -march=native
   endif
 
-  JUCE_CPPFLAGS := $(DEPFLAGS) -DLINUX=1 -DDEBUG=1 -D_DEBUG=1 -DJUCER_LINUX_MAKE_6D53C8B4=1 -DJUCE_APP_VERSION=5.4.4 -DJUCE_APP_VERSION_HEX=0x50404 $(shell pkg-config --cflags x11 xinerama xext freetype2 webkit2gtk-4.0 gtk+-x11-3.0) -pthread -I../../JuceLibraryCode -I../../../../modules $(CPPFLAGS)
+  JUCE_CPPFLAGS := $(DEPFLAGS) -DLINUX=1 -DDEBUG=1 -D_DEBUG=1 -DJUCER_LINUX_MAKE_6D53C8B4=1 -DJUCE_APP_VERSION=5.4.5 -DJUCE_APP_VERSION_HEX=0x50405 $(shell pkg-config --cflags x11 xinerama xext freetype2 webkit2gtk-4.0 gtk+-x11-3.0) -pthread -I../../JuceLibraryCode -I../../../../modules $(CPPFLAGS)
   JUCE_CPPFLAGS_APP := -DJucePlugin_Build_VST=0 -DJucePlugin_Build_VST3=0 -DJucePlugin_Build_AU=0 -DJucePlugin_Build_AUv3=0 -DJucePlugin_Build_RTAS=0 -DJucePlugin_Build_AAX=0 -DJucePlugin_Build_Standalone=0 -DJucePlugin_Build_Unity=0
   JUCE_TARGET_APP := Projucer
 
@@ -56,7 +56,7 @@ ifeq ($(CONFIG),Release)
     TARGET_ARCH := -march=native
   endif
 
-  JUCE_CPPFLAGS := $(DEPFLAGS) -DLINUX=1 -DNDEBUG=1 -DJUCER_LINUX_MAKE_6D53C8B4=1 -DJUCE_APP_VERSION=5.4.4 -DJUCE_APP_VERSION_HEX=0x50404 $(shell pkg-config --cflags x11 xinerama xext freetype2 webkit2gtk-4.0 gtk+-x11-3.0) -pthread -I../../JuceLibraryCode -I../../../../modules $(CPPFLAGS)
+  JUCE_CPPFLAGS := $(DEPFLAGS) -DLINUX=1 -DNDEBUG=1 -DJUCER_LINUX_MAKE_6D53C8B4=1 -DJUCE_APP_VERSION=5.4.5 -DJUCE_APP_VERSION_HEX=0x50405 $(shell pkg-config --cflags x11 xinerama xext freetype2 webkit2gtk-4.0 gtk+-x11-3.0) -pthread -I../../JuceLibraryCode -I../../../../modules $(CPPFLAGS)
   JUCE_CPPFLAGS_APP := -DJucePlugin_Build_VST=0 -DJucePlugin_Build_VST3=0 -DJucePlugin_Build_AU=0 -DJucePlugin_Build_AUv3=0 -DJucePlugin_Build_RTAS=0 -DJucePlugin_Build_AAX=0 -DJucePlugin_Build_Standalone=0 -DJucePlugin_Build_Unity=0
   JUCE_TARGET_APP := Projucer
 
index 00eb365fc3c2f8a4b994520927aed4c4984a0efb..c221483427aa4c830132fe82365fb364d639a3f6 100644 (file)
         </dict>\r
       </dict>\r
     </dict>\r
+    <key>NSMicrophoneUsageDescription</key>\r
+    <string>This app requires audio input. If you do not have an audio interface connected it will use the built-in microphone.</string>\r
+    <key>NSCameraUsageDescription</key>\r
+    <string>This app requires access to the camera to function correctly.</string>\r
     <key>CFBundleExecutable</key>\r
     <string>${EXECUTABLE_NAME}</string>\r
     <key>CFBundleIconFile</key>\r
@@ -33,9 +37,9 @@
     <key>CFBundleSignature</key>\r
     <string>????</string>\r
     <key>CFBundleShortVersionString</key>\r
-    <string>5.4.4</string>\r
+    <string>5.4.5</string>\r
     <key>CFBundleVersion</key>\r
-    <string>5.4.4</string>\r
+    <string>5.4.5</string>\r
     <key>NSHumanReadableCopyright</key>\r
     <string>ROLI Ltd.</string>\r
     <key>NSHighResolutionCapable</key>\r
diff --git a/extras/Projucer/Builds/MacOSX/Projucer.entitlements b/extras/Projucer/Builds/MacOSX/Projucer.entitlements
new file mode 100644 (file)
index 0000000..6631ffa
--- /dev/null
@@ -0,0 +1,6 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
+<plist version="1.0">
+<dict>
+</dict>
+</plist>
index e5af3062ac0fb0cae3ec81def4623d0f81522ef7..6db9d9057c4232ccc7a46f731ea5a0d08a523e30 100644 (file)
                        path = "../../../../modules/juce_graphics";
                        sourceTree = "SOURCE_ROOT";
                };
+               B7017BD3427B46FBAAAE448A = {
+                       isa = PBXFileReference;
+                       lastKnownFileType = text.plist.xml;
+                       name = Projucer.entitlements;
+                       path = Projucer.entitlements;
+                       sourceTree = "SOURCE_ROOT";
+               };
                B8385E9A644BD3CD94876448 = {
                        isa = PBXFileReference;
                        lastKnownFileType = sourcecode.c.h;
                                CLANG_CXX_LANGUAGE_STANDARD = "c++11";
                                CLANG_CXX_LIBRARY = "libc++";
                                CLANG_LINK_OBJC_RUNTIME = NO;
+                               CODE_SIGN_IDENTITY = "";
                                COMBINE_HIDPI_IMAGES = YES;
                                CONFIGURATION_BUILD_DIR = "$(PROJECT_DIR)/build/$(CONFIGURATION)";
                                COPY_PHASE_STRIP = NO;
                                        "_DEBUG=1",
                                        "DEBUG=1",
                                        "JUCER_XCODE_MAC_F6D2F4CF=1",
-                                       "JUCE_APP_VERSION=5.4.4",
-                                       "JUCE_APP_VERSION_HEX=0x50404",
+                                       "JUCE_APP_VERSION=5.4.5",
+                                       "JUCE_APP_VERSION_HEX=0x50405",
                                        "JucePlugin_Build_VST=0",
                                        "JucePlugin_Build_VST3=0",
                                        "JucePlugin_Build_AU=0",
                                CLANG_CXX_LANGUAGE_STANDARD = "c++11";
                                CLANG_CXX_LIBRARY = "libc++";
                                CLANG_LINK_OBJC_RUNTIME = NO;
+                               CODE_SIGN_IDENTITY = "";
                                COMBINE_HIDPI_IMAGES = YES;
                                CONFIGURATION_BUILD_DIR = "$(PROJECT_DIR)/build/$(CONFIGURATION)";
                                DEAD_CODE_STRIPPING = YES;
                                        "_NDEBUG=1",
                                        "NDEBUG=1",
                                        "JUCER_XCODE_MAC_F6D2F4CF=1",
-                                       "JUCE_APP_VERSION=5.4.4",
-                                       "JUCE_APP_VERSION_HEX=0x50404",
+                                       "JUCE_APP_VERSION=5.4.5",
+                                       "JUCE_APP_VERSION_HEX=0x50405",
                                        "JucePlugin_Build_VST=0",
                                        "JucePlugin_Build_VST3=0",
                                        "JucePlugin_Build_AU=0",
                                CLANG_WARN_SUSPICIOUS_MOVE = YES;
                                CLANG_WARN_UNREACHABLE_CODE = YES;
                                CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
+                               CODE_SIGN_IDENTITY = "";
                                DEBUG_INFORMATION_FORMAT = dwarf;
                                ENABLE_STRICT_OBJC_MSGSEND = YES;
                                ENABLE_TESTABILITY = YES;
                                CLANG_WARN_SUSPICIOUS_MOVE = YES;
                                CLANG_WARN_UNREACHABLE_CODE = YES;
                                CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
+                               CODE_SIGN_IDENTITY = "";
                                DEBUG_INFORMATION_FORMAT = dwarf;
                                ENABLE_STRICT_OBJC_MSGSEND = YES;
                                GCC_C_LANGUAGE_STANDARD = c11;
index 6405421d64d9d78f11ecabe938e8abff22055061..a025ed0944177d7cb875ab568d87c4f7775a3b5f 100644 (file)
@@ -64,7 +64,7 @@
       <Optimization>Disabled</Optimization>\r
       <DebugInformationFormat>ProgramDatabase</DebugInformationFormat>\r
       <AdditionalIncludeDirectories>..\..\JuceLibraryCode;..\..\..\..\modules;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>\r
-      <PreprocessorDefinitions>_CRT_SECURE_NO_WARNINGS;WIN32;_WINDOWS;DEBUG;_DEBUG;JUCER_VS2015_78A5022=1;JUCE_APP_VERSION=5.4.4;JUCE_APP_VERSION_HEX=0x50404;JucePlugin_Build_VST=0;JucePlugin_Build_VST3=0;JucePlugin_Build_AU=0;JucePlugin_Build_AUv3=0;JucePlugin_Build_RTAS=0;JucePlugin_Build_AAX=0;JucePlugin_Build_Standalone=0;JucePlugin_Build_Unity=0;%(PreprocessorDefinitions)</PreprocessorDefinitions>\r
+      <PreprocessorDefinitions>_CRT_SECURE_NO_WARNINGS;WIN32;_WINDOWS;DEBUG;_DEBUG;JUCER_VS2015_78A5022=1;JUCE_APP_VERSION=5.4.5;JUCE_APP_VERSION_HEX=0x50405;JucePlugin_Build_VST=0;JucePlugin_Build_VST3=0;JucePlugin_Build_AU=0;JucePlugin_Build_AUv3=0;JucePlugin_Build_RTAS=0;JucePlugin_Build_AAX=0;JucePlugin_Build_Standalone=0;JucePlugin_Build_Unity=0;%(PreprocessorDefinitions)</PreprocessorDefinitions>\r
       <RuntimeLibrary>MultiThreadedDebugDLL</RuntimeLibrary>\r
       <RuntimeTypeInfo>true</RuntimeTypeInfo>\r
       <PrecompiledHeader/>\r
     <ClCompile>\r
       <Optimization>Full</Optimization>\r
       <AdditionalIncludeDirectories>..\..\JuceLibraryCode;..\..\..\..\modules;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>\r
-      <PreprocessorDefinitions>_CRT_SECURE_NO_WARNINGS;WIN32;_WINDOWS;NDEBUG;JUCER_VS2015_78A5022=1;JUCE_APP_VERSION=5.4.4;JUCE_APP_VERSION_HEX=0x50404;JucePlugin_Build_VST=0;JucePlugin_Build_VST3=0;JucePlugin_Build_AU=0;JucePlugin_Build_AUv3=0;JucePlugin_Build_RTAS=0;JucePlugin_Build_AAX=0;JucePlugin_Build_Standalone=0;JucePlugin_Build_Unity=0;%(PreprocessorDefinitions)</PreprocessorDefinitions>\r
+      <PreprocessorDefinitions>_CRT_SECURE_NO_WARNINGS;WIN32;_WINDOWS;NDEBUG;JUCER_VS2015_78A5022=1;JUCE_APP_VERSION=5.4.5;JUCE_APP_VERSION_HEX=0x50405;JucePlugin_Build_VST=0;JucePlugin_Build_VST3=0;JucePlugin_Build_AU=0;JucePlugin_Build_AUv3=0;JucePlugin_Build_RTAS=0;JucePlugin_Build_AAX=0;JucePlugin_Build_Standalone=0;JucePlugin_Build_Unity=0;%(PreprocessorDefinitions)</PreprocessorDefinitions>\r
       <RuntimeLibrary>MultiThreaded</RuntimeLibrary>\r
       <RuntimeTypeInfo>true</RuntimeTypeInfo>\r
       <PrecompiledHeader/>\r
index 6ac9b991bd62ae583f45d5d482fe8c953b84fe6c..c41432352aa234636f672bedf2bf3c221d408859 100644 (file)
@@ -7,7 +7,7 @@
 #include <windows.h>\r
 \r
 VS_VERSION_INFO VERSIONINFO\r
-FILEVERSION  5,4,4,0\r
+FILEVERSION  5,4,5,0\r
 BEGIN\r
   BLOCK "StringFileInfo"\r
   BEGIN\r
@@ -16,9 +16,9 @@ BEGIN
       VALUE "CompanyName",  "ROLI Ltd.\0"\r
       VALUE "LegalCopyright",  "ROLI Ltd.\0"\r
       VALUE "FileDescription",  "Projucer\0"\r
-      VALUE "FileVersion",  "5.4.4\0"\r
+      VALUE "FileVersion",  "5.4.5\0"\r
       VALUE "ProductName",  "Projucer\0"\r
-      VALUE "ProductVersion",  "5.4.4\0"\r
+      VALUE "ProductVersion",  "5.4.5\0"\r
     END\r
   END\r
 \r
index 3e780f2f57abaddc50803be6790a2e01d5da2911..7c8751a7fb46df0fe8be8cb6bb2437f3e39524c0 100644 (file)
@@ -64,7 +64,7 @@
       <Optimization>Disabled</Optimization>\r
       <DebugInformationFormat>ProgramDatabase</DebugInformationFormat>\r
       <AdditionalIncludeDirectories>..\..\JuceLibraryCode;..\..\..\..\modules;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>\r
-      <PreprocessorDefinitions>_CRT_SECURE_NO_WARNINGS;WIN32;_WINDOWS;DEBUG;_DEBUG;JUCER_VS2017_78A5024=1;JUCE_APP_VERSION=5.4.4;JUCE_APP_VERSION_HEX=0x50404;JucePlugin_Build_VST=0;JucePlugin_Build_VST3=0;JucePlugin_Build_AU=0;JucePlugin_Build_AUv3=0;JucePlugin_Build_RTAS=0;JucePlugin_Build_AAX=0;JucePlugin_Build_Standalone=0;JucePlugin_Build_Unity=0;%(PreprocessorDefinitions)</PreprocessorDefinitions>\r
+      <PreprocessorDefinitions>_CRT_SECURE_NO_WARNINGS;WIN32;_WINDOWS;DEBUG;_DEBUG;JUCER_VS2017_78A5024=1;JUCE_APP_VERSION=5.4.5;JUCE_APP_VERSION_HEX=0x50405;JucePlugin_Build_VST=0;JucePlugin_Build_VST3=0;JucePlugin_Build_AU=0;JucePlugin_Build_AUv3=0;JucePlugin_Build_RTAS=0;JucePlugin_Build_AAX=0;JucePlugin_Build_Standalone=0;JucePlugin_Build_Unity=0;%(PreprocessorDefinitions)</PreprocessorDefinitions>\r
       <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>\r
       <RuntimeTypeInfo>true</RuntimeTypeInfo>\r
       <PrecompiledHeader/>\r
     <ClCompile>\r
       <Optimization>Full</Optimization>\r
       <AdditionalIncludeDirectories>..\..\JuceLibraryCode;..\..\..\..\modules;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>\r
-      <PreprocessorDefinitions>_CRT_SECURE_NO_WARNINGS;WIN32;_WINDOWS;NDEBUG;JUCER_VS2017_78A5024=1;JUCE_APP_VERSION=5.4.4;JUCE_APP_VERSION_HEX=0x50404;JucePlugin_Build_VST=0;JucePlugin_Build_VST3=0;JucePlugin_Build_AU=0;JucePlugin_Build_AUv3=0;JucePlugin_Build_RTAS=0;JucePlugin_Build_AAX=0;JucePlugin_Build_Standalone=0;JucePlugin_Build_Unity=0;%(PreprocessorDefinitions)</PreprocessorDefinitions>\r
+      <PreprocessorDefinitions>_CRT_SECURE_NO_WARNINGS;WIN32;_WINDOWS;NDEBUG;JUCER_VS2017_78A5024=1;JUCE_APP_VERSION=5.4.5;JUCE_APP_VERSION_HEX=0x50405;JucePlugin_Build_VST=0;JucePlugin_Build_VST3=0;JucePlugin_Build_AU=0;JucePlugin_Build_AUv3=0;JucePlugin_Build_RTAS=0;JucePlugin_Build_AAX=0;JucePlugin_Build_Standalone=0;JucePlugin_Build_Unity=0;%(PreprocessorDefinitions)</PreprocessorDefinitions>\r
       <RuntimeLibrary>MultiThreaded</RuntimeLibrary>\r
       <RuntimeTypeInfo>true</RuntimeTypeInfo>\r
       <PrecompiledHeader/>\r
index 6ac9b991bd62ae583f45d5d482fe8c953b84fe6c..c41432352aa234636f672bedf2bf3c221d408859 100644 (file)
@@ -7,7 +7,7 @@
 #include <windows.h>\r
 \r
 VS_VERSION_INFO VERSIONINFO\r
-FILEVERSION  5,4,4,0\r
+FILEVERSION  5,4,5,0\r
 BEGIN\r
   BLOCK "StringFileInfo"\r
   BEGIN\r
@@ -16,9 +16,9 @@ BEGIN
       VALUE "CompanyName",  "ROLI Ltd.\0"\r
       VALUE "LegalCopyright",  "ROLI Ltd.\0"\r
       VALUE "FileDescription",  "Projucer\0"\r
-      VALUE "FileVersion",  "5.4.4\0"\r
+      VALUE "FileVersion",  "5.4.5\0"\r
       VALUE "ProductName",  "Projucer\0"\r
-      VALUE "ProductVersion",  "5.4.4\0"\r
+      VALUE "ProductVersion",  "5.4.5\0"\r
     END\r
   END\r
 \r
index d13b3cde6bb2d1fd05572f7688b2fe1974cb6b26..0a28052e5811f24bc1fca93688007689bb731cff 100644 (file)
@@ -64,7 +64,7 @@
       <Optimization>Disabled</Optimization>\r
       <DebugInformationFormat>ProgramDatabase</DebugInformationFormat>\r
       <AdditionalIncludeDirectories>..\..\JuceLibraryCode;..\..\..\..\modules;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>\r
-      <PreprocessorDefinitions>_CRT_SECURE_NO_WARNINGS;WIN32;_WINDOWS;DEBUG;_DEBUG;JUCER_VS2019_78A5026=1;JUCE_APP_VERSION=5.4.4;JUCE_APP_VERSION_HEX=0x50404;JucePlugin_Build_VST=0;JucePlugin_Build_VST3=0;JucePlugin_Build_AU=0;JucePlugin_Build_AUv3=0;JucePlugin_Build_RTAS=0;JucePlugin_Build_AAX=0;JucePlugin_Build_Standalone=0;JucePlugin_Build_Unity=0;%(PreprocessorDefinitions)</PreprocessorDefinitions>\r
+      <PreprocessorDefinitions>_CRT_SECURE_NO_WARNINGS;WIN32;_WINDOWS;DEBUG;_DEBUG;JUCER_VS2019_78A5026=1;JUCE_APP_VERSION=5.4.5;JUCE_APP_VERSION_HEX=0x50405;JucePlugin_Build_VST=0;JucePlugin_Build_VST3=0;JucePlugin_Build_AU=0;JucePlugin_Build_AUv3=0;JucePlugin_Build_RTAS=0;JucePlugin_Build_AAX=0;JucePlugin_Build_Standalone=0;JucePlugin_Build_Unity=0;%(PreprocessorDefinitions)</PreprocessorDefinitions>\r
       <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>\r
       <RuntimeTypeInfo>true</RuntimeTypeInfo>\r
       <PrecompiledHeader/>\r
     <ClCompile>\r
       <Optimization>Full</Optimization>\r
       <AdditionalIncludeDirectories>..\..\JuceLibraryCode;..\..\..\..\modules;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>\r
-      <PreprocessorDefinitions>_CRT_SECURE_NO_WARNINGS;WIN32;_WINDOWS;NDEBUG;JUCER_VS2019_78A5026=1;JUCE_APP_VERSION=5.4.4;JUCE_APP_VERSION_HEX=0x50404;JucePlugin_Build_VST=0;JucePlugin_Build_VST3=0;JucePlugin_Build_AU=0;JucePlugin_Build_AUv3=0;JucePlugin_Build_RTAS=0;JucePlugin_Build_AAX=0;JucePlugin_Build_Standalone=0;JucePlugin_Build_Unity=0;%(PreprocessorDefinitions)</PreprocessorDefinitions>\r
+      <PreprocessorDefinitions>_CRT_SECURE_NO_WARNINGS;WIN32;_WINDOWS;NDEBUG;JUCER_VS2019_78A5026=1;JUCE_APP_VERSION=5.4.5;JUCE_APP_VERSION_HEX=0x50405;JucePlugin_Build_VST=0;JucePlugin_Build_VST3=0;JucePlugin_Build_AU=0;JucePlugin_Build_AUv3=0;JucePlugin_Build_RTAS=0;JucePlugin_Build_AAX=0;JucePlugin_Build_Standalone=0;JucePlugin_Build_Unity=0;%(PreprocessorDefinitions)</PreprocessorDefinitions>\r
       <RuntimeLibrary>MultiThreaded</RuntimeLibrary>\r
       <RuntimeTypeInfo>true</RuntimeTypeInfo>\r
       <PrecompiledHeader/>\r
index 6ac9b991bd62ae583f45d5d482fe8c953b84fe6c..c41432352aa234636f672bedf2bf3c221d408859 100644 (file)
@@ -7,7 +7,7 @@
 #include <windows.h>\r
 \r
 VS_VERSION_INFO VERSIONINFO\r
-FILEVERSION  5,4,4,0\r
+FILEVERSION  5,4,5,0\r
 BEGIN\r
   BLOCK "StringFileInfo"\r
   BEGIN\r
@@ -16,9 +16,9 @@ BEGIN
       VALUE "CompanyName",  "ROLI Ltd.\0"\r
       VALUE "LegalCopyright",  "ROLI Ltd.\0"\r
       VALUE "FileDescription",  "Projucer\0"\r
-      VALUE "FileVersion",  "5.4.4\0"\r
+      VALUE "FileVersion",  "5.4.5\0"\r
       VALUE "ProductName",  "Projucer\0"\r
-      VALUE "ProductVersion",  "5.4.4\0"\r
+      VALUE "ProductVersion",  "5.4.5\0"\r
     END\r
   END\r
 \r
index 3620ea15355970adadf2bc06a8cc225b0b0f2158..dffd5af7550e94b407c0657b379c451d176483a1 100644 (file)
@@ -66,6 +66,8 @@
 \r
 #define JUCE_USE_DARK_SPLASH_SCREEN 1\r
 \r
+#define JUCE_PROJUCER_VERSION 0x50405\r
+\r
 //==============================================================================\r
 #define JUCE_MODULE_AVAILABLE_juce_analytics            1\r
 #define JUCE_MODULE_AVAILABLE_juce_core                 1\r
index f3f49db042621d7c71578420857c133ce910e09b..765b42656df8c9ba4cd7cba64cf68ee751f328df 100644 (file)
 \r
 #include "BinaryData.h"\r
 \r
+#if defined (JUCE_PROJUCER_VERSION) && JUCE_PROJUCER_VERSION < JUCE_VERSION\r
+ /** If you've hit this error then the version of the Projucer that was used to generate this project is\r
+     older than the version of the JUCE modules being included. To fix this error, re-save your project\r
+     using the latest version of the Projucer or, if you aren't using the Projucer to manage your project,\r
+     remove the JUCE_PROJUCER_VERSION define from the AppConfig.h file.\r
+ */\r
+ #error "This project was last saved using an outdated version of the Projucer! Re-save this project with the latest version to fix this error."\r
+#endif\r
+\r
 #if ! DONT_SET_USING_JUCE_NAMESPACE\r
  // If your code uses a lot of JUCE classes, then this will obviously save you\r
  // a lot of typing, but can be disabled by setting DONT_SET_USING_JUCE_NAMESPACE.\r
@@ -36,7 +45,7 @@ namespace ProjectInfo
 {\r
     const char* const  projectName    = "Projucer";\r
     const char* const  companyName    = "ROLI Ltd.";\r
-    const char* const  versionString  = "5.4.4";\r
-    const int          versionNumber  = 0x50404;\r
+    const char* const  versionString  = "5.4.5";\r
+    const int          versionNumber  = 0x50405;\r
 }\r
 #endif\r
index 4f6b407791742bb501c07e950ec0cd0c2b0a0f39..6f4f708036e2bd33276a8047666dfcaeb0452a9e 100644 (file)
@@ -1,14 +1,15 @@
 <?xml version="1.0" encoding="UTF-8"?>\r
 \r
 <JUCERPROJECT id="M70qfTRRk" name="Projucer" projectType="guiapp" juceFolder="../../juce"\r
-              jucerVersion="5.4.4" version="5.4.4" bundleIdentifier="com.juce.theprojucer"\r
+              jucerVersion="5.4.5" version="5.4.5" bundleIdentifier="com.juce.theprojucer"\r
               splashScreenColour="Dark" displaySplashScreen="0" reportAppUsage="0"\r
               companyName="ROLI Ltd." companyCopyright="ROLI Ltd." cppLanguageStandard="11">\r
   <EXPORTFORMATS>\r
     <XCODE_MAC targetFolder="Builds/MacOSX" vstFolder="~/SDKs/vstsdk2.4" rtasFolder="~/SDKs/PT_80_SDK"\r
                documentExtensions=".jucer" objCExtraSuffix="zkVtji" bigIcon="rv1F4h"\r
                customPList="&lt;plist&gt;&#10;&lt;dict&gt;&#10;&#9;&lt;key&gt;NSAppTransportSecurity&lt;/key&gt;&#10;&#9;&lt;dict&gt;&#10;&#9;&#9;&lt;key&gt;NSAllowsArbitraryLoads&lt;/key&gt;&#10;&#9;&#9;&lt;true/&gt;&#10;&#9;&#9;&lt;key&gt;NSExceptionDomains&lt;/key&gt;&#10;&#9;&#9;&lt;dict&gt;&#10;&#9;&#9;&#9;&lt;key&gt;amazonaws.com&lt;/key&gt;&#10;&#9;&#9;&#9;&lt;dict&gt;&#10;&#9;&#9;&#9;&#9;&lt;key&gt;NSExceptionAllowsInsecureHTTPLoads&lt;/key&gt;&#10;&#9;&#9;&#9;&#9;&lt;true/&gt;&#10;&#9;&#9;&#9;&#9;&lt;key&gt;NSIncludesSubdomains&lt;/key&gt;&#10;&#9;&#9;&#9;&#9;&lt;true/&gt;&#10;&#9;&#9;&#9;&lt;/dict&gt;&#10;&#9;&#9;&lt;/dict&gt;&#10;&#9;&lt;/dict&gt;&#10;&lt;/dict&gt;&#10;&lt;/plist&gt;"\r
-               extraFrameworks="AudioUnit; Accelerate; AVFoundation; CoreAudio; CoreAudioKit; CoreMIDI; DiscRecording; QuartzCore; AudioToolbox; OpenGL; QTKit; QuickTime">\r
+               extraFrameworks="AudioUnit; Accelerate; AVFoundation; CoreAudio; CoreAudioKit; CoreMIDI; DiscRecording; QuartzCore; AudioToolbox; OpenGL; QTKit; QuickTime"\r
+               microphonePermissionNeeded="1" cameraPermissionNeeded="1">\r
       <CONFIGURATIONS>\r
         <CONFIGURATION name="Debug" isDebug="1" targetName="Projucer" cppLibType="libc++"\r
                        recommendedWarnings="LLVM"/>\r
index aa33c486c8ddaf8271031bfe985f57d97f1d9722..cdaae6cd7623013967c9b5c43f1773b332b3b03b 100644 (file)
@@ -81,19 +81,19 @@ public:
         auto leftSlice   = bounds.removeFromLeft (150);\r
         auto centreSlice = bounds;\r
 \r
-        //======================================================================\r
+        //==============================================================================\r
         rightSlice.removeFromRight (20);\r
         auto iconSlice = rightSlice.removeFromRight (100);\r
         huckleberryLogoBounds = iconSlice.removeFromBottom (100).toFloat();\r
 \r
-        //======================================================================\r
+        //==============================================================================\r
         juceLogoBounds = leftSlice.removeFromTop (150).toFloat();\r
         juceLogoBounds.setWidth (juceLogoBounds.getWidth() + 100);\r
         juceLogoBounds.setHeight (juceLogoBounds.getHeight() + 100);\r
 \r
         copyrightLabel.setBounds (leftSlice.removeFromBottom (20));\r
 \r
-        //======================================================================\r
+        //==============================================================================\r
         auto titleHeight = 40;\r
 \r
         centreSlice.removeFromTop ((centreSlice.getHeight() / 2) - (titleHeight / 2));\r
index 67f20243f4bc0d62a95259158b492a03dabc2f75..b1f8aef02b7b89deec20d1a96474f3d261ad0259 100644 (file)
@@ -510,7 +510,7 @@ void ProjucerApplication::createColourSchemeItems (PopupMenu& menu)
 \r
     menu.addSubMenu ("Colour Scheme", colourSchemeMenu);\r
 \r
-    //==========================================================================\r
+    //==============================================================================\r
     PopupMenu editorColourSchemeMenu;\r
 \r
     auto& appearanceSettings = getAppSettings().appearance;\r
@@ -625,7 +625,7 @@ void ProjucerApplication::createExamplesPopupMenu (PopupMenu& menu) noexcept
     }\r
 }\r
 \r
-//==========================================================================\r
+//==============================================================================\r
 static File getJUCEExamplesDirectoryPathFromGlobal()\r
 {\r
     auto globalPath = File::createFileWithoutCheckingPath (getAppSettings().getStoredPath (Ids::jucePath, TargetOS::getThisOS()).get().toString()\r
@@ -722,7 +722,7 @@ void ProjucerApplication::findAndLaunchExample (int selectedIndex)
     Analytics::getInstance()->logEvent ("Example Opened", data, ProjucerAnalyticsEvent::exampleEvent);\r
 }\r
 \r
-//==========================================================================\r
+//==============================================================================\r
 static String getPlatformSpecificFileExtension()\r
 {\r
    #if JUCE_MAC\r
@@ -940,7 +940,7 @@ void ProjucerApplication::launchDemoRunner()
     }\r
 }\r
 \r
-//==========================================================================\r
+//==============================================================================\r
 void ProjucerApplication::handleMainMenuCommand (int menuItemID)\r
 {\r
     if (menuItemID >= recentProjectsBaseID && menuItemID < (recentProjectsBaseID + 100))\r
index 0fa9313fd22cae84cf72ad1c3b185d971ac49c2c..5b6a4a4f513e366ac6fe2398789cad99c95be46a 100644 (file)
@@ -147,7 +147,7 @@ void PaintElementImage::fillInGeneratedCode (GeneratedCode& code, String& paintM
 \r
                 r << "    jassert (" << imageVariable << " != 0);\n"\r
                   << "    if (" << imageVariable << " != 0)\n"\r
-                  << "        " << imageVariable  << "->drawWithin (g, Rectangle<float> (x, y, width, height),\n"\r
+                  << "        " << imageVariable  << "->drawWithin (g, Rectangle<int> (x, y, width, height).toFloat(),\n"\r
                   << "    " << String::repeatedString (" ", imageVariable.length() + 18)\r
                   << (mode == stretched ? "RectanglePlacement::stretchToFit"\r
                                         : (mode == proportionalReducingOnly ? "RectanglePlacement::centred | RectanglePlacement::onlyReduceInSize"\r
index 33a4a326b8a633a91eb2ea94321a16c68af5bd31..4cc84f0281e46b859afc50d0739ef19c6ef83550 100644 (file)
@@ -368,7 +368,7 @@ private:
     Project& project;\r
     ValueTree exportersTree;\r
 \r
-    //==========================================================================\r
+    //==============================================================================\r
     void valueTreeChildAdded (ValueTree& parentTree, ValueTree&) override         { refreshIfNeeded (parentTree); }\r
     void valueTreeChildRemoved (ValueTree& parentTree, ValueTree&, int) override  { refreshIfNeeded (parentTree); }\r
     void valueTreeChildOrderChanged (ValueTree& parentTree, int, int) override    { refreshIfNeeded (parentTree); }\r
index 11b215e7e0d9f51d745e2ad977c97735e7095779..096c53f66af0c6ae5ff4ce9f11cdf177fb3d9f97 100644 (file)
@@ -172,7 +172,7 @@ private:
 \r
     Rectangle<int> textBounds;\r
 \r
-    //==========================================================================\r
+    //==============================================================================\r
     String getErrorMessage()\r
     {\r
         showDownloadButton = false;\r
index bcd061f94b27dcf6d010624423ac19f82840988e..dbeb8a1bff8926d8b1fa8c4a510be33e04ba1c56 100644 (file)
@@ -27,7 +27,7 @@
 #pragma once\r
 \r
 \r
-//==========================================================================\r
+//==============================================================================\r
 struct ProjectSettingsComponent  : public Component,\r
                                    private ChangeListener\r
 {\r
index 53b8a620e024d5967e3b303a123b7b6fc95da52e..193fe17d1c63ea7a46ad082b4b3d62d77f9a51e2 100644 (file)
@@ -35,7 +35,7 @@
 #include "../../LiveBuildEngine/jucer_DiagnosticMessage.h"\r
 #include "../../LiveBuildEngine/jucer_CompileEngineClient.h"\r
 \r
-//======================================================================\r
+//==============================================================================\r
 HeaderComponent::HeaderComponent()\r
 {\r
     addAndMakeVisible (configLabel);\r
@@ -66,13 +66,13 @@ HeaderComponent::~HeaderComponent()
     }\r
 }\r
 \r
-//======================================================================\r
+//==============================================================================\r
 void HeaderComponent::resized()\r
 {\r
     auto bounds = getLocalBounds();\r
     configLabel.setFont ({ bounds.getHeight() / 3.0f });\r
 \r
-    //======================================================================\r
+    //==============================================================================\r
     {\r
         auto headerBounds = bounds.removeFromLeft (tabsWidth);\r
 \r
@@ -87,7 +87,7 @@ void HeaderComponent::resized()
         projectNameLabel.setBounds (headerBounds);\r
     }\r
 \r
-    //======================================================================\r
+    //==============================================================================\r
     auto exporterWidth = jmin (400, bounds.getWidth() / 2);\r
     Rectangle<int> exporterBounds (0, 0, exporterWidth, bounds.getHeight());\r
 \r
@@ -114,7 +114,7 @@ void HeaderComponent::paint (Graphics& g)
                                                     runAppButton->getWidth(), runAppButton->getHeight());\r
 }\r
 \r
-//======================================================================\r
+//==============================================================================\r
 void HeaderComponent::setCurrentProject (Project* p) noexcept\r
 {\r
     project = p;\r
@@ -148,7 +148,7 @@ void HeaderComponent::setCurrentProject (Project* p) noexcept
     }\r
 }\r
 \r
-//======================================================================\r
+//==============================================================================\r
 void HeaderComponent::updateExporters() noexcept\r
 {\r
     auto selectedName = getSelectedExporterName();\r
@@ -203,7 +203,7 @@ bool HeaderComponent::canCurrentExporterLaunchProject() const noexcept
     return false;\r
 }\r
 \r
-//======================================================================\r
+//==============================================================================\r
 int HeaderComponent::getUserButtonWidth() const noexcept\r
 {\r
     return userSettingsButton->getWidth();\r
@@ -215,7 +215,7 @@ void HeaderComponent::sidebarTabsWidthChanged (int newWidth) noexcept
     resized();\r
 }\r
 \r
-//======================================================================\r
+//==============================================================================\r
 void HeaderComponent::showUserSettings() noexcept\r
 {\r
    #if JUCER_ENABLE_GPL_MODE\r
@@ -233,7 +233,7 @@ void HeaderComponent::showUserSettings() noexcept
     userSettingsWindow = &CallOutBox::launchAsynchronously (content, userSettingsButton->getScreenBounds(), nullptr);\r
 }\r
 \r
-//==========================================================================\r
+//==============================================================================\r
 void HeaderComponent::lookAndFeelChanged()\r
 {\r
     if (userSettingsWindow != nullptr)\r
@@ -261,7 +261,7 @@ void HeaderComponent::timerCallback()
     repaint();\r
 }\r
 \r
-//======================================================================\r
+//==============================================================================\r
 static void sendProjectButtonAnalyticsEvent (StringRef label)\r
 {\r
     StringPairArray data;\r
@@ -351,7 +351,7 @@ void HeaderComponent::updateUserAvatar() noexcept
     }\r
 }\r
 \r
-//======================================================================\r
+//==============================================================================\r
 void HeaderComponent::buildPing()\r
 {\r
     if (! isTimerRunning())\r
index 540b3840ac2c51e1368a55f76f5099aad7e3b050..0ebac87326567dbc30e907df872117ba841af39a 100644 (file)
@@ -43,33 +43,33 @@ public:
     HeaderComponent();\r
     ~HeaderComponent() override;\r
 \r
-    //==========================================================================\r
+    //==============================================================================\r
     void resized() override;\r
     void paint (Graphics&) override;\r
 \r
-    //==========================================================================\r
+    //==============================================================================\r
     void setCurrentProject (Project*) noexcept;\r
 \r
-    //==========================================================================\r
+    //==============================================================================\r
     void updateExporters() noexcept;\r
     String getSelectedExporterName() const noexcept;\r
     bool canCurrentExporterLaunchProject() const noexcept;\r
 \r
-    //==========================================================================\r
+    //==============================================================================\r
     int getUserButtonWidth() const noexcept;\r
     void sidebarTabsWidthChanged (int newWidth) noexcept;\r
 \r
-    //==========================================================================\r
+    //==============================================================================\r
     void showUserSettings() noexcept;\r
 \r
 private:\r
-    //==========================================================================\r
+    //==============================================================================\r
     void lookAndFeelChanged() override;\r
     void changeListenerCallback (ChangeBroadcaster* source) override;\r
     void valueChanged (Value&) override;\r
     void timerCallback() override;\r
 \r
-    //==========================================================================\r
+    //==============================================================================\r
     void valueTreeChildAdded (ValueTree& parentTree, ValueTree&) override        { updateIfNeeded (parentTree); }\r
     void valueTreeChildRemoved (ValueTree& parentTree, ValueTree&, int) override { updateIfNeeded (parentTree); }\r
     void valueTreeChildOrderChanged (ValueTree& parentTree, int, int) override   { updateIfNeeded (parentTree); }\r
@@ -80,19 +80,19 @@ private:
             updateExporters();\r
     }\r
 \r
-    //==========================================================================\r
+    //==============================================================================\r
     void initialiseButtons() noexcept;\r
 \r
     void updateName() noexcept;\r
     void updateExporterButton() noexcept;\r
     void updateUserAvatar() noexcept;\r
 \r
-    //==========================================================================\r
+    //==============================================================================\r
     void buildPing();\r
     void buildFinished (bool);\r
     void setRunAppButtonState (bool);\r
 \r
-    //==========================================================================\r
+    //==============================================================================\r
     int tabsWidth = 200;\r
     bool isBuilding = false;\r
 \r
index 81a4c68f3b07fe9a5a1d29e98620269d133af83a..0b2ef9f60a60967d9efb6268fdbbf8a05fbe38b8 100644 (file)
@@ -122,24 +122,24 @@ public:
         bounds.removeFromLeft (5);\r
         g.setColour (rowIsSelected ? findColour (defaultHighlightedTextColourId) : findColour (widgetTextColourId));\r
 \r
-        //======================================================================\r
+        //==============================================================================\r
         auto moduleID = project.getEnabledModules().getModuleID (rowNumber);\r
 \r
         g.drawFittedText (moduleID, bounds.removeFromLeft (roundToInt (listHeader->getProportionAtIndex (0) * width)), Justification::centredLeft, 1);\r
 \r
-        //======================================================================\r
+        //==============================================================================\r
         auto version = project.getEnabledModules().getModuleInfo (moduleID).getVersion();\r
         if (version.isEmpty())\r
             version = "?";\r
 \r
         g.drawFittedText (version, bounds.removeFromLeft (roundToInt (listHeader->getProportionAtIndex (1) * width)), Justification::centredLeft, 1);\r
 \r
-        //======================================================================\r
+        //==============================================================================\r
         auto copyLocally = project.getEnabledModules().shouldCopyModuleFilesLocally (moduleID).getValue() ? "Yes" : "No";\r
 \r
         g.drawFittedText (copyLocally, bounds.removeFromLeft (roundToInt (listHeader->getProportionAtIndex (2) * width)), Justification::centredLeft, 1);\r
 \r
-        //======================================================================\r
+        //==============================================================================\r
         String pathText;\r
 \r
         if (project.getEnabledModules().shouldUseGlobalPath (moduleID))\r
index 52d52045b609bae0d3d8d053f438cbec32912d9d..8e3a367c3e2c28058150e9265bda90e94c8f0e3a 100644 (file)
@@ -255,7 +255,7 @@ void ProjectContentComponent::rebuildProjectTabs()
         addAndMakeVisible (sidebarTabs);\r
         createProjectTabs();\r
 \r
-        //======================================================================\r
+        //==============================================================================\r
         auto& settings = project->getStoredProperties();\r
 \r
         auto lastTreeWidth = settings.getValue ("projectPanelWidth").getIntValue();\r
@@ -271,7 +271,7 @@ void ProjectContentComponent::rebuildProjectTabs()
             projectTab->setPanelHeightProportion (i, settings.getValue ("projectTabPanelHeight" + String (i), "1")\r
                                                              .getFloatValue());\r
 \r
-        //======================================================================\r
+        //==============================================================================\r
         resizerBar.reset (new ResizableEdgeComponent (&sidebarTabs, &sidebarSizeConstrainer,\r
                                                       ResizableEdgeComponent::rightEdge));\r
         addAndMakeVisible (resizerBar.get());\r
index d6519f3a12faf9120e923c06212bbf156f5ba2a6..45f5b35124975120db413648dee80b0ce50c54da 100644 (file)
@@ -1036,7 +1036,7 @@ void Project::createPropertyEditors (PropertyListBuilder& props)
                                              "Include BinaryData.h in the JuceHeader.h file");\r
 \r
     props.add (new TextPropertyComponent (binaryDataNamespaceValue, "BinaryData Namespace", 256, false),\r
-                                          "The namespace containing the binary assests.");\r
+                                          "The namespace containing the binary assets.");\r
 \r
     props.add (new ChoicePropertyComponent (cppStandardValue, "C++ Language Standard",\r
                                             { "C++11", "C++14", "C++17", "Use Latest" },\r
index e7617adb3cf97f6e4f082b732f6c8ca03e3c3889..f47c1331a42473f462d97259dad82e8da0f8d5a0 100644 (file)
@@ -570,8 +570,6 @@ public:
 \r
                     if (cppStandard == "11") // VS doesn't support the C++11 flag so we have to bump it to C++14\r
                         cppStandard = "14";\r
-                    else if (cppStandard == "17") // nor does it support the C++17 flag, so we'll just use latest for now until it's added\r
-                        cppStandard = "latest";\r
 \r
                     cl->createNewChildElement ("LanguageStandard")->addTextElement ("stdcpp" + cppStandard);\r
                 }\r
index 0a2e995d699cfcb87f614a98e92fc168cae02565..1764dcaae7879abc544d6430f349c828197c4c02 100644 (file)
@@ -104,6 +104,9 @@ public:
           cameraPermissionNeededValue                  (settings, Ids::cameraPermissionNeeded,                  getUndoManager()),\r
           cameraPermissionTextValue                    (settings, Ids::cameraPermissionText,                    getUndoManager(),\r
                                                         "This app requires access to the camera to function correctly."),\r
+          iosBluetoothPermissionNeededValue            (settings, Ids::iosBluetoothPermissionNeeded,            getUndoManager()),\r
+          iosBluetoothPermissionTextValue              (settings, Ids::iosBluetoothPermissionText,              getUndoManager(),\r
+                                                        "This app requires access to Bluetooth to function correctly."),\r
           uiFileSharingEnabledValue                    (settings, Ids::UIFileSharingEnabled,                    getUndoManager()),\r
           uiSupportsDocumentBrowserValue               (settings, Ids::UISupportsDocumentBrowser,               getUndoManager()),\r
           uiStatusBarHiddenValue                       (settings, Ids::UIStatusBarHidden,                       getUndoManager()),\r
@@ -173,6 +176,9 @@ public:
     bool isCameraPermissionEnabled() const             { return cameraPermissionNeededValue.get(); }\r
     String getCameraPermissionTextString() const       { return cameraPermissionTextValue.get(); }\r
 \r
+    bool isBluetoothPermissionEnabled() const          { return iosBluetoothPermissionNeededValue.get(); }\r
+    String getBluetoothPermissionTextString() const    { return iosBluetoothPermissionTextValue.get(); }\r
+\r
     bool isInAppPurchasesEnabled() const               { return iosInAppPurchasesValue.get(); }\r
     bool isBackgroundAudioEnabled() const              { return iosBackgroundAudioValue.get(); }\r
     bool isBackgroundBleEnabled() const                { return iosBackgroundBleValue.get(); }\r
@@ -187,7 +193,7 @@ public:
 \r
     bool shouldKeepCustomXcodeSchemes() const          { return keepCustomXcodeSchemesValue.get(); }\r
 \r
-    String getIosDevelopmentTeamIDString() const       { return iosDevelopmentTeamIDValue.get(); }\r
+    String getDevelopmentTeamIDString() const          { return iosDevelopmentTeamIDValue.get(); }\r
     String getAppGroupIdString() const                 { return iosAppGroupsIDValue.get(); }\r
 \r
     String getDefaultLaunchStoryboardName() const      { jassert (iOS); return "LaunchScreen"; }\r
@@ -398,6 +404,17 @@ public:
                                                             "Camera Access Text", 1024, false),\r
                    "A short description of why your app requires camera access.");\r
 \r
+        if (iOS)\r
+        {\r
+            props.add (new ChoicePropertyComponent (iosBluetoothPermissionNeededValue, "Bluetooth Access"),\r
+                       "Enable this to allow your app to use Bluetooth on iOS 13.0 and above. "\r
+                       "The user of your app will be prompted to grant Bluetooth access permissions.");\r
+\r
+            props.add (new TextPropertyComponentWithEnablement (iosBluetoothPermissionTextValue, iosBluetoothPermissionNeededValue,\r
+                                                                "Bluetooth Access Text", 1024, false),\r
+                       "A short description of why your app requires Bluetooth access.");\r
+        }\r
+\r
         props.add (new ChoicePropertyComponent (iosInAppPurchasesValue, "In-App Purchases Capability"),\r
                    "Enable this to grant your app the capability for in-app purchases. "\r
                    "This option requires that you specify a valid Development Team ID.");\r
@@ -468,7 +485,7 @@ public:
                    "This is useful if you want to use different bundle identifiers for Mac and iOS exporters in the same project.");\r
 \r
         props.add (new TextPropertyComponent (iosDevelopmentTeamIDValue, "Development Team ID", 10, false),\r
-                   "The Development Team ID to be used for setting up code-signing your iOS app. This is a ten-character "\r
+                   "The Development Team ID to be used for setting up code-signing your app. This is a ten-character "\r
                    "string (for example, \"S7B6T5XJ2Q\") that describes the distribution certificate Apple issued to you. "\r
                    "You can find this string in the OS X app Keychain Access under \"Certificates\".");\r
 \r
@@ -610,7 +627,7 @@ protected:
               osxArchitecture              (config, Ids::osxArchitecture,              getUndoManager(), osxArch_Default),\r
               customXcodeFlags             (config, Ids::customXcodeFlags,             getUndoManager()),\r
               plistPreprocessorDefinitions (config, Ids::plistPreprocessorDefinitions, getUndoManager()),\r
-              codeSignIdentity             (config, Ids::codeSigningIdentity,          getUndoManager(), iOS ? "iPhone Developer" : "Mac Developer"),\r
+              codeSignIdentity             (config, Ids::codeSigningIdentity,          getUndoManager()),\r
               fastMathEnabled              (config, Ids::fastMath,                     getUndoManager()),\r
               stripLocalSymbolsEnabled     (config, Ids::stripLocalSymbols,            getUndoManager()),\r
               pluginBinaryCopyStepEnabled  (config, Ids::enablePluginBinaryCopyStep,   getUndoManager(), true),\r
@@ -627,7 +644,7 @@ protected:
             optimisationLevelValue.setDefault (isDebug() ? gccO0 : gccO3);\r
         }\r
 \r
-        //==========================================================================\r
+        //==============================================================================\r
         void createConfigProperties (PropertyListBuilder& props) override\r
         {\r
             addXcodePluginInstallPathProperties (props);\r
@@ -684,7 +701,7 @@ protected:
             return "${CURRENT_ARCH}";\r
         }\r
 \r
-        //==========================================================================\r
+        //==============================================================================\r
         String getOSXArchitectureString() const                 { return osxArchitecture.get(); }\r
         String getPListPreprocessorDefinitionsString() const    { return plistPreprocessorDefinitions.get(); }\r
 \r
@@ -698,7 +715,6 @@ protected:
         String getOSXDeploymentTargetString() const             { return osxDeploymentTarget.get(); }\r
 \r
         String getCodeSignIdentityString() const                { return codeSignIdentity.get(); }\r
-        bool isUsingDefaultCodeSignIdentity() const             { return codeSignIdentity.isUsingDefault(); }\r
 \r
         String getiOSDeploymentTargetString() const             { return iosDeploymentTarget.get(); }\r
 \r
@@ -711,7 +727,7 @@ protected:
         String getUnityPluginBinaryLocationString() const       { return unityPluginBinaryLocation.get(); }\r
 \r
     private:\r
-        //==========================================================================\r
+        //==============================================================================\r
         bool iOS;\r
 \r
         ValueWithDefault osxSDKVersion, osxDeploymentTarget, iosDeploymentTarget, osxArchitecture,\r
@@ -720,7 +736,7 @@ protected:
                          vstBinaryLocation, vst3BinaryLocation, auBinaryLocation, rtasBinaryLocation,\r
                          aaxBinaryLocation, unityPluginBinaryLocation;\r
 \r
-        //==========================================================================\r
+        //==============================================================================\r
         void addXcodePluginInstallPathProperties (PropertyListBuilder& props)\r
         {\r
             auto isBuildingAnyPlugins = (project.shouldBuildVST() || project.shouldBuildVST3() || project.shouldBuildAU()\r
@@ -1070,7 +1086,7 @@ public:
         {\r
             auto attributes = getID() + " = { ";\r
 \r
-            auto developmentTeamID = owner.getIosDevelopmentTeamIDString();\r
+            auto developmentTeamID = owner.getDevelopmentTeamIDString();\r
 \r
             if (developmentTeamID.isNotEmpty())\r
             {\r
@@ -1308,7 +1324,9 @@ public:
             if (owner.iOS)\r
             {\r
                 s.set ("ASSETCATALOG_COMPILER_APPICON_NAME", "AppIcon");\r
-                s.set ("ASSETCATALOG_COMPILER_LAUNCHIMAGE_NAME", "LaunchImage");\r
+\r
+                if (! owner.shouldAddStoryboardToProject())\r
+                    s.set ("ASSETCATALOG_COMPILER_LAUNCHIMAGE_NAME", "LaunchImage");\r
             }\r
             else\r
             {\r
@@ -1323,15 +1341,15 @@ public:
             s.set ("GCC_VERSION", gccVersion);\r
             s.set ("CLANG_LINK_OBJC_RUNTIME", "NO");\r
 \r
-            if (isUsingCodeSigning (config))\r
-            {\r
-                s.set (owner.iOS ? "\"CODE_SIGN_IDENTITY[sdk=iphoneos*]\"" : "CODE_SIGN_IDENTITY",\r
-                       config.getCodeSignIdentityString().quoted());\r
+            auto codeSigningIdentity = owner.getCodeSigningIdentity (config);\r
+            s.set (owner.iOS ? "\"CODE_SIGN_IDENTITY[sdk=iphoneos*]\"" : "CODE_SIGN_IDENTITY",\r
+                   codeSigningIdentity.quoted());\r
+\r
+            if (codeSigningIdentity.isNotEmpty())\r
                 s.set ("PROVISIONING_PROFILE_SPECIFIER", "\"\"");\r
-            }\r
 \r
-            if (owner.getIosDevelopmentTeamIDString().isNotEmpty())\r
-                s.set ("DEVELOPMENT_TEAM", owner.getIosDevelopmentTeamIDString());\r
+            if (owner.getDevelopmentTeamIDString().isNotEmpty())\r
+                s.set ("DEVELOPMENT_TEAM", owner.getDevelopmentTeamIDString());\r
 \r
             if (shouldAddEntitlements())\r
                 s.set ("CODE_SIGN_ENTITLEMENTS", owner.getEntitlementsFileName().quoted());\r
@@ -1480,7 +1498,6 @@ public:
                     }\r
                 }\r
 \r
-                flags.add (owner.replacePreprocessorTokens (config, owner.getExtraLinkerFlagsString()));\r
                 flags.add (owner.getExternalLibraryFlags (config));\r
 \r
                 auto libs = owner.xcodeLibs;\r
@@ -1490,6 +1507,7 @@ public:
                     flags.add (getLinkerFlagForLib (l));\r
             }\r
 \r
+            flags.add (owner.replacePreprocessorTokens (config, owner.getExtraLinkerFlagsString()));\r
             flags = getCleanedStringArray (flags);\r
         }\r
 \r
@@ -1517,6 +1535,12 @@ public:
 \r
             if (owner.iOS)\r
             {\r
+                if (owner.isBluetoothPermissionEnabled())\r
+                {\r
+                    addPlistDictionaryKey (dict, "NSBluetoothAlwaysUsageDescription", owner.getBluetoothPermissionTextString());\r
+                    addPlistDictionaryKey (dict, "NSBluetoothPeripheralUsageDescription", owner.getBluetoothPermissionTextString()); // needed for pre iOS 13.0\r
+                }\r
+\r
                 addPlistDictionaryKeyBool (dict, "LSRequiresIPhoneOS", true);\r
 \r
                 if (type != AudioUnitv3PlugIn)\r
@@ -1919,12 +1943,6 @@ public:
             return {};\r
         }\r
 \r
-        bool isUsingCodeSigning (const XcodeBuildConfiguration& config) const\r
-        {\r
-            return (! config.isUsingDefaultCodeSignIdentity())\r
-                     || owner.getIosDevelopmentTeamIDString().isNotEmpty();\r
-        }\r
-\r
         //==============================================================================\r
         const XcodeProjectExporter& owner;\r
 \r
@@ -1958,7 +1976,7 @@ private:
                      iPadScreenOrientationValue, customXcodeResourceFoldersValue, customXcassetsFolderValue,\r
                      appSandboxValue, appSandboxOptionsValue,\r
                      hardenedRuntimeValue, hardenedRuntimeOptionsValue,\r
-                     microphonePermissionNeededValue, microphonePermissionsTextValue, cameraPermissionNeededValue, cameraPermissionTextValue,\r
+                     microphonePermissionNeededValue, microphonePermissionsTextValue, cameraPermissionNeededValue, cameraPermissionTextValue, iosBluetoothPermissionNeededValue, iosBluetoothPermissionTextValue,\r
                      uiFileSharingEnabledValue, uiSupportsDocumentBrowserValue, uiStatusBarHiddenValue, documentExtensionsValue, iosInAppPurchasesValue,\r
                      iosBackgroundAudioValue, iosBackgroundBleValue, iosPushNotificationsValue, iosAppGroupsValue, iCloudPermissionsValue,\r
                      iosDevelopmentTeamIDValue, iosAppGroupsIDValue, keepCustomXcodeSchemesValue, useHeaderMapValue, customLaunchStoryboardValue,\r
@@ -2115,10 +2133,7 @@ private:
 \r
     void addFilesAndGroupsToProject (StringArray& topLevelGroupIDs) const\r
     {\r
-        auto entitlements = getEntitlements();\r
-\r
-        if (entitlements.size() > 0)\r
-            topLevelGroupIDs.add (addEntitlementsFile (entitlements));\r
+        addEntitlementsFile();\r
 \r
         for (auto& group : getAllGroups())\r
         {\r
@@ -2526,6 +2541,16 @@ private:
         return sanitisePath (searchPath);\r
     }\r
 \r
+    String getCodeSigningIdentity (const XcodeBuildConfiguration& config) const\r
+    {\r
+        auto identity = config.getCodeSignIdentityString();\r
+\r
+        if (identity.isEmpty() && getDevelopmentTeamIDString().isNotEmpty())\r
+            return iOS ? "iPhone Developer" : "Mac Developer";\r
+\r
+        return identity;\r
+    }\r
+\r
     StringPairArray getProjectSettings (const XcodeBuildConfiguration& config) const\r
     {\r
         StringPairArray s;\r
@@ -2583,18 +2608,15 @@ private:
                 s.set ("ONLY_ACTIVE_ARCH", "YES");\r
         }\r
 \r
+        s.set (iOS ? "\"CODE_SIGN_IDENTITY[sdk=iphoneos*]\"" : "CODE_SIGN_IDENTITY",\r
+               getCodeSigningIdentity (config).quoted());\r
+\r
         if (iOS)\r
         {\r
-            s.set ("\"CODE_SIGN_IDENTITY[sdk=iphoneos*]\"", config.getCodeSignIdentityString().quoted());\r
             s.set ("SDKROOT", "iphoneos");\r
             s.set ("TARGETED_DEVICE_FAMILY", getDeviceFamilyString().quoted());\r
             s.set ("IPHONEOS_DEPLOYMENT_TARGET", config.getiOSDeploymentTargetString());\r
         }\r
-        else\r
-        {\r
-            if (! config.isUsingDefaultCodeSignIdentity() || getIosDevelopmentTeamIDString().isNotEmpty())\r
-                s.set ("CODE_SIGN_IDENTITY", config.getCodeSignIdentityString().quoted());\r
-        }\r
 \r
         s.set ("ZERO_LINK", "NO");\r
 \r
@@ -3128,7 +3150,7 @@ private:
         return entitlements;\r
     }\r
 \r
-    String addEntitlementsFile (StringPairArray entitlements) const\r
+    String addEntitlementsFile() const\r
     {\r
         String content =\r
             "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n"\r
@@ -3136,6 +3158,7 @@ private:
             "<plist version=\"1.0\">\n"\r
             "<dict>\n";\r
 \r
+        auto entitlements = getEntitlements();\r
         auto keys = entitlements.getAllKeys();\r
 \r
         for (auto& key : keys)\r
index b21a1aff77eb89de5cc9699f36a3fa8083d48607..c2711ecc9b75d62b667be07bf9e5e7fb45cd7c69 100644 (file)
@@ -458,7 +458,9 @@ private:
             << newLine\r
             << "// END SECTION A" << newLine\r
             << newLine\r
-            << "#define JUCE_USE_DARK_SPLASH_SCREEN "  << (project.getSplashScreenColourString() == "Dark" ? "1" : "0") << newLine;\r
+            << "#define JUCE_USE_DARK_SPLASH_SCREEN "  << (project.getSplashScreenColourString() == "Dark" ? "1" : "0") << newLine\r
+            << newLine\r
+            << "#define JUCE_PROJUCER_VERSION 0x" << String::toHexString (ProjectInfo::versionNumber) << newLine;\r
 \r
         out << newLine\r
             << "//==============================================================================" << newLine;\r
@@ -556,6 +558,15 @@ private:
             out << CodeHelpers::createIncludeStatement (project.getBinaryDataHeaderFile(), appConfigFile) << newLine;\r
 \r
         out << newLine\r
+            << "#if defined (JUCE_PROJUCER_VERSION) && JUCE_PROJUCER_VERSION < JUCE_VERSION" << newLine\r
+            << " /** If you've hit this error then the version of the Projucer that was used to generate this project is" << newLine\r
+            << "     older than the version of the JUCE modules being included. To fix this error, re-save your project" << newLine\r
+            << "     using the latest version of the Projucer or, if you aren't using the Projucer to manage your project," << newLine\r
+            << "     remove the JUCE_PROJUCER_VERSION define from the AppConfig.h file." << newLine\r
+            << " */" << newLine\r
+            << " #error \"This project was last saved using an outdated version of the Projucer! Re-save this project with the latest version to fix this error.\"" << newLine\r
+            << "#endif" << newLine\r
+            << newLine\r
             << "#if ! DONT_SET_USING_JUCE_NAMESPACE" << newLine\r
             << " // If your code uses a lot of JUCE classes, then this will obviously save you" << newLine\r
             << " // a lot of typing, but can be disabled by setting DONT_SET_USING_JUCE_NAMESPACE." << newLine\r
index 1b6ad2022914fa96b4bd13b36d8c537f3602e21e..5a3ef9cbc35ee2804f96fcedba14670895591c01 100644 (file)
@@ -252,6 +252,8 @@ namespace Ids
     DECLARE_ID (iCloudPermissions);\r
     DECLARE_ID (iosDevelopmentTeamID);\r
     DECLARE_ID (iosAppGroupsId);\r
+    DECLARE_ID (iosBluetoothPermissionNeeded);\r
+    DECLARE_ID (iosBluetoothPermissionText);\r
     DECLARE_ID (duplicateAppExResourcesFolder);\r
     DECLARE_ID (buildToolsVersion);\r
     DECLARE_ID (gradleVersion);\r
diff --git a/extras/UnitTestRunner/Builds/MacOSX/UnitTestRunner.entitlements b/extras/UnitTestRunner/Builds/MacOSX/UnitTestRunner.entitlements
new file mode 100644 (file)
index 0000000..6631ffa
--- /dev/null
@@ -0,0 +1,6 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
+<plist version="1.0">
+<dict>
+</dict>
+</plist>
index 9ecf9cae1c6c97c249cb1bcd0c45a861b57a7fef..02ced2bb59bdc286b6106ac0760a7d322163bd5b 100644 (file)
                        path = System/Library/Frameworks/CoreMedia.framework;
                        sourceTree = SDKROOT;
                };
+               911BC81C9C4E07C2E2FD68C1 = {
+                       isa = PBXFileReference;
+                       lastKnownFileType = text.plist.xml;
+                       name = UnitTestRunner.entitlements;
+                       path = UnitTestRunner.entitlements;
+                       sourceTree = "SOURCE_ROOT";
+               };
                9514F6D920549F8A44B2E332 = {
                        isa = PBXFileReference;
                        lastKnownFileType = file;
                                CLANG_CXX_LANGUAGE_STANDARD = "c++14";
                                CLANG_CXX_LIBRARY = "libc++";
                                CLANG_LINK_OBJC_RUNTIME = NO;
+                               CODE_SIGN_IDENTITY = "";
                                COMBINE_HIDPI_IMAGES = YES;
                                CONFIGURATION_BUILD_DIR = "$(PROJECT_DIR)/build/$(CONFIGURATION)";
                                COPY_PHASE_STRIP = NO;
                                CLANG_CXX_LANGUAGE_STANDARD = "c++14";
                                CLANG_CXX_LIBRARY = "libc++";
                                CLANG_LINK_OBJC_RUNTIME = NO;
+                               CODE_SIGN_IDENTITY = "";
                                COMBINE_HIDPI_IMAGES = YES;
                                CONFIGURATION_BUILD_DIR = "$(PROJECT_DIR)/build/$(CONFIGURATION)";
                                DEAD_CODE_STRIPPING = YES;
                                CLANG_WARN_SUSPICIOUS_MOVE = YES;
                                CLANG_WARN_UNREACHABLE_CODE = YES;
                                CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
+                               CODE_SIGN_IDENTITY = "";
                                DEBUG_INFORMATION_FORMAT = dwarf;
                                ENABLE_STRICT_OBJC_MSGSEND = YES;
                                ENABLE_TESTABILITY = YES;
                                CLANG_WARN_SUSPICIOUS_MOVE = YES;
                                CLANG_WARN_UNREACHABLE_CODE = YES;
                                CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
+                               CODE_SIGN_IDENTITY = "";
                                DEBUG_INFORMATION_FORMAT = dwarf;
                                ENABLE_STRICT_OBJC_MSGSEND = YES;
                                GCC_C_LANGUAGE_STANDARD = c11;
index 6dafd30d3811390f45499e17b56bd123c53d2bd9..b6d6721d0625c0c3e55dacf5aaa8644d18b23e19 100644 (file)
     <ClCompile Include="..\..\..\..\modules\juce_blocks_basics\topology\internal\juce_BlockImplementation.cpp">\r
       <ExcludedFromBuild>true</ExcludedFromBuild>\r
     </ClCompile>\r
+    <ClCompile Include="..\..\..\..\modules\juce_blocks_basics\topology\internal\juce_BlockSerialReader.cpp">\r
+      <ExcludedFromBuild>true</ExcludedFromBuild>\r
+    </ClCompile>\r
     <ClCompile Include="..\..\..\..\modules\juce_blocks_basics\topology\internal\juce_ConnectedDeviceGroup.cpp">\r
       <ExcludedFromBuild>true</ExcludedFromBuild>\r
     </ClCompile>\r
     <ClCompile Include="..\..\..\..\modules\juce_data_structures\juce_data_structures.cpp">\r
       <ExcludedFromBuild>true</ExcludedFromBuild>\r
     </ClCompile>\r
+    <ClCompile Include="..\..\..\..\modules\juce_dsp\containers\juce_AudioBlock_test.cpp">\r
+      <ExcludedFromBuild>true</ExcludedFromBuild>\r
+    </ClCompile>\r
     <ClCompile Include="..\..\..\..\modules\juce_dsp\containers\juce_SIMDRegister_test.cpp">\r
       <ExcludedFromBuild>true</ExcludedFromBuild>\r
     </ClCompile>\r
index 8a3ee6eca5c18cf0faddc9d54d62f79489689387..40c5b96d75a566d11db5dda89245a6370dcb8d00 100644 (file)
     <ClCompile Include="..\..\..\..\modules\juce_blocks_basics\topology\internal\juce_BlockImplementation.cpp">\r
       <Filter>JUCE Modules\juce_blocks_basics\topology\internal</Filter>\r
     </ClCompile>\r
+    <ClCompile Include="..\..\..\..\modules\juce_blocks_basics\topology\internal\juce_BlockSerialReader.cpp">\r
+      <Filter>JUCE Modules\juce_blocks_basics\topology\internal</Filter>\r
+    </ClCompile>\r
     <ClCompile Include="..\..\..\..\modules\juce_blocks_basics\topology\internal\juce_ConnectedDeviceGroup.cpp">\r
       <Filter>JUCE Modules\juce_blocks_basics\topology\internal</Filter>\r
     </ClCompile>\r
     <ClCompile Include="..\..\..\..\modules\juce_data_structures\juce_data_structures.mm">\r
       <Filter>JUCE Modules\juce_data_structures</Filter>\r
     </ClCompile>\r
+    <ClCompile Include="..\..\..\..\modules\juce_dsp\containers\juce_AudioBlock_test.cpp">\r
+      <Filter>JUCE Modules\juce_dsp\containers</Filter>\r
+    </ClCompile>\r
     <ClCompile Include="..\..\..\..\modules\juce_dsp\containers\juce_SIMDRegister_test.cpp">\r
       <Filter>JUCE Modules\juce_dsp\containers</Filter>\r
     </ClCompile>\r
index 9b33ada2a0cb64e002d1b4c63c9644fa5d109fff..8fda398210cf952afe070cb82a48576eb7be59d5 100644 (file)
     <ClCompile Include="..\..\..\..\modules\juce_blocks_basics\topology\internal\juce_BlockImplementation.cpp">\r
       <ExcludedFromBuild>true</ExcludedFromBuild>\r
     </ClCompile>\r
+    <ClCompile Include="..\..\..\..\modules\juce_blocks_basics\topology\internal\juce_BlockSerialReader.cpp">\r
+      <ExcludedFromBuild>true</ExcludedFromBuild>\r
+    </ClCompile>\r
     <ClCompile Include="..\..\..\..\modules\juce_blocks_basics\topology\internal\juce_ConnectedDeviceGroup.cpp">\r
       <ExcludedFromBuild>true</ExcludedFromBuild>\r
     </ClCompile>\r
     <ClCompile Include="..\..\..\..\modules\juce_data_structures\juce_data_structures.cpp">\r
       <ExcludedFromBuild>true</ExcludedFromBuild>\r
     </ClCompile>\r
+    <ClCompile Include="..\..\..\..\modules\juce_dsp\containers\juce_AudioBlock_test.cpp">\r
+      <ExcludedFromBuild>true</ExcludedFromBuild>\r
+    </ClCompile>\r
     <ClCompile Include="..\..\..\..\modules\juce_dsp\containers\juce_SIMDRegister_test.cpp">\r
       <ExcludedFromBuild>true</ExcludedFromBuild>\r
     </ClCompile>\r
index 7b2bfeee6fd64ba549859233845535d6ea0f8963..473a89cd408af41206af11c1a0ca7f40e5fc452c 100644 (file)
     <ClCompile Include="..\..\..\..\modules\juce_blocks_basics\topology\internal\juce_BlockImplementation.cpp">\r
       <Filter>JUCE Modules\juce_blocks_basics\topology\internal</Filter>\r
     </ClCompile>\r
+    <ClCompile Include="..\..\..\..\modules\juce_blocks_basics\topology\internal\juce_BlockSerialReader.cpp">\r
+      <Filter>JUCE Modules\juce_blocks_basics\topology\internal</Filter>\r
+    </ClCompile>\r
     <ClCompile Include="..\..\..\..\modules\juce_blocks_basics\topology\internal\juce_ConnectedDeviceGroup.cpp">\r
       <Filter>JUCE Modules\juce_blocks_basics\topology\internal</Filter>\r
     </ClCompile>\r
     <ClCompile Include="..\..\..\..\modules\juce_data_structures\juce_data_structures.mm">\r
       <Filter>JUCE Modules\juce_data_structures</Filter>\r
     </ClCompile>\r
+    <ClCompile Include="..\..\..\..\modules\juce_dsp\containers\juce_AudioBlock_test.cpp">\r
+      <Filter>JUCE Modules\juce_dsp\containers</Filter>\r
+    </ClCompile>\r
     <ClCompile Include="..\..\..\..\modules\juce_dsp\containers\juce_SIMDRegister_test.cpp">\r
       <Filter>JUCE Modules\juce_dsp\containers</Filter>\r
     </ClCompile>\r
index 2257f5355720072ca471cdfdb749bdeb90270393..e270488f1b4538d44ef60687064c54090a794edd 100644 (file)
@@ -47,6 +47,8 @@
 \r
 #define JUCE_USE_DARK_SPLASH_SCREEN 1\r
 \r
+#define JUCE_PROJUCER_VERSION 0x50405\r
+\r
 //==============================================================================\r
 #define JUCE_MODULE_AVAILABLE_juce_analytics              1\r
 #define JUCE_MODULE_AVAILABLE_juce_audio_basics           1\r
index b4cfd548cb52fe9996761e80eca0a3fb0fb18b0c..1b016ebae4c8a19ad6785ffc7660ffa54d65aa35 100644 (file)
 #include <juce_video/juce_video.h>\r
 \r
 \r
+#if defined (JUCE_PROJUCER_VERSION) && JUCE_PROJUCER_VERSION < JUCE_VERSION\r
+ /** If you've hit this error then the version of the Projucer that was used to generate this project is\r
+     older than the version of the JUCE modules being included. To fix this error, re-save your project\r
+     using the latest version of the Projucer or, if you aren't using the Projucer to manage your project,\r
+     remove the JUCE_PROJUCER_VERSION define from the AppConfig.h file.\r
+ */\r
+ #error "This project was last saved using an outdated version of the Projucer! Re-save this project with the latest version to fix this error."\r
+#endif\r
+\r
 #if ! DONT_SET_USING_JUCE_NAMESPACE\r
  // If your code uses a lot of JUCE classes, then this will obviously save you\r
  // a lot of typing, but can be disabled by setting DONT_SET_USING_JUCE_NAMESPACE.\r
index a57260a90ec299e5867985c02de57c2fa03b5aa4..6cbcabaa9662ce02eaf2e5a1ec2593e493ebc69f 100644 (file)
@@ -1,7 +1,7 @@
 <?xml version="1.0" encoding="UTF-8"?>\r
 \r
 <JUCERPROJECT id="Z2Xzcp" name="UnitTestRunner" projectType="consoleapp" bundleIdentifier="com.roli.UnitTestRunner"\r
-              jucerVersion="5.4.4" defines="JUCE_UNIT_TESTS=1" displaySplashScreen="0"\r
+              jucerVersion="5.4.5" defines="JUCE_UNIT_TESTS=1" displaySplashScreen="0"\r
               reportAppUsage="0" companyName="ROLI Ltd." companyCopyright="ROLI Ltd.">\r
   <MAINGROUP id="GZdWCU" name="UnitTestRunner">\r
     <GROUP id="{22894462-E1A9-036F-ED94-B51A50C87552}" name="Source">\r
index ab2260832c5533f40a778809419423d77d348f57..146de870e6bedabc707e5f9c0a6a11660e34504c 100644 (file)
@@ -47,6 +47,8 @@
 \r
 #define JUCE_USE_DARK_SPLASH_SCREEN 1\r
 \r
+#define JUCE_PROJUCER_VERSION 0x50405\r
+\r
 //==============================================================================\r
 #define JUCE_MODULE_AVAILABLE_juce_audio_basics          1\r
 #define JUCE_MODULE_AVAILABLE_juce_audio_devices         1\r
index c7101cce7dd2ea3e113e66fb225daf9d71ff4ebd..91fef65b932be2620f4e71c47bcda615b275b8c6 100644 (file)
 #include <juce_video/juce_video.h>\r
 \r
 \r
+#if defined (JUCE_PROJUCER_VERSION) && JUCE_PROJUCER_VERSION < JUCE_VERSION\r
+ /** If you've hit this error then the version of the Projucer that was used to generate this project is\r
+     older than the version of the JUCE modules being included. To fix this error, re-save your project\r
+     using the latest version of the Projucer or, if you aren't using the Projucer to manage your project,\r
+     remove the JUCE_PROJUCER_VERSION define from the AppConfig.h file.\r
+ */\r
+ #error "This project was last saved using an outdated version of the Projucer! Re-save this project with the latest version to fix this error."\r
+#endif\r
+\r
 #if ! DONT_SET_USING_JUCE_NAMESPACE\r
  // If your code uses a lot of JUCE classes, then this will obviously save you\r
  // a lot of typing, but can be disabled by setting DONT_SET_USING_JUCE_NAMESPACE.\r
index 34f601e708baba2ffac5925317a6d7a4db9ae0c3..d713ca99bc3ed30dda968b2216ad0ab4f1f8eb6e 100644 (file)
@@ -1,7 +1,7 @@
 <?xml version="1.0" encoding="UTF-8"?>\r
 \r
 <JUCERPROJECT id="IvabE4" name="WindowsDLL" projectType="library" juceLinkage="none"\r
-              bundleIdentifier="com.roli.jucedll" jucerVersion="5.4.4" defines="JUCE_DLL_BUILD=1"\r
+              bundleIdentifier="com.roli.jucedll" jucerVersion="5.4.5" defines="JUCE_DLL_BUILD=1"\r
               displaySplashScreen="0" reportAppUsage="0" companyName="ROLI Ltd."\r
               companyCopyright="ROLI Ltd.">\r
   <EXPORTFORMATS>\r
index 571f7b034113abb46b57b6efe6fb5b4379de39c5..ebe41e9faf8db9675d124750d89e7fe5f220735c 100644 (file)
@@ -108,7 +108,7 @@ OS X:
     "i386", for example).\r
 \r
 Visual Studio:\r
-    VisualStudio{year}/{arch}/{run-time}, where {year} is the four digit year of the Visual Studio\r
+    libs/VisualStudio{year}/{arch}/{run-time}, where {year} is the four digit year of the Visual Studio\r
     release, arch is the target architecture in Visual Studio ("x64" or "Win32", for example), and\r
     {runtime} is the type of the run-time library indicated by the corresponding compiler flag\r
     ("MD", "MDd", "MT", "MTd").\r
index f119738f3e1c7e1aa080f054d351d819d6c8206d..0bf9255ed6e69cc3885607bca463f657676ac648 100644 (file)
@@ -35,7 +35,7 @@
 \r
   ID:               juce_analytics\r
   vendor:           juce\r
-  version:          5.4.4\r
+  version:          5.4.5\r
   name:             JUCE analytics classes\r
   description:      Classes to collect analytics and send to destinations\r
   website:          http://www.juce.com/juce\r
index 617c7ced1ed17abe5b46a62a7e1823196c6675d4..83a108310e0787a045bb249c1abd19dc14c3a425 100644 (file)
@@ -31,7 +31,7 @@
 \r
   ID:               juce_audio_basics\r
   vendor:           juce\r
-  version:          5.4.4\r
+  version:          5.4.5\r
   name:             JUCE audio and MIDI data classes\r
   description:      Classes for audio buffer manipulation, midi message handling, synthesis, etc.\r
   website:          http://www.juce.com/juce\r
index ab3ca754f2f7384bd8f51355f1864e6d52acd665..2d89a34efafb607c5eb77e8cbfcb612b05cdb75a 100644 (file)
@@ -42,6 +42,9 @@ public:
     CatmullRomInterpolator() noexcept;\r
     ~CatmullRomInterpolator() noexcept;\r
 \r
+    CatmullRomInterpolator (CatmullRomInterpolator&&) noexcept = default;\r
+    CatmullRomInterpolator& operator= (CatmullRomInterpolator&&) noexcept = default;\r
+\r
     /** Resets the state of the interpolator.\r
         Call this when there's a break in the continuity of the input data stream.\r
     */\r
index 6914e465c04941a86daf6725001096245760a885..25598e7500e89533831643649438845d0146c0fe 100644 (file)
@@ -42,6 +42,9 @@ public:
     LagrangeInterpolator() noexcept;\r
     ~LagrangeInterpolator() noexcept;\r
 \r
+    LagrangeInterpolator (LagrangeInterpolator&&) noexcept = default;\r
+    LagrangeInterpolator& operator= (LagrangeInterpolator&&) noexcept = default;\r
+\r
     /** Resets the state of the interpolator.\r
         Call this when there's a break in the continuity of the input data stream.\r
     */\r
index 7dbe01013235df14a8163e0b7d1bde3472fa498b..a26a3bf49cc00a6363d8fab5222d92882c107f01 100644 (file)
@@ -1098,12 +1098,19 @@ bool AudioDeviceManager::isMidiInputEnabled (const String& name) const
 \r
 void AudioDeviceManager::addMidiInputCallback (const String& name, MidiInputCallback* callbackToAdd)\r
 {\r
-    for (auto& device : MidiInput::getAvailableDevices())\r
+    if (name.isEmpty())\r
     {\r
-        if (device.name == name)\r
+        addMidiInputDeviceCallback ({}, callbackToAdd);\r
+    }\r
+    else\r
+    {\r
+        for (auto& device : MidiInput::getAvailableDevices())\r
         {\r
-            addMidiInputDeviceCallback (device.identifier, callbackToAdd);\r
-            return;\r
+            if (device.name == name)\r
+            {\r
+                addMidiInputDeviceCallback (device.identifier, callbackToAdd);\r
+                return;\r
+            }\r
         }\r
     }\r
 }\r
index d6e1e990768dd31394ead6ea52a36ff667a84bfa..a7f816e979bd0021bb05ed81ba3350a55f78d748 100644 (file)
      installed, or you've not got your paths set up correctly to find its header\r
      files.\r
   */\r
-  #include <rtdk.h>\r
   #include <Bela.h>\r
   #include <Midi.h>\r
  #endif\r
index 8b476b90dfbf86e96d3afa483dbf6fe1d20625c9..20a2c5f6480afd182e58d3b707ff91206e0813cd 100644 (file)
@@ -31,7 +31,7 @@
 \r
   ID:               juce_audio_devices\r
   vendor:           juce\r
-  version:          5.4.4\r
+  version:          5.4.5\r
   name:             JUCE audio and MIDI I/O device classes\r
   description:      Classes to play and record from audio and MIDI I/O devices\r
   website:          http://www.juce.com/juce\r
index 3fbf5fe78ee47817dd300f0ec739c4209647fab8..4d2025072a3c4b185ac58bbb04c0ed4196ea1a70 100644 (file)
@@ -1434,7 +1434,7 @@ public:
     }\r
 \r
 private:\r
-    //=============================================================================\r
+    //==============================================================================\r
     void* (*threadEntryProc) (void*) = nullptr;\r
     void* threadUserPtr = nullptr;\r
 \r
index 3f0229f86c38e7e6d02ff440e0d3a6f66f379046..7e67c1d00664b370c7858083f13dfd791d6c3881 100644 (file)
@@ -315,6 +315,12 @@ struct OpenSLEngineHolder
     SlRef<SLEngineItf_> engine;\r
 };\r
 \r
+OpenSLEngineHolder& getEngineHolder()\r
+{\r
+    static OpenSLEngineHolder holder;\r
+    return holder;\r
+}\r
+\r
 //==============================================================================\r
 class SLRealtimeThread;\r
 \r
@@ -458,11 +464,11 @@ public:
 \r
             SLObjectItf obj = nullptr;\r
 \r
-            SharedResourcePointer<OpenSLEngineHolder> holder;\r
+            auto& holder = getEngineHolder();\r
 \r
-            if (auto e = *holder->engine)\r
+            if (auto e = *holder.engine)\r
             {\r
-                auto status = e->CreateAudioPlayer (holder->engine, &obj, &source, &sink, 2,\r
+                auto status = e->CreateAudioPlayer (holder.engine, &obj, &source, &sink, 2,\r
                                                     queueInterfaces, interfaceRequired);\r
 \r
                 if (status != SL_RESULT_SUCCESS || obj == nullptr || (*obj)->Realize(obj, 0) != SL_RESULT_SUCCESS)\r
@@ -503,11 +509,11 @@ public:
 \r
             SLObjectItf obj = nullptr;\r
 \r
-            SharedResourcePointer<OpenSLEngineHolder> holder;\r
+            auto& holder = getEngineHolder();\r
 \r
-            if (auto e = *holder->engine)\r
+            if (auto e = *holder.engine)\r
             {\r
-                auto status = e->CreateAudioRecorder (holder->engine, &obj, &source, &sink, 2, queueInterfaces, interfaceRequired);\r
+                auto status = e->CreateAudioRecorder (holder.engine, &obj, &source, &sink, 2, queueInterfaces, interfaceRequired);\r
 \r
                 if (status != SL_RESULT_SUCCESS || obj == nullptr || (*obj)->Realize (obj, 0) != SL_RESULT_SUCCESS)\r
                 {\r
@@ -556,9 +562,10 @@ public:
 \r
             if (outputChannels > 0)\r
             {\r
-                SharedResourcePointer<OpenSLEngineHolder> holder;\r
+                auto& holder = getEngineHolder();\r
                 SLObjectItf obj = nullptr;\r
-                auto err = (*holder->engine)->CreateOutputMix (holder->engine, &obj, 0, nullptr, nullptr);\r
+\r
+                auto err = (*holder.engine)->CreateOutputMix (holder.engine, &obj, 0, nullptr, nullptr);\r
 \r
                 if (err != SL_RESULT_SUCCESS || obj == nullptr || *obj == nullptr\r
                      || (*obj)->Realize (obj, 0) != SL_RESULT_SUCCESS)\r
@@ -814,7 +821,7 @@ public:
         outputLatency = (int) ((longestLatency * outputLatency) / totalLatency) & ~15;\r
 \r
         // You can only create this class if you are sure that your hardware supports OpenSL\r
-        jassert (engineHolder->slLibrary.getNativeHandle() != nullptr);\r
+        jassert (getEngineHolder().slLibrary.getNativeHandle() != nullptr);\r
     }\r
 \r
     ~OpenSLAudioIODevice() override\r
@@ -1032,8 +1039,6 @@ private:
     friend class SLRealtimeThread;\r
 \r
     //==============================================================================\r
-    SharedResourcePointer<OpenSLEngineHolder> engineHolder;\r
-\r
     int actualBufferSize = 0, sampleRate = 0, audioBuffersToEnqueue = 0;\r
     int inputLatency, outputLatency;\r
     bool deviceOpen = false, audioProcessingEnabled = true;\r
@@ -1346,13 +1351,13 @@ public:
     }\r
 \r
 private:\r
-    //=============================================================================\r
+    //==============================================================================\r
     static void staticFinished (SLAndroidSimpleBufferQueueItf, void* context)\r
     {\r
         static_cast<SLRealtimeThread*> (context)->finished();\r
     }\r
 \r
-    //=============================================================================\r
+    //==============================================================================\r
     DynamicLibrary slLibrary { "libOpenSLES.so" };\r
 \r
     SlRef<SLEngineItf_>    engine;\r
index 363e3c571d44cbf99696e154a98b9dd51188204a..b13eceb50e6b838f6f74bb9c89ed2f45c0c170ec 100755 (executable)
@@ -56,7 +56,7 @@ public:
 \r
     void poll()\r
     {\r
-        int receivedBytes = 0;\r
+        size_t receivedBytes = 0;\r
 \r
         for (;;)\r
         {\r
@@ -70,7 +70,7 @@ public:
 \r
             if (receivedBytes == buffer.size())\r
             {\r
-                pushMidiData (receivedBytes);\r
+                pushMidiData (static_cast<int> (receivedBytes));\r
                 receivedBytes = 0;\r
             }\r
         }\r
@@ -89,6 +89,11 @@ public:
         return devices;\r
     }\r
 \r
+    void pushMidiMessage (juce::MidiMessage& message)\r
+    {\r
+        concatenator.pushMidiData (message.getRawData(), message.getRawDataSize(), Time::getMillisecondCounter() * 0.001, midiInput, *midiCallback);\r
+    }\r
+\r
 private:\r
     void pushMidiData (int length)\r
     {\r
@@ -144,7 +149,7 @@ private:
 \r
             auto subCount = snd_rawmidi_info_get_subdevices_count (info);\r
 \r
-            for (int sub = 0; sub < subCount; ++sub)\r
+            for (size_t sub = 0; sub < subCount; ++sub)\r
             {\r
                 snd_rawmidi_info_set_subdevice (info, sub);\r
 \r
@@ -161,8 +166,8 @@ private:
         snd_ctl_close (ctl);\r
     }\r
 \r
-    String midiPort;\r
     MidiInput* const midiInput;\r
+    String midiPort;\r
     MidiInputCallback* const midiCallback;\r
 \r
     Midi midi;\r
@@ -190,8 +195,26 @@ public:
     }\r
 \r
     //==============================================================================\r
-    StringArray getOutputChannelNames() override           { return { "Out #1", "Out #2" }; }\r
-    StringArray getInputChannelNames() override            { return { "In #1",  "In #2" }; }\r
+    StringArray getOutputChannelNames() override\r
+    {\r
+        StringArray result;\r
+\r
+        for (int i = 1; i <= actualNumberOfOutputs; i++)\r
+            result.add ("Out #" + std::to_string (i));\r
+\r
+        return result;\r
+    }\r
+\r
+    StringArray getInputChannelNames() override\r
+    {\r
+        StringArray result;\r
+\r
+        for (int i = 1; i <= actualNumberOfInputs; i++)\r
+            result.add ("In #" + std::to_string (i));\r
+\r
+        return result;\r
+    }\r
+\r
     Array<double> getAvailableSampleRates() override       { return { 44100.0 }; }\r
     Array<int> getAvailableBufferSizes() override          { /* TODO: */ return { getDefaultBufferSize() }; }\r
     int getDefaultBufferSize() override                    { return defaultSettings.periodSize; }\r
@@ -213,15 +236,27 @@ public:
         auto numIns = getNumContiguousSetBits (inputChannels);\r
         auto numOuts = getNumContiguousSetBits (outputChannels);\r
 \r
-        settings.useAnalog            = 0;\r
-        settings.useDigital           = 0;\r
-        settings.numAudioInChannels   = numIns;\r
-        settings.numAudioOutChannels  = numOuts;\r
+        // Input and Output channels are numbered as follows\r
+        //\r
+        // 0  .. 1  - audio\r
+        // 2  .. 9  - analog\r
+\r
+        if (numIns > 2 || numOuts > 2)\r
+        {\r
+            settings.useAnalog            = true;\r
+            settings.numAnalogInChannels  = std::max (numIns - 2, 8);\r
+            settings.numAnalogOutChannels = std::max (numOuts - 2, 8);\r
+            settings.uniformSampleRate    = true;\r
+        }\r
+\r
+        settings.numAudioInChannels   = std::max (numIns, 2);\r
+        settings.numAudioOutChannels  = std::max (numOuts, 2);\r
+\r
         settings.detectUnderruns      = 1;\r
         settings.setup                = setupCallback;\r
         settings.render               = renderCallback;\r
         settings.cleanup              = cleanupCallback;\r
-        settings.interleave           = 1;\r
+        settings.interleave           = 0;\r
 \r
         if (bufferSizeSamples > 0)\r
             settings.periodSize = bufferSizeSamples;\r
@@ -240,10 +275,7 @@ public:
         actualNumberOfInputs  = jmin (numIns, actualNumberOfInputs);\r
         actualNumberOfOutputs = jmin (numOuts, actualNumberOfOutputs);\r
 \r
-        audioInBuffer.setSize (actualNumberOfInputs, actualBufferSize);\r
         channelInBuffer.calloc (actualNumberOfInputs);\r
-\r
-        audioOutBuffer.setSize (actualNumberOfOutputs, actualBufferSize);\r
         channelOutBuffer.calloc (actualNumberOfOutputs);\r
 \r
         return {};\r
@@ -265,10 +297,7 @@ public:
             actualNumberOfInputs = 0;\r
             actualNumberOfOutputs = 0;\r
 \r
-            audioInBuffer.setSize (0, 0);\r
             channelInBuffer.free();\r
-\r
-            audioOutBuffer.setSize (0, 0);\r
             channelOutBuffer.free();\r
         }\r
     }\r
@@ -298,9 +327,6 @@ public:
         }\r
         else\r
         {\r
-            audioInBuffer.clear();\r
-            audioOutBuffer.clear();\r
-\r
             callback = newCallback;\r
             isRunning = (Bela_startAudio() == 0);\r
 \r
@@ -342,7 +368,7 @@ public:
     //==============================================================================\r
     int getCurrentBufferSizeSamples() override            { return actualBufferSize; }\r
     double getCurrentSampleRate() override                { return 44100.0; }\r
-    int getCurrentBitDepth() override                     { return 24; }\r
+    int getCurrentBitDepth() override                     { return 16; }\r
     BigInteger getActiveOutputChannels() const override   { BigInteger b; b.setRange (0, actualNumberOfOutputs, true); return b; }\r
     BigInteger getActiveInputChannels() const override    { BigInteger b; b.setRange (0, actualNumberOfInputs, true);  return b; }\r
     int getOutputLatencyInSamples() override              { /* TODO */ return 0; }\r
@@ -353,12 +379,13 @@ public:
     static const char* const belaTypeName;\r
 \r
 private:\r
+\r
     //==============================================================================\r
     bool setup (BelaContext& context)\r
     {\r
         actualBufferSize      = context.audioFrames;\r
-        actualNumberOfInputs  = context.audioInChannels;\r
-        actualNumberOfOutputs = context.audioOutChannels;\r
+        actualNumberOfInputs  = context.audioInChannels + context.analogInChannels;\r
+        actualNumberOfOutputs = context.audioOutChannels + context.analogOutChannels;\r
         isBelaOpen = true;\r
         firstCallback = true;\r
 \r
@@ -384,59 +411,29 @@ private:
         if (callback != nullptr)\r
         {\r
             jassert (context.audioFrames <= actualBufferSize);\r
-            auto numSamples = jmin (context.audioFrames, actualBufferSize);\r
-            auto interleaved = ((context.flags & BELA_FLAG_INTERLEAVED) != 0);\r
-            auto numIns  = jmin (actualNumberOfInputs,  (int) context.audioInChannels);\r
-            auto numOuts = jmin (actualNumberOfOutputs, (int) context.audioOutChannels);\r
-\r
-            int ch;\r
-\r
-            if (interleaved && context.audioInChannels > 1)\r
-            {\r
-                for (ch = 0; ch < numIns; ++ch)\r
-                {\r
-                    using DstSampleType = AudioData::Pointer<AudioData::Float32, AudioData::NativeEndian, AudioData::NonInterleaved, AudioData::NonConst>;\r
-                    using SrcSampleType = AudioData::Pointer<AudioData::Float32, AudioData::NativeEndian, AudioData::Interleaved,    AudioData::Const>;\r
+            jassert ((context.flags & BELA_FLAG_INTERLEAVED) == 0);\r
 \r
-                    channelInBuffer[ch] = audioInBuffer.getWritePointer (ch);\r
-                    DstSampleType dstData (audioInBuffer.getWritePointer (ch));\r
-                    SrcSampleType srcData (context.audioIn + ch, context.audioInChannels);\r
-                    dstData.convertSamples (srcData, numSamples);\r
-                }\r
-            }\r
-            else\r
+            // Setup channelInBuffers\r
+            for (int ch = 0; ch < actualNumberOfInputs; ++ch)\r
             {\r
-                for (ch = 0; ch < numIns; ++ch)\r
-                    channelInBuffer[ch] = context.audioIn + (ch * numSamples);\r
+                if (ch < analogChannelStart)\r
+                    channelInBuffer[ch] = &context.audioIn[ch * context.audioFrames];\r
+                else\r
+                    channelInBuffer[ch] = &context.analogIn[(ch - analogChannelStart) * context.analogFrames];\r
             }\r
 \r
-            for (; ch < actualNumberOfInputs; ++ch)\r
+            // Setup channelOutBuffers\r
+            for (int ch = 0; ch < actualNumberOfOutputs; ++ch)\r
             {\r
-                channelInBuffer[ch] = audioInBuffer.getWritePointer(ch);\r
-                zeromem (audioInBuffer.getWritePointer (ch), sizeof (float) * numSamples);\r
+                if (ch < analogChannelStart)\r
+                    channelOutBuffer[ch] = &context.audioOut[ch * context.audioFrames];\r
+                else\r
+                    channelOutBuffer[ch] = &context.analogOut[(ch - analogChannelStart) * context.audioFrames];\r
             }\r
 \r
-            for (int i = 0; i < actualNumberOfOutputs; ++i)\r
-                channelOutBuffer[i] = ((interleaved && context.audioOutChannels > 1) || i >= context.audioOutChannels ? audioOutBuffer.getWritePointer (i)\r
-                                                                                                                      : context.audioOut + (i * numSamples));\r
-\r
             callback->audioDeviceIOCallback (channelInBuffer.getData(), actualNumberOfInputs,\r
                                              channelOutBuffer.getData(), actualNumberOfOutputs,\r
-                                             numSamples);\r
-\r
-            if (interleaved && context.audioOutChannels > 1)\r
-            {\r
-                for (int i = 0; i < numOuts; ++i)\r
-                {\r
-                    using DstSampleType = AudioData::Pointer<AudioData::Float32, AudioData::NativeEndian, AudioData::Interleaved,    AudioData::NonConst>;\r
-                    using SrcSampleType = AudioData::Pointer<AudioData::Float32, AudioData::NativeEndian, AudioData::NonInterleaved, AudioData::Const>;\r
-\r
-                    SrcSampleType srcData (channelOutBuffer[i]);\r
-                    DstSampleType dstData (context.audioOut + i, context.audioOutChannels);\r
-\r
-                    dstData.convertSamples (srcData, numSamples);\r
-                }\r
-            }\r
+                                             context.audioFrames);\r
         }\r
     }\r
 \r
@@ -448,6 +445,7 @@ private:
             callback->audioDeviceStopped();\r
     }\r
 \r
+    const int analogChannelStart  = 2;\r
 \r
     //==============================================================================\r
     uint64_t expectedElapsedAudioSamples = 0;\r
@@ -490,10 +488,11 @@ private:
     uint32_t actualBufferSize = 0;\r
     int actualNumberOfInputs = 0, actualNumberOfOutputs = 0;\r
 \r
-    AudioBuffer<float> audioInBuffer, audioOutBuffer;\r
     HeapBlock<const float*> channelInBuffer;\r
     HeapBlock<float*> channelOutBuffer;\r
 \r
+    bool includeAnalogSupport;\r
+\r
     JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR (BelaAudioIODevice)\r
 };\r
 \r
@@ -504,7 +503,6 @@ struct BelaAudioIODeviceType  : public AudioIODeviceType
 {\r
     BelaAudioIODeviceType() : AudioIODeviceType ("Bela") {}\r
 \r
-    // TODO: support analog outputs\r
     StringArray getDeviceNames (bool) const override                       { return StringArray (BelaAudioIODevice::belaTypeName); }\r
     void scanForDevices() override                                         {}\r
     int getDefaultDeviceIndex (bool) const override                        { return 0; }\r
@@ -513,6 +511,7 @@ struct BelaAudioIODeviceType  : public AudioIODeviceType
 \r
     AudioIODevice* createDevice (const String& outputName, const String& inputName) override\r
     {\r
+        // TODO: switching whether to support analog/digital with possible multiple Bela device types?\r
         if (outputName == BelaAudioIODevice::belaTypeName || inputName == BelaAudioIODevice::belaTypeName)\r
             return new BelaAudioIODevice();\r
 \r
index 69b0d6d20cc9ce3a5e33210af0ece549bf56bd88..6e9aa954791db08cd8c3ccf4e5f9c358246d006e 100644 (file)
@@ -60,7 +60,16 @@ namespace CoreMidiHelpers
         SInt32 objectID = 0;\r
 \r
         if (CHECK_ERROR (MIDIObjectGetIntegerProperty (entity, kMIDIPropertyUniqueID, &objectID)))\r
+        {\r
             info.identifier = String (objectID);\r
+        }\r
+        else\r
+        {\r
+            ScopedCFString str;\r
+\r
+            if (CHECK_ERROR (MIDIObjectGetStringProperty (entity, kMIDIPropertyUniqueID, &str.cfString)))\r
+                info.identifier = String::fromCFString (str.cfString);\r
+        }\r
 \r
         return info;\r
     }\r
@@ -211,9 +220,22 @@ namespace CoreMidiHelpers
 \r
         if (! hasEnabledNetworkSession)\r
         {\r
-            MIDINetworkSession* session = [MIDINetworkSession defaultSession];\r
-            session.enabled = YES;\r
-            session.connectionPolicy = MIDINetworkConnectionPolicy_Anyone;\r
+            auto iOSVersion = nsStringToJuce ([[UIDevice currentDevice] systemVersion]);\r
+            auto majorVersion = StringArray::fromTokens (iOSVersion, ".", {})[0].getIntValue();\r
+\r
+            if (majorVersion == 13)\r
+            {\r
+                // From the Xcode 11 release notes known issues:\r
+                // Attempting to create an MIDINetworkSession in a simulated device running\r
+                // iOS 13 won’t succeed. (54484923)\r
+                jassertfalse;\r
+            }\r
+            else\r
+            {\r
+                MIDINetworkSession* session = [MIDINetworkSession defaultSession];\r
+                session.enabled = YES;\r
+                session.connectionPolicy = MIDINetworkConnectionPolicy_Anyone;\r
+            }\r
 \r
             hasEnabledNetworkSession = true;\r
         }\r
@@ -375,7 +397,7 @@ namespace CoreMidiHelpers
     static Array<MIDIEndpointRef> getEndpoints (bool isInput)\r
     {\r
         Array<MIDIEndpointRef> endpoints;\r
-        auto numDevices = (isInput ? MIDIGetNumberOfSources() : MIDIGetNumberOfDevices());\r
+        auto numDevices = (isInput ? MIDIGetNumberOfSources() : MIDIGetNumberOfDestinations());\r
 \r
         for (ItemCount i = 0; i < numDevices; ++i)\r
             endpoints.add (isInput ? MIDIGetSource (i) : MIDIGetDestination (i));\r
index 039da4afabb8038530f612b862d3303af86930d8..330b86b2c03e76901af065ec4b49bab8d47ffec1 100644 (file)
@@ -494,6 +494,9 @@ public:
             if (status != noErr)\r
                 return false;\r
 \r
+            if (numFramesToRead == 0)\r
+                break;\r
+\r
             if ((int) numFramesToRead < numThisTime)\r
             {\r
                 numThisTime = (int) numFramesToRead;\r
index 17a85349dbafbe55dd2a5b8b24695d007a1e6b80..179d89f804fe5112a462c0d55406b09fde5c34bc 100644 (file)
@@ -35,7 +35,7 @@
 \r
   ID:               juce_audio_formats\r
   vendor:           juce\r
-  version:          5.4.4\r
+  version:          5.4.5\r
   name:             JUCE audio file format codecs\r
   description:      Classes for reading and writing various audio file formats.\r
   website:          http://www.juce.com/juce\r
index f61496638c734d73569e5dd98300c38bc896065e..adc374e1e817dcafc1d91723621d1f9c2f566494 100644 (file)
@@ -1521,7 +1521,7 @@ namespace AAXClasses
                                                   : juceParameters.getParamID (audioProcessor, parameterIndex);\r
 \r
                 aaxParamIDs.add (paramID);\r
-                auto aaxParamID = aaxParamIDs.getReference (parameterIndex++).getCharPointer();\r
+                auto* aaxParamID = aaxParamIDs.getReference (parameterIndex++).toRawUTF8();\r
 \r
                 paramMap.set (AAXClasses::getAAXParamHash (aaxParamID), juceParam);\r
 \r
@@ -1910,7 +1910,7 @@ namespace AAXClasses
         inline AAX_CParamID getAAXParamIDFromJuceIndex (int index) const noexcept\r
         {\r
             if (isPositiveAndBelow (index, aaxParamIDs.size()))\r
-                return aaxParamIDs.getReference (index).getCharPointer();\r
+                return aaxParamIDs.getReference (index).toRawUTF8();\r
 \r
             return nullptr;\r
         }\r
index 9c73eca29334d96ca4b36335ada780f9c7a1c2b7..0cc15378bda276e8702d0771e3ec8351fdfdd7ea 100644 (file)
@@ -42,7 +42,8 @@ namespace juce
     @tags{Audio}\r
 */\r
 class StandalonePluginHolder    : private AudioIODeviceCallback,\r
-                                  private Timer\r
+                                  private Timer,\r
+                                  private Value::Listener\r
 {\r
 public:\r
     //==============================================================================\r
@@ -78,9 +79,11 @@ public:
 \r
         : settings (settingsToUse, takeOwnershipOfSettings),\r
           channelConfiguration (channels),\r
-          shouldMuteInput (! isInterAppAudioConnected()),\r
           autoOpenMidiDevices (shouldAutoOpenMidiDevices)\r
     {\r
+        shouldMuteInput.addListener (this);\r
+        shouldMuteInput = ! isInterAppAudioConnected();\r
+\r
         createPlugin();\r
 \r
         auto inChannels = (channelConfiguration.size() > 0 ? channelConfiguration[0].numIns\r
@@ -158,6 +161,7 @@ public:
     //==============================================================================\r
     Value& getMuteInputValue()                           { return shouldMuteInput; }\r
     bool getProcessorHasPotentialFeedbackLoop() const    { return processorHasPotentialFeedbackLoop; }\r
+    void valueChanged (Value& value) override            { muteInput = (bool) value.getValue(); }\r
 \r
     //==============================================================================\r
     File getLastFile() const\r
@@ -406,6 +410,7 @@ public:
 \r
     // avoid feedback loop by default\r
     bool processorHasPotentialFeedbackLoop = true;\r
+    std::atomic<bool> muteInput { true };\r
     Value shouldMuteInput;\r
     AudioBuffer<float> emptyBuffer;\r
     bool autoOpenMidiDevices;\r
@@ -492,9 +497,7 @@ private:
                                 int numOutputChannels,\r
                                 int numSamples) override\r
     {\r
-        const bool inputMuted = shouldMuteInput.getValue();\r
-\r
-        if (inputMuted)\r
+        if (muteInput)\r
         {\r
             emptyBuffer.clear();\r
             inputChannelData = emptyBuffer.getArrayOfReadPointers();\r
index 3ede36fabce16fc3e0b5acf0f4763df73b4fd65d..9b9a7f9f38ea4bb4643d5c49ccebe1d6412d582c 100644 (file)
@@ -1110,18 +1110,35 @@ public:
             deleteEditor (true);\r
         }\r
 \r
-        if (chunkMemoryTime > 0\r
-             && chunkMemoryTime < juce::Time::getApproximateMillisecondCounter() - 2000\r
-             && ! recursionCheck)\r
         {\r
-            chunkMemory.reset();\r
-            chunkMemoryTime = 0;\r
+            ScopedLock lock (stateInformationLock);\r
+\r
+            if (chunkMemoryTime > 0\r
+                 && chunkMemoryTime < juce::Time::getApproximateMillisecondCounter() - 2000\r
+                 && ! recursionCheck)\r
+            {\r
+                chunkMemory.reset();\r
+                chunkMemoryTime = 0;\r
+            }\r
         }\r
 \r
         if (editorComp != nullptr)\r
             editorComp->checkVisibility();\r
     }\r
 \r
+    void setHasEditorFlag (bool shouldSetHasEditor)\r
+    {\r
+        auto hasEditor = (vstEffect.flags & Vst2::effFlagsHasEditor) != 0;\r
+\r
+        if (shouldSetHasEditor == hasEditor)\r
+            return;\r
+\r
+        if (shouldSetHasEditor)\r
+            vstEffect.flags |= Vst2::effFlagsHasEditor;\r
+        else\r
+            vstEffect.flags &= ~Vst2::effFlagsHasEditor;\r
+    }\r
+\r
     void createEditorComp()\r
     {\r
         if (hasShutdown || processor == nullptr)\r
@@ -1131,12 +1148,12 @@ public:
         {\r
             if (auto* ed = processor->createEditorIfNeeded())\r
             {\r
-                vstEffect.flags |= Vst2::effFlagsHasEditor;\r
+                setHasEditorFlag (true);\r
                 editorComp.reset (new EditorCompWrapper (*this, *ed));\r
             }\r
             else\r
             {\r
-                vstEffect.flags &= ~Vst2::effFlagsHasEditor;\r
+                setHasEditorFlag (false);\r
             }\r
         }\r
 \r
@@ -1702,10 +1719,7 @@ private:
     pointer_sized_int handleOpen (VstOpCodeArguments)\r
     {\r
         // Note: most hosts call this on the UI thread, but wavelab doesn't, so be careful in here.\r
-        if (processor->hasEditor())\r
-            vstEffect.flags |= Vst2::effFlagsHasEditor;\r
-        else\r
-            vstEffect.flags &= ~Vst2::effFlagsHasEditor;\r
+        setHasEditorFlag (processor->hasEditor());\r
 \r
         return 0;\r
     }\r
@@ -1857,7 +1871,9 @@ private:
         auto data = (void**) args.ptr;\r
         bool onlyStoreCurrentProgramData = (args.index != 0);\r
 \r
+        ScopedLock lock (stateInformationLock);\r
         chunkMemory.reset();\r
+\r
         if (onlyStoreCurrentProgramData)\r
             processor->getCurrentProgramStateInformation (chunkMemory);\r
         else\r
@@ -1880,15 +1896,19 @@ private:
             int32 byteSize = (int32) args.value;\r
             bool onlyRestoreCurrentProgramData = (args.index != 0);\r
 \r
-            chunkMemory.reset();\r
-            chunkMemoryTime = 0;\r
-\r
-            if (byteSize > 0 && data != nullptr)\r
             {\r
-                if (onlyRestoreCurrentProgramData)\r
-                    processor->setCurrentProgramStateInformation (data, byteSize);\r
-                else\r
-                    processor->setStateInformation (data, byteSize);\r
+                ScopedLock lock (stateInformationLock);\r
+\r
+                chunkMemory.reset();\r
+                chunkMemoryTime = 0;\r
+\r
+                if (byteSize > 0 && data != nullptr)\r
+                {\r
+                    if (onlyRestoreCurrentProgramData)\r
+                        processor->setCurrentProgramStateInformation (data, byteSize);\r
+                    else\r
+                        processor->setStateInformation (data, byteSize);\r
+                }\r
             }\r
         }\r
 \r
@@ -2272,8 +2292,9 @@ private:
     double sampleRate = 44100.0;\r
     int32 blockSize = 1024;\r
     Vst2::AEffect vstEffect;\r
+    CriticalSection stateInformationLock;\r
     juce::MemoryBlock chunkMemory;\r
-    juce::uint32 chunkMemoryTime = 0;\r
+    uint32 chunkMemoryTime = 0;\r
     std::unique_ptr<EditorCompWrapper> editorComp;\r
     Vst2::ERect editorBounds;\r
     MidiBuffer midiEvents;\r
index cd06128abd202efa37ccafa61de3e3ecf96c6c4a..d94d022a2dba1d0039ffea0808635439d8387877 100644 (file)
@@ -319,7 +319,7 @@ private:
     }\r
 \r
     //==============================================================================\r
-    Atomic<int> refCount;\r
+    std::atomic<int> refCount { 0 };\r
     std::unique_ptr<AudioProcessor> audioProcessor;\r
 \r
     //==============================================================================\r
@@ -469,7 +469,7 @@ public:
                 // Only update the AudioProcessor here if we're not playing,\r
                 // otherwise we get parallel streams of parameter value updates\r
                 // during playback\r
-                if (owner.vst3IsPlaying.get() == 0)\r
+                if (! owner.vst3IsPlaying)\r
                 {\r
                     auto value = static_cast<float> (v);\r
 \r
@@ -888,7 +888,7 @@ public:
                                                                                          / static_cast<Vst::ParamValue> (pluginInstance->getNumPrograms() - 1));\r
         }\r
 \r
-        if (componentHandler != nullptr)\r
+        if (componentHandler != nullptr && ! inSetupProcessing)\r
             componentHandler->restartComponent (Vst::kLatencyChanged | Vst::kParamValuesChanged);\r
     }\r
 \r
@@ -932,7 +932,9 @@ private:
     Vst::ParamID midiControllerToParameter[numMIDIChannels][Vst::kCountCtrlNumber];\r
 \r
     //==============================================================================\r
-    Atomic<int> vst3IsPlaying { 0 };\r
+    std::atomic<bool> vst3IsPlaying     { false },\r
+                      inSetupProcessing { false };\r
+\r
     float lastScaleFactorReceived = 1.0f;\r
 \r
     void setupParameters()\r
@@ -1197,10 +1199,12 @@ private:
                 {\r
                     if (auto* constrainer = editor->getConstrainer())\r
                     {\r
-                        auto minW = (double) constrainer->getMinimumWidth();\r
-                        auto maxW = (double) constrainer->getMaximumWidth();\r
-                        auto minH = (double) constrainer->getMinimumHeight();\r
-                        auto maxH = (double) constrainer->getMaximumHeight();\r
+                        auto scale = editor->getTransform().getScaleFactor();\r
+\r
+                        auto minW = (double) (constrainer->getMinimumWidth()  * scale);\r
+                        auto maxW = (double) (constrainer->getMaximumWidth()  * scale);\r
+                        auto minH = (double) (constrainer->getMinimumHeight() * scale);\r
+                        auto maxH = (double) (constrainer->getMaximumHeight() * scale);\r
 \r
                         auto width  = (double) (rectToCheck->right - rectToCheck->left);\r
                         auto height = (double) (rectToCheck->bottom - rectToCheck->top);\r
@@ -1460,7 +1464,7 @@ private:
                        #if JUCE_MAC\r
                         if (host.isWavelab() || host.isReaper())\r
                        #else\r
-                        if (host.isWavelab())\r
+                        if (host.isWavelab() || host.isAbletonLive())\r
                        #endif\r
                             setBounds (0, 0, w, h);\r
                     }\r
@@ -1578,7 +1582,7 @@ public:
     ~JuceVST3Component() override\r
     {\r
         if (juceVST3EditController != nullptr)\r
-            juceVST3EditController->vst3IsPlaying = 0;\r
+            juceVST3EditController->vst3IsPlaying = false;\r
 \r
         if (pluginInstance != nullptr)\r
             if (pluginInstance->getPlayHead() == this)\r
@@ -1644,7 +1648,7 @@ public:
     tresult PLUGIN_API disconnect (IConnectionPoint*) override\r
     {\r
         if (juceVST3EditController != nullptr)\r
-            juceVST3EditController->vst3IsPlaying = 0;\r
+            juceVST3EditController->vst3IsPlaying = false;\r
 \r
         juceVST3EditController = nullptr;\r
         return kResultTrue;\r
@@ -2350,6 +2354,8 @@ public:
 \r
     tresult PLUGIN_API setupProcessing (Vst::ProcessSetup& newSetup) override\r
     {\r
+        ScopedInSetupProcessingSetter inSetupProcessingSetter (juceVST3EditController);\r
+\r
         if (canProcessSampleSize (newSetup.symbolicSampleSize) != kResultTrue)\r
             return kResultFalse;\r
 \r
@@ -2470,14 +2476,14 @@ public:
             processContext = *data.processContext;\r
 \r
             if (juceVST3EditController != nullptr)\r
-                juceVST3EditController->vst3IsPlaying = processContext.state & Vst::ProcessContext::kPlaying;\r
+                juceVST3EditController->vst3IsPlaying = (processContext.state & Vst::ProcessContext::kPlaying) != 0;\r
         }\r
         else\r
         {\r
             zerostruct (processContext);\r
 \r
             if (juceVST3EditController != nullptr)\r
-                juceVST3EditController->vst3IsPlaying = 0;\r
+                juceVST3EditController->vst3IsPlaying = false;\r
         }\r
 \r
         midiBuffer.clear();\r
@@ -2513,6 +2519,26 @@ public:
     }\r
 \r
 private:\r
+    //==============================================================================\r
+    struct ScopedInSetupProcessingSetter\r
+    {\r
+        ScopedInSetupProcessingSetter (JuceVST3EditController* c)\r
+            : controller (c)\r
+        {\r
+            if (controller != nullptr)\r
+                controller->inSetupProcessing = true;\r
+        }\r
+\r
+        ~ScopedInSetupProcessingSetter()\r
+        {\r
+            if (controller != nullptr)\r
+                controller->inSetupProcessing = false;\r
+        }\r
+\r
+    private:\r
+        JuceVST3EditController* controller = nullptr;\r
+    };\r
+\r
     //==============================================================================\r
     template <typename FloatType>\r
     void processAudio (Vst::ProcessData& data, Array<FloatType*>& channelList)\r
@@ -2732,7 +2758,7 @@ private:
     //==============================================================================\r
     ScopedJuceInitialiser_GUI libraryInitialiser;\r
 \r
-    Atomic<int> refCount { 1 };\r
+    std::atomic<int> refCount { 1 };\r
 \r
     AudioProcessor* pluginInstance;\r
     ComSmartPtr<Vst::IHostApplication> host;\r
@@ -3049,7 +3075,7 @@ struct JucePluginFactory  : public IPluginFactory3
 \r
 private:\r
     //==============================================================================\r
-    Atomic<int> refCount { 1 };\r
+    std::atomic<int> refCount { 1 };\r
     const PFactoryInfo factoryInfo;\r
     ComSmartPtr<Vst::IHostApplication> host;\r
 \r
index 4988e5b6900e9b771eca3830f0f8270bb972cf93..d884d0ac9c60c7962118c7b82bab495729470eaf 100644 (file)
@@ -35,7 +35,7 @@
 \r
   ID:               juce_audio_plugin_client\r
   vendor:           juce\r
-  version:          5.4.4\r
+  version:          5.4.5\r
   name:             JUCE audio plugin wrapper classes\r
   description:      Classes for building VST, VST3, AudioUnit, AAX and RTAS plugins.\r
   website:          http://www.juce.com/juce\r
index af6e491b877cd4dc73b8d79b1f2f1e63011d65db..33974d48713f6d0a769ecfcfe01094f6ef9e991e 100644 (file)
@@ -1213,8 +1213,11 @@ public:
         if (AudioUnitGetProperty (audioUnit, kAudioUnitProperty_FactoryPresets,\r
                                   kAudioUnitScope_Global, 0, &presets, &sz) == noErr)\r
         {\r
-            num = (int) CFArrayGetCount (presets);\r
-            CFRelease (presets);\r
+            if (presets != nullptr)\r
+            {\r
+                num = (int) CFArrayGetCount (presets);\r
+                CFRelease (presets);\r
+            }\r
         }\r
 \r
         return num;\r
index 63b95b979322e5033dec7e369c5b677d7202218f..14810fb59a995fd391de025765a014a2f183088f 100644 (file)
@@ -189,8 +189,8 @@ static void toProcessContext (Vst::ProcessContext& context, AudioPlayHead* playH
         AudioPlayHead::CurrentPositionInfo position;\r
         playHead->getCurrentPosition (position);\r
 \r
-        context.projectTimeSamples  = position.timeInSamples; //Must always be valid, as stated by the VST3 SDK\r
-        context.projectTimeMusic    = position.timeInSeconds; //Does not always need to be valid...\r
+        context.projectTimeSamples  = position.timeInSamples; // Must always be valid, as stated by the VST3 SDK\r
+        context.projectTimeMusic    = position.ppqPosition;   // Does not always need to be valid...\r
         context.tempo               = position.bpm;\r
         context.timeSigNumerator    = position.timeSigNumerator;\r
         context.timeSigDenominator  = position.timeSigDenominator;\r
index 35293b8b1c503b4b4ad02dbcb9351e4f5aed20c5..85dfb785cc0a76ea51c71a811310d90aefa507f7 100644 (file)
@@ -2796,7 +2796,11 @@ public:
 \r
         Vst2::ERect* rect = nullptr;\r
         dispatch (Vst2::effEditGetRect, 0, 0, &rect, 0);\r
-        setSize (rect->right - rect->left, rect->bottom - rect->top);\r
+\r
+        if (rect != nullptr)\r
+            setSize (rect->right - rect->left, rect->bottom - rect->top);\r
+        else\r
+            setSize (1, 1);\r
 \r
         setOpaque (true);\r
         setVisible (true);\r
index cb46f60c9681be1db8fe0f7074066cf178b837d1..62b0f498d8dfcec4a047d2112b1cd6d5aef599a7 100644 (file)
@@ -35,7 +35,7 @@
 \r
   ID:               juce_audio_processors\r
   vendor:           juce\r
-  version:          5.4.4\r
+  version:          5.4.5\r
   name:             JUCE audio processor classes\r
   description:      Classes for loading and playing VST, AU, LADSPA, or internally-generated audio processors.\r
   website:          http://www.juce.com/juce\r
index f36e3553624d55f3b735accf4594d18ea1db1621..04a11a92328947f0df276e8007bbf540217fe1ef 100644 (file)
@@ -1011,7 +1011,7 @@ public:
     /** Returns the group of parameters managed by this AudioProcessor. */\r
     const AudioProcessorParameterGroup& getParameterTree() const;\r
 \r
-    /** Returns the group of parameters managed by this AudioProcessor. */\r
+    /** Sets the group of parameters managed by this AudioProcessor. */\r
     void setParameterTree (AudioProcessorParameterGroup&& newTree);\r
 \r
     /** A processor should implement this method so that the host can ask it to\r
index 1fb8a495da8891106a225af03d7d072539ac1b74..f7ce5789fb06c942f0f2cb47d0ededed2571bb0a 100644 (file)
@@ -162,6 +162,7 @@ public:
     struct JUCE_API  Connection\r
     {\r
         //==============================================================================\r
+        Connection() = default;\r
         Connection (NodeAndChannel source, NodeAndChannel destination) noexcept;\r
 \r
         Connection (const Connection&) = default;\r
@@ -173,10 +174,10 @@ public:
 \r
         //==============================================================================\r
         /** The channel and node which is the input source for this connection. */\r
-        NodeAndChannel source;\r
+        NodeAndChannel source { {}, 0 };\r
 \r
         /** The channel and node which is the input source for this connection. */\r
-        NodeAndChannel destination;\r
+        NodeAndChannel destination { {}, 0 };\r
     };\r
 \r
     //==============================================================================\r
index 0981e119764eb80781ce064a8f15dbcf7c75627c..23714e2b8d4155a6abef34ed3ba202bfe8578d50 100644 (file)
@@ -42,7 +42,7 @@ public:
     */\r
     AudioProcessorParameterWithID (const String& parameterID,\r
                                    const String& parameterName,\r
-                                   const String& parameterLabel = String(),\r
+                                   const String& parameterLabel = {},\r
                                    Category parameterCategory = AudioProcessorParameter::genericParameter);\r
 \r
     /** Destructor. */\r
@@ -60,11 +60,11 @@ public:
     /** Provides access to the parameter's category. */\r
     const Category category;\r
 \r
-private:\r
     String getName (int) const override;\r
     String getLabel() const override;\r
     Category getCategory() const override;\r
 \r
+private:\r
     JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR (AudioProcessorParameterWithID)\r
 };\r
 \r
index 681d3e0f048bc22bca9c6d4d48db548f8678428d..ad36c5aa0d186bf5af0382c9f0264c3a6d82498c 100644 (file)
@@ -71,7 +71,9 @@ void AudioProcessorValueTreeState::Parameter::valueChanged (float newValue)
         return;\r
 \r
     lastValue = newValue;\r
-    sendValueChangedMessageToListeners (newValue);\r
+\r
+    if (onValueChanged != nullptr)\r
+        onValueChanged();\r
 }\r
 \r
 //==============================================================================\r
@@ -87,6 +89,9 @@ public:
           unnormalisedValue (getRange().convertFrom0to1 (parameter.getDefaultValue()))\r
     {\r
         parameter.addListener (this);\r
+\r
+        if (auto* ptr = dynamic_cast<Parameter*> (&parameter))\r
+            ptr->onValueChanged = [this] { parameterValueChanged ({}, {}); };\r
     }\r
 \r
     ~ParameterAdapter() override        { parameter.removeListener (this); }\r
index a0cc2b0e0f587d0ae61336dee37c46e0f6b47eb4..f1ee8a434abc0458489602e35d2b8214168bf9ac 100644 (file)
@@ -362,6 +362,10 @@ public:
     UndoManager* const undoManager;\r
 \r
     //==============================================================================\r
+private:\r
+    class ParameterAdapter;\r
+\r
+public:\r
     /** A parameter class that maintains backwards compatibility with deprecated\r
         AudioProcessorValueTreeState functionality.\r
 \r
@@ -416,9 +420,13 @@ public:
     private:\r
         void valueChanged (float) override;\r
 \r
+        std::function<void()> onValueChanged;\r
+\r
         const float unsnappedDefault;\r
         const bool metaParameter, automatable, discrete, boolean;\r
-        float lastValue = 0.0f;\r
+        float lastValue = -1.0f;\r
+\r
+        friend class AudioProcessorValueTreeState::ParameterAdapter;\r
     };\r
 \r
     //==============================================================================\r
@@ -523,8 +531,6 @@ private:
                                                                             bool, bool, bool, AudioProcessorParameter::Category, bool));\r
 \r
     //==============================================================================\r
-    class ParameterAdapter;\r
-\r
    #if JUCE_UNIT_TESTS\r
     friend struct ParameterAdapterTests;\r
    #endif\r
index 02bd03b0eb3f58b16ca4805f15d92952030bb606..303632067a602eb23e921415fd7e85b03eafc64c 100644 (file)
@@ -125,7 +125,7 @@ public:
     AudioDeviceManager& deviceManager;\r
 \r
 private:\r
-    //=============================================================================\r
+    //==============================================================================\r
     AudioDeviceManager defaultDeviceManager;\r
     AudioSourcePlayer audioSourcePlayer;\r
     bool usingCustomDeviceManager;\r
index 72adf9a28c66ba7570c4a8eda4e9462283d078f8..e346c70b4b60038164c343957f17769bdee33353 100644 (file)
@@ -35,7 +35,7 @@
 \r
   ID:               juce_audio_utils\r
   vendor:           juce\r
-  version:          5.4.4\r
+  version:          5.4.5\r
   name:             JUCE extra audio utility classes\r
   description:      Classes for audio-related GUI and miscellaneous tasks.\r
   website:          http://www.juce.com/juce\r
index eccb0b82e285ce85d2225796658103f3ee58e807..2b564aa1fb693867293d95aae75ed0f6e4834a58 100644 (file)
@@ -51,7 +51,7 @@ public:
             setBounds (bounds);\r
 \r
         toFront (true);\r
-        setOpaque (! bounds.isEmpty());\r
+        setOpaque (true);\r
 \r
         controller = [[CABTMIDICentralViewController alloc] init];\r
         nativeSelectorComponent.setView ([controller view]);\r
index eddc0b9a768f9124caf840efb5a969a9a17bcb8e..41def683c666ca546c3ab83613b26d55bae56c1e 100644 (file)
@@ -320,7 +320,7 @@ public:
     /** Metadata for a given config item */\r
     struct ConfigMetaData\r
     {\r
-        static constexpr int32 numOptionNames = 8;\r
+        static constexpr int32 numOptionNames = 16;\r
 \r
         enum class ConfigType\r
         {\r
index 0b288c6f258017bf252327876d392cba638440c3..e93e5857e03d2ccae1221c81f3f8cd2bc0db2ad5 100644 (file)
@@ -47,7 +47,7 @@ struct BlockConfigManager
     void setDeviceIndex (TopologyIndex newDeviceIndex)                       { deviceIndex = newDeviceIndex; }\r
     void setDeviceComms (PhysicalTopologySource::DeviceConnection* newConn)  { deviceConnection = newConn; }\r
 \r
-    static constexpr uint32 numConfigItems = 64;\r
+    static constexpr uint32 numConfigItems = 69;\r
 \r
     /** Structure describing a configuration */\r
     struct ConfigDescription\r
@@ -100,10 +100,17 @@ struct BlockConfigManager
         { mode,                 4,      1,      5,      false,  "Mode",                 ConfigType::integer,    {},               "Play mode" },\r
         { volume,               100,    0,      127,    false,  "Volume",               ConfigType::integer,    {},               "Play mode" },\r
         { scale,                0,      0,      18,     false,  "Scale",                ConfigType::integer,    {},               "Play mode" }, // NOTE: Should be options\r
+        { key,                  0,      0,      11,     false,  "Key",                  ConfigType::options,    { "C", "C#", "D", "D#",\r
+                                                                                                                  "E", "F", "F#", "G",\r
+                                                                                                                  "G#", "A", "A#", "B"}, "Play mode" },\r
         { hideMode,             0,      0,      1,      false,  "Hide Mode",            ConfigType::boolean,    {},               "Play mode" },\r
         { chord,                0,      0,      127,    false,  "Chord",                ConfigType::integer,    {},               "Play mode" }, // NOTE: Should be options\r
         { arpPattern,           0,      0,      127,    false,  "Arp Pattern",          ConfigType::integer,    {},               "Play mode" },\r
         { tempo,                120,    1,      300,    false,  "Tempo",                ConfigType::integer,    {},               "Rhythm" },\r
+        { key,                  0,      0,      11,     false,  "Key",                  ConfigType::options,    { "C", "C#", "D", "D#",\r
+                                                                                                                  "E", "F", "F#", "G",\r
+                                                                                                                  "G#", "A", "A#", "B"}, "Play mode" },\r
+        { autoTransposeToKey,   0,      0,      1,      false,  "Auto Transpose To Key",ConfigType::boolean,    {},               "Pitch" },\r
         { xTrackingMode,        1,      1,      4,      false,  "Glide Tracking Mode",  ConfigType::options,    { "Multi-Channel",\r
                                                                                                                   "Last Played",\r
                                                                                                                   "Highest",\r
@@ -122,6 +129,9 @@ struct BlockConfigManager
                                                                                                                   "Hardest" },    "Play mode" },\r
 \r
         { gammaCorrection,      0,      0,      1,      false,  "Gamma Correction",     ConfigType::boolean,    {},               {} },\r
+        { globalKeyColour,      INT32_MIN, INT32_MIN, INT32_MAX, false,  "Global Key Colour", ConfigType::colour, {},             "Colour" },\r
+        { rootKeyColour,        INT32_MIN, INT32_MIN, INT32_MAX, false,  "Root Key Colour"  , ConfigType::colour, {},             "Colour" },\r
+        { brightness,           100,    0,    100,      false,  "Brightness",           ConfigType::integer,    {},               "Colour" },\r
 \r
         // These can be defined for unique usage for a given Littlefoot script\r
         { user0,                0,    0,      127,      false,  {},                     ConfigType::integer,    {},               {} },\r
index 2b99311d3af4ca803013c432ce74dfe319fc64d8..5f7287d9397077bf0f409e8f2bd484961b0011b8 100644 (file)
@@ -137,7 +137,7 @@ public:
     void clear() noexcept                      { touches.clear(); }\r
 \r
 private:\r
-    //==========================================================================\r
+    //==============================================================================\r
     static bool matches (const TouchSurface::Touch& t1,\r
                          const TouchSurface::Touch& t2) noexcept\r
     {\r
index 5ae9a83b598ab045b71e56301b24624ae183d8a1..aa8f3396ce613ef2d8f4eefa7cae35129a6befbc 100644 (file)
@@ -31,7 +31,7 @@
 \r
   ID:                 juce_blocks_basics\r
   vendor:             juce\r
-  version:            5.4.4\r
+  version:            5.4.5\r
   name:               Provides low-level control over ROLI BLOCKS devices\r
   description:        JUCE wrapper for low-level control over ROLI BLOCKS devices.\r
   website:            http://developer.roli.com\r
index c124ecd0f12b227fa0031fec055cdd4ae1651b73..045244790f99645b305064e571be4b638ce78f9f 100644 (file)
 \r
   ==============================================================================\r
 */\r
+#ifndef JUCE_DUMP_LITTLEFOOT_HEAP_STATUS\r
+  #define JUCE_DUMP_LITTLEFOOT_HEAP_STATUS 0\r
+#endif\r
 \r
-#define JUCE_DUMP_LITTLEFOOT_HEAP_STATUS 0\r
+#if JUCE_DUMP_LITTLEFOOT_HEAP_STATUS\r
+ #define JUCE_LOG_LITTLEFOOT_HEAP(text) DBG(text)\r
+#else\r
+ #define JUCE_LOG_LITTLEFOOT_HEAP(text)\r
+#endif\r
 \r
 namespace littlefoot\r
 {\r
@@ -43,15 +50,27 @@ struct LittleFootRemoteHeap
         resetDeviceStateToUnknown();\r
     }\r
 \r
-    void clear() noexcept\r
+    void reset()\r
     {\r
+        JUCE_LOG_LITTLEFOOT_HEAP ("Resetting heap state");\r
+        clearTargetData();\r
+        resetDeviceStateToUnknown();\r
+        lastPacketIndexReceived = 0;\r
+    }\r
+\r
+    void clearTargetData() noexcept\r
+    {\r
+        JUCE_LOG_LITTLEFOOT_HEAP ("Clearing target heap data");\r
         zeromem (targetData, sizeof (targetData));\r
-        invalidateData();\r
+        needsSyncing = true;\r
+        programStateKnown = false;\r
     }\r
 \r
     void resetDeviceStateToUnknown()\r
     {\r
-        invalidateData();\r
+        JUCE_LOG_LITTLEFOOT_HEAP ("Resetting device state to unknown");\r
+        needsSyncing = true;\r
+        programStateKnown = false;\r
         messagesSent.clear();\r
         resetDataRangeToUnknown (0, ImplementationClass::maxBlockSize);\r
     }\r
@@ -66,20 +85,19 @@ struct LittleFootRemoteHeap
 \r
     void setByte (size_t offset, uint8 value) noexcept\r
     {\r
-        if (offset < blockSize)\r
+        if (offset >= blockSize)\r
         {\r
-            if (targetData[offset] != value)\r
-            {\r
-                targetData[offset] = value;\r
-                needsSyncing = true;\r
-\r
-                if (programStateKnown && offset < programSize)\r
-                    programStateKnown = false;\r
-            }\r
+            jassertfalse;\r
+            return;\r
         }\r
-        else\r
+\r
+        if (targetData[offset] != value)\r
         {\r
-            jassertfalse;\r
+            targetData[offset] = value;\r
+            needsSyncing = true;\r
+\r
+            if (offset < programSize)\r
+                programStateKnown = false;\r
         }\r
     }\r
 \r
@@ -99,8 +117,14 @@ struct LittleFootRemoteHeap
 \r
         if (readLittleEndianBitsInBuffer (targetData, startBit, numBits) != value)\r
         {\r
+            JUCE_LOG_LITTLEFOOT_HEAP ("Set bits sync " << String (startBit) << " " << String (numBits) << String (value));\r
+\r
             writeLittleEndianBitsInBuffer (targetData, startBit, numBits, value);\r
-            invalidateData();\r
+\r
+            needsSyncing = true;\r
+\r
+            if (startBit < programSize)\r
+                programStateKnown = false;\r
         }\r
     }\r
 \r
@@ -113,12 +137,6 @@ struct LittleFootRemoteHeap
         return 0;\r
     }\r
 \r
-    void invalidateData() noexcept\r
-    {\r
-        needsSyncing = true;\r
-        programStateKnown = false;\r
-    }\r
-\r
     bool isFullySynced() const noexcept\r
     {\r
         return ! needsSyncing;\r
@@ -167,7 +185,8 @@ struct LittleFootRemoteHeap
 \r
             m->dispatchTime = Time::getCurrentTime();\r
             bi.sendMessageToDevice (m->packet);\r
-            //DBG ("Sending packet " << (int) m->packetIndex << " - " << m->packet.size() << " bytes, device " << bi.getDeviceIndex());\r
+\r
+            JUCE_LOG_LITTLEFOOT_HEAP ("Sending packet " << (int) m->packetIndex << " - " << m->packet.size() << " bytes, device " << bi.getDeviceIndex());\r
 \r
             if (getTotalSizeOfMessagesSent() > 200)\r
                 break;\r
@@ -176,43 +195,45 @@ struct LittleFootRemoteHeap
 \r
     void handleACKFromDevice (ImplementationClass& bi, uint32 packetIndex) noexcept\r
     {\r
-        //DBG ("ACK " << (int) packetIndex << "   device " << (int) bi.getDeviceIndex());\r
+        if (packetIndex == lastPacketIndexReceived)\r
+            return;\r
 \r
-        if (lastPacketIndexReceived != packetIndex)\r
-        {\r
-            lastPacketIndexReceived = packetIndex;\r
+        JUCE_LOG_LITTLEFOOT_HEAP ("ACK " << (int) packetIndex << "   device " << (int) bi.getDeviceIndex()\r
+                                  << ", last packet received " << String (lastPacketIndexReceived));\r
 \r
-            for (int i = messagesSent.size(); --i >= 0;)\r
-            {\r
-                auto& m = *messagesSent.getUnchecked(i);\r
+        lastPacketIndexReceived = packetIndex;\r
 \r
-                if (m.packetIndex == packetIndex)\r
-                {\r
-                    for (uint32 j = 0; j < blockSize; ++j)\r
-                        deviceState[j] = m.resultDataState[j];\r
+        for (int i = messagesSent.size(); --i >= 0;)\r
+        {\r
+            auto& m = *messagesSent.getUnchecked(i);\r
 \r
-                    programStateKnown = false;\r
-                    messagesSent.removeRange (0, i + 1);\r
-                    dumpStatus();\r
-                    sendChanges (bi, false);\r
+            if (m.packetIndex == packetIndex)\r
+            {\r
+                for (uint32 j = 0; j < blockSize; ++j)\r
+                    deviceState[j] = m.resultDataState[j];\r
 \r
-                    if (messagesSent.isEmpty())\r
-                        needsSyncing = false;\r
+                programStateKnown = false;\r
+                messagesSent.removeRange (0, i + 1);\r
+                dumpStatus();\r
+                sendChanges (bi, false);\r
 \r
-                    return;\r
+                if (messagesSent.isEmpty())\r
+                {\r
+                    JUCE_LOG_LITTLEFOOT_HEAP ("Heap fully synced");\r
+                    needsSyncing = false;\r
                 }\r
-            }\r
 \r
-            resetDeviceStateToUnknown();\r
+                return;\r
+            }\r
         }\r
+\r
+        resetDeviceStateToUnknown();\r
     }\r
 \r
     bool isProgramLoaded() noexcept\r
     {\r
         if (! programStateKnown)\r
         {\r
-            programStateKnown = true;\r
-\r
             uint8 deviceMemory[ImplementationClass::maxBlockSize];\r
 \r
             for (size_t i = 0; i < blockSize; ++i)\r
@@ -221,6 +242,8 @@ struct LittleFootRemoteHeap
             littlefoot::Program prog (deviceMemory, (uint32) blockSize);\r
             programLoaded = prog.checksumMatches();\r
             programSize = prog.getProgramSize();\r
+\r
+            programStateKnown = true;\r
         }\r
 \r
         return programLoaded;\r
@@ -287,8 +310,8 @@ private:
 \r
         ignoreUnused (proportionOK);\r
 \r
-        DBG ("Heap: " << areas << "  " << String (roundToInt (100 * proportionOK)) << "%  "\r
-               << (isProgramLoaded() ? "Ready" : "Loading"));\r
+        JUCE_LOG_LITTLEFOOT_HEAP ("Heap: " << areas << "  " << String (roundToInt (100 * proportionOK))\r
+                                     << "%  " << (isProgramLoaded() ? "Ready" : "Loading"));\r
        #endif\r
     }\r
 \r
index 4a38c41683cdccbf1bd26a06745566c31ffe1ae4..b2399d5007be1719c553674af8293a7d70d58181 100644 (file)
@@ -303,12 +303,17 @@ enum ConfigItemId
     chord               = 24,\r
     arpPattern          = 25,\r
     tempo               = 26,\r
+    key                 = 27,\r
+    autoTransposeToKey  = 28,\r
     // Tracking\r
     xTrackingMode       = 30,\r
     yTrackingMode       = 31,\r
     zTrackingMode       = 32,\r
     // Graphics\r
     gammaCorrection     = 33,\r
+    globalKeyColour     = 34,\r
+    rootKeyColour       = 35,\r
+    brightness          = 36,\r
     // User\r
     user0               = 64,\r
     user1               = 65,\r
@@ -348,7 +353,7 @@ static constexpr uint8 numberOfUserConfigs = 32;
 static constexpr uint8 maxConfigIndex = uint8 (ConfigItemId::user0) + numberOfUserConfigs;\r
 \r
 static constexpr uint8 configUserConfigNameLength = 32;\r
-static constexpr uint8 configMaxOptions = 8;\r
+static constexpr uint8 configMaxOptions = 16;\r
 static constexpr uint8 configOptionNameLength = 16;\r
 \r
 //==============================================================================\r
@@ -591,6 +596,14 @@ static constexpr const char* ledProgramLittleFootFunctions[] =
     "setButtonMinMaxDefault/viiii",\r
     "setButtonColours/viii",\r
     "setButtonTriState/vii",\r
+    "padControllerInitDefault/vb",\r
+    "padControllerReset/v",\r
+    "padControllerRegenDefault/v",\r
+    "padControllerRepaint/v",\r
+    "padControllerDrawPad/vi",\r
+    "setUseDefaultKeyHandler/vb",\r
+    "setUseDefaultKeyHandler/vbb",\r
+\r
     nullptr\r
 };\r
 \r
index f7f581c1ce6aa24f3c2f172d6167dfb9f26e6409..6d3a7fbde12e3377e6f6210cc7d6dbbf30556569 100644 (file)
@@ -83,16 +83,11 @@ public:
         if (connectionTime == Time())\r
             connectionTime = Time::getCurrentTime();\r
 \r
-        versionNumber = deviceInfo.version.asString();\r
-        name = deviceInfo.name.asString();\r
-        isMaster = deviceInfo.isMaster;\r
-        masterUID = deviceInfo.masterUid;\r
-        batteryCharging = deviceInfo.batteryCharging;\r
-        batteryLevel = deviceInfo.batteryLevel;\r
-        topologyIndex = deviceInfo.index;\r
+        updateDeviceInfo (deviceInfo);\r
+\r
+        remoteHeap.reset();\r
 \r
         setProgram (nullptr);\r
-        remoteHeap.resetDeviceStateToUnknown();\r
 \r
         if (auto surface = dynamic_cast<TouchSurfaceImplementation*> (touchSurface.get()))\r
             surface->activateTouchSurface();\r
@@ -100,6 +95,17 @@ public:
         updateMidiConnectionListener();\r
     }\r
 \r
+    void updateDeviceInfo (const DeviceInfo& deviceInfo)\r
+    {\r
+        versionNumber = deviceInfo.version.asString();\r
+        name = deviceInfo.name.asString();\r
+        isMaster = deviceInfo.isMaster;\r
+        masterUID = deviceInfo.masterUid;\r
+        batteryCharging = deviceInfo.batteryCharging;\r
+        batteryLevel = deviceInfo.batteryLevel;\r
+        topologyIndex = deviceInfo.index;\r
+    }\r
+\r
     void setToMaster (bool shouldBeMaster)\r
     {\r
         isMaster = shouldBeMaster;\r
@@ -289,7 +295,7 @@ public:
 \r
         if (program == nullptr)\r
         {\r
-            remoteHeap.clear();\r
+            remoteHeap.clearTargetData();\r
             return Result::ok();\r
         }\r
 \r
@@ -311,7 +317,7 @@ public:
         programSize = (uint32) size;\r
 \r
         remoteHeap.resetDataRangeToUnknown (0, remoteHeap.blockSize);\r
-        remoteHeap.clear();\r
+        remoteHeap.clearTargetData();\r
         remoteHeap.sendChanges (*this, true);\r
 \r
         remoteHeap.resetDataRangeToUnknown (0, (uint32) size);\r
@@ -504,10 +510,15 @@ public:
 \r
         remoteHeap.sendChanges (*this, false);\r
 \r
-        if (lastMessageSendTime < Time::getCurrentTime() - RelativeTime::milliseconds (pingIntervalMs))\r
+        if (lastMessageSendTime < Time::getCurrentTime() - getPingInterval())\r
             sendCommandMessage (BlocksProtocol::ping);\r
     }\r
 \r
+    RelativeTime getPingInterval()\r
+    {\r
+        return RelativeTime::milliseconds (isMaster ? masterPingIntervalMs : dnaPingIntervalMs);\r
+    }\r
+\r
     //==============================================================================\r
     int32 getLocalConfigValue (uint32 item) override\r
     {\r
@@ -629,7 +640,8 @@ public:
 \r
     MIDIDeviceConnection* listenerToMidiConnection = nullptr;\r
 \r
-    static constexpr int pingIntervalMs = 400;\r
+    static constexpr int masterPingIntervalMs = 400;\r
+    static constexpr int dnaPingIntervalMs = 1666;\r
 \r
     static constexpr uint32 maxBlockSize = BlocksProtocol::padBlockProgramAndHeapSize;\r
     static constexpr uint32 maxPacketCounter = BlocksProtocol::PacketCounter::maxValue;\r
diff --git a/modules/juce_blocks_basics/topology/internal/juce_BlockSerialReader.cpp b/modules/juce_blocks_basics/topology/internal/juce_BlockSerialReader.cpp
new file mode 100644 (file)
index 0000000..c4a94e9
--- /dev/null
@@ -0,0 +1,130 @@
+/*\r
+  ==============================================================================\r
+\r
+   This file is part of the JUCE library.\r
+   Copyright (c) 2019 - ROLI Ltd.\r
+\r
+   JUCE is an open source library subject to commercial or open-source\r
+   licensing.\r
+\r
+   The code included in this file is provided under the terms of the ISC license\r
+   http://www.isc.org/downloads/software-support-policy/isc-license. Permission\r
+   To use, copy, modify, and/or distribute this software for any purpose with or\r
+   without fee is hereby granted provided that the above copyright notice and\r
+   this permission notice appear in all copies.\r
+\r
+   JUCE IS PROVIDED "AS IS" WITHOUT ANY WARRANTY, AND ALL WARRANTIES, WHETHER\r
+   EXPRESSED OR IMPLIED, INCLUDING MERCHANTABILITY AND FITNESS FOR PURPOSE, ARE\r
+   DISCLAIMED.\r
+\r
+  ==============================================================================\r
+*/\r
+\r
+namespace juce\r
+{\r
+    class BlockSerialReader\r
+        : private MIDIDeviceConnection::Listener,\r
+          private Timer\r
+    {\r
+    public:\r
+        //==============================================================================\r
+        BlockSerialReader (MIDIDeviceConnection& deviceConnectionToUse) : deviceConnection (deviceConnectionToUse)\r
+        {\r
+            deviceConnection.addListener (this);\r
+            startTimer (10);\r
+        }\r
+\r
+        ~BlockSerialReader() override\r
+        {\r
+            deviceConnection.removeListener (this);\r
+        }\r
+\r
+        bool hasSerial() const { return serial.isNotEmpty(); }\r
+\r
+        String getSerial() const { return serial; }\r
+\r
+    private:\r
+        MIDIDeviceConnection& deviceConnection;\r
+        String serial;\r
+\r
+        bool shouldStop() { return hasSerial(); }\r
+\r
+        //==============================================================================\r
+        void timerCallback() override\r
+        {\r
+            if (shouldStop())\r
+            {\r
+                stopTimer();\r
+                return;\r
+            }\r
+\r
+            sendRequest();\r
+            startTimer (300);\r
+        }\r
+\r
+        void sendRequest()\r
+        {\r
+            const uint8 dumpRequest[] = { 0xf0, 0x00, 0x21, 0x10, 0x78, 0x3f, 0xf7 };\r
+            deviceConnection.sendMessageToDevice (dumpRequest, sizeof (dumpRequest));\r
+        }\r
+\r
+        void handleIncomingMidiMessage (const MidiMessage& message) override\r
+        {\r
+            if (hasSerial())\r
+                return;\r
+\r
+            if (isResponse (message))\r
+                parseResponse (message);\r
+        }\r
+\r
+        void connectionBeingDeleted (const MIDIDeviceConnection&) override\r
+        {\r
+            stopTimer();\r
+        }\r
+\r
+        bool isResponse (const MidiMessage message)\r
+        {\r
+            const uint8 roliDumpHeader[] = { 0xf0, 0x00, 0x21, 0x10, 0x78};\r
+            return memcmp (message.getRawData(), roliDumpHeader, sizeof (roliDumpHeader)) == 0;\r
+        }\r
+\r
+        void parseResponse (const MidiMessage& message)\r
+        {\r
+            int index = findMacAddressStart (message);\r
+\r
+            if (index >= 0)\r
+            {\r
+                const int macSize = 17;\r
+                const int offset = index + macSize;\r
+                const int serialSize = 16;\r
+\r
+                if (message.getRawDataSize() - offset < serialSize)\r
+                {\r
+                    jassertfalse;\r
+                    return;\r
+                }\r
+\r
+                serial = String ((const char*)message.getRawData() + offset, serialSize);\r
+            }\r
+        }\r
+\r
+        int findMacAddressStart (const MidiMessage& message)\r
+        {\r
+            const uint8 macStart[] = { '4', '8', ':', 'B', '6', ':', '2', '0', ':' };\r
+            return findSequence (macStart, sizeof (macStart), message);\r
+        }\r
+\r
+        int findSequence (const uint8* sequence, int sequenceSize, const MidiMessage& message)\r
+        {\r
+            for (int i = 0; i < message.getRawDataSize() - sequenceSize; i++)\r
+            {\r
+                if (memcmp (message.getRawData() + i, sequence, size_t (sequenceSize)) == 0)\r
+                    return i;\r
+            }\r
+\r
+            return -1;\r
+        }\r
+\r
+        JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR (BlockSerialReader)\r
+    };\r
+}\r
index cab84e8850e647753d61c0b112355a00e0328577..5d4c8615fb30af9fb4c250d8151eb360ae579a69 100644 (file)
@@ -49,6 +49,8 @@ struct ConnectedDeviceGroup  : private AsyncUpdater,
             setMidiMessageCallback();\r
         }\r
 \r
+        initialiseSerialReader();\r
+\r
         startTimer (200);\r
         sendTopologyRequest();\r
     }\r
@@ -294,12 +296,13 @@ private:
     Array<MemoryBlock> incomingPackets;\r
 \r
     std::unique_ptr<DepreciatedVersionReader> depreciatedVersionReader;\r
+    std::unique_ptr<BlockSerialReader> masterSerialReader;\r
 \r
     struct TouchStart { float x, y; };\r
     TouchList<TouchStart> touchStartPositions;\r
 \r
     static constexpr Block::UID invalidUid = 0;\r
-    Block::UID masterBlock = invalidUid;\r
+    Block::UID masterBlockUid = invalidUid;\r
 \r
     //==============================================================================\r
     void timerCallback() override\r
@@ -313,7 +316,8 @@ private:
 \r
         checkApiTimeouts (now);\r
         startApiModeOnConnectedBlocks();\r
-        requestMasterBlockVersionIfNeeded();\r
+        checkMasterBlockVersion();\r
+        checkMasterSerial();\r
     }\r
 \r
     //==============================================================================\r
@@ -394,7 +398,7 @@ private:
     }\r
 \r
     //==============================================================================\r
-    void requestMasterBlockVersionIfNeeded()\r
+    void checkMasterBlockVersion()\r
     {\r
         if (depreciatedVersionReader == nullptr)\r
             return;\r
@@ -403,7 +407,7 @@ private:
 \r
         if (masterVersion.isNotEmpty())\r
         {\r
-            const auto masterIndex = getIndexFromDeviceID (masterBlock);\r
+            const auto masterIndex = getIndexFromDeviceID (masterBlockUid);\r
 \r
             if (masterIndex >= 0)\r
                 setVersion (BlocksProtocol::TopologyIndex (masterIndex), masterVersion);\r
@@ -422,7 +426,7 @@ private:
             if (info->version == versionNumber)\r
                 return;\r
 \r
-            if (info->uid == masterBlock)\r
+            if (info->uid == masterBlockUid)\r
                 depreciatedVersionReader.reset();\r
 \r
             info->version = versionNumber;\r
@@ -430,6 +434,72 @@ private:
         }\r
     }\r
 \r
+    //==============================================================================\r
+    void checkMasterSerial()\r
+    {\r
+        if (masterSerialReader == nullptr)\r
+            initialiseSerialReader();\r
+\r
+        if (masterSerialReader == nullptr)\r
+            return;\r
+\r
+        if (masterBlockUid != invalidUid && masterSerialReader->hasSerial())\r
+        {\r
+            auto uid = getBlockUIDFromSerialNumber (masterSerialReader->getSerial());\r
+\r
+            if (uid != masterBlockUid)\r
+                updateMasterUid (uid);\r
+        }\r
+    }\r
+\r
+    void updateMasterUid (const Block::UID newMasterUid)\r
+    {\r
+        LOG_CONNECTIVITY ("Updating master from " + String (masterBlockUid) + " to " + String (newMasterUid));\r
+\r
+        masterBlockUid = newMasterUid;\r
+\r
+        Array<DeviceInfo> devicesToUpdate;\r
+\r
+        for (auto& info : currentDeviceInfo)\r
+        {\r
+            if (info.masterUid != masterBlockUid)\r
+            {\r
+                info.masterUid = masterBlockUid;\r
+\r
+                info.isMaster = info.uid == masterBlockUid;\r
+\r
+                devicesToUpdate.add (info);\r
+            }\r
+        }\r
+\r
+        detector.handleDevicesUpdated (devicesToUpdate);\r
+    }\r
+\r
+    Block::UID determineMasterBlockUid (Array<BlocksProtocol::DeviceStatus> devices)\r
+    {\r
+        if (masterSerialReader != nullptr && masterSerialReader->hasSerial())\r
+        {\r
+            auto foundSerial = masterSerialReader->getSerial();\r
+            for (const auto& device : incomingTopologyDevices)\r
+            {\r
+                if (device.serialNumber.asString() == foundSerial)\r
+                {\r
+                    LOG_CONNECTIVITY ("Found master from serial " + foundSerial);\r
+                    return getBlockUIDFromSerialNumber (foundSerial);\r
+                }\r
+            }\r
+        }\r
+\r
+        if (devices.size() > 0)\r
+        {\r
+            LOG_CONNECTIVITY ("Found master from first device " + devices[0].serialNumber.asString());\r
+            return getBlockUIDFromSerialNumber (incomingTopologyDevices[0].serialNumber);\r
+        }\r
+\r
+        jassertfalse;\r
+        return invalidUid;\r
+    }\r
+\r
     //==============================================================================\r
     struct BlockPingTime\r
     {\r
@@ -491,15 +561,16 @@ private:
 \r
     void forceApiDisconnected (Block::UID uid)\r
     {\r
-        Array<Block::UID> toRemove;\r
-\r
         for (auto dependentUID : detector.getDnaDependentDeviceUIDs (uid))\r
             removeDevice (dependentUID);\r
 \r
         removeDevice (uid);\r
 \r
-        if (uid == masterBlock)\r
-            masterBlock = invalidUid;\r
+        if (uid == masterBlockUid)\r
+        {\r
+            masterBlockUid = invalidUid;\r
+            masterSerialReader.reset();\r
+        }\r
 \r
         scheduleNewTopologyRequest();\r
     }\r
@@ -637,22 +708,19 @@ private:
         for (const auto& uid : toRemove)\r
             removeDevice (uid);\r
 \r
+        if (masterBlockUid == invalidUid)\r
+        {\r
+            masterBlockUid = determineMasterBlockUid (incomingTopologyDevices);\r
+            initialiseVersionReader();\r
+        }\r
+\r
         //Add new devices\r
         for (const auto& device : incomingTopologyDevices)\r
         {\r
             const auto uid = getBlockUIDFromSerialNumber (device.serialNumber);\r
 \r
-            if (! getDeviceInfoFromUID (uid))\r
+            if (getDeviceInfoFromUID (uid) == nullptr)\r
             {\r
-                // For backwards compatibility we assume the first device we see in a group is the master and won't change\r
-                if (masterBlock == invalidUid)\r
-                {\r
-                    masterBlock = uid;\r
-\r
-                    if (auto midiDeviceConnection = static_cast<MIDIDeviceConnection*> (deviceConnection.get()))\r
-                        depreciatedVersionReader = std::make_unique<DepreciatedVersionReader> (*midiDeviceConnection);\r
-                }\r
-\r
                 currentDeviceInfo.add ({ uid,\r
                                          device.index,\r
                                          device.serialNumber,\r
@@ -660,7 +728,7 @@ private:
                                          BlocksProtocol::BlockName(),\r
                                          device.batteryLevel,\r
                                          device.batteryCharging,\r
-                                         masterBlock });\r
+                                         masterBlockUid });\r
             }\r
         }\r
     }\r
@@ -699,6 +767,18 @@ private:
         detector.handleConnectionsChanged();\r
     }\r
 \r
+    void initialiseVersionReader()\r
+    {\r
+        if (auto midiDeviceConnection = static_cast<MIDIDeviceConnection*> (deviceConnection.get()))\r
+            depreciatedVersionReader = std::make_unique<DepreciatedVersionReader> (*midiDeviceConnection);\r
+    }\r
+\r
+    void initialiseSerialReader()\r
+    {\r
+        if (auto midiDeviceConnection = static_cast<MIDIDeviceConnection*> (deviceConnection.get()))\r
+            masterSerialReader = std::make_unique<BlockSerialReader> (*midiDeviceConnection);\r
+    }\r
+\r
     JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR (ConnectedDeviceGroup)\r
 };\r
 \r
index 1fb6c6924d58714354ec450fb1b14df2c7407d94..09bffab6254863cafe3d525b0e2f84331704b203 100644 (file)
@@ -177,27 +177,41 @@ struct Detector   : public ReferenceCountedObject,
         triggerAsyncUpdate();\r
     }\r
 \r
-    void handleDeviceUpdated (const DeviceInfo& info)\r
+    void handleDevicesUpdated (const Array<DeviceInfo>& infos)\r
     {\r
-        if (containsBlockWithUID (blocksToRemove, info.uid))\r
-            return;\r
+        bool shouldTriggerUpdate { false };\r
 \r
-        const auto blockIt = std::find_if (currentTopology.blocks.begin(), currentTopology.blocks.end(),\r
-                                           [uid = info.uid] (Block::Ptr block) { return uid == block->uid; });\r
-\r
-        if (blockIt != currentTopology.blocks.end())\r
+        for (auto& info : infos)\r
         {\r
-            const Block::Ptr block { *blockIt };\r
+            if (containsBlockWithUID (blocksToRemove, info.uid))\r
+                continue;\r
+\r
+            const auto blockIt = std::find_if (currentTopology.blocks.begin(), currentTopology.blocks.end(),\r
+                                               [uid = info.uid] (Block::Ptr block) { return uid == block->uid; });\r
 \r
-            if (auto blockImpl = BlockImpl::getFrom (block.get()))\r
-                blockImpl->markReconnected (info);\r
 \r
-            if (! containsBlockWithUID (blocksToAdd, info.uid))\r
+            if (blockIt != currentTopology.blocks.end())\r
             {\r
-                blocksToUpdate.addIfNotAlreadyThere (block);\r
-                triggerAsyncUpdate();\r
+                const Block::Ptr block { *blockIt };\r
+\r
+                if (auto blockImpl = BlockImpl::getFrom (block.get()))\r
+                    blockImpl->updateDeviceInfo (info);\r
+\r
+                if (! containsBlockWithUID (blocksToAdd, info.uid))\r
+                {\r
+                    blocksToUpdate.addIfNotAlreadyThere (block);\r
+                    shouldTriggerUpdate = true;\r
+                }\r
             }\r
         }\r
+\r
+        if (shouldTriggerUpdate)\r
+            triggerAsyncUpdate();\r
+    }\r
+\r
+    void handleDeviceUpdated (const DeviceInfo& info)\r
+    {\r
+        handleDevicesUpdated ({ info });\r
     }\r
 \r
     void handleBatteryChargingChanged (Block::UID deviceID, const BlocksProtocol::BatteryCharging isCharging)\r
index b2297cef048fcc1288bb4aaa285b8489d7bc7c29..eab5583f18fefe2fd325dac649c8b2e742561449 100644 (file)
@@ -47,13 +47,24 @@ struct PhysicalTopologySource::DetectorHolder  : private Timer
 \r
     void handleTimerTick()\r
     {\r
-        for (auto& b : detector->currentTopology.blocks)\r
-            if (auto bi = BlockImplementation<Detector>::getFrom (*b))\r
-                bi->handleTimerTick();\r
+        auto blocks = detector->currentTopology.blocks;\r
+\r
+        if (blocks.size() == 0)\r
+            return;\r
+\r
+        if (nextIndexToTick >= blocks.size())\r
+            nextIndexToTick = 0;\r
+\r
+        if (auto* bi = BlockImplementation<Detector>::getFrom (*blocks [nextIndexToTick]))\r
+            bi->handleTimerTick();\r
+\r
+        nextIndexToTick = (nextIndexToTick + 1) % blocks.size();\r
     }\r
 \r
     PhysicalTopologySource& topologySource;\r
     Detector::Ptr detector;\r
+\r
+    int nextIndexToTick {0};\r
 };\r
 \r
 } // namespace juce\r
index 56fb9e34c1cf52f30daef43ec4cfcb3c9dacdc9f..6861db66935961544e698c6d07366b7dd7f65572 100644 (file)
@@ -67,7 +67,7 @@ struct MIDIDeviceConnection  : public PhysicalTopologySource::DeviceConnection,
     {\r
         JUCE_ASSERT_MESSAGE_MANAGER_IS_LOCKED // This method must only be called from the message thread!\r
 \r
-        jassert (dataSize > sizeof (BlocksProtocol::roliSysexHeader) + 2);\r
+        jassert (dataSize > sizeof (BlocksProtocol::roliSysexHeader) + 1);\r
         jassert (memcmp (data, BlocksProtocol::roliSysexHeader, sizeof (BlocksProtocol::roliSysexHeader) - 1) == 0);\r
         jassert (static_cast<const uint8*> (data)[dataSize - 1] == 0xf7);\r
 \r
index 521473e048e6360363bfc9fcdddfe8347f8b323c..e08d54b8b4cf2e42feeba3e20855c83677465d46 100644 (file)
 \r
 //==============================================================================\r
 /** These can be useful when debugging the topology. */\r
-#define LOG_BLOCKS_CONNECTIVITY 0\r
-#define LOG_BLOCKS_PINGS 0\r
-#define DUMP_BANDWIDTH_STATS 0\r
-#define DUMP_TOPOLOGY 0\r
+\r
+#ifndef LOG_BLOCKS_CONNECTIVITY\r
+  #define LOG_BLOCKS_CONNECTIVITY 0\r
+#endif\r
+\r
+#ifndef LOG_BLOCKS_PINGS\r
+  #define LOG_BLOCKS_PINGS 0\r
+#endif\r
+\r
+#ifndef DUMP_BANDWIDTH_STATS\r
+  #define DUMP_BANDWIDTH_STATS 0\r
+#endif\r
+\r
+#ifndef DUMP_TOPOLOGY\r
+  #define DUMP_TOPOLOGY 0\r
+#endif\r
 \r
 #define TOPOLOGY_LOG(text) \\r
  JUCE_BLOCK_WITH_FORCED_SEMICOLON (juce::String buf ("Topology Src:   "); \\r
@@ -51,6 +63,7 @@
 #include "internal/juce_MIDIDeviceDetector.cpp"\r
 #include "internal/juce_DeviceInfo.cpp"\r
 #include "internal/juce_DepreciatedVersionReader.cpp"\r
+#include "internal/juce_BlockSerialReader.cpp"\r
 #include "internal/juce_ConnectedDeviceGroup.cpp"\r
 #include "internal/juce_BlockImplementation.cpp"\r
 #include "internal/juce_Detector.cpp"\r
index 390bf327c48ea4f6986d9791d8944e414e95244b..fa1be4124acbef17468347ce32284112db9fbdeb 100644 (file)
@@ -54,7 +54,7 @@ public:
     /** This method will tell, if an other PhysicalTopologySource has locked the Midi connection */\r
     bool isLockedFromOutside() const;\r
 \r
-    //==========================================================================\r
+    //==============================================================================\r
     /** For custom transport systems, this represents a connected device */\r
     struct DeviceConnection\r
     {\r
@@ -86,7 +86,7 @@ protected:
     virtual void handleTimerTick();\r
 \r
 private:\r
-    //==========================================================================\r
+    //==============================================================================\r
     DeviceDetector* customDetector = nullptr;\r
     friend struct Detector;\r
     struct DetectorHolder;\r
index fb7e02d2cf6770393a87ac618da69395de1df611..1e6baffbf03cfd8adf5f59fa5556167decbb7293 100644 (file)
@@ -43,7 +43,7 @@ public:
     /** Destructor. */\r
     ~RuleBasedTopologySource() override;\r
 \r
-    //==========================================================================\r
+    //==============================================================================\r
     /** Returns the currently active topology. */\r
     BlockTopology getCurrentTopology() const override;\r
 \r
@@ -80,7 +80,7 @@ public:
     bool isActive() const override;\r
 \r
 private:\r
-    //==========================================================================\r
+    //==============================================================================\r
     struct Internal;\r
     std::unique_ptr<Internal> internal;\r
 };\r
index 899288bfcbdfca26d9e6fb8936c489c3b3614599..d7360ba5bf4d9aada701d9a34fe0248f188c8d0b 100644 (file)
@@ -30,7 +30,7 @@ namespace juce
 class TopologySource\r
 {\r
 public:\r
-    //==========================================================================\r
+    //==============================================================================\r
     /** Destructor. */\r
     virtual ~TopologySource() = default;\r
 \r
@@ -43,7 +43,7 @@ public:
     /** Returns true, if the TopologySource is currently trying to connect the block devices */\r
     virtual bool isActive() const = 0;\r
 \r
-    //==========================================================================\r
+    //==============================================================================\r
     /** Used to receive callbacks for topology changes */\r
     struct Listener\r
     {\r
@@ -71,7 +71,7 @@ public:
     virtual void cancelAllActiveTouches() noexcept {}\r
 \r
 protected:\r
-    //==========================================================================\r
+    //==============================================================================\r
     ListenerList<Listener> listeners;\r
 };\r
 \r
index 452e6fd9a4b29d88c671f2afc9cc0518f49b2903..5080c705f9f55cf89fdde5de90b9e8d8179c4e61 100644 (file)
@@ -35,7 +35,7 @@
 \r
   ID:               juce_box2d\r
   vendor:           juce\r
-  version:          5.4.4\r
+  version:          5.4.5\r
   name:             JUCE wrapper for the Box2D physics engine\r
   description:      The Box2D physics engine and some utility classes.\r
   website:          http://www.juce.com/juce\r
index c307fc7351f6bdfd281d10b435abcae350cacc27..9e8f153c7bfd23d8d8f6cc20504b354e29a98f58 100644 (file)
@@ -89,7 +89,6 @@ public:
 \r
     /** Returns the value of a named item.\r
         If the name isn't found, this will return a void variant.\r
-        @see getProperty\r
     */\r
     const var& operator[] (const Identifier& name) const noexcept;\r
 \r
index 155f790337cd009e094f2639d753cb758190a7ff..f3e926688378df25db0c9ceeb068562b41a8d27a 100644 (file)
@@ -281,15 +281,15 @@ public:
     //==============================================================================\r
     /** Appends a new object to the end of the array.\r
 \r
-        Note that the this object will be deleted by the OwnedArray when it\r
-        is removed, so be careful not to delete it somewhere else.\r
+        Note that this object will be deleted by the OwnedArray when it is removed,\r
+        so be careful not to delete it somewhere else.\r
 \r
         Also be careful not to add the same object to the array more than once,\r
         as this will obviously cause deletion of dangling pointers.\r
 \r
         @param newObject    the new object to add to the array\r
         @returns            the new object that was added\r
-        @see set, insert, addIfNotAlreadyThere, addSorted\r
+        @see set, insert, addSorted\r
     */\r
     ObjectClass* add (ObjectClass* newObject)\r
     {\r
@@ -300,15 +300,15 @@ public:
 \r
     /** Appends a new object to the end of the array.\r
 \r
-        Note that the this object will be deleted by the OwnedArray when it\r
-        is removed, so be careful not to delete it somewhere else.\r
+        Note that this object will be deleted by the OwnedArray when it is removed,\r
+        so be careful not to delete it somewhere else.\r
 \r
         Also be careful not to add the same object to the array more than once,\r
         as this will obviously cause deletion of dangling pointers.\r
 \r
         @param newObject    the new object to add to the array\r
         @returns            the new object that was added\r
-        @see set, insert, addIfNotAlreadyThere, addSorted\r
+        @see set, insert, addSorted\r
     */\r
     ObjectClass* add (std::unique_ptr<ObjectClass> newObject)\r
     {\r
@@ -317,8 +317,8 @@ public:
 \r
     /** Inserts a new object into the array at the given index.\r
 \r
-        Note that the this object will be deleted by the OwnedArray when it\r
-        is removed, so be careful not to delete it somewhere else.\r
+        Note that this object will be deleted by the OwnedArray when it is removed,\r
+        so be careful not to delete it somewhere else.\r
 \r
         If the index is less than 0 or greater than the size of the array, the\r
         element will be added to the end of the array.\r
@@ -331,7 +331,7 @@ public:
         @param indexToInsertAt      the index at which the new element should be inserted\r
         @param newObject            the new object to add to the array\r
         @returns                    the new object that was added\r
-        @see add, addSorted, addIfNotAlreadyThere, set\r
+        @see add, addSorted, set\r
     */\r
     ObjectClass* insert (int indexToInsertAt, ObjectClass* newObject)\r
     {\r
@@ -342,8 +342,8 @@ public:
 \r
     /** Inserts a new object into the array at the given index.\r
 \r
-        Note that the this object will be deleted by the OwnedArray when it\r
-        is removed, so be careful not to delete it somewhere else.\r
+        Note that this object will be deleted by the OwnedArray when it is removed,\r
+        so be careful not to delete it somewhere else.\r
 \r
         If the index is less than 0 or greater than the size of the array, the\r
         element will be added to the end of the array.\r
@@ -356,7 +356,7 @@ public:
         @param indexToInsertAt      the index at which the new element should be inserted\r
         @param newObject            the new object to add to the array\r
         @returns                    the new object that was added\r
-        @see add, addSorted, addIfNotAlreadyThere, set\r
+        @see add, addSorted, set\r
     */\r
     ObjectClass* insert (int indexToInsertAt, std::unique_ptr<ObjectClass> newObject)\r
     {\r
index 70f87f594b9f34bda4f7410e53577931fc7d53ae..e07968b1924a0ae5629f74504c628cb88ccba408 100644 (file)
@@ -1197,6 +1197,28 @@ public:
 \r
         expect (demoFolder.deleteRecursively());\r
         expect (! demoFolder.exists());\r
+\r
+        {\r
+            URL url ("https://audio.dev/foo/bar/");\r
+            expectEquals (url.toString (false), String ("https://audio.dev/foo/bar/"));\r
+            expectEquals (url.getChildURL ("x").toString (false), String ("https://audio.dev/foo/bar/x"));\r
+            expectEquals (url.getParentURL().toString (false), String ("https://audio.dev/foo"));\r
+            expectEquals (url.getParentURL().getParentURL().toString (false), String ("https://audio.dev/"));\r
+            expectEquals (url.getParentURL().getParentURL().getParentURL().toString (false), String ("https://audio.dev/"));\r
+            expectEquals (url.getParentURL().getChildURL ("x").toString (false), String ("https://audio.dev/foo/x"));\r
+            expectEquals (url.getParentURL().getParentURL().getParentURL().getChildURL ("x").toString (false), String ("https://audio.dev/x"));\r
+        }\r
+\r
+        {\r
+            URL url ("https://audio.dev/foo/bar");\r
+            expectEquals (url.toString (false), String ("https://audio.dev/foo/bar"));\r
+            expectEquals (url.getChildURL ("x").toString (false), String ("https://audio.dev/foo/bar/x"));\r
+            expectEquals (url.getParentURL().toString (false), String ("https://audio.dev/foo"));\r
+            expectEquals (url.getParentURL().getParentURL().toString (false), String ("https://audio.dev/"));\r
+            expectEquals (url.getParentURL().getParentURL().getParentURL().toString (false), String ("https://audio.dev/"));\r
+            expectEquals (url.getParentURL().getChildURL ("x").toString (false), String ("https://audio.dev/foo/x"));\r
+            expectEquals (url.getParentURL().getParentURL().getParentURL().getChildURL ("x").toString (false), String ("https://audio.dev/x"));\r
+        }\r
     }\r
 };\r
 \r
index 890cd3680ede482cc28bee9f8065cc821a950386..a7d26cd6da191ee3bead93aff4071666144998aa 100755 (executable)
 #endif\r
 \r
 #if JUCE_BELA\r
- #include <native/timer.h>\r
+ #include <alchemy/timer.h>\r
 #endif\r
 \r
 #undef check\r
index f6c80dc15d80a1fa8e4c7519d5b038339da7f72b..9cd414694650a1deced41b01f201ee251bc00abf 100644 (file)
@@ -32,7 +32,7 @@
 \r
   ID:               juce_core\r
   vendor:           juce\r
-  version:          5.4.4\r
+  version:          5.4.5\r
   name:             JUCE core classes\r
   description:      The essential set of basic JUCE classes, as required by all the other JUCE modules. Includes text, container, memory, threading and i/o functionality.\r
   website:          http://www.juce.com/juce\r
index ad8081db577a4c88a88a99e83e053f00702ae426..1c21885e4f16487977ac06c6cf9f9c83e357561c 100644 (file)
@@ -122,6 +122,8 @@ public:
     {\r
         if (! shouldDelete)\r
             object.release();\r
+        else\r
+            object.reset();\r
     }\r
 \r
     /** Does the same thing as reset(). */\r
index e1d076130fd2e22081084262f23f211184bc3274..be61c20033b93e91ae4ab7023f4ed651283ee69c 100644 (file)
@@ -90,7 +90,7 @@ public:
     static bool JUCE_CALLTYPE valueExists (const String& regValuePath, WoW64Mode mode = WoW64_Default);\r
 \r
     /** Returns true if the given key exists in the registry. */\r
-    static bool JUCE_CALLTYPE keyExists (const String& regValuePath, WoW64Mode mode = WoW64_Default);\r
+    static bool JUCE_CALLTYPE keyExists (const String& regKeyPath, WoW64Mode mode = WoW64_Default);\r
 \r
     /** Deletes a registry value. */\r
     static bool JUCE_CALLTYPE deleteValue (const String& regValuePath, WoW64Mode mode = WoW64_Default);\r
index dc5d53c000320c96b8c60ace6901f06e66b7eff6..f9281e1f9b5c6fa8cbf721b433811347bf1e5a61 100644 (file)
  #include <objc/runtime.h>\r
  #include <objc/objc.h>\r
  #include <objc/message.h>\r
+ #include <poll.h>\r
 \r
 //==============================================================================\r
 #elif JUCE_WINDOWS\r
  #include <sys/vfs.h>\r
  #include <sys/wait.h>\r
  #include <utime.h>\r
+ #include <poll.h>\r
 \r
 //==============================================================================\r
 #elif JUCE_BSD\r
  #include <sys/types.h>\r
  #include <sys/wait.h>\r
  #include <utime.h>\r
+ #include <poll.h>\r
 \r
 //==============================================================================\r
 #elif JUCE_ANDROID\r
  #include <fnmatch.h>\r
  #include <sys/wait.h>\r
  #include <android/api-level.h>\r
+ #include <poll.h>\r
 \r
  // If you are getting include errors here, then you to re-build the Projucer\r
  // and re-save your .jucer file.\r
index 89d70ca753004dd11df555ac0b645ae552c77f14..d9eb2633031953a1b1c36d640d251ba204e3d379 100644 (file)
@@ -418,13 +418,27 @@ jobject ActivityLifecycleCallbacks::invoke (jobject proxy, jobject method, jobje
     auto activity = env->GetArrayLength (args) > 0 ? env->GetObjectArrayElement (args, 0) : (jobject) nullptr;\r
     auto bundle   = env->GetArrayLength (args) > 1 ? env->GetObjectArrayElement (args, 1) : (jobject) nullptr;\r
 \r
-    if      (methodName == "onActivityCreated")             { onActivityCreated (activity, bundle); return nullptr; }\r
-    else if (methodName == "onActivityDestroyed")           { onActivityDestroyed (activity); return nullptr; }\r
-    else if (methodName == "onActivityPaused")              { onActivityPaused (activity); return nullptr; }\r
-    else if (methodName == "onActivityResumed")             { onActivityResumed (activity); return nullptr; }\r
-    else if (methodName == "onActivitySaveInstanceState")   { onActivitySaveInstanceState (activity, bundle); return nullptr; }\r
-    else if (methodName == "onActivityStarted")             { onActivityStarted (activity); return nullptr; }\r
-    else if (methodName == "onActivityStopped")             { onActivityStopped (activity); return nullptr; }\r
+    if      (methodName == "onActivityPreCreated")             { onActivityPreCreated (activity, bundle);            return nullptr; }\r
+    else if (methodName == "onActivityPreDestroyed")           { onActivityPreDestroyed (activity);                  return nullptr; }\r
+    else if (methodName == "onActivityPrePaused")              { onActivityPrePaused (activity);                     return nullptr; }\r
+    else if (methodName == "onActivityPreResumed")             { onActivityPreResumed (activity);                    return nullptr; }\r
+    else if (methodName == "onActivityPreSaveInstanceState")   { onActivityPreSaveInstanceState (activity, bundle);  return nullptr; }\r
+    else if (methodName == "onActivityPreStarted")             { onActivityPreStarted (activity);                    return nullptr; }\r
+    else if (methodName == "onActivityPreStopped")             { onActivityPreStopped (activity);                    return nullptr; }\r
+    else if (methodName == "onActivityCreated")                { onActivityCreated (activity, bundle);               return nullptr; }\r
+    else if (methodName == "onActivityDestroyed")              { onActivityDestroyed (activity);                     return nullptr; }\r
+    else if (methodName == "onActivityPaused")                 { onActivityPaused (activity);                        return nullptr; }\r
+    else if (methodName == "onActivityResumed")                { onActivityResumed (activity);                       return nullptr; }\r
+    else if (methodName == "onActivitySaveInstanceState")      { onActivitySaveInstanceState (activity, bundle);     return nullptr; }\r
+    else if (methodName == "onActivityStarted")                { onActivityStarted (activity);                       return nullptr; }\r
+    else if (methodName == "onActivityStopped")                { onActivityStopped (activity);                       return nullptr; }\r
+    else if (methodName == "onActivityPostCreated")            { onActivityPostCreated (activity, bundle);           return nullptr; }\r
+    else if (methodName == "onActivityPostDestroyed")          { onActivityPostDestroyed (activity);                 return nullptr; }\r
+    else if (methodName == "onActivityPostPaused")             { onActivityPostPaused (activity);                    return nullptr; }\r
+    else if (methodName == "onActivityPostResumed")            { onActivityPostResumed (activity);                   return nullptr; }\r
+    else if (methodName == "onActivityPostSaveInstanceState")  { onActivityPostSaveInstanceState (activity, bundle); return nullptr; }\r
+    else if (methodName == "onActivityPostStarted")            { onActivityPostStarted (activity);                   return nullptr; }\r
+    else if (methodName == "onActivityPostStopped")            { onActivityPostStopped (activity);                   return nullptr; }\r
 \r
     return AndroidInterfaceImplementer::invoke (proxy, method, args);\r
 }\r
index 753c166fc14ad4656ada14dbd3b17d851b27f3c4..edf7fadd3d3f11de82c7cd19604393284f4721fd 100644 (file)
@@ -875,13 +875,29 @@ LocalRef<jobject> CreateJavaInterface (AndroidInterfaceImplementer* implementer,
 class ActivityLifecycleCallbacks     : public AndroidInterfaceImplementer\r
 {\r
 public:\r
-    virtual void onActivityCreated (jobject /*activity*/, jobject /*bundle*/) {}\r
-    virtual void onActivityDestroyed (jobject /*activity*/) {}\r
-    virtual void onActivityPaused (jobject /*activity*/) {}\r
-    virtual void onActivityResumed (jobject /*activity*/) {}\r
-    virtual void onActivitySaveInstanceState (jobject /*activity*/, jobject /*bundle*/) {}\r
-    virtual void onActivityStarted (jobject /*activity*/) {}\r
-    virtual void onActivityStopped (jobject /*activity*/) {}\r
+    virtual void onActivityPreCreated            (jobject /*activity*/, jobject /*bundle*/)  {}\r
+    virtual void onActivityPreDestroyed          (jobject /*activity*/)                      {}\r
+    virtual void onActivityPrePaused             (jobject /*activity*/)                      {}\r
+    virtual void onActivityPreResumed            (jobject /*activity*/)                      {}\r
+    virtual void onActivityPreSaveInstanceState  (jobject /*activity*/, jobject /*bundle*/)  {}\r
+    virtual void onActivityPreStarted            (jobject /*activity*/)                      {}\r
+    virtual void onActivityPreStopped            (jobject /*activity*/)                      {}\r
+\r
+    virtual void onActivityCreated               (jobject /*activity*/, jobject /*bundle*/)  {}\r
+    virtual void onActivityDestroyed             (jobject /*activity*/)                      {}\r
+    virtual void onActivityPaused                (jobject /*activity*/)                      {}\r
+    virtual void onActivityResumed               (jobject /*activity*/)                      {}\r
+    virtual void onActivitySaveInstanceState     (jobject /*activity*/, jobject /*bundle*/)  {}\r
+    virtual void onActivityStarted               (jobject /*activity*/)                      {}\r
+    virtual void onActivityStopped               (jobject /*activity*/)                      {}\r
+\r
+    virtual void onActivityPostCreated           (jobject /*activity*/, jobject /*bundle*/)  {}\r
+    virtual void onActivityPostDestroyed         (jobject /*activity*/)                      {}\r
+    virtual void onActivityPostPaused            (jobject /*activity*/)                      {}\r
+    virtual void onActivityPostResumed           (jobject /*activity*/)                      {}\r
+    virtual void onActivityPostSaveInstanceState (jobject /*activity*/, jobject /*bundle*/)  {}\r
+    virtual void onActivityPostStarted           (jobject /*activity*/)                      {}\r
+    virtual void onActivityPostStopped           (jobject /*activity*/)                      {}\r
 \r
 private:\r
     jobject invoke (jobject, jobject, jobjectArray) override;\r
index 5ec41865669bb8c56af1b7fbbb17b941b74cfd52..61e6f3a3f561975f5124696d3ab1f7b7278546df 100644 (file)
@@ -205,16 +205,10 @@ public:
                 bytesToRead = static_cast<int> (chunkEnd - position);\r
         }\r
 \r
-        fd_set readbits;\r
-        FD_ZERO (&readbits);\r
-        FD_SET (socketHandle, &readbits);\r
+        pollfd pfd { socketHandle, POLLIN, 0 };\r
 \r
-        struct timeval tv;\r
-        tv.tv_sec = jmax (1, timeOutMs / 1000);\r
-        tv.tv_usec = 0;\r
-\r
-        if (select (socketHandle + 1, &readbits, 0, 0, &tv) <= 0)\r
-            return 0;   // (timeout)\r
+        if (poll (&pfd, 1, timeOutMs) <= 0)\r
+            return 0; // (timeout)\r
 \r
         auto bytesRead = jmax (0, (int) recv (socketHandle, buffer, (size_t) bytesToRead, MSG_WAITALL));\r
 \r
index af8b39646aa9792da74fb7faffc0f4470e4ad61c..72b810a5bf50e5ea55f8bf79b492527332a05d20 100644 (file)
@@ -172,15 +172,8 @@ private:
 \r
     static void waitForInput (int handle, int timeoutMsecs) noexcept\r
     {\r
-        struct timeval timeout;\r
-        timeout.tv_sec = timeoutMsecs / 1000;\r
-        timeout.tv_usec = (timeoutMsecs % 1000) * 1000;\r
-\r
-        fd_set rset;\r
-        FD_ZERO (&rset);\r
-        FD_SET (handle, &rset);\r
-\r
-        select (handle + 1, &rset, nullptr, nullptr, &timeout);\r
+        pollfd pfd { handle, POLLIN, 0 };\r
+        poll (&pfd, 1, timeoutMsecs);\r
     }\r
 \r
     JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR (Pimpl)\r
index f2dcadad721fba05bf6c0561cf88cfdd512ed33b..e035a107a2b0dc8fab1c916f79be59bf1010e40f 100644 (file)
@@ -400,13 +400,19 @@ void File::getFileTimesInternal (int64& modificationTime, int64& accessTime, int
 \r
     if (juce_stat (fullPath, info))\r
     {\r
+      #if JUCE_MAC || (JUCE_IOS && __DARWIN_ONLY_64_BIT_INO_T)\r
+        modificationTime  = (int64) info.st_mtimespec.tv_sec * 1000 + info.st_mtimespec.tv_nsec / 1000000;\r
+        accessTime        = (int64) info.st_atimespec.tv_sec * 1000 + info.st_atimespec.tv_nsec / 1000000;\r
+        creationTime      = (int64) info.st_birthtimespec.tv_sec * 1000 + info.st_birthtimespec.tv_nsec / 1000000;\r
+      #else\r
         modificationTime  = (int64) info.st_mtime * 1000;\r
         accessTime        = (int64) info.st_atime * 1000;\r
-       #if JUCE_MAC || JUCE_IOS\r
+       #if JUCE_IOS\r
         creationTime      = (int64) info.st_birthtime * 1000;\r
        #else\r
         creationTime      = (int64) info.st_ctime * 1000;\r
        #endif\r
+      #endif\r
     }\r
 }\r
 \r
@@ -416,11 +422,32 @@ bool File::setFileTimesInternal (int64 modificationTime, int64 accessTime, int64
 \r
     if ((modificationTime != 0 || accessTime != 0) && juce_stat (fullPath, info))\r
     {\r
+       #if JUCE_MAC || (JUCE_IOS && __DARWIN_ONLY_64_BIT_INO_T)\r
+        struct timeval times[2];\r
+\r
+        bool setModificationTime = (modificationTime != 0);\r
+        bool setAccessTime       = (accessTime != 0);\r
+\r
+        times[0].tv_sec  = setAccessTime ? static_cast<__darwin_time_t> (accessTime / 1000)\r
+                                         : info.st_atimespec.tv_sec;\r
+\r
+        times[0].tv_usec = setAccessTime ? static_cast<__darwin_suseconds_t> ((accessTime % 1000) * 1000)\r
+                                         : static_cast<__darwin_suseconds_t> (info.st_atimespec.tv_nsec / 1000);\r
+\r
+        times[1].tv_sec  = setModificationTime ? static_cast<__darwin_time_t> (modificationTime / 1000)\r
+                                               : info.st_mtimespec.tv_sec;\r
+\r
+        times[1].tv_usec = setModificationTime ? static_cast<__darwin_suseconds_t> ((modificationTime % 1000) * 1000)\r
+                                               : static_cast<__darwin_suseconds_t> (info.st_mtimespec.tv_nsec / 1000);\r
+\r
+        return utimes (fullPath.toUTF8(), times) == 0;\r
+       #else\r
         struct utimbuf times;\r
         times.actime  = accessTime != 0       ? static_cast<time_t> (accessTime / 1000)       : static_cast<time_t> (info.st_atime);\r
         times.modtime = modificationTime != 0 ? static_cast<time_t> (modificationTime / 1000) : static_cast<time_t> (info.st_mtime);\r
 \r
         return utime (fullPath.toUTF8(), &times) == 0;\r
+       #endif\r
     }\r
 \r
     return false;\r
index e1b5f5b814274b013c20d3a139a33f6f0b222e19..afd29824d776bb161675e44b16105aa7219494cc 100644 (file)
@@ -49,7 +49,7 @@ struct RegistryKeyWrapper
 \r
     ~RegistryKeyWrapper()\r
     {\r
-        if (key != 0)\r
+        if (key != nullptr)\r
             RegCloseKey (key);\r
     }\r
 \r
@@ -73,7 +73,7 @@ struct RegistryKeyWrapper
     {\r
         const RegistryKeyWrapper key (regValuePath, true, wow64Flags);\r
 \r
-        return key.key != 0\r
+        return key.key != nullptr\r
                 && RegSetValueEx (key.key, key.wideCharValueName, 0, type,\r
                                   reinterpret_cast<const BYTE*> (data),\r
                                   (DWORD) dataSize) == ERROR_SUCCESS;\r
@@ -83,7 +83,7 @@ struct RegistryKeyWrapper
     {\r
         const RegistryKeyWrapper key (regValuePath, false, wow64Flags);\r
 \r
-        if (key.key != 0)\r
+        if (key.key != nullptr)\r
         {\r
             for (unsigned long bufferSize = 1024; ; bufferSize *= 2)\r
             {\r
@@ -121,16 +121,16 @@ struct RegistryKeyWrapper
         return defaultValue;\r
     }\r
 \r
-    static bool keyExists (const String& regValuePath, const DWORD wow64Flags)\r
+    static bool keyExists (const String& regKeyPath, const DWORD wow64Flags)\r
     {\r
-        return RegistryKeyWrapper (regValuePath, false, wow64Flags).key != 0;\r
+        return RegistryKeyWrapper (regKeyPath + "\\", false, wow64Flags).key != nullptr;\r
     }\r
 \r
     static bool valueExists (const String& regValuePath, const DWORD wow64Flags)\r
     {\r
         const RegistryKeyWrapper key (regValuePath, false, wow64Flags);\r
 \r
-        if (key.key == 0)\r
+        if (key.key == nullptr)\r
             return false;\r
 \r
         unsigned char buffer [512];\r
@@ -143,7 +143,7 @@ struct RegistryKeyWrapper
         return result == ERROR_SUCCESS || result == ERROR_MORE_DATA;\r
     }\r
 \r
-    HKEY key = 0;\r
+    HKEY key = nullptr;\r
     const wchar_t* wideCharValueName = nullptr;\r
     String valueName;\r
 \r
@@ -186,23 +186,23 @@ bool JUCE_CALLTYPE WindowsRegistry::valueExists (const String& regValuePath, WoW
     return RegistryKeyWrapper::valueExists (regValuePath, (DWORD) mode);\r
 }\r
 \r
-bool JUCE_CALLTYPE WindowsRegistry::keyExists (const String& regValuePath, WoW64Mode mode)\r
+bool JUCE_CALLTYPE WindowsRegistry::keyExists (const String& regKeyPath, WoW64Mode mode)\r
 {\r
-    return RegistryKeyWrapper::keyExists (regValuePath, (DWORD) mode);\r
+    return RegistryKeyWrapper::keyExists (regKeyPath, (DWORD) mode);\r
 }\r
 \r
 bool JUCE_CALLTYPE WindowsRegistry::deleteValue (const String& regValuePath, WoW64Mode mode)\r
 {\r
     const RegistryKeyWrapper key (regValuePath, true, (DWORD) mode);\r
 \r
-    return key.key != 0 && RegDeleteValue (key.key, key.wideCharValueName) == ERROR_SUCCESS;\r
+    return key.key != nullptr && RegDeleteValue (key.key, key.wideCharValueName) == ERROR_SUCCESS;\r
 }\r
 \r
 static bool deleteKeyNonRecursive (const String& regKeyPath, WindowsRegistry::WoW64Mode mode)\r
 {\r
     const RegistryKeyWrapper key (regKeyPath, true, (DWORD) mode);\r
 \r
-    return key.key != 0 && RegDeleteKey (key.key, key.wideCharValueName) == ERROR_SUCCESS;\r
+    return key.key != nullptr && RegDeleteKey (key.key, key.wideCharValueName) == ERROR_SUCCESS;\r
 }\r
 \r
 bool JUCE_CALLTYPE WindowsRegistry::deleteKey (const String& regKeyPath, WoW64Mode mode)\r
index 8430badfa6ed0bdd95231c7b4d7df5ccc5ac101c..1c15fc56453367da354c38e90722805c18ca77a6 100644 (file)
@@ -33,19 +33,22 @@ namespace juce
 #endif\r
 \r
 #if JUCE_WINDOWS\r
- typedef int       juce_socklen_t;\r
- typedef int       juce_recvsend_size_t;\r
- typedef SOCKET    SocketHandle;\r
+ using juce_socklen_t       = int;\r
+ using juce_recvsend_size_t = int;\r
+ using SocketHandle         = SOCKET;\r
+ #if ! JUCE_MINGW\r
+  using pollfd              = WSAPOLLFD;\r
+ #endif\r
  static const SocketHandle invalidSocket = INVALID_SOCKET;\r
 #elif JUCE_ANDROID\r
typedef socklen_t juce_socklen_t;\r
typedef size_t    juce_recvsend_size_t;\r
typedef int       SocketHandle;\r
using juce_socklen_t       = socklen_t;\r
using juce_recvsend_size_t = size_t;\r
using SocketHandle         = int;\r
  static const SocketHandle invalidSocket = -1;\r
 #else\r
typedef socklen_t juce_socklen_t;\r
typedef socklen_t juce_recvsend_size_t;\r
typedef int       SocketHandle;\r
using juce_socklen_t       = socklen_t;\r
using juce_recvsend_size_t = socklen_t;\r
using SocketHandle         = int;\r
  static const SocketHandle invalidSocket = -1;\r
 #endif\r
 \r
@@ -87,7 +90,7 @@ namespace SocketHelpers
 \r
     static bool resetSocketOptions (SocketHandle handle, bool isDatagram, bool allowBroadcast) noexcept\r
     {\r
-        return handle >= 0\r
+        return handle != invalidSocket\r
                 && setOption (handle, SO_RCVBUF, (int) 65536)\r
                 && setOption (handle, SO_SNDBUF, (int) 65536)\r
                 && (isDatagram ? ((! allowBroadcast) || setOption (handle, SO_BROADCAST, (int) 1))\r
@@ -147,7 +150,7 @@ namespace SocketHelpers
 \r
     static bool bindSocket (SocketHandle handle, int port, const String& address) noexcept\r
     {\r
-        if (handle < 0 || ! isValidPortNumber (port))\r
+        if (handle == invalidSocket || ! isValidPortNumber (port))\r
             return false;\r
 \r
         struct sockaddr_in addr;\r
@@ -163,7 +166,7 @@ namespace SocketHelpers
 \r
     static int getBoundPort (SocketHandle handle) noexcept\r
     {\r
-        if (handle >= 0)\r
+        if (handle != invalidSocket)\r
         {\r
             struct sockaddr_in addr;\r
             socklen_t len = sizeof (addr);\r
@@ -186,6 +189,33 @@ namespace SocketHelpers
         return "0.0.0.0";\r
     }\r
 \r
+    static bool setSocketBlockingState (SocketHandle handle, bool shouldBlock) noexcept\r
+    {\r
+       #if JUCE_WINDOWS\r
+        u_long nonBlocking = shouldBlock ? 0 : (u_long) 1;\r
+        return ioctlsocket (handle, FIONBIO, &nonBlocking) == 0;\r
+       #else\r
+        int socketFlags = fcntl (handle, F_GETFL, 0);\r
+\r
+        if (socketFlags == -1)\r
+            return false;\r
+\r
+        if (shouldBlock)\r
+            socketFlags &= ~O_NONBLOCK;\r
+        else\r
+            socketFlags |= O_NONBLOCK;\r
+\r
+        return fcntl (handle, F_SETFL, socketFlags) == 0;\r
+       #endif\r
+    }\r
+\r
+   #if ! JUCE_WINDOWS\r
+    static bool getSocketBlockingState (SocketHandle handle)\r
+    {\r
+        return (fcntl (handle, F_GETFL, 0) & O_NONBLOCK) == 0;\r
+    }\r
+   #endif\r
+\r
     static int readSocket (SocketHandle handle,\r
                            void* destBuffer, int maxBytesToRead,\r
                            std::atomic<bool>& connected,\r
@@ -194,6 +224,11 @@ namespace SocketHelpers
                            String* senderIP = nullptr,\r
                            int* senderPort = nullptr) noexcept\r
     {\r
+       #if ! JUCE_WINDOWS\r
+        if (blockUntilSpecifiedAmountHasArrived != getSocketBlockingState (handle))\r
+       #endif\r
+            setSocketBlockingState (handle, blockUntilSpecifiedAmountHasArrived);\r
+\r
         int bytesRead = 0;\r
 \r
         while (bytesRead < maxBytesToRead)\r
@@ -251,8 +286,9 @@ namespace SocketHelpers
         if (! lock.isLocked())\r
             return -1;\r
 \r
-        int h = handle.load();\r
+        auto h = handle.load();\r
 \r
+       #if JUCE_MINGW\r
         struct timeval timeout;\r
         struct timeval* timeoutp;\r
 \r
@@ -276,24 +312,36 @@ namespace SocketHelpers
         fd_set* const prset = forReading ? &rset : nullptr;\r
         fd_set* const pwset = forReading ? nullptr : &wset;\r
 \r
-       #if JUCE_WINDOWS\r
         if (select ((int) h + 1, prset, pwset, 0, timeoutp) < 0)\r
             return -1;\r
        #else\r
-        {\r
-            int result = 0;\r
+        short eventsFlag = (forReading ? POLLIN : POLLOUT);\r
+        pollfd pfd { (SocketHandle) h, eventsFlag, 0 };\r
 \r
-            for (;;)\r
-            {\r
-                result = select (h + 1, prset, pwset, nullptr, timeoutp);\r
+        int result = 0;\r
 \r
-                if (result >= 0 || errno != EINTR)\r
-                    break;\r
+        for (;;)\r
+        {\r
+           #if JUCE_WINDOWS\r
+            result = WSAPoll (&pfd, 1, timeoutMsecs);\r
+           #else\r
+            result = poll (&pfd, 1, timeoutMsecs);\r
+           #endif\r
+\r
+            if (result >= 0\r
+               #if JUCE_WINDOWS\r
+                || result == SOCKET_ERROR\r
+               #else\r
+                || errno != EINTR\r
+               #endif\r
+                )\r
+            {\r
+                break;\r
             }\r
-\r
-            if (result < 0)\r
-                return -1;\r
         }\r
+\r
+        if (result < 0)\r
+            return -1;\r
        #endif\r
 \r
         // we are closing\r
@@ -309,26 +357,10 @@ namespace SocketHelpers
                 return -1;\r
         }\r
 \r
+       #if JUCE_MINGW\r
         return FD_ISSET (h, forReading ? &rset : &wset) ? 1 : 0;\r
-    }\r
-\r
-    static bool setSocketBlockingState (SocketHandle handle, bool shouldBlock) noexcept\r
-    {\r
-       #if JUCE_WINDOWS\r
-        u_long nonBlocking = shouldBlock ? 0 : (u_long) 1;\r
-        return ioctlsocket (handle, FIONBIO, &nonBlocking) == 0;\r
        #else\r
-        int socketFlags = fcntl (handle, F_GETFL, 0);\r
-\r
-        if (socketFlags == -1)\r
-            return false;\r
-\r
-        if (shouldBlock)\r
-            socketFlags &= ~O_NONBLOCK;\r
-        else\r
-            socketFlags |= O_NONBLOCK;\r
-\r
-        return fcntl (handle, F_SETFL, socketFlags) == 0;\r
+        return (pfd.revents & eventsFlag) != 0;\r
        #endif\r
     }\r
 \r
@@ -688,8 +720,6 @@ int DatagramSocket::read (void* destBuffer, int maxBytesToRead, bool shouldBlock
         return -1;\r
 \r
     std::atomic<bool> connected { true };\r
-\r
-    SocketHelpers::setSocketBlockingState (handle, shouldBlock);\r
     return SocketHelpers::readSocket (handle, destBuffer, maxBytesToRead,\r
                                       connected, shouldBlock, readLock);\r
 }\r
@@ -700,8 +730,6 @@ int DatagramSocket::read (void* destBuffer, int maxBytesToRead, bool shouldBlock
         return -1;\r
 \r
     std::atomic<bool> connected { true };\r
-\r
-    SocketHelpers::setSocketBlockingState (handle, shouldBlock);\r
     return SocketHelpers::readSocket (handle, destBuffer, maxBytesToRead, connected,\r
                                       shouldBlock, readLock, &senderIPAddress, &senderPort);\r
 }\r
index 72d2536ecdb5a27fb75e94d8499d67673bc2c506..26169129a514fde0b694d184744356d70b1dcb78 100644 (file)
@@ -135,7 +135,7 @@ URL::DownloadTask::DownloadTask() {}
 URL::DownloadTask::~DownloadTask() {}\r
 \r
 //==============================================================================\r
-URL::URL() noexcept {}\r
+URL::URL() {}\r
 \r
 URL::URL (const String& u)  : url (u)\r
 {\r
@@ -171,7 +171,6 @@ URL::URL (File localFile)
             url = "/" + url;\r
     }\r
 \r
-\r
     url = "file://" + url;\r
 \r
     jassert (isWellFormed());\r
@@ -287,6 +286,20 @@ namespace URLHelpers
         else\r
             path += suffix;\r
     }\r
+\r
+    static String removeLastPathSection (const String& url)\r
+    {\r
+        auto startOfPath = findStartOfPath (url);\r
+        auto lastSlash = url.lastIndexOfChar ('/');\r
+\r
+        if (lastSlash > startOfPath && lastSlash == url.length() - 1)\r
+            return removeLastPathSection (url.dropLastCharacters (1));\r
+\r
+        if (lastSlash < 0)\r
+            return url;\r
+\r
+        return url.substring (0, std::max (startOfPath, lastSlash));\r
+    }\r
 }\r
 \r
 void URL::addParameter (const String& name, const String& value)\r
@@ -344,10 +357,10 @@ String URL::getScheme() const
     return url.substring (0, URLHelpers::findEndOfScheme (url) - 1);\r
 }\r
 \r
-#ifndef JUCE_ANDROID\r
+#if ! JUCE_ANDROID\r
 bool URL::isLocalFile() const\r
 {\r
-    return (getScheme() == "file");\r
+    return getScheme() == "file";\r
 }\r
 \r
 File URL::getLocalFile() const\r
@@ -371,7 +384,7 @@ File URL::fileFromFileSchemeURL (const URL& fileURL)
 \r
     auto path = removeEscapeChars (fileURL.getDomainInternal (true)).replace ("+", "%2B");\r
 \r
-   #ifdef JUCE_WINDOWS\r
+   #if JUCE_WINDOWS\r
     bool isUncPath = (! fileURL.url.startsWith ("file:///"));\r
    #else\r
     path = File::getSeparatorString() + path;\r
@@ -382,7 +395,7 @@ File URL::fileFromFileSchemeURL (const URL& fileURL)
     for (auto urlElement : urlElements)\r
         path += File::getSeparatorString() + removeEscapeChars (urlElement.replace ("+", "%2B"));\r
 \r
-   #ifdef JUCE_WINDOWS\r
+   #if JUCE_WINDOWS\r
     if (isUncPath)\r
         path = "\\\\" + path;\r
    #endif\r
@@ -406,10 +419,10 @@ URL URL::withNewDomainAndPath (const String& newURL) const
 \r
 URL URL::withNewSubPath (const String& newPath) const\r
 {\r
-    const int startOfPath = URLHelpers::findStartOfPath (url);\r
-\r
     URL u (*this);\r
 \r
+    auto startOfPath = URLHelpers::findStartOfPath (url);\r
+\r
     if (startOfPath > 0)\r
         u.url = url.substring (0, startOfPath);\r
 \r
@@ -417,6 +430,13 @@ URL URL::withNewSubPath (const String& newPath) const
     return u;\r
 }\r
 \r
+URL URL::getParentURL() const\r
+{\r
+    URL u (*this);\r
+    u.url = URLHelpers::removeLastPathSection (u.url);\r
+    return u;\r
+}\r
+\r
 URL URL::getChildURL (const String& subPath) const\r
 {\r
     URL u (*this);\r
@@ -482,18 +502,15 @@ void URL::createHeadersAndPostData (String& headers, MemoryBlock& postDataToWrit
 //==============================================================================\r
 bool URL::isProbablyAWebsiteURL (const String& possibleURL)\r
 {\r
-    static const char* validProtocols[] = { "http:", "ftp:", "https:" };\r
-\r
-    for (auto* protocol : validProtocols)\r
+    for (auto* protocol : { "http:", "https:", "ftp:" })\r
         if (possibleURL.startsWithIgnoreCase (protocol))\r
             return true;\r
 \r
-    if (possibleURL.containsChar ('@')\r
-        || possibleURL.containsChar (' '))\r
+    if (possibleURL.containsChar ('@') || possibleURL.containsChar (' '))\r
         return false;\r
 \r
-    const String topLevelDomain (possibleURL.upToFirstOccurrenceOf ("/", false, false)\r
-                                 .fromLastOccurrenceOf (".", false, false));\r
+    auto topLevelDomain = possibleURL.upToFirstOccurrenceOf ("/", false, false)\r
+                                     .fromLastOccurrenceOf (".", false, false);\r
 \r
     return topLevelDomain.isNotEmpty() && topLevelDomain.length() <= 3;\r
 }\r
@@ -520,8 +537,7 @@ String URL::getDomainInternal (bool ignorePort) const
 }\r
 \r
 #if JUCE_IOS\r
-URL::Bookmark::Bookmark (void* bookmarkToUse)\r
-    : data (bookmarkToUse)\r
+URL::Bookmark::Bookmark (void* bookmarkToUse) : data (bookmarkToUse)\r
 {\r
 }\r
 \r
@@ -612,12 +628,10 @@ private:
 \r
                 return urlToUse.getLocalFile();\r
             }\r
-            else\r
-            {\r
-                auto desc = [error localizedDescription];\r
-                ignoreUnused (desc);\r
-                jassertfalse;\r
-            }\r
+\r
+            auto desc = [error localizedDescription];\r
+            ignoreUnused (desc);\r
+            jassertfalse;\r
         }\r
 \r
         return urlToUse.getLocalFile();\r
@@ -659,10 +673,9 @@ InputStream* URL::createInputStream (bool usePostCommand,
        #else\r
         return getLocalFile().createInputStream();\r
        #endif\r
-\r
     }\r
 \r
-    std::unique_ptr<WebInputStream> wi (new WebInputStream (*this, usePostCommand));\r
+    auto wi = std::make_unique<WebInputStream> (*this, usePostCommand);\r
 \r
     struct ProgressCallbackCaller  : public WebInputStream::Listener\r
     {\r
index 8660339514d78b40198377e36752629d06957a66..6e60882222c33a96ec73f66963b82f3c090ff8b6 100644 (file)
@@ -39,7 +39,7 @@ class JUCE_API  URL
 public:\r
     //==============================================================================\r
     /** Creates an empty URL. */\r
-    URL() noexcept;\r
+    URL();\r
 \r
     /** Creates a URL from a string.\r
         This will parse any embedded parameters after a '?' character and store them\r
@@ -148,6 +148,11 @@ public:
     */\r
     URL withNewSubPath (const String& newPath) const;\r
 \r
+    /** Attempts to return a URL which is the parent folder containing this URL.\r
+        If there isn't a parent, this method will just return a copy of this URL.\r
+    */\r
+    URL getParentURL() const;\r
+\r
     /** Returns a new URL that refers to a sub-path relative to this one.\r
         E.g. if the URL is "http://www.xyz.com/foo" and you call this with\r
         "bar", it'll return "http://www.xyz.com/foo/bar". Note that there's no way for\r
@@ -263,7 +268,7 @@ public:
     URL withPOSTData (const MemoryBlock& postData) const;\r
 \r
     /** Returns the data that was set using withPOSTData(). */\r
-    String getPostData() const noexcept                             { return postData.toString(); }\r
+    String getPostData() const                                      { return postData.toString(); }\r
 \r
     /** Returns the data that was set using withPOSTData() as MemoryBlock. */\r
     const MemoryBlock& getPostDataAsMemoryBlock() const noexcept    { return postData; }\r
@@ -338,12 +343,12 @@ public:
     InputStream* createInputStream (bool doPostLikeRequest,\r
                                     OpenStreamProgressCallback* progressCallback = nullptr,\r
                                     void* progressCallbackContext = nullptr,\r
-                                    String extraHeaders = String(),\r
+                                    String extraHeaders = {},\r
                                     int connectionTimeOutMs = 0,\r
                                     StringPairArray* responseHeaders = nullptr,\r
                                     int* statusCode = nullptr,\r
                                     int numRedirectsToFollow = 5,\r
-                                    String httpRequestCmd = String()) const;\r
+                                    String httpRequestCmd = {}) const;\r
 \r
     /** Attempts to open an output stream to a URL for writing\r
 \r
index e9861cfb440c57f54c5d24774221e591cf541730..42712c73fd0f0e2318ae3c843a489d471e539c43 100644 (file)
@@ -117,7 +117,7 @@ namespace std
     template<typename T, typename... Args>\r
     unique_ptr<T> make_unique (Args&&... args)\r
     {\r
-        return unique_ptr<T> (new T (forward<Args> (args)...));\r
+        return unique_ptr<T> (new T (std::forward<Args> (args)...));\r
     }\r
 }\r
 #endif\r
index 316de1fb07326c64639098ec1c3b620a9ad3bad7..34aed37315a0f59fcbadc358427c84891116c7da 100644 (file)
@@ -29,7 +29,7 @@
 */\r
 #define JUCE_MAJOR_VERSION      5\r
 #define JUCE_MINOR_VERSION      4\r
-#define JUCE_BUILDNUMBER        4\r
+#define JUCE_BUILDNUMBER        5\r
 \r
 /** Current JUCE version number.\r
 \r
index 4650e16f17d0f8ee92ba1f644f107e0131353ed3..5e15212d0eadf0d7e3436703aad4f6dd9948cd9f 100644 (file)
@@ -43,7 +43,8 @@ PerformanceCounter::PerformanceCounter (const String& name, int runsPerPrintout,
 \r
 PerformanceCounter::~PerformanceCounter()\r
 {\r
-    printStatistics();\r
+    if (stats.numRuns > 0)\r
+        printStatistics();\r
 }\r
 \r
 PerformanceCounter::Statistics::Statistics() noexcept\r
index da1197419478c982ebc82c5f82d73097593f7869..86d5ca36c6960c46bf82514c510771d7409713a9 100644 (file)
@@ -35,7 +35,7 @@
 \r
   ID:               juce_cryptography\r
   vendor:           juce\r
-  version:          5.4.4\r
+  version:          5.4.5\r
   name:             JUCE cryptography classes\r
   description:      Classes for various basic cryptography functions, including RSA, Blowfish, MD5, SHA, etc.\r
   website:          http://www.juce.com/juce\r
index 0bca62ba61f7ad2f5778db4241709c863ca03df8..85ec23f5419529031e1312295e379abb3094491a 100644 (file)
@@ -35,7 +35,7 @@
 \r
   ID:               juce_data_structures\r
   vendor:           juce\r
-  version:          5.4.4\r
+  version:          5.4.5\r
   name:             JUCE data model helper classes\r
   description:      Classes for undo/redo management, and smart data structures.\r
   website:          http://www.juce.com/juce\r
index 6ffcda7570d6e49e1de85d1c9ac0a5b558f170a7..7f289cdf088d430a37fe6f4fae4ed5740f615736 100644 (file)
@@ -78,15 +78,15 @@ public:
 \r
     //==============================================================================\r
     /** Create a zero-sized AudioBlock. */\r
-    forcedinline AudioBlock() noexcept = default;\r
+    AudioBlock() noexcept = default;\r
 \r
     /** Creates an AudioBlock from a pointer to an array of channels.\r
         AudioBlock does not copy nor own the memory pointed to by dataToUse.\r
         Therefore it is the user's responsibility to ensure that the memory is retained\r
         throughout the life-time of the AudioBlock and released when no longer needed.\r
     */\r
-    forcedinline AudioBlock (SampleType* const* channelData,\r
-                             size_t numberOfChannels, size_t numberOfSamples) noexcept\r
+    constexpr AudioBlock (SampleType* const* channelData,\r
+                          size_t numberOfChannels, size_t numberOfSamples) noexcept\r
         : channels (channelData),\r
           numChannels (static_cast<ChannelCountType> (numberOfChannels)),\r
           numSamples (numberOfSamples)\r
@@ -98,8 +98,8 @@ public:
         Therefore it is the user's responsibility to ensure that the memory is retained\r
         throughout the life-time of the AudioBlock and released when no longer needed.\r
     */\r
-    forcedinline AudioBlock (SampleType* const* channelData, size_t numberOfChannels,\r
-                             size_t startSampleIndex, size_t numberOfSamples) noexcept\r
+    constexpr AudioBlock (SampleType* const* channelData, size_t numberOfChannels,\r
+                          size_t startSampleIndex, size_t numberOfSamples) noexcept\r
         : channels (channelData),\r
           numChannels (static_cast<ChannelCountType> (numberOfChannels)),\r
           startSample (startSampleIndex),\r
@@ -144,7 +144,7 @@ public:
         throughout the life-time of the AudioBlock without being modified.\r
     */\r
     template <typename OtherSampleType>\r
-    AudioBlock (AudioBuffer<OtherSampleType>& buffer) noexcept\r
+    constexpr AudioBlock (AudioBuffer<OtherSampleType>& buffer) noexcept\r
         : channels (buffer.getArrayOfWritePointers()),\r
           numChannels (static_cast<ChannelCountType> (buffer.getNumChannels())),\r
           numSamples (static_cast<size_t> (buffer.getNumSamples()))\r
@@ -196,7 +196,7 @@ public:
 \r
     //==============================================================================\r
     template <typename OtherSampleType>\r
-    bool operator== (const AudioBlock<OtherSampleType>& other) const noexcept\r
+    constexpr bool operator== (const AudioBlock<OtherSampleType>& other) const noexcept\r
     {\r
         return std::equal (channels,\r
                            channels + numChannels,\r
@@ -207,25 +207,20 @@ public:
     }\r
 \r
     template <typename OtherSampleType>\r
-    bool operator!= (const AudioBlock<OtherSampleType>& other) const noexcept\r
+    constexpr bool operator!= (const AudioBlock<OtherSampleType>& other) const noexcept\r
     {\r
         return ! (*this == other);\r
     }\r
 \r
     //==============================================================================\r
-    forcedinline size_t getNumSamples() const noexcept           { return numSamples; }\r
-    forcedinline size_t getNumChannels() const noexcept          { return static_cast<size_t> (numChannels); }\r
+    /** Returns the number of channels referenced by this block. */\r
+    constexpr size_t getNumChannels() const noexcept          { return static_cast<size_t> (numChannels); }\r
 \r
-    /** Returns a raw pointer into one of the channels in this block. */\r
-    forcedinline const SampleType* getChannelPointer (size_t channel) const noexcept\r
-    {\r
-        jassert (channel < numChannels);\r
-        jassert (numSamples > 0);\r
-        return channels[channel] + startSample;\r
-    }\r
+    /** Returns the number of samples referenced by this block. */\r
+    constexpr size_t getNumSamples()  const noexcept          { return numSamples; }\r
 \r
     /** Returns a raw pointer into one of the channels in this block. */\r
-    forcedinline SampleType* getChannelPointer (size_t channel) noexcept\r
+    SampleType* getChannelPointer (size_t channel) const noexcept\r
     {\r
         jassert (channel < numChannels);\r
         jassert (numSamples > 0);\r
@@ -233,7 +228,7 @@ public:
     }\r
 \r
     /** Returns an AudioBlock that represents one of the channels in this block. */\r
-    forcedinline AudioBlock getSingleChannelBlock (size_t channel) const noexcept\r
+    AudioBlock getSingleChannelBlock (size_t channel) const noexcept\r
     {\r
         jassert (channel < numChannels);\r
         return AudioBlock (channels + channel, 1, startSample, numSamples);\r
@@ -243,7 +238,7 @@ public:
         @param channelStart       First channel of the subset\r
         @param numChannelsToUse   Count of channels in the subset\r
     */\r
-    forcedinline AudioBlock getSubsetChannelBlock (size_t channelStart, size_t numChannelsToUse) const noexcept\r
+    AudioBlock getSubsetChannelBlock (size_t channelStart, size_t numChannelsToUse) const noexcept\r
     {\r
         jassert (channelStart < numChannels);\r
         jassert ((channelStart + numChannelsToUse) <= numChannels);\r
@@ -260,7 +255,7 @@ public:
     {\r
         jassert (isPositiveAndBelow (channel, numChannels));\r
         jassert (isPositiveAndBelow (sampleIndex, numSamples));\r
-        return channels[channel][startSample + sampleIndex];\r
+        return channels[channel][(size_t) startSample + (size_t) sampleIndex];\r
     }\r
 \r
     /** Modifies a sample in the buffer.\r
@@ -268,11 +263,11 @@ public:
         an assertion will be thrown, but in a release build, you're into 'undefined behaviour'\r
         territory.\r
     */\r
-    void setSample (int destChannel, int destSample, SampleType newValue) noexcept\r
+    void setSample (int destChannel, int destSample, SampleType newValue) const noexcept\r
     {\r
         jassert (isPositiveAndBelow (destChannel, numChannels));\r
         jassert (isPositiveAndBelow (destSample, numSamples));\r
-        channels[destChannel][startSample + destSample] = newValue;\r
+        channels[destChannel][(size_t) startSample + (size_t) destSample] = newValue;\r
     }\r
 \r
     /** Adds a value to a sample in the buffer.\r
@@ -280,79 +275,52 @@ public:
         an assertion will be thrown, but in a release build, you're into 'undefined behaviour'\r
         territory.\r
     */\r
-    void addSample (int destChannel, int destSample, SampleType valueToAdd) noexcept\r
+    void addSample (int destChannel, int destSample, SampleType valueToAdd) const noexcept\r
     {\r
         jassert (isPositiveAndBelow (destChannel, numChannels));\r
         jassert (isPositiveAndBelow (destSample, numSamples));\r
-        channels[destChannel][startSample + destSample] += valueToAdd;\r
+        channels[destChannel][(size_t) startSample + (size_t) destSample] += valueToAdd;\r
     }\r
 \r
     //==============================================================================\r
-    /** Clear the memory described by this AudioBlock. */\r
-    forcedinline AudioBlock& clear() noexcept\r
-    {\r
-        auto n = static_cast<int> (numSamples * sizeFactor);\r
-\r
-        for (size_t ch = 0; ch < numChannels; ++ch)\r
-            FloatVectorOperations::clear (channelPtr (ch), n);\r
+    /** Clears the memory referenced by this AudioBlock. */\r
+    AudioBlock&       clear()       noexcept   { clearInternal(); return *this; }\r
+    const AudioBlock& clear() const noexcept   { clearInternal(); return *this; }\r
 \r
-        return *this;\r
-    }\r
-\r
-    /** Fill memory with value. */\r
-    forcedinline AudioBlock& JUCE_VECTOR_CALLTYPE fill (SampleType value) noexcept\r
-    {\r
-        auto n = static_cast<int> (numSamples * sizeFactor);\r
-\r
-        for (size_t ch = 0; ch < numChannels; ++ch)\r
-            FloatVectorOperations::fill (channelPtr (ch), value, n);\r
-\r
-        return *this;\r
-    }\r
+    /** Fills the memory referenced by this AudioBlock with value. */\r
+    AudioBlock&       JUCE_VECTOR_CALLTYPE fill (SampleType value)       noexcept   { fillInternal (value); return *this; }\r
+    const AudioBlock& JUCE_VECTOR_CALLTYPE fill (SampleType value) const noexcept   { fillInternal (value); return *this; }\r
 \r
-    /** Copy the values in src to the receiver. */\r
+    /** Copies the values in src to this block. */\r
     template <typename OtherSampleType>\r
-    forcedinline AudioBlock& copy (const AudioBlock<OtherSampleType>& src) noexcept\r
-    {\r
-        auto maxChannels = jmin (src.numChannels, numChannels);\r
-        auto n = static_cast<int> (jmin (src.numSamples, numSamples) * sizeFactor);\r
-\r
-        for (size_t ch = 0; ch < maxChannels; ++ch)\r
-            FloatVectorOperations::copy (channelPtr (ch), src.channelPtr (ch), n);\r
-\r
-        return *this;\r
-    }\r
+    AudioBlock&       copyFrom (const AudioBlock<OtherSampleType>& src)       noexcept   { copyFromInternal (src); return *this; }\r
+    template <typename OtherSampleType>\r
+    const AudioBlock& copyFrom (const AudioBlock<OtherSampleType>& src) const noexcept   { copyFromInternal (src); return *this; }\r
 \r
-    /** Copy the values from a JUCE's AudioBuffer to the receiver.\r
+    /** Copy the values from a JUCE's AudioBuffer to this block.\r
 \r
         All indices and sizes are in the receiver's units, i.e. if SampleType is a\r
         SIMDRegister then incrementing srcPos by one will increase the sample position\r
         in the AudioBuffer's units by a factor of SIMDRegister<SampleType>::SIMDNumElements.\r
     */\r
-    forcedinline AudioBlock& copyFrom (const AudioBuffer<NumericType>& src, size_t srcPos = 0, size_t dstPos = 0,\r
-                                       size_t numElements = std::numeric_limits<size_t>::max())\r
-    {\r
-        auto srclen = static_cast<size_t> (src.getNumSamples()) / sizeFactor;\r
-        auto n = static_cast<int> (jmin (srclen - srcPos, numSamples - dstPos, numElements) * sizeFactor);\r
-        auto maxChannels = jmin (static_cast<size_t> (src.getNumChannels()), static_cast<size_t> (numChannels));\r
-\r
-        for (size_t ch = 0; ch < maxChannels; ++ch)\r
-            FloatVectorOperations::copy (channelPtr (ch) + dstPos,\r
-                                         src.getReadPointer (static_cast<int> (ch),\r
-                                                             static_cast<int> (srcPos * sizeFactor)),\r
-                                         n);\r
+    template <typename OtherSampleType>\r
+    AudioBlock&       copyFrom (const AudioBuffer<OtherSampleType>& src,\r
+                                size_t srcPos = 0, size_t dstPos = 0,\r
+                                size_t numElements = std::numeric_limits<size_t>::max())         { copyFromInternal (src, srcPos, dstPos, numElements); return *this; }\r
+    template <typename OtherSampleType>\r
+    const AudioBlock& copyFrom (const AudioBuffer<OtherSampleType>& src,\r
+                                size_t srcPos = 0, size_t dstPos = 0,\r
+                                size_t numElements = std::numeric_limits<size_t>::max()) const   { copyFromInternal (src, srcPos, dstPos, numElements); return *this; }\r
 \r
-        return *this;\r
-    }\r
 \r
-    /** Copy the values from the receiver to a JUCE's AudioBuffer.\r
+    /** Copies the values from this block to an AudioBuffer.\r
 \r
         All indices and sizes are in the receiver's units, i.e. if SampleType is a\r
         SIMDRegister then incrementing dstPos by one will increase the sample position\r
         in the AudioBuffer's units by a factor of SIMDRegister<SampleType>::SIMDNumElements.\r
     */\r
-    forcedinline const AudioBlock& copyTo (AudioBuffer<NumericType>& dst, size_t srcPos = 0, size_t dstPos = 0,\r
-                                           size_t numElements = std::numeric_limits<size_t>::max()) const\r
+    void copyTo (AudioBuffer<typename std::remove_const<NumericType>::type>& dst, size_t srcPos = 0, size_t dstPos = 0,\r
+                 size_t numElements = std::numeric_limits<size_t>::max()) const\r
     {\r
         auto dstlen = static_cast<size_t> (dst.getNumSamples()) / sizeFactor;\r
         auto n = static_cast<int> (jmin (numSamples - srcPos, dstlen - dstPos, numElements) * sizeFactor);\r
@@ -361,30 +329,19 @@ public:
         for (size_t ch = 0; ch < maxChannels; ++ch)\r
             FloatVectorOperations::copy (dst.getWritePointer (static_cast<int> (ch),\r
                                                               static_cast<int> (dstPos * sizeFactor)),\r
-                                         channelPtr (ch) + srcPos, n);\r
-\r
-        return *this;\r
+                                         getChannelPointer (ch) + srcPos, n);\r
     }\r
 \r
-    /** Move memory within the receiver from the position srcPos to the position dstPos.\r
+    /** Move memory within this block from the position srcPos to the position dstPos.\r
         If numElements is not specified then move will move the maximum amount of memory.\r
     */\r
-    forcedinline AudioBlock& move (size_t srcPos, size_t dstPos,\r
-                                   size_t numElements = std::numeric_limits<size_t>::max()) noexcept\r
-    {\r
-        jassert (srcPos <= numSamples && dstPos <= numSamples);\r
-        auto len = jmin (numSamples - srcPos, numSamples - dstPos, numElements) * sizeof (SampleType);\r
-\r
-        if (len != 0)\r
-            for (size_t ch = 0; ch < numChannels; ++ch)\r
-                ::memmove (getChannelPointer (ch) + dstPos,\r
-                           getChannelPointer (ch) + srcPos, len);\r
-\r
-        return *this;\r
-    }\r
+    AudioBlock&       move (size_t srcPos, size_t dstPos,\r
+                            size_t numElements = std::numeric_limits<size_t>::max())       noexcept   { moveInternal (srcPos, dstPos, numElements); return *this; }\r
+    const AudioBlock& move (size_t srcPos, size_t dstPos,\r
+                            size_t numElements = std::numeric_limits<size_t>::max()) const noexcept   { moveInternal (srcPos, dstPos, numElements); return *this; }\r
 \r
     //==============================================================================\r
-    /** Return a new AudioBlock pointing to a sub-block inside the receiver. This\r
+    /** Return a new AudioBlock pointing to a sub-block inside this block. This\r
         function does not copy the memory and you must ensure that the original memory\r
         pointed to by the receiver remains valid through-out the life-time of the\r
         returned sub-block.\r
@@ -393,7 +350,7 @@ public:
                            will become the first element of the return value.\r
         @param newLength   The number of elements of the newly created sub-block.\r
     */\r
-    inline AudioBlock getSubBlock (size_t newOffset, size_t newLength) const noexcept\r
+    AudioBlock getSubBlock (size_t newOffset, size_t newLength) const noexcept\r
     {\r
         jassert (newOffset < numSamples);\r
         jassert (newOffset + newLength <= numSamples);\r
@@ -401,168 +358,391 @@ public:
         return AudioBlock (channels, numChannels, startSample + newOffset, newLength);\r
     }\r
 \r
-    /** Return a new AudioBlock pointing to a sub-block inside the receiver. This\r
+    /** Return a new AudioBlock pointing to a sub-block inside this block. This\r
         function does not copy the memory and you must ensure that the original memory\r
         pointed to by the receiver remains valid through-out the life-time of the\r
         returned sub-block.\r
 \r
-        @param newOffset   The index of an element inside the receiver which will\r
+        @param newOffset   The index of an element inside the block which will\r
                            will become the first element of the return value.\r
                            The return value will include all subsequent elements\r
                            of the receiver.\r
     */\r
-    inline AudioBlock getSubBlock (size_t newOffset) const noexcept\r
+    AudioBlock getSubBlock (size_t newOffset) const noexcept\r
     {\r
         return getSubBlock (newOffset, getNumSamples() - newOffset);\r
     }\r
 \r
     //==============================================================================\r
-    /** Adds a fixed value to the receiver. */\r
-    forcedinline AudioBlock& JUCE_VECTOR_CALLTYPE add (SampleType value) noexcept\r
+    /** Adds a fixed value to the elements in this block. */\r
+    AudioBlock&       JUCE_VECTOR_CALLTYPE add (SampleType value)       noexcept   { addInternal (value); return *this; }\r
+    const AudioBlock& JUCE_VECTOR_CALLTYPE add (SampleType value) const noexcept   { addInternal (value); return *this; }\r
+\r
+    /** Adds the elements in the src block to the elements in this block. */\r
+    template <typename OtherSampleType>\r
+    AudioBlock&       add (AudioBlock<OtherSampleType> src)       noexcept   { addInternal (src); return *this; }\r
+    template <typename OtherSampleType>\r
+    const AudioBlock& add (AudioBlock<OtherSampleType> src) const noexcept   { addInternal (src); return *this; }\r
+\r
+    /** Adds a fixed value to each source value and replaces the contents of this block. */\r
+    template <typename OtherSampleType>\r
+    AudioBlock&       JUCE_VECTOR_CALLTYPE replaceWithSumOf (AudioBlock<OtherSampleType> src, SampleType value)      noexcept    { replaceWithSumOfInternal (src, value); return *this; }\r
+    template <typename OtherSampleType>\r
+    const AudioBlock& JUCE_VECTOR_CALLTYPE replaceWithSumOf (AudioBlock<OtherSampleType> src, SampleType value) const noexcept   { replaceWithSumOfInternal (src, value); return *this; }\r
+\r
+    /** Adds each source1 value to the corresponding source2 value and replaces the contents of this block. */\r
+    template <typename Src1SampleType, typename Src2SampleType>\r
+    AudioBlock&       replaceWithSumOf (AudioBlock<Src1SampleType> src1, AudioBlock<Src2SampleType> src2)       noexcept   { replaceWithSumOfInternal (src1, src2); return *this; }\r
+    template <typename Src1SampleType, typename Src2SampleType>\r
+    const AudioBlock& replaceWithSumOf (AudioBlock<Src1SampleType> src1, AudioBlock<Src2SampleType> src2) const noexcept   { replaceWithSumOfInternal (src1, src2); return *this; }\r
+\r
+    //==============================================================================\r
+    /** Subtracts a fixed value from the elements in this block. */\r
+    AudioBlock&       JUCE_VECTOR_CALLTYPE subtract (SampleType value)       noexcept   { subtractInternal (value); return *this; }\r
+    const AudioBlock& JUCE_VECTOR_CALLTYPE subtract (SampleType value) const noexcept   { subtractInternal (value); return *this; }\r
+\r
+    /** Subtracts the source values from the elements in this block. */\r
+    template <typename OtherSampleType>\r
+    AudioBlock&       subtract (AudioBlock<OtherSampleType> src)       noexcept   { subtractInternal (src); return *this; }\r
+    template <typename OtherSampleType>\r
+    const AudioBlock& subtract (AudioBlock<OtherSampleType> src) const noexcept   { subtractInternal (src); return *this; }\r
+\r
+    /** Subtracts a fixed value from each source value and replaces the contents of this block. */\r
+    template <typename OtherSampleType>\r
+    AudioBlock&       JUCE_VECTOR_CALLTYPE replaceWithDifferenceOf (AudioBlock<OtherSampleType> src, SampleType value)       noexcept   { replaceWithDifferenceOfInternal (src, value); return *this; }\r
+    template <typename OtherSampleType>\r
+    const AudioBlock& JUCE_VECTOR_CALLTYPE replaceWithDifferenceOf (AudioBlock<OtherSampleType> src, SampleType value) const noexcept   { replaceWithDifferenceOfInternal (src, value); return *this; }\r
+\r
+    /** Subtracts each source2 value from the corresponding source1 value and replaces the contents of this block. */\r
+    template <typename Src1SampleType, typename Src2SampleType>\r
+    AudioBlock&       replaceWithDifferenceOf (AudioBlock<Src1SampleType> src1, AudioBlock<Src2SampleType> src2)       noexcept   { replaceWithDifferenceOfInternal (src1, src2); return *this; }\r
+    template <typename Src1SampleType, typename Src2SampleType>\r
+    const AudioBlock& replaceWithDifferenceOf (AudioBlock<Src1SampleType> src1, AudioBlock<Src2SampleType> src2) const noexcept   { replaceWithDifferenceOfInternal (src1, src2); return *this; }\r
+\r
+    //==============================================================================\r
+    /** Multiplies the elements in this block by a fixed value. */\r
+    AudioBlock&       JUCE_VECTOR_CALLTYPE multiplyBy (SampleType value)       noexcept   { multiplyByInternal (value); return *this; }\r
+    const AudioBlock& JUCE_VECTOR_CALLTYPE multiplyBy (SampleType value) const noexcept   { multiplyByInternal (value); return *this; }\r
+\r
+    /** Multiplies the elements in this block by the elements in the src block */\r
+    template <typename OtherSampleType>\r
+    AudioBlock&       multiplyBy (AudioBlock<OtherSampleType> src)       noexcept   { multiplyByInternal (src); return *this; }\r
+    template <typename OtherSampleType>\r
+    const AudioBlock& multiplyBy (AudioBlock<OtherSampleType> src) const noexcept   { multiplyByInternal (src); return *this; }\r
+\r
+    /** Replaces the elements in this block with the product of the elements in the source src block and a fixed value. */\r
+    template <typename OtherSampleType>\r
+    AudioBlock&       JUCE_VECTOR_CALLTYPE replaceWithProductOf (AudioBlock<OtherSampleType> src, SampleType value)       noexcept   { replaceWithProductOfInternal (src, value); return *this; }\r
+    template <typename OtherSampleType>\r
+    const AudioBlock& JUCE_VECTOR_CALLTYPE replaceWithProductOf (AudioBlock<OtherSampleType> src, SampleType value) const noexcept   { replaceWithProductOfInternal (src, value); return *this; }\r
+\r
+    /** Replaces the elements in this block with the product of the elements in the src1 and scr2 blocks. */\r
+    template <typename Src1SampleType, typename Src2SampleType>\r
+    AudioBlock&       replaceWithProductOf (AudioBlock<Src1SampleType> src1, AudioBlock<Src2SampleType> src2)       noexcept   { replaceWithProductOfInternal (src1, src2); return *this; }\r
+    template <typename Src1SampleType, typename Src2SampleType>\r
+    const AudioBlock& replaceWithProductOf (AudioBlock<Src1SampleType> src1, AudioBlock<Src2SampleType> src2) const noexcept   { replaceWithProductOfInternal (src1, src2); return *this; }\r
+\r
+    //==============================================================================\r
+    /** Multiplies each channels of this block by a smoothly changing value. */\r
+    template <typename SmoothingType>\r
+    AudioBlock&       multiplyBy (SmoothedValue<SampleType, SmoothingType>& value)       noexcept   { multiplyByInternal (value); return *this; }\r
+    template <typename SmoothingType>\r
+    const AudioBlock& multiplyBy (SmoothedValue<SampleType, SmoothingType>& value) const noexcept   { multiplyByInternal (value); return *this; }\r
+\r
+    /** Replaces each channel of this block with the product of the src block and a smoothed value. */\r
+    template <typename OtherSampleType, typename SmoothingType>\r
+    AudioBlock&       replaceWithProductOf (AudioBlock<OtherSampleType> src, SmoothedValue<SampleType, SmoothingType>& value)       noexcept   { replaceWithProductOfInternal (src, value); return *this; }\r
+    template <typename OtherSampleType, typename SmoothingType>\r
+    const AudioBlock& replaceWithProductOf (AudioBlock<OtherSampleType> src, SmoothedValue<SampleType, SmoothingType>& value) const noexcept   { replaceWithProductOfInternal (src, value); return *this; }\r
+\r
+    //==============================================================================\r
+    /** Multiplies each value in src by a fixed value and adds the result to this block. */\r
+    template <typename OtherSampleType>\r
+    AudioBlock&       JUCE_VECTOR_CALLTYPE addProductOf (AudioBlock<OtherSampleType> src, SampleType factor)       noexcept   { addProductOfInternal (src, factor); return *this; }\r
+    template <typename OtherSampleType>\r
+    const AudioBlock& JUCE_VECTOR_CALLTYPE addProductOf (AudioBlock<OtherSampleType> src, SampleType factor) const noexcept   { addProductOfInternal (src, factor); return *this; }\r
+\r
+    /** Multiplies each value in srcA with the corresponding value in srcB and adds the result to this block. */\r
+    template <typename Src1SampleType, typename Src2SampleType>\r
+    AudioBlock&       addProductOf (AudioBlock<Src1SampleType> src1, AudioBlock<Src2SampleType> src2)       noexcept   { addProductOfInternal (src1, src2); return *this; }\r
+    template <typename Src1SampleType, typename Src2SampleType>\r
+    const AudioBlock& addProductOf (AudioBlock<Src1SampleType> src1, AudioBlock<Src2SampleType> src2) const noexcept   { addProductOfInternal (src1, src2); return *this; }\r
+\r
+    //==============================================================================\r
+    /** Negates each value of this block. */\r
+    AudioBlock&       negate()       noexcept   { negateInternal(); return *this; }\r
+    const AudioBlock& negate() const noexcept   { negateInternal(); return *this; }\r
+\r
+    /** Replaces the contents of this block with the negative of the values in the src block. */\r
+    template <typename OtherSampleType>\r
+    AudioBlock&       replaceWithNegativeOf (AudioBlock<OtherSampleType> src)       noexcept   { replaceWithNegativeOfInternal (src); return *this; }\r
+    template <typename OtherSampleType>\r
+    const AudioBlock& replaceWithNegativeOf (AudioBlock<OtherSampleType> src) const noexcept   { replaceWithNegativeOfInternal (src); return *this; }\r
+\r
+    /** Replaces the contents of this block with the absolute values of the src block. */\r
+    template <typename OtherSampleType>\r
+    AudioBlock&       replaceWithAbsoluteValueOf (AudioBlock<OtherSampleType> src)       noexcept   { replaceWithAbsoluteValueOfInternal (src); return *this; }\r
+    template <typename OtherSampleType>\r
+    const AudioBlock& replaceWithAbsoluteValueOf (AudioBlock<OtherSampleType> src) const noexcept   { replaceWithAbsoluteValueOfInternal (src); return *this; }\r
+\r
+    //==============================================================================\r
+    /** Replaces each element of this block with the minimum of the corresponding element of the source arrays. */\r
+    template <typename Src1SampleType, typename Src2SampleType>\r
+    AudioBlock&       replaceWithMinOf (AudioBlock<Src1SampleType> src1, AudioBlock<Src2SampleType> src2)       noexcept   { replaceWithMinOfInternal (src1, src2); return *this; }\r
+    template <typename Src1SampleType, typename Src2SampleType>\r
+    const AudioBlock& replaceWithMinOf (AudioBlock<Src1SampleType> src1, AudioBlock<Src2SampleType> src2) const noexcept   { replaceWithMinOfInternal (src1, src2); return *this; }\r
+\r
+    /** Replaces each element of this block with the maximum of the corresponding element of the source arrays. */\r
+    template <typename Src1SampleType, typename Src2SampleType>\r
+    AudioBlock&       replaceWithMaxOf (AudioBlock<Src1SampleType> src1, AudioBlock<Src2SampleType> src2)       noexcept   { replaceWithMaxOfInternal (src1, src2); return *this; }\r
+    template <typename Src1SampleType, typename Src2SampleType>\r
+    const AudioBlock& replaceWithMaxOf (AudioBlock<Src1SampleType> src1, AudioBlock<Src2SampleType> src2) const noexcept   { replaceWithMaxOfInternal (src1, src2); return *this; }\r
+\r
+    //==============================================================================\r
+    /** Finds the minimum and maximum value of the buffer. */\r
+    Range<typename std::remove_const<NumericType>::type> findMinAndMax() const noexcept\r
+    {\r
+        if (numChannels == 0)\r
+            return {};\r
+\r
+        auto n = static_cast<int> (numSamples * sizeFactor);\r
+        auto minmax = FloatVectorOperations::findMinAndMax (getChannelPointer (0), n);\r
+\r
+        for (size_t ch = 1; ch < numChannels; ++ch)\r
+            minmax = minmax.getUnionWith (FloatVectorOperations::findMinAndMax (getChannelPointer (ch), n));\r
+\r
+        return minmax;\r
+    }\r
+\r
+    //==============================================================================\r
+    // Convenient operator wrappers.\r
+    AudioBlock&       JUCE_VECTOR_CALLTYPE operator+= (SampleType value)       noexcept   { return add (value); }\r
+    const AudioBlock& JUCE_VECTOR_CALLTYPE operator+= (SampleType value) const noexcept   { return add (value); }\r
+\r
+    AudioBlock&                            operator+= (AudioBlock src)         noexcept   { return add (src); }\r
+    const AudioBlock&                      operator+= (AudioBlock src)   const noexcept   { return add (src); }\r
+\r
+    AudioBlock&       JUCE_VECTOR_CALLTYPE operator-= (SampleType value)       noexcept   { return subtract (value); }\r
+    const AudioBlock& JUCE_VECTOR_CALLTYPE operator-= (SampleType value) const noexcept   { return subtract (value); }\r
+\r
+    AudioBlock&                            operator-= (AudioBlock src)         noexcept   { return subtract (src); }\r
+    const AudioBlock&                      operator-= (AudioBlock src)   const noexcept   { return subtract (src); }\r
+\r
+    AudioBlock&       JUCE_VECTOR_CALLTYPE operator*= (SampleType value)       noexcept   { return multiplyBy (value); }\r
+    const AudioBlock& JUCE_VECTOR_CALLTYPE operator*= (SampleType value) const noexcept   { return multiplyBy (value); }\r
+\r
+    AudioBlock&                            operator*= (AudioBlock src)         noexcept   { return multiplyBy (src); }\r
+    const AudioBlock&                      operator*= (AudioBlock src)   const noexcept   { return multiplyBy (src); }\r
+\r
+    template <typename SmoothingType>\r
+    AudioBlock&       operator*= (SmoothedValue<SampleType, SmoothingType>& value)       noexcept   { return multiplyBy (value); }\r
+    template <typename SmoothingType>\r
+    const AudioBlock& operator*= (SmoothedValue<SampleType, SmoothingType>& value) const noexcept   { return multiplyBy (value); }\r
+\r
+    //==============================================================================\r
+    // This class can only be used with floating point types\r
+    static_assert (std::is_same<std::remove_const_t<SampleType>, float>::value\r
+                    || std::is_same<std::remove_const_t<SampleType>, double>::value\r
+                  #if JUCE_USE_SIMD\r
+                    || std::is_same<std::remove_const_t<SampleType>, SIMDRegister<float>>::value\r
+                    || std::is_same<std::remove_const_t<SampleType>, SIMDRegister<double>>::value\r
+                  #endif\r
+                   , "AudioBlock only supports single or double precision floating point types");\r
+\r
+    //==============================================================================\r
+    /** Applies a function to each value in an input block, putting the result into an output block.\r
+        The function supplied must take a SampleType as its parameter, and return a SampleType.\r
+        The two blocks must have the same number of channels and samples.\r
+    */\r
+    template <typename Src1SampleType, typename Src2SampleType, typename FunctionType>\r
+    static void process (AudioBlock<Src1SampleType> inBlock, AudioBlock<Src2SampleType> outBlock, FunctionType&& function)\r
+    {\r
+        auto len = inBlock.getNumSamples();\r
+        auto numChans = inBlock.getNumChannels();\r
+\r
+        jassert (len == outBlock.getNumSamples());\r
+        jassert (numChans == outBlock.getNumChannels());\r
+\r
+        for (ChannelCountType c = 0; c < numChans; ++c)\r
+        {\r
+            auto* src = inBlock.getChannelPointer (c);\r
+            auto* dst = outBlock.getChannelPointer (c);\r
+\r
+            for (size_t i = 0; i < len; ++i)\r
+                dst[i] = function (src[i]);\r
+        }\r
+    }\r
+\r
+private:\r
+    //==============================================================================\r
+    void JUCE_VECTOR_CALLTYPE clearInternal() const noexcept\r
     {\r
         auto n = static_cast<int> (numSamples * sizeFactor);\r
 \r
         for (size_t ch = 0; ch < numChannels; ++ch)\r
-            FloatVectorOperations::add (channelPtr (ch), value, n);\r
+            FloatVectorOperations::clear (getChannelPointer (ch), n);\r
+    }\r
 \r
-        return *this;\r
+    void JUCE_VECTOR_CALLTYPE fillInternal (SampleType value) const noexcept\r
+    {\r
+        auto n = static_cast<int> (numSamples * sizeFactor);\r
+\r
+        for (size_t ch = 0; ch < numChannels; ++ch)\r
+            FloatVectorOperations::fill (getChannelPointer (ch), value, n);\r
+    }\r
+\r
+    template <typename OtherSampleType>\r
+    void copyFromInternal (const AudioBlock<OtherSampleType>& src) const noexcept\r
+    {\r
+        auto maxChannels = jmin (src.numChannels, numChannels);\r
+        auto n = static_cast<int> (jmin (src.numSamples, numSamples) * sizeFactor);\r
+\r
+        for (size_t ch = 0; ch < maxChannels; ++ch)\r
+            FloatVectorOperations::copy (getChannelPointer (ch), src.getChannelPointer (ch), n);\r
+    }\r
+\r
+    template <typename OtherSampleType>\r
+    void copyFromInternal (const AudioBuffer<OtherSampleType>& src, size_t srcPos, size_t dstPos, size_t numElements) const\r
+    {\r
+        auto srclen = static_cast<size_t> (src.getNumSamples()) / sizeFactor;\r
+        auto n = static_cast<int> (jmin (srclen - srcPos, numSamples - dstPos, numElements) * sizeFactor);\r
+        auto maxChannels = jmin (static_cast<size_t> (src.getNumChannels()), static_cast<size_t> (numChannels));\r
+\r
+        for (size_t ch = 0; ch < maxChannels; ++ch)\r
+            FloatVectorOperations::copy (getChannelPointer (ch) + dstPos,\r
+                                         src.getReadPointer (static_cast<int> (ch),\r
+                                                             static_cast<int> (srcPos * sizeFactor)),\r
+                                         n);\r
+    }\r
+\r
+    void moveInternal (size_t srcPos, size_t dstPos,\r
+                       size_t numElements = std::numeric_limits<size_t>::max()) const noexcept\r
+    {\r
+        jassert (srcPos <= numSamples && dstPos <= numSamples);\r
+        auto len = jmin (numSamples - srcPos, numSamples - dstPos, numElements) * sizeof (SampleType);\r
+\r
+        if (len != 0)\r
+            for (size_t ch = 0; ch < numChannels; ++ch)\r
+                ::memmove (getChannelPointer (ch) + dstPos,\r
+                           getChannelPointer (ch) + srcPos, len);\r
+    }\r
+\r
+    //==============================================================================\r
+    void JUCE_VECTOR_CALLTYPE addInternal (SampleType value) const noexcept\r
+    {\r
+        auto n = static_cast<int> (numSamples * sizeFactor);\r
+\r
+        for (size_t ch = 0; ch < numChannels; ++ch)\r
+            FloatVectorOperations::add (getChannelPointer (ch), value, n);\r
     }\r
 \r
-    /** Adds the source values to the receiver. */\r
     template <typename OtherSampleType>\r
-    forcedinline AudioBlock& add (AudioBlock<OtherSampleType> src) noexcept\r
+    void addInternal (AudioBlock<OtherSampleType> src) const noexcept\r
     {\r
         jassert (numChannels == src.numChannels);\r
         auto n = static_cast<int> (jmin (numSamples, src.numSamples) * sizeFactor);\r
 \r
         for (size_t ch = 0; ch < numChannels; ++ch)\r
-            FloatVectorOperations::add (channelPtr (ch), src.channelPtr (ch), n);\r
-\r
-        return *this;\r
+            FloatVectorOperations::add (getChannelPointer (ch), src.getChannelPointer (ch), n);\r
     }\r
 \r
-    /** Adds a fixed value to each source value and stores it in the destination array of the receiver. */\r
     template <typename OtherSampleType>\r
-    forcedinline AudioBlock& JUCE_VECTOR_CALLTYPE add (AudioBlock<OtherSampleType> src, SampleType value) noexcept\r
+    void JUCE_VECTOR_CALLTYPE replaceWithSumOfInternal (AudioBlock<OtherSampleType> src, SampleType value) const noexcept\r
     {\r
         jassert (numChannels == src.numChannels);\r
         auto n = static_cast<int> (jmin (numSamples, src.numSamples) * sizeFactor);\r
 \r
         for (size_t ch = 0; ch < numChannels; ++ch)\r
-            FloatVectorOperations::add (channelPtr (ch), src.channelPtr (ch), value, n);\r
-\r
-        return *this;\r
+            FloatVectorOperations::add (getChannelPointer (ch), src.getChannelPointer (ch), value, n);\r
     }\r
 \r
-    /** Adds each source1 value to the corresponding source2 value and stores it in the destination array of the receiver. */\r
     template <typename Src1SampleType, typename Src2SampleType>\r
-    forcedinline AudioBlock& add (AudioBlock<Src1SampleType> src1, AudioBlock<Src2SampleType> src2) noexcept\r
+    void replaceWithSumOfInternal (AudioBlock<Src1SampleType> src1, AudioBlock<Src2SampleType> src2) const noexcept\r
     {\r
         jassert (numChannels == src1.numChannels && src1.numChannels == src2.numChannels);\r
         auto n = static_cast<int> (jmin (numSamples, src1.numSamples, src2.numSamples) * sizeFactor);\r
 \r
         for (size_t ch = 0; ch < numChannels; ++ch)\r
-            FloatVectorOperations::add (channelPtr (ch), src1.channelPtr (ch), src2.getChannelPointer (ch), n);\r
-\r
-        return *this;\r
+            FloatVectorOperations::add (getChannelPointer (ch), src1.getChannelPointer (ch), src2.getChannelPointer (ch), n);\r
     }\r
 \r
-    /** Subtracts a fixed value from the receiver. */\r
-    forcedinline AudioBlock& JUCE_VECTOR_CALLTYPE subtract (SampleType value) noexcept\r
+    //==============================================================================\r
+    constexpr void JUCE_VECTOR_CALLTYPE subtractInternal (SampleType value) const noexcept\r
     {\r
-        return add (value * static_cast<SampleType> (-1.0));\r
+        addInternal (value * static_cast<SampleType> (-1.0));\r
     }\r
 \r
-    /** Subtracts the source values from the receiver. */\r
     template <typename OtherSampleType>\r
-    forcedinline AudioBlock& subtract (AudioBlock<OtherSampleType> src) noexcept\r
+    void subtractInternal (AudioBlock<OtherSampleType> src) const noexcept\r
     {\r
         jassert (numChannels == src.numChannels);\r
         auto n = static_cast<int> (jmin (numSamples, src.numSamples) * sizeFactor);\r
 \r
         for (size_t ch = 0; ch < numChannels; ++ch)\r
-            FloatVectorOperations::subtract (channelPtr (ch), src.channelPtr (ch), n);\r
-\r
-        return *this;\r
+            FloatVectorOperations::subtract (getChannelPointer (ch), src.getChannelPointer (ch), n);\r
     }\r
 \r
-    /** Subtracts a fixed value from each source value and stores it in the destination array of the receiver. */\r
     template <typename OtherSampleType>\r
-    forcedinline AudioBlock& JUCE_VECTOR_CALLTYPE subtract (AudioBlock<OtherSampleType> src, SampleType value) noexcept\r
+    void JUCE_VECTOR_CALLTYPE replaceWithDifferenceOfInternal (AudioBlock<OtherSampleType> src, SampleType value) const noexcept\r
     {\r
-        return add (src, static_cast<SampleType> (-1.0) * value);\r
+        replaceWithSumOfInternal (src, static_cast<SampleType> (-1.0) * value);\r
     }\r
 \r
-    /** Subtracts each source2 value from the corresponding source1 value and stores it in the destination array of the receiver. */\r
     template <typename Src1SampleType, typename Src2SampleType>\r
-    forcedinline AudioBlock& subtract (AudioBlock<Src1SampleType> src1, AudioBlock<Src2SampleType> src2) noexcept\r
+    void replaceWithDifferenceOfInternal (AudioBlock<Src1SampleType> src1, AudioBlock<Src2SampleType> src2) const noexcept\r
     {\r
         jassert (numChannels == src1.numChannels && src1.numChannels == src2.numChannels);\r
         auto n = static_cast<int> (jmin (numSamples, src1.numSamples, src2.numSamples) * sizeFactor);\r
 \r
         for (size_t ch = 0; ch < numChannels; ++ch)\r
-            FloatVectorOperations::subtract (channelPtr (ch), src1.channelPtr (ch), src2.channelPtr (ch), n);\r
-\r
-        return *this;\r
+            FloatVectorOperations::subtract (getChannelPointer (ch), src1.getChannelPointer (ch), src2.getChannelPointer (ch), n);\r
     }\r
 \r
-    /** Multiplies a fixed value to the receiver. */\r
-    forcedinline AudioBlock& JUCE_VECTOR_CALLTYPE multiply (SampleType value) noexcept\r
+    //==============================================================================\r
+    void JUCE_VECTOR_CALLTYPE multiplyByInternal (SampleType value) const noexcept\r
     {\r
         auto n = static_cast<int> (numSamples * sizeFactor);\r
 \r
         for (size_t ch = 0; ch < numChannels; ++ch)\r
-            FloatVectorOperations::multiply (channelPtr (ch), value, n);\r
-\r
-        return *this;\r
+            FloatVectorOperations::multiply (getChannelPointer (ch), value, n);\r
     }\r
 \r
-    /** Multiplies the source values to the receiver. */\r
     template <typename OtherSampleType>\r
-    forcedinline AudioBlock& multiply (AudioBlock<OtherSampleType> src) noexcept\r
+    void multiplyByInternal (AudioBlock<OtherSampleType> src) const noexcept\r
     {\r
         jassert (numChannels == src.numChannels);\r
         auto n = static_cast<int> (jmin (numSamples, src.numSamples) * sizeFactor);\r
 \r
         for (size_t ch = 0; ch < numChannels; ++ch)\r
-            FloatVectorOperations::multiply (channelPtr (ch), src.channelPtr (ch), n);\r
-\r
-        return *this;\r
+            FloatVectorOperations::multiply (getChannelPointer (ch), src.getChannelPointer (ch), n);\r
     }\r
 \r
-    /** Multiplies a fixed value to each source value and stores it in the destination array of the receiver. */\r
     template <typename OtherSampleType>\r
-    forcedinline AudioBlock& JUCE_VECTOR_CALLTYPE multiply (AudioBlock<OtherSampleType> src, SampleType value) noexcept\r
+    void JUCE_VECTOR_CALLTYPE replaceWithProductOfInternal (AudioBlock<OtherSampleType> src, SampleType value) const noexcept\r
     {\r
         jassert (numChannels == src.numChannels);\r
         auto n = static_cast<int> (jmin (numSamples, src.numSamples) * sizeFactor);\r
 \r
         for (size_t ch = 0; ch < numChannels; ++ch)\r
-            FloatVectorOperations::multiply (channelPtr (ch), src.channelPtr (ch), value, n);\r
-\r
-        return *this;\r
+            FloatVectorOperations::multiply (getChannelPointer (ch), src.getChannelPointer (ch), value, n);\r
     }\r
 \r
-    /** Multiplies each source1 value to the corresponding source2 value and stores it in the destination array of the receiver. */\r
     template <typename Src1SampleType, typename Src2SampleType>\r
-    forcedinline AudioBlock& multiply (AudioBlock<Src1SampleType> src1, AudioBlock<Src2SampleType> src2) noexcept\r
+    void replaceWithProductOfInternal (AudioBlock<Src1SampleType> src1, AudioBlock<Src2SampleType> src2) const noexcept\r
     {\r
         jassert (numChannels == src1.numChannels && src1.numChannels == src2.numChannels);\r
         auto n = static_cast<int> (jmin (numSamples, src1.numSamples, src2.numSamples) * sizeFactor);\r
 \r
         for (size_t ch = 0; ch < numChannels; ++ch)\r
-            FloatVectorOperations::multiply (channelPtr (ch), src1.channelPtr (ch), src2.channelPtr (ch), n);\r
-\r
-        return *this;\r
+            FloatVectorOperations::multiply (getChannelPointer (ch), src1.getChannelPointer (ch), src2.getChannelPointer (ch), n);\r
     }\r
 \r
-    /** Multiplies all channels of the AudioBlock by a smoothly changing value and stores them . */\r
     template <typename SmoothingType>\r
-    AudioBlock& multiply (SmoothedValue<SampleType, SmoothingType>& value) noexcept\r
+    void multiplyByInternal (SmoothedValue<SampleType, SmoothingType>& value) const noexcept\r
     {\r
         if (! value.isSmoothing())\r
         {\r
-            *this *= value.getTargetValue();\r
+            multiplyByInternal (value.getTargetValue());\r
         }\r
         else\r
         {\r
@@ -571,22 +751,19 @@ public:
                 const auto scaler = value.getNextValue();\r
 \r
                 for (size_t ch = 0; ch < numChannels; ++ch)\r
-                    channelPtr (ch)[i] *= scaler;\r
+                    getChannelPointer (ch)[i] *= scaler;\r
             }\r
         }\r
-\r
-        return *this;\r
     }\r
 \r
-    /** Multiplies all channels of the source by a smoothly changing value and stores them in the receiver. */\r
     template <typename OtherSampleType, typename SmoothingType>\r
-    AudioBlock& multiply (AudioBlock<OtherSampleType> src, SmoothedValue<SampleType, SmoothingType>& value) noexcept\r
+    void replaceWithProductOfInternal (AudioBlock<OtherSampleType> src, SmoothedValue<SampleType, SmoothingType>& value) const noexcept\r
     {\r
         jassert (numChannels == src.numChannels);\r
 \r
         if (! value.isSmoothing())\r
         {\r
-            multiply (src, value.getTargetValue());\r
+            replaceWithProductOfInternal (src, value.getTargetValue());\r
         }\r
         else\r
         {\r
@@ -597,162 +774,79 @@ public:
                 const auto scaler = value.getNextValue();\r
 \r
                 for (size_t ch = 0; ch < numChannels; ++ch)\r
-                    channelPtr (ch)[i] = scaler * src.getChannelPointer (ch)[i];\r
+                    getChannelPointer (ch)[i] = scaler * src.getChannelPointer (ch)[i];\r
             }\r
         }\r
-\r
-        return *this;\r
     }\r
 \r
-    /** Multiplies each value in src with factor and adds the result to the receiver. */\r
+    //==============================================================================\r
     template <typename OtherSampleType>\r
-    forcedinline AudioBlock& JUCE_VECTOR_CALLTYPE addWithMultiply (AudioBlock<OtherSampleType> src, SampleType factor) noexcept\r
+    void JUCE_VECTOR_CALLTYPE addProductOfInternal (AudioBlock<OtherSampleType> src, SampleType factor) const noexcept\r
     {\r
         jassert (numChannels == src.numChannels);\r
         auto n = static_cast<int> (jmin (numSamples, src.numSamples) * sizeFactor);\r
 \r
         for (size_t ch = 0; ch < numChannels; ++ch)\r
-            FloatVectorOperations::addWithMultiply (channelPtr (ch), src.channelPtr (ch), factor, n);\r
-\r
-        return *this;\r
+            FloatVectorOperations::addWithMultiply (getChannelPointer (ch), src.getChannelPointer (ch), factor, n);\r
     }\r
 \r
-    /** Multiplies each value in srcA with the corresponding value in srcB and adds the result to the receiver. */\r
     template <typename Src1SampleType, typename Src2SampleType>\r
-    forcedinline AudioBlock& addWithMultiply (AudioBlock<Src1SampleType> src1, AudioBlock<Src2SampleType> src2) noexcept\r
+    void addProductOfInternal (AudioBlock<Src1SampleType> src1, AudioBlock<Src2SampleType> src2) const noexcept\r
     {\r
         jassert (numChannels == src1.numChannels && src1.numChannels == src2.numChannels);\r
         auto n = static_cast<int> (jmin (numSamples, src1.numSamples, src2.numSamples) * sizeFactor);\r
 \r
         for (size_t ch = 0; ch < numChannels; ++ch)\r
-            FloatVectorOperations::addWithMultiply (channelPtr (ch), src1.channelPtr (ch), src2.channelPtr (ch), n);\r
-\r
-        return *this;\r
+            FloatVectorOperations::addWithMultiply (getChannelPointer (ch), src1.getChannelPointer (ch), src2.getChannelPointer (ch), n);\r
     }\r
 \r
-    /** Negates each value of the receiver. */\r
-    forcedinline AudioBlock& negate() noexcept\r
+    //==============================================================================\r
+    constexpr void negateInternal() const noexcept\r
     {\r
-        return multiply (static_cast<SampleType> (-1.0));\r
+        multiplyByInternal (static_cast<SampleType> (-1.0));\r
     }\r
 \r
-    /** Negates each value of source and stores it in the receiver. */\r
     template <typename OtherSampleType>\r
-    forcedinline AudioBlock& replaceWithNegativeOf (AudioBlock<OtherSampleType> src) noexcept\r
+    void replaceWithNegativeOfInternal (AudioBlock<OtherSampleType> src) const noexcept\r
     {\r
         jassert (numChannels == src.numChannels);\r
         auto n = static_cast<int> (jmin (numSamples, src.numSamples) * sizeFactor);\r
 \r
         for (size_t ch = 0; ch < numChannels; ++ch)\r
-            FloatVectorOperations::negate (channelPtr (ch), src.channelPtr (ch), n);\r
-\r
-        return *this;\r
+            FloatVectorOperations::negate (getChannelPointer (ch), src.getChannelPointer (ch), n);\r
     }\r
 \r
-    /** Takes the absolute value of each element of src and stores it inside the receiver. */\r
     template <typename OtherSampleType>\r
-    forcedinline AudioBlock& replaceWithAbsoluteValueOf (AudioBlock<OtherSampleType> src) noexcept\r
+    void replaceWithAbsoluteValueOfInternal (AudioBlock<OtherSampleType> src) const noexcept\r
     {\r
         jassert (numChannels == src.numChannels);\r
         auto n = static_cast<int> (jmin (numSamples, src.numSamples) * sizeFactor);\r
 \r
         for (size_t ch = 0; ch < numChannels; ++ch)\r
-            FloatVectorOperations::abs (channelPtr (ch), src.channelPtr (ch), n);\r
-\r
-        return *this;\r
+            FloatVectorOperations::abs (getChannelPointer (ch), src.getChannelPointer (ch), n);\r
     }\r
 \r
-    /** Each element of receiver will be the minimum of the corresponding element of the source arrays. */\r
+    //==============================================================================\r
     template <typename Src1SampleType, typename Src2SampleType>\r
-    forcedinline AudioBlock& min (AudioBlock<Src1SampleType> src1, AudioBlock<Src2SampleType> src2) noexcept\r
+    void replaceWithMinOfInternal (AudioBlock<Src1SampleType> src1, AudioBlock<Src2SampleType> src2) const noexcept\r
     {\r
         jassert (numChannels == src1.numChannels && src1.numChannels == src2.numChannels);\r
         auto n = static_cast<int> (jmin (src1.numSamples, src2.numSamples, numSamples) * sizeFactor);\r
 \r
         for (size_t ch = 0; ch < numChannels; ++ch)\r
-            FloatVectorOperations::min (channelPtr (ch), src1.channelPtr (ch), src2.channelPtr (ch), n);\r
-\r
-        return *this;\r
+            FloatVectorOperations::min (getChannelPointer (ch), src1.getChannelPointer (ch), src2.getChannelPointer (ch), n);\r
     }\r
 \r
-    /** Each element of the receiver will be the maximum of the corresponding element of the source arrays. */\r
     template <typename Src1SampleType, typename Src2SampleType>\r
-    forcedinline AudioBlock& max (AudioBlock<Src1SampleType> src1, AudioBlock<Src2SampleType> src2) noexcept\r
+    void replaceWithMaxOfInternal (AudioBlock<Src1SampleType> src1, AudioBlock<Src2SampleType> src2) const noexcept\r
     {\r
         jassert (numChannels == src1.numChannels && src1.numChannels == src2.numChannels);\r
         auto n = static_cast<int> (jmin (src1.numSamples, src2.numSamples, numSamples) * sizeFactor);\r
 \r
         for (size_t ch = 0; ch < numChannels; ++ch)\r
-            FloatVectorOperations::max (channelPtr (ch), src1.channelPtr (ch), src2.channelPtr (ch), n);\r
-\r
-        return *this;\r
+            FloatVectorOperations::max (getChannelPointer (ch), src1.getChannelPointer (ch), src2.getChannelPointer (ch), n);\r
     }\r
 \r
-    /** Finds the minimum and maximum value of the buffer. */\r
-    forcedinline Range<NumericType> findMinAndMax() const noexcept\r
-    {\r
-        if (numChannels == 0)\r
-            return {};\r
-\r
-        auto n = static_cast<int> (numSamples * sizeFactor);\r
-        auto minmax = FloatVectorOperations::findMinAndMax (channelPtr (0), n);\r
-\r
-        for (size_t ch = 1; ch < numChannels; ++ch)\r
-            minmax = minmax.getUnionWith (FloatVectorOperations::findMinAndMax (channelPtr (ch), n));\r
-\r
-        return minmax;\r
-    }\r
-\r
-    //==============================================================================\r
-    // convenient operator wrappers\r
-    forcedinline AudioBlock& JUCE_VECTOR_CALLTYPE operator+= (SampleType src) noexcept   { return add (src); }\r
-    forcedinline AudioBlock&                      operator+= (AudioBlock src) noexcept   { return add (src); }\r
-    forcedinline AudioBlock& JUCE_VECTOR_CALLTYPE operator-= (SampleType src) noexcept   { return subtract (src); }\r
-    forcedinline AudioBlock&                      operator-= (AudioBlock src) noexcept   { return subtract (src); }\r
-    forcedinline AudioBlock& JUCE_VECTOR_CALLTYPE operator*= (SampleType src) noexcept   { return multiply (src); }\r
-    forcedinline AudioBlock&                      operator*= (AudioBlock src) noexcept   { return multiply (src); }\r
-    template <typename SmoothingType>\r
-    forcedinline AudioBlock&                      operator*= (SmoothedValue<SampleType, SmoothingType>& value) noexcept   { return multiply (value); }\r
-\r
-    //==============================================================================\r
-    // This class can only be used with floating point types\r
-    static_assert (std::is_same<std::remove_const_t<SampleType>, float>::value\r
-                    || std::is_same<std::remove_const_t<SampleType>, double>::value\r
-                  #if JUCE_USE_SIMD\r
-                    || std::is_same<std::remove_const_t<SampleType>, SIMDRegister<float>>::value\r
-                    || std::is_same<std::remove_const_t<SampleType>, SIMDRegister<double>>::value\r
-                  #endif\r
-                   , "AudioBlock only supports single or double precision floating point types");\r
-\r
-    //==============================================================================\r
-    /** Applies a function to each value in an input block, putting the result into an output block.\r
-        The function supplied must take a SampleType as its parameter, and return a SampleType.\r
-        The two blocks must have the same number of channels and samples.\r
-    */\r
-    template <typename Src1SampleType, typename Src2SampleType, typename FunctionType>\r
-    static void process (AudioBlock<Src1SampleType> inBlock, AudioBlock<Src2SampleType> outBlock, FunctionType&& function)\r
-    {\r
-        auto len = inBlock.getNumSamples();\r
-        auto numChans = inBlock.getNumChannels();\r
-\r
-        jassert (len == outBlock.getNumSamples());\r
-        jassert (numChans == outBlock.getNumChannels());\r
-\r
-        for (ChannelCountType c = 0; c < numChans; ++c)\r
-        {\r
-            auto* src = inBlock.getChannelPointer (c);\r
-            auto* dst = outBlock.getChannelPointer (c);\r
-\r
-            for (size_t i = 0; i < len; ++i)\r
-                dst[i] = function (src[i]);\r
-        }\r
-    }\r
-\r
-private:\r
-    //==============================================================================\r
-    NumericType*       channelPtr (size_t ch) noexcept          { return reinterpret_cast<NumericType*>       (getChannelPointer (ch)); }\r
-    const NumericType* channelPtr (size_t ch) const noexcept    { return reinterpret_cast<const NumericType*> (getChannelPointer (ch)); }\r
-\r
     //==============================================================================\r
     using ChannelCountType = unsigned int;\r
 \r
diff --git a/modules/juce_dsp/containers/juce_AudioBlock_test.cpp b/modules/juce_dsp/containers/juce_AudioBlock_test.cpp
new file mode 100644 (file)
index 0000000..f0192e8
--- /dev/null
@@ -0,0 +1,342 @@
+/*\r
+  ==============================================================================\r
+\r
+   This file is part of the JUCE library.\r
+   Copyright (c) 2017 - ROLI Ltd.\r
+\r
+   JUCE is an open source library subject to commercial or open-source\r
+   licensing.\r
+\r
+   By using JUCE, you agree to the terms of both the JUCE 5 End-User License\r
+   Agreement and JUCE 5 Privacy Policy (both updated and effective as of the\r
+   27th April 2017).\r
+\r
+   End User License Agreement: www.juce.com/juce-5-licence\r
+   Privacy Policy: www.juce.com/juce-5-privacy-policy\r
+\r
+   Or: You may also use this code under the terms of the GPL v3 (see\r
+   www.gnu.org/licenses).\r
+\r
+   JUCE IS PROVIDED "AS IS" WITHOUT ANY WARRANTY, AND ALL WARRANTIES, WHETHER\r
+   EXPRESSED OR IMPLIED, INCLUDING MERCHANTABILITY AND FITNESS FOR PURPOSE, ARE\r
+   DISCLAIMED.\r
+\r
+  ==============================================================================\r
+*/\r
+\r
+namespace juce\r
+{\r
+namespace dsp\r
+{\r
+\r
+class AudioBlockUnitTests   : public UnitTest\r
+{\r
+public:\r
+    AudioBlockUnitTests()\r
+        : UnitTest ("AudioBlock", UnitTestCategories::dsp)\r
+    {}\r
+\r
+    void runTest() override\r
+    {\r
+        beginTest ("Equality");\r
+        {\r
+            expect (block == block);\r
+            expect (block != otherBlock);\r
+        }\r
+\r
+        beginTest ("Constructors");\r
+        {\r
+            expect (block == AudioBlock<float> (data.getArrayOfWritePointers(), (size_t) data.getNumChannels(), (size_t) data.getNumSamples()));\r
+            expect (block == AudioBlock<float> (data.getArrayOfWritePointers(), (size_t) data.getNumChannels(), (size_t) 0, (size_t) data.getNumSamples()));\r
+            expect (block == AudioBlock<float> (block));\r
+\r
+            expect (block == AudioBlock<const float> (data.getArrayOfWritePointers(), (size_t) data.getNumChannels(), (size_t) data.getNumSamples()));\r
+            expect (block == AudioBlock<const float> (data.getArrayOfWritePointers(), (size_t) data.getNumChannels(), (size_t) 0, (size_t) data.getNumSamples()));\r
+            expect (block == AudioBlock<const float> (block));\r
+        }\r
+\r
+        beginTest ("Swap");\r
+        {\r
+            resetBlocks();\r
+\r
+            expect (block != otherBlock);\r
+            expectEquals (block.getSample (0, 0), 1.0f);\r
+            expectEquals (block.getSample (0, 4), 5.0f);\r
+            expectEquals (otherBlock.getSample (0, 0), -1.0f);\r
+            expectEquals (otherBlock.getSample (0, 3), -4.0f);\r
+\r
+            block.swap (otherBlock);\r
+\r
+            expect (block != otherBlock);\r
+            expectEquals (otherBlock.getSample (0, 0), 1.0f);\r
+            expectEquals (otherBlock.getSample (0, 4), 5.0f);\r
+            expectEquals (block.getSample (0, 0), -1.0f);\r
+            expectEquals (block.getSample (0, 3), -4.0f);\r
+        }\r
+\r
+        beginTest ("Getters and setters");\r
+        {\r
+            resetBlocks();\r
+\r
+            expectEquals ((int) block.getNumChannels(), data.getNumChannels());\r
+            expectEquals ((int) block.getNumSamples(),  data.getNumSamples());\r
+\r
+            expectEquals (block.getChannelPointer (0)[2], 3.0f);\r
+            block.getChannelPointer (0)[2] = 999.0f;\r
+            expectEquals (block.getChannelPointer (0)[2], 999.0f);\r
+\r
+            expectEquals (block.getSample (0, 4), 5.0f);\r
+            expectEquals (block.getSample (1, 4), 11.0f);\r
+\r
+            expectEquals (block.getSingleChannelBlock (1).getSample (0, 3), block.getSample (1, 3));\r
+\r
+            expectEquals (block.getSubsetChannelBlock (0, 2).getSample (1, 3), block.getSample (1, 3));\r
+            expectEquals (block.getSubsetChannelBlock (1, 1).getSample (0, 3), block.getSample (1, 3));\r
+\r
+            block.setSample (1, 1, 777.0f);\r
+            expectEquals (block.getSample (1, 1), 777.0f);\r
+\r
+            block.addSample (1, 1, 1.0f);\r
+            expectEquals (block.getSample (1, 1), 778.0f);\r
+        }\r
+\r
+        beginTest ("Copying");\r
+        {\r
+            block.clear();\r
+            expectEquals (block.getSample (0, 2), 0.0f);\r
+            expectEquals (block.getSample (1, 4), 0.0f);\r
+\r
+            block.fill (456.0f);\r
+            expectEquals (block.getSample (0, 2), 456.0f);\r
+            expectEquals (block.getSample (1, 4), 456.0f);\r
+\r
+            block.copyFrom (otherBlock);\r
+            expect (block != otherBlock);\r
+            expectEquals (block.getSample (0, 2), otherBlock.getSample (0, 2));\r
+            expectEquals (block.getSample (1, 4), otherBlock.getSample (1, 4));\r
+\r
+            resetBlocks();\r
+\r
+            AudioBuffer<float> otherBuffer ((int) block.getNumChannels(), (int) block.getNumSamples());\r
+            otherBlock.copyTo (otherBuffer);\r
+            expectEquals (otherBlock.getSample (0, 2), otherBuffer.getSample (0, 2));\r
+            expectEquals (otherBlock.getSample (1, 4), otherBuffer.getSample (1, 4));\r
+\r
+            block.copyFrom (otherBuffer);\r
+            expectEquals (block.getSample (0, 2), otherBlock.getSample (0, 2));\r
+            expectEquals (block.getSample (1, 4), otherBlock.getSample (1, 4));\r
+\r
+            float testSample1 = block.getSample (0, 2);\r
+            float testSample2 = block.getSample (1, 3);\r
+            expect (testSample1 != block.getSample (0, 4));\r
+            expect (testSample2 != block.getSample (1, 5));\r
+            block.move (0, 2);\r
+            expectEquals (block.getSample (0, 4), testSample1);\r
+            expectEquals (block.getSample (1, 5), testSample2);\r
+        }\r
+\r
+        beginTest ("Addition");\r
+        {\r
+            resetBlocks();\r
+\r
+            block.add (15.0f);\r
+            expectEquals (block.getSample (0, 4), 20.0f);\r
+            expectEquals (block.getSample (1, 4), 26.0f);\r
+\r
+            block.add (otherBlock);\r
+            expectEquals (block.getSample (0, 4), 15.0f);\r
+            expectEquals (block.getSample (1, 4), 15.0f);\r
+\r
+            block.replaceWithSumOf (otherBlock, 9.0f);\r
+            expectEquals (block.getSample (0, 4), 4.0f);\r
+            expectEquals (block.getSample (1, 4), -2.0f);\r
+\r
+            resetBlocks();\r
+\r
+            block.replaceWithSumOf (block, otherBlock);\r
+            expectEquals (block.getSample (0, 4), 0.0f);\r
+            expectEquals (block.getSample (1, 4), 0.0f);\r
+        }\r
+\r
+        beginTest ("Subtraction");\r
+        {\r
+            resetBlocks();\r
+\r
+            block.subtract (15.0f);\r
+            expectEquals (block.getSample (0, 4), -10.0f);\r
+            expectEquals (block.getSample (1, 4), -4.0f);\r
+\r
+            block.subtract (otherBlock);\r
+            expectEquals (block.getSample (0, 4), -5.0f);\r
+            expectEquals (block.getSample (1, 4), 7.0f);\r
+\r
+            block.replaceWithDifferenceOf (otherBlock, 9.0f);\r
+            expectEquals (block.getSample (0, 4), -14.0f);\r
+            expectEquals (block.getSample (1, 4), -20.0f);\r
+\r
+            resetBlocks();\r
+\r
+            block.replaceWithDifferenceOf (block, otherBlock);\r
+            expectEquals (block.getSample (0, 4), 10.0f);\r
+            expectEquals (block.getSample (1, 4), 22.0f);\r
+        }\r
+\r
+        beginTest ("Multiplication");\r
+        {\r
+            resetBlocks();\r
+\r
+            block.multiplyBy (10.0f);\r
+            expectEquals (block.getSample (0, 4), 50.0f);\r
+            expectEquals (block.getSample (1, 4), 110.0f);\r
+\r
+            block.multiplyBy (otherBlock);\r
+            expectEquals (block.getSample (0, 4), -250.0f);\r
+            expectEquals (block.getSample (1, 4), -1210.0f);\r
+\r
+            block.replaceWithProductOf (otherBlock, 3.0f);\r
+            expectEquals (block.getSample (0, 4), -15.0f);\r
+            expectEquals (block.getSample (1, 4), -33.0f);\r
+\r
+            resetBlocks();\r
+\r
+            block.replaceWithProductOf (block, otherBlock);\r
+            expectEquals (block.getSample (0, 4), -25.0f);\r
+            expectEquals (block.getSample (1, 4), -121.0f);\r
+        }\r
+\r
+        beginTest ("Smoothing");\r
+        {\r
+            block.fill (1.0f);\r
+            SmoothedValue<float> sv { 1.0f };\r
+            sv.reset (1, 4);\r
+            sv.setTargetValue (0.0f);\r
+\r
+            block.multiplyBy (sv);\r
+            expect (block.getSample (0, 2) < 1.0f);\r
+            expect (block.getSample (1, 2) < 1.0f);\r
+            expect (block.getSample (0, 2) > 0.0f);\r
+            expect (block.getSample (1, 2) > 0.0f);\r
+            expectEquals (block.getSample (0, 5), 0.0f);\r
+            expectEquals (block.getSample (1, 5), 0.0f);\r
+\r
+            sv.setCurrentAndTargetValue (-1.0f);\r
+            sv.setTargetValue (0.0f);\r
+            otherBlock.fill (-1.0f);\r
+            block.replaceWithProductOf (otherBlock, sv);\r
+            expect (block.getSample (0, 2) < 1.0f);\r
+            expect (block.getSample (1, 2) < 1.0f);\r
+            expect (block.getSample (0, 2) > 0.0f);\r
+            expect (block.getSample (1, 2) > 0.0f);\r
+            expectEquals (block.getSample (0, 5), 0.0f);\r
+            expectEquals (block.getSample (1, 5), 0.0f);\r
+        }\r
+\r
+        beginTest ("Multiply add");\r
+        {\r
+            resetBlocks();\r
+\r
+            block.addProductOf (otherBlock, -1.0f);\r
+            expectEquals (block.getSample (0, 4), 10.0f);\r
+            expectEquals (block.getSample (1, 4), 22.0f);\r
+\r
+            block.addProductOf (otherBlock, otherBlock);\r
+            expectEquals (block.getSample (0, 4), 35.0f);\r
+            expectEquals (block.getSample (1, 4), 143.0f);\r
+        }\r
+\r
+        beginTest ("Negative abs min max");\r
+        {\r
+            resetBlocks();\r
+            otherBlock.negate();\r
+\r
+            block.add (otherBlock);\r
+            expectEquals (block.getSample (0, 4), 10.0f);\r
+            expectEquals (block.getSample (1, 4), 22.0f);\r
+\r
+            block.replaceWithNegativeOf (otherBlock);\r
+            expectEquals (block.getSample (0, 4), -5.0f);\r
+            expectEquals (block.getSample (1, 4), -11.0f);\r
+\r
+            block.clear();\r
+            otherBlock.negate();\r
+            block.replaceWithAbsoluteValueOf (otherBlock);\r
+            expectEquals (block.getSample (0, 4), 5.0f);\r
+            expectEquals (block.getSample (1, 4), 11.0f);\r
+\r
+            resetBlocks();\r
+            block.replaceWithMinOf (block, otherBlock);\r
+            expectEquals (block.getSample (0, 4), -5.0f);\r
+            expectEquals (block.getSample (1, 4), -11.0f);\r
+\r
+            resetBlocks();\r
+            block.replaceWithMaxOf (block, otherBlock);\r
+            expectEquals (block.getSample (0, 4), 5.0f);\r
+            expectEquals (block.getSample (1, 4), 11.0f);\r
+\r
+            resetBlocks();\r
+            auto range = block.findMinAndMax();\r
+            expectEquals (range.getStart(), 1.0f);\r
+            expectEquals (range.getEnd(), 12.0f);\r
+        }\r
+\r
+        beginTest ("Operators");\r
+        {\r
+            resetBlocks();\r
+            block += 10.0f;\r
+            expectEquals (block.getSample (0, 4), 15.0f);\r
+            expectEquals (block.getSample (1, 4), 21.0f);\r
+            block += otherBlock;\r
+            expectEquals (block.getSample (0, 4), 10.0f);\r
+            expectEquals (block.getSample (1, 4), 10.0f);\r
+\r
+            resetBlocks();\r
+            block -= 10.0f;\r
+            expectEquals (block.getSample (0, 4), -5.0f);\r
+            expectEquals (block.getSample (1, 4), 1.0f);\r
+            block -= otherBlock;\r
+            expectEquals (block.getSample (0, 4), 0.0f);\r
+            expectEquals (block.getSample (1, 4), 12.0f);\r
+\r
+            resetBlocks();\r
+            block *= 10.0f;\r
+            expectEquals (block.getSample (0, 4), 50.0f);\r
+            expectEquals (block.getSample (1, 4), 110.0f);\r
+            block *= otherBlock;\r
+            expectEquals (block.getSample (0, 4), -250.0f);\r
+            expectEquals (block.getSample (1, 4), -1210.0f);\r
+        }\r
+\r
+        beginTest ("Process");\r
+        {\r
+            resetBlocks();\r
+            AudioBlock<float>::process (block, otherBlock, [](float x) { return x + 1.0f; });\r
+            expectEquals (otherBlock.getSample (0, 4), 6.0f);\r
+            expectEquals (otherBlock.getSample (1, 4), 12.0f);\r
+        }\r
+    }\r
+\r
+private:\r
+    AudioBuffer<float> data { 2, 6 }, otherData { 2, 6 };\r
+    AudioBlock<float> block { data }, otherBlock { otherData };\r
+\r
+    void resetBlocks()\r
+    {\r
+        auto value = 1.0f;\r
+\r
+        for (size_t c = 0; c < block.getNumChannels(); ++c)\r
+        {\r
+            for (size_t i = 0; i < block.getNumSamples(); ++i)\r
+            {\r
+                block.setSample ((int) c, (int) i, value);\r
+                value += 1.0f;\r
+            }\r
+        }\r
+\r
+        otherBlock.replaceWithNegativeOf (block);\r
+    }\r
+};\r
+\r
+static AudioBlockUnitTests audioBlockUnitTests;\r
+\r
+} // namespace dsp\r
+} // namespace juce\r
index f0b5ab2f76d019f317ecb8230caf98f3dd50d8f0..3288651c06b27714ad823da8d28ccc2188d34f72 100644 (file)
@@ -768,7 +768,7 @@ struct Convolution::Pimpl  : private Thread
         }\r
 \r
         if (input.getNumChannels() > 1 && currentInfo.wantsStereo == false)\r
-            output.getSingleChannelBlock (1).copy (output.getSingleChannelBlock (0));\r
+            output.getSingleChannelBlock (1).copyFrom (output.getSingleChannelBlock (0));\r
     }\r
 \r
     //==============================================================================\r
@@ -1212,7 +1212,7 @@ void Convolution::processSamples (const AudioBlock<const float>& input, AudioBlo
 \r
     if (volumeDry[0].isSmoothing())\r
     {\r
-        dry.copy (input);\r
+        dry.copyFrom (input);\r
 \r
         for (size_t channel = 0; channel < numChannels; ++channel)\r
             volumeDry[channel].applyGain (dry.getChannelPointer (channel), (int) numSamples);\r
index 56748f14500194b283c7cd13f666505576d0d14e..0d61a417e0f09df2827e935c9b4370a7671fd205 100644 (file)
@@ -89,6 +89,7 @@
   #include "containers/juce_SIMDRegister_test.cpp"\r
  #endif\r
 \r
+ #include "containers/juce_AudioBlock_test.cpp"\r
  #include "frequency/juce_FFT_test.cpp"\r
  #include "processors/juce_FIRFilter_test.cpp"\r
 #endif\r
index 2f446d1dee19c9d7793d4801a594ece4ce7c5a6a..68abb03ea588f9fa6f8cc11cb2747195a51faf19 100644 (file)
@@ -36,7 +36,7 @@
 \r
   ID:                 juce_dsp\r
   vendor:             juce\r
-  version:            5.4.4\r
+  version:            5.4.5\r
   name:               JUCE DSP classes\r
   description:        Classes for audio buffer manipulation, digital audio processing, filtering, oversampling, fast math functions etc.\r
   website:            http://www.juce.com/juce\r
index 4348cdb3e1838fe235da47205d1fd01496250000..a279f61793e968a179be52b46b0c25164c3c1fd1 100644 (file)
@@ -114,7 +114,7 @@ public:
             bias.skip (static_cast<int> (len));\r
 \r
             if (context.usesSeparateInputAndOutputBlocks())\r
-                outBlock.copy (inBlock);\r
+                outBlock.copyFrom (inBlock);\r
 \r
             return;\r
         }\r
index 3c542b571afaa9320d71fa2ca8987bf9193c3642..21a3391ddca6308fcf693f6af01a0b7dcc015595 100644 (file)
@@ -110,7 +110,7 @@ public:
             gain.skip (static_cast<int> (len));\r
 \r
             if (context.usesSeparateInputAndOutputBlocks())\r
-                outBlock.copy (inBlock);\r
+                outBlock.copyFrom (inBlock);\r
 \r
             return;\r
         }\r
index 8b38aaf7843a64cd163ebaa5cd69a02745b96ab1..f3f302d47d0645851627adedf7b2d3f6ebac398a 100644 (file)
@@ -92,7 +92,7 @@ public:
 \r
         if (! enabled || context.isBypassed)\r
         {\r
-            outputBlock.copy (inputBlock);\r
+            outputBlock.copyFrom (inputBlock);\r
             return;\r
         }\r
 \r
index 109047b55c310096a17e39b748c2ee0f9fbf8abf..a7b1c8f66b22c5dc4b8ca7347d120a4a48a22353 100644 (file)
@@ -38,7 +38,7 @@ struct Oversampling<SampleType>::OversamplingStage
     OversamplingStage (size_t numChans, size_t newFactor)  : numChannels (numChans), factor (newFactor) {}\r
     virtual ~OversamplingStage() {}\r
 \r
-    //===============================================================================\r
+    //==============================================================================\r
     virtual SampleType getLatencyInSamples() = 0;\r
 \r
     virtual void initProcessing (size_t maximumNumberOfSamplesBeforeOversampling)\r
@@ -66,7 +66,7 @@ struct Oversampling<SampleType>::OversamplingStage
 };\r
 \r
 \r
-//===============================================================================\r
+//==============================================================================\r
 /** Dummy oversampling stage class which simply copies and pastes the input\r
     signal, which could be equivalent to a "one time" oversampling processing.\r
 */\r
@@ -77,7 +77,7 @@ struct OversamplingDummy   : public Oversampling<SampleType>::OversamplingStage
 \r
     OversamplingDummy (size_t numChans) : ParentType (numChans, 1) {}\r
 \r
-    //===============================================================================\r
+    //==============================================================================\r
     SampleType getLatencyInSamples() override\r
     {\r
         return 0;\r
@@ -98,13 +98,13 @@ struct OversamplingDummy   : public Oversampling<SampleType>::OversamplingStage
         jassert (outputBlock.getNumChannels() <= static_cast<size_t> (ParentType::buffer.getNumChannels()));\r
         jassert (outputBlock.getNumSamples() * ParentType::factor <= static_cast<size_t> (ParentType::buffer.getNumSamples()));\r
 \r
-        outputBlock.copy (ParentType::getProcessedSamples (outputBlock.getNumSamples()));\r
+        outputBlock.copyFrom (ParentType::getProcessedSamples (outputBlock.getNumSamples()));\r
     }\r
 \r
     JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR (OversamplingDummy)\r
 };\r
 \r
-//===============================================================================\r
+//==============================================================================\r
 /** Oversampling stage class performing 2 times oversampling using the Filter\r
     Design FIR Equiripple method. The resulting filter is linear phase,\r
     symmetric, and has every two samples but the middle one equal to zero,\r
@@ -138,7 +138,7 @@ struct Oversampling2TimesEquirippleFIR  : public Oversampling<SampleType>::Overs
         position.resize (static_cast<int> (this->numChannels));\r
     }\r
 \r
-    //===============================================================================\r
+    //==============================================================================\r
     SampleType getLatencyInSamples() override\r
     {\r
         return static_cast<SampleType> (coefficientsUp.getFilterOrder() + coefficientsDown.getFilterOrder()) * 0.5f;\r
@@ -247,17 +247,17 @@ struct Oversampling2TimesEquirippleFIR  : public Oversampling<SampleType>::Overs
     }\r
 \r
 private:\r
-    //===============================================================================\r
+    //==============================================================================\r
     dsp::FIR::Coefficients<SampleType> coefficientsUp, coefficientsDown;\r
     AudioBuffer<SampleType> stateUp, stateDown, stateDown2;\r
     Array<size_t> position;\r
 \r
-    //===============================================================================\r
+    //==============================================================================\r
     JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR (Oversampling2TimesEquirippleFIR)\r
 };\r
 \r
 \r
-//===============================================================================\r
+//==============================================================================\r
 /** Oversampling stage class performing 2 times oversampling using the Filter\r
     Design IIR Polyphase Allpass Cascaded method. The resulting filter is minimum\r
     phase, and provided with a method to get the exact resulting latency.\r
@@ -299,7 +299,7 @@ struct Oversampling2TimesPolyphaseIIR  : public Oversampling<SampleType>::Oversa
         delayDown.resize (static_cast<int> (this->numChannels));\r
     }\r
 \r
-    //===============================================================================\r
+    //==============================================================================\r
     SampleType getLatencyInSamples() override\r
     {\r
         return latency;\r
@@ -453,7 +453,7 @@ struct Oversampling2TimesPolyphaseIIR  : public Oversampling<SampleType>::Oversa
     }\r
 \r
 private:\r
-    //===============================================================================\r
+    //==============================================================================\r
     /** This function calculates the equivalent high order IIR filter of a given\r
         polyphase cascaded allpass filters structure.\r
     */\r
@@ -515,19 +515,19 @@ private:
         return coeffs;\r
     }\r
 \r
-    //===============================================================================\r
+    //==============================================================================\r
     Array<SampleType> coefficientsUp, coefficientsDown;\r
     SampleType latency;\r
 \r
     AudioBuffer<SampleType> v1Up, v1Down;\r
     Array<SampleType> delayDown;\r
 \r
-    //===============================================================================\r
+    //==============================================================================\r
     JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR (Oversampling2TimesPolyphaseIIR)\r
 };\r
 \r
 \r
-//===============================================================================\r
+//==============================================================================\r
 template <typename SampleType>\r
 Oversampling<SampleType>::Oversampling (size_t newNumChannels)\r
     : numChannels (newNumChannels)\r
@@ -590,7 +590,7 @@ Oversampling<SampleType>::~Oversampling()
     stages.clear();\r
 }\r
 \r
-//===============================================================================\r
+//==============================================================================\r
 template <typename SampleType>\r
 void Oversampling<SampleType>::addDummyOversamplingStage()\r
 {\r
@@ -627,7 +627,7 @@ void Oversampling<SampleType>::clearOversamplingStages()
     factorOversampling = 1u;\r
 }\r
 \r
-//===============================================================================\r
+//==============================================================================\r
 template <typename SampleType>\r
 SampleType Oversampling<SampleType>::getLatencyInSamples() noexcept\r
 {\r
@@ -649,7 +649,7 @@ size_t Oversampling<SampleType>::getOversamplingFactor() noexcept
     return factorOversampling;\r
 }\r
 \r
-//===============================================================================\r
+//==============================================================================\r
 template <typename SampleType>\r
 void Oversampling<SampleType>::initProcessing (size_t maximumNumberOfSamplesBeforeOversampling)\r
 {\r
index 7c428180dff6c3e03911603bdf2403a4757ce403..e4fbb9db09a42779b8b85f087f24e20dbfa2269b 100644 (file)
@@ -29,7 +29,7 @@ namespace juce
 namespace dsp\r
 {\r
 \r
-//===============================================================================\r
+//==============================================================================\r
 /**\r
     A processing class performing multi-channel oversampling.\r
 \r
@@ -65,7 +65,7 @@ public:
         numFilterTypes\r
     };\r
 \r
-    //===============================================================================\r
+    //==============================================================================\r
     /**\r
         Constructor of the oversampling class. All the processing parameters must be\r
         provided at the creation of the oversampling object.\r
@@ -96,7 +96,7 @@ public:
     /** Destructor. */\r
     ~Oversampling();\r
 \r
-    //===============================================================================\r
+    //==============================================================================\r
     /** Returns the latency in samples of the whole processing. Use this information\r
         in your main processor to compensate the additional latency involved with\r
         the oversampling, for example with a dry / wet functionality, and to report\r
@@ -110,7 +110,7 @@ public:
     /** Returns the current oversampling factor. */\r
     size_t getOversamplingFactor() noexcept;\r
 \r
-    //===============================================================================\r
+    //==============================================================================\r
     /** Must be called before any processing, to set the buffer sizes of the internal\r
         buffers of the oversampling processing.\r
     */\r
@@ -135,7 +135,7 @@ public:
     */\r
     void processSamplesDown (dsp::AudioBlock<SampleType>& outputBlock) noexcept;\r
 \r
-    //===============================================================================\r
+    //==============================================================================\r
     /** Adds a new oversampling stage to the Oversampling class, multiplying the\r
         current oversampling factor by two. This is used with the default constructor\r
         to create custom oversampling chains, requiring a call to the\r
@@ -179,7 +179,7 @@ public:
     */\r
     void clearOversamplingStages();\r
 \r
-    //===============================================================================\r
+    //==============================================================================\r
     size_t factorOversampling = 1;\r
     size_t numChannels = 1;\r
 \r
@@ -188,11 +188,11 @@ public:
    #endif\r
 \r
 private:\r
-    //===============================================================================\r
+    //==============================================================================\r
     OwnedArray<OversamplingStage> stages;\r
     bool isReady = false;\r
 \r
-    //===============================================================================\r
+    //==============================================================================\r
     JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR (Oversampling)\r
 };\r
 \r
index a2ff3953432ef28f35e3d593c352793a98dfb146..3e75a55b8c0d9d6bee35970c36560585d13791d4 100644 (file)
@@ -85,7 +85,7 @@ public:
 \r
         jassert (inputBlock.getNumSamples() == numSamples);\r
 \r
-        outputBlock.copy (inputBlock);\r
+        outputBlock.copyFrom (inputBlock);\r
 \r
         if (! enabled || context.isBypassed)\r
             return;\r
index f93151d1a3806c3ccfa093749c03c136c7ce6dfc..8a2c624a771ee5e0125fe127a365b3399f3ed415 100644 (file)
@@ -58,7 +58,7 @@ struct WaveShaper
         if (context.isBypassed)\r
         {\r
             if (context.usesSeparateInputAndOutputBlocks())\r
-                context.getOutputBlock().copy (context.getInputBlock());\r
+                context.getOutputBlock().copyFrom (context.getInputBlock());\r
         }\r
         else\r
         {\r
index 92fecfeea58fb93b1f656f3dc5543d08e4de8977..078c50dca9f6350e7ac524601caff9dd1d9ead13 100644 (file)
@@ -31,7 +31,7 @@
 \r
   ID:               juce_events\r
   vendor:           juce\r
-  version:          5.4.4\r
+  version:          5.4.5\r
   name:             JUCE message and event handling classes\r
   description:      Classes for running an application's main event loop and sending/receiving messages, timers, etc.\r
   website:          http://www.juce.com/juce\r
index a5f0260c4fb8355fa4f9b944467570f4de362efe..1b286ca68da34737d75d40ab82cafe534d0f1d34 100644 (file)
@@ -206,10 +206,17 @@ public:
     virtual void memoryWarningReceived()     { jassertfalse; }\r
 \r
     //==============================================================================\r
-    /** Override this method to be informed when the back button is pressed on a device.\r
+    /** This will be called when the back button on a device is pressed. The return value\r
+        should be used to indicate whether the back button event has been handled by\r
+        the application, for example if you want to implement custom navigation instead\r
+        of the standard behaviour on Android.\r
+\r
         This is currently only implemented on Android devices.\r
+\r
+        @returns  true if the event has been handled, or false if the default OS\r
+                  behaviour should happen\r
      */\r
-    virtual void backButtonPressed() {}\r
+    virtual bool backButtonPressed() { return false; }\r
 \r
     //==============================================================================\r
     /** Signals that the main message loop should stop and the application should terminate.\r
index 8904f3844e494944695c680da2a38fb7f454e471..726554a9e5b6315739b2e6684ae6402862437556 100644 (file)
@@ -184,16 +184,16 @@ void* MessageManager::callFunctionOnMessageThread (MessageCallbackFunction* func
     return nullptr;\r
 }\r
 \r
-void MessageManager::callAsync (std::function<void()> fn)\r
+bool MessageManager::callAsync (std::function<void()> fn)\r
 {\r
     struct AsyncCallInvoker  : public MessageBase\r
     {\r
-        AsyncCallInvoker (std::function<void()> f) : callback (std::move (f)) { post(); }\r
+        AsyncCallInvoker (std::function<void()> f) : callback (std::move (f)) {}\r
         void messageCallback() override  { callback(); }\r
         std::function<void()> callback;\r
     };\r
 \r
-    new AsyncCallInvoker (std::move (fn));\r
+    return (new AsyncCallInvoker (std::move (fn)))->post();\r
 }\r
 \r
 //==============================================================================\r
index b90513212a947f4576805fbd0209bbd0d77dbcda..fd5e1013cd21efb4b216904d473b980b1beaf036 100644 (file)
@@ -94,8 +94,12 @@ public:
    #endif\r
 \r
     //==============================================================================\r
-    /** Asynchronously invokes a function or C++11 lambda on the message thread. */\r
-    static void callAsync (std::function<void()> functionToCall);\r
+    /** Asynchronously invokes a function or C++11 lambda on the message thread.\r
+\r
+        @returns  true if the message was successfully posted to the message queue,\r
+                  or false otherwise.\r
+    */\r
+    static bool callAsync (std::function<void()> functionToCall);\r
 \r
     /** Calls a function using the message-thread.\r
 \r
index cb7aded887521f1e3c832ffd64f9cd0dc53803d9..4aac0967de3892eb6da939fe5a0227cb8965308e 100644 (file)
@@ -34,8 +34,11 @@ namespace LinuxEventLoop
         @param fd            the file descriptor to be monitored\r
         @param readCallback  a callback that will be called when the file descriptor has\r
                              data to read. The file descriptor will be passed as an argument\r
+        @param eventMask     a bit mask specifying the events you are interested in for the\r
+                             file descriptor. The possible values for this are defined in\r
+                             <poll.h>\r
     */\r
-    void registerFdCallback (int fd, std::function<void(int)> readCallback);\r
+    void registerFdCallback (int fd, std::function<void(int)> readCallback, short eventMask = 1 /*POLLIN*/);\r
 \r
     /** Unregisters a previously registered file descriptor.\r
 \r
index 9f20e95b45ae2d3a61f9b1244cd2d421e4c0833d..7287d6c4b61519e5b1b78407bbc1f49f79f7cfbc 100644 (file)
@@ -20,8 +20,6 @@
   ==============================================================================\r
 */\r
 \r
-#include <poll.h>\r
-\r
 namespace juce\r
 {\r
 \r
@@ -38,7 +36,7 @@ public:
         LinuxEventLoop::registerFdCallback (getReadHandle(),\r
                                             [this] (int fd)\r
                                             {\r
-                                                if (auto msg = popNextMessage (fd))\r
+                                                while (auto msg = popNextMessage (fd))\r
                                                 {\r
                                                     JUCE_TRY\r
                                                     {\r
@@ -77,7 +75,7 @@ public:
     }\r
 \r
     //==============================================================================\r
-    JUCE_DECLARE_SINGLETON_SINGLETHREADED_MINIMAL (InternalMessageQueue)\r
+    JUCE_DECLARE_SINGLETON (InternalMessageQueue, false)\r
 \r
 private:\r
     CriticalSection lock;\r
@@ -119,12 +117,12 @@ public:
         fdReadCallbacks.reserve (8);\r
     }\r
 \r
-    void registerFdCallback (int fd, std::function<void(int)>&& cb)\r
+    void registerFdCallback (int fd, std::function<void(int)>&& cb, short eventMask)\r
     {\r
         const ScopedLock sl (lock);\r
 \r
         fdReadCallbacks.push_back ({ fd, std::move (cb) });\r
-        pfds.push_back ({ fd, POLLIN, 0 });\r
+        pfds.push_back ({ fd, eventMask, 0 });\r
     }\r
 \r
     void unregisterFdCallback (int fd)\r
@@ -183,7 +181,7 @@ public:
     }\r
 \r
     //==============================================================================\r
-    JUCE_DECLARE_SINGLETON_SINGLETHREADED_MINIMAL (InternalRunLoop)\r
+    JUCE_DECLARE_SINGLETON (InternalRunLoop, false)\r
 \r
 private:\r
     CriticalSection lock;\r
@@ -273,10 +271,10 @@ bool MessageManager::dispatchNextMessageOnSystemQueue (bool returnIfNoPendingMes
 }\r
 \r
 //==============================================================================\r
-void LinuxEventLoop::registerFdCallback (int fd, std::function<void(int)> readCallback)\r
+void LinuxEventLoop::registerFdCallback (int fd, std::function<void(int)> readCallback, short eventMask)\r
 {\r
     if (auto* runLoop = InternalRunLoop::getInstanceWithoutCreating())\r
-        runLoop->registerFdCallback (fd, std::move (readCallback));\r
+        runLoop->registerFdCallback (fd, std::move (readCallback), eventMask);\r
 }\r
 \r
 void LinuxEventLoop::unregisterFdCallback (int fd)\r
index 5b503f0a5815ac466aa2dc41eddd5adb5fa231d9..95b5f2576e17dfd27481cf422da9ebf845c2d186 100644 (file)
@@ -195,7 +195,7 @@ public:
     /** Tries to draw a text string inside a given space.\r
 \r
         This does its best to make the given text readable within the specified rectangle,\r
-        so it useful for labelling things.\r
+        so it's useful for labelling things.\r
 \r
         If the text is too big, it'll be squashed horizontally or broken over multiple lines\r
         if the maximumLinesToUse value allows this. If the text just won't fit into the space,\r
@@ -220,7 +220,7 @@ public:
     /** Tries to draw a text string inside a given space.\r
 \r
         This does its best to make the given text readable within the specified rectangle,\r
-        so it useful for labelling things.\r
+        so it's useful for labelling things.\r
 \r
         If the text is too big, it'll be squashed horizontally or broken over multiple lines\r
         if the maximumLinesToUse value allows this. If the text just won't fit into the space,\r
index 8e29d40de2560feb92f4ccc23936131ac4530f2f..7aa7e807bbb9fb719e5ad829879b3f8708c9b61e 100644 (file)
@@ -202,7 +202,7 @@ public:
     /** Tries to fit some text within a given space.\r
 \r
         This does its best to make the given text readable within the specified rectangle,\r
-        so it useful for labelling things.\r
+        so it's useful for labelling things.\r
 \r
         If the text is too big, it'll be squashed horizontally or broken over multiple lines\r
         if the maximumLinesToUse value allows this. If the text just won't fit into the space,\r
index 1591490bc10dfff1aeda92bf4c5cc6b345e03754..8b2444cf6f5b0b2ee8d2646d02627f8de8151b78 100644 (file)
@@ -617,66 +617,4 @@ void TextLayout::recalculateSize()
     }\r
 }\r
 \r
-//==============================================================================\r
-#if JUCE_UNIT_TESTS\r
-\r
-struct TextLayoutTests  : public UnitTest\r
-{\r
-    TextLayoutTests()\r
-        : UnitTest ("Text Layout", UnitTestCategories::text)\r
-    {}\r
-\r
-    static TextLayout createLayout (StringRef text, float width)\r
-    {\r
-        Font fontToUse (12.0f);\r
-\r
-        AttributedString string (text);\r
-        string.setFont (std::move (fontToUse));\r
-\r
-        TextLayout layout;\r
-        layout.createLayout (std::move (string), width);\r
-\r
-        return layout;\r
-    }\r
-\r
-    void testLineBreaks (const String& line, float width, const StringArray& expected)\r
-    {\r
-        const auto layout = createLayout (line, width);\r
-\r
-        beginTest ("A line is split into expected pieces");\r
-        {\r
-            expectEquals (layout.getNumLines(), expected.size());\r
-\r
-            const auto limit = jmin (layout.getNumLines(), expected.size());\r
-\r
-            for (int i = 0; i != limit; ++i)\r
-                expectEquals (substring (line, layout.getLine (i).stringRange), expected[i]);\r
-        }\r
-    }\r
-\r
-    void runTest() override\r
-    {\r
-        const String shortLine ("hello world");\r
-        testLineBreaks (shortLine, 1.0e7f, { shortLine });\r
-\r
-        testLineBreaks ("this line should be split",\r
-                        60.0f,\r
-                        { "this line ",\r
-                          "should be ",\r
-                          "split" });\r
-\r
-        testLineBreaks ("these\nlines \nhave\n weird  \n spacing  ",\r
-                        80.0f,\r
-                        { "these\n",\r
-                          "lines \n",\r
-                          "have\n",\r
-                          " weird  \n",\r
-                          " spacing  " });\r
-    }\r
-};\r
-\r
-static TextLayoutTests textLayoutTests;\r
-\r
-#endif\r
-\r
 } // namespace juce\r
index f6e0b993d5458901e654b3e66cf8015604522590..81bd2f5eeaa6d4f77e9edcebd7b52283b6db3f22 100644 (file)
@@ -386,7 +386,7 @@ public:
         destRegion.clear();\r
 \r
         if (! rect.isEmpty())\r
-            for (auto& r : rects)\r
+            for (auto r : rects)\r
                 if (rect.intersectRectangle (r))\r
                     destRegion.rects.add (r);\r
 \r
index 5e3b6700e58d4dd5892256c90c7e4e44b5c0d5c1..10d2c36046b384eaf9681071f68122dfbe9ce06e 100644 (file)
@@ -326,13 +326,13 @@ public:
             The coordinate you provide here isn't checked, so it's the caller's responsibility to make\r
             sure it's not out-of-range.\r
         */\r
-        inline uint8* getLinePointer (int y) const noexcept                 { return data + y * lineStride; }\r
+        inline uint8* getLinePointer (int y) const noexcept                 { return data + (size_t) y * (size_t) lineStride; }\r
 \r
         /** Returns a pointer to a pixel in the image.\r
             The coordinates you give here are not checked, so it's the caller's responsibility to make sure they're\r
             not out-of-range.\r
         */\r
-        inline uint8* getPixelPointer (int x, int y) const noexcept         { return data + y * lineStride + x * pixelStride; }\r
+        inline uint8* getPixelPointer (int x, int y) const noexcept         { return data + (size_t) y * (size_t) lineStride + (size_t) x * (size_t) pixelStride; }\r
 \r
         /** Returns the colour of a given pixel.\r
             For performance reasons, this won't do any bounds-checking on the coordinates, so it's the caller's\r
index 1617a6df9f84519df4ebccc6c47a34addf75cf54..87d08424f9521bd01cec0f81747d353d57caf5ce 100644 (file)
@@ -35,7 +35,7 @@
 \r
   ID:               juce_graphics\r
   vendor:           juce\r
-  version:          5.4.4\r
+  version:          5.4.5\r
   name:             JUCE graphics classes\r
   description:      Classes for 2D vector graphics, image loading/saving, font handling, etc.\r
   website:          http://www.juce.com/juce\r
index 16ca13e6fbbc6fa078e0b7369503c7fc99550dbf..f34002a69d2ea20a506db8ac3e3c0dcca3ddd1f0 100644 (file)
@@ -629,8 +629,8 @@ void CoreGraphicsContext::setFont (const Font& newFont)
 \r
             auto cgTransformToJuceTransform = [](CGAffineTransform& t) -> AffineTransform\r
             {\r
-                return { (float) t.a, (float) t.b, (float) t.tx,\r
-                         (float) t.c, (float) t.d, (float) t.ty };\r
+                return { (float) t.a, (float) t.c, (float) t.tx,\r
+                         (float) t.b, (float) t.d, (float) t.ty };\r
             };\r
 \r
             state->fontTransform = cgTransformToJuceTransform (fontTransform);\r
@@ -649,7 +649,7 @@ void CoreGraphicsContext::drawGlyph (int glyphNumber, const AffineTransform& tra
 {\r
     if (state->fontRef != nullptr && state->fillType.isColour())\r
     {\r
-        if (transform.isOnlyTranslation())\r
+        if (transform.isOnlyTranslation() && state->fontTransform.isOnlyTranslation())\r
         {\r
             auto t = transform.followedBy (state->inverseFontTransform);\r
 \r
index 74bbfa497c91fc913a40314c012941db089925e7..6ae7035d04167a26f8fb7deacc46e6644245d601 100644 (file)
@@ -41,7 +41,7 @@ namespace CoreTextTypeLayout
         if (! availableStyles.contains (style))\r
         {\r
             if (font.isItalic())  // Fake-up an italic font if there isn't a real one.\r
-                requiredTransform = CGAffineTransformMake (1.0f, 0, 0.25f, 1.0f, 0, 0);\r
+                requiredTransform = CGAffineTransformMake (1.0f, 0, 0.1f, 1.0f, 0, 0);\r
 \r
             return availableStyles[0];\r
         }\r
index 2e6a9dcdc6752aa8cf8148bf2f70a4bcc7e16f1a..e6c0b74afd0f4251d52b3b3b39c993c5db6758ad 100644 (file)
@@ -35,7 +35,7 @@
 \r
   ID:               juce_gui_basics\r
   vendor:           juce\r
-  version:          5.4.4\r
+  version:          5.4.5\r
   name:             JUCE GUI core classes\r
   description:      Basic user-interface components and related classes.\r
   website:          http://www.juce.com/juce\r
index b357411123be0c8c5ab366faeac9d3d8ce6a4c22..e239e80cf9098490f5f938a57206ff05bb6178e5 100644 (file)
@@ -29,13 +29,13 @@ namespace juce
 \r
 struct Grid::SizeCalculation\r
 {\r
-    static float getTotalAbsoluteSize (const juce::Array<Grid::TrackInfo>& tracks, Px gapSize) noexcept\r
+    static float getTotalAbsoluteSize (const Array<Grid::TrackInfo>& tracks, Px gapSize) noexcept\r
     {\r
         float totalCellSize = 0.0f;\r
 \r
         for (const auto& trackInfo : tracks)\r
-            if (! trackInfo.isFraction || trackInfo.hasKeyword)\r
-                totalCellSize += trackInfo.size;\r
+            if (! trackInfo.isFractional() || trackInfo.isAuto())\r
+                totalCellSize += trackInfo.getSize();\r
 \r
         float totalGap = tracks.size() > 1 ? static_cast<float> ((tracks.size() - 1) * gapSize.pixels)\r
                                            : 0.0f;\r
@@ -43,45 +43,45 @@ struct Grid::SizeCalculation
         return totalCellSize + totalGap;\r
     }\r
 \r
-    static float getRelativeUnitSize (float size, float totalAbsolute, const juce::Array<Grid::TrackInfo>& tracks) noexcept\r
+    static float getRelativeUnitSize (float size, float totalAbsolute, const Array<Grid::TrackInfo>& tracks) noexcept\r
     {\r
-        const float totalRelative = juce::jlimit (0.0f, size, size - totalAbsolute);\r
+        const float totalRelative = jlimit (0.0f, size, size - totalAbsolute);\r
         float factorsSum = 0.0f;\r
 \r
         for (const auto& trackInfo : tracks)\r
-            if (trackInfo.isFraction)\r
-                factorsSum += trackInfo.size;\r
+            if (trackInfo.isFractional())\r
+                factorsSum += trackInfo.getSize();\r
 \r
         jassert (factorsSum != 0.0f);\r
         return totalRelative / factorsSum;\r
     }\r
 \r
     //==============================================================================\r
-    static float getTotalAbsoluteHeight (const juce::Array<Grid::TrackInfo>& rowTracks, Px rowGap)\r
+    static float getTotalAbsoluteHeight (const Array<Grid::TrackInfo>& rowTracks, Px rowGap)\r
     {\r
         return getTotalAbsoluteSize (rowTracks, rowGap);\r
     }\r
 \r
-    static float getTotalAbsoluteWidth (const juce::Array<Grid::TrackInfo>& columnTracks, Px columnGap)\r
+    static float getTotalAbsoluteWidth (const Array<Grid::TrackInfo>& columnTracks, Px columnGap)\r
     {\r
         return getTotalAbsoluteSize (columnTracks, columnGap);\r
     }\r
 \r
-    static float getRelativeWidthUnit (float gridWidth, Px columnGap, const juce::Array<Grid::TrackInfo>& columnTracks)\r
+    static float getRelativeWidthUnit (float gridWidth, Px columnGap, const Array<Grid::TrackInfo>& columnTracks)\r
     {\r
         return getRelativeUnitSize (gridWidth, getTotalAbsoluteWidth (columnTracks, columnGap), columnTracks);\r
     }\r
 \r
-    static float getRelativeHeightUnit (float gridHeight, Px rowGap, const juce::Array<Grid::TrackInfo>& rowTracks)\r
+    static float getRelativeHeightUnit (float gridHeight, Px rowGap, const Array<Grid::TrackInfo>& rowTracks)\r
     {\r
         return getRelativeUnitSize (gridHeight, getTotalAbsoluteHeight (rowTracks, rowGap), rowTracks);\r
     }\r
 \r
     //==============================================================================\r
-    static bool hasAnyFractions (const juce::Array<Grid::TrackInfo>& tracks)\r
+    static bool hasAnyFractions (const Array<Grid::TrackInfo>& tracks)\r
     {\r
         for (auto& t : tracks)\r
-            if (t.isFraction)\r
+            if (t.isFractional())\r
                 return true;\r
 \r
         return false;\r
@@ -89,8 +89,8 @@ struct Grid::SizeCalculation
 \r
     void computeSizes (float gridWidth, float gridHeight,\r
                        Px columnGapToUse, Px rowGapToUse,\r
-                       const juce::Array<Grid::TrackInfo>& columnTracks,\r
-                       const juce::Array<Grid::TrackInfo>& rowTracks)\r
+                       const Array<Grid::TrackInfo>& columnTracks,\r
+                       const Array<Grid::TrackInfo>& rowTracks)\r
     {\r
         if (hasAnyFractions (columnTracks))\r
             relativeWidthUnit = getRelativeWidthUnit (gridWidth, columnGapToUse, columnTracks);\r
@@ -118,19 +118,19 @@ struct Grid::PlacementHelpers
     //==============================================================================\r
     struct LineRange { int start, end; };\r
     struct LineArea  { LineRange column, row; };\r
-    struct LineInfo  { juce::StringArray lineNames; };\r
+    struct LineInfo  { StringArray lineNames; };\r
 \r
     struct NamedArea\r
     {\r
-        juce::String name;\r
+        String name;\r
         LineArea lines;\r
     };\r
 \r
     //==============================================================================\r
-    static juce::Array<LineInfo> getArrayOfLinesFromTracks (const juce::Array<Grid::TrackInfo>& tracks)\r
+    static Array<LineInfo> getArrayOfLinesFromTracks (const Array<Grid::TrackInfo>& tracks)\r
     {\r
         // fill line info array\r
-        juce::Array<LineInfo> lines;\r
+        Array<LineInfo> lines;\r
 \r
         for (int i = 1; i <= tracks.size(); ++i)\r
         {\r
@@ -139,7 +139,7 @@ struct Grid::PlacementHelpers
             if (i == 1) // start line\r
             {\r
                 LineInfo li;\r
-                li.lineNames.add (currentTrack.startLineName);\r
+                li.lineNames.add (currentTrack.getStartLineName());\r
                 lines.add (li);\r
             }\r
 \r
@@ -148,8 +148,8 @@ struct Grid::PlacementHelpers
                 const auto& prevTrack = tracks.getReference (i - 2);\r
 \r
                 LineInfo li;\r
-                li.lineNames.add (prevTrack.endLineName);\r
-                li.lineNames.add (currentTrack.startLineName);\r
+                li.lineNames.add (prevTrack.getEndLineName());\r
+                li.lineNames.add (currentTrack.getStartLineName());\r
 \r
                 lines.add (li);\r
             }\r
@@ -157,7 +157,7 @@ struct Grid::PlacementHelpers
             if (i == tracks.size()) // end line\r
             {\r
                 LineInfo li;\r
-                li.lineNames.add (currentTrack.endLineName);\r
+                li.lineNames.add (currentTrack.getEndLineName());\r
                 lines.add (li);\r
             }\r
         }\r
@@ -169,7 +169,7 @@ struct Grid::PlacementHelpers
 \r
     //==============================================================================\r
     static int deduceAbsoluteLineNumberFromLineName (GridItem::Property prop,\r
-                                                     const juce::Array<Grid::TrackInfo>& tracks)\r
+                                                     const Array<Grid::TrackInfo>& tracks)\r
     {\r
         jassert (prop.hasAbsolute());\r
 \r
@@ -180,14 +180,14 @@ struct Grid::PlacementHelpers
         {\r
             for (const auto& name : lines.getReference (i).lineNames)\r
             {\r
-                if (prop.name == name)\r
+                if (prop.getName() == name)\r
                 {\r
                     ++count;\r
                     break;\r
                 }\r
             }\r
 \r
-            if (count == prop.number)\r
+            if (count == prop.getNumber())\r
                 return i + 1;\r
         }\r
 \r
@@ -196,19 +196,19 @@ struct Grid::PlacementHelpers
     }\r
 \r
     static int deduceAbsoluteLineNumber (GridItem::Property prop,\r
-                                         const juce::Array<Grid::TrackInfo>& tracks)\r
+                                         const Array<Grid::TrackInfo>& tracks)\r
     {\r
         jassert (prop.hasAbsolute());\r
 \r
         if (prop.hasName())\r
             return deduceAbsoluteLineNumberFromLineName (prop, tracks);\r
 \r
-        return prop.number > 0 ? prop.number : tracks.size() + 2 + prop.number;\r
+        return prop.getNumber() > 0 ? prop.getNumber() : tracks.size() + 2 + prop.getNumber();\r
     }\r
 \r
     static int deduceAbsoluteLineNumberFromNamedSpan (int startLineNumber,\r
                                                       GridItem::Property propertyWithSpan,\r
-                                                      const juce::Array<Grid::TrackInfo>& tracks)\r
+                                                      const Array<Grid::TrackInfo>& tracks)\r
     {\r
         jassert (propertyWithSpan.hasSpan());\r
 \r
@@ -219,14 +219,14 @@ struct Grid::PlacementHelpers
         {\r
             for (const auto& name : lines.getReference (i).lineNames)\r
             {\r
-                if (propertyWithSpan.name == name)\r
+                if (propertyWithSpan.getName() == name)\r
                 {\r
                     ++count;\r
                     break;\r
                 }\r
             }\r
 \r
-            if (count == propertyWithSpan.number)\r
+            if (count == propertyWithSpan.getNumber())\r
                 return i + 1;\r
         }\r
 \r
@@ -236,18 +236,18 @@ struct Grid::PlacementHelpers
 \r
     static int deduceAbsoluteLineNumberBasedOnSpan (int startLineNumber,\r
                                                     GridItem::Property propertyWithSpan,\r
-                                                    const juce::Array<Grid::TrackInfo>& tracks)\r
+                                                    const Array<Grid::TrackInfo>& tracks)\r
     {\r
         jassert (propertyWithSpan.hasSpan());\r
 \r
         if (propertyWithSpan.hasName())\r
             return deduceAbsoluteLineNumberFromNamedSpan (startLineNumber, propertyWithSpan, tracks);\r
 \r
-        return startLineNumber + propertyWithSpan.number;\r
+        return startLineNumber + propertyWithSpan.getNumber();\r
     }\r
 \r
     //==============================================================================\r
-    static LineRange deduceLineRange (GridItem::StartAndEndProperty prop, const juce::Array<Grid::TrackInfo>& tracks)\r
+    static LineRange deduceLineRange (GridItem::StartAndEndProperty prop, const Array<Grid::TrackInfo>& tracks)\r
     {\r
         LineRange s;\r
 \r
@@ -295,7 +295,7 @@ struct Grid::PlacementHelpers
 \r
     static LineArea deduceLineArea (const GridItem& item,\r
                                     const Grid& grid,\r
-                                    const std::map<juce::String, LineArea>& namedAreas)\r
+                                    const std::map<String, LineArea>& namedAreas)\r
     {\r
         if (item.area.isNotEmpty() && ! grid.templateAreas.isEmpty())\r
         {\r
@@ -310,12 +310,12 @@ struct Grid::PlacementHelpers
     }\r
 \r
     //==============================================================================\r
-    static juce::Array<juce::StringArray> parseAreasProperty (const juce::StringArray& areasStrings)\r
+    static Array<StringArray> parseAreasProperty (const StringArray& areasStrings)\r
     {\r
-        juce::Array<juce::StringArray> strings;\r
+        Array<StringArray> strings;\r
 \r
         for (const auto& areaString : areasStrings)\r
-            strings.add (juce::StringArray::fromTokens (areaString, false));\r
+            strings.add (StringArray::fromTokens (areaString, false));\r
 \r
         if (strings.size() > 0)\r
         {\r
@@ -328,7 +328,7 @@ struct Grid::PlacementHelpers
         return strings;\r
     }\r
 \r
-    static NamedArea findArea (juce::Array<juce::StringArray>& stringsArrays)\r
+    static NamedArea findArea (Array<StringArray>& stringsArrays)\r
     {\r
         NamedArea area;\r
 \r
@@ -370,11 +370,11 @@ struct Grid::PlacementHelpers
     }\r
 \r
     //==============================================================================\r
-    static std::map<juce::String, LineArea> deduceNamedAreas (const juce::StringArray& areasStrings)\r
+    static std::map<String, LineArea> deduceNamedAreas (const StringArray& areasStrings)\r
     {\r
         auto stringsArrays = parseAreasProperty (areasStrings);\r
 \r
-        std::map<juce::String, LineArea> areas;\r
+        std::map<String, LineArea> areas;\r
 \r
         for (auto area = findArea (stringsArrays); area.name.isNotEmpty(); area = findArea (stringsArrays))\r
         {\r
@@ -389,19 +389,19 @@ struct Grid::PlacementHelpers
     }\r
 \r
     //==============================================================================\r
-    static float getCoord (int trackNumber, float relativeUnit, Px gap, const juce::Array<Grid::TrackInfo>& tracks)\r
+    static float getCoord (int trackNumber, float relativeUnit, Px gap, const Array<Grid::TrackInfo>& tracks)\r
     {\r
         float c = 0;\r
 \r
         for (const auto* it = tracks.begin(); it != tracks.begin() + trackNumber - 1; ++it)\r
-            c += (it->isFraction ? it->size * relativeUnit : it->size) + static_cast<float> (gap.pixels);\r
+            c += it->getAbsoluteSize (relativeUnit) + static_cast<float> (gap.pixels);\r
 \r
         return c;\r
     }\r
 \r
-    static juce::Rectangle<float> getCellBounds (int columnNumber, int rowNumber,\r
-                                                 const juce::Array<Grid::TrackInfo>& columnTracks,\r
-                                                 const juce::Array<Grid::TrackInfo>& rowTracks,\r
+    static Rectangle<float> getCellBounds (int columnNumber, int rowNumber,\r
+                                                 const Array<Grid::TrackInfo>& columnTracks,\r
+                                                 const Array<Grid::TrackInfo>& rowTracks,\r
                                                  Grid::SizeCalculation calculation,\r
                                                  Px columnGap, Px rowGap)\r
     {\r
@@ -412,17 +412,15 @@ struct Grid::PlacementHelpers
         const auto y = getCoord (rowNumber, calculation.relativeHeightUnit, rowGap, rowTracks);\r
 \r
         const auto& columnTrackInfo = columnTracks.getReference (columnNumber - 1);\r
-        const float width = columnTrackInfo.isFraction ? columnTrackInfo.size * calculation.relativeWidthUnit\r
-                                                       : columnTrackInfo.size;\r
+        const float width = columnTrackInfo.getAbsoluteSize (calculation.relativeWidthUnit);\r
 \r
         const auto& rowTrackInfo = rowTracks.getReference (rowNumber - 1);\r
-        const float height = rowTrackInfo.isFraction ? rowTrackInfo.size * calculation.relativeHeightUnit\r
-                                                     : rowTrackInfo.size;\r
+        const float height = rowTrackInfo.getAbsoluteSize (calculation.relativeHeightUnit);\r
 \r
         return { x, y, width, height };\r
     }\r
 \r
-    static juce::Rectangle<float> alignCell (juce::Rectangle<float> area,\r
+    static Rectangle<float> alignCell (Rectangle<float> area,\r
                                              int columnNumber, int rowNumber,\r
                                              int numberOfColumns, int numberOfRows,\r
                                              Grid::SizeCalculation calculation,\r
@@ -486,10 +484,10 @@ struct Grid::PlacementHelpers
         return area;\r
     }\r
 \r
-    static juce::Rectangle<float> getAreaBounds (int columnLineNumberStart, int columnLineNumberEnd,\r
+    static Rectangle<float> getAreaBounds (int columnLineNumberStart, int columnLineNumberEnd,\r
                                                  int rowLineNumberStart, int rowLineNumberEnd,\r
-                                                 const juce::Array<Grid::TrackInfo>& columnTracks,\r
-                                                 const juce::Array<Grid::TrackInfo>& rowTracks,\r
+                                                 const Array<Grid::TrackInfo>& columnTracks,\r
+                                                 const Array<Grid::TrackInfo>& rowTracks,\r
                                                  Grid::SizeCalculation calculation,\r
                                                  Grid::AlignContent alignContent,\r
                                                  Grid::JustifyContent justifyContent,\r
@@ -529,7 +527,7 @@ struct Grid::PlacementHelpers
 //==============================================================================\r
 struct Grid::AutoPlacement\r
 {\r
-    using ItemPlacementArray = juce::Array<std::pair<GridItem*, Grid::PlacementHelpers::LineArea>>;\r
+    using ItemPlacementArray = Array<std::pair<GridItem*, Grid::PlacementHelpers::LineArea>>;\r
 \r
     //==============================================================================\r
     struct OccupancyPlane\r
@@ -722,10 +720,10 @@ struct Grid::AutoPlacement
     static int getSpanFromAuto (GridItem::StartAndEndProperty prop)\r
     {\r
         if (prop.end.hasSpan())\r
-            return prop.end.number;\r
+            return prop.end.getNumber();\r
 \r
         if (prop.start.hasSpan())\r
-            return prop.start.number;\r
+            return prop.start.getNumber();\r
 \r
         return 1;\r
     }\r
@@ -735,12 +733,12 @@ struct Grid::AutoPlacement
     {\r
         const auto namedAreas = Grid::PlacementHelpers::deduceNamedAreas (grid.templateAreas);\r
 \r
-        OccupancyPlane plane (juce::jmax (grid.templateColumns.size() + 1, 2),\r
-                              juce::jmax (grid.templateRows.size() + 1, 2),\r
+        OccupancyPlane plane (jmax (grid.templateColumns.size() + 1, 2),\r
+                              jmax (grid.templateRows.size() + 1, 2),\r
                               isColumnAutoFlow (grid.autoFlow));\r
 \r
         ItemPlacementArray itemPlacementArray;\r
-        juce::Array<GridItem*> sortedItems;\r
+        Array<GridItem*> sortedItems;\r
 \r
         for (auto& item : grid.items)\r
             sortedItems.add (&item);\r
@@ -836,12 +834,12 @@ struct Grid::AutoPlacement
         return { columnEndLine, rowEndLine };\r
     }\r
 \r
-    static std::pair<juce::Array<TrackInfo>, juce::Array<TrackInfo>> createImplicitTracks (const Grid& grid,\r
+    static std::pair<Array<TrackInfo>, Array<TrackInfo>> createImplicitTracks (const Grid& grid,\r
                                                                                            const ItemPlacementArray& items)\r
     {\r
         const auto columnAndRowLineEnds = getHighestEndLinesNumbers (items);\r
 \r
-        juce::Array<TrackInfo> implicitColumnTracks, implicitRowTracks;\r
+        Array<TrackInfo> implicitColumnTracks, implicitRowTracks;\r
 \r
         for (int i = grid.templateColumns.size() + 1; i < columnAndRowLineEnds.first; i++)\r
             implicitColumnTracks.add (grid.autoColumns);\r
@@ -853,8 +851,8 @@ struct Grid::AutoPlacement
     }\r
 \r
     //==============================================================================\r
-    static void applySizeForAutoTracks (juce::Array<Grid::TrackInfo>& columns,\r
-                                        juce::Array<Grid::TrackInfo>& rows,\r
+    static void applySizeForAutoTracks (Array<Grid::TrackInfo>& columns,\r
+                                        Array<Grid::TrackInfo>& rows,\r
                                         const ItemPlacementArray& itemPlacementArray)\r
     {\r
         auto isSpan = [](Grid::PlacementHelpers::LineRange r) -> bool { return std::abs (r.end - r.start) > 1; };\r
@@ -881,11 +879,11 @@ struct Grid::AutoPlacement
         };\r
 \r
         for (int i = 0; i < rows.size(); i++)\r
-            if (rows.getReference (i).hasKeyword)\r
+            if (rows.getReference (i).isAuto())\r
                 rows.getReference (i).size = getHighestItemOnRow (i + 1, itemPlacementArray);\r
 \r
         for (int i = 0; i < columns.size(); i++)\r
-            if (columns.getReference (i).hasKeyword)\r
+            if (columns.getReference (i).isAuto())\r
                 columns.getReference (i).size = getHighestItemOnColumn (i + 1, itemPlacementArray);\r
     }\r
 };\r
@@ -893,9 +891,9 @@ struct Grid::AutoPlacement
 //==============================================================================\r
 struct Grid::BoxAlignment\r
 {\r
-    static juce::Rectangle<float> alignItem (const GridItem& item,\r
+    static Rectangle<float> alignItem (const GridItem& item,\r
                                              const Grid& grid,\r
-                                             juce::Rectangle<float> area)\r
+                                             Rectangle<float> area)\r
     {\r
         // if item align is auto, inherit value from grid\r
         Grid::AlignItems alignType = Grid::AlignItems::start;\r
@@ -912,32 +910,26 @@ struct Grid::BoxAlignment
             justifyType = static_cast<Grid::JustifyItems> (item.justifySelf);\r
 \r
         // subtract margin from area\r
-        area = juce::BorderSize<float> (item.margin.top, item.margin.left, item.margin.bottom, item.margin.right)\r
+        area = BorderSize<float> (item.margin.top, item.margin.left, item.margin.bottom, item.margin.right)\r
                   .subtractedFrom (area);\r
 \r
         // align and justify\r
         auto r = area;\r
 \r
-        if (item.width != (float) GridItem::notAssigned)\r
-            r.setWidth (item.width);\r
-\r
-        if (item.height != (float) GridItem::notAssigned)\r
-            r.setHeight (item.height);\r
+        if (item.width     != (float) GridItem::notAssigned)  r.setWidth  (item.width);\r
+        if (item.height    != (float) GridItem::notAssigned)  r.setHeight (item.height);\r
+        if (item.maxWidth  != (float) GridItem::notAssigned)  r.setWidth  (jmin (item.maxWidth,  r.getWidth()));\r
+        if (item.minWidth  > 0.0f)                            r.setWidth  (jmax (item.minWidth,  r.getWidth()));\r
+        if (item.maxHeight != (float) GridItem::notAssigned)  r.setHeight (jmin (item.maxHeight, r.getHeight()));\r
+        if (item.minHeight > 0.0f)                            r.setHeight (jmax (item.minHeight, r.getHeight()));\r
 \r
         if (alignType == Grid::AlignItems::start && justifyType == Grid::JustifyItems::start)\r
             return r;\r
 \r
-        if (alignType == Grid::AlignItems::end)\r
-            r.setY (r.getY() + (area.getHeight() - r.getHeight()));\r
-\r
-        if (justifyType == Grid::JustifyItems::end)\r
-            r.setX (r.getX() + (area.getWidth() - r.getWidth()));\r
-\r
-        if (alignType == Grid::AlignItems::center)\r
-            r.setCentre (r.getCentreX(), area.getCentreY());\r
-\r
-        if (justifyType == Grid::JustifyItems::center)\r
-            r.setCentre (area.getCentreX(), r.getCentreY());\r
+        if (alignType   == Grid::AlignItems::end)       r.setY (r.getY() + (area.getHeight() - r.getHeight()));\r
+        if (justifyType == Grid::JustifyItems::end)     r.setX (r.getX() + (area.getWidth()  - r.getWidth()));\r
+        if (alignType   == Grid::AlignItems::center)    r.setCentre (r.getCentreX(),    area.getCentreY());\r
+        if (justifyType == Grid::JustifyItems::center)  r.setCentre (area.getCentreX(), r.getCentreY());\r
 \r
         return r;\r
     }\r
@@ -950,44 +942,52 @@ Grid::TrackInfo::TrackInfo (Px sizeInPixels) noexcept : size (static_cast<float>
 \r
 Grid::TrackInfo::TrackInfo (Fr fractionOfFreeSpace) noexcept : size ((float)fractionOfFreeSpace.fraction), isFraction (true) {}\r
 \r
-Grid::TrackInfo::TrackInfo (Px sizeInPixels, const juce::String& endLineNameToUse) noexcept : Grid::TrackInfo (sizeInPixels)\r
+Grid::TrackInfo::TrackInfo (Px sizeInPixels, const String& endLineNameToUse) noexcept : Grid::TrackInfo (sizeInPixels)\r
 {\r
     endLineName = endLineNameToUse;\r
 }\r
 \r
-Grid::TrackInfo::TrackInfo (Fr fractionOfFreeSpace, const juce::String& endLineNameToUse) noexcept : Grid::TrackInfo (fractionOfFreeSpace)\r
+Grid::TrackInfo::TrackInfo (Fr fractionOfFreeSpace, const String& endLineNameToUse) noexcept : Grid::TrackInfo (fractionOfFreeSpace)\r
 {\r
     endLineName = endLineNameToUse;\r
 }\r
 \r
-Grid::TrackInfo::TrackInfo (const juce::String& startLineNameToUse, Px sizeInPixels) noexcept : Grid::TrackInfo (sizeInPixels)\r
+Grid::TrackInfo::TrackInfo (const String& startLineNameToUse, Px sizeInPixels) noexcept : Grid::TrackInfo (sizeInPixels)\r
 {\r
     startLineName = startLineNameToUse;\r
 }\r
 \r
-Grid::TrackInfo::TrackInfo (const juce::String& startLineNameToUse, Fr fractionOfFreeSpace) noexcept : Grid::TrackInfo (fractionOfFreeSpace)\r
+Grid::TrackInfo::TrackInfo (const String& startLineNameToUse, Fr fractionOfFreeSpace) noexcept : Grid::TrackInfo (fractionOfFreeSpace)\r
 {\r
     startLineName = startLineNameToUse;\r
 }\r
 \r
-Grid::TrackInfo::TrackInfo (const juce::String& startLineNameToUse, Px sizeInPixels, const juce::String& endLineNameToUse) noexcept\r
+Grid::TrackInfo::TrackInfo (const String& startLineNameToUse, Px sizeInPixels, const String& endLineNameToUse) noexcept\r
   : Grid::TrackInfo (startLineNameToUse, sizeInPixels)\r
 {\r
     endLineName = endLineNameToUse;\r
 }\r
 \r
-Grid::TrackInfo::TrackInfo (const juce::String& startLineNameToUse, Fr fractionOfFreeSpace, const juce::String& endLineNameToUse) noexcept\r
+Grid::TrackInfo::TrackInfo (const String& startLineNameToUse, Fr fractionOfFreeSpace, const String& endLineNameToUse) noexcept\r
   : Grid::TrackInfo (startLineNameToUse, fractionOfFreeSpace)\r
 {\r
     endLineName = endLineNameToUse;\r
 }\r
 \r
+float Grid::TrackInfo::getAbsoluteSize (float relativeFractionalUnit) const\r
+{\r
+    if (isFractional())\r
+        return size * relativeFractionalUnit;\r
+    else\r
+        return size;\r
+}\r
+\r
 //==============================================================================\r
 Grid::Grid() noexcept {}\r
 Grid::~Grid() noexcept {}\r
 \r
 //==============================================================================\r
-void Grid::performLayout (juce::Rectangle<int> targetArea)\r
+void Grid::performLayout (Rectangle<int> targetArea)\r
 {\r
     const auto itemsAndAreas = Grid::AutoPlacement().deduceAllItems (*this);\r
 \r
index 86e87719ad9ba0ca0cec1ff9ebd472899afeec97..64c5d3e01a5cdbb2e09db08cb2027384e55a295b 100644 (file)
@@ -67,35 +67,37 @@ public:
     {\r
         /** Creates a track with auto dimension. */\r
         TrackInfo() noexcept;\r
-        /** */\r
+\r
         TrackInfo (Px sizeInPixels) noexcept;\r
-        /** */\r
         TrackInfo (Fr fractionOfFreeSpace) noexcept;\r
 \r
-        /** */\r
-        TrackInfo (Px sizeInPixels, const juce::String& endLineNameToUse) noexcept;\r
-        /** */\r
-        TrackInfo (Fr fractionOfFreeSpace, const juce::String& endLineNameToUse) noexcept;\r
+        TrackInfo (Px sizeInPixels, const String& endLineNameToUse) noexcept;\r
+        TrackInfo (Fr fractionOfFreeSpace, const String& endLineNameToUse) noexcept;\r
+\r
+        TrackInfo (const String& startLineNameToUse, Px sizeInPixels) noexcept;\r
+        TrackInfo (const String& startLineNameToUse, Fr fractionOfFreeSpace) noexcept;\r
+\r
+        TrackInfo (const String& startLineNameToUse, Px sizeInPixels, const String& endLineNameToUse) noexcept;\r
+        TrackInfo (const String& startLineNameToUse, Fr fractionOfFreeSpace, const String& endLineNameToUse) noexcept;\r
 \r
-        /** */\r
-        TrackInfo (const juce::String& startLineNameToUse, Px sizeInPixels) noexcept;\r
-        /** */\r
-        TrackInfo (const juce::String& startLineNameToUse, Fr fractionOfFreeSpace) noexcept;\r
+        bool isAuto() const noexcept { return hasKeyword; }\r
+        bool isFractional() const noexcept { return isFraction; }\r
+        bool isPixels() const noexcept { return ! isFraction; }\r
+        const String& getStartLineName() const noexcept { return startLineName; }\r
+        const String& getEndLineName() const noexcept { return endLineName; }\r
 \r
-        /** */\r
-        TrackInfo (const juce::String& startLineNameToUse, Px sizeInPixels, const juce::String& endLineNameToUse) noexcept;\r
-        /** */\r
-        TrackInfo (const juce::String& startLineNameToUse, Fr fractionOfFreeSpace, const juce::String& endLineNameToUse) noexcept;\r
+        /** Get the track's size - which might mean an absolute pixels value or a fractional ratio. */\r
+        float getSize() const noexcept { return size; }\r
 \r
     private:\r
         friend class Grid;\r
-        friend class GridItem;\r
+        float getAbsoluteSize (float relativeFractionalUnit) const;\r
 \r
         float size = 0; // Either a fraction or an absolute size in pixels\r
         bool isFraction = false;\r
         bool hasKeyword = false;\r
 \r
-        juce::String startLineName, endLineName;\r
+        String startLineName, endLineName;\r
     };\r
 \r
     //==============================================================================\r
@@ -177,13 +179,13 @@ public:
 \r
     //==============================================================================\r
     /** The set of column tracks to lay out. */\r
-    juce::Array<TrackInfo> templateColumns;\r
+    Array<TrackInfo> templateColumns;\r
 \r
     /** The set of row tracks to lay out. */\r
-    juce::Array<TrackInfo> templateRows;\r
+    Array<TrackInfo> templateRows;\r
 \r
     /** Template areas */\r
-    juce::StringArray templateAreas;\r
+    StringArray templateAreas;\r
 \r
     /** The row track for auto dimension. */\r
     TrackInfo autoRows;\r
@@ -201,11 +203,11 @@ public:
 \r
     //==============================================================================\r
     /** The set of items to lay-out. */\r
-    juce::Array<GridItem> items;\r
+    Array<GridItem> items;\r
 \r
     //==============================================================================\r
     /** Lays-out the grid's items within the given rectangle. */\r
-    void performLayout (juce::Rectangle<int>);\r
+    void performLayout (Rectangle<int>);\r
 \r
     //==============================================================================\r
     /** Returns the number of columns. */\r
index da6c9356b674b7ddb83c200d32c0ad38df7f4f70..f85e0d85ee458b038bc4f40f90c3d501c44268e0 100644 (file)
@@ -36,11 +36,11 @@ GridItem::Property::Property (GridItem::Keyword keyword) noexcept : isAuto (keyw
     jassert (keyword == GridItem::Keyword::autoValue);\r
 }\r
 \r
-GridItem::Property::Property (const char* lineNameToUse) noexcept : GridItem::Property (juce::String (lineNameToUse))\r
+GridItem::Property::Property (const char* lineNameToUse) noexcept : GridItem::Property (String (lineNameToUse))\r
 {\r
 }\r
 \r
-GridItem::Property::Property (const juce::String& lineNameToUse) noexcept : name (lineNameToUse), number (1)\r
+GridItem::Property::Property (const String& lineNameToUse) noexcept : name (lineNameToUse), number (1)\r
 {\r
 }\r
 \r
@@ -48,7 +48,7 @@ GridItem::Property::Property (int numberToUse) noexcept : number (numberToUse)
 {\r
 }\r
 \r
-GridItem::Property::Property (int numberToUse, const juce::String& lineNameToUse) noexcept\r
+GridItem::Property::Property (int numberToUse, const String& lineNameToUse) noexcept\r
     : name (lineNameToUse), number (numberToUse)\r
 {\r
 }\r
@@ -72,8 +72,8 @@ GridItem::Margin::Margin (float t, float r, float b, float l) noexcept : left (l
 GridItem::GridItem() noexcept {}\r
 GridItem::~GridItem() noexcept {}\r
 \r
-GridItem::GridItem (juce::Component& componentToUse) noexcept  : associatedComponent (&componentToUse) {}\r
-GridItem::GridItem (juce::Component* componentToUse) noexcept  : associatedComponent (componentToUse) {}\r
+GridItem::GridItem (Component& componentToUse) noexcept  : associatedComponent (&componentToUse) {}\r
+GridItem::GridItem (Component* componentToUse) noexcept  : associatedComponent (componentToUse) {}\r
 \r
 void GridItem::setArea (Property rowStart, Property columnStart, Property rowEnd, Property columnEnd)\r
 {\r
@@ -89,7 +89,7 @@ void GridItem::setArea (Property rowStart, Property columnStart)
     row.start = rowStart;\r
 }\r
 \r
-void GridItem::setArea (const juce::String& areaName)\r
+void GridItem::setArea (const String& areaName)\r
 {\r
     area = areaName;\r
 }\r
@@ -108,7 +108,7 @@ GridItem GridItem::withArea (Property rowStart, Property columnStart) const noex
     return gi;\r
 }\r
 \r
-GridItem GridItem::withArea (const juce::String& areaName) const noexcept\r
+GridItem GridItem::withArea (const String& areaName) const noexcept\r
 {\r
     auto gi = *this;\r
     gi.setArea (areaName);\r
index 30f95c6e32cb5b9e106b19b0a7a44c5098435ea6..9361334897cc207ae1c39667572d5f031188d272 100644 (file)
@@ -48,57 +48,50 @@ public:
             jassert (numberToUse > 0);\r
         }\r
 \r
-        explicit Span (int numberToUse, const juce::String& nameToUse) : Span (numberToUse)\r
+        explicit Span (int numberToUse, const String& nameToUse) : Span (numberToUse)\r
         {\r
             /* Name must not be empty */\r
             jassert (nameToUse.isNotEmpty());\r
             name = nameToUse;\r
         }\r
 \r
-        explicit Span (const juce::String& nameToUse) : name (nameToUse)\r
+        explicit Span (const String& nameToUse) : name (nameToUse)\r
         {\r
             /* Name must not be empty */\r
             jassert (nameToUse.isNotEmpty());\r
         }\r
 \r
         int number = 1;\r
-        juce::String name;\r
+        String name;\r
     };\r
 \r
     //==============================================================================\r
     /** Represents a property. */\r
     struct Property\r
     {\r
-        /** */\r
         Property() noexcept;\r
 \r
-        /** */\r
         Property (Keyword keyword) noexcept;\r
 \r
-        /** */\r
         Property (const char* lineNameToUse) noexcept;\r
 \r
-        /** */\r
-        Property (const juce::String& lineNameToUse) noexcept;\r
+        Property (const String& lineNameToUse) noexcept;\r
 \r
-        /** */\r
         Property (int numberToUse) noexcept;\r
 \r
-        /** */\r
-        Property (int numberToUse, const juce::String& lineNameToUse) noexcept;\r
+        Property (int numberToUse, const String& lineNameToUse) noexcept;\r
 \r
-        /** */\r
         Property (Span spanToUse) noexcept;\r
 \r
-    private:\r
-        bool hasSpan() const noexcept       { return isSpan && ! isAuto; }\r
-        bool hasAbsolute() const noexcept   { return ! (isSpan || isAuto);  }\r
-        bool hasAuto() const noexcept       { return isAuto; }\r
-        bool hasName() const noexcept       { return name.isNotEmpty(); }\r
-\r
-        friend class Grid;\r
+        bool hasSpan() const noexcept          { return isSpan && ! isAuto; }\r
+        bool hasAbsolute() const noexcept      { return ! (isSpan || isAuto);  }\r
+        bool hasAuto() const noexcept          { return isAuto; }\r
+        bool hasName() const noexcept          { return name.isNotEmpty(); }\r
+        const String& getName() const noexcept { return name; }\r
+        int getNumber() const noexcept         { return number; }\r
 \r
-        juce::String name;\r
+    private:\r
+        String name;\r
         int number = 1; /** Either an absolute line number or number of lines to span across. */\r
         bool isSpan = false;\r
         bool isAuto = false;\r
@@ -132,16 +125,16 @@ public:
     /** Creates an item with default parameters. */\r
     GridItem() noexcept;\r
     /** Creates an item with a given Component to use. */\r
-    GridItem (juce::Component& componentToUse) noexcept;\r
+    GridItem (Component& componentToUse) noexcept;\r
     /** Creates an item with a given Component to use. */\r
-    GridItem (juce::Component* componentToUse) noexcept;\r
+    GridItem (Component* componentToUse) noexcept;\r
 \r
     /** Destructor. */\r
     ~GridItem() noexcept;\r
 \r
     //==============================================================================\r
     /** If this is non-null, it represents a Component whose bounds are controlled by this item. */\r
-    juce::Component* associatedComponent = nullptr;\r
+    Component* associatedComponent = nullptr;\r
 \r
     //==============================================================================\r
     /** Determines the order used to lay out items in their grid container. */\r
@@ -164,7 +157,7 @@ public:
     StartAndEndProperty row    = { Keyword::autoValue, Keyword::autoValue };\r
 \r
     /** */\r
-    juce::String area;\r
+    String area;\r
 \r
     //==============================================================================\r
     enum\r
@@ -174,12 +167,12 @@ public:
     };\r
 \r
     /* TODO: move all of this into a common class that is shared with the FlexItem */\r
-    float width = notAssigned;\r
-    float minWidth = 0;\r
+    float width    = notAssigned;\r
+    float minWidth = 0.0f;\r
     float maxWidth = notAssigned;\r
 \r
-    float height = notAssigned;\r
-    float minHeight = 0;\r
+    float height    = notAssigned;\r
+    float minHeight = 0.0f;\r
     float maxHeight = notAssigned;\r
 \r
     /** Represents a margin. */\r
@@ -200,7 +193,7 @@ public:
     Margin margin;\r
 \r
     /** The item's current bounds. */\r
-    juce::Rectangle<float> currentBounds;\r
+    Rectangle<float> currentBounds;\r
 \r
     /** Short-hand */\r
     void setArea (Property rowStart, Property columnStart, Property rowEnd, Property columnEnd);\r
@@ -209,7 +202,7 @@ public:
     void setArea (Property rowStart, Property columnStart);\r
 \r
     /** Short-hand */\r
-    void setArea (const juce::String& areaName);\r
+    void setArea (const String& areaName);\r
 \r
     /** Short-hand */\r
     GridItem withArea (Property rowStart, Property columnStart, Property rowEnd, Property columnEnd) const noexcept;\r
@@ -218,7 +211,7 @@ public:
     GridItem withArea (Property rowStart, Property columnStart) const noexcept;\r
 \r
     /** Short-hand */\r
-    GridItem withArea (const juce::String& areaName)  const noexcept;\r
+    GridItem withArea (const String& areaName)  const noexcept;\r
 \r
     /** Returns a copy of this object with a new row property. */\r
     GridItem withRow (StartAndEndProperty row) const noexcept;\r
index 70c21dc178e89dadf3085cca35771c3880f594d8..e674a52d33e39d02efc88060e24278ca545c8283 100644 (file)
@@ -219,7 +219,7 @@ void SidePanel::mouseUp (const MouseEvent&)
     }\r
 }\r
 \r
-//==========================================================================\r
+//==============================================================================\r
 void SidePanel::lookAndFeelChanged()\r
 {\r
     auto& lf = getLookAndFeel();\r
index 9753ab6b972dc7219a1f1f663190c16805e14fba..263f55ef320bfb4eed06b283064d2d8b4882646f 100644 (file)
@@ -181,8 +181,8 @@ public:
         titleTextColour           = 0x100f002,\r
         shadowBaseColour          = 0x100f003,\r
         dismissButtonNormalColour = 0x100f004,\r
-        dismissButtonOverColour   = 0x100f004,\r
-        dismissButtonDownColour   = 0x100f005\r
+        dismissButtonOverColour   = 0x100f005,\r
+        dismissButtonDownColour   = 0x100f006\r
     };\r
 \r
     //==============================================================================\r
@@ -193,7 +193,7 @@ public:
     std::function<void(bool)> onPanelShowHide;\r
 \r
 private:\r
-    //==========================================================================\r
+    //==============================================================================\r
     Component* parent = nullptr;\r
     OptionalScopedPointer<Component> contentComponent;\r
     OptionalScopedPointer<Component> titleBarComponent;\r
@@ -216,7 +216,7 @@ private:
 \r
     bool shouldShowDismissButton = true;\r
 \r
-    //==========================================================================\r
+    //==============================================================================\r
     void lookAndFeelChanged() override;\r
     void componentMovedOrResized (Component&, bool wasMoved, bool wasResized) override;\r
 \r
index 6b47010343b49456baa93f1a17bbb9b16e6efbba..cbd79a66a7c3f982ce80784c7dfcc861438f2e26 100644 (file)
@@ -80,7 +80,10 @@ struct ItemComponent  : public Component
             customComp = *new HeaderItemComponent (item.text);\r
 \r
         if (customComp != nullptr)\r
+        {\r
+            setItem (*customComp, &item);\r
             addAndMakeVisible (*customComp);\r
+        }\r
 \r
         parent.addAndMakeVisible (this);\r
 \r
@@ -96,6 +99,9 @@ struct ItemComponent  : public Component
 \r
     ~ItemComponent() override\r
     {\r
+        if (customComp != nullptr)\r
+            setItem (*customComp, nullptr);\r
+\r
         removeChildComponent (customComp.get());\r
     }\r
 \r
@@ -1589,6 +1595,7 @@ void PopupMenu::addSeparator()
 void PopupMenu::addSectionHeader (String title)\r
 {\r
     Item i (std::move (title));\r
+    i.itemID = 0;\r
     i.isSectionHeader = true;\r
     addItem (std::move (i));\r
 }\r
@@ -1892,6 +1899,12 @@ void PopupMenu::setLookAndFeel (LookAndFeel* const newLookAndFeel)
     lookAndFeel = newLookAndFeel;\r
 }\r
 \r
+void PopupMenu::setItem (CustomComponent& c, const Item* itemToUse)\r
+{\r
+    c.item = itemToUse;\r
+    c.repaint();\r
+}\r
+\r
 //==============================================================================\r
 PopupMenu::CustomComponent::CustomComponent (bool autoTrigger)\r
     : triggeredAutomatically (autoTrigger)\r
index 6da361ab2a8c10b95f43395ede17e5ddccf07e54..95c6661f4d9815dfa5dbe5b83ee1db1bf003bfc5 100644 (file)
@@ -699,6 +699,13 @@ public:
         */\r
         bool isItemHighlighted() const noexcept                 { return isHighlighted; }\r
 \r
+        /** Returns a pointer to the Item that holds this custom component, if this\r
+            component is currently held by an Item.\r
+            You can query the Item for information that you might want to use\r
+            in your paint() method, such as the item's enabled and ticked states.\r
+        */\r
+        const PopupMenu::Item* getItem() const noexcept         { return item; }\r
+\r
         /** @internal */\r
         bool isTriggeredAutomatically() const noexcept          { return triggeredAutomatically; }\r
         /** @internal */\r
@@ -707,6 +714,9 @@ public:
     private:\r
         //==============================================================================\r
         bool isHighlighted = false, triggeredAutomatically;\r
+        const PopupMenu::Item* item = nullptr;\r
+\r
+        friend PopupMenu;\r
 \r
         JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR (CustomComponent)\r
     };\r
@@ -812,6 +822,8 @@ private:
     Component* createWindow (const Options&, ApplicationCommandManager**) const;\r
     int showWithOptionalCallback (const Options&, ModalComponentManager::Callback*, bool);\r
 \r
+    static void setItem (CustomComponent&, const Item*);\r
+\r
    #if JUCE_CATCH_DEPRECATED_CODE_MISUSE\r
     // These methods have new implementations now - see its new definition\r
     int drawPopupMenuItem (Graphics&, int, int, bool, bool, bool, bool, bool, const String&, const String&, Image*, const Colour*) { return 0; }\r
index 16ee696b567611d2ddf974bfa97cb724e18055f1..b985f3d4ade47f66f952ab5fe6109e64ce45a728 100644 (file)
@@ -30,60 +30,82 @@ namespace juce
 // This byte-code is generated from native/javacore/app/com/roli/juce/JuceSharingContentProvider.java with min sdk version 16\r
 // See juce_core/native/java/README.txt on how to generate this byte-code.\r
 static const uint8 javaJuceSharingContentProvider[] =\r
-{31,139,8,8,143,106,229,91,0,3,74,117,99,101,83,104,97,114,105,110,103,67,111,110,116,101,110,116,80,114,111,118,105,100,\r
-101,114,46,100,101,120,0,149,151,93,108,20,85,20,199,207,157,153,157,253,236,178,91,170,20,145,178,229,83,80,216,242,165,\r
-96,5,11,45,72,183,91,139,161,52,218,190,56,221,157,148,129,221,153,101,102,118,133,23,2,106,162,209,196,24,125,64,19,73,\r
-48,33,106,140,15,36,26,227,131,49,152,24,163,241,65,77,148,248,160,209,152,152,24,193,68,227,131,6,37,241,127,63,118,219,\r
-173,197,232,194,111,238,185,231,156,123,238,185,231,222,153,206,148,237,19,137,190,173,219,105,239,208,216,231,67,47,106,\r
-177,200,154,39,135,207,172,189,226,63,113,230,173,189,99,175,63,244,123,185,131,168,70,68,39,38,182,117,146,250,157,79,\r
-17,141,146,212,223,4,46,48,34,110,252,3,109,4,237,103,26,209,82,222,71,171,163,189,132,203,80,156,40,103,16,125,111,18,\r
-253,4,126,6,191,129,107,224,58,232,137,18,245,130,53,96,3,216,2,14,131,6,120,25,188,11,190,1,191,128,100,140,104,19,112,\r
-192,235,224,50,184,6,110,193,28,187,192,3,192,6,117,240,52,120,6,60,15,206,130,115,224,101,240,10,120,3,188,9,222,6,159,\r
-128,175,192,183,224,42,136,38,136,214,129,33,48,5,60,240,8,56,5,206,130,87,193,69,240,54,120,31,124,12,62,5,95,130,31,\r
-192,21,240,43,248,19,24,73,162,197,96,57,88,5,242,224,78,176,27,12,131,7,65,9,56,224,56,56,9,78,129,199,192,83,0,101,37,\r
-148,142,16,138,208,37,148,159,176,45,148,6,139,64,6,100,73,238,193,98,208,165,246,229,102,176,4,116,147,220,143,91,193,\r
-106,176,134,228,190,240,223,195,168,189,166,228,10,228,152,154,235,4,100,148,65,236,231,105,165,71,233,233,89,200,248,47,\r
-108,252,23,83,50,247,143,170,60,94,48,229,92,205,3,179,92,201,231,249,62,43,249,53,200,43,148,124,17,242,42,37,191,11,\r
-121,165,146,63,130,220,171,228,47,32,231,148,252,181,41,215,177,120,78,14,93,42,135,4,170,181,85,212,42,69,247,137,122,\r
-201,126,82,245,83,168,214,157,196,215,28,19,99,13,172,176,143,248,154,22,137,190,9,253,58,17,51,45,250,9,81,105,222,74,\r
-125,2,255,214,171,120,36,218,36,109,16,109,156,238,17,241,101,220,20,42,113,187,104,53,186,67,180,58,109,20,45,163,77,\r
-202,190,89,180,81,218,34,90,131,182,171,252,250,213,184,93,162,53,105,183,26,191,71,237,253,1,177,231,49,149,151,172,185,\r
-169,106,193,247,171,15,157,109,50,61,113,94,178,170,70,77,251,0,236,35,202,158,82,118,109,142,253,32,236,211,202,206,245,\r
-157,144,187,83,179,114,111,74,158,201,13,41,238,31,17,250,231,146,114,142,41,198,168,150,211,104,128,38,53,126,66,117,\r
-120,242,179,118,46,41,207,137,151,209,225,127,8,91,89,235,139,146,198,210,34,119,83,248,92,104,197,208,97,53,104,32,50,\r
-169,105,136,17,129,149,231,117,49,41,215,121,8,241,107,227,113,210,54,167,17,139,137,92,222,73,202,181,214,50,60,183,149,\r
-168,79,45,195,207,253,84,198,16,59,25,17,167,154,232,189,164,90,7,246,155,199,229,249,125,152,148,117,24,239,53,104,57,\r
-171,245,165,104,139,145,162,30,150,197,222,247,176,117,34,183,152,152,39,78,186,170,212,103,173,56,89,68,150,119,211,229,\r
-57,58,77,100,133,103,86,83,151,153,157,239,251,121,243,117,252,203,124,166,26,115,37,41,239,233,241,45,24,163,241,49,131,\r
-145,20,237,128,159,155,225,51,165,88,143,150,101,157,184,222,118,189,3,215,117,76,222,227,89,17,167,19,126,188,202,140,\r
-174,183,205,221,48,121,5,111,60,119,68,172,33,158,154,173,89,206,160,182,223,29,243,250,59,230,245,121,55,138,168,89,220,\r
-161,186,144,179,226,94,213,148,28,17,109,151,208,102,91,122,93,84,47,218,58,151,89,209,231,232,170,205,170,216,252,126,\r
-202,42,61,151,155,177,179,202,175,139,204,123,28,215,9,119,19,27,38,99,184,88,44,82,132,95,139,196,10,180,162,80,47,217,\r
-135,142,88,190,227,206,12,122,110,104,187,225,65,223,107,56,101,219,223,116,212,106,88,196,138,164,193,85,231,254,102,81,\r
-252,168,183,104,185,101,223,115,202,249,146,28,146,159,55,180,159,86,220,200,101,194,170,212,237,160,159,214,255,195,193,\r
-183,131,252,158,32,176,195,253,78,197,30,178,131,146,239,212,66,15,177,150,182,92,203,86,104,77,91,129,157,31,172,251,\r
-129,215,54,77,203,52,106,133,190,115,162,233,144,109,57,184,118,152,63,236,59,115,195,121,65,158,207,53,54,29,216,126,\r
-131,103,221,59,215,116,208,242,75,118,101,126,50,59,139,37,175,154,247,189,138,147,63,138,210,229,111,92,191,213,77,161,\r
-153,203,189,255,127,104,123,122,27,254,115,128,126,90,89,44,91,149,134,115,44,111,185,174,23,90,161,227,185,249,125,110,\r
-169,226,5,220,187,98,5,216,131,158,5,124,134,93,23,25,75,123,239,2,246,81,187,58,173,28,248,54,118,22,249,41,201,87,44,\r
-119,38,63,54,125,212,46,133,237,186,67,33,207,174,159,210,237,197,160,174,133,86,72,108,130,244,137,97,156,184,137,2,25,\r
-19,5,33,225,236,77,20,113,112,39,138,5,28,92,126,29,38,54,73,139,167,22,152,37,105,149,74,118,16,236,175,88,51,1,69,248,\r
-98,109,74,150,188,74,189,234,222,111,85,237,128,150,170,195,198,171,214,204,101,144,187,149,169,167,205,52,55,173,125,13,\r
-168,105,89,155,253,62,59,196,164,182,85,29,63,89,67,220,155,218,140,99,53,219,229,1,168,179,77,253,64,221,246,79,146,89,\r
-182,43,118,104,83,196,22,97,151,204,216,225,66,39,141,210,51,237,83,68,209,231,18,25,71,188,32,164,56,191,142,123,135,\r
-177,66,211,113,145,104,72,70,197,43,29,35,163,106,5,199,40,93,117,170,54,119,71,212,16,149,53,170,94,25,67,93,84,129,98,\r
-158,59,136,184,200,33,234,185,114,113,29,30,82,110,221,124,240,104,174,192,168,89,225,17,74,212,124,143,239,45,14,0,69,\r
-142,203,101,224,118,173,87,144,71,128,229,72,75,71,75,220,227,163,254,113,212,54,28,243,203,124,246,240,136,19,144,201,\r
-175,171,251,200,172,215,202,124,118,189,238,59,252,82,161,72,131,63,21,200,20,77,64,155,244,3,219,215,71,211,27,119,109,\r
-164,187,40,154,222,53,73,203,140,3,219,7,118,72,213,42,173,111,32,154,158,196,147,24,38,178,244,194,208,190,104,154,30,\r
-99,90,97,39,20,14,205,176,2,250,227,90,97,20,205,16,156,168,170,21,238,22,166,134,20,138,58,254,116,108,156,26,193,147,\r
-119,36,50,178,103,104,223,126,97,157,50,10,163,34,150,214,193,70,186,83,90,90,91,107,100,239,94,114,75,83,88,166,45,98,\r
-35,183,106,221,137,238,36,105,26,195,159,238,103,115,145,211,167,141,75,49,237,81,141,76,246,93,140,171,53,174,142,157,\r
-57,109,60,30,103,80,39,216,133,56,49,35,110,104,73,232,46,9,93,147,69,236,199,56,99,127,129,139,9,198,62,0,95,129,171,\r
-224,124,146,177,31,193,75,41,249,110,75,234,89,222,108,155,223,30,252,57,223,252,254,208,105,246,27,196,160,217,239,16,\r
-222,54,191,69,76,154,253,30,209,51,82,230,127,207,88,78,190,75,15,64,54,115,82,207,223,161,88,70,190,103,139,119,228,156,\r
-156,151,127,191,232,202,159,191,243,24,57,57,31,127,47,34,53,86,188,123,101,100,174,252,91,233,111,138,244,241,33,100,13,\r
-0,0};\r
+{100,101,120,10,48,51,53,0,66,68,79,209,68,153,2,8,5,37,136,73,129,38,235,114,135,129,180,66,79,170,89,247,100,13,0,0,112,0,0,\r
+0,120,86,52,18,0,0,0,0,0,0,0,0,160,12,0,0,77,0,0,0,112,0,0,0,21,0,0,0,164,1,0,0,18,0,0,0,248,1,0,0,5,0,0,0,208,2,0,0,25,0,0,0,\r
+248,2,0,0,3,0,0,0,192,3,0,0,68,9,0,0,32,4,0,0,226,6,0,0,234,6,0,0,237,6,0,0,243,6,0,0,250,6,0,0,253,6,0,0,30,7,0,0,33,7,0,0,37,\r
+7,0,0,42,7,0,0,50,7,0,0,85,7,0,0,118,7,0,0,161,7,0,0,188,7,0,0,221,7,0,0,240,7,0,0,11,8,0,0,46,8,0,0,105,8,0,0,170,8,0,0,214,\r
+8,0,0,250,8,0,0,26,9,0,0,61,9,0,0,81,9,0,0,101,9,0,0,117,9,0,0,139,9,0,0,142,9,0,0,147,9,0,0,151,9,0,0,157,9,0,0,161,9,0,0,166,\r
+9,0,0,172,9,0,0,179,9,0,0,182,9,0,0,203,9,0,0,216,9,0,0,223,9,0,0,236,9,0,0,7,10,0,0,39,10,0,0,68,10,0,0,91,10,0,0,111,10,0,\r
+0,119,10,0,0,126,10,0,0,151,10,0,0,167,10,0,0,176,10,0,0,182,10,0,0,193,10,0,0,201,10,0,0,207,10,0,0,213,10,0,0,229,10,0,0,235,\r
+10,0,0,241,10,0,0,251,10,0,0,4,11,0,0,19,11,0,0,29,11,0,0,35,11,0,0,47,11,0,0,54,11,0,0,62,11,0,0,73,11,0,0,88,11,0,0,99,11,\r
+0,0,105,11,0,0,113,11,0,0,121,11,0,0,126,11,0,0,131,11,0,0,138,11,0,0,1,0,0,0,4,0,0,0,10,0,0,0,11,0,0,0,12,0,0,0,13,0,0,0,14,\r
+0,0,0,15,0,0,0,16,0,0,0,17,0,0,0,18,0,0,0,19,0,0,0,20,0,0,0,21,0,0,0,22,0,0,0,23,0,0,0,24,0,0,0,25,0,0,0,28,0,0,0,36,0,0,0,37,\r
+0,0,0,3,0,0,0,0,0,0,0,96,6,0,0,2,0,0,0,0,0,0,0,108,6,0,0,8,0,0,0,4,0,0,0,120,6,0,0,9,0,0,0,5,0,0,0,128,6,0,0,8,0,0,0,7,0,0,0,\r
+144,6,0,0,6,0,0,0,9,0,0,0,0,0,0,0,8,0,0,0,9,0,0,0,120,6,0,0,7,0,0,0,17,0,0,0,152,6,0,0,28,0,0,0,18,0,0,0,0,0,0,0,29,0,0,0,18,\r
+0,0,0,160,6,0,0,30,0,0,0,18,0,0,0,168,6,0,0,31,0,0,0,18,0,0,0,176,6,0,0,35,0,0,0,18,0,0,0,188,6,0,0,34,0,0,0,18,0,0,0,200,6,\r
+0,0,33,0,0,0,18,0,0,0,212,6,0,0,32,0,0,0,18,0,0,0,220,6,0,0,36,0,0,0,19,0,0,0,0,0,0,0,8,0,0,0,20,0,0,0,120,6,0,0,10,0,1,0,51,0,\r
+0,0,10,0,12,0,71,0,0,0,11,0,1,0,51,0,0,0,11,0,12,0,71,0,0,0,12,0,16,0,54,0,0,0,2,0,8,0,0,0,0,0,4,0,5,0,48,0,0,0,6,0,15,0,0,0,\r
+0,0,6,0,8,0,39,0,0,0,8,0,14,0,0,0,0,0,10,0,13,0,0,0,0,0,10,0,8,0,39,0,0,0,10,0,10,0,41,0,0,0,11,0,12,0,0,0,0,0,11,0,11,0,42,0,\r
+0,0,11,0,9,0,60,0,0,0,12,0,8,0,0,0,0,0,12,0,17,0,43,0,0,0,12,0,2,0,44,0,0,0,12,0,3,0,45,0,0,0,12,0,1,0,46,0,0,0,12,0,17,0,49,0,\r
+0,0,12,0,7,0,50,0,0,0,12,0,4,0,53,0,0,0,12,0,16,0,59,0,0,0,12,0,2,0,61,0,0,0,12,0,6,0,62,0,0,0,12,0,3,0,65,0,0,0,12,0,0,0,72,\r
+0,0,0,16,0,8,0,0,0,0,0,10,0,0,0,17,0,0,0,6,0,0,0,0,0,0,0,5,0,0,0,48,6,0,0,52,12,0,0,0,0,0,0,11,0,0,0,17,0,0,0,8,0,0,0,0,0,0,0,\r
+5,0,0,0,64,6,0,0,75,12,0,0,0,0,0,0,12,0,0,0,17,0,0,0,2,0,0,0,0,0,0,0,5,0,0,0,80,6,0,0,98,12,0,0,0,0,0,0,2,0,0,0,18,12,0,0,24,\r
+12,0,0,2,0,0,0,18,12,0,0,33,12,0,0,1,0,0,0,42,12,0,0,5,0,5,0,2,0,0,0,146,11,0,0,8,0,0,0,91,1,1,0,112,32,2,0,64,0,90,2,0,0,14,\r
+0,3,0,1,0,3,0,0,0,157,11,0,0,9,0,0,0,111,16,3,0,2,0,83,32,0,0,112,48,7,0,2,1,14,0,0,0,6,0,6,0,3,0,0,0,164,11,0,0,8,0,0,0,91,1,\r
+3,0,112,48,4,0,64,5,90,2,2,0,14,0,5,0,3,0,5,0,0,0,176,11,0,0,6,0,0,0,83,32,2,0,112,84,9,0,2,49,14,0,2,0,1,0,1,0,0,0,184,11,0,\r
+0,11,0,0,0,112,16,0,0,1,0,34,0,16,0,112,16,24,0,0,0,91,16,4,0,14,0,0,0,5,0,4,0,0,0,0,0,190,11,0,0,2,0,0,0,18,0,15,0,5,0,3,0,3,\r
+0,1,0,198,11,0,0,12,0,0,0,84,33,4,0,29,1,112,48,12,0,50,4,12,0,30,1,17,0,13,0,30,1,39,0,3,0,0,0,8,0,1,0,1,0,9,0,3,0,2,0,0,0,0,\r
+0,208,11,0,0,2,0,0,0,18,0,17,0,4,0,3,0,0,0,0,0,214,11,0,0,2,0,0,0,18,0,17,0,2,0,1,0,0,0,0,0,221,11,0,0,2,0,0,0,18,16,15,0,5,\r
+0,3,0,3,0,1,0,226,11,0,0,12,0,0,0,84,33,4,0,29,1,112,48,13,0,50,4,12,0,30,1,17,0,13,0,30,1,39,0,3,0,0,0,8,0,1,0,1,0,9,0,6,0,3,\r
+0,3,0,1,0,235,11,0,0,21,0,0,0,84,50,4,0,29,2,112,48,13,0,67,5,12,0,56,0,8,0,110,16,1,0,0,0,12,1,30,2,17,1,18,1,30,2,40,253,13,\r
+1,30,2,39,1,0,0,3,0,0,0,17,0,1,0,1,0,18,0,8,0,6,0,6,0,1,0,253,11,0,0,12,0,0,0,84,33,4,0,29,1,118,6,14,0,2,0,12,0,30,1,17,0,13,\r
+0,30,1,39,0,3,0,0,0,8,0,1,0,1,0,9,0,6,0,5,0,0,0,0,0,9,12,0,0,2,0,0,0,18,0,15,0,32,4,0,0,0,0,0,0,0,0,0,0,0,0,0,0,44,4,0,0,0,0,\r
+0,0,0,0,0,0,0,0,0,0,56,4,0,0,0,0,0,0,0,0,0,0,0,0,0,0,4,0,0,0,7,0,3,0,17,0,20,0,3,0,0,0,7,0,17,0,20,0,0,0,2,0,0,0,7,0,17,0,5,0,\r
+0,0,7,0,20,0,17,0,20,0,17,0,0,0,2,0,0,0,7,0,3,0,1,0,0,0,7,0,0,0,2,0,0,0,0,0,17,0,1,0,0,0,1,0,0,0,3,0,0,0,1,0,0,0,17,0,0,0,4,\r
+0,0,0,12,0,1,0,17,0,0,0,3,0,0,0,12,0,1,0,20,0,0,0,2,0,0,0,17,0,0,0,1,0,0,0,20,0,6,60,105,110,105,116,62,0,1,73,0,4,73,76,76,76,\r
+0,5,73,76,76,76,76,0,1,74,0,31,74,117,99,101,83,104,97,114,105,110,103,67,111,110,116,101,110,116,80,114,111,118,105,100,101,\r
+114,46,106,97,118,97,0,1,76,0,2,76,76,0,3,76,76,76,0,6,76,76,76,76,76,76,0,33,76,97,110,100,114,111,105,100,47,99,111,110,116,\r
+101,110,116,47,67,111,110,116,101,110,116,80,114,111,118,105,100,101,114,59,0,31,76,97,110,100,114,111,105,100,47,99,111,110,\r
+116,101,110,116,47,67,111,110,116,101,110,116,86,97,108,117,101,115,59,0,41,76,97,110,100,114,111,105,100,47,99,111,110,116,\r
+101,110,116,47,114,101,115,47,65,115,115,101,116,70,105,108,101,68,101,115,99,114,105,112,116,111,114,59,0,25,76,97,110,100,114,\r
+111,105,100,47,100,97,116,97,98,97,115,101,47,67,117,114,115,111,114,59,0,31,76,97,110,100,114,111,105,100,47,100,97,116,97,98,\r
+97,115,101,47,77,97,116,114,105,120,67,117,114,115,111,114,59,0,17,76,97,110,100,114,111,105,100,47,110,101,116,47,85,114,105,\r
+59,0,25,76,97,110,100,114,111,105,100,47,111,115,47,70,105,108,101,79,98,115,101,114,118,101,114,59,0,33,76,97,110,100,114,111,\r
+105,100,47,111,115,47,80,97,114,99,101,108,70,105,108,101,68,101,115,99,114,105,112,116,111,114,59,0,57,76,99,111,109,47,114,\r
+111,108,105,47,106,117,99,101,47,74,117,99,101,83,104,97,114,105,110,103,67,111,110,116,101,110,116,80,114,111,118,105,100,101,\r
+114,36,80,114,111,118,105,100,101,114,67,117,114,115,111,114,59,0,63,76,99,111,109,47,114,111,108,105,47,106,117,99,101,47,\r
+74,117,99,101,83,104,97,114,105,110,103,67,111,110,116,101,110,116,80,114,111,118,105,100,101,114,36,80,114,111,118,105,100,101,\r
+114,70,105,108,101,79,98,115,101,114,118,101,114,59,0,42,76,99,111,109,47,114,111,108,105,47,106,117,99,101,47,74,117,99,101,\r
+83,104,97,114,105,110,103,67,111,110,116,101,110,116,80,114,111,118,105,100,101,114,59,0,34,76,100,97,108,118,105,107,47,97,\r
+110,110,111,116,97,116,105,111,110,47,69,110,99,108,111,115,105,110,103,67,108,97,115,115,59,0,30,76,100,97,108,118,105,107,47,\r
+97,110,110,111,116,97,116,105,111,110,47,73,110,110,101,114,67,108,97,115,115,59,0,33,76,100,97,108,118,105,107,47,97,110,110,\r
+111,116,97,116,105,111,110,47,77,101,109,98,101,114,67,108,97,115,115,101,115,59,0,18,76,106,97,118,97,47,108,97,110,103,47,\r
+79,98,106,101,99,116,59,0,18,76,106,97,118,97,47,108,97,110,103,47,83,116,114,105,110,103,59,0,14,80,114,111,118,105,100,101,\r
+114,67,117,114,115,111,114,0,20,80,114,111,118,105,100,101,114,70,105,108,101,79,98,115,101,114,118,101,114,0,1,86,0,3,86,73,\r
+76,0,2,86,74,0,4,86,74,73,76,0,2,86,76,0,3,86,76,73,0,4,86,76,74,76,0,5,86,76,74,76,73,0,1,90,0,19,91,76,106,97,118,97,47,108,\r
+97,110,103,47,83,116,114,105,110,103,59,0,11,97,99,99,101,115,115,70,108,97,103,115,0,5,99,108,111,115,101,0,11,99,111,108,117,\r
+109,110,78,97,109,101,115,0,25,99,111,110,116,101,110,116,83,104,97,114,101,114,67,117,114,115,111,114,67,108,111,115,101,100,\r
+0,30,99,111,110,116,101,110,116,83,104,97,114,101,114,70,105,108,101,79,98,115,101,114,118,101,114,69,118,101,110,116,0,27,99,\r
+111,110,116,101,110,116,83,104,97,114,101,114,71,101,116,83,116,114,101,97,109,84,121,112,101,115,0,21,99,111,110,116,101,110,\r
+116,83,104,97,114,101,114,79,112,101,110,70,105,108,101,0,18,99,111,110,116,101,110,116,83,104,97,114,101,114,81,117,101,114,\r
+121,0,6,100,101,108,101,116,101,0,5,101,118,101,110,116,0,23,103,101,116,80,97,114,99,101,108,70,105,108,101,68,101,115,99,114,\r
+105,112,116,111,114,0,14,103,101,116,83,116,114,101,97,109,84,121,112,101,115,0,7,103,101,116,84,121,112,101,0,4,104,111,115,\r
+116,0,9,104,111,115,116,84,111,85,115,101,0,6,105,110,115,101,114,116,0,4,108,111,99,107,0,4,109,97,115,107,0,14,109,105,109,\r
+101,84,121,112,101,70,105,108,116,101,114,0,4,109,111,100,101,0,4,110,97,109,101,0,8,111,110,67,114,101,97,116,101,0,7,111,110,\r
+69,118,101,110,116,0,13,111,112,101,110,65,115,115,101,116,70,105,108,101,0,8,111,112,101,110,70,105,108,101,0,4,112,97,116,\r
+104,0,10,112,114,111,106,101,99,116,105,111,110,0,5,113,117,101,114,121,0,6,114,101,115,117,108,116,0,9,115,101,108,101,99,116,\r
+105,111,110,0,13,115,101,108,101,99,116,105,111,110,65,114,103,115,0,9,115,111,114,116,79,114,100,101,114,0,4,116,104,105,115,\r
+0,6,116,104,105,115,36,48,0,6,117,112,100,97,116,101,0,3,117,114,105,0,3,117,114,108,0,5,118,97,108,117,101,0,6,118,97,108,117,\r
+101,115,0,46,3,72,53,41,7,14,45,61,45,0,55,0,7,14,61,90,0,27,4,72,53,64,56,7,14,45,61,45,0,35,2,48,64,7,14,90,0,15,0,7,14,61,0,\r
+97,3,74,68,69,7,14,0,131,1,2,74,57,7,14,61,105,0,103,1,74,7,14,0,84,2,74,77,7,14,0,68,0,7,14,0,109,2,74,58,7,14,61,105,0,118,\r
+2,74,58,7,14,61,76,3,0,67,5,45,91,75,5,0,0,75,5,75,65,68,69,70,7,14,61,105,0,91,4,74,77,68,69,7,14,0,2,13,1,75,24,12,2,14,2,38,\r
+4,17,58,23,26,2,14,2,38,4,17,58,23,27,2,15,1,75,28,2,24,10,24,11,0,2,2,1,0,2,1,144,32,5,128,128,4,192,8,2,130,2,0,6,1,224,8,\r
+0,2,2,1,2,2,1,144,32,8,129,128,4,132,9,1,130,2,0,10,1,164,9,0,1,4,9,4,2,11,129,128,4,192,9,1,130,2,0,1,130,2,0,1,130,2,0,15,1,\r
+232,9,1,1,252,9,1,1,176,10,1,1,196,10,1,1,216,10,1,1,236,10,1,1,160,11,1,1,232,11,1,1,156,12,0,0,16,0,0,0,0,0,0,0,1,0,0,0,0,\r
+0,0,0,1,0,0,0,77,0,0,0,112,0,0,0,2,0,0,0,21,0,0,0,164,1,0,0,3,0,0,0,18,0,0,0,248,1,0,0,4,0,0,0,5,0,0,0,208,2,0,0,5,0,0,0,25,0,\r
+0,0,248,2,0,0,6,0,0,0,3,0,0,0,192,3,0,0,3,16,0,0,3,0,0,0,32,4,0,0,1,32,0,0,14,0,0,0,64,4,0,0,6,32,0,0,3,0,0,0,48,6,0,0,1,16,\r
+0,0,13,0,0,0,96,6,0,0,2,32,0,0,77,0,0,0,226,6,0,0,3,32,0,0,14,0,0,0,146,11,0,0,4,32,0,0,4,0,0,0,18,12,0,0,0,32,0,0,3,0,0,0,52,\r
+12,0,0,0,16,0,0,1,0,0,0,160,12,0,0,0,0};\r
 \r
 //==============================================================================\r
 #define JNI_CLASS_MEMBERS(METHOD, STATICMETHOD, FIELD, STATICFIELD, CALLBACK) \\r
@@ -533,7 +555,7 @@ public:
 \r
     //==============================================================================\r
     jobject openFile (const LocalRef<jobject>& contentProvider,\r
-                    const LocalRef<jobject>& uri, const LocalRef<jstring>& mode)\r
+                      const LocalRef<jobject>& uri, const LocalRef<jstring>& mode)\r
     {\r
         ignoreUnused (mode);\r
 \r
@@ -553,8 +575,8 @@ public:
     }\r
 \r
     jobject query (const LocalRef<jobject>& contentProvider, const LocalRef<jobject>& uri,\r
-                 const LocalRef<jobjectArray>& projection, const LocalRef<jobject>& selection,\r
-                 const LocalRef<jobjectArray>& selectionArgs, const LocalRef<jobject>& sortOrder)\r
+                   const LocalRef<jobjectArray>& projection, const LocalRef<jobject>& selection,\r
+                   const LocalRef<jobjectArray>& selectionArgs, const LocalRef<jobject>& sortOrder)\r
     {\r
         ignoreUnused (selection, selectionArgs, sortOrder);\r
 \r
@@ -837,7 +859,7 @@ private:
      CALLBACK (contentSharerGetStreamTypes, "contentSharerGetStreamTypes", "(Landroid/net/Uri;Ljava/lang/String;)[Ljava/lang/String;") \\r
 \r
 \r
-    DECLARE_JNI_CLASS_WITH_BYTECODE (JuceSharingContentProvider, "com/roli/juce/JuceSharingContentProvider", 16, javaJuceSharingContentProvider, sizeof(javaJuceSharingContentProvider))\r
+    DECLARE_JNI_CLASS_WITH_BYTECODE (JuceSharingContentProvider, "com/roli/juce/JuceSharingContentProvider", 16, javaJuceSharingContentProvider, sizeof (javaJuceSharingContentProvider))\r
     #undef JNI_CLASS_MEMBERS\r
 \r
     static jobject JNICALL contentSharerQuery (JNIEnv*, jobject contentProvider, jobject uri, jobjectArray projection,\r
index 92700f9fe42bb5cae24e54a76e26c5453ca3be9d..18be24d45dbb8695d57ba37f57498c646e18aab3 100644 (file)
@@ -677,12 +677,29 @@ public:
 \r
     void handleBackButtonCallback()\r
     {\r
+        bool handled = false;\r
+\r
         if (auto* app = JUCEApplicationBase::getInstance())\r
-            app->backButtonPressed();\r
+            handled = app->backButtonPressed();\r
 \r
         if (Component* kiosk = Desktop::getInstance().getKioskModeComponent())\r
             if (kiosk->getPeer() == this)\r
                 setNavBarsHidden (navBarsHidden);\r
+\r
+        if (! handled)\r
+        {\r
+            auto* env = getEnv();\r
+            LocalRef<jobject> activity (getCurrentActivity());\r
+\r
+            if (activity != nullptr)\r
+            {\r
+                jmethodID finishMethod = env->GetMethodID (AndroidActivity, "finish", "()V");\r
+\r
+                if (finishMethod != nullptr)\r
+                    env->CallVoidMethod (activity.get(), finishMethod);\r
+            }\r
+        }\r
+\r
     }\r
 \r
     void handleKeyboardHiddenCallback()\r
index 40e5e1ccd8eb4c823ed53d3f0acd611d79e46713..c44e331e0b66cde32f227f0f081c884e3aeffde1 100644 (file)
@@ -958,6 +958,8 @@ static double getScaleForDisplay (const String& name, double dpi)
 \r
                     if (scaleFactor > 0.0)\r
                         return scaleFactor;\r
+\r
+                    return 1.0;\r
                 }\r
             }\r
         }\r
@@ -1259,10 +1261,13 @@ public:
 \r
     Point<int> getScreenPosition (bool physical) const\r
     {\r
+        auto screenBounds = (parentWindow == 0 ? bounds\r
+                                               : bounds.translated (parentScreenPosition.x, parentScreenPosition.y));\r
+\r
         if (physical)\r
-            return Desktop::getInstance().getDisplays().logicalToPhysical (bounds.getTopLeft());\r
+            return Desktop::getInstance().getDisplays().logicalToPhysical (screenBounds.getTopLeft());\r
 \r
-        return bounds.getTopLeft();\r
+        return screenBounds.getTopLeft();\r
     }\r
 \r
     Rectangle<int> getBounds() const override                            { return bounds; }\r
@@ -2397,6 +2402,7 @@ private:
     friend class LinuxRepaintManager;\r
     Window windowH = {}, parentWindow = {}, keyProxy = {};\r
     Rectangle<int> bounds;\r
+    Point<int> parentScreenPosition;\r
     Image taskbarImage;\r
     bool fullScreen = false, mapped = false, focused = false;\r
     Visual* visual = {};\r
@@ -2853,9 +2859,23 @@ private:
 \r
             ScopedXLock xlock (display);\r
 \r
-            if (XGetGeometry (display, (::Drawable) windowH, &root, &wx, &wy, &ww, &wh, &bw, &bitDepth) && parentWindow == 0)\r
-                if (! XTranslateCoordinates (display, windowH, root, 0, 0, &wx, &wy, &child))\r
-                    wx = wy = 0;\r
+            if (XGetGeometry (display, (::Drawable) windowH, &root, &wx, &wy, &ww, &wh, &bw, &bitDepth))\r
+            {\r
+                int rootX = 0, rootY = 0;\r
+\r
+                if (! XTranslateCoordinates (display, windowH, root, 0, 0, &rootX, &rootY, &child))\r
+                    rootX = rootY = 0;\r
+\r
+                if (parentWindow == 0)\r
+                {\r
+                    wx = rootX;\r
+                    wy = rootY;\r
+                }\r
+                else\r
+                {\r
+                    parentScreenPosition = Desktop::getInstance().getDisplays().physicalToLogical (Point<int> (rootX, rootY));\r
+                }\r
+            }\r
 \r
             Rectangle<int> physicalBounds (wx, wy, (int) ww, (int) wh);\r
 \r
index bbc565b72e4f9ebc3ad3608bf6272ba0e9dff177..30817dba04dad2c5140b6c97b25ee2f03d46dd1c 100644 (file)
@@ -465,7 +465,10 @@ void CodeEditorComponent::paint (Graphics& g)
     g.fillAll (findColour (CodeEditorComponent::backgroundColourId));\r
 \r
     auto gutterSize = getGutterSize();\r
-    g.reduceClipRegion (gutterSize, 0, verticalScrollBar.getX() - gutterSize, horizontalScrollBar.getY());\r
+    auto bottom = horizontalScrollBar.isVisible() ? horizontalScrollBar.getY() : getHeight();\r
+    auto right  = verticalScrollBar.isVisible()   ? verticalScrollBar.getX()   : getWidth();\r
+\r
+    g.reduceClipRegion (gutterSize, 0, right - gutterSize, bottom);\r
 \r
     g.setFont (font);\r
 \r
index 3f76c6e1f5e242c010782ec97144affffaec504f..223610516720f4a1f5799ad543d263eb62b2840f 100644 (file)
@@ -35,7 +35,7 @@
 \r
   ID:               juce_gui_extra\r
   vendor:           juce\r
-  version:          5.4.4\r
+  version:          5.4.5\r
   name:             JUCE extended GUI classes\r
   description:      Miscellaneous GUI classes for specialised tasks.\r
   website:          http://www.juce.com/juce\r
index ec98d6249574f705830810fb188a9f84ac3dc6eb..742486a50c226b7697119a3fca7f1bcace8763b6 100644 (file)
@@ -50,7 +50,7 @@ public:
     JUCE_DECLARE_SINGLETON (PushNotifications, false)\r
    #endif\r
 \r
-    //==========================================================================\r
+    //==============================================================================\r
     /** Represents a notification that can be sent or received. */\r
     struct Notification\r
     {\r
@@ -107,7 +107,7 @@ public:
             /**@}*/\r
         };\r
 \r
-        //==========================================================================\r
+        //==============================================================================\r
         /** @name Common fields */\r
         /**@{*/\r
 \r
@@ -149,7 +149,7 @@ public:
 \r
         /**@}*/\r
 \r
-        //==========================================================================\r
+        //==============================================================================\r
         /** @name iOS only fields */\r
         /**@{*/\r
 \r
@@ -161,7 +161,7 @@ public:
 \r
         /**@}*/\r
 \r
-        //==========================================================================\r
+        //==============================================================================\r
         /** @name Android only fields */\r
         /**@{*/\r
 \r
@@ -323,7 +323,7 @@ public:
     };\r
 \r
 \r
-    //==========================================================================\r
+    //==============================================================================\r
     /** Describes settings we want to use for current device. Note that at the\r
         moment this is only used on iOS and partially on OSX.\r
 \r
@@ -438,7 +438,7 @@ public:
     */\r
     void requestSettingsUsed();\r
 \r
-    //==========================================================================\r
+    //==============================================================================\r
     /** Android API level 26 or higher only: Represents notification channel through which\r
         notifications will be sent. Starting from Android API level 26, you should call setupChannels()\r
         at the start of your application, before posting any notifications. Then, when sending notifications,\r
@@ -491,7 +491,7 @@ public:
     */\r
     void setupChannels (const Array<ChannelGroup>& groups, const Array<Channel>& channels);\r
 \r
-    //==========================================================================\r
+    //==============================================================================\r
     /** iOS only: sends an asynchronous request to retrieve a list of notifications that were\r
         scheduled and not yet delivered.\r
 \r
@@ -505,7 +505,7 @@ public:
     /** Unschedules all pending local notifications. iOS only. */\r
     void removeAllPendingLocalNotifications();\r
 \r
-    //==========================================================================\r
+    //==============================================================================\r
     /** Checks whether notifications are enabled for given application.\r
         On iOS and OSX this will always return true, use requestSettingsUsed() instead.\r
     */\r
@@ -535,7 +535,7 @@ public:
     /** Removes all notifications that were delivered. */\r
     void removeAllDeliveredNotifications();\r
 \r
-    //==========================================================================\r
+    //==============================================================================\r
     /** Retrieves current device token. Note, it is not a good idea to cache this token\r
         because it may change in the meantime. Always call this method to get the current\r
         token value.\r
@@ -587,7 +587,7 @@ public:
                               int timeToLive,\r
                               const StringPairArray& additionalData);\r
 \r
-    //==========================================================================\r
+    //==============================================================================\r
     /** Register a listener (ideally on application startup) to receive information about\r
         notifications received and any callbacks to async functions called.\r
     */\r
index 41bd3de2e0e415783058bba72d0d2f3c78208443..9d77b2cb38887b57e6d608a0906b7a70a7f23c71 100644 (file)
@@ -189,7 +189,7 @@ DECLARE_JNI_CLASS_WITH_MIN_SDK (RemoteInputBuilder, "android/app/RemoteInput$Bui
  DECLARE_JNI_CLASS_WITH_MIN_SDK (StatusBarNotification, "android/service/notification/StatusBarNotification", 23)\r
  #undef JNI_CLASS_MEMBERS\r
 \r
-//==========================================================================\r
+//==============================================================================\r
 #if defined(JUCE_FIREBASE_INSTANCE_ID_SERVICE_CLASSNAME)\r
  #define JNI_CLASS_MEMBERS(METHOD, STATICMETHOD, FIELD, STATICFIELD, CALLBACK) \\r
    STATICMETHOD (getInstance, "getInstance", "()Lcom/google/firebase/iid/FirebaseInstanceId;") \\r
@@ -265,7 +265,7 @@ bool PushNotifications::Notification::isValid() const noexcept
     return isValidForPreApi26;\r
 }\r
 \r
-//==========================================================================\r
+//==============================================================================\r
 struct PushNotifications::Pimpl\r
 {\r
     Pimpl (PushNotifications& p)\r
@@ -287,7 +287,7 @@ struct PushNotifications::Pimpl
         return true;\r
     }\r
 \r
-    //==========================================================================\r
+    //==============================================================================\r
     void sendLocalNotification (const PushNotifications::Notification& n)\r
     {\r
         // All required fields have to be setup!\r
@@ -434,7 +434,7 @@ struct PushNotifications::Pimpl
         }\r
     }\r
 \r
-    //==========================================================================\r
+    //==============================================================================\r
     String getDeviceToken() const\r
     {\r
       #if defined(JUCE_FIREBASE_INSTANCE_ID_SERVICE_CLASSNAME)\r
@@ -460,7 +460,7 @@ struct PushNotifications::Pimpl
       #endif\r
     }\r
 \r
-    //==========================================================================\r
+    //==============================================================================\r
     void subscribeToTopic (const String& topic)\r
     {\r
       #if defined(JUCE_FIREBASE_MESSAGING_SERVICE_CLASSNAME)\r
index 484f271a624de30cdcc9d0babf5c2a6371e0fe07..f6d3253a18aa8e49db60137ef77fe3c3da5153f5 100644 (file)
@@ -457,6 +457,10 @@ public:
         }\r
 \r
         receiver.reset (new CommandReceiver (this, inChannel));\r
+\r
+        pfds.push_back ({ threadControl[0],  POLLIN, 0 });\r
+        pfds.push_back ({ receiver->getFd(), POLLIN, 0 });\r
+\r
         startThread();\r
 \r
         xembed.reset (new XEmbedComponent (windowHandle));\r
@@ -602,17 +606,10 @@ private:
 \r
             receiver->tryNextRead();\r
 \r
-            fd_set set;\r
-            FD_ZERO (&set);\r
-            FD_SET (threadControl[0],  &set);\r
-            FD_SET (receiver->getFd(), &set);\r
-\r
-            int max_fd = jmax (threadControl[0], receiver->getFd());\r
-\r
             int result = 0;\r
 \r
             while (result == 0 || (result < 0 && errno == EINTR))\r
-                result = select (max_fd + 1, &set, nullptr, nullptr, nullptr);\r
+                result = poll (&pfds.front(), static_cast<nfds_t> (pfds.size()), 0);\r
 \r
             if (result < 0)\r
                 break;\r
@@ -702,6 +699,7 @@ private:
     int threadControl[2];\r
     std::unique_ptr<XEmbedComponent> xembed;\r
     WaitableEvent threadBlocker;\r
+    std::vector<pollfd> pfds;\r
 };\r
 \r
 //==============================================================================\r
index d7343c38e719435c6a0d3ccb9ecf7367cc06c402..19f67c98c3e8209211b0708b952dc5666745b52b 100644 (file)
@@ -35,7 +35,7 @@
 \r
   ID:               juce_opengl\r
   vendor:           juce\r
-  version:          5.4.4\r
+  version:          5.4.5\r
   name:             JUCE OpenGL classes\r
   description:      Classes for rendering OpenGL in a JUCE window.\r
   website:          http://www.juce.com/juce\r
index 1b6f08821b45a290932012ea11a33ea8bc2c2654..9850c1154af6fdbddc39e0992db23225373ba5be 100644 (file)
@@ -296,6 +296,8 @@ public:
                 transform = AffineTransform::scale ((float) newArea.getWidth()  / (float) localBounds.getWidth(),\r
                                                     (float) newArea.getHeight() / (float) localBounds.getHeight());\r
 \r
+                nativeContext->updateWindowPosition (peer->getAreaCoveredBy (component));\r
+\r
                 if (canTriggerUpdate)\r
                     invalidateAll();\r
             }\r
index 179d9b3af005474c1ab40ea487a60571f65ad7b6..23235a68988c6439bb25374f8e0fe0a67920b9a1 100644 (file)
@@ -40,7 +40,11 @@ public:
 \r
     bool initialise()\r
     {\r
-        return frameBuffer.initialise (context, width, height);\r
+        if (! frameBuffer.initialise (context, width, height))\r
+            return false;\r
+\r
+        frameBuffer.clear (Colours::transparentBlack);\r
+        return true;\r
     }\r
 \r
     std::unique_ptr<LowLevelGraphicsContext> createLowLevelContext() override\r
@@ -53,7 +57,12 @@ public:
 \r
     ImagePixelData::Ptr clone() override\r
     {\r
-        Image newImage (*new OpenGLFrameBufferImage (context, width, height));\r
+        std::unique_ptr<OpenGLFrameBufferImage> im (new OpenGLFrameBufferImage (context, width, height));\r
+\r
+        if (! im->initialise())\r
+            return ImagePixelData::Ptr();\r
+\r
+        Image newImage (im.release());\r
         Graphics g (newImage);\r
         g.drawImageAt (Image (*this), 0, 0, false);\r
 \r
@@ -192,7 +201,6 @@ ImagePixelData::Ptr OpenGLImageType::create (Image::PixelFormat, int width, int
     if (! im->initialise())\r
         return ImagePixelData::Ptr();\r
 \r
-    im->frameBuffer.clear (Colours::transparentBlack);\r
     return *im.release();\r
 }\r
 \r
index 69740dfe2d0f95d1f8c314df19b5c40beb6f359e..e4edc3d90eb63c6f0577406d98de30e9173eace7 100644 (file)
@@ -35,7 +35,7 @@
 \r
   ID:               juce_osc\r
   vendor:           juce\r
-  version:          5.4.4\r
+  version:          5.4.5\r
   name:             JUCE OSC classes\r
   description:      Open Sound Control implementation.\r
   website:          http://www.juce.com/juce\r
index d06dc64ea41b99a321ac21abcd36499f66b0ec1f..35033642d843a2aa8d80b5b29fec39422cbe71b1 100644 (file)
@@ -35,7 +35,7 @@
 \r
   ID:               juce_product_unlocking\r
   vendor:           juce\r
-  version:          5.4.4\r
+  version:          5.4.5\r
   name:             JUCE Online marketplace support\r
   description:      Classes for online product authentication\r
   website:          http://www.juce.com/juce\r
index 1e12c76cafbf7a972ed207ff72384638776ebc00..dc1fd76092d32015c333890dbd22c7d0db563b24 100644 (file)
@@ -36,7 +36,7 @@
 \r
   ID:               juce_video\r
   vendor:           juce\r
-  version:          5.4.4\r
+  version:          5.4.5\r
   name:             JUCE video playback and capture classes\r
   description:      Classes for playing video and capturing camera input.\r
   website:          http://www.juce.com/juce\r
@@ -57,7 +57,7 @@
 //==============================================================================\r
 #include <juce_gui_extra/juce_gui_extra.h>\r
 \r
-//=============================================================================\r
+//==============================================================================\r
 /** Config: JUCE_USE_CAMERA\r
     Enables camera support using the CameraDevice class (Mac, Windows, iOS, Android).\r
 */\r
@@ -79,7 +79,7 @@
  #undef JUCE_USE_CAMERA\r
 #endif\r
 \r
-//=============================================================================\r
+//==============================================================================\r
 /** Config: JUCE_SYNC_VIDEO_VOLUME_WITH_OS_MEDIA_VOLUME\r
     Enables synchronisation between video playback volume and OS media volume.\r
     Currently supported on Android only.\r
@@ -98,6 +98,6 @@
  #define JUCE_VIDEO_LOG(x) {}\r
 #endif\r
 \r
-//=============================================================================\r
+//==============================================================================\r
 #include "playback/juce_VideoComponent.h"\r
 #include "capture/juce_CameraDevice.h"\r
index 7c7beeadccc0c1ebfc905befa1662b84dfb1741f..5b64a881ca1e54ab8bf14ddeb9e748b4d9c1f91c 100644 (file)
@@ -1032,7 +1032,7 @@ private:
             }\r
 \r
         private:\r
-            //=============================================================================\r
+            //==============================================================================\r
             struct StateInfo\r
             {\r
                 int playbackStateFlag = 0, allowedActions = 0;\r
index 2e3e4a19aa5a0dc264831ee7a14a6c298b0107f0..b162ba29c4969f8aa5699210abd8b5772099564b 100644 (file)
@@ -26,7 +26,7 @@
 \r
 namespace VideoRenderers\r
 {\r
-    //======================================================================\r
+    //==============================================================================\r
     struct Base\r
     {\r
         virtual ~Base() {}\r
@@ -39,7 +39,7 @@ namespace VideoRenderers
         virtual HRESULT getVideoSize (long& videoWidth, long& videoHeight) = 0;\r
     };\r
 \r
-    //======================================================================\r
+    //==============================================================================\r
     struct VMR7  : public Base\r
     {\r
         VMR7() {}\r
@@ -99,7 +99,7 @@ namespace VideoRenderers
     };\r
 \r
 \r
-    //======================================================================\r
+    //==============================================================================\r
     struct EVR  : public Base\r
     {\r
         EVR() {}\r
@@ -390,7 +390,7 @@ private:
 \r
     std::unique_ptr<ComponentWatcher> componentWatcher;\r
 \r
-    //======================================================================\r
+    //==============================================================================\r
     struct DirectShowContext    : public AsyncUpdater\r
     {\r
         DirectShowContext (Pimpl& c)  : component (c)\r
@@ -404,7 +404,7 @@ private:
             CoUninitialize();\r
         }\r
 \r
-        //======================================================================\r
+        //==============================================================================\r
         void updateWindowPosition (const Rectangle<int>& newBounds)\r
         {\r
             nativeWindow->setWindowPosition (newBounds);\r
@@ -415,7 +415,7 @@ private:
             nativeWindow->showWindow (shouldBeVisible);\r
         }\r
 \r
-        //======================================================================\r
+        //==============================================================================\r
         void repaint()\r
         {\r
             if (hasVideo)\r
@@ -434,7 +434,7 @@ private:
                 videoRenderer->displayModeChanged();\r
         }\r
 \r
-        //======================================================================\r
+        //==============================================================================\r
         void peerChanged()\r
         {\r
             deleteNativeWindow();\r
@@ -489,7 +489,7 @@ private:
             triggerAsyncUpdate();\r
         }\r
 \r
-        //======================================================================\r
+        //==============================================================================\r
         Result loadFile (const String& fileOrURLPath)\r
         {\r
             jassert (state == uninitializedState);\r
@@ -668,7 +668,7 @@ private:
             }\r
         }\r
 \r
-        //======================================================================\r
+        //==============================================================================\r
         void play()\r
         {\r
             mediaControl->Run();\r
@@ -687,7 +687,7 @@ private:
             state = pausedState;\r
         }\r
 \r
-        //======================================================================\r
+        //==============================================================================\r
         Rectangle<int> getVideoSize() const noexcept\r
         {\r
             long width = 0, height = 0;\r
@@ -698,7 +698,7 @@ private:
             return { (int) width, (int) height };\r
         }\r
 \r
-        //======================================================================\r
+        //==============================================================================\r
         double getDuration() const\r
         {\r
             REFTIME duration;\r
@@ -744,7 +744,7 @@ private:
         State state = uninitializedState;\r
 \r
     private:\r
-        //======================================================================\r
+        //==============================================================================\r
         enum { graphEventID = WM_APP + 0x43f0 };\r
 \r
         Pimpl& component;\r
@@ -762,7 +762,7 @@ private:
 \r
         bool hasVideo = false, needToUpdateViewport = true, needToRecreateNativeWindow = false;\r
 \r
-        //======================================================================\r
+        //==============================================================================\r
         bool createNativeWindow()\r
         {\r
             jassert (nativeWindow == nullptr);\r
@@ -839,7 +839,7 @@ private:
             return false;\r
         }\r
 \r
-        //======================================================================\r
+        //==============================================================================\r
         struct NativeWindowClass   : private DeletedAtShutdown\r
         {\r
             bool isRegistered() const noexcept              { return atom != 0; }\r
@@ -899,7 +899,7 @@ private:
             JUCE_DECLARE_NON_COPYABLE (NativeWindowClass)\r
         };\r
 \r
-        //======================================================================\r
+        //==============================================================================\r
         struct NativeWindow\r
         {\r
             NativeWindow (HWND parentToAddTo, void* userData)\r
index 07ce04f31bf86788202732f6d504c893d4931a3a..8d01e1b54b75872a5e3f68cfe446e35b2c15324b 100644 (file)
@@ -51,29 +51,12 @@ VideoComponent::~VideoComponent()
 \r
 Result VideoComponent::load (const File& file)\r
 {\r
-   #if JUCE_ANDROID || JUCE_IOS\r
-    ignoreUnused (file);\r
-    jassertfalse;\r
-    return Result::fail ("load() is not supported on this platform. Use loadAsync() instead.");\r
-   #else\r
-    auto r = pimpl->load (file);\r
-    resized();\r
-    return r;\r
-   #endif\r
+    return loadInternal (file, false);\r
 }\r
 \r
 Result VideoComponent::load (const URL& url)\r
 {\r
-   #if JUCE_ANDROID || JUCE_IOS\r
-    // You need to use loadAsync on Android & iOS.\r
-    ignoreUnused (url);\r
-    jassertfalse;\r
-    return Result::fail ("load() is not supported on this platform. Use loadAsync() instead.");\r
-   #else\r
-    auto r = pimpl->load (url);\r
-    resized();\r
-    return r;\r
-   #endif\r
+    return loadInternal (url, false);\r
 }\r
 \r
 void VideoComponent::loadAsync (const URL& url, std::function<void(const URL&, Result)> callback)\r
@@ -87,7 +70,7 @@ void VideoComponent::loadAsync (const URL& url, std::function<void(const URL&, R
    #if JUCE_ANDROID || JUCE_IOS || JUCE_MAC\r
     pimpl->loadAsync (url, callback);\r
    #else\r
-    auto result = load (url);\r
+    auto result = loadInternal (url, true);\r
     callback (url, result);\r
    #endif\r
 }\r
@@ -158,6 +141,27 @@ void VideoComponent::timerCallback()
     resized();\r
 }\r
 \r
+template<class FileOrURL>\r
+Result VideoComponent::loadInternal (const FileOrURL& fileOrUrl, bool loadAsync)\r
+{\r
+   #if JUCE_ANDROID || JUCE_IOS\r
+    ignoreUnused (fileOrUrl, loadAsync);\r
+\r
+    // You need to use loadAsync on Android & iOS.\r
+    jassertfalse;\r
+    return Result::fail ("load() is not supported on this platform. Use loadAsync() instead.");\r
+   #else\r
+    auto result = pimpl->load (fileOrUrl);\r
+\r
+    if (loadAsync)\r
+        startTimer (50);\r
+    else\r
+       resized();\r
+\r
+    return result;\r
+   #endif\r
+}\r
+\r
 #endif\r
 \r
 } // namespace juce\r
index a41c169f786a36fbc31bdbcce454444c65fa4032..99f0a1473f4f6890d6e474bf665893e1dde3750e 100644 (file)
@@ -179,6 +179,9 @@ private:
     void resized() override;\r
     void timerCallback() override;\r
 \r
+    template<class FileOrURL>\r
+    Result loadInternal (const FileOrURL&, bool);\r
+\r
     JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR (VideoComponent)\r
 };\r
 \r