admin管理员组

文章数量:821254

Qt for android手机屏幕当鼠标用

由于无线鼠标忘记带回家了,想躺在床上看电视(电视机屏幕当显示器)怎么办呢?HOHO,我们的手机屏幕本来就是个触摸板,嘿嘿,那就用手机屏幕当鼠标好了。
大致的思路就是电脑和手机用Tcp通信,毕竟是都连着路由器的。主要用到的模块就是QTcpServer,QTcpSocket.

#include <QObject>
#include  <QSystemTrayIcon>
class Widget;
class QTcpServer;
class QTcpSocket;class controller : public QObject
{Q_OBJECT
public:explicit controller(QObject *parent = 0);typedef enum{mouseMove,mouseSingleClick,mouseDoubleClick,mouseRightClick} mouseAction;~controller();private:QTcpServer* tcpserver;QTcpSocket* clientSocket;quint16 blockSize;Widget* widget;QSystemTrayIcon* sysIcon;private:void TranslateMessage();public slots:void onConnected();void onReadyRead();void onDisConnected();void onSysIconActRe(QSystemTrayIcon::ActivationReason reason);
#include "controller.h"
#include <QTcpSocket>
#include <QTcpServer>
#include <QDataStream>
#include <windows.h>
#include "widget.h"
#include <QHostAddress>controller::controller(QObject *parent) : QObject(parent)
{tcpserver = new QTcpServer(this);widget = new Widget;widget->show();sysIcon = new QSystemTrayIcon(this);sysIcon->setIcon(QIcon(":/computer_16px.ico"));sysIcon->hide();sysIcon->setToolTip("工作中");//    installEventFilter(sysIcon);tcpserver->listen(QHostAddress::Any,15333);  //监听15333端口blockSize = 0;connect(tcpserver,SIGNAL(newConnection()),SLOT(onConnected()));connect(widget,SIGNAL(sg_hide()),sysIcon,SLOT(show()));connect(sysIcon,SIGNAL(activated(QSystemTrayIcon::ActivationReason)),SLOT(onSysIconActRe(QSystemTrayIcon::ActivationReason)));}
void controller::onReadyRead()
{QDataStream in(clientSocket);in.setVersion(QDataStream::Qt_5_8);while(clientSocket->bytesAvailable()>=sizeof(quint16)){if(blockSize==0) in>>blockSize;if(clientSocket->bytesAvailable()<blockSize) break;TranslateMessage();//  widget->appendLog("收到消息");blockSize=0;}
}void controller::TranslateMessage()
{QDataStream in(clientSocket);in.setVersion(QDataStream::Qt_5_8);qint16 actionType;in>>actionType;
//  DWORD dx,dy;int px,py;switch(actionType){case mouseMove:in>>px>>py;
//      dx = px*GetSystemMetrics(SM_CXSCREEN);
//      dy = py*GetSystemMetrics(SM_CYSCREEN);mouse_event(MOUSEEVENTF_MOVE,px,py,0,0);
//      qDebug()<<dx<<dy;break;case mouseSingleClick:mouse_event(MOUSEEVENTF_LEFTDOWN,0,0,0,0);mouse_event(MOUSEEVENTF_LEFTUP,0,0,0,0);break;case mouseDoubleClick:mouse_event(MOUSEEVENTF_LEFTDOWN,0,0,0,0);mouse_event(MOUSEEVENTF_LEFTDOWN,0,0,0,0);mouse_event(MOUSEEVENTF_LEFTUP,0,0,0,0);break;case mouseRightClick:mouse_event(MOUSEEVENTF_RIGHTDOWN,0,0,0,0);mouse_event(MOUSEEVENTF_RIGHTUP,0,0,0,0);break;}
}
void controller::onConnected()
{clientSocket = tcpserver->nextPendingConnection();connect(clientSocket,SIGNAL(readyRead()),SLOT(onReadyRead()));connect(clientSocket,SIGNAL(disconnected()),SLOT(onDisConnected()));widget->appendLog("建立连接!");widget->appendLog("客户IP:"+clientSocket->peerAddress().toString());widget->appendLog("客户名:"+clientSocket->peerName());}
void controller::onDisConnected()
{widget->appendLog("断开连接!");clientSocket->deleteLater();
}controller::~controller()
{widget->deleteLater();
}void controller::onSysIconActRe(QSystemTrayIcon::ActivationReason reason)
{if(reason == QSystemTrayIcon::DoubleClick){widget->show();sysIcon->hide();}
}

这是PC端的主要代码 , 界面用的是之前写的模板。
下面是安卓端的,就更简单了,主要就是一个触摸区域和鼠标左右键。

#include <QDialog>
class QTcpSocket;
class QTimer;namespace Ui {
class Dialog;
}class Dialog : public QDialog
{Q_OBJECTpublic:explicit Dialog(QWidget *parent = 0);~Dialog();enum{mouseMove,mouseSingleClick,mouseDoubleClick,mouseRightClick};
private:Ui::Dialog *ui;QTcpSocket* tcpSocket;QPoint  move_pre_position;QTimer* clickTimer;public slots:void onBtn_connectClicked();void onBtn_disconnectClicked();void onClick_TimerRunout();void onConnected();void onDisconnected();void onBtn_LeftClicked();void onBtn_RightClicked();protected:void mouseMoveEvent(QMouseEvent*);void mousePressEvent(QMouseEvent*);};
#include "dialog.h"
#include "ui_dialog.h"
#include <QTcpSocket>
#include <QHostAddress>
#include <QMouseEvent>
#include <QDataStream>
#include <QTimer>Dialog::Dialog(QWidget *parent) :QDialog(parent),ui(new Ui::Dialog)
{ui->setupUi(this);showFullScreen();tcpSocket = new QTcpSocket(this);tcpSocket->bind(ui->lineEdit_port->text().toInt());connect(ui->btn_connect,SIGNAL(clicked(bool)),SLOT(onBtn_connectClicked()));clickTimer = new QTimer(this);clickTimer->setInterval(100);clickTimer->setSingleShot(true);connect(clickTimer,SIGNAL(timeout()),SLOT(onClick_TimerRunout()));connect(tcpSocket,SIGNAL(connected()),SLOT(onConnected()));connect(tcpSocket,SIGNAL(disconnected()),SLOT(onDisconnected()));connect(ui->btn_disconnect,SIGNAL(clicked(bool)),SLOT(onBtn_disconnectClicked()));connect(ui->Btn_Left,SIGNAL(clicked(bool)),SLOT(onBtn_LeftClicked()));connect(ui->Btn_Right,SIGNAL(clicked(bool)),SLOT(onBtn_RightClicked()));}Dialog::~Dialog()
{delete ui;
}void Dialog::onBtn_connectClicked()
{tcpSocket->connectToHost(QHostAddress(ui->lineEdit_ip->text()),ui->lineEdit_port->text().toInt());}
void Dialog::onBtn_disconnectClicked()
{tcpSocket->disconnectFromHost();
}void Dialog::mouseMoveEvent(QMouseEvent* event)
{if(tcpSocket->state() == QAbstractSocket::ConnectedState){QPoint movePos = event->pos() - move_pre_position;int move_x,move_y;move_x = movePos.x();move_y = movePos.y();QByteArray  data;QDataStream out(&data,QIODevice::WriteOnly);out.setVersion(QDataStream::Qt_5_8);out<<quint16(0)<<(qint16)mouseMove<<move_x<<move_y;out.device()->seek(0);out<<(quint16)(data.size()-sizeof(quint16));tcpSocket->write(data);move_pre_position = event->pos();
//        ui->textBrowser->append(QVariant(move_x).toString()+QVariant(move_y).toString());}}
void Dialog::mousePressEvent(QMouseEvent *event)
{move_pre_position = event->pos();  //记录当前位置}void Dialog::onClick_TimerRunout()
{QByteArray  data;QDataStream out(&data,QIODevice::WriteOnly);out.setVersion(QDataStream::Qt_5_8);out<<quint16(0)<<(qint16)mouseSingleClick;out.device()->seek(0);out<<(quint16)(data.size()-sizeof(quint16));tcpSocket->write(data);
}void Dialog::onConnected()
{ui->textBrowser->append("连接电脑成功!");ui->textBrowser->append("电脑名:"+tcpSocket->peerName());}void Dialog::onDisconnected()
{ui->textBrowser->append("已断开连接");
}
void Dialog::onBtn_LeftClicked()
{if(tcpSocket->state() == QAbstractSocket::ConnectedState){QByteArray  data;QDataStream out(&data,QIODevice::WriteOnly);out.setVersion(QDataStream::Qt_5_8);if(clickTimer->isActive()){out<<quint16(0)<<(qint16)mouseDoubleClick;clickTimer->stop();out.device()->seek(0);out<<(quint16)(data.size()-sizeof(quint16));tcpSocket->write(data);}else{clickTimer->start();    //双击单击判断}}
}
void Dialog::onBtn_RightClicked()
{if(tcpSocket->state() == QAbstractSocket::ConnectedState){QByteArray  data;QDataStream out(&data,QIODevice::WriteOnly);out.setVersion(QDataStream::Qt_5_8);out<<quint16(0)<<(qint16)mouseRightClick;clickTimer->stop();out.device()->seek(0);out<<(quint16)(data.size()-sizeof(quint16));tcpSocket->write(data);}
}

由于之前写过一个仿QQ的聊天程序(也就基本的聊天功能啦),这次几乎没碰到问题。主要会发生的问题就是TcpSocket的读写,可以参考上面的onReadyRead函数。(因为Tcp可能一下接到几条消息,会粘连所以要注意)。还有就是我不知道Qt有没有自带的函数可以实现任意区域的鼠标事件,我用的是windows的函数, mouse_event.
下面贴下运行效果啦:

本文标签: Qt for android手机屏幕当鼠标用