IOS:AVAudioSession 不工作
Posted
技术标签:
【中文标题】IOS:AVAudioSession 不工作【英文标题】:IOS: AVAudioSession not working 【发布时间】:2018-08-10 17:45:42 【问题描述】:我正在尝试使用 AVAudiosession,但它抛出了这个运行时错误:
[avas] AVAudioSessionPortImpl.mm:56:ValidateRequiredFields:Unknown selected data source for Port Speaker (type Speaker)
。如果它有帮助,我正在尝试只录制音频,并监控当前的分贝。我将类别设置为AVAudioSessionCategoryRecord
,将模式设置为AVAudioSessionModeMeasurement
。
这是代码:
class ViewController: UIViewController
let captureSession = AVCaptureSession()
var recording = false;
var ready = false;
let audioSession = AVAudioSession.sharedInstance()
@IBOutlet public weak var dBLabel: UILabel!
func alert(title: String, message: String = "", handler: ((UIAlertAction) -> Swift.Void)? = nil) -> Void
var usedMessage: String
if(message.characters.count < 1)
usedMessage = title;
else
usedMessage = message;
let alert = UIAlertController(title: title, message: usedMessage, preferredStyle: .alert)
alert.addAction(UIAlertAction(title: NSLocalizedString("OK", comment: "Default action"), style: .default, handler: handler))
self.present(alert, animated: true, completion: nil)
override func viewDidLoad()
super.viewDidLoad()
func checkPermission()
switch AVCaptureDevice.authorizationStatus(forMediaType: AVMediaTypeAudio)
case .authorized:
NSLog("Authorized for Microphone Use")
case .notDetermined:
AVCaptureDevice.requestAccess(forMediaType: AVMediaTypeAudio, completionHandler: granted in
self.checkPermission()
)
case .denied:
let alert = UIAlertController(title: "Denied Access to Microphone", message: "You denied access to the microphone, please enable access in settings", preferredStyle: .alert)
alert.addAction(UIAlertAction(title: "Go to Settings", style: .default, handler: _ in
guard let settingsUrl = URL(string: UIApplicationOpenSettingsURLString) else
return
if UIApplication.shared.canOpenURL(settingsUrl)
UIApplication.shared.open(settingsUrl, completionHandler: (success) in
)
))
alert.addAction(UIAlertAction(title: NSLocalizedString("Cancel", comment: "Cancel"), style: .cancel, handler: nil))
self.present(alert, animated: true, completion: nil)
case .restricted:
alert(title: "Restricted",message: "You cannot enable the microphone, so you cannot use the app", handler: _ in
NSLog("The \"OK\" alert occured.")
)
@IBAction func toggleRecord(_ sender: UIButton)
if(!ready)
return
NSLog("Toggled Recording")
recording = !recording;
if(recording)
sender.setImage(UIImage(named: "MicIconHighlighted.png"), for: .normal)
sender.setImage(UIImage(named: "MicIconHighlightedSelected.png"), for: .highlighted)
//captureSession.startRunning()
do
try audioSession.setActive(true)
catch
NSLog("Activating AudioSession Failed")
else
sender.setImage(UIImage(named: "MicIcon.png"), for: .normal)
sender.setImage(UIImage(named: "MicIconSelected.png"), for: .highlighted)
//captureSession.stopRunning()
do
try audioSession.setActive(false)
catch
NSLog("Deactivating AudioSession Failed")
override func viewDidAppear(_ animated: Bool)
super.viewDidAppear(animated)
checkPermission()
do
try audioSession.setCategory(AVAudioSessionCategoryPlayAndRecord)
catch
NSLog("Setting category on AudioSession failed")
do
try audioSession.setMode(AVAudioSessionModeMeasurement)
catch
NSLog("Setting mode on AudioSession failed")
do
try audioSession.overrideOutputAudioPort(AVAudioSessionPortOverride.speaker)
catch
NSLog("Failed Setting Audio Output Data Source")
//NSLog("debug info: \(audioSession.outputDataSources!.count)");
/*captureSession.beginConfiguration()
let audioDeviceInput: AVCaptureDeviceInput
let audioDevice = AVCaptureDevice.defaultDevice(withMediaType: AVMediaTypeAudio)
if(audioDevice != nil && (audioDevice?.isConnected)!)
NSLog("Audio Device Name: \(audioDevice!.localizedName)")
else
NSLog("AVCapture Device default audio device failed or device not connected")
do
audioDeviceInput = try AVCaptureDeviceInput(device: audioDevice)
catch
alert(title: "Failed to create Capture Device",message: "Failed to create Capture Device", handler: nil)
return
if(captureSession.canAddInput(audioDeviceInput))
captureSession.addInput(audioDeviceInput)
else
alert(title: "Failed to Add Input",message: "Failed to add Audio Input Device", handler: nil)
let audioOutput = AVCaptureAudioDataOutput()
var audioRecorder = AVAudioRecorder()
audioRecorder.
var audioQueue = DispatchQueue(label: "audioqueue", attributes: .concurrent)
audioOutput.setSampleBufferDelegate(AudioOutputSampleBufferDelegate(vc: self), queue: audioQueue)
NSLog("Current Queue: \(audioOutput.sampleBufferCallbackQueue.description)")
if(captureSession.canAddOutput(audioOutput))
captureSession.addOutput(audioOutput)
captureSession.commitConfiguration()
else
alert(title: "Failed to Add Output",message: "Failed to add Audio Output Device", handler: nil)
*/
ready = true
override func didReceiveMemoryWarning()
super.didReceiveMemoryWarning()
// Dispose of any resources that can be recreated.
【问题讨论】:
如果您在设置 AVAudioSession 参数的位置共享代码会很有帮助 我更新了它以包含类别和模式 尝试将 AVAudioSessionCategoryRecord 更改为 AVAudioSessionCategoryPlayAndRecord 它仍然给出那个错误。问题是,我设置了它(使用上面的设置)并将其设置为活动状态,但除此之外我什么也不做。我什至不需要播放功能。我也尝试使用 AVCaptureSession,它给出了同样的错误 我在 iOS 12 官方版本和 XCode 10 官方版本中看到了同样的错误。关于如何修复它的任何意见? 【参考方案1】:AVAudioSession 在 Swift 4.2 中有一些变化
在 viewDidAppear() 下,试试这个:
// Prepare Audio Session
self.audioSession = AVAudioSession.sharedInstance()
try audioSession.setCategory(AVAudioSession.Category.playAndRecord, mode: .measurement, options: .defaultToSpeaker)
try audioSession.setActive(true, options: .notifyOthersOnDeactivation)
当我在 Xcode 10 中将语言转换为 Swift 4.2 时,它对我有用 你可以去...
编辑、转换、到当前的 Swift 语法...
【讨论】:
太棒了。这对我有用。我仍然收到错误消息:“AVAudioSessionPortImpl.mm:56:ValidateRequiredFields: Unknown selected data source for Port Speaker (type: Speaker)”。但是在添加 try audioSession.setActive(false, options: .notifyOthersOnDeactivation) 之后,audiosession 被正确停用,任何其他 audioSession 恢复播放。【参考方案2】:在 viewWillAppear() 中粘贴 AVAudioSession 有一些变化,更正了 Swift 5.0 的语法 声明 var recordingSession: AVAudioSession!
recordingSession = AVAudioSession.sharedInstance()
do
try recordingSession.setCategory(.playAndRecord, mode: .spokenAudio, options: .defaultToSpeaker)
try recordingSession.setActive(true, options: .notifyOthersOnDeactivation)
recordingSession.requestRecordPermission() [unowned self] allowed in
DispatchQueue.main.async
if allowed
self.loadRecorder()
else
// failed to record!
catch
// failed to record!
`
【讨论】:
以上是关于IOS:AVAudioSession 不工作的主要内容,如果未能解决你的问题,请参考以下文章
ios开发之--AVAudioPlayer制作了一款播放器,耳机有声音,扬声器没声音
AVAudioSession.requestRecordPermission 不显示对话框