I'm (unsuccessfully) trying to play an audio file stored in Firebase using AVAudioPlayer.
I'm getting the following error message: Error creating audio player: The operation couldn’t be completed. (OSStatus error 2003334207.)
Here's the code for my Audio Player View Model:
class AudioPlayerViewModel: ObservableObject {
private var audioPlayer: AVAudioPlayer?
func playAudioFromUrl(from storagePath: String) {
let storage = Storage.storage()
let storageRef = storage.reference()
let audioRef = storageRef.child(storagePath)
audioRef.downloadURL { url, error in
print(audioRef)
guard let audioURL = url, error == nil else {
print("Error fetching audio URL: \(error?.localizedDescription ?? "")")
return
}
print("Audio URL: \(audioURL)")
print("Audio URL String: \(audioURL.absoluteString)")
do {
self.audioPlayer = try AVAudioPlayer(contentsOf: audioURL)
self.audioPlayer?.prepareToPlay()
self.audioPlayer?.play()
} catch {
print("Error creating audio player: \(error.localizedDescription)")
if let nsError = error as NSError? {
print("Error code: \(nsError.code)")
}
}
}
}
func stopAudio() {
audioPlayer?.stop()
}
}
And the code for my view:
struct PlaybackControlsView: View {
var audioPath: String
@ObservedObject private var audioPlayerVM = AudioPlayerViewModel()
var body: some View {
VStack {
// Add UI elements here, e.g., play and stop buttons
Button("Play Audio") {
audioPlayerVM.playAudioFromUrl(from: "Stories/\(audioPath).mp3")
}
.padding()
Button("Stop Audio") {
audioPlayerVM.stopAudio()
}
.padding()
}
}
}
#Preview {
PlaybackControlsView(audioPath: "example")
}
Not sure where I'm going wrong here. Any help would be greatly appreciated.
You could try this approach using AVPlayer
with a url, instead of
the AVAudioPlayer
that seems to only play audio data from a file or buffer.
class AudioPlayerViewModel2: ObservableObject {
private var audioPlayer: AVPlayer? // <-- here
func playAudioFromUrl(from storagePath: String) {
let storage = Storage.storage()
let storageRef = storage.reference()
let audioRef = storageRef.child(storagePath)
audioRef.downloadURL { url, error in
print(audioRef)
guard let audioURL = url, error == nil else {
print("Error fetching audio URL: \(error?.localizedDescription ?? "")")
return
}
print("Audio URL: \(audioURL)")
print("Audio URL String: \(audioURL.absoluteString)")
// --- here
let playerItem = AVPlayerItem(url: audioURL)
self.audioPlayer = AVPlayer(playerItem: playerItem)
self.audioPlayer?.volume = 10
self.audioPlayer?.play()
}
}
func stopAudio() {
audioPlayer?.pause()
}
}