您的位置:首页 > 编程语言

半透明子窗体MFC实现

2015-03-06 09:55 127 查看
上一篇说了大概的思路,但是写的时候就可能遇到各种问题,下面给出完整的步骤源代码。

先建立一个MFC的对话框程序,然后添加类CTransparentWnd,以下给出改动后的代码。

1、CTransparentWnd类

#pragma once

class CTransparentWnd:public CWnd

{

public:

    CTransparentWnd(void);

    ~CTransparentWnd(void);

public:

    BOOL Create(HWND hpWnd);

public:

    void OnParentMoved();

private:

    BOOL m_bCreated;

};

#include "StdAfx.h"

#include "TransparentWnd.h"

CTransparentWnd::CTransparentWnd(void)

    :m_bCreated(FALSE)

{

}

CTransparentWnd::~CTransparentWnd(void)

{

}

BOOL CTransparentWnd::Create(HWND hpWnd)

{

    LPCTSTR clsName = AfxRegisterWndClass(CS_HREDRAW|CS_VREDRAW,

        0,(HBRUSH)GetStockObject(BLACK_BRUSH));

    if(!CWnd::CreateEx(WS_EX_LAYERED|WS_EX_TOOLWINDOW,

        clsName,NULL,WS_POPUP,0,0,0,0,hpWnd,NULL))

    {

        return FALSE;

    }

    SetLayeredWindowAttributes(0,100,LWA_ALPHA);

    return m_bCreated = TRUE;

}

void CTransparentWnd::OnParentMoved()

{

    if(!m_bCreated)

        return;

    CWnd* ppWnd = this->GetParent();

    CRect rect;

    ppWnd->GetWindowRect(&rect);

    this->MoveWindow(rect.left,rect.top,100,rect.Height());

}

2、生成的主Dlg

// TestDlgDlg.h : 头文件

//

#pragma once

#include "TransparentWnd.h"

// CTestDlgDlg 对话框

class CTestDlgDlg : public CDialogEx

{

private:

    CTransparentWnd m_tranWnd;

// 构造

public:

    CTestDlgDlg(CWnd* pParent = NULL);    // 标准构造函数

// 对话框数据

    enum { IDD = IDD_TESTDLG_DIALOG };

    protected:

    virtual void DoDataExchange(CDataExchange* pDX);    // DDX/DDV 支持

// 实现

protected:

    HICON m_hIcon;

    // 生成的消息映射函数

    virtual BOOL OnInitDialog();

    afx_msg void OnSysCommand(UINT nID, LPARAM lParam);

    afx_msg void OnPaint();

    afx_msg HCURSOR OnQueryDragIcon();

    DECLARE_MESSAGE_MAP()

public:

    afx_msg void OnMove(int x, int y);

};

// TestDlgDlg.cpp : 实现文件

//

#include "stdafx.h"

#include "TestDlg.h"

#include "TestDlgDlg.h"

#include "afxdialogex.h"

#ifdef _DEBUG

#define new DEBUG_NEW

#endif

// 用于应用程序“关于”菜单项的 CAboutDlg 对话框

class CAboutDlg : public CDialogEx

{

public:

    CAboutDlg();

// 对话框数据

    enum { IDD = IDD_ABOUTBOX };

    protected:

    virtual void DoDataExchange(CDataExchange* pDX);    // DDX/DDV 支持

// 实现

protected:

    DECLARE_MESSAGE_MAP()

};

CAboutDlg::CAboutDlg() : CDialogEx(CAboutDlg::IDD)

{

}

void CAboutDlg::DoDataExchange(CDataExchange* pDX)

{

    CDialogEx::DoDataExchange(pDX);

}

BEGIN_MESSAGE_MAP(CAboutDlg, CDialogEx)

END_MESSAGE_MAP()

// CTestDlgDlg 对话框

CTestDlgDlg::CTestDlgDlg(CWnd* pParent /*=NULL*/)

    : CDialogEx(CTestDlgDlg::IDD, pParent)

{

    m_hIcon = AfxGetApp()->LoadIcon(IDR_MAINFRAME);

}

void CTestDlgDlg::DoDataExchange(CDataExchange* pDX)

{

    CDialogEx::DoDataExchange(pDX);

}

BEGIN_MESSAGE_MAP(CTestDlgDlg, CDialogEx)

    ON_WM_SYSCOMMAND()

    ON_WM_PAINT()

    ON_WM_QUERYDRAGICON()

    ON_WM_MOVE()

END_MESSAGE_MAP()

// CTestDlgDlg 消息处理程序

BOOL CTestDlgDlg::OnInitDialog()

{

    CDialogEx::OnInitDialog();

    // 将“关于...”菜单项添加到系统菜单中。

    // IDM_ABOUTBOX 必须在系统命令范围内。

    ASSERT((IDM_ABOUTBOX & 0xFFF0) == IDM_ABOUTBOX);

    ASSERT(IDM_ABOUTBOX < 0xF000);

    CMenu* pSysMenu = GetSystemMenu(FALSE);

    if (pSysMenu != NULL)

    {

        BOOL bNameValid;

        CString strAboutMenu;

        bNameValid = strAboutMenu.LoadString(IDS_ABOUTBOX);

        ASSERT(bNameValid);

        if (!strAboutMenu.IsEmpty())

        {

            pSysMenu->AppendMenu(MF_SEPARATOR);

            pSysMenu->AppendMenu(MF_STRING, IDM_ABOUTBOX, strAboutMenu);

        }

    }

    // 设置此对话框的图标。当应用程序主窗口不是对话框时,框架将自动

    //  执行此操作

    SetIcon(m_hIcon, TRUE);            // 设置大图标

    SetIcon(m_hIcon, FALSE);        // 设置小图标

    // TODO: 在此添加额外的初始化代码

    m_tranWnd.Create(this->m_hWnd);

    m_tranWnd.ShowWindow(SW_SHOW);

    m_tranWnd.OnParentMoved();

    return TRUE;  // 除非将焦点设置到控件,否则返回 TRUE

}

void CTestDlgDlg::OnSysCommand(UINT nID, LPARAM lParam)

{

    if ((nID & 0xFFF0) == IDM_ABOUTBOX)

    {

        CAboutDlg dlgAbout;

        dlgAbout.DoModal();

    }

    else

    {

        CDialogEx::OnSysCommand(nID, lParam);

    }

}

// 如果向对话框添加最小化按钮,则需要下面的代码

//  来绘制该图标。对于使用文档/视图模型的 MFC 应用程序,

//  这将由框架自动完成。

void CTestDlgDlg::OnPaint()

{

    if (IsIconic())

    {

        CPaintDC dc(this); // 用于绘制的设备上下文

        SendMessage(WM_ICONERASEBKGND, reinterpret_cast<WPARAM>(dc.GetSafeHdc()), 0);

        // 使图标在工作区矩形中居中

        int cxIcon = GetSystemMetrics(SM_CXICON);

        int cyIcon = GetSystemMetrics(SM_CYICON);

        CRect rect;

        GetClientRect(&rect);

        int x = (rect.Width() - cxIcon + 1) / 2;

        int y = (rect.Height() - cyIcon + 1) / 2;

        // 绘制图标

        dc.DrawIcon(x, y, m_hIcon);

    }

    else

    {

        CDialogEx::OnPaint();

    }

}

//当用户拖动最小化窗口时系统调用此函数取得光标

//显示。

HCURSOR CTestDlgDlg::OnQueryDragIcon()

{

    return static_cast<HCURSOR>
4000
(m_hIcon);

}

void CTestDlgDlg::OnMove(int x, int y)

{

    CDialogEx::OnMove(x, y);

    // TODO: 在此处添加消息处理程序代码

    this->m_tranWnd.OnParentMoved();

}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息