Python笔记:c++内嵌python,c++主窗口如何传递给脚本中的QDialog,使用的是pybind11

发布于:2025-05-15 ⋅ 阅读:(12) ⋅ 点赞:(0)

1. 问题描述

用的是python 3.8.20, qt版本使用的是5.15.2, PySide的版本是5.15.2, pybind11的版本为2.13.6

网上说在python脚本中直接用PySide2自带的QWinWidget,如from PySide2.QtWinExtras import QWinWidget,但我用的版本中说没有QWinWidget,所以就网上找了QWinWidget的源码,直接
在c++宿主程序中编译,后使用pybind11导出到解释器:

开始想到的是直接构造一个隐藏的QWidget,关联的是MFC的主窗口句柄,然后将指针导出到解释器,

PYBIND11_EMBEDDED_MODULE(TestApp, m)
{
	m.def("GetMainWidget", []() { 
		static auto pWidget = new QWinWidget(AfxGetMainWnd()->m_hWnd);
		return pWidget; });
}

然后再Python脚本端

dlg = MyUIDialog( TestApp.GetMainWidget )

但执行时提示如下错误

TypeError: ‘PySide2.QtWidgets.QDialog’ called with wrong argument
types: PySide2.QtWidgets.QDialog(QWinWidget) Supported signatures:
PySide2.QtWidgets.QDialog(typing.Union[PySide2.QtWidgets.QWidget,
NoneType] = None, PySide2.QtCore.Qt.WindowFlags =
Default(Qt.WindowFlags))

以为是不识别基类,直接构造QWidget

PYBIND11_EMBEDDED_MODULE(TestApp, m)
{
	m.def("GetMainWidget", []() { 
		static auto pWidget = new QWidget();
		return pWidget; });
}

但执行时提示如下错误

TypeError: ‘PySide2.QtWidgets.QDialog’ called with wrong argument types:
PySide2.QtWidgets.QDialog(QWidget)
Supported signatures:
PySide2.QtWidgets.QDialog(typing.Union[PySide2.QtWidgets.QWidget, NoneType] = None, PySide2.QtCore.Qt.WindowFlags = Default(Qt.WindowFlags))

看样子,PySide2只认识PySide2.QtWidgets.QWidget,不任务QWidget呀。

2. 解决方案

后面查找资料得知,需要使用PySide2中的QtWidgets.QWidget.find,在脚本环境中重新获得Widget指针才行,find在windows下接受的是个winId

PYBIND11_EMBEDDED_MODULE(TestApp, m)
{
	m.def("GetMainWidget", []() { 
		static auto pWidget = new QWinWidget(AfxGetMainWnd()->m_hWnd);
		return pWidget->winId(); });
}

python脚本:

main_window = QtWidgets.QWidget.find(TestApp.GetMainWidget())   # 通过Qt API转换指针
dlg = MyUIDialog( main_window  )

在这里插入图片描述


网站公告

今日签到

点亮在社区的每一天
去签到