Chinaunix首页 | 论坛 | 博客
  • 博客访问: 2287348
  • 博文数量: 668
  • 博客积分: 10016
  • 博客等级: 上将
  • 技术积分: 8588
  • 用 户 组: 普通用户
  • 注册时间: 2008-05-29 19:22
文章分类

全部博文(668)

文章存档

2011年(1)

2010年(2)

2009年(273)

2008年(392)

分类:

2009-08-14 10:55:51

③ decoder_pframe

P帧是主要的编码类型,解码器可以根据编码器的功能支持把多余的代码屏蔽。XviD支持的解码器较复杂,如B帧解码、GMC等,这里主要讨论解码SP档级的码流。

P帧的解码decoder_pframe()的流程如图14-9所示。

 
图14-9  decoder_pframe()流程图
根据该流程,代码实现如下。
void decoder_pframe(DECODER * dec, Bitstream * bs,
int rounding,int reduced_ resolution,
int quant,int fcode,int intra_dc_threshold)
{
uint32_t x, y;
uint32_t bound;
VECTOR  mv;
const VECTOR zerovec={0,0};
uint32_t mb_width = dec->mb_width;
uint32_t mb_height = dec->mb_height;
uint32_t width = dec->width;
uint32_t edged_width = dec->edged_width;
/*循环所有宏块*/
for (y=0; yfor (x = 0; x < mb_width; x++) {
MACROBLOCK *mb;
mb = &dec->mbs[y * dec->mb_width + x];
if (!(BitstreamGetBit(bs)))               /*当前宏块已经被编码*/
{
uint32_t mcbpc, cbpc, cbpy, cbp;
uint32_t intra, acpred_flag = 0;
mcbpc = get_mcbpc_inter(bs);            /*解码得到mcbpc*/
mb->mode = mcbpc & 7;
cbpc = (mcbpc >> 4);                       /*组合得到cbpc*/
intra = (mb->mode == MODE_INTRA);       /*是否Intra宏块*/
if (intra)  acpred_flag = BitstreamGetBit(bs);  /*Intra块的AC预测*/
cbpy = get_cbpy_asm_dm642(bs,intra);      /*解码得到cbpy*/
cbp = (cbpy << 2) | cbpc;                  /*组合得到CBP*/
mb->quant = quant;                         /*量化初始化*/
if (mb->mode == MODE_INTER){ /*编码模式是MODE_INTER*/
get_motion_vector(dec, bs, x, y, 0,&mv, fcode, bound);
/*解码得到MV.x , MV.y*/
mb->mvs[0] = mb->mvs[1] = mb->mvs[2] = mb->mvs[3] = mv;
/*初始化MVS*/
decoder_mbinter(dec, mb, x, y, cbp, bs, mv, 0,x);
/*Inter 解码*/
}  else {                  /*编码模式是MODE_INTRA */
mb->mvs[0].x = mb->mvs[1].x = mb->mvs[2]
.x = mb->mvs[3].x = 0;/*MVS置0 */
mb->mvs[0].y = mb->mvs[1].y = mb->mvs[2]
.y = mb->mvs[3].y = 0;/* MVS置0*/
decoder_mbintra(dec, mb, x, y, acpred_flag, cbp,/*解码Intra块*/
bs, quant,
intra_dc_threshold, bound);
continue;
}
} else {                                  
/*当前宏块没有被编码not_coded */
mb->mode = MODE_NOT_CODED;
mb->quant = quant;
mb->mvs[0].x = mb->mvs[1].x = mb->mvs[2]
.x = mb->mvs[3].x = 0;/* MVS置0*/
mb->mvs[0].y = mb->mvs[1].y = mb->mvs[2]
.y = mb->mvs[3].y = 0;/* MVS置0*/
decoder_mbinter(dec, mb, x, y, 0,
bs, zerovec, 0, x);/* Inter解码*/
}
} //x 循环
} //y 循环
}
上述代码实现P帧的解码,根据前面编码的流程知道,宏块有3种编码模式:Inter、Intra和not_coded。而对于not_coded同样是属于Inter块的编码范畴,在解码中同样要作运动补偿,只是不再做实质的解码工作。
阅读(831) | 评论(0) | 转发(0) |
给主人留下些什么吧!~~