使用AVAudioPlayer播放MP3在设备上无法工作

19

我正在用iOS 4.2的3GS iPhone测试我的应用。

我使用以下代码在我的IBAction中播放声音。在模拟器中(iPad和iPhone都是),它完美地工作 - 我可以听到声音。

NSString *pathToMusicFile1 = [[NSBundle mainBundle] pathForResource:@"alarm" ofType:@"mp3"];
NSError *error;
alarmSound = [[AVAudioPlayer alloc]initWithContentsOfURL:[NSURL fileURLWithPath:pathToMusicFile1] error:&error]; 
NSLog(@"Song1 Loaded");
if (alarmSound == nil) {
    NSLog(@"Error playing sound");
} else {
    alarmSound.numberOfLoops = 20;
    alarmSound.volume = 1.0;
    [alarmSound play];
}

我已经正确地声明了所有的头文件和框架等,因为我可以在模拟器中听到声音。

我也检查过我的手机没有静音!我从 iPhone 的通用 GUI 中听到其他声音。(例如日期选择器)

我还清理了所有目标并删除了应用程序以重新安装。

有什么想法是错的吗?!

4个回答

48

所以,我也遇到了这个问题 - 我非常确定它是同一个问题......

我们的应用在应用商店中已经有一年左右的时间,最近我们需要更改一些内容,尽管没有任何实际功能上的变化。

突然间,声音停止工作了 - 在最新的 sdk 版本(版本 4.0)中的模拟器和设备上(再次运行 iOS 4)均如此。

对我们一直有效的代码是这样的...

NSString *sound_file;
if ((sound_file = [[NSBundle mainBundle] pathForResource:@"track1" ofType:@"mp3"])){

NSURL *url = [[NSURL alloc] initFileURLWithPath:sound_file];
audioPlayer = [[AVAudioPlayer alloc] initWithContentsOfURL:url error:NULL];
audioPlayer.delegate = self;
[url release];

[audioPlayer prepareToPlay];
[audioPlayer play];

}

最后,我发现您现在需要设置AVAudioSession播放类型,才能像以前一样通过扬声器播放声音! 将以下代码行放入您的应用程序委托applicationDidFinishLaunching事件处理程序中...

- (void)applicationDidFinishLaunching:(UIApplication *)application {

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

不要忘记在你的应用代理文件.h中添加include(如果还没有导入AVFoundation框架,则需要导入)...

#import <AVFoundation/AVAudioSession.h>
希望现在你的设备可以播放声音了。不要被我认为可能是另一个问题所困扰,即声音仍然无法在模拟器中播放。我看到其他帖子表明这种情况,但我不确定这有多普遍。我发现如果我选择iPad 3.2作为模拟器,它至少在那个上面工作了。太棒了!对我来说似乎很疯狂的是,这肯定会影响很多人,但很难找到关于这个应该是相当知名的问题的信息或建议 - 毕竟,我在论坛上看到了许多没有得到答复的帖子。无论如何,希望这可以帮助其他人。

哇,这个方法对我有用,我遇到了同样的问题,谢谢@Jon Andrews! - Dhaval Panchal
4
据我所知,代码[[AVAudioSession sharedInstance] setCategory:AVAudioSessionCategoryPlayback error:nil];会简单地覆盖静音开关并允许在手机锁屏时播放声音。 - epetousis
终于!花了一个小时的谷歌搜索、转换、导入、尝试,最终终于成功了。非常感谢! - karpathy
希望我能加100。非常感谢@Jon。 - Yama
太棒了!我可以解决类似的问题。在我的情况下,它在iOS5设备上无法工作,但模拟器可以。谢谢。 - zono
谢谢你的提示!代码在 iPhone 上完美运行,但在 iPad 4 上没有任何反应。我从未意识到它设置了静音开关(音量也很低,但调高音量也没有任何改变)。 - gnasher729

26

将"audioPlayer"变量作为属性非常重要,特别是在ARC下,否则它会在播放之前被释放!

我花费了半个小时并进行了一些搜索,才有了这个顿悟时刻。

现在我的声音完美无缺!


5
经过整整一个小时的头痛,我终于找到了这篇文章。谢谢。 - James Boutcher
太棒了!你让我的一天都变得美好了! :) - Krutika Sonawala

17

我的问题是iOS在文件得到播放的机会之前自动释放了我的AVAudioPlayer实例。奇怪的是,这只发生在MP3文件上,而不是AU文件上。解决方法是不要将其设置为autorelease,然后在委托方法中释放它...

- (void)playSound:(NSString *)sound
{
    AVAudioPlayer *audioPlayer = [[AVAudioPlayer alloc] initWithContentsOfURL:[NSURL fileURLWithPath:[[NSBundle mainBundle] pathForResource:sound ofType:@""]] error:NULL];
    audioPlayer.delegate = self;
    [audioPlayer play];
}

...然后在委托方法中...

- (void)audioPlayerDidFinishPlaying:(AVAudioPlayer *)player successfully:(BOOL)flag
{
    [player release];
}

现在运作良好。


19
ARC 在播放器播放前就释放了它。将播放器设置为属性解决了这个问题。 - Andy
1
ARC 对我也造成了同样的问题,将其作为属性解决了。谢谢 Andy。 - AndyDunn
我曾经遇到过同样的问题,这个方法很有效。 - Halle

1

你试过使用 [NSURL URLWithString:pathToMusicFile1]; 而不是 fileURLWithPath: 吗?


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接