恒美微站 Logo 恒美微站
  • 首页
  • 关于我们
  • 建站服务
  • 主题模板
  • 案例展示
  • 资讯中心
  • 联系我们

记录使用 MFC 打开文件对话框读取一张图片并做简单的灰度转换算法简单学习过程

  • 首页
  • 资讯中心
  • /
  • 记录使用 MFC 打开文件对话框读取一张图片并做简单的灰度转换算法简单学习过程

相关资讯

2026年折叠电钢琴选购指南:4款特伦斯型号参数横评+场景化选型方案 2026/8/26 18:02:23
【阅读笔记】基于残差信息的上采样Fast Image/Video Upsampling 2026/8/26 17:57:22
SA8303 2.0‑7.5V 2.5A 单通道 H 桥电机驱动芯片|电池供电直流有刷电机驱动方案 2026/8/26 17:57:22

最新资讯

TVA-World具身智能的跨代际协同演化研究
RK3568_Android15实现从App调用到内核接口的全系统开发----操作GPIO控制LED
RK3568 Android 13 移植 EC20-CE 4G 模块全记录
Spring Boot中编写单元测试
YOLO 小目标涨点|2504 张输电线路销钉绝缘子 4 类 VOC/YOLO 数据集,无人机电力缺陷检测落地全流程
NVIDIA ACE-RTL 论文精读:RTL 专用模型进入 Agent 闭环,为什么能把 Spec-to-RTL APR 推到 96.15%?

今日推荐

Python random 模块常用函数详解:从入门到实战
Hermes接入团队协作后,我推翻了三个效率假设
免费AI大模型调教指南:打造专属网文写作助手

本周热门

Nextcloud 桌面客户端:把同步交给它,你只管改文件
如何将 HTML 转成 Word 文档且格式不丢失?html-to-docx 使用教程
Anki 批量操作卡片完整指南:一次搞定上千张,不再逐张修改

本月精选

如何用DamaiHelper实现演唱会门票的智能自动化抢购:完整技术解决方案指南
第4篇:59 倍性能差距的索引瓶颈定位——一次教科书级的全表扫描调优
终极歌词批量下载神器:5分钟解决离线音乐库歌词同步难题

记录使用 MFC 打开文件对话框读取一张图片并做简单的灰度转换算法简单学习过程

发布时间:2026/8/26 18:02:23
记录使用 MFC 打开文件对话框读取一张图片并做简单的灰度转换算法简单学习过程 由于刚开始接触MFC做一个简单的图片读取并且转成灰度图同时进行边缘检测任务后续可能在此基础上在进行改进我目前做的是直接用代码生成一个对话框不是在资源里面添加对话框一、创建VS程序首先创建一个文件打开事件处理程序这样就可以使用文件下面的打开按钮打开一张自己想要的图片在资源文件中右键查看.rc代码右键双击打开→添加事件处理程序→选择View接下来就可以在这里面操作了首先我随便响应了一个AfxMessageBox消息框来验证是否成功在这里还需要将字符集改成多字节字符集右键→属性→高级自己的想法在做一些简单的图像算法处理的时候我将对话框和图像算法的代码都放在imageshowView.cpp里面进行操作这样操作不好的一个地方是所有代码都在同一个地方非常乱不方便后续操作因此在这个基础上进行了改进对话框和图像算法都单独作为.cpp来进行创建然后再在imageshowView.cpp进行调用展示即可。补充一下自己的做法这种做法感觉有点复杂void CimageshowView::OnDraw(CDC* pDC) { CimageshowDoc* pDoc GetDocument(); ASSERT_VALID(pDoc); if (!pDoc) return; if (0 s_fOpenFile) { return; } BITMAPINFO bmi; memset(bmi, 0, sizeof(BITMAPINFO)); bmi.bmiHeader.biSize sizeof(BITMAPINFOHEADER); bmi.bmiHeader.biWidth img_w; bmi.bmiHeader.biHeight img_h; bmi.bmiHeader.biPlanes 1; bmi.bmiHeader.biBitCount 24; bmi.bmiHeader.biCompression BI_RGB; SetDIBitsToDevice( pDC-m_hDC, 0, 0, img_w, img_h, 0, 0, 0, img_h, img_rgb, bmi, DIB_RGB_COLORS); } void RgbToYuv(int w, int h, BYTE* imgRGB1, BYTE* imgGray1) { BYTE* pSrc imgRGB1; BYTE* pDst imgGray1; for (int y 0; y h; y) { for (int x 0; x w; x) { int B pSrc[0]; int G pSrc[1]; int R pSrc[2]; int Y (int)(0.299 * R 0.587 * G 0.114 * B); pDst[0] Y; pDst[1] Y; pDst[2] Y; pSrc 3; pDst 3; } } } void EdgeDetect(SIZE sz, PBYTE pSrcGray, PBYTE pDstGray) { ASSERT(pSrcGray); ASSERT(pDstGray); int w sz.cx; int h sz.cy; /*memset(pDstGray, 0, w * h);*/ for (int y 1; y h - 1; y) { for (int x 1; x w - 1; x) { int v00 pSrcGray[(y - 1) * w (x - 1)]; int v01 pSrcGray[(y - 1) * w x]; int v02 pSrcGray[(y - 1) * w (x 1)]; int v10 pSrcGray[y * w (x - 1)]; int v11 pSrcGray[y * w x]; int v12 pSrcGray[y * w (x 1)]; int v20 pSrcGray[(y 1) * w (x - 1)]; int v21 pSrcGray[(y 1) * w x]; int v22 pSrcGray[(y 1) * w (x 1)]; int g 4 * v11 - v01 - v10 - v12 - v21; if (g 0) g -g; if (g 255) g 255; pDstGray[y * w x] (BYTE)g; } } } void ShowEdgeImage(PSTR lpszTitle, SIZE sz, PBYTE pRGB) { ASSERT(pRGB); int w sz.cx; int h sz.cy; int img_size w * h; ASSERT(w IMG_MAX_WIDTH h IMG_MAX_HEIGTH img_size IMG_MAX_SIZE); static BYTE s_pGray[IMG_MAX_SIZE]; static BYTE s_pEdge[IMG_MAX_SIZE]; static BYTE s_pEdgeRGB[IMG_MAX_SIZE * 3]; PBYTE pGray s_pGray; PBYTE pEdge s_pEdge; RgbToYuv(w, h, pRGB, s_pEdgeRGB); for (int i 0; i img_size; i) { pGray[i] s_pEdgeRGB[i * 3]; } EdgeDetect(sz, pGray, pEdge); for (int i 0; i img_size; i) { BYTE e pEdge[i]; s_pEdgeRGB[i * 3 0] e; s_pEdgeRGB[i * 3 1] e; s_pEdgeRGB[i * 3 2] e; } CImageDlg dlg(AfxGetMainWnd(), lpszTitle, sz, s_pEdgeRGB, 24); dlg.DoModal(); }对上述进行了改进二、将一幅彩色图像转换为灰度图像并显示1、单独创建一个对话框用来显示各种图片imgdlg.cpp和imgdlg.h.cppCImageDlg::CImageDlg(CWnd* pParent, PSTR lpszTitle, SIZE sz, PBYTE pImg, int nBPP) : CDialog() { m_pWndFocus GetFocus(); // 保存当前焦点窗口关闭时还原 int cbBytes sizeof(DLGTEMPLATE) 4096; // 在内存中构造一个对话框模板 m_hdt GlobalAlloc(GMEM_FIXED, cbBytes); // GMEM_FIXED分配固定地址内存 DLGTEMPLATE* pdt (DLGTEMPLATE*)GlobalLock(m_hdt); // 锁定内存并获得可写指针 memset(pdt, 0, cbBytes); pdt-style DS_MODALFRAME | WS_POPUP | WS_CAPTION | WS_SYSMENU; pdt-dwExtendedStyle 0; GlobalUnlock(m_hdt); strcpy_s(m_szTitle, lpszTitle); // 安全版本保存标题到成员变量 m_szImg sz; ASSERT(8 nBPP || 24 nBPP); m_nBPP nBPP; // 保存图像位深 int rgb_bytes sz.cx * sz.cy * 3; m_pRGB (PBYTE)malloc(rgb_bytes); ASSERT(m_pRGB); memcpy(m_pRGB, pImg, rgb_bytes); // 复制图像数据到成员缓冲区 BOOL code InitModalIndirect(m_hdt, pParent); // 初始化模态对话框 // 构造右键弹出菜单 m_menuCmd.CreatePopupMenu(); // 循环数组总字节数 / 单个元素字节数 元素个数 for (int i 0; i sizeof(menuid) / sizeof(menuid[0]); i) { PPOPUPMENUID lpmi menuid[i]; // 取得当前菜单项的指针 int flag MF_BYPOSITION | lpmi-nFlag; // 插入菜单项后面在OnRButtonDown里会被弹出显示 m_menuCmd.InsertMenu(0, flag, lpmi-idCmd, lpmi-lpszItem); } } CImageDlg::~CImageDlg() { if (m_pRGB) { free(m_pRGB); m_pRGB 0; } m_menuCmd.DestroyMenu(); if (m_hdt) { GlobalFree(m_hdt); } }2、简单的图像处理算法方案一单独创建RgbToYuv.cpp的代码如下.h我想的是直接在.cpp里面创建一个类来继承CImageDlg然后在view.cpp里面进行调用这样写出来又存在一个问题每次使用时都得写一个DoModal()来调用对话框而且前面我已经写了一个对话框来显示图片了所以这里就很多余我又进行了改进方案二RgbToYuv.cppRgbToYuv.hview.cpp这样写下来和方案一差不多每次都在调用方案三最佳RgbToYuv.cpp.hview.cpp这种方案就直接在view.cpp中调用RgbToYuv和ShowGrayImage函数来显示对话框里面的图像了就不用像之前两种方案里面那样每次都得调用一个对话框。运行结果如下总结在学习这个之前得先了解c和mfc的一些相关知识不然就会搞得很复杂没有逻辑。如果有更好的解决办法可以多多交流

关于恒美微站

恒美微站专注于为个体商户、工作室提供极简自助建站服务,让每个人都能轻松拥有专业网站。

快速链接

  • 关于我们
  • 建站服务
  • 主题模板
  • 案例展示
  • 资讯中心

服务项目

  • 可视化建站
  • 拖拽编辑
  • 主题定制
  • SEO 优化
  • 网站托管

联系方式

  • 📍 地址:北京市朝阳区建国路 88 号
  • 📞 电话:400-888-8888
  • ✉️ 邮箱:info@hmyw.cn
  • 🕐 时间:周一至周日 9:00-18:00

© 2024 恒美微站 hmyw.cn 版权所有 | 京 ICP 备 12345678 号