2013-06-21 3 views
1

내 문제에 대한 자세한 설명을하려고합니다.AVQueuePlayer 및 오디오 세션 문제

앱 사운드에서 사용하는 상점에있는 앱이 있습니다. 현재 일부 사운드가 겹쳐서 순서대로 재생할 수 있기 때문에 AVQueuePlayer를 사용하고 있습니다. 중요하지 않을 수도있는 AVPlayer를 사용하여 퍼간 동영상을 재생하는 동안이 사운드가 많이 재생됩니다. 문제는 전체 앱에서 소리가 멈추었 음을보고하는 것입니다. 나는 이것을 스스로 재현 할 수 없지만 우리는 많은 활동적인 사용자를 가지고 있으며, 어떤 사람들에 의해보고된다. 보고 될 때마다 우리는 조용한 스위치 나 음량을 낮춰서 앱을 재시작하지 않을 때마다 항상 문제를 해결합니다. 때때로 우리는 변경없이 소리없이 마술처럼 돌아 왔다는 말을 들었습니다. 나는 또한 airplay와 블루투스를 사용할 때 일어나는 몇 가지 보고서를 가지고있다. 그러나 그것은 문제 또는 우연의 합병증 일 수있다.

아래 코드는 내가 사용하고있는 코드이며 설정이 잘못되었거나 사용하지 않아도되지만이 코드는 99.9 %의 시간 동안 작동합니다.

나는 사용자의 iPod 음악의 볼륨을 낮추기 위해 내가 연주하는 모든 소리에 더킹을 ​​사용합니다. 여기

은 (어쩌면 그 규칙의 혼합에 대한 모든 시작과 죄송 필요하지 않습니다) appDidFinishLaunchingWithOptions 내 초기화입니다 :

AudioSessionInitialize (NULL, NULL, NULL, NULL); 

    [[AVAudioSession sharedInstance] setCategory:AVAudioSessionCategoryPlayback error:nil]; 

    UInt32 sessionCategory = kAudioSessionCategory_AmbientSound; 
    AudioSessionSetProperty (kAudioSessionProperty_AudioCategory, sizeof (sessionCategory), &sessionCategory); 

    [[AVAudioSession sharedInstance] setActive:YES withFlags:AVAudioSessionSetActiveFlags_NotifyOthersOnDeactivation error:nil]; 

나는 사운드를 재생할 때 :

-(void)playSound: (NSString *)soundString 
{ 
    OSStatus propertySetError = 0; 
    UInt32 allowMixing = true; 
    propertySetError |= AudioSessionSetProperty(kAudioSessionProperty_OtherMixableAudioShouldDuck, sizeof(allowMixing), &allowMixing); 

    [[AVAudioSession sharedInstance] setActive:YES withFlags:AVAudioSessionSetActiveFlags_NotifyOthersOnDeactivation error:nil]; 

    NSURL *thisUrl = [NSURL fileURLWithPath:[NSString stringWithFormat:@"%@/%@.caf", [[NSBundle mainBundle] resourcePath], soundString]]; 

    AVPlayerItem *item = [[AVPlayerItem alloc] initWithURL:thisUrl]; 

    [[NSNotificationCenter defaultCenter] addObserver:self 
              selector:@selector(reachedEndOfItem:) 
               name:AVPlayerItemDidPlayToEndTimeNotification 
               object:item]; 

    if(_audioPlayerQueue == nil) 
    { 
     _audioPlayerQueue = [[AVQueuePlayer alloc] initWithItems:[NSArray arrayWithObject:item]]; 
    } 
    else 
    { 
     if([_audioPlayerQueue canInsertItem:item afterItem:nil]) 
     { 
      [_audioPlayerQueue insertItem:item afterItem:nil]; 
     } 
    } 

    if(_audioPlayerQueue == nil) 
    { 
     NSLog(@"error"); 
    } 
    else 
    { 
     [_audioPlayerQueue play]; 
    } 

    return; 
} 

사운드가 재생 완료 :

- (void)reachedEndOfItem: (AVPlayerItem*)item 
{ 
    [self performSelector:@selector(turnOffDucking) withObject:nil afterDelay:0.5f]; 
} 

- (void)turnOffDucking 
{ 
    NSLog(@"reached end"); 

    [[AVAudioSession sharedInstance] setActive:NO withFlags:AVAudioSessionSetActiveFlags_NotifyOthersOnDeactivation error:nil]; 

    OSStatus propertySetError = 0; 
    UInt32 allowMixing = false; 
    propertySetError |= AudioSessionSetProperty(kAudioSessionProperty_OtherMixableAudioShouldDuck, sizeof(allowMixing), &allowMixing); 
} 

내가하는 일에 대한 통찰력 wr ong, 오디오 세션이나 알려진 버그/문제에 대해 사용해야하는 설정은 매우 유용 할 것입니다. 비디오를 재생할 때 약간의 성능 문제가 발생할 수 있고 iPod 음악을 일렬로 재생할 때 다른 오디오 엔진을 사용하고 싶지만이 방법으로 오디오를 재생하는 것이 좋습니다.

제공 할 수있는 도움에 감사드립니다.

+0

두 개의 다른 스레드가 앱에서 동시에 오디오 세션을 수정할 수있는 가능성이 있습니까? 나는 과거에 비슷한 문제가 있었고 동시 스레드 접근이 이유라고 알았다. – Hejazi

+0

이것을 쓰고 난 후에 나는 그것이 실제로 문제라고 느낀다. 그래서 내 "performSelectorAfterDelay"가 문제라고 말하고 있습니까? 그 이유는 세션이 여전히 활성 상태 일 때 알림이 발생하여 더킹이 꺼지지 않기 때문입니다. – rooster117

+0

예, 지연이 종료되는 동시에 다른 스레드가 오디오 세션을 수정하려고하는 이유가 될 수 있습니다. 그래서 다시 코드를 확인하고'playSound'에 대한 모든 호출이 메인 스레드에서 이루어 지도록하는 것이 좋습니다. – Hejazi

답변

0

- 라이언

나는 과거에 비슷한 문제가 있었다 동시 스레드 액세스 이유 것을 발견했다.

특히, 나는 performSelectorAfterDelay을 호출하는 것이 다른 스레드가 오디오 세션을 수정하려고 시도하는 것과 동시에 지연이 종료되는 이유라고 생각합니다. 그러면 오디오 세션에 액세스하려고하는 두 개의 서로 다른 스레드가 생길 것입니다.

그래서 코드를 다시 확인하고 playSound에 대한 모든 호출이 기본 스레드에서 이루어 지도록하는 것이 좋습니다.

블록의 호출이, 키 - 값 관찰자를, 또는 통지 핸들러는 특정 스레드 또는 큐에 만들어 질 보장되지 않습니다 또한,이 performSelectorOnMainThread 대신 performSelectorAfterDelaythe docs로를 사용하는 것이 더 좋을 수는 말한다. 대신 AV Foundation은 내부 작업을 수행하는 스레드 또는 대기열에서 이러한 핸들러를 호출합니다.

+0

답변으로 받아들입니다. 앞으로 3 일 안에 그것을 확인할 방법이 없지만 문서가 꽤 설득력이 있고 소리주기는 오디오 세션에 동시에 액세스하고 다른 스레드에서 무작위로 나처럼 공통적이라고 보입니다. – rooster117