You've already forked libopenshot
mirror of
https://github.com/OpenShot/libopenshot.git
synced 2026-03-02 08:53:52 -08:00
Merge branch 'develop' into timeline-inheritance
This commit is contained in:
47
.github/workflows/ci.yml
vendored
47
.github/workflows/ci.yml
vendored
@@ -6,35 +6,43 @@ jobs:
|
||||
strategy:
|
||||
matrix:
|
||||
os: [ubuntu-18.04, ubuntu-20.04]
|
||||
compiler: [gcc, clang]
|
||||
compiler:
|
||||
- { cc: gcc, cpp: g++ }
|
||||
- { cc: clang, cpp: clang++ }
|
||||
env:
|
||||
CC: ${{ matrix.compiler }}
|
||||
CC: ${{ matrix.compiler.cc }}
|
||||
CXX: ${{ matrix.compiler.cpp }}
|
||||
CODECOV_TOKEN: 'dc94d508-39d3-4369-b1c6-321749f96f7c'
|
||||
|
||||
steps:
|
||||
- uses: actions/checkout@v2
|
||||
# Work around a codecov issue detecting commit SHAs
|
||||
# see: https://community.codecov.io/t/issue-detecting-commit-sha-please-run-actions-checkout-with-fetch-depth-1-or-set-to-0/2571
|
||||
with:
|
||||
# Work around a codecov issue detecting commit SHAs
|
||||
# see: https://community.codecov.io/t/issue-detecting-commit-sha-please-run-actions-checkout-with-fetch-depth-1-or-set-to-0/2571
|
||||
fetch-depth: 0
|
||||
|
||||
- name: Checkout OpenShotAudio
|
||||
uses: actions/checkout@v2
|
||||
with:
|
||||
repository: OpenShot/libopenshot-audio
|
||||
path: audio
|
||||
|
||||
- uses: haya14busa/action-cond@v1
|
||||
id: coverage
|
||||
with:
|
||||
cond: ${{ matrix.compiler == 'clang' }}
|
||||
cond: ${{ matrix.compiler.cc == 'gcc' }}
|
||||
if_true: "-DENABLE_COVERAGE:BOOL=1"
|
||||
if_false: "-DENABLE_COVERAGE:BOOL=0"
|
||||
|
||||
- name: Install dependencies
|
||||
shell: bash
|
||||
run: |
|
||||
sudo add-apt-repository ppa:openshot.developers/libopenshot-daily
|
||||
sudo apt update
|
||||
sudo apt remove libzmq5 # See actions/virtual-environments#3317
|
||||
sudo apt install \
|
||||
cmake swig doxygen graphviz curl lcov \
|
||||
libopenshot-audio-dev libasound2-dev \
|
||||
qtbase5-dev qtbase5-dev-tools \
|
||||
libasound2-dev \
|
||||
qtbase5-dev qtbase5-dev-tools libqt5svg5-dev \
|
||||
libfdk-aac-dev libavcodec-dev libavformat-dev libavdevice-dev libavutil-dev libavfilter-dev libswscale-dev libpostproc-dev libswresample-dev \
|
||||
libzmq3-dev libmagick++-dev \
|
||||
libopencv-dev libprotobuf-dev protobuf-compiler
|
||||
@@ -43,13 +51,30 @@ jobs:
|
||||
wget https://launchpad.net/ubuntu/+archive/primary/+files/catch2_2.13.0-1_all.deb
|
||||
sudo dpkg -i catch2_2.13.0-1_all.deb
|
||||
|
||||
- uses: actions/cache@v2
|
||||
id: cache
|
||||
with:
|
||||
path: audio/build
|
||||
key: audio-${{ matrix.os }}-${{ matrix.compiler.cpp }}-${{ hashFiles('audio/CMakeLists.txt') }}
|
||||
|
||||
- name: Build OpenShotAudio (if not cached)
|
||||
if: steps.cache.outputs.cache-hit != 'true'
|
||||
shell: bash
|
||||
run: |
|
||||
pushd audio
|
||||
if [ ! -d build ]; then
|
||||
mkdir build
|
||||
cmake -B build -S .
|
||||
fi
|
||||
cmake --build build
|
||||
popd
|
||||
|
||||
- name: Build libopenshot
|
||||
shell: bash
|
||||
run: |
|
||||
mkdir build
|
||||
pushd build
|
||||
cmake -B . -S .. -DCMAKE_INSTALL_PREFIX:PATH="dist" -DCMAKE_BUILD_TYPE="Debug" "${{ steps.coverage.outputs.value }}"
|
||||
cmake -B . -S .. -DCMAKE_INSTALL_PREFIX:PATH="dist" -DCMAKE_BUILD_TYPE="Debug" -DOpenShotAudio_ROOT="../audio/build" "${{ steps.coverage.outputs.value }}"
|
||||
cmake --build . -- VERBOSE=1
|
||||
popd
|
||||
|
||||
@@ -67,7 +92,7 @@ jobs:
|
||||
cmake --build . --target install -- VERBOSE=1
|
||||
popd
|
||||
|
||||
- uses: codecov/codecov-action@v1
|
||||
if: ${{ matrix.compiler == 'clang' }}
|
||||
- uses: codecov/codecov-action@v2.1.0
|
||||
if: ${{ matrix.compiler.cc == 'gcc' }}
|
||||
with:
|
||||
file: build/coverage.info
|
||||
|
||||
@@ -40,8 +40,8 @@ For more information, please visit <http://www.openshot.org/>.
|
||||
set(CMAKE_MODULE_PATH "${CMAKE_SOURCE_DIR}/cmake/Modules")
|
||||
|
||||
################ PROJECT VERSION ####################
|
||||
set(PROJECT_VERSION_FULL "0.2.5-dev3")
|
||||
set(PROJECT_SO_VERSION 19)
|
||||
set(PROJECT_VERSION_FULL "0.2.7-dev")
|
||||
set(PROJECT_SO_VERSION 21)
|
||||
|
||||
# Remove the dash and anything following, to get the #.#.# version for project()
|
||||
STRING(REGEX REPLACE "\-.*$" "" VERSION_NUM "${PROJECT_VERSION_FULL}")
|
||||
@@ -99,6 +99,12 @@ if(ENABLE_TESTS)
|
||||
set(BUILD_TESTING ${ENABLE_TESTS})
|
||||
endif()
|
||||
|
||||
### JUCE requires one of -DDEBUG or -DNDEBUG set on the
|
||||
### compile command line. CMake automatically sets -DNDEBUG
|
||||
### on all non-debug configs, so we'll just add -DDEBUG to
|
||||
### the debug build flags
|
||||
set(CMAKE_CXX_FLAGS_DEBUG "${CMAKE_CXX_FLAGS_DEBUG} -DDEBUG")
|
||||
|
||||
#### Work around a GCC < 9 bug with handling of _Pragma() in macros
|
||||
#### See https://gcc.gnu.org/bugzilla/show_bug.cgi?id=55578
|
||||
if ((${CMAKE_CXX_COMPILER_ID} STREQUAL "GNU") AND
|
||||
@@ -200,6 +206,7 @@ if(BUILD_TESTING)
|
||||
if(VERBOSE_TESTS)
|
||||
list(APPEND CTEST_OPTIONS "-VV")
|
||||
endif()
|
||||
list(APPEND CTEST_OPTIONS "--output-on-failure")
|
||||
add_subdirectory(tests)
|
||||
endif()
|
||||
add_feature_info("Unit tests" ${BUILD_TESTING} "Compile unit tests for library functions")
|
||||
@@ -211,6 +218,7 @@ if (ENABLE_COVERAGE AND DEFINED UNIT_TEST_TARGETS)
|
||||
"examples/*"
|
||||
"${CMAKE_CURRENT_BINARY_DIR}/bindings/*"
|
||||
"${CMAKE_CURRENT_BINARY_DIR}/src/*_autogen/*"
|
||||
"audio/*"
|
||||
)
|
||||
setup_target_for_coverage_lcov(
|
||||
NAME coverage
|
||||
|
||||
@@ -95,6 +95,12 @@ if (DEFINED _inc)
|
||||
set_property(SOURCE openshot.i PROPERTY INCLUDE_DIRECTORIES ${_inc})
|
||||
endif()
|
||||
|
||||
### (FINALLY!)
|
||||
### Properly manage dependencies (regenerate bindings after changes)
|
||||
if (CMAKE_VERSION VERSION_GREATER 3.20)
|
||||
set_property(SOURCE openshot.i PROPERTY USE_SWIG_DEPENDENCIES TRUE)
|
||||
endif()
|
||||
|
||||
### Add the SWIG interface file (which defines all the SWIG methods)
|
||||
if (CMAKE_VERSION VERSION_LESS 3.8.0)
|
||||
swig_add_module(pyopenshot python openshot.i)
|
||||
|
||||
@@ -111,6 +111,12 @@ if (DEFINED _inc)
|
||||
set_property(SOURCE openshot.i PROPERTY INCLUDE_DIRECTORIES ${_inc})
|
||||
endif()
|
||||
|
||||
### (FINALLY!)
|
||||
### Properly manage dependencies (regenerate bindings after changes)
|
||||
if (CMAKE_VERSION VERSION_GREATER 3.20)
|
||||
set_property(SOURCE openshot.i PROPERTY USE_SWIG_DEPENDENCIES TRUE)
|
||||
endif()
|
||||
|
||||
### Add the SWIG interface file (which defines all the SWIG methods)
|
||||
if (CMAKE_VERSION VERSION_LESS 3.8.0)
|
||||
swig_add_module(rbopenshot ruby openshot.i)
|
||||
|
||||
@@ -34,21 +34,23 @@ This module defines the following variables:
|
||||
|
||||
::
|
||||
|
||||
FFMPEG_FOUND - System has the all required components.
|
||||
FFMPEG_INCLUDE_DIRS - Include directory necessary for using the required components headers.
|
||||
FFMPEG_LIBRARIES - Link these to use the required ffmpeg components.
|
||||
FFMPEG_DEFINITIONS - Compiler switches required for using the required ffmpeg components.
|
||||
FFmpeg_FOUND - System has the all required components.
|
||||
FFmpeg_INCLUDE_DIRS - Include directory necessary for using the required components headers.
|
||||
FFmpeg_LIBRARIES - Link these to use the required ffmpeg components.
|
||||
FFmpeg_DEFINITIONS - Compiler switches required for using the required ffmpeg components.
|
||||
FFmpeg_VERSION - The FFmpeg package version found.
|
||||
|
||||
For each component, ``<component>_FOUND`` will be set if the component is available.
|
||||
|
||||
For each ``<component>_FOUND``, the following variables will be defined:
|
||||
For each component, ``FFmpeg_<component>_FOUND`` will be set if the component is available.
|
||||
|
||||
For each ``FFmpeg_<component>_FOUND``, the following variables will be defined:
|
||||
|
||||
::
|
||||
|
||||
<component>_INCLUDE_DIRS - Include directory necessary for using the <component> headers
|
||||
<component>_LIBRARIES - Link these to use <component>
|
||||
<component>_DEFINITIONS - Compiler switches required for using <component>
|
||||
<component>_VERSION - The components version
|
||||
FFmpeg_<component>_INCLUDE_DIRS - Include directory necessary for using the
|
||||
<component> headers
|
||||
FFmpeg_<component>_LIBRARIES - Link these to use <component>
|
||||
FFmpeg_<component>_DEFINITIONS - Compiler switches required for <component>
|
||||
FFmpeg_<component>_VERSION - The components version
|
||||
|
||||
Backwards compatibility
|
||||
^^^^^^^^^^^^^^^^^^^^^^^
|
||||
@@ -57,10 +59,20 @@ For compatibility with previous versions of this module, uppercase names
|
||||
for FFmpeg and for all components are also recognized, and all-uppercase
|
||||
versions of the cache variables are also created.
|
||||
|
||||
Revision history
|
||||
^^^^^^^^^^^^^^^^
|
||||
ca. 2019 - Create CMake targets for discovered components
|
||||
2019-06-25 - No longer probe for non-requested components
|
||||
- Added fallback version.h parsing for components, when
|
||||
pkgconfig is missing
|
||||
- Added parsing of libavutil/ffversion.h for FFmpeg_VERSION
|
||||
- Adopt standard FFmpeg_<component>_<property> variable names
|
||||
- Switch to full signature for FPHSA, use HANDLE_COMPONENTS
|
||||
|
||||
Copyright (c) 2006, Matthias Kretz, <kretz@kde.org>
|
||||
Copyright (c) 2008, Alexander Neundorf, <neundorf@kde.org>
|
||||
Copyright (c) 2011, Michael Jansen, <kde@michael-jansen.biz>
|
||||
Copyright (c) 2019, FeRD (Frank Dana) <ferdnyc@gmail.com>
|
||||
Copyright (c) 2019-2021, FeRD (Frank Dana) <ferdnyc@gmail.com>
|
||||
|
||||
Redistribution and use is allowed according to the terms of the BSD license.
|
||||
For details see the accompanying COPYING-CMAKE-SCRIPTS file.
|
||||
@@ -84,16 +96,44 @@ endif ()
|
||||
# Marks the given component as found if both *_LIBRARIES AND *_INCLUDE_DIRS is present.
|
||||
#
|
||||
macro(set_component_found _component )
|
||||
if (${_component}_LIBRARIES AND ${_component}_INCLUDE_DIRS)
|
||||
if (FFmpeg_${_component}_LIBRARIES AND FFmpeg_${_component}_INCLUDE_DIRS)
|
||||
# message(STATUS "FFmpeg - ${_component} found.")
|
||||
set(${_component}_FOUND TRUE)
|
||||
else ()
|
||||
if (NOT FFmpeg_FIND_QUIETLY AND NOT FFMPEG_FIND_QUIETLY)
|
||||
message(STATUS "FFmpeg - ${_component} not found.")
|
||||
endif ()
|
||||
set(FFmpeg_${_component}_FOUND TRUE)
|
||||
#else ()
|
||||
# if (NOT FFmpeg_FIND_QUIETLY AND NOT FFMPEG_FIND_QUIETLY)
|
||||
# message(STATUS "FFmpeg - ${_component} not found.")
|
||||
# endif ()
|
||||
endif ()
|
||||
endmacro()
|
||||
|
||||
#
|
||||
### Macro: parse_lib_version
|
||||
#
|
||||
# Reads the file '${_pkgconfig}/version.h' in the component's _INCLUDE_DIR,
|
||||
# and parses #define statements for COMPONENT_VERSION_(MAJOR|MINOR|PATCH)
|
||||
# into a dotted string ${_component}_VERSION.
|
||||
#
|
||||
# Needed if the version is not supplied via pkgconfig's PC_${_component}_VERSION
|
||||
macro(parse_lib_version _component _libname )
|
||||
set(_version_h "${FFmpeg_${_component}_INCLUDE_DIRS}/${_libname}/version.h")
|
||||
if(EXISTS "${_version_h}")
|
||||
#message(STATUS "Parsing ${_component} version from ${_version_h}")
|
||||
string(TOUPPER "${_libname}" _prefix)
|
||||
set(_parts)
|
||||
foreach(_lvl MAJOR MINOR MICRO)
|
||||
file(STRINGS "${_version_h}" _lvl_version
|
||||
REGEX "^[ \t]*#define[ \t]+${_prefix}_VERSION_${_lvl}[ \t]+[0-9]+[ \t]*$")
|
||||
string(REGEX REPLACE
|
||||
"^.*${_prefix}_VERSION_${_lvl}[ \t]+([0-9]+)[ \t]*$"
|
||||
"\\1"
|
||||
_lvl_match "${_lvl_version}")
|
||||
list(APPEND _parts "${_lvl_match}")
|
||||
endforeach()
|
||||
list(JOIN _parts "." FFmpeg_${_component}_VERSION)
|
||||
message(STATUS "Found ${_component} version: ${FFmpeg_${_component}_VERSION}")
|
||||
endif()
|
||||
endmacro()
|
||||
|
||||
#
|
||||
### Macro: find_component
|
||||
#
|
||||
@@ -109,9 +149,9 @@ macro(find_component _component _pkgconfig _library _header)
|
||||
if (PKG_CONFIG_FOUND)
|
||||
pkg_check_modules(PC_${_component} ${_pkgconfig})
|
||||
endif ()
|
||||
endif (NOT WIN32)
|
||||
endif()
|
||||
|
||||
find_path(${_component}_INCLUDE_DIRS ${_header}
|
||||
find_path(FFmpeg_${_component}_INCLUDE_DIRS ${_header}
|
||||
HINTS
|
||||
/opt/
|
||||
/opt/include/
|
||||
@@ -123,7 +163,7 @@ macro(find_component _component _pkgconfig _library _header)
|
||||
ffmpeg
|
||||
)
|
||||
|
||||
find_library(${_component}_LIBRARIES NAMES ${_library}
|
||||
find_library(FFmpeg_${_component}_LIBRARIES NAMES ${_library}
|
||||
HINTS
|
||||
${PC_${_component}_LIBDIR}
|
||||
${PC_${_component}_LIBRARY_DIRS}
|
||||
@@ -132,56 +172,86 @@ macro(find_component _component _pkgconfig _library _header)
|
||||
$ENV{FFMPEGDIR}/bin/
|
||||
)
|
||||
|
||||
set(${_component}_DEFINITIONS ${PC_${_component}_CFLAGS_OTHER} CACHE STRING "The ${_component} CFLAGS.")
|
||||
set(${_component}_VERSION ${PC_${_component}_VERSION} CACHE STRING "The ${_component} version number.")
|
||||
set(FFmpeg_${_component}_DEFINITIONS ${PC_${_component}_CFLAGS_OTHER} CACHE STRING "The ${_component} CFLAGS.")
|
||||
|
||||
# Take version from PkgConfig, or parse from its version.h header
|
||||
if (PC_${_component}_VERSION)
|
||||
set(FFmpeg_${_component}_VERSION ${PC_${_component}_VERSION})
|
||||
else()
|
||||
parse_lib_version(${_component} ${_pkgconfig})
|
||||
endif()
|
||||
|
||||
set(FFmpeg_${_component}_VERSION ${FFmpeg_${_component}_VERSION} CACHE STRING "The ${_component} version number.")
|
||||
|
||||
set_component_found(${_component})
|
||||
|
||||
mark_as_advanced(
|
||||
${_component}_INCLUDE_DIRS
|
||||
${_component}_LIBRARIES
|
||||
${_component}_DEFINITIONS
|
||||
${_component}_VERSION
|
||||
FFmpeg_${_component}_INCLUDE_DIRS
|
||||
FFmpeg_${_component}_LIBRARIES
|
||||
FFmpeg_${_component}_DEFINITIONS
|
||||
FFmpeg_${_component}_VERSION
|
||||
)
|
||||
|
||||
endmacro()
|
||||
|
||||
#
|
||||
### Macro: parse_ff_version
|
||||
#
|
||||
# Read the libavutil/ffversion.h file and extract the definition
|
||||
# for FFMPEG_VERSION, to use as our version string.
|
||||
macro (parse_ff_version)
|
||||
set(_header "${FFmpeg_avutil_INCLUDE_DIRS}/libavutil/ffversion.h")
|
||||
if(EXISTS "${_header}")
|
||||
#message(STATUS "Parsing ffmpeg version from ${_header}")
|
||||
file(STRINGS "${_header}" _version_def
|
||||
REGEX "^#define[ \t]+FFMPEG_VERSION[ \t]+\".*\"[ \t]*$")
|
||||
string(REGEX REPLACE
|
||||
"^.*FFMPEG_VERSION[ \t]+\"(.*)\".*$"
|
||||
"\\1"
|
||||
FFmpeg_VERSION "${_version_def}")
|
||||
#message(STATUS "Found FFmpeg version: ${FFmpeg_VERSION}")
|
||||
endif()
|
||||
endmacro()
|
||||
|
||||
# Check for cached results. If there are skip the costly part.
|
||||
if (NOT FFmpeg_LIBRARIES)
|
||||
# Configs for all possible component.
|
||||
set(avcodec_params libavcodec avcodec libavcodec/avcodec.h)
|
||||
set(avdevice_params libavdevice avdevice libavdevice/avdevice.h)
|
||||
set(avformat_params libavformat avformat libavformat/avformat.h)
|
||||
set(avfilter_params libavfilter avfilter libavfilter/avfilter.h)
|
||||
set(avutil_params libavutil avutil libavutil/avutil.h)
|
||||
set(postproc_params libpostproc postproc libpostproc/postprocess.h)
|
||||
set(swscale_params libswscale swscale libswscale/swscale.h)
|
||||
set(swresample_params libswresample swresample libswresample/swresample.h)
|
||||
set(avresample_params libavresample avresample libavresample/avresample.h)
|
||||
|
||||
# Check for all possible component.
|
||||
find_component(avcodec libavcodec avcodec libavcodec/avcodec.h)
|
||||
find_component(avdevice libavdevice avdevice libavdevice/avdevice.h)
|
||||
find_component(avformat libavformat avformat libavformat/avformat.h)
|
||||
find_component(avfilter libavfilter avfilter libavfilter/avfilter.h)
|
||||
find_component(avutil libavutil avutil libavutil/avutil.h)
|
||||
find_component(postproc libpostproc postproc libpostproc/postprocess.h)
|
||||
find_component(swscale libswscale swscale libswscale/swscale.h)
|
||||
find_component(swresample libswresample swresample libswresample/swresample.h)
|
||||
find_component(avresample libavresample avresample libavresample/avresample.h)
|
||||
else()
|
||||
# Just set the noncached _FOUND vars for the components.
|
||||
foreach(_component ${FFmpeg_ALL_COMPONENTS})
|
||||
set_component_found(${_component})
|
||||
endforeach ()
|
||||
endif()
|
||||
|
||||
# Check if the requested components were found and add their stuff to the FFmpeg_* vars.
|
||||
foreach (_component ${FFmpeg_FIND_COMPONENTS})
|
||||
# Gather configs for each requested component
|
||||
foreach(_component ${FFmpeg_FIND_COMPONENTS})
|
||||
string(TOLOWER "${_component}" _component)
|
||||
if (${_component}_FOUND)
|
||||
# Only probe if not already _FOUND (expensive)
|
||||
if (NOT FFmpeg_${_component}_FOUND)
|
||||
find_component(${_component} ${${_component}_params})
|
||||
endif()
|
||||
|
||||
# Add the component's configs to the FFmpeg_* variables
|
||||
if (FFmpeg_${_component}_FOUND)
|
||||
# message(STATUS "Requested component ${_component} present.")
|
||||
set(FFmpeg_LIBRARIES ${FFmpeg_LIBRARIES} ${${_component}_LIBRARIES})
|
||||
set(FFmpeg_DEFINITIONS ${FFmpeg_DEFINITIONS} ${${_component}_DEFINITIONS})
|
||||
list(APPEND FFmpeg_INCLUDE_DIRS ${${_component}_INCLUDE_DIRS})
|
||||
set(FFmpeg_LIBRARIES ${FFmpeg_LIBRARIES} ${FFmpeg_${_component}_LIBRARIES})
|
||||
set(FFmpeg_DEFINITIONS ${FFmpeg_DEFINITIONS} ${FFmpeg_${_component}_DEFINITIONS})
|
||||
list(APPEND FFmpeg_INCLUDE_DIRS ${FFmpeg_${_component}_INCLUDE_DIRS})
|
||||
else ()
|
||||
# message(STATUS "Requested component ${_component} missing.")
|
||||
endif ()
|
||||
endforeach ()
|
||||
endforeach()
|
||||
|
||||
# Make sure we've probed for avutil
|
||||
if (NOT FFmpeg_avutil_FOUND)
|
||||
find_component(avutil libavutil avutil libavutil/avutil.h)
|
||||
endif()
|
||||
# Get the overall FFmpeg version from libavutil/ffversion.h
|
||||
parse_ff_version()
|
||||
|
||||
# Build the result lists with duplicates removed, in case of repeated
|
||||
# invocations.
|
||||
# invocations or component redundancy.
|
||||
if (FFmpeg_INCLUDE_DIRS)
|
||||
list(REMOVE_DUPLICATES FFmpeg_INCLUDE_DIRS)
|
||||
endif()
|
||||
@@ -196,57 +266,68 @@ endif ()
|
||||
set(FFmpeg_INCLUDE_DIRS ${FFmpeg_INCLUDE_DIRS} CACHE STRING "The FFmpeg include directories." FORCE)
|
||||
set(FFmpeg_LIBRARIES ${FFmpeg_LIBRARIES} CACHE STRING "The FFmpeg libraries." FORCE)
|
||||
set(FFmpeg_DEFINITIONS ${FFmpeg_DEFINITIONS} CACHE STRING "The FFmpeg cflags." FORCE)
|
||||
set(FFmpeg_VERSION ${FFmpeg_VERSION} CACHE STRING "The overall FFmpeg version.")
|
||||
|
||||
mark_as_advanced(FFmpeg_INCLUDE_DIRS
|
||||
mark_as_advanced(
|
||||
FFmpeg_INCLUDE_DIRS
|
||||
FFmpeg_LIBRARIES
|
||||
FFmpeg_DEFINITIONS)
|
||||
FFmpeg_DEFINITIONS
|
||||
FFmpeg_VERSION
|
||||
)
|
||||
|
||||
# Backwards compatibility
|
||||
foreach(_suffix INCLUDE_DIRS LIBRARIES DEFINITIONS)
|
||||
foreach(_suffix INCLUDE_DIRS LIBRARIES DEFINITIONS VERSION)
|
||||
get_property(_help CACHE FFmpeg_${_suffix} PROPERTY HELPSTRING)
|
||||
set(FFMPEG_${_suffix} ${FFmpeg_${_suffix}} CACHE STRING "${_help}" FORCE)
|
||||
mark_as_advanced(FFMPEG_${_suffix})
|
||||
endforeach()
|
||||
foreach(_component ${FFmpeg_ALL_COMPONENTS})
|
||||
if(${_component}_FOUND)
|
||||
if(FFmpeg_${_component}_FOUND)
|
||||
string(TOUPPER "${_component}" _uc_component)
|
||||
set(${_uc_component}_FOUND TRUE)
|
||||
set(FFMPEG_${_uc_component}_FOUND TRUE)
|
||||
foreach(_suffix INCLUDE_DIRS LIBRARIES DEFINITIONS VERSION)
|
||||
get_property(_help CACHE ${_component}_${_suffix} PROPERTY HELPSTRING)
|
||||
set(${_uc_component}_${_suffix} ${${_component}_${_suffix}} CACHE STRING "${_help}" FORCE)
|
||||
mark_as_advanced(${_uc_component}_${_suffix})
|
||||
get_property(_help CACHE FFmpeg_${_component}_${_suffix} PROPERTY HELPSTRING)
|
||||
set(FFMPEG_${_uc_component}_${_suffix} ${FFmpeg_${_component}_${_suffix}} CACHE STRING "${_help}" FORCE)
|
||||
mark_as_advanced(FFMPEG_${_uc_component}_${_suffix})
|
||||
endforeach()
|
||||
endif()
|
||||
endforeach()
|
||||
|
||||
# Compile the list of required vars
|
||||
set(_FFmpeg_REQUIRED_VARS FFmpeg_LIBRARIES FFmpeg_INCLUDE_DIRS)
|
||||
foreach (_component ${FFmpeg_FIND_COMPONENTS})
|
||||
list(APPEND _FFmpeg_REQUIRED_VARS
|
||||
${_component}_LIBRARIES
|
||||
${_component}_INCLUDE_DIRS)
|
||||
endforeach ()
|
||||
# XXX: HANDLE_COMPONENTS should take care of this, maybe? -FeRD
|
||||
# foreach (_component ${FFmpeg_FIND_COMPONENTS})
|
||||
# list(APPEND _FFmpeg_REQUIRED_VARS
|
||||
# FFmpeg_${_component}_LIBRARIES
|
||||
# FFmpeg_${_component}_INCLUDE_DIRS)
|
||||
# endforeach ()
|
||||
|
||||
# Give a nice error message if some of the required vars are missing.
|
||||
find_package_handle_standard_args(FFmpeg DEFAULT_MSG ${_FFmpeg_REQUIRED_VARS})
|
||||
find_package_handle_standard_args(FFmpeg
|
||||
REQUIRED_VARS ${_FFmpeg_REQUIRED_VARS}
|
||||
VERSION_VAR FFmpeg_VERSION
|
||||
HANDLE_COMPONENTS
|
||||
)
|
||||
|
||||
# Export targets for each found component
|
||||
foreach (_component ${FFmpeg_ALL_COMPONENTS})
|
||||
foreach (_component ${FFmpeg_FIND_COMPONENTS})
|
||||
|
||||
if(${_component}_FOUND)
|
||||
# message(STATUS "Creating IMPORTED target FFmpeg::${_component}")
|
||||
if(FFmpeg_${_component}_FOUND)
|
||||
#message(STATUS "Creating IMPORTED target FFmpeg::${_component}")
|
||||
|
||||
if(NOT TARGET FFmpeg::${_component})
|
||||
add_library(FFmpeg::${_component} UNKNOWN IMPORTED)
|
||||
|
||||
set_target_properties(FFmpeg::${_component} PROPERTIES
|
||||
INTERFACE_INCLUDE_DIRECTORIES "${${_component}_INCLUDE_DIRS}")
|
||||
INTERFACE_INCLUDE_DIRECTORIES
|
||||
"${FFmpeg_${_component}_INCLUDE_DIRS}")
|
||||
|
||||
set_property(TARGET FFmpeg::${_component} APPEND PROPERTY
|
||||
INTERFACE_COMPILE_DEFINITIONS "${${_component}_DEFINITIONS}")
|
||||
INTERFACE_COMPILE_DEFINITIONS
|
||||
"${FFmpeg_${_component}_DEFINITIONS}")
|
||||
|
||||
set_property(TARGET FFmpeg::${_component} APPEND PROPERTY
|
||||
IMPORTED_LOCATION "${${_component}_LIBRARIES}")
|
||||
IMPORTED_LOCATION "${FFmpeg_${_component}_LIBRARIES}")
|
||||
endif()
|
||||
|
||||
endif()
|
||||
|
||||
@@ -35,21 +35,25 @@ using namespace std;
|
||||
using namespace openshot;
|
||||
|
||||
// Constructor that reads samples from a reader
|
||||
AudioReaderSource::AudioReaderSource(ReaderBase *audio_reader, int64_t starting_frame_number, int buffer_size)
|
||||
: reader(audio_reader), frame_number(starting_frame_number),
|
||||
size(buffer_size), position(0), frame_position(0), estimated_frame(0), speed(1) {
|
||||
|
||||
// Initialize an audio buffer (based on reader)
|
||||
buffer = new juce::AudioSampleBuffer(reader->info.channels, size);
|
||||
|
||||
// initialize the audio samples to zero (silence)
|
||||
AudioReaderSource::AudioReaderSource(
|
||||
ReaderBase *audio_reader, int64_t starting_frame_number, int buffer_size
|
||||
) :
|
||||
position(0),
|
||||
size(buffer_size),
|
||||
buffer(new juce::AudioSampleBuffer(audio_reader->info.channels, buffer_size)),
|
||||
speed(1),
|
||||
reader(audio_reader),
|
||||
frame_number(starting_frame_number),
|
||||
frame_position(0),
|
||||
estimated_frame(0)
|
||||
{
|
||||
// Zero the buffer contents
|
||||
buffer->clear();
|
||||
}
|
||||
|
||||
// Destructor
|
||||
AudioReaderSource::~AudioReaderSource()
|
||||
{
|
||||
// Clear and delete the buffer
|
||||
delete buffer;
|
||||
buffer = NULL;
|
||||
}
|
||||
|
||||
@@ -130,7 +130,17 @@ set(EFFECTS_SOURCES
|
||||
effects/Pixelate.cpp
|
||||
effects/Saturation.cpp
|
||||
effects/Shift.cpp
|
||||
effects/Wave.cpp)
|
||||
effects/Wave.cpp
|
||||
audio_effects/STFT.cpp
|
||||
audio_effects/Noise.cpp
|
||||
audio_effects/Delay.cpp
|
||||
audio_effects/Echo.cpp
|
||||
audio_effects/Distortion.cpp
|
||||
audio_effects/ParametricEQ.cpp
|
||||
audio_effects/Compressor.cpp
|
||||
audio_effects/Expander.cpp
|
||||
audio_effects/Robotization.cpp
|
||||
audio_effects/Whisperization.cpp)
|
||||
|
||||
# Qt video player components
|
||||
set(QT_PLAYER_SOURCES
|
||||
@@ -186,56 +196,57 @@ target_link_libraries(openshot PUBLIC OpenShot::Audio)
|
||||
###
|
||||
|
||||
# Find the ImageMagick++ library
|
||||
find_package(ImageMagick COMPONENTS Magick++ MagickCore)
|
||||
if (ENABLE_MAGICK)
|
||||
find_package(ImageMagick COMPONENTS Magick++ MagickCore)
|
||||
|
||||
if(ImageMagick_FOUND)
|
||||
if(NOT TARGET ImageMagick::Magick++ AND NOT TARGET Magick++_TARGET)
|
||||
add_library(Magick++_TARGET INTERFACE)
|
||||
if(ImageMagick_FOUND)
|
||||
if(NOT TARGET ImageMagick::Magick++ AND NOT TARGET Magick++_TARGET)
|
||||
add_library(Magick++_TARGET INTERFACE)
|
||||
|
||||
# Include ImageMagick++ headers (needed for compile)
|
||||
set_property(TARGET Magick++_TARGET APPEND PROPERTY
|
||||
INTERFACE_INCLUDE_DIRECTORIES ${ImageMagick_INCLUDE_DIRS})
|
||||
# Include ImageMagick++ headers (needed for compile)
|
||||
set_property(TARGET Magick++_TARGET APPEND PROPERTY
|
||||
INTERFACE_INCLUDE_DIRECTORIES ${ImageMagick_INCLUDE_DIRS})
|
||||
|
||||
# Set the Quantum Depth that ImageMagick was built with (default to 16 bits)
|
||||
if(NOT DEFINED MAGICKCORE_QUANTUM_DEPTH)
|
||||
set(MAGICKCORE_QUANTUM_DEPTH 16)
|
||||
endif()
|
||||
if(NOT DEFINED MAGICKCORE_HDRI_ENABLE)
|
||||
set(MAGICKCORE_HDRI_ENABLE 0)
|
||||
endif()
|
||||
|
||||
set_property(TARGET Magick++_TARGET APPEND PROPERTY
|
||||
INTERFACE_COMPILE_DEFINITIONS
|
||||
MAGICKCORE_QUANTUM_DEPTH=${MAGICKCORE_QUANTUM_DEPTH})
|
||||
set_property(TARGET Magick++_TARGET APPEND PROPERTY
|
||||
INTERFACE_COMPILE_DEFINITIONS
|
||||
MAGICKCORE_HDRI_ENABLE=${MAGICKCORE_HDRI_ENABLE})
|
||||
|
||||
target_link_libraries(Magick++_TARGET INTERFACE
|
||||
${ImageMagick_LIBRARIES})
|
||||
|
||||
# Alias to our namespaced name
|
||||
add_library(ImageMagick::Magick++ ALIAS Magick++_TARGET)
|
||||
|
||||
# Set the Quantum Depth that ImageMagick was built with (default to 16 bits)
|
||||
if(NOT DEFINED MAGICKCORE_QUANTUM_DEPTH)
|
||||
set(MAGICKCORE_QUANTUM_DEPTH 16)
|
||||
endif()
|
||||
if(NOT DEFINED MAGICKCORE_HDRI_ENABLE)
|
||||
set(MAGICKCORE_HDRI_ENABLE 0)
|
||||
endif()
|
||||
|
||||
set_property(TARGET Magick++_TARGET APPEND PROPERTY
|
||||
INTERFACE_COMPILE_DEFINITIONS
|
||||
MAGICKCORE_QUANTUM_DEPTH=${MAGICKCORE_QUANTUM_DEPTH})
|
||||
set_property(TARGET Magick++_TARGET APPEND PROPERTY
|
||||
INTERFACE_COMPILE_DEFINITIONS
|
||||
MAGICKCORE_HDRI_ENABLE=${MAGICKCORE_HDRI_ENABLE})
|
||||
# Add optional ImageMagic-dependent sources
|
||||
target_sources(openshot PRIVATE
|
||||
ImageReader.cpp
|
||||
ImageWriter.cpp
|
||||
TextReader.cpp)
|
||||
|
||||
target_link_libraries(Magick++_TARGET INTERFACE
|
||||
${ImageMagick_LIBRARIES})
|
||||
# define a preprocessor macro (used in the C++ source)
|
||||
target_compile_definitions(openshot PUBLIC USE_IMAGEMAGICK=1)
|
||||
|
||||
# Alias to our namespaced name
|
||||
add_library(ImageMagick::Magick++ ALIAS Magick++_TARGET)
|
||||
# Link with ImageMagick library
|
||||
target_link_libraries(openshot PUBLIC ImageMagick::Magick++)
|
||||
|
||||
set(HAVE_IMAGEMAGICK TRUE CACHE BOOL "Building with ImageMagick support" FORCE)
|
||||
mark_as_advanced(HAVE_IMAGEMAGICK)
|
||||
endif()
|
||||
|
||||
# Add optional ImageMagic-dependent sources
|
||||
target_sources(openshot PRIVATE
|
||||
ImageReader.cpp
|
||||
ImageWriter.cpp
|
||||
TextReader.cpp)
|
||||
|
||||
# define a preprocessor macro (used in the C++ source)
|
||||
target_compile_definitions(openshot PUBLIC USE_IMAGEMAGICK=1)
|
||||
|
||||
# Link with ImageMagick library
|
||||
target_link_libraries(openshot PUBLIC ImageMagick::Magick++)
|
||||
|
||||
set(HAVE_IMAGEMAGICK TRUE CACHE BOOL "Building with ImageMagick support" FORCE)
|
||||
mark_as_advanced(HAVE_IMAGEMAGICK)
|
||||
endif()
|
||||
|
||||
|
||||
################### JSONCPP #####################
|
||||
# Include jsoncpp headers (needed for JSON parsing)
|
||||
if (USE_SYSTEM_JSONCPP)
|
||||
@@ -273,7 +284,7 @@ endif ()
|
||||
|
||||
################# QT5 ###################
|
||||
# Find QT5 libraries
|
||||
set(_qt_components Core Gui Widgets)
|
||||
set(_qt_components Core Gui Widgets Svg)
|
||||
find_package(Qt5 COMPONENTS ${_qt_components} REQUIRED)
|
||||
|
||||
foreach(_qt_comp IN LISTS _qt_components)
|
||||
@@ -288,31 +299,45 @@ mark_as_advanced(QT_VERSION_STR)
|
||||
|
||||
################### FFMPEG #####################
|
||||
# Find FFmpeg libraries (used for video encoding / decoding)
|
||||
find_package(FFmpeg REQUIRED COMPONENTS avcodec avformat avutil swscale)
|
||||
find_package(FFmpeg REQUIRED
|
||||
COMPONENTS avcodec avformat avutil swscale
|
||||
OPTIONAL_COMPONENTS swresample avresample
|
||||
)
|
||||
|
||||
set(all_comps avcodec avformat avutil swscale)
|
||||
if(TARGET FFmpeg::swresample)
|
||||
list(APPEND all_comps swresample)
|
||||
else()
|
||||
list(APPEND all_comps avresample)
|
||||
endif()
|
||||
set(version_comps avcodec avformat avutil)
|
||||
|
||||
# Pick a resampler. Prefer swresample if possible
|
||||
if(TARGET FFmpeg::swresample AND ${FFmpeg_avformat_VERSION} VERSION_GREATER "57.0.0")
|
||||
set(resample_lib swresample)
|
||||
set(USE_SW TRUE)
|
||||
else()
|
||||
set(resample_lib avresample)
|
||||
set(USE_SW FALSE)
|
||||
endif()
|
||||
list(APPEND all_comps ${resample_lib})
|
||||
|
||||
foreach(ff_comp IN LISTS all_comps)
|
||||
if(TARGET FFmpeg::${ff_comp})
|
||||
target_link_libraries(openshot PUBLIC FFmpeg::${ff_comp})
|
||||
# Keep track of some FFmpeg lib versions, to embed in our version header
|
||||
if(${ff_comp} IN_LIST version_comps AND ${ff_comp}_VERSION)
|
||||
if(${ff_comp} IN_LIST version_comps AND FFmpeg_${ff_comp}_VERSION)
|
||||
string(TOUPPER ${ff_comp} v_name)
|
||||
set(${v_name}_VERSION_STR ${${ff_comp}_VERSION} CACHE STRING "${ff_comp} version used" FORCE)
|
||||
set(${v_name}_VERSION_STR ${FFmpeg_${ff_comp}_VERSION} CACHE STRING "${ff_comp} version used" FORCE)
|
||||
mark_as_advanced(${v_name}_VERSION_STR)
|
||||
endif()
|
||||
endif()
|
||||
endforeach()
|
||||
|
||||
# Indicate which resampler we linked with, and set a config header flag
|
||||
add_feature_info("FFmpeg ${resample_lib}" TRUE "Audio resampling uses ${resample_lib}")
|
||||
# Set the appropriate flag in OpenShotVersion.h
|
||||
set(FFMPEG_USE_SWRESAMPLE ${USE_SW} CACHE BOOL "libswresample used for audio resampling" FORCE)
|
||||
mark_as_advanced(FFMPEG_USE_SWRESAMPLE)
|
||||
|
||||
# Version check for hardware-acceleration code
|
||||
if(USE_HW_ACCEL AND avcodec_VERSION)
|
||||
if(${avcodec_VERSION} VERSION_GREATER 57.107.100)
|
||||
if(USE_HW_ACCEL AND FFmpeg_avcodec_VERSION)
|
||||
if(${FFmpeg_avcodec_VERSION} VERSION_GREATER "57.106")
|
||||
set(HAVE_HW_ACCEL TRUE)
|
||||
endif()
|
||||
endif()
|
||||
@@ -537,4 +562,3 @@ endif()
|
||||
set(CPACK_DEBIAN_PACKAGE_MAINTAINER "Jonathan Thomas") #required
|
||||
|
||||
include(CPack)
|
||||
|
||||
|
||||
@@ -207,7 +207,7 @@ cv::Rect2d CVTracker::filter_box_jitter(size_t frameId){
|
||||
float curr_box_height = bbox.height;
|
||||
// keep the last width and height if the difference is less than 1%
|
||||
float threshold = 0.01;
|
||||
|
||||
|
||||
cv::Rect2d filtered_box = bbox;
|
||||
if(std::abs(1-(curr_box_width/last_box_width)) <= threshold){
|
||||
filtered_box.width = last_box_width;
|
||||
@@ -299,13 +299,13 @@ void CVTracker::SetJson(const std::string value) {
|
||||
// Load Json::Value into this object
|
||||
void CVTracker::SetJsonValue(const Json::Value root) {
|
||||
|
||||
// Set data from Json (if key is found)
|
||||
if (!root["protobuf_data_path"].isNull()){
|
||||
protobuf_data_path = (root["protobuf_data_path"].asString());
|
||||
}
|
||||
// Set data from Json (if key is found)
|
||||
if (!root["protobuf_data_path"].isNull()){
|
||||
protobuf_data_path = (root["protobuf_data_path"].asString());
|
||||
}
|
||||
if (!root["tracker-type"].isNull()){
|
||||
trackerType = (root["tracker-type"].asString());
|
||||
}
|
||||
trackerType = (root["tracker-type"].asString());
|
||||
}
|
||||
|
||||
if (!root["region"].isNull()){
|
||||
double x = root["region"]["normalized_x"].asDouble();
|
||||
@@ -314,20 +314,22 @@ void CVTracker::SetJsonValue(const Json::Value root) {
|
||||
double h = root["region"]["normalized_height"].asDouble();
|
||||
cv::Rect2d prev_bbox(x,y,w,h);
|
||||
bbox = prev_bbox;
|
||||
|
||||
if (!root["region"]["first-frame"].isNull()){
|
||||
start = root["region"]["first-frame"].asInt64();
|
||||
json_interval = true;
|
||||
}
|
||||
else{
|
||||
processingController->SetError(true, "No first-frame");
|
||||
error = true;
|
||||
}
|
||||
|
||||
}
|
||||
else{
|
||||
processingController->SetError(true, "No initial bounding box selected");
|
||||
error = true;
|
||||
}
|
||||
|
||||
if (!root["region"]["first-frame"].isNull()){
|
||||
start = root["region"]["first-frame"].asInt64();
|
||||
json_interval = true;
|
||||
}
|
||||
else{
|
||||
processingController->SetError(true, "No first-frame");
|
||||
error = true;
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
|
||||
18
src/Clip.cpp
18
src/Clip.cpp
@@ -121,12 +121,8 @@ void Clip::init_reader_settings() {
|
||||
|
||||
// Init reader's rotation (if any)
|
||||
void Clip::init_reader_rotation() {
|
||||
// Only init rotation from reader when needed
|
||||
if (rotation.GetCount() > 1)
|
||||
// Do nothing if more than 1 rotation Point
|
||||
return;
|
||||
else if (rotation.GetCount() == 1 && rotation.GetValue(1) != 0.0)
|
||||
// Do nothing if 1 Point, and it's not the default value
|
||||
// Dont init rotation if clip has keyframes
|
||||
if (rotation.GetCount() > 0)
|
||||
return;
|
||||
|
||||
// Init rotation
|
||||
@@ -1384,13 +1380,9 @@ QTransform Clip::get_transform(std::shared_ptr<Frame> frame, int width, int heig
|
||||
break;
|
||||
}
|
||||
case (SCALE_NONE): {
|
||||
// Calculate ratio of source size to project size
|
||||
// Even with no scaling, previews need to be adjusted correctly
|
||||
// (otherwise NONE scaling draws the frame image outside of the preview)
|
||||
float source_width_ratio = source_size.width() / float(width);
|
||||
float source_height_ratio = source_size.height() / float(height);
|
||||
source_size.scale(width * source_width_ratio, height * source_height_ratio, Qt::KeepAspectRatio);
|
||||
|
||||
// Image is already the original size (i.e. no scaling mode) relative
|
||||
// to the preview window size (i.e. timeline / preview ratio). No further
|
||||
// scaling is needed here.
|
||||
// Debug output
|
||||
ZmqLogger::Instance()->AppendDebugMethod("Clip::get_transform (Scale: SCALE_NONE)", "frame->number", frame->number, "source_width", source_size.width(), "source_height", source_size.height());
|
||||
break;
|
||||
|
||||
@@ -68,15 +68,13 @@ namespace openshot {
|
||||
CacheMemory cache;
|
||||
|
||||
/// Constructor for the base clip
|
||||
ClipBase() {
|
||||
// Initialize values
|
||||
position = 0.0;
|
||||
layer = 0;
|
||||
start = 0.0;
|
||||
end = 0.0;
|
||||
previous_properties = "";
|
||||
timeline = NULL;
|
||||
};
|
||||
ClipBase() :
|
||||
position(0.0),
|
||||
layer(0),
|
||||
start(0.0),
|
||||
end(0.0),
|
||||
previous_properties(""),
|
||||
timeline(nullptr) {}
|
||||
|
||||
// Compare a clip using the Position() property
|
||||
bool operator< ( ClipBase& a) { return (Position() < a.Position()); }
|
||||
|
||||
@@ -28,6 +28,8 @@
|
||||
* along with OpenShot Library. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#include <cmath>
|
||||
|
||||
#include "Color.h"
|
||||
#include "Exceptions.h"
|
||||
|
||||
|
||||
@@ -34,14 +34,14 @@
|
||||
using namespace openshot;
|
||||
|
||||
// Default constructor for a coordinate, delegating to the full signature
|
||||
Coordinate::Coordinate() : Coordinate::Coordinate(0, 0) {};
|
||||
Coordinate::Coordinate() : Coordinate::Coordinate(0, 0) {}
|
||||
|
||||
// Constructor which also allows the user to set the X and Y
|
||||
Coordinate::Coordinate(double x, double y) : X(x), Y(y) {};
|
||||
Coordinate::Coordinate(double x, double y) : X(x), Y(y) {}
|
||||
|
||||
// Constructor which accepts a std::pair for (X, Y)
|
||||
Coordinate::Coordinate(const std::pair<double, double>& co)
|
||||
: X(co.first), Y(co.second) {};
|
||||
: X(co.first), Y(co.second) {}
|
||||
|
||||
// Generate JSON string of this object
|
||||
std::string Coordinate::Json() const {
|
||||
|
||||
@@ -37,43 +37,57 @@
|
||||
|
||||
namespace openshot {
|
||||
|
||||
/**
|
||||
* @brief This class represents a Cartesian coordinate (X, Y) used in the Keyframe animation system.
|
||||
*
|
||||
* Animation involves the changing (i.e. interpolation) of numbers over time. A series of Coordinate
|
||||
* objects allows us to plot a specific curve or line used during interpolation. In other words, it helps us
|
||||
* control how a number changes over time (quickly or slowly).
|
||||
*
|
||||
* Please see the following <b>Example Code</b>:
|
||||
* \code
|
||||
* Coordinate c1(2,4);
|
||||
* assert(c1.X == 2.0f);
|
||||
* assert(c1.Y == 4.0f);
|
||||
* \endcode
|
||||
*/
|
||||
class Coordinate {
|
||||
public:
|
||||
double X; ///< The X value of the coordinate (usually representing the frame #)
|
||||
double Y; ///< The Y value of the coordinate (usually representing the value of the property being animated)
|
||||
/**
|
||||
* @brief A Cartesian coordinate (X, Y) used in the Keyframe animation system.
|
||||
*
|
||||
* Animation involves the changing (i.e. interpolation) of numbers over time.
|
||||
* A series of Coordinate objects allows us to plot a specific curve or line
|
||||
* used during interpolation. In other words, it helps us control how a
|
||||
* value changes over time — whether it's increasing or decreasing
|
||||
* (the direction of the slope) and how quickly (the steepness of the curve).
|
||||
*
|
||||
* Please see the following <b>Example Code</b>:
|
||||
* \code
|
||||
* Coordinate c1(2,4);
|
||||
* assert(c1.X == 2.0f);
|
||||
* assert(c1.Y == 4.0f);
|
||||
* \endcode
|
||||
*/
|
||||
class Coordinate {
|
||||
public:
|
||||
double X; ///< The X value of the coordinate (usually representing the frame #)
|
||||
double Y; ///< The Y value of the coordinate (usually representing the value of the property being animated)
|
||||
|
||||
/// The default constructor, which defaults to (0,0)
|
||||
Coordinate();
|
||||
/// The default constructor, which defaults to (0,0)
|
||||
Coordinate();
|
||||
|
||||
/// @brief Constructor which also sets the X and Y
|
||||
/// @param x The X coordinate (usually representing the frame #)
|
||||
/// @param y The Y coordinate (usually representing the value of the property being animated)
|
||||
Coordinate(double x, double y);
|
||||
/// @brief Constructor which also sets the X and Y
|
||||
/// @param x The X coordinate (usually representing the frame #)
|
||||
/// @param y The Y coordinate (usually representing the value of the property being animated)
|
||||
Coordinate(double x, double y);
|
||||
|
||||
/// @brief Constructor which accepts a std::pair tuple for {X, Y}
|
||||
/// @param co A std::pair<double, double> tuple containing (X, Y)
|
||||
Coordinate(const std::pair<double, double>& co);
|
||||
/// @brief Constructor which accepts a std::pair tuple for {X, Y}
|
||||
/// @param co A std::pair<double, double> tuple containing (X, Y)
|
||||
Coordinate(const std::pair<double, double>& co);
|
||||
|
||||
// Get and Set JSON methods
|
||||
std::string Json() const; ///< Generate JSON string of this object
|
||||
Json::Value JsonValue() const; ///< Generate Json::Value for this object
|
||||
void SetJson(const std::string value); ///< Load JSON string into this object
|
||||
void SetJsonValue(const Json::Value root); ///< Load Json::Value into this object
|
||||
};
|
||||
// Get and Set JSON methods
|
||||
std::string Json() const; ///< Generate JSON string of this object
|
||||
Json::Value JsonValue() const; ///< Generate Json::Value for this object
|
||||
void SetJson(const std::string value); ///< Load JSON string into this object
|
||||
void SetJsonValue(const Json::Value root); ///< Load Json::Value into this object
|
||||
};
|
||||
|
||||
/// Stream output operator for openshot::Coordinate
|
||||
template<class charT, class traits>
|
||||
std::basic_ostream<charT, traits>&
|
||||
operator<<(std::basic_ostream<charT, traits>& o, const openshot::Coordinate& co) {
|
||||
std::basic_ostringstream<charT, traits> s;
|
||||
s.flags(o.flags());
|
||||
s.imbue(o.getloc());
|
||||
s.precision(o.precision());
|
||||
s << "(" << co.X << ", " << co.Y << ")";
|
||||
return o << s.str();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
@@ -28,6 +28,9 @@
|
||||
* along with OpenShot Library. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#include <iostream>
|
||||
#include <iomanip>
|
||||
|
||||
#include "EffectBase.h"
|
||||
|
||||
#include "Exceptions.h"
|
||||
@@ -57,16 +60,16 @@ void EffectBase::InitEffectInfo()
|
||||
}
|
||||
|
||||
// Display file information
|
||||
void EffectBase::DisplayInfo() {
|
||||
std::cout << std::fixed << std::setprecision(2) << std::boolalpha;
|
||||
std::cout << "----------------------------" << std::endl;
|
||||
std::cout << "----- Effect Information -----" << std::endl;
|
||||
std::cout << "----------------------------" << std::endl;
|
||||
std::cout << "--> Name: " << info.name << std::endl;
|
||||
std::cout << "--> Description: " << info.description << std::endl;
|
||||
std::cout << "--> Has Video: " << info.has_video << std::endl;
|
||||
std::cout << "--> Has Audio: " << info.has_audio << std::endl;
|
||||
std::cout << "----------------------------" << std::endl;
|
||||
void EffectBase::DisplayInfo(std::ostream* out) {
|
||||
*out << std::fixed << std::setprecision(2) << std::boolalpha;
|
||||
*out << "----------------------------" << std::endl;
|
||||
*out << "----- Effect Information -----" << std::endl;
|
||||
*out << "----------------------------" << std::endl;
|
||||
*out << "--> Name: " << info.name << std::endl;
|
||||
*out << "--> Description: " << info.description << std::endl;
|
||||
*out << "--> Has Video: " << info.has_video << std::endl;
|
||||
*out << "--> Has Audio: " << info.has_audio << std::endl;
|
||||
*out << "----------------------------" << std::endl;
|
||||
}
|
||||
|
||||
// Constrain a color value from 0 to 255
|
||||
|
||||
@@ -87,7 +87,7 @@ namespace openshot
|
||||
EffectInfoStruct info;
|
||||
|
||||
/// Display effect information in the standard output stream (stdout)
|
||||
void DisplayInfo();
|
||||
void DisplayInfo(std::ostream* out=&std::cout);
|
||||
|
||||
/// Constrain a color value from 0 to 255
|
||||
int constrain(int color_value);
|
||||
|
||||
@@ -88,6 +88,33 @@ EffectBase* EffectInfo::CreateEffect(std::string effect_type) {
|
||||
else if (effect_type == "Wave")
|
||||
return new Wave();
|
||||
|
||||
else if(effect_type == "Noise")
|
||||
return new Noise();
|
||||
|
||||
else if(effect_type == "Delay")
|
||||
return new Delay();
|
||||
|
||||
else if(effect_type == "Echo")
|
||||
return new Echo();
|
||||
|
||||
else if(effect_type == "Distortion")
|
||||
return new Distortion();
|
||||
|
||||
else if(effect_type == "ParametricEQ")
|
||||
return new ParametricEQ();
|
||||
|
||||
else if(effect_type == "Compressor")
|
||||
return new Compressor();
|
||||
|
||||
else if(effect_type == "Expander")
|
||||
return new Expander();
|
||||
|
||||
else if(effect_type == "Robotization")
|
||||
return new Robotization();
|
||||
|
||||
else if(effect_type == "Whisperization")
|
||||
return new Whisperization();
|
||||
|
||||
#ifdef USE_OPENCV
|
||||
else if(effect_type == "Stabilizer")
|
||||
return new Stabilizer();
|
||||
@@ -124,6 +151,16 @@ Json::Value EffectInfo::JsonValue() {
|
||||
root.append(Saturation().JsonInfo());
|
||||
root.append(Shift().JsonInfo());
|
||||
root.append(Wave().JsonInfo());
|
||||
/* Audio */
|
||||
root.append(Noise().JsonInfo());
|
||||
root.append(Delay().JsonInfo());
|
||||
root.append(Echo().JsonInfo());
|
||||
root.append(Distortion().JsonInfo());
|
||||
root.append(ParametricEQ().JsonInfo());
|
||||
root.append(Compressor().JsonInfo());
|
||||
root.append(Expander().JsonInfo());
|
||||
root.append(Robotization().JsonInfo());
|
||||
root.append(Whisperization().JsonInfo());
|
||||
|
||||
#ifdef USE_OPENCV
|
||||
root.append(Stabilizer().JsonInfo());
|
||||
|
||||
@@ -48,6 +48,18 @@
|
||||
#include "effects/Shift.h"
|
||||
#include "effects/Wave.h"
|
||||
|
||||
/* Audio Effects */
|
||||
#include "audio_effects/Noise.h"
|
||||
#include "audio_effects/Delay.h"
|
||||
#include "audio_effects/Echo.h"
|
||||
#include "audio_effects/Distortion.h"
|
||||
#include "audio_effects/ParametricEQ.h"
|
||||
#include "audio_effects/Compressor.h"
|
||||
#include "audio_effects/Expander.h"
|
||||
#include "audio_effects/Robotization.h"
|
||||
#include "audio_effects/Whisperization.h"
|
||||
|
||||
/* OpenCV Effects */
|
||||
#ifdef USE_OPENCV
|
||||
#include "effects/ObjectDetection.h"
|
||||
#include "effects/Tracker.h"
|
||||
|
||||
53
src/Enums.h
53
src/Enums.h
@@ -80,5 +80,58 @@ namespace openshot
|
||||
VOLUME_MIX_AVERAGE, ///< Evenly divide the overlapping clips volume keyframes, so that the sum does not exceed 100%
|
||||
VOLUME_MIX_REDUCE ///< Reduce volume by about %25, and then mix (louder, but could cause pops if the sum exceeds 100%)
|
||||
};
|
||||
|
||||
|
||||
/// This enumeration determines the distortion type of Distortion Effect.
|
||||
enum DistortionType
|
||||
{
|
||||
HARD_CLIPPING,
|
||||
SOFT_CLIPPING,
|
||||
EXPONENTIAL,
|
||||
FULL_WAVE_RECTIFIER,
|
||||
HALF_WAVE_RECTIFIER,
|
||||
};
|
||||
|
||||
/// This enumeration determines the filter type of ParametricEQ Effect.
|
||||
enum FilterType
|
||||
{
|
||||
LOW_PASS,
|
||||
HIGH_PASS,
|
||||
LOW_SHELF,
|
||||
HIGH_SHELF,
|
||||
BAND_PASS,
|
||||
BAND_STOP,
|
||||
PEAKING_NOTCH,
|
||||
};
|
||||
|
||||
/// This enumeration determines the FFT size.
|
||||
enum FFTSize
|
||||
{
|
||||
FFT_SIZE_32,
|
||||
FFT_SIZE_64,
|
||||
FFT_SIZE_128,
|
||||
FFT_SIZE_256,
|
||||
FFT_SIZE_512,
|
||||
FFT_SIZE_1024,
|
||||
FFT_SIZE_2048,
|
||||
FFT_SIZE_4096,
|
||||
FFT_SIZE_8192,
|
||||
};
|
||||
|
||||
/// This enumeration determines the hop size.
|
||||
enum HopSize {
|
||||
HOP_SIZE_2,
|
||||
HOP_SIZE_4,
|
||||
HOP_SIZE_8,
|
||||
};
|
||||
|
||||
/// This enumeration determines the window type.
|
||||
enum WindowType {
|
||||
RECTANGULAR,
|
||||
BART_LETT,
|
||||
HANN,
|
||||
HAMMING,
|
||||
};
|
||||
|
||||
}
|
||||
#endif
|
||||
|
||||
@@ -33,6 +33,7 @@
|
||||
|
||||
#include "FFmpegReader.h"
|
||||
#include "Exceptions.h"
|
||||
#include "Timeline.h"
|
||||
|
||||
#include <thread> // for std::this_thread::sleep_for
|
||||
#include <chrono> // for std::chrono::milliseconds
|
||||
@@ -768,12 +769,12 @@ void FFmpegReader::UpdateVideoInfo() {
|
||||
// Check for valid duration (if found)
|
||||
if (info.duration <= 0.0f && pFormatCtx->duration >= 0)
|
||||
// Use the format's duration
|
||||
info.duration = pFormatCtx->duration / AV_TIME_BASE;
|
||||
info.duration = float(pFormatCtx->duration) / AV_TIME_BASE;
|
||||
|
||||
// Calculate duration from filesize and bitrate (if any)
|
||||
if (info.duration <= 0.0f && info.video_bit_rate > 0 && info.file_size > 0)
|
||||
// Estimate from bitrate, total bytes, and framerate
|
||||
info.duration = (info.file_size / info.video_bit_rate);
|
||||
info.duration = float(info.file_size) / info.video_bit_rate;
|
||||
|
||||
// No duration found in stream of file
|
||||
if (info.duration <= 0.0f) {
|
||||
@@ -1285,9 +1286,18 @@ void FFmpegReader::ProcessVideoPacket(int64_t requested_frame) {
|
||||
}
|
||||
|
||||
} else {
|
||||
// No scaling, use original image size (slower)
|
||||
max_width = info.width;
|
||||
max_height = info.height;
|
||||
// Scale video to equivalent unscaled size
|
||||
// Since the preview window can change sizes, we want to always
|
||||
// scale against the ratio of original video size to timeline size
|
||||
float preview_ratio = 1.0;
|
||||
if (parent->ParentTimeline()) {
|
||||
Timeline *t = (Timeline *) parent->ParentTimeline();
|
||||
preview_ratio = t->preview_width / float(t->info.width);
|
||||
}
|
||||
float max_scale_x = parent->scale_x.GetMaxPoint().co.Y;
|
||||
float max_scale_y = parent->scale_y.GetMaxPoint().co.Y;
|
||||
max_width = info.width * max_scale_x * preview_ratio;
|
||||
max_height = info.height * max_scale_y * preview_ratio;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user