Listening to mac multimedia keyboard events


It seems the mac multimedia keys are not yet supported by JUCE. I have found declarations of keycodes in KeyPress that could be used. Simply adding a shortcut in my app did not work though. Pressing the play button on the mac keyboard still brought up boring iTunes even though my App was running in the foreground.

Here is a link that shows how this could be implemented in a regular Cocoa App:

And here is SPMediaKeyTap that does the same, but in a more fancy way that prevents iTunes from starting.

It seems to make this work JUCE would need to subclass NSApplication. I have looked around in the JUCE source code but wasn’t able to find the place were this happens.

I would think having support for the mac multimedia keys would be nice. Do you think it is a good idea to add that? If so how should I go about adding this to JUCE? Just a short comment to send me on the right track should be sufficient.


Good request! I wouldn’t mind getting this myself for my own projects. It does look a bit messy though - the way to do it would be like the example where they use CGEventTapCreate to intercept the events. I think it could easily be implemented in a class of its own though, without needing to integrate it with the rest of the codebase. Haven’t time to do it myself right now but would be happy to help you get it right if you want to try…


Here is a straightforward port of SPMediaKeyTap hidden behind a pimpl and changed to use the typical JUCE listener system. It works for me.

It would be great if you could have a look. Please let me know what’s missing or what should be changed so that it can be included in JUCE.

The original extension was .mm for the .cpp file. The forum doesn’t allow uploads with the file extension .mm. You probably have to rename the file back to .mm to make the contained Objective-C compile again.


Ok, thanks - if you could refactor it to remove all the objective-C (there’s no need for the obj-C class that’s in there and the whole thing could easily be done in half the amount of code) then I’ll have a look at merging it…


I removed the Objective-C class. Also juce::Thread is now used instead of NSThread. But because I live in VFLib I don’t know how to execute and marshall values between threads using stock JUCE. Therefore two places are marked TODO in the source code where calls should be executed in the main thread and the run loop on the secondary thread respectively. Maybe someone with more cross thread messaging experience in JUCE can fill these in.

Not all Objective-C has disappeard, but much of it. I hope thats ok.


Thanks, I’ll have a look through when I get chance!


Attached is an updated version that uses a JUCE Callback to marshal the information about the key press back to the main message thread. This leaves one TODO item, performing the call to resumeTapOnTapThread on the secondary thread.


Just having a look at this… What on earth is all the process stuff doing? All those white-listed process names?? (The idea of adding all those hard-coded process IDs into a library isn’t something I’d be comfortable doing) And why’s there a thread and a run-loop? Can’t really make much sense of what all this code is supposed to be doing - can’t it be done by just adding a simple event handler on the main run-loop?


Please check out these descriptions for an explanation: