2013-07-23 17 views
11

Poniżej znajduje się struktura mojego kodu pracy do nagrywania wideo i audio:Korzystanie android MediaRecorder

pytania: 1) Dlaczego CamcorderProfile potrzebne? setProfile(...) pojawia się, aby ustawić wymiary na dowolną wartość QUALITY_HIGH, ale później ustawię żądane wymiary za pomocą setVideoSize(...), co spowoduje nadpisanie tego wymiaru. Jednak po usunięciu dwóch linii CamcorderProfile aplikacja ulega awarii pod numerem setVideoSize(...) z LogCat E/MediaRecorder(19526): setVideoSize called in an invalid state: 2.

2) Jak nie nagrywać dźwięku? Dokumentacja stwierdza, że ​​jeśli nie zostanie wywołana setAudioSource(...), nie będzie ścieżki dźwiękowej. Jednak po usunięciu tej linii aplikacja ulega awarii pod numerem setProfile(...) z LogCat E/MediaRecorder(19946): try to set the audio encoder without setting the audio source first.

3) Jeśli usunę obie linie kamery Camcorder i linię setAudioSource(...), ulegnie awarii, jak w 1).

4) Próbowałem również dodać linię

recorder.setOutputFormat(OutputFormat.DEFAULT); 

zamiast linii CamcorderProfile. Ale teraz ulega awarii na perpare(). Jeśli setAudioSource(...) nazywa się LogCat jest: E/MediaRecorder(20737): audio source is set, but audio encoder is not set jeśli nie nazywa się logcat jest: E/MediaRecorder(20544): video source is set, but video encoder is not set

Szukałem allover internet i nie mogę znaleźć dobry przykład poprawny sposób skonfigurować MediaRecorder. Here to oznacza, że ​​po API 8 powinieneś używać klasy CamcorderProfile, ale wydaje mi się, że powoduje problemy.

Każda pomoc będzie świetna! Dzięki!

Code (który działa podczas uruchamiania, jak to jest poniżej):

recorder = new MediaRecorder(); 
recorder.setCamera(<<camera>>); 
recorder.setAudioSource(MediaRecorder.AudioSource.DEFAULT); 
recorder.setVideoSource(MediaRecorder.VideoSource.DEFAULT); 

CamcorderProfile profile = CamcorderProfile.get(CamcorderProfile.QUALITY_HIGH); 
recorder.setProfile(profile); 

recorder.setOutputFile(<<Path String>>); 
recorder.setVideoSize(<<Width>>, <<Height>>); 

recorder.setPreviewDisplay(<<Surface>>); 

recorder.setOrientationHint(0); 
recorder.setMaxDuration(10000); 
recorder.setOnInfoListener(this); 

try 
{ 
    recorder.prepare(); 
    recorder.start(); 
} catch ... 

Odpowiedz

15

Nie mam dużego doświadczenia z MediaRecorder ale czytałem kilka podobnych tematów i postaram się odpowiedzieć na pytania:

1, 3 i 4) CamcorderProfile ustawia więcej niż tylko rozmiar, ale również ustawia rzeczy jako format wyjściowy i koderów (zarówno audio i video). Otrzymujesz błąd, ponieważ prawdopodobnie musisz użyć setOutputFormat zanim zadzwonisz pod numer setVideoSize i musisz po nim zadzwonić pod numer setVideoEncoder i setAudioEncoder, jeśli nie chcesz używać CamcorderProfile. [Zgodnie z tym answer]

2) Ponownie CamcorderProfile określa również właściwości audio (takich jak kodek, bitrate, próbkowania, ...), więc trzeba ustawić źródło dźwięku przed nazywając ją, dlatego aplikacja się zawiesiła. Jeśli nie chcesz nagrywać dźwięku spróbować następny kod: (nie testowałem to więc właściwie nie wiem, czy to działa, ale jestem pewien, że robi)

recorder.setVideoSource(MediaRecorder.VideoSource.DEFAULT); 
recorder.setOutputFormat(MediaRecorder.OutputFormat.MPEG_4); 
recorder.setVideoSize(WIDTH, HEIGHT); 
recorder.setVideoEncoder(MediaRecorder.VideoEncoder.DEFAULT); 
recorder.setOutputFile(PATH); 
recorder.setPreviewDisplay(SURFACE); 

recorder.prepare(); 
recorder.start(); 

Należy także pamiętać, jeśli nie chcesz używać CamcorderProfile (co oznacza, że ​​chcesz nagrywać tylko audio lub wideo), być może musisz ustawić dodatkowe parametry, aby mieć pewność, że masz odpowiednią jakość. Spójrz na poniższy przykładowy kod:

recorder = new MediaRecorder(); 
recorder.setVideoSource(MediaRecorder.VideoSource.DEFAULT); 
recorder.setAudioSource(MediaRecorder.AudioSource.DEFAULT); 

// Following code does the same as getting a CamcorderProfile (but customizable) 
recorder.setOutputFormat(MediaRecorder.OutputFormat.MPEG_4); 
// Video Settings 
recorder.setVideoSize(WIDTH, HEIGHT); 
recorder.setVideoFrameRate(FRAME_RATE); 
recorder.setVideoEncoder(MediaRecorder.VideoEncoder.DEFAULT); 
recorder.setVideoEncodingBitRate(VIDEO_BITRATE); 
// Audio Settings 
recorder.setAudioChannels(AUDIO_CHANNELS); 
recorder.setAudioSamplingRate(SAMPLE_RATE); 
recorder.setAudioEncoder(MediaRecorder.AudioEncoder.DEFAULT); 
recorder.setAudioEncodingBitRate(AUDIO_BITRATE); 

// Customizable Settings such as: 
// recorder.setOutputFile(PATH); 
// recorder.setPreviewDisplay(SURFACE); 
// etc... 

// Prepare and use the MediaRecorder 
recorder.prepare(); 
recorder.start(); 
... 
recorder.stop(); 
recorder.reset(); 
recorder.release(); 

Mam nadzieję, że ci to pomoże.

+1

Masz rację, tak jak to napisałem, znalazłem kod funkcji 'setProfile()'. Zawsze wywołuje 'setAudioEncoder()', więc jeśli nie ustawisz źródła dźwięku, zawiesi się. Odpowiedzią jest skopiowanie tej funkcji, dzięki czemu nadal możesz korzystać z wbudowanych ustawień 'CamcorderProfile', ale także wybrać ustawienia, które chcesz ustawić (np. Audio). Dzięki – jacobianism

+0

Tak, jeśli chcesz użyć kamery, aby uzyskać tylko wideo, możesz to zrobić. W ten sposób można uzyskać optymalne dostępne wartości dla dowolnego urządzenia bez konieczności ich kodowania. –

+1

Po wielu poszukiwaniach Twój post zrobił mój dzień. Umieszczanie setVideoSize przed setVideoEncoder i setAudioEncoder załatwił sprawę. Dzięki – gtsouk