Thanks for showing your code.
The critical thing in your code is this part:
do {
let audioPlayer = try AVAudioPlayer(contentsOf: storedURL, fileTypeHint: AVFileType.mp3.rawValue)
audioPlayer.play()
print("sound is playing")
} catch let error {
print("Sound Play Error.lDescription -> \(error.localizedDescription)")
print("Sound Play Error -> \(error)")
}
(As was shown in your first post, nice guess!)
The problem is that the variable audioPlayer is local to the do-catch block. So, it will be lost immediately after print("sound is playing"). With audioPlayer.play(), playing the audio is just started but not finished.
The instance of AVAudioPlayer needs to be held while playing.
Please try something like this:
struct ContentView: View {
let playerManager = AudioPlayerManager.shared //<-
@State var message: String = "Test Message2"
@State var storedURL: URL?
var body: some View {
Text(message)
.onTapGesture {
guard let path = Bundle.main.path(forResource: "selectSE", ofType: "mp3") else {
print("Sound file not found")
return
}
let url = URL(fileURLWithPath: path)
do {
let fileData = try Data(contentsOf: url)
storedURL = saveDataFile(data: fileData, fileName: "test.mp3", folderName: "testFolder")
print("File Writing on View -> Success \(storedURL?.absoluteString ?? "nil") ")
} catch {
print("Data.init(contentsOf:) failed: \(error)")
}
playerManager.play(url: storedURL!) //<-
print("end of code")
}
}
//...
}
class AudioPlayerManager {
static let shared = AudioPlayerManager()
var audioPlayer: AVAudioPlayer?
func play(url: URL) {
do {
audioPlayer = try AVAudioPlayer(contentsOf: url, fileTypeHint: AVFileType.mp3.rawValue) //<- No `let`
audioPlayer?.play()
print("sound is playing")
} catch let error {
print("Sound Play Error -> \(error)")
}
}
}
You have no need to copy the sound file each time onTapGesture, but it is not critical and you may improve it later.