【发布时间】:2020-10-10 23:21:18
【问题描述】:
我有一个 xamarin.android 项目,它有一个自定义相机预览。每当我初始化相机时,它都会以横向默认打开。所以我像这样从SurfaceChanged 方法改变了方向。
private int setCameraDisplayOrientation(Activity mContext, int v)
{
var degrees = 0;
var orientation =0;
Display display = mContext.GetSystemService(Context.WindowService).JavaCast<IWindowManager>().DefaultDisplay;
Camera.CameraInfo info = new Camera.CameraInfo();
Camera.GetCameraInfo(v, info);
var rotation = windowManager.DefaultDisplay.Rotation;
DisplayMetrics dm = new DisplayMetrics();
display.GetMetrics(dm);
int width = dm.WidthPixels;
int height = dm.HeightPixels;
//Natural orientation is portrait
if ((rotation == SurfaceOrientation.Rotation0 || rotation == SurfaceOrientation.Rotation180) && height > width ||
(rotation == SurfaceOrientation.Rotation90 || rotation == SurfaceOrientation.Rotation270) && width > height)
{
switch (rotation)
{
case SurfaceOrientation.Rotation0:
degrees = 90;
break;
case SurfaceOrientation.Rotation90:
degrees = 0;
break;
case SurfaceOrientation.Rotation180:
degrees = 270;
break;
case SurfaceOrientation.Rotation270:
degrees = 180;
break;
}
}
return (degrees);
}
它工作正常。它将纵向排列前后摄像头。
问题
当我拍摄照片时,在某些设备中,它会以横向模式存储在某些设备中,它会存储纵向。无论如何,我都希望图像处于纵向模式。为了做到这一点,我尝试获取图像的Exif 数据并相应地将其旋转到纵向模式。但在三星、VIVO 等某些设备中,方向值变为“0”。我不知道如何处理该值。如果我 PreRotate 90 ,那么有些设备会解决这个问题,而有些设备会向上保存照片。
**Managing Rotation**
Android.Graphics.Bitmap loadAndResizeBitmap(string filePath)
{
Android.Graphics.Bitmap resizedBitmap = Android.Graphics.BitmapFactory.DecodeFile(filePath);
ExifInterface exif = null;
try
{
exif = new ExifInterface(filePath);
string orientation = exif.GetAttribute(ExifInterface.TagOrientation);
Android.Graphics.Matrix matrix = new Android.Graphics.Matrix();
switch (orientation)
{
case "1":
matrix.PreRotate(-90);
resizedBitmap = Android.Graphics.Bitmap.CreateBitmap(resizedBitmap, 0, 0, resizedBitmap.Width, resizedBitmap.Height, matrix, false);
matrix.Dispose();
matrix = null;
break;
case "3":
matrix.PreRotate(180);
resizedBitmap = Android.Graphics.Bitmap.CreateBitmap(resizedBitmap, 0, 0, resizedBitmap.Width, resizedBitmap.Height, matrix, false);
matrix.Dispose();
matrix = null;
break;
case "4":
matrix.PreRotate(180);
resizedBitmap = Android.Graphics.Bitmap.CreateBitmap(resizedBitmap, 0, 0, resizedBitmap.Width, resizedBitmap.Height, matrix, false);
matrix.Dispose();
matrix = null;
break;
case "5":
matrix.PreRotate(90);
resizedBitmap = Android.Graphics.Bitmap.CreateBitmap(resizedBitmap, 0, 0, resizedBitmap.Width, resizedBitmap.Height, matrix, false);
matrix.Dispose();
matrix = null;
break;
case "6": // portrait
matrix.PreRotate(90);
resizedBitmap = Android.Graphics.Bitmap.CreateBitmap(resizedBitmap, 0, 0, resizedBitmap.Width, resizedBitmap.Height, matrix, false);
matrix.Dispose();
matrix = null;
break;
case "7":
matrix.PreRotate(-90);
resizedBitmap = Android.Graphics.Bitmap.CreateBitmap(resizedBitmap, 0, 0, resizedBitmap.Width, resizedBitmap.Height, matrix, false);
matrix.Dispose();
matrix = null;
break;
case "8":
matrix.PreRotate(-90);
resizedBitmap = Android.Graphics.Bitmap.CreateBitmap(resizedBitmap, 0, 0, resizedBitmap.Width, resizedBitmap.Height, matrix, false);
matrix.Dispose();
matrix = null;
break;
case "0":
matrix.PreRotate(-90);
resizedBitmap = Android.Graphics.Bitmap.CreateBitmap(resizedBitmap, 0, 0, resizedBitmap.Width, resizedBitmap.Height, matrix, false);
matrix.Dispose();
matrix = null;
break;
}
return resizedBitmap;
}
catch (IOException ex)
{
return null;
}
}
我从Xamarin.Andoid Image rotation 得到这个想法。但不知何故,我无法传达它。会有什么问题?我应该传递 Stream 而不是文件路径吗?是因为surfaceview旋转吗?无论如何,如何在任何设备上制作捕获的图像肖像?任何帮助表示赞赏。
【问题讨论】:
-
就我个人而言,我从未见过涵盖所有 Android 设备上所有相机方向问题的单一解决方案。最大的(IHO)是一些手机有旋转传感器,一些使用“自动定位”,为了避免这些问题,你必须在捕获之前检查方向并使用相机参数来旋转方向。
-
@SushiHangover 您好,感谢您的回复。你能解释一下吗?我应该使用相机方向保存图像 exif 数据吗?
-
有很多基于 Java/Kotlin 的解决方案展示了如何正确完成此操作。我个人使用 react-native 扩展作为我的 goto 源,因为他们的开发者社区非常庞大,并且知道他们的
react-native-camera插件可以正确处理这个问题,因为我已经借用了许多 Java 来转换为 C#,如果你搜索在该插件的问题中,您会找到对正确处理方向的代码更正的引用(当然,如果您需要 100% 的合规性,您还必须针对每个型号的手机进行特殊情况) -
你用的是哪个金块?
-
@Blu 你的意思是 xamarin.forms 版本?
标签: xamarin xamarin.forms xamarin.android