Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

increase volume of audio file recorded with swift

Tags:

file

swift

audio

I am developing an application with swift. I would like to be able to increase the volume of a recorded file. Is there a way to do it directly inside the application? I found Audiokit Here and this question but it didn't help me much.

Thanks!

like image 355
Quentin Del Avatar asked Sep 11 '16 08:09

Quentin Del


2 Answers

With AudioKit

Option A: Do you just want to import a file, then play it louder than you imported it? You can use an AKBooster for that.

import AudioKit

do {
    let file = try AKAudioFile(readFileName: "yourfile.wav")
    let player = try AKAudioPlayer(file: file)
    // Define your gain below. >1 means amplifying it to be louder
    let booster = AKBooster(player, gain: 1.3)
    AudioKit.output = booster
    try AudioKit.start()
    // And then to play your file:
    player.play()
} catch {
    // Log your error
}

Just set the gain value of booster to make it louder.


Option B: You could also try normalizing the audio file, which essentially applies a multiple constant across the recording (with respect to the highest signal level in the recording) so it reaches a new target maximum that you define. Here, I set it to -4dB.

let url = Bundle.main.url(forResource: "sound", withExtension: "wav")
if let file = try? AKAudioFile(forReading: url) {
    // Set the new max level (in dB) for the gain here.
    if let normalizedFile = try? file.normalized(newMaxLevel: -4) {
        print(normalizedFile.maxLevel)
        // Play your normalizedFile...
    }
}

This method increases the amplitude of everything to a level of dB - so it won't effect the dynamics (SNR) of your file, and it only increases by the amount it needs to reach that new maximum (so you can safely apply it to ALL of your files to have them be uniform).


With AVAudioPlayer

Option A: If you want to adjust/control volume, AVAudioPlayer has a volume member but the docs say:

The playback volume for the audio player, ranging from 0.0 through 1.0 on a linear scale.

Where 1.0 is the volume of the original file and the default. So you can only make it quieter with that. Here's the code for it, in case you're interested:

let soundFileURL = Bundle.main.url(forResource: "sound", withExtension: "mp3")!
let audioPlayer = try? AVAudioPlayer(contentsOf: soundFileURL, fileTypeHint: AVFileType.mp3.rawValue)
audioPlayer?.play()
// Only play once
audioPlayer?.numberOfLoops = 0
// Set the volume of playback here.
audioPlayer?.volume = 1.0

Option B: if your sound file is too quiet, it might be coming out the receiver of the phone. In which case, you could try overriding the output port to use the speaker instead:

do {
    try AVAudioSession.sharedInstance().overrideOutputAudioPort(AVAudioSession.PortOverride.speaker)
} catch let error {
    print("Override failed: \(error)")
}

You can also set that permanently with this code (but I can't guarantee your app will get into the AppStore):

try? audioSession.setCategory(AVAudioSessionCategoryPlayAndRecord, with: AVAudioSessionCategoryOptions.defaultToSpeaker)

Option C: If Option B doesn't do it for you, you might be out of luck on 'how to make AVAudioPlayer play louder.' You're best off editing the source file with some external software yourself - I can recommend Audacity as a good option to do this.


Option D: One last option I've only heard of. You could also look into MPVolumeView, which has UI to control the system output and volume. I'm not too familiar with it though - may be approaching legacy at this point.

like image 152
jake Avatar answered Sep 19 '22 22:09

jake


I want to mention a few things here because I was working on a similar problem.

On the contrary to what's written on Apple Docs on the AVAudioPlayer.volume property (https://developer.apple.com/documentation/avfoundation/avaudioplayer/1389330-volume) the volume can go higher than 1.0... And actually this works. I bumped up the volume to 100.0 on my application and recorded audio is way louder and easier to hear.

Another thing that helped me was setting the mode of AVAudioSession like so:

do { 
   let session = AVAudioSession.sharedInstance()
   try session.setCategory(.playAndRecord, options: [.defaultToSpeaker, .allowBluetooh])
   try session.setMode(.videoRecording)
   try session.setActive(true)
} catch {
   debugPrint("Problem with AVAudioSession")
}

session.setMode(.videoRecording) is the key line here. This helps you to send the audio through the louder speakers of the phone and not just the phone call speaker that's next to the face camera in the front. I was having a problem with this and posted a question that helped me here:

AVAudioPlayer NOT playing through speaker after recording with AVAudioRecorder

like image 45
C0D3 Avatar answered Sep 17 '22 22:09

C0D3