/** * @file Xpl2Client.h * @brief TCP client for the Alchemie XPL2 printhead protocol. */ #pragma once #include "Xpl2Protocol.h" #include #include #include #include #include class Xpl2Client : public QObject { Q_OBJECT QML_ELEMENT QML_SINGLETON Q_PROPERTY (QString host READ host WRITE setHost NOTIFY hostChanged) Q_PROPERTY (bool connected READ isConnected NOTIFY connectedChanged) Q_PROPERTY (int controllerId READ controllerId NOTIFY jcVersionReceived) Q_PROPERTY ( QString firmwareVersion READ firmwareVersion NOTIFY jcVersionReceived) Q_PROPERTY ( QString hardwareVersion READ hardwareVersion NOTIFY jcVersionReceived) Q_PROPERTY (int printheadCount READ printheadCount NOTIFY jcVersionReceived) public: explicit Xpl2Client (QObject *parent = nullptr); QString host () const; void setHost (const QString &host); bool isConnected () const; int controllerId () const; QString firmwareVersion () const; QString hardwareVersion () const; int printheadCount () const; static void enableWireDebug (); Q_INVOKABLE void connectToServer (); Q_INVOKABLE void disconnectFromServer (); /** Get the just connected Jetting Controller ID and Software Version. */ Q_INVOKABLE void getJcVersion (); /** Query the specified printhead's version info. */ Q_INVOKABLE void getPhVersion (int printheadId); /* -- CN_ Control commands ----------------------------------------- */ /** Switch jetting on for all printheads. */ Q_INVOKABLE void jettingAllOn (); /** Switch jetting on for all printheads with a per-nozzle mask (180 chars). */ Q_INVOKABLE void jettingOn (const QString &jettingMask); /** Switch jetting off for all printheads. */ Q_INVOKABLE void jettingOff (); /** Switch jetting on for one printhead with a per-nozzle mask (12 chars). */ Q_INVOKABLE void phJettingOn (int printheadId, const QString &jettingMask); /** Switch jetting off for one printhead. */ Q_INVOKABLE void phJettingOff (int printheadId); /** Switch the JC identification LED on. */ Q_INVOKABLE void jcIdLedOn (); /** Switch the JC identification LED off. */ Q_INVOKABLE void jcIdLedOff (); /** Switch a printhead's identification LED on. */ Q_INVOKABLE void phIdLedOn (int printheadId); /** Switch a printhead's identification LED off. */ Q_INVOKABLE void phIdLedOff (int printheadId); /** Run calibration on all printheads. */ Q_INVOKABLE void jcCalibration (); /** Run calibration on one printhead. */ Q_INVOKABLE void phCalibration (int printheadId); /** Get nozzle calibration data for one printhead (48 floats). */ Q_INVOKABLE void phCalibrationData (int printheadId); /** Get raw nozzle calibration data for one printhead (48 floats). */ Q_INVOKABLE void phCalibrationRawData (int printheadId); /** Get the calibrated base frequency and active base frequency. */ Q_INVOKABLE void phCalibratedBaseFrequency (int printheadId); /** Start sending JC status messages at the given level and interval. */ Q_INVOKABLE void jcStatusMessagingStart (int statusLevel, int sendIntervalMs); /** Stop sending JC status messages. */ Q_INVOKABLE void jcStatusMessagingStop (); /** Start sending PH status messages at the given level and interval. */ Q_INVOKABLE void phStatusMessagingStart (int statusLevel, int sendIntervalMs); /** Stop sending PH status messages. */ Q_INVOKABLE void phStatusMessagingStop (); /** Reset fault codes for all printheads on the controller. */ Q_INVOKABLE void jcResetFaultCodes (); /** Reset fault codes for one printhead. */ Q_INVOKABLE void phResetFaultCodes (int printheadId); /** Disable nozzles on one printhead using a 12-char mask. */ Q_INVOKABLE void phNozzlesDisabled (int printheadId, const QString &mask); /* -- CF_ Configuration commands ----------------------------------- */ /** Set the printhead ID. */ Q_INVOKABLE void phSetId (int printheadId); /** De-assign the printhead ID. */ Q_INVOKABLE void phDeassignId (); /** Set jetting parameters for all printheads on the controller. */ Q_INVOKABLE void jcSetJettingParams (int dutyCycle, int pwmFreq, int drive, int nozzleDriveFreq, int nozzleDriveDutyCycle); /** Set jetting parameters for one printhead. */ Q_INVOKABLE void phSetJettingParams (int printheadId, int dutyCycle, int pwmFreq, int drive, int nozzleDriveFreq, int nozzleDriveDutyCycle); /** Get jetting parameters from one printhead. */ Q_INVOKABLE void phGetJettingParams (int printheadId); /** Save calibration for all printheads. */ Q_INVOKABLE void jcSaveCalibration (); /** Save calibration for one printhead. */ Q_INVOKABLE void phSaveCalibration (int printheadId); /** Reset calibration for all printheads. */ Q_INVOKABLE void jcResetCalibration (); /** Reset calibration for one printhead. */ Q_INVOKABLE void phResetCalibration (int printheadId); /** Set purge settings for all printheads on the controller. */ Q_INVOKABLE void jcSetPurgeSettings (int purgeIntervalMs, int purgeTimeMs); /** Switch off purge for all printheads on the controller. */ Q_INVOKABLE void jcSwitchOffPurge (); /** Set a JC setting by setter ID. */ Q_INVOKABLE void jcSetter (bool saveNewValue, int setterId, const QString &newValue); /** Set a PH setting by setter ID. */ Q_INVOKABLE void phSetter (int printheadId, bool saveNewValue, int setterId, const QString &newValue); /** Get a JC setting by getter ID. */ Q_INVOKABLE void jcGetter (bool getSavedValue, int getterId); /** Get a PH setting by getter ID. */ Q_INVOKABLE void phGetter (int printheadId, bool getSavedValue, int getterId); /** Reset settings for all printheads on the controller. */ Q_INVOKABLE void jcResetSettingsAllPrintheads (); /** Reset all settings for one printhead. */ Q_INVOKABLE void phResetAllSettings (int printheadId); /** Reboot all printheads on the controller. */ Q_INVOKABLE void jcRebootAllPrintheads (); /** Reboot one printhead. */ Q_INVOKABLE void phReboot (int printheadId); /** Reset the Jetting Controller software. */ Q_INVOKABLE void jcResetControllerSoftware (); /** Restart the Jetting Controller. */ Q_INVOKABLE void jcRestart (); /** Shut down the Jetting Controller. */ Q_INVOKABLE void jcShutdown (); /** Save settings for all printheads on the controller. */ Q_INVOKABLE void jcSaveAllPrintheadSettings (); /** Save settings for one printhead. */ Q_INVOKABLE void phSaveSettings (int printheadId); signals: void hostChanged (); void connectedChanged (); void errorOccurred (const QString &error); void statusMessage (const QString &message); void jcVersionReceived (); void phVersionReceived (int controllerId, int printheadId, const QString &mcuFirmwareVersion, const QString &mcuHardwareVersion, const QString &mcuFirmwareVariant, const QString &fpgaFirmwareVersion, const QString &fpgaHardwareVersion, const QString &bootloaderVersion); /* CN_ response signals */ void jettingAllOnResult (int controllerId, bool success); void jettingOnResult (int controllerId, bool success); void jettingOffResult (int controllerId, bool success); void phJettingOnResult (int controllerId, int printheadId, bool success); void phJettingOffResult (int controllerId, int printheadId, bool success); void jcIdLedOnResult (int controllerId, bool success); void jcIdLedOffResult (int controllerId, bool success); void phIdLedOnResult (int controllerId, int printheadId, bool success); void phIdLedOffResult (int controllerId, int printheadId, bool success); void jcCalibrationResult (int controllerId, bool success); void phCalibrationResult (int controllerId, int printheadId, bool success); void phCalibrationDataReceived (int controllerId, int printheadId, const QVariantList &frequencies); void phCalibrationRawDataReceived (int controllerId, int printheadId, const QVariantList &frequencies); void phCalibratedBaseFrequencyReceived (int controllerId, int printheadId, double baseFrequency, double activeBaseFrequency); void jcStatusMessagingStartResult (int controllerId, int statusLevel, int sendIntervalMs, bool success); void jcStatusMessagingStopResult (int controllerId, bool success); void phStatusMessagingStartResult (int controllerId, int statusLevel, int sendIntervalMs, bool success); void phStatusMessagingStopResult (int controllerId, bool success); void jcResetFaultCodesResult (int controllerId, bool success); void phResetFaultCodesResult (int controllerId, int printheadId, bool success); void phNozzlesDisabledResult (int controllerId, int printheadId, bool success); /* CF_ response signals */ void phSetIdResult (int controllerId, int printheadId, bool success); void phDeassignIdResult (int controllerId, bool success); void jcSetJettingParamsResult (int controllerId, int dutyCycle, int pwmFreq, int drive, int nozzleDriveFreq, int nozzleDriveDutyCycle, Xpl2Protocol::JettingParamsResult result); void phSetJettingParamsResult (int controllerId, int printheadId, int dutyCycle, int pwmFreq, int drive, int nozzleDriveFreq, int nozzleDriveDutyCycle, Xpl2Protocol::JettingParamsResult result); void phGetJettingParamsResult (int controllerId, int printheadId, int dutyCycle, int pwmFreq, int drive, int nozzleDriveFreq, int nozzleDriveDutyCycle, Xpl2Protocol::JettingParamsResult result); void jcSaveCalibrationResult (int controllerId, bool success); void phSaveCalibrationResult (int controllerId, int printheadId, bool success); void jcResetCalibrationResult (int controllerId, bool success); void phResetCalibrationResult (int controllerId, int printheadId, bool success); void jcSetPurgeSettingsResult (int controllerId, int purgeIntervalMs, int purgeTimeMs, bool success); void jcSwitchOffPurgeResult (int controllerId, bool success); void jcSetterResult (int controllerId, bool saveNewValue, int setterId, const QString &newValue, Xpl2Protocol::SetterResult result); void phSetterResult (int controllerId, int printheadId, bool saveNewValue, int setterId, const QString &newValue, Xpl2Protocol::SetterResult result); void jcGetterResult (int controllerId, bool savedValue, int getterId, const QString ¤tValue, bool success); void phGetterResult (int controllerId, int printheadId, bool savedValue, int getterId, const QString ¤tValue, bool success); void jcResetSettingsAllPrintheadsResult (int controllerId, bool success); void phResetAllSettingsResult (int controllerId, int printheadId, bool success); void jcRebootAllPrintheadsResult (int controllerId, bool success); void phRebootResult (int controllerId, int printheadId, bool success); void jcResetControllerSoftwareResult (int controllerId, bool success); void jcRestartResult (int controllerId, bool success); void jcShutdownResult (int controllerId, bool success); void jcSaveAllPrintheadSettingsResult (int controllerId, bool success); void phSaveSettingsResult (int controllerId, int printheadId, bool success); private slots: void onSocketConnected (); void onSocketDisconnected (); void onSocketMessageReady (); void onSocketError (QAbstractSocket::SocketError error); private: void sendCommand (QTcpSocket &socket, const QByteArray &command, const QVariantList ¶ms = {}); void dispatchCommandMessage (const Xpl2Protocol::ParsedMessage &msg); void dispatchImagingMessage (const Xpl2Protocol::ParsedMessage &msg); void dispatchStatusMessage (const Xpl2Protocol::ParsedMessage &msg); void handleKaPing (QTcpSocket &socket); void handleGsJcVersion (const QVariantList ¶ms); void handleGsPhVersion (const QVariantList ¶ms); enum class ResponseShape { JcSuccess, PhSuccess, CalData, BaseFreq, StatusStart, PurgeSettings, JcJettingParams, PhJettingParams, JcSetter, PhSetter, JcGetter, PhGetter }; struct ResponseEntry { ResponseShape shape; int minParams; std::function emitter; }; static const QHash s_responseTable; bool dispatchResponse (const QByteArray &command, const QVariantList ¶ms, const QTcpSocket *socket); void updateConnectedState (); QString logTag (const QTcpSocket *socket) const; QTcpSocket m_commandSocket; QTcpSocket m_imagingSocket; QTcpSocket m_statusSocket; QString m_host = QStringLiteral ("127.0.0.1"); quint16 m_commandPort = 9110; quint16 m_imagingPort = 9111; quint16 m_statusPort = 9112; bool m_connected = false; static bool s_wireDebug; int m_controllerId = 0; QString m_firmwareVersion; QString m_hardwareVersion; int m_printheadCount = 0; };