Androidでの録音とMP3へのローカルトランスコード
**
ローカルトランスコードによるAndroid録画
**
Android携帯電話による録音。
録画後、トランスコード操作にlameを使用する。
これは開発時に必要なもので、単純にトランスコードするためのツールで、以下のようなコード情報があります。
プロジェクトの基本構造
1. ツールキットのダウンロード
ダウンロード
ラームツールキット
使用した最新バージョン
NDK環境のインストール
2. ダサいコンテンツコピー
まず、src/main/ ディレクトリに新しい cpp フォルダを作成し、Lame のソースコードから libmp3lame を cpp フォルダにコピーしてください。
Lameソースコードのincludeフォルダにあるlame.hをlamemp3フォルダにコピーします。
lamemp3内の不要なファイルやディレクトリを削除する。.rc/am/inファイルは削除してもよい。Androidはここでは使用せず、.cと.hファイルのみを残す。
util.hのソースコードを修正します。ieee754_float32_tはLinuxやUnixではサポートされているが、Androidではサポートされていないデータ型なので、570行目のieee754_float32_tを探し、floatに変更する。
24行目の set_get.h の include<lame.h> を include"lame.h" に置き換える。
id3tag.c と machine.h ファイルで、HAVE_STRCHR と HAVE_MEMCPY の ifdef 構造体をコメントアウトすると、コンパイル時にエラーになります。
3. build.gradleの設定
Androidstudioが最新に更新されたため
defaultConfig {
applicationId "com.example.gz.testmp3"
minSdkVersion 23
targetSdkVersion 27
versionCode 1
versionName "1.0"
testInstrumentationRunner "android.support.test.runner.AndroidJUnitRunner"
externalNativeBuild{
cmake{
cppFlags "-frtti -fexceptions" //set cpp configuration parameters, c files please use CFlags
abiFilters 'armeabi-v7a', "armeabi"
}
}
ndk{
abiFilters 'armeabi-v7a', "armeabi"
}
}
sourceSets{
main{
jniLibs.srcDirs = ['libs']
}
}
cmakeで最新のNDKをダウンロードした場合、以下のようなエラーが発生します。
abis [mips64, armeabi, mips] are not supported for platform. <対応
abisは[armeabi-v7a, arm64-v8a, x86, x86_64]です。
解決策は、gradle の cmake abiFilters 設定を次のように変更します:abiFilters 'x86', 'x86_64', 'arm64-v8a ', 'armeabi-v7a'.
Google NDK r18の説明です。ARMv5 (armeabi)、MIPS、および MIPS64 のサポートが削除されました。これらのABIのいずれかをビルドしようとすると、エラーが発生します。
私のabiFiltersは、ここでは2つだけです。
4. JavaネイティブメソッドMP3Converterの作成
public class MP3Converter {
static {
System.loadLibrary("lame-mp3-utils");// make sure to write the right name here
}
// test the lame environment is installed successfully
public static native String getLameVersion();
/**
* init lame
* @param inSampleRate
* input sample rate in Hz
* @param channel
* number of channels
* @param mode
* 0 = CBR, 1 = VBR, 2 = ABR. default = 0
* @param outSampleRate
* output sample rate in Hz
* @param outBitRate
* rate compression ratio in KHz
* @param quality
* quality=0..9. 0=best (very slow). 9=worst. <br />
* recommended:<br />
* 2 near-best quality, not too slow<br />
* 5 good quality, fast<br />
* 7 ok quality, really fast
*/
public native static void init(int inSampleRate, int channel, int mode,
int outSampleRate, int outBitRate, int quality);
/**
* file convert to mp3
* it may cost a lot of time and better put it in a thread
* @param inputPath
* file path to be converted
* @param mp3Path
* mp3 output file path
*/
public native static void convertMp3(String inputPath, String mp3Path);
/**
* get converted bytes in inputBuffer
* @return
* converted bytes in inputBuffer
* to ignore the deviation of the file size,when return to -1 represents convert complete
*/@return
public native static long getConvertBytes();
}
5. C/C++を呼び出すcppを書く
この直接の使用は、Baiduの上にある、読むことができるように限定され、C + +のために理解していない
extern "C"
JNIEXPORT void JNICALL
Java_jaygoo_library_converter_MP3Converter_convertMp3(JNIEnv * env, jobject obj, jstring jInputPath, jstring jMp3Path) {
const char* cInput = env->GetStringUTFChars(jInputPath, 0);
const char* cMp3 = env->GetStringUTFChars(jMp3Path, 0);
//open input file and output file
FILE* fInput = fopen(cInput,"rb");
FILE* fMp3 = fopen(cMp3,"wb");
short int inputBuffer[BUFFER_SIZE * 2];
unsigned char mp3Buffer[BUFFER_SIZE];// You must specify at least 7200
int read = 0; // number of bytes in inputBuffer, if in the end return 0
int write = 0; // number of bytes output in mp3buffer. can be 0
long total = 0; // the bytes of reading input file
nowConvertBytes = 0;
// if you don't init lame, it will init lame use the default value
if(lame == NULL){
lameInit(44100, 2, 0, 44100, 96, 7);
}
//convert to mp3
do{
read = static_cast<int>(fread(inputBuffer, sizeof(short int) * 2, BUFFER_SIZE, fInput));
total += read * sizeof(short int)*2;
nowConvertBytes = total;
if(read ! = 0){
write = lame_encode_buffer_interleaved(lame, inputBuffer, read, mp3Buffer, BUFFER_SIZE);
//write the converted buffer to the file
fwrite(mp3Buffer, sizeof(unsigned char), static_ca
6. を呼び出すことが残っています。
/**
* Start recording
* @param mFlag
*/
public void recode(int mFlag){
if(mState ! = -1){
Log.e(mState+"1", "mState: "+mState );
Message msg = new Message();
Bundle b = new Bundle();// store data
b.putInt("cmd",CMD_RECORDFAIL);
b.putInt("msg", ErrorCode.E_STATE_RECODING);
msg.setData(b);
uiHandler.sendMessage(msg); // send message to Handler, update UI
return;
}
int mResult = -1;
AudioRecorderWav mRecord_1 = AudioRecorderWav.getInstance();
mResult = mRecord_1.startRecordAndFile(MainActivity.this);
if(mResult == ErrorCode.SUCCESS){
mState = mFlag;
uiThread = new UIThread();
new Thread(uiThread).start();
}else{
Message msg = new Message();
Bundle b = new Bundle();// store data
b.putInt("cmd",CMD_RECORDFAIL);
b.putInt("msg", mResult);
msg.setData(b);
uiHandler.sendMessage(msg); // send message to Handler, update UI
}
}
発生した可能性のある問題
rg.gradle.api.internal.tasks.compile.CompilationFailedException:
コンパイルに失敗しました。コンパイルに失敗しました。詳細はコンパイラのエラー出力をご覧ください。
解決プロセス
端末入力
gradlew compileDebugSourcesを実行します。
エラーメッセージの表示
コードダウンロード先
テストMp3
参考記事
Android NDKを使用したMP3トランスコードライブラリの実装方法を紹介
Android NDKの開発(VI) - オープンソースLAMEを使ったmp3のトランスコーディング
アプリケーションのインターフェースは以下の通りです。
関連
-
ADBサーバーがackしない問題の解決策(ADB接続の問題)
-
Android 開発において、null オブジェクトの参照で仮想メソッドを呼び出そうとする。
-
Solve Android 仮想メソッドの呼び出しに失敗する。NULLオブジェクトの参照で
-
呼び出しは、ユーザーによって拒否される可能性のある許可を必要とします。
-
Androidでコンストラクタのインテントを解決できない原因と解決策
-
アプリケーションがメインスレで仕事をしすぎている可能性がある
-
Android マルチメディア MediaPlayerの使用方法詳細
-
サービスを利用した特別な放送受信者の登録
-
AndroidのRadioButtonの中央寄せ問題(解決済み)
-
android start activity report android.content.res.Resources$NotFoundException: 文字列リソースID #0x0
最新
-
nginxです。[emerg] 0.0.0.0:80 への bind() に失敗しました (98: アドレスは既に使用中です)
-
htmlページでギリシャ文字を使うには
-
ピュアhtml+cssでの要素読み込み効果
-
純粋なhtml + cssで五輪を実現するサンプルコード
-
ナビゲーションバー・ドロップダウンメニューのHTML+CSSサンプルコード
-
タイピング効果を実現するピュアhtml+css
-
htmlの選択ボックスのプレースホルダー作成に関する質問
-
html css3 伸縮しない 画像表示効果
-
トップナビゲーションバーメニュー作成用HTML+CSS
-
html+css 実装 サイバーパンク風ボタン
おすすめ
-
Android Studio + Gradle またはコマンドラインを使用した Android apk の署名とパッケージング
-
Android プロジェクトのライブラリに armeabi-v7a、armeabi、x86 が追加されました。
-
GPSプロンプトの問題は、Callがユーザーによって拒否される可能性のある許可を必要とすることです:コードは、明示的にsをチェックする必要があります。
-
第20章 OnCheckedChangeListenerイベント (ゼロから学ぶAndroid)
-
RuntimeException: Unable to start activity ComponentInfo{xxx}: java.lang.NullPoi Androidの開発において、アクティビティを開始できません。
-
Android O (8.0) デスクトップショートカットを作成する
-
Eclipse &プラグインのよくある使用エラーとコンパイルエラー
-
adb push 権限拒否の解決策
-
Androidリストウィジェット開発詳細
-
AndroidでデータをExcelファイルに書き出す方法