• 正文
    • WAV概述
    • 音頻采樣與播放
    • wave格式解析
    • RIFF區(qū)塊
    • FORMAT區(qū)塊
    • DATA區(qū)塊
    • 單片機中播放
  • 相關推薦
申請入駐 產(chǎn)業(yè)圖譜

一文聊透WAV音頻文件格式

05/12 11:35
286
加入交流群
掃碼加入
獲取工程師必備禮包
參與熱點資訊討論

早些年給消防系統(tǒng)中做過一個報警器,為了節(jié)省資源,直接使用了單片機解碼,再加上PWM輸出直接推流到功放驅(qū)動揚聲器,這個方案里面使用音頻的PCM編碼。

后來在做平衡車的時候,也是用到了同樣的方法,為了讓flash空間更緊湊,還進行了音頻數(shù)據(jù)的ADPCM壓縮。

告訴你一個音頻壓縮算法,讓你的Flash減小四倍

做這一切之前,我們首先要獲得音頻文件,然后再進行處理或者直接把音頻放到單片機的Flash里面,這里就不得不提到WAV格式的音頻文件,這個是相對比較簡單的格式。

WAV概述

wav是window系統(tǒng)中的后綴名,它的完整叫法應嘎是Waveform Audio File Format?也就是wave文件格式,它采用RIFF(Resource Interchange File Format)文件格式結(jié)構。通常用來保存PCM格式的原始音頻數(shù)據(jù),所以通常被稱為無損音頻。但是嚴格意義上來講,WAV也可以存儲其它壓縮格式的音頻數(shù)據(jù)。

聲音文件大體上可以分為兩類,分別對應于單聲道(11.025KHz 采樣率、8Bit 的采樣值)和雙聲道(44.1KHz 采樣率、16Bit 的采樣值)。

采樣率是指:聲音信號在模數(shù)轉(zhuǎn)換過程中,1秒內(nèi)采樣的次數(shù)。采樣值是指每一次采樣周期 ?內(nèi)聲音模擬信號的電壓量化值。

對于單聲道的聲音文件,音頻細節(jié)不多,因此可以采用8bit采樣深度,11.025K的采樣頻率(8K其實也可以的),采樣數(shù)據(jù)為八位的短整數(shù)(00H-FFH);而對于雙聲道立體聲聲音文件,每次采樣數(shù)據(jù)為一個16位的整數(shù)(0000H-FFFFH),高八位和低八位分別代表左右兩個聲道。

音頻采樣與播放

人耳對頻率的識別范圍是 20HZ - 20000HZ, 如果每秒鐘能對聲音做 20000 個采樣, 回放時就足可以滿足人耳的基本需求. 所以 22050 的采樣頻率是常用的, 44100已是CD音質(zhì)。

根據(jù)奈奎斯特定理,采樣頻率超過信號頻率的2倍就可以還原出原始信號的細節(jié),因此超過48000的采樣對人耳已經(jīng)沒有意義。

就比如,早期電影幀數(shù)定為24幀,基本夠用了,不過現(xiàn)如今,120幀的刷屏也是比比皆是了,之前是低估了人眼的靈敏度。

假設我們現(xiàn)在有了一段音頻wav,采樣率為22.050KHz,采樣深度為16bit,雙通道。文件大小為424644字節(jié)。

那么音頻每秒的傳輸速率(位速, 也叫比特率、取樣率)是 22050162 = 705600(bit/s), 換算成字節(jié)單位就是 705600/8 = 88200(字節(jié)/秒),也就是位速是 705.6kbps。

播放時間:424644(總字節(jié)數(shù)) / 88200(每秒字節(jié)數(shù)) ≈ 4.8145578(秒)。

要是存儲成window可以播放的文件,也就是wave文件,除了音頻本身的信息以外,我們還需要一些其他信息放在文件的頭部, 包裝標準的 PCM 格式的 WAVE 文件(.wav)中至少帶有 42 個字節(jié)的頭信息,這在計算播放時間時應該將其去掉, ?所以就有:(424644-42) / (2205016*2/8) ≈ 4.8140816(秒)。 這樣就比較精確了。

wave格式解析

WAV文件遵循RIFF規(guī)則,其內(nèi)容以區(qū)塊(chunk)為最小單位進行存儲。

WAV文件一般由3個區(qū)塊組成:RIFF chunk、Format chunkData chunk。另外,文件中還可能包含一些可選的區(qū)塊,如:Fact chunk、Cue points chunk、Playlist chunkAssociated data list chunk等,主要用于存儲作者,轉(zhuǎn)接類的附加信息。

這里我們只看最基礎的RIFF chunkFormat chunkData chunk。

常見的wave文件的格式圖示

RIFF區(qū)塊

'RIFF'為標識

Size是整個文件的長度減去IDSize的長度,也就是自己后面的長度。

Type是WAVE表示后面需要兩個子塊:Format區(qū)塊和Data區(qū)塊

FORMAT區(qū)塊

'fmt '為標識

Size表示該區(qū)塊數(shù)據(jù)的長度(不包含IDSize的長度)

AudioFormat表示Data區(qū)塊存儲的音頻數(shù)據(jù)的格式,PCM音頻數(shù)據(jù)的值為1

NumChannels表示音頻數(shù)據(jù)的聲道數(shù),1:單聲道,2:雙聲道

SampleRate表示音頻數(shù)據(jù)的采樣率

ByteRate每秒數(shù)據(jù)字節(jié)數(shù) = SampleRate * NumChannels * BitsPerSample / 8

BlockAlign每個采樣所需的字節(jié)數(shù) = NumChannels * BitsPerSample / 8

BitsPerSample每個采樣存儲的bit數(shù),8:8bit,16:16bit,32:32bit

DATA區(qū)塊

'data'為標識

Size表示音頻數(shù)據(jù)的長度,N = ByteRate * seconds

Data音頻數(shù)據(jù)

對于Data塊,根據(jù)聲道數(shù)和采樣率的不同情況,為了方便播放,每個采樣值連續(xù)放置,如果是8bit單聲道,就一個字節(jié)一個字節(jié)排隊。如果是16bit單聲道,那就兩個字節(jié)兩個字節(jié)的排隊。

如果是雙聲道,那就先放左聲道的采樣值,再放右聲道的采樣值,這樣成對成對的排隊。

下面我們看一個具體的例子,聲音文件如下:

單片機中播放

如果要在單片機中播放wav文件,有兩種做法,一種是直接將wav文件存儲到Flash中,我們在播放相應的文件時,從相應起始地址讀取前面的12個字節(jié),判斷是否是RIFF文件,格式為WAVE,同時取出文件長度。接下來就是搜索fmt塊來解析通道數(shù),采樣頻率,采樣深度信息。

最后搜索到data塊,按照fmt提供的信息,把data數(shù)據(jù)推流到DAC中。

當然,還有一種更簡單的方式,那就是我們使用上位機解析wav文件,采用固定的采樣頻率和采樣深度,單獨取出data數(shù)據(jù)寫入到flash中。這樣只需要提供音頻的起始地址和結(jié)束地址就可以直接播放了。

當然,還有一種更簡單的方式,那就是我們使用上位機解析wav文件,采用固定的采樣頻率和采樣深度,單獨取出data數(shù)據(jù)寫入到flash中。這樣只需要提供音頻的起始地址和結(jié)束地址就可以直接播放了。

相關推薦

登錄即可解鎖
  • 海量技術文章
  • 設計資源下載
  • 產(chǎn)業(yè)鏈客戶資源
  • 寫文章/發(fā)需求
立即登錄

多年硬件從業(yè)經(jīng)驗,專注分享從研發(fā)到供應鏈,再到精益制造過程中的經(jīng)驗和感悟!