如下是轉載的文章,前段時間我也在作mic錄音方面的東東,等整理出來再總結一下。。 java
這段時間作了個有關android手機利用mic捕獲外界環境音量的小東東,多方查詢,各類研究,如今把這些東西跟童鞋們分享一下,若有不足或者差錯,還望大牛們多給意見。 android
android提供能夠實現錄音功能的有AudioRecord和MediaRecorder,其中AudioRecord是讀取Mic的音頻流,能夠邊錄音邊分析流的數據;而MediaRecorder則可以直接把Mic的數據存到文件,而且可以進行編碼(如AMR,MP3等)。 api
首先,要將你的應用加入權限(不管你是使用AudioRecord仍是MediaRecorder): 數組
<uses-permission android:name="android.permission.RECORD_AUDIO" /> dom
而後,分開介紹二者的用法。 函數
《!--AudioRecord--》 測試
一、新建錄音採樣類,實現接口: 編碼
public class MicSensor implements AudioRecord.OnRecordPositionUpdateListener spa
二、關於AudioRecord的初始化: .net
public AudioRecord (int audioSource, int sampleRateInHz, int channelConfig, int audioFormat, int bufferSizeInBytes)
audioSource: 錄音源(例如:MediaRecorder.AudioSource.MIC 指定Mic爲錄音源)
sampleRateInHz: 默認的採樣頻率,單位爲Hz。(經常使用的如44100Hz、22050Hz、16000Hz、11025Hz、8000Hz,有人說44100Hz是目前保證在全部廠商的android手機上都能使用的採樣頻率,可是我的在三星i9000上使用卻否則,經測試8000Hz彷佛更爲靠譜)
channelConfig: 描述音頻通道設置。(在此我使用了AudioFormat.CHANNEL_CONFIGURATION_MONO)
audioFormat: 音頻數據支持格式。(這個好像跟聲道有關,16bit的脈碼調製錄音應該是所謂的雙聲道,而8bit脈碼調製錄音是單聲道。AudioFormat.ENCODING_PCM_16BIT、AudioFormat.ENCODING_PCM_8BIT)
bufferSizeInBytes: 在錄製過程當中,音頻數據寫入緩衝區的總數(字節)。 從緩衝區讀取的新音頻數據總會小於此值。 getMinBufferSize(int, int, int)返回AudioRecord 實例建立成功後的最小緩衝區。 設置的值比getMinBufferSize()還小則會致使初始化失敗。
三、初始化成功後則可啓動錄音 audioRecord.startRecording()
四、編寫線程類將錄音數據讀入緩衝區,進行分析
short[] buffer = new short[bufferSize]; //short類型對應16bit音頻數據格式,byte類型對應於8bit
audioRecord.read(buffer, 0, bufferSize); //返回值是個int類型的數據長度值
五、在此須要對buffer中的數據進行一些說明:
這樣讀取的數據是在時域下的數據,直接用於計算沒有任何實際意義。須要將時域下的數據轉化爲頻域下的數據,才能訴諸於計算。
頻域(frequency domain)是指在對函數或信號進行分析時,分析其和頻率有關部份,而不是和時間有關的部份。
函數或信號能夠透過一對數學的運算子在時域及頻域之間轉換。例如傅里葉變換能夠將一個時域信號轉換成在不一樣頻率下對應的振幅及相位,其頻譜就是時域信號在頻域下的表現,而反傅里葉變換能夠將頻譜再轉換回時域的信號。
信號在時域下的圖形能夠顯示信號如何隨着時間變化,而信號在頻域下的圖形(通常稱爲頻譜)能夠顯示信號分佈在哪些頻率及其比例。頻域的表示法除了有各個頻率下的大小外,也會有各個頻率的相位,利用大小及相位的資訊能夠將各頻率的弦波給予不一樣的大小及相位,相加之後能夠還原成原始的信號。
經傅立葉變化後獲得的複數數組是個二維數組,實部和虛部的平方和取對數後乘以10就大體等於咱們一般表示音量的分貝了。
《!--MediaRecorder--》
相對於AudioRecord,MediaRecorder提供了更爲簡單的api。
設置好mediaRecorder的各個屬性,而後經過線程調用方法 mediaRecorder.getMaxAmplitude();
獲得的是瞬時的最大振幅,直接取對數而後乘以10就能夠表徵分貝了。
最後須要說明一下,android手機廠商定製的硬件不盡相同,因此mic獲取的值也只能「表徵」,而不能拿過來當真正的依據。它們雖是智能手機,但也仍是手機,機器人不是人!呵呵。。。
對了,每一個手機mic在聲信號和電信號進行轉換時都有作過電容保護,爲了其不因外界環境的過於嘈雜而易受到損壞。因此超聲波和次聲波,咱們人不容易接受的聲音,手機也不會入耳的。