diff options
Diffstat (limited to 'tracker-pt')
| -rw-r--r-- | tracker-pt/module/CMakeLists.txt | 2 | ||||
| -rw-r--r-- | tracker-pt/module/camera_kinect_ir.cpp | 182 | ||||
| -rw-r--r-- | tracker-pt/module/camera_kinect_ir.h | 70 | ||||
| -rw-r--r-- | tracker-pt/module/module.cpp | 47 | 
4 files changed, 297 insertions, 4 deletions
diff --git a/tracker-pt/module/CMakeLists.txt b/tracker-pt/module/CMakeLists.txt index 22b725c9..72d985c6 100644 --- a/tracker-pt/module/CMakeLists.txt +++ b/tracker-pt/module/CMakeLists.txt @@ -3,4 +3,6 @@ if(OpenCV_FOUND)      otr_module(tracker-pt)      target_link_libraries(${self} opentrack-tracker-pt-base)      target_include_directories(${self} PUBLIC "${CMAKE_SOURCE_DIR}/tracker-pt") +    # Add Kinect dependency if available +    otr_kinect_setup()      endif() diff --git a/tracker-pt/module/camera_kinect_ir.cpp b/tracker-pt/module/camera_kinect_ir.cpp new file mode 100644 index 00000000..ea5d2591 --- /dev/null +++ b/tracker-pt/module/camera_kinect_ir.cpp @@ -0,0 +1,182 @@ +/* Copyright (c) 2012 Patrick Ruoff + * + * Permission to use, copy, modify, and/or distribute this software for any + * purpose with or without fee is hereby granted, provided that the above + * copyright notice and this permission notice appear in all copies. + */ + +#include "camera_kinect_ir.h" +#include "frame.hpp" + +#include "compat/sleep.hpp" +#include "compat/camera-names.hpp" +#include "compat/math-imports.hpp" + +#include <opencv2/imgproc.hpp> + +#include "cv/video-property-page.hpp" + +#include <cstdlib> + +namespace pt_module { + +CameraKinectIr::CameraKinectIr(const QString& module_name) : s { module_name } +{ +} + +QString CameraKinectIr::get_desired_name() const +{ +    return desired_name; +} + +QString CameraKinectIr::get_active_name() const +{ +    return active_name; +} + +void CameraKinectIr::show_camera_settings() +{ +    const int idx = camera_name_to_index(s.camera_name); + +    if (cap && cap->isOpened()) +        video_property_page::show_from_capture(*cap, idx); +    else +        video_property_page::show(idx); +} + +CameraKinectIr::result CameraKinectIr::get_info() const +{ +    if (cam_info.res_x == 0 || cam_info.res_y == 0) +        return { false, pt_camera_info() }; +    else +        return { true, cam_info }; +} + +CameraKinectIr::result CameraKinectIr::get_frame(pt_frame& frame_) +{ +    cv::Mat& frame = frame_.as<Frame>()->mat; + +    const bool new_frame = get_frame_(frame); + +    if (new_frame) +    { +        const f dt = (f)t.elapsed_seconds(); +        t.start(); + +        // measure fps of valid frames +        constexpr f RC = f{1}/10; // seconds +        const f alpha = dt/(dt + RC); + +        if (dt_mean < dt_eps) +            dt_mean = dt; +        else +            dt_mean = (1-alpha) * dt_mean + alpha * dt; + +        cam_info.fps = dt_mean > dt_eps ? 1 / dt_mean : 0; +        cam_info.res_x = frame.cols; +        cam_info.res_y = frame.rows; +        cam_info.fov = fov; + +        return { true, cam_info }; +    } +    else +        return { false, {} }; +} + +bool CameraKinectIr::start(int idx, int fps, int res_x, int res_y) +{ + +    if (idx >= 0 && fps >= 0 && res_x >= 0 && res_y >= 0) +    { +        if (cam_desired.idx != idx || +            (int)cam_desired.fps != fps || +            cam_desired.res_x != res_x || +            cam_desired.res_y != res_y || +            !cap || !cap->isOpened() || !cap->grab()) +        { +            stop(); + +            desired_name = get_camera_names().value(idx); +            bool kinectIRSensor = false; +            if (desired_name.compare(KKinectIRSensor) == 0) +            { +                kinectIRSensor = true; +            } +            cam_desired.idx = idx; +            cam_desired.fps = fps; +            cam_desired.res_x = res_x; +            cam_desired.res_y = res_y; +            cam_desired.fov = fov; + +            cap = camera_ptr(new cv::VideoCapture(idx)); + +            if (cam_desired.res_x > 0 && cam_desired.res_y > 0) +            { +                cap->set(cv::CAP_PROP_FRAME_WIDTH,  res_x); +                cap->set(cv::CAP_PROP_FRAME_HEIGHT, res_y); +            } + +            if (fps > 0) +                cap->set(cv::CAP_PROP_FPS, fps); + +            if (cap->isOpened()) +            { +                cam_info = pt_camera_info(); +                cam_info.idx = idx; +                dt_mean = 0; +                active_name = desired_name; + +                cv::Mat tmp; + +                if (get_frame_(tmp)) +                { +                    t.start(); +                    return true; +                } +            } + +            cap = nullptr; +            return false; +        } + +        return true; +    } + +    stop(); +    return false; +} + +void CameraKinectIr::stop() +{ +    cap = nullptr; +    desired_name = QString{}; +    active_name = QString{}; +    cam_info = {}; +    cam_desired = {}; +} + +bool CameraKinectIr::get_frame_(cv::Mat& frame) +{ +    if (cap && cap->isOpened()) +    { +        for (unsigned i = 0; i < 10; i++) +        { +            if (cap->read(frame)) +                return true; +            portable::sleep(50); +        } +    } +    return false; +} + +void CameraKinectIr::camera_deleter::operator()(cv::VideoCapture* cap) +{ +    if (cap) +    { +        if (cap->isOpened()) +            cap->release(); +        delete cap; +    } +} + +} // ns pt_module diff --git a/tracker-pt/module/camera_kinect_ir.h b/tracker-pt/module/camera_kinect_ir.h new file mode 100644 index 00000000..93c3d75b --- /dev/null +++ b/tracker-pt/module/camera_kinect_ir.h @@ -0,0 +1,70 @@ +/* Copyright (c) 2012 Patrick Ruoff + * + * Permission to use, copy, modify, and/or distribute this software for any + * purpose with or without fee is hereby granted, provided that the above + * copyright notice and this permission notice appear in all copies. + */ + +#pragma once + +#if __has_include(<Kinect.h>) + +#include "pt-api.hpp" +#include "compat/timer.hpp" + +#include <memory> + +#include <opencv2/core.hpp> +#include <opencv2/videoio.hpp> + +#include <QString> + +namespace pt_module { + +/// +/// Implement our camera interface using Kinect V2 SDK IR Sensor. +/// +struct CameraKinectIr final : pt_camera +{ +    CameraKinectIr(const QString& module_name); + +    bool start(int idx, int fps, int res_x, int res_y) override; +    void stop() override; + +    result get_frame(pt_frame& Frame) override; +    result get_info() const override; + +    pt_camera_info get_desired() const override { return cam_desired; } +    QString get_desired_name() const override; +    QString get_active_name() const override; + +    void set_fov(f value) override { fov = value; } +    void show_camera_settings() override; + +private: +    [[nodiscard]] bool get_frame_(cv::Mat& frame); + +    f dt_mean = 0, fov = 30; +    Timer t; +    pt_camera_info cam_info; +    pt_camera_info cam_desired; +    QString desired_name, active_name; + +    struct camera_deleter final +    { +        void operator()(cv::VideoCapture* cap); +    }; + +    using camera_ptr = std::unique_ptr<cv::VideoCapture, camera_deleter>; + +    camera_ptr cap; + +    pt_settings s; + +    static constexpr f dt_eps = f{1}/256; +}; + +} // ns pt_module + + +#endif diff --git a/tracker-pt/module/module.cpp b/tracker-pt/module/module.cpp index db3e8fac..c3b417a7 100644 --- a/tracker-pt/module/module.cpp +++ b/tracker-pt/module/module.cpp @@ -2,6 +2,7 @@  #include "module.hpp"  #include "camera.h" +#include "camera_kinect_ir.h"  #include "compat/camera-names.hpp"  #include "frame.hpp"  #include "point_extractor.h" @@ -19,7 +20,9 @@ static const QString module_name = "tracker-pt";  namespace pt_module { -// Traits for OpenCV VideoCapture camera +/// +/// Traits for OpenCV VideoCapture camera +///  struct pt_module_traits final : pt_runtime_traits  {      pointer<pt_camera> make_camera() const override @@ -48,6 +51,41 @@ struct pt_module_traits final : pt_runtime_traits      }  }; +#if __has_include(<Kinect.h>) +/// +/// Traits for Kinect V2 IR Sensor +/// +struct KinectIrTraits final : pt_runtime_traits +{ +    pointer<pt_camera> make_camera() const override +    { +        return pointer<pt_camera>(new CameraKinectIr(module_name)); +    } + +    pointer<pt_point_extractor> make_point_extractor() const override +    { +        return pointer<pt_point_extractor>(new PointExtractor(module_name)); +    } + +    QString get_module_name() const override +    { +        return module_name; +    } + +    pointer<pt_frame> make_frame() const override +    { +        return pointer<pt_frame>(new Frame); +    } + +    pointer<pt_preview> make_preview(int w, int h) const override +    { +        return pointer<pt_preview>(new Preview(w, h)); +    } +}; +#endif + + +  struct tracker_pt : Tracker_PT  {      tracker_pt() : Tracker_PT(module_name) @@ -56,13 +94,14 @@ struct tracker_pt : Tracker_PT      pointer<pt_runtime_traits> create_traits() override      { -        // Create different traits according to settings +#if __has_include(<Kinect.h>) +        // Create Kinect traits according to settings          if (s.camera_name().compare(KKinectIRSensor) == 0)          {              // Use Kinect IR trait -            return pointer<pt_runtime_traits>(new pt_module_traits); +            return pointer<pt_runtime_traits>(new KinectIrTraits);          } - +#endif          return pointer<pt_runtime_traits>(new pt_module_traits);      }  | 
