本文采用QT_Windows_5.9 + VS2017编译器进行配置。
各个版本QT下载地址:https://download.qt.io/archive/qt/
选择想要的版本进行下载,我下载的文件是: qt-opensource-windows-x86-5.9.7.exe
一路默认至下图位置,选择自己编辑器对应的位置打钩即可。我的VS是2017的,所以在MSVS 2017 64-bit位置打钩。之后一路默认即可完成安装。
有三种基类可供选择,分别对应不同的图形结构。初次尝试用基础的Widget即可。
点击开始运行,右下角绿色进度条完成,编译成功,生成空白窗口,执行成功。安装完成!
实现一个可以关闭窗口的按钮,操作如下图所示:
OK,此时会生成下图的两个文件(.h和.cpp)
再进行修改使新生成的类继承于QPushButten
mybutten.h
#ifndef MYBUTTEN_H
#define MYBUTTEN_H
#include
class MyButtern : public QWidget
{
Q_OBJECT
public:
explicit MyButtern(QWidget *parent = nullptr);
signals:
public slots:
};
#endif // MYBUTTERN_H
修改为
#ifndef MYBUTTERN_H
#define MYBUTTERN_H
#include
class MyButtern : public QPushButton
{
Q_OBJECT
public:
explicit MyButtern(QPushButton *parent = nullptr);
signals:
public slots:
};
#endif // MYBUTTERN_H
mybutten.cpp
#include "mybuttern.h"
MyButtern::MyButtern(QWidget *parent) : QWidget(parent)
{
}
修改为
#include "mybutten.h"
MyButtern::MyButtern(QPushButton *parent) : QPushButton(parent)
{
}
widget.cpp
#include "widget.h"
#include "ui_widget.h"
#include "mybutten.h"
Widget::Widget(QWidget *parent) :
QWidget(parent),
ui(new Ui::Widget)
{
ui->setupUi(this);
MyButten *btn = new MyButten("关闭"); //创建按钮
btn->setParent(this); //将按钮依赖于父窗口
connect(btn,&MyButten::clicked,this,&QWidget::close); //建立信号槽机制
}
Widget::~Widget()
{
delete ui;
}
出现错误
因为再创建新的类之前进行过调试,只需要将文件中调试的生成部分删除,再重新运行即可。
OK,运行成功,点击红框中的按钮即可关闭窗口。
再将此按钮添加文字并移动一下吧
#include "widget.h"
#include "ui_widget.h"
#include "mybutten.h"
Widget::Widget(QWidget *parent) :
QWidget(parent),
ui(new Ui::Widget)
{
ui->setupUi(this);
MyButten *btn = new MyButten; //创建按钮
btn->setParent(this); //将按钮依赖于父窗口
connect(btn,&MyButten::clicked,this,&QWidget::close); //建立信号槽机制
btn->setText("关闭"); //添加文字
btn->move(200,100); //移动位置
}
Widget::~Widget()
{
delete ui;
}
安装Python,注意在安装界面在添加环境变量处打钩。
重新创建一个项目 名为untitled1用于测试demo。
我的路径是 C:\Users\Administrator\AppData\Local\Programs\Python\Python36\include
添加下图红框中的两条代码
替换自己相应的路径进行添加
.pro
INCLUDEPATH += -I C:\Users\Administrator\AppData\Local\Programs\Python\Python36\include
LIBS += -LC:\Users\Administrator\AppData\Local\Programs\Python\Python36\libs/ -lpython36
def greatFunc():
print("OK")
main.cpp
#include "widget.h"
#include
#include
#include
int main(int argc, char *argv[])
{
QApplication a(argc, argv);
Widget w;
w.show();
//进行初始化
Py_Initialize();
//如果初始化失败,返回
if(!Py_IsInitialized())
{
qDebug()<<"erro 1";
return a.exec();
}
//加载模块,模块名称为myModule,就是myModule.py文件
PyObject *pModule = PyImport_ImportModule("myModule");
//如果加载失败,则返回
if(!pModule)
{
qDebug()<<"erro 2";
return a.exec();
}
//加载函数greatFunc
PyObject * pFuncHello = PyObject_GetAttrString(pModule, "greatFunc");
//如果失败则返回
if(!pFuncHello)
{
qDebug()<<"erro 3";
return a.exec();
}
//调用函数
PyObject_CallFunction(pFuncHello, NULL);
//退出
Py_Finalize();
return a.exec();
}
在python的libs文件下添加python36_d.lib文件(将python36.lib赋值再重命名为python36_d.lib即可)
我的路径: C:\Users\Administrator\AppData\Local\Programs\Python\Python36\libs
运行程序,如myModule.py中代码内容:
print(OK)
OK,经过上面的实验我们已经知道了简单的信号槽使用方式和QT中如何启动python程序。那么我们就可以开始最后一部分实验。
注意:此时默认已配置好环境
新建项目,同样选择Qwidget作为基类。
新建两个C++类,MyButton用于实例化按钮来发出信号,runpython用于编写槽函数。
mypython.py(需放在debug文件夹中)
import numpy as np
def greatFunc():
a = np.ones(10)
print(a)
print("python file is runed")
runpy.pro(新加两行)
INCLUDEPATH += -I C:\Users\123\Anaconda3\include
LIBS += -LC:\Users\123\Anaconda3\libs -lpython36
mybutton.h
#ifndef MYBUTTON_H
#define MYBUTTON_H
#include
class MyButton : public QPushButton
{
Q_OBJECT
public:
explicit MyButton(QPushButton *parent = nullptr);
signals:
public slots:
};
#endif // MYBUTTON_H
mybutton.cpp
#include "mybutton.h"
MyButton::MyButton(QPushButton *parent) : QPushButton(parent)
{
}
runpython.h
#ifndef RUNPYTHON_H
#define RUNPYTHON_H
#include
class RunPython : public QObject
{
Q_OBJECT
public:
explicit RunPython(QObject *parent = nullptr);
signals:
public slots:
void run();
};
#endif // RUNPYTHON_H
runpython.cpp
#include "runpython.h"
#include
#include
RunPython::RunPython(QObject *parent) : QObject(parent)
{
}
void RunPython::run()
{
qDebug() << "run it!";
//进行初始化
Py_Initialize();
//如果初始化失败,返回
if(!Py_IsInitialized())
{
qDebug()<<"erro 1";
}
//加载模块,模块名称为myModule,就是myModule.py文件
PyObject *pModule = PyImport_ImportModule("mypython");
//如果加载失败,则返回
if(!pModule)
{
qDebug()<<"erro 2";
}
//加载函数greatFunc
PyObject * pFuncHello = PyObject_GetAttrString(pModule, "greatFunc");
//如果失败则返回
if(!pFuncHello)
{
qDebug()<<"erro 3";
}
//调用函数
PyObject_CallFunction(pFuncHello, NULL);
//退出
Py_Finalize();
}
widget.h
#ifndef WIDGET_H
#define WIDGET_H
#include
#include
namespace Ui {
class Widget;
}
class Widget : public QWidget
{
Q_OBJECT
public:
explicit Widget(QWidget *parent = nullptr);
~Widget();
RunPython* f; //新加
private:
Ui::Widget *ui;
};
#endif // WIDGET_H
widget.cpp
#include "widget.h"
#include "ui_widget.h"
#include
Widget::Widget(QWidget *parent) :
QWidget(parent),
ui(new Ui::Widget)
{
ui->setupUi(this);
QPushButton* btn = new QPushButton;
btn->setParent(this);
btn->setText("启动python脚本");
btn->move(200,100);
f = new RunPython;
connect(btn,&MyButton::clicked,f,&RunPython::run);
}
Widget::~Widget()
{
delete ui;
}
main.cpp
#include "widget.h"
#include
int main(int argc, char *argv[])
{
QApplication a(argc, argv);
Widget w;
w.show();
return a.exec();
}
以下博客内容更加详尽,给予了我很大帮助,在此表示感谢!
Qt5中使用C++调用Python
QT调用python脚本时遇到的坑(十一大坑全有)Qt5中使用C++调用Python
Qt+Python混合编程