Audio 中的 drain 和 flash

drain

当上层应用(如播放器)检测到音频文件已到达末尾(EOF)时,它会向 AudioTrack 发出停止指令。Framework 会调用 HAL 的 out_drain 接口,要求硬件把缓冲区里剩余的字节"消化"完。

drain 的两种模式

DRAIN_ALL (全部排空):等待当前缓冲区中的**所有**音频数据播放完毕后再返回。这是最常用的模式,用于正常的歌曲切换或结束。

DRAIN_EARLY_NOTIFY (提前通知):在数据即将播放完(例如还剩最后一点)时就发出回调,以便上层应用能提前准备下一首歌的数据,实现"无缝切换"。

为什么需要 drain?

如果不实现 drain 直接调用 stop 或 flush,会发生什么?

音频截断:你会听到歌曲最后几百毫秒或 1-2 秒的内容突然消失(因为这些数据还在硬件 Ring Buffer 里没播出来)。

爆音/咔哒声:直接切断模拟信号可能导致硬件输出电平瞬间归零,产生杂音。

flash

flush(冲洗/清空)操作的主要目的是立即停止播放并丢弃缓冲区中所有待播放的数据。这通常发生在用户切换歌曲、点击停止或在视频播放中执行快进/快退(Seek)操作时。

与 drain(排空)不同,flush 是"暴力"的------它不要求把剩下的音频播完,而是要求硬件立刻"清零"。

|------|--------------------|--------------------|
| 特性 | drain | flush |
| 主要目的 | 优雅地播完最后一点声音 | 立即丢弃所有声音,准备新操作 |
| 触发场景 | 歌曲自然播放结束 | 用户切歌、快进、停止 |
| 数据处理 | 等待硬件 Buffer 播放结束 | 硬件 Buffer 里的数据直接扔掉 |
| 耗时 | 较长(取决于 Buffer 大小) | 极短(几乎瞬间完成) |
| 回调 | 完成后发送 onDrainReady | 完成后不需要特殊 Ready 回调 |

为什么 Non-blocking 模式下 flush 很重要?

在非阻塞模式下,write 调用可能会因为 Buffer 满而返回 0。如果不执行 flush 就进行 Seek 操作,那么当 write 恢复时,它会继续写入旧位置之后的残余数据,导致用户在快进后听到一小段快进前的"声音残影"。执行 flush 可以确保硬件和 HAL 软件层面的"水管"被完全排空。

相关推荐
代码小书生1 天前
视频下载工具!支持8K、4K分辨率画质,视频音频文件多线程下载!字幕同步匹配下载保存到本地,自带视频格式转换功能!
音频·视频·视频下载·8k·4k·下载神器·画质
声光界7 天前
《信号处理赋能智能体音感知》
人工智能·音频·信号处理·声学
凛_Lin~~7 天前
Android录音、试听功能实现
android·音频·安卓
憨波个8 天前
【说话人日志】多说话人数据仿真 Property-Aware Simulation
人工智能·深度学习·音频·语音识别
憨波个8 天前
【说话人日志】Sortformer:将说话人日志接入多说话人 ASR
人工智能·机器学习·音频·语音识别·聚类
重生之我在安卓搞音频12 天前
一、Android 音频简介
音频·安卓
周末也要写八哥14 天前
Cubase Pro v15.0音乐创作全流程下载与安装指南
音频
海特伟业15 天前
工厂IP广播/企业IP广播/车间IP广播系统-集音乐铃声、新闻播报、紧急喊话、呼叫对讲、领导讲话、消防广播于一体的数字交互式IP广播系统方案与应用
音频
爱上珍珠的贝壳17 天前
ESP32-S3-CAM:豆包语音识别文字后控制小车(终章)——语音控制+L298N模块驱动小车
人工智能·音频·语音识别·esp32-s3·语音转文字·豆包
Code-keys18 天前
【WEKWS】论文解读 && 语音唤醒系统架构详解 && 实战
系统架构·音频·语音识别