Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
44 changes: 44 additions & 0 deletions Dockerfile
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
FROM ubuntu:20.04

WORKDIR /app
ENV preset=2
ENV mode=1
ENV nolog=0
ENV reverse=0
ENV nomt=1
ENV speed=0
ENV nogui=1
ENV DEBIAN_FRONTEND noninteractive
RUN apt-get update && \
apt install -y git
RUN git clone https://github.com/IldarGreat/dso.git
RUN apt-get install -y build-essential \
libsuitesparse-dev libeigen3-dev libboost-all-dev \
libopencv-dev

WORKDIR /app
RUN git clone --recursive https://github.com/stevenlovegrove/Pangolin.git -b v0.6
WORKDIR /app/Pangolin
RUN apt-get install -y cmake && \
apt-get clean && \
apt install -y libglew-dev && \
apt-get install -y libegl1-mesa-dev

RUN cmake -B build && \
cmake --build build

RUN apt-get install -y zlib1g-dev
WORKDIR /app/dso/thirdparty/
RUN tar -zxvf libzip-1.1.1.tar.gz
WORKDIR /app/dso/thirdparty/libzip-1.1.1/
RUN ./configure && \
make && \
cp lib/zipconf.h /usr/local/include/zipconf.h

RUN git submodule update --init

WORKDIR /app/dso/build
RUN cmake .. && \
make

ENTRYPOINT ./bin/dso_dataset files=set/sequence calib=set/camera.txt mode=${mode} preset=${preset} nolog=${nolog} reverse=${reverse} nomt=${nomt} speed=${speed} nogui=${nogui}
80 changes: 55 additions & 25 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -8,12 +8,32 @@ For more information see
* **A Photometrically Calibrated Benchmark For Monocular Visual Odometry**, *J. Engel, V. Usenko, D. Cremers*, In arXiv:1607.02555, 2016

Get some datasets from [https://vision.in.tum.de/mono-dataset](https://vision.in.tum.de/mono-dataset) .

### 2. Installation

git clone https://github.com/JakobEngel/dso.git

#### 2.1 Required Dependencies
### 2. Installation with docker

#### 2.1 Get image
##### Build image from Dockerfile.
git clone https://github.com/IldarGreat/dso.git
docker build . -t ildarthegreat/dso
##### Or pull image from dockerhub
docker pull ildarthegreat/dso
##### If you have arm based system
docker pull ildarthegreat/dsoarm64
#### 2.2 Run container
docker run \
-v {path}:/app/dso/build/set \
-e mode=2 \
... other environment (see Dockerfile)
ildarthegreat/dso (or ildarthegreat/dsoarm64)
path - it's folder that contains the calib file camera.txt and another folder named sequence that contains a sequence of images<br>
Example: .../path<br>
-camera.txt<br>
-sequence

### 3. Installation from source code

git clone https://github.com/IldarGreat/dso.git

#### 3.1 Required Dependencies

##### suitesparse and eigen3 (required).
Required. Install with
Expand All @@ -22,7 +42,7 @@ Required. Install with



#### 2.2 Optional Dependencies
#### 3.2 Optional Dependencies

##### OpenCV (highly recommended).
Used to read / write / display images.
Expand All @@ -37,7 +57,7 @@ Install with
sudo apt-get install libopencv-dev


##### Pangolin (highly recommended).
##### Pangolin v0.4! (highly recommended).
Used for 3D visualization & the GUI.
Pangolin is **only** used in `IOWrapper/Pangolin/*`. You can compile without Pangolin,
however then there is not going to be any visualization / GUI capability.
Expand All @@ -46,6 +66,16 @@ and use it instead of `PangolinDSOViewer`

Install from [https://github.com/stevenlovegrove/Pangolin](https://github.com/stevenlovegrove/Pangolin)

Or install like bellow

git clone --recursive https://github.com/stevenlovegrove/Pangolin.git -b v0.6
apt-get clean
sudo apt install libglew-dev
sudo apt-get install libegl1-mesa-dev
cd Pangolin
cmake -B build
cmake --build build


##### ziplib (recommended).
Used to read datasets with images as .zip, as e.g. in the TUM monoVO dataset.
Expand All @@ -64,7 +94,7 @@ to unzip the dataset image archives before loading them).
##### sse2neon (required for ARM builds).
After cloning, just run `git submodule update --init` to include this. It translates Intel-native SSE functions to ARM-native NEON functions during the compilation process.

#### 2.3 Build
#### 3.3 Build

cd dso
mkdir build
Expand All @@ -76,12 +106,12 @@ this will compile a library `libdso.a`, which can be linked from external projec
It will also build a binary `dso_dataset`, to run DSO on datasets. However, for this
OpenCV and Pangolin need to be installed.

If you have error with boost, please add #include <boost/bind.hpp> to IndexThreadReduce





### 3 Usage
### 4 Usage
Run on a dataset from [https://vision.in.tum.de/mono-dataset](https://vision.in.tum.de/mono-dataset) using

bin/dso_dataset \
Expand All @@ -98,17 +128,17 @@ other camera drivers, to use DSO interactively without ROS.



#### 3.1 Dataset Format.
#### 4.1 Dataset Format.
The format assumed is that of [https://vision.in.tum.de/mono-dataset](https://vision.in.tum.de/mono-dataset).
However, it should be easy to adapt it to your needs, if required. The binary is run with:

- `files=XXX` where XXX is either a folder or .zip archive containing images. They are sorted *alphabetically*. for .zip to work, need to comiple with ziplib support.
- `files=XXX` where XXX is either a folder or .zip archive containing images. They are sorted *alphabetically*. for .zip to work, need to comiple with ziplib support. You can use video_to_images.py in utils folder to split video into images. For example python video_to_images.py -v "path to video" . It create a folder 'images' desired sequence of images

- `gamma=XXX` where XXX is a gamma calibration file, containing a single row with 256 values, mapping [0..255] to the respective irradiance value, i.e. containing the *discretized inverse response function*. See TUM monoVO dataset for an example.
- `gamma=XXX` where XXX is a gamma calibration file, containing a single row with 256 values, mapping [0..255] to the respective irradiance value, i.e. containing the *discretized inverse response function*. See TUM monoVO dataset for an example or read this https://github.com/tum-vision/online_photometric_calibration

- `vignette=XXX` where XXX is a monochrome 16bit or 8bit image containing the vignette as pixelwise attenuation factors. See TUM monoVO dataset for an example.

- `calib=XXX` where XXX is a geometric camera calibration file. See below.
- `calib=XXX` where XXX is a geometric camera calibration file. See below. If you want you can use calibration.py in utils it use chessboard 6*9, to check camera calibration settings. For example python calibration.py -i "path to images of chessboard"



Expand All @@ -117,30 +147,30 @@ However, it should be easy to adapt it to your needs, if required. The binary is

###### Calibration File for Pre-Rectified Images

Pinhole fx fy cx cy 0
fx fy cx cy 0
in_width in_height
"crop" / "full" / "none" / "fx fy cx cy 0"
out_width out_height

###### Calibration File for FOV camera model:

FOV fx fy cx cy omega
fx fy cx cy omega
in_width in_height
"crop" / "full" / "fx fy cx cy 0"
out_width out_height


###### Calibration File for Radio-Tangential camera model

RadTan fx fy cx cy k1 k2 r1 r2
fx fy cx cy k1 k2 r1 r2
in_width in_height
"crop" / "full" / "fx fy cx cy 0"
out_width out_height


###### Calibration File for Equidistant camera model

EquiDistant fx fy cx cy k1 k2 k3 k4
fx fy cx cy k1 k2 k3 k4
in_width in_height
"crop" / "full" / "fx fy cx cy 0"
out_width out_height
Expand Down Expand Up @@ -183,7 +213,7 @@ outliers along those borders, and corrupt the scale-pyramid).



#### 3.2 Commandline Options
#### 4.2 Commandline Options
there are many command line options available, see `main_dso_pangolin.cpp`. some examples include
- `mode=X`:
- `mode=0` use iff a photometric calibration exists (e.g. TUM monoVO dataset).
Expand All @@ -210,11 +240,11 @@ there are many command line options available, see `main_dso_pangolin.cpp`. some



#### 3.3 Runtime Options
#### 4.3 Runtime Options
Some parameters can be reconfigured from the Pangolin GUI at runtime. Feel free to add more.


#### 3.4 Accessing Data.
#### 4.4 Accessing Data.
The easiest way to access the Data (poses, pointclouds, etc.) computed by DSO (in real-time)
is to create your own `Output3DWrapper`, and add it to the system, i.e., to `FullSystem.outputWrapper`.
The respective member functions will be called on various occations (e.g., when a new KF is created,
Expand All @@ -233,7 +263,7 @@ using the TUM RGB-D / TUM monoVO format ([timestamp x y z qx qy qz qw] of the ca



#### 3.5 Notes
#### 4.5 Notes
- the initializer is very slow, and does not work very reliably. Maybe replace by your own way to get an initialization.
- see [https://github.com/JakobEngel/dso_ros](https://github.com/JakobEngel/dso_ros) for a minimal example project on how to use the library with your own input / output procedures.
- see `settings.cpp` for a LOT of settings parameters. Most of which you shouldn't touch.
Expand All @@ -242,7 +272,7 @@ using the TUM RGB-D / TUM monoVO format ([timestamp x y z qx qy qz qw] of the ca



### 4 General Notes for Good Results
### 5 General Notes for Good Results

#### Accurate Geometric Calibration
- Please have a look at Chapter 4.3 from the DSO paper, in particular Figure 20 (Geometric Noise). Direct approaches suffer a LOT from bad geometric calibrations: Geometric distortions of 1.5 pixel already reduce the accuracy by factor 10.
Expand Down Expand Up @@ -272,7 +302,7 @@ little rotation) during initialization.
Possibly replace by your own initializer.


### 5 License
### 6 License
DSO was developed at the Technical University of Munich and Intel.
The open-source version is licensed under the GNU General Public License
Version 3 (GPLv3).
Expand Down
20 changes: 20 additions & 0 deletions builddso.bash
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
sudo apt-get install -y libsuitesparse-dev libeigen3-dev libboost-all-dev libopencv-dev libglew-dev libegl1-mesa-dev cmake zlib1g-dev curl lsb-release
user=ildar
cd /home/$user
mkdir app
cd app
git clone --recursive https://github.com/stevenlovegrove/Pangolin.git -b v0.6
cd Pangolin
mkdir build
cd build
cmake ..
make

cd /home/$user/app
git clone https://github.com/IldarGreat/dso.git
cd dso
git submodule update --init
mkdir build
cd build
cmake ..
make
8 changes: 4 additions & 4 deletions src/IOWrapper/OpenCV/ImageRW_OpenCV.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,7 @@ namespace IOWrap
{
MinimalImageB* readImageBW_8U(std::string filename)
{
cv::Mat m = cv::imread(filename, CV_LOAD_IMAGE_GRAYSCALE);
cv::Mat m = cv::imread(filename, cv::IMREAD_GRAYSCALE);
if(m.rows*m.cols==0)
{
printf("cv::imread could not read image %s! this may segfault. \n", filename.c_str());
Expand All @@ -52,7 +52,7 @@ MinimalImageB* readImageBW_8U(std::string filename)

MinimalImageB3* readImageRGB_8U(std::string filename)
{
cv::Mat m = cv::imread(filename, CV_LOAD_IMAGE_COLOR);
cv::Mat m = cv::imread(filename, cv::IMREAD_COLOR);
if(m.rows*m.cols==0)
{
printf("cv::imread could not read image %s! this may segfault. \n", filename.c_str());
Expand All @@ -70,7 +70,7 @@ MinimalImageB3* readImageRGB_8U(std::string filename)

MinimalImage<unsigned short>* readImageBW_16U(std::string filename)
{
cv::Mat m = cv::imread(filename, CV_LOAD_IMAGE_UNCHANGED);
cv::Mat m = cv::imread(filename, cv::IMREAD_UNCHANGED);
if(m.rows*m.cols==0)
{
printf("cv::imread could not read image %s! this may segfault. \n", filename.c_str());
Expand All @@ -88,7 +88,7 @@ MinimalImage<unsigned short>* readImageBW_16U(std::string filename)

MinimalImageB* readStreamBW_8U(char* data, int numBytes)
{
cv::Mat m = cv::imdecode(cv::Mat(numBytes,1,CV_8U, data), CV_LOAD_IMAGE_GRAYSCALE);
cv::Mat m = cv::imdecode(cv::Mat(numBytes,1,CV_8U, data), cv::IMREAD_GRAYSCALE);
if(m.rows*m.cols==0)
{
printf("cv::imdecode could not read stream (%d bytes)! this may segfault. \n", numBytes);
Expand Down
63 changes: 63 additions & 0 deletions utils/calibration.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,63 @@
import cv2
import numpy as np
import os
import glob
import argparse

ap = argparse.ArgumentParser()
ap.add_argument("-i", "--images", required=True, help="path to input images")
args = vars(ap.parse_args())

# Определение размеров шахматной доски
CHECKERBOARD = (6,9)
criteria = (cv2.TERM_CRITERIA_EPS + cv2.TERM_CRITERIA_MAX_ITER, 30, 0.001)
# Создание вектора для хранения векторов трехмерных точек для каждого изображения шахматной доски
objpoints = []
# Создание вектора для хранения векторов 2D точек для каждого изображения шахматной доски
imgpoints = []
# Определение мировых координат для 3D точек
objp = np.zeros((1, CHECKERBOARD[0] * CHECKERBOARD[1], 3), np.float32)
objp[0,:,:2] = np.mgrid[0:CHECKERBOARD[0], 0:CHECKERBOARD[1]].T.reshape(-1, 2)
prev_img_shape = None
# Извлечение пути отдельного изображения, хранящегося в данном каталоге
images = glob.glob(args["images"]+'/*.jpg')
for fname in images:
img = cv2.imread(fname)
gray = cv2.cvtColor(img,cv2.COLOR_BGR2GRAY)
# Найти углы шахматной доски
# Если на изображении найдено нужное количество углов, тогда ret = true
ret, corners = cv2.findChessboardCorners(gray, CHECKERBOARD, cv2.CALIB_CB_ADAPTIVE_THRESH + cv2.CALIB_CB_FAST_CHECK + cv2.CALIB_CB_NORMALIZE_IMAGE)

"""
Если желаемый номер угла обнаружен,
уточняем координаты пикселей и отображаем
их на изображениях шахматной доски
"""
if ret == True:
objpoints.append(objp)
# уточнение координат пикселей для заданных 2d точек.
corners2 = cv2.cornerSubPix(gray, corners, (11,11),(-1,-1), criteria)

imgpoints.append(corners2)
# Нарисовать и отобразить углы
img = cv2.drawChessboardCorners(img, CHECKERBOARD, corners2, ret)

cv2.imshow('img',img)
cv2.waitKey(0)
cv2.destroyAllWindows()
h,w = img.shape[:2]
"""
Выполнение калибровки камеры с помощью
Передача значения известных трехмерных точек (объектов)
и соответствующие пиксельные координаты
обнаруженные углы (imgpoints)
"""
ret, mtx, dist, rvecs, tvecs = cv2.calibrateCamera(objpoints, imgpoints, gray.shape[::-1], None, None)
print("Camera matrix : \n")
print(mtx)
print("dist : \n")
print(dist)
print("rvecs : \n")
print(rvecs)
print("tvecs : \n")
print(tvecs)
Binary file added utils/chessboard.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading