File indexing completed on 2024-12-22 05:29:17

0001 /*
0002  * Copyright 2019 Eike Hein <hein@kde.org>
0003  *
0004  * This library is free software; you can redistribute it and/or
0005  * modify it under the terms of the GNU Lesser General Public
0006  * License as published by the Free Software Foundation; either
0007  * version 2.1 of the License, or (at your option) version 3, or any
0008  * later version accepted by the membership of KDE e.V. (or its
0009  * successor approved by the membership of KDE e.V.), which shall
0010  * act as a proxy defined in Section 6 of version 3 of the license.
0011  *
0012  * This library is distributed in the hope that it will be useful,
0013  * but WITHOUT ANY WARRANTY; without even the implied warranty of
0014  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
0015  * Lesser General Public License for more details.
0016  *
0017  * You should have received a copy of the GNU Lesser General Public
0018  * License along with this library.  If not, see <http://www.gnu.org/licenses/>.
0019  */
0020 
0021 #pragma once
0022 
0023 #include <memory>
0024 
0025 #include <QObject>
0026 
0027 #include "parrotprotocol.h"
0028 #include "parrotvehicle.h"
0029 
0030 #include <QHostAddress>
0031 #include <QJsonObject>
0032 #include <QPointer>
0033 #include <QQueue>
0034 #include <QTcpSocket>
0035 #include <QTimer>
0036 #include <QUdpSocket>
0037 
0038 class ParrotConnection : public QObject
0039 {
0040     Q_OBJECT
0041 
0042 public:
0043     explicit ParrotConnection(ParrotVehicle::Type type, const QString &vehicleName, const QString &hostName, int port, QObject *parent = nullptr);
0044     ~ParrotConnection();
0045 
0046 public Q_SLOTS:
0047     void handshake(const QString &productSerial = QString());
0048     void reset();
0049     void sendCommand(Parrot::Command command, const QVariantList &arguments, bool retryForever = false);
0050     void pilot(qint8 roll, qint8 pitch, qint8 yaw, qint8 gaz);
0051 
0052 Q_SIGNALS:
0053     void stateChanged(Kirogi::AbstractVehicle::ConnectionState state) const;
0054     void commandReceived(const ParrotCommand &command) const;
0055 
0056 private Q_SLOTS:
0057     void receiveData();
0058     void pumpC2dAckQueue();
0059     void sendPilotingCommand();
0060 
0061 private:
0062     void initSockets();
0063 
0064     void processIncomingFrame(const ParrotFrame &frame);
0065 
0066     void sendAck(const ParrotFrame &frame);
0067     void sendFrame(const ParrotFrame &frame);
0068     void sendData(const QByteArray &data, quint32 size);
0069 
0070     quint8 makeSeq(quint8 bufferId);
0071 
0072     ParrotVehicle::Type m_type;
0073     QString m_vehicleName;
0074 
0075     QHostAddress m_hostAddress;
0076     int m_port;
0077 
0078     QPointer<QTcpSocket> m_handshakeSocket;
0079     QJsonObject m_handshakeResponse;
0080 
0081     // c2d = Controller-to-device, i.e. we send here.
0082     int m_c2dport;
0083     // d2c = Device-to-Controller, i.e. we listen here.
0084     int m_d2cPort;
0085 
0086     QPointer<QUdpSocket> m_d2cSocket;
0087     QPointer<QUdpSocket> m_c2dSocket;
0088 
0089     QHash<quint8, quint8> m_seq;
0090 
0091     QQueue<ParrotFrame> m_c2dAckQueue;
0092     std::unique_ptr<QTimer> m_c2dAckTimer;
0093 
0094     std::unique_ptr<QTimer> m_pilotingTimer;
0095     qint8 m_roll;
0096     qint8 m_pitch;
0097     qint8 m_yaw;
0098     qint8 m_gaz;
0099 };