diff --git a/CMakeLists.txt b/CMakeLists.txt index 6524c5e8c..e8c28db2a 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -81,8 +81,7 @@ list(APPEND OLIVE_LIBRARIES ${OPENEXR_LIBRARIES}) list(APPEND OLIVE_INCLUDE_DIRS ${OPENEXR_INCLUDES}) # Link Qt 5 -find_package(Qt5 5.6 REQUIRED - COMPONENTS +set(QT_LIBRARIES Core Gui Widgets @@ -90,8 +89,15 @@ find_package(Qt5 5.6 REQUIRED Svg LinguistTools Concurrent +) +if (UNIX AND NOT APPLE) + list(APPEND QT_LIBRARIES DBus) +endif() +find_package(Qt5 5.6 REQUIRED + COMPONENTS + ${QT_LIBRARIES} OPTIONAL_COMPONENTS - Network + Network ) if (NOT Qt5Network_FOUND) message(" Qt5::Network module not found, crash reporting will be disabled.") @@ -156,6 +162,12 @@ else() endif() endif() +if (APPLE) + list(APPEND OLIVE_LIBRARIES "-framework IOKit") +elseif(UNIX) + list(APPEND OLIVE_LIBRARIES Qt5::DBus) +endif() + # Generate Git hash set(PROJECT_LONG_VERSION ${PROJECT_VERSION}) if(EXISTS "${CMAKE_SOURCE_DIR}/.git") diff --git a/app/node/generator/text/text.cpp b/app/node/generator/text/text.cpp index bbd1e4f6b..f43908399 100644 --- a/app/node/generator/text/text.cpp +++ b/app/node/generator/text/text.cpp @@ -170,7 +170,7 @@ void TextGenerator::GenerateFrame(FramePtr frame, const GenerateJob& job) const // Transplant alpha channel to frame Color rgba = job.GetValue(kColorInput).data().value(); #if defined(Q_PROCESSOR_X86) || defined(Q_PROCESSOR_ARM) - __m128 sse_color = _mm_load_ps(rgba.data()); + __m128 sse_color = _mm_loadu_ps(rgba.data()); #endif float *frame_dst = reinterpret_cast(frame->data()); diff --git a/app/node/math/trigonometry/trigonometry.cpp b/app/node/math/trigonometry/trigonometry.cpp index d60087621..3899cc6e4 100644 --- a/app/node/math/trigonometry/trigonometry.cpp +++ b/app/node/math/trigonometry/trigonometry.cpp @@ -74,6 +74,8 @@ void TrigonometryNode::Retranslate() SetComboBoxStrings(kMethodIn, strings); SetInputName(kMethodIn, tr("Method")); + + SetInputName(kXIn, tr("Value")); } void TrigonometryNode::Value(const NodeValueRow &value, const NodeGlobals &globals, NodeValueTable *table) const diff --git a/app/render/previewautocacher.cpp b/app/render/previewautocacher.cpp index 03a94efd9..2c121745d 100644 --- a/app/render/previewautocacher.cpp +++ b/app/render/previewautocacher.cpp @@ -730,9 +730,9 @@ void PreviewAutoCacher::RequeueFrames() delayed_requeue_timer_.stop(); if (viewer_node_ + && (viewer_node_->GetVideoAutoCacheEnabled() || use_custom_range_) && viewer_node_->video_frame_cache()->HasInvalidatedRanges(viewer_node_->GetVideoLength()) && hash_tasks_.isEmpty() - && (viewer_node_->GetVideoAutoCacheEnabled() || use_custom_range_) && !IsRenderingCustomRange()) { TimeRange using_range = use_custom_range_ ? custom_autocache_range_ : cache_range_; @@ -743,11 +743,13 @@ void PreviewAutoCacher::RequeueFrames() emit StopCacheProxyTasks(); - CustomCacheTask *cct = new CustomCacheTask(viewer_node_->GetLabelOrName()); - connect(this, &PreviewAutoCacher::StopCacheProxyTasks, cct, &CustomCacheTask::Finish); - connect(this, &PreviewAutoCacher::SignalCacheProxyTaskProgress, cct, &CustomCacheTask::ProgressChanged); - connect(cct, &CustomCacheTask::Cancelled, this, &PreviewAutoCacher::CacheProxyTaskCancelled); - TaskManager::instance()->AddTask(cct); + if (use_custom_range_) { + CustomCacheTask *cct = new CustomCacheTask(viewer_node_->GetLabelOrName()); + connect(this, &PreviewAutoCacher::StopCacheProxyTasks, cct, &CustomCacheTask::Finish); + connect(this, &PreviewAutoCacher::SignalCacheProxyTaskProgress, cct, &CustomCacheTask::ProgressChanged); + connect(cct, &CustomCacheTask::Cancelled, this, &PreviewAutoCacher::CacheProxyTaskCancelled); + TaskManager::instance()->AddTask(cct); + } use_custom_range_ = false; diff --git a/app/task/export/export.cpp b/app/task/export/export.cpp index 8c4f50c82..93c7d251c 100644 --- a/app/task/export/export.cpp +++ b/app/task/export/export.cpp @@ -36,6 +36,8 @@ ExportTask::ExportTask(ViewerOutput *viewer_node, // Adjust video params to have no divider VideoParams vp = viewer_node->GetVideoParams(); vp.set_divider(1); + vp.set_time_base(params.video_params().time_base()); + vp.set_frame_rate(params.video_params().frame_rate()); set_video_params(vp); set_audio_params(viewer_node->GetAudioParams()); diff --git a/app/widget/playbackcontrols/playbackcontrols.cpp b/app/widget/playbackcontrols/playbackcontrols.cpp index 80bae6381..db318ab98 100644 --- a/app/widget/playbackcontrols/playbackcontrols.cpp +++ b/app/widget/playbackcontrols/playbackcontrols.cpp @@ -39,7 +39,7 @@ PlaybackControls::PlaybackControls(QWidget *parent) : lower_control_layout->setSpacing(0); lower_control_layout->setMargin(0); - QSizePolicy lower_container_size_policy(QSizePolicy::Minimum, QSizePolicy::Expanding); + QSizePolicy lower_container_size_policy(QSizePolicy::Maximum, QSizePolicy::Expanding); lower_container_size_policy.setHorizontalStretch(1); // In the lower-left, we create a current timecode label wrapped in a QWidget for fixed sizing diff --git a/app/widget/viewer/CMakeLists.txt b/app/widget/viewer/CMakeLists.txt index 23b401cfe..345702e69 100644 --- a/app/widget/viewer/CMakeLists.txt +++ b/app/widget/viewer/CMakeLists.txt @@ -26,6 +26,8 @@ set(OLIVE_SOURCES widget/viewer/viewerdisplay.h widget/viewer/viewerplaybacktimer.cpp widget/viewer/viewerplaybacktimer.h + widget/viewer/viewerpreventsleep.cpp + widget/viewer/viewerpreventsleep.h widget/viewer/viewerqueue.h widget/viewer/viewersafemargininfo.h widget/viewer/viewersizer.cpp diff --git a/app/widget/viewer/viewer.cpp b/app/widget/viewer/viewer.cpp index fc9c4bb1b..d883a8383 100644 --- a/app/widget/viewer/viewer.cpp +++ b/app/widget/viewer/viewer.cpp @@ -30,10 +30,6 @@ #include #include -#ifdef _WIN32 -#include "winbase.h" -#endif - #include "audio/audiomanager.h" #include "common/clamp.h" #include "common/power.h" @@ -44,6 +40,7 @@ #include "node/project/project.h" #include "render/rendermanager.h" #include "task/taskmanager.h" +#include "viewerpreventsleep.h" #include "widget/menu/menu.h" #include "window/mainwindow/mainwindow.h" @@ -436,7 +433,7 @@ void ViewerWidget::QueueNextAudioBuffer() // Clamp queue end by zero and the audio length queue_end = clamp(queue_end, rational(0), GetConnectedNode()->GetAudioLength()); - if (queue_end == audio_playback_queue_time_) { + if (queue_end <= audio_playback_queue_time_) { // This will queue nothing, so stop the loop here if (prequeuing_audio_) { DecrementPrequeuedAudio(); @@ -483,8 +480,6 @@ void ViewerWidget::ReceivedAudioBufferForPlayback() if (prequeuing_audio_) { // Add to prequeued audio buffer prequeued_audio_.append(pack); - - DecrementPrequeuedAudio(); } else { // Push directly to audio manager AudioManager::instance()->PushToOutput(GetConnectedNode()->GetAudioParams(), pack); @@ -493,6 +488,10 @@ void ViewerWidget::ReceivedAudioBufferForPlayback() } } + if (prequeuing_audio_) { + DecrementPrequeuedAudio(); + } + delete watcher; } } @@ -707,9 +706,7 @@ void ViewerWidget::PlayInternal(int speed, bool in_to_out_only) } } // Force screen to stay awake -#ifdef _WIN32 - SetThreadExecutionState(ES_DISPLAY_REQUIRED | ES_CONTINUOUS); -#endif + PreventSleep(true); } void ViewerWidget::PauseInternal() @@ -752,9 +749,7 @@ void ViewerWidget::PauseInternal() prequeuing_audio_ = 0; // Reset screen timeout timer -#ifdef _WIN32 - SetThreadExecutionState(ES_CONTINUOUS); -#endif + PreventSleep(false); } void ViewerWidget::PushScrubbedAudio() diff --git a/app/widget/viewer/viewerpreventsleep.cpp b/app/widget/viewer/viewerpreventsleep.cpp new file mode 100644 index 000000000..42d8c5a0f --- /dev/null +++ b/app/widget/viewer/viewerpreventsleep.cpp @@ -0,0 +1,74 @@ +#include "viewerpreventsleep.h" + +#include + +#if defined(Q_OS_WINDOWS) +#include +#elif defined(Q_OS_MAC) +#include +#elif defined(Q_OS_LINUX) +#include +#endif + +namespace olive { + +#if defined(Q_OS_MAC) +IOPMAssertionID assertionID = 0; +#elif defined(Q_OS_LINUX) + +#endif + +void PreventSleep(bool on) +{ +#if defined(Q_OS_WINDOWS) + SetThreadExecutionState(on ? ES_DISPLAY_REQUIRED | ES_CONTINUOUS : ES_CONTINUOUS); +#elif defined(Q_OS_MAC) + if (on) { + static const CFStringRef reasonForActivity = CFSTR("Video Playback"); + + IOPMAssertionCreateWithName(kIOPMAssertionTypeNoDisplaySleep, + kIOPMAssertionLevelOn, reasonForActivity, &assertionID); + } else if (assertionID) { + IOPMAssertionRelease(assertionID); + assertionID = 0; + } +#elif defined(Q_OS_LINUX) + QDBusConnection bus = QDBusConnection::sessionBus(); + if(bus.isConnected()) { + static const QStringList sleep_services = { + QStringLiteral("org.freedesktop.ScreenSaver"), + //QStringLiteral("org.gnome.SessionManager") + }; + static const QStringList sleep_paths = { + QStringLiteral("/org/freedesktop/ScreenSaver"), + //QStringLiteral("/org/gnome/SessionManager") + }; + static QVector sleep_cookies; + + // Initialize vector to 0 + if (sleep_cookies.isEmpty()) { + sleep_cookies.resize(sleep_services.size()); + sleep_cookies.fill(0); + } + + for (int i=0; i reply; + + if (on) { + reply = interface.call(QStringLiteral("Inhibit"), QStringLiteral("Olive Video Editor"), QStringLiteral("Video Playback")); + } else { + reply = interface.call(QStringLiteral("UnInhibit"), sleep_cookies.at(i)); + } + + if (reply.isValid()) { + sleep_cookies[i] = reply.value(); + } + } + } + } +#endif +} + +} diff --git a/app/widget/viewer/viewerpreventsleep.h b/app/widget/viewer/viewerpreventsleep.h new file mode 100644 index 000000000..482ef3a11 --- /dev/null +++ b/app/widget/viewer/viewerpreventsleep.h @@ -0,0 +1,10 @@ +#ifndef VIEWERPREVENTSLEEP_H +#define VIEWERPREVENTSLEEP_H + +namespace olive { + +void PreventSleep(bool on); + +} + +#endif // VIEWERPREVENTSLEEP_H