📄 block.cpp
字号:
//Name : Quant_blk_I
//Input : a 8*8 16-bit block coefficients to be quanted pointed by curr_block
// QUANT Parameter,QP
//Output : Quanted coefficients, qun_blk
// zero flag, return value
//Description : quant and scan
// special quant function for INTRA block for the difference
// between INTRA & INTER in quant, so you can use this function
// for quant in I picture encode directly.
//Last modified on 2002.11.22 by zj
int Quant_blk_I (INT16 *curr_blk,INT16 *qun_blk, int QP)
{
int ZeroFlag = 0;
int QPX2 = QP * 2;
if (QP)
{
*qun_blk = mmax (1, mmin (254, *curr_blk / 8));
for (int i = 1; i < 64; i++)
{
if (curr_blk[i] >= QPX2 || curr_blk[i] <= -QPX2)
{
// if QP is larger than 8, don't use extended quantization
// if (!codeoption->modified_quantization || QP >= 8)
// {
qun_blk[MixZig[i]] = mmin (127, mmax (-127, (curr_blk[i] / QPX2))) ;
// }
// else
// {
// no clipping, quantized coefficients
//qcoeff[block*64 + i] = sign (coeff[block*64 + i]) * level;
// qcoeff[tmpposition + MixZig[i]] = coeff[tmpposition + i] / QPX2;
// }
ZeroFlag=1;
}
else
qun_blk[MixZig[i]] = 0;
}
return ZeroFlag;
}
else
{
printf ("ERROR QUANT = 0 in THIS frame\n!");
exit (0);
}
}
//Name : DeQuant_blk_I
//Input : a 8*8 16-bit block for dequant, curr_blk
// quant parameter,QP
//Output : Dequanted block for IDCT, curr_block
//Dciscription : the inverse process of Quant_block_I
//Last modifid on 2002.11.22 by zj
void DeQuant_blk_I (INT16 *curr_blk, INT16 *recn_blk, int QP)
{
int i,s,ss=0;
if (QP)
{
ss = (QP%2) ? -1 : 0;
*(recn_blk) = *(curr_blk) * 8;
for (i =1; i < 64; i++)
{
if (curr_blk[MixZig[i]])
{
s = (curr_blk[MixZig[i]] > 0) ? 1 : -1;
ss *= s;
recn_blk[i] = QP * (2 * curr_blk[MixZig[i]] + s) + ss;
}
else
recn_blk[i] = 0;
}
}
else
{
printf ("ERROR!QUANT = 0 in THIS frame!\n");
exit (0);
}
}
*/
/*****************************************************************************
//Name : Quant_blk_I
//Input : a 8*8 16-bit block coefficients to be quanted pointed by curr_block
// QUANT Parameter,QP
//Output : Quanted coefficients, qun_blk
// zero flag, return value
//Description : quant and scan
// special quant function for INTRA block for the difference
// between INTRA & INTER in quant, so you can use this function
// for quant in I picture encode directly.
//Optimization: NO
//Last modified on 2002.11.22 by zj
******************************************************************************/
int Quant_blk_I_c (INT16 *curr_blk,INT16 *qun_blk, int QP)
{
int i;
int level;
int nonezero = 0;
float QPP2 = 0.5/QP;
if (QP)
{
qun_blk[0] = mmax(1,mmin(254, (curr_blk[0]+4)/8));
for (i = 1; i < 64; i++)
{
level = (abs(curr_blk[i])) * QPP2;
if (level == 0)
{
qun_blk[MixZig[i]] = 0;
}
else
{
qun_blk[MixZig[i]] = mmin(127,mmax(-127,sign(curr_blk[i]) * level));
nonezero = 1;
}
}
}
return nonezero;
}
/************************************************************************
//Name : DeQuant_blk_I
//Input : a 8*8 16-bit block for dequant, curr_blk
// quant parameter,QP
//Output : Dequanted block for IDCT, curr_block
//Dciscription : the inverse process of Quant_block_I
//Optimization : NO
//Last modifid on 2002.11.22 by zj
*************************************************************************/
void DeQuant_blk_I_c (INT16 *curr_blk, INT16 *recn_blk, int QP)
{
int i;
for (i = 0; i < 64; i++)
{
if (curr_blk[MixZig[i]])
{
if ((QP % 2) == 1)
recn_blk[i] = QP * (2*abs(curr_blk[MixZig[i]]) + 1);
else
recn_blk[i] = QP * (2*abs(curr_blk[MixZig[i]]) + 1) - 1;
recn_blk[i] = sign(curr_blk[MixZig[i]]) * recn_blk[i];
}
else
recn_blk[i] = 0;
}
recn_blk[0] = curr_blk[0]*8;
}
/*!
*******************************************************************************
*
* Name: Quant_blk_P
* Description: Quant and scan
* Input: curr_blk
* Output: qun_blk
* Optimization: NO
* Last modified: 2003.2.27
*
*******************************************************************************/
int Quant_blk_P_c (INT16 *curr_blk,INT16 *qun_blk, int QP)
{
int i;
int level;
int nonezero = 0;
int qpp = QP/2;
float qp = (float) 1 / (2*QP);
if (QP)
{
for (i = 0; i < 64; i++)
{
//level = (abs(curr_blk[i]) - QP/2) / (2*QP);
level = (abs(curr_blk[i]) - qpp) * qp;
if (!level)
{
qun_blk[MixZig[i]] = 0;
}
else
{
qun_blk[MixZig[i]] = mmin(127,mmax(-127,sign(curr_blk[i]) * level));
nonezero = 1;
}
}
}
return nonezero;
}
/* removed temporarily, may be utilized in future
int Quant_blk_P(INT16 *curr_blk, INT16 *qun_blk, int QP)
{
int ZeroFlag = 0;
int QPX2 = QP * 2;
int value;
if (QP)
{
for (int i = 0; i < 64; i++)
{
if (curr_blk[i] >= QPX2 || curr_blk[i] <= -QPX2)
{
/*! there is a little difference between the following quantification
method and tmn method
should be thinked over later
*/
/* value = (abs(curr_blk[i])-QP/2) / QPX2;
qun_blk[MixZig[i]] = mmin (127, mmax (-127, sign(curr_blk[i])*value)) ;
ZeroFlag=1;
}
else
qun_blk[MixZig[i]] = 0;
}
return ZeroFlag;
}
else
{
printf ("ERROR QUANT = 0 in THIS frame\n!");
exit (0);
}
}
*/
/*!
*******************************************************************************
*
* Name:
* Description:
* Input:
* Output:
* Last modified:
*
*******************************************************************************/
/*
void DeQuant_blk_P( INT16 *qun_blk, INT16 *curr_blk, int QP)
{
int i,s,ss=0;
if (QP)
{
ss = (QP%2) ? -1 : 0;
for (i =0; i < 64; i++)
{
if (qun_blk[MixZig[i]])
{
s = (qun_blk[MixZig[i]] > 0) ? 1 : -1;
ss *= s;
curr_blk[i] = QP * (2 * qun_blk[MixZig[i]] + s) + ss;
}
else
curr_blk[i] = 0;
}
}
else
{
printf ("ERROR!QUANT = 0 in THIS frame!\n");
exit (0);
}
}
*/
/*!
*******************************************************************************
*
* Name: DeQuant_blk_P
* Description: DeQuant and inverse scan
* Input: curr_blk
* Output: recn_blk
* Optimization: NO
* Last modified: 2003.2.27
*
*******************************************************************************/
void DeQuant_blk_P_c (INT16 *curr_blk, INT16 *recn_blk, int QP)
{
int i;
for (i = 0; i < 64; i++)
{
if (curr_blk[MixZig[i]])
{
if ((QP % 2) == 1)
recn_blk[i] = QP * (2*abs(curr_blk[MixZig[i]]) + 1);
else
recn_blk[i] = QP * (2*abs(curr_blk[MixZig[i]]) + 1) - 1;
recn_blk[i] = sign(curr_blk[MixZig[i]]) * recn_blk[i];
}
else
recn_blk[i] = 0;
}
}
/**************************************************************************************
//Name : fdct
//Input : 8*8 16-bit block data to be transformed: curr_blk.
//Output : transformed data for quant, rsltblk.
//Description : DCT transform
//Optimization: fdct_mmx.cpp(for IA)
//Last modified on 2003.2.11 by lcl
**************************************************************************************/
void fdct_c (INT16 *curr_blk, INT16 *rsltblk)
{
int j1, i, j, k;
float b[8];
float b1[8];
float d[8][8];
float f0 = (float) .7071068;
float f1 = (float) .4903926;
float f2 = (float) .4619398;
float f3 = (float) .4157348;
float f4 = (float) .3535534;
float f5 = (float) .2777851;
float f6 = (float) .1913417;
float f7 = (float) .0975452;
for (i = 0, k = 0; i < 8; i++)
{
for (j = 0; j < 4; j++)
{
j1 = 7 - j;
b1[j] = (float) curr_blk[j + k] + (float) curr_blk[j1 + k];
b1[j1] = (float) curr_blk[j + k] - (float) curr_blk[j1 + k];
}
k += 8;
b[0] = b1[0] + b1[3];
b[1] = b1[1] + b1[2];
b[2] = b1[1] - b1[2];
b[3] = b1[0] - b1[3];
b[4] = b1[4];
b[5] = (b1[6] - b1[5]) * f0;
b[6] = (b1[6] + b1[5]) * f0;
b[7] = b1[7];
d[i][0] = (b[0] + b[1]) * f4;
d[i][4] = (b[0] - b[1]) * f4;
d[i][2] = b[2] * f6 + b[3] * f2;
d[i][6] = b[3] * f6 - b[2] * f2;
b1[4] = b[4] + b[5];
b1[7] = b[7] + b[6];
b1[5] = b[4] - b[5];
b1[6] = b[7] - b[6];
d[i][1] = b1[4] * f7 + b1[7] * f1;
d[i][5] = b1[5] * f3 + b1[6] * f5;
d[i][7] = b1[7] * f7 - b1[4] * f1;
d[i][3] = b1[6] * f3 - b1[5] * f5;
}
/* Vertical transform */
for (i = 0; i < 8; i++)
{
for (j = 0; j < 4; j++)
{
j1 = 7 - j;
b1[j] = d[j][i] + d[j1][i];
b1[j1] = d[j][i] - d[j1][i];
}
b[0] = b1[0] + b1[3];
b[1] = b1[1] + b1[2];
b[2] = b1[1] - b1[2];
b[3] = b1[0] - b1[3];
b[4] = b1[4];
b[5] = (b1[6] - b1[5]) * f0;
b[6] = (b1[6] + b1[5]) * f0;
b[7] = b1[7];
rsltblk[i] = (short) ((b[0] + b[1]) * f4);
rsltblk[32 + i] = (short) ((b[0] - b[1]) * f4);
rsltblk[16 + i] = (short) (b[2] * f6 + b[3] * f2);
rsltblk[48 + i] = (short) (b[3] * f6 - b[2] * f2);
b1[4] = b[4] + b[5];
b1[7] = b[7] + b[6];
b1[5] = b[4] - b[5];
b1[6] = b[7] - b[6];
rsltblk[8 + i] = (short) (b1[4] * f7 + b1[7] * f1);
rsltblk[40 + i] = (short) (b1[5] * f3 + b1[6] * f5);
rsltblk[56 + i] = (short) (b1[7] * f7 - b1[4] * f1);
rsltblk[24 + i] = (short) (b1[6] * f3 - b1[5] * f5);
}
}
/******************************************************************************************
//Name : idct
//Input : a 8*8 16-bit block dequanted: curr_blk;
//Output : 8*8 16-bit block: des_blk
//Description : inverse DCT
//Optimization: idctmmx.asm; idct_mmx.cpp. (for IA)
//Last modified on 2002.11.22 by zj
*******************************************************************************************/
void idct_c (INT16 *curr_blk, INT16 *des_blk)
{
int j1, i, j, k;
double b[8], b1[8], d[8][8];
double f0 = .7071068;
double f1 = .4903926;
double f2 = .4619398;
double f3 = .4157348;
double f4 = .3535534;
double f5 = .2777851;
double f6 = .1913417;
double f7 = .0975452;
double e, f, g, h;
/* Horizontal */
for (i = 0, k = 0; i < 8; i++, k += 8)
{
e = ((double) curr_blk[1 + k]) * f7 - ((double) curr_blk[7 + k]) * f1;
h = ((double) curr_blk[7 + k]) * f7 + ((double) curr_blk[1 + k]) * f1;
f = ((double) curr_blk[k + 5]) * f3 - ((double) curr_blk[k + 3]) * f5;
g = ((double) curr_blk[k + 3]) * f3 + ((double) curr_blk[k + 5]) * f5;
b1[0] = ((double) (curr_blk[k + 0] + curr_blk[k + 4])) * f4;
b1[1] = ((double) (curr_blk[k + 0] - curr_blk[k + 4])) * f4;
b1[2] = ((double) curr_blk[k + 2]) * f6 - ((double) curr_blk[k + 6]) * f2;
b1[3] = ((double) curr_blk[k + 6]) * f6 + ((double) curr_blk[k + 2]) * f2;
b[4] = e + f;
b1[5] = e - f;
b1[6] = h - g;
b[7] = h + g;
b[5] = (b1[6] - b1[5]) * f0;
b[6] = (b1[6] + b1[5]) * f0;
b[0] = b1[0] + b1[3];
b[1] = b1[1] + b1[2];
b[2] = b1[1] - b1[2];
b[3] = b1[0] - b1[3];
for (j = 0; j < 4; j++)
{
j1 = 7 - j;
d[i][j] = b[j] + b[j1];
d[i][j1] = b[j] - b[j1];
}
}
/* Vertical */
for (i = 0; i < 8; i++)
{
e = d[1][i] * f7 - d[7][i] * f1;
h = d[7][i] * f7 + d[1][i] * f1;
f = d[5][i] * f3 - d[3][i] * f5;
g = d[3][i] * f3 + d[5][i] * f5;
b1[0] = (d[0][i] + d[4][i]) * f4;
b1[1] = (d[0][i] - d[4][i]) * f4;
b1[2] = d[2][i] * f6 - d[6][i] * f2;
b1[3] = d[6][i] * f6 + d[2][i] * f2;
b[4] = e + f;
b1[5] = e - f;
b1[6] = h - g;
b[7] = h + g;
b[5] = (b1[6] - b1[5]) * f0;
b[6] = (b1[6] + b1[5]) * f0;
b[0] = b1[0] + b1[3];
b[1] = b1[1] + b1[2];
b[2] = b1[1] - b1[2];
b[3] = b1[0] - b1[3];
for (j = 0, k = 0; j < 4; j++, k += 8)
{
j1 = 7 - j;
des_blk[k + i] = (INT16) mnint(b[j] + b[j1]);
des_blk[56 - k + i] = (INT16) mnint(b[j] - b[j1]);
}
}
}
/*!
*******************************************************************************
*
* Name: block_copy1
* Description: copy a block(8x8) of data to somewhere in a image
* Input: the pointer of source block, the pointer of destination,
* width of image
* Output: none
* Optimization:
* Last modified: 2002/11/20
*
*******************************************************************************/
void block_copy1_c( unsigned char *des_block, unsigned char *src_block, int lx_des)
{
unsigned char *tmp = src_block;
int i, j, k;
for (i = 0, k = 0; i < 8; i++, k+=lx_des)
{
for(j = 0; j < 8; j++)
{
*(des_block + k + j) = *tmp;
tmp++;
}
}
}
/*!
*******************************************************************************
*
* Name: block_copy2
* Description: copy a block(8x8) of data in the picture to a 8x8 block
* Input: the pointer of source block, the pointer of destination,
* width of image
* Output: none
* Optimization:
* Last modified: 2003/2/11
*
*******************************************************************************/
void block_copy2_c(INT16 *des_block, unsigned char *src_block, int lx_src)
{
INT16 *tmp = des_block;
int i, j, k;
for (i = 0, k = 0; i < 8; i++, k+=lx_src)
{
for(j = 0; j < 8; j++)
{
*tmp = (INT16) (*(src_block + k + j));
tmp++;
}
}
}
/*!
*******************************************************************************
*
* Name: block_copy3
* Description: copy a block(8x8) of data in 8x8 block to the picture
* Input: the pointer of source block, the pointer of destination,
* width of image
* Output: none
* Optimizaiton:
* Last modified: 2003/2/25
*
*******************************************************************************/
void block_copy3_c(unsigned char *des_block, INT16 *src_block, int lx_des)
{
INT16 *tmp = src_block;
int i, j, k;
for (i = 0, k = 0; i < 8; i++, k+=lx_des)
{
for(j = 0; j < 8; j++)
{
*(des_block + k + j) =(unsigned char)mmin(255, mmax(0, mnint (*tmp)));
tmp++;
}
}
}
int block_SAD(INT16 *block)
{
int sad = 0;
int i;
for (i = 0; i < 64; i++)
{
sad += absm(block[i]);
}
return sad;
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -