Decode AAC, PCM mit ffmpeg auf android
Ich gebaut habe ffmpeg 0.8.12 (Liebe) mit dem android NDK (r8c) auf ubuntu.
Dann benutze ich die generierte Bibliothek in eine andere android-Anwendung durch JNI.
Im wesentlichen das, was ich will zu tun ist, übergeben Sie einen byte-stream von java, um meine c-jni-Funktion und verwenden Sie ffmpeg decodieren, die es in ein PCM-audio-Puffer, die dann zurück an java, gespielt zu werden, mit Android-Hörgeschichte. Ich kann erfolgreich die Puffer durch auf-jni (habe die Werte) und ffmpeg scheint zu initialisieren, richtig, aber wenn er versucht zu entschlüsseln, das erste Bild, wirft es einen Fehler in der aac_decode_frame_int Methode in aacdec.c "- Kanal-element-0.0 ist nicht vergeben". Die aac-Datei spielt gut und ist gültig.
Hier ist meine jni-code für die Dekodierung
jint Java_com_example_testffmpeg_MainActivity_decodeAacBytes(JNIEnv * env,
jobject this, jbyteArray input, jint numBytes) {
//copy bytes from java
jbyte* bufferPtr = (*env)->GetByteArrayElements(env, input, NULL);
uint8_t inputBytes[numBytes + FF_INPUT_BUFFER_PADDING_SIZE];
memset(inputBytes, 0, numBytes + FF_INPUT_BUFFER_PADDING_SIZE);
memcpy(inputBytes, bufferPtr, numBytes);
(*env)->ReleaseByteArrayElements(env, input, bufferPtr, 0);
av_register_all();
AVCodec *codec = avcodec_find_decoder(CODEC_ID_AAC);
if (codec == NULL) {
LOGE("Cant find AAC codec\n");
return 0;
}
LOGI("AAC codec found\n");
AVCodecContext *avCtx = avcodec_alloc_context();
if (avCtx == NULL) {
LOGE("Could not allocate codec context\n");
return 0;
}
LOGI("codec context allocated\n");
if (avcodec_open2(avCtx, codec, NULL) < 0) {
LOGE("Could not open codec\n");
return 0;
}
LOGI("AAC codec opened");
//the input buffer
AVPacket avPacket;
av_init_packet(&avPacket);
LOGI("AVPacket initialised\n");
avPacket.size = numBytes; //input buffer size
avPacket.data = inputBytes; //the input buffer
int outSize;
int len;
uint8_t *outbuf = malloc(AVCODEC_MAX_AUDIO_FRAME_SIZE);
while (avPacket.size > 0) {
outSize = AVCODEC_MAX_AUDIO_FRAME_SIZE;
len = avcodec_decode_audio3(avCtx, (short *) outbuf, &outSize,
&avPacket);
if (len < 0) {
LOGE("Error while decoding\n");
return 0;
}
if (outSize > 0) {
LOGI("Decoded some stuff\n");
}
avPacket.size -= len;
avPacket.data += len;
}
LOGI("Freeing memory\n");
av_free_packet(&avPacket);
avcodec_close(avCtx);
av_free(avCtx);
return 0;
}
Tritt das problem auf, in den Ruf zu avcodec_decode_audio3, wenn die Decodierung ersten Auftritt. Ich trat durch die ffmpeg-code, kann aber nicht das problem zu finden. Jede Hilfe wäre sehr geschätzt werden!
- Haben Sie versucht, zu Dekodieren, um die Datei auf der host-Maschine? Ist es entschlüsselt, die von ffmpeg? Was ist SoX, es ist fähig zu tun, dass auch normalisieren, fade-in/out, Lautstärke ändern, etc?
- Ich habe nicht versucht die Dekodierung der Datei mit ffmpeg in der Konsole - ich bin versucht zu entschlüsseln, aus der Anwendungs-code, so würde dies nicht helfen, mir jedenfalls. Die Datei wird ordnungsgemäß wiedergegeben, in jedem player auf meinem Handy, es ist also nicht beschädigt.
- Ich meine zu kompilieren SoX mit NDK, bitte siehe diesen link.
- Hhmm interessant. Ich werde weiter versuchen, mit ffmpeg, aber wenn ich nicht bekommen kann es arbeiten, ich gebe SoX gehen. Danke!
Du musst angemeldet sein, um einen Kommentar abzugeben.
Müssen Sie einige zusätzliche Einstellungen für
AVCodecContext
rufen Sie voravcodec_open2
.Ich in der Regel legen Sie die erforderlichen Einstellungen (Variablen beginnend mit 'k' bedeutet vordefinierten constatns):
UPD
Tut mir Leid, ich schrieb die Parameter, die festgelegt werden müssen, die für audio - Codierung.
Für die audio-Dekodierung in der Regel ausreichend eingestellt
avCtx->channels
,ctx->sample_rate
oder setavCtx->extrdata
undavCtx->extradata_size
.Zu finden, die den Fehler verursacht, versuchen Sie, um zu sehen, die ffmpeg Ausgabe. Wenn auf dem Gerät ist schwer zu tun, leiten Sie die ffmpeg Ausgabe und führen Sie die Protokollierung durch eigenen Rückruf. Beispiel: