2016-07-07 12 views
0

Ich versuche dB auf einem iOS-Gerät zu erkennen, aber ich bin neu in AV-Audio-Stiftung kann nicht wirklich bekommen, um es herauszufinden. Ich bin auf diesen Beitrag gestoßen: iOS - Detect Blow into Mic and convert the results! (swift), aber es funktioniert nicht für mich.So erkennen Sie max dB Swift

Mein aktueller Code ist dies:

import Foundation 
import UIKit 
import AVFoundation 
import CoreAudio 

class ViewController: UIViewController { 

var recorder: AVAudioRecorder! 
var levelTimer = NSTimer() 
var lowPassResults: Double = 0.0 

override func viewDidLoad() { 
    super.viewDidLoad() 

    //make an AudioSession, set it to PlayAndRecord and make it active 
    var audioSession:AVAudioSession = AVAudioSession.sharedInstance() 
    audioSession.setCategory(AVAudioSessionCategoryPlayAndRecord, withOptions: nil) 
    audioSession.setActive(true, error: nil) 

    //set up the URL for the audio file 
    var documents: AnyObject = NSSearchPathForDirectoriesInDomains(NSSearchPathDirectory.DocumentDirectory, NSSearchPathDomainMask.UserDomainMask, true)[0] 
    var str = documents.stringByAppendingPathComponent("recordTest.caf") 
    var url = NSURL.fileURLWithPath(str as String) 

    // make a dictionary to hold the recording settings so we can instantiate our AVAudioRecorder 
    var recordSettings: [NSObject : AnyObject] = [AVFormatIDKey:kAudioFormatAppleIMA4, 
                AVSampleRateKey:44100.0, 
                AVNumberOfChannelsKey:2,AVEncoderBitRateKey:12800, 
                AVLinearPCMBitDepthKey:16, 
                AVEncoderAudioQualityKey:AVAudioQuality.Max.rawValue 

    ] 

    //declare a variable to store the returned error if we have a problem instantiating our AVAudioRecorder 
    var error: NSError? 

    //Instantiate an AVAudioRecorder 
    recorder = AVAudioRecorder(URL:url, settings: recordSettings, error: &error) 
    //If there's an error, print otherwise, run prepareToRecord and meteringEnabled to turn on metering (must be run in that order) 
    if let e = error { 
     print(e.localizedDescription) 
    } else { 
     recorder.prepareToRecord() 
     recorder.meteringEnabled = true 

     //start recording 
     recorder.record() 

     //instantiate a timer to be called with whatever frequency we want to grab metering values 
     self.levelTimer = NSTimer.scheduledTimerWithTimeInterval(0.02, target: self, selector: #selector(ViewController.levelTimerCallback), userInfo: nil, repeats: true) 

    } 

} 

//This selector/function is called every time our timer (levelTime) fires 
func levelTimerCallback() { 
    //we have to update meters before we can get the metering values 
    recorder.updateMeters() 

    //print to the console if we are beyond a threshold value. Here I've used -7 
    if recorder.averagePowerForChannel(0) > -7 { 
     print("Dis be da level I'm hearin' you in dat mic ") 
     print(recorder.averagePowerForChannel(0)) 
     print("Do the thing I want, mofo") 
    } 
} 



override func didReceiveMemoryWarning() { 
    super.didReceiveMemoryWarning() 
    // Dispose of any resources that can be recreated. 
} 


} 

Antwort

3

i zur Zeit meine app über Film machen aufbaute und lernte etwas darüber, wie in dB Schalldruckpegel zu dosieren.

die Ursprungsdaten von recorder.averagePowerForChannel nicht wirklich dB Pegel des Schalls ist, dann ist es ein Pegelbereich bereitzustellen, die -160 ist - 0, also müssen wir einige Änderungen dieser Daten vernünftiger

machen

Also habe ich etwas gefunden, das diese Daten (Wert) in dB-Level-Daten konvertiert.

(! Tut mir leid vergessen, wo ich es gefunden wurde)

Hier ist der Code

/** 
Format dBFS to dB 

- author: RÅGE_Devil_Jåmeson 
- date: (2016-07-13) 20:07:03 

- parameter dBFSValue: raw value of averagePowerOfChannel 

- returns: formatted value 
*/ 
func dBFS_convertTo_dB (dBFSValue: Float) -> Float 
{ 
var level:Float = 0.0 
let peak_bottom:Float = -60.0 // dBFS -> -160..0 so it can be -80 or -60 

if dBFSValue < peak_bottom 
{ 
    level = 0.0 
} 
else if dBFSValue >= 0.0 
{ 
    level = 1.0 
} 
else 
{ 
    let root:Float    = 2.0 
    let minAmp:Float   = powf(10.0, 0.05 * peak_bottom) 
    let inverseAmpRange:Float = 1.0/(1.0 - minAmp) 
    let amp:Float    = powf(10.0, 0.05 * dBFSValue) 
    let adjAmp:Float   = (amp - minAmp) * inverseAmpRange 

    level = powf(adjAmp, 1.0/root) 
} 
return level 
} 

mir auffiel, war, dass Sie Whit 2 Kanäle aufzeichnen, so dass es mit meinem Code etwas anders sein wird;

Wunsch könnte Ihnen helfen oder Ihnen einige Ideen: D

LAST UPDATE

Codierung ändern Sprache zu schnellen

+0

Oh, übrigens, 'averagePowerForChannel' * macht * Rückkehr Dezibel . Sie gehen von -160 nach 0, weil sie [dbFS] (https://en.wikipedia.org/wiki/DBFS) sind. -160 bedeutet Stille, und es geht den ganzen Weg * bis * bis 0, die volle Ebene ist. – Moritz

+1

oh, thx über die Sprache erwähnen (und wiki natürlich :)). Ich werde versuchen, den Code meiner Antwort schnell umzuschreiben und meine Antwort so schnell wie möglich zu ändern. –

+0

Danke für die Hilfe :) –