上次我们学习了如何美化对话框的界面,这次我们为上次的对话框添加两个按钮,一个是关闭按钮,另一个是最小化按钮,好,现在我们先看一下效果:

是不是很难看,因为我们的对话框美化了,所以我们的按钮也要美化,因为采用贴图的方式来美化,所以,我先给出这两个按钮的PNG格式的图片,该图片支持透明色,具体如下:

关闭按钮效果图:

最小化按钮效果图:

这两张效果图是我自己从网上找的,可能不是很合适,但是用来教学,完全没有问题,它们的尺寸都是108*21,每张图片都有四个小图片,第一张和第四张小图片都是透明的,所以看不见效果,我们使用这两张图片来完成按钮的美化,每张图片从左向右有四张小图片,我们只用前三张,分别对应默认状态,焦点状态,按下状态。

下面,我们来说一下如何美化按钮?

第1步,我们先在对话框上放置两个按钮,一个是关闭按钮,另一个是最小化按钮,它们对应的ID分别是IDC_BUTTON_CLOSE和IDC_BUTTON_MIN,然后将我们的按钮设置为自绘制模式,方法如下:

选择按钮,右键属性,在属性列表中找到Owner Draw选项,将其设置为True,效果图如下:

再为它们添加两个成员变量,具体如下:

CButton m_btnClose;

CButton m_btnMin;

第2步,我们新建一个类,继承自CButton,我们取名为CMyButton,为其添加3个成员变量,分别如下:

//按钮背景图像

CImage m_imgButton;

//按钮png路径,包括焦点,正常,按下3个状态

CString m_strImgPath;

//父窗口背景图片背景路径,透明png需要使用

CString m_strImgParentPath;

第3步,我们为CMyButton添加3个成员函数,分别如下:

//设置按钮背景图片路径,父窗口背景图片路径

void SetImagePath(CString strImgPath, CString strParentImgPath);

//初始化按钮,主要是调整按钮的位置,处理透明色

bool InitMyButton(int nX/*左上角X坐标*/, int nY/*左上角Y坐标*/,int nW/*图像宽*/, int nH/*图像高*/, bool bIsPng/*是否是PNG图片*/);

//自绘制函数

void DrawItem(LPDRAWITEMSTRUCT lpDrawItemStruct);

CMyButton的声明最终如下:

class CMyButton : public CButton

{

DECLARE_DYNAMIC(CMyButton)

public:

CMyButton();

virtual ~CMyButton();

//按钮背景图像

CImage m_imgButton;

//按钮png路径,包括焦点,正常,按下3个状态

CString m_strImgPath;

//父窗口背景图片背景路径,透明png需要使用

CString m_strImgParentPath;

//设置按钮背景图片路径,父窗口背景图片路径

void SetImagePath(CString strImgPath, CString strParentImgPath);

//初始化按钮,主要是调整按钮的位置,处理透明色

bool InitMyButton(int nX/*左上角X坐标*/, int nY/*左上角Y坐标*/,int nW/*图像宽*/, int nH/*图像高*/, bool bIsPng/*是否是PNG图片*/);

//自绘制函数

void DrawItem(LPDRAWITEMSTRUCT lpDrawItemStruct);

protected:

DECLARE_MESSAGE_MAP()

};

第4步,我们实现SetImagePath函数,它的功能是为按钮背景图片和父窗口背景图片成员函数初始化,具体如下:

void CMyButton::SetImagePath(CString strImgPath, CString strParentImgPath)

{

m_strImgPath = strImgPath;

m_strImgParentPath = strParentImgPath;

}

第5步,我们实现InitMyButton函数,它的功能是调整按钮在对话框上的位置,其中的参数代表该按钮在父窗口的左上角X坐标,Y坐标,宽度,高度,最后一个参数是为PNG格式图片准备的,如果是PNG带透明色的图片,需要对它进行特殊处理,具体定义如下:

bool CMyButton::InitMyButton(int nX, int nY, int nW, int nH, bool bIsPng)

{

HRESULT hr = 0;

if (m_strImgPath.IsEmpty())

return false;

hr = m_imgButton.Load(m_strImgPath);

if (FAILED(hr))

return false;

if (bIsPng)

{

if (m_imgButton.GetBPP() == 32)

{

int i = 0;

int j = 0;

for (i = 0; i < m_imgButton.GetWidth(); i++)

{

for (j = 0; j < m_imgButton.GetHeight(); j++)

{

byte * pbyte = (byte *)m_imgButton.GetPixelAddress(i, j);

pbyte[0] = pbyte[0] * pbyte[3] / 255;

pbyte[1] = pbyte[1] * pbyte[3] / 255;

pbyte[2] = pbyte[2] * pbyte[3] / 255;

}

}

}

}

MoveWindow(nX,nY,nW,nH);

return true;

}

其中MoveWindow函数是用来调整按钮位置的函数,其中的参数分别代表其在父窗口的左上角X坐标,左上角Y坐标,宽度,高度。

第6步,我们实现DrawItem函数,它是美化Button的核心函数,当我们将Button设置为自绘制后,每次按钮需要刷新,重新绘制的时候,MFC框架会调用它的DrawItem函数,在这个函数中,我们可以根据按钮当前的状态为其贴上相应的背景图。当我们按钮按钮的时候,为其贴上被按下的背景图;当我们的按钮获取焦点的时候,为其贴上获取焦点的背景图;当我们的按钮没有焦点,我们为其贴上默认的背景图片,它们对应的位置前面已经说过。为了避免闪烁,我们采用双缓冲的方式,具体代码如下:

void CMyButton::DrawItem(LPDRAWITEMSTRUCT lpDrawItemStruct)

{

if (!lpDrawItemStruct)

return;

HDC hMemDC;

HBITMAP bmpMem;

HGDIOBJ hOldObj;

bmpMem = CreateCompatibleBitmap(lpDrawItemStruct->hDC, lpDrawItemStruct->rcItem.right - lpDrawItemStruct->rcItem.left, lpDrawItemStruct->rcItem.bottom - lpDrawItemStruct->rcItem.top);

if (!bmpMem)

return;

hMemDC = CreateCompatibleDC(lpDrawItemStruct->hDC);

if (!hMemDC)

{

if (bmpMem)

{

::DeleteObject(bmpMem);

bmpMem = NULL;

}

return;

}

hOldObj = ::SelectObject(hMemDC, bmpMem);

RECT rectTmp = { 0 };

rectTmp = lpDrawItemStruct->rcItem;

MapWindowPoints(GetParent(), &rectTmp);

int nW = lpDrawItemStruct->rcItem.right - lpDrawItemStruct->rcItem.left;

int nH = lpDrawItemStruct->rcItem.bottom - lpDrawItemStruct->rcItem.top;

if (lpDrawItemStruct->itemState & ODS_SELECTED)

{

//按钮被选择

m_imgButton.BitBlt(hMemDC, 0, 0, nW, nH, nW*2, 0, SRCCOPY);

}

else if (lpDrawItemStruct->itemState & ODS_FOCUS)

{

//焦点状态

m_imgButton.BitBlt(hMemDC, 0, 0, nW, nH, nW, 0, SRCCOPY);

}

else

{

//默认状态

CImage imgParent;

imgParent.Load(m_strImgParentPath);

imgParent.Draw(hMemDC, 0, 0, nW, nH, rectTmp.left, rectTmp.top, nW, nH);

m_imgButton.AlphaBlend(hMemDC, 0, 0, nW, nH, 0, 0, nW, nH);

imgParent.Destroy();

}

::BitBlt(lpDrawItemStruct->hDC, 0, 0, nW, nH, hMemDC, 0, 0, SRCCOPY);

SelectObject(hMemDC, hOldObj);

if (bmpMem)

{

::DeleteObject(bmpMem);

bmpMem = NULL;

}

if (hMemDC)

{

::DeleteDC(hMemDC);

hMemDC = NULL;

}

return;

}

这里我们重点说一下默认状态的背景图,因为它是透明的,并且我们采用的是双缓冲,所以,为了避免最终透明色变成黑色,我们先在内存DC上贴上按钮在父窗口位置的背景图,这样可以解决透明色变成黑色的问题,如果你采用GDI+,就不用这么做,但是我们采用的是GDI。

第7步,用CMyButton替代对话框头文件中的CButton。

第8步,在对话框的InitDialog中,对两个按钮进行初始化,具体如下:

m_btnMin.SetImagePath(_T("./res/btn_min.png"), _T("./res/Background.png"));

m_btnMin.InitMyButton(516, 8, 27, 21, true);

m_btnClose.SetImagePath(_T("./res/btn_close.png"),_T("./res/Background.png"));

m_btnClose.InitMyButton(545,8,27,21,true);

第9步,编译程序,最终效果图如下:

今天,我们已经为它添加了最小化,关闭按钮,下次,我们为其添加编辑框!

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持脚本之家。

java如何美化按钮_MFC实现漂亮界面之美化按钮相关推荐

  1. Java Swing 漂亮界面beautyeye_lnf美化包的使用

    Java Swing 漂亮界面beautyeye_lnf美化包的使用 在刚刚开始学Swing时,总觉得Swing做出来的页面太难看了,但是又无可奈何,但现在好了,有了beautyeye_lnf.jar ...

  2. html搜索框美化代码单词,CSS 漂亮搜索框美化代码

    1.美化滚动条       * { & 大家都知道select下拉框是最难美化的.这里有个Jquery的插件可以使下拉框变的魔幻起来. Jquery chosen插件. 美化网页元素3.1 为 ...

  3. 用MFC做漂亮界面之美化对话框

    在windows开发当中做界面的主要技术之一就是使用MFC,通常我们看到的QQ,360,暴风影音这些漂亮的界面都可以用MFC来实现.今天我们来说一下如何用MFC美化对话框,默认情况下,对话框的背景如下 ...

  4. java rcp中lable设置透明_RCP界面美化技术(转)

    Eclipse RCP 界面概览 Eclipse RCP 简介 Eclipse 是一种基于 Java 的可扩展开源开发平台.就其自身而言,它只是一个框架和一组服务,用于通过插件组件构建开发环境.同时也 ...

  5. java相册_java 这是一个漂亮的电子音乐相册JAVA小程序 联合开发网 - pudn.com

    java 所属分类:Java编程 开发工具:Java 文件大小:14337KB 下载次数:4 上传日期:2016-12-01 17:29:09 上 传 者:关关 说明:  这是一个漂亮的电子音乐相册J ...

  6. 用MFC做漂亮界面之登录界面

    转自:https://blog.csdn.net/u011711997/article/details/79375710 前段时间由于工作原因,一直没有更新博客,今天,继续讲解如何用MFC做漂亮界面, ...

  7. java计算器如何实现运算_用java编写了一个模拟计算器的界面设计,怎么实现运算功能呢...

    用java编写了一个模拟计算器的界面设计,怎么实现运算功能呢 2020 - 9 - 16 TAG : view sourceprint?import java.awt.BorderLayout; im ...

  8. Java知多少(84)图形界面之布局设计

    在界面设计中,一个容器要放置许多组件,为了美观,为组件安排在容器中的位置,这就是布局设计.java.awt中定义了多种布局类,每种布局类对应一种布局的策略.常用的有以下布局类: FlowLayout, ...

  9. java swing 创建一个简单的QQ界面

    记录自己用java swing做的第一个简易界面. LoginAction.java package com.QQUI0819;import javax.swing.*; import java.aw ...

最新文章

  1. 2019年终总结:好好爱自己
  2. iOS更改AppIcon
  3. 美团社招Java开发一面,二面,三面,四面合并面经
  4. windows兼容Linux php,支持windows与linux的php计划任务的实现方法
  5. 刚刚,阿里开源了一项重磅炸弹,终结程序员“中年危机”!
  6. hiveserver或者hive启动出现Expected authority at index 7问题解决
  7. 服务性服务–服务到服务的通话
  8. Git : 每一行命令都算数
  9. 灰度董事总经理:BTC突破2万美元并不令人惊讶
  10. JVM笔记——技术点汇总
  11. 转:集群、分布式、负载均衡区别与联系
  12. springmvc执行流程_SpringMVC
  13. java string转number_DataBinding的简单使用(java/kotlin)
  14. xmind8 破解激活教程
  15. VR/AR 技术学习园地
  16. ORACLE 习题(一)
  17. 好客租房153-地图找房模块功能分析
  18. 计算机考研考的是英语作文,2007年考研英语作文真题及范文
  19. 教育网校搭建哪个好?
  20. 阿里云-node服务(一)阿里云 ECS 的Docker法端口映射

热门文章

  1. 91免费视频Redis+Lua解决高并发场景在线秒杀问题
  2. 5g的八大关键指标_2019互联网八大热门话题:总有一个击中你的表达欲
  3. 【初等数论】整除、公约数、同余与剩余系
  4. 新款文章,绝无仅有!微信语音aud文件转换为mp3格式
  5. linux 进程迁移,记一次成功的 linux 系统迁移
  6. 百度世界大会最全官方回顾:今天,百度更懂你!
  7. 并发编程(一)多线程基础和原理
  8. Java变成笔记4:复用类
  9. vc运行库或.net framework装不上的通用解决方法
  10. 2020YKB西医综合全程班资料