From b2a96cca77cee9bde4476aa5d86634abc392755c Mon Sep 17 00:00:00 2001 From: Jonathan Thomas Date: Sat, 7 Dec 2024 11:29:15 -0600 Subject: [PATCH 01/17] Adding debug for audio device initialization for debugging on Windows 11 --- src/Qt/AudioPlaybackThread.cpp | 3 +++ 1 file changed, 3 insertions(+) diff --git a/src/Qt/AudioPlaybackThread.cpp b/src/Qt/AudioPlaybackThread.cpp index 4ad6d825..a85348f3 100644 --- a/src/Qt/AudioPlaybackThread.cpp +++ b/src/Qt/AudioPlaybackThread.cpp @@ -85,6 +85,9 @@ namespace openshot for (const auto n : t->getDeviceNames()) { AudioDeviceInfo device = { t->getTypeName(), n.trim() }; devices.push_back(device); + std::stringstream device_debug; + device_debug << "AudioDeviceManagerSingleton::Instance (iterate audio device name: " << device.name << ")"; + ZmqLogger::Instance()->AppendDebugMethod(device_debug.str(), "rate", rate, "channels", channels); } } From 2a958bc802cd286046717c0b4c9fbb7d0ebbf390 Mon Sep 17 00:00:00 2001 From: Jonathan Thomas Date: Sat, 7 Dec 2024 12:16:17 -0600 Subject: [PATCH 02/17] Adding audio device type to debug --- src/Qt/AudioPlaybackThread.cpp | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/src/Qt/AudioPlaybackThread.cpp b/src/Qt/AudioPlaybackThread.cpp index a85348f3..587743fe 100644 --- a/src/Qt/AudioPlaybackThread.cpp +++ b/src/Qt/AudioPlaybackThread.cpp @@ -81,12 +81,16 @@ namespace openshot // Populate all possible device types and device names (starting with the user's requested settings) std::vector devices{ { requested_device } }; for (const auto t : mgr->getAvailableDeviceTypes()) { + std::stringstream type_debug; + type_debug << "AudioDeviceManagerSingleton::Instance (iterate audio device type: " << t->getTypeName() << ")"; + ZmqLogger::Instance()->AppendDebugMethod(type_debug.str(), "rate", rate, "channels", channels); + t->scanForDevices(); for (const auto n : t->getDeviceNames()) { AudioDeviceInfo device = { t->getTypeName(), n.trim() }; devices.push_back(device); std::stringstream device_debug; - device_debug << "AudioDeviceManagerSingleton::Instance (iterate audio device name: " << device.name << ")"; + device_debug << "AudioDeviceManagerSingleton::Instance (iterate audio device name: " << device.name << ", type: " << t->getTypeName() << ")"; ZmqLogger::Instance()->AppendDebugMethod(device_debug.str(), "rate", rate, "channels", channels); } } From 08e863d757ed7165baa102f85f1710f6c0628811 Mon Sep 17 00:00:00 2001 From: Jonathan Thomas Date: Sun, 8 Dec 2024 14:01:57 -0600 Subject: [PATCH 03/17] Fix thread syntax for JUCE 7.0.8 --- src/Qt/PlayerPrivate.cpp | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/src/Qt/PlayerPrivate.cpp b/src/Qt/PlayerPrivate.cpp index 9bb7fb04..2998e3ee 100644 --- a/src/Qt/PlayerPrivate.cpp +++ b/src/Qt/PlayerPrivate.cpp @@ -49,10 +49,10 @@ namespace openshot // Start the threads if (reader->info.has_audio) - audioPlayback->startThread(8); + audioPlayback->startThread(Priority::highest); if (reader->info.has_video) { - videoCache->startThread(2); - videoPlayback->startThread(4); + videoCache->startThread(Priority::high); + videoPlayback->startThread(Priority::high); } using std::chrono::duration_cast; @@ -179,7 +179,7 @@ namespace openshot if (video_position < 0) return false; stopPlayback(); - startThread(1); + startThread(Priority::normal); return true; } From 3f68bc4dc675470028bfccf4afccd967e4e0d4ae Mon Sep 17 00:00:00 2001 From: Jonathan Thomas Date: Sun, 8 Dec 2024 14:02:23 -0600 Subject: [PATCH 04/17] Temporarily remove win32 and mac builds, to test JUCE 7.0.8 and CXX standard 17 --- .gitlab-ci.yml | 53 -------------------------------------------------- CMakeLists.txt | 2 +- 2 files changed, 1 insertion(+), 54 deletions(-) diff --git a/.gitlab-ci.yml b/.gitlab-ci.yml index d5a5cc2d..78282111 100644 --- a/.gitlab-ci.yml +++ b/.gitlab-ci.yml @@ -38,33 +38,6 @@ linux-builder: tags: - linux-focal -mac-builder: - stage: build-libopenshot - artifacts: - expire_in: 6 months - paths: - - build/install-x64/* - script: - - "curl -O -J -L --header PRIVATE-TOKEN:$ACCESS_TOKEN http://gitlab.openshot.org/OpenShot/libopenshot-audio/-/jobs/artifacts/$CI_COMMIT_REF_NAME/download?job=mac-builder" - - if [ ! -f artifacts.zip ]; then - - "curl -O -J -L --header PRIVATE-TOKEN:$ACCESS_TOKEN http://gitlab.openshot.org/OpenShot/libopenshot-audio/-/jobs/artifacts/develop/download?job=mac-builder" - - fi - - unzip artifacts.zip - - export LIBOPENSHOT_AUDIO_DIR=$CI_PROJECT_DIR/build/install-x64 - - mkdir -p build; cd build; - - cmake -DCMAKE_EXE_LINKER_FLAGS="-stdlib=libc++" -DCMAKE_SHARED_LINKER_FLAGS="-stdlib=libc++" -DCMAKE_VERBOSE_MAKEFILE:BOOL=ON -D"CMAKE_INSTALL_PREFIX:PATH=$CI_PROJECT_DIR/build/install-x64" -DCMAKE_CXX_COMPILER=clang++ -DCMAKE_C_COMPILER=clang -D"CMAKE_BUILD_TYPE:STRING=Release" -D"CMAKE_OSX_SYSROOT=/Applications/Xcode.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX10.11.sdk" -D"CMAKE_OSX_DEPLOYMENT_TARGET=10.9" -DCMAKE_PREFIX_PATH=/usr/local/qt5.15.X/qt5.15/5.15.0/clang_64/ -D"CMAKE_INSTALL_RPATH_USE_LINK_PATH=1" -D"ENABLE_RUBY=0" ../ - - make -j 9 - - make install - - PROJECT_VERSION=$(grep -E '^set\(PROJECT_VERSION_FULL "(.*)' ../CMakeLists.txt | awk '{print $2}' | tr -d '")') - - PROJECT_SO=$(grep -E '^set\(PROJECT_SO_VERSION (.*)' ../CMakeLists.txt | awk '{print $2}' | tr -d ')') - - echo -e "CI_PROJECT_NAME:$CI_PROJECT_NAME\nCI_COMMIT_REF_NAME:$CI_COMMIT_REF_NAME\nCI_COMMIT_SHA:$CI_COMMIT_SHA\nCI_JOB_ID:$CI_JOB_ID\nCI_PIPELINE_ID:$CI_PIPELINE_ID\nVERSION:$PROJECT_VERSION\nSO:$PROJECT_SO" > "install-x64/share/$CI_PROJECT_NAME.env" - - git log $(git describe --tags --abbrev=0 @^)..@ --oneline --pretty=format:"- %C(auto,yellow)%h%C(auto,magenta)% %C(auto,blue)%>(12,trunc)%ad %C(auto,green)%<(25,trunc)%aN%C(auto,reset)%s%C(auto,red)% gD% D" --date=short > "install-x64/share/$CI_PROJECT_NAME.log" - when: always - except: - - tags - tags: - - mac - windows-builder-x64: stage: build-libopenshot artifacts: @@ -92,32 +65,6 @@ windows-builder-x64: tags: - windows -windows-builder-x86: - stage: build-libopenshot - artifacts: - expire_in: 6 months - paths: - - build\install-x86\* - script: - - try { Invoke-WebRequest -Uri "http://gitlab.openshot.org/OpenShot/libopenshot-audio/-/jobs/artifacts/$CI_COMMIT_REF_NAME/download?job=windows-builder-x86" -Headers @{"PRIVATE-TOKEN"="$ACCESS_TOKEN"} -OutFile "artifacts.zip" } catch { $_.Exception.Response.StatusCode.Value__ } - - if (-not (Test-Path "artifacts.zip")) { Invoke-WebRequest -Uri "http://gitlab.openshot.org/OpenShot/libopenshot-audio/-/jobs/artifacts/develop/download?job=windows-builder-x86" -Headers @{"PRIVATE-TOKEN"="$ACCESS_TOKEN"} -OutFile "artifacts.zip" } - - Expand-Archive -Path artifacts.zip -DestinationPath . - - $env:Path = "C:\msys64\mingw32\bin;C:\msys64\usr\bin;C:\msys64\usr\local\bin;" + $env:Path; - - $env:MSYSTEM = "MINGW32" - - cmake -B build -S . -DCMAKE_VERBOSE_MAKEFILE:BOOL=ON -D"babl_DIR=C:/msys64/mingw32" -D"CMAKE_INSTALL_PREFIX:PATH=$CI_PROJECT_DIR\build\install-x86" -D"OpenShotAudio_ROOT=$CI_PROJECT_DIR\build\install-x86" -D"PYTHON_MODULE_PATH=python" -D"RUBY_MODULE_PATH=ruby" -G "MinGW Makefiles" -D"CMAKE_BUILD_TYPE:STRING=Release" -D"CMAKE_CXX_FLAGS=-m32" -D"CMAKE_EXE_LINKER_FLAGS=-Wl,--large-address-aware" -D"CMAKE_C_FLAGS=-m32" - - cmake --build build - - cmake --install build - - $PROJECT_VERSION = (Select-String -Path "CMakeLists.txt" -Pattern '^set\(PROJECT_VERSION_FULL "(.*)\"' | %{$_.Matches.Groups[1].value}) - - $PROJECT_SO = (Select-String -Path "CMakeLists.txt" -Pattern '^set\(PROJECT_SO_VERSION (.*)\)' | %{$_.Matches.Groups[1].value}) - - New-Item -path "build/install-x86/share/" -Name "$CI_PROJECT_NAME.env" -Value "CI_PROJECT_NAME:$CI_PROJECT_NAME`nCI_COMMIT_REF_NAME:$CI_COMMIT_REF_NAME`nCI_COMMIT_SHA:$CI_COMMIT_SHA`nCI_JOB_ID:$CI_JOB_ID`nCI_PIPELINE_ID:$CI_PIPELINE_ID`nVERSION:$PROJECT_VERSION`nSO:$PROJECT_SO" -ItemType file -force - - $PREV_GIT_LABEL=(git describe --tags --abbrev=0 '@^') - - git log "$PREV_GIT_LABEL..@" --oneline --pretty=format:"- %C(auto,yellow)%h%C(auto,magenta)% %C(auto,blue)%>(12,trunc)%ad %C(auto,green)%<(25,trunc)%aN%C(auto,reset)%s%C(auto,red)% gD% D" --date=short > "build/install-x86/share/$CI_PROJECT_NAME.log" - when: always - except: - - tags - tags: - - windows - trigger-pipeline: stage: trigger-openshot-qt script: diff --git a/CMakeLists.txt b/CMakeLists.txt index ae03d98f..2e693b3a 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -97,7 +97,7 @@ if ((${CMAKE_CXX_COMPILER_ID} STREQUAL "GNU") AND endif() #### Set C++ standard level -set(CMAKE_CXX_STANDARD 14) +set(CMAKE_CXX_STANDARD 17) set(CMAKE_CXX_STANDARD_REQUIRED ON) set(CMAKE_CXX_EXTENSIONS OFF) From d0057517ff3fb7995095a75af9124e084f72bc0b Mon Sep 17 00:00:00 2001 From: Jonathan Thomas Date: Sun, 8 Dec 2024 16:32:52 -0600 Subject: [PATCH 05/17] Adding back win 32 build to gitlab ci --- .gitlab-ci.yml | 26 ++++++++++++++++++++++++++ 1 file changed, 26 insertions(+) diff --git a/.gitlab-ci.yml b/.gitlab-ci.yml index 78282111..51a63fd8 100644 --- a/.gitlab-ci.yml +++ b/.gitlab-ci.yml @@ -65,6 +65,32 @@ windows-builder-x64: tags: - windows +windows-builder-x86: + stage: build-libopenshot + artifacts: + expire_in: 6 months + paths: + - build\install-x86\* + script: + - try { Invoke-WebRequest -Uri "http://gitlab.openshot.org/OpenShot/libopenshot-audio/-/jobs/artifacts/$CI_COMMIT_REF_NAME/download?job=windows-builder-x86" -Headers @{"PRIVATE-TOKEN"="$ACCESS_TOKEN"} -OutFile "artifacts.zip" } catch { $_.Exception.Response.StatusCode.Value__ } + - if (-not (Test-Path "artifacts.zip")) { Invoke-WebRequest -Uri "http://gitlab.openshot.org/OpenShot/libopenshot-audio/-/jobs/artifacts/develop/download?job=windows-builder-x86" -Headers @{"PRIVATE-TOKEN"="$ACCESS_TOKEN"} -OutFile "artifacts.zip" } + - Expand-Archive -Path artifacts.zip -DestinationPath . + - $env:Path = "C:\msys64\mingw32\bin;C:\msys64\usr\bin;C:\msys64\usr\local\bin;" + $env:Path; + - $env:MSYSTEM = "MINGW32" + - cmake -B build -S . -DCMAKE_VERBOSE_MAKEFILE:BOOL=ON -D"babl_DIR=C:/msys64/mingw32" -D"CMAKE_INSTALL_PREFIX:PATH=$CI_PROJECT_DIR\build\install-x86" -D"OpenShotAudio_ROOT=$CI_PROJECT_DIR\build\install-x86" -D"PYTHON_MODULE_PATH=python" -D"RUBY_MODULE_PATH=ruby" -G "MinGW Makefiles" -D"CMAKE_BUILD_TYPE:STRING=Release" -D"CMAKE_CXX_FLAGS=-m32" -D"CMAKE_EXE_LINKER_FLAGS=-Wl,--large-address-aware" -D"CMAKE_C_FLAGS=-m32" + - cmake --build build + - cmake --install build + - $PROJECT_VERSION = (Select-String -Path "CMakeLists.txt" -Pattern '^set\(PROJECT_VERSION_FULL "(.*)\"' | %{$_.Matches.Groups[1].value}) + - $PROJECT_SO = (Select-String -Path "CMakeLists.txt" -Pattern '^set\(PROJECT_SO_VERSION (.*)\)' | %{$_.Matches.Groups[1].value}) + - New-Item -path "build/install-x86/share/" -Name "$CI_PROJECT_NAME.env" -Value "CI_PROJECT_NAME:$CI_PROJECT_NAME`nCI_COMMIT_REF_NAME:$CI_COMMIT_REF_NAME`nCI_COMMIT_SHA:$CI_COMMIT_SHA`nCI_JOB_ID:$CI_JOB_ID`nCI_PIPELINE_ID:$CI_PIPELINE_ID`nVERSION:$PROJECT_VERSION`nSO:$PROJECT_SO" -ItemType file -force + - $PREV_GIT_LABEL=(git describe --tags --abbrev=0 '@^') + - git log "$PREV_GIT_LABEL..@" --oneline --pretty=format:"- %C(auto,yellow)%h%C(auto,magenta)% %C(auto,blue)%>(12,trunc)%ad %C(auto,green)%<(25,trunc)%aN%C(auto,reset)%s%C(auto,red)% gD% D" --date=short > "build/install-x86/share/$CI_PROJECT_NAME.log" + when: always + except: + - tags + tags: + - windows + trigger-pipeline: stage: trigger-openshot-qt script: From fad9ae922a35e463566ce3ec6996a968f746b9c3 Mon Sep 17 00:00:00 2001 From: Jonathan Thomas Date: Sun, 8 Dec 2024 16:35:24 -0600 Subject: [PATCH 06/17] Making all thread priorities "high" --- src/Qt/AudioPlaybackThread.cpp | 2 +- src/Qt/PlayerPrivate.cpp | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/src/Qt/AudioPlaybackThread.cpp b/src/Qt/AudioPlaybackThread.cpp index 587743fe..10f6c751 100644 --- a/src/Qt/AudioPlaybackThread.cpp +++ b/src/Qt/AudioPlaybackThread.cpp @@ -267,7 +267,7 @@ namespace openshot audioInstance->audioDeviceManager.addAudioCallback(&player); // Create TimeSliceThread for audio buffering - time_thread.startThread(); + time_thread.startThread(Priority::high); // Connect source to transport transport.setSource( diff --git a/src/Qt/PlayerPrivate.cpp b/src/Qt/PlayerPrivate.cpp index 2998e3ee..222bfd5e 100644 --- a/src/Qt/PlayerPrivate.cpp +++ b/src/Qt/PlayerPrivate.cpp @@ -49,7 +49,7 @@ namespace openshot // Start the threads if (reader->info.has_audio) - audioPlayback->startThread(Priority::highest); + audioPlayback->startThread(Priority::high); if (reader->info.has_video) { videoCache->startThread(Priority::high); videoPlayback->startThread(Priority::high); @@ -179,7 +179,7 @@ namespace openshot if (video_position < 0) return false; stopPlayback(); - startThread(Priority::normal); + startThread(Priority::high); return true; } From bdb501558152693bc6f3285832a946d06d7269d6 Mon Sep 17 00:00:00 2001 From: Jonathan Thomas Date: Sun, 8 Dec 2024 18:24:20 -0600 Subject: [PATCH 07/17] Experimental change in audio thread sleep/waiting when paused --- src/Qt/AudioPlaybackThread.cpp | 24 ++++++++++++++++++------ src/Qt/AudioPlaybackThread.h | 5 +++++ 2 files changed, 23 insertions(+), 6 deletions(-) diff --git a/src/Qt/AudioPlaybackThread.cpp b/src/Qt/AudioPlaybackThread.cpp index 10f6c751..ca63042e 100644 --- a/src/Qt/AudioPlaybackThread.cpp +++ b/src/Qt/AudioPlaybackThread.cpp @@ -25,6 +25,8 @@ #include // for std::this_thread::sleep_for #include // for std::chrono::milliseconds #include +#include +#include using namespace juce; @@ -241,16 +243,21 @@ namespace openshot } } - // Play the audio + // Override Play and Stop to notify of state changes void AudioPlaybackThread::Play() { - // Start playing is_playing = true; + NotifyTransportStateChanged(); } - // Stop the audio void AudioPlaybackThread::Stop() { - // Stop playing is_playing = false; + NotifyTransportStateChanged(); + } + + void AudioPlaybackThread::NotifyTransportStateChanged() + { + std::lock_guard lock(transportMutex); + transportCondition.notify_all(); } // Start audio thread @@ -286,8 +293,13 @@ namespace openshot // Start the transport transport.start(); - while (!threadShouldExit() && transport.isPlaying() && is_playing) - std::this_thread::sleep_for(std::chrono::milliseconds(2)); + while (!threadShouldExit() && transport.isPlaying() && is_playing) { + // Wait until transport state changes or thread should exit + std::unique_lock lock(transportMutex); + transportCondition.wait_for(lock, std::chrono::milliseconds(10), [this]() { + return threadShouldExit() || !transport.isPlaying() || !is_playing; + }); + } // Stop audio and shutdown transport Stop(); diff --git a/src/Qt/AudioPlaybackThread.h b/src/Qt/AudioPlaybackThread.h index 8122e4f0..582e95f1 100644 --- a/src/Qt/AudioPlaybackThread.h +++ b/src/Qt/AudioPlaybackThread.h @@ -86,12 +86,17 @@ public: bool is_playing; juce::TimeSliceThread time_thread; openshot::VideoCacheThread *videoCache; /// The cache thread (for pre-roll checking) + std::mutex transportMutex; + std::condition_variable transportCondition; /// Constructor AudioPlaybackThread(openshot::VideoCacheThread* cache); /// Destructor ~AudioPlaybackThread(); + /// Notify all + void NotifyTransportStateChanged(); + /// Set the current thread's reader void Reader(openshot::ReaderBase *reader); From d1d989639b007129b242bd6d299d6388eaa4c7dd Mon Sep 17 00:00:00 2001 From: Jonathan Thomas Date: Sun, 8 Dec 2024 21:35:33 -0600 Subject: [PATCH 08/17] Debug in AudioReaderSource for Win 11 debugging --- src/AudioReaderSource.cpp | 1 + 1 file changed, 1 insertion(+) diff --git a/src/AudioReaderSource.cpp b/src/AudioReaderSource.cpp index c4d34dde..4570e06d 100644 --- a/src/AudioReaderSource.cpp +++ b/src/AudioReaderSource.cpp @@ -43,6 +43,7 @@ void AudioReaderSource::getNextAudioBlock(const juce::AudioSourceChannelInfo& in } while (remaining_samples > 0) { + std::cout << "AudioReaderSource::getNextAudioBlock: #" << remaining_samples << std::endl; try { // Get current frame object From 339a4919cd8235d35dc49c94cc3c2f7466c7c122 Mon Sep 17 00:00:00 2001 From: Jonathan Thomas Date: Mon, 9 Dec 2024 00:59:07 -0600 Subject: [PATCH 09/17] Debug in AudioReaderSource for Win 11 debugging #2 --- src/AudioReaderSource.cpp | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/AudioReaderSource.cpp b/src/AudioReaderSource.cpp index 4570e06d..207dcfef 100644 --- a/src/AudioReaderSource.cpp +++ b/src/AudioReaderSource.cpp @@ -13,6 +13,7 @@ #include "AudioReaderSource.h" #include "Exceptions.h" #include "Frame.h" +#include "ZmqLogger.h" using namespace std; @@ -43,7 +44,7 @@ void AudioReaderSource::getNextAudioBlock(const juce::AudioSourceChannelInfo& in } while (remaining_samples > 0) { - std::cout << "AudioReaderSource::getNextAudioBlock: #" << remaining_samples << std::endl; + ZmqLogger::Instance()->AppendDebugMethod("AudioReaderSource::getNextAudioBlock", "remaining_samples", remaining_samples); try { // Get current frame object From ad5a600310dd423b5219cceb238e36abe94d9de1 Mon Sep 17 00:00:00 2001 From: Jonathan Thomas Date: Mon, 9 Dec 2024 14:10:36 -0600 Subject: [PATCH 10/17] Experimental audio device manager buffer size of 512 (instead of default). Win 11 seems to use a much larger value. --- src/Qt/AudioPlaybackThread.cpp | 1 + 1 file changed, 1 insertion(+) diff --git a/src/Qt/AudioPlaybackThread.cpp b/src/Qt/AudioPlaybackThread.cpp index ca63042e..81e3c138 100644 --- a/src/Qt/AudioPlaybackThread.cpp +++ b/src/Qt/AudioPlaybackThread.cpp @@ -113,6 +113,7 @@ namespace openshot AudioDeviceManager::AudioDeviceSetup deviceSetup = AudioDeviceManager::AudioDeviceSetup(); deviceSetup.inputChannels = 0; deviceSetup.outputChannels = channels; + deviceSetup.bufferSize = 512; // Loop through common sample rates, starting with the user's requested rate // Not all sample rates are supported by audio devices, for example, many VMs From a25513b813f5526ff4d1f9529ad304f2275e3f90 Mon Sep 17 00:00:00 2001 From: Jonathan Thomas Date: Mon, 9 Dec 2024 15:15:12 -0600 Subject: [PATCH 11/17] Adding default audio buffer size to libopenshot settings, and setting default to 512. Also, adding some debugging output. This will allow users to override the default audio buffer size, to better customize for their system. --- src/AudioReaderSource.cpp | 4 ---- src/Qt/AudioPlaybackThread.cpp | 8 ++++---- src/Settings.h | 3 +++ 3 files changed, 7 insertions(+), 8 deletions(-) diff --git a/src/AudioReaderSource.cpp b/src/AudioReaderSource.cpp index 207dcfef..2c50e873 100644 --- a/src/AudioReaderSource.cpp +++ b/src/AudioReaderSource.cpp @@ -13,8 +13,6 @@ #include "AudioReaderSource.h" #include "Exceptions.h" #include "Frame.h" -#include "ZmqLogger.h" - using namespace std; using namespace openshot; @@ -44,8 +42,6 @@ void AudioReaderSource::getNextAudioBlock(const juce::AudioSourceChannelInfo& in } while (remaining_samples > 0) { - ZmqLogger::Instance()->AppendDebugMethod("AudioReaderSource::getNextAudioBlock", "remaining_samples", remaining_samples); - try { // Get current frame object if (reader) { diff --git a/src/Qt/AudioPlaybackThread.cpp b/src/Qt/AudioPlaybackThread.cpp index 81e3c138..dd7c5f7d 100644 --- a/src/Qt/AudioPlaybackThread.cpp +++ b/src/Qt/AudioPlaybackThread.cpp @@ -59,9 +59,9 @@ namespace openshot std::stringstream constructor_title; constructor_title << "AudioDeviceManagerSingleton::Instance (default audio device type: " << - Settings::Instance()->PLAYBACK_AUDIO_DEVICE_TYPE << ", default audio device name: " << - Settings::Instance()->PLAYBACK_AUDIO_DEVICE_NAME << ")"; - ZmqLogger::Instance()->AppendDebugMethod(constructor_title.str(), "channels", channels); + Settings::Instance()->PLAYBACK_AUDIO_DEVICE_TYPE << ", default audio device name: " << + Settings::Instance()->PLAYBACK_AUDIO_DEVICE_NAME << ")"; + ZmqLogger::Instance()->AppendDebugMethod(constructor_title.str(), "channels", channels, "buffer", Settings::Instance()->PLAYBACK_AUDIO_BUFFER_SIZE); // Get preferred audio device type and name (if any - these can be blank) openshot::AudioDeviceInfo requested_device = {Settings::Instance()->PLAYBACK_AUDIO_DEVICE_TYPE, @@ -113,7 +113,7 @@ namespace openshot AudioDeviceManager::AudioDeviceSetup deviceSetup = AudioDeviceManager::AudioDeviceSetup(); deviceSetup.inputChannels = 0; deviceSetup.outputChannels = channels; - deviceSetup.bufferSize = 512; + deviceSetup.bufferSize = Settings::Instance()->PLAYBACK_AUDIO_BUFFER_SIZE; // Loop through common sample rates, starting with the user's requested rate // Not all sample rates are supported by audio devices, for example, many VMs diff --git a/src/Settings.h b/src/Settings.h index 1ec165fc..e35b2be9 100644 --- a/src/Settings.h +++ b/src/Settings.h @@ -103,6 +103,9 @@ namespace openshot { /// The device type for the playback audio devices std::string PLAYBACK_AUDIO_DEVICE_TYPE = ""; + /// Size of playback buffer before audio playback starts + int PLAYBACK_AUDIO_BUFFER_SIZE = 512; + /// The current install path of OpenShot (needs to be set when using Timeline(path), since certain /// paths depend on the location of OpenShot transitions and files) std::string PATH_OPENSHOT_INSTALL = ""; From d1b6f6648e2f60c6567eac4bc06d0e9cf429969e Mon Sep 17 00:00:00 2001 From: Jonathan Thomas Date: Mon, 9 Dec 2024 22:34:20 -0600 Subject: [PATCH 12/17] Adding back Mac build to Gitlab CI --- .gitlab-ci.yml | 29 ++++++++++++++++++++++++++++- 1 file changed, 28 insertions(+), 1 deletion(-) diff --git a/.gitlab-ci.yml b/.gitlab-ci.yml index 51a63fd8..752af0c4 100644 --- a/.gitlab-ci.yml +++ b/.gitlab-ci.yml @@ -38,6 +38,33 @@ linux-builder: tags: - linux-focal +mac-builder: + stage: build-libopenshot + artifacts: + expire_in: 6 months + paths: + - build/install-x64/* + script: + - "curl -O -J -L --header PRIVATE-TOKEN:$ACCESS_TOKEN http://gitlab.openshot.org/OpenShot/libopenshot-audio/-/jobs/artifacts/$CI_COMMIT_REF_NAME/download?job=mac-builder" + - if [ ! -f artifacts.zip ]; then + - "curl -O -J -L --header PRIVATE-TOKEN:$ACCESS_TOKEN http://gitlab.openshot.org/OpenShot/libopenshot-audio/-/jobs/artifacts/develop/download?job=mac-builder" + - fi + - unzip artifacts.zip + - export LIBOPENSHOT_AUDIO_DIR=$CI_PROJECT_DIR/build/install-x64 + - mkdir -p build; cd build; + - cmake -DCMAKE_EXE_LINKER_FLAGS="-stdlib=libc++" -DCMAKE_SHARED_LINKER_FLAGS="-stdlib=libc++" -DCMAKE_VERBOSE_MAKEFILE:BOOL=ON -D"CMAKE_INSTALL_PREFIX:PATH=$CI_PROJECT_DIR/build/install-x64" -DCMAKE_CXX_COMPILER=clang++ -DCMAKE_C_COMPILER=clang -D"CMAKE_BUILD_TYPE:STRING=Release" -D"CMAKE_OSX_SYSROOT=/Applications/Xcode.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX10.11.sdk" -D"CMAKE_OSX_DEPLOYMENT_TARGET=10.9" -DCMAKE_PREFIX_PATH=/usr/local/qt5.15.X/qt5.15/5.15.0/clang_64/ -D"CMAKE_INSTALL_RPATH_USE_LINK_PATH=1" -D"ENABLE_RUBY=0" ../ + - make -j 9 + - make install + - PROJECT_VERSION=$(grep -E '^set\(PROJECT_VERSION_FULL "(.*)' ../CMakeLists.txt | awk '{print $2}' | tr -d '")') + - PROJECT_SO=$(grep -E '^set\(PROJECT_SO_VERSION (.*)' ../CMakeLists.txt | awk '{print $2}' | tr -d ')') + - echo -e "CI_PROJECT_NAME:$CI_PROJECT_NAME\nCI_COMMIT_REF_NAME:$CI_COMMIT_REF_NAME\nCI_COMMIT_SHA:$CI_COMMIT_SHA\nCI_JOB_ID:$CI_JOB_ID\nCI_PIPELINE_ID:$CI_PIPELINE_ID\nVERSION:$PROJECT_VERSION\nSO:$PROJECT_SO" > "install-x64/share/$CI_PROJECT_NAME.env" + - git log $(git describe --tags --abbrev=0 @^)..@ --oneline --pretty=format:"- %C(auto,yellow)%h%C(auto,magenta)% %C(auto,blue)%>(12,trunc)%ad %C(auto,green)%<(25,trunc)%aN%C(auto,reset)%s%C(auto,red)% gD% D" --date=short > "install-x64/share/$CI_PROJECT_NAME.log" + when: always + except: + - tags + tags: + - mac + windows-builder-x64: stage: build-libopenshot artifacts: @@ -95,7 +122,7 @@ trigger-pipeline: stage: trigger-openshot-qt script: - "curl -X POST -F token=$OPENSHOT_QT_PIPELINE_TOKEN -F ref=$CI_COMMIT_REF_NAME http://gitlab.openshot.org/api/v4/projects/3/trigger/pipeline" - when: always + when: on_success dependencies: [] except: - tags From 5c1431adcc1873060840731fe6b214131d3f9a04 Mon Sep 17 00:00:00 2001 From: Jonathan Thomas Date: Mon, 9 Dec 2024 22:36:07 -0600 Subject: [PATCH 13/17] Adding back Mac build to Gitlab CI #2, targeting SDK 10.14 --- .gitlab-ci.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.gitlab-ci.yml b/.gitlab-ci.yml index 752af0c4..2c9a47b1 100644 --- a/.gitlab-ci.yml +++ b/.gitlab-ci.yml @@ -52,7 +52,7 @@ mac-builder: - unzip artifacts.zip - export LIBOPENSHOT_AUDIO_DIR=$CI_PROJECT_DIR/build/install-x64 - mkdir -p build; cd build; - - cmake -DCMAKE_EXE_LINKER_FLAGS="-stdlib=libc++" -DCMAKE_SHARED_LINKER_FLAGS="-stdlib=libc++" -DCMAKE_VERBOSE_MAKEFILE:BOOL=ON -D"CMAKE_INSTALL_PREFIX:PATH=$CI_PROJECT_DIR/build/install-x64" -DCMAKE_CXX_COMPILER=clang++ -DCMAKE_C_COMPILER=clang -D"CMAKE_BUILD_TYPE:STRING=Release" -D"CMAKE_OSX_SYSROOT=/Applications/Xcode.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX10.11.sdk" -D"CMAKE_OSX_DEPLOYMENT_TARGET=10.9" -DCMAKE_PREFIX_PATH=/usr/local/qt5.15.X/qt5.15/5.15.0/clang_64/ -D"CMAKE_INSTALL_RPATH_USE_LINK_PATH=1" -D"ENABLE_RUBY=0" ../ + - cmake -DCMAKE_EXE_LINKER_FLAGS="-stdlib=libc++" -DCMAKE_SHARED_LINKER_FLAGS="-stdlib=libc++" -DCMAKE_VERBOSE_MAKEFILE:BOOL=ON -D"CMAKE_INSTALL_PREFIX:PATH=$CI_PROJECT_DIR/build/install-x64" -DCMAKE_CXX_COMPILER=clang++ -DCMAKE_C_COMPILER=clang -D"CMAKE_BUILD_TYPE:STRING=Release" -D"CMAKE_OSX_SYSROOT=/Applications/Xcode.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX10.14.sdk" -D"CMAKE_OSX_DEPLOYMENT_TARGET=10.9" -DCMAKE_PREFIX_PATH=/usr/local/qt5.15.X/qt5.15/5.15.0/clang_64/ -D"CMAKE_INSTALL_RPATH_USE_LINK_PATH=1" -D"ENABLE_RUBY=0" ../ - make -j 9 - make install - PROJECT_VERSION=$(grep -E '^set\(PROJECT_VERSION_FULL "(.*)' ../CMakeLists.txt | awk '{print $2}' | tr -d '")') From 05aaba65573d22884c58d6578701e89053cf840e Mon Sep 17 00:00:00 2001 From: Jonathan Thomas Date: Mon, 9 Dec 2024 22:42:26 -0600 Subject: [PATCH 14/17] Targeting 10.12, using 10.14 SDK due to Catch2 --- .gitlab-ci.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.gitlab-ci.yml b/.gitlab-ci.yml index 2c9a47b1..d67e7056 100644 --- a/.gitlab-ci.yml +++ b/.gitlab-ci.yml @@ -52,7 +52,7 @@ mac-builder: - unzip artifacts.zip - export LIBOPENSHOT_AUDIO_DIR=$CI_PROJECT_DIR/build/install-x64 - mkdir -p build; cd build; - - cmake -DCMAKE_EXE_LINKER_FLAGS="-stdlib=libc++" -DCMAKE_SHARED_LINKER_FLAGS="-stdlib=libc++" -DCMAKE_VERBOSE_MAKEFILE:BOOL=ON -D"CMAKE_INSTALL_PREFIX:PATH=$CI_PROJECT_DIR/build/install-x64" -DCMAKE_CXX_COMPILER=clang++ -DCMAKE_C_COMPILER=clang -D"CMAKE_BUILD_TYPE:STRING=Release" -D"CMAKE_OSX_SYSROOT=/Applications/Xcode.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX10.14.sdk" -D"CMAKE_OSX_DEPLOYMENT_TARGET=10.9" -DCMAKE_PREFIX_PATH=/usr/local/qt5.15.X/qt5.15/5.15.0/clang_64/ -D"CMAKE_INSTALL_RPATH_USE_LINK_PATH=1" -D"ENABLE_RUBY=0" ../ + - cmake -DCMAKE_EXE_LINKER_FLAGS="-stdlib=libc++" -DCMAKE_SHARED_LINKER_FLAGS="-stdlib=libc++" -DCMAKE_VERBOSE_MAKEFILE:BOOL=ON -D"CMAKE_INSTALL_PREFIX:PATH=$CI_PROJECT_DIR/build/install-x64" -DCMAKE_CXX_COMPILER=clang++ -DCMAKE_C_COMPILER=clang -D"CMAKE_BUILD_TYPE:STRING=Release" -D"CMAKE_OSX_SYSROOT=/Applications/Xcode.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX10.14.sdk" -D"CMAKE_OSX_DEPLOYMENT_TARGET=10.12" -DCMAKE_PREFIX_PATH=/usr/local/qt5.15.X/qt5.15/5.15.0/clang_64/ -D"CMAKE_INSTALL_RPATH_USE_LINK_PATH=1" -D"ENABLE_RUBY=0" ../ - make -j 9 - make install - PROJECT_VERSION=$(grep -E '^set\(PROJECT_VERSION_FULL "(.*)' ../CMakeLists.txt | awk '{print $2}' | tr -d '")') From 74d6140bf187261eaadba69c5ec98f624cfc4678 Mon Sep 17 00:00:00 2001 From: Jonathan Thomas Date: Mon, 9 Dec 2024 23:28:59 -0600 Subject: [PATCH 15/17] Fixing Qt string split warning --- src/effects/ObjectDetection.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/effects/ObjectDetection.cpp b/src/effects/ObjectDetection.cpp index 5d45992b..dccada87 100644 --- a/src/effects/ObjectDetection.cpp +++ b/src/effects/ObjectDetection.cpp @@ -411,7 +411,7 @@ void ObjectDetection::SetJsonValue(const Json::Value root) { QString qClassFilter = QString::fromStdString(root["class_filter"].asString()); // Split the QString by commas and automatically trim each resulting string - QStringList classList = qClassFilter.split(',', QString::SkipEmptyParts); + QStringList classList = qClassFilter.split(',', Qt::SkipEmptyParts); display_classes.clear(); // Iterate over the QStringList and add each trimmed, non-empty string From 59774831426767c7688e18fc5d389a918e716eb5 Mon Sep 17 00:00:00 2001 From: Jonathan Thomas Date: Mon, 9 Dec 2024 23:30:46 -0600 Subject: [PATCH 16/17] Fixing GetMinFrame() function to correctly + 1, since our starting frames in OpenShot always begin with 1 (not 0) --- src/Timeline.cpp | 2 +- src/Timeline.h | 2 +- tests/Timeline.cpp | 16 ++++++++-------- 3 files changed, 10 insertions(+), 10 deletions(-) diff --git a/src/Timeline.cpp b/src/Timeline.cpp index ed07e737..eb8031b2 100644 --- a/src/Timeline.cpp +++ b/src/Timeline.cpp @@ -482,7 +482,7 @@ double Timeline::GetMinTime() { int64_t Timeline::GetMinFrame() { double fps = info.fps.ToDouble(); auto min_time = GetMinTime(); - return std::round(min_time * fps); + return std::round(min_time * fps) + 1; } // Apply a FrameMapper to a clip which matches the settings of this timeline diff --git a/src/Timeline.h b/src/Timeline.h index 2072166f..e93d2a7f 100644 --- a/src/Timeline.h +++ b/src/Timeline.h @@ -289,7 +289,7 @@ namespace openshot { /// Look up the position/start time of the first timeline element double GetMinTime(); - /// Look up the start frame number of the first element on the timeline + /// Look up the start frame number of the first element on the timeline (first frame is 1) int64_t GetMinFrame(); /// Close the timeline reader (and any resources it was consuming) diff --git a/tests/Timeline.cpp b/tests/Timeline.cpp index 6e5b8244..fc1115ce 100644 --- a/tests/Timeline.cpp +++ b/tests/Timeline.cpp @@ -676,7 +676,7 @@ TEST_CASE( "GetMinFrame and GetMinTime", "[libopenshot][timeline]" ) t.AddClip(&clip1); CHECK(t.GetMinTime() == Approx(50.0).margin(0.001)); - CHECK(t.GetMinFrame() == 50 * 30); + CHECK(t.GetMinFrame() == (50 * 30) + 1); Clip clip2(path1.str()); clip2.Id("C2"); @@ -686,24 +686,24 @@ TEST_CASE( "GetMinFrame and GetMinTime", "[libopenshot][timeline]" ) t.AddClip(&clip2); CHECK(t.GetMinTime() == Approx(0.0).margin(0.001)); - CHECK(t.GetMinFrame() == 0); + CHECK(t.GetMinFrame() == 1); clip1.Position(80); // Move clip1 to start at 80 seconds clip2.Position(100); // Move clip2 to start at 100 seconds CHECK(t.GetMinTime() == Approx(80.0).margin(0.001)); - CHECK(t.GetMinFrame() == 80 * 30); + CHECK(t.GetMinFrame() == (80 * 30) + 1); clip2.Position(20); // Adjust clip2 to start at 20 seconds CHECK(t.GetMinTime() == Approx(20.0).margin(0.001)); - CHECK(t.GetMinFrame() == 20 * 30); + CHECK(t.GetMinFrame() == (20 * 30) + 1); clip2.End(35); // Adjust clip2 to end at 35 seconds CHECK(t.GetMinTime() == Approx(20.0).margin(0.001)); - CHECK(t.GetMinFrame() == 20 * 30); + CHECK(t.GetMinFrame() == (20 * 30) + 1); t.RemoveClip(&clip1); CHECK(t.GetMinTime() == Approx(20.0).margin(0.001)); - CHECK(t.GetMinFrame() == 20 * 30); + CHECK(t.GetMinFrame() == (20 * 30) + 1); // Update Clip's basic properties with JSON Diff std::stringstream json_change1; @@ -711,7 +711,7 @@ TEST_CASE( "GetMinFrame and GetMinTime", "[libopenshot][timeline]" ) t.ApplyJsonDiff(json_change1.str()); CHECK(t.GetMinTime() == Approx(5.0).margin(0.001)); - CHECK(t.GetMinFrame() == 5 * 30); + CHECK(t.GetMinFrame() == (5 * 30) + 1); // Insert NEW Clip with JSON Diff std::stringstream json_change2; @@ -719,7 +719,7 @@ TEST_CASE( "GetMinFrame and GetMinTime", "[libopenshot][timeline]" ) t.ApplyJsonDiff(json_change2.str()); CHECK(t.GetMinTime() == Approx(5.0).margin(0.001)); - CHECK(t.GetMinFrame() == 5 * 30); + CHECK(t.GetMinFrame() == (5 * 30) + 1); } TEST_CASE( "Multi-threaded Timeline GetFrame", "[libopenshot][timeline]" ) From db73d227eed81a24c907a5658ae47618d3ec12d4 Mon Sep 17 00:00:00 2001 From: Jonathan Thomas Date: Mon, 9 Dec 2024 23:37:59 -0600 Subject: [PATCH 17/17] Another fix for Qt Split, due to older version of Qt on Linux builder. Should be equivalent to Qt::SkipEmptyParts. --- src/effects/ObjectDetection.cpp | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/effects/ObjectDetection.cpp b/src/effects/ObjectDetection.cpp index dccada87..6bc01955 100644 --- a/src/effects/ObjectDetection.cpp +++ b/src/effects/ObjectDetection.cpp @@ -411,7 +411,8 @@ void ObjectDetection::SetJsonValue(const Json::Value root) { QString qClassFilter = QString::fromStdString(root["class_filter"].asString()); // Split the QString by commas and automatically trim each resulting string - QStringList classList = qClassFilter.split(',', Qt::SkipEmptyParts); + QStringList classList = qClassFilter.split(','); + classList.removeAll(""); // Skip empty parts display_classes.clear(); // Iterate over the QStringList and add each trimmed, non-empty string