• 【Win32】通过多线程自动关闭对话框的方法


    零、需求

    • 希望在Windows开机后自动弹出个对话框提示一下,过8秒后自动关闭

    一、解决

    1.建项目和源文件

    • 在VC6.0中新建Win32项目
      新建Win32项目1
      新建Win32项目2

    • 新建C++源文件
      新建C++源文件

    2.编写代码

    • 基础结构
    #include <windows.h>
    
    int WINAPI WinMain (HINSTANCE hInstance, HINSTANCE hPrevInstance, PSTR szCmdLine, int iCmdShow) 
    { 
        return 0; 
    }
    
    • 添加弹窗
    #include <windows.h>
    
    int WINAPI WinMain (HINSTANCE hInstance, HINSTANCE hPrevInstance, PSTR szCmdLine, int iCmdShow) 
    { 
        if(IDCANCEL == MessageBox(NULL, TEXT ("弹窗消息"), TEXT ("弹窗1"), MB_OKCANCEL))
        {
              //如果点击了取消
              MessageBox (NULL, TEXT ("弹窗消息"), TEXT ("弹窗2"), MB_OK);
        }
        return 0; 
    }
    
    • 添加多线程
    #include <windows.h>
    
    // 线程的运行函数
    DWORD WINAPI CloseDialog(LPVOID param)
    {
        ExitThread(0); 
        return 0;
    }
    
    int WINAPI WinMain (HINSTANCE hInstance, HINSTANCE hPrevInstance, PSTR szCmdLine, int iCmdShow) 
    { 
        DWORD parameter = 0;
        DWORD id;
        //创建线程
        CreateThread(NULL, 0, (LPTHREAD_START_ROUTINE)CloseDialog, &parameter, 0, &id);
    
        if(IDCANCEL == MessageBox(NULL, TEXT ("弹窗消息"), TEXT ("弹窗1"), MB_OKCANCEL))
        {
              //如果点击了取消
              MessageBox (NULL, TEXT ("弹窗消息"), TEXT ("弹窗2"), MB_OK);
        }
        return 0; 
    }
    
    • 完善关闭功能
    #include <windows.h>
    
    static TCHAR title[] = TEXT ("弹窗1");
    
    // 线程的运行函数
    DWORD WINAPI CloseDialog(LPVOID param)
    {
        //休眠8000ms
        Sleep(8000);
        HANDLE hWnd = ::FindWindowEx(NULL, NULL, NULL,title);
        if (hWnd)
        {
              //关闭对话框
              ::EndDialog((HWND)hWnd, IDNO);
        }
        ExitThread(0); 
        return 0;
    }
    
    int WINAPI WinMain (HINSTANCE hInstance, HINSTANCE hPrevInstance, PSTR szCmdLine, int iCmdShow) 
    { 
        DWORD parameter = 0;
        DWORD id;
        //创建线程
        CreateThread(NULL, 0, (LPTHREAD_START_ROUTINE)CloseDialog, &parameter, 0, &id);
    
        if(IDCANCEL == MessageBox(NULL, TEXT ("8秒后关闭"), title, MB_OKCANCEL))
        {
              //如果点击了取消
              MessageBox (NULL, TEXT ("不会关闭"), TEXT ("弹窗2"), MB_OK);
        }
        return 0; 
    }
    

    3.效果

    • 窗口
      窗口
      什么都不做8s后自动关闭,点确认后立即关闭,点取消后立即关闭并且弹出窗口2,窗口2不会自动关闭。

    二、总结

    下面的内容收集自互联网。

    1.CreateThread

    产生一个线程(并因而成就一个多线程程序),是以CreateThread()作为一切行动的开始。

    原型

    HANDLE CreateThread(
     LPSECURITY_ATTRIBUTES lpThreadAttributes, 
     SIZE_T dwStackSize, 
     LPTHREAD_START_ROUTINE lpStartAddress, 
     LPVOID lpParameter, 
     DWORD dwCreationFlags, 
     LPDWORD lpThreadId 
    );
    

    参数

    lpThreadAttributes:描述施行于这一新线程的security属性。NULL表示使用缺省值。

    dwStatckSize : 新线程拥有自几的堆栈,0表示使用缺省大小。

    lpStartAddress: 新线程将开始的起始地址,这是一个函数指针(在C语言中函数名成即代表函数指针)。

    lpParameter:此值将被传送到上述所指定的新线程函数去,作为参数(唯一的参数)。

    dwCreationFlags:允许你产生一个暂时挂起的线程,默认情况是“立即开始执行”。

    lpThreadId :新线程的ID会被传回到这里。

    返回值

    如果CreateThread()成功,传回一个handle,代表新线程,否则传回一个FALSE。如果失败,你可以调用GetLastError()获知原因。

    2.MessageBox

    弹出一个对话框。

    原型

    int MessageBox(          
        HWND hWnd,
        LPCTSTR lpText,
        LPCTSTR lpCaption,
        UINT uType
    );
    

    参数

    hWnd
    处理要创建的消息框的所有者窗口。如果该参数为空,则消息框没有所有者窗口。
    lpText
    指向一个包含要显示的消息的null终止字符串的指针
    lpCaption
    指向一个包含对话框标题的空终止字符串的指针。如果该参数为空,则使用默认的标题Error。
    uType
    指定对话框的内容和行为。这个参数可以是来自以下几组标志的组合。要指出在消息框中显示的按钮。

    按钮

    MB_OK
    默认值。有一个确认按钮在里面。
    MB_YESNO
    有是和否在里面。
    MB_ABORTRETRYIGNORE
    有Abort(放弃),Retry(重试)和Ignore(跳过)
    MB_YESNOCANCEL
    消息框含有三个按钮:Yes,No和Cancel
    MB_RETRYCANCEL
    有Retry(重试)和Cancel(取消)
    MB_OKCANCEL
    消息框含有两个按钮:OK和Cancel

    图标

    X 错误 MB_ICONHAND、MB_ICONSTOP、MB_ICONERROR
    ? 询问 MB_ICONQUESTION
    ! 警告 MB_ICONEXCLAMATION、MB_ICONWARNING
    i 信息 MB_ICONASTERISK、MB_ICONINFORMATION
    上面这些东西在msdn可以看到。

    返回值

    如果一个消息框有一个取消按钮,那么如果按下ESC键或者取消了取消按钮,函数将返回IDCANCEL值。
    如果消息框没有取消按钮,按ESC键就没有效果。
    如果函数失败,则返回值为0。
    如果函数成功,则返回值是下列菜单项的值之一。
    IDABORT Abort按钮被选中。
    IDCANCEL Cancel按钮被选中。
    IDCONTINUE Continue按钮被选中。
    IDIGNOR EIgnore按钮被选中。
    IDNO No按钮被选中。
    IDOK OK按钮被选中。
    IDRETRY Retry按钮被选中。
    IDYES Yes按钮被选中。

    3.FindWindowEx

    在窗口列表中寻找与指定条件相符的第一个子窗口 。
    该函数获得一个窗口的句柄,该窗口的类名和窗口名与给定的字符串相匹配。这个函数查找子窗口,从排在给定的子窗口后面的下一个子窗口开始。在查找时不区分大小写。

    原型

    HWND FindWindowEx(
    HWND hwndParent, 
    HWND hwndChildAfter,
    LPCTSTR lpszClass,
    LPCTSTR lpszWindow
    );
    

    参数

    hwndParent:要查找的子窗口所在的父窗口的句柄(如果设置了hwndParent,则表示从这个hwndParent指向的父窗口中搜索子窗口)。
    如果hwndParent为 0 ,则函数以桌面窗口为父窗口,查找桌面窗口的所有子窗口。
    Windows NT5.0 and later:如果hwndParent是HWND_MESSAGE,函数仅查找所有消息窗口。

    hwndChildAfter :子窗口句柄。查找从在Z序中的下一个子窗口开始。子窗口必须为hwndParent窗口的直接子窗口而非后代窗口。如果HwndChildAfter为NULL,查找从hwndParent的第一个子窗口开始。如果hwndParent 和 hwndChildAfter同时为NULL,则函数查找所有的顶层窗口及消息窗口。

    lpszClass:指向一个指定了类名的空结束字符串,或一个标识类名字符串的成员的指针。如果该参数为一个成员,则它必须为前次调用theGlobaIAddAtom函数产生的全局成员。该成员为16位,必须位于lpClassName的低16位,高位必须为0。

    lpszWindow:指向一个指定了窗口名(窗口标题)的空结束字符串。如果该参数为 NULL,则为所有窗口全匹配。

    返回值

    Long,找到的窗口的句柄。如未找到相符窗口,则返回零。会设置GetLastError
    如果函数成功,返回值为具有指定类名和窗口名的窗口句柄。如果函数失败,返回值为NULL。
    若想获得更多错误信息,请调用GetLastError函数。

    4.EndDialog

    该函数清除一个模态对话框,并使系统中止对对话框的任何处理。

    原型

    BOOL EndDialog(HWND hDlg,int nResult);
    

    参数

    hDlg:表示要被清除的对话框窗口。

    NResult:指定从创建对话框函数返回到应用程序的值。

    返回值

    如果函数调用成功,则返回值为非零值;如果函数调用失败则返回值为零。若想获得错误信息请调用GetLastError函数。

  • 相关阅读:
    一分钟带你了解php和Python的区别
    php保留两位小数的几种方法介绍
    示例php+mysql查询实现无限下级分类树输出
    Java学习(多表查询(内连接查询,外连接查询,子查询),事务(基本介绍,四大特征,隔离级别),DCL(管理用户,权限管理))
    掌握PHP 爬取网页的主要方法
    【数据结构】HashMap 面试题8问
    详解在PHP模板引擎smarty生成随机数的方法和math函数
    php之 Zend 内存管理器
    解析php性能分析之phpfpm慢执行日志slow log用法
    使用BaGet搭建私有nuget源
  • 原文地址:https://www.cnblogs.com/minuy/p/13389516.html
Copyright © 2020-2023  润新知