2016-05-10 12 views
3

私は自分のアプリでカメラを使用しようとしています。私はそれを風景モードとポートレートモードで使いたいと考えています。私は風景モードで写真を作成するのに問題はありませんが、私はポートレートモードで写真を保存するための良い方法を見つけていません。Androidカメラポートレートモードで画像を保存する

私はポートレートモードで映像を作りたい場合は、私はこのように、最初の肖像画にdisplayorientationを設定する必要があります。

switch (windowManager.getDefaultDisplay().getRotation()) { 
    case android.view.Surface.ROTATION_0: 
     mCamera.setDisplayOrientation(90); 
     break; 
    case android.view.Surface.ROTATION_90: 
     mCamera.setDisplayOrientation(0); 
     break; 
    case android.view.Surface.ROTATION_180: 
     mCamera.setDisplayOrientation(270); 
     break; 
    case android.view.Surface.ROTATION_270: 
     mCamera.setDisplayOrientation(180); 
     break; 
} 

しかし、その後、画像がまだランドスケープモードで保存されます。私が見つけた一つの解決策は、このようなカメラの回転パラメータを変更することであった。

public void onOrientationChanged(int orientation) { 
    if (orientation == ORIENTATION_UNKNOWN) return; 
    android.hardware.Camera.CameraInfo info = new android.hardware.Camera.CameraInfo(); 
    android.hardware.Camera.getCameraInfo(cameraId, info); 
    orientation = (orientation + 45)/90 * 90; 
    int rotation = 0; 
    if (info.facing == CameraInfo.CAMERA_FACING_FRONT) { 
     rotation = (info.orientation - orientation + 360) % 360; 
    } else { // back-facing camera 
     rotation = (info.orientation + orientation) % 360; 
    } 
    mParameters.setRotation(rotation); 
} 

このアプローチの問題は、それだけで実際に画像を(回転EXIFヘッダに向きを設定しないことです私が使用しているデバイスの場合)。

Bitmap bitmap = BitmapFactory.decodeByteArray(data,0,data.length); 
int w = bitmap.getWidth(); 
int h = bitmap.getHeight(); 
Matrix mtx = new Matrix(); 
mtx.postRotate(rotate); 
bitmap= Bitmap.createBitmap(bitmap, 0, 0, w, h, mtx, true); 
ByteArrayOutputStream stream = new ByteArrayOutputStream(); 
bitmap.compress(Bitmap.CompressFormat.PNG, 100, stream); 
currentData = stream.toByteArray(); 

しかし、このアプローチは(長すぎる)10秒かかり、私はAsyncTaskにこのコードを置くことができながら、私は、:画像は、このように取得された後

別のアプローチは、実際のデータを回転させました。 1〜数秒後にデータが必要なので、それでも私は待つ必要があります。

これまでのところ、より良い解決策は見つかりませんでした。

+0

NDKコードを書き込んで画像の回転を実行します。 – CommonsWare

+0

@CommonsWare NDKを一度も使用したことがなく、見た目を上げてみると、本当に集中的な作業や、C/C++に精通していない限り、使用しないことをお勧めします。私の問題はパフォーマンスと関係していますが、これを行うには別の(より良い)方法があるはずです。私はNDKが私のアプリケーションのいくつかを台無しにするかもしれないことにも恐れています。 –

+1

「あなたは本当に集中的なことをしています」 - 「すぐにデータが必要な」マルチメガピクセルの画像を回転させると、「本当に集中的なもの」となります。 – CommonsWare

答えて

2

私はまだ2〜2秒待つ必要がある解決策を見つけましたが、それは十分に速いです。これは私がすでに使用され、特に他のどこでもので、かなり良い解決策である私にとって

bitmap.compress(Bitmap.CompressFormat.JPEG, 100, stream); 

: それはかなり簡単な修正ですが、ちょうどMatrix.postRotateメソッドを使用しますが、変更:

bitmap.compress(Bitmap.CompressFormat.PNG, 100, stream); 

に.jpg画像になるので、Bitmapを.pngに圧縮するのはあまり意味がありませんでした。