【问题标题】:How to perform operations when playing sound in iPhone?iPhone播放声音时如何操作?
【发布时间】:2012-05-11 20:36:59
【问题描述】:

我使用 AVAudioPlayer 在我的 iPhone 应用程序中播放 MP3;我需要在特定时间(比如第 30 秒、1 分钟)执行一些操作;有没有办法根据 mp3 播放时间调用回调函数?

【问题讨论】:

  • 您必须自己创建这样的逻辑。使用计时器,根据播放状态启动/停止/重新启动该计时器(AVAudioPlayer 属性上的 KVO)。

标签: iphone avaudioplayer


【解决方案1】:

我相信最好的解决方案是在开始AVAudioPlayer 播放时开始NSTimer。您可以将计时器设置为每半秒左右触发一次。然后每次触发计时器时,查看音频播放器上的 currentTime 属性。

为了在特定的时间间隔内执行某些操作,我建议您为上次调用计时器回调时的播放时间保留一个实例变量。然后,如果您已经通过了上次回调和 this 之间的临界点,请执行您的操作。

所以,在伪代码中,定时器回调:

  1. 获取您的 AVAudioPlayer 的 currentTime
  2. 检查currentTime是否大于criticalPoint
  3. 如果是,检查lastCurrentTime是否小于criticalPoint
  4. 如果也同意,请采取行动。
  5. lastCurrentTime 设置为currentTime

【讨论】:

  • 遗憾的是,currentTime 不符合 KVO,因此计时器是您的最佳选择。
  • 在播放状态上添加KVO,通过停止/重新启动计时器来考虑暂停/停顿,这个解决方案应该是完美的。
【解决方案2】:

如果您能够使用 AVPlayer 而不是 AVAudioPlayer,您可以设置边界或周期性时间观察器:

// File URL or URL of a media library item
AVPlayer *player = [[AVPlayer alloc] initWithURL:url];        

CMTime time = CMTimeMakeWithSeconds(30.0, 600);
NSArray *times = [NSArray arrayWithObject:[NSValue valueWithCMTime:time]];

id playerObserver = [player addBoundaryTimeObserverForTimes:times queue:NULL usingBlock:^{
    NSLog(@"Playback time is 30 seconds");            
}];

[player play];

// remove the observer when you're done with the player:
[player removeTimeObserver:playerObserver];

AVPlayer 文档: http://developer.apple.com/library/ios/#documentation/AVFoundation/Reference/AVPlayer_Class/Reference/Reference.html

【讨论】:

    【解决方案3】:

    我发现this link 描述了一个似乎表明您可以获得当前播放时间的属性属性。

    如果声音正在播放,currentTime 是当前的偏移量 播放位置,从声音开始以秒为单位测量。如果 声音没有播放,currentTime 是播放位置的偏移量 从调用 play 方法开始,以秒为单位 声音的开始。

    通过设置此属性,您可以寻找声音中的特定点 文件或实现音频快进和快退功能。

    要检查时间并执行您的操作,您只需查询它:

    if (avAudioPlayerObject.currentTime == 30.0) //You may need a more broad check. Double may not be able to exactly represent 30.0s
    {
        //Do Something
    }
    

    【讨论】:

      【解决方案4】:

      使用多线程,您的目标很简单,只需这样做:

      1 :  in your main thread create a variable for storing time passed 
      2 :  create new thread like "checkthread" that check each 30-20 sec(as you need)
      3 :  if the time passed is what you want do the callback  
      

      【讨论】:

        【解决方案5】:

        是的,当然可以...这很棘手,我希望它对您有用,但对我有用..

        1- you play your mp3 file.
        

        2-[self performSelector:@selector(Operation:) withObject:Object afterDelay:30]; 然后是函数

        -(void)Operation:(id)sender;
        

        调用;所以你在 mp3 文件 30 秒后触发了函数..你可以根据你想要的时间制作许多函数..

        3- 还有其他使用计时器的解决方案

        [NSTimer scheduledTimerWithTimeInterval:0 target:self selector:@selector(CheckTime:) userInfo:nil repeats:YES];
        

        它会触发名为 Check Time 的函数

        -(void)CheckTime:(id)sender{
           if (avAudioPlayerObject.currentTime == 30.0)
           {
               //Do Something
               //Fire and function call such
               [self performSelector:@selector(Operation:) withObject:Object]
           }
        }
        

        然后你可以改变你想要的时间间隔和重复是为了让你控制是否每 5 秒重复一次这个动作.. 希望对您有所帮助..

        谢谢

        【讨论】:

        • 我认为您的第一个解决方案行不通:如果我在播放 10 秒后暂停音频文件的播放 1 秒,然后再继续播放会怎样。计时器会提前 1 秒触发。
        • 第二个应该可以工作,但我虽然用户没有控制声音暂停或恢复..但如果是这样你可以使用第二个解决方案..
        【解决方案6】:

        我认为,您想在 30 秒后播放不同的声音文件,然后使用以下代码:

        1) 将所有声音文件放入数组中,然后从文档目录中检索

        2)然后试试这个:

        -(IBAction)play_sound
        {
        
            BackgroundPlayer=[[AVAudioPlayer alloc]initWithContentsOfURL:[NSURL fileURLWithPath:[[NSBundle mainBundle]pathForResource:[Arr_tone_selected objectAtIndex:j]ofType:@"mp3"]]error:NULL];
            BackgroundPlayer.delegate=self;
        
            [BackgroundPlayer play];
        
        
        }   
        
        
        - (void)audioPlayerDidFinishPlaying:(AVAudioPlayer *)player successfully:(BOOL)flag
        {
            [BackgroundPlayer stop];
            j++;
            [self performSelector:@selector(play_sound) withObject:Object afterDelay:30];   
        }
        

        【讨论】:

        • 如果我在播放 10 秒后暂停音频文件的播放 1 秒然后继续播放会怎样。计时器会提前 1 秒触发。
        • 您的声音文件完成然后自动停止声音并在 30 秒后播放另一个声音文件,在我上面的代码中......你说我不清楚?
        • 我想我评论了错误的答案,但我认为你没有理解这个问题。 OP提到的“操作”可以是任何动作,而不仅仅是开始另一个声音。如果 OP 想要播放 45 秒长的曲目,但在播放 30 秒后仍执行该操作,该怎么办。他们没有提到他们想要播放的曲目的长度
        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2012-07-17
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多