5

I am using custom camera and working fine but the issue is image is saving with very low (poor) quality. To overcome with it , i have tried all suggestions and implementations. Like ,

parameters.setJpegQuality(100);
parameters.setPictureFormat(ImageFormat.JPEG);

this is not working. After that i have used

List<Size> sizes = cameraParams.getSupportedPictureSizes();
Camera.Size size = sizes.get(0);
for(int i=0;i<sizes.size();i++)
{
 if(sizes.get(i).width > size.width)
 size = sizes.get(i);
}
cameraParams.setPictureSize(mPictureSize.width, mPictureSize.height);

This is also not working. Its saving with poor quality still.

Note : Camera preview is showing proper with good quality but the issue is when saving captured image to sdcard folder.

Advanced help would be appreciated!!

Piyush
  • 18,895
  • 5
  • 32
  • 63

2 Answers2

5

Finally my issue solved.

Here I was setting parameters for camera preview before i was capturing the image

 public void takePicture() {
    mCamera.takePicture(new ShutterCallback() {
        @Override
        public void onShutter() {

        }
    }, new PictureCallback() {
        @Override
        public void onPictureTaken(byte[] data, Camera camera) {

        }
    }, new PictureCallback() {
        @Override
        public void onPictureTaken(final byte[] data, Camera camera) {

            data1 = data;
            if (mCamera != null) {
                mCamera.stopPreview();
            }
        }
    });
}

So before i called this function in my fragment i have set parameters before this method.

mPreview.setParams(params);// This was the mistake what i have done !
mPreview.takePicture();

finally solved after removing mPreview.setParams(params);

Piyush
  • 18,895
  • 5
  • 32
  • 63
  • i'm looking for this and can you tell me for custom camera what u used? like any library! thank u in advance. – Rucha Bhatt Joshi Dec 26 '16 at 05:12
  • No. I have not used any custom library. I have used custom class for camera preview and after that i have modified as per my requirement ! Are you working with custom camera ? @RuchaBhatt – Piyush Dec 26 '16 at 05:13
  • Can you please elaborate your solution. I am setting params to mCamera not mPreview. I am setting params before mCamera.startPreview(); But I am getting low quality image. – seema Feb 06 '17 at 13:56
  • private void setCameraParams() { Camera.Parameters params = mCamera.getParameters(); List sizes = params.getSupportedPictureSizes(); Camera.Size size = sizes.get(0); for (int i = 0; i < sizes.size(); i++) { if (sizes.get(i).width > size.width) size = sizes.get(i); } params.setPictureSize(size.width, size.height); Camera.Size bestSize = null; List sizeList = params.getSupportedPreviewSizes(); bestSize = sizeList.get(0); – seema Feb 07 '17 at 06:34
  • for(int i = 1; i < sizeList.size(); i++){ if((sizeList.get(i).width * sizeList.get(i).height) > (bestSize.width * bestSize.height)){ bestSize = sizeList.get(i); } } params.setPreviewSize(bestSize.width,bestSize.height); params.setFlashMode(Camera.Parameters.FLASH_MODE_AUTO); params.setPictureFormat(ImageFormat.JPEG); params.setJpegQuality(100); params.setRotation(90); mCamera.setDisplayOrientation(90); mCamera.setParameters(params); } – seema Feb 07 '17 at 06:34
  • Couldnt add it in single comment.... 2nd comment is in continuation of first comment. – seema Feb 07 '17 at 06:35
  • I am getting fine quality in some devices and low in others. – seema Feb 07 '17 at 06:35
  • In onSurface changed, calling above method : mCamera.setPreviewDisplay(holder); setCameraParams(); mCamera.startPreview(); – seema Feb 07 '17 at 06:37
  • In _surfaceCreated_ method you haven't set params. Why ? – Piyush Feb 07 '17 at 09:13
  • Check my custom class for [CameraPreview](https://hastebin.com/ipesihudes.java) @seema – Piyush Feb 07 '17 at 09:18
  • Ok. Will try this way also. Thanks :) – seema Feb 07 '17 at 09:39
  • Let us [continue this discussion in chat](http://chat.stackoverflow.com/rooms/135037/discussion-between-piyush-and-seema). – Piyush Feb 07 '17 at 09:42
  • So in order to set params we need to call mPreview.setParams(params) after mPreview.takePicture() ? – Arunraj Shanmugam Oct 09 '17 at 05:56
1

I can show you methods for resetting preview size:

You should change your parameters of preview at Camera.

private void setImageSize() {
        Camera.Size size = CameraUtil.findClosetImageSize(mRxCamera.getNativeCamera(), PREFER_SIZE);
        mCamera.getNativeCamera().getParameters().setPictureSize(size.width, size.height);
        WIDTH = size.width;
        HEIGHT = size.height;
    }

and after You need to change layout sizes

private void resetPreviewSize() {
        final boolean widthIsMax = mWidth > mHeight;
        final Camera.Size size = mCamera.getNativeCamera().getParameters().getPreviewSize();

        final RectF rectDisplay = new RectF();
        final RectF rectPreview = new RectF();

        rectDisplay.set(0, 0, mWidth, mHeight);

        final int width = widthIsMax ? size.width : size.height;
        final int height = widthIsMax ? size.height : size.width;
        rectPreview.set(0, 0, width, height);

        final Matrix matrix = new Matrix();
        matrix.setRectToRect(rectDisplay, rectPreview, Matrix.ScaleToFit.START);
        matrix.invert(matrix);
        matrix.mapRect(rectPreview);

        mCameraView.getLayoutParams().height = (int) (rectPreview.bottom);
        mCameraView.getLayoutParams().width = (int) (rectPreview.right);
        mCameraView.requestLayout();
    }

and if you need

public static Camera.Size findClosetImageSize(Camera camera, Point preferSize) {
    int preferX = preferSize.x;
    int preferY = preferSize.y;
    Camera.Parameters parameters = camera.getParameters();
    List<Camera.Size> allSupportSizes = parameters.getSupportedPictureSizes();
    Log.d(TAG, "all support Image size: " + dumpPreviewSizeList(allSupportSizes));
    int minDiff = Integer.MAX_VALUE;
    int index = 0;
    for (int i = 0; i < allSupportSizes.size(); i++) {
        Camera.Size size = allSupportSizes.get(i);
        int x = size.width;
        int y = size.height;

        int diff = Math.abs(x - preferX) + Math.abs(y - preferY);
        if (diff < minDiff) {
            minDiff = diff;
            index = i;
        }
    }
    return allSupportSizes.get(index);
}