I want to implement the same behavior with the native camera of iOS5
:
What's the ideal way to archive it? Are there any ways to capture the volume key pressed event?
After googling & searching around for hours, I found 1 solution: using NSNotificationCenter
:
...
[[NSNotificationCenter defaultCenter]
addObserver:self
selector:@selector(volumeChanged:)
name:@"AVSystemController_SystemVolumeDidChangeNotification"
object:nil];
...
- (void)volumeChanged:(NSNotification *)notification{
[self takePhoto];
}
However, it has 2 issues:
I've found another way to hide the "system volume overlay" and "bypass the system volume change when the volume key pressed" by myself.
The bad part: this is an super UGLY hack.
However, the good part is: this ugly hack uses NO private APIs.
Another note is: it only works for ios5+ (anyway, for my issue, since the AVSystemController_SystemVolumeDidChangeNotification only works for ios5, so this UGLY hack just fits my issue.)
The way it work: "act as a music/movie player app and let the volume key to adjust the application-volume".
Code:
// these 4 lines of code tell the system that "this app needs to play sound/music"
AVAudioPlayer* p = [[AVAudioPlayer alloc] initWithContentsOfURL:[NSURL fileURLWithPath:[[[NSBundle mainBundle] resourcePath] stringByAppendingPathComponent:@"photo-shutter.wav"]] error:NULL];
[p prepareToPlay];
[p stop];
[p release];
// these 5 lines of code tell the system that "this window has an volume view inside it, so there is no need to show a system overlay"
[[self.view viewWithTag:54870149] removeFromSuperview];
MPVolumeView* vv = [[MPVolumeView alloc] initWithFrame:CGRectMake(-100, -100, 100, 100)];
[self.view addSubview:vv];
vv.tag = 54870149;
[vv release];
(5 hours spending on discovering this super ugly method... shit... 草尼马啊!)
Another thing: if you take the above hack, you need to run the code EVERY-TIME when your app become active. So, you might need to put some code into your app delegate.
- (void)applicationDidBecomeActive:(UIApplication *)application