Java代码:RGB565转YUV420SP

  近期在弄Android外置usb摄像头开发,所获取到的数据是RGB565的,但是接收方必须要是YUV420SP格式的。(接口是基于Android手机摄像头的数据格式NV21来写的,现在要用usb摄像头所以导致数据不通)

之前接触到的都是底层C来转,现在要自己动手了。开启百度之旅,百度都翻到10页之后了,基本都是YUV转RGB的,偶尔有RGB转YUV的也是C语言的。C也看不懂啊!

也翻到一篇关于java的,但是是图片转YUV,传入类型是通过bitmap来获取到的int[],而我获取到的数据源是byte[]的RGB565格式,用byte[]转成int[],不能用。

查了很多的资料,都是在介绍互转的公式。

后来绝望了

试着翻译C,很多基本数据都不会翻译。没走通。。。

用ndk来编译.so来跑C代码,但是不会转java到C的基本数据。。。还是没走通

决定还是从java代码入手吧

又看起之前找到的一篇java代码:Java实现的RGB转YUV420方法

接下来寻找怎样把我的byte[]转换成int[],无意中,真的是无意中发现的。RGB565 数据 如何 保存为图片

终于找到了我想要的,泪奔ing...........

下面进入拼接环节了,先将byte[]转成int[],然后转YUV,居然成功跑起来了。

但是画面数据怎么是这个样子

Java代码:RGB565转YUV420SP_第1张图片

能确定转是转成功了,但是有瑕疵。MMP。。。

最后实在不知道哪里的问题,请教了总监。。。。大佬不亏是大佬。问我这个byte有没有符号。这是啥,一脸懵逼,后来查了下,把byte转成int的符号去掉。运行,完美!!!!!!!!!!!!!!!!!!!

下面是代码,特此记录:以后基础还需多多努力

public static byte[] rgb565toYuv420sp(byte[] rgb565, int width, int height) {
		int len = width * height;
		byte[] yuv = new byte[len * 3 / 2];
		int y, u, v;
		int tmpColor[] = new int[width * height];
		for (int j = 0; j < width * height; j++) {
			// 去掉字节符号,图像字节都是无符号的
			int c = rgb565[j * 2 + 0] & 0x0ff;
			int d = rgb565[j * 2 + 1] & 0x0ff;
			int tmpint = c + d * 256;
			int a = 0xff;
			int r = (tmpint & 0xf800) >> 11;
			int g = (tmpint & 0x07e0) >> 5;
			int b = (tmpint & 0x001f);

			r = r << 3;
			g = g << 2;
			b = b << 3;
			tmpColor[j] = (a << 24) | (r << 16) | (g << 8) | (b);
		}
		for (int i = 0; i < height; i++) {
			for (int j = 0; j < width; j++) {
				// 屏蔽ARGB的透明度值
				int rgb = tmpColor[i * width + j] & 0x00FFFFFF;
				// 像素的颜色顺序为bgr,移位运算。
				int r = rgb & 0xFF;
				int g = (rgb >> 8) & 0xFF;
				int b = (rgb >> 16) & 0xFF;
				// 套用公式
				y = ((66 * r + 129 * g + 25 * b + 128) >> 8) + 16;
				u = ((-38 * r - 74 * g + 112 * b + 128) >> 8) + 128;
				v = ((112 * r - 94 * g - 18 * b + 128) >> 8) + 128;
				// 调整
				y = y < 16 ? 16 : (y > 255 ? 255 : y);
				u = u < 0 ? 0 : (u > 255 ? 255 : u);
				v = v < 0 ? 0 : (v > 255 ? 255 : v);
				// 赋值
				yuv[i * width + j] = (byte) y;
				yuv[len + (i >> 1) * width + (j & ~1) + 0] = (byte) u;
				yuv[len + +(i >> 1) * width + (j & ~1) + 1] = (byte) v;
			}
		}
		return yuv;
	}

 

 

你可能感兴趣的:(Android,Java)