使用Core Audio实现对声卡输出的捕捉
涉及的接口有:
- IMMDeviceEnumerator
- IMMDevice
- IAudioClient
- IAudioCaptureClient
主要过程:
- 创建多媒体设备枚举器(IMMDeviceEnumerator)
- 通过多媒体设备枚举器获取声卡接口(IMMDevice)
- 通过声卡接口获取声卡客户端接口(IAudioClient)
- 通过声卡客户端接口(IAudioClient)可获取声卡输出的音频参数、初始化声卡、获取声卡输出缓冲区的大小、开启/停止对声卡输出的采集
- 通过声卡采集客户端接口(IAudioCaptureClient)可获取采集的声卡输出数据,并对内部缓冲区进行控制
- 通过声卡输出客户端接口(IAudioRenderClient)可将采集的声音数据写入声音输出设备的缓存单元,输出设备可以通过IAudioClient::GetService函数获取 IAudioRenderClient 接口。
代码示例:
//首先枚举你的音频设备,你可以在这个时候获取到你机器上所有可用的设备,并指定你需要用到的那个设备
hr = CoCreateInstance(
CLSID_MMDeviceEnumerator, NULL,
CLSCTX_ALL, IID_IMMDeviceEnumerator,
(void**)&pEnumerator);
EXIT_ON_ERROR(hr)
hr = pEnumerator->GetDefaultAudioEndpoint(
eCapture, eConsole, &pDevice);
EXIT_ON_ERROR(hr)
//创建一个管理对象,通过它可以获取到你需要的一切数据
hr = pDevice->Activate(
IID_IAudioClient, CLSCTX_ALL,
NULL, (void**)&pAudioClient);
EXIT_ON_ERROR(hr)
hr = pAudioClient->GetMixFormat(&pwfx);
EXIT_ON_ERROR(hr)
//初始化管理对象,在这里,你可以指定它的最大缓冲区长度,这个很重要,应用程序控制数据块的大小以及延时长短都靠这里的初始化,具体参数大家看看文档解释
hr = pAudioClient->Initialize(
AUDCLNT_SHAREMODE_SHARED,
0,
hnsRequestedDuration,
0,
pwfx,
NULL);
EXIT_ON_ERROR(hr)
//这个buffersize,指的是缓冲区最多可以存放多少帧的数据量
hr = pAudioClient->GetBufferSize(&bufferFrameCount);
EXIT_ON_ERROR(hr)
//创建采集管理接口,这个接口很简单,没什么重要的东西
hr = pAudioClient->GetService(
IID_IAudioCaptureClient,
(void**)&pCaptureClient);
EXIT_ON_ERROR(hr)
// Notify the audio sink which format to use.
hr = pMySink->SetFormat(pwfx);
EXIT_ON_ERROR(hr)
// Calculate the actual duration of the allocated buffer.
hnsActualDuration = (double)REFTIMES_PER_SEC *
bufferFrameCount / pwfx->nSamplesPerSec;
hr = pAudioClient->Start(); // Start recording.
EXIT_ON_ERROR(hr)
// Each loop fills about half of the shared buffer.
while (bDone == FALSE)
{
//让程序暂停运行一段时间,缓冲区里在这段时间会被填充数据
Sleep(hnsActualDuration/REFTIMES_PER_MILLISEC/2);
hr = pCaptureClient->GetNextPacketSize(&packetLength);
EXIT_ON_ERROR(hr)
while (packetLength != 0)
{
//锁定缓冲区,获取数据
hr = pCaptureClient->GetBuffer(
&pData,
&numFramesAvailable,
&flags, NULL, NULL);
EXIT_ON_ERROR(hr)
if (flags & AUDCLNT_BUFFERFLAGS_SILENT)
{
pData = NULL;
}
hr = pMySink->CopyData(
pData, numFramesAvailable, &bDone);
EXIT_ON_ERROR(hr)
hr = pCaptureClient->ReleaseBuffer(numFramesAvailable);
EXIT_ON_ERROR(hr)
hr = pCaptureClient->GetNextPacketSize(&packetLength);
EXIT_ON_ERROR(hr)
}
}
hr = pAudioClient->Stop();
EXIT_ON_ERROR(hr)
查看录制的音频可以用 audacity 这个软件
使用Core Audio实现对声卡输出的捕捉的更多相关文章
- 使用Core Audio实现VoIP通用音频模块
最近一直在做iOS音频技术相关的项目,由于单项直播SDK,互动直播SDK(iOS/Mac),短视频SDK,都会用到音频技术,因此在这里收集三个SDK的音频技术需求,开发一个通用的音频模块用于三个SDK ...
- Core Audio(二)
用户模式音频组件 在windows vista中,core audio apis充当用户模式音频子系统的基础,core audio apis作为用户模式系统组件的一个thin layer,它用来将用户 ...
- Core Audio(一)
Core Audio APIs core audio apis是vista之后引入的,不使用与之前的windows版本:core audio apis提供访问endpoint devices,比如耳机 ...
- Core Audio 在Vista/Win7上实现
应用范围:Vista / win7, 不支持XP 1. 关于Windows Core Auido APIs 在Windowss Vista及Windows 7操作系统下,微软为应用程序提供了一套新的音 ...
- 使用 Windows Core Audio APs 进行 Loopback Recording 并生成 WAV 文件
参考文档 COM Coding Practices Audio File Format Specifications Core Audio APIs Loopback Recording #inclu ...
- Core Audio(三)
音频终端设备(Audio Endpoint Devices) endpoint device指的是应用程序的数据通道上起始或终止的硬件设备,如扬声器,耳机,话筒等:沿着数据通道可能穿越一定数目的硬件和 ...
- windows core audio apis
这个播放流程有一次当初不是很理解,做个记录,代码中的中文部分,原文档是有解释的:To move a stream of rendering data through the endpoint buff ...
- Net Core 控制台程序使用Nlog 输出到log文件
using CoreImportDataApp.Common; using Microsoft.Extensions.Configuration; using Microsoft.Extensions ...
- win7 audio repeater 虚拟声卡 屏幕录像专家
随机推荐
- android:碎片的概念
碎片(Fragment)是一种可以嵌入在活动当中的 UI 片段,它能让程序更加合理和充分 地利用大屏幕的空间,因而在平板上应用的非常广泛.虽然碎片对你来说应该是个全新的概 念,但我相信你学习起来应该毫 ...
- lua去掉字符串中的UTF-8的BOM三个字节
废话不多说,还是先说点吧,项目中lua读取的text文件如果有BOM,客户端解析就会报错,所以我看了看,任务编辑器swGameTaskEditor 在写入文件的时候,也不知道为什么有的文件就是UTF- ...
- Android典型界面设计(4)——使用ActionBar+Fragment实现tab切换
一.问题描述 之前我们使用ViewPager+Fragment区域内头部导航,在Android 3.0之后Google增加了新的ActionBar,可方便的实现屏幕Head部区域的 设计如返回键.标题 ...
- 微信出现BUG,发送“ 两位数字+15个句号 ”,双方系统会卡崩……
刚刚,有网友反映称,微信出现了新的bug.例如,在微信中发“两位数字+15个句号”(另一说法是任意数字,任意15个标点符号),如果有华为手机或者安卓手机收到,就会卡死. 用安卓手机的朋友可以试一下,不 ...
- SqlSession介绍
SqlSession是MyBatis的关键对象,是执行持久化操作的对象,类似于JDBC中的Connection.它是应用程序与持久存储层之间执行交互操作的一个单线程对象,也是MyBatis执行持久化操 ...
- Notes 和 Domino 已知限制
Notes 和 Domino 已知限制 功能测试 限制数据库的最大大小是多少? 最大的 OS 文件大小限制 -(最大为 64GB)文本域的最大大小是多少? 15KB(存储):15KB,显示在视图列中R ...
- c++类大四个默认函数-构造函数 析构函数 拷贝构造函数 赋值构造函数
每个类只有一个析构函数和一个赋值函数,但可以有多个构造函数(包含一个拷贝构造函数,其它的称为普通构造函数).对于任意一个类A,如果不编写上述函数,C++编译器将自动为A 产生四个缺省的函数,例如: A ...
- 12C -- ORA-12850: 无法在所有指定实例上分配从属进程: 需要 2, 已分配 1
使用客户端连接到oracle 12.2.0.1 rac数据库,报以下错误信息: ORA-12850: 无法在所有指定实例上分配从属进程: 需要 2, 已分配 1 因为没有mos账号,只好谷歌一下了.找 ...
- [svc]对称加密/非对称加密细枝末节-如何做到数据传输的authentication/data integrity/confidentiality(私密)
对称/非对称/混合加密的冷知识 数据在互联网上传输,要考虑安全性. 讲到安全,要从三方面考虑: 1.authentication 每一个IP包的认证,确保合法源的数据 2.data integrity ...
- LayaBox IDE 安装后执行项目报错解决方案的一些记录
1.打开IDE后出现“路径xxx未指向有效地tsserver安装.将禁用TypeScript语言功能.”提示: 这是由于杀毒软件吧ts对应的js文件作为病毒删除导致的,一般到杀毒软件的历史界面中将ts ...