From 124a626bb8aff150ebcd2cb135fd0ef6e3f9cf8b Mon Sep 17 00:00:00 2001 From: Julian Oes Date: Fri, 22 Mar 2024 07:31:42 +1300 Subject: [PATCH] camera-manager: add absolute zoom Turns out that works despite the manual saying otherwise. --- camera-manager/siyi_camera.hpp | 42 +++++++++++++++++++++++++++++--- camera-manager/siyi_cli.cpp | 23 ++++++++++++++--- camera-manager/siyi_protocol.cpp | 1 + camera-manager/siyi_protocol.hpp | 17 +++++++++++++ 4 files changed, 76 insertions(+), 7 deletions(-) diff --git a/camera-manager/siyi_camera.hpp b/camera-manager/siyi_camera.hpp index fb544a3..4cc3fa5 100644 --- a/camera-manager/siyi_camera.hpp +++ b/camera-manager/siyi_camera.hpp @@ -3,6 +3,7 @@ #include "siyi_protocol.hpp" #include +#include namespace siyi { @@ -311,7 +312,7 @@ class Camera { _messager.send(_serializer.assemble_message(manual_zoom)); - // We don't seem to be getting anything back. + // We don't seem to be getting anything back, it just times out. //const auto maybe_ack_manual_zoom = // _deserializer.disassemble_message(_messager.receive()); @@ -323,8 +324,41 @@ class Camera { return true; } - [[nodiscard]] unsigned zoom() const { - return _ack_manual_zoom.zoom_multiple; + // Unavailable + //[[nodiscard]] unsigned zoom() const { + // return _ack_manual_zoom.zoom_multiple; + //} + + bool absolute_zoom(float factor) + { + auto message = siyi::AbsoluteZoom{}; + + if (factor > static_cast(0x1E)) { + std::cerr << "zoom factor too high" << std::endl; + return false; + } + if (factor < 1.f) { + std::cerr << "zoom factor too small" << std::endl; + return false; + } + + message.absolute_movement_integer = static_cast(factor); + message.absolute_movement_fractional = static_cast(std::roundf((factor-static_cast(message.absolute_movement_integer)) * 10.f)); + + std::cerr << "Sending abs zoom: " << (int)message.absolute_movement_integer << "." << (int)message.absolute_movement_fractional << std::endl; + + _messager.send(_serializer.assemble_message(message)); + + // We don't seem to be getting anything back, it just times out. + //const auto maybe_ack_manual_zoom = + // _deserializer.disassemble_message(_messager.receive()); + + //if (maybe_ack_manual_zoom) { + // std::cerr << "current zoom: " << maybe_ack_manual_zoom.value().zoom_multiple << '\n'; + // _ack_manual_zoom = maybe_ack_manual_zoom.value(); + // return false; + //} + return true; } private: @@ -335,7 +369,7 @@ class Camera { AckFirmwareVersion _version{}; AckGetStreamResolution _recording_settings{}; AckGetStreamResolution _stream_settings{}; - AckManualZoom _ack_manual_zoom{}; + // AckManualZoom _ack_manual_zoom{}; }; } // siyi diff --git a/camera-manager/siyi_cli.cpp b/camera-manager/siyi_cli.cpp index 44ce727..178853e 100644 --- a/camera-manager/siyi_cli.cpp +++ b/camera-manager/siyi_cli.cpp @@ -1,6 +1,7 @@ #include "siyi_camera.hpp" #include #include +#include #include void print_usage(const std::string_view& bin_name) @@ -19,6 +20,7 @@ void print_usage(const std::string_view& bin_name) << " - in (to start zooming in)\n" << " - out (to start zooming out)\n" << " - stop (to stop zooming)\n" + << " - (1.0 to 6.0)\n" << "\n" << " get settings Show all settings for stream or recording\n\n" << "\n" @@ -287,9 +289,15 @@ int main(int argc, char* argv[]) return 1; } } else { - std::cout << "Invalid zoom command" << std::endl; - print_usage(argv[0]); - return 1; + float factor; + try { + factor = std::stof(option.data()); + } catch (std::invalid_argument&) { + std::cout << "Invalid zoom command" << std::endl; + print_usage(argv[0]); + return 1; + }; + siyi_camera.absolute_zoom(factor); } } else { std::cout << "Not enough arguments\n"; @@ -297,6 +305,15 @@ int main(int argc, char* argv[]) return 1; } + } else if (action == "zoom") { + if (argc >= 3) { + + } else { + std::cout << "Not enough arguments\n"; + print_usage(argv[0]); + return 1; + } + } else { std::cout << "Unknown command\n"; print_usage(argv[0]); diff --git a/camera-manager/siyi_protocol.cpp b/camera-manager/siyi_protocol.cpp index fad6ed5..89abb1a 100644 --- a/camera-manager/siyi_protocol.cpp +++ b/camera-manager/siyi_protocol.cpp @@ -24,6 +24,7 @@ bool Messager::send(const std::vector& message) std::cerr << "Error sending UDP packet: " << strerror(errno) << std::endl; return false; } + // std::cerr << "Sent " << sent << std::endl; return true; } diff --git a/camera-manager/siyi_protocol.hpp b/camera-manager/siyi_protocol.hpp index 0ca0003..2cc9354 100644 --- a/camera-manager/siyi_protocol.hpp +++ b/camera-manager/siyi_protocol.hpp @@ -207,6 +207,23 @@ class ManualZoom : public Payload { std::int8_t zoom{}; }; +class AbsoluteZoom : public Payload { +public: + [[nodiscard]] std::vector bytes_impl() const { + std::vector result; + result.push_back(absolute_movement_integer); + result.push_back(absolute_movement_fractional); + return result; + } + + static std::uint8_t cmd_id_impl() { + return 0x0F; + } + + std::uint8_t absolute_movement_integer{}; + std::uint8_t absolute_movement_fractional{}; +}; + class Messager { public: