QT小项目----获取指定的进程列表,添加关闭按钮,显示进程ID

QT小项目----获取指定的进程列表,添加关闭按钮,显示进程ID

今天分享一个QT的小项目;

项目功能:获取windows下当前运行指定的进程列表,获取进程的窗口句柄,给窗口句柄发送键盘事件"Ctrl + C"

项目关键词:QTableWidget,  struct ,QMap, HANDLE, 信号绑定

struct PROCESSTYPE //进程信息,有部分字段本此分享中使用不到

关键头文件:
#include <tlhelp32.h>
#include "Psapi.h"
#pragma comment(lib,"user32.lib")
#pragma comment (lib,"Psapi.lib")



第一步设计.h文件

#ifndef MAINWINDOW_H
#define MAINWINDOW_H

#include <QMainWindow>
#include <QMap>

struct PROCESSTYPE{  //进程信息
    int ID;             //当前进程id
    QString Name;       //进程名称
    QString Path;       //进程完整路径
    int relationId;     //关联进程id(暂时不使用)
    bool isHas;         //关联进程是否关闭(暂时不使用)
};
namespace Ui {
class MainWindow;
}

class MainWindow : public QMainWindow
{
    Q_OBJECT

public:
    explicit MainWindow(QWidget *parent = 0);
    ~MainWindow();
    void init();                        //初始化
    void getSnapshot();                 //获取进程列表
    void showProcessListByTableView();  //显示进程列表
public slots:
    void OnBtnCloseGM();                //关闭信号

private slots:
    void on_refresh_clicked();          //刷新进程列表

private:
    Ui::MainWindow *ui;
    QMap<int, PROCESSTYPE> gameProcessInfo; //进程map
};

#endif // MAINWINDOW_H

.cpp文件

头文件

#include <QDebug>
#include <QMessageBox>
#include <Windows.h>
#include <tlhelp32.h>
#include "Psapi.h"
#pragma comment(lib,"user32.lib")
#pragma comment (lib,"Psapi.lib")
#include "mainwindow.h"

init()函数

setWindowIcon()设置左上角窗口的图标(项目中导入资源的方法请自行百度,有很多)

调用进程列表刷新函数on_refresh_clicked()

void MainWindow::init()
{
    this->setWindowIcon(QIcon(":/bt_icon/images/Alien.ico"));
    on_refresh_clicked();

}


on_refresh_clicked()刷新函数

清空QTableWidget列表  ;获取需要的进程列表,刷新显示列表

void MainWindow::on_refresh_clicked()
{
    for(int row = ui->tableWidget->rowCount() - 1;row >= 0; row--)
    {
        ui->tableWidget->removeRow(row);
    }
    getSnapshot();
    showProcessListByTableView();
}


getSnapshot() 遍历当前所有的进程,筛选要查找的xxx.exe进程;保存相关的信息到gameProcessInfo  QMap容器中


void MainWindow::getSnapshot()
{
    HANDLE hProcess = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, NULL);
    if(!hProcess){

        qDebug() << "CreateToolhelp32Snapshot failed!";
        return;
    }

    PROCESSENTRY32 info;
    info.dwSize = sizeof(PROCESSENTRY32);
    if(!Process32First(hProcess, &info)){

        qDebug() << "Process32First null";
        return;
    }

    gameProcessInfo.clear();
    bool haveNext = true;
    while(haveNext){

        haveNext = Process32Next(hProcess, &info);
        if(haveNext){

            HANDLE hProcess = OpenProcess(PROCESS_ALL_ACCESS, TRUE, info.th32ProcessID);

            wchar_t path[MAX_PATH+1];
            DWORD dwpath = sizeof(path);
            if(QueryFullProcessImageName(hProcess,0,path,&dwpath))
            {
                if(QString::fromWCharArray(info.szExeFile) == "xxx.exe")
                {
                    QString s = QString::fromWCharArray(path);
                    PROCESSTYPE tmp;
                    tmp.ID = info.th32ProcessID;
                    tmp.Name = QString::fromWCharArray(info.szExeFile);
                    tmp.Path = s;
                    tmp.isHas = false;
                    tmp.relationId = 0;
                    gameProcessInfo[info.th32ProcessID]=tmp;
                    //qDebug() << s;
                    qDebug() << info.th32ProcessID << "  " << info.pcPriClassBase << "  " << QString::fromWCharArray(info.szExeFile) << "  " << hProcess;
                }
            }
        }
    }


}


showProcessListByTableView()显示进程到  QTableWidget 

设计3列 进程路径   关闭按钮  进程ID

ui->tableWidget->horizontalHeader()->setSectionResizeMode(QHeaderView::Fixed);//禁止鼠标拖拽
ui->tableWidget->setEditTriggers(QAbstractItemView::NoEditTriggers);//禁止修改单元格

void MainWindow::showProcessListByTableView()
{
    ui->tableWidget->setColumnCount(3);
    ui->tableWidget->setColumnWidth(0, 690);  //0 设置列宽
    ui->tableWidget->setColumnWidth(1, 90); //1 设置列宽
    ui->tableWidget->setColumnWidth(2, 90);  //2 设置列宽
    ui->tableWidget->horizontalHeader()->setSectionResizeMode(QHeaderView::Fixed);//禁止鼠标拖拽
    ui->tableWidget->setEditTriggers(QAbstractItemView::NoEditTriggers);//禁止修改单元格

    QStringList sListHeader;
    sListHeader<<"路径"<<"GM关闭"<<"进程ID";
    ui->tableWidget->setHorizontalHeaderLabels(sListHeader);//设置表头

    int index = 0;
    QMap<int, PROCESSTYPE>::iterator it = gameProcessInfo.begin();
    for (;it!=gameProcessInfo.end();it++){
        int iRow = ui->tableWidget->rowCount();
        ui->tableWidget->setRowCount(iRow + 1);//总行数增加1
        QPushButton *button_gm = new QPushButton("XXX关闭");
        // 绑定信号
        connect(button_gm, SIGNAL(clicked()), this, SLOT(OnBtnCloseGM()));
        ui->tableWidget->setCellWidget(index,1,button_gm);


        QTableWidgetItem* item_path = new QTableWidgetItem(it.value().Path);
        ui->tableWidget->setItem(index, 0, item_path);

        QTableWidgetItem* item_id = new QTableWidgetItem(QObject::tr("%1").arg(it.value().ID));
        ui->tableWidget->setItem(index, 2, item_id);
        index++;

    }




}


OnBtnCloseGM()绑定的响应函数

void MainWindow::OnBtnCloseGM()
{
    QPushButton *pushBtn = dynamic_cast<QPushButton*>(this->sender());
    if(pushBtn == 0)
        return;
    int x = pushBtn->frameGeometry().x();
    int y = pushBtn->frameGeometry().y();
    QModelIndex index = ui->tableWidget->indexAt(QPoint(x, y));
    int row = index.row();
    int colum = index.column();
    qDebug() << QObject::tr("Dial, row: %1, colum: %2").arg(row).arg(colum);


    if(ui->tableWidget->item(row,3) != NULL){
        int processId = ui->tableWidget->item(row,3)->text().toInt();
        qDebug() << processId;

        if (gameProcessInfo.find(processId)!=gameProcessInfo.end()){
            QMap<int, PROCESSTYPE>::iterator it = gameProcessInfo.find(processId);
            QString TitleName(it.value().Path);

            LPCWSTR Appcaption = reinterpret_cast<LPCWSTR>(TitleName.data());

            HWND appwnd;
            appwnd = ::FindWindowW(NULL,Appcaption);
            if(appwnd){
                SetForegroundWindow(appwnd);
                keybd_event(VK_CONTROL,0,0,0);//按下Ctrl
                keybd_event('C',0,0,0);//按下C

                keybd_event('C',0,KEYEVENTF_KEYUP,0);//弹起C
                keybd_event(VK_CONTROL,0,KEYEVENTF_KEYUP,0);//弹起Ctrl

                pushBtn->setText("CLOSED");
            }else{
                QMessageBox::information(NULL,  "Title",  "GM CLOSED!", QMessageBox::Yes | QMessageBox::No, QMessageBox::Yes);
            }
        }
    }
}