65.9K
CodeProject 正在变化。 阅读更多。
Home

WTL 头像控件

starIconstarIconstarIcon
emptyStarIcon
starIcon
emptyStarIcon

3.62/5 (8投票s)

2007年11月8日

CPOL

2分钟阅读

viewsIcon

38110

downloadIcon

785

WTL 控件,用于显示全彩和灰度图片,并支持缩放和保存结果文件。

Screenshot - avatar-demo.png

Screenshot - avatar-demo2.png

引言

这是我在 The Code Project 上的第一篇文章,希望对该网站的其他读者有所帮助。本文介绍了一个简单的控件,用于显示全彩和转换(例如灰度化)的图片,并支持调整大小和保存结果文件。本文的代码可以作为图片转换的示例。

特点

  • 支持不同格式的图像(BMP、GIF、PNG、JPEG、JPG)
  • 允许将原始图片调整为实际控件大小
  • 允许用户通过过滤器生成不同的图像
  • 具有将结果图片保存到文件的功能

背景

欢迎具备在 WTL 中处理 Windows 事件的基本知识。

Using the Code

该控件使用 Visual Studio 2003 和 WTL 7.1 开发。它仅在 Windows XP 下进行了测试。代码基于 GDI+ 技术构建,因此需要 gdiplus.dll

  • 将以下文件复制到您的应用程序目录,然后将其添加到您的项目中
    • wtl_avatar_control.h
    • wtl_avatar_control.cpp
  • 在对话框类的定义文件中插入 #include "wtl_avatar_control.h"
  • 将一个新的成员变量添加到对话框类

    //
    CStaticAvatar m_wndPicture;
    //
  • 子类化任何控件(通常是静态控件,例如 IDC_PICTURE),您希望在其中显示头像图片。一个好的位置是在 OnInitDialog 方法中。

    ///
    m_wndPicture.SubclassWindow(GetDlgItem(IDC_PICTURE));
    SendMessage(GetDlgItem(IDC_RADIO1),
        (UINT) BM_SETCHECK, (WPARAM)BST_CHECKED, (LPARAM)0);
    m_wndPicture.SetCurrentPictureID(0);
    //

类图

Class diagramm

序列图

Class diagramm

关注点

示例的主要功能集中在 CAvatarProcessor 类和一组过滤器 CImageFilter 中。CAvatarProcessor 提供了将不同过滤器应用于图像的能力,从而获得不同的结果图片。CStaticAvatar 使用 CAvatarPicture 的单个实例,但准备并应用了许多图像过滤器以获得不同的效果。对于原始图像的操作,使用 ATL::CImage 类。创建“禁用”图像已实现为复合过滤器 CImageFilterDisable

  1. 使用 CImageFilterStretch 将图像调整为实际控件大小,并使用 WHITEONBLACK 作为 SetStretchBltMode() 方法的参数。

    void CImageFilterDisable::Apply(ImageFilterData* pData)
    {
    m_stretch.SetStretchBltMode(WHITEONBLACK);
    m_stretch.Apply(pData);
    m_color.SetColor(CImageFilterColor::eGrey);
    m_color.Apply(pData);
    };
  2. 其他颜色过滤器实现为具有不同支持颜色的单个类。

    Screenshot - avatar-demo3.png

    enum eColor {eNone =0, eRed, eGreen, eBlue, eGrey};
    void CImageFilterColor::Apply(ImageFilterData* pData)
    {
        if(m_Color == eNone || !pData)
            return;
    
        byte clr=0;
        COLORREF px = RGB(0,0,0);
        for(int x=0;xrcClient.Width();x++)
        {
            for(int y=0;yrcClient.Height();y++)
            {
                px = pData->dc.GetPixel(x,y);
                switch(m_Color)
                {
                case eRed:   
                    clr = GetRValue(px); 
                    px = RGB(clr,0,0);
                    break;
                case eGreen: 
                    clr = GetGValue(px); 
                    px = RGB(0,clr,0);
                    break;
                case eBlue:  
                    clr = GetBValue(px); 
                    px = RGB(0,0,clr);
                    break;
                case eGrey:  
                    clr = (GetRValue(px)+GetGValue(px)+GetBValue(px))/3; 
                    px = RGB(clr,clr,clr);
                    break;
                }
                pData->dc.SetPixelV(x,y,px);
            }
        };
    };
  3. ImageFilters 系统实现了“策略”模式,其中 CImageFilter 类是抽象策略,而 ImageFilterData 保持处理状态。

历史

  • 2007 年 11 月 8 日 -- 发布原始版本
  • 版本 1.1 -- 更新了 CAvatarPicture 的实现,使其能够获得更灵活的代码
© . All rights reserved.