C++ 重载EditBox默认ContextMenu(含详细代码)

2023-10-14 04:59

本文主要是介绍C++ 重载EditBox默认ContextMenu(含详细代码),希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

本人微信公众号:CPP进阶之旅
如果觉得这篇文章对您有帮助,欢迎关注 “CPP进阶之旅” 学习更多技术干货

C++ 重载EditBox默认ContextMenu

      • 问题背景
      • 自定义右键菜单
      • 重载系统默认右键菜单
      • 参考资料
      • 重要说明

问题背景

      在做windows下的C++客户端程序开发的时候,经常会遇到自定义右键菜单的功能点的开发。
      这时候,我们一般只需要在窗口的事件过程中处理WM_CONTEXTMENU消息。处理时,根据需要可以使用CreatePopupMenu创建弹出菜单,并插入指定的子菜单项,最后处理对应菜单项的消息这样的流程来实现一个自定义的右键菜单列表。也可以通过拿到菜单项的句柄,枚举并修改菜单列表的形式重载一些已经实现的或者已经定义的菜单列表。
      之前遇到一个需求,需要继承Edit默认的右键菜单,在此基础上添加一些自定义的右键菜单项。然而,按照之前的理解,写代码的过程中发现,WM_CONTEXTMENU消息触发的时候,不能获取到默认的右键菜单句柄信息,也就拿不到右键菜单中的菜单列表条目。因此也不能继续进行右键菜单项的自定义操作。下面用代码演示一下,一般自定义右键菜单的方法和在editbox中实现重载默认Context的方法。

自定义右键菜单

在这里用代码表示一般的右键菜单创建和处理的过程:

//编辑框事件处理
#define EDIT_NEW_MENU_ITEM WM_USER + 800
static LRESULT CALLBACK WndProcForEditCtrl(HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam) {switch (message) {case WM_CONTEXTMENU: {//创建菜单项列表HMENU popup = CreatePopupMenu();WCHAR temp[50] = {0};wcscpy(temp, L"自定义菜单");AppendMenu(popup, MF_STRING, (UINT_PTR)EDIT_NEW_MENU_ITEM, tmp);POINT pt = {GET_X_LPARAM(lParam), GET_Y_LPARAM(lParam)};TrackPopupMenu(popup, TPM_LEFTALIGN | TPM_LEFTBUTTON | TPM_RIGHTBUTTON, pt.x,pt.y, 0,hwnd, nullptr);return true;}break;case EDIT_NEW_MENU_ITEM:{//根据具体的需求处理消息}break;default:break;}return DefWindowProc(hwnd, message, wParam, lParam);
}

重载系统默认右键菜单

//获取列表中pos处的菜单项
MENUITEMINFO GetMenuInfoByPosition(HMENU menu, UINT nPos) {TCHAR szMenuStr[256] = {0};MENUITEMINFO mInfo = {0};mInfo.cbSize = sizeof(mInfo);mInfo.fMask = 0 |MIIM_CHECKMARKS | MIIM_DATA | MIIM_ID | MIIM_STATE | MIIM_SUBMENU| MIIM_TYPE| 0;mInfo.dwTypeData = szMenuStr;mInfo.cch = _countof(szMenuStr);GetMenuItemInfo(menu, nPos, TRUE, &mInfo);return mInfo;
}#define EDIT_NEW_MENU_ITEM WM_USER + 800
static bool isInitMenu = true;
static LRESULT CALLBACK WndProcForEditCtrl(HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam) {switch (message) {case WM_CONTEXTMENU: {isInitMenu = true;} break;case WM_ENTERIDLE: {if (wParam == MSGF_MENU) {//表示为菜单消息,当wParam为MSGF_DIALOGBOX表示的是对话框消息//这里表示菜单进入空闲状态if (isInitMenu) {isInitMenu = false;MENUBARINFO mbi;memset(&mbi, 0, sizeof(MENUBARINFO));mbi.cbSize = sizeof(MENUBARINFO);GetMenuBarInfo((HWND)lParam, OBJID_CLIENT, 0, &mbi);if (::IsMenu((HMENU)mbi.hMenu)) {for (int i = 0; i < GetMenuItemCount(mbi.hMenu) - 1; i++) {MENUITEMINFO menuInfo = GetMenuInfoByPosition(mbi.hMenu, i);auto aa = menuInfo.dwTypeData;if (str::Len(menuInfo.dwTypeData)) {WCHAR menuName[50] = {0};wcscpy(menuName, menuInfo.dwTypeData);win::menu::SetText(mbi.hMenu, menuInfo.wID, menuName);}}WCHAR menuStr[50] = {0};wcscpy(menuStr, L"自定义菜单");AppendMenu(mbi.hMenu, MF_STRING, (UINT_PTR)9000, menuStr);}}}} break;default:break;}return DefWindowProc(hwnd, message, wParam, lParam);
}

参考资料

https://stackoverrun.com/cn/q/1566456
https://docs.microsoft.com/en-us/troubleshoot/cpp/cannot-change-state-menu-item

重要说明

欢迎关注我的个人微信公众号,查看专业的客户端/服务端开发知识、笔试面试题目、程序员职场经验与心得分享。
在这里插入图片描述

这篇关于C++ 重载EditBox默认ContextMenu(含详细代码)的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/208322

相关文章

springboot集成Lucene的详细指南

《springboot集成Lucene的详细指南》这篇文章主要为大家详细介绍了springboot集成Lucene的详细指南,文中的示例代码讲解详细,具有一定的借鉴价值,感兴趣的小伙伴可以跟随小编一起... 目录添加依赖创建配置类创建实体类创建索引服务类创建搜索服务类创建控制器类使用示例以下是 Spring

Flutter实现文字镂空效果的详细步骤

《Flutter实现文字镂空效果的详细步骤》:本文主要介绍如何使用Flutter实现文字镂空效果,包括创建基础应用结构、实现自定义绘制器、构建UI界面以及实现颜色选择按钮等步骤,并详细解析了混合模... 目录引言实现原理开始实现步骤1:创建基础应用结构步骤2:创建主屏幕步骤3:实现自定义绘制器步骤4:构建U

SpringBoot中四种AOP实战应用场景及代码实现

《SpringBoot中四种AOP实战应用场景及代码实现》面向切面编程(AOP)是Spring框架的核心功能之一,它通过预编译和运行期动态代理实现程序功能的统一维护,在SpringBoot应用中,AO... 目录引言场景一:日志记录与性能监控业务需求实现方案使用示例扩展:MDC实现请求跟踪场景二:权限控制与

C#如何调用C++库

《C#如何调用C++库》:本文主要介绍C#如何调用C++库方式,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地方,望不吝赐教... 目录方法一:使用P/Invoke1. 导出C++函数2. 定义P/Invoke签名3. 调用C++函数方法二:使用C++/CLI作为桥接1. 创建C++/CL

IntelliJ IDEA 中配置 Spring MVC 环境的详细步骤及问题解决

《IntelliJIDEA中配置SpringMVC环境的详细步骤及问题解决》:本文主要介绍IntelliJIDEA中配置SpringMVC环境的详细步骤及问题解决,本文分步骤结合实例给大... 目录步骤 1:创建 Maven Web 项目步骤 2:添加 Spring MVC 依赖1、保存后执行2、将新的依赖

利用Python调试串口的示例代码

《利用Python调试串口的示例代码》在嵌入式开发、物联网设备调试过程中,串口通信是最基础的调试手段本文将带你用Python+ttkbootstrap打造一款高颜值、多功能的串口调试助手,需要的可以了... 目录概述:为什么需要专业的串口调试工具项目架构设计1.1 技术栈选型1.2 关键类说明1.3 线程模

Python Transformers库(NLP处理库)案例代码讲解

《PythonTransformers库(NLP处理库)案例代码讲解》本文介绍transformers库的全面讲解,包含基础知识、高级用法、案例代码及学习路径,内容经过组织,适合不同阶段的学习者,对... 目录一、基础知识1. Transformers 库简介2. 安装与环境配置3. 快速上手示例二、核心模

如何为Yarn配置国内源的详细教程

《如何为Yarn配置国内源的详细教程》在使用Yarn进行项目开发时,由于网络原因,直接使用官方源可能会导致下载速度慢或连接失败,配置国内源可以显著提高包的下载速度和稳定性,本文将详细介绍如何为Yarn... 目录一、查询当前使用的镜像源二、设置国内源1. 设置为淘宝镜像源2. 设置为其他国内源三、还原为官方

最详细安装 PostgreSQL方法及常见问题解决

《最详细安装PostgreSQL方法及常见问题解决》:本文主要介绍最详细安装PostgreSQL方法及常见问题解决,介绍了在Windows系统上安装PostgreSQL及Linux系统上安装Po... 目录一、在 Windows 系统上安装 PostgreSQL1. 下载 PostgreSQL 安装包2.

Java的栈与队列实现代码解析

《Java的栈与队列实现代码解析》栈是常见的线性数据结构,栈的特点是以先进后出的形式,后进先出,先进后出,分为栈底和栈顶,栈应用于内存的分配,表达式求值,存储临时的数据和方法的调用等,本文给大家介绍J... 目录栈的概念(Stack)栈的实现代码队列(Queue)模拟实现队列(双链表实现)循环队列(循环数组