source: SHVCSoftware/branches/SHM-4.1-dev/source/Lib/TLibEncoder/TEncSearch.cpp @ 982

Last change on this file since 982 was 532, checked in by seregin, 11 years ago

update to HM-12.1 base

  • Property svn:eol-style set to native
File size: 239.1 KB
Line 
1/* The copyright in this software is being made available under the BSD
2 * License, included below. This software may be subject to other third party
3 * and contributor rights, including patent rights, and no such rights are
4 * granted under this license. 
5 *
6 * Copyright (c) 2010-2013, ITU/ISO/IEC
7 * All rights reserved.
8 *
9 * Redistribution and use in source and binary forms, with or without
10 * modification, are permitted provided that the following conditions are met:
11 *
12 *  * Redistributions of source code must retain the above copyright notice,
13 *    this list of conditions and the following disclaimer.
14 *  * Redistributions in binary form must reproduce the above copyright notice,
15 *    this list of conditions and the following disclaimer in the documentation
16 *    and/or other materials provided with the distribution.
17 *  * Neither the name of the ITU/ISO/IEC nor the names of its contributors may
18 *    be used to endorse or promote products derived from this software without
19 *    specific prior written permission.
20 *
21 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
22 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
23 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
24 * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS
25 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
26 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
27 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
28 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
29 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
30 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
31 * THE POSSIBILITY OF SUCH DAMAGE.
32 */
33
34/** \file     TEncSearch.cpp
35 \brief    encoder search class
36 */
37
38#include "TLibCommon/TypeDef.h"
39#include "TLibCommon/TComRom.h"
40#include "TLibCommon/TComMotionInfo.h"
41#include "TEncSearch.h"
42#include <math.h>
43
44//! \ingroup TLibEncoder
45//! \{
46
47static const TComMv s_acMvRefineH[9] =
48{
49  TComMv(  0,  0 ), // 0
50  TComMv(  0, -1 ), // 1
51  TComMv(  0,  1 ), // 2
52  TComMv( -1,  0 ), // 3
53  TComMv(  1,  0 ), // 4
54  TComMv( -1, -1 ), // 5
55  TComMv(  1, -1 ), // 6
56  TComMv( -1,  1 ), // 7
57  TComMv(  1,  1 )  // 8
58};
59
60static const TComMv s_acMvRefineQ[9] =
61{
62  TComMv(  0,  0 ), // 0
63  TComMv(  0, -1 ), // 1
64  TComMv(  0,  1 ), // 2
65  TComMv( -1, -1 ), // 5
66  TComMv(  1, -1 ), // 6
67  TComMv( -1,  0 ), // 3
68  TComMv(  1,  0 ), // 4
69  TComMv( -1,  1 ), // 7
70  TComMv(  1,  1 )  // 8
71};
72
73static const UInt s_auiDFilter[9] =
74{
75  0, 1, 0,
76  2, 3, 2,
77  0, 1, 0
78};
79
80TEncSearch::TEncSearch()
81{
82  m_ppcQTTempCoeffY  = NULL;
83  m_ppcQTTempCoeffCb = NULL;
84  m_ppcQTTempCoeffCr = NULL;
85  m_pcQTTempCoeffY   = NULL;
86  m_pcQTTempCoeffCb  = NULL;
87  m_pcQTTempCoeffCr  = NULL;
88#if ADAPTIVE_QP_SELECTION
89  m_ppcQTTempArlCoeffY  = NULL;
90  m_ppcQTTempArlCoeffCb = NULL;
91  m_ppcQTTempArlCoeffCr = NULL;
92  m_pcQTTempArlCoeffY   = NULL;
93  m_pcQTTempArlCoeffCb  = NULL;
94  m_pcQTTempArlCoeffCr  = NULL;
95#endif
96  m_puhQTTempTrIdx   = NULL;
97  m_puhQTTempCbf[0] = m_puhQTTempCbf[1] = m_puhQTTempCbf[2] = NULL;
98  m_pcQTTempTComYuv  = NULL;
99  m_pcEncCfg = NULL;
100  m_pcEntropyCoder = NULL;
101  m_pTempPel = NULL;
102  m_pSharedPredTransformSkip[0] = m_pSharedPredTransformSkip[1] = m_pSharedPredTransformSkip[2] = NULL;
103  m_pcQTTempTUCoeffY   = NULL;
104  m_pcQTTempTUCoeffCb  = NULL;
105  m_pcQTTempTUCoeffCr  = NULL;
106#if ADAPTIVE_QP_SELECTION
107  m_ppcQTTempTUArlCoeffY  = NULL;
108  m_ppcQTTempTUArlCoeffCb = NULL;
109  m_ppcQTTempTUArlCoeffCr = NULL;
110#endif
111  m_puhQTTempTransformSkipFlag[0] = NULL;
112  m_puhQTTempTransformSkipFlag[1] = NULL;
113  m_puhQTTempTransformSkipFlag[2] = NULL;
114  setWpScalingDistParam( NULL, -1, REF_PIC_LIST_X );
115}
116
117TEncSearch::~TEncSearch()
118{
119  if ( m_pTempPel )
120  {
121    delete [] m_pTempPel;
122    m_pTempPel = NULL;
123  }
124 
125  if ( m_pcEncCfg )
126  {
127    const UInt uiNumLayersAllocated = m_pcEncCfg->getQuadtreeTULog2MaxSize()-m_pcEncCfg->getQuadtreeTULog2MinSize()+1;
128    for( UInt ui = 0; ui < uiNumLayersAllocated; ++ui )
129    {
130      delete[] m_ppcQTTempCoeffY[ui];
131      delete[] m_ppcQTTempCoeffCb[ui];
132      delete[] m_ppcQTTempCoeffCr[ui];
133#if ADAPTIVE_QP_SELECTION
134      delete[] m_ppcQTTempArlCoeffY[ui];
135      delete[] m_ppcQTTempArlCoeffCb[ui];
136      delete[] m_ppcQTTempArlCoeffCr[ui];
137#endif
138      m_pcQTTempTComYuv[ui].destroy();
139    }
140  }
141  delete[] m_ppcQTTempCoeffY;
142  delete[] m_ppcQTTempCoeffCb;
143  delete[] m_ppcQTTempCoeffCr;
144  delete[] m_pcQTTempCoeffY;
145  delete[] m_pcQTTempCoeffCb;
146  delete[] m_pcQTTempCoeffCr;
147#if ADAPTIVE_QP_SELECTION
148  delete[] m_ppcQTTempArlCoeffY;
149  delete[] m_ppcQTTempArlCoeffCb;
150  delete[] m_ppcQTTempArlCoeffCr;
151  delete[] m_pcQTTempArlCoeffY;
152  delete[] m_pcQTTempArlCoeffCb;
153  delete[] m_pcQTTempArlCoeffCr;
154#endif
155  delete[] m_puhQTTempTrIdx;
156  delete[] m_puhQTTempCbf[0];
157  delete[] m_puhQTTempCbf[1];
158  delete[] m_puhQTTempCbf[2];
159  delete[] m_pcQTTempTComYuv;
160  delete[] m_pSharedPredTransformSkip[0];
161  delete[] m_pSharedPredTransformSkip[1];
162  delete[] m_pSharedPredTransformSkip[2];
163  delete[] m_pcQTTempTUCoeffY;
164  delete[] m_pcQTTempTUCoeffCb;
165  delete[] m_pcQTTempTUCoeffCr;
166#if ADAPTIVE_QP_SELECTION
167  delete[] m_ppcQTTempTUArlCoeffY;
168  delete[] m_ppcQTTempTUArlCoeffCb;
169  delete[] m_ppcQTTempTUArlCoeffCr;
170#endif
171  delete[] m_puhQTTempTransformSkipFlag[0];
172  delete[] m_puhQTTempTransformSkipFlag[1];
173  delete[] m_puhQTTempTransformSkipFlag[2];
174  m_pcQTTempTransformSkipTComYuv.destroy();
175  m_tmpYuvPred.destroy();
176}
177
178void TEncSearch::init(TEncCfg*      pcEncCfg,
179                      TComTrQuant*  pcTrQuant,
180                      Int           iSearchRange,
181                      Int           bipredSearchRange,
182                      Int           iFastSearch,
183                      Int           iMaxDeltaQP,
184                      TEncEntropy*  pcEntropyCoder,
185                      TComRdCost*   pcRdCost,
186                      TEncSbac*** pppcRDSbacCoder,
187                      TEncSbac*   pcRDGoOnSbacCoder
188                      )
189{
190  m_pcEncCfg             = pcEncCfg;
191  m_pcTrQuant            = pcTrQuant;
192  m_iSearchRange         = iSearchRange;
193  m_bipredSearchRange    = bipredSearchRange;
194  m_iFastSearch          = iFastSearch;
195  m_iMaxDeltaQP          = iMaxDeltaQP;
196  m_pcEntropyCoder       = pcEntropyCoder;
197  m_pcRdCost             = pcRdCost;
198 
199  m_pppcRDSbacCoder     = pppcRDSbacCoder;
200  m_pcRDGoOnSbacCoder   = pcRDGoOnSbacCoder;
201 
202  m_bUseSBACRD          = pppcRDSbacCoder ? true : false;
203 
204  for (Int iDir = 0; iDir < 2; iDir++)
205  {
206    for (Int iRefIdx = 0; iRefIdx < 33; iRefIdx++)
207    {
208      m_aaiAdaptSR[iDir][iRefIdx] = iSearchRange;
209    }
210  }
211 
212  m_puiDFilter = s_auiDFilter + 4;
213 
214  // initialize motion cost
215#if !FIX203
216  m_pcRdCost->initRateDistortionModel( m_iSearchRange << 2 );
217#endif
218 
219  for( Int iNum = 0; iNum < AMVP_MAX_NUM_CANDS+1; iNum++)
220  {
221    for( Int iIdx = 0; iIdx < AMVP_MAX_NUM_CANDS; iIdx++)
222    {
223      if (iIdx < iNum)
224        m_auiMVPIdxCost[iIdx][iNum] = xGetMvpIdxBits(iIdx, iNum);
225      else
226        m_auiMVPIdxCost[iIdx][iNum] = MAX_INT;
227    }
228  }
229 
230  initTempBuff();
231 
232  m_pTempPel = new Pel[g_uiMaxCUWidth*g_uiMaxCUHeight];
233 
234  const UInt uiNumLayersToAllocate = pcEncCfg->getQuadtreeTULog2MaxSize()-pcEncCfg->getQuadtreeTULog2MinSize()+1;
235  m_ppcQTTempCoeffY  = new TCoeff*[uiNumLayersToAllocate];
236  m_ppcQTTempCoeffCb = new TCoeff*[uiNumLayersToAllocate];
237  m_ppcQTTempCoeffCr = new TCoeff*[uiNumLayersToAllocate];
238  m_pcQTTempCoeffY   = new TCoeff [g_uiMaxCUWidth*g_uiMaxCUHeight   ];
239  m_pcQTTempCoeffCb  = new TCoeff [g_uiMaxCUWidth*g_uiMaxCUHeight>>2];
240  m_pcQTTempCoeffCr  = new TCoeff [g_uiMaxCUWidth*g_uiMaxCUHeight>>2];
241#if ADAPTIVE_QP_SELECTION
242  m_ppcQTTempArlCoeffY  = new Int*[uiNumLayersToAllocate];
243  m_ppcQTTempArlCoeffCb = new Int*[uiNumLayersToAllocate];
244  m_ppcQTTempArlCoeffCr = new Int*[uiNumLayersToAllocate];
245  m_pcQTTempArlCoeffY   = new Int [g_uiMaxCUWidth*g_uiMaxCUHeight   ];
246  m_pcQTTempArlCoeffCb  = new Int [g_uiMaxCUWidth*g_uiMaxCUHeight>>2];
247  m_pcQTTempArlCoeffCr  = new Int [g_uiMaxCUWidth*g_uiMaxCUHeight>>2];
248#endif
249 
250  const UInt uiNumPartitions = 1<<(g_uiMaxCUDepth<<1);
251  m_puhQTTempTrIdx   = new UChar  [uiNumPartitions];
252  m_puhQTTempCbf[0]  = new UChar  [uiNumPartitions];
253  m_puhQTTempCbf[1]  = new UChar  [uiNumPartitions];
254  m_puhQTTempCbf[2]  = new UChar  [uiNumPartitions];
255  m_pcQTTempTComYuv  = new TComYuv[uiNumLayersToAllocate];
256  for( UInt ui = 0; ui < uiNumLayersToAllocate; ++ui )
257  {
258    m_ppcQTTempCoeffY[ui]  = new TCoeff[g_uiMaxCUWidth*g_uiMaxCUHeight   ];
259    m_ppcQTTempCoeffCb[ui] = new TCoeff[g_uiMaxCUWidth*g_uiMaxCUHeight>>2];
260    m_ppcQTTempCoeffCr[ui] = new TCoeff[g_uiMaxCUWidth*g_uiMaxCUHeight>>2];
261#if ADAPTIVE_QP_SELECTION
262    m_ppcQTTempArlCoeffY[ui]  = new Int[g_uiMaxCUWidth*g_uiMaxCUHeight   ];
263    m_ppcQTTempArlCoeffCb[ui] = new Int[g_uiMaxCUWidth*g_uiMaxCUHeight>>2];
264    m_ppcQTTempArlCoeffCr[ui] = new Int[g_uiMaxCUWidth*g_uiMaxCUHeight>>2];
265#endif
266    m_pcQTTempTComYuv[ui].create( g_uiMaxCUWidth, g_uiMaxCUHeight );
267  }
268  m_pSharedPredTransformSkip[0] = new Pel[MAX_TS_WIDTH*MAX_TS_HEIGHT];
269  m_pSharedPredTransformSkip[1] = new Pel[MAX_TS_WIDTH*MAX_TS_HEIGHT];
270  m_pSharedPredTransformSkip[2] = new Pel[MAX_TS_WIDTH*MAX_TS_HEIGHT];
271  m_pcQTTempTUCoeffY  = new TCoeff[MAX_TS_WIDTH*MAX_TS_HEIGHT];
272  m_pcQTTempTUCoeffCb = new TCoeff[MAX_TS_WIDTH*MAX_TS_HEIGHT];
273  m_pcQTTempTUCoeffCr = new TCoeff[MAX_TS_WIDTH*MAX_TS_HEIGHT];
274#if ADAPTIVE_QP_SELECTION
275  m_ppcQTTempTUArlCoeffY  = new Int[MAX_TS_WIDTH*MAX_TS_HEIGHT];
276  m_ppcQTTempTUArlCoeffCb = new Int[MAX_TS_WIDTH*MAX_TS_HEIGHT];
277  m_ppcQTTempTUArlCoeffCr = new Int[MAX_TS_WIDTH*MAX_TS_HEIGHT];
278#endif
279  m_pcQTTempTransformSkipTComYuv.create( g_uiMaxCUWidth, g_uiMaxCUHeight );
280
281  m_puhQTTempTransformSkipFlag[0] = new UChar  [uiNumPartitions];
282  m_puhQTTempTransformSkipFlag[1] = new UChar  [uiNumPartitions];
283  m_puhQTTempTransformSkipFlag[2] = new UChar  [uiNumPartitions];
284  m_tmpYuvPred.create(MAX_CU_SIZE, MAX_CU_SIZE);
285}
286
287#if FASTME_SMOOTHER_MV
288#define FIRSTSEARCHSTOP     1
289#else
290#define FIRSTSEARCHSTOP     0
291#endif
292
293#define TZ_SEARCH_CONFIGURATION                                                                                 \
294const Int  iRaster                  = 5;  /* TZ soll von aussen ?ergeben werden */                            \
295const Bool bTestOtherPredictedMV    = 0;                                                                      \
296const Bool bTestZeroVector          = 1;                                                                      \
297const Bool bTestZeroVectorStart     = 0;                                                                      \
298const Bool bTestZeroVectorStop      = 0;                                                                      \
299const Bool bFirstSearchDiamond      = 1;  /* 1 = xTZ8PointDiamondSearch   0 = xTZ8PointSquareSearch */        \
300const Bool bFirstSearchStop         = FIRSTSEARCHSTOP;                                                        \
301const UInt uiFirstSearchRounds      = 3;  /* first search stop X rounds after best match (must be >=1) */     \
302const Bool bEnableRasterSearch      = 1;                                                                      \
303const Bool bAlwaysRasterSearch      = 0;  /* ===== 1: BETTER but factor 2 slower ===== */                     \
304const Bool bRasterRefinementEnable  = 0;  /* enable either raster refinement or star refinement */            \
305const Bool bRasterRefinementDiamond = 0;  /* 1 = xTZ8PointDiamondSearch   0 = xTZ8PointSquareSearch */        \
306const Bool bStarRefinementEnable    = 1;  /* enable either star refinement or raster refinement */            \
307const Bool bStarRefinementDiamond   = 1;  /* 1 = xTZ8PointDiamondSearch   0 = xTZ8PointSquareSearch */        \
308const Bool bStarRefinementStop      = 0;                                                                      \
309const UInt uiStarRefinementRounds   = 2;  /* star refinement stop X rounds after best match (must be >=1) */  \
310
311
312__inline Void TEncSearch::xTZSearchHelp( TComPattern* pcPatternKey, IntTZSearchStruct& rcStruct, const Int iSearchX, const Int iSearchY, const UChar ucPointNr, const UInt uiDistance )
313{
314  UInt  uiSad;
315 
316  Pel*  piRefSrch;
317 
318  piRefSrch = rcStruct.piRefY + iSearchY * rcStruct.iYStride + iSearchX;
319 
320  //-- jclee for using the SAD function pointer
321  m_pcRdCost->setDistParam( pcPatternKey, piRefSrch, rcStruct.iYStride,  m_cDistParam );
322 
323  // fast encoder decision: use subsampled SAD when rows > 8 for integer ME
324  if ( m_pcEncCfg->getUseFastEnc() )
325  {
326    if ( m_cDistParam.iRows > 8 )
327    {
328      m_cDistParam.iSubShift = 1;
329    }
330  }
331
332  setDistParamComp(0);  // Y component
333
334  // distortion
335  m_cDistParam.bitDepth = g_bitDepthY;
336  uiSad = m_cDistParam.DistFunc( &m_cDistParam );
337 
338  // motion cost
339  uiSad += m_pcRdCost->getCost( iSearchX, iSearchY );
340 
341  if( uiSad < rcStruct.uiBestSad )
342  {
343    rcStruct.uiBestSad      = uiSad;
344    rcStruct.iBestX         = iSearchX;
345    rcStruct.iBestY         = iSearchY;
346    rcStruct.uiBestDistance = uiDistance;
347    rcStruct.uiBestRound    = 0;
348    rcStruct.ucPointNr      = ucPointNr;
349  }
350}
351
352__inline Void TEncSearch::xTZ2PointSearch( TComPattern* pcPatternKey, IntTZSearchStruct& rcStruct, TComMv* pcMvSrchRngLT, TComMv* pcMvSrchRngRB )
353{
354  Int   iSrchRngHorLeft   = pcMvSrchRngLT->getHor();
355  Int   iSrchRngHorRight  = pcMvSrchRngRB->getHor();
356  Int   iSrchRngVerTop    = pcMvSrchRngLT->getVer();
357  Int   iSrchRngVerBottom = pcMvSrchRngRB->getVer();
358 
359  // 2 point search,                   //   1 2 3
360  // check only the 2 untested points  //   4 0 5
361  // around the start point            //   6 7 8
362  Int iStartX = rcStruct.iBestX;
363  Int iStartY = rcStruct.iBestY;
364  switch( rcStruct.ucPointNr )
365  {
366    case 1:
367    {
368      if ( (iStartX - 1) >= iSrchRngHorLeft )
369      {
370        xTZSearchHelp( pcPatternKey, rcStruct, iStartX - 1, iStartY, 0, 2 );
371      }
372      if ( (iStartY - 1) >= iSrchRngVerTop )
373      {
374        xTZSearchHelp( pcPatternKey, rcStruct, iStartX, iStartY - 1, 0, 2 );
375      }
376    }
377      break;
378    case 2:
379    {
380      if ( (iStartY - 1) >= iSrchRngVerTop )
381      {
382        if ( (iStartX - 1) >= iSrchRngHorLeft )
383        {
384          xTZSearchHelp( pcPatternKey, rcStruct, iStartX - 1, iStartY - 1, 0, 2 );
385        }
386        if ( (iStartX + 1) <= iSrchRngHorRight )
387        {
388          xTZSearchHelp( pcPatternKey, rcStruct, iStartX + 1, iStartY - 1, 0, 2 );
389        }
390      }
391    }
392      break;
393    case 3:
394    {
395      if ( (iStartY - 1) >= iSrchRngVerTop )
396      {
397        xTZSearchHelp( pcPatternKey, rcStruct, iStartX, iStartY - 1, 0, 2 );
398      }
399      if ( (iStartX + 1) <= iSrchRngHorRight )
400      {
401        xTZSearchHelp( pcPatternKey, rcStruct, iStartX + 1, iStartY, 0, 2 );
402      }
403    }
404      break;
405    case 4:
406    {
407      if ( (iStartX - 1) >= iSrchRngHorLeft )
408      {
409        if ( (iStartY + 1) <= iSrchRngVerBottom )
410        {
411          xTZSearchHelp( pcPatternKey, rcStruct, iStartX - 1, iStartY + 1, 0, 2 );
412        }
413        if ( (iStartY - 1) >= iSrchRngVerTop )
414        {
415          xTZSearchHelp( pcPatternKey, rcStruct, iStartX - 1, iStartY - 1, 0, 2 );
416        }
417      }
418    }
419      break;
420    case 5:
421    {
422      if ( (iStartX + 1) <= iSrchRngHorRight )
423      {
424        if ( (iStartY - 1) >= iSrchRngVerTop )
425        {
426          xTZSearchHelp( pcPatternKey, rcStruct, iStartX + 1, iStartY - 1, 0, 2 );
427        }
428        if ( (iStartY + 1) <= iSrchRngVerBottom )
429        {
430          xTZSearchHelp( pcPatternKey, rcStruct, iStartX + 1, iStartY + 1, 0, 2 );
431        }
432      }
433    }
434      break;
435    case 6:
436    {
437      if ( (iStartX - 1) >= iSrchRngHorLeft )
438      {
439        xTZSearchHelp( pcPatternKey, rcStruct, iStartX - 1, iStartY , 0, 2 );
440      }
441      if ( (iStartY + 1) <= iSrchRngVerBottom )
442      {
443        xTZSearchHelp( pcPatternKey, rcStruct, iStartX, iStartY + 1, 0, 2 );
444      }
445    }
446      break;
447    case 7:
448    {
449      if ( (iStartY + 1) <= iSrchRngVerBottom )
450      {
451        if ( (iStartX - 1) >= iSrchRngHorLeft )
452        {
453          xTZSearchHelp( pcPatternKey, rcStruct, iStartX - 1, iStartY + 1, 0, 2 );
454        }
455        if ( (iStartX + 1) <= iSrchRngHorRight )
456        {
457          xTZSearchHelp( pcPatternKey, rcStruct, iStartX + 1, iStartY + 1, 0, 2 );
458        }
459      }
460    }
461      break;
462    case 8:
463    {
464      if ( (iStartX + 1) <= iSrchRngHorRight )
465      {
466        xTZSearchHelp( pcPatternKey, rcStruct, iStartX + 1, iStartY, 0, 2 );
467      }
468      if ( (iStartY + 1) <= iSrchRngVerBottom )
469      {
470        xTZSearchHelp( pcPatternKey, rcStruct, iStartX, iStartY + 1, 0, 2 );
471      }
472    }
473      break;
474    default:
475    {
476      assert( false );
477    }
478      break;
479  } // switch( rcStruct.ucPointNr )
480}
481
482__inline Void TEncSearch::xTZ8PointSquareSearch( TComPattern* pcPatternKey, IntTZSearchStruct& rcStruct, TComMv* pcMvSrchRngLT, TComMv* pcMvSrchRngRB, const Int iStartX, const Int iStartY, const Int iDist )
483{
484  Int   iSrchRngHorLeft   = pcMvSrchRngLT->getHor();
485  Int   iSrchRngHorRight  = pcMvSrchRngRB->getHor();
486  Int   iSrchRngVerTop    = pcMvSrchRngLT->getVer();
487  Int   iSrchRngVerBottom = pcMvSrchRngRB->getVer();
488 
489  // 8 point search,                   //   1 2 3
490  // search around the start point     //   4 0 5
491  // with the required  distance       //   6 7 8
492  assert( iDist != 0 );
493  const Int iTop        = iStartY - iDist;
494  const Int iBottom     = iStartY + iDist;
495  const Int iLeft       = iStartX - iDist;
496  const Int iRight      = iStartX + iDist;
497  rcStruct.uiBestRound += 1;
498 
499  if ( iTop >= iSrchRngVerTop ) // check top
500  {
501    if ( iLeft >= iSrchRngHorLeft ) // check top left
502    {
503      xTZSearchHelp( pcPatternKey, rcStruct, iLeft, iTop, 1, iDist );
504    }
505    // top middle
506    xTZSearchHelp( pcPatternKey, rcStruct, iStartX, iTop, 2, iDist );
507   
508    if ( iRight <= iSrchRngHorRight ) // check top right
509    {
510      xTZSearchHelp( pcPatternKey, rcStruct, iRight, iTop, 3, iDist );
511    }
512  } // check top
513  if ( iLeft >= iSrchRngHorLeft ) // check middle left
514  {
515    xTZSearchHelp( pcPatternKey, rcStruct, iLeft, iStartY, 4, iDist );
516  }
517  if ( iRight <= iSrchRngHorRight ) // check middle right
518  {
519    xTZSearchHelp( pcPatternKey, rcStruct, iRight, iStartY, 5, iDist );
520  }
521  if ( iBottom <= iSrchRngVerBottom ) // check bottom
522  {
523    if ( iLeft >= iSrchRngHorLeft ) // check bottom left
524    {
525      xTZSearchHelp( pcPatternKey, rcStruct, iLeft, iBottom, 6, iDist );
526    }
527    // check bottom middle
528    xTZSearchHelp( pcPatternKey, rcStruct, iStartX, iBottom, 7, iDist );
529   
530    if ( iRight <= iSrchRngHorRight ) // check bottom right
531    {
532      xTZSearchHelp( pcPatternKey, rcStruct, iRight, iBottom, 8, iDist );
533    }
534  } // check bottom
535}
536
537__inline Void TEncSearch::xTZ8PointDiamondSearch( TComPattern* pcPatternKey, IntTZSearchStruct& rcStruct, TComMv* pcMvSrchRngLT, TComMv* pcMvSrchRngRB, const Int iStartX, const Int iStartY, const Int iDist )
538{
539  Int   iSrchRngHorLeft   = pcMvSrchRngLT->getHor();
540  Int   iSrchRngHorRight  = pcMvSrchRngRB->getHor();
541  Int   iSrchRngVerTop    = pcMvSrchRngLT->getVer();
542  Int   iSrchRngVerBottom = pcMvSrchRngRB->getVer();
543 
544  // 8 point search,                   //   1 2 3
545  // search around the start point     //   4 0 5
546  // with the required  distance       //   6 7 8
547  assert ( iDist != 0 );
548  const Int iTop        = iStartY - iDist;
549  const Int iBottom     = iStartY + iDist;
550  const Int iLeft       = iStartX - iDist;
551  const Int iRight      = iStartX + iDist;
552  rcStruct.uiBestRound += 1;
553 
554  if ( iDist == 1 ) // iDist == 1
555  {
556    if ( iTop >= iSrchRngVerTop ) // check top
557    {
558      xTZSearchHelp( pcPatternKey, rcStruct, iStartX, iTop, 2, iDist );
559    }
560    if ( iLeft >= iSrchRngHorLeft ) // check middle left
561    {
562      xTZSearchHelp( pcPatternKey, rcStruct, iLeft, iStartY, 4, iDist );
563    }
564    if ( iRight <= iSrchRngHorRight ) // check middle right
565    {
566      xTZSearchHelp( pcPatternKey, rcStruct, iRight, iStartY, 5, iDist );
567    }
568    if ( iBottom <= iSrchRngVerBottom ) // check bottom
569    {
570      xTZSearchHelp( pcPatternKey, rcStruct, iStartX, iBottom, 7, iDist );
571    }
572  }
573  else // if (iDist != 1)
574  {
575    if ( iDist <= 8 )
576    {
577      const Int iTop_2      = iStartY - (iDist>>1);
578      const Int iBottom_2   = iStartY + (iDist>>1);
579      const Int iLeft_2     = iStartX - (iDist>>1);
580      const Int iRight_2    = iStartX + (iDist>>1);
581     
582      if (  iTop >= iSrchRngVerTop && iLeft >= iSrchRngHorLeft &&
583          iRight <= iSrchRngHorRight && iBottom <= iSrchRngVerBottom ) // check border
584      {
585        xTZSearchHelp( pcPatternKey, rcStruct, iStartX,  iTop,      2, iDist    );
586        xTZSearchHelp( pcPatternKey, rcStruct, iLeft_2,  iTop_2,    1, iDist>>1 );
587        xTZSearchHelp( pcPatternKey, rcStruct, iRight_2, iTop_2,    3, iDist>>1 );
588        xTZSearchHelp( pcPatternKey, rcStruct, iLeft,    iStartY,   4, iDist    );
589        xTZSearchHelp( pcPatternKey, rcStruct, iRight,   iStartY,   5, iDist    );
590        xTZSearchHelp( pcPatternKey, rcStruct, iLeft_2,  iBottom_2, 6, iDist>>1 );
591        xTZSearchHelp( pcPatternKey, rcStruct, iRight_2, iBottom_2, 8, iDist>>1 );
592        xTZSearchHelp( pcPatternKey, rcStruct, iStartX,  iBottom,   7, iDist    );
593      }
594      else // check border
595      {
596        if ( iTop >= iSrchRngVerTop ) // check top
597        {
598          xTZSearchHelp( pcPatternKey, rcStruct, iStartX, iTop, 2, iDist );
599        }
600        if ( iTop_2 >= iSrchRngVerTop ) // check half top
601        {
602          if ( iLeft_2 >= iSrchRngHorLeft ) // check half left
603          {
604            xTZSearchHelp( pcPatternKey, rcStruct, iLeft_2, iTop_2, 1, (iDist>>1) );
605          }
606          if ( iRight_2 <= iSrchRngHorRight ) // check half right
607          {
608            xTZSearchHelp( pcPatternKey, rcStruct, iRight_2, iTop_2, 3, (iDist>>1) );
609          }
610        } // check half top
611        if ( iLeft >= iSrchRngHorLeft ) // check left
612        {
613          xTZSearchHelp( pcPatternKey, rcStruct, iLeft, iStartY, 4, iDist );
614        }
615        if ( iRight <= iSrchRngHorRight ) // check right
616        {
617          xTZSearchHelp( pcPatternKey, rcStruct, iRight, iStartY, 5, iDist );
618        }
619        if ( iBottom_2 <= iSrchRngVerBottom ) // check half bottom
620        {
621          if ( iLeft_2 >= iSrchRngHorLeft ) // check half left
622          {
623            xTZSearchHelp( pcPatternKey, rcStruct, iLeft_2, iBottom_2, 6, (iDist>>1) );
624          }
625          if ( iRight_2 <= iSrchRngHorRight ) // check half right
626          {
627            xTZSearchHelp( pcPatternKey, rcStruct, iRight_2, iBottom_2, 8, (iDist>>1) );
628          }
629        } // check half bottom
630        if ( iBottom <= iSrchRngVerBottom ) // check bottom
631        {
632          xTZSearchHelp( pcPatternKey, rcStruct, iStartX, iBottom, 7, iDist );
633        }
634      } // check border
635    }
636    else // iDist > 8
637    {
638      if ( iTop >= iSrchRngVerTop && iLeft >= iSrchRngHorLeft &&
639          iRight <= iSrchRngHorRight && iBottom <= iSrchRngVerBottom ) // check border
640      {
641        xTZSearchHelp( pcPatternKey, rcStruct, iStartX, iTop,    0, iDist );
642        xTZSearchHelp( pcPatternKey, rcStruct, iLeft,   iStartY, 0, iDist );
643        xTZSearchHelp( pcPatternKey, rcStruct, iRight,  iStartY, 0, iDist );
644        xTZSearchHelp( pcPatternKey, rcStruct, iStartX, iBottom, 0, iDist );
645        for ( Int index = 1; index < 4; index++ )
646        {
647          Int iPosYT = iTop    + ((iDist>>2) * index);
648          Int iPosYB = iBottom - ((iDist>>2) * index);
649          Int iPosXL = iStartX - ((iDist>>2) * index);
650          Int iPosXR = iStartX + ((iDist>>2) * index);
651          xTZSearchHelp( pcPatternKey, rcStruct, iPosXL, iPosYT, 0, iDist );
652          xTZSearchHelp( pcPatternKey, rcStruct, iPosXR, iPosYT, 0, iDist );
653          xTZSearchHelp( pcPatternKey, rcStruct, iPosXL, iPosYB, 0, iDist );
654          xTZSearchHelp( pcPatternKey, rcStruct, iPosXR, iPosYB, 0, iDist );
655        }
656      }
657      else // check border
658      {
659        if ( iTop >= iSrchRngVerTop ) // check top
660        {
661          xTZSearchHelp( pcPatternKey, rcStruct, iStartX, iTop, 0, iDist );
662        }
663        if ( iLeft >= iSrchRngHorLeft ) // check left
664        {
665          xTZSearchHelp( pcPatternKey, rcStruct, iLeft, iStartY, 0, iDist );
666        }
667        if ( iRight <= iSrchRngHorRight ) // check right
668        {
669          xTZSearchHelp( pcPatternKey, rcStruct, iRight, iStartY, 0, iDist );
670        }
671        if ( iBottom <= iSrchRngVerBottom ) // check bottom
672        {
673          xTZSearchHelp( pcPatternKey, rcStruct, iStartX, iBottom, 0, iDist );
674        }
675        for ( Int index = 1; index < 4; index++ )
676        {
677          Int iPosYT = iTop    + ((iDist>>2) * index);
678          Int iPosYB = iBottom - ((iDist>>2) * index);
679          Int iPosXL = iStartX - ((iDist>>2) * index);
680          Int iPosXR = iStartX + ((iDist>>2) * index);
681         
682          if ( iPosYT >= iSrchRngVerTop ) // check top
683          {
684            if ( iPosXL >= iSrchRngHorLeft ) // check left
685            {
686              xTZSearchHelp( pcPatternKey, rcStruct, iPosXL, iPosYT, 0, iDist );
687            }
688            if ( iPosXR <= iSrchRngHorRight ) // check right
689            {
690              xTZSearchHelp( pcPatternKey, rcStruct, iPosXR, iPosYT, 0, iDist );
691            }
692          } // check top
693          if ( iPosYB <= iSrchRngVerBottom ) // check bottom
694          {
695            if ( iPosXL >= iSrchRngHorLeft ) // check left
696            {
697              xTZSearchHelp( pcPatternKey, rcStruct, iPosXL, iPosYB, 0, iDist );
698            }
699            if ( iPosXR <= iSrchRngHorRight ) // check right
700            {
701              xTZSearchHelp( pcPatternKey, rcStruct, iPosXR, iPosYB, 0, iDist );
702            }
703          } // check bottom
704        } // for ...
705      } // check border
706    } // iDist <= 8
707  } // iDist == 1
708}
709
710//<--
711
712UInt TEncSearch::xPatternRefinement( TComPattern* pcPatternKey,
713                                    TComMv baseRefMv,
714                                    Int iFrac, TComMv& rcMvFrac )
715{
716  UInt  uiDist;
717  UInt  uiDistBest  = MAX_UINT;
718  UInt  uiDirecBest = 0;
719 
720  Pel*  piRefPos;
721  Int iRefStride = m_filteredBlock[0][0].getStride();
722  m_pcRdCost->setDistParam( pcPatternKey, m_filteredBlock[0][0].getLumaAddr(), iRefStride, 1, m_cDistParam, m_pcEncCfg->getUseHADME() );
723 
724  const TComMv* pcMvRefine = (iFrac == 2 ? s_acMvRefineH : s_acMvRefineQ);
725 
726  for (UInt i = 0; i < 9; i++)
727  {
728    TComMv cMvTest = pcMvRefine[i];
729    cMvTest += baseRefMv;
730   
731    Int horVal = cMvTest.getHor() * iFrac;
732    Int verVal = cMvTest.getVer() * iFrac;
733    piRefPos = m_filteredBlock[ verVal & 3 ][ horVal & 3 ].getLumaAddr();
734    if ( horVal == 2 && ( verVal & 1 ) == 0 )
735    {
736      piRefPos += 1;
737    }
738    if ( ( horVal & 1 ) == 0 && verVal == 2 )
739    {
740      piRefPos += iRefStride;
741    }
742    cMvTest = pcMvRefine[i];
743    cMvTest += rcMvFrac;
744
745    setDistParamComp(0);  // Y component
746
747    m_cDistParam.pCur = piRefPos;
748    m_cDistParam.bitDepth = g_bitDepthY;
749    uiDist = m_cDistParam.DistFunc( &m_cDistParam );
750    uiDist += m_pcRdCost->getCost( cMvTest.getHor(), cMvTest.getVer() );
751   
752    if ( uiDist < uiDistBest )
753    {
754      uiDistBest  = uiDist;
755      uiDirecBest = i;
756    }
757  }
758 
759  rcMvFrac = pcMvRefine[uiDirecBest];
760 
761  return uiDistBest;
762}
763
764Void
765TEncSearch::xEncSubdivCbfQT( TComDataCU*  pcCU,
766                            UInt         uiTrDepth,
767                            UInt         uiAbsPartIdx,
768                            Bool         bLuma,
769                            Bool         bChroma )
770{
771  UInt  uiFullDepth     = pcCU->getDepth(0) + uiTrDepth;
772  UInt  uiTrMode        = pcCU->getTransformIdx( uiAbsPartIdx );
773  UInt  uiSubdiv        = ( uiTrMode > uiTrDepth ? 1 : 0 );
774  UInt  uiLog2TrafoSize = g_aucConvertToBit[pcCU->getSlice()->getSPS()->getMaxCUWidth()] + 2 - uiFullDepth;
775
776  if( pcCU->getPredictionMode(0) == MODE_INTRA && pcCU->getPartitionSize(0) == SIZE_NxN && uiTrDepth == 0 )
777  {
778    assert( uiSubdiv );
779  }
780  else if( uiLog2TrafoSize > pcCU->getSlice()->getSPS()->getQuadtreeTULog2MaxSize() )
781  {
782    assert( uiSubdiv );
783  }
784  else if( uiLog2TrafoSize == pcCU->getSlice()->getSPS()->getQuadtreeTULog2MinSize() )
785  {
786    assert( !uiSubdiv );
787  }
788  else if( uiLog2TrafoSize == pcCU->getQuadtreeTULog2MinSizeInCU(uiAbsPartIdx) )
789  {
790    assert( !uiSubdiv );
791  }
792  else
793  {
794    assert( uiLog2TrafoSize > pcCU->getQuadtreeTULog2MinSizeInCU(uiAbsPartIdx) );
795    if( bLuma )
796    {
797      m_pcEntropyCoder->encodeTransformSubdivFlag( uiSubdiv, 5 - uiLog2TrafoSize );
798    }
799  }
800 
801  if ( bChroma )
802  {
803    if( uiLog2TrafoSize > 2 )
804    {
805      if( uiTrDepth==0 || pcCU->getCbf( uiAbsPartIdx, TEXT_CHROMA_U, uiTrDepth-1 ) )
806      {
807        m_pcEntropyCoder->encodeQtCbf( pcCU, uiAbsPartIdx, TEXT_CHROMA_U, uiTrDepth );
808      }
809      if( uiTrDepth==0 || pcCU->getCbf( uiAbsPartIdx, TEXT_CHROMA_V, uiTrDepth-1 ) )
810      {
811        m_pcEntropyCoder->encodeQtCbf( pcCU, uiAbsPartIdx, TEXT_CHROMA_V, uiTrDepth );
812      }
813    }
814  }
815
816  if( uiSubdiv )
817  {
818    UInt uiQPartNum = pcCU->getPic()->getNumPartInCU() >> ( ( uiFullDepth + 1 ) << 1 );
819    for( UInt uiPart = 0; uiPart < 4; uiPart++ )
820    {
821      xEncSubdivCbfQT( pcCU, uiTrDepth + 1, uiAbsPartIdx + uiPart * uiQPartNum, bLuma, bChroma );
822    }
823    return;
824  }
825 
826  //===== Cbfs =====
827  if( bLuma )
828  {
829    m_pcEntropyCoder->encodeQtCbf( pcCU, uiAbsPartIdx, TEXT_LUMA,     uiTrMode );
830  }
831}
832
833Void
834TEncSearch::xEncCoeffQT( TComDataCU*  pcCU,
835                        UInt         uiTrDepth,
836                        UInt         uiAbsPartIdx,
837                        TextType     eTextType,
838                        Bool         bRealCoeff )
839{
840  UInt  uiFullDepth     = pcCU->getDepth(0) + uiTrDepth;
841  UInt  uiTrMode        = pcCU->getTransformIdx( uiAbsPartIdx );
842  UInt  uiSubdiv        = ( uiTrMode > uiTrDepth ? 1 : 0 );
843  UInt  uiLog2TrafoSize = g_aucConvertToBit[pcCU->getSlice()->getSPS()->getMaxCUWidth()] + 2 - uiFullDepth;
844  UInt  uiChroma        = ( eTextType != TEXT_LUMA ? 1 : 0 );
845 
846  if( uiSubdiv )
847  {
848    UInt uiQPartNum = pcCU->getPic()->getNumPartInCU() >> ( ( uiFullDepth + 1 ) << 1 );
849      for( UInt uiPart = 0; uiPart < 4; uiPart++ )
850      {
851        xEncCoeffQT( pcCU, uiTrDepth + 1, uiAbsPartIdx + uiPart * uiQPartNum, eTextType, bRealCoeff );
852      }
853    return;
854  }
855 
856  if( eTextType != TEXT_LUMA && uiLog2TrafoSize == 2 )
857  {
858    assert( uiTrDepth > 0 );
859    uiTrDepth--;
860    UInt uiQPDiv = pcCU->getPic()->getNumPartInCU() >> ( ( pcCU->getDepth( 0 ) + uiTrDepth ) << 1 );
861    Bool bFirstQ = ( ( uiAbsPartIdx % uiQPDiv ) == 0 );
862    if( !bFirstQ )
863    {
864      return;
865    }
866  }
867 
868  //===== coefficients =====
869  UInt    uiWidth         = pcCU->getWidth  ( 0 ) >> ( uiTrDepth + uiChroma );
870  UInt    uiHeight        = pcCU->getHeight ( 0 ) >> ( uiTrDepth + uiChroma );
871  UInt    uiCoeffOffset   = ( pcCU->getPic()->getMinCUWidth() * pcCU->getPic()->getMinCUHeight() * uiAbsPartIdx ) >> ( uiChroma << 1 );
872  UInt    uiQTLayer       = pcCU->getSlice()->getSPS()->getQuadtreeTULog2MaxSize() - uiLog2TrafoSize;
873  TCoeff* pcCoeff         = 0;
874  switch( eTextType )
875  {
876    case TEXT_LUMA:     pcCoeff = ( bRealCoeff ? pcCU->getCoeffY () : m_ppcQTTempCoeffY [uiQTLayer] );  break;
877    case TEXT_CHROMA_U: pcCoeff = ( bRealCoeff ? pcCU->getCoeffCb() : m_ppcQTTempCoeffCb[uiQTLayer] );  break;
878    case TEXT_CHROMA_V: pcCoeff = ( bRealCoeff ? pcCU->getCoeffCr() : m_ppcQTTempCoeffCr[uiQTLayer] );  break;
879    default:            assert(0);
880  }
881  pcCoeff += uiCoeffOffset;
882 
883  m_pcEntropyCoder->encodeCoeffNxN( pcCU, pcCoeff, uiAbsPartIdx, uiWidth, uiHeight, uiFullDepth, eTextType );
884}
885
886
887Void
888TEncSearch::xEncIntraHeader( TComDataCU*  pcCU,
889                            UInt         uiTrDepth,
890                            UInt         uiAbsPartIdx,
891                            Bool         bLuma,
892                            Bool         bChroma )
893{
894  if( bLuma )
895  {
896    // CU header
897    if( uiAbsPartIdx == 0 )
898    {
899      if( !pcCU->getSlice()->isIntra() )
900      {
901        if (pcCU->getSlice()->getPPS()->getTransquantBypassEnableFlag())
902        {
903          m_pcEntropyCoder->encodeCUTransquantBypassFlag( pcCU, 0, true );
904        }
905        m_pcEntropyCoder->encodeSkipFlag( pcCU, 0, true );
906        m_pcEntropyCoder->encodePredMode( pcCU, 0, true );
907      }
908   
909      m_pcEntropyCoder  ->encodePartSize( pcCU, 0, pcCU->getDepth(0), true );
910
911      if (pcCU->isIntra(0) && pcCU->getPartitionSize(0) == SIZE_2Nx2N )
912      {
913        m_pcEntropyCoder->encodeIPCMInfo( pcCU, 0, true );
914
915        if ( pcCU->getIPCMFlag (0))
916        {
917          return;
918        }
919      }
920    }
921    // luma prediction mode
922    if( pcCU->getPartitionSize(0) == SIZE_2Nx2N )
923    {
924      if( uiAbsPartIdx == 0 )
925      {
926        m_pcEntropyCoder->encodeIntraDirModeLuma ( pcCU, 0 );
927      }
928    }
929    else
930    {
931      UInt uiQNumParts = pcCU->getTotalNumPart() >> 2;
932      if( uiTrDepth == 0 )
933      {
934        assert( uiAbsPartIdx == 0 );
935        for( UInt uiPart = 0; uiPart < 4; uiPart++ )
936        {
937          m_pcEntropyCoder->encodeIntraDirModeLuma ( pcCU, uiPart * uiQNumParts );
938        }
939      }
940      else if( ( uiAbsPartIdx % uiQNumParts ) == 0 )
941      {
942        m_pcEntropyCoder->encodeIntraDirModeLuma ( pcCU, uiAbsPartIdx );
943      }
944    }
945  }
946  if( bChroma )
947  {
948    // chroma prediction mode
949    if( uiAbsPartIdx == 0 )
950    {
951      m_pcEntropyCoder->encodeIntraDirModeChroma( pcCU, 0, true );
952    }
953  }
954}
955
956
957UInt
958TEncSearch::xGetIntraBitsQT( TComDataCU*  pcCU,
959                            UInt         uiTrDepth,
960                            UInt         uiAbsPartIdx,
961                            Bool         bLuma,
962                            Bool         bChroma,
963                            Bool         bRealCoeff /* just for test */ )
964{
965  m_pcEntropyCoder->resetBits();
966  xEncIntraHeader ( pcCU, uiTrDepth, uiAbsPartIdx, bLuma, bChroma );
967  xEncSubdivCbfQT ( pcCU, uiTrDepth, uiAbsPartIdx, bLuma, bChroma );
968 
969  if( bLuma )
970  {
971    xEncCoeffQT   ( pcCU, uiTrDepth, uiAbsPartIdx, TEXT_LUMA,      bRealCoeff );
972  }
973  if( bChroma )
974  {
975    xEncCoeffQT   ( pcCU, uiTrDepth, uiAbsPartIdx, TEXT_CHROMA_U,  bRealCoeff );
976    xEncCoeffQT   ( pcCU, uiTrDepth, uiAbsPartIdx, TEXT_CHROMA_V,  bRealCoeff );
977  }
978  UInt   uiBits = m_pcEntropyCoder->getNumberOfWrittenBits();
979  return uiBits;
980}
981
982UInt
983TEncSearch::xGetIntraBitsQTChroma( TComDataCU*  pcCU,
984                                  UInt         uiTrDepth,
985                                  UInt         uiAbsPartIdx,
986                                  UInt         uiChromaId,
987                                  Bool         bRealCoeff /* just for test */ )
988{
989  m_pcEntropyCoder->resetBits();
990  if( uiChromaId == TEXT_CHROMA_U)
991  {
992    xEncCoeffQT   ( pcCU, uiTrDepth, uiAbsPartIdx, TEXT_CHROMA_U,  bRealCoeff );
993  }
994  else if(uiChromaId == TEXT_CHROMA_V)
995  {
996    xEncCoeffQT   ( pcCU, uiTrDepth, uiAbsPartIdx, TEXT_CHROMA_V,  bRealCoeff );
997  }
998
999  UInt   uiBits = m_pcEntropyCoder->getNumberOfWrittenBits();
1000  return uiBits;
1001}
1002
1003Void
1004TEncSearch::xIntraCodingLumaBlk( TComDataCU* pcCU,
1005                                UInt        uiTrDepth,
1006                                UInt        uiAbsPartIdx,
1007                                TComYuv*    pcOrgYuv, 
1008                                TComYuv*    pcPredYuv, 
1009                                TComYuv*    pcResiYuv, 
1010                                UInt&       ruiDist,
1011                                Int        default0Save1Load2 )
1012{
1013  UInt    uiLumaPredMode    = pcCU     ->getLumaIntraDir     ( uiAbsPartIdx );
1014  UInt    uiFullDepth       = pcCU     ->getDepth   ( 0 )  + uiTrDepth;
1015  UInt    uiWidth           = pcCU     ->getWidth   ( 0 ) >> uiTrDepth;
1016  UInt    uiHeight          = pcCU     ->getHeight  ( 0 ) >> uiTrDepth;
1017  UInt    uiStride          = pcOrgYuv ->getStride  ();
1018  Pel*    piOrg             = pcOrgYuv ->getLumaAddr( uiAbsPartIdx );
1019  Pel*    piPred            = pcPredYuv->getLumaAddr( uiAbsPartIdx );
1020  Pel*    piResi            = pcResiYuv->getLumaAddr( uiAbsPartIdx );
1021  Pel*    piReco            = pcPredYuv->getLumaAddr( uiAbsPartIdx );
1022 
1023  UInt    uiLog2TrSize      = g_aucConvertToBit[ pcCU->getSlice()->getSPS()->getMaxCUWidth() >> uiFullDepth ] + 2;
1024  UInt    uiQTLayer         = pcCU->getSlice()->getSPS()->getQuadtreeTULog2MaxSize() - uiLog2TrSize;
1025  UInt    uiNumCoeffPerInc  = pcCU->getSlice()->getSPS()->getMaxCUWidth() * pcCU->getSlice()->getSPS()->getMaxCUHeight() >> ( pcCU->getSlice()->getSPS()->getMaxCUDepth() << 1 );
1026  TCoeff* pcCoeff           = m_ppcQTTempCoeffY[ uiQTLayer ] + uiNumCoeffPerInc * uiAbsPartIdx;
1027#if ADAPTIVE_QP_SELECTION
1028  Int*    pcArlCoeff        = m_ppcQTTempArlCoeffY[ uiQTLayer ] + uiNumCoeffPerInc * uiAbsPartIdx;
1029#endif
1030  Pel*    piRecQt           = m_pcQTTempTComYuv[ uiQTLayer ].getLumaAddr( uiAbsPartIdx );
1031  UInt    uiRecQtStride     = m_pcQTTempTComYuv[ uiQTLayer ].getStride  ();
1032 
1033  UInt    uiZOrder          = pcCU->getZorderIdxInCU() + uiAbsPartIdx;
1034  Pel*    piRecIPred        = pcCU->getPic()->getPicYuvRec()->getLumaAddr( pcCU->getAddr(), uiZOrder );
1035  UInt    uiRecIPredStride  = pcCU->getPic()->getPicYuvRec()->getStride  ();
1036  Bool    useTransformSkip  = pcCU->getTransformSkip(uiAbsPartIdx, TEXT_LUMA);
1037  //===== init availability pattern =====
1038  Bool  bAboveAvail = false;
1039  Bool  bLeftAvail  = false;
1040  if(default0Save1Load2 != 2)
1041  {
1042    pcCU->getPattern()->initPattern   ( pcCU, uiTrDepth, uiAbsPartIdx );
1043    pcCU->getPattern()->initAdiPattern( pcCU, uiAbsPartIdx, uiTrDepth, m_piYuvExt, m_iYuvExtStride, m_iYuvExtHeight, bAboveAvail, bLeftAvail );
1044    //===== get prediction signal =====
1045    predIntraLumaAng( pcCU->getPattern(), uiLumaPredMode, piPred, uiStride, uiWidth, uiHeight, bAboveAvail, bLeftAvail );
1046    // save prediction
1047    if(default0Save1Load2 == 1)
1048    {
1049      Pel*  pPred   = piPred;
1050      Pel*  pPredBuf = m_pSharedPredTransformSkip[0];
1051      Int k = 0;
1052      for( UInt uiY = 0; uiY < uiHeight; uiY++ )
1053      {
1054        for( UInt uiX = 0; uiX < uiWidth; uiX++ )
1055        {
1056          pPredBuf[ k ++ ] = pPred[ uiX ];
1057        }
1058        pPred += uiStride;
1059      }
1060    }
1061  }
1062  else 
1063  {
1064    // load prediction
1065    Pel*  pPred   = piPred;
1066    Pel*  pPredBuf = m_pSharedPredTransformSkip[0];
1067    Int k = 0;
1068    for( UInt uiY = 0; uiY < uiHeight; uiY++ )
1069    {
1070      for( UInt uiX = 0; uiX < uiWidth; uiX++ )
1071      {
1072        pPred[ uiX ] = pPredBuf[ k ++ ];
1073      }
1074      pPred += uiStride;
1075    }
1076  }
1077  //===== get residual signal =====
1078  {
1079    // get residual
1080    Pel*  pOrg    = piOrg;
1081    Pel*  pPred   = piPred;
1082    Pel*  pResi   = piResi;
1083    for( UInt uiY = 0; uiY < uiHeight; uiY++ )
1084    {
1085      for( UInt uiX = 0; uiX < uiWidth; uiX++ )
1086      {
1087        pResi[ uiX ] = pOrg[ uiX ] - pPred[ uiX ];
1088      }
1089      pOrg  += uiStride;
1090      pResi += uiStride;
1091      pPred += uiStride;
1092    }
1093  }
1094 
1095  //===== transform and quantization =====
1096  //--- init rate estimation arrays for RDOQ ---
1097  if( useTransformSkip? m_pcEncCfg->getUseRDOQTS():m_pcEncCfg->getUseRDOQ())
1098  {
1099    m_pcEntropyCoder->estimateBit( m_pcTrQuant->m_pcEstBitsSbac, uiWidth, uiWidth, TEXT_LUMA );
1100  }
1101  //--- transform and quantization ---
1102  UInt uiAbsSum = 0;
1103  pcCU       ->setTrIdxSubParts ( uiTrDepth, uiAbsPartIdx, uiFullDepth );
1104
1105#if REPN_FORMAT_IN_VPS
1106  m_pcTrQuant->setQPforQuant    ( pcCU->getQP( 0 ), TEXT_LUMA, pcCU->getSlice()->getQpBDOffsetY(), 0 );
1107#else
1108  m_pcTrQuant->setQPforQuant    ( pcCU->getQP( 0 ), TEXT_LUMA, pcCU->getSlice()->getSPS()->getQpBDOffsetY(), 0 );
1109#endif
1110
1111#if RDOQ_CHROMA_LAMBDA
1112  m_pcTrQuant->selectLambda     (TEXT_LUMA); 
1113#endif
1114
1115  m_pcTrQuant->transformNxN     ( pcCU, piResi, uiStride, pcCoeff, 
1116#if ADAPTIVE_QP_SELECTION
1117    pcArlCoeff, 
1118#endif
1119    uiWidth, uiHeight, uiAbsSum, TEXT_LUMA, uiAbsPartIdx,useTransformSkip );
1120 
1121  //--- set coded block flag ---
1122  pcCU->setCbfSubParts          ( ( uiAbsSum ? 1 : 0 ) << uiTrDepth, TEXT_LUMA, uiAbsPartIdx, uiFullDepth );
1123  //--- inverse transform ---
1124  if( uiAbsSum )
1125  {
1126    Int scalingListType = 0 + g_eTTable[(Int)TEXT_LUMA];
1127    assert(scalingListType < 6);
1128    m_pcTrQuant->invtransformNxN( pcCU->getCUTransquantBypass(uiAbsPartIdx), TEXT_LUMA,pcCU->getLumaIntraDir( uiAbsPartIdx ), piResi, uiStride, pcCoeff, uiWidth, uiHeight, scalingListType, useTransformSkip );
1129  }
1130  else
1131  {
1132    Pel* pResi = piResi;
1133    memset( pcCoeff, 0, sizeof( TCoeff ) * uiWidth * uiHeight );
1134    for( UInt uiY = 0; uiY < uiHeight; uiY++ )
1135    {
1136      memset( pResi, 0, sizeof( Pel ) * uiWidth );
1137      pResi += uiStride;
1138    }
1139  }
1140 
1141  //===== reconstruction =====
1142  {
1143    Pel* pPred      = piPred;
1144    Pel* pResi      = piResi;
1145    Pel* pReco      = piReco;
1146    Pel* pRecQt     = piRecQt;
1147    Pel* pRecIPred  = piRecIPred;
1148    for( UInt uiY = 0; uiY < uiHeight; uiY++ )
1149    {
1150      for( UInt uiX = 0; uiX < uiWidth; uiX++ )
1151      {
1152        pReco    [ uiX ] = ClipY( pPred[ uiX ] + pResi[ uiX ] );
1153        pRecQt   [ uiX ] = pReco[ uiX ];
1154        pRecIPred[ uiX ] = pReco[ uiX ];
1155      }
1156      pPred     += uiStride;
1157      pResi     += uiStride;
1158      pReco     += uiStride;
1159      pRecQt    += uiRecQtStride;
1160      pRecIPred += uiRecIPredStride;
1161    }
1162  }
1163 
1164  //===== update distortion =====
1165  ruiDist += m_pcRdCost->getDistPart(g_bitDepthY, piReco, uiStride, piOrg, uiStride, uiWidth, uiHeight );
1166}
1167
1168Void
1169TEncSearch::xIntraCodingChromaBlk( TComDataCU* pcCU,
1170                                  UInt        uiTrDepth,
1171                                  UInt        uiAbsPartIdx,
1172                                  TComYuv*    pcOrgYuv, 
1173                                  TComYuv*    pcPredYuv, 
1174                                  TComYuv*    pcResiYuv, 
1175                                  UInt&       ruiDist,
1176                                  UInt        uiChromaId,
1177                                  Int        default0Save1Load2 )
1178{
1179  UInt uiOrgTrDepth = uiTrDepth;
1180  UInt uiFullDepth  = pcCU->getDepth( 0 ) + uiTrDepth;
1181  UInt uiLog2TrSize = g_aucConvertToBit[ pcCU->getSlice()->getSPS()->getMaxCUWidth() >> uiFullDepth ] + 2;
1182  if( uiLog2TrSize == 2 )
1183  {
1184    assert( uiTrDepth > 0 );
1185    uiTrDepth--;
1186    UInt uiQPDiv = pcCU->getPic()->getNumPartInCU() >> ( ( pcCU->getDepth( 0 ) + uiTrDepth ) << 1 );
1187    Bool bFirstQ = ( ( uiAbsPartIdx % uiQPDiv ) == 0 );
1188    if( !bFirstQ )
1189    {
1190      return;
1191    }
1192  }
1193 
1194  TextType  eText             = ( uiChromaId > 0 ? TEXT_CHROMA_V : TEXT_CHROMA_U );
1195  UInt      uiChromaPredMode  = pcCU     ->getChromaIntraDir( uiAbsPartIdx );
1196  UInt      uiWidth           = pcCU     ->getWidth   ( 0 ) >> ( uiTrDepth + 1 );
1197  UInt      uiHeight          = pcCU     ->getHeight  ( 0 ) >> ( uiTrDepth + 1 );
1198  UInt      uiStride          = pcOrgYuv ->getCStride ();
1199  Pel*      piOrg             = ( uiChromaId > 0 ? pcOrgYuv ->getCrAddr( uiAbsPartIdx ) : pcOrgYuv ->getCbAddr( uiAbsPartIdx ) );
1200  Pel*      piPred            = ( uiChromaId > 0 ? pcPredYuv->getCrAddr( uiAbsPartIdx ) : pcPredYuv->getCbAddr( uiAbsPartIdx ) );
1201  Pel*      piResi            = ( uiChromaId > 0 ? pcResiYuv->getCrAddr( uiAbsPartIdx ) : pcResiYuv->getCbAddr( uiAbsPartIdx ) );
1202  Pel*      piReco            = ( uiChromaId > 0 ? pcPredYuv->getCrAddr( uiAbsPartIdx ) : pcPredYuv->getCbAddr( uiAbsPartIdx ) );
1203 
1204  UInt      uiQTLayer         = pcCU->getSlice()->getSPS()->getQuadtreeTULog2MaxSize() - uiLog2TrSize;
1205  UInt      uiNumCoeffPerInc  = ( pcCU->getSlice()->getSPS()->getMaxCUWidth() * pcCU->getSlice()->getSPS()->getMaxCUHeight() >> ( pcCU->getSlice()->getSPS()->getMaxCUDepth() << 1 ) ) >> 2;
1206  TCoeff*   pcCoeff           = ( uiChromaId > 0 ? m_ppcQTTempCoeffCr[ uiQTLayer ] : m_ppcQTTempCoeffCb[ uiQTLayer ] ) + uiNumCoeffPerInc * uiAbsPartIdx;
1207#if ADAPTIVE_QP_SELECTION
1208  Int*      pcArlCoeff        = ( uiChromaId > 0 ? m_ppcQTTempArlCoeffCr[ uiQTLayer ] : m_ppcQTTempArlCoeffCb[ uiQTLayer ] ) + uiNumCoeffPerInc * uiAbsPartIdx;
1209#endif
1210  Pel*      piRecQt           = ( uiChromaId > 0 ? m_pcQTTempTComYuv[ uiQTLayer ].getCrAddr( uiAbsPartIdx ) : m_pcQTTempTComYuv[ uiQTLayer ].getCbAddr( uiAbsPartIdx ) );
1211  UInt      uiRecQtStride     = m_pcQTTempTComYuv[ uiQTLayer ].getCStride();
1212 
1213  UInt      uiZOrder          = pcCU->getZorderIdxInCU() + uiAbsPartIdx;
1214  Pel*      piRecIPred        = ( uiChromaId > 0 ? pcCU->getPic()->getPicYuvRec()->getCrAddr( pcCU->getAddr(), uiZOrder ) : pcCU->getPic()->getPicYuvRec()->getCbAddr( pcCU->getAddr(), uiZOrder ) );
1215  UInt      uiRecIPredStride  = pcCU->getPic()->getPicYuvRec()->getCStride();
1216  Bool      useTransformSkipChroma       = pcCU->getTransformSkip(uiAbsPartIdx, eText);
1217  //===== update chroma mode =====
1218  if( uiChromaPredMode == DM_CHROMA_IDX )
1219  {
1220    uiChromaPredMode          = pcCU->getLumaIntraDir( 0 );
1221  }
1222 
1223  //===== init availability pattern =====
1224  Bool  bAboveAvail = false;
1225  Bool  bLeftAvail  = false;
1226  if( default0Save1Load2 != 2 )
1227  {
1228    pcCU->getPattern()->initPattern         ( pcCU, uiTrDepth, uiAbsPartIdx );
1229
1230    pcCU->getPattern()->initAdiPatternChroma( pcCU, uiAbsPartIdx, uiTrDepth, m_piYuvExt, m_iYuvExtStride, m_iYuvExtHeight, bAboveAvail, bLeftAvail );
1231    Int*  pPatChroma  = ( uiChromaId > 0 ? pcCU->getPattern()->getAdiCrBuf( uiWidth, uiHeight, m_piYuvExt ) : pcCU->getPattern()->getAdiCbBuf( uiWidth, uiHeight, m_piYuvExt ) );
1232
1233    //===== get prediction signal =====
1234    predIntraChromaAng( pPatChroma, uiChromaPredMode, piPred, uiStride, uiWidth, uiHeight, bAboveAvail, bLeftAvail );
1235
1236    // save prediction
1237    if( default0Save1Load2 == 1 )
1238    {
1239      Pel*  pPred   = piPred;
1240      Pel*  pPredBuf = m_pSharedPredTransformSkip[1 + uiChromaId];
1241      Int k = 0;
1242      for( UInt uiY = 0; uiY < uiHeight; uiY++ )
1243      {
1244        for( UInt uiX = 0; uiX < uiWidth; uiX++ )
1245        {
1246          pPredBuf[ k ++ ] = pPred[ uiX ];
1247        }
1248        pPred += uiStride;
1249      }
1250    }
1251  }
1252  else
1253  {
1254    // load prediction
1255    Pel*  pPred   = piPred;
1256    Pel*  pPredBuf = m_pSharedPredTransformSkip[1 + uiChromaId];
1257    Int k = 0;
1258    for( UInt uiY = 0; uiY < uiHeight; uiY++ )
1259    {
1260      for( UInt uiX = 0; uiX < uiWidth; uiX++ )
1261      {
1262        pPred[ uiX ] = pPredBuf[ k ++ ];
1263      }
1264      pPred += uiStride;
1265    }
1266  }
1267  //===== get residual signal =====
1268  {
1269    // get residual
1270    Pel*  pOrg    = piOrg;
1271    Pel*  pPred   = piPred;
1272    Pel*  pResi   = piResi;
1273    for( UInt uiY = 0; uiY < uiHeight; uiY++ )
1274    {
1275      for( UInt uiX = 0; uiX < uiWidth; uiX++ )
1276      {
1277        pResi[ uiX ] = pOrg[ uiX ] - pPred[ uiX ];
1278      }
1279      pOrg  += uiStride;
1280      pResi += uiStride;
1281      pPred += uiStride;
1282    }
1283  }
1284 
1285  //===== transform and quantization =====
1286  {
1287    //--- init rate estimation arrays for RDOQ ---
1288    if( useTransformSkipChroma? m_pcEncCfg->getUseRDOQTS():m_pcEncCfg->getUseRDOQ())
1289    {
1290      m_pcEntropyCoder->estimateBit( m_pcTrQuant->m_pcEstBitsSbac, uiWidth, uiWidth, eText );
1291    }
1292    //--- transform and quantization ---
1293    UInt uiAbsSum = 0;
1294
1295    Int curChromaQpOffset;
1296    if(eText == TEXT_CHROMA_U)
1297    {
1298      curChromaQpOffset = pcCU->getSlice()->getPPS()->getChromaCbQpOffset() + pcCU->getSlice()->getSliceQpDeltaCb();
1299    }
1300    else
1301    {
1302      curChromaQpOffset = pcCU->getSlice()->getPPS()->getChromaCrQpOffset() + pcCU->getSlice()->getSliceQpDeltaCr();
1303    }
1304    m_pcTrQuant->setQPforQuant     ( pcCU->getQP( 0 ), TEXT_CHROMA, pcCU->getSlice()->getSPS()->getQpBDOffsetC(), curChromaQpOffset );
1305
1306#if RDOQ_CHROMA_LAMBDA
1307    m_pcTrQuant->selectLambda(eText);
1308#endif
1309    m_pcTrQuant->transformNxN      ( pcCU, piResi, uiStride, pcCoeff, 
1310#if ADAPTIVE_QP_SELECTION
1311                                     pcArlCoeff, 
1312#endif
1313                                     uiWidth, uiHeight, uiAbsSum, eText, uiAbsPartIdx, useTransformSkipChroma );
1314    //--- set coded block flag ---
1315    pcCU->setCbfSubParts           ( ( uiAbsSum ? 1 : 0 ) << uiOrgTrDepth, eText, uiAbsPartIdx, pcCU->getDepth(0) + uiTrDepth );
1316    //--- inverse transform ---
1317    if( uiAbsSum )
1318    {
1319      Int scalingListType = 0 + g_eTTable[(Int)eText];
1320      assert(scalingListType < 6);
1321      m_pcTrQuant->invtransformNxN( pcCU->getCUTransquantBypass(uiAbsPartIdx), TEXT_CHROMA, REG_DCT, piResi, uiStride, pcCoeff, uiWidth, uiHeight, scalingListType, useTransformSkipChroma );
1322    }
1323    else
1324    {
1325      Pel* pResi = piResi;
1326      memset( pcCoeff, 0, sizeof( TCoeff ) * uiWidth * uiHeight );
1327      for( UInt uiY = 0; uiY < uiHeight; uiY++ )
1328      {
1329        memset( pResi, 0, sizeof( Pel ) * uiWidth );
1330        pResi += uiStride;
1331      }
1332    }
1333  }
1334 
1335  //===== reconstruction =====
1336  {
1337    Pel* pPred      = piPred;
1338    Pel* pResi      = piResi;
1339    Pel* pReco      = piReco;
1340    Pel* pRecQt     = piRecQt;
1341    Pel* pRecIPred  = piRecIPred;
1342    for( UInt uiY = 0; uiY < uiHeight; uiY++ )
1343    {
1344      for( UInt uiX = 0; uiX < uiWidth; uiX++ )
1345      {
1346        pReco    [ uiX ] = ClipC( pPred[ uiX ] + pResi[ uiX ] );
1347        pRecQt   [ uiX ] = pReco[ uiX ];
1348        pRecIPred[ uiX ] = pReco[ uiX ];
1349      }
1350      pPred     += uiStride;
1351      pResi     += uiStride;
1352      pReco     += uiStride;
1353      pRecQt    += uiRecQtStride;
1354      pRecIPred += uiRecIPredStride;
1355    }
1356  }
1357 
1358  //===== update distortion =====
1359  ruiDist += m_pcRdCost->getDistPart(g_bitDepthC, piReco, uiStride, piOrg, uiStride, uiWidth, uiHeight, eText );
1360}
1361
1362
1363
1364Void
1365TEncSearch::xRecurIntraCodingQT( TComDataCU*  pcCU, 
1366                                UInt         uiTrDepth,
1367                                UInt         uiAbsPartIdx, 
1368                                Bool         bLumaOnly,
1369                                TComYuv*     pcOrgYuv, 
1370                                TComYuv*     pcPredYuv, 
1371                                TComYuv*     pcResiYuv, 
1372                                UInt&        ruiDistY,
1373                                UInt&        ruiDistC,
1374#if HHI_RQT_INTRA_SPEEDUP
1375                                Bool         bCheckFirst,
1376#endif
1377                                Double&      dRDCost )
1378{
1379  UInt    uiFullDepth   = pcCU->getDepth( 0 ) +  uiTrDepth;
1380  UInt    uiLog2TrSize  = g_aucConvertToBit[ pcCU->getSlice()->getSPS()->getMaxCUWidth() >> uiFullDepth ] + 2;
1381  Bool    bCheckFull    = ( uiLog2TrSize  <= pcCU->getSlice()->getSPS()->getQuadtreeTULog2MaxSize() );
1382  Bool    bCheckSplit   = ( uiLog2TrSize  >  pcCU->getQuadtreeTULog2MinSizeInCU(uiAbsPartIdx) );
1383 
1384#if HHI_RQT_INTRA_SPEEDUP
1385  Int maxTuSize = pcCU->getSlice()->getSPS()->getQuadtreeTULog2MaxSize();
1386  Int isIntraSlice = (pcCU->getSlice()->getSliceType() == I_SLICE);
1387  // don't check split if TU size is less or equal to max TU size
1388  Bool noSplitIntraMaxTuSize = bCheckFull;
1389  if(m_pcEncCfg->getRDpenalty() && ! isIntraSlice)
1390  {
1391    // in addition don't check split if TU size is less or equal to 16x16 TU size for non-intra slice
1392    noSplitIntraMaxTuSize = ( uiLog2TrSize  <= min(maxTuSize,4) );
1393
1394    // if maximum RD-penalty don't check TU size 32x32
1395    if(m_pcEncCfg->getRDpenalty()==2)
1396    {
1397      bCheckFull    = ( uiLog2TrSize  <= min(maxTuSize,4));
1398    }
1399  }
1400  if( bCheckFirst && noSplitIntraMaxTuSize )
1401  {
1402    bCheckSplit = false;
1403  }
1404#else
1405  Int maxTuSize = pcCU->getSlice()->getSPS()->getQuadtreeTULog2MaxSize();
1406  Int isIntraSlice = (pcCU->getSlice()->getSliceType() == I_SLICE);
1407  // if maximum RD-penalty don't check TU size 32x32
1408  if((m_pcEncCfg->getRDpenalty()==2)  && !isIntraSlice)
1409  {
1410    bCheckFull    = ( uiLog2TrSize  <= min(maxTuSize,4));
1411  }
1412#endif
1413  Double  dSingleCost   = MAX_DOUBLE;
1414  UInt    uiSingleDistY = 0;
1415  UInt    uiSingleDistC = 0;
1416  UInt    uiSingleCbfY  = 0;
1417  UInt    uiSingleCbfU  = 0;
1418  UInt    uiSingleCbfV  = 0;
1419  Bool    checkTransformSkip  = pcCU->getSlice()->getPPS()->getUseTransformSkip();
1420  UInt    widthTransformSkip  = pcCU->getWidth ( 0 ) >> uiTrDepth;
1421  UInt    heightTransformSkip = pcCU->getHeight( 0 ) >> uiTrDepth;
1422  Int     bestModeId    = 0;
1423  Int     bestModeIdUV[2] = {0, 0};
1424  checkTransformSkip         &= (widthTransformSkip == 4 && heightTransformSkip == 4);
1425  checkTransformSkip         &= (!pcCU->getCUTransquantBypass(0));
1426  checkTransformSkip         &= (!((pcCU->getQP( 0 ) == 0) && (pcCU->getSlice()->getSPS()->getUseLossless())));
1427  if ( m_pcEncCfg->getUseTransformSkipFast() )
1428  {
1429    checkTransformSkip       &= (pcCU->getPartitionSize(uiAbsPartIdx)==SIZE_NxN);
1430  }
1431  if( bCheckFull )
1432  {
1433    if(checkTransformSkip == true)
1434    {
1435      //----- store original entropy coding status -----
1436      if( m_bUseSBACRD)
1437      {
1438        m_pcRDGoOnSbacCoder->store( m_pppcRDSbacCoder[ uiFullDepth ][ CI_QT_TRAFO_ROOT ] );
1439      }
1440      UInt   singleDistYTmp     = 0;
1441      UInt   singleDistCTmp     = 0;
1442      UInt   singleCbfYTmp      = 0;
1443      UInt   singleCbfUTmp      = 0;
1444      UInt   singleCbfVTmp      = 0;
1445      Double singleCostTmp      = 0;
1446      Int    default0Save1Load2 = 0;
1447      Int    firstCheckId       = 0;
1448
1449      UInt   uiQPDiv = pcCU->getPic()->getNumPartInCU() >> ( ( pcCU->getDepth( 0 ) + (uiTrDepth - 1) ) << 1 );
1450      Bool   bFirstQ = ( ( uiAbsPartIdx % uiQPDiv ) == 0 );
1451
1452      for(Int modeId = firstCheckId; modeId < 2; modeId ++)
1453      {
1454        singleDistYTmp = 0;
1455        singleDistCTmp = 0;
1456        pcCU ->setTransformSkipSubParts ( modeId, TEXT_LUMA, uiAbsPartIdx, uiFullDepth ); 
1457        if(modeId == firstCheckId)
1458        {
1459          default0Save1Load2 = 1;
1460        }
1461        else
1462        {
1463          default0Save1Load2 = 2;
1464        }
1465        //----- code luma block with given intra prediction mode and store Cbf-----
1466        xIntraCodingLumaBlk( pcCU, uiTrDepth, uiAbsPartIdx, pcOrgYuv, pcPredYuv, pcResiYuv, singleDistYTmp,default0Save1Load2); 
1467        singleCbfYTmp = pcCU->getCbf( uiAbsPartIdx, TEXT_LUMA, uiTrDepth );
1468        //----- code chroma blocks with given intra prediction mode and store Cbf-----
1469        if( !bLumaOnly )
1470        {
1471          if(bFirstQ)
1472          {
1473            pcCU ->setTransformSkipSubParts ( modeId, TEXT_CHROMA_U, uiAbsPartIdx, uiFullDepth); 
1474            pcCU ->setTransformSkipSubParts ( modeId, TEXT_CHROMA_V, uiAbsPartIdx, uiFullDepth); 
1475          }
1476          xIntraCodingChromaBlk ( pcCU, uiTrDepth, uiAbsPartIdx, pcOrgYuv, pcPredYuv, pcResiYuv, singleDistCTmp, 0, default0Save1Load2); 
1477          xIntraCodingChromaBlk ( pcCU, uiTrDepth, uiAbsPartIdx, pcOrgYuv, pcPredYuv, pcResiYuv, singleDistCTmp, 1, default0Save1Load2); 
1478          singleCbfUTmp = pcCU->getCbf( uiAbsPartIdx, TEXT_CHROMA_U, uiTrDepth );
1479          singleCbfVTmp = pcCU->getCbf( uiAbsPartIdx, TEXT_CHROMA_V, uiTrDepth );
1480        }
1481        //----- determine rate and r-d cost -----
1482        if(modeId == 1 && singleCbfYTmp == 0)
1483        {
1484          //In order not to code TS flag when cbf is zero, the case for TS with cbf being zero is forbidden.
1485          singleCostTmp = MAX_DOUBLE; 
1486        }
1487        else
1488        {
1489          UInt uiSingleBits = xGetIntraBitsQT( pcCU, uiTrDepth, uiAbsPartIdx, true, !bLumaOnly, false );
1490          singleCostTmp     = m_pcRdCost->calcRdCost( uiSingleBits, singleDistYTmp + singleDistCTmp );
1491        }
1492
1493        if(singleCostTmp < dSingleCost)
1494        {
1495          dSingleCost   = singleCostTmp;
1496          uiSingleDistY = singleDistYTmp;
1497          uiSingleDistC = singleDistCTmp;
1498          uiSingleCbfY  = singleCbfYTmp;
1499          uiSingleCbfU  = singleCbfUTmp;
1500          uiSingleCbfV  = singleCbfVTmp;
1501          bestModeId    = modeId;
1502          if(bestModeId == firstCheckId)
1503          {
1504            xStoreIntraResultQT(pcCU, uiTrDepth, uiAbsPartIdx,bLumaOnly );
1505            if( m_bUseSBACRD) 
1506            {
1507              m_pcRDGoOnSbacCoder->store( m_pppcRDSbacCoder[ uiFullDepth ][ CI_TEMP_BEST ] );
1508            }
1509          }
1510        }
1511        if(modeId == firstCheckId)
1512        {
1513          m_pcRDGoOnSbacCoder->load ( m_pppcRDSbacCoder[ uiFullDepth ][ CI_QT_TRAFO_ROOT ] );
1514        }
1515      }
1516
1517      pcCU ->setTransformSkipSubParts ( bestModeId, TEXT_LUMA, uiAbsPartIdx, uiFullDepth ); 
1518
1519      if(bestModeId == firstCheckId)
1520      {
1521        xLoadIntraResultQT(pcCU, uiTrDepth, uiAbsPartIdx,bLumaOnly );
1522        pcCU->setCbfSubParts  ( uiSingleCbfY << uiTrDepth, TEXT_LUMA, uiAbsPartIdx, uiFullDepth );
1523        if( !bLumaOnly )
1524        {
1525          if(bFirstQ)
1526          {
1527            pcCU->setCbfSubParts( uiSingleCbfU << uiTrDepth, TEXT_CHROMA_U, uiAbsPartIdx, pcCU->getDepth( 0 ) + uiTrDepth - 1 );
1528            pcCU->setCbfSubParts( uiSingleCbfV << uiTrDepth, TEXT_CHROMA_V, uiAbsPartIdx, pcCU->getDepth( 0 ) + uiTrDepth - 1 );
1529          }
1530        }
1531        if(m_bUseSBACRD)
1532        {
1533          m_pcRDGoOnSbacCoder->load( m_pppcRDSbacCoder[ uiFullDepth ][ CI_TEMP_BEST ] );
1534        } 
1535      }
1536
1537      if( !bLumaOnly )
1538      {
1539        bestModeIdUV[0] = bestModeIdUV[1] = bestModeId;
1540        if(bFirstQ && bestModeId == 1)
1541        {
1542          //In order not to code TS flag when cbf is zero, the case for TS with cbf being zero is forbidden.
1543          if(uiSingleCbfU == 0)
1544          {
1545            pcCU ->setTransformSkipSubParts ( 0, TEXT_CHROMA_U, uiAbsPartIdx, uiFullDepth); 
1546            bestModeIdUV[0] = 0;
1547          }
1548          if(uiSingleCbfV == 0)
1549          {
1550            pcCU ->setTransformSkipSubParts ( 0, TEXT_CHROMA_V, uiAbsPartIdx, uiFullDepth); 
1551            bestModeIdUV[1] = 0;
1552          }
1553        }
1554      }
1555    }
1556    else
1557    {
1558      pcCU ->setTransformSkipSubParts ( 0, TEXT_LUMA, uiAbsPartIdx, uiFullDepth ); 
1559      //----- store original entropy coding status -----
1560      if( m_bUseSBACRD && bCheckSplit )
1561      {
1562        m_pcRDGoOnSbacCoder->store( m_pppcRDSbacCoder[ uiFullDepth ][ CI_QT_TRAFO_ROOT ] );
1563      }
1564      //----- code luma block with given intra prediction mode and store Cbf-----
1565      dSingleCost   = 0.0;
1566      xIntraCodingLumaBlk( pcCU, uiTrDepth, uiAbsPartIdx, pcOrgYuv, pcPredYuv, pcResiYuv, uiSingleDistY ); 
1567      if( bCheckSplit )
1568      {
1569        uiSingleCbfY = pcCU->getCbf( uiAbsPartIdx, TEXT_LUMA, uiTrDepth );
1570      }
1571      //----- code chroma blocks with given intra prediction mode and store Cbf-----
1572      if( !bLumaOnly )
1573      {
1574        pcCU ->setTransformSkipSubParts ( 0, TEXT_CHROMA_U, uiAbsPartIdx, uiFullDepth ); 
1575        pcCU ->setTransformSkipSubParts ( 0, TEXT_CHROMA_V, uiAbsPartIdx, uiFullDepth ); 
1576        xIntraCodingChromaBlk ( pcCU, uiTrDepth, uiAbsPartIdx, pcOrgYuv, pcPredYuv, pcResiYuv, uiSingleDistC, 0 ); 
1577        xIntraCodingChromaBlk ( pcCU, uiTrDepth, uiAbsPartIdx, pcOrgYuv, pcPredYuv, pcResiYuv, uiSingleDistC, 1 ); 
1578        if( bCheckSplit )
1579        {
1580          uiSingleCbfU = pcCU->getCbf( uiAbsPartIdx, TEXT_CHROMA_U, uiTrDepth );
1581          uiSingleCbfV = pcCU->getCbf( uiAbsPartIdx, TEXT_CHROMA_V, uiTrDepth );
1582        }
1583      }
1584      //----- determine rate and r-d cost -----
1585      UInt uiSingleBits = xGetIntraBitsQT( pcCU, uiTrDepth, uiAbsPartIdx, true, !bLumaOnly, false );
1586      if(m_pcEncCfg->getRDpenalty() && (uiLog2TrSize==5) && !isIntraSlice)
1587      {
1588        uiSingleBits=uiSingleBits*4; 
1589      }
1590      dSingleCost       = m_pcRdCost->calcRdCost( uiSingleBits, uiSingleDistY + uiSingleDistC );
1591    }
1592  }
1593 
1594  if( bCheckSplit )
1595  {
1596    //----- store full entropy coding status, load original entropy coding status -----
1597    if( m_bUseSBACRD )
1598    {
1599      if( bCheckFull )
1600      {
1601        m_pcRDGoOnSbacCoder->store( m_pppcRDSbacCoder[ uiFullDepth ][ CI_QT_TRAFO_TEST ] );
1602        m_pcRDGoOnSbacCoder->load ( m_pppcRDSbacCoder[ uiFullDepth ][ CI_QT_TRAFO_ROOT ] );
1603      }
1604      else
1605      {
1606        m_pcRDGoOnSbacCoder->store( m_pppcRDSbacCoder[ uiFullDepth ][ CI_QT_TRAFO_ROOT ] );
1607      }
1608    }
1609    //----- code splitted block -----
1610    Double  dSplitCost      = 0.0;
1611    UInt    uiSplitDistY    = 0;
1612    UInt    uiSplitDistC    = 0;
1613    UInt    uiQPartsDiv     = pcCU->getPic()->getNumPartInCU() >> ( ( uiFullDepth + 1 ) << 1 );
1614    UInt    uiAbsPartIdxSub = uiAbsPartIdx;
1615
1616    UInt    uiSplitCbfY = 0;
1617    UInt    uiSplitCbfU = 0;
1618    UInt    uiSplitCbfV = 0;
1619
1620    for( UInt uiPart = 0; uiPart < 4; uiPart++, uiAbsPartIdxSub += uiQPartsDiv )
1621    {
1622#if HHI_RQT_INTRA_SPEEDUP
1623      xRecurIntraCodingQT( pcCU, uiTrDepth + 1, uiAbsPartIdxSub, bLumaOnly, pcOrgYuv, pcPredYuv, pcResiYuv, uiSplitDistY, uiSplitDistC, bCheckFirst, dSplitCost );
1624#else
1625      xRecurIntraCodingQT( pcCU, uiTrDepth + 1, uiAbsPartIdxSub, bLumaOnly, pcOrgYuv, pcPredYuv, pcResiYuv, uiSplitDistY, uiSplitDistC, dSplitCost );
1626#endif
1627
1628      uiSplitCbfY |= pcCU->getCbf( uiAbsPartIdxSub, TEXT_LUMA, uiTrDepth + 1 );
1629      if(!bLumaOnly)
1630      {
1631        uiSplitCbfU |= pcCU->getCbf( uiAbsPartIdxSub, TEXT_CHROMA_U, uiTrDepth + 1 );
1632        uiSplitCbfV |= pcCU->getCbf( uiAbsPartIdxSub, TEXT_CHROMA_V, uiTrDepth + 1 );
1633      }
1634    }
1635
1636    for( UInt uiOffs = 0; uiOffs < 4 * uiQPartsDiv; uiOffs++ )
1637    {
1638      pcCU->getCbf( TEXT_LUMA )[ uiAbsPartIdx + uiOffs ] |= ( uiSplitCbfY << uiTrDepth );
1639    }
1640    if( !bLumaOnly )
1641    {
1642      for( UInt uiOffs = 0; uiOffs < 4 * uiQPartsDiv; uiOffs++ )
1643      {
1644        pcCU->getCbf( TEXT_CHROMA_U )[ uiAbsPartIdx + uiOffs ] |= ( uiSplitCbfU << uiTrDepth );
1645        pcCU->getCbf( TEXT_CHROMA_V )[ uiAbsPartIdx + uiOffs ] |= ( uiSplitCbfV << uiTrDepth );
1646      }
1647    }
1648    //----- restore context states -----
1649    if( m_bUseSBACRD )
1650    {
1651      m_pcRDGoOnSbacCoder->load ( m_pppcRDSbacCoder[ uiFullDepth ][ CI_QT_TRAFO_ROOT ] );
1652    }
1653    //----- determine rate and r-d cost -----
1654    UInt uiSplitBits = xGetIntraBitsQT( pcCU, uiTrDepth, uiAbsPartIdx, true, !bLumaOnly, false );
1655    dSplitCost       = m_pcRdCost->calcRdCost( uiSplitBits, uiSplitDistY + uiSplitDistC );
1656   
1657    //===== compare and set best =====
1658    if( dSplitCost < dSingleCost )
1659    {
1660      //--- update cost ---
1661      ruiDistY += uiSplitDistY;
1662      ruiDistC += uiSplitDistC;
1663      dRDCost  += dSplitCost;
1664      return;
1665    }
1666    //----- set entropy coding status -----
1667    if( m_bUseSBACRD )
1668    {
1669      m_pcRDGoOnSbacCoder->load ( m_pppcRDSbacCoder[ uiFullDepth ][ CI_QT_TRAFO_TEST ] );
1670    }
1671   
1672    //--- set transform index and Cbf values ---
1673    pcCU->setTrIdxSubParts( uiTrDepth, uiAbsPartIdx, uiFullDepth );
1674    pcCU->setCbfSubParts  ( uiSingleCbfY << uiTrDepth, TEXT_LUMA, uiAbsPartIdx, uiFullDepth );
1675    pcCU ->setTransformSkipSubParts  ( bestModeId, TEXT_LUMA, uiAbsPartIdx, uiFullDepth ); 
1676    if( !bLumaOnly )
1677    {
1678      pcCU->setCbfSubParts( uiSingleCbfU << uiTrDepth, TEXT_CHROMA_U, uiAbsPartIdx, uiFullDepth );
1679      pcCU->setCbfSubParts( uiSingleCbfV << uiTrDepth, TEXT_CHROMA_V, uiAbsPartIdx, uiFullDepth );
1680      pcCU->setTransformSkipSubParts ( bestModeIdUV[0], TEXT_CHROMA_U, uiAbsPartIdx, uiFullDepth); 
1681      pcCU->setTransformSkipSubParts ( bestModeIdUV[1], TEXT_CHROMA_V, uiAbsPartIdx, uiFullDepth); 
1682    }
1683   
1684    //--- set reconstruction for next intra prediction blocks ---
1685    UInt  uiWidth     = pcCU->getWidth ( 0 ) >> uiTrDepth;
1686    UInt  uiHeight    = pcCU->getHeight( 0 ) >> uiTrDepth;
1687    UInt  uiQTLayer   = pcCU->getSlice()->getSPS()->getQuadtreeTULog2MaxSize() - uiLog2TrSize;
1688    UInt  uiZOrder    = pcCU->getZorderIdxInCU() + uiAbsPartIdx;
1689    Pel*  piSrc       = m_pcQTTempTComYuv[ uiQTLayer ].getLumaAddr( uiAbsPartIdx );
1690    UInt  uiSrcStride = m_pcQTTempTComYuv[ uiQTLayer ].getStride  ();
1691    Pel*  piDes       = pcCU->getPic()->getPicYuvRec()->getLumaAddr( pcCU->getAddr(), uiZOrder );
1692    UInt  uiDesStride = pcCU->getPic()->getPicYuvRec()->getStride  ();
1693    for( UInt uiY = 0; uiY < uiHeight; uiY++, piSrc += uiSrcStride, piDes += uiDesStride )
1694    {
1695      for( UInt uiX = 0; uiX < uiWidth; uiX++ )
1696      {
1697        piDes[ uiX ] = piSrc[ uiX ];
1698      }
1699    }
1700    if( !bLumaOnly )
1701    {
1702      uiWidth   >>= 1;
1703      uiHeight  >>= 1;
1704      piSrc       = m_pcQTTempTComYuv[ uiQTLayer ].getCbAddr  ( uiAbsPartIdx );
1705      uiSrcStride = m_pcQTTempTComYuv[ uiQTLayer ].getCStride ();
1706      piDes       = pcCU->getPic()->getPicYuvRec()->getCbAddr ( pcCU->getAddr(), uiZOrder );
1707      uiDesStride = pcCU->getPic()->getPicYuvRec()->getCStride();
1708      for( UInt uiY = 0; uiY < uiHeight; uiY++, piSrc += uiSrcStride, piDes += uiDesStride )
1709      {
1710        for( UInt uiX = 0; uiX < uiWidth; uiX++ )
1711        {
1712          piDes[ uiX ] = piSrc[ uiX ];
1713        }
1714      }
1715      piSrc       = m_pcQTTempTComYuv[ uiQTLayer ].getCrAddr  ( uiAbsPartIdx );
1716      piDes       = pcCU->getPic()->getPicYuvRec()->getCrAddr ( pcCU->getAddr(), uiZOrder );
1717      for( UInt uiY = 0; uiY < uiHeight; uiY++, piSrc += uiSrcStride, piDes += uiDesStride )
1718      {
1719        for( UInt uiX = 0; uiX < uiWidth; uiX++ )
1720        {
1721          piDes[ uiX ] = piSrc[ uiX ];
1722        }
1723      }
1724    }
1725  }
1726  ruiDistY += uiSingleDistY;
1727  ruiDistC += uiSingleDistC;
1728  dRDCost  += dSingleCost;
1729}
1730
1731
1732Void
1733TEncSearch::xSetIntraResultQT( TComDataCU* pcCU,
1734                              UInt        uiTrDepth,
1735                              UInt        uiAbsPartIdx,
1736                              Bool        bLumaOnly,
1737                              TComYuv*    pcRecoYuv )
1738{
1739  UInt uiFullDepth  = pcCU->getDepth(0) + uiTrDepth;
1740  UInt uiTrMode     = pcCU->getTransformIdx( uiAbsPartIdx );
1741  if(  uiTrMode == uiTrDepth )
1742  {
1743    UInt uiLog2TrSize = g_aucConvertToBit[ pcCU->getSlice()->getSPS()->getMaxCUWidth() >> uiFullDepth ] + 2;
1744    UInt uiQTLayer    = pcCU->getSlice()->getSPS()->getQuadtreeTULog2MaxSize() - uiLog2TrSize;
1745   
1746    Bool bSkipChroma  = false;
1747    Bool bChromaSame  = false;
1748    if( !bLumaOnly && uiLog2TrSize == 2 )
1749    {
1750      assert( uiTrDepth > 0 );
1751      UInt uiQPDiv = pcCU->getPic()->getNumPartInCU() >> ( ( pcCU->getDepth( 0 ) + uiTrDepth - 1 ) << 1 );
1752      bSkipChroma  = ( ( uiAbsPartIdx % uiQPDiv ) != 0 );
1753      bChromaSame  = true;
1754    }
1755   
1756    //===== copy transform coefficients =====
1757    UInt uiNumCoeffY    = ( pcCU->getSlice()->getSPS()->getMaxCUWidth() * pcCU->getSlice()->getSPS()->getMaxCUHeight() ) >> ( uiFullDepth << 1 );
1758    UInt uiNumCoeffIncY = ( pcCU->getSlice()->getSPS()->getMaxCUWidth() * pcCU->getSlice()->getSPS()->getMaxCUHeight() ) >> ( pcCU->getSlice()->getSPS()->getMaxCUDepth() << 1 );
1759    TCoeff* pcCoeffSrcY = m_ppcQTTempCoeffY [ uiQTLayer ] + ( uiNumCoeffIncY * uiAbsPartIdx );
1760    TCoeff* pcCoeffDstY = pcCU->getCoeffY ()              + ( uiNumCoeffIncY * uiAbsPartIdx );
1761    ::memcpy( pcCoeffDstY, pcCoeffSrcY, sizeof( TCoeff ) * uiNumCoeffY );
1762#if ADAPTIVE_QP_SELECTION
1763    Int* pcArlCoeffSrcY = m_ppcQTTempArlCoeffY [ uiQTLayer ] + ( uiNumCoeffIncY * uiAbsPartIdx );
1764    Int* pcArlCoeffDstY = pcCU->getArlCoeffY ()              + ( uiNumCoeffIncY * uiAbsPartIdx );
1765    ::memcpy( pcArlCoeffDstY, pcArlCoeffSrcY, sizeof( Int ) * uiNumCoeffY );
1766#endif
1767    if( !bLumaOnly && !bSkipChroma )
1768    {
1769      UInt uiNumCoeffC    = ( bChromaSame ? uiNumCoeffY    : uiNumCoeffY    >> 2 );
1770      UInt uiNumCoeffIncC = uiNumCoeffIncY >> 2;
1771      TCoeff* pcCoeffSrcU = m_ppcQTTempCoeffCb[ uiQTLayer ] + ( uiNumCoeffIncC * uiAbsPartIdx );
1772      TCoeff* pcCoeffSrcV = m_ppcQTTempCoeffCr[ uiQTLayer ] + ( uiNumCoeffIncC * uiAbsPartIdx );
1773      TCoeff* pcCoeffDstU = pcCU->getCoeffCb()              + ( uiNumCoeffIncC * uiAbsPartIdx );
1774      TCoeff* pcCoeffDstV = pcCU->getCoeffCr()              + ( uiNumCoeffIncC * uiAbsPartIdx );
1775      ::memcpy( pcCoeffDstU, pcCoeffSrcU, sizeof( TCoeff ) * uiNumCoeffC );
1776      ::memcpy( pcCoeffDstV, pcCoeffSrcV, sizeof( TCoeff ) * uiNumCoeffC );
1777#if ADAPTIVE_QP_SELECTION
1778      Int* pcArlCoeffSrcU = m_ppcQTTempArlCoeffCb[ uiQTLayer ] + ( uiNumCoeffIncC * uiAbsPartIdx );
1779      Int* pcArlCoeffSrcV = m_ppcQTTempArlCoeffCr[ uiQTLayer ] + ( uiNumCoeffIncC * uiAbsPartIdx );
1780      Int* pcArlCoeffDstU = pcCU->getArlCoeffCb()              + ( uiNumCoeffIncC * uiAbsPartIdx );
1781      Int* pcArlCoeffDstV = pcCU->getArlCoeffCr()              + ( uiNumCoeffIncC * uiAbsPartIdx );
1782      ::memcpy( pcArlCoeffDstU, pcArlCoeffSrcU, sizeof( Int ) * uiNumCoeffC );
1783      ::memcpy( pcArlCoeffDstV, pcArlCoeffSrcV, sizeof( Int ) * uiNumCoeffC );
1784#endif
1785    }
1786   
1787    //===== copy reconstruction =====
1788    m_pcQTTempTComYuv[ uiQTLayer ].copyPartToPartLuma( pcRecoYuv, uiAbsPartIdx, 1 << uiLog2TrSize, 1 << uiLog2TrSize );
1789    if( !bLumaOnly && !bSkipChroma )
1790    {
1791      UInt uiLog2TrSizeChroma = ( bChromaSame ? uiLog2TrSize : uiLog2TrSize - 1 );
1792      m_pcQTTempTComYuv[ uiQTLayer ].copyPartToPartChroma( pcRecoYuv, uiAbsPartIdx, 1 << uiLog2TrSizeChroma, 1 << uiLog2TrSizeChroma );
1793    }
1794  }
1795  else
1796  {
1797    UInt uiNumQPart  = pcCU->getPic()->getNumPartInCU() >> ( ( uiFullDepth + 1 ) << 1 );
1798    for( UInt uiPart = 0; uiPart < 4; uiPart++ )
1799    {
1800      xSetIntraResultQT( pcCU, uiTrDepth + 1, uiAbsPartIdx + uiPart * uiNumQPart, bLumaOnly, pcRecoYuv );
1801    }
1802  }
1803}
1804
1805Void
1806TEncSearch::xStoreIntraResultQT( TComDataCU* pcCU,
1807                                UInt        uiTrDepth,
1808                                UInt        uiAbsPartIdx,
1809                                Bool        bLumaOnly )
1810{
1811  UInt uiFullDepth  = pcCU->getDepth(0) + uiTrDepth;
1812  UInt uiTrMode     = pcCU->getTransformIdx( uiAbsPartIdx );
1813  assert(  uiTrMode == uiTrDepth );
1814  UInt uiLog2TrSize = g_aucConvertToBit[ pcCU->getSlice()->getSPS()->getMaxCUWidth() >> uiFullDepth ] + 2;
1815  UInt uiQTLayer    = pcCU->getSlice()->getSPS()->getQuadtreeTULog2MaxSize() - uiLog2TrSize;
1816
1817  Bool bSkipChroma  = false;
1818  Bool bChromaSame  = false;
1819  if( !bLumaOnly && uiLog2TrSize == 2 )
1820  {
1821    assert( uiTrDepth > 0 );
1822    UInt uiQPDiv = pcCU->getPic()->getNumPartInCU() >> ( ( pcCU->getDepth( 0 ) + uiTrDepth - 1 ) << 1 );
1823    bSkipChroma  = ( ( uiAbsPartIdx % uiQPDiv ) != 0 );
1824    bChromaSame  = true;
1825  }
1826
1827  //===== copy transform coefficients =====
1828  UInt uiNumCoeffY    = ( pcCU->getSlice()->getSPS()->getMaxCUWidth() * pcCU->getSlice()->getSPS()->getMaxCUHeight() ) >> ( uiFullDepth << 1 );
1829  UInt uiNumCoeffIncY = ( pcCU->getSlice()->getSPS()->getMaxCUWidth() * pcCU->getSlice()->getSPS()->getMaxCUHeight() ) >> ( pcCU->getSlice()->getSPS()->getMaxCUDepth() << 1 );
1830  TCoeff* pcCoeffSrcY = m_ppcQTTempCoeffY [ uiQTLayer ] + ( uiNumCoeffIncY * uiAbsPartIdx );
1831  TCoeff* pcCoeffDstY = m_pcQTTempTUCoeffY;
1832
1833  ::memcpy( pcCoeffDstY, pcCoeffSrcY, sizeof( TCoeff ) * uiNumCoeffY );
1834#if ADAPTIVE_QP_SELECTION
1835  Int* pcArlCoeffSrcY = m_ppcQTTempArlCoeffY [ uiQTLayer ] + ( uiNumCoeffIncY * uiAbsPartIdx );
1836  Int* pcArlCoeffDstY = m_ppcQTTempTUArlCoeffY;
1837  ::memcpy( pcArlCoeffDstY, pcArlCoeffSrcY, sizeof( Int ) * uiNumCoeffY );
1838#endif
1839  if( !bLumaOnly && !bSkipChroma )
1840  {
1841    UInt uiNumCoeffC    = ( bChromaSame ? uiNumCoeffY    : uiNumCoeffY    >> 2 );
1842    UInt uiNumCoeffIncC = uiNumCoeffIncY >> 2;
1843    TCoeff* pcCoeffSrcU = m_ppcQTTempCoeffCb[ uiQTLayer ] + ( uiNumCoeffIncC * uiAbsPartIdx );
1844    TCoeff* pcCoeffSrcV = m_ppcQTTempCoeffCr[ uiQTLayer ] + ( uiNumCoeffIncC * uiAbsPartIdx );
1845    TCoeff* pcCoeffDstU = m_pcQTTempTUCoeffCb;
1846    TCoeff* pcCoeffDstV = m_pcQTTempTUCoeffCr;
1847    ::memcpy( pcCoeffDstU, pcCoeffSrcU, sizeof( TCoeff ) * uiNumCoeffC );
1848    ::memcpy( pcCoeffDstV, pcCoeffSrcV, sizeof( TCoeff ) * uiNumCoeffC );
1849#if ADAPTIVE_QP_SELECTION
1850    Int* pcArlCoeffSrcU = m_ppcQTTempArlCoeffCb[ uiQTLayer ] + ( uiNumCoeffIncC * uiAbsPartIdx );
1851    Int* pcArlCoeffSrcV = m_ppcQTTempArlCoeffCr[ uiQTLayer ] + ( uiNumCoeffIncC * uiAbsPartIdx );
1852    Int* pcArlCoeffDstU = m_ppcQTTempTUArlCoeffCb;
1853    Int* pcArlCoeffDstV = m_ppcQTTempTUArlCoeffCr;
1854    ::memcpy( pcArlCoeffDstU, pcArlCoeffSrcU, sizeof( Int ) * uiNumCoeffC );
1855    ::memcpy( pcArlCoeffDstV, pcArlCoeffSrcV, sizeof( Int ) * uiNumCoeffC );
1856#endif
1857  }
1858
1859  //===== copy reconstruction =====
1860  m_pcQTTempTComYuv[ uiQTLayer ].copyPartToPartLuma( &m_pcQTTempTransformSkipTComYuv, uiAbsPartIdx, 1 << uiLog2TrSize, 1 << uiLog2TrSize );
1861
1862  if( !bLumaOnly && !bSkipChroma )
1863  {
1864    UInt uiLog2TrSizeChroma = ( bChromaSame ? uiLog2TrSize : uiLog2TrSize - 1 );
1865    m_pcQTTempTComYuv[ uiQTLayer ].copyPartToPartChroma( &m_pcQTTempTransformSkipTComYuv, uiAbsPartIdx, 1 << uiLog2TrSizeChroma, 1 << uiLog2TrSizeChroma );
1866  }
1867}
1868
1869Void
1870TEncSearch::xLoadIntraResultQT( TComDataCU* pcCU,
1871                               UInt        uiTrDepth,
1872                               UInt        uiAbsPartIdx,
1873                               Bool        bLumaOnly )
1874{
1875  UInt uiFullDepth  = pcCU->getDepth(0) + uiTrDepth;
1876  UInt uiTrMode     = pcCU->getTransformIdx( uiAbsPartIdx );
1877  assert(  uiTrMode == uiTrDepth );
1878  UInt uiLog2TrSize = g_aucConvertToBit[ pcCU->getSlice()->getSPS()->getMaxCUWidth() >> uiFullDepth ] + 2;
1879  UInt uiQTLayer    = pcCU->getSlice()->getSPS()->getQuadtreeTULog2MaxSize() - uiLog2TrSize;
1880
1881  Bool bSkipChroma  = false;
1882  Bool bChromaSame  = false;
1883  if( !bLumaOnly && uiLog2TrSize == 2 )
1884  {
1885    assert( uiTrDepth > 0 );
1886    UInt uiQPDiv = pcCU->getPic()->getNumPartInCU() >> ( ( pcCU->getDepth( 0 ) + uiTrDepth - 1 ) << 1 );
1887    bSkipChroma  = ( ( uiAbsPartIdx % uiQPDiv ) != 0 );
1888    bChromaSame  = true;
1889  }
1890
1891  //===== copy transform coefficients =====
1892  UInt uiNumCoeffY    = ( pcCU->getSlice()->getSPS()->getMaxCUWidth() * pcCU->getSlice()->getSPS()->getMaxCUHeight() ) >> ( uiFullDepth << 1 );
1893  UInt uiNumCoeffIncY = ( pcCU->getSlice()->getSPS()->getMaxCUWidth() * pcCU->getSlice()->getSPS()->getMaxCUHeight() ) >> ( pcCU->getSlice()->getSPS()->getMaxCUDepth() << 1 );
1894  TCoeff* pcCoeffDstY = m_ppcQTTempCoeffY [ uiQTLayer ] + ( uiNumCoeffIncY * uiAbsPartIdx );
1895  TCoeff* pcCoeffSrcY = m_pcQTTempTUCoeffY;
1896
1897  ::memcpy( pcCoeffDstY, pcCoeffSrcY, sizeof( TCoeff ) * uiNumCoeffY );
1898#if ADAPTIVE_QP_SELECTION
1899  Int* pcArlCoeffDstY = m_ppcQTTempArlCoeffY [ uiQTLayer ] + ( uiNumCoeffIncY * uiAbsPartIdx );
1900  Int* pcArlCoeffSrcY = m_ppcQTTempTUArlCoeffY;
1901  ::memcpy( pcArlCoeffDstY, pcArlCoeffSrcY, sizeof( Int ) * uiNumCoeffY );
1902#endif
1903  if( !bLumaOnly && !bSkipChroma )
1904  {
1905    UInt uiNumCoeffC    = ( bChromaSame ? uiNumCoeffY    : uiNumCoeffY    >> 2 );
1906    UInt uiNumCoeffIncC = uiNumCoeffIncY >> 2;
1907    TCoeff* pcCoeffDstU = m_ppcQTTempCoeffCb[ uiQTLayer ] + ( uiNumCoeffIncC * uiAbsPartIdx );
1908    TCoeff* pcCoeffDstV = m_ppcQTTempCoeffCr[ uiQTLayer ] + ( uiNumCoeffIncC * uiAbsPartIdx );
1909    TCoeff* pcCoeffSrcU = m_pcQTTempTUCoeffCb;
1910    TCoeff* pcCoeffSrcV = m_pcQTTempTUCoeffCr;
1911    ::memcpy( pcCoeffDstU, pcCoeffSrcU, sizeof( TCoeff ) * uiNumCoeffC );
1912    ::memcpy( pcCoeffDstV, pcCoeffSrcV, sizeof( TCoeff ) * uiNumCoeffC );
1913#if ADAPTIVE_QP_SELECTION
1914    Int* pcArlCoeffDstU = m_ppcQTTempArlCoeffCb[ uiQTLayer ] + ( uiNumCoeffIncC * uiAbsPartIdx );
1915    Int* pcArlCoeffDstV = m_ppcQTTempArlCoeffCr[ uiQTLayer ] + ( uiNumCoeffIncC * uiAbsPartIdx );
1916    Int* pcArlCoeffSrcU = m_ppcQTTempTUArlCoeffCb;
1917    Int* pcArlCoeffSrcV = m_ppcQTTempTUArlCoeffCr;
1918    ::memcpy( pcArlCoeffDstU, pcArlCoeffSrcU, sizeof( Int ) * uiNumCoeffC );
1919    ::memcpy( pcArlCoeffDstV, pcArlCoeffSrcV, sizeof( Int ) * uiNumCoeffC );
1920#endif
1921  }
1922
1923  //===== copy reconstruction =====
1924  m_pcQTTempTransformSkipTComYuv.copyPartToPartLuma( &m_pcQTTempTComYuv[ uiQTLayer ] , uiAbsPartIdx, 1 << uiLog2TrSize, 1 << uiLog2TrSize );
1925
1926  if( !bLumaOnly && !bSkipChroma )
1927  {
1928    UInt uiLog2TrSizeChroma = ( bChromaSame ? uiLog2TrSize : uiLog2TrSize - 1 );
1929    m_pcQTTempTransformSkipTComYuv.copyPartToPartChroma( &m_pcQTTempTComYuv[ uiQTLayer ], uiAbsPartIdx, 1 << uiLog2TrSizeChroma, 1 << uiLog2TrSizeChroma );
1930  }
1931
1932  UInt    uiZOrder          = pcCU->getZorderIdxInCU() + uiAbsPartIdx;
1933  Pel*    piRecIPred        = pcCU->getPic()->getPicYuvRec()->getLumaAddr( pcCU->getAddr(), uiZOrder );
1934  UInt    uiRecIPredStride  = pcCU->getPic()->getPicYuvRec()->getStride  ();
1935  Pel*    piRecQt           = m_pcQTTempTComYuv[ uiQTLayer ].getLumaAddr( uiAbsPartIdx );
1936  UInt    uiRecQtStride     = m_pcQTTempTComYuv[ uiQTLayer ].getStride  ();
1937  UInt    uiWidth           = pcCU     ->getWidth   ( 0 ) >> uiTrDepth;
1938  UInt    uiHeight          = pcCU     ->getHeight  ( 0 ) >> uiTrDepth;
1939  Pel* pRecQt     = piRecQt;
1940  Pel* pRecIPred  = piRecIPred;
1941  for( UInt uiY = 0; uiY < uiHeight; uiY++ )
1942  {
1943    for( UInt uiX = 0; uiX < uiWidth; uiX++ )
1944    {
1945      pRecIPred[ uiX ] = pRecQt   [ uiX ];
1946    }
1947    pRecQt    += uiRecQtStride;
1948    pRecIPred += uiRecIPredStride;
1949  }
1950
1951  if( !bLumaOnly && !bSkipChroma )
1952  {
1953    piRecIPred = pcCU->getPic()->getPicYuvRec()->getCbAddr( pcCU->getAddr(), uiZOrder );
1954    piRecQt    = m_pcQTTempTComYuv[ uiQTLayer ].getCbAddr( uiAbsPartIdx );
1955    pRecQt     = piRecQt;
1956    pRecIPred  = piRecIPred;
1957    for( UInt uiY = 0; uiY < uiHeight; uiY++ )
1958    {
1959      for( UInt uiX = 0; uiX < uiWidth; uiX++ )
1960      {
1961        pRecIPred[ uiX ] = pRecQt[ uiX ];
1962      }
1963      pRecQt    += uiRecQtStride;
1964      pRecIPred += uiRecIPredStride;
1965    }
1966
1967    piRecIPred = pcCU->getPic()->getPicYuvRec()->getCrAddr( pcCU->getAddr(), uiZOrder );
1968    piRecQt    = m_pcQTTempTComYuv[ uiQTLayer ].getCrAddr( uiAbsPartIdx );
1969    pRecQt     = piRecQt;
1970    pRecIPred  = piRecIPred;
1971    for( UInt uiY = 0; uiY < uiHeight; uiY++ )
1972    {
1973      for( UInt uiX = 0; uiX < uiWidth; uiX++ )
1974      {
1975        pRecIPred[ uiX ] = pRecQt[ uiX ];
1976      }
1977      pRecQt    += uiRecQtStride;
1978      pRecIPred += uiRecIPredStride;
1979    }
1980  }
1981}
1982
1983Void
1984TEncSearch::xStoreIntraResultChromaQT( TComDataCU* pcCU,
1985                                      UInt        uiTrDepth,
1986                                      UInt        uiAbsPartIdx,
1987                                      UInt        stateU0V1Both2 )
1988{
1989  UInt uiFullDepth = pcCU->getDepth(0) + uiTrDepth;
1990  UInt uiTrMode    = pcCU->getTransformIdx( uiAbsPartIdx );
1991  if(  uiTrMode == uiTrDepth )
1992  {
1993    UInt uiLog2TrSize = g_aucConvertToBit[ pcCU->getSlice()->getSPS()->getMaxCUWidth() >> uiFullDepth ] + 2;
1994    UInt uiQTLayer    = pcCU->getSlice()->getSPS()->getQuadtreeTULog2MaxSize() - uiLog2TrSize;
1995
1996    Bool bChromaSame = false;
1997    if( uiLog2TrSize == 2 )
1998    {
1999      assert( uiTrDepth > 0 );
2000      uiTrDepth --;
2001      UInt uiQPDiv = pcCU->getPic()->getNumPartInCU() >> ( ( pcCU->getDepth( 0 ) + uiTrDepth) << 1 );
2002      if( ( uiAbsPartIdx % uiQPDiv ) != 0 )
2003      {
2004        return;
2005      }
2006      bChromaSame = true;
2007    }
2008
2009    //===== copy transform coefficients =====
2010    UInt uiNumCoeffC    = ( pcCU->getSlice()->getSPS()->getMaxCUWidth() * pcCU->getSlice()->getSPS()->getMaxCUHeight() ) >> ( uiFullDepth << 1 );
2011    if( !bChromaSame )
2012    {
2013      uiNumCoeffC     >>= 2;
2014    }
2015    UInt uiNumCoeffIncC = ( pcCU->getSlice()->getSPS()->getMaxCUWidth() * pcCU->getSlice()->getSPS()->getMaxCUHeight() ) >> ( ( pcCU->getSlice()->getSPS()->getMaxCUDepth() << 1 ) + 2 );
2016    if(stateU0V1Both2 == 0 || stateU0V1Both2 == 2)
2017    {
2018      TCoeff* pcCoeffSrcU = m_ppcQTTempCoeffCb[ uiQTLayer ] + ( uiNumCoeffIncC * uiAbsPartIdx );
2019      TCoeff* pcCoeffDstU = m_pcQTTempTUCoeffCb;
2020      ::memcpy( pcCoeffDstU, pcCoeffSrcU, sizeof( TCoeff ) * uiNumCoeffC );
2021
2022#if ADAPTIVE_QP_SELECTION   
2023      Int* pcArlCoeffSrcU = m_ppcQTTempArlCoeffCb[ uiQTLayer ] + ( uiNumCoeffIncC * uiAbsPartIdx );
2024      Int* pcArlCoeffDstU = m_ppcQTTempTUArlCoeffCb;
2025      ::memcpy( pcArlCoeffDstU, pcArlCoeffSrcU, sizeof( Int ) * uiNumCoeffC );
2026#endif
2027    }
2028    if(stateU0V1Both2 == 1 || stateU0V1Both2 == 2)
2029    {
2030      TCoeff* pcCoeffSrcV = m_ppcQTTempCoeffCr[ uiQTLayer ] + ( uiNumCoeffIncC * uiAbsPartIdx );
2031      TCoeff* pcCoeffDstV = m_pcQTTempTUCoeffCr;
2032      ::memcpy( pcCoeffDstV, pcCoeffSrcV, sizeof( TCoeff ) * uiNumCoeffC );
2033#if ADAPTIVE_QP_SELECTION   
2034      Int* pcArlCoeffSrcV = m_ppcQTTempArlCoeffCr[ uiQTLayer ] + ( uiNumCoeffIncC * uiAbsPartIdx );
2035      Int* pcArlCoeffDstV = m_ppcQTTempTUArlCoeffCr;
2036      ::memcpy( pcArlCoeffDstV, pcArlCoeffSrcV, sizeof( Int ) * uiNumCoeffC );
2037#endif
2038    }
2039
2040    //===== copy reconstruction =====
2041    UInt uiLog2TrSizeChroma = ( bChromaSame ? uiLog2TrSize : uiLog2TrSize - 1 );
2042    m_pcQTTempTComYuv[ uiQTLayer ].copyPartToPartChroma(&m_pcQTTempTransformSkipTComYuv, uiAbsPartIdx, 1 << uiLog2TrSizeChroma, 1 << uiLog2TrSizeChroma, stateU0V1Both2 );
2043  }
2044}
2045
2046
2047Void
2048TEncSearch::xLoadIntraResultChromaQT( TComDataCU* pcCU,
2049                                     UInt        uiTrDepth,
2050                                     UInt        uiAbsPartIdx,
2051                                     UInt        stateU0V1Both2 )
2052{
2053  UInt uiFullDepth = pcCU->getDepth(0) + uiTrDepth;
2054  UInt uiTrMode    = pcCU->getTransformIdx( uiAbsPartIdx );
2055  if(  uiTrMode == uiTrDepth )
2056  {
2057    UInt uiLog2TrSize = g_aucConvertToBit[ pcCU->getSlice()->getSPS()->getMaxCUWidth() >> uiFullDepth ] + 2;
2058    UInt uiQTLayer    = pcCU->getSlice()->getSPS()->getQuadtreeTULog2MaxSize() - uiLog2TrSize;
2059
2060    Bool bChromaSame = false;
2061    if( uiLog2TrSize == 2 )
2062    {
2063      assert( uiTrDepth > 0 );
2064      uiTrDepth --;
2065      UInt uiQPDiv = pcCU->getPic()->getNumPartInCU() >> ( ( pcCU->getDepth( 0 ) + uiTrDepth ) << 1 );
2066      if( ( uiAbsPartIdx % uiQPDiv ) != 0 )
2067      {
2068        return;
2069      }
2070      bChromaSame = true;
2071    }
2072
2073    //===== copy transform coefficients =====
2074    UInt uiNumCoeffC = ( pcCU->getSlice()->getSPS()->getMaxCUWidth() * pcCU->getSlice()->getSPS()->getMaxCUHeight() ) >> ( uiFullDepth << 1 );
2075    if( !bChromaSame )
2076    {
2077      uiNumCoeffC >>= 2;
2078    }
2079    UInt uiNumCoeffIncC = ( pcCU->getSlice()->getSPS()->getMaxCUWidth() * pcCU->getSlice()->getSPS()->getMaxCUHeight() ) >> ( ( pcCU->getSlice()->getSPS()->getMaxCUDepth() << 1 ) + 2 );
2080
2081    if(stateU0V1Both2 ==0 || stateU0V1Both2 == 2)
2082    {
2083      TCoeff* pcCoeffDstU = m_ppcQTTempCoeffCb[ uiQTLayer ] + ( uiNumCoeffIncC * uiAbsPartIdx );
2084      TCoeff* pcCoeffSrcU = m_pcQTTempTUCoeffCb;
2085      ::memcpy( pcCoeffDstU, pcCoeffSrcU, sizeof( TCoeff ) * uiNumCoeffC );
2086#if ADAPTIVE_QP_SELECTION   
2087      Int* pcArlCoeffDstU = m_ppcQTTempArlCoeffCb[ uiQTLayer ] + ( uiNumCoeffIncC * uiAbsPartIdx );
2088      Int* pcArlCoeffSrcU = m_ppcQTTempTUArlCoeffCb;
2089      ::memcpy( pcArlCoeffDstU, pcArlCoeffSrcU, sizeof( Int ) * uiNumCoeffC );
2090#endif
2091    }
2092    if(stateU0V1Both2 ==1 || stateU0V1Both2 == 2)
2093    {
2094      TCoeff* pcCoeffDstV = m_ppcQTTempCoeffCr[ uiQTLayer ] + ( uiNumCoeffIncC * uiAbsPartIdx );
2095      TCoeff* pcCoeffSrcV = m_pcQTTempTUCoeffCr;
2096      ::memcpy( pcCoeffDstV, pcCoeffSrcV, sizeof( TCoeff ) * uiNumCoeffC );
2097#if ADAPTIVE_QP_SELECTION   
2098      Int* pcArlCoeffDstV = m_ppcQTTempArlCoeffCr[ uiQTLayer ] + ( uiNumCoeffIncC * uiAbsPartIdx );
2099      Int* pcArlCoeffSrcV = m_ppcQTTempTUArlCoeffCr;       
2100      ::memcpy( pcArlCoeffDstV, pcArlCoeffSrcV, sizeof( Int ) * uiNumCoeffC );
2101#endif
2102    }
2103
2104    //===== copy reconstruction =====
2105    UInt uiLog2TrSizeChroma = ( bChromaSame ? uiLog2TrSize : uiLog2TrSize - 1 );
2106    m_pcQTTempTransformSkipTComYuv.copyPartToPartChroma( &m_pcQTTempTComYuv[ uiQTLayer ], uiAbsPartIdx, 1 << uiLog2TrSizeChroma, 1 << uiLog2TrSizeChroma, stateU0V1Both2);
2107
2108    UInt    uiZOrder          = pcCU->getZorderIdxInCU() + uiAbsPartIdx;
2109    UInt    uiWidth           = pcCU->getWidth   ( 0 ) >> (uiTrDepth + 1);
2110    UInt    uiHeight          = pcCU->getHeight  ( 0 ) >> (uiTrDepth + 1);
2111    UInt    uiRecQtStride     = m_pcQTTempTComYuv[ uiQTLayer ].getCStride  ();
2112    UInt    uiRecIPredStride  = pcCU->getPic()->getPicYuvRec()->getCStride  ();
2113
2114    if(stateU0V1Both2 ==0 || stateU0V1Both2 == 2)
2115    {
2116      Pel* piRecIPred = pcCU->getPic()->getPicYuvRec()->getCbAddr( pcCU->getAddr(), uiZOrder );
2117      Pel* piRecQt    = m_pcQTTempTComYuv[ uiQTLayer ].getCbAddr( uiAbsPartIdx );
2118      Pel* pRecQt     = piRecQt;
2119      Pel* pRecIPred  = piRecIPred;
2120      for( UInt uiY = 0; uiY < uiHeight; uiY++ )
2121      {
2122        for( UInt uiX = 0; uiX < uiWidth; uiX++ )
2123        {
2124          pRecIPred[ uiX ] = pRecQt[ uiX ];
2125        }
2126        pRecQt    += uiRecQtStride;
2127        pRecIPred += uiRecIPredStride;
2128      }
2129    }
2130    if(stateU0V1Both2 == 1 || stateU0V1Both2 == 2)
2131    {
2132      Pel* piRecIPred = pcCU->getPic()->getPicYuvRec()->getCrAddr( pcCU->getAddr(), uiZOrder );
2133      Pel* piRecQt    = m_pcQTTempTComYuv[ uiQTLayer ].getCrAddr( uiAbsPartIdx );
2134      Pel* pRecQt     = piRecQt;
2135      Pel* pRecIPred  = piRecIPred;
2136      for( UInt uiY = 0; uiY < uiHeight; uiY++ )
2137      {
2138        for( UInt uiX = 0; uiX < uiWidth; uiX++ )
2139        {
2140          pRecIPred[ uiX ] = pRecQt[ uiX ];
2141        }
2142        pRecQt    += uiRecQtStride;
2143        pRecIPred += uiRecIPredStride;
2144      }
2145    }
2146  }
2147}
2148
2149Void
2150TEncSearch::xRecurIntraChromaCodingQT( TComDataCU*  pcCU, 
2151                                      UInt         uiTrDepth,
2152                                      UInt         uiAbsPartIdx, 
2153                                      TComYuv*     pcOrgYuv, 
2154                                      TComYuv*     pcPredYuv, 
2155                                      TComYuv*     pcResiYuv, 
2156                                      UInt&        ruiDist )
2157{
2158  UInt uiFullDepth = pcCU->getDepth( 0 ) +  uiTrDepth;
2159  UInt uiTrMode    = pcCU->getTransformIdx( uiAbsPartIdx );
2160  if(  uiTrMode == uiTrDepth )
2161  {
2162    Bool checkTransformSkip = pcCU->getSlice()->getPPS()->getUseTransformSkip();
2163    UInt uiLog2TrSize = g_aucConvertToBit[ pcCU->getSlice()->getSPS()->getMaxCUWidth() >> uiFullDepth ] + 2;
2164
2165    UInt actualTrDepth = uiTrDepth;
2166    if( uiLog2TrSize == 2 )
2167    {
2168      assert( uiTrDepth > 0 );
2169      actualTrDepth--;
2170      UInt uiQPDiv = pcCU->getPic()->getNumPartInCU() >> ( ( pcCU->getDepth( 0 ) + actualTrDepth) << 1 );
2171      Bool bFirstQ = ( ( uiAbsPartIdx % uiQPDiv ) == 0 );
2172      if( !bFirstQ )
2173      {
2174        return;
2175      }
2176    }
2177
2178    checkTransformSkip &= (uiLog2TrSize <= 3);
2179    if ( m_pcEncCfg->getUseTransformSkipFast() )
2180    {
2181      checkTransformSkip &= (uiLog2TrSize < 3);
2182      if (checkTransformSkip)
2183      {
2184        Int nbLumaSkip = 0;
2185        for(UInt absPartIdxSub = uiAbsPartIdx; absPartIdxSub < uiAbsPartIdx + 4; absPartIdxSub ++)
2186        {
2187          nbLumaSkip += pcCU->getTransformSkip(absPartIdxSub, TEXT_LUMA);
2188        }
2189        checkTransformSkip &= (nbLumaSkip > 0);
2190      }
2191    }
2192
2193    if(checkTransformSkip)
2194    {
2195        //use RDO to decide whether Cr/Cb takes TS
2196        if( m_bUseSBACRD )
2197        {
2198          m_pcRDGoOnSbacCoder->store( m_pppcRDSbacCoder[uiFullDepth][CI_QT_TRAFO_ROOT] );
2199        }
2200
2201        for(Int chromaId = 0; chromaId < 2; chromaId ++)
2202        {
2203          Double  dSingleCost    = MAX_DOUBLE;
2204          Int     bestModeId     = 0;
2205          UInt    singleDistC    = 0;
2206          UInt    singleCbfC     = 0;
2207          UInt    singleDistCTmp = 0;
2208          Double  singleCostTmp  = 0;
2209          UInt    singleCbfCTmp  = 0;
2210
2211          Int     default0Save1Load2 = 0;
2212          Int     firstCheckId       = 0;
2213
2214          for(Int chromaModeId = firstCheckId; chromaModeId < 2; chromaModeId ++)
2215          {
2216            pcCU->setTransformSkipSubParts ( chromaModeId, (TextType)(chromaId + 2), uiAbsPartIdx, pcCU->getDepth( 0 ) +  actualTrDepth); 
2217            if(chromaModeId == firstCheckId)
2218            {
2219              default0Save1Load2 = 1;
2220            }
2221            else
2222            {
2223              default0Save1Load2 = 2;
2224            }
2225            singleDistCTmp = 0;
2226            xIntraCodingChromaBlk( pcCU, uiTrDepth, uiAbsPartIdx, pcOrgYuv, pcPredYuv, pcResiYuv, singleDistCTmp, chromaId ,default0Save1Load2);
2227            singleCbfCTmp = pcCU->getCbf( uiAbsPartIdx, (TextType)(chromaId + 2), uiTrDepth);
2228           
2229            if(chromaModeId == 1 && singleCbfCTmp == 0)
2230            {
2231              //In order not to code TS flag when cbf is zero, the case for TS with cbf being zero is forbidden.
2232              singleCostTmp = MAX_DOUBLE;
2233            }
2234            else
2235            {
2236              UInt bitsTmp = xGetIntraBitsQTChroma( pcCU,uiTrDepth, uiAbsPartIdx,chromaId + 2, false );
2237              singleCostTmp  = m_pcRdCost->calcRdCost( bitsTmp, singleDistCTmp);
2238            }
2239
2240            if(singleCostTmp < dSingleCost)
2241            {
2242              dSingleCost = singleCostTmp;
2243              singleDistC = singleDistCTmp;
2244              bestModeId  = chromaModeId;
2245              singleCbfC  = singleCbfCTmp;
2246
2247              if(bestModeId == firstCheckId)
2248              {
2249                xStoreIntraResultChromaQT(pcCU, uiTrDepth, uiAbsPartIdx,chromaId);
2250                if( m_bUseSBACRD) 
2251                {
2252                  m_pcRDGoOnSbacCoder->store( m_pppcRDSbacCoder[ uiFullDepth ][ CI_TEMP_BEST ] );
2253                }
2254              }
2255            }
2256            if(chromaModeId == firstCheckId)
2257            {
2258              m_pcRDGoOnSbacCoder->load ( m_pppcRDSbacCoder[ uiFullDepth ][ CI_QT_TRAFO_ROOT ] );
2259            }
2260          }
2261
2262          if(bestModeId == firstCheckId)
2263          {
2264            xLoadIntraResultChromaQT(pcCU, uiTrDepth, uiAbsPartIdx,chromaId);
2265            pcCU->setCbfSubParts ( singleCbfC << uiTrDepth, (TextType)(chromaId + 2), uiAbsPartIdx, pcCU->getDepth(0) + actualTrDepth );
2266            if(m_bUseSBACRD)
2267            {
2268              m_pcRDGoOnSbacCoder->load( m_pppcRDSbacCoder[ uiFullDepth ][ CI_TEMP_BEST ] );
2269            } 
2270          }
2271          pcCU ->setTransformSkipSubParts( bestModeId, (TextType)(chromaId + 2), uiAbsPartIdx, pcCU->getDepth( 0 ) +  actualTrDepth ); 
2272          ruiDist += singleDistC;
2273
2274          if(chromaId == 0)
2275          {
2276            if( m_bUseSBACRD )
2277            {
2278              m_pcRDGoOnSbacCoder->store( m_pppcRDSbacCoder[uiFullDepth][CI_QT_TRAFO_ROOT] );
2279            }
2280          }
2281        }
2282    }
2283    else
2284    {
2285      pcCU ->setTransformSkipSubParts( 0, TEXT_CHROMA_U, uiAbsPartIdx, pcCU->getDepth( 0 ) +  actualTrDepth ); 
2286      pcCU ->setTransformSkipSubParts( 0, TEXT_CHROMA_V, uiAbsPartIdx, pcCU->getDepth( 0 ) +  actualTrDepth ); 
2287      xIntraCodingChromaBlk( pcCU, uiTrDepth, uiAbsPartIdx, pcOrgYuv, pcPredYuv, pcResiYuv, ruiDist, 0 ); 
2288      xIntraCodingChromaBlk( pcCU, uiTrDepth, uiAbsPartIdx, pcOrgYuv, pcPredYuv, pcResiYuv, ruiDist, 1 ); 
2289    }
2290  }
2291  else
2292  {
2293    UInt uiSplitCbfU     = 0;
2294    UInt uiSplitCbfV     = 0;
2295    UInt uiQPartsDiv     = pcCU->getPic()->getNumPartInCU() >> ( ( uiFullDepth + 1 ) << 1 );
2296    UInt uiAbsPartIdxSub = uiAbsPartIdx;
2297    for( UInt uiPart = 0; uiPart < 4; uiPart++, uiAbsPartIdxSub += uiQPartsDiv )
2298    {
2299      xRecurIntraChromaCodingQT( pcCU, uiTrDepth + 1, uiAbsPartIdxSub, pcOrgYuv, pcPredYuv, pcResiYuv, ruiDist );
2300      uiSplitCbfU |= pcCU->getCbf( uiAbsPartIdxSub, TEXT_CHROMA_U, uiTrDepth + 1 );
2301      uiSplitCbfV |= pcCU->getCbf( uiAbsPartIdxSub, TEXT_CHROMA_V, uiTrDepth + 1 );
2302    }
2303    for( UInt uiOffs = 0; uiOffs < 4 * uiQPartsDiv; uiOffs++ )
2304    {
2305      pcCU->getCbf( TEXT_CHROMA_U )[ uiAbsPartIdx + uiOffs ] |= ( uiSplitCbfU << uiTrDepth );
2306      pcCU->getCbf( TEXT_CHROMA_V )[ uiAbsPartIdx + uiOffs ] |= ( uiSplitCbfV << uiTrDepth );
2307    }
2308  }
2309}
2310
2311Void
2312TEncSearch::xSetIntraResultChromaQT( TComDataCU* pcCU,
2313                                    UInt        uiTrDepth,
2314                                    UInt        uiAbsPartIdx,
2315                                    TComYuv*    pcRecoYuv )
2316{
2317  UInt uiFullDepth  = pcCU->getDepth(0) + uiTrDepth;
2318  UInt uiTrMode     = pcCU->getTransformIdx( uiAbsPartIdx );
2319  if(  uiTrMode == uiTrDepth )
2320  {
2321    UInt uiLog2TrSize = g_aucConvertToBit[ pcCU->getSlice()->getSPS()->getMaxCUWidth() >> uiFullDepth ] + 2;
2322    UInt uiQTLayer    = pcCU->getSlice()->getSPS()->getQuadtreeTULog2MaxSize() - uiLog2TrSize;
2323   
2324    Bool bChromaSame  = false;
2325    if( uiLog2TrSize == 2 )
2326    {
2327      assert( uiTrDepth > 0 );
2328      UInt uiQPDiv = pcCU->getPic()->getNumPartInCU() >> ( ( pcCU->getDepth( 0 ) + uiTrDepth - 1 ) << 1 );
2329      if( ( uiAbsPartIdx % uiQPDiv ) != 0 )
2330      {
2331        return;
2332      }
2333      bChromaSame     = true;
2334    }
2335   
2336    //===== copy transform coefficients =====
2337    UInt uiNumCoeffC    = ( pcCU->getSlice()->getSPS()->getMaxCUWidth() * pcCU->getSlice()->getSPS()->getMaxCUHeight() ) >> ( uiFullDepth << 1 );
2338    if( !bChromaSame )
2339    {
2340      uiNumCoeffC     >>= 2;
2341    }
2342    UInt uiNumCoeffIncC = ( pcCU->getSlice()->getSPS()->getMaxCUWidth() * pcCU->getSlice()->getSPS()->getMaxCUHeight() ) >> ( ( pcCU->getSlice()->getSPS()->getMaxCUDepth() << 1 ) + 2 );
2343    TCoeff* pcCoeffSrcU = m_ppcQTTempCoeffCb[ uiQTLayer ] + ( uiNumCoeffIncC * uiAbsPartIdx );
2344    TCoeff* pcCoeffSrcV = m_ppcQTTempCoeffCr[ uiQTLayer ] + ( uiNumCoeffIncC * uiAbsPartIdx );
2345    TCoeff* pcCoeffDstU = pcCU->getCoeffCb()              + ( uiNumCoeffIncC * uiAbsPartIdx );
2346    TCoeff* pcCoeffDstV = pcCU->getCoeffCr()              + ( uiNumCoeffIncC * uiAbsPartIdx );
2347    ::memcpy( pcCoeffDstU, pcCoeffSrcU, sizeof( TCoeff ) * uiNumCoeffC );
2348    ::memcpy( pcCoeffDstV, pcCoeffSrcV, sizeof( TCoeff ) * uiNumCoeffC );
2349#if ADAPTIVE_QP_SELECTION   
2350    Int* pcArlCoeffSrcU = m_ppcQTTempArlCoeffCb[ uiQTLayer ] + ( uiNumCoeffIncC * uiAbsPartIdx );
2351    Int* pcArlCoeffSrcV = m_ppcQTTempArlCoeffCr[ uiQTLayer ] + ( uiNumCoeffIncC * uiAbsPartIdx );
2352    Int* pcArlCoeffDstU = pcCU->getArlCoeffCb()              + ( uiNumCoeffIncC * uiAbsPartIdx );
2353    Int* pcArlCoeffDstV = pcCU->getArlCoeffCr()              + ( uiNumCoeffIncC * uiAbsPartIdx );
2354    ::memcpy( pcArlCoeffDstU, pcArlCoeffSrcU, sizeof( Int ) * uiNumCoeffC );
2355    ::memcpy( pcArlCoeffDstV, pcArlCoeffSrcV, sizeof( Int ) * uiNumCoeffC );
2356#endif
2357   
2358    //===== copy reconstruction =====
2359    UInt uiLog2TrSizeChroma = ( bChromaSame ? uiLog2TrSize : uiLog2TrSize - 1 );
2360    m_pcQTTempTComYuv[ uiQTLayer ].copyPartToPartChroma( pcRecoYuv, uiAbsPartIdx, 1 << uiLog2TrSizeChroma, 1 << uiLog2TrSizeChroma );
2361  }
2362  else
2363  {
2364    UInt uiNumQPart  = pcCU->getPic()->getNumPartInCU() >> ( ( uiFullDepth + 1 ) << 1 );
2365    for( UInt uiPart = 0; uiPart < 4; uiPart++ )
2366    {
2367      xSetIntraResultChromaQT( pcCU, uiTrDepth + 1, uiAbsPartIdx + uiPart * uiNumQPart, pcRecoYuv );
2368    }
2369  }
2370}
2371
2372
2373Void
2374TEncSearch::preestChromaPredMode( TComDataCU* pcCU, 
2375                                 TComYuv*    pcOrgYuv, 
2376                                 TComYuv*    pcPredYuv )
2377{
2378  UInt  uiWidth     = pcCU->getWidth ( 0 ) >> 1;
2379  UInt  uiHeight    = pcCU->getHeight( 0 ) >> 1;
2380  UInt  uiStride    = pcOrgYuv ->getCStride();
2381  Pel*  piOrgU      = pcOrgYuv ->getCbAddr ( 0 );
2382  Pel*  piOrgV      = pcOrgYuv ->getCrAddr ( 0 );
2383  Pel*  piPredU     = pcPredYuv->getCbAddr ( 0 );
2384  Pel*  piPredV     = pcPredYuv->getCrAddr ( 0 );
2385 
2386  //===== init pattern =====
2387  Bool  bAboveAvail = false;
2388  Bool  bLeftAvail  = false;
2389  pcCU->getPattern()->initPattern         ( pcCU, 0, 0 );
2390  pcCU->getPattern()->initAdiPatternChroma( pcCU, 0, 0, m_piYuvExt, m_iYuvExtStride, m_iYuvExtHeight, bAboveAvail, bLeftAvail );
2391  Int*  pPatChromaU = pcCU->getPattern()->getAdiCbBuf( uiWidth, uiHeight, m_piYuvExt );
2392  Int*  pPatChromaV = pcCU->getPattern()->getAdiCrBuf( uiWidth, uiHeight, m_piYuvExt );
2393 
2394  //===== get best prediction modes (using SAD) =====
2395  UInt  uiMinMode   = 0;
2396  UInt  uiMaxMode   = 4;
2397  UInt  uiBestMode  = MAX_UINT;
2398  UInt  uiMinSAD    = MAX_UINT;
2399  for( UInt uiMode  = uiMinMode; uiMode < uiMaxMode; uiMode++ )
2400  {
2401    //--- get prediction ---
2402    predIntraChromaAng( pPatChromaU, uiMode, piPredU, uiStride, uiWidth, uiHeight, bAboveAvail, bLeftAvail );
2403    predIntraChromaAng( pPatChromaV, uiMode, piPredV, uiStride, uiWidth, uiHeight, bAboveAvail, bLeftAvail );
2404   
2405    //--- get SAD ---
2406    UInt  uiSAD  = m_pcRdCost->calcHAD(g_bitDepthC, piOrgU, uiStride, piPredU, uiStride, uiWidth, uiHeight );
2407    uiSAD       += m_pcRdCost->calcHAD(g_bitDepthC, piOrgV, uiStride, piPredV, uiStride, uiWidth, uiHeight );
2408    //--- check ---
2409    if( uiSAD < uiMinSAD )
2410    {
2411      uiMinSAD   = uiSAD;
2412      uiBestMode = uiMode;
2413    }
2414  }
2415 
2416  //===== set chroma pred mode =====
2417  pcCU->setChromIntraDirSubParts( uiBestMode, 0, pcCU->getDepth( 0 ) );
2418}
2419
2420Void
2421TEncSearch::estIntraPredQT( TComDataCU* pcCU, 
2422                           TComYuv*    pcOrgYuv, 
2423                           TComYuv*    pcPredYuv, 
2424                           TComYuv*    pcResiYuv, 
2425                           TComYuv*    pcRecoYuv,
2426                           UInt&       ruiDistC,
2427                           Bool        bLumaOnly )
2428{
2429  UInt    uiDepth        = pcCU->getDepth(0);
2430  UInt    uiNumPU        = pcCU->getNumPartInter();
2431  UInt    uiInitTrDepth  = pcCU->getPartitionSize(0) == SIZE_2Nx2N ? 0 : 1;
2432  UInt    uiWidth        = pcCU->getWidth (0) >> uiInitTrDepth;
2433  UInt    uiHeight       = pcCU->getHeight(0) >> uiInitTrDepth;
2434  UInt    uiQNumParts    = pcCU->getTotalNumPart() >> 2;
2435  UInt    uiWidthBit     = pcCU->getIntraSizeIdx(0);
2436  UInt    uiOverallDistY = 0;
2437  UInt    uiOverallDistC = 0;
2438  UInt    CandNum;
2439  Double  CandCostList[ FAST_UDI_MAX_RDMODE_NUM ];
2440 
2441  //===== set QP and clear Cbf =====
2442  if ( pcCU->getSlice()->getPPS()->getUseDQP() == true)
2443  {
2444    pcCU->setQPSubParts( pcCU->getQP(0), 0, uiDepth );
2445  }
2446  else
2447  {
2448    pcCU->setQPSubParts( pcCU->getSlice()->getSliceQp(), 0, uiDepth );
2449  }
2450 
2451  //===== loop over partitions =====
2452  UInt uiPartOffset = 0;
2453  for( UInt uiPU = 0; uiPU < uiNumPU; uiPU++, uiPartOffset += uiQNumParts )
2454  {
2455    //===== init pattern for luma prediction =====
2456    Bool bAboveAvail = false;
2457    Bool bLeftAvail  = false;
2458    pcCU->getPattern()->initPattern   ( pcCU, uiInitTrDepth, uiPartOffset );
2459    pcCU->getPattern()->initAdiPattern( pcCU, uiPartOffset, uiInitTrDepth, m_piYuvExt, m_iYuvExtStride, m_iYuvExtHeight, bAboveAvail, bLeftAvail );
2460   
2461    //===== determine set of modes to be tested (using prediction signal only) =====
2462    Int numModesAvailable     = 35; //total number of Intra modes
2463    Pel* piOrg         = pcOrgYuv ->getLumaAddr( uiPU, uiWidth );
2464    Pel* piPred        = pcPredYuv->getLumaAddr( uiPU, uiWidth );
2465    UInt uiStride      = pcPredYuv->getStride();
2466    UInt uiRdModeList[FAST_UDI_MAX_RDMODE_NUM];
2467    Int numModesForFullRD = g_aucIntraModeNumFast[ uiWidthBit ];
2468   
2469    Bool doFastSearch = (numModesForFullRD != numModesAvailable);
2470    if (doFastSearch)
2471    {
2472      assert(numModesForFullRD < numModesAvailable);
2473#if FAST_INTRA_SHVC
2474      Int   uiPreds[3] = {-1, -1, -1};
2475      Int   iMode = -1;
2476      Bool  skipFastHAD = false;
2477      Int numCand = pcCU->getIntraDirLumaPredictor( uiPartOffset, uiPreds, &iMode );
2478
2479      if ( m_pcEncCfg->getUseFastIntraScalable() )
2480      {
2481        if( pcCU->getLayerId() > 0 )
2482        {
2483          numModesAvailable = pcCU->reduceSetOfIntraModes(uiPartOffset, uiPreds, iMode );
2484          if( numModesForFullRD > numModesAvailable ) //fast HAD can be skipped
2485          {
2486            skipFastHAD = true;
2487            numModesForFullRD = numModesAvailable;
2488            for( Int i=0; i < numModesForFullRD; i++ ) 
2489              uiRdModeList[ i ] = g_reducedSetIntraModes[ i ];
2490          }
2491        }
2492      }
2493#endif
2494
2495      for( Int i=0; i < numModesForFullRD; i++ ) 
2496      {
2497        CandCostList[ i ] = MAX_DOUBLE;
2498      }
2499      CandNum = 0;
2500     
2501      for( Int modeIdx = 0; modeIdx < numModesAvailable; modeIdx++ )
2502      {
2503        UInt uiMode = modeIdx;
2504#if FAST_INTRA_SHVC
2505        if ( m_pcEncCfg->getUseFastIntraScalable() )
2506        {
2507          if( skipFastHAD )//indicates that fast HAD can be skipped
2508            break;
2509          uiMode = ( iMode==0 ) ? g_reducedSetIntraModes[modeIdx] : uiMode; //(iMode=0) indicates reduced set of modes
2510        }
2511#endif
2512
2513        predIntraLumaAng( pcCU->getPattern(), uiMode, piPred, uiStride, uiWidth, uiHeight, bAboveAvail, bLeftAvail );
2514       
2515        // use hadamard transform here
2516        UInt uiSad = m_pcRdCost->calcHAD(g_bitDepthY, piOrg, uiStride, piPred, uiStride, uiWidth, uiHeight );
2517       
2518        UInt   iModeBits = xModeBitsIntra( pcCU, uiMode, uiPU, uiPartOffset, uiDepth, uiInitTrDepth );
2519        Double cost      = (Double)uiSad + (Double)iModeBits * m_pcRdCost->getSqrtLambda();
2520       
2521        CandNum += xUpdateCandList( uiMode, cost, numModesForFullRD, uiRdModeList, CandCostList );
2522      }
2523   
2524#if FAST_UDI_USE_MPM
2525#if FAST_INTRA_SHVC == 0
2526      Int uiPreds[3] = {-1, -1, -1};
2527      Int iMode = -1;
2528      Int numCand = pcCU->getIntraDirLumaPredictor( uiPartOffset, uiPreds, &iMode );
2529#endif
2530      if( iMode >= 0 )
2531      {
2532        numCand = iMode;
2533      }
2534     
2535      for( Int j=0; j < numCand; j++)
2536      {
2537        Bool mostProbableModeIncluded = false;
2538        Int mostProbableMode = uiPreds[j];
2539       
2540        for( Int i=0; i < numModesForFullRD; i++)
2541        {
2542          mostProbableModeIncluded |= (mostProbableMode == uiRdModeList[i]);
2543        }
2544        if (!mostProbableModeIncluded)
2545        {
2546          uiRdModeList[numModesForFullRD++] = mostProbableMode;
2547        }
2548      }
2549#endif // FAST_UDI_USE_MPM
2550    }
2551    else
2552    {
2553      for( Int i=0; i < numModesForFullRD; i++)
2554      {
2555        uiRdModeList[i] = i;
2556      }
2557    }
2558   
2559    //===== check modes (using r-d costs) =====
2560#if HHI_RQT_INTRA_SPEEDUP_MOD
2561    UInt   uiSecondBestMode  = MAX_UINT;
2562    Double dSecondBestPUCost = MAX_DOUBLE;
2563#endif
2564   
2565    UInt    uiBestPUMode  = 0;
2566    UInt    uiBestPUDistY = 0;
2567    UInt    uiBestPUDistC = 0;
2568    Double  dBestPUCost   = MAX_DOUBLE;
2569    for( UInt uiMode = 0; uiMode < numModesForFullRD; uiMode++ )
2570    {
2571      // set luma prediction mode
2572      UInt uiOrgMode = uiRdModeList[uiMode];
2573     
2574      pcCU->setLumaIntraDirSubParts ( uiOrgMode, uiPartOffset, uiDepth + uiInitTrDepth );
2575     
2576      // set context models
2577      if( m_bUseSBACRD )
2578      {
2579        m_pcRDGoOnSbacCoder->load( m_pppcRDSbacCoder[uiDepth][CI_CURR_BEST] );
2580      }
2581     
2582      // determine residual for partition
2583      UInt   uiPUDistY = 0;
2584      UInt   uiPUDistC = 0;
2585      Double dPUCost   = 0.0;
2586#if HHI_RQT_INTRA_SPEEDUP
2587      xRecurIntraCodingQT( pcCU, uiInitTrDepth, uiPartOffset, bLumaOnly, pcOrgYuv, pcPredYuv, pcResiYuv, uiPUDistY, uiPUDistC, true, dPUCost );
2588#else
2589      xRecurIntraCodingQT( pcCU, uiInitTrDepth, uiPartOffset, bLumaOnly, pcOrgYuv, pcPredYuv, pcResiYuv, uiPUDistY, uiPUDistC, dPUCost );
2590#endif
2591     
2592      // check r-d cost
2593      if( dPUCost < dBestPUCost )
2594      {
2595#if HHI_RQT_INTRA_SPEEDUP_MOD
2596        uiSecondBestMode  = uiBestPUMode;
2597        dSecondBestPUCost = dBestPUCost;
2598#endif
2599        uiBestPUMode  = uiOrgMode;
2600        uiBestPUDistY = uiPUDistY;
2601        uiBestPUDistC = uiPUDistC;
2602        dBestPUCost   = dPUCost;
2603       
2604        xSetIntraResultQT( pcCU, uiInitTrDepth, uiPartOffset, bLumaOnly, pcRecoYuv );
2605       
2606        UInt uiQPartNum = pcCU->getPic()->getNumPartInCU() >> ( ( pcCU->getDepth(0) + uiInitTrDepth ) << 1 );
2607        ::memcpy( m_puhQTTempTrIdx,  pcCU->getTransformIdx()       + uiPartOffset, uiQPartNum * sizeof( UChar ) );
2608        ::memcpy( m_puhQTTempCbf[0], pcCU->getCbf( TEXT_LUMA     ) + uiPartOffset, uiQPartNum * sizeof( UChar ) );
2609        ::memcpy( m_puhQTTempCbf[1], pcCU->getCbf( TEXT_CHROMA_U ) + uiPartOffset, uiQPartNum * sizeof( UChar ) );
2610        ::memcpy( m_puhQTTempCbf[2], pcCU->getCbf( TEXT_CHROMA_V ) + uiPartOffset, uiQPartNum * sizeof( UChar ) );
2611        ::memcpy( m_puhQTTempTransformSkipFlag[0], pcCU->getTransformSkip(TEXT_LUMA)     + uiPartOffset, uiQPartNum * sizeof( UChar ) );
2612        ::memcpy( m_puhQTTempTransformSkipFlag[1], pcCU->getTransformSkip(TEXT_CHROMA_U) + uiPartOffset, uiQPartNum * sizeof( UChar ) );
2613        ::memcpy( m_puhQTTempTransformSkipFlag[2], pcCU->getTransformSkip(TEXT_CHROMA_V) + uiPartOffset, uiQPartNum * sizeof( UChar ) );
2614      }
2615#if HHI_RQT_INTRA_SPEEDUP_MOD
2616      else if( dPUCost < dSecondBestPUCost )
2617      {
2618        uiSecondBestMode  = uiOrgMode;
2619        dSecondBestPUCost = dPUCost;
2620      }
2621#endif
2622    } // Mode loop
2623   
2624#if HHI_RQT_INTRA_SPEEDUP
2625#if HHI_RQT_INTRA_SPEEDUP_MOD
2626    for( UInt ui =0; ui < 2; ++ui )
2627#endif
2628    {
2629#if HHI_RQT_INTRA_SPEEDUP_MOD
2630      UInt uiOrgMode   = ui ? uiSecondBestMode  : uiBestPUMode;
2631      if( uiOrgMode == MAX_UINT )
2632      {
2633        break;
2634      }
2635#else
2636      UInt uiOrgMode = uiBestPUMode;
2637#endif
2638     
2639      pcCU->setLumaIntraDirSubParts ( uiOrgMode, uiPartOffset, uiDepth + uiInitTrDepth );
2640     
2641      // set context models
2642      if( m_bUseSBACRD )
2643      {
2644        m_pcRDGoOnSbacCoder->load( m_pppcRDSbacCoder[uiDepth][CI_CURR_BEST] );
2645      }
2646     
2647      // determine residual for partition
2648      UInt   uiPUDistY = 0;
2649      UInt   uiPUDistC = 0;
2650      Double dPUCost   = 0.0;
2651      xRecurIntraCodingQT( pcCU, uiInitTrDepth, uiPartOffset, bLumaOnly, pcOrgYuv, pcPredYuv, pcResiYuv, uiPUDistY, uiPUDistC, false, dPUCost );
2652     
2653      // check r-d cost
2654      if( dPUCost < dBestPUCost )
2655      {
2656        uiBestPUMode  = uiOrgMode;
2657        uiBestPUDistY = uiPUDistY;
2658        uiBestPUDistC = uiPUDistC;
2659        dBestPUCost   = dPUCost;
2660       
2661        xSetIntraResultQT( pcCU, uiInitTrDepth, uiPartOffset, bLumaOnly, pcRecoYuv );
2662       
2663        UInt uiQPartNum = pcCU->getPic()->getNumPartInCU() >> ( ( pcCU->getDepth(0) + uiInitTrDepth ) << 1 );
2664        ::memcpy( m_puhQTTempTrIdx,  pcCU->getTransformIdx()       + uiPartOffset, uiQPartNum * sizeof( UChar ) );
2665        ::memcpy( m_puhQTTempCbf[0], pcCU->getCbf( TEXT_LUMA     ) + uiPartOffset, uiQPartNum * sizeof( UChar ) );
2666        ::memcpy( m_puhQTTempCbf[1], pcCU->getCbf( TEXT_CHROMA_U ) + uiPartOffset, uiQPartNum * sizeof( UChar ) );
2667        ::memcpy( m_puhQTTempCbf[2], pcCU->getCbf( TEXT_CHROMA_V ) + uiPartOffset, uiQPartNum * sizeof( UChar ) );
2668        ::memcpy( m_puhQTTempTransformSkipFlag[0], pcCU->getTransformSkip(TEXT_LUMA)     + uiPartOffset, uiQPartNum * sizeof( UChar ) );
2669        ::memcpy( m_puhQTTempTransformSkipFlag[1], pcCU->getTransformSkip(TEXT_CHROMA_U) + uiPartOffset, uiQPartNum * sizeof( UChar ) );
2670        ::memcpy( m_puhQTTempTransformSkipFlag[2], pcCU->getTransformSkip(TEXT_CHROMA_V) + uiPartOffset, uiQPartNum * sizeof( UChar ) );
2671      }
2672    } // Mode loop
2673#endif
2674   
2675    //--- update overall distortion ---
2676    uiOverallDistY += uiBestPUDistY;
2677    uiOverallDistC += uiBestPUDistC;
2678   
2679    //--- update transform index and cbf ---
2680    UInt uiQPartNum = pcCU->getPic()->getNumPartInCU() >> ( ( pcCU->getDepth(0) + uiInitTrDepth ) << 1 );
2681    ::memcpy( pcCU->getTransformIdx()       + uiPartOffset, m_puhQTTempTrIdx,  uiQPartNum * sizeof( UChar ) );
2682    ::memcpy( pcCU->getCbf( TEXT_LUMA     ) + uiPartOffset, m_puhQTTempCbf[0], uiQPartNum * sizeof( UChar ) );
2683    ::memcpy( pcCU->getCbf( TEXT_CHROMA_U ) + uiPartOffset, m_puhQTTempCbf[1], uiQPartNum * sizeof( UChar ) );
2684    ::memcpy( pcCU->getCbf( TEXT_CHROMA_V ) + uiPartOffset, m_puhQTTempCbf[2], uiQPartNum * sizeof( UChar ) );
2685    ::memcpy( pcCU->getTransformSkip(TEXT_LUMA)     + uiPartOffset, m_puhQTTempTransformSkipFlag[0], uiQPartNum * sizeof( UChar ) );
2686    ::memcpy( pcCU->getTransformSkip(TEXT_CHROMA_U) + uiPartOffset, m_puhQTTempTransformSkipFlag[1], uiQPartNum * sizeof( UChar ) );
2687    ::memcpy( pcCU->getTransformSkip(TEXT_CHROMA_V) + uiPartOffset, m_puhQTTempTransformSkipFlag[2], uiQPartNum * sizeof( UChar ) );
2688    //--- set reconstruction for next intra prediction blocks ---
2689    if( uiPU != uiNumPU - 1 )
2690    {
2691      Bool bSkipChroma  = false;
2692      Bool bChromaSame  = false;
2693      UInt uiLog2TrSize = g_aucConvertToBit[ pcCU->getSlice()->getSPS()->getMaxCUWidth() >> ( pcCU->getDepth(0) + uiInitTrDepth ) ] + 2;
2694      if( !bLumaOnly && uiLog2TrSize == 2 )
2695      {
2696        assert( uiInitTrDepth  > 0 );
2697        bSkipChroma  = ( uiPU != 0 );
2698        bChromaSame  = true;
2699      }
2700     
2701      UInt    uiCompWidth   = pcCU->getWidth ( 0 ) >> uiInitTrDepth;
2702      UInt    uiCompHeight  = pcCU->getHeight( 0 ) >> uiInitTrDepth;
2703      UInt    uiZOrder      = pcCU->getZorderIdxInCU() + uiPartOffset;
2704      Pel*    piDes         = pcCU->getPic()->getPicYuvRec()->getLumaAddr( pcCU->getAddr(), uiZOrder );
2705      UInt    uiDesStride   = pcCU->getPic()->getPicYuvRec()->getStride();
2706      Pel*    piSrc         = pcRecoYuv->getLumaAddr( uiPartOffset );
2707      UInt    uiSrcStride   = pcRecoYuv->getStride();
2708      for( UInt uiY = 0; uiY < uiCompHeight; uiY++, piSrc += uiSrcStride, piDes += uiDesStride )
2709      {
2710        for( UInt uiX = 0; uiX < uiCompWidth; uiX++ )
2711        {
2712          piDes[ uiX ] = piSrc[ uiX ];
2713        }
2714      }
2715      if( !bLumaOnly && !bSkipChroma )
2716      {
2717        if( !bChromaSame )
2718        {
2719          uiCompWidth   >>= 1;
2720          uiCompHeight  >>= 1;
2721        }
2722        piDes         = pcCU->getPic()->getPicYuvRec()->getCbAddr( pcCU->getAddr(), uiZOrder );
2723        uiDesStride   = pcCU->getPic()->getPicYuvRec()->getCStride();
2724        piSrc         = pcRecoYuv->getCbAddr( uiPartOffset );
2725        uiSrcStride   = pcRecoYuv->getCStride();
2726        for( UInt uiY = 0; uiY < uiCompHeight; uiY++, piSrc += uiSrcStride, piDes += uiDesStride )
2727        {
2728          for( UInt uiX = 0; uiX < uiCompWidth; uiX++ )
2729          {
2730            piDes[ uiX ] = piSrc[ uiX ];
2731          }
2732        }
2733        piDes         = pcCU->getPic()->getPicYuvRec()->getCrAddr( pcCU->getAddr(), uiZOrder );
2734        piSrc         = pcRecoYuv->getCrAddr( uiPartOffset );
2735        for( UInt uiY = 0; uiY < uiCompHeight; uiY++, piSrc += uiSrcStride, piDes += uiDesStride )
2736        {
2737          for( UInt uiX = 0; uiX < uiCompWidth; uiX++ )
2738          {
2739            piDes[ uiX ] = piSrc[ uiX ];
2740          }
2741        }
2742      }
2743    }
2744   
2745    //=== update PU data ====
2746    pcCU->setLumaIntraDirSubParts     ( uiBestPUMode, uiPartOffset, uiDepth + uiInitTrDepth );
2747    pcCU->copyToPic                   ( uiDepth, uiPU, uiInitTrDepth );
2748  } // PU loop
2749 
2750 
2751  if( uiNumPU > 1 )
2752  { // set Cbf for all blocks
2753    UInt uiCombCbfY = 0;
2754    UInt uiCombCbfU = 0;
2755    UInt uiCombCbfV = 0;
2756    UInt uiPartIdx  = 0;
2757    for( UInt uiPart = 0; uiPart < 4; uiPart++, uiPartIdx += uiQNumParts )
2758    {
2759      uiCombCbfY |= pcCU->getCbf( uiPartIdx, TEXT_LUMA,     1 );
2760      uiCombCbfU |= pcCU->getCbf( uiPartIdx, TEXT_CHROMA_U, 1 );
2761      uiCombCbfV |= pcCU->getCbf( uiPartIdx, TEXT_CHROMA_V, 1 );
2762    }
2763    for( UInt uiOffs = 0; uiOffs < 4 * uiQNumParts; uiOffs++ )
2764    {
2765      pcCU->getCbf( TEXT_LUMA     )[ uiOffs ] |= uiCombCbfY;
2766      pcCU->getCbf( TEXT_CHROMA_U )[ uiOffs ] |= uiCombCbfU;
2767      pcCU->getCbf( TEXT_CHROMA_V )[ uiOffs ] |= uiCombCbfV;
2768    }
2769  }
2770 
2771  //===== reset context models =====
2772  if(m_bUseSBACRD)
2773  {
2774    m_pcRDGoOnSbacCoder->load(m_pppcRDSbacCoder[uiDepth][CI_CURR_BEST]);
2775  }
2776 
2777  //===== set distortion (rate and r-d costs are determined later) =====
2778  ruiDistC                   = uiOverallDistC;
2779  pcCU->getTotalDistortion() = uiOverallDistY + uiOverallDistC;
2780}
2781
2782
2783
2784Void
2785TEncSearch::estIntraPredChromaQT( TComDataCU* pcCU, 
2786                                 TComYuv*    pcOrgYuv, 
2787                                 TComYuv*    pcPredYuv, 
2788                                 TComYuv*    pcResiYuv, 
2789                                 TComYuv*    pcRecoYuv,
2790                                 UInt        uiPreCalcDistC )
2791{
2792  UInt    uiDepth     = pcCU->getDepth(0);
2793  UInt    uiBestMode  = 0;
2794  UInt    uiBestDist  = 0;
2795  Double  dBestCost   = MAX_DOUBLE;
2796 
2797  //----- init mode list -----
2798  UInt  uiMinMode = 0;
2799  UInt  uiModeList[ NUM_CHROMA_MODE ];
2800  pcCU->getAllowedChromaDir( 0, uiModeList );
2801  UInt  uiMaxMode = NUM_CHROMA_MODE;
2802
2803  //----- check chroma modes -----
2804  for( UInt uiMode = uiMinMode; uiMode < uiMaxMode; uiMode++ )
2805  {
2806    //----- restore context models -----
2807    if( m_bUseSBACRD )
2808    {
2809      m_pcRDGoOnSbacCoder->load( m_pppcRDSbacCoder[uiDepth][CI_CURR_BEST] );
2810    }
2811   
2812    //----- chroma coding -----
2813    UInt    uiDist = 0;
2814    pcCU->setChromIntraDirSubParts  ( uiModeList[uiMode], 0, uiDepth );
2815    xRecurIntraChromaCodingQT       ( pcCU,   0, 0, pcOrgYuv, pcPredYuv, pcResiYuv, uiDist );
2816    if( m_bUseSBACRD && pcCU->getSlice()->getPPS()->getUseTransformSkip() )
2817    {
2818      m_pcRDGoOnSbacCoder->load( m_pppcRDSbacCoder[uiDepth][CI_CURR_BEST] );
2819    }
2820    UInt    uiBits = xGetIntraBitsQT( pcCU,   0, 0, false, true, false );
2821    Double  dCost  = m_pcRdCost->calcRdCost( uiBits, uiDist );
2822   
2823    //----- compare -----
2824    if( dCost < dBestCost )
2825    {
2826      dBestCost   = dCost;
2827      uiBestDist  = uiDist;
2828      uiBestMode  = uiModeList[uiMode];
2829      UInt  uiQPN = pcCU->getPic()->getNumPartInCU() >> ( uiDepth << 1 );
2830      xSetIntraResultChromaQT( pcCU, 0, 0, pcRecoYuv );
2831      ::memcpy( m_puhQTTempCbf[1], pcCU->getCbf( TEXT_CHROMA_U ), uiQPN * sizeof( UChar ) );
2832      ::memcpy( m_puhQTTempCbf[2], pcCU->getCbf( TEXT_CHROMA_V ), uiQPN * sizeof( UChar ) );
2833      ::memcpy( m_puhQTTempTransformSkipFlag[1], pcCU->getTransformSkip( TEXT_CHROMA_U ), uiQPN * sizeof( UChar ) );
2834      ::memcpy( m_puhQTTempTransformSkipFlag[2], pcCU->getTransformSkip( TEXT_CHROMA_V ), uiQPN * sizeof( UChar ) );
2835    }
2836  }
2837 
2838  //----- set data -----
2839  UInt  uiQPN = pcCU->getPic()->getNumPartInCU() >> ( uiDepth << 1 );
2840  ::memcpy( pcCU->getCbf( TEXT_CHROMA_U ), m_puhQTTempCbf[1], uiQPN * sizeof( UChar ) );
2841  ::memcpy( pcCU->getCbf( TEXT_CHROMA_V ), m_puhQTTempCbf[2], uiQPN * sizeof( UChar ) );
2842  ::memcpy( pcCU->getTransformSkip( TEXT_CHROMA_U ), m_puhQTTempTransformSkipFlag[1], uiQPN * sizeof( UChar ) );
2843  ::memcpy( pcCU->getTransformSkip( TEXT_CHROMA_V ), m_puhQTTempTransformSkipFlag[2], uiQPN * sizeof( UChar ) );
2844  pcCU->setChromIntraDirSubParts( uiBestMode, 0, uiDepth );
2845  pcCU->getTotalDistortion      () += uiBestDist - uiPreCalcDistC;
2846 
2847  //----- restore context models -----
2848  if( m_bUseSBACRD )
2849  {
2850    m_pcRDGoOnSbacCoder->load( m_pppcRDSbacCoder[uiDepth][CI_CURR_BEST] );
2851  }
2852}
2853
2854/** Function for encoding and reconstructing luma/chroma samples of a PCM mode CU.
2855 * \param pcCU pointer to current CU
2856 * \param uiAbsPartIdx part index
2857 * \param piOrg pointer to original sample arrays
2858 * \param piPCM pointer to PCM code arrays
2859 * \param piPred pointer to prediction signal arrays
2860 * \param piResi pointer to residual signal arrays
2861 * \param piReco pointer to reconstructed sample arrays
2862 * \param uiStride stride of the original/prediction/residual sample arrays
2863 * \param uiWidth block width
2864 * \param uiHeight block height
2865 * \param ttText texture component type
2866 * \returns Void
2867 */
2868Void TEncSearch::xEncPCM (TComDataCU* pcCU, UInt uiAbsPartIdx, Pel* piOrg, Pel* piPCM, Pel* piPred, Pel* piResi, Pel* piReco, UInt uiStride, UInt uiWidth, UInt uiHeight, TextType eText )
2869{
2870  UInt uiX, uiY;
2871  UInt uiReconStride;
2872  Pel* pOrg  = piOrg;
2873  Pel* pPCM  = piPCM;
2874  Pel* pPred = piPred;
2875  Pel* pResi = piResi;
2876  Pel* pReco = piReco;
2877  Pel* pRecoPic;
2878  Int shiftPcm;
2879
2880  if( eText == TEXT_LUMA)
2881  {
2882    uiReconStride = pcCU->getPic()->getPicYuvRec()->getStride();
2883    pRecoPic      = pcCU->getPic()->getPicYuvRec()->getLumaAddr(pcCU->getAddr(), pcCU->getZorderIdxInCU()+uiAbsPartIdx);
2884    shiftPcm = g_bitDepthY - pcCU->getSlice()->getSPS()->getPCMBitDepthLuma();
2885  }
2886  else
2887  {
2888    uiReconStride = pcCU->getPic()->getPicYuvRec()->getCStride();
2889
2890    if( eText == TEXT_CHROMA_U )
2891    {
2892      pRecoPic = pcCU->getPic()->getPicYuvRec()->getCbAddr(pcCU->getAddr(), pcCU->getZorderIdxInCU()+uiAbsPartIdx);
2893    }
2894    else
2895    {
2896      pRecoPic = pcCU->getPic()->getPicYuvRec()->getCrAddr(pcCU->getAddr(), pcCU->getZorderIdxInCU()+uiAbsPartIdx);
2897    }
2898    shiftPcm = g_bitDepthC - pcCU->getSlice()->getSPS()->getPCMBitDepthChroma();
2899  }
2900
2901  // Reset pred and residual
2902  for( uiY = 0; uiY < uiHeight; uiY++ )
2903  {
2904    for( uiX = 0; uiX < uiWidth; uiX++ )
2905    {
2906      pPred[uiX] = 0;
2907      pResi[uiX] = 0;
2908    }
2909    pPred += uiStride;
2910    pResi += uiStride;
2911  }
2912
2913  // Encode
2914  for( uiY = 0; uiY < uiHeight; uiY++ )
2915  {
2916    for( uiX = 0; uiX < uiWidth; uiX++ )
2917    {
2918      pPCM[uiX] = pOrg[uiX]>> shiftPcm;
2919    }
2920    pPCM += uiWidth;
2921    pOrg += uiStride;
2922  }
2923
2924  pPCM  = piPCM;
2925
2926  // Reconstruction
2927  for( uiY = 0; uiY < uiHeight; uiY++ )
2928  {
2929    for( uiX = 0; uiX < uiWidth; uiX++ )
2930    {
2931      pReco   [uiX] = pPCM[uiX]<< shiftPcm;
2932      pRecoPic[uiX] = pReco[uiX];
2933    }
2934    pPCM += uiWidth;
2935    pReco += uiStride;
2936    pRecoPic += uiReconStride;
2937  }
2938}
2939
2940/**  Function for PCM mode estimation.
2941 * \param pcCU
2942 * \param pcOrgYuv
2943 * \param rpcPredYuv
2944 * \param rpcResiYuv
2945 * \param rpcRecoYuv
2946 * \returns Void
2947 */
2948Void TEncSearch::IPCMSearch( TComDataCU* pcCU, TComYuv* pcOrgYuv, TComYuv*& rpcPredYuv, TComYuv*& rpcResiYuv, TComYuv*& rpcRecoYuv )
2949{
2950  UInt   uiDepth        = pcCU->getDepth(0);
2951  UInt   uiWidth        = pcCU->getWidth(0);
2952  UInt   uiHeight       = pcCU->getHeight(0);
2953  UInt   uiStride       = rpcPredYuv->getStride();
2954  UInt   uiStrideC      = rpcPredYuv->getCStride();
2955  UInt   uiWidthC       = uiWidth  >> 1;
2956  UInt   uiHeightC      = uiHeight >> 1;
2957  UInt   uiDistortion = 0;
2958  UInt   uiBits;
2959
2960  Double dCost;
2961
2962  Pel*    pOrig;
2963  Pel*    pResi;
2964  Pel*    pReco;
2965  Pel*    pPred;
2966  Pel*    pPCM;
2967
2968  UInt uiAbsPartIdx = 0;
2969
2970  UInt uiMinCoeffSize = pcCU->getPic()->getMinCUWidth()*pcCU->getPic()->getMinCUHeight();
2971  UInt uiLumaOffset   = uiMinCoeffSize*uiAbsPartIdx;
2972  UInt uiChromaOffset = uiLumaOffset>>2;
2973
2974  // Luminance
2975  pOrig    = pcOrgYuv->getLumaAddr(0, uiWidth);
2976  pResi    = rpcResiYuv->getLumaAddr(0, uiWidth);
2977  pPred    = rpcPredYuv->getLumaAddr(0, uiWidth);
2978  pReco    = rpcRecoYuv->getLumaAddr(0, uiWidth);
2979  pPCM     = pcCU->getPCMSampleY() + uiLumaOffset;
2980
2981  xEncPCM ( pcCU, 0, pOrig, pPCM, pPred, pResi, pReco, uiStride, uiWidth, uiHeight, TEXT_LUMA );
2982
2983  // Chroma U
2984  pOrig    = pcOrgYuv->getCbAddr();
2985  pResi    = rpcResiYuv->getCbAddr();
2986  pPred    = rpcPredYuv->getCbAddr();
2987  pReco    = rpcRecoYuv->getCbAddr();
2988  pPCM     = pcCU->getPCMSampleCb() + uiChromaOffset;
2989
2990  xEncPCM ( pcCU, 0, pOrig, pPCM, pPred, pResi, pReco, uiStrideC, uiWidthC, uiHeightC, TEXT_CHROMA_U );
2991
2992  // Chroma V
2993  pOrig    = pcOrgYuv->getCrAddr();
2994  pResi    = rpcResiYuv->getCrAddr();
2995  pPred    = rpcPredYuv->getCrAddr();
2996  pReco    = rpcRecoYuv->getCrAddr();
2997  pPCM     = pcCU->getPCMSampleCr() + uiChromaOffset;
2998
2999  xEncPCM ( pcCU, 0, pOrig, pPCM, pPred, pResi, pReco, uiStrideC, uiWidthC, uiHeightC, TEXT_CHROMA_V );
3000
3001  m_pcEntropyCoder->resetBits();
3002  xEncIntraHeader ( pcCU, uiDepth, uiAbsPartIdx, true, false);
3003  uiBits = m_pcEntropyCoder->getNumberOfWrittenBits();
3004
3005  dCost = m_pcRdCost->calcRdCost( uiBits, uiDistortion );
3006
3007  if(m_bUseSBACRD)
3008  {
3009    m_pcRDGoOnSbacCoder->load(m_pppcRDSbacCoder[uiDepth][CI_CURR_BEST]);
3010  }
3011
3012  pcCU->getTotalBits()       = uiBits;
3013  pcCU->getTotalCost()       = dCost;
3014  pcCU->getTotalDistortion() = uiDistortion;
3015
3016  pcCU->copyToPic(uiDepth, 0, 0);
3017}
3018
3019Void TEncSearch::xGetInterPredictionError( TComDataCU* pcCU, TComYuv* pcYuvOrg, Int iPartIdx, UInt& ruiErr, Bool bHadamard )
3020{
3021  motionCompensation( pcCU, &m_tmpYuvPred, REF_PIC_LIST_X, iPartIdx );
3022
3023  UInt uiAbsPartIdx = 0;
3024  Int iWidth = 0;
3025  Int iHeight = 0;
3026  pcCU->getPartIndexAndSize( iPartIdx, uiAbsPartIdx, iWidth, iHeight );
3027
3028  DistParam cDistParam;
3029
3030  cDistParam.bApplyWeight = false;
3031
3032  m_pcRdCost->setDistParam( cDistParam, g_bitDepthY,
3033                            pcYuvOrg->getLumaAddr( uiAbsPartIdx ), pcYuvOrg->getStride(), 
3034                            m_tmpYuvPred .getLumaAddr( uiAbsPartIdx ), m_tmpYuvPred .getStride(), 
3035                            iWidth, iHeight, m_pcEncCfg->getUseHADME() );
3036  ruiErr = cDistParam.DistFunc( &cDistParam );
3037}
3038
3039/** estimation of best merge coding
3040 * \param pcCU
3041 * \param pcYuvOrg
3042 * \param iPUIdx
3043 * \param uiInterDir
3044 * \param pacMvField
3045 * \param uiMergeIndex
3046 * \param ruiCost
3047 * \param ruiBits
3048 * \param puhNeighCands
3049 * \param bValid
3050 * \returns Void
3051 */
3052Void TEncSearch::xMergeEstimation( TComDataCU* pcCU, TComYuv* pcYuvOrg, Int iPUIdx, UInt& uiInterDir, TComMvField* pacMvField, UInt& uiMergeIndex, UInt& ruiCost, TComMvField* cMvFieldNeighbours, UChar* uhInterDirNeighbours, Int& numValidMergeCand )
3053{
3054  UInt uiAbsPartIdx = 0;
3055  Int iWidth = 0;
3056  Int iHeight = 0; 
3057
3058  pcCU->getPartIndexAndSize( iPUIdx, uiAbsPartIdx, iWidth, iHeight );
3059  UInt uiDepth = pcCU->getDepth( uiAbsPartIdx );
3060  PartSize partSize = pcCU->getPartitionSize( 0 );
3061  if ( pcCU->getSlice()->getPPS()->getLog2ParallelMergeLevelMinus2() && partSize != SIZE_2Nx2N && pcCU->getWidth( 0 ) <= 8 )
3062  {
3063    pcCU->setPartSizeSubParts( SIZE_2Nx2N, 0, uiDepth );
3064    if ( iPUIdx == 0 )
3065    {
3066      pcCU->getInterMergeCandidates( 0, 0, cMvFieldNeighbours,uhInterDirNeighbours, numValidMergeCand );
3067    }
3068    pcCU->setPartSizeSubParts( partSize, 0, uiDepth );
3069  }
3070  else
3071  {
3072    pcCU->getInterMergeCandidates( uiAbsPartIdx, iPUIdx, cMvFieldNeighbours, uhInterDirNeighbours, numValidMergeCand );
3073  }
3074  xRestrictBipredMergeCand( pcCU, iPUIdx, cMvFieldNeighbours, uhInterDirNeighbours, numValidMergeCand );
3075
3076  ruiCost = MAX_UINT;
3077  for( UInt uiMergeCand = 0; uiMergeCand < numValidMergeCand; ++uiMergeCand )
3078  {
3079#if REF_IDX_ME_ZEROMV
3080    Bool bZeroMVILR = pcCU->xCheckZeroMVILRMerge(uhInterDirNeighbours[uiMergeCand], cMvFieldNeighbours[0 + 2*uiMergeCand], cMvFieldNeighbours[1 + 2*uiMergeCand]);
3081    if(bZeroMVILR)
3082    {
3083#endif
3084#if N0383_IL_CONSTRAINED_TILE_SETS_SEI
3085    if (!(pcCU->isInterLayerReference(uhInterDirNeighbours[uiMergeCand], cMvFieldNeighbours[0 + 2*uiMergeCand], cMvFieldNeighbours[1 + 2*uiMergeCand]) && m_disableILP))
3086    {
3087#endif
3088      UInt uiCostCand = MAX_UINT;
3089      UInt uiBitsCand = 0;
3090     
3091      PartSize ePartSize = pcCU->getPartitionSize( 0 );
3092
3093      pcCU->getCUMvField(REF_PIC_LIST_0)->setAllMvField( cMvFieldNeighbours[0 + 2*uiMergeCand], ePartSize, uiAbsPartIdx, 0, iPUIdx );
3094      pcCU->getCUMvField(REF_PIC_LIST_1)->setAllMvField( cMvFieldNeighbours[1 + 2*uiMergeCand], ePartSize, uiAbsPartIdx, 0, iPUIdx );
3095
3096      xGetInterPredictionError( pcCU, pcYuvOrg, iPUIdx, uiCostCand, m_pcEncCfg->getUseHADME() );
3097      uiBitsCand = uiMergeCand + 1;
3098      if (uiMergeCand == m_pcEncCfg->getMaxNumMergeCand() -1)
3099      {
3100         uiBitsCand--;
3101      }
3102      uiCostCand = uiCostCand + m_pcRdCost->getCost( uiBitsCand );
3103      if ( uiCostCand < ruiCost )
3104      {
3105        ruiCost = uiCostCand;
3106        pacMvField[0] = cMvFieldNeighbours[0 + 2*uiMergeCand];
3107        pacMvField[1] = cMvFieldNeighbours[1 + 2*uiMergeCand];
3108        uiInterDir = uhInterDirNeighbours[uiMergeCand];
3109        uiMergeIndex = uiMergeCand;
3110      }
3111#if N0383_IL_CONSTRAINED_TILE_SETS_SEI
3112    }
3113#endif
3114#if REF_IDX_ME_ZEROMV
3115    }
3116#endif
3117  }
3118}
3119
3120/** convert bi-pred merge candidates to uni-pred
3121 * \param pcCU
3122 * \param puIdx
3123 * \param mvFieldNeighbours
3124 * \param interDirNeighbours
3125 * \param numValidMergeCand
3126 * \returns Void
3127 */
3128Void TEncSearch::xRestrictBipredMergeCand( TComDataCU* pcCU, UInt puIdx, TComMvField* mvFieldNeighbours, UChar* interDirNeighbours, Int numValidMergeCand )
3129{
3130  if ( pcCU->isBipredRestriction(puIdx) )
3131  {
3132    for( UInt mergeCand = 0; mergeCand < numValidMergeCand; ++mergeCand )
3133    {
3134      if ( interDirNeighbours[mergeCand] == 3 )
3135      {
3136        interDirNeighbours[mergeCand] = 1;
3137        mvFieldNeighbours[(mergeCand << 1) + 1].setMvField(TComMv(0,0), -1);
3138      }
3139    }
3140  }
3141}
3142
3143/** search of the best candidate for inter prediction
3144 * \param pcCU
3145 * \param pcOrgYuv
3146 * \param rpcPredYuv
3147 * \param rpcResiYuv
3148 * \param rpcRecoYuv
3149 * \param bUseRes
3150 * \returns Void
3151 */
3152#if AMP_MRG
3153Void TEncSearch::predInterSearch( TComDataCU* pcCU, TComYuv* pcOrgYuv, TComYuv*& rpcPredYuv, TComYuv*& rpcResiYuv, TComYuv*& rpcRecoYuv, Bool bUseRes, Bool bUseMRG )
3154#else
3155Void TEncSearch::predInterSearch( TComDataCU* pcCU, TComYuv* pcOrgYuv, TComYuv*& rpcPredYuv, TComYuv*& rpcResiYuv, TComYuv*& rpcRecoYuv, Bool bUseRes )
3156#endif
3157{
3158  m_acYuvPred[0].clear();
3159  m_acYuvPred[1].clear();
3160  m_cYuvPredTemp.clear();
3161  rpcPredYuv->clear();
3162 
3163  if ( !bUseRes )
3164  {
3165    rpcResiYuv->clear();
3166  }
3167 
3168  rpcRecoYuv->clear();
3169 
3170  TComMv        cMvSrchRngLT;
3171  TComMv        cMvSrchRngRB;
3172 
3173  TComMv        cMvZero;
3174  TComMv        TempMv; //kolya
3175 
3176  TComMv        cMv[2];
3177  TComMv        cMvBi[2];
3178  TComMv        cMvTemp[2][33];
3179 
3180  Int           iNumPart    = pcCU->getNumPartInter();
3181  Int           iNumPredDir = pcCU->getSlice()->isInterP() ? 1 : 2;
3182 
3183  TComMv        cMvPred[2][33];
3184 
3185  TComMv        cMvPredBi[2][33];
3186  Int           aaiMvpIdxBi[2][33];
3187 
3188  Int           aaiMvpIdx[2][33];
3189  Int           aaiMvpNum[2][33];
3190 
3191  AMVPInfo aacAMVPInfo[2][33];
3192 
3193  Int           iRefIdx[2]={0,0}; //If un-initialized, may cause SEGV in bi-directional prediction iterative stage.
3194  Int           iRefIdxBi[2];
3195 
3196  UInt          uiPartAddr;
3197  Int           iRoiWidth, iRoiHeight;
3198 
3199  UInt          uiMbBits[3] = {1, 1, 0};
3200 
3201  UInt          uiLastMode = 0;
3202  Int           iRefStart, iRefEnd;
3203 
3204  PartSize      ePartSize = pcCU->getPartitionSize( 0 );
3205
3206  Int           bestBiPRefIdxL1 = 0;
3207  Int           bestBiPMvpL1 = 0;
3208  UInt          biPDistTemp = MAX_INT;
3209
3210#if ZERO_MVD_EST
3211  Int           aiZeroMvdMvpIdx[2] = {-1, -1};
3212  Int           aiZeroMvdRefIdx[2] = {0, 0};
3213  Int           iZeroMvdDir = -1;
3214#endif
3215
3216  TComMvField cMvFieldNeighbours[MRG_MAX_NUM_CANDS << 1]; // double length for mv of both lists
3217  UChar uhInterDirNeighbours[MRG_MAX_NUM_CANDS];
3218  Int numValidMergeCand = 0 ;
3219
3220  for ( Int iPartIdx = 0; iPartIdx < iNumPart; iPartIdx++ )
3221  {
3222    UInt          uiCost[2] = { MAX_UINT, MAX_UINT };
3223    UInt          uiCostBi  =   MAX_UINT;
3224    UInt          uiCostTemp;
3225   
3226    UInt          uiBits[3];
3227    UInt          uiBitsTemp;
3228#if ZERO_MVD_EST
3229    UInt          uiZeroMvdCost = MAX_UINT;
3230    UInt          uiZeroMvdCostTemp;
3231    UInt          uiZeroMvdBitsTemp;
3232    UInt          uiZeroMvdDistTemp = MAX_UINT;
3233    UInt          auiZeroMvdBits[3];
3234#endif
3235    UInt          bestBiPDist = MAX_INT;
3236
3237    UInt          uiCostTempL0[MAX_NUM_REF];
3238    for (Int iNumRef=0; iNumRef < MAX_NUM_REF; iNumRef++)
3239    {
3240      uiCostTempL0[iNumRef] = MAX_UINT;
3241    }
3242    UInt          uiBitsTempL0[MAX_NUM_REF];
3243
3244    TComMv        mvValidList1;
3245    Int           refIdxValidList1 = 0;
3246    UInt          bitsValidList1 = MAX_UINT;
3247    UInt          costValidList1 = MAX_UINT;
3248
3249    xGetBlkBits( ePartSize, pcCU->getSlice()->isInterP(), iPartIdx, uiLastMode, uiMbBits);
3250   
3251    pcCU->getPartIndexAndSize( iPartIdx, uiPartAddr, iRoiWidth, iRoiHeight );
3252   
3253#if AMP_MRG
3254    Bool bTestNormalMC = true;
3255   
3256    if ( bUseMRG && pcCU->getWidth( 0 ) > 8 && iNumPart == 2 )
3257    {
3258      bTestNormalMC = false;
3259    }
3260   
3261    if (bTestNormalMC)
3262    {
3263#endif
3264
3265    //  Uni-directional prediction
3266    for ( Int iRefList = 0; iRefList < iNumPredDir; iRefList++ )
3267    {
3268      RefPicList  eRefPicList = ( iRefList ? REF_PIC_LIST_1 : REF_PIC_LIST_0 );
3269     
3270      for ( Int iRefIdxTemp = 0; iRefIdxTemp < pcCU->getSlice()->getNumRefIdx(eRefPicList); iRefIdxTemp++ )
3271      {
3272#if N0383_IL_CONSTRAINED_TILE_SETS_SEI
3273        if (pcCU->getSlice()->getRefPic( eRefPicList, iRefIdxTemp )->isILR(pcCU->getLayerId()) && m_disableILP)
3274        {
3275          continue;
3276        }
3277#endif
3278#if (ENCODER_FAST_MODE)
3279        TComPic* pcPic    = pcCU->getSlice()->getRefPic( eRefPicList, iRefIdxTemp );
3280        if( pcPic->isILR(pcCU->getLayerId()) && (ePartSize == SIZE_2Nx2N) ) 
3281        {
3282          continue;
3283        }
3284#endif
3285
3286        uiBitsTemp = uiMbBits[iRefList];
3287        if ( pcCU->getSlice()->getNumRefIdx(eRefPicList) > 1 )
3288        {
3289          uiBitsTemp += iRefIdxTemp+1;
3290          if ( iRefIdxTemp == pcCU->getSlice()->getNumRefIdx(eRefPicList)-1 ) uiBitsTemp--;
3291        }
3292#if ZERO_MVD_EST
3293        xEstimateMvPredAMVP( pcCU, pcOrgYuv, iPartIdx, eRefPicList, iRefIdxTemp, cMvPred[iRefList][iRefIdxTemp], false, &biPDistTemp, &uiZeroMvdDistTemp);
3294#else
3295        xEstimateMvPredAMVP( pcCU, pcOrgYuv, iPartIdx, eRefPicList, iRefIdxTemp, cMvPred[iRefList][iRefIdxTemp], false, &biPDistTemp);
3296#endif
3297        aaiMvpIdx[iRefList][iRefIdxTemp] = pcCU->getMVPIdx(eRefPicList, uiPartAddr);
3298        aaiMvpNum[iRefList][iRefIdxTemp] = pcCU->getMVPNum(eRefPicList, uiPartAddr);
3299       
3300        if(pcCU->getSlice()->getMvdL1ZeroFlag() && iRefList==1 && biPDistTemp < bestBiPDist)
3301        {
3302#if REF_IDX_ME_ZEROMV
3303          Bool bZeroMVILR = pcCU->xCheckZeroMVILRMvdL1Zero(iRefList, iRefIdxTemp, aaiMvpIdx[iRefList][iRefIdxTemp]);
3304          if(bZeroMVILR)
3305          {
3306#endif
3307          bestBiPDist = biPDistTemp;
3308          bestBiPMvpL1 = aaiMvpIdx[iRefList][iRefIdxTemp];
3309          bestBiPRefIdxL1 = iRefIdxTemp;
3310#if REF_IDX_ME_ZEROMV
3311          }
3312#endif
3313        }
3314
3315        uiBitsTemp += m_auiMVPIdxCost[aaiMvpIdx[iRefList][iRefIdxTemp]][AMVP_MAX_NUM_CANDS];
3316#if ZERO_MVD_EST
3317        if ( iRefList == 0 || pcCU->getSlice()->getList1IdxToList0Idx( iRefIdxTemp ) < 0 )
3318        {
3319          uiZeroMvdBitsTemp = uiBitsTemp;
3320          uiZeroMvdBitsTemp += 2; //zero mvd bits
3321
3322          m_pcRdCost->getMotionCost( 1, 0 );
3323          uiZeroMvdCostTemp = uiZeroMvdDistTemp + m_pcRdCost->getCost(uiZeroMvdBitsTemp);
3324
3325          if (uiZeroMvdCostTemp < uiZeroMvdCost)
3326          {
3327            uiZeroMvdCost = uiZeroMvdCostTemp;
3328            iZeroMvdDir = iRefList + 1;
3329            aiZeroMvdRefIdx[iRefList] = iRefIdxTemp;
3330            aiZeroMvdMvpIdx[iRefList] = aaiMvpIdx[iRefList][iRefIdxTemp];
3331            auiZeroMvdBits[iRefList] = uiZeroMvdBitsTemp;
3332          }         
3333        }
3334#endif
3335       
3336#if GPB_SIMPLE_UNI
3337        if ( iRefList == 1 )    // list 1
3338        {
3339          if ( pcCU->getSlice()->getList1IdxToList0Idx( iRefIdxTemp ) >= 0 )
3340          {
3341            cMvTemp[1][iRefIdxTemp] = cMvTemp[0][pcCU->getSlice()->getList1IdxToList0Idx( iRefIdxTemp )];
3342            uiCostTemp = uiCostTempL0[pcCU->getSlice()->getList1IdxToList0Idx( iRefIdxTemp )];
3343            /*first subtract the bit-rate part of the cost of the other list*/
3344            uiCostTemp -= m_pcRdCost->getCost( uiBitsTempL0[pcCU->getSlice()->getList1IdxToList0Idx( iRefIdxTemp )] );
3345            /*correct the bit-rate part of the current ref*/
3346            m_pcRdCost->setPredictor  ( cMvPred[iRefList][iRefIdxTemp] );
3347            uiBitsTemp += m_pcRdCost->getBits( cMvTemp[1][iRefIdxTemp].getHor(), cMvTemp[1][iRefIdxTemp].getVer() );
3348            /*calculate the correct cost*/
3349            uiCostTemp += m_pcRdCost->getCost( uiBitsTemp );
3350          }
3351          else
3352          {
3353            xMotionEstimation ( pcCU, pcOrgYuv, iPartIdx, eRefPicList, &cMvPred[iRefList][iRefIdxTemp], iRefIdxTemp, cMvTemp[iRefList][iRefIdxTemp], uiBitsTemp, uiCostTemp );
3354          }
3355        }
3356        else
3357        {
3358          xMotionEstimation ( pcCU, pcOrgYuv, iPartIdx, eRefPicList, &cMvPred[iRefList][iRefIdxTemp], iRefIdxTemp, cMvTemp[iRefList][iRefIdxTemp], uiBitsTemp, uiCostTemp );
3359        }
3360#else
3361        xMotionEstimation ( pcCU, pcOrgYuv, iPartIdx, eRefPicList, &cMvPred[iRefList][iRefIdxTemp], iRefIdxTemp, cMvTemp[iRefList][iRefIdxTemp], uiBitsTemp, uiCostTemp );
3362#endif
3363        xCopyAMVPInfo(pcCU->getCUMvField(eRefPicList)->getAMVPInfo(), &aacAMVPInfo[iRefList][iRefIdxTemp]); // must always be done ( also when AMVP_MODE = AM_NONE )
3364        xCheckBestMVP(pcCU, eRefPicList, cMvTemp[iRefList][iRefIdxTemp], cMvPred[iRefList][iRefIdxTemp], aaiMvpIdx[iRefList][iRefIdxTemp], uiBitsTemp, uiCostTemp);
3365
3366        if ( iRefList == 0 )
3367        {
3368          uiCostTempL0[iRefIdxTemp] = uiCostTemp;
3369          uiBitsTempL0[iRefIdxTemp] = uiBitsTemp;
3370        }
3371        if ( uiCostTemp < uiCost[iRefList] )
3372        {
3373          uiCost[iRefList] = uiCostTemp;
3374          uiBits[iRefList] = uiBitsTemp; // storing for bi-prediction
3375
3376          // set motion
3377          cMv[iRefList]     = cMvTemp[iRefList][iRefIdxTemp];
3378          iRefIdx[iRefList] = iRefIdxTemp;
3379        }
3380
3381        if ( iRefList == 1 && uiCostTemp < costValidList1 && pcCU->getSlice()->getList1IdxToList0Idx( iRefIdxTemp ) < 0 )
3382        {
3383          costValidList1 = uiCostTemp;
3384          bitsValidList1 = uiBitsTemp;
3385
3386          // set motion
3387          mvValidList1     = cMvTemp[iRefList][iRefIdxTemp];
3388          refIdxValidList1 = iRefIdxTemp;
3389        }
3390      }
3391    }
3392    //  Bi-directional prediction
3393#if REF_IDX_ME_ZEROMV
3394    if ( (pcCU->getSlice()->isInterB()) && (pcCU->isBipredRestriction(iPartIdx) == false) && !(pcCU->getSlice()->getMvdL1ZeroFlag() && bestBiPDist == MAX_INT) )
3395#else
3396    if ( (pcCU->getSlice()->isInterB()) && (pcCU->isBipredRestriction(iPartIdx) == false) )
3397#endif
3398    {
3399     
3400      cMvBi[0] = cMv[0];            cMvBi[1] = cMv[1];
3401      iRefIdxBi[0] = iRefIdx[0];    iRefIdxBi[1] = iRefIdx[1];
3402     
3403      ::memcpy(cMvPredBi, cMvPred, sizeof(cMvPred));
3404      ::memcpy(aaiMvpIdxBi, aaiMvpIdx, sizeof(aaiMvpIdx));
3405     
3406      UInt uiMotBits[2];
3407
3408      if(pcCU->getSlice()->getMvdL1ZeroFlag())
3409      {
3410        xCopyAMVPInfo(&aacAMVPInfo[1][bestBiPRefIdxL1], pcCU->getCUMvField(REF_PIC_LIST_1)->getAMVPInfo());
3411        pcCU->setMVPIdxSubParts( bestBiPMvpL1, REF_PIC_LIST_1, uiPartAddr, iPartIdx, pcCU->getDepth(uiPartAddr));
3412        aaiMvpIdxBi[1][bestBiPRefIdxL1] = bestBiPMvpL1;
3413        cMvPredBi[1][bestBiPRefIdxL1]   = pcCU->getCUMvField(REF_PIC_LIST_1)->getAMVPInfo()->m_acMvCand[bestBiPMvpL1];
3414
3415        cMvBi[1] = cMvPredBi[1][bestBiPRefIdxL1];
3416        iRefIdxBi[1] = bestBiPRefIdxL1;
3417        pcCU->getCUMvField( REF_PIC_LIST_1 )->setAllMv( cMvBi[1], ePartSize, uiPartAddr, 0, iPartIdx );
3418        pcCU->getCUMvField( REF_PIC_LIST_1 )->setAllRefIdx( iRefIdxBi[1], ePartSize, uiPartAddr, 0, iPartIdx );
3419        TComYuv* pcYuvPred = &m_acYuvPred[1];
3420        motionCompensation( pcCU, pcYuvPred, REF_PIC_LIST_1, iPartIdx );
3421
3422        uiMotBits[0] = uiBits[0] - uiMbBits[0];
3423        uiMotBits[1] = uiMbBits[1];
3424
3425        if ( pcCU->getSlice()->getNumRefIdx(REF_PIC_LIST_1) > 1 )
3426        {
3427          uiMotBits[1] += bestBiPRefIdxL1+1;
3428          if ( bestBiPRefIdxL1 == pcCU->getSlice()->getNumRefIdx(REF_PIC_LIST_1)-1 ) uiMotBits[1]--;
3429        }
3430
3431        uiMotBits[1] += m_auiMVPIdxCost[aaiMvpIdxBi[1][bestBiPRefIdxL1]][AMVP_MAX_NUM_CANDS];
3432
3433        uiBits[2] = uiMbBits[2] + uiMotBits[0] + uiMotBits[1];
3434
3435        cMvTemp[1][bestBiPRefIdxL1] = cMvBi[1];
3436      }
3437      else
3438      {
3439        uiMotBits[0] = uiBits[0] - uiMbBits[0];
3440        uiMotBits[1] = uiBits[1] - uiMbBits[1];
3441        uiBits[2] = uiMbBits[2] + uiMotBits[0] + uiMotBits[1];
3442      }
3443
3444      // 4-times iteration (default)
3445      Int iNumIter = 4;
3446     
3447      // fast encoder setting: only one iteration
3448      if ( m_pcEncCfg->getUseFastEnc() || pcCU->getSlice()->getMvdL1ZeroFlag())
3449      {
3450        iNumIter = 1;
3451      }
3452     
3453      for ( Int iIter = 0; iIter < iNumIter; iIter++ )
3454      {
3455       
3456        Int         iRefList    = iIter % 2;
3457        if ( m_pcEncCfg->getUseFastEnc() )
3458        {
3459          if( uiCost[0] <= uiCost[1] )
3460          {
3461            iRefList = 1;
3462          }
3463          else
3464          {
3465            iRefList = 0;
3466          }
3467        }
3468        else if ( iIter == 0 )
3469        {
3470          iRefList = 0;
3471        }
3472        if ( iIter == 0 && !pcCU->getSlice()->getMvdL1ZeroFlag())
3473        {
3474          pcCU->getCUMvField(RefPicList(1-iRefList))->setAllMv( cMv[1-iRefList], ePartSize, uiPartAddr, 0, iPartIdx );
3475          pcCU->getCUMvField(RefPicList(1-iRefList))->setAllRefIdx( iRefIdx[1-iRefList], ePartSize, uiPartAddr, 0, iPartIdx );
3476          TComYuv*  pcYuvPred = &m_acYuvPred[1-iRefList];
3477          motionCompensation ( pcCU, pcYuvPred, RefPicList(1-iRefList), iPartIdx );
3478        }
3479        RefPicList  eRefPicList = ( iRefList ? REF_PIC_LIST_1 : REF_PIC_LIST_0 );
3480
3481        if(pcCU->getSlice()->getMvdL1ZeroFlag())
3482        {
3483          iRefList = 0;
3484          eRefPicList = REF_PIC_LIST_0;
3485        }
3486
3487        Bool bChanged = false;
3488       
3489#if (ENCODER_FAST_MODE)
3490        Bool     testIter = true;
3491        TComPic* pcPic    = pcCU->getSlice()->getRefPic( RefPicList(1 - iRefList), iRefIdxBi[1 - iRefList] );
3492        if(pcPic->isILR(pcCU->getLayerId()) && (ePartSize == SIZE_2Nx2N))
3493        {
3494          testIter = false;  //the fixed part is ILR, skip this iteration       
3495        }
3496#if N0383_IL_CONSTRAINED_TILE_SETS_SEI
3497        if (pcPic->isILR(pcCU->getLayerId()) && m_disableILP)
3498        {
3499          testIter = false;
3500        }
3501#endif
3502        if(testIter)
3503        {
3504#endif
3505        iRefStart = 0;
3506        iRefEnd   = pcCU->getSlice()->getNumRefIdx(eRefPicList)-1;
3507       
3508        for ( Int iRefIdxTemp = iRefStart; iRefIdxTemp <= iRefEnd; iRefIdxTemp++ )
3509        {
3510#if (ENCODER_FAST_MODE)
3511          Bool testRefIdx = true;
3512          pcPic           = pcCU->getSlice()->getRefPic( RefPicList(iRefList) , iRefIdxTemp );
3513          if(pcPic->isILR(pcCU->getLayerId()) && (ePartSize == SIZE_2Nx2N))
3514          {
3515            testRefIdx = false;  //the refined part is ILR, skip this reference pic           
3516          }
3517#if N0383_IL_CONSTRAINED_TILE_SETS_SEI
3518          if (pcPic->isILR(pcCU->getLayerId()) && m_disableILP)
3519          {
3520            testRefIdx = false;
3521          }
3522#endif
3523          if(testRefIdx)
3524          {
3525#endif
3526          uiBitsTemp = uiMbBits[2] + uiMotBits[1-iRefList];
3527          if ( pcCU->getSlice()->getNumRefIdx(eRefPicList) > 1 )
3528          {
3529            uiBitsTemp += iRefIdxTemp+1;
3530            if ( iRefIdxTemp == pcCU->getSlice()->getNumRefIdx(eRefPicList)-1 ) uiBitsTemp--;
3531          }
3532          uiBitsTemp += m_auiMVPIdxCost[aaiMvpIdxBi[iRefList][iRefIdxTemp]][AMVP_MAX_NUM_CANDS];
3533          // call ME
3534          xMotionEstimation ( pcCU, pcOrgYuv, iPartIdx, eRefPicList, &cMvPredBi[iRefList][iRefIdxTemp], iRefIdxTemp, cMvTemp[iRefList][iRefIdxTemp], uiBitsTemp, uiCostTemp, true );
3535          xCopyAMVPInfo(&aacAMVPInfo[iRefList][iRefIdxTemp], pcCU->getCUMvField(eRefPicList)->getAMVPInfo());
3536          xCheckBestMVP(pcCU, eRefPicList, cMvTemp[iRefList][iRefIdxTemp], cMvPredBi[iRefList][iRefIdxTemp], aaiMvpIdxBi[iRefList][iRefIdxTemp], uiBitsTemp, uiCostTemp);
3537
3538          if ( uiCostTemp < uiCostBi )
3539          {
3540            bChanged = true;
3541           
3542            cMvBi[iRefList]     = cMvTemp[iRefList][iRefIdxTemp];
3543            iRefIdxBi[iRefList] = iRefIdxTemp;
3544           
3545            uiCostBi            = uiCostTemp;
3546            uiMotBits[iRefList] = uiBitsTemp - uiMbBits[2] - uiMotBits[1-iRefList];
3547            uiBits[2]           = uiBitsTemp;
3548           
3549            if(iNumIter!=1)
3550            {
3551              //  Set motion
3552              pcCU->getCUMvField( eRefPicList )->setAllMv( cMvBi[iRefList], ePartSize, uiPartAddr, 0, iPartIdx );
3553              pcCU->getCUMvField( eRefPicList )->setAllRefIdx( iRefIdxBi[iRefList], ePartSize, uiPartAddr, 0, iPartIdx );
3554
3555              TComYuv* pcYuvPred = &m_acYuvPred[iRefList];
3556              motionCompensation( pcCU, pcYuvPred, eRefPicList, iPartIdx );
3557            }
3558          }
3559#if (ENCODER_FAST_MODE)
3560          }
3561#endif
3562        }
3563#if (ENCODER_FAST_MODE)
3564        } // for loop-iRefIdxTemp
3565#endif
3566       
3567        if ( !bChanged )
3568        {
3569          if ( uiCostBi <= uiCost[0] && uiCostBi <= uiCost[1] )
3570          {
3571            xCopyAMVPInfo(&aacAMVPInfo[0][iRefIdxBi[0]], pcCU->getCUMvField(REF_PIC_LIST_0)->getAMVPInfo());
3572            xCheckBestMVP(pcCU, REF_PIC_LIST_0, cMvBi[0], cMvPredBi[0][iRefIdxBi[0]], aaiMvpIdxBi[0][iRefIdxBi[0]], uiBits[2], uiCostBi);
3573            if(!pcCU->getSlice()->getMvdL1ZeroFlag())
3574            {
3575              xCopyAMVPInfo(&aacAMVPInfo[1][iRefIdxBi[1]], pcCU->getCUMvField(REF_PIC_LIST_1)->getAMVPInfo());
3576              xCheckBestMVP(pcCU, REF_PIC_LIST_1, cMvBi[1], cMvPredBi[1][iRefIdxBi[1]], aaiMvpIdxBi[1][iRefIdxBi[1]], uiBits[2], uiCostBi);
3577            }
3578          }
3579          break;
3580        }
3581      } // for loop-iter
3582    } // if (B_SLICE)
3583#if ZERO_MVD_EST
3584    if ( (pcCU->getSlice()->isInterB()) && (pcCU->isBipredRestriction(iPartIdx) == false) )
3585    {
3586      m_pcRdCost->getMotionCost( 1, 0 );
3587
3588      for ( Int iL0RefIdxTemp = 0; iL0RefIdxTemp <= pcCU->getSlice()->getNumRefIdx(REF_PIC_LIST_0)-1; iL0RefIdxTemp++ )
3589      for ( Int iL1RefIdxTemp = 0; iL1RefIdxTemp <= pcCU->getSlice()->getNumRefIdx(REF_PIC_LIST_1)-1; iL1RefIdxTemp++ )
3590      {
3591        UInt uiRefIdxBitsTemp = 0;
3592        if ( pcCU->getSlice()->getNumRefIdx(REF_PIC_LIST_0) > 1 )
3593        {
3594          uiRefIdxBitsTemp += iL0RefIdxTemp+1;
3595          if ( iL0RefIdxTemp == pcCU->getSlice()->getNumRefIdx(REF_PIC_LIST_0)-1 ) uiRefIdxBitsTemp--;
3596        }
3597        if ( pcCU->getSlice()->getNumRefIdx(REF_PIC_LIST_1) > 1 )
3598        {
3599          uiRefIdxBitsTemp += iL1RefIdxTemp+1;
3600          if ( iL1RefIdxTemp == pcCU->getSlice()->getNumRefIdx(REF_PIC_LIST_1)-1 ) uiRefIdxBitsTemp--;
3601        }
3602
3603        Int iL0MVPIdx = 0;
3604        Int iL1MVPIdx = 0;
3605
3606        for (iL0MVPIdx = 0; iL0MVPIdx < aaiMvpNum[0][iL0RefIdxTemp]; iL0MVPIdx++)
3607        {
3608          for (iL1MVPIdx = 0; iL1MVPIdx < aaiMvpNum[1][iL1RefIdxTemp]; iL1MVPIdx++)
3609          {
3610            uiZeroMvdBitsTemp = uiRefIdxBitsTemp;
3611            uiZeroMvdBitsTemp += uiMbBits[2];
3612            uiZeroMvdBitsTemp += m_auiMVPIdxCost[iL0MVPIdx][aaiMvpNum[0][iL0RefIdxTemp]] + m_auiMVPIdxCost[iL1MVPIdx][aaiMvpNum[1][iL1RefIdxTemp]];
3613            uiZeroMvdBitsTemp += 4; //zero mvd for both directions
3614            pcCU->getCUMvField( REF_PIC_LIST_0 )->setAllMvField( aacAMVPInfo[0][iL0RefIdxTemp].m_acMvCand[iL0MVPIdx], iL0RefIdxTemp, ePartSize, uiPartAddr, iPartIdx, 0 );
3615            pcCU->getCUMvField( REF_PIC_LIST_1 )->setAllMvField( aacAMVPInfo[1][iL1RefIdxTemp].m_acMvCand[iL1MVPIdx], iL1RefIdxTemp, ePartSize, uiPartAddr, iPartIdx, 0 );
3616 
3617            xGetInterPredictionError( pcCU, pcOrgYuv, iPartIdx, uiZeroMvdDistTemp, m_pcEncCfg->getUseHADME() );
3618            uiZeroMvdCostTemp = uiZeroMvdDistTemp + m_pcRdCost->getCost( uiZeroMvdBitsTemp );
3619            if (uiZeroMvdCostTemp < uiZeroMvdCost)
3620            {
3621              uiZeroMvdCost = uiZeroMvdCostTemp;
3622              iZeroMvdDir = 3;
3623              aiZeroMvdMvpIdx[0] = iL0MVPIdx;
3624              aiZeroMvdMvpIdx[1] = iL1MVPIdx;
3625              aiZeroMvdRefIdx[0] = iL0RefIdxTemp;
3626              aiZeroMvdRefIdx[1] = iL1RefIdxTemp;
3627              auiZeroMvdBits[2] = uiZeroMvdBitsTemp;
3628            }
3629          }
3630        }
3631      }
3632    }
3633#endif
3634
3635#if AMP_MRG
3636    } //end if bTestNormalMC
3637#endif
3638    //  Clear Motion Field
3639    pcCU->getCUMvField(REF_PIC_LIST_0)->setAllMvField( TComMvField(), ePartSize, uiPartAddr, 0, iPartIdx );
3640    pcCU->getCUMvField(REF_PIC_LIST_1)->setAllMvField( TComMvField(), ePartSize, uiPartAddr, 0, iPartIdx );
3641    pcCU->getCUMvField(REF_PIC_LIST_0)->setAllMvd    ( cMvZero,       ePartSize, uiPartAddr, 0, iPartIdx );
3642    pcCU->getCUMvField(REF_PIC_LIST_1)->setAllMvd    ( cMvZero,       ePartSize, uiPartAddr, 0, iPartIdx );
3643
3644    pcCU->setMVPIdxSubParts( -1, REF_PIC_LIST_0, uiPartAddr, iPartIdx, pcCU->getDepth(uiPartAddr));
3645    pcCU->setMVPNumSubParts( -1, REF_PIC_LIST_0, uiPartAddr, iPartIdx, pcCU->getDepth(uiPartAddr));
3646    pcCU->setMVPIdxSubParts( -1, REF_PIC_LIST_1, uiPartAddr, iPartIdx, pcCU->getDepth(uiPartAddr));
3647    pcCU->setMVPNumSubParts( -1, REF_PIC_LIST_1, uiPartAddr, iPartIdx, pcCU->getDepth(uiPartAddr));
3648   
3649    UInt uiMEBits = 0;
3650    // Set Motion Field_
3651    cMv[1] = mvValidList1;
3652    iRefIdx[1] = refIdxValidList1;
3653    uiBits[1] = bitsValidList1;
3654    uiCost[1] = costValidList1;
3655#if AMP_MRG
3656    if (bTestNormalMC)
3657    {
3658#endif
3659#if ZERO_MVD_EST
3660    if (uiZeroMvdCost <= uiCostBi && uiZeroMvdCost <= uiCost[0] && uiZeroMvdCost <= uiCost[1])
3661    {
3662      if (iZeroMvdDir == 3)
3663      {
3664        uiLastMode = 2;
3665
3666        pcCU->getCUMvField(REF_PIC_LIST_0)->setAllMvField( aacAMVPInfo[0][aiZeroMvdRefIdx[0]].m_acMvCand[aiZeroMvdMvpIdx[0]], aiZeroMvdRefIdx[0], ePartSize, uiPartAddr, iPartIdx, 0 );
3667        pcCU->getCUMvField(REF_PIC_LIST_1)->setAllMvField( aacAMVPInfo[1][aiZeroMvdRefIdx[1]].m_acMvCand[aiZeroMvdMvpIdx[1]], aiZeroMvdRefIdx[1], ePartSize, uiPartAddr, iPartIdx, 0 );
3668 
3669        pcCU->setInterDirSubParts( 3, uiPartAddr, iPartIdx, pcCU->getDepth(0) );
3670       
3671        pcCU->setMVPIdxSubParts( aiZeroMvdMvpIdx[0], REF_PIC_LIST_0, uiPartAddr, iPartIdx, pcCU->getDepth(uiPartAddr));
3672        pcCU->setMVPNumSubParts( aaiMvpNum[0][aiZeroMvdRefIdx[0]], REF_PIC_LIST_0, uiPartAddr, iPartIdx, pcCU->getDepth(uiPartAddr));
3673        pcCU->setMVPIdxSubParts( aiZeroMvdMvpIdx[1], REF_PIC_LIST_1, uiPartAddr, iPartIdx, pcCU->getDepth(uiPartAddr));
3674        pcCU->setMVPNumSubParts( aaiMvpNum[1][aiZeroMvdRefIdx[1]], REF_PIC_LIST_1, uiPartAddr, iPartIdx, pcCU->getDepth(uiPartAddr));
3675        uiMEBits = auiZeroMvdBits[2];
3676      }
3677      else if (iZeroMvdDir == 1)
3678      {       
3679        uiLastMode = 0;
3680
3681        pcCU->getCUMvField(REF_PIC_LIST_0)->setAllMvField( aacAMVPInfo[0][aiZeroMvdRefIdx[0]].m_acMvCand[aiZeroMvdMvpIdx[0]], aiZeroMvdRefIdx[0], ePartSize, uiPartAddr, iPartIdx, 0 );
3682
3683        pcCU->setInterDirSubParts( 1, uiPartAddr, iPartIdx, pcCU->getDepth(0) );
3684       
3685        pcCU->setMVPIdxSubParts( aiZeroMvdMvpIdx[0], REF_PIC_LIST_0, uiPartAddr, iPartIdx, pcCU->getDepth(uiPartAddr));
3686        pcCU->setMVPNumSubParts( aaiMvpNum[0][aiZeroMvdRefIdx[0]], REF_PIC_LIST_0, uiPartAddr, iPartIdx, pcCU->getDepth(uiPartAddr));
3687        uiMEBits = auiZeroMvdBits[0];
3688      }
3689      else if (iZeroMvdDir == 2)
3690      {
3691        uiLastMode = 1;
3692
3693        pcCU->getCUMvField(REF_PIC_LIST_1)->setAllMvField( aacAMVPInfo[1][aiZeroMvdRefIdx[1]].m_acMvCand[aiZeroMvdMvpIdx[1]], aiZeroMvdRefIdx[1], ePartSize, uiPartAddr, iPartIdx, 0 );
3694
3695        pcCU->setInterDirSubParts( 2, uiPartAddr, iPartIdx, pcCU->getDepth(0) );
3696       
3697        pcCU->setMVPIdxSubParts( aiZeroMvdMvpIdx[1], REF_PIC_LIST_1, uiPartAddr, iPartIdx, pcCU->getDepth(uiPartAddr));
3698        pcCU->setMVPNumSubParts( aaiMvpNum[1][aiZeroMvdRefIdx[1]], REF_PIC_LIST_1, uiPartAddr, iPartIdx, pcCU->getDepth(uiPartAddr));
3699        uiMEBits = auiZeroMvdBits[1];
3700      }
3701      else
3702      {
3703        assert(0);
3704      }
3705    }
3706    else
3707#endif
3708    if ( uiCostBi <= uiCost[0] && uiCostBi <= uiCost[1])
3709    {
3710      uiLastMode = 2;
3711      pcCU->getCUMvField(REF_PIC_LIST_0)->setAllMv( cMvBi[0], ePartSize, uiPartAddr, 0, iPartIdx );
3712      pcCU->getCUMvField(REF_PIC_LIST_0)->setAllRefIdx( iRefIdxBi[0], ePartSize, uiPartAddr, 0, iPartIdx );
3713      pcCU->getCUMvField(REF_PIC_LIST_1)->setAllMv( cMvBi[1], ePartSize, uiPartAddr, 0, iPartIdx );
3714      pcCU->getCUMvField(REF_PIC_LIST_1)->setAllRefIdx( iRefIdxBi[1], ePartSize, uiPartAddr, 0, iPartIdx );
3715     
3716      TempMv = cMvBi[0] - cMvPredBi[0][iRefIdxBi[0]];
3717      pcCU->getCUMvField(REF_PIC_LIST_0)->setAllMvd    ( TempMv,                 ePartSize, uiPartAddr, 0, iPartIdx );
3718     
3719      TempMv = cMvBi[1] - cMvPredBi[1][iRefIdxBi[1]];
3720      pcCU->getCUMvField(REF_PIC_LIST_1)->setAllMvd    ( TempMv,                 ePartSize, uiPartAddr, 0, iPartIdx );
3721     
3722      pcCU->setInterDirSubParts( 3, uiPartAddr, iPartIdx, pcCU->getDepth(0) );
3723     
3724      pcCU->setMVPIdxSubParts( aaiMvpIdxBi[0][iRefIdxBi[0]], REF_PIC_LIST_0, uiPartAddr, iPartIdx, pcCU->getDepth(uiPartAddr));
3725      pcCU->setMVPNumSubParts( aaiMvpNum[0][iRefIdxBi[0]], REF_PIC_LIST_0, uiPartAddr, iPartIdx, pcCU->getDepth(uiPartAddr));
3726      pcCU->setMVPIdxSubParts( aaiMvpIdxBi[1][iRefIdxBi[1]], REF_PIC_LIST_1, uiPartAddr, iPartIdx, pcCU->getDepth(uiPartAddr));
3727      pcCU->setMVPNumSubParts( aaiMvpNum[1][iRefIdxBi[1]], REF_PIC_LIST_1, uiPartAddr, iPartIdx, pcCU->getDepth(uiPartAddr));
3728
3729      uiMEBits = uiBits[2];
3730    }
3731    else if ( uiCost[0] <= uiCost[1] )
3732    {
3733      uiLastMode = 0;
3734      pcCU->getCUMvField(REF_PIC_LIST_0)->setAllMv( cMv[0], ePartSize, uiPartAddr, 0, iPartIdx );
3735      pcCU->getCUMvField(REF_PIC_LIST_0)->setAllRefIdx( iRefIdx[0], ePartSize, uiPartAddr, 0, iPartIdx );
3736      TempMv = cMv[0] - cMvPred[0][iRefIdx[0]];
3737      pcCU->getCUMvField(REF_PIC_LIST_0)->setAllMvd    ( TempMv,                 ePartSize, uiPartAddr, 0, iPartIdx );
3738      pcCU->setInterDirSubParts( 1, uiPartAddr, iPartIdx, pcCU->getDepth(0) );
3739     
3740      pcCU->setMVPIdxSubParts( aaiMvpIdx[0][iRefIdx[0]], REF_PIC_LIST_0, uiPartAddr, iPartIdx, pcCU->getDepth(uiPartAddr));
3741      pcCU->setMVPNumSubParts( aaiMvpNum[0][iRefIdx[0]], REF_PIC_LIST_0, uiPartAddr, iPartIdx, pcCU->getDepth(uiPartAddr));
3742
3743      uiMEBits = uiBits[0];
3744    }
3745    else
3746    {
3747      uiLastMode = 1;
3748      pcCU->getCUMvField(REF_PIC_LIST_1)->setAllMv( cMv[1], ePartSize, uiPartAddr, 0, iPartIdx );
3749      pcCU->getCUMvField(REF_PIC_LIST_1)->setAllRefIdx( iRefIdx[1], ePartSize, uiPartAddr, 0, iPartIdx );
3750      TempMv = cMv[1] - cMvPred[1][iRefIdx[1]];
3751      pcCU->getCUMvField(REF_PIC_LIST_1)->setAllMvd    ( TempMv,                 ePartSize, uiPartAddr, 0, iPartIdx );
3752      pcCU->setInterDirSubParts( 2, uiPartAddr, iPartIdx, pcCU->getDepth(0) );
3753     
3754      pcCU->setMVPIdxSubParts( aaiMvpIdx[1][iRefIdx[1]], REF_PIC_LIST_1, uiPartAddr, iPartIdx, pcCU->getDepth(uiPartAddr));
3755      pcCU->setMVPNumSubParts( aaiMvpNum[1][iRefIdx[1]], REF_PIC_LIST_1, uiPartAddr, iPartIdx, pcCU->getDepth(uiPartAddr));
3756
3757      uiMEBits = uiBits[1];
3758    }
3759#if AMP_MRG
3760    } // end if bTestNormalMC
3761#endif
3762
3763    if ( pcCU->getPartitionSize( uiPartAddr ) != SIZE_2Nx2N )
3764    {
3765      UInt uiMRGInterDir = 0;     
3766      TComMvField cMRGMvField[2];
3767      UInt uiMRGIndex = 0;
3768
3769      UInt uiMEInterDir = 0;
3770      TComMvField cMEMvField[2];
3771
3772      m_pcRdCost->getMotionCost( 1, 0 );
3773#if AMP_MRG
3774      // calculate ME cost
3775      UInt uiMEError = MAX_UINT;
3776      UInt uiMECost = MAX_UINT;
3777
3778      if (bTestNormalMC)
3779      {
3780        xGetInterPredictionError( pcCU, pcOrgYuv, iPartIdx, uiMEError, m_pcEncCfg->getUseHADME() );
3781        uiMECost = uiMEError + m_pcRdCost->getCost( uiMEBits );
3782      }
3783#else
3784      // calculate ME cost
3785      UInt uiMEError = MAX_UINT;
3786      xGetInterPredictionError( pcCU, pcOrgYuv, iPartIdx, uiMEError, m_pcEncCfg->getUseHADME() );
3787      UInt uiMECost = uiMEError + m_pcRdCost->getCost( uiMEBits );
3788#endif
3789      // save ME result.
3790      uiMEInterDir = pcCU->getInterDir( uiPartAddr );
3791      pcCU->getMvField( pcCU, uiPartAddr, REF_PIC_LIST_0, cMEMvField[0] );
3792      pcCU->getMvField( pcCU, uiPartAddr, REF_PIC_LIST_1, cMEMvField[1] );
3793
3794      // find Merge result
3795      UInt uiMRGCost = MAX_UINT;
3796      xMergeEstimation( pcCU, pcOrgYuv, iPartIdx, uiMRGInterDir, cMRGMvField, uiMRGIndex, uiMRGCost, cMvFieldNeighbours, uhInterDirNeighbours, numValidMergeCand);
3797      if ( uiMRGCost < uiMECost )
3798      {
3799        // set Merge result
3800        pcCU->setMergeFlagSubParts ( true,          uiPartAddr, iPartIdx, pcCU->getDepth( uiPartAddr ) );
3801        pcCU->setMergeIndexSubParts( uiMRGIndex,    uiPartAddr, iPartIdx, pcCU->getDepth( uiPartAddr ) );
3802        pcCU->setInterDirSubParts  ( uiMRGInterDir, uiPartAddr, iPartIdx, pcCU->getDepth( uiPartAddr ) );
3803        pcCU->getCUMvField( REF_PIC_LIST_0 )->setAllMvField( cMRGMvField[0], ePartSize, uiPartAddr, 0, iPartIdx );
3804        pcCU->getCUMvField( REF_PIC_LIST_1 )->setAllMvField( cMRGMvField[1], ePartSize, uiPartAddr, 0, iPartIdx );
3805
3806        pcCU->getCUMvField(REF_PIC_LIST_0)->setAllMvd    ( cMvZero,            ePartSize, uiPartAddr, 0, iPartIdx );
3807        pcCU->getCUMvField(REF_PIC_LIST_1)->setAllMvd    ( cMvZero,            ePartSize, uiPartAddr, 0, iPartIdx );
3808
3809        pcCU->setMVPIdxSubParts( -1, REF_PIC_LIST_0, uiPartAddr, iPartIdx, pcCU->getDepth(uiPartAddr));
3810        pcCU->setMVPNumSubParts( -1, REF_PIC_LIST_0, uiPartAddr, iPartIdx, pcCU->getDepth(uiPartAddr));
3811        pcCU->setMVPIdxSubParts( -1, REF_PIC_LIST_1, uiPartAddr, iPartIdx, pcCU->getDepth(uiPartAddr));
3812        pcCU->setMVPNumSubParts( -1, REF_PIC_LIST_1, uiPartAddr, iPartIdx, pcCU->getDepth(uiPartAddr));
3813      }
3814      else
3815      {
3816        // set ME result
3817        pcCU->setMergeFlagSubParts( false,        uiPartAddr, iPartIdx, pcCU->getDepth( uiPartAddr ) );
3818        pcCU->setInterDirSubParts ( uiMEInterDir, uiPartAddr, iPartIdx, pcCU->getDepth( uiPartAddr ) );
3819        pcCU->getCUMvField( REF_PIC_LIST_0 )->setAllMvField( cMEMvField[0], ePartSize, uiPartAddr, 0, iPartIdx );
3820        pcCU->getCUMvField( REF_PIC_LIST_1 )->setAllMvField( cMEMvField[1], ePartSize, uiPartAddr, 0, iPartIdx );
3821      }
3822    }
3823
3824    //  MC
3825    motionCompensation ( pcCU, rpcPredYuv, REF_PIC_LIST_X, iPartIdx );
3826   
3827  } //  end of for ( Int iPartIdx = 0; iPartIdx < iNumPart; iPartIdx++ )
3828
3829  setWpScalingDistParam( pcCU, -1, REF_PIC_LIST_X );
3830
3831  return;
3832}
3833
3834// AMVP
3835#if ZERO_MVD_EST
3836Void TEncSearch::xEstimateMvPredAMVP( TComDataCU* pcCU, TComYuv* pcOrgYuv, UInt uiPartIdx, RefPicList eRefPicList, Int iRefIdx, TComMv& rcMvPred, Bool bFilled, UInt* puiDistBiP, UInt* puiDist  )
3837#else
3838Void TEncSearch::xEstimateMvPredAMVP( TComDataCU* pcCU, TComYuv* pcOrgYuv, UInt uiPartIdx, RefPicList eRefPicList, Int iRefIdx, TComMv& rcMvPred, Bool bFilled, UInt* puiDistBiP )
3839#endif
3840{
3841  AMVPInfo* pcAMVPInfo = pcCU->getCUMvField(eRefPicList)->getAMVPInfo();
3842 
3843  TComMv  cBestMv;
3844  Int     iBestIdx = 0;
3845  TComMv  cZeroMv;
3846  TComMv  cMvPred;
3847  UInt    uiBestCost = MAX_INT;
3848  UInt    uiPartAddr = 0;
3849  Int     iRoiWidth, iRoiHeight;
3850  Int     i;
3851 
3852  pcCU->getPartIndexAndSize( uiPartIdx, uiPartAddr, iRoiWidth, iRoiHeight );
3853  // Fill the MV Candidates
3854  if (!bFilled)
3855  {
3856    pcCU->fillMvpCand( uiPartIdx, uiPartAddr, eRefPicList, iRefIdx, pcAMVPInfo );
3857  }
3858 
3859  // initialize Mvp index & Mvp
3860  iBestIdx = 0;
3861  cBestMv  = pcAMVPInfo->m_acMvCand[0];
3862#if !ZERO_MVD_EST
3863  if (pcAMVPInfo->iN <= 1)
3864  {
3865    rcMvPred = cBestMv;
3866   
3867    pcCU->setMVPIdxSubParts( iBestIdx, eRefPicList, uiPartAddr, uiPartIdx, pcCU->getDepth(uiPartAddr));
3868    pcCU->setMVPNumSubParts( pcAMVPInfo->iN, eRefPicList, uiPartAddr, uiPartIdx, pcCU->getDepth(uiPartAddr));
3869
3870    if(pcCU->getSlice()->getMvdL1ZeroFlag() && eRefPicList==REF_PIC_LIST_1)
3871    {
3872#if ZERO_MVD_EST
3873      (*puiDistBiP) = xGetTemplateCost( pcCU, uiPartIdx, uiPartAddr, pcOrgYuv, &m_cYuvPredTemp, rcMvPred, 0, AMVP_MAX_NUM_CANDS, eRefPicList, iRefIdx, iRoiWidth, iRoiHeight, uiDist );
3874#else
3875      (*puiDistBiP) = xGetTemplateCost( pcCU, uiPartIdx, uiPartAddr, pcOrgYuv, &m_cYuvPredTemp, rcMvPred, 0, AMVP_MAX_NUM_CANDS, eRefPicList, iRefIdx, iRoiWidth, iRoiHeight);
3876#endif
3877    }
3878    return;
3879  }
3880#endif 
3881  if (bFilled)
3882  {
3883    assert(pcCU->getMVPIdx(eRefPicList,uiPartAddr) >= 0);
3884    rcMvPred = pcAMVPInfo->m_acMvCand[pcCU->getMVPIdx(eRefPicList,uiPartAddr)];
3885    return;
3886  }
3887 
3888  m_cYuvPredTemp.clear();
3889#if ZERO_MVD_EST
3890  UInt uiDist;
3891#endif
3892  //-- Check Minimum Cost.
3893  for ( i = 0 ; i < pcAMVPInfo->iN; i++)
3894  {
3895    UInt uiTmpCost;
3896#if ZERO_MVD_EST
3897    uiTmpCost = xGetTemplateCost( pcCU, uiPartIdx, uiPartAddr, pcOrgYuv, &m_cYuvPredTemp, pcAMVPInfo->m_acMvCand[i], i, AMVP_MAX_NUM_CANDS, eRefPicList, iRefIdx, iRoiWidth, iRoiHeight, uiDist );
3898#else
3899    uiTmpCost = xGetTemplateCost( pcCU, uiPartIdx, uiPartAddr, pcOrgYuv, &m_cYuvPredTemp, pcAMVPInfo->m_acMvCand[i], i, AMVP_MAX_NUM_CANDS, eRefPicList, iRefIdx, iRoiWidth, iRoiHeight);
3900#endif     
3901    if ( uiBestCost > uiTmpCost )
3902    {
3903      uiBestCost = uiTmpCost;
3904      cBestMv   = pcAMVPInfo->m_acMvCand[i];
3905      iBestIdx  = i;
3906      (*puiDistBiP) = uiTmpCost;
3907#if ZERO_MVD_EST
3908      (*puiDist) = uiDist;
3909#endif
3910    }
3911  }
3912
3913  m_cYuvPredTemp.clear();
3914 
3915  // Setting Best MVP
3916  rcMvPred = cBestMv;
3917  pcCU->setMVPIdxSubParts( iBestIdx, eRefPicList, uiPartAddr, uiPartIdx, pcCU->getDepth(uiPartAddr));
3918  pcCU->setMVPNumSubParts( pcAMVPInfo->iN, eRefPicList, uiPartAddr, uiPartIdx, pcCU->getDepth(uiPartAddr));
3919  return;
3920}
3921
3922UInt TEncSearch::xGetMvpIdxBits(Int iIdx, Int iNum)
3923{
3924  assert(iIdx >= 0 && iNum >= 0 && iIdx < iNum);
3925 
3926  if (iNum == 1)
3927  {
3928    return 0;
3929  }
3930 
3931  UInt uiLength = 1;
3932  Int iTemp = iIdx;
3933  if ( iTemp == 0 )
3934  {
3935    return uiLength;
3936  }
3937 
3938  Bool bCodeLast = ( iNum-1 > iTemp );
3939 
3940  uiLength += (iTemp-1);
3941 
3942  if( bCodeLast )
3943  {
3944    uiLength++;
3945  }
3946 
3947  return uiLength;
3948}
3949
3950Void TEncSearch::xGetBlkBits( PartSize eCUMode, Bool bPSlice, Int iPartIdx, UInt uiLastMode, UInt uiBlkBit[3])
3951{
3952  if ( eCUMode == SIZE_2Nx2N )
3953  {
3954    uiBlkBit[0] = (! bPSlice) ? 3 : 1;
3955    uiBlkBit[1] = 3;
3956    uiBlkBit[2] = 5;
3957  }
3958  else if ( (eCUMode == SIZE_2NxN || eCUMode == SIZE_2NxnU) || eCUMode == SIZE_2NxnD )
3959  {
3960    UInt aauiMbBits[2][3][3] = { { {0,0,3}, {0,0,0}, {0,0,0} } , { {5,7,7}, {7,5,7}, {9-3,9-3,9-3} } };
3961    if ( bPSlice )
3962    {
3963      uiBlkBit[0] = 3;
3964      uiBlkBit[1] = 0;
3965      uiBlkBit[2] = 0;
3966    }
3967    else
3968    {
3969      ::memcpy( uiBlkBit, aauiMbBits[iPartIdx][uiLastMode], 3*sizeof(UInt) );
3970    }
3971  }
3972  else if ( (eCUMode == SIZE_Nx2N || eCUMode == SIZE_nLx2N) || eCUMode == SIZE_nRx2N )
3973  {
3974    UInt aauiMbBits[2][3][3] = { { {0,2,3}, {0,0,0}, {0,0,0} } , { {5,7,7}, {7-2,7-2,9-2}, {9-3,9-3,9-3} } };
3975    if ( bPSlice )
3976    {
3977      uiBlkBit[0] = 3;
3978      uiBlkBit[1] = 0;
3979      uiBlkBit[2] = 0;
3980    }
3981    else
3982    {
3983      ::memcpy( uiBlkBit, aauiMbBits[iPartIdx][uiLastMode], 3*sizeof(UInt) );
3984    }
3985  }
3986  else if ( eCUMode == SIZE_NxN )
3987  {
3988    uiBlkBit[0] = (! bPSlice) ? 3 : 1;
3989    uiBlkBit[1] = 3;
3990    uiBlkBit[2] = 5;
3991  }
3992  else
3993  {
3994    printf("Wrong!\n");
3995    assert( 0 );
3996  }
3997}
3998
3999Void TEncSearch::xCopyAMVPInfo (AMVPInfo* pSrc, AMVPInfo* pDst)
4000{
4001  pDst->iN = pSrc->iN;
4002  for (Int i = 0; i < pSrc->iN; i++)
4003  {
4004    pDst->m_acMvCand[i] = pSrc->m_acMvCand[i];
4005  }
4006}
4007
4008Void TEncSearch::xCheckBestMVP ( TComDataCU* pcCU, RefPicList eRefPicList, TComMv cMv, TComMv& rcMvPred, Int& riMVPIdx, UInt& ruiBits, UInt& ruiCost )
4009{
4010  AMVPInfo* pcAMVPInfo = pcCU->getCUMvField(eRefPicList)->getAMVPInfo();
4011 
4012  assert(pcAMVPInfo->m_acMvCand[riMVPIdx] == rcMvPred);
4013 
4014  if (pcAMVPInfo->iN < 2) return;
4015 
4016  m_pcRdCost->getMotionCost( 1, 0 );
4017  m_pcRdCost->setCostScale ( 0    );
4018 
4019  Int iBestMVPIdx = riMVPIdx;
4020 
4021  m_pcRdCost->setPredictor( rcMvPred );
4022  Int iOrgMvBits  = m_pcRdCost->getBits(cMv.getHor(), cMv.getVer());
4023  iOrgMvBits += m_auiMVPIdxCost[riMVPIdx][AMVP_MAX_NUM_CANDS];
4024  Int iBestMvBits = iOrgMvBits;
4025 
4026  for (Int iMVPIdx = 0; iMVPIdx < pcAMVPInfo->iN; iMVPIdx++)
4027  {
4028    if (iMVPIdx == riMVPIdx) continue;
4029   
4030    m_pcRdCost->setPredictor( pcAMVPInfo->m_acMvCand[iMVPIdx] );
4031   
4032    Int iMvBits = m_pcRdCost->getBits(cMv.getHor(), cMv.getVer());
4033    iMvBits += m_auiMVPIdxCost[iMVPIdx][AMVP_MAX_NUM_CANDS];
4034   
4035    if (iMvBits < iBestMvBits)
4036    {
4037      iBestMvBits = iMvBits;
4038      iBestMVPIdx = iMVPIdx;
4039    }
4040  }
4041 
4042  if (iBestMVPIdx != riMVPIdx)  //if changed
4043  {
4044    rcMvPred = pcAMVPInfo->m_acMvCand[iBestMVPIdx];
4045   
4046    riMVPIdx = iBestMVPIdx;
4047    UInt uiOrgBits = ruiBits;
4048    ruiBits = uiOrgBits - iOrgMvBits + iBestMvBits;
4049    ruiCost = (ruiCost - m_pcRdCost->getCost( uiOrgBits ))  + m_pcRdCost->getCost( ruiBits );
4050  }
4051}
4052
4053UInt TEncSearch::xGetTemplateCost( TComDataCU* pcCU,
4054                                  UInt        uiPartIdx,
4055                                  UInt      uiPartAddr,
4056                                  TComYuv*    pcOrgYuv,
4057                                  TComYuv*    pcTemplateCand,
4058                                  TComMv      cMvCand,
4059                                  Int         iMVPIdx,
4060                                  Int     iMVPNum,
4061                                  RefPicList  eRefPicList,
4062                                  Int         iRefIdx,
4063                                  Int         iSizeX,
4064                                  Int         iSizeY
4065                               #if ZERO_MVD_EST
4066                                , UInt&       ruiDist
4067                               #endif
4068                                  )
4069{
4070  UInt uiCost  = MAX_INT;
4071 
4072  TComPicYuv* pcPicYuvRef = pcCU->getSlice()->getRefPic( eRefPicList, iRefIdx )->getPicYuvRec();
4073 
4074  pcCU->clipMv( cMvCand );
4075
4076  // prediction pattern
4077#if O0194_WEIGHTED_PREDICTION_CGS
4078  // Bug Fix (It did not check WP for BSlices)
4079  if ( pcCU->getSlice()->getPPS()->getUseWP())
4080#else
4081  if ( pcCU->getSlice()->getPPS()->getUseWP() && pcCU->getSlice()->getSliceType()==P_SLICE )
4082#endif
4083  {
4084    xPredInterLumaBlk( pcCU, pcPicYuvRef, uiPartAddr, &cMvCand, iSizeX, iSizeY, pcTemplateCand, true );
4085  }
4086  else
4087  {
4088    xPredInterLumaBlk( pcCU, pcPicYuvRef, uiPartAddr, &cMvCand, iSizeX, iSizeY, pcTemplateCand, false );
4089  }
4090
4091#if O0194_WEIGHTED_PREDICTION_CGS
4092  if ( pcCU->getSlice()->getPPS()->getUseWP())
4093  ///< Bug Fix (It did not check WP for BSlices)
4094#else
4095  if ( pcCU->getSlice()->getPPS()->getUseWP() && pcCU->getSlice()->getSliceType()==P_SLICE )
4096#endif
4097  {
4098    xWeightedPredictionUni( pcCU, pcTemplateCand, uiPartAddr, iSizeX, iSizeY, eRefPicList, pcTemplateCand, iRefIdx );
4099  }
4100
4101  // calc distortion
4102#if ZERO_MVD_EST
4103  m_pcRdCost->getMotionCost( 1, 0 );
4104  DistParam cDistParam;
4105  m_pcRdCost->setDistParam( cDistParam, g_bitDepthY,
4106                            pcOrgYuv->getLumaAddr(uiPartAddr), pcOrgYuv->getStride(), 
4107                            pcTemplateCand->getLumaAddr(uiPartAddr), pcTemplateCand->getStride(), 
4108                            iSizeX, iSizeY, m_pcEncCfg->getUseHADME() );
4109  ruiDist = cDistParam.DistFunc( &cDistParam );
4110  uiCost = ruiDist + m_pcRdCost->getCost( m_auiMVPIdxCost[iMVPIdx][iMVPNum] );
4111#else
4112  uiCost = m_pcRdCost->getDistPart(g_bitDepthY, pcTemplateCand->getLumaAddr(uiPartAddr), pcTemplateCand->getStride(), pcOrgYuv->getLumaAddr(uiPartAddr), pcOrgYuv->getStride(), iSizeX, iSizeY, TEXT_LUMA, DF_SAD );
4113  uiCost = (UInt) m_pcRdCost->calcRdCost( m_auiMVPIdxCost[iMVPIdx][iMVPNum], uiCost, false, DF_SAD );
4114#endif
4115  return uiCost;
4116}
4117
4118Void TEncSearch::xMotionEstimation( TComDataCU* pcCU, TComYuv* pcYuvOrg, Int iPartIdx, RefPicList eRefPicList, TComMv* pcMvPred, Int iRefIdxPred, TComMv& rcMv, UInt& ruiBits, UInt& ruiCost, Bool bBi  )
4119{
4120  UInt          uiPartAddr;
4121  Int           iRoiWidth;
4122  Int           iRoiHeight;
4123 
4124  TComMv        cMvHalf, cMvQter;
4125  TComMv        cMvSrchRngLT;
4126  TComMv        cMvSrchRngRB;
4127 
4128  TComYuv*      pcYuv = pcYuvOrg;
4129  m_iSearchRange = m_aaiAdaptSR[eRefPicList][iRefIdxPred];
4130 
4131  Int           iSrchRng      = ( bBi ? m_bipredSearchRange : m_iSearchRange );
4132  TComPattern*  pcPatternKey  = pcCU->getPattern        ();
4133 
4134  Double        fWeight       = 1.0;
4135 
4136  pcCU->getPartIndexAndSize( iPartIdx, uiPartAddr, iRoiWidth, iRoiHeight );
4137 
4138  if ( bBi )
4139  {
4140    TComYuv*  pcYuvOther = &m_acYuvPred[1-(Int)eRefPicList];
4141    pcYuv                = &m_cYuvPredTemp;
4142   
4143    pcYuvOrg->copyPartToPartYuv( pcYuv, uiPartAddr, iRoiWidth, iRoiHeight );
4144   
4145    pcYuv->removeHighFreq( pcYuvOther, uiPartAddr, iRoiWidth, iRoiHeight );
4146   
4147    fWeight = 0.5;
4148  }
4149 
4150  //  Search key pattern initialization
4151  pcPatternKey->initPattern( pcYuv->getLumaAddr( uiPartAddr ),
4152                            pcYuv->getCbAddr  ( uiPartAddr ),
4153                            pcYuv->getCrAddr  ( uiPartAddr ),
4154                            iRoiWidth,
4155                            iRoiHeight,
4156                            pcYuv->getStride(),
4157                            0, 0 );
4158 
4159  Pel*        piRefY      = pcCU->getSlice()->getRefPic( eRefPicList, iRefIdxPred )->getPicYuvRec()->getLumaAddr( pcCU->getAddr(), pcCU->getZorderIdxInCU() + uiPartAddr );
4160  Int         iRefStride  = pcCU->getSlice()->getRefPic( eRefPicList, iRefIdxPred )->getPicYuvRec()->getStride();
4161 
4162  TComMv      cMvPred = *pcMvPred;
4163 
4164  if ( bBi )  xSetSearchRange   ( pcCU, rcMv   , iSrchRng, cMvSrchRngLT, cMvSrchRngRB );
4165  else        xSetSearchRange   ( pcCU, cMvPred, iSrchRng, cMvSrchRngLT, cMvSrchRngRB );
4166 
4167  m_pcRdCost->getMotionCost ( 1, 0 );
4168 
4169  m_pcRdCost->setPredictor  ( *pcMvPred );
4170  m_pcRdCost->setCostScale  ( 2 );
4171
4172  setWpScalingDistParam( pcCU, iRefIdxPred, eRefPicList );
4173  //  Do integer search
4174#if REF_IDX_ME_ZEROMV
4175  if( pcCU->getSlice()->getRefPic( eRefPicList, iRefIdxPred )->isILR(pcCU->getLayerId()))  //ILR reference pic
4176  {
4177    rcMv.setZero();  //use Mv(0, 0) for integer ME
4178  }
4179  else  //non ILR reference pic
4180  {
4181    if ( !m_iFastSearch || bBi ) 
4182    { 
4183      xPatternSearch      ( pcPatternKey, piRefY, iRefStride, &cMvSrchRngLT, &cMvSrchRngRB, rcMv, ruiCost ); 
4184    } 
4185    else 
4186    { 
4187      rcMv = *pcMvPred; 
4188      xPatternSearchFast  ( pcCU, pcPatternKey, piRefY, iRefStride, &cMvSrchRngLT, &cMvSrchRngRB, rcMv, ruiCost ); 
4189    }
4190  }
4191#else
4192  if ( !m_iFastSearch || bBi )
4193  {
4194    xPatternSearch      ( pcPatternKey, piRefY, iRefStride, &cMvSrchRngLT, &cMvSrchRngRB, rcMv, ruiCost );
4195  }
4196  else
4197  {
4198    rcMv = *pcMvPred;
4199    xPatternSearchFast  ( pcCU, pcPatternKey, piRefY, iRefStride, &cMvSrchRngLT, &cMvSrchRngRB, rcMv, ruiCost );
4200  }
4201#endif
4202 
4203  m_pcRdCost->getMotionCost( 1, 0 );
4204  m_pcRdCost->setCostScale ( 1 );
4205
4206#if REF_IDX_ME_ZEROMV
4207  if( pcCU->getSlice()->getRefPic( eRefPicList, iRefIdxPred )->isILR(pcCU->getLayerId()))  //ILR reference pic
4208  {
4209    xPatternSearchFracDIFMv0( pcCU, pcPatternKey, piRefY, iRefStride, &rcMv, cMvHalf, cMvQter, ruiCost, bBi );
4210  }
4211  else    //non ILR reference pic
4212  {
4213    xPatternSearchFracDIF( pcCU, pcPatternKey, piRefY, iRefStride, &rcMv, cMvHalf, cMvQter, ruiCost, bBi );
4214  }
4215#else
4216  xPatternSearchFracDIF( pcCU, pcPatternKey, piRefY, iRefStride, &rcMv, cMvHalf, cMvQter, ruiCost,bBi );
4217#endif
4218
4219  m_pcRdCost->setCostScale( 0 );
4220  rcMv <<= 2;
4221  rcMv += (cMvHalf <<= 1);
4222  rcMv +=  cMvQter;
4223 
4224  UInt uiMvBits = m_pcRdCost->getBits( rcMv.getHor(), rcMv.getVer() );
4225 
4226  ruiBits      += uiMvBits;
4227  ruiCost       = (UInt)( floor( fWeight * ( (Double)ruiCost - (Double)m_pcRdCost->getCost( uiMvBits ) ) ) + (Double)m_pcRdCost->getCost( ruiBits ) );
4228}
4229
4230
4231Void TEncSearch::xSetSearchRange ( TComDataCU* pcCU, TComMv& cMvPred, Int iSrchRng, TComMv& rcMvSrchRngLT, TComMv& rcMvSrchRngRB )
4232{
4233  Int  iMvShift = 2;
4234  TComMv cTmpMvPred = cMvPred;
4235  pcCU->clipMv( cTmpMvPred );
4236
4237  rcMvSrchRngLT.setHor( cTmpMvPred.getHor() - (iSrchRng << iMvShift) );
4238  rcMvSrchRngLT.setVer( cTmpMvPred.getVer() - (iSrchRng << iMvShift) );
4239 
4240  rcMvSrchRngRB.setHor( cTmpMvPred.getHor() + (iSrchRng << iMvShift) );
4241  rcMvSrchRngRB.setVer( cTmpMvPred.getVer() + (iSrchRng << iMvShift) );
4242  pcCU->clipMv        ( rcMvSrchRngLT );
4243  pcCU->clipMv        ( rcMvSrchRngRB );
4244 
4245  rcMvSrchRngLT >>= iMvShift;
4246  rcMvSrchRngRB >>= iMvShift;
4247}
4248
4249Void TEncSearch::xPatternSearch( TComPattern* pcPatternKey, Pel* piRefY, Int iRefStride, TComMv* pcMvSrchRngLT, TComMv* pcMvSrchRngRB, TComMv& rcMv, UInt& ruiSAD )
4250{
4251  Int   iSrchRngHorLeft   = pcMvSrchRngLT->getHor();
4252  Int   iSrchRngHorRight  = pcMvSrchRngRB->getHor();
4253  Int   iSrchRngVerTop    = pcMvSrchRngLT->getVer();
4254  Int   iSrchRngVerBottom = pcMvSrchRngRB->getVer();
4255 
4256  UInt  uiSad;
4257  UInt  uiSadBest         = MAX_UINT;
4258  Int   iBestX = 0;
4259  Int   iBestY = 0;
4260 
4261  Pel*  piRefSrch;
4262 
4263  //-- jclee for using the SAD function pointer
4264  m_pcRdCost->setDistParam( pcPatternKey, piRefY, iRefStride,  m_cDistParam );
4265 
4266  // fast encoder decision: use subsampled SAD for integer ME
4267  if ( m_pcEncCfg->getUseFastEnc() )
4268  {
4269    if ( m_cDistParam.iRows > 8 )
4270    {
4271      m_cDistParam.iSubShift = 1;
4272    }
4273  }
4274 
4275  piRefY += (iSrchRngVerTop * iRefStride);
4276  for ( Int y = iSrchRngVerTop; y <= iSrchRngVerBottom; y++ )
4277  {
4278    for ( Int x = iSrchRngHorLeft; x <= iSrchRngHorRight; x++ )
4279    {
4280      //  find min. distortion position
4281      piRefSrch = piRefY + x;
4282      m_cDistParam.pCur = piRefSrch;
4283
4284      setDistParamComp(0);
4285
4286      m_cDistParam.bitDepth = g_bitDepthY;
4287      uiSad = m_cDistParam.DistFunc( &m_cDistParam );
4288     
4289      // motion cost
4290      uiSad += m_pcRdCost->getCost( x, y );
4291     
4292      if ( uiSad < uiSadBest )
4293      {
4294        uiSadBest = uiSad;
4295        iBestX    = x;
4296        iBestY    = y;
4297      }
4298    }
4299    piRefY += iRefStride;
4300  }
4301 
4302  rcMv.set( iBestX, iBestY );
4303 
4304  ruiSAD = uiSadBest - m_pcRdCost->getCost( iBestX, iBestY );
4305  return;
4306}
4307
4308Void TEncSearch::xPatternSearchFast( TComDataCU* pcCU, TComPattern* pcPatternKey, Pel* piRefY, Int iRefStride, TComMv* pcMvSrchRngLT, TComMv* pcMvSrchRngRB, TComMv& rcMv, UInt& ruiSAD )
4309{
4310  pcCU->getMvPredLeft       ( m_acMvPredictors[0] );
4311  pcCU->getMvPredAbove      ( m_acMvPredictors[1] );
4312  pcCU->getMvPredAboveRight ( m_acMvPredictors[2] );
4313 
4314  switch ( m_iFastSearch )
4315  {
4316    case 1:
4317      xTZSearch( pcCU, pcPatternKey, piRefY, iRefStride, pcMvSrchRngLT, pcMvSrchRngRB, rcMv, ruiSAD );
4318      break;
4319     
4320    default:
4321      break;
4322  }
4323}
4324
4325Void TEncSearch::xTZSearch( TComDataCU* pcCU, TComPattern* pcPatternKey, Pel* piRefY, Int iRefStride, TComMv* pcMvSrchRngLT, TComMv* pcMvSrchRngRB, TComMv& rcMv, UInt& ruiSAD )
4326{
4327  Int   iSrchRngHorLeft   = pcMvSrchRngLT->getHor();
4328  Int   iSrchRngHorRight  = pcMvSrchRngRB->getHor();
4329  Int   iSrchRngVerTop    = pcMvSrchRngLT->getVer();
4330  Int   iSrchRngVerBottom = pcMvSrchRngRB->getVer();
4331 
4332  TZ_SEARCH_CONFIGURATION
4333 
4334  UInt uiSearchRange = m_iSearchRange;
4335  pcCU->clipMv( rcMv );
4336  rcMv >>= 2;
4337  // init TZSearchStruct
4338  IntTZSearchStruct cStruct;
4339  cStruct.iYStride    = iRefStride;
4340  cStruct.piRefY      = piRefY;
4341  cStruct.uiBestSad   = MAX_UINT;
4342 
4343  // set rcMv (Median predictor) as start point and as best point
4344  xTZSearchHelp( pcPatternKey, cStruct, rcMv.getHor(), rcMv.getVer(), 0, 0 );
4345 
4346  // test whether one of PRED_A, PRED_B, PRED_C MV is better start point than Median predictor
4347  if ( bTestOtherPredictedMV )
4348  {
4349    for ( UInt index = 0; index < 3; index++ )
4350    {
4351      TComMv cMv = m_acMvPredictors[index];
4352      pcCU->clipMv( cMv );
4353      cMv >>= 2;
4354      xTZSearchHelp( pcPatternKey, cStruct, cMv.getHor(), cMv.getVer(), 0, 0 );
4355    }
4356  }
4357 
4358  // test whether zero Mv is better start point than Median predictor
4359  if ( bTestZeroVector )
4360  {
4361    xTZSearchHelp( pcPatternKey, cStruct, 0, 0, 0, 0 );
4362  }
4363 
4364  // start search
4365  Int  iDist = 0;
4366  Int  iStartX = cStruct.iBestX;
4367  Int  iStartY = cStruct.iBestY;
4368 
4369  // first search
4370  for ( iDist = 1; iDist <= (Int)uiSearchRange; iDist*=2 )
4371  {
4372    if ( bFirstSearchDiamond == 1 )
4373    {
4374      xTZ8PointDiamondSearch ( pcPatternKey, cStruct, pcMvSrchRngLT, pcMvSrchRngRB, iStartX, iStartY, iDist );
4375    }
4376    else
4377    {
4378      xTZ8PointSquareSearch  ( pcPatternKey, cStruct, pcMvSrchRngLT, pcMvSrchRngRB, iStartX, iStartY, iDist );
4379    }
4380   
4381    if ( bFirstSearchStop && ( cStruct.uiBestRound >= uiFirstSearchRounds ) ) // stop criterion
4382    {
4383      break;
4384    }
4385  }
4386 
4387  // test whether zero Mv is a better start point than Median predictor
4388  if ( bTestZeroVectorStart && ((cStruct.iBestX != 0) || (cStruct.iBestY != 0)) )
4389  {
4390    xTZSearchHelp( pcPatternKey, cStruct, 0, 0, 0, 0 );
4391    if ( (cStruct.iBestX == 0) && (cStruct.iBestY == 0) )
4392    {
4393      // test its neighborhood
4394      for ( iDist = 1; iDist <= (Int)uiSearchRange; iDist*=2 )
4395      {
4396        xTZ8PointDiamondSearch( pcPatternKey, cStruct, pcMvSrchRngLT, pcMvSrchRngRB, 0, 0, iDist );
4397        if ( bTestZeroVectorStop && (cStruct.uiBestRound > 0) ) // stop criterion
4398        {
4399          break;
4400        }
4401      }
4402    }
4403  }
4404 
4405  // calculate only 2 missing points instead 8 points if cStruct.uiBestDistance == 1
4406  if ( cStruct.uiBestDistance == 1 )
4407  {
4408    cStruct.uiBestDistance = 0;
4409    xTZ2PointSearch( pcPatternKey, cStruct, pcMvSrchRngLT, pcMvSrchRngRB );
4410  }
4411 
4412  // raster search if distance is too big
4413  if ( bEnableRasterSearch && ( ((Int)(cStruct.uiBestDistance) > iRaster) || bAlwaysRasterSearch ) )
4414  {
4415    cStruct.uiBestDistance = iRaster;
4416    for ( iStartY = iSrchRngVerTop; iStartY <= iSrchRngVerBottom; iStartY += iRaster )
4417    {
4418      for ( iStartX = iSrchRngHorLeft; iStartX <= iSrchRngHorRight; iStartX += iRaster )
4419      {
4420        xTZSearchHelp( pcPatternKey, cStruct, iStartX, iStartY, 0, iRaster );
4421      }
4422    }
4423  }
4424 
4425  // raster refinement
4426  if ( bRasterRefinementEnable && cStruct.uiBestDistance > 0 )
4427  {
4428    while ( cStruct.uiBestDistance > 0 )
4429    {
4430      iStartX = cStruct.iBestX;
4431      iStartY = cStruct.iBestY;
4432      if ( cStruct.uiBestDistance > 1 )
4433      {
4434        iDist = cStruct.uiBestDistance >>= 1;
4435        if ( bRasterRefinementDiamond == 1 )
4436        {
4437          xTZ8PointDiamondSearch ( pcPatternKey, cStruct, pcMvSrchRngLT, pcMvSrchRngRB, iStartX, iStartY, iDist );
4438        }
4439        else
4440        {
4441          xTZ8PointSquareSearch  ( pcPatternKey, cStruct, pcMvSrchRngLT, pcMvSrchRngRB, iStartX, iStartY, iDist );
4442        }
4443      }
4444     
4445      // calculate only 2 missing points instead 8 points if cStruct.uiBestDistance == 1
4446      if ( cStruct.uiBestDistance == 1 )
4447      {
4448        cStruct.uiBestDistance = 0;
4449        if ( cStruct.ucPointNr != 0 )
4450        {
4451          xTZ2PointSearch( pcPatternKey, cStruct, pcMvSrchRngLT, pcMvSrchRngRB );
4452        }
4453      }
4454    }
4455  }
4456 
4457  // start refinement
4458  if ( bStarRefinementEnable && cStruct.uiBestDistance > 0 )
4459  {
4460    while ( cStruct.uiBestDistance > 0 )
4461    {
4462      iStartX = cStruct.iBestX;
4463      iStartY = cStruct.iBestY;
4464      cStruct.uiBestDistance = 0;
4465      cStruct.ucPointNr = 0;
4466      for ( iDist = 1; iDist < (Int)uiSearchRange + 1; iDist*=2 )
4467      {
4468        if ( bStarRefinementDiamond == 1 )
4469        {
4470          xTZ8PointDiamondSearch ( pcPatternKey, cStruct, pcMvSrchRngLT, pcMvSrchRngRB, iStartX, iStartY, iDist );
4471        }
4472        else
4473        {
4474          xTZ8PointSquareSearch  ( pcPatternKey, cStruct, pcMvSrchRngLT, pcMvSrchRngRB, iStartX, iStartY, iDist );
4475        }
4476        if ( bStarRefinementStop && (cStruct.uiBestRound >= uiStarRefinementRounds) ) // stop criterion
4477        {
4478          break;
4479        }
4480      }
4481     
4482      // calculate only 2 missing points instead 8 points if cStrukt.uiBestDistance == 1
4483      if ( cStruct.uiBestDistance == 1 )
4484      {
4485        cStruct.uiBestDistance = 0;
4486        if ( cStruct.ucPointNr != 0 )
4487        {
4488          xTZ2PointSearch( pcPatternKey, cStruct, pcMvSrchRngLT, pcMvSrchRngRB );
4489        }
4490      }
4491    }
4492  }
4493 
4494  // write out best match
4495  rcMv.set( cStruct.iBestX, cStruct.iBestY );
4496  ruiSAD = cStruct.uiBestSad - m_pcRdCost->getCost( cStruct.iBestX, cStruct.iBestY );
4497}
4498
4499Void TEncSearch::xPatternSearchFracDIF(TComDataCU* pcCU,
4500                                       TComPattern* pcPatternKey,
4501                                       Pel* piRefY,
4502                                       Int iRefStride,
4503                                       TComMv* pcMvInt,
4504                                       TComMv& rcMvHalf,
4505                                       TComMv& rcMvQter,
4506                                       UInt& ruiCost
4507                                       ,Bool biPred
4508                                       )
4509{
4510  //  Reference pattern initialization (integer scale)
4511  TComPattern cPatternRoi;
4512  Int         iOffset    = pcMvInt->getHor() + pcMvInt->getVer() * iRefStride;
4513  cPatternRoi.initPattern( piRefY +  iOffset,
4514                          NULL,
4515                          NULL,
4516                          pcPatternKey->getROIYWidth(),
4517                          pcPatternKey->getROIYHeight(),
4518                          iRefStride,
4519                          0, 0 );
4520 
4521  //  Half-pel refinement
4522  xExtDIFUpSamplingH ( &cPatternRoi, biPred );
4523 
4524  rcMvHalf = *pcMvInt;   rcMvHalf <<= 1;    // for mv-cost
4525  TComMv baseRefMv(0, 0);
4526  ruiCost = xPatternRefinement( pcPatternKey, baseRefMv, 2, rcMvHalf   );
4527 
4528  m_pcRdCost->setCostScale( 0 );
4529 
4530  xExtDIFUpSamplingQ ( &cPatternRoi, rcMvHalf, biPred );
4531  baseRefMv = rcMvHalf;
4532  baseRefMv <<= 1;
4533 
4534  rcMvQter = *pcMvInt;   rcMvQter <<= 1;    // for mv-cost
4535  rcMvQter += rcMvHalf;  rcMvQter <<= 1;
4536  ruiCost = xPatternRefinement( pcPatternKey, baseRefMv, 1, rcMvQter );
4537}
4538
4539/** encode residual and calculate rate-distortion for a CU block
4540 * \param pcCU
4541 * \param pcYuvOrg
4542 * \param pcYuvPred
4543 * \param rpcYuvResi
4544 * \param rpcYuvResiBest
4545 * \param rpcYuvRec
4546 * \param bSkipRes
4547 * \returns Void
4548 */
4549Void TEncSearch::encodeResAndCalcRdInterCU( TComDataCU* pcCU, TComYuv* pcYuvOrg, TComYuv* pcYuvPred, TComYuv*& rpcYuvResi, TComYuv*& rpcYuvResiBest, TComYuv*& rpcYuvRec, Bool bSkipRes )
4550{
4551  if ( pcCU->isIntra(0) )
4552  {
4553    return;
4554  }
4555 
4556  Bool      bHighPass    = pcCU->getSlice()->getDepth() ? true : false;
4557  UInt      uiBits       = 0, uiBitsBest = 0;
4558  UInt      uiDistortion = 0, uiDistortionBest = 0;
4559 
4560  UInt      uiWidth      = pcCU->getWidth ( 0 );
4561  UInt      uiHeight     = pcCU->getHeight( 0 );
4562 
4563  //  No residual coding : SKIP mode
4564  if ( bSkipRes )
4565  {
4566    pcCU->setSkipFlagSubParts( true, 0, pcCU->getDepth(0) );
4567
4568    rpcYuvResi->clear();
4569   
4570    pcYuvPred->copyToPartYuv( rpcYuvRec, 0 );
4571   
4572    uiDistortion = m_pcRdCost->getDistPart(g_bitDepthY, rpcYuvRec->getLumaAddr(), rpcYuvRec->getStride(),  pcYuvOrg->getLumaAddr(), pcYuvOrg->getStride(),  uiWidth,      uiHeight      )
4573    + m_pcRdCost->getDistPart(g_bitDepthC, rpcYuvRec->getCbAddr(),   rpcYuvRec->getCStride(), pcYuvOrg->getCbAddr(),   pcYuvOrg->getCStride(), uiWidth >> 1, uiHeight >> 1, TEXT_CHROMA_U )
4574    + m_pcRdCost->getDistPart(g_bitDepthC, rpcYuvRec->getCrAddr(),   rpcYuvRec->getCStride(), pcYuvOrg->getCrAddr(),   pcYuvOrg->getCStride(), uiWidth >> 1, uiHeight >> 1, TEXT_CHROMA_V );
4575
4576    if( m_bUseSBACRD )
4577    {
4578      m_pcRDGoOnSbacCoder->load(m_pppcRDSbacCoder[pcCU->getDepth(0)][CI_CURR_BEST]);
4579    }
4580   
4581    m_pcEntropyCoder->resetBits();
4582    if (pcCU->getSlice()->getPPS()->getTransquantBypassEnableFlag())
4583    {
4584      m_pcEntropyCoder->encodeCUTransquantBypassFlag(pcCU, 0, true);
4585    }
4586    m_pcEntropyCoder->encodeSkipFlag(pcCU, 0, true);
4587    m_pcEntropyCoder->encodeMergeIndex( pcCU, 0, true );
4588   
4589    uiBits = m_pcEntropyCoder->getNumberOfWrittenBits();
4590    pcCU->getTotalBits()       = uiBits;
4591    pcCU->getTotalDistortion() = uiDistortion;
4592    pcCU->getTotalCost()       = m_pcRdCost->calcRdCost( uiBits, uiDistortion );
4593   
4594    if( m_bUseSBACRD )
4595    {
4596      m_pcRDGoOnSbacCoder->store(m_pppcRDSbacCoder[pcCU->getDepth(0)][CI_TEMP_BEST]);
4597    }
4598   
4599    pcCU->setCbfSubParts( 0, 0, 0, 0, pcCU->getDepth( 0 ) );
4600    pcCU->setTrIdxSubParts( 0, 0, pcCU->getDepth(0) );
4601   
4602    return;
4603  }
4604 
4605  //  Residual coding.
4606  Int    qp, qpBest = 0, qpMin, qpMax;
4607  Double  dCost, dCostBest = MAX_DOUBLE;
4608 
4609  UInt uiTrLevel = 0;
4610  if( (pcCU->getWidth(0) > pcCU->getSlice()->getSPS()->getMaxTrSize()) )
4611  {
4612    while( pcCU->getWidth(0) > (pcCU->getSlice()->getSPS()->getMaxTrSize()<<uiTrLevel) ) uiTrLevel++;
4613  }
4614  UInt uiMaxTrMode = 1 + uiTrLevel;
4615 
4616  while((uiWidth>>uiMaxTrMode) < (g_uiMaxCUWidth>>g_uiMaxCUDepth)) uiMaxTrMode--;
4617 
4618#if REPN_FORMAT_IN_VPS
4619  qpMin =  bHighPass ? Clip3( -pcCU->getSlice()->getQpBDOffsetY(), MAX_QP, pcCU->getQP(0) - m_iMaxDeltaQP ) : pcCU->getQP( 0 );
4620  qpMax =  bHighPass ? Clip3( -pcCU->getSlice()->getQpBDOffsetY(), MAX_QP, pcCU->getQP(0) + m_iMaxDeltaQP ) : pcCU->getQP( 0 );
4621#else
4622  qpMin =  bHighPass ? Clip3( -pcCU->getSlice()->getSPS()->getQpBDOffsetY(), MAX_QP, pcCU->getQP(0) - m_iMaxDeltaQP ) : pcCU->getQP( 0 );
4623  qpMax =  bHighPass ? Clip3( -pcCU->getSlice()->getSPS()->getQpBDOffsetY(), MAX_QP, pcCU->getQP(0) + m_iMaxDeltaQP ) : pcCU->getQP( 0 );
4624#endif
4625
4626  rpcYuvResi->subtract( pcYuvOrg, pcYuvPred, 0, uiWidth );
4627
4628  for ( qp = qpMin; qp <= qpMax; qp++ )
4629  {
4630    dCost = 0.;
4631    uiBits = 0;
4632    uiDistortion = 0;
4633    if( m_bUseSBACRD )
4634    {
4635      m_pcRDGoOnSbacCoder->load( m_pppcRDSbacCoder[ pcCU->getDepth( 0 ) ][ CI_CURR_BEST ] );
4636    }
4637   
4638    UInt uiZeroDistortion = 0;
4639    xEstimateResidualQT( pcCU, 0, 0, 0, rpcYuvResi,  pcCU->getDepth(0), dCost, uiBits, uiDistortion, &uiZeroDistortion );
4640   
4641    m_pcEntropyCoder->resetBits();
4642    m_pcEntropyCoder->encodeQtRootCbfZero( pcCU );
4643    UInt zeroResiBits = m_pcEntropyCoder->getNumberOfWrittenBits();
4644    Double dZeroCost = m_pcRdCost->calcRdCost( zeroResiBits, uiZeroDistortion );
4645    if(pcCU->isLosslessCoded( 0 ))
4646    { 
4647      dZeroCost = dCost + 1;
4648    }
4649    if ( dZeroCost < dCost )
4650    {
4651      dCost        = dZeroCost;
4652      uiBits       = 0;
4653      uiDistortion = uiZeroDistortion;
4654     
4655      const UInt uiQPartNum = pcCU->getPic()->getNumPartInCU() >> (pcCU->getDepth(0) << 1);
4656      ::memset( pcCU->getTransformIdx()      , 0, uiQPartNum * sizeof(UChar) );
4657      ::memset( pcCU->getCbf( TEXT_LUMA )    , 0, uiQPartNum * sizeof(UChar) );
4658      ::memset( pcCU->getCbf( TEXT_CHROMA_U ), 0, uiQPartNum * sizeof(UChar) );
4659      ::memset( pcCU->getCbf( TEXT_CHROMA_V ), 0, uiQPartNum * sizeof(UChar) );
4660      ::memset( pcCU->getCoeffY()            , 0, uiWidth * uiHeight * sizeof( TCoeff )      );
4661      ::memset( pcCU->getCoeffCb()           , 0, uiWidth * uiHeight * sizeof( TCoeff ) >> 2 );
4662      ::memset( pcCU->getCoeffCr()           , 0, uiWidth * uiHeight * sizeof( TCoeff ) >> 2 );
4663      pcCU->setTransformSkipSubParts ( 0, 0, 0, 0, pcCU->getDepth(0) );
4664    }
4665    else
4666    {
4667      xSetResidualQTData( pcCU, 0, 0, 0, NULL, pcCU->getDepth(0), false );
4668    }
4669   
4670    if( m_bUseSBACRD )
4671    {
4672      m_pcRDGoOnSbacCoder->load( m_pppcRDSbacCoder[pcCU->getDepth(0)][CI_CURR_BEST] );
4673    }
4674#if 0 // check
4675    {
4676      m_pcEntropyCoder->resetBits();
4677      m_pcEntropyCoder->encodeCoeff( pcCU, 0, pcCU->getDepth(0), pcCU->getWidth(0), pcCU->getHeight(0) );
4678      const UInt uiBitsForCoeff = m_pcEntropyCoder->getNumberOfWrittenBits();
4679      if( m_bUseSBACRD )
4680      {
4681        m_pcRDGoOnSbacCoder->load( m_pppcRDSbacCoder[pcCU->getDepth(0)][CI_CURR_BEST] );
4682      }
4683      if( uiBitsForCoeff != uiBits )
4684        assert( 0 );
4685    }
4686#endif
4687    uiBits = 0;
4688    {
4689      TComYuv *pDummy = NULL;
4690      xAddSymbolBitsInter( pcCU, 0, 0, uiBits, pDummy, NULL, pDummy );
4691    }
4692   
4693   
4694    Double dExactCost = m_pcRdCost->calcRdCost( uiBits, uiDistortion );
4695    dCost = dExactCost;
4696   
4697    if ( dCost < dCostBest )
4698    {
4699      if ( !pcCU->getQtRootCbf( 0 ) )
4700      {
4701        rpcYuvResiBest->clear();
4702      }
4703      else
4704      {
4705        xSetResidualQTData( pcCU, 0, 0, 0, rpcYuvResiBest, pcCU->getDepth(0), true );
4706      }
4707     
4708      if( qpMin != qpMax && qp != qpMax )
4709      {
4710        const UInt uiQPartNum = pcCU->getPic()->getNumPartInCU() >> (pcCU->getDepth(0) << 1);
4711        ::memcpy( m_puhQTTempTrIdx, pcCU->getTransformIdx(),        uiQPartNum * sizeof(UChar) );
4712        ::memcpy( m_puhQTTempCbf[0], pcCU->getCbf( TEXT_LUMA ),     uiQPartNum * sizeof(UChar) );
4713        ::memcpy( m_puhQTTempCbf[1], pcCU->getCbf( TEXT_CHROMA_U ), uiQPartNum * sizeof(UChar) );
4714        ::memcpy( m_puhQTTempCbf[2], pcCU->getCbf( TEXT_CHROMA_V ), uiQPartNum * sizeof(UChar) );
4715        ::memcpy( m_pcQTTempCoeffY,  pcCU->getCoeffY(),  uiWidth * uiHeight * sizeof( TCoeff )      );
4716        ::memcpy( m_pcQTTempCoeffCb, pcCU->getCoeffCb(), uiWidth * uiHeight * sizeof( TCoeff ) >> 2 );
4717        ::memcpy( m_pcQTTempCoeffCr, pcCU->getCoeffCr(), uiWidth * uiHeight * sizeof( TCoeff ) >> 2 );
4718#if ADAPTIVE_QP_SELECTION
4719        ::memcpy( m_pcQTTempArlCoeffY,  pcCU->getArlCoeffY(),  uiWidth * uiHeight * sizeof( Int )      );
4720        ::memcpy( m_pcQTTempArlCoeffCb, pcCU->getArlCoeffCb(), uiWidth * uiHeight * sizeof( Int ) >> 2 );
4721        ::memcpy( m_pcQTTempArlCoeffCr, pcCU->getArlCoeffCr(), uiWidth * uiHeight * sizeof( Int ) >> 2 );
4722#endif
4723        ::memcpy( m_puhQTTempTransformSkipFlag[0], pcCU->getTransformSkip(TEXT_LUMA),     uiQPartNum * sizeof( UChar ) );
4724        ::memcpy( m_puhQTTempTransformSkipFlag[1], pcCU->getTransformSkip(TEXT_CHROMA_U), uiQPartNum * sizeof( UChar ) );
4725        ::memcpy( m_puhQTTempTransformSkipFlag[2], pcCU->getTransformSkip(TEXT_CHROMA_V), uiQPartNum * sizeof( UChar ) );
4726      }
4727      uiBitsBest       = uiBits;
4728      uiDistortionBest = uiDistortion;
4729      dCostBest        = dCost;
4730      qpBest           = qp;
4731      if( m_bUseSBACRD )
4732      {
4733        m_pcRDGoOnSbacCoder->store( m_pppcRDSbacCoder[ pcCU->getDepth( 0 ) ][ CI_TEMP_BEST ] );
4734      }
4735    }
4736  }
4737 
4738  assert ( dCostBest != MAX_DOUBLE );
4739 
4740  if( qpMin != qpMax && qpBest != qpMax )
4741  {
4742    if( m_bUseSBACRD )
4743    {
4744      assert( 0 ); // check
4745      m_pcRDGoOnSbacCoder->load( m_pppcRDSbacCoder[ pcCU->getDepth( 0 ) ][ CI_TEMP_BEST ] );
4746    }
4747    // copy best cbf and trIdx to pcCU
4748    const UInt uiQPartNum = pcCU->getPic()->getNumPartInCU() >> (pcCU->getDepth(0) << 1);
4749    ::memcpy( pcCU->getTransformIdx(),       m_puhQTTempTrIdx,  uiQPartNum * sizeof(UChar) );
4750    ::memcpy( pcCU->getCbf( TEXT_LUMA ),     m_puhQTTempCbf[0], uiQPartNum * sizeof(UChar) );
4751    ::memcpy( pcCU->getCbf( TEXT_CHROMA_U ), m_puhQTTempCbf[1], uiQPartNum * sizeof(UChar) );
4752    ::memcpy( pcCU->getCbf( TEXT_CHROMA_V ), m_puhQTTempCbf[2], uiQPartNum * sizeof(UChar) );
4753    ::memcpy( pcCU->getCoeffY(),  m_pcQTTempCoeffY,  uiWidth * uiHeight * sizeof( TCoeff )      );
4754    ::memcpy( pcCU->getCoeffCb(), m_pcQTTempCoeffCb, uiWidth * uiHeight * sizeof( TCoeff ) >> 2 );
4755    ::memcpy( pcCU->getCoeffCr(), m_pcQTTempCoeffCr, uiWidth * uiHeight * sizeof( TCoeff ) >> 2 );
4756#if ADAPTIVE_QP_SELECTION
4757    ::memcpy( pcCU->getArlCoeffY(),  m_pcQTTempArlCoeffY,  uiWidth * uiHeight * sizeof( Int )      );
4758    ::memcpy( pcCU->getArlCoeffCb(), m_pcQTTempArlCoeffCb, uiWidth * uiHeight * sizeof( Int ) >> 2 );
4759    ::memcpy( pcCU->getArlCoeffCr(), m_pcQTTempArlCoeffCr, uiWidth * uiHeight * sizeof( Int ) >> 2 );
4760#endif
4761    ::memcpy( pcCU->getTransformSkip(TEXT_LUMA),     m_puhQTTempTransformSkipFlag[0], uiQPartNum * sizeof( UChar ) );
4762    ::memcpy( pcCU->getTransformSkip(TEXT_CHROMA_U), m_puhQTTempTransformSkipFlag[1], uiQPartNum * sizeof( UChar ) );
4763    ::memcpy( pcCU->getTransformSkip(TEXT_CHROMA_V), m_puhQTTempTransformSkipFlag[2], uiQPartNum * sizeof( UChar ) );
4764  }
4765  rpcYuvRec->addClip ( pcYuvPred, rpcYuvResiBest, 0, uiWidth );
4766 
4767  // update with clipped distortion and cost (qp estimation loop uses unclipped values)
4768    uiDistortionBest = m_pcRdCost->getDistPart(g_bitDepthY, rpcYuvRec->getLumaAddr(), rpcYuvRec->getStride(),  pcYuvOrg->getLumaAddr(), pcYuvOrg->getStride(),  uiWidth,      uiHeight      )
4769    + m_pcRdCost->getDistPart(g_bitDepthC, rpcYuvRec->getCbAddr(),   rpcYuvRec->getCStride(), pcYuvOrg->getCbAddr(),   pcYuvOrg->getCStride(), uiWidth >> 1, uiHeight >> 1, TEXT_CHROMA_U )
4770    + m_pcRdCost->getDistPart(g_bitDepthC, rpcYuvRec->getCrAddr(),   rpcYuvRec->getCStride(), pcYuvOrg->getCrAddr(),   pcYuvOrg->getCStride(), uiWidth >> 1, uiHeight >> 1, TEXT_CHROMA_V );
4771  dCostBest = m_pcRdCost->calcRdCost( uiBitsBest, uiDistortionBest );
4772 
4773  pcCU->getTotalBits()       = uiBitsBest;
4774  pcCU->getTotalDistortion() = uiDistortionBest;
4775  pcCU->getTotalCost()       = dCostBest;
4776 
4777  if ( pcCU->isSkipped(0) )
4778  {
4779    pcCU->setCbfSubParts( 0, 0, 0, 0, pcCU->getDepth( 0 ) );
4780  }
4781 
4782  pcCU->setQPSubParts( qpBest, 0, pcCU->getDepth(0) );
4783}
4784
4785Void TEncSearch::xEstimateResidualQT( TComDataCU* pcCU, UInt uiQuadrant, UInt uiAbsPartIdx, UInt absTUPartIdx, TComYuv* pcResi, const UInt uiDepth, Double &rdCost, UInt &ruiBits, UInt &ruiDist, UInt *puiZeroDist )
4786{
4787  const UInt uiTrMode = uiDepth - pcCU->getDepth( 0 );
4788 
4789  assert( pcCU->getDepth( 0 ) == pcCU->getDepth( uiAbsPartIdx ) );
4790  const UInt uiLog2TrSize = g_aucConvertToBit[pcCU->getSlice()->getSPS()->getMaxCUWidth() >> uiDepth]+2;
4791 
4792  UInt SplitFlag = ((pcCU->getSlice()->getSPS()->getQuadtreeTUMaxDepthInter() == 1) && pcCU->getPredictionMode(uiAbsPartIdx) == MODE_INTER && ( pcCU->getPartitionSize(uiAbsPartIdx) != SIZE_2Nx2N ));
4793  Bool bCheckFull;
4794  if ( SplitFlag && uiDepth == pcCU->getDepth(uiAbsPartIdx) && ( uiLog2TrSize >  pcCU->getQuadtreeTULog2MinSizeInCU(uiAbsPartIdx) ) )
4795  {
4796     bCheckFull = false;
4797  }
4798  else
4799  {
4800     bCheckFull =  ( uiLog2TrSize <= pcCU->getSlice()->getSPS()->getQuadtreeTULog2MaxSize() );
4801  }
4802
4803  const Bool bCheckSplit  = ( uiLog2TrSize >  pcCU->getQuadtreeTULog2MinSizeInCU(uiAbsPartIdx) );
4804 
4805  assert( bCheckFull || bCheckSplit );
4806 
4807  Bool  bCodeChroma   = true;
4808  UInt  uiTrModeC     = uiTrMode;
4809  UInt  uiLog2TrSizeC = uiLog2TrSize-1;
4810  if( uiLog2TrSize == 2 )
4811  {
4812    uiLog2TrSizeC++;
4813    uiTrModeC    --;
4814    UInt  uiQPDiv = pcCU->getPic()->getNumPartInCU() >> ( ( pcCU->getDepth( 0 ) + uiTrModeC ) << 1 );
4815    bCodeChroma   = ( ( uiAbsPartIdx % uiQPDiv ) == 0 );
4816  }
4817 
4818  const UInt uiSetCbf = 1 << uiTrMode;
4819  // code full block
4820  Double dSingleCost = MAX_DOUBLE;
4821  UInt uiSingleBits = 0;
4822  UInt uiSingleDist = 0;
4823  UInt uiAbsSumY = 0, uiAbsSumU = 0, uiAbsSumV = 0;
4824  UInt uiBestTransformMode[3] = {0};
4825
4826  if( m_bUseSBACRD )
4827  {
4828    m_pcRDGoOnSbacCoder->store( m_pppcRDSbacCoder[ uiDepth ][ CI_QT_TRAFO_ROOT ] );
4829  }
4830 
4831  if( bCheckFull )
4832  {
4833    const UInt uiNumCoeffPerAbsPartIdxIncrement = pcCU->getSlice()->getSPS()->getMaxCUWidth() * pcCU->getSlice()->getSPS()->getMaxCUHeight() >> ( pcCU->getSlice()->getSPS()->getMaxCUDepth() << 1 );
4834    const UInt uiQTTempAccessLayer = pcCU->getSlice()->getSPS()->getQuadtreeTULog2MaxSize() - uiLog2TrSize;
4835    TCoeff *pcCoeffCurrY = m_ppcQTTempCoeffY [uiQTTempAccessLayer] +  uiNumCoeffPerAbsPartIdxIncrement * uiAbsPartIdx;
4836    TCoeff *pcCoeffCurrU = m_ppcQTTempCoeffCb[uiQTTempAccessLayer] + (uiNumCoeffPerAbsPartIdxIncrement * uiAbsPartIdx>>2);
4837    TCoeff *pcCoeffCurrV = m_ppcQTTempCoeffCr[uiQTTempAccessLayer] + (uiNumCoeffPerAbsPartIdxIncrement * uiAbsPartIdx>>2);
4838#if ADAPTIVE_QP_SELECTION   
4839    Int *pcArlCoeffCurrY = m_ppcQTTempArlCoeffY [uiQTTempAccessLayer] +  uiNumCoeffPerAbsPartIdxIncrement * uiAbsPartIdx;
4840    Int *pcArlCoeffCurrU = m_ppcQTTempArlCoeffCb[uiQTTempAccessLayer] + (uiNumCoeffPerAbsPartIdxIncrement * uiAbsPartIdx>>2);
4841    Int *pcArlCoeffCurrV = m_ppcQTTempArlCoeffCr[uiQTTempAccessLayer] + (uiNumCoeffPerAbsPartIdxIncrement * uiAbsPartIdx>>2);   
4842#endif
4843   
4844    Int trWidth = 0, trHeight = 0, trWidthC = 0, trHeightC = 0;
4845    UInt absTUPartIdxC = uiAbsPartIdx;
4846
4847    trWidth  = trHeight  = 1 << uiLog2TrSize;
4848    trWidthC = trHeightC = 1 <<uiLog2TrSizeC;
4849    pcCU->setTrIdxSubParts( uiDepth - pcCU->getDepth( 0 ), uiAbsPartIdx, uiDepth );
4850    Double minCostY = MAX_DOUBLE;
4851    Double minCostU = MAX_DOUBLE;
4852    Double minCostV = MAX_DOUBLE;
4853    Bool checkTransformSkipY  = pcCU->getSlice()->getPPS()->getUseTransformSkip() && trWidth == 4 && trHeight == 4;
4854    Bool checkTransformSkipUV = pcCU->getSlice()->getPPS()->getUseTransformSkip() && trWidthC == 4 && trHeightC == 4;
4855
4856    checkTransformSkipY         &= (!pcCU->isLosslessCoded(0));
4857    checkTransformSkipUV        &= (!pcCU->isLosslessCoded(0));
4858
4859    pcCU->setTransformSkipSubParts ( 0, TEXT_LUMA, uiAbsPartIdx, uiDepth ); 
4860    if( bCodeChroma )
4861    {
4862      pcCU->setTransformSkipSubParts ( 0, TEXT_CHROMA_U, uiAbsPartIdx, pcCU->getDepth(0)+uiTrModeC ); 
4863      pcCU->setTransformSkipSubParts ( 0, TEXT_CHROMA_V, uiAbsPartIdx, pcCU->getDepth(0)+uiTrModeC ); 
4864    }
4865
4866    if (m_pcEncCfg->getUseRDOQ())
4867    {
4868      m_pcEntropyCoder->estimateBit(m_pcTrQuant->m_pcEstBitsSbac, trWidth, trHeight, TEXT_LUMA );       
4869    }
4870
4871#if REPN_FORMAT_IN_VPS
4872    m_pcTrQuant->setQPforQuant( pcCU->getQP( 0 ), TEXT_LUMA, pcCU->getSlice()->getQpBDOffsetY(), 0 );
4873#else
4874    m_pcTrQuant->setQPforQuant( pcCU->getQP( 0 ), TEXT_LUMA, pcCU->getSlice()->getSPS()->getQpBDOffsetY(), 0 );
4875#endif
4876
4877#if RDOQ_CHROMA_LAMBDA
4878    m_pcTrQuant->selectLambda(TEXT_LUMA); 
4879#endif
4880    m_pcTrQuant->transformNxN( pcCU, pcResi->getLumaAddr( absTUPartIdx ), pcResi->getStride (), pcCoeffCurrY, 
4881#if ADAPTIVE_QP_SELECTION
4882                                 pcArlCoeffCurrY, 
4883#endif     
4884                                 trWidth,   trHeight,    uiAbsSumY, TEXT_LUMA,     uiAbsPartIdx );
4885   
4886    pcCU->setCbfSubParts( uiAbsSumY ? uiSetCbf : 0, TEXT_LUMA, uiAbsPartIdx, uiDepth );
4887   
4888    if( bCodeChroma )
4889    {
4890      if (m_pcEncCfg->getUseRDOQ())
4891      {
4892        m_pcEntropyCoder->estimateBit(m_pcTrQuant->m_pcEstBitsSbac, trWidthC, trHeightC, TEXT_CHROMA );         
4893      }
4894
4895      Int curChromaQpOffset = pcCU->getSlice()->getPPS()->getChromaCbQpOffset() + pcCU->getSlice()->getSliceQpDeltaCb();
4896      m_pcTrQuant->setQPforQuant( pcCU->getQP( 0 ), TEXT_CHROMA, pcCU->getSlice()->getSPS()->getQpBDOffsetC(), curChromaQpOffset );
4897
4898#if RDOQ_CHROMA_LAMBDA
4899      m_pcTrQuant->selectLambda(TEXT_CHROMA_U);
4900#endif
4901
4902      m_pcTrQuant->transformNxN( pcCU, pcResi->getCbAddr(absTUPartIdxC), pcResi->getCStride(), pcCoeffCurrU, 
4903#if ADAPTIVE_QP_SELECTION
4904                                 pcArlCoeffCurrU, 
4905#endif       
4906                                 trWidthC, trHeightC, uiAbsSumU, TEXT_CHROMA_U, uiAbsPartIdx );
4907
4908      curChromaQpOffset = pcCU->getSlice()->getPPS()->getChromaCrQpOffset() + pcCU->getSlice()->getSliceQpDeltaCr();
4909      m_pcTrQuant->setQPforQuant( pcCU->getQP( 0 ), TEXT_CHROMA, pcCU->getSlice()->getSPS()->getQpBDOffsetC(), curChromaQpOffset );
4910     
4911#if RDOQ_CHROMA_LAMBDA
4912      m_pcTrQuant->selectLambda(TEXT_CHROMA_V);
4913#endif
4914
4915      m_pcTrQuant->transformNxN( pcCU, pcResi->getCrAddr(absTUPartIdxC), pcResi->getCStride(), pcCoeffCurrV, 
4916#if ADAPTIVE_QP_SELECTION
4917                                 pcArlCoeffCurrV, 
4918#endif       
4919                                 trWidthC, trHeightC, uiAbsSumV, TEXT_CHROMA_V, uiAbsPartIdx );
4920
4921      pcCU->setCbfSubParts( uiAbsSumU ? uiSetCbf : 0, TEXT_CHROMA_U, uiAbsPartIdx, pcCU->getDepth(0)+uiTrModeC );
4922      pcCU->setCbfSubParts( uiAbsSumV ? uiSetCbf : 0, TEXT_CHROMA_V, uiAbsPartIdx, pcCU->getDepth(0)+uiTrModeC );
4923    }
4924   
4925    m_pcEntropyCoder->resetBits();
4926   
4927    m_pcEntropyCoder->encodeQtCbf( pcCU, uiAbsPartIdx, TEXT_LUMA,     uiTrMode );
4928
4929    m_pcEntropyCoder->encodeCoeffNxN( pcCU, pcCoeffCurrY, uiAbsPartIdx,  trWidth,  trHeight,    uiDepth, TEXT_LUMA );
4930    const UInt uiSingleBitsY = m_pcEntropyCoder->getNumberOfWrittenBits();
4931   
4932    UInt uiSingleBitsU = 0;
4933    UInt uiSingleBitsV = 0;
4934    if( bCodeChroma )
4935    {
4936      m_pcEntropyCoder->encodeQtCbf   ( pcCU, uiAbsPartIdx, TEXT_CHROMA_U, uiTrMode );
4937      m_pcEntropyCoder->encodeCoeffNxN( pcCU, pcCoeffCurrU, uiAbsPartIdx, trWidthC, trHeightC, uiDepth, TEXT_CHROMA_U );
4938      uiSingleBitsU = m_pcEntropyCoder->getNumberOfWrittenBits() - uiSingleBitsY;
4939     
4940      m_pcEntropyCoder->encodeQtCbf   ( pcCU, uiAbsPartIdx, TEXT_CHROMA_V, uiTrMode );
4941      m_pcEntropyCoder->encodeCoeffNxN( pcCU, pcCoeffCurrV, uiAbsPartIdx, trWidthC, trHeightC, uiDepth, TEXT_CHROMA_V );
4942      uiSingleBitsV = m_pcEntropyCoder->getNumberOfWrittenBits() - ( uiSingleBitsY + uiSingleBitsU );
4943    }
4944   
4945    const UInt uiNumSamplesLuma = 1 << (uiLog2TrSize<<1);
4946    const UInt uiNumSamplesChro = 1 << (uiLog2TrSizeC<<1);
4947   
4948    ::memset( m_pTempPel, 0, sizeof( Pel ) * uiNumSamplesLuma ); // not necessary needed for inside of recursion (only at the beginning)
4949   
4950    UInt uiDistY = m_pcRdCost->getDistPart(g_bitDepthY, m_pTempPel, trWidth, pcResi->getLumaAddr( absTUPartIdx ), pcResi->getStride(), trWidth, trHeight ); // initialized with zero residual destortion
4951
4952    if ( puiZeroDist )
4953    {
4954      *puiZeroDist += uiDistY;
4955    }
4956    if( uiAbsSumY )
4957    {
4958      Pel *pcResiCurrY = m_pcQTTempTComYuv[ uiQTTempAccessLayer ].getLumaAddr( absTUPartIdx );
4959
4960#if REPN_FORMAT_IN_VPS
4961      m_pcTrQuant->setQPforQuant( pcCU->getQP( 0 ), TEXT_LUMA, pcCU->getSlice()->getSPS()->getQpBDOffsetY(), 0 );
4962#else
4963      m_pcTrQuant->setQPforQuant( pcCU->getQP( 0 ), TEXT_LUMA, pcCU->getSlice()->getSPS()->getQpBDOffsetY(), 0 );
4964#endif
4965
4966      Int scalingListType = 3 + g_eTTable[(Int)TEXT_LUMA];
4967      assert(scalingListType < 6);     
4968      m_pcTrQuant->invtransformNxN( pcCU->getCUTransquantBypass(uiAbsPartIdx), TEXT_LUMA,REG_DCT, pcResiCurrY, m_pcQTTempTComYuv[uiQTTempAccessLayer].getStride(),  pcCoeffCurrY, trWidth, trHeight, scalingListType );//this is for inter mode only
4969     
4970      const UInt uiNonzeroDistY = m_pcRdCost->getDistPart(g_bitDepthY, m_pcQTTempTComYuv[uiQTTempAccessLayer].getLumaAddr( absTUPartIdx ), m_pcQTTempTComYuv[uiQTTempAccessLayer].getStride(),
4971      pcResi->getLumaAddr( absTUPartIdx ), pcResi->getStride(), trWidth,trHeight );
4972      if (pcCU->isLosslessCoded(0)) 
4973      {
4974        uiDistY = uiNonzeroDistY;
4975      }
4976      else
4977      {
4978        const Double singleCostY = m_pcRdCost->calcRdCost( uiSingleBitsY, uiNonzeroDistY );
4979        m_pcEntropyCoder->resetBits();
4980        m_pcEntropyCoder->encodeQtCbfZero( pcCU, TEXT_LUMA,     uiTrMode );
4981        const UInt uiNullBitsY   = m_pcEntropyCoder->getNumberOfWrittenBits();
4982        const Double nullCostY   = m_pcRdCost->calcRdCost( uiNullBitsY, uiDistY );
4983        if( nullCostY < singleCostY ) 
4984        {   
4985          uiAbsSumY = 0;
4986          ::memset( pcCoeffCurrY, 0, sizeof( TCoeff ) * uiNumSamplesLuma );
4987          if( checkTransformSkipY )
4988          {
4989            minCostY = nullCostY;
4990          }
4991        }
4992        else
4993        {
4994          uiDistY = uiNonzeroDistY;
4995          if( checkTransformSkipY )
4996          {
4997            minCostY = singleCostY;
4998          }
4999        }
5000      }
5001    }
5002    else if( checkTransformSkipY )
5003    {
5004      m_pcEntropyCoder->resetBits();
5005      m_pcEntropyCoder->encodeQtCbfZero( pcCU, TEXT_LUMA, uiTrMode );
5006      const UInt uiNullBitsY = m_pcEntropyCoder->getNumberOfWrittenBits();
5007      minCostY = m_pcRdCost->calcRdCost( uiNullBitsY, uiDistY );
5008    }
5009
5010    if( !uiAbsSumY )
5011    {
5012      Pel *pcPtr =  m_pcQTTempTComYuv[uiQTTempAccessLayer].getLumaAddr( absTUPartIdx );
5013      const UInt uiStride = m_pcQTTempTComYuv[uiQTTempAccessLayer].getStride();
5014      for( UInt uiY = 0; uiY < trHeight; ++uiY )
5015      {
5016        ::memset( pcPtr, 0, sizeof( Pel ) * trWidth );
5017        pcPtr += uiStride;
5018      } 
5019    }
5020   
5021    UInt uiDistU = 0;
5022    UInt uiDistV = 0;
5023    if( bCodeChroma )
5024    {
5025      uiDistU = m_pcRdCost->getDistPart(g_bitDepthC, m_pTempPel, trWidthC, pcResi->getCbAddr( absTUPartIdxC ), pcResi->getCStride(), trWidthC, trHeightC
5026                                        , TEXT_CHROMA_U
5027                                        ); // initialized with zero residual destortion
5028      if ( puiZeroDist )
5029      {
5030        *puiZeroDist += uiDistU;
5031      }
5032      if( uiAbsSumU )
5033      {
5034        Pel *pcResiCurrU = m_pcQTTempTComYuv[uiQTTempAccessLayer].getCbAddr( absTUPartIdxC );
5035
5036        Int curChromaQpOffset = pcCU->getSlice()->getPPS()->getChromaCbQpOffset() + pcCU->getSlice()->getSliceQpDeltaCb();
5037        m_pcTrQuant->setQPforQuant( pcCU->getQP( 0 ), TEXT_CHROMA, pcCU->getSlice()->getSPS()->getQpBDOffsetC(), curChromaQpOffset );
5038
5039        Int scalingListType = 3 + g_eTTable[(Int)TEXT_CHROMA_U];
5040        assert(scalingListType < 6);
5041        m_pcTrQuant->invtransformNxN( pcCU->getCUTransquantBypass(uiAbsPartIdx), TEXT_CHROMA,REG_DCT, pcResiCurrU, m_pcQTTempTComYuv[uiQTTempAccessLayer].getCStride(), pcCoeffCurrU, trWidthC, trHeightC, scalingListType  );
5042       
5043        const UInt uiNonzeroDistU = m_pcRdCost->getDistPart(g_bitDepthC, m_pcQTTempTComYuv[uiQTTempAccessLayer].getCbAddr( absTUPartIdxC), m_pcQTTempTComYuv[uiQTTempAccessLayer].getCStride(),
5044                                                            pcResi->getCbAddr( absTUPartIdxC), pcResi->getCStride(), trWidthC, trHeightC
5045                                                            , TEXT_CHROMA_U
5046                                                            );
5047
5048        if(pcCU->isLosslessCoded(0)) 
5049        {
5050          uiDistU = uiNonzeroDistU;
5051        }
5052        else
5053        {
5054          const Double dSingleCostU = m_pcRdCost->calcRdCost( uiSingleBitsU, uiNonzeroDistU );
5055          m_pcEntropyCoder->resetBits();
5056          m_pcEntropyCoder->encodeQtCbfZero( pcCU, TEXT_CHROMA_U,     uiTrMode );
5057          const UInt uiNullBitsU    = m_pcEntropyCoder->getNumberOfWrittenBits();
5058          const Double dNullCostU   = m_pcRdCost->calcRdCost( uiNullBitsU, uiDistU );
5059          if( dNullCostU < dSingleCostU )
5060          {
5061            uiAbsSumU = 0;
5062            ::memset( pcCoeffCurrU, 0, sizeof( TCoeff ) * uiNumSamplesChro );
5063            if( checkTransformSkipUV )
5064            {
5065              minCostU = dNullCostU;
5066            }
5067          }
5068          else
5069          {
5070            uiDistU = uiNonzeroDistU;
5071            if( checkTransformSkipUV )
5072            {
5073              minCostU = dSingleCostU;
5074            }
5075          }
5076        }
5077      }
5078      else if( checkTransformSkipUV )
5079      {
5080        m_pcEntropyCoder->resetBits();
5081        m_pcEntropyCoder->encodeQtCbfZero( pcCU, TEXT_CHROMA_U, uiTrMode );
5082        const UInt uiNullBitsU = m_pcEntropyCoder->getNumberOfWrittenBits();
5083        minCostU = m_pcRdCost->calcRdCost( uiNullBitsU, uiDistU );
5084      }
5085      if( !uiAbsSumU )
5086      {
5087        Pel *pcPtr =  m_pcQTTempTComYuv[uiQTTempAccessLayer].getCbAddr( absTUPartIdxC );
5088          const UInt uiStride = m_pcQTTempTComYuv[uiQTTempAccessLayer].getCStride();
5089        for( UInt uiY = 0; uiY < trHeightC; ++uiY )
5090        {
5091          ::memset( pcPtr, 0, sizeof(Pel) * trWidthC );
5092          pcPtr += uiStride;
5093        }
5094      }
5095     
5096      uiDistV = m_pcRdCost->getDistPart(g_bitDepthC, m_pTempPel, trWidthC, pcResi->getCrAddr( absTUPartIdxC), pcResi->getCStride(), trWidthC, trHeightC
5097                                        , TEXT_CHROMA_V
5098                                        ); // initialized with zero residual destortion
5099      if ( puiZeroDist )
5100      {
5101        *puiZeroDist += uiDistV;
5102      }
5103      if( uiAbsSumV )
5104      {
5105        Pel *pcResiCurrV = m_pcQTTempTComYuv[uiQTTempAccessLayer].getCrAddr( absTUPartIdxC );
5106        Int curChromaQpOffset = pcCU->getSlice()->getPPS()->getChromaCrQpOffset() + pcCU->getSlice()->getSliceQpDeltaCr();
5107        m_pcTrQuant->setQPforQuant( pcCU->getQP( 0 ), TEXT_CHROMA, pcCU->getSlice()->getSPS()->getQpBDOffsetC(), curChromaQpOffset );
5108
5109        Int scalingListType = 3 + g_eTTable[(Int)TEXT_CHROMA_V];
5110        assert(scalingListType < 6);
5111        m_pcTrQuant->invtransformNxN( pcCU->getCUTransquantBypass(uiAbsPartIdx), TEXT_CHROMA,REG_DCT, pcResiCurrV, m_pcQTTempTComYuv[uiQTTempAccessLayer].getCStride(), pcCoeffCurrV, trWidthC, trHeightC, scalingListType );
5112       
5113        const UInt uiNonzeroDistV = m_pcRdCost->getDistPart(g_bitDepthC, m_pcQTTempTComYuv[uiQTTempAccessLayer].getCrAddr( absTUPartIdxC ), m_pcQTTempTComYuv[uiQTTempAccessLayer].getCStride(),
5114                                                            pcResi->getCrAddr( absTUPartIdxC ), pcResi->getCStride(), trWidthC, trHeightC
5115                                                            , TEXT_CHROMA_V
5116                                                            );
5117        if (pcCU->isLosslessCoded(0)) 
5118        {
5119          uiDistV = uiNonzeroDistV;
5120        }
5121        else
5122        {
5123          const Double dSingleCostV = m_pcRdCost->calcRdCost( uiSingleBitsV, uiNonzeroDistV );
5124          m_pcEntropyCoder->resetBits();
5125          m_pcEntropyCoder->encodeQtCbfZero( pcCU, TEXT_CHROMA_V,     uiTrMode );
5126          const UInt uiNullBitsV    = m_pcEntropyCoder->getNumberOfWrittenBits();
5127          const Double dNullCostV   = m_pcRdCost->calcRdCost( uiNullBitsV, uiDistV );
5128          if( dNullCostV < dSingleCostV )
5129          {
5130            uiAbsSumV = 0;
5131            ::memset( pcCoeffCurrV, 0, sizeof( TCoeff ) * uiNumSamplesChro );
5132            if( checkTransformSkipUV )
5133            {
5134              minCostV = dNullCostV;
5135            }
5136          }
5137          else
5138          {
5139            uiDistV = uiNonzeroDistV;
5140            if( checkTransformSkipUV )
5141            {
5142              minCostV = dSingleCostV;
5143            }
5144          }
5145        }
5146      }
5147      else if( checkTransformSkipUV )
5148      {
5149        m_pcEntropyCoder->resetBits();
5150        m_pcEntropyCoder->encodeQtCbfZero( pcCU, TEXT_CHROMA_V, uiTrMode );
5151        const UInt uiNullBitsV = m_pcEntropyCoder->getNumberOfWrittenBits();
5152        minCostV = m_pcRdCost->calcRdCost( uiNullBitsV, uiDistV );
5153      }
5154      if( !uiAbsSumV )
5155      {
5156        Pel *pcPtr =  m_pcQTTempTComYuv[uiQTTempAccessLayer].getCrAddr( absTUPartIdxC );
5157        const UInt uiStride = m_pcQTTempTComYuv[uiQTTempAccessLayer].getCStride();
5158        for( UInt uiY = 0; uiY < trHeightC; ++uiY )
5159        {   
5160          ::memset( pcPtr, 0, sizeof(Pel) * trWidthC );
5161          pcPtr += uiStride;
5162        }
5163      }
5164    }
5165    pcCU->setCbfSubParts( uiAbsSumY ? uiSetCbf : 0, TEXT_LUMA, uiAbsPartIdx, uiDepth );
5166    if( bCodeChroma )
5167    {
5168      pcCU->setCbfSubParts( uiAbsSumU ? uiSetCbf : 0, TEXT_CHROMA_U, uiAbsPartIdx, pcCU->getDepth(0)+uiTrModeC );
5169      pcCU->setCbfSubParts( uiAbsSumV ? uiSetCbf : 0, TEXT_CHROMA_V, uiAbsPartIdx, pcCU->getDepth(0)+uiTrModeC );
5170    }
5171
5172    if( checkTransformSkipY )
5173    {
5174      UInt uiNonzeroDistY, uiAbsSumTransformSkipY;
5175      Double dSingleCostY;
5176
5177      Pel *pcResiCurrY = m_pcQTTempTComYuv[ uiQTTempAccessLayer ].getLumaAddr( absTUPartIdx );
5178      UInt resiYStride = m_pcQTTempTComYuv[ uiQTTempAccessLayer ].getStride();
5179
5180      TCoeff bestCoeffY[32*32];
5181      memcpy( bestCoeffY, pcCoeffCurrY, sizeof(TCoeff) * uiNumSamplesLuma );
5182     
5183#if ADAPTIVE_QP_SELECTION
5184      TCoeff bestArlCoeffY[32*32];
5185      memcpy( bestArlCoeffY, pcArlCoeffCurrY, sizeof(TCoeff) * uiNumSamplesLuma );
5186#endif
5187
5188      Pel bestResiY[32*32];
5189      for ( Int i = 0; i < trHeight; ++i )
5190      {
5191        memcpy( &bestResiY[i*trWidth], pcResiCurrY+i*resiYStride, sizeof(Pel) * trWidth );
5192      }
5193
5194      if( m_bUseSBACRD )
5195      {
5196        m_pcRDGoOnSbacCoder->load( m_pppcRDSbacCoder[ uiDepth ][ CI_QT_TRAFO_ROOT ] );
5197      }
5198
5199      pcCU->setTransformSkipSubParts ( 1, TEXT_LUMA, uiAbsPartIdx, uiDepth );
5200
5201      if (m_pcEncCfg->getUseRDOQTS())
5202      {
5203        m_pcEntropyCoder->estimateBit( m_pcTrQuant->m_pcEstBitsSbac, trWidth, trHeight, TEXT_LUMA );       
5204      }
5205
5206#if REPN_FORMAT_IN_VPS
5207      m_pcTrQuant->setQPforQuant( pcCU->getQP( 0 ), TEXT_LUMA, pcCU->getSlice()->getQpBDOffsetY(), 0 );
5208#else
5209      m_pcTrQuant->setQPforQuant( pcCU->getQP( 0 ), TEXT_LUMA, pcCU->getSlice()->getSPS()->getQpBDOffsetY(), 0 );
5210#endif
5211
5212#if RDOQ_CHROMA_LAMBDA
5213      m_pcTrQuant->selectLambda(TEXT_LUMA);
5214#endif
5215      m_pcTrQuant->transformNxN( pcCU, pcResi->getLumaAddr( absTUPartIdx ), pcResi->getStride (), pcCoeffCurrY, 
5216#if ADAPTIVE_QP_SELECTION
5217        pcArlCoeffCurrY, 
5218#endif     
5219        trWidth,   trHeight,    uiAbsSumTransformSkipY, TEXT_LUMA, uiAbsPartIdx, true );
5220      pcCU->setCbfSubParts( uiAbsSumTransformSkipY ? uiSetCbf : 0, TEXT_LUMA, uiAbsPartIdx, uiDepth );
5221
5222      if( uiAbsSumTransformSkipY != 0 )
5223      {
5224        m_pcEntropyCoder->resetBits();
5225        m_pcEntropyCoder->encodeQtCbf( pcCU, uiAbsPartIdx, TEXT_LUMA, uiTrMode );
5226        m_pcEntropyCoder->encodeCoeffNxN( pcCU, pcCoeffCurrY, uiAbsPartIdx, trWidth, trHeight, uiDepth, TEXT_LUMA );
5227        const UInt uiTsSingleBitsY = m_pcEntropyCoder->getNumberOfWrittenBits();
5228
5229#if REPN_FORMAT_IN_VPS
5230        m_pcTrQuant->setQPforQuant( pcCU->getQP( 0 ), TEXT_LUMA, pcCU->getSlice()->getQpBDOffsetY(), 0 );
5231#else
5232        m_pcTrQuant->setQPforQuant( pcCU->getQP( 0 ), TEXT_LUMA, pcCU->getSlice()->getSPS()->getQpBDOffsetY(), 0 );
5233#endif
5234
5235        Int scalingListType = 3 + g_eTTable[(Int)TEXT_LUMA];
5236        assert(scalingListType < 6);     
5237
5238        m_pcTrQuant->invtransformNxN( pcCU->getCUTransquantBypass(uiAbsPartIdx), TEXT_LUMA,REG_DCT, pcResiCurrY, m_pcQTTempTComYuv[uiQTTempAccessLayer].getStride(),  pcCoeffCurrY, trWidth, trHeight, scalingListType, true );
5239
5240        uiNonzeroDistY = m_pcRdCost->getDistPart(g_bitDepthY, m_pcQTTempTComYuv[uiQTTempAccessLayer].getLumaAddr( absTUPartIdx ), m_pcQTTempTComYuv[uiQTTempAccessLayer].getStride(),
5241          pcResi->getLumaAddr( absTUPartIdx ), pcResi->getStride(), trWidth, trHeight );
5242
5243        dSingleCostY = m_pcRdCost->calcRdCost( uiTsSingleBitsY, uiNonzeroDistY );
5244      }
5245
5246      if( !uiAbsSumTransformSkipY || minCostY < dSingleCostY )
5247      {
5248        pcCU->setTransformSkipSubParts ( 0, TEXT_LUMA, uiAbsPartIdx, uiDepth );
5249        memcpy( pcCoeffCurrY, bestCoeffY, sizeof(TCoeff) * uiNumSamplesLuma );
5250#if ADAPTIVE_QP_SELECTION
5251        memcpy( pcArlCoeffCurrY, bestArlCoeffY, sizeof(TCoeff) * uiNumSamplesLuma );
5252#endif
5253        for( Int i = 0; i < trHeight; ++i )
5254        {
5255          memcpy( pcResiCurrY+i*resiYStride, &bestResiY[i*trWidth], sizeof(Pel) * trWidth );
5256        }
5257      }
5258      else
5259      {
5260        uiDistY = uiNonzeroDistY;
5261        uiAbsSumY = uiAbsSumTransformSkipY;
5262        uiBestTransformMode[0] = 1;
5263      }
5264
5265      pcCU->setCbfSubParts( uiAbsSumY ? uiSetCbf : 0, TEXT_LUMA, uiAbsPartIdx, uiDepth );
5266    }
5267
5268    if( bCodeChroma && checkTransformSkipUV  )
5269    {
5270      UInt uiNonzeroDistU, uiNonzeroDistV, uiAbsSumTransformSkipU, uiAbsSumTransformSkipV;
5271      Double dSingleCostU, dSingleCostV;
5272
5273      Pel *pcResiCurrU = m_pcQTTempTComYuv[uiQTTempAccessLayer].getCbAddr( absTUPartIdxC );
5274      Pel *pcResiCurrV = m_pcQTTempTComYuv[uiQTTempAccessLayer].getCrAddr( absTUPartIdxC );
5275      UInt resiCStride = m_pcQTTempTComYuv[uiQTTempAccessLayer].getCStride();
5276
5277      TCoeff bestCoeffU[32*32], bestCoeffV[32*32];
5278      memcpy( bestCoeffU, pcCoeffCurrU, sizeof(TCoeff) * uiNumSamplesChro );
5279      memcpy( bestCoeffV, pcCoeffCurrV, sizeof(TCoeff) * uiNumSamplesChro );
5280
5281#if ADAPTIVE_QP_SELECTION
5282      TCoeff bestArlCoeffU[32*32], bestArlCoeffV[32*32];
5283      memcpy( bestArlCoeffU, pcArlCoeffCurrU, sizeof(TCoeff) * uiNumSamplesChro );
5284      memcpy( bestArlCoeffV, pcArlCoeffCurrV, sizeof(TCoeff) * uiNumSamplesChro );
5285#endif
5286
5287      Pel bestResiU[32*32], bestResiV[32*32];
5288      for (Int i = 0; i < trHeightC; ++i )
5289      {
5290        memcpy( &bestResiU[i*trWidthC], pcResiCurrU+i*resiCStride, sizeof(Pel) * trWidthC );
5291        memcpy( &bestResiV[i*trWidthC], pcResiCurrV+i*resiCStride, sizeof(Pel) * trWidthC );
5292      }
5293
5294      if( m_bUseSBACRD )
5295      {
5296        m_pcRDGoOnSbacCoder->load( m_pppcRDSbacCoder[ uiDepth ][ CI_QT_TRAFO_ROOT ] );
5297      }
5298
5299      pcCU->setTransformSkipSubParts ( 1, TEXT_CHROMA_U, uiAbsPartIdx, pcCU->getDepth(0)+uiTrModeC ); 
5300      pcCU->setTransformSkipSubParts ( 1, TEXT_CHROMA_V, uiAbsPartIdx, pcCU->getDepth(0)+uiTrModeC );
5301
5302      if (m_pcEncCfg->getUseRDOQTS())
5303      {
5304        m_pcEntropyCoder->estimateBit(m_pcTrQuant->m_pcEstBitsSbac, trWidthC, trHeightC, TEXT_CHROMA );         
5305      }
5306
5307      Int curChromaQpOffset = pcCU->getSlice()->getPPS()->getChromaCbQpOffset() + pcCU->getSlice()->getSliceQpDeltaCb();
5308      m_pcTrQuant->setQPforQuant( pcCU->getQP( 0 ), TEXT_CHROMA, pcCU->getSlice()->getSPS()->getQpBDOffsetC(), curChromaQpOffset );
5309
5310#if RDOQ_CHROMA_LAMBDA
5311      m_pcTrQuant->selectLambda(TEXT_CHROMA_U);
5312#endif
5313
5314      m_pcTrQuant->transformNxN( pcCU, pcResi->getCbAddr(absTUPartIdxC), pcResi->getCStride(), pcCoeffCurrU, 
5315#if ADAPTIVE_QP_SELECTION
5316        pcArlCoeffCurrU, 
5317#endif       
5318        trWidthC, trHeightC, uiAbsSumTransformSkipU, TEXT_CHROMA_U, uiAbsPartIdx, true );
5319      curChromaQpOffset = pcCU->getSlice()->getPPS()->getChromaCrQpOffset() + pcCU->getSlice()->getSliceQpDeltaCr();
5320      m_pcTrQuant->setQPforQuant( pcCU->getQP( 0 ), TEXT_CHROMA, pcCU->getSlice()->getSPS()->getQpBDOffsetC(), curChromaQpOffset );
5321#if RDOQ_CHROMA_LAMBDA
5322      m_pcTrQuant->selectLambda(TEXT_CHROMA_V);
5323#endif
5324      m_pcTrQuant->transformNxN( pcCU, pcResi->getCrAddr(absTUPartIdxC), pcResi->getCStride(), pcCoeffCurrV, 
5325#if ADAPTIVE_QP_SELECTION
5326        pcArlCoeffCurrV, 
5327#endif       
5328        trWidthC, trHeightC, uiAbsSumTransformSkipV, TEXT_CHROMA_V, uiAbsPartIdx, true );
5329
5330      pcCU->setCbfSubParts( uiAbsSumTransformSkipU ? uiSetCbf : 0, TEXT_CHROMA_U, uiAbsPartIdx, pcCU->getDepth(0)+uiTrModeC );
5331      pcCU->setCbfSubParts( uiAbsSumTransformSkipV ? uiSetCbf : 0, TEXT_CHROMA_V, uiAbsPartIdx, pcCU->getDepth(0)+uiTrModeC );
5332
5333      m_pcEntropyCoder->resetBits();
5334      uiSingleBitsU = 0;
5335      uiSingleBitsV = 0;
5336
5337      if( uiAbsSumTransformSkipU )
5338      {
5339        m_pcEntropyCoder->encodeQtCbf   ( pcCU, uiAbsPartIdx, TEXT_CHROMA_U, uiTrMode );
5340        m_pcEntropyCoder->encodeCoeffNxN( pcCU, pcCoeffCurrU, uiAbsPartIdx, trWidthC, trHeightC, uiDepth, TEXT_CHROMA_U );
5341        uiSingleBitsU = m_pcEntropyCoder->getNumberOfWrittenBits();   
5342
5343        curChromaQpOffset = pcCU->getSlice()->getPPS()->getChromaCbQpOffset() + pcCU->getSlice()->getSliceQpDeltaCb();
5344        m_pcTrQuant->setQPforQuant( pcCU->getQP( 0 ), TEXT_CHROMA, pcCU->getSlice()->getSPS()->getQpBDOffsetC(), curChromaQpOffset );
5345
5346        Int scalingListType = 3 + g_eTTable[(Int)TEXT_CHROMA_U];
5347        assert(scalingListType < 6);
5348
5349        m_pcTrQuant->invtransformNxN( pcCU->getCUTransquantBypass(uiAbsPartIdx), TEXT_CHROMA,REG_DCT, pcResiCurrU, m_pcQTTempTComYuv[uiQTTempAccessLayer].getCStride(), pcCoeffCurrU, trWidthC, trHeightC, scalingListType, true  );
5350
5351        uiNonzeroDistU = m_pcRdCost->getDistPart(g_bitDepthC, m_pcQTTempTComYuv[uiQTTempAccessLayer].getCbAddr( absTUPartIdxC), m_pcQTTempTComYuv[uiQTTempAccessLayer].getCStride(),
5352                                                 pcResi->getCbAddr( absTUPartIdxC), pcResi->getCStride(), trWidthC, trHeightC
5353                                                 , TEXT_CHROMA_U
5354                                                 );
5355
5356        dSingleCostU = m_pcRdCost->calcRdCost( uiSingleBitsU, uiNonzeroDistU );
5357      }
5358
5359      if( !uiAbsSumTransformSkipU || minCostU < dSingleCostU )
5360      {
5361        pcCU->setTransformSkipSubParts ( 0, TEXT_CHROMA_U, uiAbsPartIdx, pcCU->getDepth(0)+uiTrModeC ); 
5362
5363        memcpy( pcCoeffCurrU, bestCoeffU, sizeof (TCoeff) * uiNumSamplesChro );
5364#if ADAPTIVE_QP_SELECTION
5365        memcpy( pcArlCoeffCurrU, bestArlCoeffU, sizeof (TCoeff) * uiNumSamplesChro );
5366#endif
5367        for( Int i = 0; i < trHeightC; ++i )
5368        {
5369          memcpy( pcResiCurrU+i*resiCStride, &bestResiU[i*trWidthC], sizeof(Pel) * trWidthC );
5370        }
5371      }
5372      else
5373      {
5374        uiDistU = uiNonzeroDistU;
5375        uiAbsSumU = uiAbsSumTransformSkipU;
5376        uiBestTransformMode[1] = 1;
5377      }
5378
5379      if( uiAbsSumTransformSkipV )
5380      {
5381        m_pcEntropyCoder->encodeQtCbf   ( pcCU, uiAbsPartIdx, TEXT_CHROMA_V, uiTrMode );
5382        m_pcEntropyCoder->encodeCoeffNxN( pcCU, pcCoeffCurrV, uiAbsPartIdx, trWidthC, trHeightC, uiDepth, TEXT_CHROMA_V );
5383        uiSingleBitsV = m_pcEntropyCoder->getNumberOfWrittenBits() - uiSingleBitsU;
5384
5385        curChromaQpOffset = pcCU->getSlice()->getPPS()->getChromaCrQpOffset() + pcCU->getSlice()->getSliceQpDeltaCr();
5386        m_pcTrQuant->setQPforQuant( pcCU->getQP( 0 ), TEXT_CHROMA, pcCU->getSlice()->getSPS()->getQpBDOffsetC(), curChromaQpOffset );
5387
5388        Int scalingListType = 3 + g_eTTable[(Int)TEXT_CHROMA_V];
5389        assert(scalingListType < 6);
5390
5391        m_pcTrQuant->invtransformNxN( pcCU->getCUTransquantBypass(uiAbsPartIdx), TEXT_CHROMA,REG_DCT, pcResiCurrV, m_pcQTTempTComYuv[uiQTTempAccessLayer].getCStride(), pcCoeffCurrV, trWidthC, trHeightC, scalingListType, true );
5392
5393        uiNonzeroDistV = m_pcRdCost->getDistPart(g_bitDepthC, m_pcQTTempTComYuv[uiQTTempAccessLayer].getCrAddr( absTUPartIdxC ), m_pcQTTempTComYuv[uiQTTempAccessLayer].getCStride(),
5394                                                 pcResi->getCrAddr( absTUPartIdxC ), pcResi->getCStride(), trWidthC, trHeightC
5395                                                 , TEXT_CHROMA_V
5396                                                 );
5397
5398        dSingleCostV = m_pcRdCost->calcRdCost( uiSingleBitsV, uiNonzeroDistV );
5399      }
5400
5401      if( !uiAbsSumTransformSkipV || minCostV < dSingleCostV )
5402      {
5403        pcCU->setTransformSkipSubParts ( 0, TEXT_CHROMA_V, uiAbsPartIdx, pcCU->getDepth(0)+uiTrModeC ); 
5404
5405        memcpy( pcCoeffCurrV, bestCoeffV, sizeof(TCoeff) * uiNumSamplesChro );
5406#if ADAPTIVE_QP_SELECTION
5407        memcpy( pcArlCoeffCurrV, bestArlCoeffV, sizeof(TCoeff) * uiNumSamplesChro );
5408#endif
5409        for( Int i = 0; i < trHeightC; ++i )
5410        {
5411          memcpy( pcResiCurrV+i*resiCStride, &bestResiV[i*trWidthC], sizeof(Pel) * trWidthC );
5412        }
5413      }
5414      else
5415      {
5416        uiDistV = uiNonzeroDistV;
5417        uiAbsSumV = uiAbsSumTransformSkipV;
5418        uiBestTransformMode[2] = 1;
5419      }
5420
5421      pcCU->setCbfSubParts( uiAbsSumU ? uiSetCbf : 0, TEXT_CHROMA_U, uiAbsPartIdx, pcCU->getDepth(0)+uiTrModeC );
5422      pcCU->setCbfSubParts( uiAbsSumV ? uiSetCbf : 0, TEXT_CHROMA_V, uiAbsPartIdx, pcCU->getDepth(0)+uiTrModeC );
5423    }
5424
5425    if( m_bUseSBACRD )
5426    {
5427      m_pcRDGoOnSbacCoder->load( m_pppcRDSbacCoder[ uiDepth ][ CI_QT_TRAFO_ROOT ] );
5428    }
5429
5430    m_pcEntropyCoder->resetBits();
5431
5432    if( uiLog2TrSize > pcCU->getQuadtreeTULog2MinSizeInCU(uiAbsPartIdx) )
5433    {
5434      m_pcEntropyCoder->encodeTransformSubdivFlag( 0, 5 - uiLog2TrSize );
5435    }
5436
5437    if( bCodeChroma )
5438    {
5439      m_pcEntropyCoder->encodeQtCbf( pcCU, uiAbsPartIdx, TEXT_CHROMA_U, uiTrMode );
5440      m_pcEntropyCoder->encodeQtCbf( pcCU, uiAbsPartIdx, TEXT_CHROMA_V, uiTrMode );
5441    }
5442
5443    m_pcEntropyCoder->encodeQtCbf( pcCU, uiAbsPartIdx, TEXT_LUMA,     uiTrMode );
5444
5445    m_pcEntropyCoder->encodeCoeffNxN( pcCU, pcCoeffCurrY, uiAbsPartIdx, trWidth, trHeight,    uiDepth, TEXT_LUMA );
5446
5447    if( bCodeChroma )
5448    {
5449      m_pcEntropyCoder->encodeCoeffNxN( pcCU, pcCoeffCurrU, uiAbsPartIdx, trWidthC, trHeightC, uiDepth, TEXT_CHROMA_U );
5450      m_pcEntropyCoder->encodeCoeffNxN( pcCU, pcCoeffCurrV, uiAbsPartIdx, trWidthC, trHeightC, uiDepth, TEXT_CHROMA_V );
5451    }
5452
5453    uiSingleBits = m_pcEntropyCoder->getNumberOfWrittenBits();
5454
5455    uiSingleDist = uiDistY + uiDistU + uiDistV;
5456    dSingleCost = m_pcRdCost->calcRdCost( uiSingleBits, uiSingleDist );
5457  } 
5458 
5459  // code sub-blocks
5460  if( bCheckSplit )
5461  {
5462    if( m_bUseSBACRD && bCheckFull )
5463    {
5464      m_pcRDGoOnSbacCoder->store( m_pppcRDSbacCoder[ uiDepth ][ CI_QT_TRAFO_TEST ] );
5465      m_pcRDGoOnSbacCoder->load ( m_pppcRDSbacCoder[ uiDepth ][ CI_QT_TRAFO_ROOT ] );
5466    }
5467    UInt uiSubdivDist = 0;
5468    UInt uiSubdivBits = 0;
5469    Double dSubdivCost = 0.0;
5470   
5471    const UInt uiQPartNumSubdiv = pcCU->getPic()->getNumPartInCU() >> ((uiDepth + 1 ) << 1);
5472    for( UInt ui = 0; ui < 4; ++ui )
5473    {
5474      UInt nsAddr = uiAbsPartIdx + ui * uiQPartNumSubdiv;
5475      xEstimateResidualQT( pcCU, ui, uiAbsPartIdx + ui * uiQPartNumSubdiv, nsAddr, pcResi, uiDepth + 1, dSubdivCost, uiSubdivBits, uiSubdivDist, bCheckFull ? NULL : puiZeroDist );
5476    }
5477   
5478    UInt uiYCbf = 0;
5479    UInt uiUCbf = 0;
5480    UInt uiVCbf = 0;
5481    for( UInt ui = 0; ui < 4; ++ui )
5482    {
5483      uiYCbf |= pcCU->getCbf( uiAbsPartIdx + ui * uiQPartNumSubdiv, TEXT_LUMA,     uiTrMode + 1 );
5484      uiUCbf |= pcCU->getCbf( uiAbsPartIdx + ui * uiQPartNumSubdiv, TEXT_CHROMA_U, uiTrMode + 1 );
5485      uiVCbf |= pcCU->getCbf( uiAbsPartIdx + ui * uiQPartNumSubdiv, TEXT_CHROMA_V, uiTrMode + 1 );
5486    }
5487    for( UInt ui = 0; ui < 4 * uiQPartNumSubdiv; ++ui )
5488    {
5489      pcCU->getCbf( TEXT_LUMA     )[uiAbsPartIdx + ui] |= uiYCbf << uiTrMode;
5490      pcCU->getCbf( TEXT_CHROMA_U )[uiAbsPartIdx + ui] |= uiUCbf << uiTrMode;
5491      pcCU->getCbf( TEXT_CHROMA_V )[uiAbsPartIdx + ui] |= uiVCbf << uiTrMode;
5492    }
5493   
5494    if( m_bUseSBACRD )
5495    {
5496      m_pcRDGoOnSbacCoder->load( m_pppcRDSbacCoder[ uiDepth ][ CI_QT_TRAFO_ROOT ] );
5497    }
5498    m_pcEntropyCoder->resetBits();
5499   
5500    xEncodeResidualQT( pcCU, uiAbsPartIdx, uiDepth, true,  TEXT_LUMA );
5501    xEncodeResidualQT( pcCU, uiAbsPartIdx, uiDepth, false, TEXT_LUMA );
5502    xEncodeResidualQT( pcCU, uiAbsPartIdx, uiDepth, false, TEXT_CHROMA_U );
5503    xEncodeResidualQT( pcCU, uiAbsPartIdx, uiDepth, false, TEXT_CHROMA_V );
5504
5505    uiSubdivBits = m_pcEntropyCoder->getNumberOfWrittenBits();
5506    dSubdivCost  = m_pcRdCost->calcRdCost( uiSubdivBits, uiSubdivDist );
5507   
5508    if( uiYCbf || uiUCbf || uiVCbf || !bCheckFull )
5509    {
5510      if( dSubdivCost < dSingleCost )
5511      {
5512        rdCost += dSubdivCost;
5513        ruiBits += uiSubdivBits;
5514        ruiDist += uiSubdivDist;
5515        return;
5516      }
5517    }
5518    pcCU->setTransformSkipSubParts ( uiBestTransformMode[0], TEXT_LUMA, uiAbsPartIdx, uiDepth ); 
5519    if(bCodeChroma)
5520    {
5521      pcCU->setTransformSkipSubParts ( uiBestTransformMode[1], TEXT_CHROMA_U, uiAbsPartIdx, pcCU->getDepth(0)+uiTrModeC ); 
5522      pcCU->setTransformSkipSubParts ( uiBestTransformMode[2], TEXT_CHROMA_V, uiAbsPartIdx, pcCU->getDepth(0)+uiTrModeC ); 
5523    }
5524    assert( bCheckFull );
5525    if( m_bUseSBACRD )
5526    {
5527      m_pcRDGoOnSbacCoder->load( m_pppcRDSbacCoder[ uiDepth ][ CI_QT_TRAFO_TEST ] );
5528    }
5529  }
5530  rdCost += dSingleCost;
5531  ruiBits += uiSingleBits;
5532  ruiDist += uiSingleDist;
5533 
5534  pcCU->setTrIdxSubParts( uiTrMode, uiAbsPartIdx, uiDepth );
5535 
5536  pcCU->setCbfSubParts( uiAbsSumY ? uiSetCbf : 0, TEXT_LUMA, uiAbsPartIdx, uiDepth );
5537  if( bCodeChroma )
5538  {
5539    pcCU->setCbfSubParts( uiAbsSumU ? uiSetCbf : 0, TEXT_CHROMA_U, uiAbsPartIdx, pcCU->getDepth(0)+uiTrModeC );
5540    pcCU->setCbfSubParts( uiAbsSumV ? uiSetCbf : 0, TEXT_CHROMA_V, uiAbsPartIdx, pcCU->getDepth(0)+uiTrModeC );
5541  }
5542}
5543
5544Void TEncSearch::xEncodeResidualQT( TComDataCU* pcCU, UInt uiAbsPartIdx, const UInt uiDepth, Bool bSubdivAndCbf, TextType eType )
5545{
5546  assert( pcCU->getDepth( 0 ) == pcCU->getDepth( uiAbsPartIdx ) );
5547  const UInt uiCurrTrMode = uiDepth - pcCU->getDepth( 0 );
5548  const UInt uiTrMode = pcCU->getTransformIdx( uiAbsPartIdx );
5549 
5550  const Bool bSubdiv = uiCurrTrMode != uiTrMode;
5551 
5552  const UInt uiLog2TrSize = g_aucConvertToBit[pcCU->getSlice()->getSPS()->getMaxCUWidth() >> uiDepth]+2;
5553
5554  if( bSubdivAndCbf && uiLog2TrSize <= pcCU->getSlice()->getSPS()->getQuadtreeTULog2MaxSize() && uiLog2TrSize > pcCU->getQuadtreeTULog2MinSizeInCU(uiAbsPartIdx) )
5555  {
5556    m_pcEntropyCoder->encodeTransformSubdivFlag( bSubdiv, 5 - uiLog2TrSize );
5557  }
5558
5559  assert( pcCU->getPredictionMode(uiAbsPartIdx) != MODE_INTRA );
5560    if( bSubdivAndCbf )
5561    {
5562      const Bool bFirstCbfOfCU = uiCurrTrMode == 0;
5563      if( bFirstCbfOfCU || uiLog2TrSize > 2 )
5564      {
5565        if( bFirstCbfOfCU || pcCU->getCbf( uiAbsPartIdx, TEXT_CHROMA_U, uiCurrTrMode - 1 ) )
5566        {
5567          m_pcEntropyCoder->encodeQtCbf( pcCU, uiAbsPartIdx, TEXT_CHROMA_U, uiCurrTrMode );
5568        }
5569        if( bFirstCbfOfCU || pcCU->getCbf( uiAbsPartIdx, TEXT_CHROMA_V, uiCurrTrMode - 1 ) )
5570        {
5571          m_pcEntropyCoder->encodeQtCbf( pcCU, uiAbsPartIdx, TEXT_CHROMA_V, uiCurrTrMode );
5572        }
5573      }
5574      else if( uiLog2TrSize == 2 )
5575      {
5576        assert( pcCU->getCbf( uiAbsPartIdx, TEXT_CHROMA_U, uiCurrTrMode ) == pcCU->getCbf( uiAbsPartIdx, TEXT_CHROMA_U, uiCurrTrMode - 1 ) );
5577        assert( pcCU->getCbf( uiAbsPartIdx, TEXT_CHROMA_V, uiCurrTrMode ) == pcCU->getCbf( uiAbsPartIdx, TEXT_CHROMA_V, uiCurrTrMode - 1 ) );
5578      }
5579    }
5580 
5581  if( !bSubdiv )
5582  {
5583    const UInt uiNumCoeffPerAbsPartIdxIncrement = pcCU->getSlice()->getSPS()->getMaxCUWidth() * pcCU->getSlice()->getSPS()->getMaxCUHeight() >> ( pcCU->getSlice()->getSPS()->getMaxCUDepth() << 1 );
5584    //assert( 16 == uiNumCoeffPerAbsPartIdxIncrement ); // check
5585    const UInt uiQTTempAccessLayer = pcCU->getSlice()->getSPS()->getQuadtreeTULog2MaxSize() - uiLog2TrSize;
5586    TCoeff *pcCoeffCurrY = m_ppcQTTempCoeffY [uiQTTempAccessLayer] +  uiNumCoeffPerAbsPartIdxIncrement * uiAbsPartIdx;
5587    TCoeff *pcCoeffCurrU = m_ppcQTTempCoeffCb[uiQTTempAccessLayer] + (uiNumCoeffPerAbsPartIdxIncrement * uiAbsPartIdx>>2);
5588    TCoeff *pcCoeffCurrV = m_ppcQTTempCoeffCr[uiQTTempAccessLayer] + (uiNumCoeffPerAbsPartIdxIncrement * uiAbsPartIdx>>2);
5589   
5590    Bool  bCodeChroma   = true;
5591    UInt  uiTrModeC     = uiTrMode;
5592    UInt  uiLog2TrSizeC = uiLog2TrSize-1;
5593    if( uiLog2TrSize == 2 )
5594    {
5595      uiLog2TrSizeC++;
5596      uiTrModeC    --;
5597      UInt  uiQPDiv = pcCU->getPic()->getNumPartInCU() >> ( ( pcCU->getDepth( 0 ) + uiTrModeC ) << 1 );
5598      bCodeChroma   = ( ( uiAbsPartIdx % uiQPDiv ) == 0 );
5599    }
5600   
5601    if( bSubdivAndCbf )
5602    {
5603      m_pcEntropyCoder->encodeQtCbf( pcCU, uiAbsPartIdx, TEXT_LUMA,     uiTrMode );
5604    }
5605    else
5606    {
5607      if( eType == TEXT_LUMA     && pcCU->getCbf( uiAbsPartIdx, TEXT_LUMA,     uiTrMode ) )
5608      {
5609        Int trWidth  = 1 << uiLog2TrSize;
5610        Int trHeight = 1 << uiLog2TrSize;
5611        m_pcEntropyCoder->encodeCoeffNxN( pcCU, pcCoeffCurrY, uiAbsPartIdx, trWidth, trHeight,    uiDepth, TEXT_LUMA );
5612      }
5613      if( bCodeChroma )
5614      {
5615        Int trWidth  = 1 << uiLog2TrSizeC;
5616        Int trHeight = 1 << uiLog2TrSizeC;
5617        if( eType == TEXT_CHROMA_U && pcCU->getCbf( uiAbsPartIdx, TEXT_CHROMA_U, uiTrMode ) )
5618        {
5619          m_pcEntropyCoder->encodeCoeffNxN( pcCU, pcCoeffCurrU, uiAbsPartIdx, trWidth, trHeight, uiDepth, TEXT_CHROMA_U );
5620        }
5621        if( eType == TEXT_CHROMA_V && pcCU->getCbf( uiAbsPartIdx, TEXT_CHROMA_V, uiTrMode ) )
5622        {
5623          m_pcEntropyCoder->encodeCoeffNxN( pcCU, pcCoeffCurrV, uiAbsPartIdx, trWidth, trHeight, uiDepth, TEXT_CHROMA_V );
5624        }
5625      }
5626    }
5627  }
5628  else
5629  {
5630    if( bSubdivAndCbf || pcCU->getCbf( uiAbsPartIdx, eType, uiCurrTrMode ) )
5631    {
5632      const UInt uiQPartNumSubdiv = pcCU->getPic()->getNumPartInCU() >> ((uiDepth + 1 ) << 1);
5633      for( UInt ui = 0; ui < 4; ++ui )
5634      {
5635        xEncodeResidualQT( pcCU, uiAbsPartIdx + ui * uiQPartNumSubdiv, uiDepth + 1, bSubdivAndCbf, eType );
5636      }
5637    }
5638  }
5639}
5640
5641Void TEncSearch::xSetResidualQTData( TComDataCU* pcCU, UInt uiQuadrant, UInt uiAbsPartIdx, UInt absTUPartIdx, TComYuv* pcResi, UInt uiDepth, Bool bSpatial )
5642{
5643  assert( pcCU->getDepth( 0 ) == pcCU->getDepth( uiAbsPartIdx ) );
5644  const UInt uiCurrTrMode = uiDepth - pcCU->getDepth( 0 );
5645  const UInt uiTrMode = pcCU->getTransformIdx( uiAbsPartIdx );
5646
5647  if( uiCurrTrMode == uiTrMode )
5648  {
5649    const UInt uiLog2TrSize = g_aucConvertToBit[pcCU->getSlice()->getSPS()->getMaxCUWidth() >> uiDepth]+2;
5650    const UInt uiQTTempAccessLayer = pcCU->getSlice()->getSPS()->getQuadtreeTULog2MaxSize() - uiLog2TrSize;
5651
5652    Bool  bCodeChroma   = true;
5653    UInt  uiTrModeC     = uiTrMode;
5654    UInt  uiLog2TrSizeC = uiLog2TrSize-1;
5655    if( uiLog2TrSize == 2 )
5656    {
5657      uiLog2TrSizeC++;
5658      uiTrModeC    --;
5659      UInt  uiQPDiv = pcCU->getPic()->getNumPartInCU() >> ( ( pcCU->getDepth( 0 ) + uiTrModeC ) << 1 );
5660      bCodeChroma   = ( ( uiAbsPartIdx % uiQPDiv ) == 0 );
5661    }
5662
5663    if( bSpatial )
5664    {     
5665      Int trWidth  = 1 << uiLog2TrSize;
5666      Int trHeight = 1 << uiLog2TrSize;
5667      m_pcQTTempTComYuv[uiQTTempAccessLayer].copyPartToPartLuma    ( pcResi, absTUPartIdx, trWidth , trHeight );
5668
5669      if( bCodeChroma )
5670      {
5671        m_pcQTTempTComYuv[uiQTTempAccessLayer].copyPartToPartChroma( pcResi, uiAbsPartIdx, 1 << uiLog2TrSizeC, 1 << uiLog2TrSizeC );
5672      }
5673    }
5674    else
5675    {
5676      UInt    uiNumCoeffPerAbsPartIdxIncrement = pcCU->getSlice()->getSPS()->getMaxCUWidth() * pcCU->getSlice()->getSPS()->getMaxCUHeight() >> ( pcCU->getSlice()->getSPS()->getMaxCUDepth() << 1 );
5677      UInt    uiNumCoeffY = ( 1 << ( uiLog2TrSize << 1 ) );
5678      TCoeff* pcCoeffSrcY = m_ppcQTTempCoeffY [uiQTTempAccessLayer] +  uiNumCoeffPerAbsPartIdxIncrement * uiAbsPartIdx;
5679      TCoeff* pcCoeffDstY = pcCU->getCoeffY() + uiNumCoeffPerAbsPartIdxIncrement * uiAbsPartIdx;
5680      ::memcpy( pcCoeffDstY, pcCoeffSrcY, sizeof( TCoeff ) * uiNumCoeffY );
5681#if ADAPTIVE_QP_SELECTION
5682      Int* pcArlCoeffSrcY = m_ppcQTTempArlCoeffY [uiQTTempAccessLayer] +  uiNumCoeffPerAbsPartIdxIncrement * uiAbsPartIdx;
5683      Int* pcArlCoeffDstY = pcCU->getArlCoeffY() + uiNumCoeffPerAbsPartIdxIncrement * uiAbsPartIdx;
5684      ::memcpy( pcArlCoeffDstY, pcArlCoeffSrcY, sizeof( Int ) * uiNumCoeffY );
5685#endif
5686      if( bCodeChroma )
5687      {
5688        UInt    uiNumCoeffC = ( 1 << ( uiLog2TrSizeC << 1 ) );
5689        TCoeff* pcCoeffSrcU = m_ppcQTTempCoeffCb[uiQTTempAccessLayer] + (uiNumCoeffPerAbsPartIdxIncrement * uiAbsPartIdx>>2);
5690        TCoeff* pcCoeffSrcV = m_ppcQTTempCoeffCr[uiQTTempAccessLayer] + (uiNumCoeffPerAbsPartIdxIncrement * uiAbsPartIdx>>2);
5691        TCoeff* pcCoeffDstU = pcCU->getCoeffCb() + (uiNumCoeffPerAbsPartIdxIncrement * uiAbsPartIdx>>2);
5692        TCoeff* pcCoeffDstV = pcCU->getCoeffCr() + (uiNumCoeffPerAbsPartIdxIncrement * uiAbsPartIdx>>2);
5693        ::memcpy( pcCoeffDstU, pcCoeffSrcU, sizeof( TCoeff ) * uiNumCoeffC );
5694        ::memcpy( pcCoeffDstV, pcCoeffSrcV, sizeof( TCoeff ) * uiNumCoeffC );
5695#if ADAPTIVE_QP_SELECTION
5696        Int* pcArlCoeffSrcU = m_ppcQTTempArlCoeffCb[uiQTTempAccessLayer] + (uiNumCoeffPerAbsPartIdxIncrement * uiAbsPartIdx>>2);
5697        Int* pcArlCoeffSrcV = m_ppcQTTempArlCoeffCr[uiQTTempAccessLayer] + (uiNumCoeffPerAbsPartIdxIncrement * uiAbsPartIdx>>2);
5698        Int* pcArlCoeffDstU = pcCU->getArlCoeffCb() + (uiNumCoeffPerAbsPartIdxIncrement * uiAbsPartIdx>>2);
5699        Int* pcArlCoeffDstV = pcCU->getArlCoeffCr() + (uiNumCoeffPerAbsPartIdxIncrement * uiAbsPartIdx>>2);
5700        ::memcpy( pcArlCoeffDstU, pcArlCoeffSrcU, sizeof( Int ) * uiNumCoeffC );
5701        ::memcpy( pcArlCoeffDstV, pcArlCoeffSrcV, sizeof( Int ) * uiNumCoeffC );
5702#endif
5703      }
5704    }
5705  }
5706  else
5707  {
5708    const UInt uiQPartNumSubdiv = pcCU->getPic()->getNumPartInCU() >> ((uiDepth + 1 ) << 1);
5709    for( UInt ui = 0; ui < 4; ++ui )
5710    {
5711      UInt nsAddr = uiAbsPartIdx + ui * uiQPartNumSubdiv;
5712      xSetResidualQTData( pcCU, ui, uiAbsPartIdx + ui * uiQPartNumSubdiv, nsAddr, pcResi, uiDepth + 1, bSpatial );
5713    }
5714  }
5715}
5716
5717UInt TEncSearch::xModeBitsIntra( TComDataCU* pcCU, UInt uiMode, UInt uiPU, UInt uiPartOffset, UInt uiDepth, UInt uiInitTrDepth )
5718{
5719  if( m_bUseSBACRD )
5720  {
5721    // Reload only contexts required for coding intra mode information
5722    m_pcRDGoOnSbacCoder->loadIntraDirModeLuma( m_pppcRDSbacCoder[uiDepth][CI_CURR_BEST] );
5723  }
5724 
5725  pcCU->setLumaIntraDirSubParts ( uiMode, uiPartOffset, uiDepth + uiInitTrDepth );
5726 
5727  m_pcEntropyCoder->resetBits();
5728  m_pcEntropyCoder->encodeIntraDirModeLuma ( pcCU, uiPartOffset);
5729 
5730  return m_pcEntropyCoder->getNumberOfWrittenBits();
5731}
5732
5733UInt TEncSearch::xUpdateCandList( UInt uiMode, Double uiCost, UInt uiFastCandNum, UInt * CandModeList, Double * CandCostList )
5734{
5735  UInt i;
5736  UInt shift=0;
5737 
5738  while ( shift<uiFastCandNum && uiCost<CandCostList[ uiFastCandNum-1-shift ] ) shift++;
5739 
5740  if( shift!=0 )
5741  {
5742    for(i=1; i<shift; i++)
5743    {
5744      CandModeList[ uiFastCandNum-i ] = CandModeList[ uiFastCandNum-1-i ];
5745      CandCostList[ uiFastCandNum-i ] = CandCostList[ uiFastCandNum-1-i ];
5746    }
5747    CandModeList[ uiFastCandNum-shift ] = uiMode;
5748    CandCostList[ uiFastCandNum-shift ] = uiCost;
5749    return 1;
5750  }
5751 
5752  return 0;
5753}
5754
5755/** add inter-prediction syntax elements for a CU block
5756 * \param pcCU
5757 * \param uiQp
5758 * \param uiTrMode
5759 * \param ruiBits
5760 * \param rpcYuvRec
5761 * \param pcYuvPred
5762 * \param rpcYuvResi
5763 * \returns Void
5764 */
5765Void  TEncSearch::xAddSymbolBitsInter( TComDataCU* pcCU, UInt uiQp, UInt uiTrMode, UInt& ruiBits, TComYuv*& rpcYuvRec, TComYuv*pcYuvPred, TComYuv*& rpcYuvResi )
5766{
5767  if(pcCU->getMergeFlag( 0 ) && pcCU->getPartitionSize( 0 ) == SIZE_2Nx2N && !pcCU->getQtRootCbf( 0 ))
5768  {
5769    pcCU->setSkipFlagSubParts( true, 0, pcCU->getDepth(0) );
5770
5771    m_pcEntropyCoder->resetBits();
5772    if(pcCU->getSlice()->getPPS()->getTransquantBypassEnableFlag())
5773    {
5774      m_pcEntropyCoder->encodeCUTransquantBypassFlag(pcCU, 0, true);
5775    }
5776    m_pcEntropyCoder->encodeSkipFlag(pcCU, 0, true);
5777    m_pcEntropyCoder->encodeMergeIndex(pcCU, 0, true);
5778    ruiBits += m_pcEntropyCoder->getNumberOfWrittenBits();
5779  }
5780  else
5781  {
5782    m_pcEntropyCoder->resetBits();
5783    if(pcCU->getSlice()->getPPS()->getTransquantBypassEnableFlag())
5784    {
5785      m_pcEntropyCoder->encodeCUTransquantBypassFlag(pcCU, 0, true);
5786    }
5787    m_pcEntropyCoder->encodeSkipFlag ( pcCU, 0, true );
5788    m_pcEntropyCoder->encodePredMode( pcCU, 0, true );
5789    m_pcEntropyCoder->encodePartSize( pcCU, 0, pcCU->getDepth(0), true );
5790    m_pcEntropyCoder->encodePredInfo( pcCU, 0, true );
5791    Bool bDummy = false;
5792    m_pcEntropyCoder->encodeCoeff   ( pcCU, 0, pcCU->getDepth(0), pcCU->getWidth(0), pcCU->getHeight(0), bDummy );
5793   
5794    ruiBits += m_pcEntropyCoder->getNumberOfWrittenBits();
5795  }
5796}
5797
5798/**
5799 * \brief Generate half-sample interpolated block
5800 *
5801 * \param pattern Reference picture ROI
5802 * \param biPred    Flag indicating whether block is for biprediction
5803 */
5804Void TEncSearch::xExtDIFUpSamplingH( TComPattern* pattern, Bool biPred )
5805{
5806  Int width      = pattern->getROIYWidth();
5807  Int height     = pattern->getROIYHeight();
5808  Int srcStride  = pattern->getPatternLStride();
5809 
5810  Int intStride = m_filteredBlockTmp[0].getStride();
5811  Int dstStride = m_filteredBlock[0][0].getStride();
5812  Short *intPtr;
5813  Short *dstPtr;
5814  Int filterSize = NTAPS_LUMA;
5815  Int halfFilterSize = (filterSize>>1);
5816  Pel *srcPtr = pattern->getROIY() - halfFilterSize*srcStride - 1;
5817 
5818  m_if.filterHorLuma(srcPtr, srcStride, m_filteredBlockTmp[0].getLumaAddr(), intStride, width+1, height+filterSize, 0, false);
5819  m_if.filterHorLuma(srcPtr, srcStride, m_filteredBlockTmp[2].getLumaAddr(), intStride, width+1, height+filterSize, 2, false);
5820 
5821  intPtr = m_filteredBlockTmp[0].getLumaAddr() + halfFilterSize * intStride + 1; 
5822  dstPtr = m_filteredBlock[0][0].getLumaAddr();
5823  m_if.filterVerLuma(intPtr, intStride, dstPtr, dstStride, width+0, height+0, 0, false, true);
5824 
5825  intPtr = m_filteredBlockTmp[0].getLumaAddr() + (halfFilterSize-1) * intStride + 1; 
5826  dstPtr = m_filteredBlock[2][0].getLumaAddr();
5827  m_if.filterVerLuma(intPtr, intStride, dstPtr, dstStride, width+0, height+1, 2, false, true);
5828 
5829  intPtr = m_filteredBlockTmp[2].getLumaAddr() + halfFilterSize * intStride;
5830  dstPtr = m_filteredBlock[0][2].getLumaAddr();
5831  m_if.filterVerLuma(intPtr, intStride, dstPtr, dstStride, width+1, height+0, 0, false, true);
5832 
5833  intPtr = m_filteredBlockTmp[2].getLumaAddr() + (halfFilterSize-1) * intStride;
5834  dstPtr = m_filteredBlock[2][2].getLumaAddr();
5835  m_if.filterVerLuma(intPtr, intStride, dstPtr, dstStride, width+1, height+1, 2, false, true);
5836}
5837
5838/**
5839 * \brief Generate quarter-sample interpolated blocks
5840 *
5841 * \param pattern    Reference picture ROI
5842 * \param halfPelRef Half-pel mv
5843 * \param biPred     Flag indicating whether block is for biprediction
5844 */
5845Void TEncSearch::xExtDIFUpSamplingQ( TComPattern* pattern, TComMv halfPelRef, Bool biPred )
5846{
5847  Int width      = pattern->getROIYWidth();
5848  Int height     = pattern->getROIYHeight();
5849  Int srcStride  = pattern->getPatternLStride();
5850 
5851  Pel *srcPtr;
5852  Int intStride = m_filteredBlockTmp[0].getStride();
5853  Int dstStride = m_filteredBlock[0][0].getStride();
5854  Short *intPtr;
5855  Short *dstPtr;
5856  Int filterSize = NTAPS_LUMA;
5857 
5858  Int halfFilterSize = (filterSize>>1);
5859
5860  Int extHeight = (halfPelRef.getVer() == 0) ? height + filterSize : height + filterSize-1;
5861 
5862  // Horizontal filter 1/4
5863  srcPtr = pattern->getROIY() - halfFilterSize * srcStride - 1;
5864  intPtr = m_filteredBlockTmp[1].getLumaAddr();
5865  if (halfPelRef.getVer() > 0)
5866  {
5867    srcPtr += srcStride;
5868  }
5869  if (halfPelRef.getHor() >= 0)
5870  {
5871    srcPtr += 1;
5872  }
5873  m_if.filterHorLuma(srcPtr, srcStride, intPtr, intStride, width, extHeight, 1, false);
5874 
5875  // Horizontal filter 3/4
5876  srcPtr = pattern->getROIY() - halfFilterSize*srcStride - 1;
5877  intPtr = m_filteredBlockTmp[3].getLumaAddr();
5878  if (halfPelRef.getVer() > 0)
5879  {
5880    srcPtr += srcStride;
5881  }
5882  if (halfPelRef.getHor() > 0)
5883  {
5884    srcPtr += 1;
5885  }
5886  m_if.filterHorLuma(srcPtr, srcStride, intPtr, intStride, width, extHeight, 3, false);       
5887 
5888  // Generate @ 1,1
5889  intPtr = m_filteredBlockTmp[1].getLumaAddr() + (halfFilterSize-1) * intStride;
5890  dstPtr = m_filteredBlock[1][1].getLumaAddr();
5891  if (halfPelRef.getVer() == 0)
5892  {
5893    intPtr += intStride;
5894  }
5895  m_if.filterVerLuma(intPtr, intStride, dstPtr, dstStride, width, height, 1, false, true);
5896 
5897  // Generate @ 3,1
5898  intPtr = m_filteredBlockTmp[1].getLumaAddr() + (halfFilterSize-1) * intStride;
5899  dstPtr = m_filteredBlock[3][1].getLumaAddr();
5900  m_if.filterVerLuma(intPtr, intStride, dstPtr, dstStride, width, height, 3, false, true);
5901 
5902  if (halfPelRef.getVer() != 0)
5903  {
5904    // Generate @ 2,1
5905    intPtr = m_filteredBlockTmp[1].getLumaAddr() + (halfFilterSize-1) * intStride;
5906    dstPtr = m_filteredBlock[2][1].getLumaAddr();
5907    if (halfPelRef.getVer() == 0)
5908    {
5909      intPtr += intStride;
5910    }
5911    m_if.filterVerLuma(intPtr, intStride, dstPtr, dstStride, width, height, 2, false, true);
5912   
5913    // Generate @ 2,3
5914    intPtr = m_filteredBlockTmp[3].getLumaAddr() + (halfFilterSize-1) * intStride;
5915    dstPtr = m_filteredBlock[2][3].getLumaAddr();
5916    if (halfPelRef.getVer() == 0)
5917    {
5918      intPtr += intStride;
5919    }
5920    m_if.filterVerLuma(intPtr, intStride, dstPtr, dstStride, width, height, 2, false, true);
5921  }
5922  else
5923  {
5924    // Generate @ 0,1
5925    intPtr = m_filteredBlockTmp[1].getLumaAddr() + halfFilterSize * intStride;
5926    dstPtr = m_filteredBlock[0][1].getLumaAddr();
5927    m_if.filterVerLuma(intPtr, intStride, dstPtr, dstStride, width, height, 0, false, true);
5928   
5929    // Generate @ 0,3
5930    intPtr = m_filteredBlockTmp[3].getLumaAddr() + halfFilterSize * intStride;
5931    dstPtr = m_filteredBlock[0][3].getLumaAddr();
5932    m_if.filterVerLuma(intPtr, intStride, dstPtr, dstStride, width, height, 0, false, true);
5933  }
5934 
5935  if (halfPelRef.getHor() != 0)
5936  {
5937    // Generate @ 1,2
5938    intPtr = m_filteredBlockTmp[2].getLumaAddr() + (halfFilterSize-1) * intStride;
5939    dstPtr = m_filteredBlock[1][2].getLumaAddr();
5940    if (halfPelRef.getHor() > 0)
5941    {
5942      intPtr += 1;
5943    }
5944    if (halfPelRef.getVer() >= 0)
5945    {
5946      intPtr += intStride;
5947    }
5948    m_if.filterVerLuma(intPtr, intStride, dstPtr, dstStride, width, height, 1, false, true);
5949   
5950    // Generate @ 3,2
5951    intPtr = m_filteredBlockTmp[2].getLumaAddr() + (halfFilterSize-1) * intStride;
5952    dstPtr = m_filteredBlock[3][2].getLumaAddr();
5953    if (halfPelRef.getHor() > 0)
5954    {
5955      intPtr += 1;
5956    }
5957    if (halfPelRef.getVer() > 0)
5958    {
5959      intPtr += intStride;
5960    }
5961    m_if.filterVerLuma(intPtr, intStride, dstPtr, dstStride, width, height, 3, false, true); 
5962  }
5963  else
5964  {
5965    // Generate @ 1,0
5966    intPtr = m_filteredBlockTmp[0].getLumaAddr() + (halfFilterSize-1) * intStride + 1;
5967    dstPtr = m_filteredBlock[1][0].getLumaAddr();
5968    if (halfPelRef.getVer() >= 0)
5969    {
5970      intPtr += intStride;
5971    }
5972    m_if.filterVerLuma(intPtr, intStride, dstPtr, dstStride, width, height, 1, false, true);
5973   
5974    // Generate @ 3,0
5975    intPtr = m_filteredBlockTmp[0].getLumaAddr() + (halfFilterSize-1) * intStride + 1;
5976    dstPtr = m_filteredBlock[3][0].getLumaAddr();
5977    if (halfPelRef.getVer() > 0)
5978    {
5979      intPtr += intStride;
5980    }
5981    m_if.filterVerLuma(intPtr, intStride, dstPtr, dstStride, width, height, 3, false, true);
5982  }
5983 
5984  // Generate @ 1,3
5985  intPtr = m_filteredBlockTmp[3].getLumaAddr() + (halfFilterSize-1) * intStride;
5986  dstPtr = m_filteredBlock[1][3].getLumaAddr();
5987  if (halfPelRef.getVer() == 0)
5988  {
5989    intPtr += intStride;
5990  }
5991  m_if.filterVerLuma(intPtr, intStride, dstPtr, dstStride, width, height, 1, false, true);
5992 
5993  // Generate @ 3,3
5994  intPtr = m_filteredBlockTmp[3].getLumaAddr() + (halfFilterSize-1) * intStride;
5995  dstPtr = m_filteredBlock[3][3].getLumaAddr();
5996  m_if.filterVerLuma(intPtr, intStride, dstPtr, dstStride, width, height, 3, false, true);
5997}
5998
5999/** set wp tables
6000 * \param TComDataCU* pcCU
6001 * \param iRefIdx
6002 * \param eRefPicListCur
6003 * \returns Void
6004 */
6005Void  TEncSearch::setWpScalingDistParam( TComDataCU* pcCU, Int iRefIdx, RefPicList eRefPicListCur )
6006{
6007  if ( iRefIdx<0 )
6008  {
6009    m_cDistParam.bApplyWeight = false;
6010    return;
6011  }
6012
6013  TComSlice       *pcSlice  = pcCU->getSlice();
6014  TComPPS         *pps      = pcCU->getSlice()->getPPS();
6015  wpScalingParam  *wp0 , *wp1;
6016  m_cDistParam.bApplyWeight = ( pcSlice->getSliceType()==P_SLICE && pps->getUseWP() ) || ( pcSlice->getSliceType()==B_SLICE && pps->getWPBiPred() ) ;
6017  if ( !m_cDistParam.bApplyWeight ) return;
6018
6019  Int iRefIdx0 = ( eRefPicListCur == REF_PIC_LIST_0 ) ? iRefIdx : (-1);
6020  Int iRefIdx1 = ( eRefPicListCur == REF_PIC_LIST_1 ) ? iRefIdx : (-1);
6021
6022  getWpScaling( pcCU, iRefIdx0, iRefIdx1, wp0 , wp1 );
6023
6024  if ( iRefIdx0 < 0 ) wp0 = NULL;
6025  if ( iRefIdx1 < 0 ) wp1 = NULL;
6026
6027  m_cDistParam.wpCur  = NULL;
6028
6029  if ( eRefPicListCur == REF_PIC_LIST_0 )
6030  {
6031    m_cDistParam.wpCur = wp0;
6032  }
6033  else
6034  {
6035    m_cDistParam.wpCur = wp1;
6036  }
6037}
6038
6039#if REF_IDX_ME_ZEROMV
6040Void TEncSearch::xPatternSearchFracDIFMv0(TComDataCU* pcCU,
6041                                          TComPattern* pcPatternKey,
6042                                          Pel* piRefY,
6043                                          Int iRefStride,
6044                                          TComMv* pcMvInt,
6045                                          TComMv& rcMvHalf,
6046                                          TComMv& rcMvQter,
6047                                          UInt& ruiCost,
6048                                          Bool biPred
6049                                          )
6050{
6051  assert(pcMvInt->getHor() == 0 && pcMvInt->getVer() == 0);
6052  Int         iOffset    = pcMvInt->getHor() + pcMvInt->getVer() * iRefStride;
6053  m_pcRdCost->setDistParam( pcPatternKey, piRefY + iOffset, iRefStride, 1, m_cDistParam, m_pcEncCfg->getUseHADME() );
6054  m_pcRdCost->setCostScale ( 2 );
6055  setDistParamComp(0);
6056  ruiCost = m_cDistParam.DistFunc( &m_cDistParam );  //SATD
6057  ruiCost += m_pcRdCost->getCost( pcMvInt->getHor(), pcMvInt->getVer() );  //SATD rdCost
6058  rcMvHalf.setZero();
6059  rcMvQter.setZero();
6060}
6061#endif
6062
6063#if ENCODER_FAST_MODE
6064Bool TEncSearch::predInterSearchILRUni( TComDataCU* pcCU, TComYuv* pcOrgYuv, TComYuv*& rpcPredYuv, TComYuv*& rpcResiYuv, TComYuv*& rpcRecoYuv, UInt refLayerId )
6065{
6066    rpcPredYuv->clear();
6067    rpcRecoYuv->clear();
6068
6069    Int           iNumPredDir = pcCU->getSlice()->isInterP() ? 1 : 2;
6070
6071    TComMv        cMv[2];
6072    TComMv        cMvPred[2][33];
6073    TComMv        cMvTemp[2][33];
6074    TComMv        TempMv;
6075
6076    Int           iRefIdx[2]={0,0};
6077
6078    Int           aaiMvpIdx[2][33];
6079    Int           aaiMvpNum[2][33];
6080
6081    UInt          uiMbBits[3] = {1, 1, 0};
6082    UInt          uiLastMode = 0;
6083
6084    UInt          uiCost[2]   = { MAX_UINT, MAX_UINT };     //uni, rdCost
6085    UInt          uiCostTemp;
6086    UInt          biPDistTemp = MAX_INT;
6087    UInt          uiBitsTemp;
6088
6089    PartSize      ePartSize = pcCU->getPartitionSize( 0 );  //2Nx2N
6090    Int           iPartIdx  = 0;                            //one PU in CU
6091    UInt          uiPartAddr;
6092    Int           iRoiWidth, iRoiHeight;
6093    Bool          bILRSearched = false;
6094
6095    xGetBlkBits( ePartSize, pcCU->getSlice()->isInterP(), iPartIdx, uiLastMode, uiMbBits);
6096    pcCU->getPartIndexAndSize( iPartIdx, uiPartAddr, iRoiWidth, iRoiHeight );
6097
6098    for( Int iRefList = 0; iRefList < iNumPredDir; iRefList++)  //list
6099    {
6100        if(bILRSearched)
6101           continue;
6102
6103        RefPicList  eRefPicList = ( iRefList ? REF_PIC_LIST_1 : REF_PIC_LIST_0 );
6104
6105        Int  iRefIdxTemp = -1;
6106        Bool foundILR    = false;
6107
6108        for( Int refIdx = 0; refIdx < pcCU->getSlice()->getNumRefIdx(eRefPicList); refIdx++ )
6109        {
6110            if( pcCU->getSlice()->getRefPic(eRefPicList, refIdx)->isILR(pcCU->getLayerId()) && pcCU->getSlice()->getRefPic(eRefPicList, refIdx)->getLayerId() == refLayerId )
6111            {
6112                iRefIdxTemp = refIdx;
6113                foundILR    = true;
6114                bILRSearched = true;
6115                break;
6116            }
6117        }
6118
6119        if(!foundILR)  //no ILR in eRefPiclist
6120        {
6121            continue; 
6122        }
6123
6124        uiBitsTemp = uiMbBits[iRefList];
6125        if ( pcCU->getSlice()->getNumRefIdx(eRefPicList) > 1 ) 
6126        { 
6127            uiBitsTemp += iRefIdxTemp+1; 
6128            if ( iRefIdxTemp == pcCU->getSlice()->getNumRefIdx(eRefPicList)-1 ) uiBitsTemp--; 
6129        }
6130
6131        xEstimateMvPredAMVP( pcCU, pcOrgYuv, iPartIdx, eRefPicList, iRefIdxTemp, cMvPred[iRefList][iRefIdxTemp], false, &biPDistTemp);
6132        aaiMvpIdx[iRefList][iRefIdxTemp] = pcCU->getMVPIdx(eRefPicList, uiPartAddr);
6133        aaiMvpNum[iRefList][iRefIdxTemp] = pcCU->getMVPNum(eRefPicList, uiPartAddr);
6134
6135        uiBitsTemp += m_auiMVPIdxCost[aaiMvpIdx[iRefList][iRefIdxTemp]][AMVP_MAX_NUM_CANDS];
6136
6137        xMotionEstimation ( pcCU, pcOrgYuv, iPartIdx, eRefPicList, &cMvPred[iRefList][iRefIdxTemp], iRefIdxTemp, cMvTemp[iRefList][iRefIdxTemp], uiBitsTemp, uiCostTemp );
6138        xCheckBestMVP(pcCU, eRefPicList, cMvTemp[iRefList][iRefIdxTemp], cMvPred[iRefList][iRefIdxTemp], aaiMvpIdx[iRefList][iRefIdxTemp], uiBitsTemp, uiCostTemp);
6139
6140        if( uiCostTemp < uiCost[iRefList] )
6141        {
6142            uiCost[iRefList] = uiCostTemp;
6143
6144            cMv[iRefList]     = cMvTemp[iRefList][iRefIdxTemp];
6145            iRefIdx[iRefList] = iRefIdxTemp;
6146
6147            pcCU->getCUMvField(eRefPicList)->setAllMv( cMv[iRefList], ePartSize, uiPartAddr, 0, iPartIdx );
6148            pcCU->getCUMvField(eRefPicList)->setAllRefIdx( iRefIdx[iRefList], ePartSize, uiPartAddr, 0, iPartIdx );
6149        }
6150    }
6151
6152    if( uiCost[0] == MAX_UINT && uiCost[1] == MAX_UINT )  //no ILR in both list0 and list1
6153    {
6154        return false;
6155    }
6156
6157    //  Clear Motion Field
6158    pcCU->getCUMvField(REF_PIC_LIST_0)->setAllMvField( TComMvField(), ePartSize, uiPartAddr, 0, iPartIdx ); 
6159    pcCU->getCUMvField(REF_PIC_LIST_1)->setAllMvField( TComMvField(), ePartSize, uiPartAddr, 0, iPartIdx ); 
6160    pcCU->getCUMvField(REF_PIC_LIST_0)->setAllMvd    ( TComMv(),      ePartSize, uiPartAddr, 0, iPartIdx ); 
6161    pcCU->getCUMvField(REF_PIC_LIST_1)->setAllMvd    ( TComMv(),      ePartSize, uiPartAddr, 0, iPartIdx );
6162
6163    pcCU->setMVPIdxSubParts( -1, REF_PIC_LIST_0, uiPartAddr, iPartIdx, pcCU->getDepth(uiPartAddr)); 
6164    pcCU->setMVPNumSubParts( -1, REF_PIC_LIST_0, uiPartAddr, iPartIdx, pcCU->getDepth(uiPartAddr)); 
6165    pcCU->setMVPIdxSubParts( -1, REF_PIC_LIST_1, uiPartAddr, iPartIdx, pcCU->getDepth(uiPartAddr)); 
6166    pcCU->setMVPNumSubParts( -1, REF_PIC_LIST_1, uiPartAddr, iPartIdx, pcCU->getDepth(uiPartAddr));
6167
6168    if( uiCost[0] <= uiCost[1] )  //list0 ILR
6169    {
6170        pcCU->getCUMvField(REF_PIC_LIST_0)->setAllMv    ( cMv[0], ePartSize, uiPartAddr, 0, iPartIdx );
6171        pcCU->getCUMvField(REF_PIC_LIST_0)->setAllRefIdx( iRefIdx[0], ePartSize, uiPartAddr, 0, iPartIdx );
6172
6173        TempMv = cMv[0] - cMvPred[0][iRefIdx[0]]; 
6174        pcCU->getCUMvField(REF_PIC_LIST_0)->setAllMvd( TempMv, ePartSize, uiPartAddr, 0, iPartIdx );
6175
6176        pcCU->setInterDirSubParts( 1, uiPartAddr, iPartIdx, pcCU->getDepth(0) );
6177
6178        pcCU->setMVPIdxSubParts( aaiMvpIdx[0][iRefIdx[0]], REF_PIC_LIST_0, uiPartAddr, iPartIdx, pcCU->getDepth(uiPartAddr)); 
6179        pcCU->setMVPNumSubParts( aaiMvpNum[0][iRefIdx[0]], REF_PIC_LIST_0, uiPartAddr, iPartIdx, pcCU->getDepth(uiPartAddr));
6180    }
6181    else if( uiCost[1] < uiCost[0] )  //list1 ILR
6182    {
6183        pcCU->getCUMvField(REF_PIC_LIST_1)->setAllMv    ( cMv[1], ePartSize, uiPartAddr, 0, iPartIdx );
6184        pcCU->getCUMvField(REF_PIC_LIST_1)->setAllRefIdx( iRefIdx[1], ePartSize, uiPartAddr, 0, iPartIdx );
6185
6186        TempMv = cMv[1] - cMvPred[1][iRefIdx[1]]; 
6187        pcCU->getCUMvField(REF_PIC_LIST_1)->setAllMvd( TempMv, ePartSize, uiPartAddr, 0, iPartIdx );
6188
6189        pcCU->setInterDirSubParts( 2, uiPartAddr, iPartIdx, pcCU->getDepth(0) );
6190
6191        pcCU->setMVPIdxSubParts( aaiMvpIdx[1][iRefIdx[1]], REF_PIC_LIST_1, uiPartAddr, iPartIdx, pcCU->getDepth(uiPartAddr)); 
6192        pcCU->setMVPNumSubParts( aaiMvpNum[1][iRefIdx[1]], REF_PIC_LIST_1, uiPartAddr, iPartIdx, pcCU->getDepth(uiPartAddr));
6193    }
6194    else
6195    {
6196        assert(0);
6197    }
6198
6199    pcCU->setMergeFlagSubParts( false, uiPartAddr, iPartIdx, pcCU->getDepth( uiPartAddr ) );
6200
6201    motionCompensation ( pcCU, rpcPredYuv, REF_PIC_LIST_X, iPartIdx );
6202    setWpScalingDistParam( pcCU, -1, REF_PIC_LIST_X );
6203
6204    return true;
6205}
6206#endif
6207
6208//! \}
Note: See TracBrowser for help on using the repository browser.