在应用程序内控制AVAudioSession.Mode.voicePrompt的音量

时间:2019-03-25 16:08:39

标签: ios swift avfoundation text-to-speech

我正在使用文本在项目中进行语音语音转换。从iOS 12开始,Apple引入了一个名为AVAudioSession.Mode的新voicePrompt。 这个功能与其他功能完全不同,例如,它具有自己的音量滑块,例如与Apple Maps应用共享。

当用户按下提高音量按钮时,它会使用AVAudioSession模式更改系统范围的音量,但不会更改voicePrompt的范围。 但是,如果使用voicePrompt的应用当前正在播放音频,则电话音量按钮现在可以完全独立于其他全局设置来控制这组音量。

与我认为已经存在一段时间的Android不同,在iOS上看到它很奇怪。我可能会误认为这个假设,但是关键是我想采用一种应用程序内方式来控制此音量,因为几乎所有应用程序用户都不了解这种行为。 他们不了解,要更改音量,应用必须先积极播放音频/使用SpeechSyntheziser,然后才能更改与之关联的音量。

导入MPVolumeView时,可以通过使用MediaPlayer在应用程序内部控制全局音量。 有人知道如何从应用程序内部控制voicePrompt模式的音量吗?

1 个答案:

答案 0 :(得分:0)

根据我的经验,从音量角度来看,voicePrompt模式与默认模式没有什么不同。您可以通过更改媒体音量(实际上是通过MPVolumeView)来更改音量:

默认情况下,如果没有媒体正在播放,则硬件音量按钮将始终控制系统音量(铃声和警报声音)。如果正在播放媒体,则它们控制“媒体”的音量。 (我同意这一定会让用户感到困惑)但这是标准行为,不能在代码中更改。用户可以在iOS设置应用>声音和触觉>使用按钮更改中更改此设置。

不确定是否会对您有所帮助,但我编写了此扩展程序来更改您应用中的媒体音量:

extension MPVolumeView {
static func setVolume(_ volume: Float) {
    let volumeView = MPVolumeView(frame: .zero)
    if let slider = volumeView.subviews.first(where: { $0 is UISlider }) as? UISlider {
        DispatchQueue.main.asyncAfter(deadline: DispatchTime.now() + 0.02) {
            slider.value = volume
        }
        // Optional - Remove the HUD
        // if let app = UIApplication.shared.delegate as? AppDelegate, let window = app.window {
        //    volumeView.alpha = 0.000001
        //    window.addSubview(volumeView)
        // }
    }
}

static func changeVolume(change: Float) {
    let volumeView = MPVolumeView(frame: .zero)
    if let slider = volumeView.subviews.first(where: { $0 is UISlider }) as? UISlider {
        DispatchQueue.main.asyncAfter(deadline: DispatchTime.now() + 0.02) {
            let currentVolume = round(slider.value * 16)/16
            slider.value = currentVolume + change
        }
        // Optional - Remove the HUD
        // if let app = UIApplication.shared.delegate as? AppDelegate, let window = app.window {
        //    volumeView.alpha = 0.000001
        //    window.addSubview(volumeView)
        // }
    }
}

static func increaseVolume() {
    MPVolumeView.changeVolume(change: 1/16)
}

static func decreaseVolume() {
    MPVolumeView.changeVolume(change: -1/16)
}
}

现在,这将更改媒体音量。您可以为应用中播放的语音到语音或声音文件设置不同的音量。

要更改声音文件的音量,请使用

AVPlayerInstance.volume = 0.5 

要将语音量更改为语音,我们

AVSpeechUtteranceInstance.volume = 0.5

但是:您在此处设置的音量值与媒体音量相关。因此,最多,您的声音可以像媒体播放的声音一样响亮,再也不会响亮! (如果有办法,请告诉我,因为我认为即使在回避音乐时,尤其是在使用蓝牙耳机或车载设备时,我的文本到语音提示也应该响亮。)

到目前为止,我还没有发现默认模式和voicePrompt模式之间的任何区别(我希望它可能会增加文本到语音的音量,但不会)。它的文档当前没有说出任何有用的信息,因此就目前而言,我不使用.voicePrompt模式。至少直到获得更多有关其特定用途和差异的文档为止。 (如果您知道有什么不同,请很好奇,让我知道。)