QT系列:
本文源码:QT异步命令行,通过信号和槽进行响应
信号和槽
尽管目前已经完成了一个看上去能用的命令行,但从程序的结构来说,并不十分QT。
QT编程中最与众不同的概念其实是信号和槽,而QProcess这种炫酷的功能,显然也会提供相应的信号,以实现更加方便的异步操作。如果查看源代码,可以看到QProcess中定义了如下信号
Q_SIGNALS:
void started(QPrivateSignal);
void finished(int exitCode, QProcess::ExitStatus exitStatus = NormalExit);
void errorOccurred(QProcess::ProcessError error);
void stateChanged(QProcess::ProcessState state, QPrivateSignal);
void readyReadStandardOutput(QPrivateSignal);
void readyReadStandardError(QPrivateSignal);
接下来新建两个函数和最后两个信号相绑定,故而先在头文件中添加全局变量
private slots:
void on_lineCode_returnPressed();
void readStdOut();
void readStdErr();
private:
Ui::MainWindow *ui;
QProcess* cmd;
QString codes;
然后在源文件的构造函数MainWindow下添加connect
cmd = new QProcess(this);
connect(cmd,SIGNAL(readyReadStandardOutput()),SLOT(readStdOut()));
connect(cmd,SIGNAL(readyReadStandardError()),SLOT(readStdErr()));
并在源文件中加入
void MainWindow::readStdOut(){
ui->txtRecv->append(codes);
ui->txtRecv->append(cmd->readAllStandardOutput());
}
void MainWindow::readStdErr(){
ui->txtError->append(codes);
ui->txtError->append(cmd->readAllStandardError());
}
这时再运行程序,输入一些耗时的操作,比如ipconfig
,在输入命令之后,的确不再占用输入框,而过了一会儿,ipconfig
的值返回到了文本浏览器中。
有朋友可能会问了,中文乱码是怎么回事?请先不要在意这些细节。
实现cd功能
cd就是chdir,就是Choice Directory,在命令行中用于更改工作路径。
但目前有一个非常不舒服的问题,就是cd这个命令在这里是无效的。原因在于,cd可以改变命令行所在的文件夹,但不能改变QT程序的工作路径。
所以接下来仅针对cd
这个命令来做一个功能,即更改QT程序所在路径。
首先继续添加类成员
private:
int dealCd(QString path);
int dealLocal(QString str);
然后在源文件中实现
int MainWindow::dealCd(QString path){
codes = QDir::currentPath() + ">" + codes;
ui->txtRecv->append(codes);
QDir::setCurrent(path);
ui->txtRecv->append("current path:"+QDir::currentPath());
return 1;
}
int MainWindow::dealLocal(QString str){
QStringList para = str.split(" ");
if(para[0]=="cd")
return dealCd(para[1]);
return 0;
}
将回车时对应的动作改为
void MainWindow::on_lineCode_returnPressed()
{
codes = ui->lineCode->text();
ui->lineCode->setText("");
if(dealLocal(codes))
return;
codes.replace(".","^.");
QStringList para = codes.split(" ");
cmd->start(para.first(),para.sliced(1));
codes = QDir::currentPath() + ">" + codes;
if(cmd->error()==0)
ui->txtError->append(codes+" error!!!\n请输入正确的指令");
}
效果为
最后的最后,加上一个exit
用来退出程序,再加上一个cls
清理文本浏览器,由于比较简单,故不再赘述,其效果为