<div>
</div>// // // Project : VideoNet version 1.1. // Description : Peer to Peer Video Conferencing over the LAN. // Author : Nagareshwar Y Talekar ( nsry2002@yahoo.co.in) // Date : 15-6-2004. // // // File description : // Name : convert.cpp // Details : Conversion routine from RGB24 to YUV420 & YUV420 to RGB24. // / #include "convert.h" // Conversion from RGB to YUV420 int RGB2YUV_YR[256], RGB2YUV_YG[256], RGB2YUV_YB[256]; int RGB2YUV_UR[256], RGB2YUV_UG[256], RGB2YUV_UBVR[256]; int RGB2YUV_VG[256], RGB2YUV_VB[256]; // Conversion from YUV420 to RGB24 static long int crv_tab[256]; static long int cbu_tab[256]; static long int cgu_tab[256]; static long int cgv_tab[256]; static long int tab_76309[256]; static unsigned char clp[1024]; //for clip in CCIR601 static unsigned char convert_uu[320*240]; static unsigned char convert_vv[320*240]; int ConvertRGB2YUV(int w,int h,unsigned char *bmp,unsigned char *yuv); // // Table used for RGB to YUV420 conversion // void InitLookupTable() { int i; for (i = 0; i < 256; i++) RGB2YUV_YR[i] = (float)65.481 * (i<<8); for (i = 0; i < 256; i++) RGB2YUV_YG[i] = (float)128.553 * (i<<8); for (i = 0; i < 256; i++) RGB2YUV_YB[i] = (float)24.966 * (i<<8); for (i = 0; i < 256; i++) RGB2YUV_UR[i] = (float)37.797 * (i<<8); for (i = 0; i < 256; i++) RGB2YUV_UG[i] = (float)74.203 * (i<<8); for (i = 0; i < 256; i++) RGB2YUV_VG[i] = (float)93.786 * (i<<8); for (i = 0; i < 256; i++) RGB2YUV_VB[i] = (float)18.214 * (i<<8); for (i = 0; i < 256; i++) RGB2YUV_UBVR[i] = (float)112 * (i<<8); } // // Convert from RGB24 to YUV420 // int ConvertRGB2YUV(int w,int h,unsigned char *bmp,unsigned char *yuv) { unsigned char *u,*v,*y; unsigned char *pu1,*pu2,*pu3,*pu4; unsigned char *pv1,*pv2,*pv3,*pv4; unsigned char *r,*g,*b; int i,j; if(convert_uu==NULL || convert_vv==NULL) return 0; y=yuv; // u=convert_uu; // v=convert_vv; v=convert_uu; u=convert_vv; // Get r,g,b pointers from bmp image data.... r=bmp; g=bmp+1; b=bmp+2; //Get YUV values for rgb values... for(i=0;i >16; *u++=(-RGB2YUV_UR[*r] -RGB2YUV_UG[*g]+RGB2YUV_UBVR[*b]+8388608)>>16; *v++=( RGB2YUV_UBVR[*r]-RGB2YUV_VG[*g]-RGB2YUV_VB[*b]+8388608)>>16; r+=3; g+=3; b+=3; } } // Now sample the U & V to obtain YUV 4:2:0 format // Sampling mechanism... /* @ -> Y # -> U or V @ @ @ @ # # @ @ @ @ @ @ @ @ # # @ @ @ @ */ // Get the right pointers... u=yuv+w*h; v=u+(w*h)/4; // For U pu1=convert_uu; pu2=pu1+1; pu3=pu1+w; pu4=pu3+1; // For V pv1=convert_vv; pv2=pv1+1; pv3=pv1+w; pv4=pv3+1; // Do sampling.... for(i=0;i >2; *v++=(*pv1+*pv2+*pv3+*pv4)>>2; pu1+=2; pu2+=2; pu3+=2; pu4+=2; pv1+=2; pv2+=2; pv3+=2; pv4+=2; } pu1+=w; pu2+=w; pu3+=w; pu4+=w; pv1+=w; pv2+=w; pv3+=w; pv4+=w; } return 1; } // //Initialize conversion table for YUV420 to RGB // void InitConvertTable() { long int crv,cbu,cgu,cgv; int i,ind; crv = 104597; cbu = 132201; /* fra matrise i global.h */ cgu = 25675; cgv = 53279; for (i = 0; i < 256; i++) { crv_tab[i] = (i-128) * crv; cbu_tab[i] = (i-128) * cbu; cgu_tab[i] = (i-128) * cgu; cgv_tab[i] = (i-128) * cgv; tab_76309[i] = 76309*(i-16); } for (i=0; i<384; i++) clp[i] =0; ind=384; for (i=0;i<256; i++) clp[ind++]=i; ind=640; for (i=0;i<384;i++) clp[ind++]=255; } // // Convert from YUV420 to RGB24 // void ConvertYUV2RGB(unsigned char *src0,unsigned char *src1,unsigned char *src2,unsigned char *dst_ori, int width,int height) { int y1,y2,u,v; unsigned char *py1,*py2; int i,j, c1, c2, c3, c4; unsigned char *d1, *d2; py1=src0; py2=py1+width; d1=dst_ori; d2=d1+3*width; for (j = 0; j < height; j += 2) { for (i = 0; i < width; i += 2) { u = *src1++; v = *src2++; c1 = crv_tab[v]; c2 = cgu_tab[u]; c3 = cgv_tab[v]; c4 = cbu_tab[u]; //up-left y1 = tab_76309[*py1++]; *d1++ = clp[384+((y1 + c1)>>16)]; *d1++ = clp[384+((y1 - c2 - c3)>>16)]; *d1++ = clp[384+((y1 + c4)>>16)]; //down-left y2 = tab_76309[*py2++]; *d2++ = clp[384+((y2 + c1)>>16)]; *d2++ = clp[384+((y2 - c2 - c3)>>16)]; *d2++ = clp[384+((y2 + c4)>>16)]; //up-right y1 = tab_76309[*py1++]; *d1++ = clp[384+((y1 + c1)>>16)]; *d1++ = clp[384+((y1 - c2 - c3)>>16)]; *d1++ = clp[384+((y1 + c4)>>16)]; //down-right y2 = tab_76309[*py2++]; *d2++ = clp[384+((y2 + c1)>>16)]; *d2++ = clp[384+((y2 - c2 - c3)>>16)]; *d2++ = clp[384+((y2 + c4)>>16)]; } d1 += 3*width; d2 += 3*width; py1+= width; py2+= width; } }
编辑文章 - 博客频道 - CSDN.NET
最新推荐文章于 2018-12-29 16:08:16 发布