Setrotation(90) to Take Picture in Portrait Mode Does Not Work on Samsung Devices

setRotation(90) to take picture in portrait mode does not work on samsung devices

I try to answer this in relation to the Exif tag. This is what I did:

Bitmap realImage = BitmapFactory.decodeStream(stream);

ExifInterface exif=new ExifInterface(getRealPathFromURI(imagePath));

Log.d("EXIF value", exif.getAttribute(ExifInterface.TAG_ORIENTATION));
if(exif.getAttribute(ExifInterface.TAG_ORIENTATION).equalsIgnoreCase("6")){

realImage=ImageUtil.rotate(realImage, 90);
}else if(exif.getAttribute(ExifInterface.TAG_ORIENTATION).equalsIgnoreCase("8")){
realImage=ImageUtil.rotate(realImage, 270);
}else if(exif.getAttribute(ExifInterface.TAG_ORIENTATION).equalsIgnoreCase("3")){
realImage=ImageUtil.rotate(realImage, 180);
}

The ImageUtil.rotate():

public static Bitmap rotate(Bitmap bitmap, int degree) {
int w = bitmap.getWidth();
int h = bitmap.getHeight();

Matrix mtx = new Matrix();
mtx.postRotate(degree);

return Bitmap.createBitmap(bitmap, 0, 0, w, h, mtx, true);
}

Controlling the camera to take pictures in portrait doesn't rotate the final images

The problem is when I saved the image I didn't do well.

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

String timeStamp = new SimpleDateFormat( "yyyyMMdd_HHmmss").format( new Date( ));
output_file_name = Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_DCIM) + File.separator + timeStamp + ".jpeg";

File pictureFile = new File(output_file_name);
if (pictureFile.exists()) {
pictureFile.delete();
}

try {
FileOutputStream fos = new FileOutputStream(pictureFile);

Bitmap realImage = BitmapFactory.decodeByteArray(data, 0, data.length);

ExifInterface exif=new ExifInterface(pictureFile.toString());

Log.d("EXIF value", exif.getAttribute(ExifInterface.TAG_ORIENTATION));
if(exif.getAttribute(ExifInterface.TAG_ORIENTATION).equalsIgnoreCase("6")){
realImage= rotate(realImage, 90);
} else if(exif.getAttribute(ExifInterface.TAG_ORIENTATION).equalsIgnoreCase("8")){
realImage= rotate(realImage, 270);
} else if(exif.getAttribute(ExifInterface.TAG_ORIENTATION).equalsIgnoreCase("3")){
realImage= rotate(realImage, 180);
} else if(exif.getAttribute(ExifInterface.TAG_ORIENTATION).equalsIgnoreCase("0")){
realImage= rotate(realImage, 90);
}

boolean bo = realImage.compress(Bitmap.CompressFormat.JPEG, 100, fos);

fos.close();

((ImageView) findViewById(R.id.imageview)).setImageBitmap(realImage);

Log.d("Info", bo + "");

} catch (FileNotFoundException e) {
Log.d("Info", "File not found: " + e.getMessage());
} catch (IOException e) {
Log.d("TAG", "Error accessing file: " + e.getMessage());
}
}

public static Bitmap rotate(Bitmap bitmap, int degree) {
int w = bitmap.getWidth();
int h = bitmap.getHeight();

Matrix mtx = new Matrix();
// mtx.postRotate(degree);
mtx.setRotate(degree);

return Bitmap.createBitmap(bitmap, 0, 0, w, h, mtx, true);
}

Photo rotated from camera (SAMSUNG device)

UPD 29.08.2018 I found that this method doesn't work with Samsung device based on Android 8+. I don't have Samsung s8 (for example) and can't understand why this again does not work there. If someone can test and check why this not work - let's try to fix this together.


I found how to fix: well it's really stupid and very hard for me.

First step get activity result

 @Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
if (requestCode == CAMERA_REQUEST && resultCode == Activity.RESULT_OK) {

String _path = Environment.getExternalStorageDirectory() + File.separator + "TakenFromCamera.jpg";
String p1 = Environment.getExternalStorageDirectory().toString();
String fName = "/TakenFromCamera.jpg";
final int rotation = getImageOrientation(_path);
File file = resaveBitmap(p1, fName, rotation);
Bitmap mBitmap = BitmapFactory.decodeFile(_path);

Main steps it's getImageOrientation before changes in file.

  1. getImageOrientation (by path)
  2. resave file (if need send to server, if you need only for preview we can skip this step)
  3. get correct bitmap from file

For preview it's enough to perform only steps 1 and 3, and using this function - just rotate bitmap.

private Bitmap checkRotationFromCamera(Bitmap bitmap, String pathToFile, int rotate) {
Matrix matrix = new Matrix();
matrix.postRotate(rotate);
Bitmap rotatedBitmap = Bitmap.createBitmap(bitmap, 0, 0, bitmap.getWidth(), bitmap.getHeight(), matrix, true);
return rotatedBitmap;
}

getImageOrientation

public static int getImageOrientation(String imagePath) {
int rotate = 0;
try {
ExifInterface exif = new ExifInterface(imagePath);
int orientation = exif.getAttributeInt(ExifInterface.TAG_ORIENTATION, 1);
switch (orientation) {
case ExifInterface.ORIENTATION_ROTATE_270:
rotate = 270;
break;
case ExifInterface.ORIENTATION_ROTATE_180:
rotate = 180;
break;
case ExifInterface.ORIENTATION_ROTATE_90:
rotate = 90;
break;
}
} catch (IOException e) {
e.printStackTrace();
}
return rotate;
}

and resaveBitmap if need

private File resaveBitmap(String path, String filename, int rotation) { //help for fix landscape photos
String extStorageDirectory = path;
OutputStream outStream = null;
File file = new File(filename);
if (file.exists()) {
file.delete();
file = new File(extStorageDirectory, filename);
}
try {
// make a new bitmap from your file
Bitmap bitmap = BitmapFactory.decodeFile(path + filename);
bitmap = checkRotationFromCamera(bitmap, path + filename, rotation);
bitmap = Bitmap.createScaledBitmap(bitmap, (int) ((float) bitmap.getWidth() * 0.3f), (int) ((float) bitmap.getHeight() * 0.3f), false);
bitmap = Utils.getCircleImage(bitmap);
outStream = new FileOutputStream(path + filename);
bitmap.compress(Bitmap.CompressFormat.JPEG, 100, outStream);
outStream.flush();
outStream.close();
} catch (Exception e) {
e.printStackTrace();
}
return file;
}

Camera capture orientation on samsung devices in android

This is the code I've done this with (it is working for every device):

this part is where I set the taken photo to the imageview in the main activity:

            try {
File imageFile = new File(cursor.getString(0));
ExifInterface exif = new ExifInterface(
imageFile.getAbsolutePath());
int orientation = exif.getAttributeInt(
ExifInterface.TAG_ORIENTATION,
ExifInterface.ORIENTATION_NORMAL);
switch (orientation) {
case ExifInterface.ORIENTATION_ROTATE_270:
rotate = 270;
break;
case ExifInterface.ORIENTATION_ROTATE_180:
rotate = 180;
break;
case ExifInterface.ORIENTATION_ROTATE_90:
rotate = 90;
break;
}

Log.v("", "Exif orientation: " + orientation);
} catch (Exception e) {
e.printStackTrace();
}
Matrix matrix = new Matrix();
matrix.postRotate(rotate);
bmp = Bitmap.createBitmap(bmp, 0, 0, bmp.getWidth(), bmp.getHeight(), matrix, true);
testImage.setImageBitmap(null);
testImage.setImageBitmap(bmp);

constant values in camera activity:

  private static final int ORIENTATION_PORTRAIT_NORMAL =  1;
private static final int ORIENTATION_PORTRAIT_INVERTED = 2;
private static final int ORIENTATION_LANDSCAPE_NORMAL = 3;
private static final int ORIENTATION_LANDSCAPE_INVERTED = 4;
private OrientationEventListener mOrientationEventListener;
private int mOrientation = -1;

callback function in camera activity:

      Camera.PictureCallback photoCallback=new Camera.PictureCallback(){
public void onPictureTaken(final byte[] data, final Camera camera){

dialog=ProgressDialog.show(CameraActivity.this,"","Please wait while the photo is being saved..");
new Thread(){
public void run(){
try{
Thread.sleep(1000);
}
catch(Exception ex){}
onPictureTake(data,camera);
}
}.start();
}
};

take photo function in camera activity:

      public void onPictureTake(byte[] data, Camera camera){
switch (mOrientation) {
case ORIENTATION_PORTRAIT_NORMAL:
rotate = 90;
break;
case ORIENTATION_LANDSCAPE_NORMAL:
rotate = 0;
break;
case ORIENTATION_PORTRAIT_INVERTED:
rotate = 270;
break;
case ORIENTATION_LANDSCAPE_INVERTED:
rotate = 180;
break;
}

Matrix matrix = new Matrix();
matrix.postRotate(rotate);
bmp = BitmapFactory.decodeByteArray(data, 0, data.length);
bmp = Bitmap.createBitmap(bmp, 0, 0, bmp.getWidth(), bmp.getHeight(), matrix, true);
mutableBitmap = bmp.copy(Bitmap.Config.ARGB_8888, true);
savePhoto(mutableBitmap);
dialog.dismiss();
flag = 0;
finish();
}

orientation listenner which is called in onresume in camera activity:

mOrientationEventListener = new OrientationEventListener(this, SensorManager.SENSOR_DELAY_NORMAL) {

@SuppressWarnings("deprecation")
@Override
public void onOrientationChanged(int orientation) {

// determine our orientation based on sensor response
int lastOrientation = mOrientation;

Display display = ((WindowManager)getSystemService(WINDOW_SERVICE)).getDefaultDisplay();
int rotation = getWindowManager().getDefaultDisplay().getRotation();
System.out.println(rotation+"");

if (display.getOrientation() != Surface.ROTATION_0) { // landscape oriented devices
System.out.println("LANDSCAPE");
if (orientation >= 315 || orientation < 45) {
if (mOrientation != ORIENTATION_LANDSCAPE_NORMAL) {
mOrientation = ORIENTATION_LANDSCAPE_NORMAL;
}
} else if (orientation < 315 && orientation >= 225) {
if (mOrientation != ORIENTATION_PORTRAIT_INVERTED) {
mOrientation = ORIENTATION_PORTRAIT_INVERTED;
}
} else if (orientation < 225 && orientation >= 135) {
if (mOrientation != ORIENTATION_LANDSCAPE_INVERTED) {
mOrientation = ORIENTATION_LANDSCAPE_INVERTED;
}
} else if (orientation <135 && orientation > 45) {
if (mOrientation != ORIENTATION_PORTRAIT_NORMAL) {
mOrientation = ORIENTATION_PORTRAIT_NORMAL;
}
}
} else { // portrait oriented devices
System.out.println("PORTRAIT");
if (orientation >= 315 || orientation < 45) {
if (mOrientation != ORIENTATION_PORTRAIT_NORMAL) {
mOrientation = ORIENTATION_PORTRAIT_NORMAL;
}
} else if (orientation < 315 && orientation >= 225) {
if (mOrientation != ORIENTATION_LANDSCAPE_NORMAL) {
mOrientation = ORIENTATION_LANDSCAPE_NORMAL;
}
} else if (orientation < 225 && orientation >= 135) {
if (mOrientation != ORIENTATION_PORTRAIT_INVERTED) {
mOrientation = ORIENTATION_PORTRAIT_INVERTED;
}
} else if (orientation <135 && orientation > 45) {
if (mOrientation != ORIENTATION_LANDSCAPE_INVERTED) {
mOrientation = ORIENTATION_LANDSCAPE_INVERTED;
}
}
}

}
};


Related Topics



Leave a reply



Submit