初探MFC程序混合使用QT

一、背景

随着操作系统国产化替代的趋势越发明显,软件支持国际化、跨平台,已然是必须做的一件事情。原有的软件UI层用的是MFC,将其换成QT,想必是一种较好的方案。对于大型软件,特别是已发布,但还处于不断迭代的阶段,如果直接更换UI库,那么工作量还是很大,若人员较少,那么时间可能会持续挺久。倘若可以逐步替换,那么就比较经济了。

经过自己的摸索实践,MFC换QT应该是可以做到逐步替换,至少目前经过初步测试,可以支撑我的结论。

二、核心代码说明

  1. 新建一个MFC多文档程序,在MFC App类中增加一个QApplication* m_pQtApp的成员。
    在这里插入图片描述

  2. 在MFC App的InitInstance函数中创建QApplication

    BOOL CMFCAppWithQtApp::InitInstance()
    {
    	//qt 初始化
    	int nArgs = 0;
    	m_pQtApp = new QApplication(nArgs, nullptr);
    
    	//If this property is true, the applications quits when the last visible 
    	//primary window (i.e. window with no parent) is closed.
    	m_pQtApp->setQuitOnLastWindowClosed(false);
    
    	//其他代码:略
    	//....
    	//
    }
    
    
  3. 重载MFC App类的Run函数,使其调用qt的消息循环,针对windows,qt底层实现也是windows的消息循环,所以这里改了,MFC的窗口也能正常工作。

    int CMFCAppWithQtApp::Run()
    {
    //	return CWinAppEx::Run();
    
    	if (!m_pQtApp)
    	{
    		return -1;
    	}
    
    	//调用QT的消息循环
    	int nCode = m_pQtApp->exec();
    	delete m_pQtApp;
    	m_pQtApp = nullptr;
    	return nCode;
    }
    

    此处相对于MFC的run,少调用了OnIdle函数,根据QT帮助文档可知,可以创建一个超时时间为0的QTimer,然后在超时函数中调用MFC App的OnIdle。如果不调用OnIdle函数,一些功能可能会没有,如UpdateCmdUI将不起作用。

    To make your application perform idle processing (by executing a special function whenever there are no pending events), use a QTimer with 0 timeout. More advanced idle processing schemes can be achieved using processEvents().

  4. 从QDialog派生一个对话框类,做下测试,主要测试下qt的窗口显示,以及信号槽机制是否正常工作。

    #pragma once
    
    #include <QDialog>
    
    class DlgQT_Test : public QDialog
    {
    	Q_OBJECT
    
    public:
    	DlgQT_Test(QWidget *parent = Q_NULLPTR);
    	~DlgQT_Test();
    
    };
    
    
    #include "stdafx.h" //MFC移值完后再去除
    #include "DlgQT_Test.h"
    #include ".\GeneratedFiles\Debug\moc_DlgQT_Test.cpp"
    #include <QTableWidget>
    #include <QVBoxLayout>
    #include <QPushButton>
    #include <QFileSystemModel>
    #include <QDir>
    #include <QTreeView>
    #include <QMessageBox>
    
    DlgQT_Test::DlgQT_Test(QWidget *parent)
    	: QDialog(parent)
    {
    	auto pVLayout = new QVBoxLayout();
    	this->setLayout(pVLayout);
    
    	this->setStyleSheet("QPushButton{background-color: rgb(255, 0, 0);border-style: outset;border-width: 2px;border-radius: 10px; border-color: beige;font: bold 14px;min-width: 10em;padding: 6px;}");
    
    	QFileSystemModel *model = new QFileSystemModel;
    	model->setRootPath(QDir::currentPath());
    	QTreeView *tree = new QTreeView();
    	tree->setModel(model);
    	pVLayout->addWidget(tree);
    
    	auto pTestBtn = new QPushButton(QStringLiteral("按钮"), this);
    	pVLayout->addWidget(pTestBtn);
    
    	//按钮消息响应
    	QObject::connect(pTestBtn, &QPushButton::clicked, [=](bool)
    	{
    		QMessageBox::information(this, QStringLiteral("QT消息框"),
    			QStringLiteral("测试QT弹出消息框"));
    	});
    }
    
    DlgQT_Test::~DlgQT_Test()
    {
    
    }
    

    注意以上代码中有一行#include ".\GeneratedFiles\Debug\moc_DlgQT_Test.cpp" ,因为是MFC工程,moc_DlgQT_Test.cpp文件是我用qt的moc.exe来生成的,然后在此处包含进来参与编译,生成命令为

    E:\Qt\Qt5.5.1\5.5\msvc2013\bin\moc.exe -o .\GeneratedFiles\Debug\moc_DlgQT_Test.cpp .\DlgQT_Test.h
    
  5. 在MainFrame类中增加测试函数,打开以上qt对话框,进行测试

    void CMainFrame::OnButton2()
    {
    	DlgQT_Test myQTDlg;
    	myQTDlg.exec();
    }
    
    

三、运行演示

在这里插入图片描述

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:/a/603151.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

vue 开发环境的搭建

一、整个流程&#xff1a; 安装nodejs >> 安装vue >> 安装vue-cli >> 初始化 webpack(生成代码) >> 安装依赖 >> 运行vue程序 二、详细安装流程&#xff1a; 1.安装nodejs 下载&#xff1a;https://nodejs.org/dist/v12.18.3/node-v12.18.3-x…

《米小圈上学记》|快乐读书,从身边的人身边的事开始!

时间&#xff0c;抓住了就是黄金&#xff0c;虚度了就是流水;书&#xff0c;看了就是学问&#xff0c;没看就是废纸:抱负&#xff0c;努力了才叫幻想&#xff0c;放弃了那只是妄想。读书&#xff0c;不一定能转变命运&#xff0c;但肯定能让我们安静&#xff0c;安静本身就是一…

【触摸案例-手势解锁案例-连线到按钮 Objective-C语言】

一、接下来,我们接着来说这个,连线的问题啊, 1.连线的问题啊,也就是说,我现在点击一个按钮, 在移动到下一个按钮的时候,在两个按钮中间,在两个按钮都亮起来的时候呢,我们肯定是让它去画一条线的,那么, 1)首先,如果我现在从第一个按钮,连到第二个按钮,那么,这条…

二叉树的实现(详解,数据结构)

目录 一&#xff0c;二叉树需要实现的功能 二&#xff0c;下面是各功能详解 0.思想&#xff1a; 1.创建二叉树结点&#xff1a; 2.通过前序遍历的数组"ABD##E#H##CF##G##"构建二叉树 3.二叉树销毁&#xff1a; 4.前序遍历&#xff1a; 5.中序遍历&#xff1a;…

小红书「打工人」生存现状实录

近年来&#xff0c;“打工人”一词频繁出现在内容场景中。调研小红书数据显示&#xff0c;近一年“打工人、职场”相关笔记声量增长440%&#xff0c;预估互动总量增长128%&#xff0c;热度高涨。 职场年轻人正披着“打工人”的外壳&#xff0c;不断自嘲中寻求身份认同。基于此&…

各种流量包特征

[CVE-2013-1966] Apache Struts2 远程命令执行漏洞 要执行的命令在exec里面&#xff0c;而且回显数据包里面有明显执行结果回显 [CVE-2017-8046] Spring Data Rest 远程命令执行漏洞 回显不明显&#xff0c;考试提供的解码工具不能解密&#xff0c; [CVE-2017-12149] JBOSS…

java多线程编码应用1——java多线程CompletableFuture使用技巧

在实际项目开发过程中&#xff0c;大部分程序的执行顺序都是按照代码编写的先后顺序&#xff0c;依次从上往下挨个执行的&#xff0c;但是对于统计或者批量操作数据时&#xff0c;是否有更好的方案呢&#xff1f;这时候就可以考虑使用多线程编程&#xff0c;异步并行执行多个任…

Flink checkpoint 源码分析- Checkpoint snapshot 处理流程

背景 在上一篇博客中我们分析了代码中barrier的是如何流动改的。Flink checkpoint 源码分析- Checkpoint barrier 传递源码分析-CSDN博客 最后跟踪到了代码org.apache.flink.streaming.runtime.io.checkpointing.CheckpointedInputGate#handleEvent 现在我们接着跟踪相应代…

投资线上黄金是否属于外汇交易?探究黄金与外汇市场的关系

在金融市场中&#xff0c;线上黄金投资和外汇交易都是备受关注的领域。许多人可能会混淆这两者&#xff0c;认为投资线上黄金也是一种外汇交易。但实际上&#xff0c;尽管线上黄金和外汇交易有一些相似之处&#xff0c;但它们在本质上是不同的投资领域。本文将探讨投资线上黄金…

前端 Android App 上架详细流程 (Android App)

1、准备上架所需要的材料 先在需要上架的官方网站注册账号。提前把手机号&#xff0c;名字&#xff0c;身份证等等材料准备好&#xff0c;完成开发者实名认证&#xff1b;软著是必要的&#xff0c;提前准备好&#xff0c;软著申请时间比较长大概需要1-2周时间才能下来&#xf…

流畅的python-学习笔记_序列修改+散列+切片

vector第一版 reprlib.repr用于选取有限长度较长变量 vector第二版切片 注意切片还有indices属性&#xff0c;它可以入参一个序列长度&#xff0c;根据此序列长度&#xff0c;转化不规矩的start stop stride&#xff0c; vector第三版动态存取属性 obj.attra时&#xff0c;先…

构建 imx6ull sd 卡启动

1. 硬件环境 imx6ull 256MB tf 卡 512 MB 的 ddr&#xff1b; ubuntu 20.04&#xff1b; 芯片默认的启动方式是通过 LCD_DATA0 ~ LCD_DATA23&#xff1b;上下拉方式来确认的&#xff1b; 需要注意的上下拉是 BOOT_CFG1[7] BOOT_CFG1[6] BOOT_CFG1[5] 启动选择 和 BOOT_CF…

leetcode-矩阵最长递增路径-102

题目要求 思路 1.通过双循环去把每一个结点作为起始点进行统计&#xff0c;将返回的路径长度存放在res中&#xff0c;取最大的res的长度。 2.递归中需要的几个值&#xff0c;x和y当前结点的坐标&#xff0c;pre用于存储上一个结点的元素值&#xff0c;因为要求是路径上的元素是…

3D 交互展示该怎么做?

在博维数孪&#xff08;Bowell&#xff09;平台制作3D交互展示的流程相对简单&#xff0c;主要分为以下几个步骤&#xff1a; 1、准备3D模型&#xff1a;首先&#xff0c;你需要有一个3D模型。如果你有3D建模的经验&#xff0c;可以使用3ds Max或Blender等软件自行创建。如果没…

前后端分离项目中的一些疑惑

1、前后端分离项目&#xff0c;浏览器发起请求后&#xff0c;请求的是前端服务器还是后端服务器&#xff1f; 在前后端分离的项目中&#xff0c;当浏览器发起请求时&#xff0c;它首先会请求的是前端服务器。 前后端分离的工作流程大致如下&#xff1a; 用户在浏览器中输入网…

Echarts散点图的29个配置项,散点图可以随心所欲啦。

1-9 当使用 ECharts 绘制散点图时&#xff0c;可以配置以下一些常用的选项&#xff1a; 1. tooltip&#xff1a;配置提示框组件&#xff0c;用于显示鼠标悬停在散点上时的提示信息。 2. legend&#xff1a;配置图例组件&#xff0c;用于展示不同散点的标识和名称。 3. xAxis…

图数据库 之 Neo4j 与 AI 大模型的结合绘制知识图谱

引言 随着信息时代的到来&#xff0c;海量的文本数据成为了我们获取知识的重要来源。然而&#xff0c;如何从这些文本数据中提取出有用的信息&#xff0c;并将其以可视化的方式展示出来&#xff0c;一直是一个具有挑战性的问题。近年来&#xff0c;随着人工智能技术的发展&…

rust使用serde_json转换Value为rust中的数据类型

为了方便转换未知json数据&#xff0c;我们可以使用serde提供的value类型来进行转换&#xff0c;将json字符串转化为Value值&#xff0c;然后可以快速使用get方法来获取值&#xff1a; let json_str r#"{"name": "John","age": 30,"c…

科技控必看!让你轻松成为机器人领域达人

科技控们注意了&#xff01;你是不是经常对机器人技术充满无限的好奇&#xff0c;却又因为缺乏合适的渠道而难以深入了解和亲身体验呢&#xff1f;别担心&#xff0c;BFT机器人&#xff0c;正是你探索机器人世界的绝佳之地&#xff01; 在这里&#xff0c;你将发现一个充满惊喜…

政安晨:【Keras机器学习示例演绎】(三十九)—— 使用 FNet 进行文本分类

目录 简介 模型 设置 加载数据集 对数据进行标记 格式化数据集 建立模型 训练我们的模型 与变换器模型比较 政安晨的个人主页&#xff1a;政安晨 欢迎 &#x1f44d;点赞✍评论⭐收藏 收录专栏: TensorFlow与Keras机器学习实战 希望政安晨的博客能够对您有所裨益&…