minor fixes

This commit is contained in:
Michael Zanetti 2022-05-08 14:45:16 +02:00
parent 767baba7e4
commit 8eeeeb12f6
4 changed files with 109 additions and 38 deletions

View File

@ -44,6 +44,7 @@
#include <QColor> #include <QColor>
#include <QTimer> #include <QTimer>
#include <QDataStream> #include <QDataStream>
#include <QJsonDocument>
IntegrationPluginOwlet::IntegrationPluginOwlet() IntegrationPluginOwlet::IntegrationPluginOwlet()
{ {
@ -852,7 +853,55 @@ void IntegrationPluginOwlet::setupThing(ThingSetupInfo *info)
params.insert("ledCount", thing->paramValue(ws2812ThingLedCountParamTypeId).toUInt()); params.insert("ledCount", thing->paramValue(ws2812ThingLedCountParamTypeId).toUInt());
params.insert("ledMode", "WS2812Mode" + thing->paramValue(ws2812ThingLedModeParamTypeId).toString()); params.insert("ledMode", "WS2812Mode" + thing->paramValue(ws2812ThingLedModeParamTypeId).toString());
params.insert("ledClock", "WS2812Clock" + thing->paramValue(ws2812ThingLedClockParamTypeId).toString()); params.insert("ledClock", "WS2812Clock" + thing->paramValue(ws2812ThingLedClockParamTypeId).toString());
client->sendCommand("GPIO.ConfigurePin", params); int id = client->sendCommand("GPIO.ConfigurePin", params);
connect(client, &OwletClient::replyReceived, thing, [id, client, thing](int commandId, const QVariantMap &/*params*/){
if (id != commandId)
return;
qCDebug(dcOwlet()) << "Configuration sent...";
QVariantMap params;
params.insert("id", thing->paramValue(ws2812ThingPinParamTypeId).toUInt());
params.insert("power", thing->stateValue(ws2812PowerStateTypeId).toBool());
params.insert("brightness", thing->stateValue(ws2812BrightnessStateTypeId).toInt());
QColor color = thing->stateValue(ws2812ColorStateTypeId).value<QColor>();
params.insert("color", (color.rgb() & 0xFFFFFF));
int effect = thing->stateValue(ws2812EffectStateTypeId).toInt();
params.insert("effect", effect);
qCDebug(dcOwlet()) << "Initializing" << QJsonDocument::fromVariant(params).toJson();
client->sendCommand("GPIO.ControlPin", params);
connect(client, &OwletClient::notificationReceived, thing, [=](const QString &name, const QVariantMap &params){
qCDebug(dcOwlet()) << "***Notif" << name << params;
if (thing->thingClassId() == digitalInputThingClassId) {
if (params.value("id").toInt() == thing->paramValue(digitalInputThingPinParamTypeId)) {
thing->setStateValue(digitalInputPowerStateTypeId, params.value("power").toBool());
}
}
if (thing->thingClassId() == digitalOutputThingClassId) {
if (params.value("id").toInt() == thing->paramValue(digitalOutputThingPinParamTypeId)) {
thing->setStateValue(digitalOutputPowerStateTypeId, params.value("power").toBool());
}
}
if (thing->thingClassId() == ws2812ThingClassId) {
if (name == "GPIO.PinChanged") {
if (params.contains("power")) {
thing->setStateValue(ws2812PowerStateTypeId, params.value("power").toBool());
}
if (params.contains("brightness")) {
thing->setStateValue(ws2812BrightnessStateTypeId, params.value("brightness").toInt());
}
if (params.contains("color")) {
thing->setStateValue(ws2812ColorStateTypeId, params.value("color").value<QColor>());
}
if (params.contains("effect")) {
thing->setStateValue(ws2812EffectStateTypeId, params.value("effect").toInt());
}
}
}
});
});
} }
@ -870,36 +919,6 @@ void IntegrationPluginOwlet::setupThing(ThingSetupInfo *info)
thing->setStateValue("connected", false); thing->setStateValue("connected", false);
}); });
connect(client, &OwletClient::notificationReceived, this, [=](const QString &name, const QVariantMap &params){
qCDebug(dcOwlet()) << "***Notif" << name << params;
if (thing->thingClassId() == digitalInputThingClassId) {
if (params.value("id").toInt() == thing->paramValue(digitalInputThingPinParamTypeId)) {
thing->setStateValue(digitalInputPowerStateTypeId, params.value("power").toBool());
}
}
if (thing->thingClassId() == digitalOutputThingClassId) {
if (params.value("id").toInt() == thing->paramValue(digitalOutputThingPinParamTypeId)) {
thing->setStateValue(digitalOutputPowerStateTypeId, params.value("power").toBool());
}
}
if (thing->thingClassId() == ws2812ThingClassId) {
if (name == "GPIO.PinChanged") {
if (params.contains("power")) {
thing->setStateValue(ws2812PowerStateTypeId, params.value("power").toBool());
}
if (params.contains("brightness")) {
thing->setStateValue(ws2812BrightnessStateTypeId, params.value("brightness").toInt());
}
if (params.contains("color")) {
thing->setStateValue(ws2812ColorStateTypeId, params.value("color").value<QColor>());
}
if (params.contains("effect")) {
thing->setStateValue(ws2812EffectStateTypeId, params.value("effect").toInt());
}
}
}
});
client->transport()->connectTransport(); client->transport()->connectTransport();
} }

View File

@ -55,6 +55,9 @@ public:
void executeAction(ThingActionInfo *info) override; void executeAction(ThingActionInfo *info) override;
void thingRemoved(Thing *thing) override; void thingRemoved(Thing *thing) override;
private:
void processActionQueue(Thing *thing);
private: private:
ZeroConfServiceBrowser *m_zeroConfBrowser = nullptr; ZeroConfServiceBrowser *m_zeroConfBrowser = nullptr;
@ -76,6 +79,9 @@ private:
void setupArduinoChildThing(OwletSerialClient *client, quint8 pinId, OwletSerialClient::PinMode pinMode); void setupArduinoChildThing(OwletSerialClient *client, quint8 pinId, OwletSerialClient::PinMode pinMode);
void configurePin(OwletSerialClient *client, quint8 pinId, OwletSerialClient::PinMode pinMode); void configurePin(OwletSerialClient *client, quint8 pinId, OwletSerialClient::PinMode pinMode);
QString getPinName(Thing *parent, quint8 pinId); QString getPinName(Thing *parent, quint8 pinId);
QHash<Thing*, QList<ThingActionInfo*>> m_actionQueue;
QHash<Thing*, ThingActionInfo*> m_pendingActions;
}; };
#endif // INTEGRATIONPLUGINOWLET_H #endif // INTEGRATIONPLUGINOWLET_H

View File

@ -11,6 +11,17 @@ OwletClient::OwletClient(OwletTransport *transport, QObject *parent) :
{ {
transport->setParent(this); transport->setParent(this);
m_commandTimeoutTimer.setInterval(5000);
connect(&m_commandTimeoutTimer, &QTimer::timeout, this, [=](){
if (m_pendingCommandId != -1) {
QVariantMap params;
params.insert("error", "TimeoutError");
emit replyReceived(m_pendingCommandId, params);
m_pendingCommandId = -1;
sendNextRequest();
}
});
connect(m_transport, &OwletTransport::dataReceived, this, &OwletClient::dataReceived); connect(m_transport, &OwletTransport::dataReceived, this, &OwletClient::dataReceived);
connect(m_transport, &OwletTransport::error, this, &OwletClient::error); connect(m_transport, &OwletTransport::error, this, &OwletClient::error);
connect(m_transport, &OwletTransport::connectedChanged, this, [=](bool isConnected){ connect(m_transport, &OwletTransport::connectedChanged, this, [=](bool isConnected){
@ -39,13 +50,18 @@ int OwletClient::sendCommand(const QString &method, const QVariantMap &params)
return -1; return -1;
} }
int id = ++m_commandId; quint16 id = ++m_commandId;
QVariantMap packet; QVariantMap packet;
packet.insert("id", id); packet.insert("id", id);
packet.insert("method", method); packet.insert("method", method);
packet.insert("params", params); packet.insert("params", params);
m_transport->sendData(QJsonDocument::fromVariant(packet).toJson(QJsonDocument::Compact)); qCDebug(dcOwlet) << "Sending command" << qUtf8Printable(QJsonDocument::fromVariant(packet).toJson());
Command cmd;
cmd.id = id;
cmd.payload = packet;
m_commandQueue.append(cmd);
sendNextRequest();
return id; return id;
} }
@ -60,10 +76,9 @@ void OwletClient::dataReceived(const QByteArray &data)
QJsonParseError error; QJsonParseError error;
QJsonDocument jsonDoc = QJsonDocument::fromJson(m_receiveBuffer.left(splitIndex), &error); QJsonDocument jsonDoc = QJsonDocument::fromJson(m_receiveBuffer.left(splitIndex), &error);
if (error.error != QJsonParseError::NoError) { if (error.error != QJsonParseError::NoError) {
// qWarning() << "Could not parse json data from nymea" << m_receiveBuffer.left(splitIndex) << error.errorString(); qCWarning(dcOwlet) << "Could not parse json data from nymea" << m_receiveBuffer.left(splitIndex) << error.errorString();
return; return;
} }
// qDebug() << "received response" << qUtf8Printable(jsonDoc.toJson(QJsonDocument::Indented));
m_receiveBuffer = m_receiveBuffer.right(m_receiveBuffer.length() - splitIndex - 1); m_receiveBuffer = m_receiveBuffer.right(m_receiveBuffer.length() - splitIndex - 1);
if (!m_receiveBuffer.isEmpty()) { if (!m_receiveBuffer.isEmpty()) {
staticMetaObject.invokeMethod(this, "dataReceived", Qt::QueuedConnection, Q_ARG(QByteArray, QByteArray())); staticMetaObject.invokeMethod(this, "dataReceived", Qt::QueuedConnection, Q_ARG(QByteArray, QByteArray()));
@ -72,11 +87,31 @@ void OwletClient::dataReceived(const QByteArray &data)
QVariantMap packet = jsonDoc.toVariant().toMap(); QVariantMap packet = jsonDoc.toVariant().toMap();
if (packet.contains("notification")) { if (packet.contains("notification")) {
qCDebug(dcOwlet()) << "Notification received:" << packet; qCDebug(dcOwlet()) << "Notification received:" << qUtf8Printable(QJsonDocument::fromVariant(packet).toJson());
emit notificationReceived(packet.value("notification").toString(), packet.value("params").toMap()); emit notificationReceived(packet.value("notification").toString(), packet.value("params").toMap());
} else if (packet.contains("id")) { } else if (packet.contains("id")) {
qCDebug(dcOwlet()) << "reply received:" << packet; qCDebug(dcOwlet()) << "Reply received:" << qUtf8Printable(QJsonDocument::fromVariant(packet).toJson());
int id = packet.value("id").toInt(); int id = packet.value("id").toInt();
if (id == m_pendingCommandId) {
m_pendingCommandId = -1;
sendNextRequest();
}
emit replyReceived(id, packet.value("params").toMap()); emit replyReceived(id, packet.value("params").toMap());
} else {
qCWarning(dcOwlet) << "Unhandled data from owlet" << qUtf8Printable(jsonDoc.toJson(QJsonDocument::Indented));
} }
} }
void OwletClient::sendNextRequest()
{
if (m_commandQueue.isEmpty()) {
return;
}
if (m_pendingCommandId != -1) {
return;
}
Command cmd = m_commandQueue.takeFirst();
m_pendingCommandId = cmd.id;
m_transport->sendData(QJsonDocument::fromVariant(cmd.payload).toJson(QJsonDocument::Compact));
m_commandTimeoutTimer.start();
}

View File

@ -4,6 +4,7 @@
#include <QObject> #include <QObject>
#include <QHostAddress> #include <QHostAddress>
#include <QTcpSocket> #include <QTcpSocket>
#include <QTimer>
class OwletTransport; class OwletTransport;
@ -30,12 +31,22 @@ signals:
private slots: private slots:
void dataReceived(const QByteArray &data); void dataReceived(const QByteArray &data);
void sendNextRequest();
private: private:
struct Command {
int id;
QVariantMap payload;
};
OwletTransport *m_transport = nullptr; OwletTransport *m_transport = nullptr;
int m_commandId = 0; quint16 m_commandId = 0;
QByteArray m_receiveBuffer; QByteArray m_receiveBuffer;
QList<Command> m_commandQueue;
qint32 m_pendingCommandId = -1;
QTimer m_commandTimeoutTimer;
}; };
#endif // OWLETCLIENT_H #endif // OWLETCLIENT_H