Android中使用Opus 1.3.1

Opus是一个开放格式的有损声音编码的格式,并在其使用上没有任何专利或限制。还可以处理各种音频应用,包括IP语音、视频会议、游戏内聊天、流音乐、甚至远程现场音乐表演。它可以从低比特率窄带语音扩展到非常高清音频的立体声音乐。支持的功能包括:

6 kb/秒到510 kb/秒的比特率;单一频道最高256 kb/秒

采样率从8 kHz(窄带)到48 kHz(全频)

帧大小从2.5毫秒到60毫秒

支持恒定比特率(CBR)、受约束比特率(CVBR)和可变比特率(VBR)

支持语音(SILK层)和音乐(CELT层)的单独或混合模式

支持单声道和立体声;支持多达255个音轨(多数据流的帧)

可动态调节比特率,音频带宽和帧大小

良好的鲁棒性丢失率和数据包丢失隐藏(PLC)

浮点和定点实现

Ndk编译产生Opus so库

快捷获取so库传送门:https://download.csdn.net/download/fepengwang/18623320

下载Opus源码

https://download.csdn.net/download/fepengwang/18623164

使用NDK-Build编译

解压下载好的opus-1.3.1.tar.gz

编写Android.mk文件到opus-1.3.1\

LOCAL_PATH := $(call my-dir)include $(CLEAR_VARS)
#我使用的是NDK 18
#NDK 17及以上不再支持ABIs [mips64, armeabi, mips]
APP_ABI := armeabi-v7a arm64-v8a x86 x86_64
APP_CPPFLAGS += -std=c++11
APP_STL := gnustl_shared
APP_PLATFORM := android-16include $(LOCAL_PATH)/celt_sources.mk
include $(LOCAL_PATH)/silk_sources.mk
include $(LOCAL_PATH)/opus_sources.mkLOCAL_MODULE        := opus# Fixed point sources
SILK_SOURCES        += $(SILK_SOURCES_FIXED)# ARM build
CELT_SOURCES        += $(CELT_SOURCES_ARM)
SILK_SOURCES        += $(SILK_SOURCES_ARM)
LOCAL_SRC_FILES     := \$(CELT_SOURCES) $(SILK_SOURCES) $(OPUS_SOURCES) $(OPUS_SOURCES_FLOAT)LOCAL_LDLIBS        := -lm -llog
LOCAL_C_INCLUDES    := \$(LOCAL_PATH)/include \$(LOCAL_PATH)/silk \$(LOCAL_PATH)/silk/fixed \$(LOCAL_PATH)/celt
LOCAL_CFLAGS        := -DNULL=0 -DSOCKLEN_T=socklen_t -DLOCALE_NOT_USED -D_LARGEFILE_SOURCE=1 -D_FILE_OFFSET_BITS=64
LOCAL_CFLAGS        += -Drestrict='' -D__EMX__ -DOPUS_BUILD -DFIXED_POINT -DUSE_ALLOCA -DHAVE_LRINT -DHAVE_LRINTF -O3 -fno-math-errno
LOCAL_CPPFLAGS      := -DBSD=1
LOCAL_CPPFLAGS      += -ffast-math -O3 -funroll-loopsinclude $(BUILD_SHARED_LIBRARY)

编译

$ cd opus-1.3.1
$ ndk-build APP_BUILD_SCRIPT=Android.mk NDK_PROJECT_PATH=.

注意:如果失败,看一下是否配置了ndk-build的环境变量


在libs中查看自己配置的平台是否完全产生,这里需要等2分钟左右哦!

转载请注明出处:https://blog.csdn.net/fepengwang/article/details/116714006#comments_16390157

在Android中使用so库

拷贝文件至Android项目中
opus-1.3.1/include —> app\src\main\cpp
opus-1.3.1/libs/* —> app\src\main\jniLibs\

以下为JNI文件内容

#include <jni.h>
#include <opus.h>#ifdef __cplusplus
extern "C" {#endifJNIEXPORT jlong JNICALL Java_com_wpf_opususedemo_utils_OpusUtils_createEncoder(JNIEnv *env, jobject thiz, jint sampleRateInHz, jint channelConfig, jint complexity) {int error;OpusEncoder *pOpusEnc = opus_encoder_create(sampleRateInHz, channelConfig,OPUS_APPLICATION_RESTRICTED_LOWDELAY,&error);if (pOpusEnc) {opus_encoder_ctl(pOpusEnc, OPUS_SET_VBR(0));//0:CBR, 1:VBRopus_encoder_ctl(pOpusEnc, OPUS_SET_VBR_CONSTRAINT(true));opus_encoder_ctl(pOpusEnc, OPUS_SET_BITRATE(32000));opus_encoder_ctl(pOpusEnc, OPUS_SET_COMPLEXITY(complexity));//8    0~10opus_encoder_ctl(pOpusEnc, OPUS_SET_SIGNAL(OPUS_SIGNAL_VOICE));opus_encoder_ctl(pOpusEnc, OPUS_SET_LSB_DEPTH(16));opus_encoder_ctl(pOpusEnc, OPUS_SET_DTX(0));opus_encoder_ctl(pOpusEnc, OPUS_SET_INBAND_FEC(0));opus_encoder_ctl(pOpusEnc, OPUS_SET_PACKET_LOSS_PERC(0));}return (jlong) pOpusEnc;
}
JNIEXPORT jlong JNICALL Java_com_wpf_opususedemo_utils_OpusUtils_createDecoder(JNIEnv *env, jobject thiz, jint sampleRateInHz, jint channelConfig) {int error;OpusDecoder *pOpusDec = opus_decoder_create(sampleRateInHz, channelConfig, &error);return (jlong) pOpusDec;
}
JNIEXPORT jint JNICALL Java_com_wpf_opususedemo_utils_OpusUtils_encode(JNIEnv *env, jobject thiz, jlong pOpusEnc, jshortArray samples, jint offset,jbyteArray bytes) {OpusEncoder *pEnc = (OpusEncoder *) pOpusEnc;if (!pEnc || !samples || !bytes)return 0;jshort *pSamples = env->GetShortArrayElements(samples, 0);jsize nSampleSize = env->GetArrayLength(samples);jbyte *pBytes = env->GetByteArrayElements(bytes, 0);jsize nByteSize = env->GetArrayLength(bytes);if (nSampleSize - offset < 320 || nByteSize <= 0)return 0;int nRet = opus_encode(pEnc, pSamples + offset, nSampleSize, (unsigned char *) pBytes,nByteSize);env->ReleaseShortArrayElements(samples, pSamples, 0);env->ReleaseByteArrayElements(bytes, pBytes, 0);return nRet;
}
JNIEXPORT jint JNICALL Java_com_wpf_opususedemo_utils_OpusUtils_decode(JNIEnv *env, jobject thiz, jlong pOpusDec, jbyteArray bytes,jshortArray samples) {OpusDecoder *pDec = (OpusDecoder *) pOpusDec;if (!pDec || !samples || !bytes)return 0;jshort *pSamples = env->GetShortArrayElements(samples, 0);jbyte *pBytes = env->GetByteArrayElements(bytes, 0);jsize nByteSize = env->GetArrayLength(bytes);jsize nShortSize = env->GetArrayLength(samples);if (nByteSize <= 0 || nShortSize <= 0) {return -1;}int nRet = opus_decode(pDec, (unsigned char *) pBytes, nByteSize, pSamples, nShortSize, 0);env->ReleaseShortArrayElements(samples, pSamples, 0);env->ReleaseByteArrayElements(bytes, pBytes, 0);return nRet;
}
JNIEXPORT void JNICALL Java_com_wpf_opususedemo_utils_OpusUtils_destroyEncoder(JNIEnv *env, jobject thiz, jlong pOpusEnc) {OpusEncoder *pEnc = (OpusEncoder *) pOpusEnc;if (!pEnc)return;opus_encoder_destroy(pEnc);
}
JNIEXPORT void JNICALL Java_com_wpf_opususedemo_utils_OpusUtils_destroyDecoder(JNIEnv *env, jobject thiz, jlong pOpusDec) {OpusDecoder *pDec = (OpusDecoder *) pOpusDec;if (!pDec)return;opus_decoder_destroy(pDec);
}
#ifdef __cplusplus
}
#endif

注意注意
CMakeLists.txt内容的编写!!!受自己本地NDK开发环境的影响,3.4.3版本中必须添加${CMAKE_CURRENT_SOURCE_DIR}否则会报错

这里记录一下我的踩坑:missing and no known rule to make it

解决方式:

CMakeLists.txt中配置的路径都是默认相对于CMakeLists.txt,但是在路径前还是要添加CMakeLists.txt的相对位置标识符${CMAKE_CURRENT_SOURCE_DIR}

CMakeList.tex内容:

cmake_minimum_required(VERSION 3.10.2)#set(libs_DIR src/main/jniLibs/${ANDROID_ABI}/libopus.so)
set(libs_include_DIR src/main/cpp/opus/include)
#支持-std=gnu++11
set(CMAKE_VERBOSE_MAKEFILE on)
set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -std=gnu++11")find_library( # Sets the name of the path variable.log-liblog )
add_library( # Sets the name of the library.opus-useSHARED${CMAKE_CURRENT_SOURCE_DIR}/src/main/cpp/opus-use.cpp)#关联头文件目录到库名
target_include_directories(opus-use # 库名PRIVATE # 库属性${CMAKE_CURRENT_SOURCE_DIR}/src/main/cpp/opus/include # 头文件目录
)#[[
每个库要单独添加一次
add_library(第三方库名称 共享动态库 导入)
set_target_properties(第三方库名称配置导入库具体第三方库路径
)
]]
add_library(opus_my SHARED IMPORTED)
set_target_properties(opus_myPROPERTIES IMPORTED_LOCATION${CMAKE_CURRENT_SOURCE_DIR}/src/main/jniLibs/${ANDROID_ABI}/libopus.so
)target_link_libraries( # Specifies the target library.opus-use${log-lib}opus_my)

完整版代码链接
https://download.csdn.net/download/fepengwang/18631244

在Android中使用Opus 1.3.1(Ndk编译使用Opus so库)相关推荐

  1. android NDK编译openblas和向量检索库faiss

    设置android SDK和NDK路径 例如: export SDK_PATH=/root/codes/my_sdk/sdk/ export NDK_PATH=/root/codes/my_sdk/s ...

  2. Android中如何APP视屏如何去除广告

    生死看淡,不服就干! http://www.wjdiankong.cn 目录视图 摘要视图 订阅 微信小程序实战项目--点餐系统 程序员11月书讯,评论得书啦 Get IT技能知识库,50个领域一键直 ...

  3. Android开发实践:在任意目录执行NDK编译

    本文暂时不讲述如何用NDK编译第三方开源代码库,而是先以简单的例子讲述如何在任意目录把自己写的C代码编译成Android可使用的静态库/动态库. 1. 准备环境 首先,你得安装了Android的NDK ...

  4. 在Android中实现OPUS编码

    将PCM转换成OPUS编码 Opus是一个有损声音编码的格式,由Xiph.Org基金会开发,之后由IETF(互联网工程任务组)进行标准化,目标是希望用单一格式包含声音和语音,取代Speex和Vorbi ...

  5. android视频剪辑处理第三方,Android 中通过 FFmpeg 命令对音视频编辑处理

    以下文章来源于DevYk ,作者DevYK 音视频编辑器 前言 有时候我们想对音视频进行加工处理,比如视频编辑.添加字幕.裁剪等功能处理,虽然 Github 上开源了一些比较不错的项目,但是如果我们想 ...

  6. Android 中通过 FFmpeg 命令对音视频编辑处理(已开源)

    视音频编辑器 前言 有时候我们想对音视频进行加工处理,比如视频编辑.添加字幕.裁剪等功能处理,虽然 Github 上开源了一些比较不错的项目,但是如果我们想在此项目上进行二次开发,比如我想拿到该项目的 ...

  7. Android中实现为TextView添加多个可点击的文本

    这篇文章主要介绍了Android中实现为TextView添加多个可点击的文本,可实现类似Android社交软件显示点赞用户并通过用户名称进入该用户主页的功能,是非常实用的技巧,需要的朋友可以参考下.具 ...

  8. android 弹出fragment,Android中ViewPager获取当前显示的Fragment

    前言 在项目中,有时会用到在ViewPager中显示同样类型的Fragment,同时这样的Fragment的个数是动态的,但是PagerAdapter没有给我们提供getCurrentFragment ...

  9. android 读取内部存储文件格式,Android中的数据储存之文件存储

    当我们在使用各种程序时,其实际上是在和各种数据打交道,当我们聊QQ,刷微博,看新闻,其实都是在和里面的数据交互 例如在聊天时发出的消息,以及在登录时输入的账号密码,其实都是瞬时数据,那什么是瞬时数据呢 ...

最新文章

  1. 6位技术大咖11月倾心巨献,大数据+安全主题的技术分享合集【阿里云MVP 干货集锦】...
  2. 关于 继承、扩展和协议,深度好文
  3. 使用脚本创建查找修改销毁游戏对象
  4. java解析lrc_java中用正则表达式解析LRC文件
  5. Angular全套知识讲解,错过必悔!
  6. python 源码保护_Python代码保护
  7. 每天一道LeetCode-----实现一个栈,提供一个接口用于返回栈中最小值
  8. Java生鲜电商平台-SpringCloud微服务架构高并发参数优化实战
  9. 【CodeForces - 438D】The Child and Sequence(线段树区间取模操作)
  10. HashMap源码分析(搞懂HashMap看这个就够了)
  11. mysql模糊查询LIKE、REGEXP(正则)的详解(在可视化工具navicat下)
  12. 批量添加后缀_掌握这 6 个批量处理技巧,少做 80% 的无用功!
  13. matlab中的myerr,Error in 'MPC1/S-Function' while executing MATLAB S-function 'MY_MPCCon...
  14. CentOS6.5和RedHat6.5下以rpm方式安装mysql-5.6.20
  15. 回溯法 之 马周游(马跳日)问题
  16. CreateProcess()无法启动应用?
  17. matlab分析电路,基于Matlab的电路节点分析法
  18. 小步快跑是这样玩的(下)
  19. 81.【SpringMVC】
  20. 网线品质差的三大影响

热门文章

  1. RHRP1560-ASEMI大功率快恢复二极管15A 600V
  2. 【转载】嵌入式开发板通过串口与PC互相传送文件
  3. [LOJ#522]「LibreOJ β Round #3」绯色 IOI(危机)
  4. AdobeFlash playe不是最新版本解决办法
  5. Qt软件开发_解决中文路径无法识别问题
  6. 弄懂企业营销之——微信私域社群运营(案例分析)
  7. 【深圳专场】从安防监控到害虫识别,目标检测核心技术全揭秘
  8. 2021年中国物联网(IoT),保障公共安全市场趋势报告、技术动态创新及2027年市场预测
  9. 安装系统后桌面没有计算机,装了新系统桌面没有显示我的电脑解决方法
  10. linux查看qq进程,Linux 进程初始堆栈内容查看