MFC对话框里利用CHtmlView加载界面(四)————分层窗口设置


        在学会了 利用CHtmlView 在MFC对话框上显示网页,并支持JavaScript 和 MFC 之间的互相通信后。 当然就想: 我们为什么不能只用HTML 作为前端界面, 而底层用MFC实现逻辑呢? 这样就完全不需要用到MFC对话框的界面风格了。


        本文就讲告诉大家如何实现 用HTML代替MFC的对话框界面。

       首先解决的问题为: 如何使MFC对话框完全被HTML界面覆盖?

        答案就在窗口风格设置上。 

        首先我们消除对话框上方的系统菜单栏:ModifyStyle(WS_CAPTION , 0);

        这里有必要解释下ModifyStyle函数。

     

BOOL ModifyStyle(
   DWORD dwRemove,
   DWORD dwAdd,
   UINT nFlags = 0
);

dwRemove指定在样式修改时要移除的窗口样式。 dwAdd 指定在样式修改时要添加的窗口样式。

ModifyStyle(WS_CAPTION , 0);相当于将WS_CAPTION 风格移除。 此风格为:对话框上方的系统菜单栏,包含了对话框的名称、关闭、最大化、最小化等按钮。

我们只需要上述设置,就可以移除整个系统菜单栏。

  

 这里注意到:系统菜单框 会占据 对话框客户区一定区域,具体为宽度 15,高度 20。

而我们的html界面的宽度为962, 高度632, 所以如果在有菜单栏的风格中,要想将html全面显示,则对话框宽度,高度至少应设置为977, 652.

  消除系统菜单栏后,再用ModifyStyleEx( WS_EX_DLGMODALFRAME, 0) 消除对话框四边的双边,即上图的红色标记部分。

消除后如图:



这双边去除后,可以看到界面上多余了一部分对话框,这是就需要我们设置对话框框的大小,刚好为html界面大小。

如下图,这样就将html完全覆盖了对话框界面。



但是仅仅这样做时,我们发现在将界面最小化后再次弹出时,界面会出现闪烁。我分析闪烁的根本原因为:MFC对话框要先绘制背景,然后再绘制html,这样就会出现闪烁。

故,利用windows分层窗口( LayeredWindows)来将背景对话框透明化,这样就能避免闪烁了。

具体的步骤如下:

一:设置窗口风格为分层窗口(WS_EX_LAYERED):

   有两种方法可以设置窗口属性:

   方法一:

    ModifyStyleEx(0,WS_EX_LAYERED); //设置窗口扩展风格为:分层窗口

   方法二:

    SetWindowLong(GetSafeHwnd(),GWL_EXSTYLE,WS_EX_LAYERED);

   当设置了窗口风格为分层窗口后, 如果你未调用SetLayeredWindowAttributesUpdateLayeredWindow为其设置透明情况,那么默认将为全透明,不会弹出任何窗口。

二:设置背景透明属性

::SetLayeredWindowAttributes(GetSafeHwnd(),RGB(255, 0, 255), 255,LWA_COLORKEY); //将背景颜色为RGB(255, 0, 255)透明化

或:

this->SetLayeredWindowAttributes(RGB(255, 0, 255), 255, LWA_COLORKEY );//将背景颜色为RGB(255, 0, 255)透明化

三:设置对话框背景颜色

   SetLayeredWindowAttributes中,有一项为设置透明颜色, 表示在绘制对话框背景时,如果为透明颜色,则让其透明。 这就需要我们在背景绘制时,将其绘制为透明颜色,使其透明。

 设置对话框背景的方式:

 在OnPaint函数中:


voidCMFCHtmlTest1Dlg::OnPaint()

{

    if (IsIconic())

    {

        。。。

    }

    else

    {

        CPaintDCdc(this);

        RECTrect;

        GetClientRect(&rect);

        dc.FillSolidRect(&rect,RGB(255, 0, 255));  //设置对话框背景颜色

 

        CDialogEx::OnPaint();

    }

}


未透明 和 透明窗口 效果如图:




利用分层窗口,我们就解决了弹出界面闪烁问题。

最终这些设置我都在OnInitDialog()完成:

BOOLCMFCHtmlTest1Dlg::OnInitDialog()

{

    CDialogEx::OnInitDialog();

 

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

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

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

    ASSERT(IDM_ABOUTBOX < 0xF000);

 

    CMenu*pSysMenu = GetSystemMenu(FALSE);

    if (pSysMenu !=NULL)

    {

        BOOLbNameValid;

        CStringstrAboutMenu;

        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: 在此添加额外的初始化代码

    ModifyStyle(WS_CAPTION , 0); //移除对话框 上方的系统菜单栏

    ModifyStyleEx(WS_EX_DLGMODALFRAME, 0);//分层窗口,并且不在任务栏里显示,不带双边

    SetWindowLong(GetSafeHwnd(),GWL_EXSTYLE,WS_EX_LAYERED);

   

    CRectrtDesk;

    GetWindowRect(rtDesk);

    MoveWindow(rtDesk.left,rtDesk.top,width, height);


    this->SetLayeredWindowAttributes(RGB(255, 0, 255), 255, LWA_COLORKEY );

 

    m_HtmlView.CreateFromStatic(IDC_STATIC1,this); //加载html

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

}




猜你喜欢

转载自blog.csdn.net/qq_20828983/article/details/72654784