首页  编辑  

获取系统托盘中各个图标的信息

Tags: /超级猛料/OS.操作系统/任务栏/   Date Created:

系统托盘中的图标列表和对应程序信息

By Kingron

要获取系统托盘图标中的信息,包括图标个数,Hint信息,对应进程等,可以按以下的方式进行:

首先获取TrayIcon区域的句柄,其实TrayIcon托盘为一个ToolBar,上面的为ToolButton,我们可以按普通的Toolbar来进行处理即可,但是Windows限制了进程边界,因此我们无法直接获取Toolbar消息返回的数据,必须采取跨进程读取数据的方式才能获取数据,如果跨进程获取数据请参考《获取/隐藏系统托盘指定图标》。

给Tray Toolbar发送一下消息即可:

struct TRAYDATA

{

   HWND hwnd;                

   UINT uID;                

   UINT uCallbackMessage;    

   DWORD Reserved[2];        

   HICON hIcon;                

};

TRAYDATA在XP下有效!

用int count = (int)::SendMessage(m_hTrayWnd, TB_BUTTONCOUNT, 0, 0);获取托盘图标的总数.

然后用一个循环获取每一个图标的信息即可:

CProcessData<TBBUTTON> data(dwTrayPid);

TBBUTTON tb = {0};

TRAYDATA tray = {0};

TrayItemInfo tifo = {0};

for(int i=0; i<count; i++)

{  

   /// 使用VirtualAlloc在Explorer内开启TrayData的内存空间    

   SendMessage(m_hTrayWnd, TB_GETBUTTON, i, TrayData); /// TrayData必须在Explorer的进程空间内

   /// ReadProcessMemroy读取TrayData

   DWORD dwProcessId = 0;

   GetWindowThreadProcessId(tray.hwnd,&dwProcessId);

   tifo.sProcessPath = GetFilenameFromPid(dwProcessId);        

   wchar_t TipChar;

   wchar_t sTip[1024] = {0};

   wchar_t* pTip = (wchar_t*)tb.iString;        

   if(!(tb.fsState&TBSTATE_HIDDEN))

   {            

       int x = 0;

       do

       {    

           if(x == 1023)

           {

               wcscpy(sTip,L"[ToolTip was either too long or not set]");    

               break;

           }

           data.ReadData<wchar_t>(&TipChar, (LPCVOID)pTip++);

       }while(sTip[x++] = TipChar);

   }

   else

       wcscpy(sTip,L"[Hidden Icon]");                

   USES_CONVERSION;

   tifo.sTip = W2T(sTip);

   tifo.hwnd = tray.hwnd;

   tifo.uCallbackMessage = tray.uCallbackMessage;

   tifo.uID = tray.uID;

   tifo.bVisible = !(tb.fsState & TBSTATE_HIDDEN);

   int iconindex = 0;

   ICONINFO  iinfo;

   if(GetIconInfo(tray.hIcon,&iinfo) != 0)

   {            

       iconindex = m_Image16List.Add(tray.hIcon);

   }