2012-04-27 2 views
0

책임의 한계와 법적 고지 발생하지 setImage를 지연 : 부드러운 :-) 그렇게 될 ... 나는 아이폰 OS 프로그래밍 비교적 새로운 해요, 난 그냥 재미를 위해 함께 가서 자신에게 기본을 가르치려고 노력하고는 AVAudioPlayer는


AVAudioplayer를 사용하여 일련의 .mp3 파일을 함께 재생하는 앱을 만들고 있습니다. 지금까지 그 부분이 잘 작동하고 있습니다. IBActions 및 IBOutlets가 연결되었습니다. 버튼을 클릭하면 오디오가 재생됩니다.

내 문제는 다음과 같습니다. 내 재생 버튼이 Interface Builder에 정의 된 초기 상태로 main.storyboard에 직접 추가되고 설정 및 맞춤 설정되었습니다. 재생을 클릭하면 버튼의 이미지가 재생 중임을 나타내도록 이미지를 변경하려고합니다. 그러나 오디오가 시작 되 자마자보기가 일시 중지 된 것처럼 보입니다. 버튼 이미지는 오디오가 재생 될 때까지 동일하게 유지됩니다. 그래야만 버튼 이미지 자체가 업데이트됩니다.

또한이 특정 단추에 연결되지 않은 다른 임의의 UIImageView의 이미지를 설정하려고했습니다. 같은 경험. playAudioArray 메서드를 주석 처리하는 즉시 버튼 스왑이 작동합니다.


    -(IBAction)start_playing:(UIButton*)pressed_button { 
    [_btn_start setImage:[UIImage imageNamed:@"btn_on-active"] forState:UIControlStateNormal]; 

    [self playAudioArray]; 
    } 

나는 충분히 나아 갔다. 희망/의견/제안 ??

감사 만 - 드류

#

업데이트 :

내가이 lopp 내 오디오 플레이어가있을 때 뷰를 업데이트하는 분해 것으로 나타났습니다. 이 코드는 잘 작동 ...


    if (audioPlayer.playing == YES) {

[audioPlayer pause]; 
[sender setImage:[UIImage imageNamed:@"btn_on.png"] forState:UIControlStateNormal]; 
[_btn_stop setImage:[UIImage imageNamed:@"btn_off.png"] forState:UIControlStateNormal]; 

} else { 

NSString *path = [[NSBundle mainBundle] pathForResource:@"audio_file1" ofType:@"mp3"]; 
audioPlayer = [[AVAudioPlayer alloc] initWithContentsOfURL:[NSURL fileURLWithPath:path] error:NULL]; 
audioPlayer.volume = 1.0; 
audioPlayer.numberOfLoops = 0; 
[audioPlayer setMeteringEnabled: YES]; 
[audioPlayer play]; 


//changes the image when the button is pressed 
[sender setImage:[UIImage imageNamed:@"btn_on.png"] forState:UIControlStateNormal]; 
[_btn_stop setImage:[UIImage imageNamed:@"btn_off.png"] forState:UIControlStateNormal]; 

} 

하지만이 코드는 아래의하지 않습니다하지 않습니다.


    } else {

//changes the image when the button is pressed 
[sender setImage:[UIImage imageNamed:@"btn_on.png"] forState:UIControlStateNormal]; 
[_btn_stop setImage:[UIImage imageNamed:@"btn_off.png"] forState:UIControlStateNormal]; 

NSArray *theSoundArray = [NSArray arrayWithObjects:@"audio1",@"audio2",@"audio3",nil]; 

for (int i = 0; i < totalSoundsInQueue;) { 

NSString *sound = [theSoundArray objectAtIndex:i]; 

// Wait until the audio player is not playing anything 
while(![audioPlayer isPlaying]){ 

NSString *path = [[NSBundle mainBundle] pathForResource:@"mom" ofType:@"mp3"]; 
audioPlayer = [[AVAudioPlayer alloc] initWithContentsOfURL:[NSURL fileURLWithPath:path] error:NULL]; 
audioPlayer.volume = 1.0; 
audioPlayer.numberOfLoops = 0; 
[audioPlayer setMeteringEnabled: YES]; 
[audioPlayer play]; 

i++; 

}   

} 

} 

오디오가 잘 재생

는, 내 모든 소리를 반복하고 오류가 발생하지 않습니다. 루프가 끝난 후에 만 ​​'내 상태'버튼 만 설정됩니다. 나는 루핑 방법의 여러 가지 유형의 번호로 이것을 시도했습니다. 왜냐하면, 각각 동안, ... 내가 소리를 통해 반복하기 시작할 때마다 오디오 재생은 훌륭하게 작동하지만, 디스플레이는 모든 초점을 잃어버린다.

나에게 떠오릅니다. 루프가 끝나면 "정지"버튼이 클릭 가능한 (탭 가능) 특성을 잃어 버립니다. 루프가 끝날 때까지. 내가 루프에 없다면 정지 버튼이 문제없이 작동합니다.

죄송합니다. 여기에서 완전히 새로운 실수를하는 경우 ... 생각/의견 누구?

+0

'playAudioArray' 메소드가'_btn_start'의 상태를 설정합니까? –

+0

아니, start_playing 메서드의 맨 위에 설정되어 있습니다 (첫 번째 줄). – Drew

답변

0

for loop이 주 스레드를 묶어 UI가 응답하지 않게 만듭니다. for 루프를 계속 실행하는 대신 AVAudioPlayer의 대리자로 설정하십시오. 오디오 플레이어 재생이 끝나면 대표자에게 - (void) audioPlayerDidReachEnd; 메시지를 전송합니다 (구현해야 함). 그런 다음 해당 구현의 대기열에서 다음 오디오 파일을 재생할 수 있습니다. 어쨌든 위임자로 자신을 설정하고 싶습니다.AVAudioPlayer는 (들어오는 전화와 같은) 중단 및 오류 해독에 대한 위임 메시지를 보냅니다. 이러한 이벤트를 정상적으로 처리하려고합니다.

오디오가 잘 작동하는 이유는 우선 순위가 높고 별도의 스레드에서 실행된다는 것입니다. UI가 응답하지 않는 이유는 비록 애니메이션/UI 변경이 별도의 스레드에서 발생하더라도 주 스레드에서 초기화되기 때문입니다. 그러나 모든 UI 변경 사항은 실행 루프의 끝까지 대기합니다 (그래서 최적화가 가능합니다). 그러나 모든 오디오 파일이 재생 될 때까지 for loop이 끝나지 않으므로 실행 루프가 종료되지 않습니다. 오디오 파일은 for loop에서 시작되어 별도의 스레드에서 실행되므로 순서대로 재생할 수 있습니다. 말이된다? 일반적으로, 당신은 정말로 메인 스레드를 묶고 싶지 않습니다.

+0

감사합니다. 귀하의 제안은 도움이되었습니다. 결국 for 루프와 while 루프를 모두 제거하고 각각의 사운드를 개별적으로 처리하고 각각의 이전 사운드가 끝난 후에 새로운 재생 방법을 사용하는 것으로 끝났습니다. 감사합니다. – Drew

관련 문제