Y'CbCr is often confused with the YUV color space, and typically the terms YCbCr and YUV are used interchangeably, leading to some confusion; when referring to signals in video or digital form, the term "YUV" mostly means "Y'CbCr".
--源自wikipedia—YUV
Y'UV is often used as the term for YCbCr. However, they are different formats. Y'UV is an analog system with scale factors different from the digital Y'CbCr system.
In digital video/image systems, Y'CbCr is the most common way to express color in a way suitable for compression/transmission. The confusion stems from computer implementations and text-books erroneously using the term YUV where Y'CbCr would be correct.
--源自wikipedia—YcbCr
实际上,数字视频编码中所说的YUV就是YCbCr。
RGB to YUV Conversion
Y = (0.257 * R) + (0.504 * G) + (0.098 * B) + 16
Cr = V = (0.439 * R) - (0.368 * G) - (0.071 * B) + 128
Cb = U = -(0.148 * R) - (0.291 * G) + (0.439 * B) + 128
如果是rgb是12bit的话
Y = (0.257 * R) + (0.504 * G) + (0.098 * B) + 256
Cr = V = (0.439 * R) - (0.368 * G) - (0.071 * B) + 2048
Cb = U = -(0.148 * R) - (0.291 * G) + (0.439 * B) + 2048
YUV to RGB Conversion
B = 1.164(Y - 16) + 2.018(U - 128)
G = 1.164(Y - 16) - 0.813(V - 128) - 0.391(U - 128)
R = 1.164(Y - 16) + 1.596(V - 128)
In both these cases, you have to clamp the output values
Ø 系数矩阵整型化
在RGB2YCbCr的公式中左右各乘以1024即左移10位
Y << 10 = (263 * R) + (516 * G) + (100 * B) + 262144
Cr << 10 = (450 * R) - (377 * G) - ( 73 * B) + 2097152
Cb << 10 = -(152 * R) - (298 * G) + (450 * B) + 2097152
负数取补,保守一点,系数取12位
Y << 10 = (12'h107 * R) + (12'h204 * G) + (12'h064 * B) + 24'h040000
Cr << 10 = (12'h1C2 * R) + (12'hE87 * G) + (12'hFB7 * B) + 24'h200000
Cb << 10 = (12'hF68 * R) + (12'hED6 * G) + (12'h1C2 * B) + 24'h200000
友晶的D5M中采样出来的RGB格式是各占12bit,最终YCrCb要截取成8位的,还是在转换之前保持精度,在转换之后再截取吧。以下设计方法参考友晶DE2系列中YCbCr2RGB的参考例程。
系数12位有符号,输入的RGB数据是12位无符号,乘加之后输出数据为26位。在MegaWizard Plug-In Manager工具中配置如下。
不好的一点,没有找到ALTMUT_ADD核中datab为常数的配置,应该是没有的,可以手动用其它乘法器核(设置一个相乘的系数为常数)和加法器核来搭。
Ø RGB2YCrCb核的设计
采用了3个乘加器,之后又各自用了3个加法器和移位器,来完成RGB到YUV的转换工作。rgb2yuv.v的代码如下
// Author(s):
// - Huailu Ren, hlren.pub@gmail.com, http://lunix.cnblogs.com
//
// Revision 1.0 21:58 2011-7-30 hlren
// created
//
// synopsys translate_off
`timescale 1 ps / 1 ps
// synopsys translate_on
module RGB2YCrCb (
iCLK,
iRESET,
iRed,
iGreen,
iBlue,
iDVAL,
oY,
oCb,
oCr,
oDVAL
);
// Input
input iCLK,iRESET,iDVAL;
input [11:0] iRed,iGreen,iBlue;
// Output
output reg [11:0] oY,oCb,oCr;
output reg oDVAL;
// Internal Registers/Wires
reg [3:0] oDVAL_d;
reg [15:0] tY_r,tU_r,tV_r;
wire [25:0] tY,tU,tV;
always@(posedge iCLK)
begin
if(iRESET)
begin
oDVAL<=0;
oDVAL_d<=0;
oY <=0;
oCr<=0;
oCb<=0;
end
else
begin
// Red
if(tY_r[15])
oY<=0;
else if(tY_r[14:0]>4095)
oY<=4095;
else
oY<=tY_r[11:0];
// Green
if(tU_r[15])
oCr<=0;
else if(tU_r[14:0]>4095)
oCr<=4095;
else
oCr<=tU_r[11:0];
// Blue
if(tV_r[15])
oCb<=0;
else if(tV_r[14:0]>4095)
oCb<=4095;
else
oCb<=tV_r[11<