/* * VizionStreamer - Main Application * Copyright (c) 2025 Maik Jurischka * * Licensed under CC BY-NC-SA 4.0 * https://creativecommons.org/licenses/by-nc-sa/4.0/ */ #include #include #include #include #include #include "vizionstreamer/SocketServer.h" #include "vizionstreamer/CameraController.h" std::atomic g_running(true); void signalHandler(int signal) { std::cout << "\nReceived signal " << signal << ", shutting down..." << std::endl; g_running = false; } int main() { // Setup signal handlers for clean shutdown signal(SIGINT, signalHandler); signal(SIGTERM, signalHandler); // List available cameras std::vector devList; const int deviceCount = VxDiscoverCameraDevices(devList); if (deviceCount == 0) { std::cout << "No cameras found" << std::endl; return -1; } std::cout << "Found " << deviceCount << " camera(s):" << std::endl; for (size_t i = 0; i < devList.size(); i++) { std::cout << "[" << i << "] " << devList[i] << std::endl; } // Find VCI-AR0234 camera int cameraIndex = -1; for (size_t i = 0; i < devList.size(); i++) { if (devList[i].find("VCI-AR0234") != std::string::npos) { cameraIndex = static_cast(i); std::cout << "Selected camera [" << cameraIndex << "]: " << devList[i] << std::endl; break; } } if (cameraIndex == -1) { std::cout << "VCI-AR0234 camera not found, using default (index 0)" << std::endl; cameraIndex = 0; } // Open camera auto cam = VxInitialCameraDevice(cameraIndex); if (!cam || VxOpen(cam) != 0) { std::cout << "Failed to initialize/open camera" << std::endl; return -1; } // Get and set default format std::vector fmtList; if (VxGetFormatList(cam, fmtList) != 0) { std::cout << "Failed to get format list" << std::endl; VxClose(cam); return -1; } if (VxSetFormat(cam, fmtList[0]) != 0) { std::cout << "Failed to set format" << std::endl; VxClose(cam); return -1; } std::cout << "Initial format: " << fmtList[0].width << "x" << fmtList[0].height << " @ " << fmtList[0].framerate << " fps" << std::endl; const auto controller = std::make_shared(cam); const std::string socketPath = "/tmp/vizion_control.sock"; SocketServer server(socketPath); if (!server.start([controller](const std::string& cmd) { return controller->processCommand(cmd); })) { std::cout << "Failed to start socket server" << std::endl; VxClose(cam); return -1; } std::cout << "\n========================================" << std::endl; std::cout << "VizionStreamer Ready" << std::endl; std::cout << "Author: Maik Jurischka " << std::endl; std::cout << "License: CC BY-NC-SA 4.0 -> https://creativecommons.org/licenses/by-nc-sa/4.0/" << std::endl; std::cout << "========================================" << std::endl << std::endl; std::cout << "Control socket: " << socketPath << std::endl; std::cout << "Default pipeline: videoconvert ! autovideosink" << std::endl; std::cout << "\nQuick start:" << std::endl; std::cout << R"( echo '{"command":"start_stream"}' | socat - UNIX-CONNECT:)" << socketPath << std::endl; std::cout << "\nTo change pipeline before starting:" << std::endl; std::cout << R"( echo '{"command":"set_pipeline","params":{"pipeline":"YOUR_PIPELINE"}}' | socat - UNIX-CONNECT:)" << socketPath << std::endl; std::cout << "\nPress Ctrl+C to exit.\n" << std::endl; while (g_running) { std::this_thread::sleep_for(std::chrono::milliseconds(100)); } std::cout << "Shutting down..." << std::endl; if (controller->getStreamingEngine()->isRunning()) { controller->getStreamingEngine()->stop(); } server.stop(); VxClose(cam); std::cout << "Shutdown complete." << std::endl; return 0; }