Разрешение CamcorderProfile.QUALITY_HIGH обеспечивает зеленое мерцающее видео
Я пока не нашел объяснений. В основном у меня есть класс видеозаписи, который отлично работает, когда setVideoSize() установлен на 720 x 480 на моей Samsung Galaxy S2.
Я хочу, чтобы он записывался с максимально возможным разрешением, поэтому с помощью CamcorderProfile.QUALITY_HIGH. Я могу получить различные свойства записи самого высокого качества и установить их в своем классе. Это работает для формата файла, частоты кадров видео, кодеров и скорости передачи данных, однако, когда я пытаюсь установить размер видео на ширину и высоту, возвращаемые CamcorderProfile (1920 x 1080), записанное видео просто зеленое мерцание.
Я заметил, что если я сменил 720 x 480 на 720 x 481, он сделал то же самое. Поэтому я могу только предположить, что это происходит, когда разрешение не поддерживается телефоном. Тем не менее, видеокамера, к которой пришел телефон, может записываться в 1920 x 1080 и обеспечивает отличную запись.
Я могу только предположить с таким высоким разрешением. Мне нужно установить некоторые другие параметры по-разному, но я просто не могу понять, какими они могут быть.
У кого-нибудь еще была эта проблема?
Заранее благодарим за любые ответы.
Ответы
Ответ 1
Я столкнулся с этим вопросом, пытаясь решить ту же проблему.
Решение дано над разработчиком xda http://forum.xda-developers.com/showthread.php?t=1104970&page=8. Кажется, вам нужно установить неясный параметр "cam_mode" для записи высокой четкости:
camera = Camera.open();
Camera.Parameters param = camera.getParameters();
param.set( "cam_mode", 1 );
camera.setParameters( param );
В mediarecorder вы можете использовать
mediarecorder.setVideoSize(1920, 1080);
хотя это также будет работать:
mediarecorder.setProfile(CamcorderProfile.get(CamcorderProfile.QUALITY_HIGH));
(У последнего, похоже, есть битрейт видео со скоростью 20 Мбит/с, поэтому вам может потребоваться немного уменьшить это!) Я обнаружил, что мне не нужно было устанавливать размер предварительного просмотра до 1920x1080.
(редактировать) Вам также нужно установить
parame.setFocusMode(Camera.Parameters.FOCUS_MODE_CONTINUOUS_VIDEO);
или
param.setFocusMode(Camera.Parameters.FOCUS_MODE_INFINITY);
в противном случае вы получите задержку за несколько секунд до запуска камеры!
Что касается того, почему Samsung внедрил Camera таким образом, я понятия не имею. Это, конечно, не разработчик дружелюбный!
Ответ 2
Вот как мне удалось сделать эту работу на Samsung Galaxy S2. Критическая точка здесь - установить такое же разрешение как в параметрах камеры, так и в размере видеорекордера. Кроме того, уже упоминался взлом "cam_mode". Итак, я разрешил пользователю выбирать один из трех режимов качества: низкий (800x480), средний (1280x720) и высокий (1920x1080):
enum InternalCameraQuality {
LOW, MEDIUM, HIGH
}
и при создании/заполнении камеры и рекордера я сделал
// signature types are irrelevant here
File start(DeviceHandler handler, FileHelper fh) throws IOException {
file = fh.createTempFile(".mp4");
camera = Camera.open();
setCameraParameters(camera);
camera.setPreviewDisplay(getHolder());
camera.unlock();
recorder = new MediaRecorder();
recorder.setCamera(camera);
setRecorderParameters(recorder);
recorder.prepare();
recorder.start();
return file;
}
void setCameraParameters(Camera camera) {
Camera.Parameters param = camera.getParameters();
// getParams() simply returns some field holding configuration parameters
// only the 'quality' parameter is relevant here
if (getParams().quality != InternalCameraQuality.LOW) {
// Samsung Galaxy hack for HD video
param.set("cam_mode", 1);
}
Pair<Integer, Integer> resolution = getResolution(getParams().quality);
param.setPreviewSize(resolution.first, resolution.second);
param.setFocusMode(Camera.Parameters.FOCUS_MODE_INFINITY);
camera.setParameters(param);
}
void setRecorderParameters(MediaRecorder recorder) {
recorder.setAudioSource(MediaRecorder.AudioSource.MIC);
recorder.setVideoSource(MediaRecorder.VideoSource.CAMERA);
Pair<Integer, Integer> resolution = getResolution(getParams().quality);
CamcorderProfile profile = CamcorderProfile.get(CamcorderProfile.QUALITY_HIGH);
profile.videoFrameWidth = resolution.first;
profile.videoFrameHeight = resolution.second;
recorder.setProfile(profile);
recorder.setOutputFile(file.getAbsolutePath());
recorder.setPreviewDisplay(getHolder().getSurface());
}
Pair<Integer, Integer> getResolution(InternalCameraQuality quality) {
final int width, height;
switch (quality) {
case LOW:
width = 800;
height = 480;
break;
case MEDIUM:
width = 1280;
height = 720;
break;
case HIGH:
width = 1920;
height = 1080;
break;
default:
throw new IllegalArgumentException("Unknown quality: " + quality.name());
}
return Pair.create(width, height);
}
Обратите внимание, что вы должны использовать взломы "cam_mode" только для среднего и высокого качества, иначе зеленое мерцание появится в режиме низкого качества. Также вы можете настроить другие параметры профиля, если вам нужно.
Надеюсь, это помогло.
Ответ 3
Хорошо, я проверил множество вариантов и единственная версия, которая хорошо работает на реальных устройствах:
CamcorderProfile camcorderProfile = CamcorderProfile.get(CamcorderProfile.QUALITY_HIGH);
// THREE_GPP works well but only on Phones
// camcorderProfile.fileFormat = MediaRecorder.OutputFormat.THREE_GPP;
// so better you use MPEG_4 for most Devices and PC
camcorderProfile.fileFormat = MediaRecorder.OutputFormat.MPEG_4;
camcorderProfile.videoCodec = MediaRecorder.VideoEncoder.MPEG_4_SP;
mrec.setProfile(camcorderProfile);
Ответ 4
У меня были аналогичные проблемы, подобные этому в прошлом.
Что вы делаете, кажется, все в порядке, но вот несколько советов, которые могут помочь отладить проблему:
Убедитесь, что вы выбрали поддерживаемое разрешение
int cameraId = 0; // using back facing camera
Camera camera = Camera.open(cameraId);
Camera.Parameters cameraParams = camera.getParameters();
List<Camera.Size> supportedPreviewSizes = cameraParams.getSupportedPreviewSizez();
// find suitable Camera preview size from list and set your CamcorderProfile to use that new size
После того, как вы разместите подходящий размер предварительного просмотра, убедитесь, что reset ваш SurfaceView - вам нужно будет изменить его размер, чтобы вносить изменения в соотношение сторон
API MediaRecorder использует SurfaceView, поэтому, если ваш поверхностный вид не настроен правильно, это приведет к появлению зеленого фликкера, который вы видите
Убедитесь, что вы используете скорость передачи видео, которая может поддерживать новое разрешение, - попробуйте бить скорость передачи видео, чтобы удвоить то, что было изначально установлено (* обратите внимание, что это резко влияет на размер вашего выходного файла)
CamcorderProfile.QUALITY_HIGH возвращает максимально возможное разрешение камеры. Убедитесь, что вы используете правильный идентификатор камеры (спереди или сзади) - возможно, камера заднего вида поддерживает 1080p, но камера переднего обзора не работает?
Надеюсь, что советы помогут!
Ответ 5
List<Size> ls = parameters.getSupportedPreviewSizes();
Size size = ls.get(1);
sizes 1 ----------960 720
sizes 2 ----------800 480
sizes 3 ----------720 480
sizes 5 -----------640 384
sizes 6 ----------576 432
sizes 7 ----------480 320
это список размеров и многое другое в android.