Loading [MathJax]/jax/output/CommonHTML/config.js
首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
社区首页 >问答首页 >MTAudioProcessingTap在iOS上的应用

MTAudioProcessingTap在iOS上的应用
EN

Stack Overflow用户
提问于 2014-03-30 16:15:42
回答 1查看 1.3K关注 0票数 3

所以,我试着用Accelerate.framework阅读关于FFT的所有内容,并得到一个与MTAudioProcessingTap一起工作的例子,但是我觉得我做错了什么,我的点不应该是这样的。

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
#import "AudioTap.h"


#pragma mark - TapContext

typedef struct TapContext {
    void *audioTap;
    Float64 sampleRate;
    UInt32 numSamples;
    FFTSetup fftSetup;
    COMPLEX_SPLIT split;
    float *window;
    float *inReal;

} TapContext;


#pragma mark - AudioTap Callbacks

static void TapInit(MTAudioProcessingTapRef tap, void *clientInfo, void **tapStorageOut)
{
    TapContext *context = calloc(1, sizeof(TapContext));
    context->audioTap = clientInfo;
    context->sampleRate = NAN;
    context->numSamples = 4096;

    vDSP_Length log2n = log2f((float)context->numSamples);

    int nOver2 = context->numSamples/2;

    context->inReal = (float *) malloc(context->numSamples * sizeof(float));
    context->split.realp = (float *) malloc(nOver2*sizeof(float));
    context->split.imagp = (float *) malloc(nOver2*sizeof(float));

    context->fftSetup = vDSP_create_fftsetup(log2n, FFT_RADIX2);

    context->window = (float *) malloc(context->numSamples * sizeof(float));
    vDSP_hann_window(context->window, context->numSamples, vDSP_HANN_DENORM);



    *tapStorageOut = context;
}

static void TapPrepare(MTAudioProcessingTapRef tap, CMItemCount numberFrames, const AudioStreamBasicDescription *format)
{
    TapContext *context = (TapContext *)MTAudioProcessingTapGetStorage(tap);
    context->sampleRate = format->mSampleRate;

    if (format->mFormatFlags & kAudioFormatFlagIsNonInterleaved) {
        NSLog(@"is Non Interleaved");
    }

    if (format->mFormatFlags & kAudioFormatFlagIsSignedInteger) {
        NSLog(@"dealing with integers");
    }
}


static  void TapProcess(MTAudioProcessingTapRef tap, CMItemCount numberFrames, MTAudioProcessingTapFlags flags,
                        AudioBufferList *bufferListInOut, CMItemCount *numberFramesOut, MTAudioProcessingTapFlags *flagsOut)
{


    OSStatus status;

    status = MTAudioProcessingTapGetSourceAudio(tap, numberFrames, bufferListInOut, flagsOut, NULL, numberFramesOut);
    if (status != noErr) {
        NSLog(@"MTAudioProcessingTapGetSourceAudio: %d", (int)status);
        return;
    }

    //UInt32 bufferCount = bufferListInOut->mNumberBuffers;

    AudioBuffer *firstBuffer = &bufferListInOut->mBuffers[1];

    float *bufferData = firstBuffer->mData;
    //UInt32 dataSize = firstBuffer->mDataByteSize;
    //printf(": %li", dataSize);





    TapContext *context = (TapContext *)MTAudioProcessingTapGetStorage(tap);

    vDSP_vmul(bufferData, 1, context->window, 1, context->inReal, 1, context->numSamples);

    vDSP_ctoz((COMPLEX *)context->inReal, 2, &context->split, 1, context->numSamples/2);


    vDSP_Length log2n = log2f((float)context->numSamples);
    vDSP_fft_zrip(context->fftSetup, &context->split, 1, log2n, FFT_FORWARD);
    context->split.imagp[0] = 0.0;

    UInt32 i;


    NSMutableArray *outData = [NSMutableArray array];

    [outData addObject:[NSNumber numberWithFloat:0]];
    for( i = 1; i < context->numSamples; i++) {
        float power = context->split.realp[i] * context->split.realp[i] + context->split.imagp[i] * context->split.imagp[i];
        //amp[i] = sqrtf(power);

        [outData addObject:[NSNumber numberWithFloat:sqrtf(power)]];
    }


    AudioTap *audioTap = (__bridge AudioTap *)context->audioTap;
    [audioTap updateSpectrum:outData];

}

static void TapUnprepare(MTAudioProcessingTapRef tap)
{

}

static void TapFinalize(MTAudioProcessingTapRef tap)
{
    TapContext *context = (TapContext *)MTAudioProcessingTapGetStorage(tap);

    free(context->split.realp);
    free(context->split.imagp);
    free(context->inReal);
    free(context->window);

    context->fftSetup = nil;
    context->audioTap = nil;
    free(context);
}






#pragma mark - AudioTap Implementation


@implementation AudioTap

- (id)initWithTrack:(AVAssetTrack *)track frameSize:(UInt32)frameSize
{

    self = [super init];
    if (self) {

        _assetTrack = track;
        _frameSize = frameSize;

        [self setupAudioTap];

    }
    return self;

}

- (void)setupAudioTap
{
    //MTAudioProcessingTap
    MTAudioProcessingTapCallbacks callbacks;

    callbacks.version = kMTAudioProcessingTapCallbacksVersion_0;

    callbacks.init = TapInit;
    callbacks.prepare = TapPrepare;
    callbacks.process = TapProcess;
    callbacks.unprepare = TapUnprepare;
    callbacks.finalize = TapFinalize;
    callbacks.clientInfo = (__bridge void *)self;

    MTAudioProcessingTapRef tapRef;
    OSStatus err = MTAudioProcessingTapCreate(kCFAllocatorDefault, &callbacks,
                                              kMTAudioProcessingTapCreationFlag_PostEffects, &tapRef);

    if (err || !tapRef) {
        NSLog(@"Unable to create AudioProcessingTap.");
        return;
    }

    //Audio Mix
    AVMutableAudioMixInputParameters *inputParams = [AVMutableAudioMixInputParameters
                                                     audioMixInputParametersWithTrack:_assetTrack];

    inputParams.audioTapProcessor = tapRef;

    AVMutableAudioMix *audioMix = [AVMutableAudioMix audioMix];
    audioMix.inputParameters = @[inputParams];
    _audioMix = audioMix;
}



- (void)updateSpectrum:(NSArray *)data
{
    @autoreleasepool
    {
        dispatch_async(dispatch_get_main_queue(), ^{
            // Forward left and right channel volume to delegate.
            if (_delegate && [_delegate respondsToSelector:@selector(updateSpectrum:)]) {
                [_delegate updateSpectrum:data];
            }
        });
    }
}

@end

我读到audioBuffer->mData属性可能是浮点数(即SInt32等)以外的其他东西,如果是这样的话,如何确保在尝试对其进行快速傅立叶变换之前,正确地转换它?

EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2014-03-31 07:28:56

图长和实际FFT幅值结果长度(2^log2n)/2是不一样的。

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/22751685

复制
相关文章
java解析xml工具类[通俗易懂]
发布者:全栈程序员栈长,转载请注明出处:https://javaforall.cn/143972.html原文链接:https://javaforall.cn
全栈程序员站长
2022/08/31
1.4K0
Java XML解析工具类
发布者:全栈程序员栈长,转载请注明出处:https://javaforall.cn/162472.html原文链接:https://javaforall.cn
全栈程序员站长
2022/09/16
1.3K0
java 解析处理XML字符串
String text = "<members> <member>sitinspring</member> </members>"; org.dom4j.Document document = DocumentHelper.parseText(text); String text1 = document.selectSingleNode("/members/member").getText(); System.out.println(text1); <dependency> <groupId>ja
前Thoughtworks-杨焱
2021/12/08
4720
java解析XML格式字符串
一个字符串 <message>HELLO!</message>,怎样解析得到HELLO!? 正则表达式可以轻松解决,但是节点多了就搞不定了。 1、使用JDOM String xml = "<mess
matinal
2020/11/27
1.9K0
Java解析XML字符串「建议收藏」
在网上找了很多Java语言解析XML字符串的资料,很多内容写得很繁复,没有普适性,遂自己动手写了一个用Java解析XML的工具类。话不多说,直接看下面代码:
全栈程序员站长
2022/09/05
7090
xml解析---Java解析xml文件
dom4j解析xml文件、之前用下面的方法,90M的xml,500万行,解析完插入数据库,单线程,不到1小时搞定,而只是解析数据,只用了7秒。
IT云清
2019/01/22
7.1K0
java 解析xml报文(字符串)「建议收藏」
发布者:全栈程序员栈长,转载请注明出处:https://javaforall.cn/135916.html原文链接:https://javaforall.cn
全栈程序员站长
2022/09/05
1.9K0
JAVA解析XML格式字符串「建议收藏」
发布者:全栈程序员栈长,转载请注明出处:https://javaforall.cn/140692.html原文链接:https://javaforall.cn
全栈程序员站长
2022/09/01
2.2K0
Java解析XML字符串格式「建议收藏」
dom4j是一个Java的XML API,是jdom的升级品,用来读写XML文件的。dom4j是一个十分优秀的JavaXML API,具有性能优异、功能强大和极其易使用的特点,它的性能超过sun公司官方的dom技术,同时它也是一个开放源代码的软件,可以在SourceForge上找到它。在IBM developerWorks上面还可以找到一篇文章,对主流的Java XML API进行的性能、功能和易用性的评测,所以可以知道dom4j无论在哪个方面都是非常出色的。如今可以看到越来越多的Java软件都在使用dom4j来读写XML,特别值得一提的是连Sun的JAXM也在用dom4j。
全栈程序员站长
2022/09/05
1K0
xml解析工具-jdom
前言:近期接触SSH框架的时候,经常得配置一下xml文件;今天闲来没事就挖挖xml解析的原理供大伙儿分享。本文主要通过一个简单的例子解析一个xml文件。明白其中缘由之后,大家想定义自己的xml也绝非难事~
云海谷天
2022/08/09
7510
xml解析工具-jdom
Java 解析 XML[通俗易懂]
JAXP是JavaSE的一部分,在javax.xml.parsers包下,分别针对dom与sax提供了如下解析器:
全栈程序员站长
2022/09/05
1.9K0
xml解析---Java解析xml文件 /江格式解析
本文源于:http://www.cnblogs.com/Qian123/p/5231303.html点击这里
IT云清
2019/01/22
4K0
字符串解析成XML
用户3519280
2023/07/07
1520
Python解析XML字符串
# -*- coding: utf-8 -*- import xml.sax   import xml.sax.handler   class XMLHandler(xml.sax.handler.ContentHandler):   def __init__(self):   self.buffer = ""                     self.mapping = {}                   def startElement(se
py3study
2020/01/10
1.4K0
java 解析 XML实例
package com.hseact.fecp.servlet; import java.io.IOException; import javax.xml.parsers.DocumentBuilder; import javax.xml.parsers.DocumentBuilderFactory; import javax.xml.parsers.ParserConfigurationException; import org.json.JSONObject; import org.json.XM
庞小明
2018/03/07
1.4K0
Java解析XML文件
1.DOM方式解析XML Dom解析是将xml文件全部载入到内存,组装成一颗dom树,然后通过节点以及节点之间的关系来解析xml文件,与平台无关,java提供的一种基础的解析XML文件的API,理解较简单,但是由于整个文档都需要载入内存,不适用于文档较大时。
全栈程序员站长
2022/08/18
1.9K0
[ java 工具类] xml字符串解析成Map(DOM解析)
package com.tencent.jungle.wechat.util; import com.google.inject.Singleton; import org.w3c.dom.Document; import org.w3c.dom.Node; import org.w3c.dom.NodeList; import org.xml.sax.InputSource; import javax.xml.parsers.DocumentBuilder; import javax.xml.pars
Tencent JCoder
2018/12/14
3.3K0
java xml解析框架_JAVA解析xml的五种方式对比
本篇文章主要对比Java即系xml的五种方式,这五种方式各有利弊,大家可以看情况采用哪一种。
全栈程序员站长
2022/09/05
1.7K0
tinyXml直接解析XML字符串
tinyxml性能太差了,小文件还行,大文件痛苦死了 pugixml是一个不错的选择
用户3519280
2023/07/06
2970
Java解析XML的实践
通过这段代码,重点是需要理解他的解析过程,就可以根据实际用到的XML格式,写出对应的解析逻辑。
bisal
2023/02/16
1K0

相似问题

是否可以以编程方式更改全局偏移表/GOT或过程链接表/PLT?

38

过程链接表和调用关系表

11

用于链接表中行的存储过程

10

防止GDB中的PLT (过程链接表)断点

46

EF和链接表

21
添加站长 进交流群

领取专属 10元无门槛券

AI混元助手 在线答疑

扫码加入开发者社群
关注 腾讯云开发者公众号

洞察 腾讯核心技术

剖析业界实践案例

扫码关注腾讯云开发者公众号
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档
查看详情【社区公告】 技术创作特训营有奖征文