├── .gitmodules ├── LICENSE ├── README.md ├── data ├── calib.txt ├── calib_davis.txt └── samples.tar.bz2 ├── images └── screenshot.png └── src ├── CMakeLists.txt ├── common.cpp ├── common.cu ├── common.cuh ├── common.h ├── direct.cu ├── direct.cuh ├── dvscameraworker.cpp ├── dvscameraworker.h ├── eigenhelpers.h ├── event.h ├── live_tracking_gui.cpp ├── parameters.cpp ├── parameters.h ├── resources ├── camera.png ├── fileopen.png ├── fileopenevents.png ├── filesave.png ├── filesaveevents.png ├── pause.png ├── play.png ├── reset.png ├── resources.qrc └── vlo_logo.png ├── scopedtimer.h ├── trackingmainwindow.cpp ├── trackingmainwindow.h ├── trackingworker.cpp └── trackingworker.h /.gitmodules: -------------------------------------------------------------------------------- 1 | [submodule "imageutilities"] 2 | path = imageutilities 3 | url = https://github.com/VLOGroup/imageutilities 4 | [submodule "libcaer"] 5 | path = libcaer 6 | url = https://github.com/inilabs/libcaer 7 | [submodule "cnpy"] 8 | path = cnpy 9 | url = https://github.com/rogersce/cnpy 10 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | GNU LESSER GENERAL PUBLIC LICENSE 2 | Version 3, 29 June 2007 3 | 4 | Copyright (C) 2007 Free Software Foundation, Inc. 5 | Everyone is permitted to copy and distribute verbatim copies 6 | of this license document, but changing it is not allowed. 7 | 8 | 9 | This version of the GNU Lesser General Public License incorporates 10 | the terms and conditions of version 3 of the GNU General Public 11 | License, supplemented by the additional permissions listed below. 12 | 13 | 0. Additional Definitions. 14 | 15 | As used herein, "this License" refers to version 3 of the GNU Lesser 16 | General Public License, and the "GNU GPL" refers to version 3 of the GNU 17 | General Public License. 18 | 19 | "The Library" refers to a covered work governed by this License, 20 | other than an Application or a Combined Work as defined below. 21 | 22 | An "Application" is any work that makes use of an interface provided 23 | by the Library, but which is not otherwise based on the Library. 24 | Defining a subclass of a class defined by the Library is deemed a mode 25 | of using an interface provided by the Library. 26 | 27 | A "Combined Work" is a work produced by combining or linking an 28 | Application with the Library. The particular version of the Library 29 | with which the Combined Work was made is also called the "Linked 30 | Version". 31 | 32 | The "Minimal Corresponding Source" for a Combined Work means the 33 | Corresponding Source for the Combined Work, excluding any source code 34 | for portions of the Combined Work that, considered in isolation, are 35 | based on the Application, and not on the Linked Version. 36 | 37 | The "Corresponding Application Code" for a Combined Work means the 38 | object code and/or source code for the Application, including any data 39 | and utility programs needed for reproducing the Combined Work from the 40 | Application, but excluding the System Libraries of the Combined Work. 41 | 42 | 1. Exception to Section 3 of the GNU GPL. 43 | 44 | You may convey a covered work under sections 3 and 4 of this License 45 | without being bound by section 3 of the GNU GPL. 46 | 47 | 2. Conveying Modified Versions. 48 | 49 | If you modify a copy of the Library, and, in your modifications, a 50 | facility refers to a function or data to be supplied by an Application 51 | that uses the facility (other than as an argument passed when the 52 | facility is invoked), then you may convey a copy of the modified 53 | version: 54 | 55 | a) under this License, provided that you make a good faith effort to 56 | ensure that, in the event an Application does not supply the 57 | function or data, the facility still operates, and performs 58 | whatever part of its purpose remains meaningful, or 59 | 60 | b) under the GNU GPL, with none of the additional permissions of 61 | this License applicable to that copy. 62 | 63 | 3. Object Code Incorporating Material from Library Header Files. 64 | 65 | The object code form of an Application may incorporate material from 66 | a header file that is part of the Library. You may convey such object 67 | code under terms of your choice, provided that, if the incorporated 68 | material is not limited to numerical parameters, data structure 69 | layouts and accessors, or small macros, inline functions and templates 70 | (ten or fewer lines in length), you do both of the following: 71 | 72 | a) Give prominent notice with each copy of the object code that the 73 | Library is used in it and that the Library and its use are 74 | covered by this License. 75 | 76 | b) Accompany the object code with a copy of the GNU GPL and this license 77 | document. 78 | 79 | 4. Combined Works. 80 | 81 | You may convey a Combined Work under terms of your choice that, 82 | taken together, effectively do not restrict modification of the 83 | portions of the Library contained in the Combined Work and reverse 84 | engineering for debugging such modifications, if you also do each of 85 | the following: 86 | 87 | a) Give prominent notice with each copy of the Combined Work that 88 | the Library is used in it and that the Library and its use are 89 | covered by this License. 90 | 91 | b) Accompany the Combined Work with a copy of the GNU GPL and this license 92 | document. 93 | 94 | c) For a Combined Work that displays copyright notices during 95 | execution, include the copyright notice for the Library among 96 | these notices, as well as a reference directing the user to the 97 | copies of the GNU GPL and this license document. 98 | 99 | d) Do one of the following: 100 | 101 | 0) Convey the Minimal Corresponding Source under the terms of this 102 | License, and the Corresponding Application Code in a form 103 | suitable for, and under terms that permit, the user to 104 | recombine or relink the Application with a modified version of 105 | the Linked Version to produce a modified Combined Work, in the 106 | manner specified by section 6 of the GNU GPL for conveying 107 | Corresponding Source. 108 | 109 | 1) Use a suitable shared library mechanism for linking with the 110 | Library. A suitable mechanism is one that (a) uses at run time 111 | a copy of the Library already present on the user's computer 112 | system, and (b) will operate properly with a modified version 113 | of the Library that is interface-compatible with the Linked 114 | Version. 115 | 116 | e) Provide Installation Information, but only if you would otherwise 117 | be required to provide such information under section 6 of the 118 | GNU GPL, and only to the extent that such information is 119 | necessary to install and execute a modified version of the 120 | Combined Work produced by recombining or relinking the 121 | Application with a modified version of the Linked Version. (If 122 | you use option 4d0, the Installation Information must accompany 123 | the Minimal Corresponding Source and Corresponding Application 124 | Code. If you use option 4d1, you must provide the Installation 125 | Information in the manner specified by section 6 of the GNU GPL 126 | for conveying Corresponding Source.) 127 | 128 | 5. Combined Libraries. 129 | 130 | You may place library facilities that are a work based on the 131 | Library side by side in a single library together with other library 132 | facilities that are not Applications and are not covered by this 133 | License, and convey such a combined library under terms of your 134 | choice, if you do both of the following: 135 | 136 | a) Accompany the combined library with a copy of the same work based 137 | on the Library, uncombined with any other library facilities, 138 | conveyed under the terms of this License. 139 | 140 | b) Give prominent notice with the combined library that part of it 141 | is a work based on the Library, and explaining where to find the 142 | accompanying uncombined form of the same work. 143 | 144 | 6. Revised Versions of the GNU Lesser General Public License. 145 | 146 | The Free Software Foundation may publish revised and/or new versions 147 | of the GNU Lesser General Public License from time to time. Such new 148 | versions will be similar in spirit to the present version, but may 149 | differ in detail to address new problems or concerns. 150 | 151 | Each version is given a distinguishing version number. If the 152 | Library as you received it specifies that a certain numbered version 153 | of the GNU Lesser General Public License "or any later version" 154 | applies to it, you have the option of following the terms and 155 | conditions either of that published version or of any later version 156 | published by the Free Software Foundation. If the Library as you 157 | received it does not specify a version number of the GNU Lesser 158 | General Public License, you may choose any version of the GNU Lesser 159 | General Public License ever published by the Free Software Foundation. 160 | 161 | If the Library as you received it specifies that a proxy can decide 162 | whether future versions of the GNU Lesser General Public License shall 163 | apply, that proxy's public statement of acceptance of any version is 164 | permanent authorization for you to choose that version for the 165 | Library. 166 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # Real-Time Panoramic Tracking for Event Cameras 2 | This repository provides software for our publication "Real-Time Panoramic Tracking for Event Cameras", ICCP 2017. 3 | 4 | If you use this code please cite the following publication (https://arxiv.org/abs/1703.05161): 5 | ~~~ 6 | @inproceedings{reinbacher_iccp2017, 7 | author = {Christian Reinbacher and Gottfried Munda and Thomas Pock}, 8 | title = {{Real-Time Panoramic Tracking for Event Cameras}}, 9 | booktitle = {2017 International Conference on Computational Photography (ICCP)}, 10 | year = {2017}, 11 | } 12 | ~~~ 13 | 14 | ## Compiling 15 | For your convenience, the required libraries that are on Github are added as 16 | submodules. So clone this repository with `--recursive` or do a 17 | ~~~ 18 | git submodule update --init --recursive 19 | ~~~ 20 | after cloning. 21 | 22 | This software requires: 23 | - GCC >= 4.9 24 | - CMake >= 3.2 25 | - Qt >= 5.6 26 | - ImageUtilities (https://github.com/VLOGroup/imageutilities) with the `iugui`, `iuio` and `iumath` modules 27 | - libcaer >=2.0 (https://github.com/inilabs/libcaer) 28 | - cnpy (https://github.com/rogersce/cnpy) 29 | - DVS128 camera (can also load events from files) 30 | 31 | To compile, first build and install ImageUtilities, then: 32 | ~~~ 33 | cd cnpy 34 | cmake . 35 | make 36 | (sudo) make install 37 | cd ../libcaer 38 | cmake . 39 | make 40 | (sudo) make install 41 | cd .. 42 | mkdir build 43 | cd build 44 | cmake ../src 45 | make -j6 46 | ~~~ 47 | 48 | Per default, the application will compile to support the iniLabs DVS128. 49 | 50 | ## Usage 51 | Launch `live_tracking_gui ` to get to the main application which should look like this: 52 | 53 | 54 | Camera calibration files are included in the `data/` folder, the format is as follows: 55 | ~~~ 56 | <3x3 camera intrinsics matrix> 57 | 58 | 59 | 60 | ~~~ 61 | 62 | Clicking on the play button with an attached camera will start the live reconstruction method. Alternatively, events can be loaded from text files with one event per line: 63 | ~~~ 64 | 65 | ... 66 | ... 67 | ~~~ 68 | 69 | If you don't own a camera, there is sample data available in the `data/` directory. Simply extract it, load it in the application and press the play button. 70 | -------------------------------------------------------------------------------- /data/calib.txt: -------------------------------------------------------------------------------- 1 | 157.8954 0 64.0000 2 | 0 157.8954 64.0000 3 | 0 0 1.0000 4 | 800 5 | 400 6 | -0.1814 7 | -------------------------------------------------------------------------------- /data/calib_davis.txt: -------------------------------------------------------------------------------- 1 | 199.092366542 0 132.192071378 2 | 0 198.82882047 110.712660011 3 | 0 0 1.0000 4 | 800 5 | 400 6 | -0.368436311798 7 | -------------------------------------------------------------------------------- /data/samples.tar.bz2: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/VLOGroup/dvs-panotracking/c610baa720c99845284150318dcf2345c50705ee/data/samples.tar.bz2 -------------------------------------------------------------------------------- /images/screenshot.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/VLOGroup/dvs-panotracking/c610baa720c99845284150318dcf2345c50705ee/images/screenshot.png -------------------------------------------------------------------------------- /src/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | PROJECT(dvs_panotracking) 2 | 3 | cmake_minimum_required(VERSION 2.8) 4 | FILE(TO_CMAKE_PATH "${CMAKE_CURRENT_SOURCE_DIR}/cmake/" OT_CMAKE_MODULE_PATH) 5 | SET(CMAKE_MODULE_PATH ${OT_CMAKE_MODULE_PATH}) 6 | 7 | set(CMAKE_BUILD_TYPE Release) 8 | 9 | 10 | ##----------------------------------------------------------------------------- 11 | # ImageUtilities 12 | #change the following line to whatever graphics card you have 13 | set(ImageUtilities_DIR $ENV{IMAGEUTILITIES_ROOT}) 14 | set(IMAGEUTILITIES_PREFER_STATIC_LIBRARIES false) 15 | find_package(ImageUtilities REQUIRED COMPONENTS iucore iuio iumath iugui) 16 | cuda_include_directories(${IMAGEUTILITIES_INCLUDE_DIR}) 17 | include_directories(${IMAGEUTILITIES_INCLUDE_DIR}) 18 | 19 | ##----------------------------------------------------------------------------- 20 | ## Qt5 21 | set(CMAKE_AUTOMOC ON) 22 | find_package(Qt5Core) 23 | find_package(Qt5Widgets) 24 | find_package(Qt5OpenGL) 25 | qt5_add_resources(UI_RESOURCES ${CMAKE_CURRENT_SOURCE_DIR}/resources/resources.qrc) 26 | ##----------------------------------------------------------------------------- 27 | ## Eigen 28 | #find_package(Eigen3 REQUIRED) 29 | #include_directories(${EIGEN3_INCLUDE_DIR}) 30 | include_directories(/usr/include/eigen3) 31 | ## Compiler Flags 32 | if(WIN32) 33 | SET(CMAKE_SHARED_LINKER_FLAGS "${CMAKE_SHARED_LINKER_FLAGS} /NODEFAULTLIB:LIBCMT.lib /MDd") 34 | endif(WIN32) 35 | add_definitions("-std=c++11 -fpermissive -O3 -DPARALLEL -ffast-math") 36 | 37 | SET(CUDA_FILES 38 | ${CMAKE_CURRENT_SOURCE_DIR}/common.cu 39 | ${CMAKE_CURRENT_SOURCE_DIR}/direct.cu 40 | ${CMAKE_CURRENT_SOURCE_DIR}/common.cpp 41 | ${CMAKE_CURRENT_SOURCE_DIR}/parameters.cpp) 42 | SET(HEADER_FILES 43 | ${CMAKE_CURRENT_SOURCE_DIR}/event.h 44 | ${CMAKE_CURRENT_SOURCE_DIR}/scopedtimer.h 45 | ${CMAKE_CURRENT_SOURCE_DIR}/common.h 46 | ${CMAKE_CURRENT_SOURCE_DIR}/common.cuh 47 | ${CMAKE_CURRENT_SOURCE_DIR}/direct.cuh 48 | ${CMAKE_CURRENT_SOURCE_DIR}/parameters.h) 49 | 50 | if(WIN32) 51 | cuda_add_library(dvs-tracking-common ${CUDA_FILES}) 52 | else(WIN32) 53 | cuda_add_library(dvs-tracking-common STATIC ${CUDA_FILES}) 54 | target_link_libraries(dvs-tracking-common ${IMAGEUTILITIES_LIBRARIES}) 55 | endif(WIN32) 56 | target_link_libraries(dvs-tracking-common ${OpenCV_LIBRARIES} ${OpenCV_LIBS} cnpy) 57 | 58 | SET ( GUI_FILES 59 | ${CMAKE_CURRENT_SOURCE_DIR}/live_tracking_gui.cpp 60 | ${CMAKE_CURRENT_SOURCE_DIR}/trackingmainwindow.cpp 61 | ${CMAKE_CURRENT_SOURCE_DIR}/dvscameraworker.cpp 62 | ${CMAKE_CURRENT_SOURCE_DIR}/trackingworker.cpp) 63 | 64 | link_directories(/usr/local/lib/x86_64-linux-gnu/) # libcaer 65 | link_directories(/usr/local/lib64/) 66 | CUDA_ADD_EXECUTABLE(live_tracking_gui ${GUI_FILES} ${HEADER_FILES} ${UI_RESOURCES}) 67 | TARGET_LINK_LIBRARIES(live_tracking_gui dvs-tracking-common X11 Qt5::Widgets Qt5::OpenGL caer) 68 | 69 | 70 | -------------------------------------------------------------------------------- /src/common.cpp: -------------------------------------------------------------------------------- 1 | // This file is part of dvs-panotracking. 2 | // 3 | // Copyright (C) 2017 Christian Reinbacher 4 | // Institute for Computer Graphics and Vision, Graz University of Technology 5 | // https://www.tugraz.at/institute/icg/teams/team-pock/ 6 | // 7 | // dvs-panotracking is free software: you can redistribute it and/or modify it under the 8 | // terms of the GNU General Public License as published by the Free Software 9 | // Foundation, either version 3 of the License, or any later version. 10 | // 11 | // dvs-panotracking is distributed in the hope that it will be useful, but WITHOUT ANY 12 | // WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS 13 | // FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. 14 | // 15 | // You should have received a copy of the GNU General Public License 16 | // along with this program. If not, see . 17 | 18 | #include "common.h" 19 | #include 20 | #include "cnpy.h" 21 | #include "iu/iuio.h" 22 | #include "iu/iumath.h" 23 | #include "iu/iuio/openexrio.h" 24 | #include 25 | 26 | void saveEvents(std::string filename, std::vector &events) 27 | { 28 | // create text file and go through all events 29 | std::ofstream file; 30 | 31 | file.open(filename); 32 | for (int i=0;i127 || event.y_undist<0 || event.y_undist>127) 55 | return false; 56 | else 57 | return true; 58 | } 59 | 60 | void loadEvents(std::vector& events, const Matrix3fr &K, float radial, std::string filename) 61 | { 62 | std::ifstream ifs; 63 | ifs.open(filename.c_str(),std::ifstream::in); 64 | if(ifs.good()) 65 | { 66 | Event temp_event; 67 | double time; 68 | // // throw away the first events 69 | // for(int i=0;i<100000;i++) 70 | // { 71 | // ifs >> time; 72 | // ifs >> temp_event.y; 73 | // ifs >> temp_event.x; 74 | // ifs >> temp_event.polarity; 75 | // } 76 | while(!ifs.eof()) 77 | { 78 | ifs >> temp_event.t; 79 | ifs >> temp_event.x; 80 | ifs >> temp_event.y; 81 | ifs >> temp_event.polarity; 82 | 83 | if(!undistortPoint(temp_event,K,radial)) // no points outside the original image 84 | continue; 85 | 86 | events.push_back(temp_event); 87 | } 88 | ifs.close(); 89 | } 90 | } 91 | 92 | 93 | void loadEvents(std::vector& events, std::string filename) 94 | { 95 | std::ifstream ifs; 96 | ifs.open(filename.c_str(),std::ifstream::in); 97 | if(ifs.good()) 98 | { 99 | Event temp_event; 100 | // double time; 101 | // // throw away the first events 102 | // for(int i=0;i<100000;i++) 103 | // { 104 | // ifs >> time; 105 | // ifs >> temp_event.y; 106 | // ifs >> temp_event.x; 107 | // ifs >> temp_event.polarity; 108 | // } 109 | while(!ifs.eof()) 110 | { 111 | ifs >> temp_event.t; 112 | ifs >> temp_event.x; 113 | ifs >> temp_event.y; 114 | ifs >> temp_event.polarity; 115 | 116 | events.push_back(temp_event); 117 | } 118 | ifs.close(); 119 | } 120 | } 121 | 122 | void saveState(std::string filename, const iu::ImageGpu_32f_C1 *mat, bool as_png, bool as_npy, bool as_exr) 123 | { 124 | iu::ImageCpu_32f_C1 in_cpu(mat->width(),mat->height()); 125 | iu::Size<2> sz = mat->size(); 126 | const unsigned int shape[] = {sz.width,sz.height}; 127 | iu::copy(mat,&in_cpu); 128 | if(as_npy) { 129 | // save current image as npy 130 | cnpy::npy_save(filename + ".npy",in_cpu.data(),shape,2); 131 | } 132 | if(as_png) { 133 | // save current image as png 134 | iu::imsave(&in_cpu,filename + ".png",true); 135 | } 136 | if(as_exr) { 137 | iu::OpenEXROutputFile out(filename + ".exr", in_cpu.size()); 138 | out.add_channel("u", in_cpu); 139 | out.write(); 140 | } 141 | } 142 | 143 | void saveState(std::string filename, const iu::ImageGpu_8u_C4 *mat) 144 | { 145 | iu::ImageCpu_8u_C4 in_cpu(mat->width(),mat->height()); 146 | iu::Size<2> sz = mat->size(); 147 | const unsigned int shape[] = {sz.width,sz.height}; 148 | iu::copy(mat,&in_cpu); 149 | // save current image as png 150 | iu::imsave(&in_cpu,filename + ".png",true); 151 | } 152 | -------------------------------------------------------------------------------- /src/common.cu: -------------------------------------------------------------------------------- 1 | // This file is part of dvs-panotracking. 2 | // 3 | // Copyright (C) 2017 Christian Reinbacher 4 | // Institute for Computer Graphics and Vision, Graz University of Technology 5 | // https://www.tugraz.at/institute/icg/teams/team-pock/ 6 | // 7 | // dvs-panotracking is free software: you can redistribute it and/or modify it under the 8 | // terms of the GNU General Public License as published by the Free Software 9 | // Foundation, either version 3 of the License, or any later version. 10 | // 11 | // dvs-panotracking is distributed in the hope that it will be useful, but WITHOUT ANY 12 | // WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS 13 | // FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. 14 | // 15 | // You should have received a copy of the GNU General Public License 16 | // along with this program. If not, see . 17 | 18 | #include "common.h" 19 | #include "common.cuh" 20 | #include "iu/iumath.h" 21 | #include "iu/iucore.h" 22 | 23 | inline __device__ float sum(float3 val) 24 | { 25 | return val.x+val.y+val.z; 26 | } 27 | inline __device__ float sum(float2 val) 28 | { 29 | return val.x+val.y; 30 | } 31 | 32 | inline __device__ float2 abs(float2 val) 33 | { 34 | return make_float2(abs(val.x),abs(val.y)); 35 | } 36 | 37 | __global__ void set_events_kernel(iu::ImageGpu_32f_C1::KernelData output, iu::LinearDeviceMemory_32f_C2::KernelData events) 38 | { 39 | int event_id = blockIdx.x*blockDim.x + threadIdx.x; 40 | 41 | if(event_id(tex_input,x/scale+0.5f,y/scale+0.5f); 56 | } 57 | } 58 | 59 | __global__ void upsample_exp_kernel(iu::ImageGpu_32f_C1::KernelData output, cudaTextureObject_t tex_input, float scale) 60 | { 61 | int x = blockIdx.x*blockDim.x + threadIdx.x; 62 | int y = blockIdx.y*blockDim.y + threadIdx.y; 63 | 64 | if(x(tex_input,x/scale+0.5f,y/scale+0.5f)); 67 | } 68 | } 69 | namespace cuda { 70 | inline uint divUp(uint a, uint b) { return (a + b - 1) / b; } 71 | 72 | void setEvents(iu::ImageGpu_32f_C1 *output, iu::LinearDeviceMemory_32f_C2 *events_gpu) 73 | { 74 | int gpu_block_x = GPU_BLOCK_SIZE*GPU_BLOCK_SIZE; 75 | int gpu_block_y = 1; 76 | 77 | // compute number of Blocks 78 | int nb_x = divUp(events_gpu->numel(),gpu_block_x); 79 | int nb_y = 1; 80 | 81 | dim3 dimBlock(gpu_block_x,gpu_block_y); 82 | dim3 dimGrid(nb_x,nb_y); 83 | 84 | set_events_kernel <<< dimGrid, dimBlock>>>(*output,*events_gpu); 85 | CudaCheckError(); 86 | } 87 | 88 | void upsample(iu::ImageGpu_32f_C1 *in, iu::ImageGpu_32f_C1 *out, UpsampleMethod method, bool exponentiate) 89 | { 90 | int width = out->width(); 91 | int height = out->height(); 92 | 93 | int gpu_block_x = GPU_BLOCK_SIZE; 94 | int gpu_block_y = GPU_BLOCK_SIZE; 95 | 96 | // compute number of Blocks 97 | int nb_x = iu::divUp(width,gpu_block_x); 98 | int nb_y = iu::divUp(height,gpu_block_y); 99 | 100 | dim3 dimBlock(gpu_block_x,gpu_block_y); 101 | dim3 dimGrid(nb_x,nb_y); 102 | 103 | in->prepareTexture(cudaReadModeElementType,method==UPSAMPLE_LINEAR? cudaFilterModeLinear:cudaFilterModePoint,cudaAddressModeClamp); 104 | if(exponentiate) 105 | upsample_exp_kernel <<>>(*out,in->getTexture(),out->width()/in->width()); 106 | else 107 | upsample_kernel <<>>(*out,in->getTexture(),out->width()/in->width()); 108 | CudaCheckError(); 109 | } 110 | 111 | } // namespace cuda 112 | -------------------------------------------------------------------------------- /src/common.cuh: -------------------------------------------------------------------------------- 1 | // This file is part of dvs-panotracking. 2 | // 3 | // Copyright (C) 2017 Christian Reinbacher 4 | // Institute for Computer Graphics and Vision, Graz University of Technology 5 | // https://www.tugraz.at/institute/icg/teams/team-pock/ 6 | // 7 | // dvs-panotracking is free software: you can redistribute it and/or modify it under the 8 | // terms of the GNU General Public License as published by the Free Software 9 | // Foundation, either version 3 of the License, or any later version. 10 | // 11 | // dvs-panotracking is distributed in the hope that it will be useful, but WITHOUT ANY 12 | // WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS 13 | // FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. 14 | // 15 | // You should have received a copy of the GNU General Public License 16 | // along with this program. If not, see . 17 | 18 | #ifndef COMMON_CUH 19 | #define COMMON_CUH 20 | 21 | #include 22 | #include 23 | 24 | 25 | namespace cuda { 26 | 27 | enum UpsampleMethod { 28 | UPSAMPLE_LINEAR, 29 | UPSAMPLE_NEAREST 30 | }; 31 | 32 | void setEvents(iu::ImageGpu_32f_C1 *output, iu::LinearDeviceMemory_32f_C2 *events_gpu); 33 | void upsample(iu::ImageGpu_32f_C1 *in, iu::ImageGpu_32f_C1 *out, UpsampleMethod method, bool exponentiate = false); 34 | 35 | } 36 | #endif 37 | -------------------------------------------------------------------------------- /src/common.h: -------------------------------------------------------------------------------- 1 | // This file is part of dvs-panotracking. 2 | // 3 | // Copyright (C) 2017 Christian Reinbacher 4 | // Institute for Computer Graphics and Vision, Graz University of Technology 5 | // https://www.tugraz.at/institute/icg/teams/team-pock/ 6 | // 7 | // dvs-panotracking is free software: you can redistribute it and/or modify it under the 8 | // terms of the GNU General Public License as published by the Free Software 9 | // Foundation, either version 3 of the License, or any later version. 10 | // 11 | // dvs-panotracking is distributed in the hope that it will be useful, but WITHOUT ANY 12 | // WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS 13 | // FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. 14 | // 15 | // You should have received a copy of the GNU General Public License 16 | // along with this program. If not, see . 17 | 18 | #ifndef COMMON_H 19 | #define COMMON_H 20 | #include "iu/iucore.h" 21 | #include "event.h" 22 | #include 23 | #include 24 | #include 25 | 26 | #define GPU_BLOCK_SIZE 16 27 | #define TIME_CONSTANT 1e-6f 28 | 29 | typedef Eigen::Matrix Matrix3fr; 30 | 31 | // IO functions 32 | void loadEvents(std::vector& events, const Matrix3fr& K, float radial, std::string filename); 33 | void loadEvents(std::vector& events,std::string filename); 34 | void saveEvents(std::string filename, std::vector &events); 35 | void saveState(std::string filename, const iu::ImageGpu_32f_C1 *mat, bool as_png, bool as_npy, bool as_exr); 36 | void saveState(std::string filename, const iu::ImageGpu_8u_C4 *mat); 37 | // helper function 38 | bool undistortPoint(Event& event, const Matrix3fr& K, float radial); 39 | 40 | // Define this to turn on error checking 41 | #define CUDA_ERROR_CHECK 42 | 43 | #define CudaSafeCall( err ) __cudaSafeCall( err, __FILE__, __LINE__ ) 44 | #define CudaCheckError() __cudaCheckError( __FILE__, __LINE__ ) 45 | 46 | inline void __cudaSafeCall( cudaError err, const char *file, const int line ) 47 | { 48 | #ifdef CUDA_ERROR_CHECK 49 | if ( cudaSuccess != err ) 50 | { 51 | fprintf( stderr, "cudaSafeCall() failed at %s:%i : %s\n", 52 | file, line, cudaGetErrorString( err ) ); 53 | exit( -1 ); 54 | } 55 | #endif 56 | 57 | return; 58 | } 59 | 60 | inline void __cudaCheckError( const char *file, const int line ) 61 | { 62 | #ifdef CUDA_ERROR_CHECK 63 | //cudaDeviceSynchronize(); 64 | cudaError err = cudaGetLastError(); 65 | if ( cudaSuccess != err ) 66 | { 67 | fprintf( stderr, "cudaCheckError() failed at %s:%i : %s\n", 68 | file, line, cudaGetErrorString( err ) ); 69 | exit( -1 ); 70 | 71 | } 72 | #endif 73 | 74 | } 75 | #endif // COMMON_H 76 | -------------------------------------------------------------------------------- /src/direct.cu: -------------------------------------------------------------------------------- 1 | // This file is part of dvs-panotracking. 2 | // 3 | // Copyright (C) 2017 Christian Reinbacher 4 | // Institute for Computer Graphics and Vision, Graz University of Technology 5 | // https://www.tugraz.at/institute/icg/teams/team-pock/ 6 | // 7 | // dvs-panotracking is free software: you can redistribute it and/or modify it under the 8 | // terms of the GNU General Public License as published by the Free Software 9 | // Foundation, either version 3 of the License, or any later version. 10 | // 11 | // dvs-panotracking is distributed in the hope that it will be useful, but WITHOUT ANY 12 | // WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS 13 | // FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. 14 | // 15 | // You should have received a copy of the GNU General Public License 16 | // along with this program. If not, see . 17 | 18 | #include "direct.cuh" 19 | #include "iu/iuhelpermath.h" 20 | 21 | __constant__ float2 const_pp; 22 | __constant__ float3 const_Kcaminv[3]; 23 | __constant__ float3 const_Kcam[3]; 24 | __constant__ float const_scale; 25 | 26 | 27 | __device__ float3 ProjectLine(float2 pos) 28 | { 29 | float3 posh = make_float3(pos.x,pos.y,1.f); 30 | float3 p; 31 | p.x = dot(posh,const_Kcaminv[0]); 32 | p.y = dot(posh,const_Kcaminv[1]); 33 | p.z = dot(posh,const_Kcaminv[2]); 34 | return p; 35 | } 36 | 37 | __device__ __host__ float3 RotatePoint(float3 pos, float3* rotation) 38 | { 39 | float3 point; 40 | 41 | point.x = dot(pos,rotation[0]); 42 | point.y = dot(pos,rotation[1]); 43 | point.z = dot(pos,rotation[2]); 44 | return point; 45 | } 46 | 47 | inline __device__ __host__ void eye3(float3* out, float scale) 48 | { 49 | out[0] = make_float3(scale,0.0f,0.0f); 50 | out[1] = make_float3(0.0f,scale,0.0f); 51 | out[2] = make_float3(0.0f,0.0f,scale); 52 | } 53 | 54 | inline __device__ __host__ void crossmat(float3* out, float3 vec, float scale) 55 | { 56 | vec*=scale; 57 | out[0] = make_float3(0.0,-vec.z,vec.y); 58 | out[1] = make_float3(vec.z,0.0,-vec.x); 59 | out[2] = make_float3(-vec.y,vec.x,0.0); 60 | } 61 | 62 | inline __device__ __host__ void outerproduct(float3* out, float3 vec, float scale) 63 | { 64 | out[0] = make_float3(vec.x*vec.x, vec.x*vec.y, vec.x*vec.z)*scale; 65 | out[1] = make_float3(vec.y*vec.x, vec.y*vec.y, vec.y*vec.z)*scale; 66 | out[2] = make_float3(vec.z*vec.x, vec.z*vec.y, vec.z*vec.z)*scale; 67 | } 68 | 69 | 70 | __device__ __host__ void rodrigues(float3 in, float3* out) 71 | { 72 | float theta = length(in); 73 | if(theta<1e-8f) 74 | { 75 | eye3(out,1); 76 | return; 77 | } 78 | float3 omega = in/theta; 79 | float alpha = cos(theta); 80 | float beta = sin(theta); 81 | float gamma = 1 - alpha; 82 | 83 | // R = eye(3)*alpha + crossmat(omega)*beta + omega*omega'*gamma 84 | float3 tempmat[3]; 85 | eye3(tempmat,alpha); 86 | out[0] = tempmat[0]; 87 | out[1] = tempmat[1]; 88 | out[2] = tempmat[2]; 89 | crossmat(tempmat,omega,beta); 90 | out[0] += tempmat[0]; 91 | out[1] += tempmat[1]; 92 | out[2] += tempmat[2]; 93 | outerproduct(tempmat,omega,gamma); 94 | out[0] += tempmat[0]; 95 | out[1] += tempmat[1]; 96 | out[2] += tempmat[2]; 97 | } 98 | 99 | inline __device__ int2 round(float2 p) 100 | { 101 | return make_int2(round(p.x), round(p.y)); 102 | } 103 | 104 | __device__ int2 InsideImage(float2 point, int width, int height) 105 | { 106 | int2 retval = round(point); 107 | if(retval.x<0 || retval.x>width || retval.y<0 || retval.y>height) 108 | { 109 | retval = make_int2(-1,-1); 110 | } 111 | return retval; 112 | } 113 | 114 | inline __device__ __host__ float3 RotatePointSpherical(float3 pos, float3* rotation) 115 | { 116 | return RotatePoint(make_float3(pos.z,pos.x,pos.y),rotation); 117 | } 118 | 119 | __device__ float2 ProjectMapSpherical(float3 pos) 120 | { 121 | float2 point; 122 | float el = pos.z/sqrt(pos.x*pos.x+pos.y*pos.y); 123 | float az = atan2(pos.y,pos.x); 124 | 125 | point.x = az/M_PI*const_pp.x*const_scale+const_pp.x; 126 | point.y = el*const_pp.y*const_scale/(const_pp.x/const_pp.y)+const_pp.y; 127 | 128 | return point; 129 | } 130 | 131 | 132 | __global__ void updateOccurences_kernel(iu::ImageGpu_32f_C1::KernelData occurences, iu::LinearDeviceMemory_32f_C2::KernelData events, float3 pose){ 133 | int event_id = blockIdx.x*blockDim.x + threadIdx.x; 134 | 135 | if(event_id=0) 142 | occurences(idx.x,idx.y)++; 143 | } 144 | } 145 | 146 | __global__ void updateNormalization_kernel(iu::ImageGpu_32f_C1::KernelData normalization, float3 pose, float3 old_pose, int cam_width, int cam_height){ 147 | int x = blockIdx.x*blockDim.x + threadIdx.x; 148 | int y = blockIdx.y*blockDim.y + threadIdx.y; 149 | 150 | if(x=0){ 158 | rodrigues(old_pose,R); 159 | float2 p_m_old = ProjectMapSpherical(RotatePointSpherical(ProjectLine(make_float2(x,y)),R)); 160 | normalization(curr_idx.x,curr_idx.y)+=length(p_m_old-p_m_curr); 161 | } 162 | } 163 | } 164 | 165 | __global__ void updateMap_kernel(iu::ImageGpu_32f_C1::KernelData map, iu::ImageGpu_32f_C1::KernelData occurences, iu::ImageGpu_32f_C1::KernelData normalization) { 166 | int x = blockIdx.x*blockDim.x + threadIdx.x; 167 | int y = blockIdx.y*blockDim.y + threadIdx.y; 168 | 169 | if(x(map,xx+0.5f,yy) - tex2D(map,xx-0.5f,yy), 185 | tex2D(map,xx,yy+0.5f) - tex2D(map,xx,yy-0.5f), 186 | tex2D(map,xx,yy), 187 | 0.f); 188 | } 189 | } 190 | 191 | __global__ void createOutput1_kernel(iu::ImageGpu_8u_C4::KernelData output, iu::ImageGpu_32f_C1::KernelData map) 192 | { 193 | int x = blockIdx.x*blockDim.x + threadIdx.x; 194 | int y = blockIdx.y*blockDim.y + threadIdx.y; 195 | 196 | if(x=0) 216 | output(idx.x,idx.y) = make_uchar4(255*(1.f-quality),255*quality,0,255); 217 | } 218 | } 219 | 220 | __global__ void createOutput3_kernel(iu::ImageGpu_8u_C4::KernelData output, iu::LinearDeviceMemory_32f_C2::KernelData events, float3 pose) 221 | { 222 | int event_id = blockIdx.x*blockDim.x + threadIdx.x;; 223 | 224 | if(event_id=0) 231 | output(idx.x,idx.y) = make_uchar4(0,255,0,255); 232 | } 233 | } 234 | 235 | namespace cuda{ 236 | 237 | // -------------Interface functions------------------------------- 238 | void setCameraMatrices(Eigen::Matrix& Kcam, Eigen::Matrix& Kcaminv, float p_x, float p_y, float scale) 239 | { 240 | cudaMemcpyToSymbol(const_Kcam, Kcam.data(), 3 * sizeof(float3)); 241 | CudaCheckError(); 242 | cudaMemcpyToSymbol(const_Kcaminv, Kcaminv.data(), 3 * sizeof(float3)); 243 | CudaCheckError(); 244 | cudaMemcpyToSymbol(const_scale,&scale, sizeof(float)); 245 | CudaCheckError(); 246 | float2 pp = make_float2(p_x,p_y); 247 | 248 | cudaMemcpyToSymbol(const_pp, &pp, sizeof(float2)); 249 | CudaCheckError(); 250 | 251 | } 252 | 253 | void updateMap(iu::ImageGpu_32f_C1 *map, iu::ImageGpu_32f_C1 *occurences, iu::ImageGpu_32f_C1 *normalization, iu::LinearDeviceMemory_32f_C2 *events, float3 pose, float3 old_pose, int cam_width, int cam_height) 254 | { 255 | int gpu_block_x = GPU_BLOCK_SIZE*GPU_BLOCK_SIZE; 256 | int gpu_block_y = 1; 257 | 258 | // compute number of Blocks 259 | int nb_x = iu::divUp(events->numel(),gpu_block_x); 260 | int nb_y = 1; 261 | 262 | dim3 dimBlock(gpu_block_x,gpu_block_y); 263 | dim3 dimGrid(nb_x,nb_y); 264 | 265 | updateOccurences_kernel<<>>(*occurences,*events,pose); 266 | CudaCheckError(); 267 | 268 | gpu_block_x = GPU_BLOCK_SIZE; 269 | gpu_block_y = GPU_BLOCK_SIZE; 270 | 271 | // compute number of Blocks 272 | nb_x = iu::divUp(cam_width,gpu_block_x); 273 | nb_y = iu::divUp(cam_height,gpu_block_y); 274 | 275 | dimBlock = dim3(gpu_block_x,gpu_block_y); 276 | dimGrid = dim3(nb_x,nb_y); 277 | 278 | updateNormalization_kernel<<>>(*normalization,pose,old_pose,cam_width,cam_height); 279 | CudaCheckError(); 280 | 281 | nb_x = iu::divUp(map->width(),gpu_block_x); 282 | nb_y = iu::divUp(map->height(),gpu_block_y); 283 | 284 | dimBlock = dim3(gpu_block_x,gpu_block_y); 285 | dimGrid = dim3(nb_x,nb_y); 286 | 287 | updateMap_kernel<<>>(*map,*occurences,*normalization); 288 | CudaCheckError(); 289 | } 290 | 291 | void getGradients(iu::LinearDeviceMemory_32f_C4 *output, iu::ImageGpu_32f_C1* map, iu::LinearDeviceMemory_32f_C2 *events, float3 pose) { 292 | int gpu_block_x = GPU_BLOCK_SIZE*GPU_BLOCK_SIZE; 293 | int gpu_block_y = 1; 294 | 295 | // compute number of Blocks 296 | int nb_x = iu::divUp(events->numel(),gpu_block_x); 297 | int nb_y = 1; 298 | 299 | dim3 dimBlock(gpu_block_x,gpu_block_y); 300 | dim3 dimGrid(nb_x,nb_y); 301 | 302 | getGradients_kernel<<>>(*output,map->getTexture(),*events,pose); 303 | CudaCheckError(); 304 | } 305 | 306 | void createOutput(iu::ImageGpu_8u_C4 *out, iu::ImageGpu_32f_C1 *map, iu::LinearDeviceMemory_32f_C2 *events, float3 pose, int cam_width, int cam_height, float quality){ 307 | int nb_x = iu::divUp(out->width(),GPU_BLOCK_SIZE); 308 | int nb_y = iu::divUp(out->height(),GPU_BLOCK_SIZE); 309 | 310 | dim3 dimBlock(GPU_BLOCK_SIZE,GPU_BLOCK_SIZE); 311 | dim3 dimGrid(nb_x,nb_y); 312 | 313 | createOutput1_kernel<<>>(*out,*map); 314 | 315 | nb_x = iu::divUp(cam_width,GPU_BLOCK_SIZE); 316 | nb_y = iu::divUp(cam_height,GPU_BLOCK_SIZE); 317 | 318 | dimBlock = dim3(GPU_BLOCK_SIZE,GPU_BLOCK_SIZE); 319 | dimGrid = dim3(nb_x,nb_y); 320 | if(quality>0) 321 | createOutput2_kernel<<>>(*out,pose,cam_width,cam_height,min(quality,1.f)); 322 | 323 | if(events) { 324 | nb_x = iu::divUp(events->numel(),GPU_BLOCK_SIZE); 325 | nb_y = 1; 326 | dimBlock = dim3(GPU_BLOCK_SIZE*GPU_BLOCK_SIZE,1); 327 | dimGrid = dim3(nb_x,nb_y); 328 | createOutput3_kernel<<>>(*out,*events,pose); 329 | } 330 | CudaCheckError(); 331 | } 332 | 333 | } 334 | -------------------------------------------------------------------------------- /src/direct.cuh: -------------------------------------------------------------------------------- 1 | // This file is part of dvs-panotracking. 2 | // 3 | // Copyright (C) 2017 Christian Reinbacher 4 | // Institute for Computer Graphics and Vision, Graz University of Technology 5 | // https://www.tugraz.at/institute/icg/teams/team-pock/ 6 | // 7 | // dvs-panotracking is free software: you can redistribute it and/or modify it under the 8 | // terms of the GNU General Public License as published by the Free Software 9 | // Foundation, either version 3 of the License, or any later version. 10 | // 11 | // dvs-panotracking is distributed in the hope that it will be useful, but WITHOUT ANY 12 | // WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS 13 | // FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. 14 | // 15 | // You should have received a copy of the GNU General Public License 16 | // along with this program. If not, see . 17 | 18 | #ifndef DIRECT_CUH 19 | #define DIRECT_CUH 20 | #include 21 | #include 22 | 23 | #include "common.h" 24 | 25 | namespace cuda { 26 | void setCameraMatrices(Matrix3fr &Kcam, Matrix3fr &Kcaminv, float p_x, float p_y, float scale); 27 | void updateMap(iu::ImageGpu_32f_C1 *map, iu::ImageGpu_32f_C1 *occurences, iu::ImageGpu_32f_C1 *normalization, iu::LinearDeviceMemory_32f_C2 *events, float3 pose, float3 old_pose, int cam_width, int cam_height); 28 | void getGradients(iu::LinearDeviceMemory_32f_C4 *output, iu::ImageGpu_32f_C1* map, iu::LinearDeviceMemory_32f_C2 *events, float3 pose); 29 | void createOutput(iu::ImageGpu_8u_C4 *out, iu::ImageGpu_32f_C1 *map, iu::LinearDeviceMemory_32f_C2 *events, float3 pose, int cam_width, int cam_height, float quality); 30 | } 31 | 32 | #endif //DIRECT_CUH 33 | -------------------------------------------------------------------------------- /src/dvscameraworker.cpp: -------------------------------------------------------------------------------- 1 | // This file is part of dvs-panotracking. 2 | // 3 | // Copyright (C) 2017 Christian Reinbacher 4 | // Institute for Computer Graphics and Vision, Graz University of Technology 5 | // https://www.tugraz.at/institute/icg/teams/team-pock/ 6 | // 7 | // dvs-panotracking is free software: you can redistribute it and/or modify it under the 8 | // terms of the GNU General Public License as published by the Free Software 9 | // Foundation, either version 3 of the License, or any later version. 10 | // 11 | // dvs-panotracking is distributed in the hope that it will be useful, but WITHOUT ANY 12 | // WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS 13 | // FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. 14 | // 15 | // You should have received a copy of the GNU General Public License 16 | // along with this program. If not, see . 17 | 18 | #include "dvscameraworker.h" 19 | 20 | void DVSCameraWorker::run() 21 | { 22 | if(init()) { 23 | running_ = true; 24 | while(running_) 25 | { 26 | // get event and update timestamps 27 | caerEventPacketContainer packetContainer = caerDeviceDataGet(dvs128_handle_); 28 | if (packetContainer == NULL) { 29 | msleep(1); 30 | continue; // Skip if nothing there. 31 | } 32 | events_buffer_.clear(); 33 | int32_t packetNum = caerEventPacketContainerGetEventPacketsNumber(packetContainer); 34 | for (int32_t i = 0; i < packetNum; i++) { 35 | caerEventPacketHeader packetHeader = caerEventPacketContainerGetEventPacket(packetContainer, i); 36 | if (packetHeader == NULL) { 37 | continue; // Skip if nothing there. 38 | } 39 | // Packet 0 is always the special events packet for DVS128, while packet is the polarity events packet. 40 | if (i == POLARITY_EVENT) { 41 | 42 | caerPolarityEventPacket polarity = (caerPolarityEventPacket) packetHeader; 43 | for (int32_t caerPolarityIteratorCounter = 0; caerPolarityIteratorCounter < caerEventPacketHeaderGetEventNumber(&(polarity)->packetHeader);caerPolarityIteratorCounter++) { 44 | caerPolarityEvent caerPolarityIteratorElement = caerPolarityEventPacketGetEvent(polarity, caerPolarityIteratorCounter); 45 | if (!caerPolarityEventIsValid(caerPolarityIteratorElement)) { continue; } 46 | Event event; 47 | event.t = caerPolarityEventGetTimestamp(caerPolarityIteratorElement)*1e-6; 48 | event.x = caerPolarityEventGetX(caerPolarityIteratorElement); // don't know why it is other way round? 49 | event.y = caerPolarityEventGetY(caerPolarityIteratorElement); 50 | event.polarity = caerPolarityEventGetPolarity(caerPolarityIteratorElement)?1.0f:-1.0f; 51 | // if(undistortPoint(event,params.K_cam,params.radial)) 52 | events_buffer_.push_back(event); 53 | } 54 | } 55 | } 56 | caerEventPacketContainerFree(packetContainer); 57 | ugly_->addEvents(events_buffer_); 58 | } 59 | deinit(); 60 | } 61 | } 62 | 63 | DVSCameraWorker::DVSCameraWorker(TrackingWorker *worker):ugly_(worker) 64 | { 65 | 66 | } 67 | 68 | bool DVSCameraWorker::init() 69 | { 70 | // init camera 71 | // Open a DVS128, give it a device ID of 1, and don't care about USB bus or SN restrictions. 72 | dvs128_handle_ = caerDeviceOpen(1, CAER_DEVICE_DVS128, 0, 0, NULL); 73 | if (dvs128_handle_ == NULL) { 74 | return false; 75 | } 76 | // // Let's take a look at the information we have on the device. 77 | // struct caer_dvs128_info dvs128_info = caerDVS128InfoGet(dvs128_handle_); 78 | 79 | // printf("%s --- ID: %d, Master: %d, DVS X: %d, DVS Y: %d, Logic: %d.\n", dvs128_info.deviceString, 80 | // dvs128_info.deviceID, dvs128_info.deviceIsMaster, dvs128_info.dvsSizeX, dvs128_info.dvsSizeY, 81 | // dvs128_info.logicVersion); 82 | caerDeviceSendDefaultConfig(dvs128_handle_); 83 | 84 | // Values taken from DVS_FAST 85 | // caerDeviceConfigSet(dvs128_handle_, DVS128_CONFIG_BIAS, DVS128_CONFIG_BIAS_CAS, 1992); 86 | // caerDeviceConfigSet(dvs128_handle_, DVS128_CONFIG_BIAS, DVS128_CONFIG_BIAS_DIFF, 13125); 87 | // caerDeviceConfigSet(dvs128_handle_, DVS128_CONFIG_BIAS, DVS128_CONFIG_BIAS_DIFFON, 209996); 88 | // caerDeviceConfigSet(dvs128_handle_, DVS128_CONFIG_BIAS, DVS128_CONFIG_BIAS_DIFFOFF, 132); 89 | // caerDeviceConfigSet(dvs128_handle_, DVS128_CONFIG_BIAS, DVS128_CONFIG_BIAS_FOLL, 271); 90 | // caerDeviceConfigSet(dvs128_handle_, DVS128_CONFIG_BIAS, DVS128_CONFIG_BIAS_INJGND, 1108364); 91 | // caerDeviceConfigSet(dvs128_handle_, DVS128_CONFIG_BIAS, DVS128_CONFIG_BIAS_PR, 217); 92 | // caerDeviceConfigSet(dvs128_handle_, DVS128_CONFIG_BIAS, DVS128_CONFIG_BIAS_PUX, 8159221); 93 | // caerDeviceConfigSet(dvs128_handle_, DVS128_CONFIG_BIAS, DVS128_CONFIG_BIAS_PUY, 16777215); 94 | // caerDeviceConfigSet(dvs128_handle_, DVS128_CONFIG_BIAS, DVS128_CONFIG_BIAS_REFR, 969); 95 | // caerDeviceConfigSet(dvs128_handle_, DVS128_CONFIG_BIAS, DVS128_CONFIG_BIAS_REQ, 309590); 96 | // caerDeviceConfigSet(dvs128_handle_, DVS128_CONFIG_BIAS, DVS128_CONFIG_BIAS_REQPD, 16777215); 97 | // Values taken from DVS_SLOW 98 | caerDeviceConfigSet(dvs128_handle_, DVS128_CONFIG_BIAS, DVS128_CONFIG_BIAS_CAS, 54); 99 | caerDeviceConfigSet(dvs128_handle_, DVS128_CONFIG_BIAS, DVS128_CONFIG_BIAS_DIFF, 30153); 100 | caerDeviceConfigSet(dvs128_handle_, DVS128_CONFIG_BIAS, DVS128_CONFIG_BIAS_DIFFON, 482443); 101 | caerDeviceConfigSet(dvs128_handle_, DVS128_CONFIG_BIAS, DVS128_CONFIG_BIAS_DIFFOFF, 132); 102 | caerDeviceConfigSet(dvs128_handle_, DVS128_CONFIG_BIAS, DVS128_CONFIG_BIAS_FOLL, 51); 103 | caerDeviceConfigSet(dvs128_handle_, DVS128_CONFIG_BIAS, DVS128_CONFIG_BIAS_INJGND, 1108364); 104 | caerDeviceConfigSet(dvs128_handle_, DVS128_CONFIG_BIAS, DVS128_CONFIG_BIAS_PR, 3); 105 | caerDeviceConfigSet(dvs128_handle_, DVS128_CONFIG_BIAS, DVS128_CONFIG_BIAS_PUX, 8159221); 106 | caerDeviceConfigSet(dvs128_handle_, DVS128_CONFIG_BIAS, DVS128_CONFIG_BIAS_PUY, 16777215); 107 | caerDeviceConfigSet(dvs128_handle_, DVS128_CONFIG_BIAS, DVS128_CONFIG_BIAS_REFR, 6); 108 | caerDeviceConfigSet(dvs128_handle_, DVS128_CONFIG_BIAS, DVS128_CONFIG_BIAS_REQ, 159147); 109 | caerDeviceConfigSet(dvs128_handle_, DVS128_CONFIG_BIAS, DVS128_CONFIG_BIAS_REQPD, 16777215); 110 | 111 | caerDeviceDataStart(dvs128_handle_, NULL, NULL, NULL, NULL, NULL); 112 | caerDeviceConfigSet(dvs128_handle_, CAER_HOST_CONFIG_DATAEXCHANGE, CAER_HOST_CONFIG_DATAEXCHANGE_BLOCKING, true); 113 | return true; 114 | } 115 | 116 | void DVSCameraWorker::deinit() 117 | { 118 | caerDeviceDataStop(dvs128_handle_); 119 | 120 | caerDeviceClose(&dvs128_handle_); 121 | } 122 | 123 | -------------------------------------------------------------------------------- /src/dvscameraworker.h: -------------------------------------------------------------------------------- 1 | // This file is part of dvs-panotracking. 2 | // 3 | // Copyright (C) 2017 Christian Reinbacher 4 | // Institute for Computer Graphics and Vision, Graz University of Technology 5 | // https://www.tugraz.at/institute/icg/teams/team-pock/ 6 | // 7 | // dvs-panotracking is free software: you can redistribute it and/or modify it under the 8 | // terms of the GNU General Public License as published by the Free Software 9 | // Foundation, either version 3 of the License, or any later version. 10 | // 11 | // dvs-panotracking is distributed in the hope that it will be useful, but WITHOUT ANY 12 | // WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS 13 | // FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. 14 | // 15 | // You should have received a copy of the GNU General Public License 16 | // along with this program. If not, see . 17 | 18 | #ifndef DVSCAMERAWORKER_H 19 | #define DVSCAMERAWORKER_H 20 | 21 | #include 22 | #include 23 | #include 24 | #include 25 | 26 | #include "event.h" 27 | #include "trackingworker.h" 28 | 29 | class DVSCameraWorker : public QThread 30 | { 31 | Q_OBJECT 32 | void run() Q_DECL_OVERRIDE; 33 | public: 34 | DVSCameraWorker(TrackingWorker *worker = 0); 35 | public slots: 36 | void stop(void){running_=false;} 37 | 38 | protected: 39 | bool init(void); 40 | void deinit(void); 41 | std::vector events_buffer_; 42 | caerDeviceHandle dvs128_handle_; 43 | TrackingWorker *ugly_; 44 | bool running_; 45 | }; 46 | 47 | #endif // DVSCAMERAWORKER_H 48 | -------------------------------------------------------------------------------- /src/eigenhelpers.h: -------------------------------------------------------------------------------- 1 | #ifndef EIGENHELPERS_H 2 | #define EIGENHELPERS_H 3 | 4 | #include 5 | 6 | // define a atan2 binary functor 7 | struct atan2Op { 8 | EIGEN_EMPTY_STRUCT_CTOR(atan2Op) 9 | float operator()(const float& a, const float& b) const { return atan2(a,b); } 10 | }; 11 | 12 | #endif // EIGENHELPERS_H 13 | -------------------------------------------------------------------------------- /src/event.h: -------------------------------------------------------------------------------- 1 | // This file is part of dvs-panotracking. 2 | // 3 | // Copyright (C) 2017 Christian Reinbacher 4 | // Institute for Computer Graphics and Vision, Graz University of Technology 5 | // https://www.tugraz.at/institute/icg/teams/team-pock/ 6 | // 7 | // dvs-panotracking is free software: you can redistribute it and/or modify it under the 8 | // terms of the GNU General Public License as published by the Free Software 9 | // Foundation, either version 3 of the License, or any later version. 10 | // 11 | // dvs-panotracking is distributed in the hope that it will be useful, but WITHOUT ANY 12 | // WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS 13 | // FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. 14 | // 15 | // You should have received a copy of the GNU General Public License 16 | // along with this program. If not, see . 17 | 18 | #ifndef EVENT_H 19 | #define EVENT_H 20 | 21 | typedef struct 22 | { 23 | int x; 24 | int y; 25 | float x_undist; 26 | float y_undist; 27 | float t; 28 | float polarity; 29 | }Event; 30 | 31 | #endif // EVENT_H 32 | -------------------------------------------------------------------------------- /src/live_tracking_gui.cpp: -------------------------------------------------------------------------------- 1 | // This file is part of dvs-panotracking. 2 | // 3 | // Copyright (C) 2017 Christian Reinbacher 4 | // Institute for Computer Graphics and Vision, Graz University of Technology 5 | // https://www.tugraz.at/institute/icg/teams/team-pock/ 6 | // 7 | // dvs-panotracking is free software: you can redistribute it and/or modify it under the 8 | // terms of the GNU General Public License as published by the Free Software 9 | // Foundation, either version 3 of the License, or any later version. 10 | // 11 | // dvs-panotracking is distributed in the hope that it will be useful, but WITHOUT ANY 12 | // WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS 13 | // FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. 14 | // 15 | // You should have received a copy of the GNU General Public License 16 | // along with this program. If not, see . 17 | 18 | // system includes 19 | #include 20 | #include 21 | #include 22 | #include "iu/iugui.h" 23 | #include 24 | 25 | #include "event.h" 26 | #include "scopedtimer.h" 27 | #include "trackingmainwindow.h" 28 | #include "common.h" 29 | 30 | int main(int argc, char**argv) 31 | { 32 | 33 | int numDevices = 0; 34 | CudaSafeCall(cudaGetDeviceCount(&numDevices)); 35 | std::cout << "found " << numDevices << " devices" << std::endl; 36 | 37 | for (int device = 0; device < numDevices; ++device) 38 | { 39 | cudaDeviceProp deviceProperties; 40 | CudaSafeCall(cudaGetDeviceProperties(&deviceProperties, device)); 41 | std::cout << "device number=" << device << " info= " << deviceProperties.name << std::endl; 42 | } 43 | 44 | int deviceNumber = 0; 45 | // if (numDevices > 1) 46 | // deviceNumber = 1; 47 | 48 | QApplication app(argc, argv); 49 | TrackingMainWindow window(argv[1],deviceNumber); 50 | window.show(); 51 | 52 | return app.exec(); 53 | 54 | 55 | 56 | } 57 | -------------------------------------------------------------------------------- /src/parameters.cpp: -------------------------------------------------------------------------------- 1 | // This file is part of dvs-panotracking. 2 | // 3 | // Copyright (C) 2017 Christian Reinbacher 4 | // Institute for Computer Graphics and Vision, Graz University of Technology 5 | // https://www.tugraz.at/institute/icg/teams/team-pock/ 6 | // 7 | // dvs-panotracking is free software: you can redistribute it and/or modify it under the 8 | // terms of the GNU General Public License as published by the Free Software 9 | // Foundation, either version 3 of the License, or any later version. 10 | // 11 | // dvs-panotracking is distributed in the hope that it will be useful, but WITHOUT ANY 12 | // WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS 13 | // FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. 14 | // 15 | // You should have received a copy of the GNU General Public License 16 | // along with this program. If not, see . 17 | 18 | #include "parameters.h" 19 | #include 20 | 21 | Parameters::Parameters() 22 | { 23 | } 24 | 25 | void Parameters::readFromfile(std::string filename) 26 | { 27 | // load intrinsics 28 | std::ifstream intrinsics_file; 29 | intrinsics_file.open(filename.c_str()); 30 | std::string intrinsics_file_line; 31 | for(size_t i=0; i<3; ++i) 32 | { 33 | std::getline(intrinsics_file,intrinsics_file_line); 34 | 35 | std::stringstream str(intrinsics_file_line); 36 | str >> K_cam(i,0) >> K_cam(i,1) >> K_cam(i,2); 37 | } 38 | std::getline(intrinsics_file,intrinsics_file_line); 39 | std::stringstream(intrinsics_file_line) >> output_size_x; 40 | std::getline(intrinsics_file,intrinsics_file_line); 41 | std::stringstream(intrinsics_file_line) >> output_size_y; 42 | std::getline(intrinsics_file,intrinsics_file_line); 43 | std::stringstream(intrinsics_file_line) >> radial; 44 | intrinsics_file.close(); 45 | 46 | K_caminv = K_cam.inverse(); 47 | px = output_size_x/2.f; 48 | py = output_size_y/2.f; 49 | } 50 | -------------------------------------------------------------------------------- /src/parameters.h: -------------------------------------------------------------------------------- 1 | // This file is part of dvs-panotracking. 2 | // 3 | // Copyright (C) 2017 Christian Reinbacher 4 | // Institute for Computer Graphics and Vision, Graz University of Technology 5 | // https://www.tugraz.at/institute/icg/teams/team-pock/ 6 | // 7 | // dvs-panotracking is free software: you can redistribute it and/or modify it under the 8 | // terms of the GNU General Public License as published by the Free Software 9 | // Foundation, either version 3 of the License, or any later version. 10 | // 11 | // dvs-panotracking is distributed in the hope that it will be useful, but WITHOUT ANY 12 | // WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS 13 | // FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. 14 | // 15 | // You should have received a copy of the GNU General Public License 16 | // along with this program. If not, see . 17 | 18 | #ifndef PARAMETERS_H 19 | #define PARAMETERS_H 20 | 21 | #include 22 | #include 23 | 24 | #include "common.h" 25 | 26 | class Parameters 27 | { 28 | public: 29 | Parameters(); 30 | void readFromfile(std::string filename); 31 | int input_size; 32 | int output_size_x; 33 | int output_size_y; 34 | Matrix3fr K_caminv; 35 | Matrix3fr K_cam; 36 | float px; 37 | float py; 38 | float radial; // only distortion parameter 39 | }; 40 | 41 | #endif // PARAMETERS_H 42 | -------------------------------------------------------------------------------- /src/resources/camera.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/VLOGroup/dvs-panotracking/c610baa720c99845284150318dcf2345c50705ee/src/resources/camera.png -------------------------------------------------------------------------------- /src/resources/fileopen.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/VLOGroup/dvs-panotracking/c610baa720c99845284150318dcf2345c50705ee/src/resources/fileopen.png -------------------------------------------------------------------------------- /src/resources/fileopenevents.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/VLOGroup/dvs-panotracking/c610baa720c99845284150318dcf2345c50705ee/src/resources/fileopenevents.png -------------------------------------------------------------------------------- /src/resources/filesave.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/VLOGroup/dvs-panotracking/c610baa720c99845284150318dcf2345c50705ee/src/resources/filesave.png -------------------------------------------------------------------------------- /src/resources/filesaveevents.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/VLOGroup/dvs-panotracking/c610baa720c99845284150318dcf2345c50705ee/src/resources/filesaveevents.png -------------------------------------------------------------------------------- /src/resources/pause.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/VLOGroup/dvs-panotracking/c610baa720c99845284150318dcf2345c50705ee/src/resources/pause.png -------------------------------------------------------------------------------- /src/resources/play.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/VLOGroup/dvs-panotracking/c610baa720c99845284150318dcf2345c50705ee/src/resources/play.png -------------------------------------------------------------------------------- /src/resources/reset.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/VLOGroup/dvs-panotracking/c610baa720c99845284150318dcf2345c50705ee/src/resources/reset.png -------------------------------------------------------------------------------- /src/resources/resources.qrc: -------------------------------------------------------------------------------- 1 | 2 | 3 | play.png 4 | pause.png 5 | fileopen.png 6 | filesave.png 7 | reset.png 8 | camera.png 9 | vlo_logo.png 10 | filesaveevents.png 11 | fileopenevents.png 12 | 13 | 14 | -------------------------------------------------------------------------------- /src/resources/vlo_logo.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/VLOGroup/dvs-panotracking/c610baa720c99845284150318dcf2345c50705ee/src/resources/vlo_logo.png -------------------------------------------------------------------------------- /src/scopedtimer.h: -------------------------------------------------------------------------------- 1 | /* 2 | * scopedtimer.h 3 | * 4 | * Created on: July 18, 2011 5 | * Author: Peter Innerhofer 6 | */ 7 | 8 | #ifndef SCOPED_TIMER_HPP 9 | #define SCOPED_TIMER_HPP 10 | 11 | #include 12 | 13 | #if !defined(WIN32) 14 | # include 15 | #else 16 | # include 17 | #endif 18 | #include 19 | 20 | 21 | 22 | //! A class measuring the time until leaving the scope. 23 | /*! A typical usage is like: 24 | * \code 25 | * { 26 | * Timer t("Time used in scope: "); 27 | * // do anything 28 | * } 29 | * \endcode 30 | */ 31 | class ScopedTimer 32 | { 33 | public: 34 | //! Returns the current time in us. 35 | static inline double 36 | getCurrentTime() 37 | { 38 | #if defined(WIN32) 39 | LARGE_INTEGER t, freq; 40 | ::QueryPerformanceFrequency(&freq); 41 | ::QueryPerformanceCounter(&t); 42 | return 1000000.0 * t.QuadPart / freq.QuadPart; 43 | #else 44 | timeval tv; 45 | gettimeofday(&tv, 0); 46 | return tv.tv_sec * 1000000.0 + tv.tv_usec; 47 | #endif 48 | } 49 | 50 | //! Constructs the timer with a given message and starts timing. 51 | ScopedTimer(char const * msg) 52 | : _msg(msg), _accum(0), _elapsed(0) 53 | { 54 | _start = getCurrentTime(); 55 | } 56 | 57 | //! Constructs the timer with an accumulator and starts timing. 58 | ScopedTimer(double& accum) 59 | : _msg(0), _accum(&accum), _elapsed(0) 60 | { 61 | _start = getCurrentTime(); 62 | } 63 | 64 | ScopedTimer() 65 | : _msg(0), _accum(0), _elapsed(0) 66 | { 67 | _start = getCurrentTime(); 68 | } 69 | 70 | //! Destructs the timer and emits a message and/or updates the accumulator. 71 | ~ScopedTimer() 72 | { 73 | double const end = getCurrentTime(); 74 | if (_msg != 0) 75 | { 76 | std::cout << _msg << (end-_start)/1000000 << "sec" << std::endl; 77 | } 78 | if (_accum != 0) 79 | { 80 | *_accum += (end-_start)/1000000; 81 | } 82 | } 83 | 84 | void printTime(char const * msg2 = 0) 85 | { 86 | double const end = getCurrentTime(); 87 | if (_msg != 0 && msg2 != 0) 88 | { 89 | std::cout << _msg << " " << msg2 << (end-_start)/1000000 << "sec" << std::endl; 90 | } 91 | else if (_msg != 0) 92 | { 93 | std::cout << _msg << (end-_start)/1000000 << "sec" << std::endl; 94 | } 95 | 96 | } 97 | 98 | void start() 99 | { 100 | _elapsed=0; 101 | _start = getCurrentTime(); 102 | } 103 | 104 | void stop() 105 | { 106 | if (_start != 0) 107 | { 108 | _elapsed+=getCurrentTime()-_start; 109 | _start=0; 110 | } 111 | } 112 | 113 | void cont() 114 | { 115 | _start = getCurrentTime(); 116 | } 117 | 118 | double getElapsedSeconds() 119 | { 120 | double time(getCurrentTime()); 121 | if (_start != 0) _elapsed+=time-_start; 122 | _start=time; 123 | return(_elapsed/1000000.0); 124 | } 125 | 126 | protected: 127 | char const * _msg; 128 | double _start; 129 | double * _accum; 130 | double _elapsed; 131 | }; 132 | 133 | 134 | #endif 135 | -------------------------------------------------------------------------------- /src/trackingmainwindow.cpp: -------------------------------------------------------------------------------- 1 | // This file is part of dvs-panotracking. 2 | // 3 | // Copyright (C) 2017 Christian Reinbacher 4 | // Institute for Computer Graphics and Vision, Graz University of Technology 5 | // https://www.tugraz.at/institute/icg/teams/team-pock/ 6 | // 7 | // dvs-panotracking is free software: you can redistribute it and/or modify it under the 8 | // terms of the GNU General Public License as published by the Free Software 9 | // Foundation, either version 3 of the License, or any later version. 10 | // 11 | // dvs-panotracking is distributed in the hope that it will be useful, but WITHOUT ANY 12 | // WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS 13 | // FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. 14 | // 15 | // You should have received a copy of the GNU General Public License 16 | // along with this program. If not, see . 17 | 18 | #include "trackingmainwindow.h" 19 | #include 20 | #include 21 | #include 22 | #include 23 | #include 24 | #include 25 | #include 26 | #include 27 | #include 28 | #include 29 | #include 30 | #include 31 | #include 32 | #include "common.h" 33 | //#define DAVIS 34 | 35 | TrackingMainWindow::TrackingMainWindow(char *camera_configuration_file, int device_number) : QMainWindow(NULL) 36 | { 37 | #ifdef DAVIS 38 | int width = 240; 39 | int height = 180; 40 | #else 41 | int width = 128; 42 | int height = 128; 43 | #endif 44 | parameters_.readFromfile(camera_configuration_file); 45 | tracking_worker_ = new TrackingWorker(parameters_,width,height, device_number,1.5f); 46 | camera_worker_ = new DVSCameraWorker(tracking_worker_); 47 | 48 | std::cout << parameters_.K_cam << std::endl; 49 | 50 | mdi_area_ = new QMdiArea(this); 51 | setCentralWidget(mdi_area_); 52 | 53 | output_win_ = new iu::Qt5ImageGpuWidget(iu::Size<2>(parameters_.output_size_x,parameters_.output_size_y),this); 54 | QMdiSubWindow* window = mdi_area_->addSubWindow(output_win_); 55 | window->setGeometry(QRect(0,0,parameters_.output_size_x+10,parameters_.output_size_y+40)); 56 | window->setWindowTitle("Output Map"); 57 | window->setWindowFlags(Qt::CustomizeWindowHint|Qt::WindowTitleHint); 58 | window->setMaximumSize(QSize(parameters_.output_size_x+10,parameters_.output_size_y+40)); 59 | window->setMinimumSize(QSize(parameters_.output_size_x+10,parameters_.output_size_y+40)); 60 | 61 | status_bar_ = statusBar(); 62 | 63 | show(); 64 | 65 | while(!output_win_->isValid()) // wait until events are processed and window is created 66 | QApplication::instance()->processEvents(); 67 | 68 | 69 | dock_ = new QDockWidget("Parameters", this); 70 | QGridLayout* layout = new QGridLayout; 71 | spin_events_per_image_ = new QSpinBox; 72 | spin_events_per_image_->setMinimum(1); 73 | spin_events_per_image_->setMaximum(10000); 74 | spin_events_per_image_->setValue(1500); 75 | spin_events_per_image_->setSingleStep(100); 76 | spin_image_skip_ = new QSpinBox; 77 | spin_image_skip_->setMinimum(1); 78 | spin_image_skip_->setMaximum(10000); 79 | spin_image_skip_->setValue(5); 80 | spin_image_skip_->setSingleStep(1); 81 | spin_iterations_ = new QSpinBox; 82 | spin_iterations_->setMinimum(1); 83 | spin_iterations_->setMaximum(1000); 84 | spin_iterations_->setValue(10); 85 | spin_iterations_->setSingleStep(1); 86 | spin_acceleration_ = new QDoubleSpinBox; 87 | spin_acceleration_->setMinimum(0); 88 | spin_acceleration_->setMaximum(1); 89 | spin_acceleration_->setValue(0.4); 90 | spin_acceleration_->setSingleStep(0.1); 91 | action_start_ = new QAction(QIcon(":play.png"),tr("&Start algorithm"),this); 92 | action_stop_ = new QAction(QIcon(":pause.png"),tr("S&top algorithm"),this); 93 | action_camera_ = new QAction(QIcon(":camera.png"),tr("St&art camera"),this); 94 | check_show_camera_pose_ = new QCheckBox("Show camera pose?"); 95 | check_show_camera_pose_->setChecked(true); 96 | check_show_camera_pose_->setToolTip("Display the current estimated pose"); 97 | check_show_input_events_ = new QCheckBox("Show input events?"); 98 | check_show_input_events_->setChecked(true); 99 | check_show_input_events_->setToolTip("Display the current events"); 100 | 101 | QGroupBox* parameters = new QGroupBox; 102 | QLabel* label_iterations = new QLabel("Iterations:"); 103 | spin_iterations_->setToolTip("Optimization iterations per pose update"); 104 | QLabel* label_acceleration = new QLabel("Accel. Factor:"); 105 | spin_acceleration_->setToolTip("Weighting of momentum term in optimization"); 106 | QLabel* label_image_skip = new QLabel("Show every nth image:"); 107 | spin_image_skip_->setToolTip("Only display every xth image on screen"); 108 | QLabel* label_events_per_image = new QLabel("Events/image:"); 109 | spin_events_per_image_->setToolTip("Accumulate x events before reconstructing an image"); 110 | QSpacerItem *space = new QSpacerItem(1,1,QSizePolicy::Minimum, QSizePolicy::MinimumExpanding); 111 | 112 | layout->addWidget(label_events_per_image, 0, 0, 1, 1); 113 | layout->addWidget(spin_events_per_image_, 0, 1, 1, 1); 114 | layout->addWidget(label_image_skip, 1, 0, 1, 1); 115 | layout->addWidget(spin_image_skip_, 1, 1, 1, 1); 116 | layout->addWidget(label_iterations, 2, 0, 1, 1); 117 | layout->addWidget(spin_iterations_, 2, 1, 1, 1); 118 | layout->addWidget(label_acceleration, 3, 0, 1, 1); 119 | layout->addWidget(spin_acceleration_, 3, 1, 1, 1); 120 | layout->addWidget(check_show_camera_pose_ ,4, 0, 1, 2); 121 | layout->addWidget(check_show_input_events_,5, 0, 1, 2); 122 | layout->addItem(space, 6, 0,-1,-1); 123 | 124 | parameters->setLayout(layout); 125 | dock_->setWidget(parameters); 126 | dock_->setFeatures(QDockWidget::NoDockWidgetFeatures); 127 | dock_->setSizePolicy(QSizePolicy::MinimumExpanding,QSizePolicy::Minimum); 128 | addDockWidget(Qt::LeftDockWidgetArea, dock_); 129 | 130 | connect(spin_events_per_image_,SIGNAL(valueChanged(int)),tracking_worker_,SLOT(updateEventsPerImage(int))); 131 | connect(spin_image_skip_,SIGNAL(valueChanged(int)),tracking_worker_,SLOT(updateImageSkip(int))); 132 | connect(spin_iterations_,SIGNAL(valueChanged(int)),tracking_worker_,SLOT(updateIterations(int))); 133 | connect(spin_acceleration_,SIGNAL(valueChanged(double)),tracking_worker_,SLOT(updateAcceleration(double))); 134 | connect(tracking_worker_,SIGNAL(update_output(iu::ImageGpu_8u_C4*)),output_win_,SLOT(update_image(iu::ImageGpu_8u_C4*))); 135 | connect(tracking_worker_,SIGNAL(update_info(const QString&,int)),status_bar_,SLOT(showMessage(const QString&,int))); 136 | connect(action_start_,SIGNAL(triggered(bool)),this,SLOT(startTracking())); 137 | connect(action_stop_,SIGNAL(triggered(bool)),this,SLOT(stopTracking())); 138 | connect(action_camera_,SIGNAL(triggered(bool)),this,SLOT(startCamera())); 139 | connect(check_show_camera_pose_,SIGNAL(clicked(bool)),tracking_worker_,SLOT(updateShowCameraPose(bool))); 140 | connect(check_show_input_events_,SIGNAL(clicked(bool)),tracking_worker_,SLOT(updateShowInputEvents(bool))); 141 | 142 | // Menu Stuff 143 | action_open_ = new QAction(QIcon(":fileopenevents.png"),tr("&Load events from file"),this); 144 | connect(action_open_,SIGNAL(triggered(bool)),this,SLOT(loadEvents())); 145 | action_save_events_ = new QAction(QIcon(":filesaveevents.png"),tr("Sa&ve events to file"),this); 146 | connect(action_save_events_,SIGNAL(triggered(bool)),this,SLOT(saveEvents())); 147 | action_save_state_ = new QAction(QIcon(":filesave.png"),tr("Sa&ve state to file"),this); 148 | connect(action_save_state_,SIGNAL(triggered(bool)),this,SLOT(saveState())); 149 | action_view_about_ = new QAction(tr("Abo&ut"),this); 150 | connect(action_view_about_,SIGNAL(triggered(bool)),this,SLOT(showAbout())); 151 | 152 | menu_file_ = menuBar()->addMenu(tr("&File")); 153 | menu_file_->addAction(action_open_); 154 | menu_file_->addAction(action_save_events_); 155 | menu_file_->addAction(action_save_state_); 156 | 157 | menu_view_ = menuBar()->addMenu(tr("&View")); 158 | menu_view_->addAction(action_view_about_); 159 | 160 | QToolBar *toolbar = new QToolBar; 161 | toolbar->setMovable(false); 162 | toolbar->addAction(action_start_); 163 | toolbar->addAction(action_stop_); 164 | toolbar->addAction(action_camera_); 165 | toolbar->addSeparator(); 166 | toolbar->addAction(action_open_); 167 | toolbar->addAction(action_save_events_); 168 | toolbar->addAction(action_save_state_); 169 | addToolBar(Qt::LeftToolBarArea,toolbar); 170 | 171 | // Window title 172 | setWindowTitle("Real-Time DVS Tracking"); 173 | setGeometry(QRect(0,0,parameters_.output_size_x+10+dock_->geometry().width()+220,(parameters_.output_size_y+10)+90)); 174 | setWindowIcon(QIcon(":vlo_logo.png")); 175 | } 176 | 177 | TrackingMainWindow::~TrackingMainWindow() 178 | { 179 | stopTracking(); 180 | tracking_worker_->wait(); 181 | camera_worker_->wait(); 182 | } 183 | 184 | void TrackingMainWindow::startTracking() 185 | { 186 | tracking_worker_->stop(); 187 | if(events_.empty()) { // start camera thread 188 | camera_worker_->start(); 189 | } else { 190 | tracking_worker_->addEvents(events_); 191 | } 192 | tracking_worker_->start(); 193 | } 194 | 195 | void TrackingMainWindow::stopTracking() 196 | { 197 | tracking_worker_->stop(); 198 | camera_worker_->stop(); 199 | } 200 | 201 | void TrackingMainWindow::startCamera() 202 | { 203 | events_.clear(); 204 | startTracking(); 205 | } 206 | 207 | void TrackingMainWindow::loadEvents() 208 | { 209 | QString fileName = QFileDialog::getOpenFileName(this, 210 | tr("Open Event File"), "", tr("Event Files (*.aer2 *.dat *.txt)")); 211 | status_bar_->showMessage("Loading...",0); 212 | readevents(fileName.toStdString()); 213 | } 214 | 215 | void TrackingMainWindow::saveEvents() 216 | { 217 | stopTracking(); 218 | QString fileName = QFileDialog::getSaveFileName(this, 219 | tr("Save Events to File"),"/home/christian/data/testdata/event_camera_testdata",tr("Event Files (*.aer2)")); 220 | tracking_worker_->saveEvents(fileName.toStdString()); 221 | } 222 | 223 | void TrackingMainWindow::saveState() 224 | { 225 | QString fileName = QFileDialog::getSaveFileName(this, 226 | tr("Save State File"),"/home/christian/data/testdata/event_camera_testdata",tr("All Files, no ext (*.*)")); 227 | tracking_worker_->saveCurrentState(fileName.toStdString()); 228 | } 229 | 230 | void TrackingMainWindow::showAbout() 231 | { 232 | QMessageBox::about(this,"About","Demo application for our publication\n" 233 | "Real-Time Panorama Tracking for Event Cameras\n" 234 | "(c) Institute for Computer Graphics and Vision\n" 235 | " Vision, Learning and Optimization Group, 2017\n"); 236 | } 237 | 238 | void TrackingMainWindow::readevents(std::string filename) 239 | { 240 | QFileInfo info(filename.c_str()); 241 | events_.clear(); 242 | if(info.suffix()=="aer2" || info.suffix()=="txt") { 243 | ::loadEvents(events_,filename); 244 | } else if(info.suffix()=="dat"){ // read Bardow files 245 | Event temp_event; 246 | float first_timestamp=0; 247 | float time; 248 | float last_timestamp=0; 249 | bool normalize_time=true; 250 | std::ifstream ifs; 251 | ifs.open(filename.c_str(),std::ios::in|std::ios::binary); 252 | if(ifs.good()) { 253 | unsigned int data; 254 | 255 | while(!ifs.eof()) { 256 | ifs.read((char*)&data,4); 257 | time = data; 258 | // if(first_timestamp==0) { 259 | // first_timestamp=time; 260 | // } 261 | time-=first_timestamp; 262 | ifs.read((char*)&data,4); 263 | temp_event.x = (data & 0x000001FF); 264 | temp_event.y = (data & 0x0001FE00) >> 9; 265 | temp_event.polarity = (data & 0x00020000) >> 17; 266 | // if(flip_ud) 267 | // temp_event.y = 127-temp_event.y; 268 | temp_event.t = time*TIME_CONSTANT; 269 | temp_event.polarity=temp_event.polarity>0?1:-1; 270 | events_.push_back(temp_event); 271 | } 272 | ifs.close(); 273 | } 274 | } 275 | status_bar_->showMessage(tr("Loaded a file with %1 events").arg(events_.size()),0); 276 | } 277 | 278 | TrackingMainWindow::TrackingMainWindow() 279 | { 280 | 281 | } 282 | -------------------------------------------------------------------------------- /src/trackingmainwindow.h: -------------------------------------------------------------------------------- 1 | // This file is part of dvs-panotracking. 2 | // 3 | // Copyright (C) 2017 Christian Reinbacher 4 | // Institute for Computer Graphics and Vision, Graz University of Technology 5 | // https://www.tugraz.at/institute/icg/teams/team-pock/ 6 | // 7 | // dvs-panotracking is free software: you can redistribute it and/or modify it under the 8 | // terms of the GNU General Public License as published by the Free Software 9 | // Foundation, either version 3 of the License, or any later version. 10 | // 11 | // dvs-panotracking is distributed in the hope that it will be useful, but WITHOUT ANY 12 | // WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS 13 | // FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. 14 | // 15 | // You should have received a copy of the GNU General Public License 16 | // along with this program. If not, see . 17 | 18 | #ifndef DENOISINGMAINWINDOW_H 19 | #define DENOISINGMAINWINDOW_H 20 | 21 | #include 22 | #include 23 | #include 24 | #include 25 | #include 26 | #include 27 | #include 28 | #include 29 | #include 30 | #include 31 | #include 32 | 33 | #include "parameters.h" 34 | #include 35 | #include "event.h" 36 | #include "iu/iugui.h" 37 | #include "trackingworker.h" 38 | #include "dvscameraworker.h" 39 | 40 | 41 | class TrackingMainWindow : public QMainWindow 42 | { 43 | Q_OBJECT 44 | public: 45 | TrackingMainWindow(); 46 | TrackingMainWindow(char* camera_configuration_file, int device_number); 47 | ~TrackingMainWindow(); 48 | 49 | protected slots: 50 | void startTracking(); 51 | void stopTracking(); 52 | void startCamera(); 53 | void loadEvents(); 54 | void saveEvents(); 55 | void showAbout(); 56 | void saveState(); 57 | 58 | protected: 59 | void readevents(std::string filename); 60 | 61 | iu::Qt5ImageGpuWidget *output_win_; 62 | std::vector events_; 63 | TrackingWorker *tracking_worker_; 64 | DVSCameraWorker *camera_worker_; 65 | Parameters parameters_; 66 | 67 | QMdiArea *mdi_area_; 68 | QStatusBar *status_bar_; 69 | QTimer update_gl_timer_; 70 | QDockWidget* dock_; 71 | 72 | QSpinBox *spin_iterations_; 73 | QSpinBox *spin_image_skip_; 74 | QSpinBox *spin_events_per_image_; 75 | QDoubleSpinBox *spin_acceleration_; 76 | QCheckBox *check_show_camera_pose_; 77 | QCheckBox *check_show_input_events_; 78 | 79 | QAction *action_start_; 80 | QAction *action_stop_; 81 | QAction *action_camera_; 82 | 83 | QMenu *menu_file_; 84 | QAction *action_open_; 85 | QAction *action_save_events_; 86 | QAction *action_save_state_; 87 | QMenu *menu_view_; 88 | QAction *action_view_about_; 89 | 90 | bool simple_mode_; 91 | }; 92 | 93 | #endif // DENOISINGMAINWINDOW_H 94 | -------------------------------------------------------------------------------- /src/trackingworker.cpp: -------------------------------------------------------------------------------- 1 | // This file is part of dvs-panotracking. 2 | // 3 | // Copyright (C) 2017 Christian Reinbacher 4 | // Institute for Computer Graphics and Vision, Graz University of Technology 5 | // https://www.tugraz.at/institute/icg/teams/team-pock/ 6 | // 7 | // dvs-panotracking is free software: you can redistribute it and/or modify it under the 8 | // terms of the GNU General Public License as published by the Free Software 9 | // Foundation, either version 3 of the License, or any later version. 10 | // 11 | // dvs-panotracking is distributed in the hope that it will be useful, but WITHOUT ANY 12 | // WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS 13 | // FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. 14 | // 15 | // You should have received a copy of the GNU General Public License 16 | // along with this program. If not, see . 17 | 18 | #include 19 | #include 20 | #include "trackingworker.h" 21 | #include "common.cuh" 22 | #include "common.h" 23 | #include "direct.cuh" 24 | #include "cnpy.h" 25 | #include "iu/iuio.h" 26 | #include "iu/iumath.h" 27 | #include "eigenhelpers.h" 28 | 29 | TrackingWorker::TrackingWorker(const Parameters &cam_parameters, int width, int height, int device_number, float upscale) 30 | { 31 | device_number_ = device_number; 32 | CudaSafeCall(cudaSetDevice(device_number_)); 33 | width_ = width; 34 | height_ = height; 35 | output_ = new iu::ImageGpu_32f_C1(cam_parameters.output_size_x,cam_parameters.output_size_y); 36 | output_color_ = new iu::ImageGpu_8u_C4(cam_parameters.output_size_x,cam_parameters.output_size_y); 37 | occurences_ = new iu::ImageGpu_32f_C1(cam_parameters.output_size_x,cam_parameters.output_size_y); 38 | normalization_ = new iu::ImageGpu_32f_C1(cam_parameters.output_size_x,cam_parameters.output_size_y); 39 | 40 | iu::math::fill(*occurences_,0.f); 41 | iu::math::fill(*normalization_, 1.f); 42 | iu::math::fill(*output_, 0.f); 43 | 44 | events_per_image_=1500; 45 | iterations_ = 10; 46 | image_skip_ = 5; 47 | 48 | camera_parameters_ = cam_parameters; 49 | upscale_ = upscale; 50 | tracking_quality_ = 1; 51 | image_id_ = 0; 52 | 53 | cuda::setCameraMatrices(camera_parameters_.K_cam,camera_parameters_.K_caminv,camera_parameters_.px,camera_parameters_.py,upscale_); 54 | 55 | events_cpu_ = NULL; 56 | events_gpu_ = NULL; 57 | image_gradients_cpu_ = NULL; 58 | image_gradients_gpu_ = NULL; 59 | 60 | pose_.setZero(); 61 | old_pose_ = pose_; 62 | 63 | R_sphere_ << 0,0,1, 64 | 1,0,0, 65 | 0,1,0; 66 | 67 | lambda_ = 100.f; 68 | lambda_a_ = 2.f; 69 | lambda_b_ = 10.f; 70 | alpha_ = 0.4f; 71 | 72 | show_camera_pose_ = true; 73 | show_events_ = true; 74 | } 75 | 76 | void TrackingWorker::addEvents(std::vector &events) 77 | { 78 | if(all_events_.size()>0) { 79 | all_events_.clear();; 80 | } 81 | QMutexLocker lock(&mutex_events_); 82 | for(int i=0;ievents_per_image_; 108 | mutex_events_.unlock(); 109 | if(image_available) { 110 | mutex_events_.lock(); 111 | std::vector temp_events; 112 | for (int i=0;i &events) 143 | { 144 | iu::IuCudaTimer timer; 145 | double time_map; 146 | double time_track; 147 | 148 | // Keep CPU<->GPU interface memory up-to-date 149 | if(!events_cpu_ || events_cpu_->numel()!= events.size()) 150 | events_cpu_ = new iu::LinearHostMemory_32f_C2(events.size()); 151 | if(!events_gpu_ || events_gpu_->numel()!= events.size()) 152 | events_gpu_ = new iu::LinearDeviceMemory_32f_C2(events.size()); 153 | if(!image_gradients_cpu_ || image_gradients_cpu_->numel()!= events.size()) 154 | image_gradients_cpu_ = new iu::LinearHostMemory_32f_C4(events.size()); 155 | if(!image_gradients_gpu_ || image_gradients_gpu_->numel()!= events.size()) 156 | image_gradients_gpu_ = new iu::LinearDeviceMemory_32f_C4(events.size()); 157 | 158 | for (int i=0;idata(i) = make_float2(events[i].x_undist,events[i].y_undist); 161 | } 162 | iu::copy(events_cpu_,events_gpu_); 163 | 164 | if(image_id_>10){ // First few poses are crap anyhow, since there is no map. 165 | timer.start(); 166 | bool successfull = updatePose(); 167 | time_track = timer.elapsed(); 168 | if(successfull && tracking_quality_>0.25f) {// first few events often contain only noise. Update map only when tracking is good (arbitrary th). 169 | timer.start(); 170 | cuda::updateMap(output_,occurences_,normalization_,events_gpu_,make_float3(pose_(0),pose_(1),pose_(2)),make_float3(old_pose_(0),old_pose_(1),old_pose_(2)),width_,height_); 171 | time_map = timer.elapsed(); 172 | } 173 | } else { 174 | cuda::updateMap(output_,occurences_,normalization_,events_gpu_,make_float3(pose_(0),pose_(1),pose_(2)),make_float3(old_pose_(0),old_pose_(1),old_pose_(2)),width_,height_); 175 | } 176 | image_id_++; 177 | if(image_skip_>0 && (image_id_ % image_skip_)==0) { 178 | 179 | emit update_info(tr("Track: %1ms Map: %2ms. Quality: %3").arg(time_track).arg(time_map).arg(tracking_quality_),0); 180 | cuda::createOutput(output_color_,output_,show_events_? events_gpu_:NULL,make_float3(pose_(0),pose_(1),pose_(2)),width_,height_,show_camera_pose_?tracking_quality_:-1.f); 181 | emit update_output(output_color_); 182 | 183 | } 184 | } 185 | 186 | Matrix3fr TrackingWorker::rodrigues(Eigen::Vector3f in) 187 | { 188 | float theta = in.norm(); 189 | if(theta<1e-8f) 190 | { 191 | return Matrix3fr::Identity(); 192 | } 193 | Eigen::Vector3f omega = in/theta; 194 | float alpha = cos(theta); 195 | float beta = sin(theta); 196 | float gamma = 1 - alpha; 197 | 198 | // R = eye(3)*alpha + crossmat(omega)*beta + omega*omega'*gamma 199 | return Matrix3fr::Identity() * alpha + crossmat(omega)*beta + omega*omega.transpose()*gamma; 200 | } 201 | 202 | Matrix3fr TrackingWorker::crossmat(Eigen::Vector3f t) 203 | { 204 | Matrix3fr t_hat; 205 | t_hat << 0, -t(2), t(1), 206 | t(2), 0, -t(0), 207 | -t(1), t(0), 0; 208 | return t_hat; 209 | } 210 | 211 | bool TrackingWorker::updatePose() 212 | { 213 | 214 | // Pre-calculate stuff which doesn't change between iterations 215 | Eigen::Map< Eigen::Matrix2Xf> events((float*)events_cpu_->data(),2,events_cpu_->numel()); 216 | Eigen::Matrix3Xf points(3,events.cols()); 217 | points.topLeftCorner(events.rows(),events.cols()) = events; 218 | points.bottomRows<1>().setOnes(); 219 | points = R_sphere_ * camera_parameters_.K_caminv * points; 220 | 221 | Eigen::Matrix3Xf X_hat(3,events.cols()); 222 | Eigen::RowVectorXf X_hat_norm(events.cols()); 223 | Eigen::MatrixX3f J(events.cols(),3); 224 | Eigen::MatrixX3f dG_dgsi(9,3); 225 | Eigen::Matrix3Xf dg_dG(3,9); 226 | Eigen::Matrix3f JtJ(3,3); 227 | Eigen::Matrix2Xf dPI_dg(2,3); 228 | Eigen::Map< Eigen::Matrix4Xf > dM_dx((float*)image_gradients_cpu_->data(),4,events_cpu_->numel()); 229 | Eigen::Map< Eigen::VectorXf, 0, Eigen::Stride<0,4> > M(&image_gradients_cpu_->data(0)->z,events_cpu_->numel()); 230 | 231 | old_pose_ = pose_; 232 | Eigen::Vector3f old_pose = pose_; 233 | Eigen::Vector3f init_pose = pose_; 234 | Eigen::Vector3f accel_pose = pose_; 235 | for(int iteration=0; iteration move to CPU 240 | cuda::getGradients(image_gradients_gpu_,output_,events_gpu_,make_float3(accel_pose(0),accel_pose(1),accel_pose(2))); 241 | iu::copy(image_gradients_gpu_,image_gradients_cpu_); 242 | dG_dgsi << crossmat(-R.row(0)),crossmat(-R.row(1)),crossmat(-R.row(2)); 243 | JtJ.setZero(); 244 | for(int id=0;id(0,id).transpose()*dPI_dg * dg_dG * dG_dgsi; 256 | JtJ += J.row(id).transpose()*J.row(id); 257 | } 258 | // Gauss-Newton with prox 259 | float alpha=1.f; 260 | old_pose = pose_; 261 | pose_ = accel_pose - (JtJ + alpha*JtJ.diagonal().asDiagonal().toDenseMatrix()).inverse()*((J.transpose()*-M) - alpha*(accel_pose-init_pose)); 262 | accel_pose = pose_ + alpha_*(pose_-old_pose); 263 | } 264 | tracking_quality_ = std::min(M.sum()/M.size()*upscale_,1.f); 265 | return true; 266 | } 267 | 268 | void TrackingWorker::saveCurrentState(std::string filename) 269 | { 270 | saveState(filename,output_color_); 271 | } 272 | 273 | void TrackingWorker::clearEvents() 274 | { 275 | QMutexLocker lock(&mutex_events_); 276 | std::queue empty; 277 | std::swap(events_,empty); 278 | } 279 | 280 | 281 | -------------------------------------------------------------------------------- /src/trackingworker.h: -------------------------------------------------------------------------------- 1 | // This file is part of dvs-panotracking. 2 | // 3 | // Copyright (C) 2017 Christian Reinbacher 4 | // Institute for Computer Graphics and Vision, Graz University of Technology 5 | // https://www.tugraz.at/institute/icg/teams/team-pock/ 6 | // 7 | // dvs-panotracking is free software: you can redistribute it and/or modify it under the 8 | // terms of the GNU General Public License as published by the Free Software 9 | // Foundation, either version 3 of the License, or any later version. 10 | // 11 | // dvs-panotracking is distributed in the hope that it will be useful, but WITHOUT ANY 12 | // WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS 13 | // FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. 14 | // 15 | // You should have received a copy of the GNU General Public License 16 | // along with this program. If not, see . 17 | 18 | #ifndef DENOISINGWORKER_H 19 | #define DENOISINGWORKER_H 20 | 21 | #include 22 | #include 23 | #include 24 | #include 25 | 26 | #include "iu/iucore.h" 27 | #include "event.h" 28 | #include "parameters.h" 29 | 30 | 31 | class TrackingWorker : public QThread 32 | { 33 | Q_OBJECT 34 | void run() Q_DECL_OVERRIDE; 35 | public: 36 | TrackingWorker(const Parameters& cam_parameters, int width=128, int height=128, int device_number=0, float upscale=1.f); 37 | void addEvents(std::vector& events); 38 | void saveEvents(std::string filename); 39 | void saveCurrentState(std::string filename); 40 | void track(std::vector& events); 41 | Eigen::Vector3f getPose(void){return pose_;} 42 | 43 | signals: 44 | void update_output(iu::ImageGpu_8u_C4*); 45 | void update_info(const QString&,int); 46 | 47 | public slots: 48 | void stop(); 49 | void updateEventsPerImage(int value){events_per_image_ = value;} 50 | void updateIterations(int value){iterations_ = value;} 51 | void updateImageSkip(int value){image_skip_ = value;} 52 | void updateShowCameraPose(bool value){show_camera_pose_ = value;} 53 | void updateShowInputEvents(bool value){show_events_ = value;} 54 | void updateScale(float value); 55 | void updateAcceleration(double value){alpha_ = value;} 56 | 57 | protected: 58 | 59 | bool updatePose(void); 60 | void clearEvents(void); 61 | Matrix3fr rodrigues(Eigen::Vector3f in); 62 | Matrix3fr crossmat(Eigen::Vector3f t); 63 | 64 | int events_per_image_; 65 | int iterations_; 66 | int width_; 67 | int height_; 68 | Parameters camera_parameters_; 69 | 70 | bool show_camera_pose_; 71 | bool show_events_; 72 | int device_number_; 73 | bool running_; 74 | int image_id_; 75 | int image_skip_; 76 | float upscale_; 77 | 78 | std::queue events_; 79 | std::vector all_events_; 80 | QMutex mutex_events_; 81 | iu::ImageGpu_32f_C1 *output_; 82 | iu::ImageGpu_8u_C4 *output_color_; 83 | iu::ImageGpu_32f_C1 *occurences_; 84 | iu::ImageGpu_32f_C1 *normalization_; 85 | 86 | iu::LinearHostMemory_32f_C2 *events_cpu_; 87 | iu::LinearDeviceMemory_32f_C2 * events_gpu_; 88 | iu::LinearHostMemory_32f_C4 *image_gradients_cpu_; 89 | iu::LinearDeviceMemory_32f_C4 * image_gradients_gpu_; 90 | 91 | Eigen::Vector3f pose_; 92 | Eigen::Vector3f old_pose_; 93 | Matrix3fr R_sphere_; 94 | float tracking_quality_; 95 | 96 | // optimizer 97 | float lambda_; 98 | float lambda_a_; 99 | float lambda_b_; 100 | float alpha_; 101 | }; 102 | 103 | #endif // DENOISINGWORKER_H 104 | --------------------------------------------------------------------------------