1 先尝试各种模式搜索,P16x16,P8x8,P16x8,P8x16,P4x4,P4x4,P8x4,P4x8
B16x16,B8x8,B16x8,B8X16 这些搜索模式
2 以P16x16 搜索为例,mb_analyse_inter_p16x16 函数实现
for( int i_ref = 0; i_ref < h->mb.pic.i_fref[0]; i_ref++ )
{
x264_me_search_ref( h, &m, mvc, i_mvc, p_halfpel_thresh );// 搜索每一个参考帧,从中找到合适的参考宏块
}
void x264_me_search_ref( x264_t *h, x264_me_t *m, int16_t (*mvc)[2], int i_mvc, int *p_halfpel_thresh )
{
int bpred_mx = x264_clip3( m->mvp[0], SPEL(mv_x_min), SPEL(mv_x_max) );
int bpred_my = x264_clip3( m->mvp[1], SPEL(mv_y_min), SPEL(mv_y_max) );
pmv = pack16to32_mask( bpred_mx, bpred_my );
pmx = FPEL( bpred_mx );
pmy = FPEL( bpred_my );
//先获取之前的搜索mvp,以之前的mvp为原点开始搜索,并不是按照当前的宏块位置开始的
switch( h->mb.i_me_method )
{
case X264_ME_DIA:
{
}
case X264_ME_HEX:
case X264_ME_UMH:
case X264_ME_ESA:
case X264_ME_TESA:
}
以钻石搜索为例,
bcost <<= 4;// 把 方向低4bits 空出来
int i = i_me_range;
do
{// 搜索四个方向,找cost最小的
COST_MV_X4_DIR( 0,-1, 0,1, -1,0, 1,0, costs );// 这是个什么形状?
COPY1_IF_LT( bcost, (costs[0]<<4)+1 );//
COPY1_IF_LT( bcost, (costs[1]<<4)+3 );//
COPY1_IF_LT( bcost, (costs[2]<<4)+4 );//
COPY1_IF_LT( bcost, (costs[3]<<4)+12 );//
if( !(bcost&15) )// 如果上面 4 次没有找到合适的 宏块 为何这样判断,因为如果找到了,低4 bit会有上面的 1,3,4,12 这几个方向值,找不到的意思是没有找到比之前搜索到的bcost小的宏块,编码器认为,这次没已经没有搜索到了,下次更不会搜索到,因为bcost的趋势已经是在增大了,
break;
bmx -= (bcost<<28)>>30;// 按照cost大小决定下一次搜索跳过多少个像素
bmy -= (bcost<<30)>>30;
bcost &= ~15;// 1111 bits nagetive
} while( --i && CHECK_MVRANGE(bmx, bmy) );//搜索范围控制,按像素为单位的
bcost >>= 4;
再看看HEX搜索,
COST_MV_X3_DIR( -2,0, -1, 2, 1, 2, costs );
COST_MV_X3_DIR( 2,0, 1,-2, -1,-2, costs+4 ); /* +4 for 16-byte alignment */
补充一下,这里HEX搜索完后还会来一把正方形搜索
附上代码:
bcost <<= 4;
COST_MV_X4_DIR( 0,-1, 0,1, -1,0, 1,0, costs );
COPY1_IF_LT( bcost, (costs[0]<<4)+1 );
COPY1_IF_LT( bcost, (costs[1]<<4)+2 );
COPY1_IF_LT( bcost, (costs[2]<<4)+3 );
COPY1_IF_LT( bcost, (costs[3]<<4)+4 );
COST_MV_X4_DIR( -1,-1, -1,1, 1,-1, 1,1, costs );
COPY1_IF_LT( bcost, (costs[0]<<4)+5 );
COPY1_IF_LT( bcost, (costs[1]<<4)+6 );
COPY1_IF_LT( bcost, (costs[2]<<4)+7 );
COPY1_IF_LT( bcost, (costs[3]<<4)+8 );
bmx += square1[bcost&15][0];
bmy += square1[bcost&15][1];
bcost >>= 4;