From cde055e29b9ee6f8711de1993c0eca9dfbbc0390 Mon Sep 17 00:00:00 2001 From: Bruno Herbelin Date: Sun, 26 Dec 2021 01:20:44 +0100 Subject: [PATCH] Implementation of Session control With Session recall from OSC --- ControlManager.cpp | 65 ++++++++++++++++++++++++++++++++----- ControlManager.h | 6 +++- rsc/osc/vimix.mk1.touchosc | Bin 2071 -> 2130 bytes 3 files changed, 62 insertions(+), 9 deletions(-) diff --git a/ControlManager.cpp b/ControlManager.cpp index 91c1674..97974b4 100644 --- a/ControlManager.cpp +++ b/ControlManager.cpp @@ -29,6 +29,7 @@ #include "BaseToolkit.h" #include "Mixer.h" #include "Source.h" +#include "ActionManager.h" #include "ControlManager.h" @@ -81,13 +82,21 @@ void Control::RequestListener::ProcessMessage( const osc::ReceivedMessage& m, // Output target: concerns attributes of the rendering output else if ( target.compare(OSC_OUTPUT) == 0 ) { - if ( attribute.compare(OSC_SYNC) == 0) { + if ( attribute.compare(OSC_SYNC) == 0 || Control::manager().receiveOutputAttribute(attribute, m.ArgumentStream())) { // send the global status Control::manager().sendOutputStatus(remoteEndpoint); } - else - if ( Control::manager().receiveOutputAttribute(attribute, m.ArgumentStream()) ) - Control::manager().sendOutputStatus(remoteEndpoint); + } + // Session target: concerns attributes of the session + else if ( target.compare(OSC_SESSION) == 0 ) + { + if ( attribute.compare(OSC_SYNC) == 0 || Control::manager().receiveSessionAttribute(attribute, m.ArgumentStream()) ) { + // send the global status + Control::manager().sendOutputStatus(remoteEndpoint); + // send the status of all sources + Control::manager().sendSourcesStatus(remoteEndpoint, m.ArgumentStream()); + } + } // ALL sources target: apply attribute to all sources of the session else if ( target.compare(OSC_ALL) == 0 ) @@ -272,7 +281,7 @@ void Control::terminate() bool Control::receiveOutputAttribute(const std::string &attribute, osc::ReceivedMessageArgumentStream arguments) { - bool send_feedback = false; + bool need_feedback = false; try { /// e.g. '/vimix/output/enable' or '/vimix/output/enable 1.0' or '/vimix/output/enable 0.0' @@ -310,7 +319,7 @@ bool Control::receiveOutputAttribute(const std::string &attribute, if (!arguments.Eos()) arguments >> f >> osc::EndMessage; Mixer::manager().session()->setFadingTarget( Mixer::manager().session()->fading() + f * 0.001); - send_feedback = true; + need_feedback = true; } else if ( attribute.compare(OSC_OUTPUT_FADE_OUT) == 0) { float f = 0.f; @@ -318,7 +327,7 @@ bool Control::receiveOutputAttribute(const std::string &attribute, if (!arguments.Eos()) arguments >> f >> osc::EndMessage; Mixer::manager().session()->setFadingTarget( Mixer::manager().session()->fading() - f * 0.001); - send_feedback = true; + need_feedback = true; } #ifdef CONTROL_DEBUG else { @@ -337,7 +346,7 @@ bool Control::receiveOutputAttribute(const std::string &attribute, Log::Info(CONTROL_OSC_MSG "Invalid argument for attribute '%s' for target 'output'", attribute.c_str()); } - return send_feedback; + return need_feedback; } bool Control::receiveSourceAttribute(Source *target, const std::string &attribute, @@ -442,6 +451,46 @@ bool Control::receiveSourceAttribute(Source *target, const std::string &attribut } + +bool Control::receiveSessionAttribute(const std::string &attribute, + osc::ReceivedMessageArgumentStream arguments) +{ + bool need_feedback = false; + + try { + if ( attribute.compare(OSC_SESSION_VERSION) == 0) { + float v = 0.f; + arguments >> v >> osc::EndMessage; + size_t id = (int) ceil(v); + std::list snapshots = Action::manager().snapshots(); + if ( id < snapshots.size() ) { + for (size_t i = 0; i < id; ++i) + snapshots.pop_back(); + uint64_t snap = snapshots.back(); + Action::manager().restore(snap); + } + need_feedback = true; + } +#ifdef CONTROL_DEBUG + else { + Log::Info(CONTROL_OSC_MSG "Ignoring attribute '%s' for target 'output'", attribute.c_str()); + } +#endif + + } + catch (osc::MissingArgumentException &e) { + Log::Info(CONTROL_OSC_MSG "Missing argument for attribute '%s' for target 'output'", attribute.c_str()); + } + catch (osc::ExcessArgumentException &e) { + Log::Info(CONTROL_OSC_MSG "Too many arguments for attribute '%s' for target 'output'", attribute.c_str()); + } + catch (osc::WrongArgumentTypeException &e) { + Log::Info(CONTROL_OSC_MSG "Invalid argument for attribute '%s' for target 'output'", attribute.c_str()); + } + + return need_feedback; +} + void Control::sendCurrentSourceAttibutes(const IpEndpointName &remoteEndpoint) { // default values diff --git a/ControlManager.h b/ControlManager.h index 72454b3..738c541 100644 --- a/ControlManager.h +++ b/ControlManager.h @@ -18,7 +18,6 @@ #define OSC_ALL "/all" #define OSC_SELECTED "/selected" #define OSC_CURRENT "/current" -#define OSC_VERSION "/version" #define OSC_NEXT "/next" #define OSC_PREVIOUS "/previous" @@ -35,6 +34,8 @@ #define OSC_SOURCE_TURN "/turn" #define OSC_SOURCE_RESET "/reset" +#define OSC_SESSION "/session" +#define OSC_SESSION_VERSION "/version" class Session; class Source; @@ -76,6 +77,9 @@ protected: bool receiveSourceAttribute(Source *target, const std::string &attribute, osc::ReceivedMessageArgumentStream arguments); + bool receiveSessionAttribute(const std::string &attribute, + osc::ReceivedMessageArgumentStream arguments); + void sendCurrentSourceAttibutes(const IpEndpointName& remoteEndpoint); void sendSourcesStatus(const IpEndpointName& remoteEndpoint, osc::ReceivedMessageArgumentStream arguments); void sendOutputStatus(const IpEndpointName& remoteEndpoint); diff --git a/rsc/osc/vimix.mk1.touchosc b/rsc/osc/vimix.mk1.touchosc index ec0801a960922b347a1bd0f6071793c417d099b0..d1ec87f879531b248a4f523e5a2a113f284fa4c4 100644 GIT binary patch delta 2087 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 J$_D@d005gR-H-qP