7

This question appears to be asked and answered many times but with no specific or accurate answer. Hence I will reframe the question for iOS7 and hope for some help.

I need to use AudioServicesPlaySystemSound to play sounds as timing is critical and this is only way to play simultaneous sound effect accurately with variable timing (try every other option).

This works well but I would like to adjust the volume. The only way it appears to be able to do this is with the buttons although some say use MPVolumeView (only works for music), some say use MPMusicPlayerController (but this also only works for music and is now depreciated), and others just say it cannot be done - which is looking more likely.

However, with iOS7 there is a slide control in settings>sounds for the ringer alert volume. Is there any way I can subclass, replicate, or access this slide control to change this volume from within the app?

Paul Pivec
  • 71
  • 2

2 Answers2

1

Apple recommends using MPVolumeView, so I came up with this:

Add volumeSlider property:

@property (nonatomic, strong) UISlider *volumeSlider;

Init MPVolumeView and add somewhere to your view (can be hidden, without frame, or empty because of showsRouteButton = NO and showsVolumeSlider = NO):

MPVolumeView *volumeView = [MPVolumeView new];
volumeView.showsRouteButton = NO;
volumeView.showsVolumeSlider = NO;
[self.view addSubview:volumeView];

Find and save reference to UISlider:

__weak __typeof(self)weakSelf = self;
[[volumeView subviews] enumerateObjectsUsingBlock:^(id obj, NSUInteger idx, BOOL *stop) {
    if ([obj isKindOfClass:[UISlider class]]) {
        __strong __typeof(weakSelf)strongSelf = weakSelf;
        strongSelf.volumeSlider = obj;
        *stop = YES;
    }
}];

Add target action for UIControlEventValueChanged:

[self.volumeSlider addTarget:self action:@selector(handleVolumeChanged:) forControlEvents:UIControlEventValueChanged];

And then update your custom control when the volume has been changed (i.e. by the hardware volume controls):

- (void)handleVolumeChanged:(id)sender
{
    NSLog(@"%s - %f", __PRETTY_FUNCTION__, self.volumeSlider.value);
    self.myCustomVolumeSliderView.value = self.volumeSlider.value;
}

and also other way around:

- (IBAction)myCustomVolumeSliderViewValueChanged:(id)sender {
    NSLog(@"set volume to: %f", self.myCustomVolumeSliderView.value);
    self.volumeSlider.value = self.myCustomVolumeSliderView.value;
}

NOTE: Make sure that setting the self.volumeSlider.value doesn't loop back to setting self.myCustomVolumeSliderView.value.

Hope this helps someone (and that Apple doesn't remove MPVolumeSlider from MPVolumeView).

msrdjan
  • 815
  • 9
  • 8
0

I think you want to control your volume through program

 - (void)setVolume:(float)Level
  {

      OSStatus errorMsg = AudioQueueSetParameter(audioQueue, kAudioQueueParam_Volume, Level);

    if (errorMsg) {
        NSLog(@"AudioQueueSetParameter returned %d when setting the volume.", errorMsg);
    }

 }
  • use this code to set volume level passing from your code by which button you want to control.
Ram S
  • 793
  • 12
  • 21
  • if this is not through programming : please refer this link http://stackoverflow.com/questions/10855874/audioservicesplaysystemsound-volume – Ram S Dec 23 '13 at 09:57