How can I make a systray (notification area) icon receive WM_MOUSEWHEEL messages?

StackOverflow https://stackoverflow.com/questions/90411

  •  01-07-2019
  •  | 
  •  

Question

I want to extend an existing application I made to make it set mixer volume by wheel-scrolling over it's notification area icon.

As far as I know, the notification area doesn't receive any WM_MOUSEWHEEL messages, but still I found an application that does exactly what I want to achieve (http://www.actualsolution.com/power_mixer). Using WinspectorSpy I've noticed some strange messages the application's form receives: 0x000003d0 and 0x000003d1, but I found no references about them.

Does anyone have any idea on how I could achieve the desired functionality?

Was it helpful?

Solution

If you want to capture mouse/keyboard events outside of your application you will need Low-level Hooks.

A nice beginners article about installing a mouse hook in Delphi is How to Hook the Mouse to Catch Events Outside of your application on About.com written by Zarko Gajic.

The user which starts your application will need administrative rights to install a hook.

After you capture the message you should determine if it's above your icon in the notification bar (which can be difficult because there is no exact api to get your position on the bar) and than process the scroll event.

OTHER TIPS

I explained about the mouse hooking, and mentioned it could be difficult to locate your exact icon. I did found the following article about how to locate a tray icon.

CTrayIconPosition - where is my tray icon? by Irek Zielinski. I think if you try to understand how it works you can turn it around and use it to check if your mouse is currently positioned above your icon.

But you should first check if the mouse is even in the tray area. I found some old code of mine (2005) which locates the correct region.

var
 hwndTaskBar, hwndTrayWnd, hwndTrayToolBar : HWND;
 rTrayToolBar : tRect;
begin
 hwndTaskBar  := FindWindowEx (0, 0, 'Shell_TrayWnd', nil);
 hwndTrayWnd  := FindWindowEx (hwndTaskBar , 0, 'TrayNotifyWnd',nil);
 hwndTrayToolBar := FindWindowEx(hwndTrayWnd, 0, 'ToolbarWindow32',nil);

 Windows.GetClientRect(hwndTrayToolBar, rTrayToolBar);
end

Using this piece of code and the knowledge from the mentioned article I think you could implement the functionality that you wanted.

Not sure if this will solve the problem but it might be worth a try as a starting point. You could create a top level transparent window that you then position over the top of the taskbar icon. That top level window will receive mouse notifications when the mouse is over it. You can then process them as required. How to find the screen location of the taskbar icon is something I do not know and so that might be an issue.

Id don't know if this will help you, but in Delphi the standard Message library states:

WM_MOUSEWHEEL = $020A;

It would also be helpful if you let as know which language you are using.

Just thought I'd point out that Power Mixer is capturing scroll wheel events on the whole taskbar, while the mouse middle click operates just on the sys tray icon.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top