Android 如何将YUV转换为横向位图? 第一种方法
当我设定Android 如何将YUV转换为横向位图? 第一种方法,android,android-bitmap,android-image,android-camera2,bytebuffer,Android,Android Bitmap,Android Image,Android Camera2,Bytebuffer,当我设定 javasetRequestedOrientation(ActivityInfo.SCREEN\u ORIENTATION\u传感器)或java setRequestedOrientation(ActivityInfo.SCREEN\u ORIENTATION\u Picture) Camera2运行正常,并从imageavailablelistener保存图像 第二种方法 当我设置java setRequestedOrientation(ActivityInfo.SCREEN\u O
javasetRequestedOrientation(ActivityInfo.SCREEN\u ORIENTATION\u传感器)代码>或java setRequestedOrientation(ActivityInfo.SCREEN\u ORIENTATION\u Picture)代码>
Camera2运行正常,并从imageavailablelistener保存图像
第二种方法
当我设置java setRequestedOrientation(ActivityInfo.SCREEN\u ORIENTATION\u横向)时代码>或java setRequestedOrientation(ActivityInfo.SCREEN\u ORIENTATION\u REVERSE\u横向)代码>
它将退出应用程序,无法保存图像
转换信用证
YUV图像到位图的方法归功于
呼叫者
private final ImageReader.OnImageAvailableListener mOnImageAvailableListener=新的ImageReader.OnImageAvailableListener(){
@凌驾
公共图像可用(图像阅读器){
最终图像=reader.acquiredlatestimage();
if(image==null)
返回;
BitmapFunctions BitmapFunctions=新的BitmapFunctions();
//QrDecoder QrDecoder=新的QrDecoder();
//将YUV转换为RGB并返回位图
位图位图=位图函数。mediaImageToBitmap(图像,活动);
实际转换函数
公共类位图函数{
私人分配;
专用分配RGB;
私有渲染脚本;
公共位图mediaImageToBitmap(图像、上下文){
最终ByteBuffer yuvBytes=图像到字节缓冲区(图像);
//将YUV转换为RGB
rs=RenderScript.create(上下文);
位图Bitmap=Bitmap.createBitmap(image.getWidth()、image.getHeight()、Bitmap.Config.ARGB_8888);
allocationRgb=Allocation.createFromBitmap(rs,位图);
allocationYuv=Allocation.createSized(rs,Element.U8(rs),yuvBytes.array().length);
allocationYuv.copyFrom(yuvBytes.array());
ScriptIntrinsicYuvToRGB scriptYuvToRgb=ScriptIntrinsicYuvToRGB.create(rs,Element.U8_4(rs));
scriptYuvToRgb.setInput(分配yuv);
scriptYuvToRgb.forEach(分配RGB);
allocationRgb.copyTo(位图);
返回位图;
}
公开无效释放(){
allocationYuv.destroy();
allocationRgb.destroy();
rs.destroy();
}
专用ByteBuffer imageToByteBuffer(最终图像){
最终矩形裁剪=image.getCropRect();
最终整型宽度=裁剪宽度();
最终整型高度=裁剪高度();
final Image.Plane[]planes=Image.getPlanes();
最后一个字节[]行数据=新字节[planes[0]。getRowStride()];
final int bufferSize=width*height*ImageFormat.getBitsPerPixel(ImageFormat.YUV_420_888)/8;
最终ByteBuffer输出=ByteBuffer.allocateDirect(bufferSize);
int channelOffset=0;
int outputStride=0;
对于(int planeIndex=0;planeIndex<3;planeIndex++){
如果(平面索引==0){
channelOffset=0;
输出步幅=1;
}否则如果(平面索引==1){
通道偏移=宽度*高度+1;
输出步幅=2;
}否则如果(平面索引==2){
通道偏移=宽度*高度;
输出步幅=2;
}
final ByteBuffer buffer=平面[planeIndex].getBuffer();
final int rowStride=平面[planeIndex].getRowStride();
final int pixelStride=平面[planeIndex].getPixelStride();
最终整数移位=(平面索引==0)?0:1;
最终整数宽度移位=宽度>>移位;
最终内部高度偏移=高度>>偏移;
buffer.position(rowStride*(crop.top>>shift)+pixelStride*(crop.left>>shift));
对于(int row=0;row
错误
ctrl+f
查找错误行
java:105是channelOffset+=outputStride
java:36是Bitmap Bitmap=Bitmap.createBitmap(image.getWidth()、image.getHeight()、Bitmap.Config.ARGB_8888)
java:302是位图Bitmap=bitmapFunctions.mediaImageToBitmap(图像,活动)
更新日期20/6/2019
现在一切正常,相同的代码没有任何变化。使用相同的电缆,但手机今天早上重新启动,并添加了Log.e(“图像大小”,“宽度=“+Image.getWidth()+”高度=“+Image.getHeight());
在我把它注释掉之后,它会再次自动退出。现在我删除了注释,它就不能再工作了。WTF
有人能给我解释一下吗?设置请求方向(ActivityInfo.SCREEN\u ORIENTATION\u SENSOR)
而不是设置这个
将其更改为清单中的强制方向。不知道为什么会这样
希望有人能给我解释。设置请求方向(ActivityInfo.SCREEN\u ORIENTATION\u SENSOR)
而不是设置此选项
将其更改为清单中的强制方向。不知道为什么会这样
希望有人能给我解释一下
2019-06-19 17:04:47.551 23356-23423/com.dsonic.datasonicscanner E/AndroidRuntime: FATAL EXCEPTION: CameraBackground
Process: com.dsonic.datasonicscanner, PID: 23356
java.lang.IllegalStateException: buffer is inaccessible
at java.nio.DirectByteBuffer.get(DirectByteBuffer.java:219)
at com.dsonic.dsoniccamera2lib.Camera2.BitmapFunctions.imageToByteBuffer(BitmapFunctions.java:105)
at com.dsonic.dsoniccamera2lib.Camera2.BitmapFunctions.mediaImageToBitmap(BitmapFunctions.java:36)
at com.dsonic.dsoniccamera2lib.Camera2.Camera2Manager$4.onImageAvailable(Camera2Manager.java:302)
at android.media.ImageReader$ListenerHandler.handleMessage(ImageReader.java:812)
at android.os.Handler.dispatchMessage(Handler.java:108)
at android.os.Looper.loop(Looper.java:166)
at android.os.HandlerThread.run(HandlerThread.java:65)