zoukankan      html  css  js  c++  java
  • windows API 创建系统托盘图标

    系统托盘在我们使用的程序中很普遍,下面我们来看一个很不错的例子,使用Win32 API实现,对理解系统托盘有些帮助。

    1. #include <windows.h>  
    2. #define IDR_PAUSE 12  
    3. #define IDR_START 13  
    4. /* 
    5. #include <shellapi.h> 
    6. #pragma   comment(lib,   "shell32.lib")  
    7. */  
    8. LPCTSTR szAppName = TEXT("服务程序");  
    9. LPCTSTR szWndName = TEXT("服务程序");  
    10. HMENU hmenu;//菜单句柄  
    11.   
    12. LRESULT CALLBACK WndProc(HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam)  
    13. {  
    14.     NOTIFYICONDATA nid;  
    15.     UINT WM_TASKBARCREATED;  
    16.     POINT pt;//用于接收鼠标坐标  
    17.     int xx;//用于接收菜单选项返回值  
    18.   
    19.     // 不要修改TaskbarCreated,这是系统任务栏自定义的消息  
    20.     WM_TASKBARCREATED = RegisterWindowMessage(TEXT("TaskbarCreated"));  
    21.     switch (message)  
    22.     {  
    23.     case WM_CREATE://窗口创建时候的消息.  
    24.         nid.cbSize = sizeof(nid);  
    25.         nid.hWnd = hwnd;  
    26.         nid.uID = 0;  
    27.         nid.uFlags = NIF_ICON | NIF_MESSAGE | NIF_TIP;  
    28.         nid.uCallbackMessage = WM_USER;  
    29.         nid.hIcon = LoadIcon(NULL, IDI_APPLICATION);  
    30.         lstrcpy(nid.szTip, szAppName);  
    31.         Shell_NotifyIcon(NIM_ADD, &nid);  
    32.         hmenu=CreatePopupMenu();//生成菜单  
    33.         AppendMenu(hmenu,MF_STRING,IDR_PAUSE,"暂停服务");//为菜单添加两个选项  
    34.         AppendMenu(hmenu,MF_STRING,IDR_START,"恢复服务");  
    35.         break;  
    36.     case WM_USER://连续使用该程序时候的消息.  
    37.         if (lParam == WM_LBUTTONDOWN)  
    38.             MessageBox(hwnd, TEXT("Win32 API 实现系统托盘程序,双击托盘可以退出!"), szAppName, MB_OK);  
    39.         if (lParam == WM_LBUTTONDBLCLK)//双击托盘的消息,退出.  
    40.             SendMessage(hwnd, WM_CLOSE, wParam, lParam);  
    41.         if (lParam == WM_RBUTTONDOWN)  
    42.         {  
    43.             GetCursorPos(&pt);//取鼠标坐标  
    44.             ::SetForegroundWindow(hwnd);//解决在菜单外单击左键菜单不消失的问题  
    45.             EnableMenuItem(hmenu,IDR_PAUSE,MF_GRAYED);//让菜单中的某一项变灰  
    46.             xx=TrackPopupMenu(hmenu,TPM_RETURNCMD,pt.x,pt.y,NULL,hwnd,NULL);//显示菜单并获取选项ID  
    47.             if(xx==IDR_PAUSE) MessageBox(hwnd, TEXT("111"), szAppName, MB_OK);  
    48.             if(xx==IDR_START) MessageBox(hwnd, TEXT("222"), szAppName, MB_OK);  
    49.             if(xx==0) PostMessage(hwnd,WM_LBUTTONDOWN,NULL,NULL);  
    50.             //MessageBox(hwnd, TEXT("右键"), szAppName, MB_OK);  
    51.         }  
    52.         break;  
    53.     case WM_DESTROY://窗口销毁时候的消息.  
    54.         Shell_NotifyIcon(NIM_DELETE, &nid);  
    55.         PostQuitMessage(0);  
    56.         break;  
    57.     default:  
    58.         /* 
    59.         * 防止当Explorer.exe 崩溃以后,程序在系统系统托盘中的图标就消失 
    60.         * 
    61.         * 原理:Explorer.exe 重新载入后会重建系统任务栏。当系统任务栏建立的时候会向系统内所有 
    62.         * 注册接收TaskbarCreated 消息的顶级窗口发送一条消息,我们只需要捕捉这个消息,并重建系 
    63.         * 统托盘的图标即可。 
    64.         */  
    65.         if (message == WM_TASKBARCREATED)  
    66.             SendMessage(hwnd, WM_CREATE, wParam, lParam);  
    67.         break;  
    68.     }  
    69.     return DefWindowProc(hwnd, message, wParam, lParam);  
    70. }  
    71.   
    72. int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance,  
    73.                    LPSTR szCmdLine, int iCmdShow)  
    74. {  
    75.     HWND hwnd;  
    76.     MSG msg;  
    77.     WNDCLASS wndclass;  
    78.   
    79.     HWND handle = FindWindow(NULL, szWndName);  
    80.     if (handle != NULL)  
    81.     {  
    82.         MessageBox(NULL, TEXT("Application is already running"), szAppName, MB_ICONERROR);  
    83.         return 0;  
    84.     }  
    85.   
    86.     wndclass.style = CS_HREDRAW | CS_VREDRAW;  
    87.     wndclass.lpfnWndProc = WndProc;  
    88.     wndclass.cbClsExtra = 0;  
    89.     wndclass.cbWndExtra = 0;  
    90.     wndclass.hInstance = hInstance;  
    91.     wndclass.hIcon = LoadIcon(NULL, IDI_APPLICATION);  
    92.     wndclass.hCursor = LoadCursor(NULL, IDC_ARROW);  
    93.     wndclass.hbrBackground = (HBRUSH)GetStockObject(WHITE_BRUSH);  
    94.     wndclass.lpszMenuName = NULL;  
    95.     wndclass.lpszClassName = szAppName;  
    96.   
    97.     if (!RegisterClass(&wndclass))  
    98.     {  
    99.         MessageBox(NULL, TEXT("This program requires Windows NT!"), szAppName, MB_ICONERROR);  
    100.         return 0;  
    101.     }  
    102.   
    103.     // 此处使用WS_EX_TOOLWINDOW 属性来隐藏显示在任务栏上的窗口程序按钮  
    104.     hwnd = CreateWindowEx(WS_EX_TOOLWINDOW,  
    105.         szAppName, szWndName,  
    106.         WS_POPUP,  
    107.         CW_USEDEFAULT,  
    108.         CW_USEDEFAULT,  
    109.         CW_USEDEFAULT,  
    110.         CW_USEDEFAULT,  
    111.         NULL, NULL, hInstance, NULL);  
    112.   
    113.     ShowWindow(hwnd, iCmdShow);  
    114.     UpdateWindow(hwnd);  
    115.   
    116.     while (GetMessage(&msg, NULL, 0, 0))  
    117.     {  
    118.         TranslateMessage(&msg);  
    119.         DispatchMessage(&msg);  
    120.     }  
    121.     return msg.wParam;  
    122. }  
  • 相关阅读:
    模板方法设计模式
    单一职责原则
    开闭原则
    uml
    迭代器模式
    观察者模式
    工厂模式
    代理模式
    idea本地Maven仓库不能下载依赖jar包的解决方案
    selenium 使用教程详解-java版本
  • 原文地址:https://www.cnblogs.com/vcerror/p/4289014.html
Copyright © 2011-2022 走看看