android SDL系列讲解(十三) 播放音乐库 SDL_mixer教程

时间:2022-04-26
本文章向大家介绍android SDL系列讲解(十三) 播放音乐库 SDL_mixer教程,主要内容包括前言、下载SDL_mixer库、配置SDL_mixer库、验证播放音乐、移植libmod 库、关于Git、安装Git、延伸flac无损解码库编译、问题、基本概念、基础应用、原理机制和需要注意的事项等,并结合实例形式分析了其使用技巧,希望通过本文能帮助到大家理解应用这部分内容。

SDL系列讲解(一) 简介

SDL系列讲解(二) 环境搭建

SDL系列讲解(三) 工具安装

SDL是什么,能干什么,为什么我们要学习它?

SDL系列讲解(四) demo讲解

SDL系列讲解(五) 调试c代码

SDL系列讲解(六) SDL_Activity流程

SDL系列讲解(七) SDL_image教程

SDL系列讲解(八) SDL_ttf教程

SDL系列讲解(九) 异常退出分析

SDL系列讲解(十) 按键处理流程

SDL系列讲解(十一) SDL_QUIT流程

SDL系列讲解(十二)创建窗口流程

前言

讲解完了图片,文字,这节我们来看下怎么播放声音。

SDL默认是可以播放wav以及pcm格式的音乐,但是使用起来比较麻烦,所以官网给我们提供了一个三方库SDL_mixer,用来支援更多的音频格式,比如mp3,midi以及ogg,关于flac无损音乐,后续有个移植过程,但是编译出来使用的时候,发现速度跟不上,有卡顿现象,有兴趣的可以去研究下。在本节的最后,会提供flac的编译方法。

下载SDL_mixer库

来到 http://www.libsdl.org/projects/SDL_mixer/ ,下载这里的SDL2_mixer-2.0.1.zip

下载下来,我们放置到jni目录,改名字为SDL2_mixer。

配置SDL_mixer库

修改appsrcmainjni下面的Android.mk,新增两行加入

include src/main/jni/SDL2_mixer/external/libmikmod-3.1.12/Android.mk

include src/main/jni/SDL2_mixer/external/smpeg2-2.0.0/Android.mk

目的在于,将SDL2_mixer里面包含的开源库编译进来。然后开始编译,爆出一个错误

修改成assert(audio->timestamp >= (double*)0); 再次编译。

然后修改android-project/app/src/main/jni/src/Android.mk

LOCAL_SHARED_LIBRARIES := SDL2 SDL2_image SDL2_ttf

LOCAL_SHARED_LIBRARIES := SDL2 SDL2_image SDL2_ttf SDL2_mixer

将我们的SDL2_mixer包含进来。

验证播放音乐

下载一首歌曲,这里下载薛之谦的《动物世界》,放置在项目的assets目录下。

然后在我们的main.c的main方法里面加入

//初始化mix,MP3格式
 if (Mix_Init(MIX_INIT_MP3) < 0) {
     printf("Mix_Init: %sn", SDL_GetError());
     return 1;
 }
 //打开设备
 if (Mix_OpenAudio(22050, MIX_DEFAULT_FORMAT, 2, 4096) < 0) {
     printf("Mix_OpenAudio: %sn", SDL_GetError());
     return 1;
 }
 Mix_Music *music = Mix_LoadMUS("dongwu.mp3");
 Mix_PlayMusic(music, SDL_TRUE);

在退出的地方,加入

然后编译,运行app,观看效果。然而你所遇到的是个bug,apk异常退出啦。

可以看到,这里是解包的大小引起,本身三方库就是解决编解码的问题,然而编解码出现问题,可以去修复,同时也可以使用其他替代,这里我们用SDL提供的第二个库libmad进行解码mp3格式。

移植libmod 库

第一步,下载git for window

打开 http://rj.baidu.com/soft/detail/30195.html?ald 进行下载即可。

关于Git

Git是一个开源的分布式版本控制系统,用于敏捷高效地处理任何或小或大的项目。

Git 是 Linus Torvalds 为了帮助管理 Linux 内核开发而开发的一个开放源码的版本控制软件。

Git 与常用的版本控制工具 CVS, Subversion 等不同,它采用了分布式版本库的方式,不必服务器端软件支持。

安装Git

主界面:

我们只需要一直下一步即可,不用管其他的操作,使用默认的即可。

安装后,我们点击电脑左下方的window图标,选择所有应用,选择git目录,选择git Bash

选择点开git Bash之后,界面为:

然后我们使用cd /d 进入d盘,然后使用

git clone https://gitorious.org/rowboat/external-libmad.git 将libmad模块抓下来。

等待下载完成,然后我们进入d盘下,将下载好的目录,复制到我们项目的appsrcmainjniSDL2_mixerexternal目录下,并且改名为libmad

然后我们修改appsrcmainjni下面的Android .mk ,加入一行:

include src/main/jni/SDL2_mixer/external/libmad/Android.mk

然后我们修改appsrcmainjniSDL2_mixer下面的Android.mk

LOCAL_C_INCLUDES := $(LOCAL_PATH)
LOCAL_CFLAGS := -DWAV_MUSIC

后面加入:

同时把本文件的

SUPPORT_MP3_SMPEG ?= true 修改成
SUPPORT_MP3_SMPEG ?= false

去掉smpeg的默认解码mp3,使用mad库进行解码。

进入appsrcmainjniSDL2_mixerexternallibmad 修改这里的Android.mk

具体为:

删除第一行的

ifeq ($(strip $(BUILD_WITH_GST)),true)

和最后一行的

endif

然后修改:

LOCAL_CFLAGS := 
    -DHAVE_CONFIG_H 
    -DFPM_DEFAULT

修改为:

LOCAL_CFLAGS :=-DHAVE_CONFIG_H -DFPM_ARM -ffast-math -O3

这里主要的是FPM_ARM,让编译arm指令集。

如果编译过程报错:

Error:error: invalid instruction mnemonic 'smull'

我们需要修改

ndk {
    abiFilters "armeabi", "armeabi-v7a", "x86" }

这里的armeabi 需要去掉,同时我们去掉x86,去掉armeabi是因为低版本的arm没有smull指令,去掉x86是因为我们手机是arm平台,为了我们快速编译apk,就先去掉它。

延伸flac无损解码库编译

不做更详细的讲解,这里将我的操作过程展示一下。因为我们一般使用的mp3 wav格式,当前已经完美支持,所以flac放在有兴趣研究的人,这里作为抛砖一下。

http://downloads.xiph.org/releases/flac/flac-1.3.2.tar.xz 下载flac库。

然后我们需要ubuntu 等linux环境,解压,进入目录,然后使用:

./configure --help 进行查看都有哪些命令,然后进行配置,配置参数里面的CC CXX这些路径,需要自己修改对应自己的真正arm编译链的位置。

./configure

--prefix=/home/andy/share/flac/cross_install --enable-cross-compile --build=i386-pc-linux-gnu --host=arm-linux --target=arm-linux --enable-ogg --disable-3dnow --disable-oggtest --disable-asm-optimizations --disable-xmms-plugin --disable-sse --disable-cpplibs --disable-shared --disable-id3libtest CC=/home/user/Android/Sdk/ndk-bundle/toolchains/arm-linux-androideabi-4.9/prebuilt/linux-x86_64/bin/arm-linux-androideabi-gcc CXX=/home/user/Android/Sdk/ndk-bundle/toolchains/arm-linux-androideabi-4.9/prebuilt/linux-x86_64/bin/arm-linux-androideabi-g++ AR=/home/user/Android/Sdk/ndk-bundle/toolchains/arm-linux-androideabi-4.9/prebuilt/linux-x86_64/bin/arm-linux-androideabi-ar LD=/home/user/Android/Sdk/ndk-bundle/toolchains/arm-linux-androideabi-4.9/prebuilt/linux-x86_64/bin/arm-linux-androideabi-ld RANLIB=/home/user/Android/Sdk/ndk-bundle/toolchains/arm-linux-androideabi-4.9/prebuilt/linux-x86_64/bin/arm-linux-androideabi-ranlib STRIP=/home/user/Android/Sdk/ndk-bundle/toolchains/arm-linux-androideabi-4.9/prebuilt/linux-x86_64/bin/arm-linux-androideabi-strip CFLAGS="-I/home/user/Android/Sdk/ndk-bundle/platforms/android-24/arch-arm/usr/include -I/media/user/big/sdl/android-project/app/src/main/jni/SDL2_mixer/external/libogg-1.3.1/include" CXXFLAGS="-I/home/user/Android/Sdk/ndk-bundle/platforms/android-24/arch-arm/usr/include -I/media/user/big/sdl/android-project/app/src/main/jni/SDL2_mixer/external/libogg-1.3.1/include" LDFLAGS=--sysroot=/home/user/Android/Sdk/ndk-bundle/platforms/android-24/arch-arm

配置通过后,我们使用make 即可完成编译,如果想看编译的具体参数等信息,可以使用make --just-print 进行只输出命令,不做实质编译,用来学习编译过程,最好不过啦。

编译过后,会出来一个libFLAC-static.a 静态库,然后我们在我们的项目jni目录下创建libs目录加入这个库:libs/libFLAC.a (改成这个名字)

在SDL2_mixer目录下的Android .mk 加入:

编译之后,这是我们可以播放flac格式的音乐了。

问题

flac编译出来,可以播放音乐,但是比较卡,具体此问题,留作疑问。