Reputation:
I am trying to take picture through my APP but taking picture works on some device yet fail some device. I am pretty sure i am doing right way, but android is not accepting setParameters. This is really annoying and not sure why is sooooo difficult to develop something on Android platform. In company we are building Android and iPhone version of each app but iPhone team always finish project about up to 3 weeks before Android. I have tried many code i found SOF or other sources but non of them working properly.
Anyway, This is my code to take picture
public class TakePicturePortrait extends Activity
{
private int screenW;
private int screenH;
@Override
public void onCreate(Bundle b)
{
super.onCreate(b);
setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_PORTRAIT);
requestWindowFeature(Window.FEATURE_NO_TITLE);
setContentView(R.layout.activity_fullscreen);
// Get Screen dimention first.
getScreenSize();
picture_guide_layout = (RelativeLayout) findViewById(R.id.picture_guide_layout);
mySurfaceView = (SurfaceView) findViewById(R.id.surface_view);
holder = mySurfaceView.getHolder();
holder.addCallback(mSurfaceListener);
holder.setType(SurfaceHolder.SURFACE_TYPE_PUSH_BUFFERS);
}
@Override
protected void onResume()
{
if (myCamera == null)
myCamera = getCameraInstance();
super.onResume();
}
@Override
public void onPause()
{
super.onPause();
releaseCamera();
}
private void releaseCamera()
{
if (myCamera != null)
{
myCamera.setPreviewCallback(null);
myCamera.release();
myCamera = null;
}
}
private static Camera getCameraInstance()
{
Camera c = null;
try
{
c = Camera.open();
}
catch (Exception e)
{
System.out.println(e.toString());
}
return c;
}
private final ShutterCallback shutterCallback = new ShutterCallback()
{
public void onShutter()
{
AudioManager mgr = (AudioManager) getSystemService(Context.AUDIO_SERVICE);
mgr.playSoundEffect(AudioManager.FLAG_PLAY_SOUND);
}
};
private SurfaceHolder.Callback mSurfaceListener = new SurfaceHolder.Callback()
{
public void surfaceCreated(SurfaceHolder holder)
{
try
{
myCamera.setPreviewDisplay(holder);
}
catch (Exception e)
{
e.printStackTrace();
}
}
public void surfaceDestroyed(SurfaceHolder holder)
{
}
@SuppressLint("InlinedApi")
public void surfaceChanged(SurfaceHolder holder, int format, int width, int height)
{
Parameters mParam = myCamera.getParameters();
int w = 0;
int h = 0;
List<Size> getPictureSize = mParam.getSupportedPictureSizes();
for(Size s: getPictureSize)
{
if(s.width < 1280)
break;
w = s.width;
h = s.height;
}
mParam.setFocusMode(Camera.Parameters.FOCUS_MODE_CONTINUOUS_PICTURE);
mParam.setPictureFormat(ImageFormat.JPEG);
mParam.setJpegQuality(90);
mParam.setPictureSize(w, h);
mParam.setRotation(fixPictureOrientation());
myCamera.stopPreview();
myCamera.setParameters(mParam);
Display display = getWindowManager().getDefaultDisplay();
if (display.getRotation() == Surface.ROTATION_0)
myCamera.setDisplayOrientation(90);
}
};
private int fixPictureOrientation()
{
Camera.CameraInfo info = new Camera.CameraInfo();
Camera.getCameraInfo(Camera.CameraInfo.CAMERA_FACING_BACK, info);
int rotation = getWindowManager().getDefaultDisplay().getRotation();
int degrees = 0;
switch (rotation)
{
case Surface.ROTATION_0 :
degrees = 0;
break; // Natural orientation
case Surface.ROTATION_90 :
degrees = 90;
break; // Landscape left
case Surface.ROTATION_180 :
degrees = 180;
break;// Upside down
case Surface.ROTATION_270 :
degrees = 270;
break;// Landscape right
}
int rotate = (info.orientation - degrees + 360) % 360;
return rotate;
}
private PictureCallback mPictureListener = new PictureCallback()
{
@Override
public void onPictureTaken(byte[] data, Camera camera)
{
data = getRotatedData(data);
String fileName = (System.currentTimeMillis() / 1000) + ".jpg";
try
{
File file = new File(PATH + "/" + fileName);
FileOutputStream out = new FileOutputStream(file);
out.write(data);
if (out != null)
out.close();
}
catch (Exception e)
{
}
myCamera.stopPreview();
}
};
public void takePicture(View v)
{
if (myCamera != null)
myCamera.takePicture(shutterCallback, null, mPictureListener);
}
private void getScreenSize()
{
screenW = getResources().getDisplayMetrics().widthPixels;
screenH = getResources().getDisplayMetrics().heightPixels;
}
private byte[] getRotatedData(byte[] data)
{
byte[] rotatedData = data;
Bitmap originalBmp = BitmapFactory.decodeByteArray(data, 0, data.length, null);
int originalW = originalBmp.getWidth();
int originalH = originalBmp.getHeight();
Matrix mat = new Matrix();
mat.postRotate(0);
Bitmap rotetedBmp = Bitmap.createBitmap(originalBmp, 0, 0, originalW, originalH, mat, true);
ByteArrayOutputStream bos = new ByteArrayOutputStream();
rotetedBmp.compress(CompressFormat.JPEG, 90, bos);
try
{
bos.flush();
}
catch (IOException e1)
{
e1.printStackTrace();
}
rotatedData = bos.toByteArray();
try
{
bos.close();
}
catch (IOException e1)
{
e1.printStackTrace();
}
return rotatedData;
}
}
at this code works Samsung S3 perfectly, but fail at Samsung S4. LogCat says problem is myCamera.setParameters(mParam);
And this is ErrLog output
11-25 10:01:40.737: E/AndroidRuntime(4257): FATAL EXCEPTION: main
11-25 10:01:40.737: E/AndroidRuntime(4257): java.lang.RuntimeException: setParameters failed
11-25 10:01:40.737: E/AndroidRuntime(4257): at android.hardware.Camera.native_setParameters(Native Method)
11-25 10:01:40.737: E/AndroidRuntime(4257): at android.hardware.Camera.setParameters(Camera.java:1003)
11-25 10:01:40.737: E/AndroidRuntime(4257): at main_app.TakePictureLandscape$2.surfaceChanged(TakePictureLandscape.java:284)
11-25 10:01:40.737: E/AndroidRuntime(4257): at android.view.SurfaceView.updateWindow(SurfaceView.java:619)
11-25 10:01:40.737: E/AndroidRuntime(4257): at android.view.SurfaceView.dispatchDraw(SurfaceView.java:398)
11-25 10:01:40.737: E/AndroidRuntime(4257): at android.view.ViewGroup.drawChild(ViewGroup.java:1669)
11-25 10:01:40.737: E/AndroidRuntime(4257): at android.view.ViewGroup.dispatchDraw(ViewGroup.java:1398)
11-25 10:01:40.737: E/AndroidRuntime(4257): at android.view.ViewGroup.drawChild(ViewGroup.java:1669)
11-25 10:01:40.737: E/AndroidRuntime(4257): at android.view.ViewGroup.dispatchDraw(ViewGroup.java:1398)
11-25 10:01:40.737: E/AndroidRuntime(4257): at android.view.View.draw(View.java:6883)
11-25 10:01:40.737: E/AndroidRuntime(4257): at android.widget.FrameLayout.draw(FrameLayout.java:357)
11-25 10:01:40.737: E/AndroidRuntime(4257): at android.view.ViewGroup.drawChild(ViewGroup.java:1671)
11-25 10:01:40.737: E/AndroidRuntime(4257): at android.view.ViewGroup.dispatchDraw(ViewGroup.java:1398)
11-25 10:01:40.737: E/AndroidRuntime(4257): at android.view.View.draw(View.java:6883)
11-25 10:01:40.737: E/AndroidRuntime(4257): at android.widget.FrameLayout.draw(FrameLayout.java:357)
11-25 10:01:40.737: E/AndroidRuntime(4257): at com.android.internal.policy.impl.PhoneWindow$DecorView.draw(PhoneWindow.java:2371)
11-25 10:01:40.737: E/AndroidRuntime(4257): at android.view.ViewRoot.draw(ViewRoot.java:1531)
11-25 10:01:40.737: E/AndroidRuntime(4257): at android.view.ViewRoot.performTraversals(ViewRoot.java:1261)
11-25 10:01:40.737: E/AndroidRuntime(4257): at android.view.ViewRoot.handleMessage(ViewRoot.java:1868)
11-25 10:01:40.737: E/AndroidRuntime(4257): at android.os.Handler.dispatchMessage(Handler.java:99)
11-25 10:01:40.737: E/AndroidRuntime(4257): at android.os.Looper.loop(Looper.java:130)
11-25 10:01:40.737: E/AndroidRuntime(4257): at android.app.ActivityThread.main(ActivityThread.java:3705)
11-25 10:01:40.737: E/AndroidRuntime(4257): at java.lang.reflect.Method.invokeNative(Native Method)
11-25 10:01:40.737: E/AndroidRuntime(4257): at java.lang.reflect.Method.invoke(Method.java:507)
11-25 10:01:40.737: E/AndroidRuntime(4257): at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:839)
11-25 10:01:40.737: E/AndroidRuntime(4257): at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:597)
11-25 10:01:40.737: E/AndroidRuntime(4257): at dalvik.system.NativeStart.main(Native Method)
Upvotes: 1
Views: 846
Reputation: 849
The camera app is always annoying coz it really depend on each of hardware. So, I think the problem on this piece
mParam.setFocusMode(Camera.Parameters.FOCUS_MODE_CONTINUOUS_PICTURE);
mParam.setPictureFormat(ImageFormat.JPEG);
mParam.setJpegQuality(90);
mParam.setPictureSize(w, h);
mParam.setRotation(fixPictureOrientation());
For ex, if devices do not support focus mode picture, you setFocusMode() like that will make setParameter fail. So make sure devices support it before setParameter,
like that: if(focusModes.contains(Parameters.FOCUS_MODE_CONTINUOUS_VIDEO)) { //set }
Try to comment and run each of line above to see which line got problem.
Upvotes: 1