![](/img/trans.png)
[英]Audio played using AVAudioPlayer is working in iPhone Simulator but not in the Device
[英]AVAudioPlayer working on Simulator but not on Real Device
當我播放錄制的音頻時,我收到此錯誤:
致命錯誤:在展開Optional值時意外發現nil
在這行代碼上:
SoundPlayer = try AVAudioPlayer(contentsOfURL: getFileURL())
但它在模擬器上完美運行,除了真實設備。
ViewController.Swift:
import UIKit
import AVFoundation
class ViewController: UIViewController, AVAudioPlayerDelegate, AVAudioRecorderDelegate {
@IBOutlet var PlayBTN: UIButton!
@IBOutlet var RecordBTN: UIButton!
var soundRecorder : AVAudioRecorder!
var SoundPlayer : AVAudioPlayer!
var fileName = "audioFile.m4a"
override func viewDidLoad() {
super.viewDidLoad()
// Do any additional setup after loading the view, typically from a nib.
setupRecorder()
}
override func didReceiveMemoryWarning() {
super.didReceiveMemoryWarning()
// Dispose of any resources that can be recreated.
}
func setupRecorder(){
let recordSettings = [AVSampleRateKey : NSNumber(float: Float(44100.0)),
AVFormatIDKey : NSNumber(int: Int32(kAudioFormatMPEG4AAC)),
AVNumberOfChannelsKey : NSNumber(int: 1),
AVEncoderAudioQualityKey : NSNumber(int: Int32(AVAudioQuality.Max.rawValue))]
do{
try soundRecorder = AVAudioRecorder(URL: getFileURL(), settings: recordSettings)
soundRecorder.delegate = self
soundRecorder.prepareToRecord()
}
catch let error as NSError {
error.description
}
}
func getCacheDirectory() -> String {
let paths = NSSearchPathForDirectoriesInDomains(NSSearchPathDirectory.DocumentDirectory, NSSearchPathDomainMask.UserDomainMask, true)
return paths[0]
}
func getFileURL() -> NSURL{
let path = (getCacheDirectory() as NSString).stringByAppendingPathComponent(fileName)
let filePath = NSURL(fileURLWithPath: path)
return filePath
}
@IBAction func Record(sender: UIButton) {
if sender.titleLabel?.text == "Record"{
soundRecorder.record()
sender.setTitle("Stop", forState: .Normal)
PlayBTN.enabled = false
}
else{
soundRecorder.stop()
sender.setTitle("Record", forState: .Normal)
PlayBTN.enabled = false
}
}
@IBAction func PlaySound(sender: UIButton) {
if sender.titleLabel?.text == "Play" {
RecordBTN.enabled = false
sender.setTitle("Stop", forState: .Normal)
preparePlayer()
SoundPlayer.play()
}
else{
SoundPlayer.stop()
sender.setTitle("Play", forState: .Normal)
}
}
func preparePlayer(){
do{
SoundPlayer = try AVAudioPlayer(contentsOfURL: getFileURL())
SoundPlayer.delegate = self
SoundPlayer.volume = 1.0
SoundPlayer.prepareToPlay()
}
catch let error as NSError {
error.description
}
}
func audioRecorderDidFinishRecording(recorder: AVAudioRecorder, successfully flag: Bool) {
PlayBTN.enabled = true
}
func audioPlayerDidFinishPlaying(player: AVAudioPlayer, successfully flag: Bool) {
RecordBTN.enabled = true
PlayBTN.setTitle("Play", forState: .Normal)
}
@IBAction func actDone(sender: AnyObject) {
//viewRecorder.hidden = true
let fm = NSFileManager.defaultManager()
let documentsDirectory = NSSearchPathForDirectoriesInDomains(.DocumentDirectory, .UserDomainMask, true)[0] as String
do {
let items = try fm.contentsOfDirectoryAtPath(documentsDirectory)
for item in items {
print(item)
}
}
catch let error as NSError {
error.description
}
}
}
ViewController.Swift的Storyboard文件:
附加信息:
注意:我已經尋找類似的SO解決方案,但沒有一個幫助我。 其中一些是由於較舊的Swift版本和不推薦使用的方法。 一些解決方案涉及從應用程序包播放音頻文件,一些使用Web URL。 所以,這種情況不同( Real Device vs Simulator )
以下是Google雲端硬盤中源代碼的鏈接。
在真實設備上,需要為setCategory()
設置AVAudioSession.sharedInstance()
這里也可以下載固定項目。
func setupRecorder(){
let audioSession = AVAudioSession.sharedInstance()
do {
try audioSession.setCategory(AVAudioSessionCategoryPlayAndRecord)
} catch let error as NSError {
print(error.description)
}
let recordSettings = [AVSampleRateKey : NSNumber(float: Float(44100.0)),
AVFormatIDKey : NSNumber(int: Int32(kAudioFormatMPEG4AAC)),
AVNumberOfChannelsKey : NSNumber(int: 1),
AVEncoderAudioQualityKey : NSNumber(int: Int32(AVAudioQuality.Max.rawValue))]
do{
try soundRecorder = AVAudioRecorder(URL: getFileURL(), settings: recordSettings)
soundRecorder.delegate = self
soundRecorder.prepareToRecord()
}
catch let error as NSError {
error.description
}
}
注意:音頻會話是您的應用和iOS之間的中介,用於配置應用的音頻行為。 如果我們為AVAudioSessionCategoryPlayAndRecord
設置類別,我們定義iOS音頻行為以允許音頻輸入(錄制)和輸出(播放)。 參考: 音頻會話編程指南
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.