kindboy18:第一个问题:发送带参数的信号为何会出现这样的问题呢?我为何没有遇到过?是不是你的形参是自定义类型,如果是自定义类型要用qRegisterMetaType注册一下的
第二个问题:QTcpSocket读数据一次只能读8k,你可以用append(m_tcpSocket->readAll())这个试一下
第三个问题:可能是 ..
(2015-08-01 16:44) 
谢谢您的关注和回答!
代码有点多,只贴了相关部分
//窗体的头文件
#ifndef COMM_H
#define COMM_H
#include <QWidget>
#include <QtNetwork/QtNetwork>
//添加部件头文件
#include <QLabel>
#include <QPushButton>
#include <QTextBrowser>
#include <QComboBox>
#include <QGroupBox>
#include <QCheckBox>
#include "message.h"
using namespace std;
namespace Ui {
class comm;
}
class comm : public QWidget
{
Q_OBJECT
public:
explicit comm(QWidget *parent = 0);
~comm();
protected:
int sendCommand(const char *command);
private:
Ui::comm *ui;
int ifStreamData;
int ifConnected;
Message* m;
//定义各种部件的变量
QLabel* chooseLabel;
QLabel* sendLabel;
QLabel* receiveLabel;
QGroupBox* basicSettingsgroupBox;
QGroupBox* filterCfggroupBox;
QGroupBox* otherCmdgroupBox;
QPushButton* setAccessModeButton;
QPushButton* ipAddrButton;
QPushButton* setScanCfgButton;
QPushButton* LCMcfgButton;
QPushButton* scanDataCfgButton;
QPushButton* outputRangeButton;
QPushButton* writeAllButton;
QPushButton* LCMstateButton;
QPushButton* deviceStateButton;
QPushButton* loadFacDefButton;
QPushButton* rebootButton;
QPushButton* clearButton;
QPushButton* sendButton;
QCheckBox* particleFiltercheckBox;
QCheckBox* meanFiltercheckBox;
QCheckBox* nto1pulseFiltercheckBox;
QCheckBox* fogFiltercheckBox;
QComboBox* sendDatacomboBox;
QTextBrowser* sendBrowser;
QTextBrowser* receiveBrowser;
//画部件的函数声明
void drawcomponents();
signals:
void threadSend(char* sendText);
private slots:
//槽函数声明
void setTextContents0();
void setTextContents1();
void setTextContents2();
void setTextContents3();
void setTextContents4();
void setTextContents5();
void setTextContents6();
void setTextContents7();
void setTextContents8();
void setTextContents9();
void setTextContents10();
void setTextContents11(int);
void setTextContents12(int);
void setTextContents13(int);
void setTextContents14(int);
void setTextContents15(int);
int sendSlot();
void programEnabled();
};
#endif // COMM_H
//窗体的源文件中相关代码
#include "comm.h"
#include "ui_comm.h"
#include "device.h"
#include <iostream>
#include <conio.h>
#include <QtGui>
#pragma execution_character_set("utf-8")
#define IP_ADDR "sWN EIIpAddr C0 A8 0 1"
//构造函数
comm::comm(QWidget *parent) :
QWidget(parent),
ui(new Ui::comm)
{
//绘制窗体
ui->setupUi(this);
resize(600,620);
drawcomponents();
//设置参数
ifStreamData = 0;
ifConnected = 0;
//启动子线程
m = new Message(receiveBrowser);
connect(this, SIGNAL(threadSend(char*)), m, SLOT(sendCommand(char*)));
connect(m, SIGNAL(deviceConnected()), this, SLOT(programEnabled()));
m->start();
}
//绘制窗体函数
void comm::drawcomponents()
{
...... //绘制组件,连接信号与槽
connect(sendButton, SIGNAL(clicked()), this, SLOT(sendSlot()));
}
//发送按键对应的处理函数
int comm::sendSlot()
{
if(ifConnected == 0)
{
receiveBrowser->append("PC is not connected to the device!\n");
return -1;
}
QString qstringCommand = sendBrowser->toPlainText();
QByteArray qbytearrayCommand = qstringCommand.toLatin1();
char* charCommand = qbytearrayCommand.data();
emit threadSend(charCommand);
return 0;
}
//设备成功连接后,使窗体可以操作的函数
void comm::programEnabled()
{
ifConnected = 1;
}
....... //其它按键对应的槽函数,肯定没影响
//析构函数
comm::~comm()
{
delete ui;
}
//子线程头文件
#ifndef MESSAGE
#define MESSAGE
#include <QThread>
#include <QtNetwork/QtNetwork>
#include <QTextBrowser>
#include <QFile>
#include <QTextStream>
using namespace std;
class Message : public QThread
{
Q_OBJECT
public:
Message(QTextBrowser* q);
~Message();
int getConnectionStaus();
protected:
void run();
private:
QTcpSocket* clientSocket;
QTextBrowser* qtb;
QFile* outfile;
QTextStream outfileStream;
int isConnected;
signals:
void deviceConnected();
private slots:
void successConnection();
int sendCommand(char *command);
};
#endif // MESSAGE
//子线程源文件
#include "message.h"
#include "device.h"
#include <QApplication>
//构造函数
Message::Message(QTextBrowser* q)
{
isConnected = 0;
qtb = q; //将界面中的文本浏览框的指针传到子线程,以便于进行输出操作
outfile = new QFile("F:\\data.txt");
outfileStream.setDevice(outfile);
}
//获取设备连接状态
int Message::getConnectionStaus()
{
return isConnected;
}
//设备连接成功的处理函数
void Message::successConnection()
{
isConnected = 1;
qtb->append("Device connected!\n");
emit deviceConnected();
}
//发送命令的函数
int Message::sendCommand(char *command)
{
quint8 bytesToSend = 2; //命令的长度加上起始符号和终止符号即为要发送的字节数
char* messageToSend; //处理后的待发送的消息
//计算需要发送的字节数
quint8 i = 0;
while(command[i++] != 0) bytesToSend++;
//对命令进行处理
messageToSend = new char [bytesToSend];
*messageToSend = 2; //起始符号的ASCII值
for(i = 1; i <= bytesToSend - 2; i++)
*(messageToSend + i) = command[i-1]; //将想要发送的命令送到发送缓冲区中
*(messageToSend + bytesToSend - 1) = 3; //终止符号的ASCII值
//如果实际发送的字节数不等于需要发送的字节数,说明发送命令失败
int bytesWritten = clientSocket->write(messageToSend, bytesToSend);
if(bytesWritten != bytesToSend)
{
qtb->append("Failed to send command!\n");
return -1;
}
else qtb->append("Send successfully!\n");
return 0;
}
//子线程的执行函数
void Message::run()
{
int recvLength = 0;
clientSocket = new QTcpSocket(); //创建套接字
connect(clientSocket, SIGNAL(connected()), this, SLOT(successConnection())); //套接字成功连接设备后执行相应的处理函数
clientSocket->connectToHost(QHostAddress(DEVICE_IP_ADDRESS), DEVICE_TCP_PORT); //连接到设备
while(1)
{
if(!clientSocket->waitForReadyRead(1000)) continue; //等待设备向PC发送报文
char readBuf[2500]{0};
recvLength = clientSocket->read(readBuf, 2500); //读取报文
qtb->append(readBuf);
if(!outfile->open(QIODevice::WriteOnly|QIODevice::Text|QIODevice::Append)) //打开文件。如果文件不存在,会创建该文件。写入的数据为文本格式,且不覆盖原来的数据
{
qtb->append("Failed to write data to document!");
break;
}
QString temp(readBuf);
outfileStream<<temp<<endl;
outfile->close();
qtb->append("");
qtb->moveCursor(QTextCursor::End); //输出滚屏
}
}
//析构函数
Message::~Message()
{
clientSocket->deleteLater();
quit();
wait();
}
关于Timer,我现在认为应该是QTcpSocket的waitForReadyRead函数使用了Timer来实现定时的功能。虽然程序实行起来没有影响,但是有时候还是会报错,导致程序终止。所以想解决这些问题,看看程序能不能不会出错退出。再次感谢您!