android lame wav 转 mp3,Android JNI Lame编解码实现wav到MP3的转换
1、JNI簡介
JNI全稱為Java Native Interface(JAVA本地調(diào)用)。從Java1.1開始,JNI成為java平臺的一部分,它允許Java代碼和其他語言寫的代碼(如C&C++)進行交互。并非從Android發(fā)布才引入JNI的概念的。
2、JNI與NDK
簡單來說,Android的NDK提供了一些交叉編譯工具鏈和Android自帶的庫,這些Android的庫可以讓開發(fā)者在編寫本地語言的程序時調(diào)用。而NDK提供的交叉編譯工具鏈就對已經(jīng)編寫好的C&C++代碼進行編譯,生成庫。
當然了,你也可以自己搭建交叉編譯環(huán)境,而不用NDK的工具和庫。然后生成庫,只要規(guī)范操作,一樣可以生成能讓JAVA層成功調(diào)用的庫文件的。
使用JNI技術(shù),其實就是在Java程序中,調(diào)用C語言的函數(shù)庫中提供的函數(shù),來完成一些Java語言無法完成的任務。由于Java語言和C語言結(jié)構(gòu)完全不相同,因此若想讓它們二者交互,則需要制定一系列的規(guī)范。JNI就是這組規(guī)范,此時 Java只和JNI交互,而由JNI去和C語言交互。
JNI技術(shù)分為兩部分:Java端和C語言端。且以Java端為主導。
|- 首先,Java程序員在Java端定義一些native方法,并將這些方法以C語言頭文件的方式提供給C程序員。
|- 然后,C程序員使用C語言,來實現(xiàn)Java程序員提供的頭文件中定義的函數(shù)。
|- 接著,C程序員將函數(shù)打包成一個庫文件,并將庫文件交給Java程序員。
在Java程序執(zhí)行的時候,若在某個類中調(diào)用了native方法,則虛擬機會通過JNI來轉(zhuǎn)調(diào)用庫文件中的C語言代碼。提示:C代碼最終是在Linux進程中執(zhí)行的,而不是在虛擬機中。
下面是一個Android調(diào)用JNI實現(xiàn)通過LAME轉(zhuǎn)碼器實現(xiàn)wav格式到MP3格式的轉(zhuǎn)換.
準備:首先下載lame源碼文件。
需要三個條件 :cgywin,cdt,ndk才能實現(xiàn)JNI的開發(fā)。
開發(fā)lame需要從http://lame.sourceforge.net/選擇Using Lame 下載源代碼。
新建工程
1、Android主界面布局
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:orientation="vertical" >
android:hint="源wav文件的路徑"
android:text="/sdcard/118/ccc.wav"
android:layout_width="match_parent"
android:layout_height="wrap_content" >
android:hint="目標MP3文件的路徑"
android:layout_width="match_parent"
android:text="/sdcard/118/ccccc.mp3"
android:layout_height="wrap_content" />
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="轉(zhuǎn)化"
android:onClick="convert"
/>
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="獲取lame版本號"
android:onClick="getversion"
/>
首先是建立JNI目錄
1、把lameC語言源碼導入jni中
2、創(chuàng)建Android.mk文件
LOCAL_PATH := $(call my-dir)
include $(CLEAR_VARS)
LOCAL_MODULE := Hello
LOCAL_SRC_FILES := bitstream.c fft.c id3tag.c mpglib_interface.c presets.c quantize.c reservoir.c tables.c util.c VbrTag.c encoder.c gain_analysis.c lame.c newmdct.c psymodel.c quantize_pvt.c set_get.c takehiro.c vbrquantize.c version.c Hello.c
LOCAL_LDLIBS += -llog
include $(BUILD_SHARED_LIBRARY)
3、編寫C語言文件
#include
#include
#include "com_example_ndkpassdata_DataProvider.h"
#include
#include
#define LOG_TAG "System.out.c"
#define LOGD(...) __android_log_print(ANDROID_LOG_DEBUG,LOG_TAG,__VA_ARGS__)
#define LOGI(...) __android_log_print(ANDROID_LOG_INFO,LOG_TAG,__VA_ARGS__)
char* Jstring2CStr(JNIEnv* env, jstring jstr) {
char* rtn = NULL;
jclass clsstring = (*env)->FindClass(env, "java/lang/String"); //String
jstring strencode = (*env)->NewStringUTF(env, "GB2312"); // 得到一個java字符串 "GB2312"
jmethodID mid = (*env)->GetMethodID(env, clsstring, "getBytes",
"(Ljava/lang/String;)[B"); //[ String.getBytes("gb2312");
jbyteArray barr = (jbyteArray)(*env)->CallObjectMethod(env, jstr, mid,
strencode); // String .getByte("GB2312");
jsize alen = (*env)->GetArrayLength(env, barr); // byte數(shù)組的長度
jbyte* ba = (*env)->GetByteArrayElements(env, barr, JNI_FALSE);
if (alen > 0) {
rtn = (char*) malloc(alen + 1); //"\0"
memcpy(rtn, ba, alen);
rtn[alen] = 0;
}
(*env)->ReleaseByteArrayElements(env, barr, ba, 0); //
return rtn;
}
JNIEXPORT jint JNICALL Java_com_example_ndkpassdata_DataProvider_add(
JNIEnv *env, jobject obj, jint x, jint y) {
LOGD("x=%d", x);
LOGD("y=%d", y);
return x + y;
}
JNIEXPORT jstring JNICALL Java_com_example_ndkpassdata_DataProvider_sayHelloInc(
JNIEnv *env, jobject obj, jstring jstr) {
char *cstr = Jstring2CStr(env, jstr);
LOGD("cstr=%s", cstr);
char arr[7] = { ‘ ‘, ‘h‘, ‘e‘, ‘l‘, ‘l‘, ‘o‘, ‘/0‘ };
strcat(cstr, arr);
LOGD("newcstr=%s", cstr);
return (*env)->NewStringUTF(env, cstr);
}
JNIEXPORT jintArray JNICALL Java_com_example_ndkpassdata_DataProvider_intMethod(
JNIEnv *env, jobject obj, jintArray arr) {
int len = (*env)->GetArrayLength(env, arr);
LOGD("SHUZU length-=%d", len);
jint *intarr = (*env)->GetIntArrayElements(env, arr, 1);
int i = 0;
for (; i < len; i++) {
LOGD("intarr[%d]=%d", i, intarr[i]);
*(intarr + i) += 10;
//intarr[i] += 10;
}
(*env)->ReleaseIntArrayElements(env, arr, intarr, len);
return arr;
}
JNIEXPORT jint JNICALL Java_com_example_ndkpassdata_DataProvider_sub(
JNIEnv *env, jclass clazz, jint x, jint y) {
LOGD("x=%d", x);
LOGD("Y=%d", y);
return x - y;
}
4、使用cgywin工具進行ndk-build編譯
成功之后
5、編寫Activity文件
package cn.itcast.lame;
import java.io.File;
import android.app.Activity;
import android.app.ProgressDialog;
import android.os.Bundle;
import android.view.View;
import android.widget.EditText;
import android.widget.Toast;
public class LameActivity extends Activity {
private EditText et_wav;
private EditText et_mp3;
private ProgressDialog pd;
public native void convertmp3(String wav,String mp3);
public native String getLameVersion();
public native void stop();
static{
System.loadLibrary("Hello");
}
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
et_wav = (EditText) this.findViewById(R.id.editText1);
et_mp3 = (EditText) this.findViewById(R.id.editText2);
pd = new ProgressDialog(this);
}
public void convert(View view){
final String mp3name = et_mp3.getText().toString().trim();
final String wavname = et_wav.getText().toString().trim();
File file = new File(wavname);
int size = (int) file.length();
System.out.println("文件大小 "+ size);
if("".equals(mp3name)||"".equals(wavname)){
Toast.makeText(this, "路徑不能為空", 1).show();
return;
}
//convertmp3(wavname,mp3name);
pd.setMessage("轉(zhuǎn)換中....");
pd.setProgressStyle(ProgressDialog.STYLE_HORIZONTAL);
pd.setMax(size); // 設置進度條的最大值
//pd.setCancelable(false);
pd.show();
new Thread(){
@Override
public void run() {
convertmp3(wavname,mp3name);
pd.dismiss();
}
}.start();
}
public void setConvertProgress(int progress){
pd.setProgress(progress);
}
public void getversion(View view){
String version = getLameVersion();
Toast.makeText(this, version, 0).show();
}
}
6、運行程序
總結(jié)
以上是生活随笔為你收集整理的android lame wav 转 mp3,Android JNI Lame编解码实现wav到MP3的转换的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: oracle to mysql demo
- 下一篇: android h5 书,android