⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 fast_me.c

📁 JM 11.0 KTA 2.1 Source Code
💻 C
📖 第 1 页 / 共 5 页
字号:
      pixel1 = weightSpic * (*ref1_line++);
      pixel2 = weightRpic * (*ref2_line++);
#ifdef  USE_HP_FILTER//BROUND
      if(input->UseHPFilter != 0)
      {
        weightedpel =  Clip3 (0, img->max_imgpel_value ,((pixel1 + pixel2  + (offsetBi<<luma_log_weight_denom) + lround) >> denom));
      }
      else
      {
        weightedpel =  Clip3 (0, img->max_imgpel_value ,((pixel1 + pixel2 + lround) >> denom) + offsetBi);
      }
#else
      weightedpel =  Clip3 (0, img->max_imgpel_value ,((pixel1 + pixel2 + lround) >> denom) + offsetBi);
#endif
      bi_diff = (*cur_line++)  - weightedpel;
      mcost += byte_abs[bi_diff];
      
      pixel1 = weightSpic * (*ref1_line++);
      pixel2 = weightRpic * (*ref2_line++);
#ifdef  USE_HP_FILTER//BROUND
      if(input->UseHPFilter != 0)
      {
        weightedpel =  Clip3 (0, img->max_imgpel_value ,((pixel1 + pixel2  + (offsetBi<<luma_log_weight_denom) + lround) >> denom));
      }
      else
      {
        weightedpel =  Clip3 (0, img->max_imgpel_value ,((pixel1 + pixel2 + lround) >> denom) + offsetBi);
      }
#else
      weightedpel =  Clip3 (0, img->max_imgpel_value ,((pixel1 + pixel2 + lround) >> denom) + offsetBi);
#endif
      bi_diff = (*cur_line++)  - weightedpel;
      mcost += byte_abs[bi_diff];
      
      pixel1 = weightSpic * (*ref1_line++);
      pixel2 = weightRpic * (*ref2_line++);
#ifdef  USE_HP_FILTER//BROUND
      if(input->UseHPFilter != 0)
      {
        weightedpel =  Clip3 (0, img->max_imgpel_value ,((pixel1 + pixel2  + (offsetBi<<luma_log_weight_denom) + lround) >> denom));
      }
      else
      {
        weightedpel =  Clip3 (0, img->max_imgpel_value ,((pixel1 + pixel2 + lround) >> denom) + offsetBi);
      }
#else
      weightedpel =  Clip3 (0, img->max_imgpel_value ,((pixel1 + pixel2 + lround) >> denom) + offsetBi);
#endif
      bi_diff = (*cur_line++)  - weightedpel;
      mcost += byte_abs[bi_diff];
      
      pixel1 = weightSpic * (*ref1_line++);
      pixel2 = weightRpic * (*ref2_line++);
#ifdef  USE_HP_FILTER//BROUND
      if(input->UseHPFilter != 0)
      {
        weightedpel =  Clip3 (0, img->max_imgpel_value ,((pixel1 + pixel2  + (offsetBi<<luma_log_weight_denom) + lround) >> denom));
      }
      else
      {
        weightedpel =  Clip3 (0, img->max_imgpel_value ,((pixel1 + pixel2 + lround) >> denom) + offsetBi);
      }
#else
      weightedpel =  Clip3 (0, img->max_imgpel_value ,((pixel1 + pixel2 + lround) >> denom) + offsetBi);
#endif
      bi_diff = (*cur_line++)  - weightedpel;
      mcost += byte_abs[bi_diff];
      if (mcost >= min_mcost) break;
    }    
    
    if (mcost >= min_mcost) break;
  }
  return mcost;
}

/*!
************************************************************************
* \brief
*    FastIntegerPelBlockMotionSearch: fast pixel block motion search 
*    this algrithm is called UMHexagonS(see JVT-D016),which includes 
*    four steps with different kinds of search patterns
* \par Input:
* pel_t**   orig_pic,     // <--  original picture
* int       ref,          // <--  reference frame (0... or -1 (backward))
* int       pic_pix_x,    // <--  absolute x-coordinate of regarded AxB block
* int       pic_pix_y,    // <--  absolute y-coordinate of regarded AxB block
* int       blocktype,    // <--  block type (1-16x16 ... 7-4x4)
* int       pred_mv_x,    // <--  motion vector predictor (x) in sub-pel units
* int       pred_mv_y,    // <--  motion vector predictor (y) in sub-pel units
* int*      mv_x,         //  --> motion vector (x) - in pel units
* int*      mv_y,         //  --> motion vector (y) - in pel units
* int       search_range, // <--  1-d search range in pel units                         
* int       min_mcost,    // <--  minimum motion cost (cost for center or huge value)
* int       lambda_factor // <--  lagrangian parameter for determining motion cost
* \par
* Two macro definitions defined in this program:
* 1. EARLY_TERMINATION: early termination algrithm, refer to JVT-D016.doc
* 2. SEARCH_ONE_PIXEL: search one pixel in search range
* \author
*   Main contributors: (see contributors.h for copyright, address and affiliation details)
*   - Zhibo Chen         <chenzhibo@tsinghua.org.cn>
*   - JianFeng Xu        <fenax@video.mdc.tsinghua.edu.cn>
*   - Xiaozhong Xu       <xxz@video.mdc.tsinghua.edu.cn>
* \date   :
*   2006.1
************************************************************************
*/
int                                     //  ==> minimum motion cost after search
FastIntegerPelBlockMotionSearch  (pel_t**   orig_pic,     // <--  not used
                                  short     ref,          // <--  reference frame (0... or -1 (backward))
                                  int       list,
                                  int       pic_pix_x,    // <--  absolute x-coordinate of regarded AxB block
                                  int       pic_pix_y,    // <--  absolute y-coordinate of regarded AxB block
                                  int       blocktype,    // <--  block type (1-16x16 ... 7-4x4)
                                  short     pred_mv_x,    // <--  motion vector predictor (x) in sub-pel units
                                  short     pred_mv_y,    // <--  motion vector predictor (y) in sub-pel units
                                  short*    mv_x,         //  --> motion vector (x) - in pel units
                                  short*    mv_y,         //  --> motion vector (y) - in pel units
                                  int       search_range, // <--  1-d search range in pel units                         
                                  int       min_mcost,    // <--  minimum motion cost (cost for center or huge value)
                                  int       lambda_factor)       // <--  lagrangian parameter for determining motion cost
{
  int   pos, cand_x, cand_y,  mcost;
  int   list_offset   = ((img->MbaffFrameFlag)&&(img->mb_data[img->current_mb_nr].mb_field))? img->current_mb_nr%2 ? 4 : 2 : 0;
  
  int   mvshift       = 2;                  // motion vector shift for getting sub-pel units
  int   blocksize_y   = input->blc_size[blocktype][1];            // vertical block size
  int   blocksize_x   = input->blc_size[blocktype][0];            // horizontal block size
  int   blocksize_x4  = blocksize_x >> 2;                         // horizontal block size in 4-pel units
  int   pred_x        = (pic_pix_x << mvshift) + pred_mv_x;       // predicted position x (in sub-pel units)
  int   pred_y        = (pic_pix_y << mvshift) + pred_mv_y;       // predicted position y (in sub-pel units)
  int   center_x      = pic_pix_x + *mv_x;                        // center position x (in pel units)
  int   center_y      = pic_pix_y + *mv_y;                        // center position y (in pel units)
  int   best_x = 0, best_y = 0;
  int   search_step,iYMinNow, iXMinNow;
  int   i,m,j; 
  float betaFourth_1,betaFourth_2;
  int  temp_Big_Hexagon_x[16];//  temp for Big_Hexagon_x;
  int  temp_Big_Hexagon_y[16];//  temp for Big_Hexagon_y; 
  short mb_x = pic_pix_x - img->opix_x; 
  short mb_y = pic_pix_y - img->opix_y;
  short pic_pix_x2 = pic_pix_x >> 2;
  short block_x = (mb_x >> 2);
  short block_y = (mb_y >> 2);
  int ET_Thred = Median_Pred_Thd_MB[blocktype];//ET threshold in use
  int   *SAD_prediction = fastme_best_cost[blocktype-1];//multi ref SAD prediction
  //===== Use weighted Reference for ME ====
  
  int  apply_weights = ( (active_pps->weighted_pred_flag && (img->type == P_SLICE || img->type == SP_SLICE)) ||
    (active_pps->weighted_bipred_idc && (img->type == B_SLICE)));  
  height=((img->MbaffFrameFlag)&&(img->mb_data[img->current_mb_nr].mb_field))?img->height/2:img->height;
  ref_pic = (apply_weights && input->UseWeightedReferenceME) ? listX[list+list_offset][ref]->imgY_11_w : listX[list+list_offset][ref]->imgY_11;
  
  
  
  //===== set function for getting reference picture lines =====
  if ((center_x > search_range) && (center_x < img->width -1-search_range-blocksize_x) &&
    (center_y > search_range) && (center_y < height-1-search_range-blocksize_y)   )
  {
    get_ref_line = FastLineX;
  }
  else
  {
    get_ref_line = UMVLineX;
  }
  
  //////allocate memory for search state//////////////////////////
  memset(McostState[0],0,(2*input->search_range+1)*(2*input->search_range+1));
  
  
  //check the center median predictor
  cand_x = center_x ;
  cand_y = center_y ;
  mcost = MV_COST (lambda_factor, mvshift, cand_x, cand_y, pred_x, pred_y);
  mcost = PartCalMad(ref_pic, orig_pic, get_ref_line,blocksize_y,blocksize_x,blocksize_x4,mcost,min_mcost,cand_x,cand_y);
  McostState[search_range][search_range] = 1;
  if (mcost < min_mcost)
  {
    min_mcost = mcost;
    best_x = cand_x;
    best_y = cand_y;
  }
  
  iXMinNow = best_x;
  iYMinNow = best_y;
  for (m = 0; m < 4; m++)
  {   
    cand_x = iXMinNow + Diamond_x[m];
    cand_y = iYMinNow + Diamond_y[m];   
    SEARCH_ONE_PIXEL
  } 
  
  if(center_x != pic_pix_x || center_y != pic_pix_y)
  {
    cand_x = pic_pix_x ;
    cand_y = pic_pix_y ;
    SEARCH_ONE_PIXEL
      
      iXMinNow = best_x;
    iYMinNow = best_y;
    for (m = 0; m < 4; m++)
    {   
      cand_x = iXMinNow + Diamond_x[m];
      cand_y = iYMinNow + Diamond_y[m];   
      SEARCH_ONE_PIXEL
    } 
  }
  /***********************************init process*************************/
  //for multi ref
  if(ref>0 && img->structure == FRAME  && min_mcost > ET_Thred && SAD_prediction[pic_pix_x2]<Multi_Ref_Thd_MB[blocktype])
    goto terminate_step;
  
  //ET_Thd1: early termination for low motion case
  if( min_mcost < ET_Thred)  
  {
    goto terminate_step;
  }
  else // hybrid search for main search loop
  {
    /****************************(MV and SAD prediction)********************************/
    setup_FME(ref, list, block_y, block_x, blocktype, img->all_mv );
    ET_Thred = Big_Hexagon_Thd_MB[blocktype];  // ET_Thd2: early termination Threshold for strong motion
    
    
    
    // Threshold defined for EARLY_TERMINATION 
    if (pred_SAD == 0) 
    {
      betaFourth_1=0;
      betaFourth_2=0;
    }
    else
    {
      betaFourth_1 = Bsize[blocktype]/(pred_SAD*pred_SAD)-AlphaFourth_1[blocktype];
      betaFourth_2 = Bsize[blocktype]/(pred_SAD*pred_SAD)-AlphaFourth_2[blocktype];
      
    }  
    /*********************************************end of init ***********************************************/
  }  
  // first_step: initial start point prediction 
  
  if(blocktype>1)
  {
    cand_x = pic_pix_x + (pred_MV_uplayer[0]/4);
    cand_y = pic_pix_y + (pred_MV_uplayer[1]/4);
    SEARCH_ONE_PIXEL
  } 
  
  
  //prediciton using mV of last ref moiton vector
  if(pred_MV_ref_flag == 1)          //Notes: for interlace case, ref==1 should be added
  {
    cand_x = pic_pix_x + (pred_MV_ref[0]/4);
    cand_y = pic_pix_y + (pred_MV_ref[1]/4);
    SEARCH_ONE_PIXEL
  }
  //small local search
  iXMinNow = best_x;
  iYMinNow = best_y;
  for (m = 0; m < 4; m++)
  {   
    cand_x = iXMinNow + Diamond_x[m];
    cand_y = iYMinNow + Diamond_y[m];   
    SEARCH_ONE_PIXEL
  } 
  
  //early termination alogrithm, refer to JVT-G016
  EARLY_TERMINATION
    
    if(blocktype>6)
      goto fourth_1_step;
    else
      goto sec_step;
    
sec_step: //Unsymmetrical-cross search 
    iXMinNow = best_x;
    iYMinNow = best_y;
    
    for(i = 1; i < search_range; i+=2)
    {
      search_step = i;
      cand_x = iXMinNow + search_step;
      cand_y = iYMinNow ;
      SEARCH_ONE_PIXEL    
        cand_x = iXMinNow - search_step;
      cand_y = iYMinNow ;
      SEARCH_ONE_PIXEL
    }
    for(i = 1; i < (search_range/2);i+=2)
    {
      search_step = i;
      cand_x = iXMinNow ;
      cand_y = iYMinNow + search_step;
      SEARCH_ONE_PIXEL
        cand_x = iXMinNow ;
      cand_y = iYMinNow - search_step;
      SEARCH_ONE_PIXEL
    }
    
    
    //early termination alogrithm, refer to JVT-G016
    EARLY_TERMINATION
      
      iXMinNow = best_x;
    iYMinNow = best_y;
    
    //third_step:    // Uneven Multi-Hexagon-grid Search 
    //sub step 1: 5x5 squre search
    for(pos=1;pos<25;pos++)
    {
      cand_x = iXMinNow + spiral_search_x[pos];
      cand_y = iYMinNow + spiral_search_y[pos];
      SEARCH_ONE_PIXEL
    }
    
    //early termination alogrithm, refer to JVT-G016
    EARLY_TERMINATION
      
      //sub step 2:  Multi-Hexagon-grid search
      memcpy(temp_Big_Hexagon_x,Big_Hexagon_x,64);
    memcpy(temp_Big_Hexagon_y,Big_Hexagon_y,64);      
    for(i=1;i<=(search_range/4); i++)
    {
      
      for (m = 0; m < 16; m++)
      {
        cand_x = iXMinNow + temp_Big_Hexagon_x[m];
        cand_y = iYMinNow + temp_Big_Hexagon_y[m];
        temp_Big_Hexagon_x[m] += Big_Hexagon_x[m];
        temp_Big_Hexagon_y[m] += Big_Hexagon_y[m];  
        
        SEARCH_ONE_PIXEL
      }
      // ET_Thd2: early termination Threshold for strong motion
      if(min_mcost < ET_Thred)
      {
        goto terminate_step;
      }

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -