├── .github ├── FUNDING.yml └── ISSUE_TEMPLATE │ ├── feature-request.md │ └── issue-report.md ├── .gitignore ├── Assets ├── LiveVisionKit_Logo.png ├── LiveVisionKit_MiniLogo.png ├── LiveVisionKit_SplashScreen.png └── LiveVisionKit_Watermark.png ├── CMakeLists.txt ├── LICENSE ├── LiveVisionKit ├── CMakeLists.txt ├── Data │ ├── Iterators.hpp │ ├── Iterators.tpp │ ├── SpatialMap.hpp │ ├── SpatialMap.tpp │ ├── StreamBuffer.hpp │ ├── StreamBuffer.tpp │ ├── VideoFrame.cpp │ └── VideoFrame.hpp ├── Directives.cpp ├── Directives.hpp ├── Filters │ ├── CompositeFilter.cpp │ ├── CompositeFilter.hpp │ ├── ConversionFilter.cpp │ ├── ConversionFilter.hpp │ ├── DeblockingFilter.cpp │ ├── DeblockingFilter.hpp │ ├── ScalingFilter.cpp │ ├── ScalingFilter.hpp │ ├── StabilizationFilter.cpp │ ├── StabilizationFilter.hpp │ ├── VideoFilter.cpp │ └── VideoFilter.hpp ├── Functions │ ├── Container.hpp │ ├── Container.tpp │ ├── Drawing.hpp │ ├── Drawing.tpp │ ├── Extensions.cpp │ ├── Extensions.hpp │ ├── Image.cpp │ ├── Image.hpp │ ├── Logic.hpp │ ├── Logic.tpp │ ├── Math.hpp │ ├── Math.tpp │ ├── OpenCL │ │ ├── Kernels.cpp │ │ ├── Kernels.hpp │ │ └── Sources │ │ │ ├── Drawing.cl │ │ │ └── FSR.cl │ ├── Text.hpp │ └── Text.tpp ├── LiveVisionKit.hpp ├── Logging │ ├── CSVLogger.cpp │ ├── CSVLogger.hpp │ ├── Logger.hpp │ └── Logger.tpp ├── Math │ ├── BoundingQuad.cpp │ ├── BoundingQuad.hpp │ ├── Homography.cpp │ ├── Homography.hpp │ ├── VirtualGrid.cpp │ ├── VirtualGrid.hpp │ ├── WarpMesh.cpp │ └── WarpMesh.hpp ├── Timing │ ├── Stopwatch.cpp │ ├── Stopwatch.hpp │ ├── TickTimer.cpp │ ├── TickTimer.hpp │ ├── Time.cpp │ └── Time.hpp ├── Utility │ ├── Configurable.hpp │ ├── Configurable.tpp │ ├── Unique.hpp │ └── Unique.tpp └── Vision │ ├── CameraCalibrator.cpp │ ├── CameraCalibrator.hpp │ ├── FeatureDetector.cpp │ ├── FeatureDetector.hpp │ ├── FrameTracker.cpp │ ├── FrameTracker.hpp │ ├── PathSmoother.cpp │ └── PathSmoother.hpp ├── Modules ├── OBS-Plugin │ ├── CMakeLists.txt │ ├── Data │ │ ├── effects │ │ │ ├── cas.effect │ │ │ ├── ffx_a.h │ │ │ ├── ffx_a_mod.h │ │ │ ├── ffx_cas.h │ │ │ ├── ffx_cas_mod.h │ │ │ ├── ffx_fsr1.h │ │ │ ├── ffx_fsr1_mod.h │ │ │ └── fsr.effect │ │ └── locale │ │ │ ├── en-GB.ini │ │ │ ├── en-US.ini │ │ │ ├── es-ES.ini │ │ │ ├── nl-NL.ini │ │ │ ├── ru-RU.ini │ │ │ ├── uk-UA.ini │ │ │ └── zh-TW.ini │ ├── Effects │ │ ├── CASEffect.cpp │ │ ├── CASEffect.hpp │ │ ├── DefaultEffect.cpp │ │ ├── DefaultEffect.hpp │ │ ├── FSREffect.cpp │ │ ├── FSREffect.hpp │ │ ├── OBSEffect.hpp │ │ └── OBSEffect.tpp │ ├── Interop │ │ ├── FrameIngest.cpp │ │ ├── FrameIngest.hpp │ │ ├── InteropContext.cpp │ │ ├── InteropContext.hpp │ │ ├── OBSFrame.cpp │ │ ├── OBSFrame.hpp │ │ ├── VisionFilter.cpp │ │ └── VisionFilter.hpp │ ├── Sources │ │ ├── Enhancement │ │ │ ├── ADBFilter.cpp │ │ │ ├── ADBFilter.hpp │ │ │ ├── ADBSource.cpp │ │ │ ├── CASFilter.cpp │ │ │ ├── CASFilter.hpp │ │ │ ├── CASSource.cpp │ │ │ ├── LCFilter.cpp │ │ │ ├── LCFilter.hpp │ │ │ └── LCSource.cpp │ │ ├── Module.cpp │ │ ├── Scaling │ │ │ ├── FSRFilter.cpp │ │ │ ├── FSRFilter.hpp │ │ │ └── FSRSource.cpp │ │ ├── Stabilisation │ │ │ ├── VSFilter.cpp │ │ │ ├── VSFilter.hpp │ │ │ └── VSSource.cpp │ │ └── Tools │ │ │ ├── CCSource.cpp │ │ │ ├── CCTool.cpp │ │ │ ├── CCTool.hpp │ │ │ ├── IngestTestFilter.cpp │ │ │ ├── IngestTestFilter.hpp │ │ │ └── IngestTestSource.cpp │ └── Utility │ │ ├── 3rdParty │ │ ├── glad.c │ │ ├── glad.h │ │ └── khrplatform.h │ │ ├── Graphics.cpp │ │ ├── Graphics.hpp │ │ ├── Locale.hpp │ │ ├── Logging.hpp │ │ ├── Logging.tpp │ │ ├── OBSDispatch.hpp │ │ ├── OBSDispatch.tpp │ │ ├── ScopedProfiler.cpp │ │ └── ScopedProfiler.hpp └── VideoEditor │ ├── Application.cpp │ ├── CMakeLists.txt │ ├── ConsoleLogger.cpp │ ├── ConsoleLogger.hpp │ ├── FilterParser.hpp │ ├── FilterParser.tpp │ ├── OptionParser.hpp │ ├── OptionParser.tpp │ ├── VideoIOConfiguration.cpp │ ├── VideoIOConfiguration.hpp │ ├── VideoProcessor.cpp │ └── VideoProcessor.hpp ├── README.md └── Scripts ├── build_deb.sh ├── build_w64.ps1 ├── setup_deb.sh └── setup_w64.ps1 /.github/FUNDING.yml: -------------------------------------------------------------------------------- 1 | # These are supported funding model platforms 2 | 3 | custom: [paypal.me/crowsinc] 4 | 5 | 6 | 7 | -------------------------------------------------------------------------------- /.github/ISSUE_TEMPLATE/feature-request.md: -------------------------------------------------------------------------------- 1 | --- 2 | name: Feature Request 3 | about: Suggest an idea for this project 4 | title: '' 5 | labels: Feature 6 | assignees: '' 7 | 8 | --- 9 | 10 | **What is the requested feature?** 11 | *Describe what it is and what it's supposed to accomplish.* 12 | 13 | 14 | **Why do you want this feature?** 15 | *Describe why it's needed, what problems it solves.* 16 | *If it is related to an issue, reference it here.* 17 | 18 | 19 | **Possible Use Cases** 20 | *Describe at least three different use cases in which this feature is useful.* 21 | 22 | 23 | **Examples** 24 | *List any academic research or existing implementations of this feature.* 25 | 26 | 27 | **Appendix** 28 | *Write anything useful which is not directly related to one of the questions above* 29 | -------------------------------------------------------------------------------- /.github/ISSUE_TEMPLATE/issue-report.md: -------------------------------------------------------------------------------- 1 | --- 2 | name: Issue Report 3 | about: Create a report to help us improve 4 | title: '' 5 | labels: Issue 6 | assignees: '' 7 | 8 | --- 9 | 10 | **System/Software Setup** 11 | - **LiveVisionKit Version:** *The version of LiveVisionKit in use.* 12 | - **OBS Studio Version:** *The version of OBS Studio in use.* 13 | - **OS:** *Windows 10, Windows 11, or the specific Linux distribution.* 14 | - **GPU:** *The graphics card and graphics driver version in use.* 15 | - **CPU:** *The processor in use.* 16 | 17 | **OBS Log:**: *A link to the OBS log corresponding with the issue. This can be done through OBS by going to - Help -> Log Files -> Upload Current Log File* 18 | 19 | **Issue Description** 20 | *Provide a clear and concise description of the issue.* 21 | 22 | **Expected Behavior** 23 | *Provide a clear and concise description of what should happen instead.* 24 | 25 | **Reproduction Steps** 26 | *Provide clear, numbered, instructions on how to reproduce the issue. If the reproduction steps look like "I opened OBS and it didn't work", then please provide more information about your OBS setup instead.* 27 | 28 | **Supporting Evidence** 29 | *If the issue is related to filter performance in a specific scene/scenario, you should provide a YouTube or Twitch link to a video which displays the issue, both with test mode on and off if the filter supports it.* 30 | 31 | **Appendix** 32 | *Write anything useful which is not directly related to one of the questions above* 33 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | # Prerequisites 2 | *.d 3 | 4 | # Compiled Object files 5 | *.slo 6 | *.lo 7 | *.o 8 | *.obj 9 | 10 | # Precompiled Headers 11 | *.gch 12 | *.pch 13 | 14 | # Compiled Dynamic libraries 15 | *.so 16 | *.dylib 17 | *.dll 18 | 19 | # Compiled Static libraries 20 | *.lai 21 | *.la 22 | *.a 23 | *.lib 24 | 25 | # Executables 26 | *.exe 27 | *.out 28 | 29 | # Eclipse CDT 30 | **/.project 31 | **/.cproject 32 | **/.autotools 33 | **/.settings/ 34 | .metadata/ 35 | **/Debug/ 36 | **/Release/ 37 | 38 | # Visual Studio 39 | *.sln 40 | *.vcxproj* 41 | **/.vs/ 42 | **/[Dd]ebug/ 43 | **/[Rr]elease/ 44 | **/x64/ 45 | **/x86/ 46 | **/ipch/ 47 | *.suo 48 | *.csproj.user 49 | *.vbproj.user 50 | *.aps 51 | *.ncb 52 | *.opendb 53 | *.opensdf 54 | *.sdf 55 | *.cachefile 56 | *.VC.db 57 | *.VC.VC.opendb 58 | *.rsuser 59 | *.user 60 | *.userosscache 61 | *.sln.docstates 62 | *.psess 63 | *.vsp 64 | *.vspx 65 | *.sap 66 | *.coverage 67 | *.coveragexml 68 | *_i.c 69 | *_p.c 70 | *_h.h 71 | *.ilk 72 | *.meta 73 | *.iobj 74 | *.pdb 75 | *.ipdb 76 | *.pgc 77 | *.pgd 78 | *.rsp 79 | *.sbr 80 | *.tlb 81 | *.tli 82 | *.tlh 83 | *.tmp 84 | *.tmp_proj 85 | *_wpftmp.csproj 86 | *.log 87 | *.tlog 88 | *.vspscc 89 | *.vssscc 90 | .builds 91 | *.pidb 92 | *.svclog 93 | *.scc 94 | 95 | # JetBrains 96 | .idea/ 97 | .idea/**/workspace.xml 98 | .idea/**/tasks.xml 99 | .idea/**/usage.statistics.xml 100 | .idea/**/dictionaries 101 | .idea/**/shelf 102 | .idea/**/aws.xml 103 | .idea/**/contentModel.xml 104 | .idea/**/dataSources/ 105 | .idea/**/dataSources.ids 106 | .idea/**/dataSources.local.xml 107 | .idea/**/sqlDataSources.xml 108 | .idea/**/dynamic.xml 109 | .idea/**/uiDesigner.xml 110 | .idea/**/dbnavigator.xml 111 | cmake-build-*/ 112 | .idea/**/mongoSettings.xml 113 | *.iws 114 | 115 | # Build System 116 | **/[Bb]uild/ 117 | **/[Dd]ependencies/ 118 | CMakeLists.txt.user 119 | CMakeCache.txt 120 | CMakeFiles 121 | CMakeScripts 122 | Testing 123 | Makefile 124 | cmake_install.cmake 125 | install_manifest.txt 126 | compile_commands.json 127 | CTestTestfile.cmake 128 | _deps -------------------------------------------------------------------------------- /Assets/LiveVisionKit_Logo.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Crowsinc/LiveVisionKit/2f7bb7065000fcd1b0c21e4acfe058acc27f309e/Assets/LiveVisionKit_Logo.png -------------------------------------------------------------------------------- /Assets/LiveVisionKit_MiniLogo.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Crowsinc/LiveVisionKit/2f7bb7065000fcd1b0c21e4acfe058acc27f309e/Assets/LiveVisionKit_MiniLogo.png -------------------------------------------------------------------------------- /Assets/LiveVisionKit_SplashScreen.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Crowsinc/LiveVisionKit/2f7bb7065000fcd1b0c21e4acfe058acc27f309e/Assets/LiveVisionKit_SplashScreen.png -------------------------------------------------------------------------------- /Assets/LiveVisionKit_Watermark.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Crowsinc/LiveVisionKit/2f7bb7065000fcd1b0c21e4acfe058acc27f309e/Assets/LiveVisionKit_Watermark.png -------------------------------------------------------------------------------- /CMakeLists.txt: -------------------------------------------------------------------------------- 1 | cmake_minimum_required(VERSION 3.21) 2 | 3 | if(APPLE) 4 | message(FATAL_ERROR "Apple systems are not supported!") 5 | endif() 6 | 7 | set(MI " ") # Message indents 8 | set_property(GLOBAL PROPERTY USE_FOLDERS ON) 9 | set_property(GLOBAL PROPERTY PREDEFINED_TARGETS_FOLDER "CMakeTargets") 10 | 11 | 12 | # Set up project 13 | project(LiveVisionKit) 14 | message(STATUS "\nConfiguring LiveVisionKit...") 15 | 16 | # Project defines 17 | set(LVK_CORE_DIR "${CMAKE_CURRENT_SOURCE_DIR}/LiveVisionKit/") 18 | set(LVK_RELEASES_DIR "Releases") 19 | set(LVK_INCLUDES_DIR "Include") 20 | set(LVK_BINARY_DIR "Binaries") 21 | set(LVK_DEBUG_POSTFIX "d") 22 | 23 | # Set default install location 24 | if(CMAKE_INSTALL_PREFIX_INITIALIZED_TO_DEFAULT) 25 | set( 26 | CMAKE_INSTALL_PREFIX 27 | "${CMAKE_BINARY_DIR}/Install/" 28 | CACHE PATH 29 | "The location to which build files will be installed" 30 | FORCE 31 | ) 32 | endif(CMAKE_INSTALL_PREFIX_INITIALIZED_TO_DEFAULT) 33 | 34 | # Project settings 35 | set(BUILD_OBS_PLUGIN "ON" CACHE BOOL "Build the OBS-Studio plugin") 36 | set(BUILD_VIDEO_EDITOR "ON" CACHE BOOL "Build the video editor CLT") 37 | set(DISABLE_CHECKS "OFF" CACHE BOOL "Compile without asserts and pre-condition checks") 38 | set(OPENCV_BUILD_PATH "./Dependencies/opencv/build/" CACHE PATH "The path to the OpenCV build folder") 39 | 40 | # Load common dependencies (OpenCV) 41 | find_package(OpenCV REQUIRED PATHS ${OPENCV_BUILD_PATH} NO_DEFAULT_PATH) 42 | if(OpenCV_FOUND) 43 | message(STATUS "${MI}Found OpenCV: YES") 44 | message(STATUS "${MI}OpenCV Version: ${OpenCV_VERSION}") 45 | message(STATUS "${MI}OpenCV Modules: ${OpenCV_LIBS}") 46 | else() 47 | message(FATAL_ERROR "Failed to find OpenCV!") 48 | endif() 49 | 50 | # If we are on Linux, we also need to load QT for OpenCV 51 | if(UNIX) 52 | find_package(Qt5 REQUIRED Core Gui Widgets Test Concurrent OpenGL) 53 | endif() 54 | 55 | # Load sub-modules 56 | add_subdirectory(LiveVisionKit) 57 | 58 | if(BUILD_VIDEO_EDITOR) 59 | message(STATUS "\nBuilding with video editor CLT...") 60 | add_subdirectory(Modules/VideoEditor) 61 | endif() 62 | 63 | if(BUILD_OBS_PLUGIN) 64 | message(STATUS "\nBuilding with LVK OBS-Studio plugin...") 65 | add_subdirectory(Modules/OBS-Plugin) 66 | endif() 67 | 68 | message(STATUS "\n") 69 | -------------------------------------------------------------------------------- /LiveVisionKit/Data/Iterators.hpp: -------------------------------------------------------------------------------- 1 | // *************************** LiveVisionKit **************************** 2 | // Copyright (C) 2022 Sebastian Di Marco (crowsinc.dev@gmail.com) 3 | // 4 | // This program is free software: you can redistribute it and/or modify 5 | // it under the terms of the GNU General Public License as published by 6 | // the Free Software Foundation, either version 3 of the License, or 7 | // (at your option) any later version. 8 | // 9 | // This program is distributed in the hope that it will be useful, 10 | // but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | // GNU General Public License for more details. 13 | // 14 | // You should have received a copy of the GNU General Public License 15 | // along with this program. If not, see . 16 | // ********************************************************************** 17 | 18 | #pragma once 19 | 20 | #include 21 | 22 | namespace lvk 23 | { 24 | 25 | template 26 | struct CircularIterator 27 | { 28 | using value_type = T; using pointer = P; using reference = R; 29 | using iterator_category = std::bidirectional_iterator_tag; 30 | using difference_type = std::ptrdiff_t; 31 | 32 | // NOTE: bounds represent accessible memory pointers. 33 | CircularIterator( 34 | pointer ptr, 35 | const std::pair data_bounds, 36 | const std::pair access_bounds, 37 | const int cycle = 0 38 | ); 39 | 40 | pointer operator->(); 41 | reference operator*() const; 42 | 43 | CircularIterator& operator++(); 44 | const CircularIterator operator++(int) const; 45 | 46 | CircularIterator& operator--(); 47 | const CircularIterator operator--(int) const; 48 | 49 | bool operator==(const CircularIterator&) const; 50 | bool operator!=(const CircularIterator&) const; 51 | 52 | difference_type operator-(const CircularIterator&) const; 53 | 54 | private: 55 | const std::pair m_DataBounds; 56 | const std::pair m_AccessBounds; 57 | 58 | pointer m_Current; 59 | int m_Cycle = 0; 60 | }; 61 | 62 | template 63 | using circular_iterator = CircularIterator; 64 | 65 | template 66 | using const_circular_iterator = CircularIterator; 67 | } 68 | 69 | 70 | #include "Iterators.tpp" -------------------------------------------------------------------------------- /LiveVisionKit/Data/StreamBuffer.hpp: -------------------------------------------------------------------------------- 1 | // *************************** LiveVisionKit **************************** 2 | // Copyright (C) 2022 Sebastian Di Marco (crowsinc.dev@gmail.com) 3 | // 4 | // This program is free software: you can redistribute it and/or modify 5 | // it under the terms of the GNU General Public License as published by 6 | // the Free Software Foundation, either version 3 of the License, or 7 | // (at your option) any later version. 8 | // 9 | // This program is distributed in the hope that it will be useful, 10 | // but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | // GNU General Public License for more details. 13 | // 14 | // You should have received a copy of the GNU General Public License 15 | // along with this program. If not, see . 16 | // ********************************************************************** 17 | 18 | #pragma once 19 | 20 | #include 21 | #include 22 | 23 | #include "Iterators.hpp" 24 | 25 | namespace lvk 26 | { 27 | 28 | template 29 | class StreamBuffer 30 | { 31 | public: 32 | using iterator = lvk::circular_iterator; 33 | using const_iterator = lvk::const_circular_iterator; 34 | public: 35 | 36 | explicit StreamBuffer(const size_t capacity); 37 | 38 | 39 | void push(T&& element); 40 | 41 | void push(const T& element); 42 | 43 | template 44 | T& advance(Args&&... args); 45 | 46 | 47 | T&& pop_oldest(); 48 | 49 | 50 | template 51 | void pad_front(Args&&... args); 52 | 53 | template 54 | void pad_back(Args&&... args); 55 | 56 | template 57 | void fill(Args&&... args); 58 | 59 | 60 | void trim(const size_t amount); 61 | 62 | void skip(const size_t amount = 1); 63 | 64 | 65 | void resize(const size_t capacity); 66 | 67 | void clear(); 68 | 69 | 70 | T& at(const size_t index); 71 | 72 | const T& at(const size_t index) const; 73 | 74 | T& operator[](const size_t index); 75 | 76 | const T& operator[](const size_t index) const; 77 | 78 | 79 | T& oldest(const int offset = 0); 80 | 81 | const T& oldest(const int offset = 0) const; 82 | 83 | T& centre(const int offset = 0); 84 | 85 | const T& centre(const int offset = 0) const; 86 | 87 | T& newest(const int offset = 0); 88 | 89 | const T& newest(const int offset = 0) const; 90 | 91 | 92 | bool is_full() const; 93 | 94 | bool is_empty() const; 95 | 96 | size_t size() const; 97 | 98 | size_t capacity() const; 99 | 100 | size_t centre_index() const; 101 | 102 | 103 | template 104 | StreamBuffer convolve(const StreamBuffer& kernel) const; 105 | 106 | template 107 | T convolve_at(const StreamBuffer& kernel, const size_t index) const; 108 | 109 | 110 | iterator begin(); 111 | 112 | const_iterator begin() const; 113 | 114 | const_iterator cbegin() const; 115 | 116 | 117 | iterator end(); 118 | 119 | const_iterator end() const; 120 | 121 | const_iterator cend() const; 122 | 123 | 124 | private: 125 | void advance_window(); 126 | 127 | size_t m_Capacity, m_Size = 0; 128 | std::vector m_InternalBuffer; 129 | size_t m_StartIndex = 0, m_EndIndex = 0; 130 | }; 131 | 132 | 133 | template 134 | std::ostream& operator<<(std::ostream& stream, const StreamBuffer& buffer); 135 | 136 | } 137 | 138 | #include "StreamBuffer.tpp" 139 | -------------------------------------------------------------------------------- /LiveVisionKit/Data/VideoFrame.hpp: -------------------------------------------------------------------------------- 1 | // *************************** LiveVisionKit **************************** 2 | // Copyright (C) 2022 Sebastian Di Marco (crowsinc.dev@gmail.com) 3 | // 4 | // This program is free software: you can redistribute it and/or modify 5 | // it under the terms of the GNU General Public License as published by 6 | // the Free Software Foundation, either version 3 of the License, or 7 | // (at your option) any later version. 8 | // 9 | // This program is distributed in the hope that it will be useful, 10 | // but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | // GNU General Public License for more details. 13 | // 14 | // You should have received a copy of the GNU General Public License 15 | // along with this program. If not, see . 16 | // ********************************************************************** 17 | 18 | #pragma once 19 | 20 | #include 21 | 22 | namespace lvk 23 | { 24 | // NOTE: use camelCase to match the cv::UMat API. 25 | struct VideoFrame : public cv::UMat 26 | { 27 | enum Format {BGR, BGRA, RGB, RGBA, YUV, GRAY, UNKNOWN}; 28 | 29 | uint64_t timestamp = 0; 30 | Format format = UNKNOWN; 31 | int& width = cols; int& height = rows; 32 | 33 | public: 34 | 35 | VideoFrame(); 36 | 37 | VideoFrame(const VideoFrame& frame); 38 | 39 | VideoFrame(VideoFrame&& frame) noexcept; 40 | 41 | explicit VideoFrame(const uint64_t timestamp); 42 | 43 | explicit VideoFrame(const cv::UMat& frame, const uint64_t timestamp = 0, const Format format = UNKNOWN); 44 | 45 | explicit VideoFrame(cv::UMat&& frame, const uint64_t timestamp = 0, const Format format = UNKNOWN) noexcept; 46 | 47 | 48 | virtual ~VideoFrame() = default; 49 | 50 | 51 | VideoFrame& operator=(VideoFrame&& frame) noexcept; 52 | 53 | VideoFrame& operator=(const VideoFrame& frame) noexcept; 54 | 55 | 56 | VideoFrame clone() const; /* override */ 57 | 58 | void copyTo(VideoFrame& dst) const; /* override */ 59 | 60 | void copyTo(VideoFrame& dst, cv::InputArray mask) const; /* override */ 61 | 62 | void copyTo(cv::OutputArray dst) const; /* override */ 63 | 64 | void copyTo(cv::OutputArray dst, cv::InputArray mask) const; /* override */ 65 | 66 | 67 | VideoFrame operator()(const cv::Rect& roi) const; /* override */ 68 | 69 | 70 | bool has_known_format() const; 71 | 72 | void reformat(const Format new_format); 73 | 74 | void reformatTo(VideoFrame& dst, const Format new_format) const; 75 | 76 | // NOTE: Ownership of the view is undefined and should not be modified. 77 | void viewAsFormat(VideoFrame& view, const Format new_format) const; 78 | 79 | }; 80 | 81 | typedef VideoFrame Frame; 82 | 83 | } -------------------------------------------------------------------------------- /LiveVisionKit/Directives.cpp: -------------------------------------------------------------------------------- 1 | // *************************** LiveVisionKit **************************** 2 | // Copyright (C) 2022 Sebastian Di Marco (crowsinc.dev@gmail.com) 3 | // 4 | // This program is free software: you can redistribute it and/or modify 5 | // it under the terms of the GNU General Public License as published by 6 | // the Free Software Foundation, either version 3 of the License, or 7 | // (at your option) any later version. 8 | // 9 | // This program is distributed in the hope that it will be useful, 10 | // but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | // GNU General Public License for more details. 13 | // 14 | // You should have received a copy of the GNU General Public License 15 | // along with this program. If not, see . 16 | // ********************************************************************** 17 | 18 | #include "Directives.hpp" 19 | 20 | #include 21 | #include 22 | 23 | #include "Timing/Time.hpp" 24 | 25 | //--------------------------------------------------------------------------------------------------------------------- 26 | 27 | std::function lvk::context::assert_handler = []( 28 | std::string file, 29 | std::string function, 30 | std::string assertion 31 | ) 32 | { 33 | std::cerr 34 | << Time::Timestamp("%F %T: ") 35 | << "Failed Assert " 36 | << file << "@" 37 | << function << "(..) ... " 38 | << assertion 39 | << std::endl; 40 | 41 | std::abort(); 42 | }; 43 | 44 | //--------------------------------------------------------------------------------------------------------------------- 45 | -------------------------------------------------------------------------------- /LiveVisionKit/Filters/CompositeFilter.hpp: -------------------------------------------------------------------------------- 1 | // *************************** LiveVisionKit **************************** 2 | // Copyright (C) 2022 Sebastian Di Marco (crowsinc.dev@gmail.com) 3 | // 4 | // This program is free software: you can redistribute it and/or modify 5 | // it under the terms of the GNU General Public License as published by 6 | // the Free Software Foundation, either version 3 of the License, or 7 | // (at your option) any later version. 8 | // 9 | // This program is distributed in the hope that it will be useful, 10 | // but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | // GNU General Public License for more details. 13 | // 14 | // You should have received a copy of the GNU General Public License 15 | // along with this program. If not, see . 16 | // ********************************************************************** 17 | 18 | #pragma once 19 | 20 | #include 21 | 22 | #include "VideoFilter.hpp" 23 | #include "Utility/Configurable.hpp" 24 | 25 | namespace lvk 26 | { 27 | 28 | struct CompositeFilterSettings 29 | { 30 | std::vector> filter_chain; 31 | bool save_outputs = false; 32 | 33 | // TODO: add pipelineing option 34 | }; 35 | 36 | class CompositeFilter final : public VideoFilter, public Configurable 37 | { 38 | public: 39 | 40 | explicit CompositeFilter(const CompositeFilterSettings& settings = {}); 41 | 42 | CompositeFilter( 43 | const std::initializer_list>& filter_chain, 44 | const CompositeFilterSettings& settings = {} 45 | ); 46 | 47 | void configure(const CompositeFilterSettings& settings) override; 48 | 49 | const std::vector>& filters() const; 50 | 51 | std::shared_ptr filters(const size_t index); 52 | 53 | const std::vector& outputs() const; 54 | 55 | const VideoFrame& outputs(const size_t index); 56 | 57 | bool is_filter_enabled(const size_t index); 58 | 59 | void disable_filter(const size_t index); 60 | 61 | void enable_filter(const size_t index); 62 | 63 | void enable_all_filters(); 64 | 65 | size_t filter_count() const; 66 | 67 | private: 68 | 69 | void filter(VideoFrame&& input, VideoFrame& output) override; 70 | 71 | std::vector m_FilterRunState; 72 | std::vector m_FilterOutputs; 73 | }; 74 | 75 | } 76 | 77 | -------------------------------------------------------------------------------- /LiveVisionKit/Filters/ConversionFilter.cpp: -------------------------------------------------------------------------------- 1 | // *************************** LiveVisionKit **************************** 2 | // Copyright (C) 2022 Sebastian Di Marco (crowsinc.dev@gmail.com) 3 | // 4 | // This program is free software: you can redistribute it and/or modify 5 | // it under the terms of the GNU General Public License as published by 6 | // the Free Software Foundation, either version 3 of the License, or 7 | // (at your option) any later version. 8 | // 9 | // This program is distributed in the hope that it will be useful, 10 | // but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | // GNU General Public License for more details. 13 | // 14 | // You should have received a copy of the GNU General Public License 15 | // along with this program. If not, see . 16 | // ********************************************************************** 17 | 18 | #include "ConversionFilter.hpp" 19 | 20 | namespace lvk 21 | { 22 | 23 | //--------------------------------------------------------------------------------------------------------------------- 24 | 25 | ConversionFilter::ConversionFilter(const ConversionFilterSettings& settings) 26 | : VideoFilter("Conversion Filter") 27 | { 28 | configure(settings); 29 | } 30 | 31 | //--------------------------------------------------------------------------------------------------------------------- 32 | 33 | ConversionFilter::ConversionFilter(const cv::ColorConversionCodes conversion_code) 34 | : ConversionFilter(ConversionFilterSettings{.conversion_code = conversion_code}) 35 | {} 36 | 37 | //--------------------------------------------------------------------------------------------------------------------- 38 | 39 | void ConversionFilter::configure(const ConversionFilterSettings& settings) 40 | { 41 | m_Settings = settings; 42 | } 43 | 44 | //--------------------------------------------------------------------------------------------------------------------- 45 | 46 | void ConversionFilter::filter(VideoFrame&& input, VideoFrame& output) 47 | { 48 | LVK_ASSERT(!input.empty()); 49 | 50 | cv::cvtColor( 51 | input, 52 | input, 53 | m_Settings.conversion_code, 54 | static_cast(m_Settings.output_channels.value_or(0)) 55 | ); 56 | 57 | output = std::move(input); 58 | } 59 | 60 | //--------------------------------------------------------------------------------------------------------------------- 61 | 62 | } -------------------------------------------------------------------------------- /LiveVisionKit/Filters/ConversionFilter.hpp: -------------------------------------------------------------------------------- 1 | // *************************** LiveVisionKit **************************** 2 | // Copyright (C) 2022 Sebastian Di Marco (crowsinc.dev@gmail.com) 3 | // 4 | // This program is free software: you can redistribute it and/or modify 5 | // it under the terms of the GNU General Public License as published by 6 | // the Free Software Foundation, either version 3 of the License, or 7 | // (at your option) any later version. 8 | // 9 | // This program is distributed in the hope that it will be useful, 10 | // but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | // GNU General Public License for more details. 13 | // 14 | // You should have received a copy of the GNU General Public License 15 | // along with this program. If not, see . 16 | // ********************************************************************** 17 | 18 | #pragma once 19 | 20 | #include 21 | #include 22 | 23 | #include "VideoFilter.hpp" 24 | #include "Utility/Configurable.hpp" 25 | 26 | namespace lvk 27 | { 28 | 29 | struct ConversionFilterSettings 30 | { 31 | cv::ColorConversionCodes conversion_code = cv::COLOR_BGR2YUV; 32 | std::optional output_channels; 33 | }; 34 | 35 | class ConversionFilter final : public VideoFilter, public Configurable 36 | { 37 | public: 38 | 39 | explicit ConversionFilter(const ConversionFilterSettings& settings = {}); 40 | 41 | explicit ConversionFilter(const cv::ColorConversionCodes conversion_code); 42 | 43 | void configure(const ConversionFilterSettings& settings) override; 44 | 45 | private: 46 | 47 | void filter(VideoFrame&& input, VideoFrame& output) override; 48 | 49 | }; 50 | 51 | } 52 | 53 | -------------------------------------------------------------------------------- /LiveVisionKit/Filters/DeblockingFilter.hpp: -------------------------------------------------------------------------------- 1 | // *************************** LiveVisionKit **************************** 2 | // Copyright (C) 2022 Sebastian Di Marco (crowsinc.dev@gmail.com) 3 | // 4 | // This program is free software: you can redistribute it and/or modify 5 | // it under the terms of the GNU General Public License as published by 6 | // the Free Software Foundation, either version 3 of the License, or 7 | // (at your option) any later version. 8 | // 9 | // This program is distributed in the hope that it will be useful, 10 | // but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | // GNU General Public License for more details. 13 | // 14 | // You should have received a copy of the GNU General Public License 15 | // along with this program. If not, see . 16 | // ********************************************************************** 17 | 18 | #pragma once 19 | 20 | #include "VideoFilter.hpp" 21 | #include "Utility/Configurable.hpp" 22 | 23 | namespace lvk 24 | { 25 | 26 | struct DeblockingFilterSettings 27 | { 28 | uint32_t detection_levels = 3; // Must be greater than 0 29 | uint32_t block_size = 16; // Must be greater than 0 30 | uint32_t filter_size = 5; // Must be odd 31 | float filter_scaling = 4; // Smaller is stronger (1/x) 32 | }; 33 | 34 | class DeblockingFilter final : public VideoFilter, public Configurable 35 | { 36 | public: 37 | 38 | explicit DeblockingFilter(DeblockingFilterSettings settings = {}); 39 | 40 | void configure(const DeblockingFilterSettings& settings) override; 41 | 42 | void draw_influence(VideoFrame& frame) const; 43 | 44 | cv::Rect filter_region() const; 45 | 46 | private: 47 | 48 | void filter(VideoFrame&& input, VideoFrame& output) override; 49 | 50 | cv::Rect m_FilterRegion{0,0,0,0}; 51 | VideoFrame m_SmoothFrame, m_DetectionFrame, m_ReferenceFrame; 52 | cv::UMat m_BlockMask{cv::UMatUsageFlags::USAGE_ALLOCATE_DEVICE_MEMORY}; 53 | cv::UMat m_KeepBlendMap{cv::UMatUsageFlags::USAGE_ALLOCATE_DEVICE_MEMORY}; 54 | cv::UMat m_DeblockBlendMap{cv::UMatUsageFlags::USAGE_ALLOCATE_DEVICE_MEMORY}; 55 | cv::UMat m_BlockGrid{cv::UMatUsageFlags::USAGE_ALLOCATE_DEVICE_MEMORY}; 56 | cv::UMat m_DeblockBuffer{cv::UMatUsageFlags::USAGE_ALLOCATE_DEVICE_MEMORY}; 57 | cv::UMat m_FloatBuffer{cv::UMatUsageFlags::USAGE_ALLOCATE_DEVICE_MEMORY}; 58 | mutable cv::UMat m_InfluenceBuffer{cv::UMatUsageFlags::USAGE_ALLOCATE_DEVICE_MEMORY}; 59 | }; 60 | 61 | } -------------------------------------------------------------------------------- /LiveVisionKit/Filters/ScalingFilter.cpp: -------------------------------------------------------------------------------- 1 | // *************************** LiveVisionKit **************************** 2 | // Copyright (C) 2022 Sebastian Di Marco (crowsinc.dev@gmail.com) 3 | // 4 | // This program is free software: you can redistribute it and/or modify 5 | // it under the terms of the GNU General Public License as published by 6 | // the Free Software Foundation, either version 3 of the License, or 7 | // (at your option) any later version. 8 | // 9 | // This program is distributed in the hope that it will be useful, 10 | // but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | // GNU General Public License for more details. 13 | // 14 | // You should have received a copy of the GNU General Public License 15 | // along with this program. If not, see . 16 | // ********************************************************************** 17 | 18 | #include "ScalingFilter.hpp" 19 | 20 | #include "Functions/Image.hpp" 21 | 22 | namespace lvk 23 | { 24 | 25 | //--------------------------------------------------------------------------------------------------------------------- 26 | 27 | ScalingFilter::ScalingFilter(const ScalingFilterSettings& settings) 28 | : VideoFilter("Scaling Filter") 29 | { 30 | configure(settings); 31 | } 32 | 33 | //--------------------------------------------------------------------------------------------------------------------- 34 | 35 | ScalingFilter::ScalingFilter(const cv::Size& output_size, const float sharpness) 36 | : ScalingFilter(ScalingFilterSettings{.output_size=output_size,.sharpness=sharpness}) 37 | {} 38 | 39 | //--------------------------------------------------------------------------------------------------------------------- 40 | 41 | void ScalingFilter::configure(const ScalingFilterSettings& settings) 42 | { 43 | LVK_ASSERT_01(settings.sharpness); 44 | LVK_ASSERT(settings.output_size.width > 0); 45 | LVK_ASSERT(settings.output_size.height > 0); 46 | 47 | m_Settings = settings; 48 | } 49 | 50 | //--------------------------------------------------------------------------------------------------------------------- 51 | 52 | void ScalingFilter::filter(VideoFrame&& input, VideoFrame& output) 53 | { 54 | LVK_ASSERT(!input.empty()); 55 | 56 | lvk::upscale(input, output, m_Settings.output_size, m_Settings.yuv_input); 57 | lvk::sharpen(output, output, m_Settings.sharpness); 58 | output.timestamp = input.timestamp; 59 | } 60 | 61 | //--------------------------------------------------------------------------------------------------------------------- 62 | 63 | } -------------------------------------------------------------------------------- /LiveVisionKit/Filters/ScalingFilter.hpp: -------------------------------------------------------------------------------- 1 | // *************************** LiveVisionKit **************************** 2 | // Copyright (C) 2022 Sebastian Di Marco (crowsinc.dev@gmail.com) 3 | // 4 | // This program is free software: you can redistribute it and/or modify 5 | // it under the terms of the GNU General Public License as published by 6 | // the Free Software Foundation, either version 3 of the License, or 7 | // (at your option) any later version. 8 | // 9 | // This program is distributed in the hope that it will be useful, 10 | // but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | // GNU General Public License for more details. 13 | // 14 | // You should have received a copy of the GNU General Public License 15 | // along with this program. If not, see . 16 | // ********************************************************************** 17 | 18 | #pragma once 19 | 20 | #include "VideoFilter.hpp" 21 | #include "Utility/Configurable.hpp" 22 | 23 | namespace lvk 24 | { 25 | 26 | struct ScalingFilterSettings 27 | { 28 | cv::Size output_size = {1920, 1080}; 29 | float sharpness = 0.8f; 30 | bool yuv_input = true; 31 | }; 32 | 33 | class ScalingFilter final : public VideoFilter, public Configurable 34 | { 35 | public: 36 | 37 | explicit ScalingFilter(const ScalingFilterSettings& settings = {}); 38 | 39 | explicit ScalingFilter(const cv::Size& output_size, const float sharpness = 0.8f); 40 | 41 | void configure(const ScalingFilterSettings& settings) override; 42 | 43 | private: 44 | 45 | void filter(VideoFrame&& input, VideoFrame& output) override; 46 | 47 | }; 48 | 49 | } 50 | 51 | -------------------------------------------------------------------------------- /LiveVisionKit/Filters/StabilizationFilter.hpp: -------------------------------------------------------------------------------- 1 | // *************************** LiveVisionKit **************************** 2 | // Copyright (C) 2022 Sebastian Di Marco (crowsinc.dev@gmail.com) 3 | // 4 | // This program is free software: you can redistribute it and/or modify 5 | // it under the terms of the GNU General Public License as published by 6 | // the Free Software Foundation, either version 3 of the License, or 7 | // (at your option) any later version. 8 | // 9 | // This program is distributed in the hope that it will be useful, 10 | // but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | // GNU General Public License for more details. 13 | // 14 | // You should have received a copy of the GNU General Public License 15 | // along with this program. If not, see . 16 | // ********************************************************************** 17 | 18 | #pragma once 19 | 20 | #include "VideoFilter.hpp" 21 | #include "Vision/FrameTracker.hpp" 22 | #include "Vision/PathSmoother.hpp" 23 | #include "Utility/Configurable.hpp" 24 | 25 | namespace lvk 26 | { 27 | 28 | struct StabilizationFilterSettings : public FrameTrackerSettings, public PathSmootherSettings 29 | { 30 | cv::Size motion_resolution = {2, 2}; 31 | 32 | cv::Scalar background_colour = {255,0,255}; 33 | bool crop_to_stable_region = false; 34 | bool stabilize_output = true; 35 | 36 | // Quality Assurance 37 | float min_scene_quality = 0.8f; 38 | float min_tracking_quality = 0.3f; 39 | }; 40 | 41 | 42 | class StabilizationFilter final : public VideoFilter, public Configurable 43 | { 44 | public: 45 | 46 | explicit StabilizationFilter(const StabilizationFilterSettings& settings = {}); 47 | 48 | void configure(const StabilizationFilterSettings& settings) override; 49 | 50 | void restart(); 51 | 52 | bool ready() const; 53 | 54 | void reset_context(); 55 | 56 | void draw_trackers(); 57 | 58 | void draw_motion_mesh(); 59 | 60 | size_t frame_delay() const; 61 | 62 | cv::Rect stable_region() const; 63 | 64 | private: 65 | 66 | void filter(VideoFrame&& input, VideoFrame& output) override; 67 | 68 | private: 69 | FrameTracker m_FrameTracker; 70 | PathSmoother m_PathSmoother; 71 | 72 | StreamBuffer m_FrameQueue{1}; 73 | VideoFrame m_WarpFrame, m_TrackingFrame; 74 | WarpMesh m_NullMotion{WarpMesh::MinimumSize}; 75 | 76 | float m_SceneQuality = 0.0f; 77 | float m_TrustFactor = 0.0f; 78 | }; 79 | 80 | } -------------------------------------------------------------------------------- /LiveVisionKit/Filters/VideoFilter.hpp: -------------------------------------------------------------------------------- 1 | // *************************** LiveVisionKit **************************** 2 | // Copyright (C) 2022 Sebastian Di Marco (crowsinc.dev@gmail.com) 3 | // 4 | // This program is free software: you can redistribute it and/or modify 5 | // it under the terms of the GNU General Public License as published by 6 | // the Free Software Foundation, either version 3 of the License, or 7 | // (at your option) any later version. 8 | // 9 | // This program is distributed in the hope that it will be useful, 10 | // but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | // GNU General Public License for more details. 13 | // 14 | // You should have received a copy of the GNU General Public License 15 | // along with this program. If not, see . 16 | // ********************************************************************** 17 | 18 | #pragma once 19 | 20 | #include 21 | #include 22 | #include 23 | 24 | #include "Utility/Unique.hpp" 25 | #include "Data/VideoFrame.hpp" 26 | #include "Timing/Stopwatch.hpp" 27 | 28 | namespace lvk 29 | { 30 | 31 | // NOTE: standard colour format is YUV. 32 | class VideoFilter : public Unique 33 | { 34 | public: 35 | 36 | explicit VideoFilter(const std::string& filter_name = "Identity Filter"); 37 | 38 | virtual ~VideoFilter() = default; 39 | 40 | const std::string& alias() const; 41 | 42 | 43 | void apply(VideoFrame&& input, VideoFrame& output, const bool profile = false); 44 | 45 | void apply(const VideoFrame& input, VideoFrame& output, const bool profile = false); 46 | 47 | void stream(cv::VideoCapture& input, const std::function& callback, const bool profile = false); 48 | 49 | 50 | void set_timing_samples(const size_t samples); 51 | 52 | const Stopwatch& timings() const; 53 | 54 | protected: 55 | 56 | virtual void filter(VideoFrame&& input, VideoFrame& output); 57 | 58 | private: 59 | Stopwatch m_FrameTimer; 60 | const std::string m_Alias; 61 | }; 62 | 63 | // Default VideoFilter is an identity filter. 64 | typedef VideoFilter IdentityFilter; 65 | } 66 | -------------------------------------------------------------------------------- /LiveVisionKit/Functions/Container.hpp: -------------------------------------------------------------------------------- 1 | // *************************** LiveVisionKit **************************** 2 | // Copyright (C) 2022 Sebastian Di Marco (crowsinc.dev@gmail.com) 3 | // 4 | // This program is free software: you can redistribute it and/or modify 5 | // it under the terms of the GNU General Public License as published by 6 | // the Free Software Foundation, either version 3 of the License, or 7 | // (at your option) any later version. 8 | // 9 | // This program is distributed in the hope that it will be useful, 10 | // but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | // GNU General Public License for more details. 13 | // 14 | // You should have received a copy of the GNU General Public License 15 | // along with this program. If not, see . 16 | // ********************************************************************** 17 | 18 | #pragma once 19 | 20 | #include 21 | #include 22 | #include 23 | #include 24 | 25 | namespace lvk 26 | { 27 | // Erase quickly without care for preserving the element ordering 28 | template 29 | void fast_erase(std::vector& data, const size_t index); 30 | 31 | template 32 | void filter(std::vector& data, const std::vector

& keep, bool invert = false); 33 | 34 | // NOTE: does not preserve element ordering 35 | template 36 | void fast_filter(std::vector& data, const std::vector

& keep, bool invert = false); 37 | 38 | // NOTE: does not preserve element ordering 39 | template 40 | void fast_filter( 41 | std::vector& data_1, 42 | std::vector& data_2, 43 | const std::vector

& keep, 44 | bool invert = false 45 | ); 46 | 47 | // NOTE: does not preserve element ordering 48 | template 49 | void fast_filter( 50 | std::vector& data_1, 51 | std::vector& data_2, 52 | std::vector& data_3, 53 | const std::vector

& keep, 54 | bool invert = false 55 | ); 56 | 57 | 58 | 59 | 60 | 61 | template 62 | float ratio_of(const std::vector& data, const T& value); 63 | 64 | 65 | template 66 | auto max(const iterator begin, const iterator end); 67 | 68 | template 69 | auto min(const iterator begin, const iterator end); 70 | 71 | template 72 | auto sum(const iterator begin, const iterator end); 73 | 74 | template 75 | auto mean(const iterator begin, const iterator end); 76 | 77 | template 78 | auto variance(const iterator begin, const iterator end); 79 | 80 | } 81 | 82 | #include "Container.tpp" 83 | 84 | -------------------------------------------------------------------------------- /LiveVisionKit/Functions/Extensions.hpp: -------------------------------------------------------------------------------- 1 | // *************************** LiveVisionKit **************************** 2 | // Copyright (C) 2022 Sebastian Di Marco (crowsinc.dev@gmail.com) 3 | // 4 | // This program is free software: you can redistribute it and/or modify 5 | // it under the terms of the GNU General Public License as published by 6 | // the Free Software Foundation, either version 3 of the License, or 7 | // (at your option) any later version. 8 | // 9 | // This program is distributed in the hope that it will be useful, 10 | // but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | // GNU General Public License for more details. 13 | // 14 | // You should have received a copy of the GNU General Public License 15 | // along with this program. If not, see . 16 | // ********************************************************************** 17 | 18 | #include 19 | 20 | namespace lvk 21 | { 22 | // cv::Size2f Operators 23 | cv::Size2f operator*(const cv::Size2f& v1, const cv::Size2f& v2); 24 | 25 | cv::Size2f operator/(const cv::Size2f& v1, const cv::Size2f& v2); 26 | 27 | cv::Size2f operator/(const float v1, const cv::Size2f& v2); 28 | 29 | cv::Size2f operator+(const cv::Size2f& v1, const float v2); 30 | 31 | cv::Size2f operator-(const cv::Size2f& v1, const float v2); 32 | 33 | // cv::Size Operators 34 | cv::Size operator*(const cv::Size& v1, const cv::Size& v2); 35 | 36 | cv::Size operator/(const cv::Size& v1, const cv::Size& v2); 37 | 38 | cv::Size operator/(const int v1, const cv::Size& v2); 39 | 40 | cv::Size operator+(const cv::Size& v1, const int v2); 41 | 42 | cv::Size operator-(const cv::Size& v1, const int v2); 43 | 44 | 45 | // cv::Point2f Operators 46 | cv::Point2f operator*(const cv::Point2f& p, const cv::Size2f& s); 47 | 48 | cv::Point2f operator/(const cv::Point2f& p, const cv::Size2f& s); 49 | 50 | cv::Point2f operator+(const cv::Point2f& p, const cv::Size2f& s); 51 | 52 | cv::Point2f operator-(const cv::Point2f& p, const cv::Size2f& s); 53 | 54 | cv::Point2f operator*(const cv::Point2f& p, const cv::Scalar& s); 55 | 56 | cv::Point2f operator/(const cv::Point2f& p, const cv::Scalar& s); 57 | 58 | cv::Point2f operator+(const cv::Point2f& p, const cv::Scalar& s); 59 | 60 | cv::Point2f operator-(const cv::Point2f& p, const cv::Scalar& s); 61 | 62 | 63 | // cv::Point Operators 64 | cv::Point operator*(const cv::Point& p, const cv::Size& s); 65 | 66 | cv::Point operator/(const cv::Point& p, const cv::Size& s); 67 | 68 | cv::Point operator+(const cv::Point& p, const cv::Size& s); 69 | 70 | cv::Point operator-(const cv::Point& p, const cv::Size& s); 71 | 72 | 73 | // cv::Scalar Operators 74 | cv::Scalar operator*(const cv::Scalar& v1, const cv::Scalar& v2); 75 | 76 | cv::Scalar operator/(const cv::Scalar& v1, const cv::Scalar& v2); 77 | 78 | cv::Scalar operator/(const cv::Scalar& v1, const double v2); 79 | 80 | cv::Scalar operator+(const cv::Scalar& v1, const double v2); 81 | 82 | cv::Scalar operator-(const cv::Scalar& v1, const double v2); 83 | 84 | } -------------------------------------------------------------------------------- /LiveVisionKit/Functions/Image.hpp: -------------------------------------------------------------------------------- 1 | // *************************** LiveVisionKit **************************** 2 | // Copyright (C) 2022 Sebastian Di Marco (crowsinc.dev@gmail.com) 3 | // 4 | // This program is free software: you can redistribute it and/or modify 5 | // it under the terms of the GNU General Public License as published by 6 | // the Free Software Foundation, either version 3 of the License, or 7 | // (at your option) any later version. 8 | // 9 | // This program is distributed in the hope that it will be useful, 10 | // but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | // GNU General Public License for more details. 13 | // 14 | // You should have received a copy of the GNU General Public License 15 | // along with this program. If not, see . 16 | // ********************************************************************** 17 | 18 | #pragma once 19 | 20 | #include 21 | #include "Data/VideoFrame.hpp" 22 | 23 | namespace lvk 24 | { 25 | 26 | void remap( 27 | const VideoFrame& src, 28 | VideoFrame& dst, 29 | const cv::Mat& homography, 30 | const cv::Scalar& background, 31 | const bool inverted = false 32 | ); 33 | 34 | void remap(const VideoFrame& src, VideoFrame& dst, const cv::UMat& offset_map, const cv::Scalar& background); 35 | 36 | void upscale(const cv::UMat& src, cv::UMat& dst, const cv::Size& size, const bool yuv = true); 37 | 38 | void sharpen(const cv::UMat& src, cv::UMat& dst, const float sharpness = 0.7f); 39 | 40 | } -------------------------------------------------------------------------------- /LiveVisionKit/Functions/Logic.hpp: -------------------------------------------------------------------------------- 1 | // *************************** LiveVisionKit **************************** 2 | // Copyright (C) 2022 Sebastian Di Marco (crowsinc.dev@gmail.com) 3 | // 4 | // This program is free software: you can redistribute it and/or modify 5 | // it under the terms of the GNU General Public License as published by 6 | // the Free Software Foundation, either version 3 of the License, or 7 | // (at your option) any later version. 8 | // 9 | // This program is distributed in the hope that it will be useful, 10 | // but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | // GNU General Public License for more details. 13 | // 14 | // You should have received a copy of the GNU General Public License 15 | // along with this program. If not, see . 16 | // ********************************************************************** 17 | 18 | #pragma once 19 | 20 | namespace lvk 21 | { 22 | template 23 | bool test_bits(const T bits, const T test_flag); 24 | 25 | template 26 | bool any_of(const T value, Options ...option); 27 | 28 | template 29 | bool all_of(const T value, Options ...option); 30 | 31 | 32 | template 33 | T hysteresis(const T state, const T thresh_lower, const T state_lower, const T thresh_upper, const T state_upper); 34 | 35 | } 36 | 37 | #include "Logic.tpp" 38 | -------------------------------------------------------------------------------- /LiveVisionKit/Functions/Logic.tpp: -------------------------------------------------------------------------------- 1 | // *************************** LiveVisionKit **************************** 2 | // Copyright (C) 2022 Sebastian Di Marco (crowsinc.dev@gmail.com) 3 | // 4 | // This program is free software: you can redistribute it and/or modify 5 | // it under the terms of the GNU General Public License as published by 6 | // the Free Software Foundation, either version 3 of the License, or 7 | // (at your option) any later version. 8 | // 9 | // This program is distributed in the hope that it will be useful, 10 | // but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | // GNU General Public License for more details. 13 | // 14 | // You should have received a copy of the GNU General Public License 15 | // along with this program. If not, see . 16 | // ********************************************************************** 17 | 18 | #pragma once 19 | 20 | #include 21 | 22 | namespace lvk 23 | { 24 | 25 | //--------------------------------------------------------------------------------------------------------------------- 26 | 27 | template 28 | inline bool test_bits(const T bits, const T test_flag) 29 | { 30 | static_assert(std::is_integral_v); 31 | 32 | return (bits & test_flag) == test_flag; 33 | } 34 | 35 | //--------------------------------------------------------------------------------------------------------------------- 36 | 37 | template 38 | inline bool any_of(const T value, Options ...option) 39 | { 40 | return (... || (value == option)); 41 | } 42 | 43 | //--------------------------------------------------------------------------------------------------------------------- 44 | 45 | template 46 | inline bool all_of(const T value, Options ...option) 47 | { 48 | return (... && (value == option)); 49 | } 50 | 51 | //--------------------------------------------------------------------------------------------------------------------- 52 | 53 | template 54 | inline T hysteresis( 55 | const T state, 56 | const T thresh_lower, const T state_lower, 57 | const T thresh_upper, const T state_upper 58 | ) 59 | { 60 | if(state >= thresh_upper) 61 | return state_upper; 62 | if(state <= thresh_lower) 63 | return state_lower; 64 | return state; 65 | } 66 | 67 | //--------------------------------------------------------------------------------------------------------------------- 68 | 69 | } -------------------------------------------------------------------------------- /LiveVisionKit/Functions/Math.hpp: -------------------------------------------------------------------------------- 1 | // *************************** LiveVisionKit **************************** 2 | // Copyright (C) 2022 Sebastian Di Marco (crowsinc.dev@gmail.com) 3 | // 4 | // This program is free software: you can redistribute it and/or modify 5 | // it under the terms of the GNU General Public License as published by 6 | // the Free Software Foundation, either version 3 of the License, or 7 | // (at your option) any later version. 8 | // 9 | // This program is distributed in the hope that it will be useful, 10 | // but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | // GNU General Public License for more details. 13 | // 14 | // You should have received a copy of the GNU General Public License 15 | // along with this program. If not, see . 16 | // ********************************************************************** 17 | 18 | #pragma once 19 | 20 | #include 21 | 22 | namespace lvk 23 | { 24 | 25 | template 26 | T to_degrees(const T& radians); 27 | 28 | template 29 | T to_radians(const T& degrees); 30 | 31 | template 32 | T angle_of(const cv::Point_& v, const cv::Point_& ref = {1, 0}); 33 | 34 | 35 | template 36 | T round_multiple(const T& value, const T& base); 37 | 38 | template 39 | T round_even(const T& value); 40 | 41 | 42 | template 43 | T ratio_of(const V& numerator, const V& denominator); 44 | 45 | 46 | template 47 | T index_2d(T x, T y, T row_length); 48 | 49 | template 50 | cv::Point_ inv_index_2d(T index, T row_length); 51 | 52 | 53 | template 54 | int sign(const T& value, const T& origin = T()); 55 | 56 | template 57 | int sign_2d(const cv::Point_& point, const cv::Point_& l1, const cv::Point_& l2); 58 | 59 | 60 | template 61 | inline V lerp(const V& current, const V& target, const T& amount); 62 | 63 | template 64 | inline V step(const V& current, const V& target, const T& amount); 65 | 66 | 67 | template 68 | bool between_01(const T& value); 69 | 70 | template 71 | bool between_01_strict(const T& value); 72 | 73 | template 74 | bool between(const T& value, const T& min, const T& max); 75 | 76 | template 77 | bool between_strict(const T& value, const T& min, const T& max); 78 | 79 | 80 | template 81 | bool within(const T& value, const T& target, const T& tolerance); 82 | 83 | template 84 | bool within_strict(const T& value, const T& target, const T& tolerance); 85 | 86 | 87 | template 88 | T exp_moving_average(const T average, const T new_sample, const float smoothing_factor); 89 | 90 | template 91 | T moving_median(const T median, const T new_sample, const float learning_rate); 92 | 93 | 94 | template 95 | cv::Rect_ crop(const cv::Size_& region, const cv::Size2f& proportions); 96 | 97 | template 98 | cv::Rect_ crop(const cv::Size_& region, const float proportion); 99 | 100 | 101 | template 102 | cv::Scalar barycentric_rect(const cv::Rect_& rect, const cv::Point_& point); 103 | 104 | } 105 | 106 | #include "Math.tpp" 107 | -------------------------------------------------------------------------------- /LiveVisionKit/Functions/OpenCL/Kernels.cpp: -------------------------------------------------------------------------------- 1 | // *************************** LiveVisionKit **************************** 2 | // Copyright (C) 2022 Sebastian Di Marco (crowsinc.dev@gmail.com) 3 | // 4 | // This program is free software: you can redistribute it and/or modify 5 | // it under the terms of the GNU General Public License as published by 6 | // the Free Software Foundation, either version 3 of the License, or 7 | // (at your option) any later version. 8 | // 9 | // This program is distributed in the hope that it will be useful, 10 | // but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | // GNU General Public License for more details. 13 | // 14 | // You should have received a copy of the GNU General Public License 15 | // along with this program. If not, see . 16 | // ********************************************************************** 17 | 18 | #include "Kernels.hpp" 19 | 20 | #include "Directives.hpp" 21 | 22 | namespace lvk::ocl 23 | { 24 | 25 | //--------------------------------------------------------------------------------------------------------------------- 26 | 27 | cv::ocl::Program load_program(const char* name, const char* source, const char* flags) 28 | { 29 | cv::String compilation_log; 30 | 31 | cv::ocl::ProgramSource program_source(name, name, source, ""); 32 | cv::ocl::Program program(program_source, flags, compilation_log); 33 | if(program.ptr() == nullptr) 34 | { 35 | // Perform custom assert with compilation error log. 36 | lvk::context::assert_handler( 37 | LVK_FILE, 38 | __func__, 39 | std::string("Failed to compile OpenCL program \'") 40 | + name + "\' with compilation log: \n\n" + compilation_log 41 | ); 42 | return {}; 43 | }; 44 | return std::move(program); 45 | } 46 | 47 | //--------------------------------------------------------------------------------------------------------------------- 48 | 49 | void optimal_groups(const cv::UMat& buffer, size_t global_groups[3], size_t local_groups[3]) 50 | { 51 | // Reset all group sizings to identity. 52 | local_groups[0] = 1; local_groups[1] = 1; local_groups[2] = 1; 53 | global_groups[0] = 1; global_groups[1] = 1; global_groups[2] = 1; 54 | 55 | // Figure out optimal and compatible 2D local and global work sizes for a kernel. 56 | // Note that this is just based on rule of thumbs, rather than concrete optimality. 57 | if(buffer.dims == 1 || buffer.cols == 1) 58 | { 59 | // 1D buffers: default to a work group of 64x1 threads. 60 | local_groups[0] = 64; 61 | global_groups[0] = static_cast(std::ceil(static_cast(buffer.rows) / 64.0f)) * 64; 62 | } 63 | else if(buffer.dims == 2) 64 | { 65 | // 2D buffers: default to a work group of 8x8 threads. 66 | local_groups[0] = 8; local_groups[1] = 8; 67 | global_groups[0] = static_cast(std::ceil(static_cast(buffer.cols) / 8.0f)) * 8; 68 | global_groups[1] = static_cast(std::ceil(static_cast(buffer.rows) / 8.0f)) * 8; 69 | } 70 | else LVK_ASSERT(false && "Buffer dimensions are not supported"); 71 | } 72 | 73 | //--------------------------------------------------------------------------------------------------------------------- 74 | 75 | } -------------------------------------------------------------------------------- /LiveVisionKit/Functions/OpenCL/Kernels.hpp: -------------------------------------------------------------------------------- 1 | // *************************** LiveVisionKit **************************** 2 | // Copyright (C) 2022 Sebastian Di Marco (crowsinc.dev@gmail.com) 3 | // 4 | // This program is free software: you can redistribute it and/or modify 5 | // it under the terms of the GNU General Public License as published by 6 | // the Free Software Foundation, either version 3 of the License, or 7 | // (at your option) any later version. 8 | // 9 | // This program is distributed in the hope that it will be useful, 10 | // but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | // GNU General Public License for more details. 13 | // 14 | // You should have received a copy of the GNU General Public License 15 | // along with this program. If not, see . 16 | // ********************************************************************** 17 | 18 | #pragma once 19 | 20 | #include 21 | #include 22 | #include 23 | 24 | namespace lvk::ocl 25 | { 26 | 27 | cv::ocl::Program load_program(const char* name, const char* source, const char* flags = ""); 28 | 29 | void optimal_groups(const cv::UMat& buffer, size_t global_groups[3], size_t local_groups[3]); 30 | 31 | // OpenCL Kernel Sources 32 | namespace src 33 | { 34 | inline const char* fsr_source = 35 | #include "Sources/FSR.cl" 36 | ; 37 | 38 | inline const char* drawing_source = 39 | #include "Sources/Drawing.cl" 40 | ; 41 | } 42 | } 43 | -------------------------------------------------------------------------------- /LiveVisionKit/Functions/Text.hpp: -------------------------------------------------------------------------------- 1 | // *************************** LiveVisionKit **************************** 2 | // Copyright (C) 2022 Sebastian Di Marco (crowsinc.dev@gmail.com) 3 | // 4 | // This program is free software: you can redistribute it and/or modify 5 | // it under the terms of the GNU General Public License as published by 6 | // the Free Software Foundation, either version 3 of the License, or 7 | // (at your option) any later version. 8 | // 9 | // This program is distributed in the hope that it will be useful, 10 | // but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | // GNU General Public License for more details. 13 | // 14 | // You should have received a copy of the GNU General Public License 15 | // along with this program. If not, see . 16 | // ********************************************************************** 17 | 18 | #pragma once 19 | 20 | #include 21 | #include 22 | #include 23 | 24 | namespace lvk 25 | { 26 | 27 | template 28 | std::vector parse_sequence( 29 | const std::string& string, 30 | const char delimiter = ',', 31 | const std::function& validate = [](auto index, auto value, auto failed){ 32 | return !failed; 33 | } 34 | ); 35 | 36 | } 37 | 38 | #include "Text.tpp" 39 | -------------------------------------------------------------------------------- /LiveVisionKit/Functions/Text.tpp: -------------------------------------------------------------------------------- 1 | // *************************** LiveVisionKit **************************** 2 | // Copyright (C) 2022 Sebastian Di Marco (crowsinc.dev@gmail.com) 3 | // 4 | // This program is free software: you can redistribute it and/or modify 5 | // it under the terms of the GNU General Public License as published by 6 | // the Free Software Foundation, either version 3 of the License, or 7 | // (at your option) any later version. 8 | // 9 | // This program is distributed in the hope that it will be useful, 10 | // but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | // GNU General Public License for more details. 13 | // 14 | // You should have received a copy of the GNU General Public License 15 | // along with this program. If not, see . 16 | // ********************************************************************** 17 | 18 | #pragma once 19 | 20 | #include 21 | #include 22 | #include 23 | #include 24 | #include 25 | 26 | #include "Directives.hpp" 27 | 28 | namespace lvk 29 | { 30 | 31 | //--------------------------------------------------------------------------------------------------------------------- 32 | 33 | template 34 | inline std::vector parse_sequence( 35 | const std::string& string, 36 | const char delimiter, 37 | const std::function& validate 38 | ) 39 | { 40 | static_assert(std::is_fundamental_v); 41 | 42 | std::stringstream parser, stream(string); 43 | std::string token; 44 | 45 | size_t index = 0; 46 | std::vector output; 47 | while(std::getline(stream, token, delimiter)) 48 | { 49 | parser.clear(); 50 | parser.str(token); 51 | 52 | T value = T{}; 53 | parser >> value; 54 | 55 | if(validate(index, value, parser.fail())) 56 | output.emplace_back(value); 57 | 58 | index++; 59 | } 60 | 61 | return output; 62 | } 63 | 64 | //--------------------------------------------------------------------------------------------------------------------- 65 | 66 | } 67 | -------------------------------------------------------------------------------- /LiveVisionKit/LiveVisionKit.hpp: -------------------------------------------------------------------------------- 1 | // *************************** LiveVisionKit **************************** 2 | // Copyright (C) 2022 Sebastian Di Marco (crowsinc.dev@gmail.com) 3 | // 4 | // This program is free software: you can redistribute it and/or modify 5 | // it under the terms of the GNU General Public License as published by 6 | // the Free Software Foundation, either version 3 of the License, or 7 | // (at your option) any later version. 8 | // 9 | // This program is distributed in the hope that it will be useful, 10 | // but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | // GNU General Public License for more details. 13 | // 14 | // You should have received a copy of the GNU General Public License 15 | // along with this program. If not, see . 16 | // ********************************************************************** 17 | 18 | // Library 19 | 20 | #include 21 | #include 22 | 23 | #include "Directives.hpp" 24 | 25 | #include "Functions/Math.hpp" 26 | #include "Functions/Text.hpp" 27 | #include "Functions/Image.hpp" 28 | #include "Functions/Logic.hpp" 29 | #include "Functions/Drawing.hpp" 30 | #include "Functions/Container.hpp" 31 | #include "Functions/Extensions.hpp" 32 | 33 | 34 | #include "Filters/VideoFilter.hpp" 35 | #include "Filters/CompositeFilter.hpp" 36 | #include "Filters/ConversionFilter.hpp" 37 | #include "Filters/DeblockingFilter.hpp" 38 | #include "Filters/StabilizationFilter.hpp" 39 | 40 | #include "Logging/Logger.hpp" 41 | #include "Logging/CSVLogger.hpp" 42 | 43 | #include "Math/WarpMesh.hpp" 44 | #include "Math/Homography.hpp" 45 | #include "Math/VirtualGrid.hpp" 46 | #include "Math/BoundingQuad.hpp" 47 | 48 | #include "Data/VideoFrame.hpp" 49 | #include "Data/SpatialMap.hpp" 50 | #include "Data/StreamBuffer.hpp" 51 | 52 | #include "Timing/Time.hpp" 53 | #include "Timing/Stopwatch.hpp" 54 | #include "Timing/TickTimer.hpp" 55 | 56 | #include "Utility/Unique.hpp" 57 | #include "Utility/Configurable.hpp" 58 | 59 | #include "Vision/FrameTracker.hpp" 60 | #include "Vision/PathSmoother.hpp" 61 | #include "Vision/FeatureDetector.hpp" 62 | #include "Vision/CameraCalibrator.hpp" 63 | 64 | 65 | 66 | -------------------------------------------------------------------------------- /LiveVisionKit/Logging/CSVLogger.cpp: -------------------------------------------------------------------------------- 1 | // *************************** LiveVisionKit **************************** 2 | // Copyright (C) 2022 Sebastian Di Marco (crowsinc.dev@gmail.com) 3 | // 4 | // This program is free software: you can redistribute it and/or modify 5 | // it under the terms of the GNU General Public License as published by 6 | // the Free Software Foundation, either version 3 of the License, or 7 | // (at your option) any later version. 8 | // 9 | // This program is distributed in the hope that it will be useful, 10 | // but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | // GNU General Public License for more details. 13 | // 14 | // You should have received a copy of the GNU General Public License 15 | // along with this program. If not, see . 16 | // ********************************************************************** 17 | 18 | #include "CSVLogger.hpp" 19 | 20 | namespace lvk 21 | { 22 | 23 | //--------------------------------------------------------------------------------------------------------------------- 24 | 25 | CSVLogger::CSVLogger(std::ostream& target) 26 | : Logger(target) 27 | { 28 | LVK_ASSERT(target.good()); 29 | } 30 | 31 | //--------------------------------------------------------------------------------------------------------------------- 32 | 33 | void CSVLogger::end_record(std::ostream& stream) 34 | { 35 | stream << "\n"; 36 | } 37 | 38 | //--------------------------------------------------------------------------------------------------------------------- 39 | 40 | void CSVLogger::begin_object(std::ostream& stream) 41 | { 42 | if(!is_new_record()) 43 | stream << ","; 44 | } 45 | 46 | //--------------------------------------------------------------------------------------------------------------------- 47 | 48 | } -------------------------------------------------------------------------------- /LiveVisionKit/Logging/CSVLogger.hpp: -------------------------------------------------------------------------------- 1 | // *************************** LiveVisionKit **************************** 2 | // Copyright (C) 2022 Sebastian Di Marco (crowsinc.dev@gmail.com) 3 | // 4 | // This program is free software: you can redistribute it and/or modify 5 | // it under the terms of the GNU General Public License as published by 6 | // the Free Software Foundation, either version 3 of the License, or 7 | // (at your option) any later version. 8 | // 9 | // This program is distributed in the hope that it will be useful, 10 | // but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | // GNU General Public License for more details. 13 | // 14 | // You should have received a copy of the GNU General Public License 15 | // along with this program. If not, see . 16 | // ********************************************************************** 17 | 18 | #pragma once 19 | 20 | #include "Logger.hpp" 21 | 22 | #include 23 | 24 | namespace lvk 25 | { 26 | 27 | class CSVLogger : public Logger 28 | { 29 | public: 30 | 31 | explicit CSVLogger(std::ostream& target); 32 | 33 | ~CSVLogger() override = default; 34 | 35 | protected: 36 | 37 | void end_record(std::ostream& stream) override; 38 | 39 | void begin_object(std::ostream& stream) override; 40 | 41 | }; 42 | 43 | } 44 | -------------------------------------------------------------------------------- /LiveVisionKit/Logging/Logger.hpp: -------------------------------------------------------------------------------- 1 | // *************************** LiveVisionKit **************************** 2 | // Copyright (C) 2022 Sebastian Di Marco (crowsinc.dev@gmail.com) 3 | // 4 | // This program is free software: you can redistribute it and/or modify 5 | // it under the terms of the GNU General Public License as published by 6 | // the Free Software Foundation, either version 3 of the License, or 7 | // (at your option) any later version. 8 | // 9 | // This program is distributed in the hope that it will be useful, 10 | // but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | // GNU General Public License for more details. 13 | // 14 | // You should have received a copy of the GNU General Public License 15 | // along with this program. If not, see . 16 | // ********************************************************************** 17 | 18 | #pragma once 19 | 20 | #include 21 | #include 22 | #include 23 | 24 | namespace lvk 25 | { 26 | 27 | class Logger 28 | { 29 | struct NextSignal {}; 30 | public: 31 | inline const static NextSignal Next = {}; 32 | 33 | explicit Logger(std::ostream& target = std::cout); 34 | 35 | virtual ~Logger() = default; 36 | 37 | template 38 | Logger& write(const T& object); 39 | 40 | template 41 | Logger& operator<<(const T& object); 42 | 43 | Logger& operator<<(const NextSignal& signal); 44 | 45 | template 46 | Logger& append(const T& object); 47 | 48 | template 49 | void operator+=(const T& object); 50 | 51 | template 52 | Logger& operator+(const T& object); 53 | 54 | std::ostream& raw(); 55 | 56 | void next(); 57 | 58 | virtual void flush(); 59 | 60 | void hold(const bool all_inputs = false); 61 | 62 | void resume(); 63 | 64 | virtual void reformat(); 65 | 66 | bool has_error() const; 67 | 68 | bool has_started() const; 69 | 70 | protected: 71 | 72 | bool is_new_record() const; 73 | 74 | const std::ios& base_format() const; 75 | 76 | virtual void begin_record(std::ostream& stream); 77 | 78 | virtual void end_record(std::ostream& stream); 79 | 80 | virtual void begin_object(std::ostream& stream); 81 | 82 | virtual void end_object(std::ostream& stream); 83 | 84 | private: 85 | std::ostream& m_Stream; 86 | std::ios m_BaseFormat; 87 | 88 | bool m_Started = false; 89 | bool m_NewRecord = true; 90 | bool m_HoldRecord = false; 91 | bool m_HoldInputs = false; 92 | }; 93 | 94 | } 95 | 96 | #include "Logger.tpp" 97 | -------------------------------------------------------------------------------- /LiveVisionKit/Math/BoundingQuad.cpp: -------------------------------------------------------------------------------- 1 | // *************************** LiveVisionKit **************************** 2 | // Copyright (C) 2022 Sebastian Di Marco (crowsinc.dev@gmail.com) 3 | // 4 | // This program is free software: you can redistribute it and/or modify 5 | // it under the terms of the GNU General Public License as published by 6 | // the Free Software Foundation, either version 3 of the License, or 7 | // (at your option) any later version. 8 | // 9 | // This program is distributed in the hope that it will be useful, 10 | // but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | // GNU General Public License for more details. 13 | // 14 | // You should have received a copy of the GNU General Public License 15 | // along with this program. If not, see . 16 | // ********************************************************************** 17 | 18 | #include "BoundingQuad.hpp" 19 | 20 | #include "Functions/Math.hpp" 21 | 22 | namespace lvk 23 | { 24 | 25 | //--------------------------------------------------------------------------------------------------------------------- 26 | 27 | BoundingQuad::BoundingQuad(const cv::Size2d& size, const Homography& homography) 28 | { 29 | // NOTE: Must follow counter-clockwise ordering 30 | m_LocalVertices.emplace_back(0, 0); 31 | m_LocalVertices.emplace_back(size.width, 0); 32 | m_LocalVertices.emplace_back(size.width, size.height); 33 | m_LocalVertices.emplace_back(0, size.height); 34 | 35 | this->transform(homography); 36 | } 37 | 38 | //--------------------------------------------------------------------------------------------------------------------- 39 | 40 | void BoundingQuad::transform(const Homography& homography) 41 | { 42 | homography.transform(m_LocalVertices, m_Vertices); 43 | } 44 | 45 | //--------------------------------------------------------------------------------------------------------------------- 46 | 47 | bool BoundingQuad::encloses(const cv::Rect2d& rect) const 48 | { 49 | const cv::Point2d tl = rect.tl(); 50 | const cv::Point2d br = rect.br(); 51 | const cv::Point2d tr(br.x, tl.y); 52 | const cv::Point2d bl(tl.x, br.y); 53 | 54 | return encloses(tl) 55 | && encloses(br) 56 | && encloses(tr) 57 | && encloses(bl); 58 | } 59 | 60 | //--------------------------------------------------------------------------------------------------------------------- 61 | 62 | bool BoundingQuad::encloses(const BoundingQuad& quad) const 63 | { 64 | return encloses(quad.m_Vertices[0]) 65 | && encloses(quad.m_Vertices[1]) 66 | && encloses(quad.m_Vertices[2]) 67 | && encloses(quad.m_Vertices[3]); 68 | } 69 | 70 | //--------------------------------------------------------------------------------------------------------------------- 71 | 72 | bool BoundingQuad::encloses(const cv::Point2d& point) const 73 | { 74 | // A point is enclosed within the quad if it is left of 75 | // every quad edge, going in a counter-clockwise order. 76 | return sign_2d(point, m_Vertices[0], m_Vertices[1]) <= 0 77 | && sign_2d(point, m_Vertices[1], m_Vertices[2]) <= 0 78 | && sign_2d(point, m_Vertices[2], m_Vertices[3]) <= 0 79 | && sign_2d(point, m_Vertices[3], m_Vertices[0]) <= 0; 80 | } 81 | 82 | //--------------------------------------------------------------------------------------------------------------------- 83 | 84 | } 85 | -------------------------------------------------------------------------------- /LiveVisionKit/Math/BoundingQuad.hpp: -------------------------------------------------------------------------------- 1 | // *************************** LiveVisionKit **************************** 2 | // Copyright (C) 2022 Sebastian Di Marco (crowsinc.dev@gmail.com) 3 | // 4 | // This program is free software: you can redistribute it and/or modify 5 | // it under the terms of the GNU General Public License as published by 6 | // the Free Software Foundation, either version 3 of the License, or 7 | // (at your option) any later version. 8 | // 9 | // This program is distributed in the hope that it will be useful, 10 | // but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | // GNU General Public License for more details. 13 | // 14 | // You should have received a copy of the GNU General Public License 15 | // along with this program. If not, see . 16 | // ********************************************************************** 17 | 18 | #pragma once 19 | 20 | #include 21 | 22 | #include "Homography.hpp" 23 | 24 | namespace lvk 25 | { 26 | 27 | class BoundingQuad 28 | { 29 | public: 30 | 31 | explicit BoundingQuad(const cv::Size2d& size, const Homography& homography = Homography::Identity()); 32 | 33 | void transform(const Homography& homography); 34 | 35 | bool encloses(const cv::Rect2d& rect) const; 36 | 37 | bool encloses(const BoundingQuad& quad) const; 38 | 39 | bool encloses(const cv::Point2d& point) const; 40 | 41 | private: 42 | std::vector m_LocalVertices, m_Vertices; 43 | }; 44 | 45 | } 46 | -------------------------------------------------------------------------------- /LiveVisionKit/Math/Homography.hpp: -------------------------------------------------------------------------------- 1 | // *************************** LiveVisionKit **************************** 2 | // Copyright (C) 2022 Sebastian Di Marco (crowsinc.dev@gmail.com) 3 | // 4 | // This program is free software: you can redistribute it and/or modify 5 | // it under the terms of the GNU General Public License as published by 6 | // the Free Software Foundation, either version 3 of the License, or 7 | // (at your option) any later version. 8 | // 9 | // This program is distributed in the hope that it will be useful, 10 | // but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | // GNU General Public License for more details. 13 | // 14 | // You should have received a copy of the GNU General Public License 15 | // along with this program. If not, see . 16 | // ********************************************************************** 17 | 18 | #pragma once 19 | 20 | #include 21 | #include 22 | 23 | namespace lvk 24 | { 25 | 26 | class Homography 27 | { 28 | public: 29 | 30 | static const Homography& Zero(); 31 | 32 | static const Homography& Identity(); 33 | 34 | static Homography FromAffineMatrix(const cv::Mat& affine); 35 | 36 | 37 | Homography(); 38 | 39 | Homography(const Homography& other); 40 | 41 | Homography(Homography&& other) noexcept; 42 | 43 | explicit Homography(const cv::Mat& matrix); 44 | 45 | explicit Homography(cv::Mat&& matrix) noexcept; 46 | 47 | 48 | void set_zero(); 49 | 50 | void set_identity(); 51 | 52 | 53 | cv::Point2d transform(const cv::Point2d& point) const; 54 | 55 | cv::Point2f transform(const cv::Point2f& point) const; 56 | 57 | cv::Point2d operator*(const cv::Point2d& point) const; 58 | 59 | cv::Point2f operator*(const cv::Point2f& point) const; 60 | 61 | 62 | void transform(const std::vector& points, std::vector& dst) const; 63 | 64 | void transform(const std::vector& points, std::vector& dst) const; 65 | 66 | std::vector operator*(const std::vector& points) const; 67 | 68 | std::vector operator*(const std::vector& points) const; 69 | 70 | 71 | void warp(const cv::UMat& src, cv::UMat& dst) const; 72 | 73 | 74 | const cv::Mat& data() const; 75 | 76 | Homography invert() const; 77 | 78 | bool is_identity() const; 79 | 80 | bool is_affine() const; 81 | 82 | bool is_zero() const; 83 | 84 | 85 | Homography& operator=(const cv::Mat& other); 86 | 87 | Homography& operator=(cv::Mat&& other) noexcept; 88 | 89 | Homography& operator=(const Homography& other); 90 | 91 | Homography& operator=(Homography&& other) noexcept; 92 | 93 | 94 | void operator+=(const Homography& other); 95 | 96 | void operator+=(const cv::Mat& other); 97 | 98 | void operator-=(const Homography& other); 99 | 100 | void operator-=(const cv::Mat& other); 101 | 102 | void operator*=(const Homography& other); 103 | 104 | void operator*=(const cv::Mat& other); 105 | 106 | void operator*=(const double scaling); 107 | 108 | void operator/=(const double scaling); 109 | 110 | private: 111 | cv::Mat m_Matrix; 112 | }; 113 | 114 | Homography operator+(const Homography& left, const Homography& right); 115 | 116 | Homography operator-(const Homography& left, const Homography& right); 117 | 118 | 119 | Homography operator*(const Homography& left, const Homography& right); 120 | 121 | Homography operator*(const Homography& homography, const double scaling); 122 | 123 | Homography operator*(const double scaling, const Homography& homography); 124 | 125 | 126 | Homography operator/(const Homography& homography, const double scaling); 127 | 128 | Homography operator/(const double scaling, const Homography& homography); 129 | 130 | } 131 | -------------------------------------------------------------------------------- /LiveVisionKit/Math/VirtualGrid.hpp: -------------------------------------------------------------------------------- 1 | // *************************** LiveVisionKit **************************** 2 | // Copyright (C) 2022 Sebastian Di Marco (crowsinc.dev@gmail.com) 3 | // 4 | // This program is free software: you can redistribute it and/or modify 5 | // it under the terms of the GNU General Public License as published by 6 | // the Free Software Foundation, either version 3 of the License, or 7 | // (at your option) any later version. 8 | // 9 | // This program is distributed in the hope that it will be useful, 10 | // but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | // GNU General Public License for more details. 13 | // 14 | // You should have received a copy of the GNU General Public License 15 | // along with this program. If not, see . 16 | // ********************************************************************** 17 | 18 | #pragma once 19 | 20 | #include 21 | #include 22 | 23 | namespace lvk 24 | { 25 | using SpatialKey = cv::Point_; 26 | 27 | class VirtualGrid 28 | { 29 | public: 30 | 31 | explicit VirtualGrid(const cv::Size& size); 32 | 33 | VirtualGrid(const cv::Size& size, const cv::Rect2f& alignment); 34 | 35 | VirtualGrid(const VirtualGrid& grid); 36 | 37 | 38 | void resize(const cv::Size& size); 39 | 40 | const cv::Size& size() const; 41 | 42 | int cols() const; 43 | 44 | int rows() const; 45 | 46 | 47 | void align(const cv::Rect2f& region); 48 | 49 | void align(const cv::Size& size, const cv::Rect2f& region); 50 | 51 | 52 | const cv::Rect2f& alignment() const; 53 | 54 | const cv::Size2f& key_size() const; 55 | 56 | 57 | cv::Mat make_grid() const; 58 | 59 | cv::Mat make_aligned_grid() const; 60 | 61 | 62 | bool test_key(const SpatialKey& key) const; 63 | 64 | size_t key_to_index(const SpatialKey& key) const; 65 | 66 | SpatialKey index_to_key(const size_t index) const; 67 | 68 | 69 | bool test_point(const cv::Point2f& point) const; 70 | 71 | SpatialKey key_of(const cv::Point2f& point) const; 72 | 73 | std::optional try_key_of(const cv::Point2f& point) const; 74 | 75 | // TODO: rename these 76 | cv::Point2f key_to_point(const SpatialKey& key) const; 77 | 78 | cv::Point2f index_to_point(const size_t index) const; 79 | 80 | 81 | 82 | void for_each(const std::function& operation) const; 83 | 84 | void for_each_aligned(const std::function& operation) const; 85 | 86 | private: 87 | cv::Size m_Resolution; 88 | cv::Rect2f m_Alignment; 89 | cv::Size2f m_KeySize; 90 | }; 91 | 92 | } 93 | -------------------------------------------------------------------------------- /LiveVisionKit/Timing/Stopwatch.hpp: -------------------------------------------------------------------------------- 1 | // Copyright (C) 2022 Sebastian Di Marco (crowsinc.dev@gmail.com) 2 | // 3 | // This program is free software: you can redistribute it and/or modify 4 | // it under the terms of the GNU General Public License as published by 5 | // the Free Software Foundation, either version 3 of the License, or 6 | // (at your option) any later version. 7 | // 8 | // This program is distributed in the hope that it will be useful, 9 | // but WITHOUT ANY WARRANTY; without even the implied warranty of 10 | // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 11 | // GNU General Public License for more details. 12 | // 13 | // You should have received a copy of the GNU General Public License 14 | // along with this program. If not, see . 15 | // ********************************************************************** 16 | 17 | #pragma once 18 | 19 | #include "Time.hpp" 20 | #include "Data/StreamBuffer.hpp" 21 | 22 | namespace lvk 23 | { 24 | 25 | class Stopwatch 26 | { 27 | public: 28 | 29 | explicit Stopwatch(const size_t history = 1); 30 | 31 | void start(); 32 | 33 | Time stop(); 34 | 35 | Time pause(); 36 | 37 | Time restart(); 38 | 39 | 40 | bool is_paused() const; 41 | 42 | bool is_running() const; 43 | 44 | 45 | Time wait_until(const Time& target_elapsed_time); 46 | 47 | Stopwatch& sync_gpu(const bool trigger = true); 48 | 49 | 50 | Time elapsed() const; 51 | 52 | Time average() const; 53 | 54 | Time deviation() const; 55 | 56 | 57 | void reset_history(); 58 | 59 | const StreamBuffer