接下来创建托盘。
要使用托盘就要用到NOTIFYICONDATA类。步骤如下:
1. 添加成员变量
class CxxxxxDlg : public CDialog {
...... Private: //tray NOTIFYICONDATA m_nid; WINDOWPLACEMENT m_wp;
...... }
2. 定义用来响应托盘鼠标操作的消息
#define WM_SHOWTASK WM_USER+100
3.添加消息响应函数的声明
class CxxxtDlg : public CDialog { ...... LRESULT OnShowTask(WPARAM wParam, LPARAM lParam); ...... };
4.在BEGIN_MESSAGE_MAP 和 END_MESSAGE_MAP 之间添加消息处理映射:
ON_MESSAGE(WM_SHOWTASK, OnShowTask)
5.添加消息处理函数的实现:
HRESULT CxxxxDlg::OnShowTask(WPARAM wParam, LPARAM lParam) { if(wParam !=IDI_ICON1 )// return 1; switch(lParam) { case WM_RBUTTONUP: // 右键起来时弹出菜单 { LPPOINT lpoint = new tagPOINT; ::GetCursorPos(lpoint); // 得到鼠标位置 CMenu menu; menu.CreatePopupMenu(); // 声明一个弹出式菜单 //增加菜单项“关闭”,点击则发送消息WM_DESTROY给主窗口(已 //隐藏),将程序结束。 menu.AppendMenu(MF_STRING, WM_DESTROY, _T("关闭")); //确定弹出式菜单的位置 menu.TrackPopupMenu(TPM_LEFTALIGN, lpoint->x ,lpoint->y, this); //资源回收 HMENU hmenu = menu.Detach(); menu.DestroyMenu(); delete lpoint; } break; case WM_LBUTTONDBLCLK: // 双击左键的处理 { // ModifyStyleEx(WS_EX_TOOLWINDOW, WS_EX_APPWINDOW); this->ShowWindow(SW_SHOWNORMAL); // 显示主窗口 SetWindowPlacement(&m_wp); //CenterWindow(); } break; } return 0; }
6. 在OnInitDialog()函数中添加:
BOOL CxxxxxxDlg::OnInitDialog() { ...... //show tray m_nid.cbSize = (DWORD)sizeof(NOTIFYICONDATA); m_nid.hWnd = this->m_hWnd; m_nid.uID = IDI_ICON1; // IDR_MAINFRAME m_nid.uFlags = NIF_ICON | NIF_MESSAGE | NIF_TIP ; m_nid.uCallbackMessage = WM_SHOWTASK; // 自定义的消息名称 m_nid.hIcon = LoadIcon(AfxGetInstanceHandle(),MAKEINTRESOURCE(IDI_ICON1)); //IDR_MAINFRAME wcscpy_s(m_nid.szTip, _T("串口通信")); // 信息提示条为"串口通信",VS2008 UNICODE编码用wcscpy_s()函数 Shell_NotifyIcon(NIM_ADD, &m_nid); // 在托盘区添加图标 //----------------------------------------- // 记录窗口初始位置,托盘恢复成窗口的时候使用 CenterWindow(); m_wp.length = sizeof(WINDOWPLACEMENT); GetWindowPlacement(&m_wp); //恢复时用 ModifyStyleEx(WS_EX_APPWINDOW, 0);//从任务栏中去掉图标 // 隐藏窗口 SetWindowPos(&wndTop,0,0,0,0,NULL);
return TRUE; }
7. 点击最小化按钮隐藏话框程序
void CXXXXXXDlg::OnSysCommand(UINT nID, LPARAM lParam) { if ((nID & 0xFFF0) == IDM_ABOUTBOX) { CAboutDlg dlgAbout; dlgAbout.DoModal(); } else if (nID == SC_MINIMIZE)// when click minimize, hide the window { ShowWindow(SW_HIDE); } else { CDialog::OnSysCommand(nID, lParam); } }
8.在 OnDestroy 函数中销毁托盘
void CxxxxDlg::OnDestroy() { CDialog::OnDestroy(); //删除托盘图标 ::Shell_NotifyIcon(NIM_DELETE, &m_nid); }
OK,搞定!
参考文章:
https://www.cnblogs.com/micq/p/6196734.html
https://www.cnblogs.com/JczmDeveloper/p/3510294.html
https://blog.csdn.net/starytx/article/details/69236378?locationNum=13&fps=1
https://www.cnblogs.com/likebeta/archive/2012/09/15/2687105.html