概述:
什么是托盘应用程序?
当你打开后会在电脑最右下角的任务栏上生成一个系统托盘,当你点击最小化或者点击关闭按钮后,若想恢复窗口,可以左键双击或者单机这个系统图标,同时鼠标右键点击,又会有其他的菜单弹出,比如退出。像QQ等可以停靠在电脑桌面的右下方:
实现操作步骤
(2)在CTrayIconDlg.cpp文件中的OnInitDialog()添加代码,使程序产生作用:
添加的代码:
//设置系统托盘
NOTIFYICONDATA NotifyIcon;
NotifyIcon.cbSize = sizeof(NOTIFYICONDATA);
//NotifyIcon.hIcon=AfxGetApp()->LoadIcon(IDR_MAINFRAME);
NotifyIcon.hIcon = m_hIcon; //上面那句也可以
NotifyIcon.hWnd = m_hWnd;
lstrcpy(NotifyIcon.szTip, _T("我的托盘程序"));
NotifyIcon.uCallbackMessage = WM_ICON_NOTIFY;//自定义消息
NotifyIcon.uFlags = NIF_ICON | NIF_MESSAGE | NIF_TIP;
Shell_NotifyIcon(NIM_ADD, &NotifyIcon); //添加系统托盘
WM_ICON_NOTIFY:是后面我们要定义的程序响应菜单。
(3) 在CTrayIconDlg.cpp文件的最开始位置添加一个自定义消息
#define WM_ICON_NOTIFY WM_USER+100
此时,编译运行程序,可以发现程序图标已经在窗口栏中:
将鼠标移动到右下角的下标,会显示“我的托盘程序”。
(4)添加OnClose()消息,当关闭程序时使图标消失
实现代码:
void CTrayIconDlg::OnClose()
{
// TODO: 在此添加消息处理程序代码和/或调用默认值
NOTIFYICONDATA nd = { 0 };
nd.cbSize = sizeof(NOTIFYICONDATA);
nd.hWnd = m_hWnd;
nd.uID = IDR_MAINFRAME;
nd.uFlags = NIF_ICON | NIF_MESSAGE | NIF_TIP;
nd.uCallbackMessage = WM_ICON_NOTIFY;
nd.hIcon = m_hIcon;
Shell_NotifyIcon(NIM_DELETE, &nd);
CDialogEx::OnClose();
}
此时,运行程序,关闭窗口,会发现右下角的图标会同时消失。
(5)修改对话框属性,设置最大化最小化按钮:
在解决方案资源管理器中点击TrayIcon.rc显示资源视图
右键对话框,选择属性,将最大化框和最小化框设置为true
(6)在TrayIconDlg.cpp中的OnSysCommand(UINT nID, LPARAM lParam)函数添加以下代码,相应最小化按钮
if (nID == SC_MINIMIZE)
{
ShowWindow(FALSE);//隐藏窗口
}
即:
void CTrayIconDlg::OnSysCommand(UINT nID, LPARAM lParam)
{
if ((nID & 0xFFF0) == IDM_ABOUTBOX)
{
CAboutDlg dlgAbout;
dlgAbout.DoModal();
}
else
{
CDialogEx::OnSysCommand(nID, lParam);
}
if (nID == SC_MINIMIZE)
{
ShowWindow(FALSE);//隐藏窗口
}
}
此时,运行程序,点击最小化,发现窗口被隐藏了,且任务栏图标消失,点击托盘上的图标没有响应,并且只能通过 任务管理器 关闭程序
(7)添加托盘图标的鼠标消息响应
①添加消息响应的宏
ON_MESSAGE(WM_ICON_NOTIFY,&CTrayIconDlg::OnTrayNotification)
放在图中位置:
②添加实现函数OnTrayNotification(WPARAM wParam, LPARAM lParam)
在TrayIconDlg.h声明函数:
public:
LRESULT OnTrayNotification(WPARAM wParam, LPARAM lParam);
在TrayIconDlg.cpp实现函数:
在文件最开始的定义定义两个宏
#define ID_MENU_RECOVER 2001
#define ID_MENU_CLOSE 2002
作为菜单项的ID
LRESULT CTrayIconDlg::OnTrayNotification(WPARAM wParam, LPARAM lParam))
{
// TODO: 在此处添加实现代码.
switch (lParam)
{
case WM_RBUTTONDOWN://鼠标右键点击图标
{
POINT point;
GetCursorPos(&point);//检索鼠标光标的位置(以屏幕坐标为单位)
CMenu menu;
menu.CreatePopupMenu();//创建弹出式菜单
menu.AppendMenuW(MF_STRING, ID_MENU_RECOVER, L"恢复");//添加菜单项
menu.AppendMenuW(MF_STRING, ID_MENU_CLOSE, L"关闭");
menu.TrackPopupMenu(TPM_RIGHTBUTTON, point.x, point.y, this);
}
break;
}
return LRESULT();
}
添加子菜单“恢复”的消息响应函数:
①添加消息响应的宏
ON_BN_CLICKED(ID_MENU_RECOVER, &CTrayIconDlg::OnRecover)
放在图示位置:
②添加实现函数OnTrayRestore()
OnTrayRestore()函数的实现:
void CTrayIconDlg::OnRecover()
{
// TODO: 在此处添加实现代码.
ShowWindow(SW_SHOW);
SetForegroundWindow();
}
为子菜单“退出”添加消息响应函数:
void CTrayIconDlg::OnTrayExit()
{
EndDialog(IDCANCEL);
}
(8)整个项目完成,运行程序:
(9)完整示例代码:
链接:https://pan.baidu.com/s/1cXO1fukiZIdgfHkIQiAU2Q?pwd=ci97
提取码:ci97