Кодировщик H264 в андроиде?

У меня возникли проблемы при попытке починить простое приложение для записи видео*. Я думаю, что я правильно следовал последовательности шагов. Ниже приведено упрощение той части кода, которая вызывает у меня проблемы. Этот код выполняется только как обратный вызов после нажатия кнопки:

if ( mRecorder != null){
    mRecorder.reset();
    mRecorder.release();
}
mRecorder = new MediaRecorder();
if(mViewer.hasSurface){
    mRecorder.setPreviewDisplay(mViewer.holder.getSurface());
    Log.d(TAG,"Surface has been set");
}
try {
    Log.d(TAG,"Sleeping for 4000 mili");
    Thread.sleep(4000);
    Log.d(TAG,"Waking up");
} catch (InterruptedException e) {
    Log.e(TAG,"InterruptedException");
    e.printStackTrace();
}
mRecorder.setVideoSource(MediaRecorder.VideoSource.CAMERA);  
mRecorder.setAudioSource(MediaRecorder.AudioSource.MIC);
mRecorder.setOutputFormat(MediaRecorder.OutputFormat.MPEG_4);
mRecorder.setVideoFrameRate(12);
mRecorder.setVideoSize(176, 144);
mRecorder.setVideoEncoder(MediaRecorder.VideoEncoder.MPEG_4_SP);
mRecorder.setAudioEncoder(MediaRecorder.AudioEncoder.AMR_NB);
mRecorder.setMaxDuration(MAX_DURATION_TEST);

String targetFile = "/sdcard/webcamera/temp.mp4";
File localFile = new File(targetFile);
if(localFile.exists()){
    Log.d(TAG,"Local file exists");
}else{
    Log.d(TAG,"Local file does not exist");
}
mRecorder.setOutputFile(targetFile);
try {
    mRecorder.prepare();
    bPrepared = true;
    Log.i(TAG,"prepared");
    return;
} catch (IllegalStateException e) {
    e.printStackTrace();            
} catch (IOException e) {
    Log.e(TAG ,"IOException");
    Log.e(TAG,"Message: "+e.getMessage());
    StackTraceElement[] array = e.getStackTrace();
    for(StackTraceElement element : array){
        Log.e(TAG,""+element.toString());
    }
}

Важная вещь, которую я здесь не понимаю, заключается в том, что всякий раз, когда я устанавливаю кодировщик видео в MPEG_4_S, он работает. С другой стороны, всякий раз, когда я устанавливаю кодировщик H264, это просто не так. Проблема в том, что этот фрагмент кода является лишь частью более крупного проекта, а остальная часть ожидает, что это видео будет закодировано с помощью h264.

Тестирую на samsung Galaxy I-7500, кстати работает на froyo. И я думаю, что у Galaxy I-9000 такая же проблема.

Меня озадачивает то, что в соответствии с этой документацией прямо здесь: http://developer.android.com/guide/appendix/media-formats.html, кодировка MPEG_4_SP вообще не должна поддерживаться, а H264 поддерживается, начиная с сот. Так почему же он вообще работает с MPEG_4_SP? и можно ли заставить его работать с H264?

Ошибка, которую я получаю, не совсем ясна.

07-11 00:01:40.626: ERROR/MediaSource(1386): Message: prepare failed.
07-11 00:01:40.766: ERROR/MediaSource(1386): android.media.MediaRecorder._prepare(Native Method)
07-11 00:01:40.766: ERROR/MediaSource(1386): android.media.MediaRecorder.prepare(MediaRecorder.java:508)
07-11 00:01:40.766: ERROR/MediaSource(1386): com.appdh.webcamera.MediaSource.prepareOutput(MediaSource.java:74)
07-11 00:01:40.766: ERROR/MediaSource(1386): com.appdh.webcamera.MainActivity.startDetectCamera(MainActivity.java:312)

* На самом деле, приложение немного сложнее, так как оно также транслирует видео по локальной сети, но та часть, которая меня здесь интересует, не имеет к этому никакого отношения. Вы можете ознакомиться с этим интересным проектом здесь: http://code.google.com/p/ipcamera-for-android/


person Bilthon    schedule 11.07.2011    source источник
comment
Обратите внимание, что любое данное мобильное устройство может поддерживать дополнительные форматы или типы файлов, не указанные в таблице.   -  person Stefan H Singer    schedule 05.09.2011
comment
поддерживает ли устройство запись в формате H.264? Вы можете протестировать его с камерой по умолчанию на устройстве или с приложением камеры, которое поставляется с исходным кодом Android. Вы также можете попробовать изменить формат аудиокодировщика на AAC вместо AMR.. поскольку в документе говорится, что его можно комбинировать только с AAC (эта информация находится в предоставленной вами ссылке)   -  person bluefalcon    schedule 06.09.2011


Ответы (2)


Как вы уже писали, поддержку кодирования H.264 можно ожидать только от устройств с сотовым сотом и более поздних версий, что в настоящее время означает только планшеты. Если вам нужен H.264, вы должны проверить сбой подготовки и либо сообщить пользователю, что устройство не поддерживается, либо лучше заблокировать устройства без H.264 с помощью рыночных фильтров. Или вы можете скомпилировать ffmpeg для Android, как это делают некоторые другие проекты. Взгляните на эти ссылки:

http://odroid.foros-phpbb.com/t338-ffmpeg-compiled-with-android-ndk

http://bambuser.com/opensource

FFmpeg на Android

person mattlaabs    schedule 07.09.2011

Вы также можете использовать JCodec.

Он поддерживает Android и имеет несколько образцов для него. Лучший способ скомпилировать его с помощью Gradle:

compile 'com.github.jcodec:jcodec:0.2.0-vg4'

но для последних улучшений и исправлений ошибок вам нужно скомпилировать из последних коммитов (новой версии от 2016 года до сих пор нет)

person Ruslan Berozov    schedule 21.07.2017