【Android 高性能音频】AAudio 音频流 缓冲区 简介 ( AAudio 音频流内部缓冲区 | 缓冲区帧容量 | 缓冲区帧大小 | 音频数据读写缓冲区 )
文章目錄
- I . AAudio 音頻流內部緩沖區(qū) 與 音頻數(shù)據(jù)讀寫緩沖區(qū) 概念
- II . AAudio 音頻流內部緩沖區(qū) 緩沖區(qū)幀容量 BufferCapacityInFrames 與 緩沖區(qū)幀大小 BufferSizeInFrames 區(qū)分
- III . AAudio 音頻流內部緩沖區(qū) 緩沖區(qū)幀容量 BufferCapacityInFrames
- IV . AAudio 音頻流內部緩沖區(qū) 緩沖區(qū)幀大小 BufferSizeInFrames
- V . AAudio 音頻流內部緩沖區(qū) 脈沖串
- VI . AAudio 音頻流內部緩沖區(qū) 工作機制 ( 播放音頻 )
- VII . AAudio 音頻流內部緩沖區(qū) 優(yōu)化
- VIII . 音頻數(shù)據(jù)讀寫緩沖區(qū)
I . AAudio 音頻流內部緩沖區(qū) 與 音頻數(shù)據(jù)讀寫緩沖區(qū) 概念
1 . AAudio 音頻流內部緩沖區(qū)本質 : 該緩沖區(qū)是在音頻設備中進行維護的 , AAudio 音頻流會先將數(shù)據(jù)傳入該緩沖區(qū) , 然后才進行播放 ;
2 . 音頻數(shù)據(jù)讀寫緩沖區(qū) : 是在內存中維護的 , 其本質就是一個 void* 類型的數(shù)組 , 其數(shù)組字節(jié)大小由用戶設定 ;
3 . 概念區(qū)分 : 注意將 AAudio 音頻流內部緩沖區(qū) 與 音頻數(shù)據(jù)讀寫緩沖區(qū) 區(qū)分清楚 ; 兩個是完全不同的概念 ;
II . AAudio 音頻流內部緩沖區(qū) 緩沖區(qū)幀容量 BufferCapacityInFrames 與 緩沖區(qū)幀大小 BufferSizeInFrames 區(qū)分
下面要區(qū)分兩個概念 , 一個是緩沖區(qū)幀容量 BufferCapacityInFrames , 一個是緩沖區(qū)幀大小 BufferSizeInFrames , 這兩個開發(fā)者都可以設置 ;
- ① 緩沖區(qū)幀容量 BufferCapacityInFrames : 是音頻設備的緩沖區(qū)最大值 ;
- ② 緩沖區(qū)幀大小 BufferSizeInFrames : 用戶實際使用的緩沖區(qū)大小 , 小于等于 緩沖區(qū)容量 ;
做一個形象的比喻 , 水杯有 2L 的容量 , 最大可以裝 2L 水 , 2L 相當于緩沖區(qū)幀容量 ; 但是我們在水杯的 1.5L 位置畫了一個最高水位線 , 表示盛水時不能高于 1.5L , 這個 1.5L 就是我們使用的實際緩沖區(qū)幀大小 ;
每幀的樣本數(shù)就是通道數(shù) , 單聲道每幀 1 個樣本 , 立體聲 每幀 2 個樣本 , 每個樣本的大小與樣本格式有關 , 16 位樣本 每個樣本 2 字節(jié) ;
III . AAudio 音頻流內部緩沖區(qū) 緩沖區(qū)幀容量 BufferCapacityInFrames
AAudio 音頻流內部 緩沖區(qū)幀容量 : 音頻設備的緩沖區(qū)最大值 ;
- ① 設置緩沖區(qū)最大容量 : 調用 AAudioStreamBuilder_setBufferCapacityInFrames() 方法可以設置音頻設備緩沖區(qū)最大容量 ;
- ② 獲取緩沖區(qū)最大容量 : 調用 AAudioStream_getBufferCapacityInFrames() 方法可以獲取當前音頻設備緩沖區(qū)的最大容量 ;
IV . AAudio 音頻流內部緩沖區(qū) 緩沖區(qū)幀大小 BufferSizeInFrames
AAudio 音頻流內部緩沖區(qū)幀大小 : 為音頻設備設置了緩沖區(qū)最大容量 , 但是我們可能用不了這么大緩沖區(qū) , 只使用其中一部分作為緩沖區(qū) ;
- ① 緩沖區(qū)幀大小 限制 : 緩沖區(qū)幀大小 BufferSizeInFrames 只能小于等于 緩沖區(qū)幀容量 BufferCapacityInFrames ;
- ② 設置 緩沖區(qū)幀大小 作用 : 增加 緩沖區(qū)幀大小 BufferSizeInFrames 會增加音頻延遲 , 反之會減小延遲 ;
- ③ 設置緩沖區(qū)幀大小 方法 : AAudioStreamBuilder_setBufferSizeInFrames() ;
- ④ 獲取緩沖區(qū)幀大小 方法 : AAudioStreamBuilder_getBufferSizeInFrames() ;
V . AAudio 音頻流內部緩沖區(qū) 脈沖串
1 . 脈沖串概念 : 音頻設備讀取 音頻內部緩沖區(qū)數(shù)據(jù)時 , 會以離散的脈沖串形式從緩沖區(qū)中讀取音頻數(shù)據(jù) , 每個脈沖串都包含多個音頻幀 ;
2 . 脈沖串設置 : 脈沖串包含的幀個數(shù) , 以及脈沖串的讀取速度 , 這兩個屬性由 Android 系統(tǒng)控制 , 與音頻設備的電路相關 ;
3 . 脈沖串屬性固定 : 脈沖串的大小 和 速度 是無法修改的 , 可以根據(jù) 內部緩沖區(qū) 包含的脈沖串數(shù)量 設置內部緩沖區(qū)大小 ;
4 . 脈沖串 性能相關 設置 : AAudio 音頻流的 內部緩沖區(qū)幀大小 是 脈沖串大小的整數(shù)倍時 , 音頻延遲最短 ;
VI . AAudio 音頻流內部緩沖區(qū) 工作機制 ( 播放音頻 )
1 . 寫出數(shù)據(jù)到內部緩沖區(qū) : 使用 AAudio 音頻流 播放音頻時 , 先將數(shù)據(jù)寫入 AAudio 音頻流的內部緩沖區(qū) , 該過程會阻塞線程 , 直到寫入完成 ;
該緩沖區(qū)為音頻設備內部維護的
2 . AAudio 音頻流 會以 離散的 脈沖串形式 , 讀取內部緩沖區(qū)中的音頻數(shù)據(jù) , 然后播放出來 ;
3 . 圖示 : 內部緩沖區(qū)工作機制如下圖 ;
VII . AAudio 音頻流內部緩沖區(qū) 優(yōu)化
1 . AAudio 音頻流內部緩沖區(qū)優(yōu)化步驟 : 設置一個合適的 緩沖區(qū)幀大小 BufferSizeInFrames , 先設置一個較大的緩沖區(qū) , 逐步減小該緩沖區(qū)大小 , 監(jiān)控 XRun ( 超限 或 欠載 ) 數(shù)值 , 當出現(xiàn)了上述情況 , 說明緩沖區(qū)減小到極限 , 出現(xiàn)了播放問題 , 此時再稍微將緩沖區(qū)調大 , 最終的緩沖區(qū)大小剛合適 , 兼顧性能與功能 ;
備選方案 : 先設置肯定出問題一個最小值 , 此時肯定會出現(xiàn)緩沖區(qū)不足的情況 , 逐步增加緩沖區(qū)大小 , 直到流暢讀寫為止 ;
2 . 調整時間 : 緩沖區(qū)大小調整的過程幾乎是一瞬間完成的 , 在開始播放第一幀數(shù)據(jù)時就已經(jīng)完成 ;
3 . 靜音調整 : 緩沖區(qū)調整時 , 可以靜音初始化緩沖區(qū)大小 , 確保用戶聽不到電流聲 ;
4 . 不斷調整 : 在音頻播放的過程中 , 系統(tǒng)的性能可能隨時改變 , 這個緩沖區(qū)的大小也要跟著實時修改 , 一旦監(jiān)測到了 欠載 UnderRun 或 超限 OverRun 就馬上調整緩沖區(qū)大小 ;
該過程可以參考上一篇博客 : 【Android 高性能音頻】AAudio 緩沖區(qū)控制 ( XRun | 欠載 UnderRun | 超限 OverRun | 獲取緩沖區(qū)大小 | 設置緩沖區(qū)大小 )
VIII . 音頻數(shù)據(jù)讀寫緩沖區(qū)
1 . 概念區(qū)分 ( AAudio 內部緩沖區(qū) / 音頻讀寫緩沖區(qū) ) : 該緩沖區(qū)是由用戶自己維護的 , 與 AAudio 音頻流緩沖區(qū)沒有任何關系 , 不要混淆這兩個概念 ;
2 . 緩沖區(qū)本質 : 音頻讀寫緩沖區(qū)是在堆內存中維護的 , 其本質就是一個 void* 類型的數(shù)組 , 其數(shù)組字節(jié)大小由用戶設定 ;
3 . 讀寫緩沖區(qū)作用 : 讀取音頻數(shù)據(jù)時 , 將音頻數(shù)據(jù)先讀取到該緩沖區(qū)中 ;
4 . 性能分析 : 該音頻數(shù)據(jù)讀寫緩沖區(qū) 與 采樣效率相關 , 采樣是需要消耗額外性能的 , 如果該緩沖區(qū)很大 , 一次采集很多樣本 , 采樣的效率會很高 , 但是減少了靈活性 , 如果采樣太少 , 就會額外消耗很多性能 ;
總結
以上是生活随笔為你收集整理的【Android 高性能音频】AAudio 音频流 缓冲区 简介 ( AAudio 音频流内部缓冲区 | 缓冲区帧容量 | 缓冲区帧大小 | 音频数据读写缓冲区 )的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 【Android 高性能音频】AAudi
- 下一篇: 【Android 高性能音频】AAudi