#pragma once #include "sad_DetectedServer.hpp" #include "spit_message.hpp" #include "spit_object.hpp" #include "spit_player.hpp" #include "spit_repo.hpp" #include "spit_type.hpp" #include #include #include using namespace std; namespace spit { class SProcessor { public: // /** Maximal length of a SPITMessage*/ // static const int MAXSPITMESSAGEBYTECOUNT = 512; enum class ProjUpdate { ServerLoaded, StartTransfer, EndTransfer, ServerClosed, }; enum class ServerEvent { Detect, Lost, Changed, }; enum class ObjectEvent { Created, Changed, Deleted }; enum class Connection { None = 0, // No Connection established.
Either no connect tried or disconnected NoneServer = 1, // Server has disconnected Lost = 2, // The connection is lost
Either because of a network crash or because the server no longer responds. Ok = 3, // Connection to the serv er is established. TryConnection = 4, // A connection to the server is tried. }; struct Callbacks { function onServerEvent; function onConnectionStatus; function onProjectUpdate; function onSpitType; function onSpitObject; function onPlay; function onPlaySpitType; function onPlayRemoteObjectStatus; function onCheckSpitTypeVeto; function onCheckSpitObjectVeto; }; struct InternalCallbacks { function sendSpitTypeInternal; }; // //------ PlayerType ------ // public: // /** continous main player, time value can be used like a timecode.
The time value is the position in server's project.
A server should use only one main player.*/ // static constexpr char PLAYERTYPE_MAIN = 0x02; // /** continous player. This player plays SPIT objects sometime during the project.*/ // static constexpr char PLAYERTYPE_CONTINOUS = 0x01; // /** diescrete player. This player is used to transmit single discrete values.*/ // static constexpr char PLAYERTYPE_DISCRETE = 0x00; // //------ Value Flag ------ // //------ used by sendRemoteObject // public: // /**Set the given value directly*/ // static constexpr char VALUEFLAG_DIRECT = 0x00; // /**Increase the existing value by the given value.
This is usefull e.g. when instead of a fader a endless wheel is used*/ // static constexpr char VALUEFLAG_INCREASE = 0x01; // /**Decrease the existing value by the given value.
This is usefull e.g. when instead of a fader a endless wheel is used*/ // static constexpr char VALUEFLAG_DECREASE = 0x02; // static constexpr int MAX_OVERTAKING_SPIT_MESSAGES = 10; //----- SProcessor ----- public: SProcessor(string name, string projName, string hostName, string guid, Callbacks calls, InternalCallbacks intern); virtual ~SProcessor(); private: Callbacks mCallbacks; InternalCallbacks mInternCallbacks; // Connection mConnectionStatus{Connection::None}; // bool mDisconnectedByServer{}; // flag true = when server disconnects string mGuid; string mName; string mProjName; string mComputerName; // string mClientProjectName; // uint8_t mMessageNumberSend{1}; // int mMessageNumberReceived{-1}; // set to -1 because the first received message will set the number (1..255) // vector> mOvertakingMessages; // // Server's info filled by parseConnectAnswer // string mServerID{}; // string mServerName{}; // string mServerComputerName{}; // int mServerStepTime{-1}; // //--- Server Project --- // string mServerProjectID; // string mServerProjectName; // int mServerFramesPerSecond; // public: // /** The ID of the client.
Every client instance should set an unique id*/ // string getID() { return mGuid; } // /** The name of the client, should be set by the user app*/ // string getName() { return mName; } // //----- Computer Params ----- // /** The name of the client's host computer*/ // string getComputerName() { return mComputerName; } // void setClientProjectName(string clientProjectName) { mClientProjectName = clientProjectName; } // string getClientProjectName() { return mClientProjectName; } // // connected Server Infos // /** The ID of the connected SPITServer*/ // string getServerID() { return mServerID; } // /** The host computername of the connected SPITServer*/ // string getServerComputerName() { return mServerComputerName; } // /** The name of the connected SPITServer*/ // string getServerName() { return mServerName; } // /** Expected Refreah Rate of the connectd SPITServer.
// * When the server plays objects, it will do so at discrete time steps.
// * Play events will take place in these time steps.. // */ // int getServerStepTime() { return mServerStepTime; } // /** Should be called when the client wants to close his project*/ // void clientProjectClose(); // /** // * Should be called whenever the client has a project loaded // */ // void clientProjectLoaded(); // void setActionSPITType(string spitypeID, bool actionAssigned); // void setActionSPITObject(string objectID, bool actionAssigned); // //--------------- SPITMessage --------------- // private: // // Reconnect to the server when connection is lost see eventConnectionStatus and eventServerDetected // bool _doReconnect{}; // true = on eventServerDetected connect to the server identified by mServerID // public: // std::vector createMessage(Message::OPPart & spitMessageOPPart); // void checkParseMessageData(vector data); // //--------------- ServerAutoDetection SAD --------------- // public: // /** Starts the autodetection of SPITServers in the local network. If a connection is tried, the autodetection should be stopped before.*/ // void startServerAutoDetect(); // /** Stops the autodetection of SPITServers in the local network*/ // void stopServerAutoDetect(); // /** Called every time a new SPITServer is detetced in the local network */ // void eventServerDetected(SadDetectedServer &server); // /** Called every time a prior detected SPITServer is is no longer found.*/ // void eventServerLost(SadDetectedServer &server); // void eventServerChanged(SadDetectedServer &server); // //--------------- Connection --------------- // public: // /** // * Tries a connection to the SPITServer // * @param p_ServerIP ip address of the SPITServer // * @param p_ServerPort port of the SPITServer // * @param p_ClientIP IP of the client // * @param p_ClientPort if "0" any free port will be used // * @param p_LoginName maybe some SPITServer need a login - liveSHOWsoftware will not. // * @param p_LoginPassword maybe some SPITServer need a login - liveSHOWsoftware will not // * @return true = the connection try is ok, SPITServer will answer with COnnectAnswer and an eventConnectionStatus will occur.
// * false = something is going wrong. (client could not bind) // */ // bool connect(string serverIP, string serverPort, string clientIP, string clientPort, string loginName = "", string loginPassword = ""); // /** // * Terminates the connection to the SPITServer. // */ // void disconnect(); // private: // void disconnectInternal(Connection cause); // void resetMessageNumberReceived(); // void parseMessage(Message& message); // void addOvertakingMessage(unique_ptr message); // void parseConnectAnswer(Message::ConnectAnswer &message); // void parseDisconnect(Message::Disconnect &message); // void parseWatchdog(Message::Watchdog &message); // void parseWatchdogAnswer(Message::WatchdogAnswer &message); // public: // /** Used internally*/ // void sendWatchdog(); // /** Used internally. When the connection to the SPITServer is lost an eventConnectionStatus will occur*/ // void eventWatchdogLost(); // //--------------- SPIT Project --------------- // private: // void parseReportProject(Message::ReportProject &message); // void parseCloseProject(Message::CloseProject &message); // public: // /** Returns the SPITServer's project ID - may be the same as the project's name*/ // string getServerProjectID(); // /** Returns the SPITServer's project name*/ // string getServerProjectName(); // /** Returns frame rate per second. This is the time resolution in which the server transmits time data. The unit of time data is always frames.*/ // int getServerFramesPerSecond(); // private: // void parseRequestProjectTransfer(Message::RequestProjectTransfer &message); // void parseStartProjectTransfer(Message::StartProjectTransfer &message); // void parseEndProjectTransfer(Message::EndProjectTransfer &message); // public: // // static void sendProject(SClient *p_PtrSProcessor); // // --------------- SPIT Types --------------- // public: // /** // * Creates a fixed SPITType for application actions that are always present and project independent.
// * Fixed SPIT types cannot be changed or deleted by the server.
// * These SPITTypes will be automatically added to the SPITType-List and sended to the server. // * @param p_ID an unique of the SPITType, these are always the same per client approach. Different client approaches should use different ids. // * @param p_GroupName a name which groups the actions/SPITTypes // * @param p_Name the name of the Action/SPITType // * @param p_DefaultDelay maybe there is an default delay until the action starts, this is only used for graphical representations, 0 is allowd // * @param p_DefaultDuration maybe the action has a default duration, this is only used for graphical representations, 0 is allowd // * @return the pointer to the new SPITType. // */ // SType *createTypeFixed(string iD, string groupName, string name, uint64_t defaultDelay, uint64_t defaultDuration); // /** // * Creates a SPITType for application actions.
// * These SPITTypes will be automatically added to the SPITType-List and sended to the server. // * @param p_ID an unique of the SPITType, these are always the same per client approach. Different client approaches should use different ids. // * @param p_GroupName a name which groups the actions/SPITTypes // * @param p_Name the name of the Action/SPITType // * @param p_DefaultDelay maybe there is an default delay until the action starts, this is only used for graphical representations, 0 is allowd // * @param p_DefaultDuration maybe the action has a default duration, this is only used for graphical representations, 0 is allowd // * @param p_Fixed true = the server is not allowed to change this SPITType, false = the server may change or delete this SPITType // * @param p_ProjectIndepended true = the SPITType belongs to a specific project, false = the SpitType always exists for every project // * @return the pointer to the new SPITType. // */ // SType *createType(string iD, string groupName, string name, uint64_t defaultDelay, uint64_t defaultDuration, bool fixed, bool projectIndepended); private: public: // @todo delete void parseReportType(Message::ReportType &message); // void parseRemoveSPITType(Message::RemoveType &message); // int sendSPITTypeInternal(SType &sType); // public: // /** // * If a client wants to change a SPITType, he should send it to the server.
// * If the SPITTye is a fixed one and not created by the client himself, then an eventSPITType can be sent from the server, which cancels the change.
// * @param spitypeID the id of the SPITType to remove. // * @return 0 = is sended, -1 = is not sended // */ // bool changeSPITType(SType *spitType); // /** // * If a client wants to remove a SPITType, he should send it to the server.
// * If the SPITTye is a fixed one and not created by the client himself, then an eventSPITType can be sent from the server, which cancels the deletion.
// * @param spitypeID the id of the SPITType to remove. // * @return 0 = is sended, -1 = is not sended // */ // int removeSPITType(string spitypeID); // public: // //--------------- SPIT Objects --------------- // private: // void parseReportSPITObject(Message::ReportObject &message); // void parseRemoveSPITObject(Message::RemoveObject &message); // int sendSPITObjectInternal(SObject *ptrObject); // public: // /** // * When the client changes a SPITObject (normally the client should not do this), then it should send the changes to the SPITServer.
// * The SPITServer may discard the changes and an eventSPITObject occurs.
// * @param spitObject the pointer to the changed SPITObject. // * @return 0 = sended, -1 = not sended // */ // bool changeSPITObject(SObject *spitObject); // /** // * When the client removes a SPITObject (normally the client should not do this), then he should send it to the SPITServer.
// * The SPITServer may discard the deletion and an eventSPITObject occurs.
// * @param objectID the id of the SPITObject to remove. // * @return 0 = sended, -1 = not sended // */ // int removeSPITObject(string objectID); // public: // //--------------- Play SPIT Objects --------------- // private: // void parsePlaySPITStart(Message::PlayStart &message); // void parsePlaySPITObject(Message::PlayObject &message); // void parsePlaySPITEnd(Message::PlayEnd &message); // void parseReportPlayStatus(Message::ReportPlayStatus &message); // public: // //--------- Remote ---------- // void sendRemoteObject(string objectID, int valuePpm = 0, char valueFlag = 0x00); // private: // bool mAbortSearch{}; // bool sAnswered{}; // void answerWatchdog() { // sAnswered = true; // } // SpitRepo mSpitObjects; // SpitRepo mRemoteSpitObjects; public: // @todo remove SpitRepo mSpitTypes; SpitRepo mRemoteSpitTypes; }; } // namespace spit