关于音频的内容,我边学习,边实践也总结了一些,从最开始实现一个简单的web音乐播放器的自定义工具栏,到后来的实现简单的音频频谱图.直到今天的对音频数据进行的进一步操作,我也是一点点的在进步.虽然很多地方,并不是那么完美和准确,但是希望能和大家能共同学习进步.

一、准备工作

声音的基本原理

首先关于音频的一些原理性的内容,在之前的https://blog.csdn.net/yun_master/article/details/104133520关于音频频谱的博客中已经简单介绍过了,这里就不详细展开来说了

前端操作内存的方法

但是如果要实现对音频PCM数据的修改,只是了解了声音的原理,恐怕还是有点不太够用.
这里还需要了解es6中提供的arrayBuffer以及其视图的相关内容,这里推荐阮一峰老师的es6入门这本书的关于arrayBuffer这个章节,进行简单的了解

web audio API

这方面的内容,也是很重要的一部分内容、但是由于web Audio API实在太多了,往往在用的时候再去看,已然是来不及了.那个时候往往是一头雾水,面对海量API无从下手,不知道从哪里入手.所以推荐利用空闲时间、从最基础的api看起.慢慢会发现,真正常用的功能所需要的,并不是特别多.
推荐MDN关于这一部分的介绍:https://developer.mozilla.org/zh-CN/docs/Web/API/Web_Audio_API

二、音频处理

如果想要快速实现一些针对音频PCM数据的处理工作,推荐使用crunker这个方法库,虽然功能有限,但是对于获取音频二进制数据、合并、拼接等工作,安装方便、使用简单.重要的是性能真的不错.
npm地址:https://www.npmjs.com/package/crunker

音频裁剪

原理:音频裁剪,其实就是对音频数据的裁剪,并拷贝出来,创建一份新的音频数据.这就是音频的裁剪.

//获取audioBuffer数据的方式之一
fetch(audioUrl).then(res => res.arrayBuffer()).then(buffer => {  // 获取音频二进制数据const audioCtx = new audioContext();audioCtx.decodeAudio(buffer).then(audioBuffer => {  // 获取音频解码后的audioBuffer数据// to do sth})});/**
* 音频裁剪
* @param audioBuffer 待裁剪的数据
* @param duration 音频总时长
* @param startOffset 裁剪偏移时间,单位s
*/
clipAudio(audioBuffer,duration,startOffset = 0){return new Promise((resolve,reject) => {// 获取音频通道数量const channels = audioBuffer,.numberOfChannels;// 获取采样率const rate = audioBuffer,.sampleRate;// 计算截取后需要的采样数量const endOffset = rate * duration;const frameCount = endOffset - 0;// 创建新的audioBuffer数据const newAudioBuffer = new AudioContext().createBuffer(channels,frameCount,rate);// 创建Float32的空间,作为copy数据的载体const anotherArray = new Float32Array(frameCount);// 裁剪后放置的起始位置const offset = 0;// 遍历通道,将每个通道的数据分别copy到对应的newAudioBuffer的通道for(let channel = 0; channel < channels;channel++){audioBuffer.copyFromChannel(anotherArray, channel, rate * startOffset);newAudioBuffer.copyToChannel(anotherArray, channel, offset);}// 完成裁剪resolve(newAudioBuffer);})}

音频音量调整

fetch(url)
.then(res => res.arrayBuffer)
.then(buffer => {const audioCtx = new AudioContext();audioCtx.decodeAudioData(buffer).then(audioBuffer => {//获取声道数量const channels = audioBuffer.numberOfChannels;// 更改每个通道内的数据for(let channel = 0; channel < channels; channel++){const channelData = audioBuffer.getChannelData(channel);for(let j = 0; j < channelData.length; j++){channelData[j] = channelData[j] * volumn; // volunm [0,1]}}})
})

除了音频裁剪之外的功能,可以利用Crunker这个第三方的库来实现.具体实现方式,可以参考crunker源码

安装

npm i crunker -S

Example

let audio = new Crunker();audio.fetchAudio("/audio/url/1.m\p3","/audio/url/2.mp3")
.then(buffers => {// => [AudioBuffer,AudioBuffer]audio.mergeAudio(buffers); // 将两个音频进行合成(非拼接)
})
.then(merged => {// => AudioBufferaudio.export(merged,"audio/mp3");
})
.then(output => {// => {blob,element,url}audio.download(output.blob);document.addpend(output.element);console.log(output.url);
})
.then(error => {// => Error Message
})audio.notSupported(() => {// Handle no brower support
})

API

crunker.fetchAudio(soneURL,anotherSongURL)

获取音频buffer数据

const crunker = new Crunker();crunker.fetchAudio(url1,url2,url3,...)
.then(buffers => {// 获取到全部音频的buffer数据,buffers为数组
})

crunker.mergeAudio(arrayOfBuffers)

合成音频为一个buffer

const resultBuffer = crunker.mergeAudio([buffer1,buffer2,buffer3,...]);

crunker.concatAudio(arrayOfBuffers);

拼接音频为一个buffer

const resultBuffer = crunker.concatAudio([buffer1,buffer2,buffer3,...]);

crunker.export(buffer,type)

导出blob和url对象
type为可选参数:‘audio/mp3’, ‘audio/wav’, ‘audio/ogg’

const blob = crunker.export(audioBuffers, "audio/mp3");

crunker.download(blob,fileName)

自动下载

crunker.play(blob)

开始播放

audio.notSupported(callback)

如果用户浏览器不支持Web audio API ,自行定义代码.

js实现音频PCM数据合并、拼接、裁剪、调节音量等功能相关推荐

  1. ffmpeg进行混音,将两路音频pcm数据合成一路输出

    ffmpeg进行混音,将两路音频pcm数据合成一路输出 audiomixer.h #ifndef AUDIOMIXER_H #define AUDIOMIXER_H#include <map&g ...

  2. AudioRecord 采集音频PCM数据

    AudioRecord 可以用来采集音频原始数据(PCM)格式,使用起来非常简单. 主要就是构造函数的定义 AudioRecord(int audioSource, int sampleRateInH ...

  3. 关于音频PCM数据2字节(16位)byte与64位double之间的转换

    1 致谢 感谢kimmking网友提供的资料 原文链接如下:http://blog.csdn.net/kimmking/article/details/8752737 2 问题描述 今天遇到一个问题 ...

  4. 使用FFMpeg将音频PCM数据生成WAV和MP3文件

    文章目录 1. 获取编码器和创建解码器上下文 2. 创建音频流和输出封装上下文 3. 编码原始数据写入到文件中 WAV音频封装格式可以存储无编码的PCM数据,而MP3封装格式中不能直接存储PCM数据, ...

  5. SQLSERVER将子查询数据合并拼接成一个字段

    业务场景: 有两张表,部门表和员工表 部门表: 部门编码        部门名称    1                     A            2                     ...

  6. 记录一个音频PCM数据由双声道转单声道出错问题

    引言 工作需要将一份 双声道的PCM数据转换成单声道数据,我采用的是将左右声道样点值对应相加求平均样点值的办法. 计算式如下: typedef int s32; typedef unsigned in ...

  7. [Android] [音视频系列]在 Android 平台使用 AudioRecord 和 AudioTrack API 完成音频 PCM 数据的采集和播放,并实现读写音频 wav 文件

    参考 官方文档地址:https://developer.android.google.cn/reference/android/media/AudioRecord GitHub 地址:https:// ...

  8. 音频PCM数据的单声道、双声道之间的转换

    在使用tinyalsa处理PCM音频数据时发现该设备只能以双声道形式打开设备. tinypcminfo工具可以查看设备信息. out和in里面channels 最大和最小值都是2.但是实际使用中有时候 ...

  9. pcm转mp3_前端音频可视化——PCM数据解决方案

    一.概述 本文的需求来自于标注团队对于音频文件的标注,需要将音频准确定位到毫秒位置进行内容标注,方便团队训练Ai模型 而产品也对标注功能提出了三项不可妥协的需求: 1.波形图必须基于音频原WAV无损格 ...

最新文章

  1. wifi无线网卡移植到andorid
  2. mysql国际化_Java的Struts框架中的主题模板和国际化设置
  3. ITK:拉普拉斯递归高斯图像滤波器
  4. Oracle redo
  5. java scheduler_RxJava Scheduler介绍
  6. everything服务器网页设置,Everything HTTP 服务器设置
  7. upper_bound和lower_bound的用法
  8. CentOS6.2(64bit)下mysql5.6.16主从同步配置
  9. html5双日期时间选择控件,bootstrap daterangepicker双日历时间段选择控件详解
  10. Genlovy_Hoo大神的杰作
  11. Win10 下搭建PHP开发环境(自定义方式)
  12. 租房软件需要的是简单易用
  13. 徐志摩《翡冷翠的一夜》
  14. 栈的操作(入栈、出栈)之一:顺序栈
  15. 锂离子电池热失控预警资料整理(三)
  16. 哈尔滨校区学员扫码绑定教练、签到、签退、评价说明
  17. 原创图片可以进行版权登记吗?
  18. 组合查询条件的合理应用
  19. php服务器内容修改时间,php设置服务器时间
  20. 多功能拓展坞设计CS5266|CapstoneCS5266带PD多合一拓展坞方案电路|CS5266方案电路图

热门文章

  1. 4.SPSS24安装教程
  2. ansible字符串的处理
  3. 1214. 波动数列
  4. 数据生成器 -支持多种类型
  5. micropython plc_PLC线到底该怎么接?PLC系统如何设计?PLC软编程方法
  6. 简单认识Anti-RootKit
  7. jsp分页技术的实现
  8. 在Ubuntu系统上安装Windows 10(真实有效)
  9. xilinx基础篇Ⅰ(8)ISE14.7下载CPLD
  10. 如何在winows的PPT里面使用醒目的思源系列字体(思源宋体/黑体)