【问题标题】:How to easily play back to back .m4a files programmatically on an iOS iPhone app如何在 iOS iPhone 应用程序上以编程方式轻松回放 .m4a 文件
【发布时间】:2012-08-26 05:04:08
【问题描述】:

如何连续播放多个 .m4a 文件?

目前,我的函数开始播放一个,使用 AudioServicesPlaySystemSound 等,使用 AudioServicesAddSystemSoundCompletion 选择回调,然后返回。声音结束后,回调让我的软件继续运行。

每当有背靠背声音时,这需要大量编码。

我的软件可以开始播放 .m4a 文件,然后以某种方式等待它完成,等待它的回调设置标志吗?我可以使用 pthread 软件做一个多任务暂停的等待循环吗?

这是我目前的代码...

// 播放声音文件后恢复game_state继续游戏。 int game_state_after_sound; 无效 play_sound_file_done ( SystemSoundID ssID, void calling_class ) { printf("\n play_sound_file_done."); // 声音现在已经完成,所以恢复 game_state 并从中断的地方继续 manage_game: game_state = game_state_after_sound; [ (GeController)calling_class manage_game]; }

// Plays sound_file_m4a and returns after playing has completed.
-(void) play_sound_file: (NSString *) sound_file_m4a
{
    printf("\n play_sound_file '%s' ", [sound_file_m4a UTF8String] );
    NSString *soundPath = [[NSBundle mainBundle] pathForResource:sound_file_m4a ofType:@"m4a"]; 
    SystemSoundID soundID; 

    AudioServicesCreateSystemSoundID((CFURLRef)[NSURL fileURLWithPath: soundPath], &soundID); 
    AudioServicesPlaySystemSound (soundID); 
    AudioServicesAddSystemSoundCompletion ( soundID, NULL, NULL, play_sound_file_done, (void*)self ); 

    game_state_after_sound = game_state;
    game_state =  DELAY_WHILE_PLAYING_SOUND;
}

********************************** AVPlayer 工作中...

但这不会产生声音。

#import <AVFoundation/AVFfoundation.h> 

-(void) play_queued_sounds: (NSString *) sound_file_m4a
{
    printf("\n queue_sound_file: '%s' ", [sound_file_m4a UTF8String] );

    AVPlayerItem *sound_file = [[AVPlayerItem alloc] initWithURL:[NSURL URLWithString:[[NSBundle mainBundle] pathForResource:sound_file_m4a ofType:@"m4a"]]]; 
    AVQueuePlayer *player = [AVQueuePlayer queuePlayerWithItems:[NSArray arrayWithObjects:sound_file, nil]];  

    [player play]; 

    return;
}

【问题讨论】:

    标签: iphone ios audio xcode4


    【解决方案1】:

    这在AVQueuePlayer 中很容易实现。您不必处理完成或任何事情,只需给它您要按顺序播放的 AVPlayerItems 并调用 play。这是一个例子:

    #import <AVFoundation/AVFfoundation.h>
    
    
    //AVPlayerItem *item1 = [[AVPlayerItem alloc] initWithURL:[NSURL URLWithString:[[NSBundle mainBundle] pathForResource:@"myFileName" ofType:@"m4a"]]];
    

    编辑:改用这个

    AVPlayerItem *item1 = [[AVPlayerItem alloc] initWithURL:[NSURL fileURLWithPath:[[NSBundle mainBundle] pathForResource:[[NSString alloc] initWithFormat:@"2"] ofType:@"mp3"]]];
    
    AVQueuePlayer *player = [AVQueuePlayer queuePlayerWithItems:[NSArray arrayWithObjects:item1, nil]];
    
    [player play];
    

    此外,这也可以通过使用从 MPMediaPickerControllerdidPickMediaItems 委托方法排队的 MPMusicPlayerController 来实现用户 iPod 库中的项目

    - (void)mediaPicker:(MPMediaPickerController *)mediaPicker didPickMediaItems:(MPMediaItemCollection *)mediaItemCollection
    {
        MPMusicPlayerController *player = [MPMusicPlayerController applicationMusicPlayer];
        [player setQueueWithItemCollection:mediaItemCollection];
        [player play];
    }
    

    【讨论】:

    • 问题:如何指定一个 .m4a 文件让它播放?是否“[self.player play];”等大家玩完?
    • @DouglasK.Bell 我编辑了我的帖子,展示了如何从您的应用程序包中检索 m4a 并播放它。使用此代码,您必须为所有要使用的 m4a 创建 AVPlayerItems,将它们添加到队列播放器的数组中,然后当您调用 play 时,队列播放器将开始播放第一个,然后继续播放每个队列中的歌曲。
    • 即使我将 AVFoundation 类添加到我的 xcode4 目标,我也得到 AVQueuePlayer 的“未知类型”。呃。我忘记了#import。对不起。
    • @DouglasK.Bell 您是否将框架导入您的控制器?将#import &lt;AVFoundation/AVFfoundation.h&gt; 添加到头文件的顶部会消除此错误。
    • 注意:我正在使用 iPhone 语音备忘录创建 .m4a 声音。使用 AudioServicesPlaySystemSound 方法可以正常播放。
    【解决方案2】:

    我无法让 AVQueuePlayer 解决方案工作。

    很好的解决方案: 对于每个要播放的声音,启动一个等待然后锁定互斥锁的线程,然后执行 AudioServicesPlaySystemSound。只需为要播放的每个连续声音启动一个线程,并使用 pthread 互斥锁来延迟每个连续线程,直到 AudioServicesAddSystemSoundCompletion 函数解锁互斥锁。像冠军一样工作。

    这是 21 世纪的嵌入式编程:解决问题!

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2011-03-23
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多