Detect headset button click on iPhone SDK
Asked Answered
T

3

11

Is there a way to detect the headset's play/pause button click?

I managed to detect the volume buttons clicks using:

AudioSessionAddPropertyListener( kAudioSessionProperty_CurrentHardwareOutputVolume , audioVolumeChangeListenerCallback, self );

But I can't find an AudioSessionProperty for the center button. What's the way to do that?

Triquetrous answered 15/9, 2011 at 9:35 Comment(0)
H
8

Everything that's done from outside your app is considered a "Remote Event". If you double-tap the Home button and press Play/Pause there, it's the equivalent of pressing the play/pause button on the headset (Same for double tapping for next, and triple tapping for previous).

Here's the guide on event handling of remote events for iOS.

Personally, I like subclassing the MainWindow (UIWindow) and overriding the sendEvent: method, so I can manage it more directly:

- (void)sendEvent:(UIEvent *)event
{
    if (event.type == UIEventTypeRemoteControl)
    {
        // Do stuff here
    }
    else
    {
        // Not my problem.
        [super sendEvent:event];
    }
}

Hope that helps, the enum for the event of the central button is UIEventSubtypeRemoteControlTogglePlayPause.

Headgear answered 18/9, 2011 at 5:48 Comment(3)
Thanks Can. I found another solution by using the method: "remoteControlReceivedWithEvent:". The solution is discussed here: iphonedevsdk.com/forum/iphone-sdk-development/…Triquetrous
@Headgear I've tried your solution and the sendEvent UIEventTypeRemoteControl event type isn't called when I press the buttons on my headset. Is there some other setup you have done to get this to work? The subclass is working as I do catch some other events.Glisten
Also, you must be playing something in order to be able to receive these events, as per the docs -> developer.apple.com/documentation/mediaplayer/…Queen
R
3

Tried all above but sadly now none seems to work. Then I took a peek at beginReceivingRemoteControlEvents and found this

In iOS 7.1 and later, use the shared MPRemoteCommandCenter object to register for remote control events. You do not need to call this method when using the shared command center object.

Then checked out MPRemoteCommandCenter and finally ended up in MPRemoteCommand documentation page.

Good thing is there is this example:

let commandCenter = MPRemoteCommandCenter.shared()
commandCenter.playCommand.addTarget(handler: { (event) in    

    // Begin playing the current track    
    self.myMusicPlayer.play()
    return MPRemoteCommandHandlerStatus.success
})

Now if we want to read middle button we can do:

MPRemoteCommandCenter.shared().togglePlayPauseCommand.addTarget { (event: MPRemoteCommandEvent) -> MPRemoteCommandHandlerStatus in

 // middle button (toggle/pause) is clicked
 print("event:", event.command)

 return .success
}

This works and I managed to get the headphone's middle button detected.

Note: I noticed there is different behaviour that depends on where we put such code above. That is when I put in View Controller the reported events are identical and when I put it in AppDelegate's didFinishLaunching the reported events are different. Either way the event is detected.

Rendezvous answered 5/10, 2019 at 14:59 Comment(0)
T
1

Can's answer was good, but I think it's outdated.

Now you need to subclass UIApplication.

code for main.m

#import <UIKit/UIKit.h>
#import "AppDelegate.h"
#import "MyUIApplication.h"

int main(int argc, char * argv[]) {
  @autoreleasepool {
    return UIApplicationMain(
      argc,
      argv,
      NSStringFromClass([MyUIApplication class]),
      NSStringFromClass([AppDelegate class]));
  }
}

Code for MyUIApplication.m:

@implementation MyUIApplication
- (void)sendEvent:(UIEvent *)event {
  if (event.type == UIEventTypeRemoteControl) {
    // Check event.subtype to see if it's a single click, double click, etc.
  } else {
    // Not my problem.
    [super sendEvent:event];
  }
}
@end

Code for AppDelegate.m:

inside of - (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {

call [application beginReceivingRemoteControlEvents];

Turki answered 18/10, 2017 at 4:58 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.