camerasource.takePicture()在某些设备中保存旋转的图像

时间:2016-09-12 05:08:34

标签: android google-vision

我正在使用vision api来跟踪脸部。我在面部位置的基础上应用了一个面具。当我从前置摄像头拍照时,我调用camerasource.takePicture()来保存图像。我在三星等设备中面临图像旋转问题,捕获图像显示面具和面部不同的位置。我使用Exif类来获取图像的方向,但它总是返回0,所以我无法旋转图像。 我正在使用以下类来getOrientation并旋转图像。

{{1}}

}

我在vision api中发现issue有任何解决方案。

4 个答案:

答案 0 :(得分:4)

我自己解决了我的问题。我从字节数据中获取方向,然后根据方向旋转我的图像。

<?php while ( $row = pg_fetch_array ( $result ) ) { ?>
<tr>
    <td><?php echo $row['client_id']; ?></td>
    <td><?php echo implode(',',json_decode($row['insurance'])); ?></td>
    <td><?php 
        $sRows = '';
        if($row['iCnt'] > 0) {
            $sRows = $row['iCnt']==1?' row':' rows';
        }                   
        echo ''.$row['iCnt'].$sRows;
    ?></td>
</tr>

下面的类用于从byte []数据获取方向。

private CameraSource.PictureCallback mPicture = new CameraSource.PictureCallback() {
    @Override
    public void onPictureTaken(byte[] bytes) {
       int orientation = Exif.getOrientation(bytes);
       Bitmap   bitmap = BitmapFactory.decodeByteArray(bytes, 0, bytes.length);
        switch(orientation) {
            case 90:
                bitmapPicture= rotateImage(bitmap, 90);

                break;
            case 180:
                bitmapPicture= rotateImage(bitmap, 180);

                break;
            case 270:
                bitmapPicture= rotateImage(bitmap, 270);

                break;
            case 0:
           // if orientation is zero we don't need to rotate this 

            default:
                break;
        }
          //write your code here to save bitmap 
        }

    }

};
  public static Bitmap rotateImage(Bitmap source, float angle) {
    Matrix matrix = new Matrix();
    matrix.postRotate(angle);
    return Bitmap.createBitmap(source, 0, 0, source.getWidth(),   source.getHeight(), matrix,
            true);
  }

答案 1 :(得分:1)

听起来像是Exif标签的问题。基本上,现代相机以相同的方向保存图像,但也保存一个标签,告诉您原始方向是什么。

您可以使用与java api捆绑在一起的Exif Interface。我更喜欢Alessandro Crugnola's Android-Exif-Interface library,它并不要求你保持文件路径

我在项目中如何使用Android-Exif-Interface:

ExifInterface exif = new ExifInterface();
Matrix matrix = new Matrix();
try {
    exif.readExif(context.getContentResolver().openInputStream(fileUri), ExifInterface.Options.OPTION_ALL);
    ExifTag tag = exif.getTag(ExifInterface.TAG_ORIENTATION);
    int orientation = tag.getValueAsInt(1);
    switch (orientation) {
        case 3: /* 180° */
            matrix.postRotate(180);
            break;
        case 6: /*  90° */
            matrix.postRotate(90);
            break;
        case 8: /* 270° */
            matrix.postRotate(-90);
            break;
    }
} catch (IOException e) {
    Log.i("INFO","expected behaviour: IOException");
    //not every picture comes from the phone, should that be the case,
    // we can't get exif tags anyway, since those aren't being transmitted
    // via http (atleast I think so. I'd need to save the picture on the SD card to
    // confirm that and I don't want to do that)
} catch(NullPointerException e){
    Log.i("INFO","expected behaviour: NullPointerException");
    //same as above, not every picture comes from the phone
}

答案 2 :(得分:0)

我遇到过与三星设备类似的问题,ExifInterface似乎无法正常使用它们保存的图像。为了解决这个问题,我使用了Glide图像库中的代码,它似乎可以正确处理原始图像旋转。

点击此链接:Glide source

那里的

getOrientation方法似乎大部分时间都在做这个工作。

答案 3 :(得分:0)

在许多情况下,pictureCallback()会收到带有未定义方向标记的Jpeg。但是您可以通过查看display rotation或运行方向监听器(如 Camera.takePicture returns a rotated byteArray )来计算实际的设备方向。