音频特效实践 您所在的位置:网站首页 audacity频谱图怎么放大 音频特效实践

音频特效实践

2024-07-16 17:11| 来源: 网络整理| 查看: 265

音频特效 基础概念 波形图

波形图横轴是时间,纵轴为强度。 这是一个波形图

频谱图

在波形图中选取一段时间的音频,快速傅立叶变换(FFT)可以得到频谱图。 频谱图的横轴为频率,纵轴为强度。 这是一个频谱图

语谱图

语谱图横轴为时间,纵轴为频率,颜色表示强度。 它是由STFT(短时傅里叶变换)得到。可以理解它是将时域的数据按固定的窗口分段进行FFT变换,然后叠加在一起。 可以把它理解为一个三位图形,但是用二维的形式呈现给了用户,即x轴为时间,y轴为频率,z轴为强度。 这是一个语谱图 以上图形是使用音频处理软件Audacity得到。

傅立叶变换 傅立叶变换可以将音频的时域数据转为频域数据。数字信号则使用DFT(离散傅立叶变换)来处理。但是因为DFT的计算量较大,实现一般会用FFT(快速傅立叶变换)。快速傅立叶变换的实现。 https://rosettacode.org/wiki/Fast_Fourier_transform#C.2B.2B一个android实现:https://github.com/paramsen/noise 效果器 均衡器(Equalizer)

均衡器可以提高/降低一段音频信号中某段频率的强度。比如我想比较喜欢一首歌的低频部分。我想将它的低频部分强度放大。则可以通过均衡器来调节低频区域的强度。 它的原理是将音频从时域进行FFT转换为频域,然后根据用户选择的中心频率,调节对应频率的强度,之后再进行FFT逆变换回时域信号。 在这里插入图片描述 软件中也会内置一些均衡器。 在这里插入图片描述

压缩效果器(Compressor)

压缩效果器,是指在时域上对声音强度所进行的一个处理。当音频的音量剧增的时候,会自动将音量调小一点。 在这里插入图片描述

阈值,当声音强度大于这个值时,之后的声音没增加 x 强度,则输出的强度只会增加 x / 比率。 比如压缩比为2:1 ,没当声音增加 2,经过压缩则只增加 1.比率,压缩的比率。建立时间,用于决定压缩器在超过阈值多久后触发压缩器来工作。释放时间,当声音低于阈值多长时间后,触发器停止工作。 混响效果器(Reverb)

实际生活中人听到的声音很多都是经过多次反射进入人耳的。你在一间教室,一个山谷、或者其他场所听到的声音都会有所不同。混响效果就是模拟这种环境。 在这里插入图片描述

效果器的实现 sox pc上的编译及使用 下载源码 git clone git://git.code.sf.net/p/sox/code sox 配置 autoreconf -i

编写sh脚本

#!/bin/bash CWD=`pwd` LOCAL=$CWD ./configure \ --prefix="$LOCAL/pc_lib" \ --enable-static \ --disable-shared \ --disable-openmp \ --without-libltdl \ --without-coreaudio 运行shell脚本构建及安装 make && make install 使用sox 构建完成之后可以在pc_lib目下下找到可执行文件sox. 如执行均衡器: sox audio.wav audio_output.wav equalizer 100.1 1.5q 3 equalizer 120 2.0q -19

上面的命令可以将audio.wav以100.1 位中心频率,宽为1.5q,强度提升3. 以及 120为中心频率宽度为 2.0q,强度降低19. 宽度为 ${x}q 表示的频宽。根据q可以计算出一个O(八度),一个O体现在频率上是2倍的频率。比如一个音调比另一个音调高一个八度,在频率上就是这个音调是另一个音调的2倍。

android上使用sox。 交叉编译配置文件 #!/bin/bash CWD=`pwd` LOCAL=$CWD NDK=~/Library/Android/sdk/ndk/22.1.7171670 NDK_SYSROOT=$NDK/toolchains/llvm/prebuilt/darwin-x86_64/sysroot export TOOLCHAIN=$NDK/toolchains/llvm/prebuilt/darwin-x86_64 export TARGET=armv7a-linux-androideabi # Set this to your minSdkVersion. export API=28 # Configure and build. export AR=$TOOLCHAIN/bin/llvm-ar export CC=$TOOLCHAIN/bin/$TARGET$API-clang export AS=$CC export CXX=$TOOLCHAIN/bin/$TARGET$API-clang++ export LD=$TOOLCHAIN/bin/ld export RANLIB=$TOOLCHAIN/bin/llvm-ranlib export STRIP=$TOOLCHAIN/bin/llvm-strip ./configure \ --prefix="$LOCAL/android_lib" \ --host $TARGET \ --with-pic \ --disable-openmp \ --without-libltdl make cmake 配置 cmake_minimum_required(VERSION 3.18) project(audioeffect) set(CMAKE_CXX_STANDARD 11) set(CMAKE_BUILD_TYPE Debug) set(CMAKE_VERBOSE_MAKEFILE ON) set(PREBUILT_DIR ${CMAKE_SOURCE_DIR}/../../../prebuilt/armv7a) message(STATUS "include ${PREBUILT_DIR}/include") file(GLOB SOURCES "*.cpp" "*.h" ) add_library(audioeffect SHARED ${SOURCES} ) add_library(sox STATIC IMPORTED GLOBAL) set_target_properties(sox PROPERTIES IMPORTED_LOCATION ${PREBUILT_DIR}/lib/libsox.a) set_target_properties(sox PROPERTIES INTERFACE_INCLUDE_DIRECTORIES ${PREBUILT_DIR}/include) target_link_libraries(audioeffect PRIVATE log PRIVATE sox) 实现一个均衡器 #include "Equalizer.h" #include "logger.h" #include #include void Equalizer::setInput(string input) { logi("%s,%s", "setInput", input.c_str()); input_ = std::move(input); } void Equalizer::setOutput(string output) { logi("%s,%s", "setOutput", output.c_str()); output_ = std::move(output); } void Equalizer::start() { assert(sox_init() == SOX_SUCCESS); in_ = sox_open_read(input_.c_str(), nullptr, nullptr, nullptr); out_ = sox_open_write(output_.c_str(), &in_->signal, nullptr, nullptr, nullptr, nullptr); chain_ = sox_create_effects_chain(&in_->encoding, &out_->encoding); // 输入 sox_effect_t *e = sox_create_effect(sox_find_effect("input")); char *args[10]; args[0] = (char *) in_; logi("in paths is %s:", args[0]); int result = sox_effect_options(e, 1, args); logi("effect input result is %d", result); assert(result == SOX_SUCCESS); sox_add_effect(chain_, e, &in_->signal, &in_->signal); free(e); // 均衡器 e = sox_create_effect(sox_find_effect("equalizer")); char *frequency = "300"; char *bandwidth = "1.25q"; char *gain = "3"; char *equalizer_chars[] = {frequency, bandwidth, gain}; result = sox_effect_options(e, 3, equalizer_chars); if (result != SOX_SUCCESS) { logi("option equalizer failed : error code is %d", result); assert(result == SOX_SUCCESS); } sox_add_effect(chain_, e, &in_->signal, &out_->signal); free(e); e = sox_create_effect(sox_find_effect("equalizer")); frequency = "300"; bandwidth = "1.25q"; gain = "30"; equalizer_chars[0] = frequency; equalizer_chars[1] = bandwidth; equalizer_chars[2] = gain; result = sox_effect_options(e, 3, equalizer_chars); if (result != SOX_SUCCESS) { logi("option equalizer failed : error code is %d", result); assert(result == SOX_SUCCESS); } sox_add_effect(chain_, e, &in_->signal, &out_->signal); free(e); // 输出 e = sox_create_effect(sox_find_effect("output")); args[0] = (char *) out_; result = sox_effect_options(e, 1, args); if (result != SOX_SUCCESS) { logi("option output effect failed : error code is %d", result); assert(result == SOX_SUCCESS); } sox_add_effect(chain_, e, &out_->signal, &out_->signal); free(e); sox_flow_effects(chain_, nullptr, nullptr); sox_delete_effects_chain(chain_); sox_close(out_); sox_close(in_); sox_quit(); }

sox的设计是一个责任链。使用时,先创建出一个chain,然后创建出需要的effect添加到chain中。上述的例子中为模式为:

input ----> equalizer1 -------> equalizer2 ----------> output

最终可以对比处理过后的音频和原音频的差异。 我这个例子中原音频的频谱为: 在这里插入图片描述 处理后为: 在这里插入图片描述

遇到的一些问题记录 编译器不支持Rewind-Pipe,根据注释提示,删掉#error FIX NEEDED HERE就行 formats.c:425:4: error: FIX NEEDED HERE #error FIX NEEDED HERE ^ 6 warnings and 1 error generated. make[1]: *** [libsox_la-formats.lo] Error 1

改法:

#elif defined _MSC_VER || defined _WIN32 || defined _WIN64 || \ defined _ISO_STDIO_ISO_H || defined __sgi fp->_ptr = fp->_base; #else /* To fix this #error, either simply remove the #error line and live without * file-type detection with pipes, or add support for your compiler in the * lines above. Test with cat monkey.wav | ./sox --info - */ // #error FIX NEEDED HERE #define NO_REWIND_PIPE (void)fp; #endif 找不到glob、globfree符号。这2个文件是在api28之后引入的,所有需要讲android api 调整为28及以上 copying selected object files to avoid basename conflicts... CCLD sox ld: error: undefined symbol: glob >>> referenced by sox.c:2606 >>> sox.o:(main) ld: error: undefined symbol: globfree >>> referenced by sox.c:2612 >>> sox.o:(main) clang: error: linker command failed with exit code 1 (use -v to see invocation) make[1]: *** [sox] Error 1 make: *** [all-recursive] Error 1 参考

https://zhuanlan.zhihu.com/p/19763358 http://sox.sourceforge.net/ https://github.com/paramsen/noise https://howtoeq.wordpress.com/2010/10/07/q-factor-and-bandwidth-in-eq-what-it-all-means/ https://developer.android.com/ndk/guides/other_build_systems



【本文地址】

公司简介

联系我们

今日新闻

    推荐新闻

    专题文章
      CopyRight 2018-2019 实验室设备网 版权所有