下午写了一篇关于NAudio的录音、播放和波形图的博客,不太满意,感觉写的太乱,又总结了下

NAudio是个相对成熟、开源的C#音频开发工具,它包含录音、播放录音、格式转换、混音调整等功能。本次介绍主要功能有音频、录音文件播放、实时音频流波形图显示等。具体如下:

1. 录音

NAudio录音主要使用WaveIn和WaveFileWriter两个类

1.1   WaveIn

WaveIn的功能是对录音的音频参数进行设置以及对数据的采集,参数如通道数、采样率、平均数据传输速率(WaveFormat)、数据回调事件、录音停止回调函数等参数

其中,DataAvailable为数据回调参数,是在录音时实时将录音数据传递出来,有需要使用录音数据的可以订阅该事件进行接收业务和相关处理。

1.2   WaveFileWriter

该类是创建相对应格式的音频文件,并提供想对应的写入数据方法、保存方法等,具体如下:

 public class WaveFileWriter : Stream
{
public WaveFileWriter(Stream outStream, WaveFormat format);
public WaveFileWriter(string filename, WaveFormat format); ~WaveFileWriter(); public override long Position { get; set; }
public override bool CanWrite { get; }
public override bool CanRead { get; }
public WaveFormat WaveFormat { get; }
public TimeSpan TotalTime { get; }
public override long Length { get; }
public string Filename { get; }
public override bool CanSeek { get; } public static void CreateWaveFile(string filename, IWaveProvider sourceProvider);
public static void CreateWaveFile16(string filename, ISampleProvider sourceProvider);
public static void WriteWavFileToStream(Stream outStream, IWaveProvider sourceProvider);
public override void Flush();
public override int Read(byte[] buffer, int offset, int count);
public override long Seek(long offset, SeekOrigin origin);
public override void SetLength(long value);
public override void Write(byte[] data, int offset, int count);
[Obsolete("Use Write instead")]
public void WriteData(byte[] data, int offset, int count);
[Obsolete("Use WriteSamples instead")]
public void WriteData(short[] samples, int offset, int count);
public void WriteSample(float sample);
public void WriteSamples(short[] samples, int offset, int count);
public void WriteSamples(float[] samples, int offset, int count);
protected override void Dispose(bool disposing);
protected virtual void UpdateHeader(BinaryWriter writer);
}

在调用上是先调用WaveIn的DataAvailable回调函数,读取其数据并写入流文件,最后保存到本地。

2. 播放录音

播放录音主要用到AudioFileReader、WaveOut三个类和接口

2.1   AudioFileReader

AudioFileReader主要负责读取音频文件,验证音频文件格式,对外部提供读取数据接口,具体如下:

 public class AudioFileReader : WaveStream, ISampleProvider
{
public AudioFileReader(string fileName); public string FileName { get; }
public override WaveFormat WaveFormat { get; }
public override long Length { get; }
public override long Position { get; set; }
public float Volume { get; set; } public override int Read(byte[] buffer, int offset, int count);
public int Read(float[] buffer, int offset, int count);
protected override void Dispose(bool disposing);
}

2.2   WaveOut

WaveOut的工作是播放音频,它调用AudioFileReader.Read进行数据读取,对读取的数据进行播放,主要工作流程是从获取数据,并将数据进行播放成音频

public class WaveOut : IWavePlayer, IDisposable, IWavePosition
{
public WaveOut();
public WaveOut(IntPtr windowHandle);
public WaveOut(WaveCallbackInfo callbackInfo); ~WaveOut(); public static int DeviceCount { get; }
public PlaybackState PlaybackState { get; }
public WaveFormat OutputWaveFormat { get; }
public int DeviceNumber { get; set; }
public int NumberOfBuffers { get; set; }
public int DesiredLatency { get; set; }
public float Volume { get; set; } public event EventHandler<StoppedEventArgs> PlaybackStopped; public static WaveOutCapabilities GetCapabilities(int devNumber);
public void Dispose();
public long GetPosition();
public void Init(IWaveProvider waveProvider);
public void Pause();
public void Play();
public void Resume();
public void Stop();
protected void Dispose(bool disposing);
}

3. 波形图绘制

录音时绘制波形图需要在DataAviliable回调函数中获取音频数据并将其从byte[]转换为float[],然后用float[]数据做为波形图的输入即可,这个过程源码上写一个数据包的波形图数据为waveSource.WaveFormat.SampleRate / 100,原理上我还没搞懂,但是的确是这么操作显示是对的,具体如下:

        private void waveSource_DataAvailable(object sender, WaveInEventArgs e)
{
if (waveFile != null)
{
waveFile.Write(e.Buffer, , e.BytesRecorded);
waveFile.Flush(); float[] sts = new float[e.Buffer.Length / ];
int outIndex = ;
for (int n = ; n < e.Buffer.Length; n += )
{
sts[outIndex++] = BitConverter.ToInt16(e.Buffer, n) / 32768f;
} for (int n = ; n < sts.Length; n += channels)
{
Add(sts[n]);
}
}
}

需要注意的是WaveFormat的通道数设置、PCM的格式设置,上述代码都是基于通道数为2、PCM为16bit的情况下,如这两项修改会发生转换和调用失败等问题

可调试Demo:示例Demo

C# NAudio录音和播放音频文件及实时绘制音频波形图(从音频流数据获取,而非设备获取)的更多相关文章

  1. C# NAudio录音和播放音频文件-实时绘制音频波形图(从音频流数据获取,而非设备获取)

    NAudio的录音和播放录音都有对应的类,我在使用Wav格式进行录音和播放录音时使用的类时WaveIn和WaveOut,这两个类是对功能的回调和一些事件触发. 在WaveIn和WaveOut之外还有对 ...

  2. 解析WAV音频文件----》生成WAV音频文件头

    前言:请各大网友尊重本人原创知识分享,谨记本人博客:南国以南i WAV音频文件介绍: WAV文件是在PC机平台上很常见的.最经典的多媒体音频文件,最早于1991年8月出现在Windows3.1操作系统 ...

  3. iOS中音频的录制与播放(本地音频文件的播放)

    iOS功能开发涉及到音频处理时,最常见的时进行录音,以及音频文件的播放.停止播放等的操作.在开发中还要避免同一个音频文件,或不同音频文件之间的处理,比如说正在播放A音频时,可以停止播放A音频,也可以播 ...

  4. 将音频文件转二进制分包存储到Redis(奇淫技巧操作)

    功能需求: 一.获取本地音频文件,进行解析成二进制数据音频流 二.将音频流转化成byte[]数组,按指定大小字节数进行分包 三.将音频流分成若干个包,以List列表形式缓存到redis数据库中 四.从 ...

  5. 浏览器音频兼容和ffmpeg的音频转码使用

    浏览器对各音/视频格式的支持问题 浏览器测试效果图 ffmpeg在音频格式转换,和从视频中提取音频的简单实用 1.百度搜索浏览器对于音频文件的兼容,排在前面的文章大部分是复制粘贴很久以前的文章,容易误 ...

  6. C# 录音和播放录音-NAudio

    在使用C#进行录音和播放录音功能上,使用NAudio是个不错的选择. NAudio是个开源,相对功能比较全面的类库,它包含录音.播放录音.格式转换.混音调整等操作,具体可以去Github上看看介绍和源 ...

  7. S3C2416裸机开发系列19_Fatfs播放录像wav音频文件

    S3C2416裸机开发系列19 Fatfs播放录像wav音频文件 国际象棋男孩    1048272975 多媒体资源,一般都是以文件的形式存储在固化存储器中.Fatfs所支持的fat32为windo ...

  8. IOS音频1:之采用四种方式播放音频文件(一)AudioToolbox AVFoundation OpenAL AUDIO QUEUE

    本文转载至 http://blog.csdn.net/u014011807/article/details/40187737 在本卷你可以学到什么? 采用四种方法设计应用于各种场合的音频播放器: 基于 ...

  9. VC++中MCI播放音频文件 【转】

    MCI播放mp3音频文件例程 源文件中需要包含头文件 Mmsystem.h,在Project->Settings->Link->Object/libray module中加入库 Wi ...

随机推荐

  1. github博客配置

    配置基础环境 1.先下载github,运行git bash,输入 12 npm installnpm install -g hexo 2.选择一个熟悉的地方创建hexo文件夹,打开文件夹,在文件夹中运 ...

  2. ansible使用指北(二)

    前言在上一篇文章里我们了解了ansible的常用模块,今天我们来了解下ansible-playbook,ansbile-playbook是一系统ansible命令的集合,其利用yaml 语言编写,an ...

  3. APP倒闭:你充值的钱会蒸发吗?

    有一句说到吐,但却又不得不说的话:资本大潮退去,才知道谁在裸泳.随着资本寒冬的来临,互联网上众多看起来狂飙突进的项目却呈现迅速萎靡态势.尤其是众多具有互联网元素的油卡.洗衣.保洁等成为重灾区,其中不少 ...

  4. iMX287A多种方法实现流水灯效果

    目录 1.流水灯在电子电路中的地位 2.硬件电路分析 3.先点个灯吧 4.shell脚本实现流水灯 5.ANSI C文件操作实现流水灯 6.Linux 系统调用实现流水灯 @ 1.流水灯在电子电路中的 ...

  5. Apple App签名机制

    概览 数字签名 签名机制与验证过程 操作流程 数字签名 摘要算法 将任意长度文本通过一个算法得到一个固定长度的文本. 源文本不同,计算结果必然不同 无法从结果反推源 例如,MD5和SHA算法 非对称加 ...

  6. 解决vue2.0下IE浏览器白屏问题

    公司新开发的项目需要兼容到IE9+ 就在index.html页面加入 <meta http-equiv="X-UA-Compatible" content="IE= ...

  7. 原生js中的常用方法的写法

    1.js深度克隆的方法 //第一种 function deepClone(obj){ var str,newObj = obj instanceof Array? [] : {}; if(typeof ...

  8. [Tensorflow-CPU完整安装过程-Win10]新手各种踩过的坑

    流程介绍:先安装Anaconda(不同Python版本对于Anaconda不同!!见图),然后就是在Anaconda Prompt里面安装Tensorflow即可. 环境介绍:Anaconda3-4. ...

  9. 编码的来源于格式简介ANSI、GBK、GB2312、UTF-8、GB18030和 UNICODE

    编码一直是让新手头疼的问题,特别是 GBK.GB2312.UTF-8 这三个比较常见的网页编码的区别,更是让许多新手晕头转向,怎么解释也解释不清楚.但是编码又是那么重要,特别在网页这一块.如果你打出来 ...

  10. [poj1062][最短路]昂贵的聘礼

    (最近总是有想让我的小博客更加充实的冲动,遇见一个不平常的题就想写下来.今天这个题姑且算是同学推荐的好题,很有意思,志之) 题目 题面 年轻的探险家来到了一个印第安部落里.在那里他和酋长的女儿相爱了, ...