Android实现远程控制PC(Android[客户端]+Qt[服务器端])

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Android实现远程控制PC(Android[客户端]+Qt[服务器端])相关的知识,希望对你有一定的参考价值。

由于本人没有无线路由器,因此用Win7自带的虚拟wifi让手机上网:Win7虚拟wifi

    但是,电脑不在我的房间,因此每天晚上在床上玩完手机还要下床去关电脑,让很懒很懒的本人很不爽,因此自己尝试着做了一个远程控制。

    软件客户端运行在Android设备上(我的手机是android的),服务器端运行在我的Win7本本上。客户端用的是Android平台应用编程,服务器端用的是Qt编写的。

    首先设置好默认端口,然后设置控制方法,为了方便起见,这里直接利用标准C中的system接口(调用shell,Win7下就是cmd命令提示符了)。客户端发送命令给服务器,服务器直接执行命令,并将标准输出返回给客户端。

    下面看一些代码,具体代码可以到这里下载:工程源代码

    服务器端:

    头文件:

    mainwindow.h

 

[cpp] view plain copy
 
  1. #ifndef MAINWINDOW_H  
  2. #define MAINWINDOW_H  
  3.   
  4. #include <QMainWindow>  
  5. #include <QtNetwork/QTcpServer>  
  6. #include <QTextDocument>  
  7. #include "server.h"  
  8.   
  9. namespace Ui {  
  10. class MainWindow;  
  11. }  
  12.   
  13. class MainWindow : public QMainWindow  
  14. {  
  15.     Q_OBJECT  
  16.       
  17. public:  
  18.     explicit MainWindow(QWidget *parent = 0);  
  19.     QTextDocument *textDocument;  
  20.     Server *server;  
  21.     ~MainWindow();  
  22. public slots:  
  23.     void getConnect();  
  24.     void execCommand(const char *command,int length,const char *add,int clientCode);  
  25.     void showText(const char *text);  
  26.   
  27. signals:  
  28.     void writeFile(int clientCode);  
  29.       
  30. private:  
  31.     Ui::MainWindow *ui;  
  32. };  
  33.   
  34. #endif // MAINWINDOW_H  

    server.h

 

 

[cpp] view plain copy
 
  1. #ifndef SERVER_H  
  2. #define SERVER_H  
  3.   
  4. #include <QTextDocument>  
  5. #include <QTcpServer>  
  6.   
  7. class MainWindow;  
  8.   
  9. class Server:public QTcpServer  
  10. {  
  11.     Q_OBJECT  
  12. private:  
  13.     int port;  
  14.     MainWindow *mainWindow;  
  15.     QHostAddress hostAddress;  
  16.     int clientNum;        //已建立的客户端连接数  
  17.   
  18. public:  
  19.     Server(MainWindow *m,int p,QHostAddress a);  
  20.     void incomingConnection(int handle);  
  21. signals:  
  22.     void printText(const char *text);  
  23.   
  24. };  
  25.   
  26. #endif // SERVER_H  

    serverthread.h

 

 

[cpp] view plain copy
 
  1. #ifndef SERVERTHREAD_H  
  2. #define SERVERTHREAD_H  
  3. #include <QThread>  
  4. #include <QTcpSocket>  
  5. #include "mainwindow.h"  
  6.   
  7. class ServerThread:public QThread  
  8. {  
  9.     Q_OBJECT  
  10. private:  
  11.     QTcpSocket *socket;  
  12.     MainWindow *mainWindow;  
  13.     int clientCode;  
  14. public:  
  15.     ServerThread(int socketDescriptor,QObject *parent,MainWindow *m,int clientCode);  
  16.     void run();  
  17. signals:  
  18.     void newCommand(const char *str,const int length,const char *add,int clientCode);  
  19. public slots:  
  20.     void receiveData();  
  21.     void readFile(int cC);  
  22. };  
  23.   
  24. #endif // SERVERTHREAD_H  

    源代码:

 

    main.cpp

 

[cpp] view plain copy
 
  1. #include <QtGui/QApplication>  
  2. #include "mainwindow.h"  
  3.   
  4. int main(int argc, char *argv[])  
  5. {  
  6.     QApplication a(argc, argv);  
  7.     MainWindow w;  
  8.     w.show();  
  9.   
  10.     return a.exec();  
  11. }  

    mainwindow.cpp

 

 

[cpp] view plain copy
 
  1. #include <QtNetwork/QHostAddress>  
  2. #include <QTextDocument>  
  3. #include <string>  
  4. #include <cstring>  
  5. #include <string.h>  
  6. #include "mainwindow.h"  
  7. #include "ui_mainwindow.h"  
  8.   
  9. MainWindow::MainWindow(QWidget *parent) :  
  10.     QMainWindow(parent),  
  11.     ui(new Ui::MainWindow)  
  12. {  
  13.     ui->setupUi(this);  
  14.     server=new Server(this,5648,QHostAddress::Any);   //初始化服务器  
  15.   
  16. }  
  17.   
  18. MainWindow::~MainWindow()  
  19. {  
  20.     delete ui;  
  21. }  
  22.   
  23. void MainWindow::getConnect()  
  24. {  
  25.     QTextDocument *textDocumentM=new QTextDocument(QString("new connect !"),this);  
  26.     ui->textEdit->setDocument(textDocumentM);  
  27.     server->nextPendingConnection();  
  28. }  
  29.   
  30. void MainWindow::execCommand(const char *command,int length,const char *add, int clientCode)  
  31. {  
  32.     QTextDocument *textDocumentC=new QTextDocument(QString("message"),this);  
  33.     char *commandStr=new char[length+15];  
  34.     strcpy(commandStr,command);  
  35.     char *para=commandStr+length;  
  36.     char *c=" > temp.txt";        //将结果重定向到一个临时文件  
  37.     strcpy(para,c);  
  38.     system(commandStr);                        //执行shell命令  
  39.     emit writeFile(clientCode);  
  40.     ui->textEdit->setDocument(textDocumentC);  
  41. }  
  42.   
  43. void MainWindow::showText(const char *text)  
  44. {  
  45.     QTextDocument *textDocumentT=new QTextDocument(QString(text),this);  
  46.     ui->textEdit->setDocument(textDocumentT);  
  47. }  

    server.cpp

 

 

[cpp] view plain copy
 
  1. #include "server.h"  
  2. #include "serverthread.h"  
  3.   
  4. Server::Server(MainWindow *m,int p,QHostAddress a)  
  5. {  
  6.     this->hostAddress=a;  
  7.     this->port=p;  
  8.     this->mainWindow=m;  
  9.     this->clientNum=0;             //初始化客户连接数  
  10.     this->QTcpServer::listen(hostAddress,quint16(port));  
  11.     connect(this,SIGNAL(printText(const char*)),this->mainWindow,SLOT(showText(const char*)));  
  12. }  
  13.   
  14. void Server::incomingConnection(int handle)  
  15. {  
  16.     char ch[]="new connection !";     
  17.     emit printText(ch);  
  18.     ServerThread *thread=new ServerThread(handle,this,mainWindow,this->clientNum);  //每建立一个连接,都会开启一个服务线程,线程有客户编号  
  19.     this->clientNum++;  
  20.     thread->start();  
  21. }  

serverthread.cpp

 

 

[cpp] view plain copy
 
  1. #include "serverthread.h"  
  2. #include <QFile>  
  3. #define COMMAND_SIZE 50  
  4. ServerThread::ServerThread(int socketDescriptor,QObject *parent,MainWindow *m,int c):QThread(parent)  
  5. {  
  6.     this->mainWindow=m;  
  7.     this->clientCode=c;  
  8.     socket=new QTcpSocket(parent);  
  9.     socket->setSocketDescriptor(socketDescriptor);  
  10. }  
  11.   
  12. void ServerThread::run()  
  13. {  
  14.     this->connect(socket,SIGNAL(readyRead()),this,SLOT(receiveData()));  
  15.     connect(this,SIGNAL(newCommand(const char*,int,const char*,int)),this->mainWindow,SLOT(execCommand(const char*,int,const char*,int)));  
  16.     connect(this->mainWindow,SIGNAL(writeFile(int)),this,SLOT(readFile(int)));  
  17.     exec();  
  18. }  
  19.   
  20. void ServerThread::receiveData()  
  21. {  
  22.     int left=socket->bytesAvailable();  
  23.     char *command=new char[COMMAND_SIZE];  
  24.     while(left>0)  
  25.     {  
  26.         int read=socket->readLine(command,COMMAND_SIZE);  //读取原始命令  
  27.         emit newCommand(command,read,"test",this->clientCode);  
  28.         left-=read;  
  29.     }  
  30. }  
  31. //读取临时文件中的标准输出信息并写入socket传回给客户端  
  32. void ServerThread::readFile(int cC)  
  33. {  
  34.     if(cC==this->clientCode)  
  35.     {  
  36.         QFile *file=new QFile("temp.txt");  
  37.         if(file->open(QIODevice::ReadWrite))  
  38.         {  
  39.             char *buffer=new char[100];  
  40.             int length;  
  41.             while((length=file->read(buffer,100))>0)  
  42.             {  
  43.                 socket->write(buffer,length);  
  44.             }  
  45.         }  
  46.         socket->flush();  
  47.         file->close();  
  48.         system("del temp.txt");//删除临时文件  
  49.     }  
  50. }  


 

客户端:

只有一个Acitvity

MainActivity.Java

 

[java] view plain copy
 
  1. package com.tobacco.phonetest;  
  2.   
  3. import java.io.BufferedReader;  
  4. import java.io.IOException;  
  5. import java.io.InputStreamReader;  
  6. import java.io.PrintWriter;  
  7. import java.net.Socket;  
  8. import java.net.UnknownHostException;  
  9.   
  10. import android.app.Activity;  
  11. import android.os.Bundle;  
  12. import android.os.Handler;  
  13. import android.util.Log;  
  14. import android.view.Menu;  
  15. import android.view.View;  
  16. import android.view.View.OnClickListener;  
  17. import android.widget.Button;  
  18. import android.widget.EditText;  
  19. import android.widget.TextView;  
  20.   
  21. public class MainActivity extends Activity implements OnClickListener,Runnable{  
  22.       
  23.     private Button button;  
  24.     private Button clear;  
  25.     private EditText editText;  
  26.     private TextView tv;  
  27.     private Socket socket;  
  28.     private PrintWriter pw;  
  29.     private BufferedReader br;  
  30.     //private InputStream is;  
  31.     private Handler handler;  
  32.   
  33.     @Override  
  34.     public void onCreate(Bundle savedInstanceState) {  
  35.         super.onCreate(savedInstanceState);  
  36.         setContentView(R.layout.activity_main);  
  37.         handler=new Handler();  
  38.         button=(Button)findViewById(R.id.button);  
  39.         clear=(Button)findViewById(R.id.clear);  
  40.         button.setOnClickListener(this);  
  41.         clear.setOnClickListener(this);  
  42.         editText=(EditText)findViewById(R.id.edittext);  
  43.         tv=(TextView)findViewById(R.id.textView);  
  44.         try {  
  45.             //socket=new Socket("tobacco5648.xicp.net",5648); //我的pc域名  
  46.             socket=new Socket("192.168.137.1",5648);   //建立socket,这里应该根据pc的ip地址进行修改  
  47.             //socket=new Socket("www.baidu.com",80);  
  48.         } catch (UnknownHostException e) {  
  49.             // TODO Auto-generated catch block  
  50.             e.printStackTrace();  
  51.             Log.e("socket","unknown host");  
  52.         } catch (IOException e) {  
  53.             // TODO Auto-generated catch block  
  54.             e.printStackTrace();  
  55.             Log.e("socket","io execption");  
  56.         }  
  57.         if(socket==null){  
  58.             Log.e("socket","null");  
  59.         }  
  60.         else  
  61.             try {  
  62.             pw=new PrintWriter(socket.getOutputStream());  
  63.             br=new BufferedReader(new InputStreamReader(socket.getInputStream(),"gbk"));  
  64.             String remote=socket.getInetAddress().getHostAddress();  
  65.             String self=socket.getLocalAddress().getHostAddress();  
  66.             tv.setText("connected!"+"\r\n"+"remote:"+remote+"\r\n"+"local:"+self+"\r\n");  
  67.             //is=socket.getInputStream();  
  68.             if(pw!=null&&br!=null){  
  69.                 new Thread(this).start();  
  70.             }  
  71.         } catch (IOException e) {  
  72.             // TODO Auto-generated catch block  
  73.             e.printStackTrace();  
  74.         }  
  75.     }  
  76.   
  77.     @Override  
  78.     public boolean onCreateOptionsMenu(Menu menu) {  
  79.         getMenuInflater().inflate(R.menu.activity_main, menu);  
  80.         return true;  
  81.     }  
  82.   
  83.     public void onClick(View view) {  
  84.         if(view==button){  
  85.             String str;  
  86.             str=editText.getText().toString();  
  87.             pw.print(str);  
  88.             pw.flush();  
  89.         }  
  90.         else if(clear==view){  
  91.             tv.setText("");  
  92.         }  
  93.           
  94.     }  
  95.   
  96.     public void run() {  
  97.         while(true){  
  98.         try {  
  99.             String str;  
  100.             while((str=br.readLine())!=null){  
  101.                 final String s=str;  
  102.                 handler.post(new Runnable(){  
  103.   
  104.                     public void run() {  
  105.                         tv.setText(tv.getText()+s+"\r\n");  
  106.                           
  107.                     }});  
  108.                   
  109.                   
  110.             }  
  111.         } catch (IOException e) {  
  112.             // TODO Auto-generated catch block  
  113.             e.printStackTrace();  
  114.         }  
  115.           
  116.     }  
  117.     }  
  118.   
  119.       

 

http://blog.csdn.net/tobacco5648/article/details/7780385

以上是关于Android实现远程控制PC(Android[客户端]+Qt[服务器端])的主要内容,如果未能解决你的问题,请参考以下文章

Android开发之远距离PC控制

Android开发之远距离PC控制

基于Android的远程视频监控系统(含源码)

极客日报:韩国成功研发变色龙软体机器人;曝新iPhone将推出摄影版“人像模式”;Android 12 Beta 4发布

如何用电脑操作android手机

Android仿自如客APP裸眼3D效果