Как записывать видео с определенной шириной и высотой на Android-устройстве samsung?

Привет, я делаю приложение для Android, в котором я использую пользовательскую камеру для записи камеры. У меня проблема с устройством samsung. Я не могу настроить профиль медиа-рекордера на CamcorderProfile.get(cameraid, CamcorderProfile.QUALITY_HIGH)

Также при попытке использовать

 profile = CamcorderProfile.get(cameraid, CamcorderProfile.QUALITY_LOW); profile.videoFrameHeight=360; profile.videoFrameWidth=640; 

То мое приложение работает на некоторых устройствах, но падает на многих устройствах. Любой тип помощи будет заметным. Спасибо заранее, проверьте код

 Camera.Parameters param = mCamera.getParameters(); param.set( "cam_mode", 1 ); // Enable video stabilization. Convenience methods not available in API // level <= 14 String vstabSupported = param.get("video-stabilization-supported"); if ("true".equals(vstabSupported)) { param.set("video-stabilization", "true"); } List<Size> sizes = mCamera.getParameters() .getSupportedVideoSizes(); mCamera.setParameters( param ); mMediaRecorder = new MediaRecorder(); // Step 1: Unlock and set camera to MediaRecorder mCamera.unlock(); mMediaRecorder.setCamera(mCamera); mMediaRecorder.setPreviewDisplay(mPreview.getHolder().getSurface()); // Step 2: Set sources mMediaRecorder.setAudioSource(MediaRecorder.AudioSource.CAMCORDER); mMediaRecorder.setVideoSource(MediaRecorder.VideoSource.CAMERA); String deviceMan = android.os.Build.MANUFACTURER; Toast.makeText(getApplicationContext(), deviceMan, Toast.LENGTH_SHORT).show(); // Step 3: Set a CamcorderProfile (requires API Level 8 or higher) CamcorderProfile profile = CamcorderProfile.get(cameraid, CamcorderProfile.QUALITY_LOW); // if(!CamcorderProfile.hasProfile(CamcorderProfile.QUALITY_HIGH)){Log.d("", "the camcorder profile instance is null"); int currentapiVersion = android.os.Build.VERSION.SDK_INT; if (currentapiVersion >= android.os.Build.VERSION_CODES.FROYO){ // Do something for froyo and above versions boolean tellbol=CamcorderProfile.hasProfile(CamcorderProfile.QUALITY_HIGH); if(deviceMan.equals("samsung")){ profile = CamcorderProfile.get(cameraid, CamcorderProfile.QUALITY_LOW); profile.videoFrameHeight=360; profile.videoFrameWidth=640; } else{ profile = CamcorderProfile.get(cameraid, CamcorderProfile.QUALITY_HIGH); } mMediaRecorder.setProfile(profile); } else{ // do something for phones running an SDK before froyo mMediaRecorder.setOutputFormat(MediaRecorder.OutputFormat.MPEG_4); mMediaRecorder.setAudioEncoder(MediaRecorder.AudioEncoder.AMR_NB); // mMediaRecorder.setVideoSize(720, 480); mMediaRecorder.setVideoEncoder(MediaRecorder.VideoEncoder.MPEG_4_SP); } // Step 4: Set output file mMediaRecorder.setOutputFile(getOutputMediaFile(MEDIA_TYPE_VIDEO).toString()); // Step 5: Set the preview output // Step 6: Prepare configured MediaRecorder try { mMediaRecorder.prepare(); } catch (IllegalStateException e) { Log.d("Video", "IllegalStateException preparing MediaRecorder: " + e.getMessage()); releaseMediaRecorder(); return false; } catch (IOException e) { Log.d("Video", "IOException preparing MediaRecorder: " + e.getMessage()); releaseMediaRecorder(); return false; } return true; 

Solutions Collecting From Web of "Как записывать видео с определенной шириной и высотой на Android-устройстве samsung?"

Это происходит потому, что вы запрашиваете нужные размеры, но не каждая камера способна к каждому измерению.

Кроме того, некоторые устройства работают с соотношением сторон камеры немного различаются, поэтому, если вы запрашиваете прямоугольник с неправильным соотношением или с размерами, отличающимися от поддерживаемых, он будет разбиваться на некоторых устройствах.

Что делать?

Шаг 1.

Вы должны проверить поддерживаемые размеры. Вы можете сделать это с помощью

 Camera.Parameters p = myCamera.getParameters(); List<Size> previewsizes = p.getSupportedPreviewSizes(); List<Size> videosizes = p.getSupportedVideoSizes(); 

И затем вы можете выбрать один. Если вы хотите автоматизировать это, вы можете пойти дальше и следовать

Шаг 2

Напишите функцию, чтобы выбрать лучший доступный размер, который получит поддерживаемые размеры и желаемый размер, что-то вроде:

 private Size getOptimalPreviewSize(List<Size> sizes, int w, int h) { final double ASPECT_TOLERANCE = 0.2; double targetRatio = (double) w / h; if (sizes == null) return null; Size optimalSize = null; double minDiff = Double.MAX_VALUE; int targetHeight = h; // Try to find an size match aspect ratio and size for (Size size : sizes) { Log.d("Camera", "Checking size " + size.width + "w " + size.height + "h"); double ratio = (double) size.width / size.height; if (Math.abs(ratio - targetRatio) > ASPECT_TOLERANCE) continue; if (Math.abs(size.height - targetHeight) < minDiff) { optimalSize = size; minDiff = Math.abs(size.height - targetHeight); } } // Cannot find the one match the aspect ratio, ignore the // requirement if (optimalSize == null) { minDiff = Double.MAX_VALUE; for (Size size : sizes) { if (Math.abs(size.height - targetHeight) < minDiff) { optimalSize = size; minDiff = Math.abs(size.height - targetHeight); } } } return optimalSize; } 

И последний шаг, установите параметры

Шаг 3

 private int desiredwidth=640, desiredheight=360; Size optimalPreviewSize = getOptimalPreviewSize(previewsizes, desiredwidth, desiredheight); Size optimalVideoSize = getOptimalPreviewSize(videosizes, desiredwidth, desiredheight); p.setPreviewSize(optimalPreviewSize.width, optimalPreviewSize.height); mCamera.unlock(); mMediaRecorder = new MediaRecorder(); mMediaRecorder.setCamera(mCamera); mMediaRecorder.setVideoSize(optimalVideoSize.width, optimalVideoSize.height); myCamera.setParameters(p); 

При этом приложение для вашей камеры будет работать на каждом устройстве с помощью камеры!

ОБНОВИТЬ

С помощью getOptimalPreviewSize, который я написал, вы получаете размер, отношение которого ближе к желаемому, и если ни один из них не является достаточно хорошим, вы получаете ту, высота которой закрыта до желаемого. Если вы хотите придавать большее значение размеру, вы можете легко изменить, что-то вроде

 private Size getOptimalPreviewSize(List<Size> sizes, int w, int h) { final double ASPECT_TOLERANCE = 0.2; double targetRatio = (double) w / h; if (sizes == null) return null; Size optimalSize = null; double minDiff = Double.MAX_VALUE; int targetHeight = h; if ( you want ratio as closed to what i asked for) { for (Size size : sizes) { Log.d("Camera", "Checking size " + size.width + "w " + size.height + "h"); double ratio = (double) size.width / size.height; if (Math.abs(ratio - targetRatio) > ASPECT_TOLERANCE) continue; if (Math.abs(size.height - targetHeight) < minDiff) { optimalSize = size; minDiff = Math.abs(size.height - targetHeight); } } } if (you want height as closed to what i asked for) { //you can do other for width minDiff = Double.MAX_VALUE; for (Size size : sizes) { if (Math.abs(size.height - targetHeight) < minDiff) { optimalSize = size; minDiff = Math.abs(size.height - targetHeight); } } } if (you want the bigest one) { minDiff = 0; for (Size size : sizes) { if ( size.height * size.width > minDiff ) { optimalSize = size; minDiff = size.height * size.width ; } } } return optimalSize; } 

С помощью параметров вы можете установить ширину и высоту предварительного просмотра видео.

  Camera.Parameters param = camera.getParameters(); param.setPreviewSize("your width" "your height"); camera.setParameters(param);