Android音视频之AudioTrack播放音频(二)

前一篇讲了如何录制wav音频文件,本篇就来讲讲如何播放wav文件,这里就是使用AudioTrack来播放音频,确切的说是播放pcm格式数据,使用AudioTrack播放也没什么难度,主要就是将数据写入到AudioTrack中就可以了,先贴代码

package cn.sskbskdrin.record.audio;

import android.media.AudioManager;
import android.media.AudioTrack;

import java.io.FileNotFoundException;
import java.io.IOException;
import java.io.RandomAccessFile;

/**
 * @author sskbskdrin
 * @date 2019/April/3
 */
public class AudioTrackManager {
    private AudioTrack audioTrack;

    private boolean playing = false;

    public AudioParams playWav(String filepath, AudioRecordManager.RecordCallback callback) {
        RandomAccessFile file = null;
        AudioParams params = null;
        try {
            file = new RandomAccessFile(filepath, "r");
            params = readWavHeader(file);
        } catch (FileNotFoundException e) {
            e.printStackTrace();
        } catch (IOException e) {
            e.printStackTrace();
        }
        if (params == null) {
            return null;
        }
        int simpleRate = params.simpleRate;
        int channelConfig = params.getOutChannelConfig();
        int audioFormat = params.getEncodingFormat();
        int minBufSize = AudioTrack.getMinBufferSize(simpleRate, channelConfig, audioFormat);
        audioTrack = new AudioTrack(AudioManager.STREAM_MUSIC, simpleRate, channelConfig, audioFormat, minBufSize,
            AudioTrack.MODE_STREAM);
        final RandomAccessFile finalFile = file;
        new Thread(() -> {
            playing = true;
            audioTrack.play();
            byte[] buffer = new byte[minBufSize];
            try {
                finalFile.seek(44);
                while (playing) {
                    int read = finalFile.read(buffer);
                    if (read > 0) {
                        audioTrack.write(buffer, 0, read);
                    } else {
                        finalFile.close();
                        playing = false;
                        audioTrack.stop();
                        audioTrack.release();
                    }
                    if (callback != null) {
                        callback.onRecord(buffer, read);
                    }
                }
            } catch (IOException e) {
                e.printStackTrace();
            }
        }).start();
        return params;
    }

    public static AudioParams readWavHeader(RandomAccessFile file) throws IOException {
        file.seek(22);
        byte channelCount = file.readByte();
        file.seek(24);
        int sampleRate = file.readByte() & 0xff;
        sampleRate |= (file.readByte() & 0xff) << 8;
        sampleRate |= (file.readByte() & 0xff) << 16;
        sampleRate |= (file.readByte() & 0xff) << 24;

        file.seek(34);
        byte bits = file.readByte();
        return new AudioParams(sampleRate, channelCount, bits);
    }

}

播放的方法,是传入文件路径,AudioRecordManager.RecordCallback可以为空。先是通过readWavHeader()方法读取wav文件的文件头信息,返回AudioParams,这个类是我前一篇文章有列出来,可以得到一些需要的数据。

关于读数据头部信息,可以参考这里,读取重要数据。

AudioTrack.getMinBufferSize(simpleRate, channelConfig, audioFormat)可以获取最小缓存大小。

AudioTrack的构造方法中,第一个参数为播放流的类型,有下面几种

AudioManager.STREAM_MUSIC //音乐

AudioManager.STREAM_VOICE_CALL //电话

AudioManager.STREAM_RING //铃声

AudioManager.STREAM_ALARM //闹钟

AudioManager.STREAM_NOTIFICATION //通知

最后了个参数是流写入的方式,有两种

AudioTrack.MODE_STREAM // 流写入

AudioTrack.MODE_STATIC //静态写入

AudioTrack.MODE_STREAM看名字大概就能知道是流的方式写入,边写边播。

AudioTrack.MODE_STATIC就是一次写完,然后播放,这种方式更适合比较短的声音播放,比如通知声音

开始播放时,先调用AudioTrack.play(),然后从wav文件的数据块开始读,即第44个字节开始,读完调用audioTrack.write写入pcm数据。当读不到数据时,停止AudioTrack,释放资源即可。

通过RandomAccessFile方式读取文件,可以记录读取的位置,并通过seek方法跳转到指定位置,可实现播放、暂停、继续播放的功能。

原文地址:https://www.cnblogs.com/sskbskdrin/p/10649591.html

时间: 2024-08-09 07:49:59

Android音视频之AudioTrack播放音频(二)的相关文章

android音视频点/直播模块开发

前言 随着音视频领域的火热,在很多领域(教育,游戏,娱乐,体育,跑步,餐饮,音乐等)尝试做音视频直播/点播功能,那么作为开发一个小白,如何快速学习音视频基础知识,了解音视频编解码的传输协议,编解码方式,以及如何技术选型,如何解决遇到的坑,本文抛砖引玉,欢迎大咖交流. 一. 音视频的基础知识 1.1 基本概念 视频是什么 静止的画面叫图像(picture).连续的图像变化每秒超过24帧(frame)画面以上时,根椐视觉暂留原理, 人眼无法辨别每付单独的静态画面,看上去是平滑连续的视觉效果.这样的连

Android音视频点/直播模块开发实践总结-zz

随着音视频领域的火热,在很多领域(教育,游戏,娱乐,体育,跑步,餐饮,音乐等)尝试做音视频直播/点播功能.那么作为开发一个小白,如何快速学习音视频基础知识,了解音视频编解码的传输协议,编解码方式,以及如何技术选型,如何解决遇到的坑. 一. 音视频的基础知识 1.1 基本概念 视频是什么 静止的画面叫图像(picture).连续的图像变化每秒超过24帧(frame)画面以上时,根椐视觉暂留原理,人眼无法辨别每付单独的静态画面,看上去是平滑连续的视觉效果.这样的连续画面叫视频.当连续图像变化每秒低于

Android 音视频开发入门指南

最近收到很多网友通过邮件或者留言说想学习音视频开发,该如何入门,我今天专门写篇文章统一回复下吧. 音视频这块,目前的确没有比较系统的教程或者书籍,网上的博客文章也都是比较零散的,希望我后面能挤出时间整一个专题详细讲一讲--目前的话,我先给出一个大的方向性的学习指南,希望对初学者有所帮助. 我一直相信带着 "任务" 去学习和实践,效率会高很多,因此我列出了一系列音视频相关的 "开发任务",从简单到困难(当然,不一定非常严格和完美,部分任务先后可调整),大家在完成任务的

Android 音视频开发学习思路

Android 音视频开发这块目前的确没有比较系统的教程或者书籍,网上的博客文章也都是比较零散的.只能通过一点点的学习和积累把这块的知识串联积累起来.在学习的过程中,遇到不懂的地方,要及时的去google或者请教大神,不要半知半解的过去. 初级入门篇: 在 Android 平台绘制一张图片,使用至少 3 种不同的 API,ImageView,SurfaceView,自定义 View 在 Android 平台使用 AudioRecord 和 AudioTrack API 完成音频 PCM 数据的采

Android 音视频深入 七 学习之路的总结和资料分享

说个实话一开始我对基于Android如何开发音视频很迷茫,甚至对音视频开发都不是很明白,我看了Android 音视频开发入门指南 http://blog.51cto.com/ticktick/1956269这篇博客,我觉得我也许不太懂音视频能干啥,但是我找到了学习音视频的门槛,对了写这个博客的人,他的博客很多都是关于音视频的很有借鉴 开始把Android原生音频API AudioFormat.AudioRecord.AudioTrack底层三剑客搞一下,不说代码非常熟,至少整个作用和相关的参数和

Android音视频即时通讯软件怎样通过JNI快速实现

Android音视频即时通讯软件怎样通过JNI快速实现 音视频通信 作为独立开发者或想缩短音视频开发周期的公司来说,想要在Android平台下实现音视频通信,最快捷的方法是寻找开源项目或调用其他公司API.之所以这么说是因为音视频通信技术涉及到底层音视频采集.解码. FFmpeg(音视频处理解决方案).媒体流传输协议等太多太多相关技术知识点.试了几个开源项目,视频差强人意,语音与视频不同步等不稳定因素.因此我把目光放到其他公司的API上(点击下载demo程序).demo程序API提供了一系列纯J

手机Android音视频采集与直播推送,实现单兵、移动监控类应用

恰逢2014 Google I/O大会,不难看出安卓在Google的推进以及本身的开放性作用下,已经快延生到生活的各个方面了,从安卓智能手机.平板,到可穿戴的Android Ware.眼镜.手表.再到Android汽车.智能家居.电视,甚至最近看新闻,日本出的几款机器人都是Android系统的,再把目光放回监控行业,传统监控中的移动终端设备,例如:单兵设备.手持设备.车载终端设备,包括家庭监控中用到的智能设备,都可以用Android系统替代了,不仅开发容易,而且易扩展,设备也更加智能了. 图 -

Android 使用系统的Activity播放音频文件 intent

Intent intent = new Intent(); intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK); intent.setAction(Intent.ACTION_VIEW); intent.setDataAndType(Uri.fromFile(new File("/sdcard/record.wav")), "audio"); startActivity(intent); 这里可以播放wav.amr.MP3等

Android 音视频深入 二 AudioTrack播放pcm(附源码下载)

本篇项目地址,名字是录音和播放PCM,求starhttps://github.com/979451341/Audio-and-video-learning-materials 1.AudioTrack官方说明AudioTrack允许PCM音频缓冲器流到音频接收器进行回放.这是通过"推"的数据对象的信号使用 write(byte[], int, int) and write(short[], int, int) 方法.一个信号可以在两种模式下运行:静态或流.在流模式中,应用程序写一个连续