Swiftで短いサウンドファイルを再生する

環境: Swift3

今回はpico.mp3という効果音ファイルがあり、それを再生する例。
まずは、このファイルをXcodeのプロジェクトに右クリックのAdd Files to **から追加する。
TARGETのBuild Phases->Copy Bundle Resourcesに追加したファイルが含まれていることを確認する。
そして以下コードを実行する。

import AudioToolbox

func playSound() {
    let url = Bundle.main.url(forResource: "pico", withExtension: "mp3")!
    var soundID: SystemSoundID = 0
    AudioServicesCreateSystemSoundID(url as CFURL, &soundID)
    AudioServicesPlaySystemSound(soundID)
}

これで再生することはできた。
が、調べていくとサウンドリソースの解放処理も入れたほうがよいらしい。
そこでPlayの後にDisposeを入れてみると、サウンドが再生されなくなった。

func playSound() {
    let url = Bundle.main.url(forResource: "pico", withExtension: "mp3")!
    var soundID: SystemSoundID = 0
    AudioServicesCreateSystemSoundID(url as CFURL, &soundID)
    AudioServicesPlaySystemSound(soundID)
    AudioServicesDisposeSystemSoundID(soundID) // サウンドが再生されなくなった
}

サウンド再生完了後に処理を実行できるAudioServicesAddSystemSoundCompletionというコールバック関数(クロージャの第1引数にsoundIDが入ってくる)があったので、そこでDisposeするように修正した。

func playSound() {
    let url = Bundle.main.url(forResource: "pico", withExtension: "mp3")!
    var soundID: SystemSoundID = 0
    AudioServicesCreateSystemSoundID(url as CFURL, &soundID)
    AudioServicesAddSystemSoundCompletion(soundID, nil, nil, { (soundID, _) in
        AudioServicesDisposeSystemSoundID(soundID)
    }, nil)
    AudioServicesPlaySystemSound(soundID)
}

これでOK

AudioServicesPlaySystemSoundで再生したサウンドの音量が変更できない問題

AudioServicesPlaySystemSoundで再生したサウンドの音量が固定でiPhoneの音量設定に合わせて変更できないことに気づいた。
一応、iPhoneの設定-> サウンドと触覚 -> ボタンで変更 をONにすることでiPhoneの音量設定に合わせて変更できるようになる。

f:id:xyk:20170221103719p:plain f:id:xyk:20170221103721p:plain

ここがOFFだとアプリ側では制御できないので、音量を制御したい場合はAVAudioPlayerを使ったほうがよいかもしれない。