2017-12-12 17 views
1

私はカスタムカメラを作成しました。アプリケーションでキャプチャボタンをクリックすると、画像が撮影されています。さらに、私はという名前の関数でバイト配列の形式でデータを取得しています.PictureTakenAndroid:Samsungデバイスは自動的に画像を回転します

グライドというライブラリを使用して、バイト配列をビットマップに変換しています。

私の問題は、サムスンのデバイスでは、画像自体が回転していることです。私はしばらくそれについて研究してきました。私は、[[]からExif情報を取得し、そのイメージを回転させるためにメタデータ抽出ライブラリと呼ばれるライブラリを見つけましたが、Samsungのデバイスでは動作しません。 メタデータ抽出ライブラリは、常に画像が回転する必要がないことを示す縦方向画像の値1を返しますが、縦方向モードで撮影された画像は常に90度回転します。写真はそれはフロントとバックカメラとメタ抽出ライブラリの両方のために90度の角度で回転させたポートレートモードで撮影されるたびに、

は1

の値が他の何かが、メタデータの抽出抽出があることを示しExif情報ストリームデータを抽出するライブラリ?

注:それは一方で24の最小APIレベルを必要とするため、私はExifInterfaceを使用することはできません、私は多くの解決策を試してみましたが、何も作業していないAPIレベルで22

をテストしています。これにはどんな解決策がありますか?

コードは以下のとおりである:

public void onPictureTaken(byte[] data, Camera camera) { 
      mCamera.stopPreview(); 

      Glide.with(this).load(data) 
    .asBitmap().centerCrop().animate(R.anim.abc_fade_in) 
    .into(new SimpleTarget<Bitmap>(width, height) { 
          @Override 
          public void onResourceReady(Bitmap resource, GlideAnimation<? super Bitmap> glideAnimation) { 
           camera_view.setVisibility(View.INVISIBLE); 
           int w = resource.getWidth(); 
           int h = resource.getHeight(); 

           // Setting post rotate to 90 

           Matrix mtx = new Matrix(); 


           try { 

            InputStream is = new ByteArrayInputStream(data); 
            Metadata metadata = ImageMetadataReader.readMetadata(is); 
            final ExifIFD0Directory exifIFD0Directory = metadata.getFirstDirectoryOfType(ExifIFD0Directory.class); 
            if (exifIFD0Directory.containsTag(ExifIFD0Directory.TAG_ORIENTATION)) { 
             final int exifOrientation = exifIFD0Directory.getInt(ExifIFD0Directory.TAG_ORIENTATION); 
             switch (exifOrientation) { 

              case 6: 
               mtx.postRotate(90); 
               break; // top left 
              case 3: 
               mtx.postRotate(180);; 
               break; // top right 
              case 8: 
               mtx.postRotate(270); 
               break; // bottom right 

             } 
             photo = Bitmap.createBitmap(resource, 0, 0, w, h, mtx, true); 
              /* Work on exifOrientation */ 
            } 


           } catch (Exception e) { 
            e.printStackTrace(); 
           } 
          } 

     } 

私はテストのためにサムスンJ5を使用しています。

答えて

1

あなたのためにライブラリは必要ありません。ここに私があなたのためのトリックを行う必要がある書いたカップルの方法です。

public static int getCapturedImageOrientation(Context context, Uri imageUri){ 
    int rotate = 0; 
    try { 
     context.getContentResolver().notifyChange(imageUri, null); 
     File imageFile = new File(imageUri.getPath()); 

     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.i("RotateImage", "Exif orientation: " + orientation); 
     Log.i("RotateImage", "Rotate value: " + rotate); 
    } catch (Exception e) { 
     Log.e(TAG, "Error getting rotation of image"); 

    } 

    return rotate; 
} 
public static int GetRotateAngle(Context context, Uri imageUri) { 
    String[] columns = { MediaStore.Images.Media.DATA, MediaStore.Images.Media.ORIENTATION }; 
    Cursor cursor = context.getContentResolver().query(imageUri, columns, null, null, null); 
    if (cursor == null) { 
     //If null, it is not in the gallery, so may be temporary image 
     return getCapturedImageOrientation(context, imageUri); 

    } 

    cursor.moveToFirst(); 

    int orientationColumnIndex = cursor.getColumnIndex(columns[1]); 
    int orientation = cursor.getInt(orientationColumnIndex); 
    cursor.close(); 
    return orientation; 
} 

これらをImageHelperというクラスにラップします。あなたはこのようにそれを使用することができます:

rotateImage(ImageHelper.GetRotateAngle(Context, mCropImageUri)); 

その後の進路rotateImageコードは次のようになります。私は、写真編集のためにこのすべてをやってトリミングし、アプリをスケーリング、そうすることができますされた。もちろん、

private void rotateImage(int degrees) { 
     Matrix mat = new Matrix(); 
     mat.postRotate(degrees); 
     mCropImage = Bitmap.createBitmap(mCropImage, 0, 0, mCropImage.getWidth(), mCropImage.getHeight(), mat, true); 
     setImageForCropping(mCropImage); 

    } 

いくつかのエキストラを無視しますが、これは後で処理する必要があります。がんばろう。

+0

ありがとうございました。最初の外観をした後、私は画像のURIを取得する場所に質問がありますか?私は – mimetype

+0

のメディアファイルに保存していません。そのコードをスキップするだけです。コードが「cursor == null」の場合にコードが通知し、getCapturedImageOrientationを呼び出すことに注意してください。これは、デバイスのメディアストアに格納していないときのためです。また、ファイル絶対パスの使用を伴わないExifInterfaceを取得する別の方法がすでに見つかりました。必要なものはすべて用意されています。コードを修正して、私が提供したgetOrientation exif処理に一致させてください。私はあなたの魔法の数字が3,6、そして8であるか分からない。私はあなたの問題をはっきりと見分けることはできませんが、上記のコードは何百ものデバイスでテストされたすべてのデバイスで動作します。 – Sam

+0

よろしくお願いいたします。 – mimetype

関連する問題