Merge branch 'master' of git://github.com/olive-editor/olive

This commit is contained in:
production
2019-04-25 20:52:57 +06:00
47 changed files with 13928 additions and 9487 deletions
+2 -2
View File
@@ -8,11 +8,11 @@ if [[ "$TRAVIS_OS_NAME" == "osx" ]]; then
elif [[ "$TRAVIS_OS_NAME" == "linux" ]]; then
if [ "$ARCH" == "x86_64" ]; then
sudo apt-get -y install qt59base qt59multimedia qt59svg libavformat-dev libavcodec-dev libavfilter-dev libavutil-dev libswscale-dev libswresample-dev frei0r-plugins-dev frei0r-plugins fuse curl
sudo apt-get -y install qt59base qt59multimedia qt59svg libavformat-dev libavcodec-dev libavfilter-dev libavutil-dev libswscale-dev libswresample-dev frei0r-plugins-dev fuse curl
fi
if [ "$ARCH" == "i386" ]; then
sudo apt-get -y install gcc-multilib g++-multilib qt59base:i386 qt59multimedia:i386 qt59svg:i386 libavformat-dev:i386 libavcodec-dev:i386 libavfilter-dev:i386 libavutil-dev:i386 libswscale-dev:i386 libswresample-dev:i386 frei0r-plugins-dev:i386 frei0r-plugins:i386 pkg-config:i386 libgl1-mesa-dev:i386 fuse:i386 curl
sudo apt-get -y install gcc-multilib g++-multilib qt59base:i386 qt59multimedia:i386 qt59svg:i386 libavformat-dev:i386 libavcodec-dev:i386 libavfilter-dev:i386 libavutil-dev:i386 libswscale-dev:i386 libswresample-dev:i386 frei0r-plugins-dev:i386 pkg-config:i386 libgl1-mesa-dev:i386 fuse:i386 curl
fi
source /opt/qt*/bin/qt*-env.sh
+480
View File
@@ -0,0 +1,480 @@
cmake_minimum_required(VERSION 3.8 FATAL_ERROR)
project(olive-editor LANGUAGES CXX)
set(CMAKE_CXX_STANDARD 11)
set(CMAKE_CXX_STANDARD_REQUIRED ON)
set(CMAKE_CXX_EXTENSIONS OFF)
set(CMAKE_AUTOMOC ON)
set(CMAKE_AUTOUIC ON)
set(CMAKE_AUTORCC ON)
set(OLIVE_DEFINITIONS -DQT_DEPRECATED_WARNINGS)
list(APPEND CMAKE_MODULE_PATH "${CMAKE_SOURCE_DIR}/cmake")
if(UNIX AND NOT APPLE AND NOT DEFINED OpenGL_GL_PREFERENCE)
set(OpenGL_GL_PREFERENCE LEGACY)
endif()
find_package(OpenGL REQUIRED)
find_package(Qt5 5.7 REQUIRED
COMPONENTS
Core
Gui
Widgets
Multimedia
OpenGL
Svg
LinguistTools
)
find_package(FFMPEG 3.4 REQUIRED
COMPONENTS
avutil
avcodec
avformat
avfilter
swscale
swresample
)
find_package(frei0r)
if(NOT FREI0R_FOUND)
list(APPEND OLIVE_DEFINITIONS -DNOFREI0R)
endif()
if(WIN32)
find_package(OpenColorIO)
if(OPENCOLORIO_FOUND)
list(APPEND OLIVE_DEFINITIONS -DOLIVE_OCIO)
endif()
endif()
if(EXISTS "${CMAKE_SOURCE_DIR}/.git")
find_package(Git)
if(GIT_FOUND)
execute_process(COMMAND ${GIT_EXECUTABLE} log -1 --format=%h
WORKING_DIRECTORY ${CMAKE_SOURCE_DIR}
OUTPUT_VARIABLE GIT_HASH
OUTPUT_STRIP_TRAILING_WHITESPACE
)
endif()
elseif(UNIX AND NOT APPLE)
# Fallback for Ubuntu/Launchpad (extracts Git hash from debian/changelog rather than Git repo)
# (see https://answers.launchpad.net/launchpad/+question/678556)
execute_process(COMMAND sh -c "grep -Po '(?<=-)(([a-z0-9])\\w+)(?=\\+)' -m 1 changelog"
WORKING_DIRECTORY ${CMAKE_SOURCE_DIR}/debian
OUTPUT_VARIABLE GIT_HASH
OUTPUT_STRIP_TRAILING_WHITESPACE
)
endif()
if(DEFINED GIT_HASH)
message("Olive: git hash = " "${GIT_HASH}")
list(APPEND OLIVE_DEFINITIONS -DGITHASH="${GIT_HASH}")
else()
message("Olive: No git hash defined!")
endif()
set(OLIVE_SOURCES
dialogs/aboutdialog.cpp
dialogs/aboutdialog.h
dialogs/actionsearch.cpp
dialogs/actionsearch.h
dialogs/advancedvideodialog.cpp
dialogs/advancedvideodialog.h
dialogs/autocutsilencedialog.cpp
dialogs/autocutsilencedialog.h
dialogs/clippropertiesdialog.cpp
dialogs/clippropertiesdialog.h
dialogs/debugdialog.cpp
dialogs/debugdialog.h
dialogs/demonotice.cpp
dialogs/demonotice.h
dialogs/exportdialog.cpp
dialogs/exportdialog.h
dialogs/loaddialog.cpp
dialogs/loaddialog.h
dialogs/mediapropertiesdialog.cpp
dialogs/mediapropertiesdialog.h
dialogs/newsequencedialog.cpp
dialogs/newsequencedialog.h
dialogs/preferencesdialog.cpp
dialogs/preferencesdialog.h
dialogs/proxydialog.cpp
dialogs/proxydialog.h
dialogs/replaceclipmediadialog.cpp
dialogs/replaceclipmediadialog.h
dialogs/speeddialog.cpp
dialogs/speeddialog.h
dialogs/texteditdialog.cpp
dialogs/texteditdialog.h
effects/fields/boolfield.cpp
effects/fields/boolfield.h
effects/fields/buttonfield.cpp
effects/fields/buttonfield.h
effects/fields/colorfield.cpp
effects/fields/colorfield.h
effects/fields/combofield.cpp
effects/fields/combofield.h
effects/fields/doublefield.cpp
effects/fields/doublefield.h
effects/fields/filefield.cpp
effects/fields/filefield.h
effects/fields/fontfield.cpp
effects/fields/fontfield.h
effects/fields/labelfield.cpp
effects/fields/labelfield.h
effects/fields/stringfield.cpp
effects/fields/stringfield.h
effects/internal/audionoiseeffect.cpp
effects/internal/audionoiseeffect.h
effects/internal/blending.frag
effects/internal/common.vert
effects/internal/cornerpin.frag
effects/internal/cornerpin.vert
effects/internal/cornerpineffect.cpp
effects/internal/cornerpineffect.h
effects/internal/crossdissolvetransition.cpp
effects/internal/crossdissolvetransition.h
effects/internal/cubetransition.h
effects/internal/dropshadow.frag
effects/internal/dropshadoweffect.cpp
effects/internal/dropshadoweffect.h
effects/internal/exponentialfadetransition.cpp
effects/internal/exponentialfadetransition.h
effects/internal/fillleftrighteffect.cpp
effects/internal/fillleftrighteffect.h
effects/internal/frei0reffect.cpp
effects/internal/frei0reffect.h
effects/internal/internalshaders.qrc
effects/internal/linearfadetransition.cpp
effects/internal/linearfadetransition.h
effects/internal/logarithmicfadetransition.cpp
effects/internal/logarithmicfadetransition.h
effects/internal/ocio.frag
effects/internal/paneffect.cpp
effects/internal/paneffect.h
effects/internal/premultiply.frag
effects/internal/richtexteffect.cpp
effects/internal/richtexteffect.h
effects/internal/shakeeffect.cpp
effects/internal/shakeeffect.h
effects/internal/solideffect.cpp
effects/internal/solideffect.h
effects/internal/texteffect.cpp
effects/internal/texteffect.h
effects/internal/timecodeeffect.cpp
effects/internal/timecodeeffect.h
effects/internal/toneeffect.cpp
effects/internal/toneeffect.h
effects/internal/transformeffect.cpp
effects/internal/transformeffect.h
effects/internal/voideffect.cpp
effects/internal/voideffect.h
effects/internal/volumeeffect.cpp
effects/internal/volumeeffect.h
effects/internal/vsthost.cpp
effects/internal/vsthost.h
effects/effect.cpp
effects/effect.h
effects/effectfield.cpp
effects/effectfield.h
effects/effectfields.h
effects/effectgizmo.cpp
effects/effectgizmo.h
effects/effectloaders.cpp
effects/effectloaders.h
effects/effectrow.cpp
effects/effectrow.h
effects/keyframe.cpp
effects/keyframe.h
effects/transition.cpp
effects/transition.h
global/config.cpp
global/config.h
global/debug.cpp
global/debug.h
global/global.cpp
global/global.h
global/math.cpp
global/math.h
global/path.cpp
global/path.h
include/vestige.h
panels/effectcontrols.cpp
panels/effectcontrols.h
panels/grapheditor.cpp
panels/grapheditor.h
panels/panels.cpp
panels/panels.h
panels/project.cpp
panels/project.h
panels/timeline.cpp
panels/timeline.h
panels/viewer.cpp
panels/viewer.h
project/clipboard.cpp
project/clipboard.h
project/footage.cpp
project/footage.h
project/loadthread.cpp
project/loadthread.h
project/media.cpp
project/media.h
project/previewgenerator.cpp
project/previewgenerator.h
project/projectelements.h
project/projectfilter.cpp
project/projectfilter.h
project/projectmodel.cpp
project/projectmodel.h
project/proxygenerator.cpp
project/proxygenerator.h
project/sourcescommon.cpp
project/sourcescommon.h
rendering/audio.cpp
rendering/audio.h
rendering/cacher.cpp
rendering/cacher.h
rendering/clipqueue.cpp
rendering/clipqueue.h
rendering/exportthread.cpp
rendering/exportthread.h
rendering/framebufferobject.cpp
rendering/framebufferobject.h
rendering/renderfunctions.cpp
rendering/renderfunctions.h
rendering/renderthread.cpp
rendering/renderthread.h
timeline/clip.cpp
timeline/clip.h
timeline/marker.cpp
timeline/marker.h
timeline/mediaimportdata.cpp
timeline/mediaimportdata.h
timeline/selection.h
timeline/sequence.cpp
timeline/sequence.h
ui/audiomonitor.cpp
ui/audiomonitor.h
ui/blur.cpp
ui/blur.h
ui/clickablelabel.cpp
ui/clickablelabel.h
ui/collapsiblewidget.cpp
ui/collapsiblewidget.h
ui/columnedgridlayout.cpp
ui/columnedgridlayout.h
ui/colorbutton.cpp
ui/colorbutton.h
ui/comboboxex.cpp
ui/comboboxex.h
ui/cursors.cpp
ui/cursors.h
ui/effectui.cpp
ui/effectui.h
ui/embeddedfilechooser.cpp
ui/embeddedfilechooser.h
ui/flowlayout.cpp
ui/flowlayout.h
ui/focusfilter.cpp
ui/focusfilter.h
ui/fontcombobox.cpp
ui/fontcombobox.h
ui/graphview.cpp
ui/graphview.h
ui/icons.cpp
ui/icons.h
ui/keyframedrawing.cpp
ui/keyframedrawing.h
ui/keyframenavigator.cpp
ui/keyframenavigator.h
ui/keyframeview.cpp
ui/keyframeview.h
ui/labelslider.cpp
ui/labelslider.h
ui/mainwindow.cpp
ui/mainwindow.h
ui/mediaiconservice.cpp
ui/mediaiconservice.h
ui/menu.cpp
ui/menu.h
ui/menuhelper.cpp
ui/menuhelper.h
ui/panel.cpp
ui/panel.h
ui/playbutton.cpp
ui/playbutton.h
ui/rectangleselect.cpp
ui/rectangleselect.h
ui/resizablescrollbar.cpp
ui/resizablescrollbar.h
ui/scrollarea.cpp
ui/scrollarea.h
ui/sourceiconview.cpp
ui/sourceiconview.h
ui/sourcetable.cpp
ui/sourcetable.h
ui/styling.cpp
ui/styling.h
ui/texteditex.cpp
ui/texteditex.h
ui/timelineheader.cpp
ui/timelineheader.h
ui/timelinetools.h
ui/timelinewidget.cpp
ui/timelinewidget.h
ui/updatenotification.cpp
ui/updatenotification.h
ui/viewercontainer.cpp
ui/viewercontainer.h
ui/viewerwidget.cpp
ui/viewerwidget.h
ui/viewerwindow.cpp
ui/viewerwindow.h
undo/comboaction.cpp
undo/comboaction.h
undo/undo.cpp
undo/undo.h
undo/undostack.cpp
undo/undostack.h
main.cpp
)
set(OLIVE_RESOURCES
cursors/cursors.qrc
effects/internal/internalshaders.qrc
icons/icons.qrc
)
set(OLIVE_EFFECTS
effects/shaders/boxblur.frag
effects/shaders/boxblur.xml
effects/shaders/bulge.frag
effects/shaders/bulge.xml
effects/shaders/chromakey.frag
effects/shaders/chromakey.xml
effects/shaders/chromaticaberration.frag
effects/shaders/chromaticaberration.xml
effects/shaders/colorcorrection.frag
effects/shaders/colorcorrection.xml
effects/shaders/colorsel.frag
effects/shaders/colorsel.xml
effects/shaders/common.frag
effects/shaders/common.vert
effects/shaders/crop.frag
effects/shaders/crop.xml
effects/shaders/crossstitch.frag
effects/shaders/crossstitch.xml
effects/shaders/directionalblur.frag
effects/shaders/directionalblur.xml
effects/shaders/dropshadow.xml.disabled
effects/shaders/emboss.frag
effects/shaders/emboss.xml
effects/shaders/findedges.frag
effects/shaders/findedges.xml.disabled
effects/shaders/fisheye.frag
effects/shaders/fisheye.xml
effects/shaders/flip.frag
effects/shaders/flip.xml
effects/shaders/gaussianblur.frag
effects/shaders/gaussianblur.xml
effects/shaders/huesatbri.frag
effects/shaders/huesatbri.xml
effects/shaders/invert.frag
effects/shaders/invert.xml
effects/shaders/lumakey.frag
effects/shaders/lumakey.xml
effects/shaders/noise.frag
effects/shaders/noise.xml
effects/shaders/pixelate.frag
effects/shaders/pixelate.xml
effects/shaders/posterize.frag
effects/shaders/posterize.xml
effects/shaders/radialblur.frag
effects/shaders/radialblur.xml
effects/shaders/ripple.frag
effects/shaders/ripple.xml
effects/shaders/sphere.frag
effects/shaders/sphere.xml
effects/shaders/swirl.frag
effects/shaders/swirl.xml
effects/shaders/tile.frag
effects/shaders/tile.xml
effects/shaders/toonify.frag
effects/shaders/toonify.xml
effects/shaders/vignette.frag
effects/shaders/vignette.xml
effects/shaders/volumetriclight.frag
effects/shaders/volumetriclight.xml
effects/shaders/wave.frag
effects/shaders/wave.xml
)
qt5_add_translation(OLIVE_QM_FILES
ts/olive_ar.ts
ts/olive_bs.ts
ts/olive_cs.ts
ts/olive_de.ts
ts/olive_es.ts
ts/olive_fr.ts
ts/olive_it.ts
ts/olive_ru.ts
ts/olive_sr.ts
ts/olive_id.ts
)
set(OLIVE_TARGET "olive-editor")
if(APPLE)
set(OLIVE_TARGET "Olive")
endif()
add_executable(${OLIVE_TARGET}
${OLIVE_SOURCES}
${OLIVE_RESOURCES}
${OLIVE_EFFECTS}
${OLIVE_QM_FILES}
)
target_compile_definitions(${OLIVE_TARGET} PRIVATE ${OLIVE_DEFINITIONS})
set(CMAKE_INCLUDE_CURRENT_DIR ON)
target_link_libraries(${OLIVE_TARGET}
PRIVATE
OpenGL::GL
Qt5::Core
Qt5::Gui
Qt5::Widgets
Qt5::Multimedia
Qt5::OpenGL
Qt5::Svg
FFMPEG::avutil
FFMPEG::avcodec
FFMPEG::avformat
FFMPEG::avfilter
FFMPEG::swscale
FFMPEG::swresample
)
if(WIN32 AND OPENCOLORIO_FOUND)
target_link_libraries(${OLIVE_TARGET} PRIVATE OpenColorIO)
endif()
if(UNIX AND NOT APPLE)
install(TARGETS ${OLIVE_TARGET} RUNTIME DESTINATION bin)
install(FILES ${OLIVE_EFFECTS} DESTINATION share/olive-editor/effects)
install(FILES packaging/linux/org.olivevideoeditor.Olive.desktop DESTINATION share/applications)
install(FILES packaging/linux/org.olivevideoeditor.Olive.appdata.xml DESTINATION share/metainfo)
install(FILES packaging/linux/org.olivevideoeditor.Olive.xml DESTINATION share/mime/packages)
install(FILES packaging/linux/icons/16x16/org.olivevideoeditor.Olive.png DESTINATION share/icons/hicolor/16x16/apps)
install(FILES packaging/linux/icons/32x32/org.olivevideoeditor.Olive.png DESTINATION share/icons/hicolor/32x32/apps)
install(FILES packaging/linux/icons/48x48/org.olivevideoeditor.Olive.png DESTINATION share/icons/hicolor/48x48/apps)
install(FILES packaging/linux/icons/64x64/org.olivevideoeditor.Olive.png DESTINATION share/icons/hicolor/64x64/apps)
install(FILES packaging/linux/icons/128x128/org.olivevideoeditor.Olive.png DESTINATION share/icons/hicolor/128x128/apps)
install(FILES packaging/linux/icons/256x256/org.olivevideoeditor.Olive.png DESTINATION share/icons/hicolor/256x256/apps)
install(FILES packaging/linux/icons/512x512/org.olivevideoeditor.Olive.png DESTINATION share/icons/hicolor/512x512/apps)
install(FILES ${OLIVE_QM_FILES} DESTINATION share/olive-editor/ts)
endif()
+26 -2
View File
@@ -1,13 +1,37 @@
[If you are requesting a feature, please try to fill out all the information below. If you are reporting a bug, you can clear the template below.]
[If you are reporting a bug, please try to fill out all the information below. If you are requesting a feature, you can clear this template.]
### I have read the following
- [ ] The [Olive Wiki](https://github.com/olive-editor/olive/wiki)
- [ ] Previous issues that include ["FR"](https://github.com/olive-editor/olive/issues?utf8=%E2%9C%93&q=is%3Aissue+is%3Aopen+FR)or ["Feature Request"](https://github.com/olive-editor/olive/issues?utf8=%E2%9C%93&q=is%3Aissue+is%3Aopen+Feature+Request)
- [ ] Olive's [Project Goals](https://github.com/olive-editor/olive/projects)
### Detailed description of the feature request
[Describe the feature request to the best of your ability. Do you know any libraries/sources that can help the Olive Team include the feature?]
### Why should Olive include the feature? What are the benefits?
[Explain the feature's importance to Olive and NLEs in general.]
---
[If you are reporting a bug, please try to fill out all the information below. If you are requesting a feature, you can clear the template above.]
### System Information
**Olive version:** [e.g. Git hash from window title or Help > About]
**Source:** [e.g. AppImage, Website etc.]
**Operating system:** [e.g. Ubuntu 18.04 64-bit]
**CPU:** [e.g. Intel i5-4300U]
**RAM:** [e.g. 8GB]
**GPU:** [e.g. NVIDIA Geforce GT 1030 2GB (Driver ver xxx.xx.xx)]
### Detailed Description
@@ -28,4 +52,4 @@
```
[If you can reproduce this issue, try running Olive through GDB and retrieving a backtrace, then paste the backtrace here. Instructions are available in the Wiki on how to acquire this backtrace.]
```
```
+193
View File
@@ -0,0 +1,193 @@
#[==[
Provides the following variables:
* `FFMPEG_INCLUDE_DIRS`: Include directories necessary to use FFMPEG.
* `FFMPEG_LIBRARIES`: Libraries necessary to use FFMPEG. Note that this only
includes libraries for the components requested.
* `FFMPEG_VERSION`: The version of FFMPEG found.
The following components are supported:
* `avcodec`
* `avdevice`
* `avfilter`
* `avformat`
* `avresample`
* `avutil`
* `swresample`
* `swscale`
For each component, the following are provided:
* `FFMPEG_<component>_FOUND`: Libraries for the component.
* `FFMPEG_<component>_INCLUDE_DIRS`: Include directories for
the component.
* `FFMPEG_<component>_LIBRARIES`: Libraries for the component.
* `FFMPEG::<component>`: A target to use with `target_link_libraries`.
Note that only components requested with `COMPONENTS` or `OPTIONAL_COMPONENTS`
are guaranteed to set these variables or provide targets.
#]==]
function (_ffmpeg_find component headername)
find_path("FFMPEG_${component}_INCLUDE_DIR"
NAMES
"lib${component}/${headername}"
PATHS
"${FFMPEG_ROOT}/include"
~/Library/Frameworks
/Library/Frameworks
/usr/local/include
/usr/include
/sw/include # Fink
/opt/local/include # DarwinPorts
/opt/csw/include # Blastwave
/opt/include
/usr/freeware/include
PATH_SUFFIXES
ffmpeg
DOC "FFMPEG's ${component} include directory")
mark_as_advanced("FFMPEG_${component}_INCLUDE_DIR")
# On Windows, static FFMPEG is sometimes built as `lib<name>.a`.
if (WIN32)
list(APPEND CMAKE_FIND_LIBRARY_SUFFIXES ".a" ".lib")
list(APPEND CMAKE_FIND_LIBRARY_PREFIXES "" "lib")
endif ()
find_library("FFMPEG_${component}_LIBRARY"
NAMES
"${component}"
PATHS
"${FFMPEG_ROOT}/lib"
~/Library/Frameworks
/Library/Frameworks
/usr/local/lib
/usr/local/lib64
/usr/lib
/usr/lib64
/sw/lib
/opt/local/lib
/opt/csw/lib
/opt/lib
/usr/freeware/lib64
"${FFMPEG_ROOT}/bin"
DOC "FFMPEG's ${component} library")
mark_as_advanced("FFMPEG_${component}_LIBRARY")
if (FFMPEG_${component}_LIBRARY AND FFMPEG_${component}_INCLUDE_DIR)
set(_deps_found TRUE)
set(_deps_link)
foreach (_ffmpeg_dep IN LISTS ARGN)
if (TARGET "FFMPEG::${_ffmpeg_dep}")
list(APPEND _deps_link "FFMPEG::${_ffmpeg_dep}")
else ()
set(_deps_found FALSE)
endif ()
endforeach ()
if (_deps_found)
add_library("FFMPEG::${component}" UNKNOWN IMPORTED)
set_target_properties("FFMPEG::${component}" PROPERTIES
IMPORTED_LOCATION "${FFMPEG_${component}_LIBRARY}"
INTERFACE_INCLUDE_DIRECTORIES "${FFMPEG_${component}_INCLUDE_DIR}"
IMPORTED_LINK_INTERFACE_LIBRARIES "${_deps_link}")
set("FFMPEG_${component}_FOUND" 1
PARENT_SCOPE)
set(version_header_path "${FFMPEG_${component}_INCLUDE_DIR}/lib${component}/version.h")
if (EXISTS "${version_header_path}")
string(TOUPPER "${component}" component_upper)
file(STRINGS "${version_header_path}" version
REGEX "#define *LIB${component_upper}_VERSION_(MAJOR|MINOR|MICRO) ")
string(REGEX REPLACE ".*_MAJOR *\([0-9]*\).*" "\\1" major "${version}")
string(REGEX REPLACE ".*_MINOR *\([0-9]*\).*" "\\1" minor "${version}")
string(REGEX REPLACE ".*_MICRO *\([0-9]*\).*" "\\1" micro "${version}")
if (NOT major STREQUAL "" AND
NOT minor STREQUAL "" AND
NOT micro STREQUAL "")
set("FFMPEG_${component}_VERSION" "${major}.${minor}.${micro}"
PARENT_SCOPE)
endif ()
endif ()
else ()
set("FFMPEG_${component}_FOUND" 0
PARENT_SCOPE)
set(what)
if (NOT FFMPEG_${component}_LIBRARY)
set(what "library")
endif ()
if (NOT FFMPEG_${component}_INCLUDE_DIR)
if (what)
string(APPEND what " or headers")
else ()
set(what "headers")
endif ()
endif ()
set("FFMPEG_${component}_NOT_FOUND_MESSAGE"
"Could not find the ${what} for ${component}."
PARENT_SCOPE)
endif ()
endif ()
endfunction ()
_ffmpeg_find(avutil avutil.h)
_ffmpeg_find(avresample avresample.h
avutil)
_ffmpeg_find(swresample swresample.h
avutil)
_ffmpeg_find(swscale swscale.h
avutil)
_ffmpeg_find(avcodec avcodec.h
avutil)
_ffmpeg_find(avformat avformat.h
avcodec avutil)
_ffmpeg_find(avfilter avfilter.h
avutil)
_ffmpeg_find(avdevice avdevice.h
avformat avutil)
if (TARGET FFMPEG::avutil)
set(_ffmpeg_version_header_path "${FFMPEG_avutil_INCLUDE_DIR}/libavutil/ffversion.h")
if (EXISTS "${_ffmpeg_version_header_path}")
file(STRINGS "${_ffmpeg_version_header_path}" _ffmpeg_version
REGEX "FFMPEG_VERSION")
string(REGEX REPLACE ".*\"n?\(.*\)\"" "\\1" FFMPEG_VERSION "${_ffmpeg_version}")
unset(_ffmpeg_version)
else ()
set(FFMPEG_VERSION FFMPEG_VERSION-NOTFOUND)
endif ()
unset(_ffmpeg_version_header_path)
endif ()
set(FFMPEG_INCLUDE_DIRS)
set(FFMPEG_LIBRARIES)
set(_ffmpeg_required_vars)
foreach (_ffmpeg_component IN LISTS FFMPEG_FIND_COMPONENTS)
if (TARGET "FFMPEG::${_ffmpeg_component}")
set(FFMPEG_${_ffmpeg_component}_INCLUDE_DIRS
"${FFMPEG_${_ffmpeg_component}_INCLUDE_DIR}")
set(FFMPEG_${_ffmpeg_component}_LIBRARIES
"${FFMPEG_${_ffmpeg_component}_LIBRARY}")
list(APPEND FFMPEG_INCLUDE_DIRS
"${FFMPEG_${_ffmpeg_component}_INCLUDE_DIRS}")
list(APPEND FFMPEG_LIBRARIES
"${FFMPEG_${_ffmpeg_component}_LIBRARIES}")
if (FFMEG_FIND_REQUIRED_${_ffmpeg_component})
list(APPEND _ffmpeg_required_vars
"FFMPEG_${_ffmpeg_required_vars}_INCLUDE_DIRS"
"FFMPEG_${_ffmpeg_required_vars}_LIBRARIES")
endif ()
endif ()
endforeach ()
unset(_ffmpeg_component)
if (FFMPEG_INCLUDE_DIRS)
list(REMOVE_DUPLICATES FFMPEG_INCLUDE_DIRS)
endif ()
include(FindPackageHandleStandardArgs)
find_package_handle_standard_args(FFMPEG
REQUIRED_VARS FFMPEG_INCLUDE_DIRS FFMPEG_LIBRARIES ${_ffmpeg_required_vars}
VERSION_VAR FFMPEG_VERSION
HANDLE_COMPONENTS)
unset(_ffmpeg_required_vars)
+94
View File
@@ -0,0 +1,94 @@
# - Find OpenColorIO library
# Find the native OpenColorIO includes and library
# This module defines
# OPENCOLORIO_INCLUDE_DIRS, where to find OpenColorIO.h, Set when
# OPENCOLORIO_INCLUDE_DIR is found.
# OPENCOLORIO_LIBRARIES, libraries to link against to use OpenColorIO.
# OPENCOLORIO_ROOT_DIR, The base directory to search for OpenColorIO.
# This can also be an environment variable.
# OPENCOLORIO_FOUND, If false, do not try to use OpenColorIO.
#
# also defined, but not for general use are
# OPENCOLORIO_LIBRARY, where to find the OpenColorIO library.
#=============================================================================
# Copyright 2012 Blender Foundation.
#
# Distributed under the OSI-approved BSD License (the "License");
# see accompanying file Copyright.txt for details.
#
# This software is distributed WITHOUT ANY WARRANTY; without even the
# implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
# See the License for more information.
#=============================================================================
# If OPENCOLORIO_ROOT_DIR was defined in the environment, use it.
IF(NOT OPENCOLORIO_ROOT_DIR AND NOT $ENV{OPENCOLORIO_ROOT_DIR} STREQUAL "")
SET(OPENCOLORIO_ROOT_DIR $ENV{OPENCOLORIO_ROOT_DIR})
ENDIF()
SET(_opencolorio_FIND_COMPONENTS
OpenColorIO
yaml-cpp
tinyxml
)
SET(_opencolorio_SEARCH_DIRS
${OPENCOLORIO_ROOT_DIR}
/usr/local
/sw # Fink
/opt/local # DarwinPorts
/opt/lib/ocio
)
FIND_PATH(OPENCOLORIO_INCLUDE_DIR
NAMES
OpenColorIO/OpenColorIO.h
HINTS
${_opencolorio_SEARCH_DIRS}
PATH_SUFFIXES
include
)
SET(_opencolorio_LIBRARIES)
FOREACH(COMPONENT ${_opencolorio_FIND_COMPONENTS})
STRING(TOUPPER ${COMPONENT} UPPERCOMPONENT)
FIND_LIBRARY(OPENCOLORIO_${UPPERCOMPONENT}_LIBRARY
NAMES
${COMPONENT}
HINTS
${_opencolorio_SEARCH_DIRS}
PATH_SUFFIXES
lib64 lib lib64/static lib/static
)
IF(OPENCOLORIO_${UPPERCOMPONENT}_LIBRARY)
LIST(APPEND _opencolorio_LIBRARIES "${OPENCOLORIO_${UPPERCOMPONENT}_LIBRARY}")
ENDIF()
ENDFOREACH()
# handle the QUIETLY and REQUIRED arguments and set OPENCOLORIO_FOUND to TRUE if
# all listed variables are TRUE
INCLUDE(FindPackageHandleStandardArgs)
FIND_PACKAGE_HANDLE_STANDARD_ARGS(OpenColorIO DEFAULT_MSG
_opencolorio_LIBRARIES OPENCOLORIO_INCLUDE_DIR)
IF(OPENCOLORIO_FOUND)
SET(OPENCOLORIO_LIBRARIES ${_opencolorio_LIBRARIES})
SET(OPENCOLORIO_INCLUDE_DIRS ${OPENCOLORIO_INCLUDE_DIR})
ENDIF(OPENCOLORIO_FOUND)
MARK_AS_ADVANCED(
OPENCOLORIO_INCLUDE_DIR
OPENCOLORIO_LIBRARY
OPENCOLORIO_OPENCOLORIO_LIBRARY
OPENCOLORIO_TINYXML_LIBRARY
OPENCOLORIO_YAML-CPP_LIBRARY
)
UNSET(COMPONENT)
UNSET(UPPERCOMPONENT)
UNSET(_opencolorio_FIND_COMPONENTS)
UNSET(_opencolorio_LIBRARIES)
UNSET(_opencolorio_SEARCH_DIRS)
+42
View File
@@ -0,0 +1,42 @@
# CMake module to search for frei0r
# Author: Rohit Yadav <rohityadav89@gmail.com>
#
# If it's found it sets FREI0R_FOUND to TRUE
# and following variables are set:
# FREI0R_INCLUDE_DIR
# Put here path to custom location
# example: /home/username/frei0r/include etc..
find_path(FREI0R_INCLUDE_DIR NAMES frei0r.h
PATHS
"$ENV{LIB_DIR}/include"
"/usr/include"
"/usr/include/frei0r"
"/usr/local/include"
"/usr/local/include/frei0r"
# Mac OS
"${CMAKE_CURRENT_SOURCE_DIR}/contribs/include"
# MingW
c:/msys/local/include
)
find_path(FREI0R_INCLUDE_DIR PATHS "${CMAKE_INCLUDE_PATH}" NAMES frei0r.h)
# TODO: If required, add code to link to some library
if(FREI0R_INCLUDE_DIR)
set(FREI0R_FOUND TRUE)
endif()
if(FREI0R_FOUND)
if(NOT FREI0R_FIND_QUIETLY)
message(STATUS "Found frei0r include-dir path: ${FREI0R_INCLUDE_DIR}")
endif()
else()
if(FREI0R_FIND_REQUIRED)
message(FATAL_ERROR "Could not find frei0r")
elseif(NOT FREI0R_FIND_QUIETLY)
message(STATUS "Could not find frei0r")
endif()
endif()
+2 -2
View File
@@ -2,12 +2,12 @@ Source: olive-editor
Section: video
Priority: optional
Maintainer: Olive Team <itsmattkc@gmail.com>
Build-Depends: debhelper (>=9), build-essential, qt5-default, qtmultimedia5-dev, libqt5opengl5-dev, libqt5svg5-dev, libqt5multimedia5-plugins, libavformat-dev, libavcodec-dev, libavutil-dev, libswscale-dev, libswresample-dev, libavfilter-dev, libpostproc-dev, git, frei0r-plugins-dev, qttools5-dev-tools
Build-Depends: debhelper (>=9), build-essential, qt5-default, qtmultimedia5-dev, libqt5opengl5-dev, libqt5svg5-dev, libqt5multimedia5-plugins, libavformat-dev, libavcodec-dev, libavutil-dev, libswscale-dev, libswresample-dev, libavfilter-dev, libpostproc-dev, git, frei0r-plugins-dev, qttools5-dev-tools, cmake, qttools5-dev
Standards-Version: 3.9.6
Homepage: https://olivevideoeditor.org/
Package: olive-editor
Architecture: any
Depends: ${misc:Depends}, ${shlibs:Depends}, libqt5multimedia5-plugins, frei0r-plugins
Depends: ${misc:Depends}, ${shlibs:Depends}, libqt5multimedia5-plugins
Description: Nonlinear video editor focused on performance and simplicity
+2
View File
@@ -53,6 +53,8 @@ AboutDialog::AboutDialog(QWidget *parent) :
// Set text formatting
label->setAlignment(Qt::AlignCenter);
label->setTextInteractionFlags(Qt::TextSelectableByMouse);
label->setCursor(Qt::IBeamCursor);
label->setWordWrap(true);
layout->addWidget(label);
+2 -2
View File
@@ -572,11 +572,11 @@ void ExportDialog::StartExport() {
// Close all effects in effect controls (prevents UI threading issues)
panel_effect_controls->Clear();
olive::Global->set_rendering_state(true);
// Close all currently open clips
close_active_clips(olive::ActiveSequence.get());
olive::Global->set_rendering_state(true);
olive::Global->save_autorecovery_file();
prep_ui_for_render(true);
+3 -1
View File
@@ -3,6 +3,8 @@
uniform sampler2D sceneTex; // 0
uniform float lensRadiusX;
uniform float lensRadiusY;
uniform float centerX;
uniform float centerY;
uniform bool circular;
uniform vec2 resolution;
// uniform vec2 lensRadius; // 0.45, 0.38
@@ -20,7 +22,7 @@ void main(void) {
vignetteCoord.x *= ar;
vignetteCoord.x -= (1.0-(1.0/ar));
}
float dist = distance(vignetteCoord, vec2(0.5,0.5));
float dist = distance(vignetteCoord, vec2(0.5 + centerX*0.01, 0.5 + centerY*0.01));
float size = (lensRadiusX*0.01);
c *= smoothstep(size, size*0.99*(1.0-lensRadiusY*0.01), dist);
gl_FragColor = c;
+4
View File
@@ -9,5 +9,9 @@
<row name="Circular">
<field type="bool" default="false" id="circular"/>
</row>
<row name="Center">
<field type="double" default="0" id="centerX"/>
<field type="double" default="0" id="centerY"/>
</row>
<shader vert="common.vert" frag="vignette.frag"/>
</effect>
+6 -1
View File
@@ -78,7 +78,8 @@ Config::Config()
default_sequence_height(1080),
default_sequence_framerate(29.97),
default_sequence_audio_frequency(48000),
default_sequence_audio_channel_layout(3)
default_sequence_audio_channel_layout(3),
locked_panels(false)
{}
void Config::load(QString path) {
@@ -239,6 +240,9 @@ void Config::load(QString path) {
} else if (stream.name() == "DefaultSequenceAudioLayout") {
stream.readNext();
default_sequence_audio_channel_layout = stream.text().toInt();
} else if (stream.name() == "LockedPanels") {
stream.readNext();
locked_panels = (stream.text() == "1");
}
}
}
@@ -313,6 +317,7 @@ void Config::save(QString path) {
stream.writeTextElement("DefaultSequenceFrameRate", QString::number(default_sequence_framerate));
stream.writeTextElement("DefaultSequenceAudioFrequency", QString::number(default_sequence_audio_frequency));
stream.writeTextElement("DefaultSequenceAudioLayout", QString::number(default_sequence_audio_channel_layout));
stream.writeTextElement("LockedPanels", QString::number(locked_panels));
stream.writeEndElement(); // configuration
stream.writeEndDocument(); // doc
+5
View File
@@ -558,6 +558,11 @@ struct Config {
*/
int default_sequence_audio_channel_layout;
/**
* @brief Sets whether panels should load locked or not
*/
bool locked_panels;
/**
* @brief Load config from file
*
+1 -1
View File
@@ -97,7 +97,7 @@ void debug_message_handler(QtMsgType type, const QMessageLogContext &context, co
debug_stream << QString("[%1] %2 (%3:%4, %5)\n")
.arg(msgTag, localMsg, context.file, QString::number(context.line), context.function);
}
debug_info.prepend(QString("<font color='%1'><b>[%2]</b> %3 (%4:%5, %6)</font><br>")
debug_info.append(QString("<font color='%1'><b>[%2]</b> %3 (%4:%5, %6)</font><br>")
.arg(fontColor, msgTag, localMsg, context.file, QString::number(context.line), context.function));
fflush(stderr);
if (olive::DebugDialog != nullptr && olive::DebugDialog->isVisible()) {
+3
View File
@@ -79,6 +79,9 @@ QList<QString> get_effects_paths() {
// folder in share folder - best for Linux
effects_paths.append(app_dir.filePath("../share/olive-editor/effects"));
// user path - best for linux
effects_paths.append(QDir(QStandardPaths::writableLocation(QStandardPaths::AppDataLocation)).filePath("effects"));
// Olive will also accept a manually provided folder with an environment variable
QString env_path(qgetenv("OLIVE_EFFECTS_PATH"));
if (!env_path.isEmpty()) effects_paths.append(env_path);
+4 -4
View File
@@ -48,10 +48,6 @@ system("which git") {
CONFIG += c++11
CONFIG(debug, debug|release) {
CONFIG += console
}
SOURCES += \
main.cpp \
ui/mainwindow.cpp \
@@ -324,6 +320,10 @@ TRANSLATIONS += \
ts/olive_id.ts
win32 {
CONFIG(debug, debug|release) {
CONFIG += console
}
RC_FILE = packaging/windows/resources.rc
LIBS += -lavutil -lavformat -lavcodec -lavfilter -lswscale -lswresample -lopengl32 -luser32
contains(DEFINES, OLIVE_OCIO) {
@@ -9,16 +9,20 @@
<summary xml:lang="de_DE">Nicht-lineares Videoschnittprogramm</summary>
<summary xml:lang="pt_BR">Editor de vídeo não-linear</summary>
<summary xml:lang="es">Editor de video no lineal</summary>
<summary xml:lang="it">Editor video non lineare</summary>
<summary xml:lang="ru">Нелинейный видеоредактор</summary>
<summary xml:lang="uk">Нелінійний відеоредактор</summary>
<summary xml:lang="uk_UA">Нелінійний відеоредактор</summary>
<summary xml:lang="id">Aplikasi edit video non-linier</summary>
<description><p>Olive is a free non-linear video editor aiming to provide a fully-featured alternative to high-end professional video editing software.</p></description>
<description xml:lang="de_DE">Olive ist ein freies nicht-lineares Videoschnittprogramm, welches eine vollwertige Alternative zu High-End Videoschnittprogrammen darstellen soll.</description>
<description xml:lang="pt_BR"><p>Olive é um editor de vídeo não-linear com o objetivo de fornecer uma alternativa completa para softwares profissionais de edição de vídeo.</p></description>
<description xml:lang="es"><p>Olive es un editor de video no lineal libre que apunta a brindar una alternativa completa al software de edición de video profesional.</p></description>
<description xml:lang="it"><p>Olive è un programma di montaggio video che mira a fornire una alternativa di alta qualità ai software professionali</p></description>
<description xml:lang="ru"><p>Olive — свободный нелинейный видеоредактор, задуманный как полноценная замена закрытым коммерческим продуктам.</p></description>
<description xml:lang="uk"><p>Olive — вільний нелінійний відеоредактор, задуманий як повноцінна заміна закритим комерційним продуктам.</p></description>
<description xml:lang="uk_UA"><p>Olive — вільний нелінійний відеоредактор, задуманий як повноцінна заміна закритим комерційним продуктам.</p></description>
<description xml:lang="id"><p>Olive adalah aplikasi edit video bersifat non-linier yang bebas dan gratis, bertujuan untuk memberikan alternatif yang lengkap untuk aplikasi edit video profesional.</p></description>
<url type="homepage">https://www.olivevideoeditor.org</url>
<url type="donation">https://www.patreon.com/olivevideoeditor</url>
<url type="bugtracker">https://github.com/olive-editor/olive/issues</url>
@@ -1,6 +1,8 @@
[Desktop Entry]
Name=Olive
Comment=Professional open-source non-linear video editor
Comment[it]=Programma di montaggio video professionale open-source
Comment[id]=Aplikasi edit video yang non-linier, profesional serta sumbernya terbuka.
Exec=olive-editor
Icon=org.olivevideoeditor.Olive
Terminal=false
+4
View File
@@ -113,6 +113,10 @@ void free_panels() {
}
void scroll_to_frame_internal(QScrollBar* bar, long frame, double zoom, int area_width) {
if (bar->value() == bar->minimum() || bar->value() == bar->maximum()) {
return;
}
int screen_point = getScreenPointFromFrame(zoom, frame) - bar->value();
int min_x = area_width*0.1;
int max_x = area_width-min_x;
+6 -15
View File
@@ -63,7 +63,6 @@ extern "C" {
Viewer::Viewer(QWidget *parent) :
Panel(parent),
playing(false),
just_played_(false),
media(nullptr),
seq(nullptr),
created_sequence(false),
@@ -419,7 +418,7 @@ void Viewer::play(bool in_to_out) {
playhead_start = seq->playhead;
playing = true;
just_played_ = true;
SetAudioWakeObject(this);
set_playpause_icon(false);
start_msecs = QDateTime::currentMSecsSinceEpoch();
@@ -428,17 +427,14 @@ void Viewer::play(bool in_to_out) {
}
void Viewer::play_wake() {
if (just_played_) {
start_msecs = QDateTime::currentMSecsSinceEpoch();
playback_updater.start();
if (audio_thread != nullptr) audio_thread->notifyReceiver();
just_played_ = false;
}
start_msecs = QDateTime::currentMSecsSinceEpoch();
playback_updater.start();
if (audio_thread != nullptr) audio_thread->notifyReceiver();
}
void Viewer::pause() {
playing = false;
just_played_ = false;
SetAudioWakeObject(nullptr);
set_playpause_icon(true);
playback_updater.stop();
playback_speed = 0;
@@ -479,11 +475,6 @@ void Viewer::pause() {
}
}
bool Viewer::WaitingForPlayWake()
{
return just_played_;
}
void Viewer::update_playhead_timecode(long p) {
current_timecode_slider->SetValue(p);
}
@@ -678,7 +669,7 @@ void Viewer::setup_ui() {
lower_control_layout->setMargin(0);
QSizePolicy timecode_container_policy(QSizePolicy::Minimum, QSizePolicy::Maximum);
QSizePolicy lower_control_policy(QSizePolicy::Expanding, QSizePolicy::Maximum);
QSizePolicy lower_control_policy(QSizePolicy::Maximum, QSizePolicy::Maximum);
// Current time code container
QWidget* current_timecode_container = new QWidget();
-2
View File
@@ -71,7 +71,6 @@ public:
void seek(long p);
void play(bool in_to_out = false);
void pause();
bool WaitingForPlayWake();
bool playing;
long playhead_start;
qint64 start_msecs;
@@ -145,7 +144,6 @@ private:
double minimum_zoom;
bool playing_in_to_out;
long last_playhead;
bool just_played_;
void set_zoom_value(double d);
void set_sb_max();
void set_playback_speed(int s);
+30
View File
@@ -401,3 +401,33 @@ void combobox_audio_sample_rates(QComboBox *combobox) {
combobox->addItem("88200 Hz", 88200);
combobox->addItem("96000 Hz", 96000);
}
QObject* audio_wake_object = nullptr;
QMutex audio_wake_mutex;
QObject* GetAudioWakeObject()
{
audio_wake_mutex.lock();
QObject* wake_object = audio_wake_object;
audio_wake_object = nullptr;
audio_wake_mutex.unlock();
return wake_object;
}
void SetAudioWakeObject(QObject *o)
{
audio_wake_mutex.lock();
audio_wake_object = o;
audio_wake_mutex.unlock();
}
void WakeAudioWakeObject() {
QObject* audio_wake_object = GetAudioWakeObject();
if (audio_wake_object != nullptr) {
QMetaObject::invokeMethod(audio_wake_object, "play_wake", Qt::QueuedConnection);
}
}
+4
View File
@@ -65,6 +65,10 @@ extern bool audio_rendering;
extern int audio_rendering_rate;
void clear_audio_ibuffer();
QObject *GetAudioWakeObject();
void SetAudioWakeObject(QObject* o);
void WakeAudioWakeObject();
int current_audio_freq();
bool is_audio_device_set();
+3 -2
View File
@@ -460,8 +460,8 @@ void Cacher::CacheAudioWorker() {
}
}
QMetaObject::invokeMethod(panel_footage_viewer, "play_wake", Qt::QueuedConnection);
QMetaObject::invokeMethod(panel_sequence_viewer, "play_wake", Qt::QueuedConnection);
// If there's a QObject waiting for audio to be rendered, wake it now
WakeAudioWakeObject();
}
bool Cacher::IsReversed()
@@ -1194,6 +1194,7 @@ void Cacher::Open()
void Cacher::Cache(long playhead, bool scrubbing, QVector<Clip*>& nests, int playback_speed)
{
if (!is_valid_state_) {
return;
}
+34 -7
View File
@@ -60,6 +60,7 @@ ExportThread::ExportThread(const ExportParams &params,
audio_stream(nullptr),
acodec(nullptr),
audio_frame(nullptr),
sws_frame(nullptr),
swr_frame(nullptr),
acodec_ctx(nullptr),
swr_ctx(nullptr),
@@ -216,6 +217,8 @@ bool ExportThread::SetupVideo() {
}
bool ExportThread::SetupAudio() {
// if video is disabled, no setup necessary
if (!params_.audio_enabled) return true;
// Find encoder for this codec
acodec = avcodec_find_encoder(static_cast<AVCodecID>(params_.audio_codec));
@@ -374,12 +377,12 @@ void ExportThread::Export()
}
// If video is enabled, set it up in the container now
if (params_.video_enabled && !SetupVideo()) {
if (!SetupVideo()) {
return;
}
// If audio is enabled, set it up in the container now
if (params_.audio_enabled && !SetupAudio()) {
if (!SetupAudio()) {
return;
}
@@ -411,9 +414,6 @@ void ExportThread::Export()
disconnect(renderer, SIGNAL(ready()), panel_sequence_viewer->viewer_widget, SLOT(queue_repaint()));
connect(renderer, SIGNAL(ready()), this, SLOT(wake()));
// Lock mutex (used for synchronization with RenderThread)
mutex.lock();
// Loop from now (set to the beginning frame earlier) to the end of the frame
while (olive::ActiveSequence->playhead <= params_.end_frame && !interrupt_) {
@@ -422,6 +422,8 @@ void ExportThread::Export()
// If we're exporting audio, run compose_audio() which will write mixed audio to the internal audio buffer
if (params_.audio_enabled) {
waiting_for_audio_ = true;
SetAudioWakeObject(this);
olive::rendering::compose_audio(nullptr, olive::ActiveSequence.get(), 1, true);
}
@@ -485,6 +487,13 @@ void ExportThread::Export()
// If we're exporting audio, copy audio from the buffer into an AVFrame for encoding
if (params_.audio_enabled) {
if (waiting_for_audio_ && !interrupt_) {
waitCond.wait(&mutex);
}
// Make sure nothing is writing while we're retrieving
audio_write_lock.lock();
// Check if the count of encoded samples exceeds the current Sequence playhead, in which case we don't need to
// encode any audio at this moment
while (!interrupt_ && file_audio_samples <= (timecode_secs*params_.audio_sampling_rate)) {
@@ -519,6 +528,9 @@ void ExportThread::Export()
// Increment by the frame's number of samples
file_audio_samples += swr_frame->nb_samples;
}
audio_write_lock.unlock();
}
// Generating encoding statistics (e.g. the time it took to encode this frame/estimated remaining time)
@@ -542,8 +554,6 @@ void ExportThread::Export()
disconnect(renderer, SIGNAL(ready()), this, SLOT(wake()));
connect(renderer, SIGNAL(ready()), panel_sequence_viewer->viewer_widget, SLOT(queue_repaint()));
mutex.unlock();
if (interrupt_) {
return;
}
@@ -552,6 +562,7 @@ void ExportThread::Export()
if (params_.audio_enabled) apkt_alloc = true;
olive::Global->set_rendering_state(false);
close_active_clips(olive::ActiveSequence.get());
// If audio is enabled, flush the rest of the audio out of swresample
if (params_.audio_enabled) {
@@ -652,9 +663,14 @@ void ExportThread::run() {
// Seek to the first frame we're exporting
panel_sequence_viewer->seek(params_.start_frame);
// Lock mutex (used for thread synchronizations)
mutex.lock();
// Run export function (which will return if there's a failure)
Export();
mutex.unlock();
// Clean up anything that was allocated in Export() (whether it succeeded or not)
Cleanup();
}
@@ -670,7 +686,18 @@ bool ExportThread::WasInterrupted()
void ExportThread::Interrupt()
{
mutex.lock();
interrupt_ = true;
waitCond.wakeAll();
mutex.unlock();
}
void ExportThread::play_wake()
{
mutex.lock();
waiting_for_audio_ = false;
waitCond.wakeAll();
mutex.unlock();
}
void ExportThread::wake() {
+4
View File
@@ -82,6 +82,8 @@ signals:
void ProgressChanged(int value, qint64 remaining_ms);
public slots:
void Interrupt();
void play_wake();
private:
bool Encode(AVFormatContext* ofmt_ctx, AVCodecContext* codec_ctx, AVFrame* frame, AVPacket* packet, AVStream* stream);
bool SetupVideo();
@@ -124,6 +126,8 @@ private:
QWaitCondition waitCond;
QString export_error;
bool waiting_for_audio_;
private slots:
void wake();
};
+15 -30
View File
@@ -278,6 +278,7 @@ GLuint olive::rendering::compose_sequence(ComposeSequenceParams &params) {
}
if (params.video) {
// set default coordinates based on the sequence, with 0 in the direct center
glPushMatrix();
glLoadIdentity();
@@ -287,6 +288,7 @@ GLuint olive::rendering::compose_sequence(ComposeSequenceParams &params) {
int half_width = s->width/2;
int half_height = s->height/2;
glOrtho(-half_width, half_width, -half_height, half_height, -1, 10);
}
// loop through current clips
@@ -600,17 +602,6 @@ GLuint olive::rendering::compose_sequence(ComposeSequenceParams &params) {
// == END FINAL DRAW ON SEQUENCE BUFFER ==
}
// prepare gizmos
/*
if ((*params.gizmos) != nullptr
&& params.nests.isEmpty()
&& ((*params.gizmos) == first_gizmo_effect
|| (*params.gizmos) == selected_effect)) {
(*params.gizmos)->gizmo_draw(timecode, coords); // set correct gizmo coords
(*params.gizmos)->gizmo_world_to_screen(); // convert gizmo coords to screen coords
}
*/
glPopMatrix();
}
} else {
@@ -620,7 +611,17 @@ GLuint olive::rendering::compose_sequence(ComposeSequenceParams &params) {
params.nests.removeLast();
} else {
// Check whether cacher is currently active, if not activate it now
if (c->cache_lock.tryLock()) {
bool got_mutex2 = false;
if (params.wait_for_mutexes) {
c->cache_lock.lock();
got_mutex2 = true;
} else {
got_mutex2 = c->cache_lock.tryLock(got_mutex2);
}
if (got_mutex2) {
c->cache_lock.unlock();
@@ -631,22 +632,6 @@ GLuint olive::rendering::compose_sequence(ComposeSequenceParams &params) {
}
}
/*
// visually update all the keyframe values
if (c->sequence == params.seq) { // only if you can currently see them
double ts = (playhead - c->timeline_in(true) + c->clip_in(true))/s->frame_rate;
for (int i=0;i<c->effects.size();i++) {
EffectPtr e = c->effects.at(i);
for (int j=0;j<e->row_count();j++) {
EffectRow* r = e->row(j);
for (int k=0;k<r->fieldCount();k++) {
r->field(k)->validate_keyframe_data(ts);
}
}
}
}
*/
}
} else {
params.texture_failed = true;
@@ -657,8 +642,8 @@ GLuint olive::rendering::compose_sequence(ComposeSequenceParams &params) {
}
}
if (audio_track_count == 0 && params.viewer != nullptr) {
params.viewer->play_wake();
if (audio_track_count == 0) {
WakeAudioWakeObject();
}
if (params.video) {
+1 -2
View File
@@ -166,8 +166,7 @@ bool Sequence::IsClipSelected(Clip *clip, bool containing)
for (int i=0;i<selections.size();i++) {
const Selection& s = selections.at(i);
if (clip->track() == s.track && ((clip->timeline_in() >= s.in && clip->timeline_out() <= s.out)
|| (!containing && !(clip->timeline_in() < s.in && clip->timeline_out() < s.in)
&& !(clip->timeline_in() > s.in && clip->timeline_out() > s.in)))) {
|| (!containing && !(clip->timeline_in() >= s.out || clip->timeline_out() <= s.in)))) {
return true;
}
}
+1180 -687
View File
File diff suppressed because it is too large Load Diff
+1199 -919
View File
File diff suppressed because it is too large Load Diff
+2539 -2090
View File
File diff suppressed because it is too large Load Diff
+1182 -717
View File
File diff suppressed because it is too large Load Diff
+1181 -946
View File
File diff suppressed because it is too large Load Diff
+1180 -687
View File
File diff suppressed because it is too large Load Diff
+564 -401
View File
File diff suppressed because it is too large Load Diff
+1992 -1526
View File
File diff suppressed because it is too large Load Diff
+30 -30
View File
@@ -349,42 +349,42 @@
<translation>%1 (закрывается)</translation>
</message>
<message>
<location filename="../ui/effectui.cpp" line="157"/>
<location filename="../ui/effectui.cpp" line="158"/>
<source>%1 (multiple)</source>
<translation>%1 (больше одного)</translation>
</message>
<message>
<location filename="../ui/effectui.cpp" line="285"/>
<location filename="../ui/effectui.cpp" line="286"/>
<source>Cu&amp;t</source>
<translation>В&amp;ырезать</translation>
</message>
<message>
<location filename="../ui/effectui.cpp" line="288"/>
<location filename="../ui/effectui.cpp" line="289"/>
<source>&amp;Copy</source>
<translation>&amp;Скопировать</translation>
</message>
<message>
<location filename="../ui/effectui.cpp" line="299"/>
<location filename="../ui/effectui.cpp" line="300"/>
<source>Move &amp;Up</source>
<translation>&amp;Поднять</translation>
</message>
<message>
<location filename="../ui/effectui.cpp" line="303"/>
<location filename="../ui/effectui.cpp" line="304"/>
<source>Move &amp;Down</source>
<translation>&amp;Опустить</translation>
</message>
<message>
<location filename="../ui/effectui.cpp" line="308"/>
<location filename="../ui/effectui.cpp" line="309"/>
<source>D&amp;elete</source>
<translation>&amp;Удалить</translation>
</message>
<message>
<location filename="../ui/effectui.cpp" line="325"/>
<location filename="../ui/effectui.cpp" line="326"/>
<source>Load Settings From File</source>
<translation>Загрузить параметры из файла</translation>
</message>
<message>
<location filename="../ui/effectui.cpp" line="327"/>
<location filename="../ui/effectui.cpp" line="328"/>
<source>Save Settings to File</source>
<translation>Сохранить параметры в файл</translation>
</message>
@@ -595,87 +595,87 @@
<context>
<name>ExportThread</name>
<message>
<location filename="../rendering/exportthread.cpp" line="78"/>
<location filename="../rendering/exportthread.cpp" line="79"/>
<source>failed to send frame to encoder (%1)</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../rendering/exportthread.cpp" line="89"/>
<location filename="../rendering/exportthread.cpp" line="90"/>
<source>failed to receive packet from encoder (%1)</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../rendering/exportthread.cpp" line="121"/>
<location filename="../rendering/exportthread.cpp" line="113"/>
<source>could not video encoder for %1</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../rendering/exportthread.cpp" line="130"/>
<location filename="../rendering/exportthread.cpp" line="122"/>
<source>could not allocate video stream</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../rendering/exportthread.cpp" line="139"/>
<location filename="../rendering/exportthread.cpp" line="131"/>
<source>could not allocate video encoding context</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../rendering/exportthread.cpp" line="188"/>
<location filename="../rendering/exportthread.cpp" line="180"/>
<source>could not open output video encoder (%1)</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../rendering/exportthread.cpp" line="196"/>
<location filename="../rendering/exportthread.cpp" line="188"/>
<source>could not copy video encoder parameters to output stream (%1)</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../rendering/exportthread.cpp" line="233"/>
<location filename="../rendering/exportthread.cpp" line="227"/>
<source>could not audio encoder for %1</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../rendering/exportthread.cpp" line="241"/>
<location filename="../rendering/exportthread.cpp" line="235"/>
<source>could not allocate audio stream</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../rendering/exportthread.cpp" line="255"/>
<location filename="../rendering/exportthread.cpp" line="249"/>
<source>could not allocate audio encoding context</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../rendering/exportthread.cpp" line="280"/>
<location filename="../rendering/exportthread.cpp" line="274"/>
<source>could not open output audio encoder (%1)</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../rendering/exportthread.cpp" line="288"/>
<location filename="../rendering/exportthread.cpp" line="282"/>
<source>could not copy audio encoder parameters to output stream (%1)</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../rendering/exportthread.cpp" line="325"/>
<location filename="../rendering/exportthread.cpp" line="319"/>
<source>could not allocate audio buffer (%1)</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../rendering/exportthread.cpp" line="356"/>
<location filename="../rendering/exportthread.cpp" line="350"/>
<source>could not create output format context</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../rendering/exportthread.cpp" line="366"/>
<location filename="../rendering/exportthread.cpp" line="360"/>
<source>could not open output file (%1)</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../rendering/exportthread.cpp" line="402"/>
<location filename="../rendering/exportthread.cpp" line="396"/>
<source>could not write output file header (%1)</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../rendering/exportthread.cpp" line="603"/>
<location filename="../rendering/exportthread.cpp" line="600"/>
<source>could not write output file trailer (%1)</source>
<translation type="unfinished"></translation>
</message>
@@ -778,7 +778,7 @@
<context>
<name>KeyframeNavigator</name>
<message>
<location filename="../ui/keyframenavigator.cpp" line="71"/>
<location filename="../ui/keyframenavigator.cpp" line="77"/>
<source>Enable Keyframes</source>
<translation>Включить ключевые кадры</translation>
</message>
@@ -3275,7 +3275,7 @@ Audio Layout: %6</source>
<context>
<name>TimelineHeader</name>
<message>
<location filename="../ui/timelineheader.cpp" line="482"/>
<location filename="../ui/timelineheader.cpp" line="486"/>
<source>Center Timecodes</source>
<translation>Центрировать тайм-код</translation>
</message>
@@ -3528,17 +3528,17 @@ Duration: %4</source>
<translation>Просмотр проекта</translation>
</message>
<message>
<location filename="../panels/viewer.cpp" line="610"/>
<location filename="../panels/viewer.cpp" line="601"/>
<source>(none)</source>
<translation>(нет)</translation>
</message>
<message>
<location filename="../panels/viewer.cpp" line="746"/>
<location filename="../panels/viewer.cpp" line="737"/>
<source>Drag video only</source>
<translation>Перетаскивать только видео</translation>
</message>
<message>
<location filename="../panels/viewer.cpp" line="753"/>
<location filename="../panels/viewer.cpp" line="744"/>
<source>Drag audio only</source>
<translation>Перетаскивать только звук</translation>
</message>
+1199 -919
View File
File diff suppressed because it is too large Load Diff
+668 -478
View File
File diff suppressed because it is too large Load Diff
+1
View File
@@ -66,6 +66,7 @@ EffectUI::EffectUI(Effect* e) :
SetTitle(effect_name);
QWidget* ui = new QWidget(this);
ui->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Maximum);
SetContents(ui);
SetExpanded(e->IsExpanded());
+6
View File
@@ -39,7 +39,11 @@ KeyframeNavigator::KeyframeNavigator(QWidget *parent, bool addLeftPad) : QWidget
key_controls->addStretch();
}
QSizePolicy button_size_policy;
button_size_policy.setRetainSizeWhenHidden(true);
left_key_nav = new QPushButton(this);
left_key_nav->setSizePolicy(button_size_policy);
left_key_nav->setIcon(olive::icon::LeftArrow);
left_key_nav->setIconSize(left_key_nav->iconSize()*0.5);
left_key_nav->setVisible(false);
@@ -48,6 +52,7 @@ KeyframeNavigator::KeyframeNavigator(QWidget *parent, bool addLeftPad) : QWidget
connect(left_key_nav, SIGNAL(clicked(bool)), this, SIGNAL(clicked()));
key_addremove = new QPushButton(this);
key_addremove->setSizePolicy(button_size_policy);
key_addremove->setIcon(olive::icon::Diamond);
key_addremove->setIconSize(key_addremove->iconSize()*0.5);
key_addremove->setVisible(false);
@@ -56,6 +61,7 @@ KeyframeNavigator::KeyframeNavigator(QWidget *parent, bool addLeftPad) : QWidget
connect(key_addremove, SIGNAL(clicked(bool)), this, SIGNAL(clicked()));
right_key_nav = new QPushButton(this);
right_key_nav->setSizePolicy(button_size_policy);
right_key_nav->setIcon(olive::icon::RightArrow);
right_key_nav->setIconSize(right_key_nav->iconSize()*0.5);
right_key_nav->setVisible(false);
+5
View File
@@ -279,6 +279,9 @@ MainWindow::MainWindow(QWidget *parent) :
olive::Global->check_for_autorecovery_file();
// lock panels if the config says so
set_panels_locked(olive::CurrentConfig.locked_panels);
// set up output audio device
init_audio();
@@ -1188,6 +1191,8 @@ void MainWindow::set_panels_locked(bool locked)
panel->setTitleBarWidget(nullptr);
}
}
olive::CurrentConfig.locked_panels = locked;
}
void MainWindow::fileMenu_About_To_Be_Shown() {
+1 -1
View File
@@ -98,7 +98,7 @@ SourceIconDelegate::SourceIconDelegate(QObject *parent) :
{
}
QSize SourceIconDelegate::sizeHint(const QStyleOptionViewItem &option, const QModelIndex &index) const
QSize SourceIconDelegate::sizeHint(const QStyleOptionViewItem &option, const QModelIndex &) const
{
if (option.decorationPosition == QStyleOptionViewItem::Top) { // Icon Mode
+3
View File
@@ -32,8 +32,11 @@ TextEditEx::TextEditEx(QWidget *parent, bool enable_rich_text) :
enable_rich_text_(enable_rich_text)
{
QVBoxLayout* layout = new QVBoxLayout(this);
layout->setMargin(0);
layout->setSpacing(0);
text_editor_ = new QTextEdit();
text_editor_->setSizePolicy(QSizePolicy::Ignored, QSizePolicy::Expanding);
connect(text_editor_, SIGNAL(textChanged()), this, SLOT(queue_text_modified()));
layout->addWidget(text_editor_);
+6 -2
View File
@@ -67,9 +67,9 @@ TimelineHeader::TimelineHeader(QWidget *parent) :
in_visible(0),
fm(font()),
dragging_markers(false),
scroll(0)
scroll(0),
height_actual(fm.height())
{
height_actual = fm.height();
setCursor(Qt::ArrowCursor);
setMouseTracking(true);
setFocusPolicy(Qt::ClickFocus);
@@ -468,6 +468,10 @@ void TimelineHeader::paintEvent(QPaintEvent*) {
path.lineTo(in_x+PLAYHEAD_SIZE+1, yoff);
path.lineTo(start);
p.fillPath(path, Qt::red);
// Draw white line at the top for clarity
p.setPen(Qt::gray);
p.drawLine(0, 0, width(), 0);
}
}
+15 -10
View File
@@ -2513,8 +2513,8 @@ void TimelineWidget::mouseMoveEvent(QMouseEvent *event) {
// threshold around a trim point that the cursor can be within and still considered "trimming"
int lim = 5;
long mouse_frame_lower = panel_timeline->getTimelineFrameFromScreenPoint(pos.x()-lim)-1;
long mouse_frame_upper = panel_timeline->getTimelineFrameFromScreenPoint(pos.x()+lim)+1;
int mouse_frame_lower = pos.x() - lim;
int mouse_frame_upper = pos.x() + lim;
// used to determine whether we the cursor found a trim point or not
bool found = false;
@@ -2576,11 +2576,14 @@ void TimelineWidget::mouseMoveEvent(QMouseEvent *event) {
}
}
int visual_in_point = panel_timeline->getTimelineScreenPointFromFrame(c->timeline_in());
int visual_out_point = panel_timeline->getTimelineScreenPointFromFrame(c->timeline_out());
// is the cursor hovering around the clip's IN point?
if (c->timeline_in() > mouse_frame_lower && c->timeline_in() < mouse_frame_upper) {
if (visual_in_point > mouse_frame_lower && visual_in_point < mouse_frame_upper) {
// test how close this IN point is to the cursor
int nc = qAbs(c->timeline_in() + 1 - panel_timeline->cursor_frame);
int nc = qAbs(visual_in_point + 1 - pos.x());
// and test whether it's closer than the last in/out point we found
if (nc < closeness) {
@@ -2595,10 +2598,10 @@ void TimelineWidget::mouseMoveEvent(QMouseEvent *event) {
}
// is the cursor hovering around the clip's OUT point?
if (c->timeline_out() > mouse_frame_lower && c->timeline_out() < mouse_frame_upper) {
if (visual_out_point > mouse_frame_lower && visual_out_point < mouse_frame_upper) {
// test how close this OUT point is to the cursor
int nc = qAbs(c->timeline_out() - 1 - panel_timeline->cursor_frame);
int nc = qAbs(visual_out_point - 1 - pos.x());
// and test whether it's closer than the last in/out point we found
if (nc < closeness) {
@@ -2620,13 +2623,14 @@ void TimelineWidget::mouseMoveEvent(QMouseEvent *event) {
if (c->opening_transition != nullptr) {
// cache the timeline frame where the transition ends
long transition_point = c->timeline_in() + c->opening_transition->get_true_length();
int transition_point = panel_timeline->getTimelineScreenPointFromFrame(c->timeline_in()
+ c->opening_transition->get_true_length());
// check if the cursor is hovering around it (within the threshold)
if (transition_point > mouse_frame_lower && transition_point < mouse_frame_upper) {
// similar to above, test how close it is and if it's closer, make this active
int nc = qAbs(transition_point - 1 - panel_timeline->cursor_frame);
int nc = qAbs(transition_point - 1 - pos.x());
if (nc < closeness) {
panel_timeline->trim_target = i;
panel_timeline->trim_type = TRIM_OUT;
@@ -2641,13 +2645,14 @@ void TimelineWidget::mouseMoveEvent(QMouseEvent *event) {
if (c->closing_transition != nullptr) {
// cache the timeline frame where the transition starts
long transition_point = c->timeline_out() - c->closing_transition->get_true_length();
int transition_point = panel_timeline->getTimelineScreenPointFromFrame(c->timeline_out()
- c->closing_transition->get_true_length());
// check if the cursor is hovering around it (within the threshold)
if (transition_point > mouse_frame_lower && transition_point < mouse_frame_upper) {
// similar to above, test how close it is and if it's closer, make this active
int nc = qAbs(transition_point + 1 - panel_timeline->cursor_frame);
int nc = qAbs(transition_point + 1 - pos.x());
if (nc < closeness) {
panel_timeline->trim_target = i;
panel_timeline->trim_type = TRIM_IN;
+1 -1
View File
@@ -229,7 +229,7 @@ void ViewerWidget::frame_update() {
}
// render the audio
olive::rendering::compose_audio(viewer, viewer->seq.get(), viewer->get_playback_speed(), viewer->WaitingForPlayWake());
olive::rendering::compose_audio(viewer, viewer->seq.get(), viewer->get_playback_speed(), false);
}
}