版本记录
版本号 | 时间 |
---|---|
V1.0 | 2017.12.26 |
前言
ios系统中有很多方式可以播放音频文件,这里我们就详细的说明下播放音乐文件的原理和实例。感兴趣的可以看我写的上面几篇。
1. 几种播放音频文件的方式(一) —— 播放本地音乐
功能需求
音效播放,音频文件必须打包成.caf、.aif、.wav
中的一种。有时候有的mp3格式的声音文件也能播放,而且API限制了时间不能超过30s。
功能实现
这里同样使用框架 #import
1. 几个函数说明
由于该框架是基于C的框架,这里使用了其中的几个函数,下面我们就解析一下。
创建音效的ID,音效的播放和销毁都靠这个ID来执行。
AudioServicesCreateSystemSoundID(CFURLRef inFileURL, SystemSoundID* outSystemSoundID)
/*!
@functiongroup AudioServices
*/
/*!
@function AudioServicesCreateSystemSoundID
@abstract Allows the application to designate an audio file for playback by the System Sound server.
@discussion Returned SystemSoundIDs are passed to AudioServicesPlayAlertSoundWithCompletion()
and AudioServicesPlaySystemSoundWithCompletion() to be played.
The maximum supported duration for a system sound is 30 secs.
@param inFileURL
A CFURLRef for an AudioFile.
@param outSystemSoundID
Returns a SystemSoundID.
*/
extern OSStatus
AudioServicesCreateSystemSoundID( CFURLRef inFileURL,
SystemSoundID* outSystemSoundID)
__OSX_AVAILABLE_STARTING(__MAC_10_5,__IPHONE_2_0);
30s的音效限制就是在这里说明的。
播放音效
AudioServicesPlaySystemSound(SystemSoundID inSystemSoundID)
/*!
This function will be deprecated in a future release. Use AudioServicesPlaySystemSoundWithCompletion instead.
@function AudioServicesPlaySystemSound
@abstract Play the sound designated by the provided SystemSoundID.
@discussion A SystemSoundID indicating the desired System Sound to be played.
@param inSystemSoundID
A SystemSoundID for the System Sound server to play.
*/
extern void
AudioServicesPlaySystemSound(SystemSoundID inSystemSoundID)
__OSX_AVAILABLE_STARTING(__MAC_10_5,__IPHONE_2_0);
销毁音效的播放
AudioServicesDisposeSystemSoundID(SystemSoundID inSystemSoundID)
/*!
@function AudioServicesDisposeSystemSoundID
@abstract Allows the System Sound server to dispose any resources needed for the provided
SystemSoundID.
@discussion Allows the application to tell the System Sound server that the resources for the
associated audio file are no longer required.
@param inSystemSoundID
A SystemSoundID that the application no longer needs to use.
*/
extern OSStatus
AudioServicesDisposeSystemSoundID(SystemSoundID inSystemSoundID)
__OSX_AVAILABLE_STARTING(__MAC_10_5,__IPHONE_2_0);
ios9以前判断音效的完成
AudioServicesAddSystemSoundCompletion(SystemSoundID inSystemSoundID,CFRunLoopRef __nullable inRunLoop, CFStringRef __nullable inRunLoopMode,AudioServicesSystemSoundCompletionProc inCompletionRoutine,void * __nullable inClientData)
/*!
This function will be deprecated in a future release. Use AudioServicesPlayAlertSoundWithCompletion
or AudioServicesPlaySystemSoundWithCompletion instead.
@function AudioServicesAddSystemSoundCompletion
@abstract Call the provided Completion Routine when provided SystemSoundID
finishes playing.
@discussion Once set, the System Sound server will send a message to the System Sound client
indicating which SystemSoundID has finished playing.
@param inSystemSoundID
The SystemSoundID to associate with the provided completion
routine.
@param inRunLoop
A CFRunLoopRef indicating the desired run loop the completion routine should
be run on. Pass NULL to use the main run loop.
@param inRunLoopMode
A CFStringRef indicating the run loop mode for the runloop where the
completion routine will be executed. Pass NULL to use kCFRunLoopDefaultMode.
@param inCompletionRoutine
An AudioServicesSystemSoundCompletionProc to be called when the provided
SystemSoundID has completed playing in the server.
@param inClientData
A void* to pass client data to the completion routine.
*/
extern OSStatus
AudioServicesAddSystemSoundCompletion( SystemSoundID inSystemSoundID,
CFRunLoopRef __nullable inRunLoop,
CFStringRef __nullable inRunLoopMode,
AudioServicesSystemSoundCompletionProc inCompletionRoutine,
void * __nullable inClientData)
__OSX_AVAILABLE_STARTING(__MAC_10_5,__IPHONE_2_0);
ios9及其以后判断音效的完成
AudioServicesPlayAlertSoundWithCompletion( SystemSoundID inSystemSoundID,void (^__nullable inCompletionBlock)(void))
/*!
@function AudioServicesPlayAlertSoundWithCompletion
@abstract Play an alert sound
@discussion Play the sound designated by the provided SystemSoundID with alert sound behavior.
@param inSystemSoundID
The SystemSoundID to be played. On the desktop the kSystemSoundID_UserPreferredAlert
constant can be passed in to play back the alert sound selected by the user
in System Preferences. On iOS there is no preferred user alert sound.
@param inCompletionBlock
The completion block gets executed for every attempt to play a system sound irrespective
of success or failure. The callbacks are issued on a serial queue and the client is
responsible for handling thread safety.
*/
extern void
AudioServicesPlayAlertSoundWithCompletion( SystemSoundID inSystemSoundID,
void (^__nullable inCompletionBlock)(void))
__OSX_AVAILABLE_STARTING(__MAC_10_11, __IPHONE_9_0);
AudioServicesPlaySystemSoundWithCompletion(SystemSoundID inSystemSoundID, void (^__nullable inCompletionBlock)(void))
/*!
@function AudioServicesPlaySystemSoundWithCompletion
@abstract Play a system sound
@discussion Play the sound designated by the provided SystemSoundID.
@param inSystemSoundID
The SystemSoundID to be played.
@param inCompletionBlock
The completion block gets executed for every attempt to play a system sound irrespective
of success or failure. The callbacks are issued on a serial queue and the client is
responsible for handling thread safety.
*/
extern void
AudioServicesPlaySystemSoundWithCompletion( SystemSoundID inSystemSoundID,
void (^__nullable inCompletionBlock)(void))
__OSX_AVAILABLE_STARTING(__MAC_10_11, __IPHONE_9_0);
带有震动的播放
AudioServicesPlayAlertSound(SystemSoundID inSystemSoundID)
/*!
This function will be deprecated in a future release. Use AudioServicesPlayAlertSoundWithCompletion instead.
@function AudioServicesPlayAlertSound
@abstract Play an Alert Sound
@discussion Play the provided SystemSoundID with AlertSound behavior.
@param inSystemSoundID
A SystemSoundID for the System Sound server to play. On the desktop you
can pass the kSystemSoundID_UserPreferredAlert constant to playback the alert sound
selected by the user in System Preferences. On iOS there is no preferred user alert sound.
*/
extern void
AudioServicesPlayAlertSound(SystemSoundID inSystemSoundID)
__OSX_AVAILABLE_STARTING(__MAC_10_5,__IPHONE_2_0);
2. 代码实现
下面直接看代码
#import "ViewController.h"
#import
@interface ViewController ()
@end
@implementation ViewController
static SystemSoundID soundID = 0;
#pragma mark - Override Base Function
- (void)viewDidLoad
{
[super viewDidLoad];
self.view.backgroundColor = [UIColor whiteColor];
//UI界面
[self initUI];
}
#pragma mark - Object Private Function
void soundCompleteCallBack(SystemSoundID soundID, void * clientDate)
{
NSLog(@"播放完成");
AudioServicesDisposeSystemSoundID(soundID);
}
- (void)playMusic
{
//获取资源地址
NSString *str = [[NSBundle mainBundle] pathForResource:@"sound" ofType:@"m4a"];
NSURL *url = [NSURL fileURLWithPath:str];
// 创建音效的ID,音效的播放和销毁都靠这个ID来执行
AudioServicesCreateSystemSoundID((__bridge CFURLRef _Nonnull)(url), &soundID);
//带有声音和震动的播放
if ([UIDevice currentDevice].systemVersion.floatValue >= 9.0) {
AudioServicesPlayAlertSoundWithCompletion(soundID, ^{
NSLog(@"播放完成");
});
}
else {
AudioServicesAddSystemSoundCompletion(soundID, NULL, NULL, soundCompleteCallBack, NULL);
};
}
- (void)stopMusic
{
AudioServicesDisposeSystemSoundID(soundID);
}
- (void)initUI
{
UIButton *button = [UIButton buttonWithType:UIButtonTypeCustom];
button.frame = CGRectMake((self.view.bounds.size.width - 200.0) * 0.5, (self.view.bounds.size.height - 200.0) * 0.5, 200.0, 200.0);
button.backgroundColor = [UIColor lightGrayColor];
button.layer.cornerRadius = 100.0;
button.layer.masksToBounds = YES;
[button setTitle:@"开始播放" forState:UIControlStateNormal];
[button setTitle:@"停止播放" forState:UIControlStateSelected];
[button setTitleColor:[UIColor blueColor] forState:UIControlStateNormal];
[button setTitleColor:[UIColor blueColor] forState:UIControlStateSelected];
[button addTarget:self action:@selector(playButtonDidClick:) forControlEvents:UIControlEventTouchUpInside];
[self.view addSubview:button];
}
#pragma mark - Action && Notification
- (void)playButtonDidClick:(UIButton *)button
{
button.selected = !button.selected;
if (button.selected) {
[self playMusic];
}
else {
[self stopMusic];
}
}
@end
这里是播放声音的同时,AudioServicesPlayAlertSoundWithCompletion
,也有震动。
功能验证
这里带有声音和震动,我就没办法给大家验证了,只能给出一个基本的界面。
后记
未完,待续~~~