File indexing completed on 2024-05-05 09:12:57
0001 /* 0002 SPDX-FileCopyrightText: 2007-2013 Urs Wolfer <uwolfer@kde.org> 0003 0004 SPDX-License-Identifier: GPL-2.0-or-later 0005 */ 0006 0007 #ifndef VNCCLIENTTHREAD_H 0008 #define VNCCLIENTTHREAD_H 0009 0010 #ifdef QTONLY 0011 #define i18n tr 0012 #else 0013 #include <KLocalizedString> 0014 #endif 0015 0016 #include "remoteview.h" 0017 0018 #include <QQueue> 0019 #include <QThread> 0020 #include <QImage> 0021 #include <QMutex> 0022 0023 extern "C" { 0024 #include <rfb/rfbclient.h> 0025 } 0026 0027 class ClientEvent 0028 { 0029 public: 0030 virtual ~ClientEvent(); 0031 0032 virtual void fire(rfbClient*) = 0; 0033 }; 0034 0035 class ReconfigureEvent: public ClientEvent 0036 { 0037 public: 0038 void fire(rfbClient*) override; 0039 }; 0040 0041 class KeyClientEvent : public ClientEvent 0042 { 0043 public: 0044 KeyClientEvent(int key, int pressed) 0045 : m_key(key), m_pressed(pressed) {} 0046 0047 void fire(rfbClient*) override; 0048 0049 private: 0050 int m_key; 0051 int m_pressed; 0052 }; 0053 0054 class PointerClientEvent : public ClientEvent 0055 { 0056 public: 0057 PointerClientEvent(int x, int y, int buttonMask) 0058 : m_x(x), m_y(y), m_buttonMask(buttonMask) {} 0059 0060 void fire(rfbClient*) override; 0061 0062 private: 0063 int m_x; 0064 int m_y; 0065 int m_buttonMask; 0066 }; 0067 0068 class ClientCutEvent : public ClientEvent 0069 { 0070 public: 0071 explicit ClientCutEvent(const QString &text) 0072 : text(text) {} 0073 0074 void fire(rfbClient*) override; 0075 0076 private: 0077 QString text; 0078 }; 0079 0080 class VncClientThread: public QThread 0081 { 0082 Q_OBJECT 0083 0084 public: 0085 enum ColorDepth { 0086 bpp32, 0087 bpp16, 0088 bpp8 0089 }; 0090 Q_ENUM(ColorDepth) 0091 0092 explicit VncClientThread(QObject *parent = nullptr); 0093 ~VncClientThread() override; 0094 const QImage image(int x = 0, int y = 0, int w = 0, int h = 0); 0095 void setImage(const QImage &img); 0096 void emitUpdated(int x, int y, int w, int h); 0097 void emitGotCut(const QString &text); 0098 void stop(); 0099 void setHost(const QString &host); 0100 void setPort(int port); 0101 void setQuality(RemoteView::Quality quality); 0102 void setDevicePixelRatio(qreal dpr); 0103 void setPassword(const QString &password) { 0104 m_password = password; 0105 } 0106 void setShowLocalCursor(bool show); 0107 const QString password() const { 0108 return m_password; 0109 } 0110 void setUsername(const QString &username) { 0111 m_username = username; 0112 } 0113 const QString username() const { 0114 return m_username; 0115 } 0116 0117 RemoteView::Quality quality() const; 0118 ColorDepth colorDepth() const; 0119 uint8_t *frameBuffer; 0120 0121 Q_SIGNALS: 0122 void imageUpdated(int x, int y, int w, int h); 0123 void gotCut(const QString &text); 0124 void gotCursor(const QCursor &cursor); 0125 void passwordRequest(bool includingUsername = false); 0126 void outputErrorMessage(const QString &message); 0127 0128 /** 0129 * When we connect/disconnect/reconnect/etc., this signal will be emitted. 0130 * 0131 * @param status Is the client connected? 0132 * @param details A sentence describing what happened. 0133 */ 0134 void clientStateChanged(RemoteView::RemoteStatus status, const QString &details); 0135 0136 public Q_SLOTS: 0137 void mouseEvent(int x, int y, int buttonMask); 0138 void keyEvent(int key, bool pressed); 0139 void clientCut(const QString &text); 0140 0141 protected: 0142 void run() override; 0143 0144 private: 0145 void setClientColorDepth(rfbClient *cl, ColorDepth cd); 0146 void setColorDepth(ColorDepth colorDepth); 0147 0148 // These static methods are callback functions for libvncclient. Each 0149 // of them calls back into the corresponding member function via some 0150 // TLS-based logic. 0151 static rfbBool newclientStatic(rfbClient *cl); 0152 static void updatefbStaticPartial(rfbClient *cl, int x, int y, int w, int h); 0153 static void updateFbStaticFinished(rfbClient *cl); 0154 static void cuttextStatic(rfbClient *cl, const char *text, int textlen); 0155 static char *passwdHandlerStatic(rfbClient *cl); 0156 static rfbCredential *credentialHandlerStatic(rfbClient *cl, int credentialType); 0157 static void outputHandlerStatic(const char *format, ...); 0158 static void cursorShapeHandlerStatic(rfbClient *cl, int xhot, int yhot, int width, int height, int bpp); 0159 0160 // Member functions corresponding to the above static methods. 0161 rfbBool newclient(); 0162 void updatefbPartial(int x, int y, int w, int h); 0163 void updatefbFinished(); 0164 void cuttext(const char *text, int textlen); 0165 char *passwdHandler(); 0166 rfbCredential *credentialHandler(int credentialType); 0167 void outputHandler(const char *format, va_list args); 0168 0169 QImage m_image; 0170 rfbClient *cl; 0171 QString m_host; 0172 QString m_password; 0173 QString m_username; 0174 int m_port; 0175 bool m_showLocalCursor; 0176 QMutex mutex; 0177 RemoteView::Quality m_quality; 0178 qreal m_devicePixelRatio; 0179 ColorDepth m_colorDepth; 0180 QQueue<ClientEvent* > m_eventQueue; 0181 //color table for 8bit indexed colors 0182 QVector<QRgb> m_colorTable; 0183 QString outputErrorMessageString; 0184 0185 QRect m_dirtyRect; 0186 0187 volatile bool m_stopped; 0188 volatile bool m_passwordError; 0189 0190 /** 0191 * Connection keepalive/reconnection support. 0192 */ 0193 struct { 0194 /** 0195 * Number of seconds between probes. If zero, we will not attempt 0196 * to enable it. 0197 */ 0198 int intervalSeconds; 0199 /** 0200 * Number of failed probes required to recognise a disconnect. 0201 */ 0202 int failedProbes; 0203 /** 0204 * Was keepalive successfully set? 0205 */ 0206 bool set; 0207 /** 0208 * Did keepalive detect a disconnect? 0209 */ 0210 volatile bool failed; 0211 } m_keepalive; 0212 0213 // Initialise the VNC client library object. 0214 bool clientCreate(bool reinitialising); 0215 0216 // Uninitialise the VNC client library object. 0217 void clientDestroy(); 0218 0219 // Turn on keepalive support. 0220 void clientSetKeepalive(); 0221 0222 // Record a state change. 0223 void clientStateChange(RemoteView::RemoteStatus status, const QString &details); 0224 QString m_previousDetails; 0225 0226 private Q_SLOTS: 0227 void checkOutputErrorMessage(); 0228 }; 0229 0230 #endif