source: 3DVCSoftware/branches/HTM-15.2-dev/source/Lib/TLibCommon/TComDataCU.cpp @ 1370

Last change on this file since 1370 was 1362, checked in by tech, 9 years ago

Align macros

  • Property svn:eol-style set to native
File size: 209.0 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-2015, 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     TComDataCU.cpp
35    \brief    CU data structure
36    \todo     not all entities are documented
37*/
38
39#include "TComDataCU.h"
40#include "TComTU.h"
41#include "TComPic.h"
42
43//! \ingroup TLibCommon
44//! \{
45
46// ====================================================================================================================
47// Constructor / destructor / create / destroy
48// ====================================================================================================================
49
50TComDataCU::TComDataCU()
51{
52  m_pcPic              = NULL;
53  m_pcSlice            = NULL;
54  m_puhDepth           = NULL;
55
56  m_skipFlag           = NULL;
57#if NH_3D_DIS
58  m_bDISFlag           = NULL;
59  m_ucDISType          = NULL;
60#endif
61  m_pePartSize         = NULL;
62  m_pePredMode         = NULL;
63  m_CUTransquantBypass = NULL;
64  m_puhWidth           = NULL;
65  m_puhHeight          = NULL;
66  m_phQP               = NULL;
67  m_ChromaQpAdj        = NULL;
68  m_pbMergeFlag        = NULL;
69  m_puhMergeIndex      = NULL;
70  for(UInt i=0; i<MAX_NUM_CHANNEL_TYPE; i++)
71  {
72    m_puhIntraDir[i]     = NULL;
73  }
74  m_puhInterDir        = NULL;
75  m_puhTrIdx           = NULL;
76
77  for (UInt comp=0; comp<MAX_NUM_COMPONENT; comp++)
78  {
79    m_puhCbf[comp]                        = NULL;
80    m_crossComponentPredictionAlpha[comp] = NULL;
81    m_puhTransformSkip[comp]              = NULL;
82    m_pcTrCoeff[comp]                     = NULL;
83#if ADAPTIVE_QP_SELECTION
84    m_pcArlCoeff[comp]                    = NULL;
85#endif
86    m_pcIPCMSample[comp]                  = NULL;
87    m_explicitRdpcmMode[comp]             = NULL;
88  }
89#if ADAPTIVE_QP_SELECTION
90  m_ArlCoeffIsAliasedAllocation = false;
91#endif
92  m_pbIPCMFlag         = NULL;
93
94  m_pCtuAboveLeft      = NULL;
95  m_pCtuAboveRight     = NULL;
96  m_pCtuAbove          = NULL;
97  m_pCtuLeft           = NULL;
98
99  for(UInt i=0; i<NUM_REF_PIC_LIST_01; i++)
100  {
101    m_apcCUColocated[i]  = NULL;
102    m_apiMVPIdx[i]       = NULL;
103    m_apiMVPNum[i]       = NULL;
104  }
105
106#if NH_3D_DMM
107  for( Int i = 0; i < NUM_DMM; i++ )
108  {
109    m_dmmDeltaDC[i][0] = NULL; 
110    m_dmmDeltaDC[i][1] = NULL;
111  }
112  m_dmm1WedgeTabIdx = NULL;
113#endif
114#if NH_3D_SDC_INTRA
115  m_pbSDCFlag             = NULL;
116  m_apSegmentDCOffset[0]  = NULL;
117  m_apSegmentDCOffset[1]  = NULL;
118#endif
119
120  m_bDecSubCu          = false;
121
122#if NH_3D_NBDV
123  m_pDvInfo              = NULL;
124#endif
125#if NH_3D_VSP
126  m_piVSPFlag            = NULL;
127#endif
128#if NH_3D_SPIVMP
129  m_pbSPIVMPFlag         = NULL;
130#endif
131#if NH_3D_ARP
132  m_puhARPW              = NULL;
133#endif
134#if NH_3D_IC
135  m_pbICFlag             = NULL;
136#endif
137#if NH_3D_DBBP
138  m_pbDBBPFlag         = NULL;
139#endif
140
141}
142
143TComDataCU::~TComDataCU()
144{
145}
146
147Void TComDataCU::create( ChromaFormat chromaFormatIDC, UInt uiNumPartition, UInt uiWidth, UInt uiHeight, Bool bDecSubCu, Int unitSize
148#if ADAPTIVE_QP_SELECTION
149                        , TCoeff *pParentARLBuffer
150#endif
151                        )
152{
153  m_bDecSubCu = bDecSubCu;
154
155  m_pcPic              = NULL;
156  m_pcSlice            = NULL;
157  m_uiNumPartition     = uiNumPartition;
158  m_unitSize = unitSize;
159
160  if ( !bDecSubCu )
161  {
162    m_phQP               = (SChar*    )xMalloc(SChar,    uiNumPartition);
163    m_puhDepth           = (UChar*    )xMalloc(UChar,    uiNumPartition);
164    m_puhWidth           = (UChar*    )xMalloc(UChar,    uiNumPartition);
165    m_puhHeight          = (UChar*    )xMalloc(UChar,    uiNumPartition);
166
167    m_ChromaQpAdj        = new UChar[ uiNumPartition ];
168    m_skipFlag           = new Bool[ uiNumPartition ];
169#if NH_3D_DIS
170    m_bDISFlag           = new Bool[ uiNumPartition ];
171    m_ucDISType          = (UChar*)xMalloc(UChar, uiNumPartition);
172#endif
173    m_pePartSize         = new SChar[ uiNumPartition ];
174    memset( m_pePartSize, NUMBER_OF_PART_SIZES,uiNumPartition * sizeof( *m_pePartSize ) );
175    m_pePredMode         = new SChar[ uiNumPartition ];
176    m_CUTransquantBypass = new Bool[ uiNumPartition ];
177
178    m_pbMergeFlag        = (Bool*  )xMalloc(Bool,   uiNumPartition);
179    m_puhMergeIndex      = (UChar* )xMalloc(UChar,  uiNumPartition);
180#if NH_3D_VSP
181    m_piVSPFlag          = (SChar* )xMalloc(SChar, uiNumPartition);
182#endif
183#if NH_3D_SPIVMP
184    m_pbSPIVMPFlag       = (Bool*  )xMalloc(Bool,   uiNumPartition);
185#endif
186
187    for (UInt ch=0; ch<MAX_NUM_CHANNEL_TYPE; ch++)
188    {
189      m_puhIntraDir[ch] = (UChar* )xMalloc(UChar,  uiNumPartition);
190    }
191    m_puhInterDir        = (UChar* )xMalloc(UChar,  uiNumPartition);
192
193    m_puhTrIdx           = (UChar* )xMalloc(UChar,  uiNumPartition);
194
195    for(UInt i=0; i<NUM_REF_PIC_LIST_01; i++)
196    {
197      const RefPicList rpl=RefPicList(i);
198      m_apiMVPIdx[rpl]       = new SChar[ uiNumPartition ];
199      m_apiMVPNum[rpl]       = new SChar[ uiNumPartition ];
200      memset( m_apiMVPIdx[rpl], -1,uiNumPartition * sizeof( SChar ) );
201    }
202
203#if NH_3D_NBDV
204    m_pDvInfo            = (DisInfo* )xMalloc(DisInfo,  uiNumPartition);
205#endif
206
207
208    for (UInt comp=0; comp<MAX_NUM_COMPONENT; comp++)
209    {
210      const ComponentID compID = ComponentID(comp);
211      const UInt chromaShift = getComponentScaleX(compID, chromaFormatIDC) + getComponentScaleY(compID, chromaFormatIDC);
212      const UInt totalSize   = (uiWidth * uiHeight) >> chromaShift;
213
214      m_crossComponentPredictionAlpha[compID] = (SChar* )xMalloc(SChar,  uiNumPartition);
215      m_puhTransformSkip[compID]              = (UChar* )xMalloc(UChar,  uiNumPartition);
216      m_explicitRdpcmMode[compID]             = (UChar* )xMalloc(UChar,  uiNumPartition);
217      m_puhCbf[compID]                        = (UChar* )xMalloc(UChar,  uiNumPartition);
218      m_pcTrCoeff[compID]                     = (TCoeff*)xMalloc(TCoeff, totalSize);
219      memset( m_pcTrCoeff[compID], 0, (totalSize * sizeof( TCoeff )) );
220
221#if ADAPTIVE_QP_SELECTION
222      if( pParentARLBuffer != 0 )
223      {
224        m_pcArlCoeff[compID] = pParentARLBuffer;
225        m_ArlCoeffIsAliasedAllocation = true;
226        pParentARLBuffer += totalSize;
227      }
228      else
229      {
230        m_pcArlCoeff[compID] = (TCoeff*)xMalloc(TCoeff, totalSize);
231        m_ArlCoeffIsAliasedAllocation = false;
232      }
233#endif
234      m_pcIPCMSample[compID] = (Pel*   )xMalloc(Pel , totalSize);
235    }
236
237    m_pbIPCMFlag         = (Bool*  )xMalloc(Bool, uiNumPartition);
238
239    for(UInt i=0; i<NUM_REF_PIC_LIST_01; i++)
240    {
241      m_acCUMvField[i].create( uiNumPartition );
242    }
243
244#if NH_3D_ARP
245    m_puhARPW            = (UChar*  )xMalloc(UChar,   uiNumPartition);
246#endif
247#if NH_3D_IC
248    m_pbICFlag           = (Bool* )xMalloc(Bool,   uiNumPartition);
249#endif
250#if NH_3D_DMM
251    for( Int i = 0; i < NUM_DMM; i++ )
252    {
253      m_dmmDeltaDC[i][0] = (Pel* )xMalloc(Pel, uiNumPartition); 
254      m_dmmDeltaDC[i][1] = (Pel* )xMalloc(Pel, uiNumPartition);
255    }
256    m_dmm1WedgeTabIdx    = (UInt*)xMalloc(UInt, uiNumPartition);
257#endif
258#if NH_3D_SDC_INTRA
259    m_pbSDCFlag             = (Bool*)xMalloc(Bool, uiNumPartition);
260    m_apSegmentDCOffset[0]  = (Pel*)xMalloc(Pel, uiNumPartition);
261    m_apSegmentDCOffset[1]  = (Pel*)xMalloc(Pel, uiNumPartition);
262#endif
263#if NH_3D_DBBP
264    m_pbDBBPFlag         = (Bool*  )xMalloc(Bool,   uiNumPartition);
265#endif
266
267  }
268  else
269  {
270    for(UInt i=0; i<NUM_REF_PIC_LIST_01; i++)
271    {
272      m_acCUMvField[i].setNumPartition(uiNumPartition );
273    }
274  }
275
276  // create motion vector fields
277
278  m_pCtuAboveLeft      = NULL;
279  m_pCtuAboveRight     = NULL;
280  m_pCtuAbove          = NULL;
281  m_pCtuLeft           = NULL;
282
283  for(UInt i=0; i<NUM_REF_PIC_LIST_01; i++)
284  {
285    m_apcCUColocated[i]  = NULL;
286  }
287}
288
289Void TComDataCU::destroy()
290{
291  // encoder-side buffer free
292  if ( !m_bDecSubCu )
293  {
294    if ( m_phQP )
295    {
296      xFree(m_phQP);
297      m_phQP = NULL;
298    }
299    if ( m_puhDepth )
300    {
301      xFree(m_puhDepth);
302      m_puhDepth = NULL;
303    }
304    if ( m_puhWidth )
305    {
306      xFree(m_puhWidth);
307      m_puhWidth = NULL;
308    }
309    if ( m_puhHeight )
310    {
311      xFree(m_puhHeight);
312      m_puhHeight = NULL;
313    }
314
315    if ( m_skipFlag )
316    {
317      delete[] m_skipFlag;
318      m_skipFlag = NULL;
319    }
320
321#if NH_3D_DIS
322    if ( m_bDISFlag           ) { delete[] m_bDISFlag;   m_bDISFlag     = NULL; }
323    if ( m_ucDISType         ) { xFree(m_ucDISType);  m_ucDISType    = NULL; }
324#endif
325
326    if ( m_pePartSize )
327    {
328      delete[] m_pePartSize;
329      m_pePartSize = NULL;
330    }
331    if ( m_pePredMode )
332    {
333      delete[] m_pePredMode;
334      m_pePredMode = NULL;
335    }
336    if ( m_ChromaQpAdj )
337    {
338      delete[] m_ChromaQpAdj;
339      m_ChromaQpAdj = NULL;
340    }
341    if ( m_CUTransquantBypass )
342    {
343      delete[] m_CUTransquantBypass;
344      m_CUTransquantBypass = NULL;
345    }
346    if ( m_puhInterDir )
347    {
348      xFree(m_puhInterDir);
349      m_puhInterDir = NULL;
350    }
351    if ( m_pbMergeFlag )
352    {
353      xFree(m_pbMergeFlag);
354      m_pbMergeFlag = NULL;
355    }
356    if ( m_puhMergeIndex )
357    {
358      xFree(m_puhMergeIndex);
359      m_puhMergeIndex  = NULL;
360    }
361
362#if NH_3D_VSP
363    if ( m_piVSPFlag )
364    {
365      xFree(m_piVSPFlag);
366      m_piVSPFlag = NULL;
367    }
368#endif
369#if NH_3D_SPIVMP
370    if ( m_pbSPIVMPFlag       ) { xFree(m_pbSPIVMPFlag);           m_pbSPIVMPFlag         = NULL; }
371#endif
372
373
374    for (UInt ch=0; ch<MAX_NUM_CHANNEL_TYPE; ch++)
375    {
376      xFree(m_puhIntraDir[ch]);
377      m_puhIntraDir[ch] = NULL;
378    }
379
380    if ( m_puhTrIdx )
381    {
382      xFree(m_puhTrIdx);
383      m_puhTrIdx = NULL;
384    }
385
386    for (UInt comp=0; comp<MAX_NUM_COMPONENT; comp++)
387    {
388      if ( m_crossComponentPredictionAlpha[comp] )
389      {
390        xFree(m_crossComponentPredictionAlpha[comp]);
391        m_crossComponentPredictionAlpha[comp] = NULL;
392      }
393      if ( m_puhTransformSkip[comp] )
394      {
395        xFree(m_puhTransformSkip[comp]);
396        m_puhTransformSkip[comp] = NULL;
397      }
398      if ( m_puhCbf[comp] )
399      {
400        xFree(m_puhCbf[comp]);
401        m_puhCbf[comp] = NULL;
402      }
403      if ( m_pcTrCoeff[comp] )
404      {
405        xFree(m_pcTrCoeff[comp]);
406        m_pcTrCoeff[comp] = NULL;
407      }
408      if ( m_explicitRdpcmMode[comp] )
409      {
410        xFree(m_explicitRdpcmMode[comp]);
411        m_explicitRdpcmMode[comp] = NULL;
412      }
413
414#if ADAPTIVE_QP_SELECTION
415      if (!m_ArlCoeffIsAliasedAllocation)
416      {
417        if ( m_pcArlCoeff[comp] )
418        {
419          xFree(m_pcArlCoeff[comp]);
420          m_pcArlCoeff[comp] = NULL;
421        }
422      }
423#endif
424
425      if ( m_pcIPCMSample[comp] )
426      {
427        xFree(m_pcIPCMSample[comp]);
428        m_pcIPCMSample[comp] = NULL;
429      }
430    }
431    if ( m_pbIPCMFlag )
432    {
433      xFree(m_pbIPCMFlag );
434      m_pbIPCMFlag = NULL;
435    }
436
437    for(UInt i=0; i<NUM_REF_PIC_LIST_01; i++)
438    {
439      const RefPicList rpl=RefPicList(i);
440      if ( m_apiMVPIdx[rpl] )
441      {
442        delete[] m_apiMVPIdx[rpl];
443        m_apiMVPIdx[rpl] = NULL;
444      }
445      if ( m_apiMVPNum[rpl] )
446      {
447        delete[] m_apiMVPNum[rpl];
448        m_apiMVPNum[rpl] = NULL;
449      }
450    }
451
452    for(UInt i=0; i<NUM_REF_PIC_LIST_01; i++)
453    {
454      const RefPicList rpl=RefPicList(i);
455      m_acCUMvField[rpl].destroy();
456    }
457#if NH_3D_NBDV
458    if ( m_pDvInfo            ) { xFree(m_pDvInfo);             m_pDvInfo           = NULL; }
459#endif
460
461
462#if NH_3D_ARP
463    if ( m_puhARPW            ) { xFree(m_puhARPW);             m_puhARPW           = NULL; }
464#endif
465#if NH_3D_IC
466    if ( m_pbICFlag           ) { xFree(m_pbICFlag);            m_pbICFlag          = NULL; }
467#endif
468
469#if NH_3D_DMM
470    for( Int i = 0; i < NUM_DMM; i++ )
471    {
472      if ( m_dmmDeltaDC[i][0] ) { xFree( m_dmmDeltaDC[i][0] ); m_dmmDeltaDC[i][0] = NULL; }
473      if ( m_dmmDeltaDC[i][1] ) { xFree( m_dmmDeltaDC[i][1] ); m_dmmDeltaDC[i][1] = NULL; }
474    }
475    if ( m_dmm1WedgeTabIdx    ) { xFree( m_dmm1WedgeTabIdx );  m_dmm1WedgeTabIdx = NULL;  }
476#endif
477#if NH_3D_SDC_INTRA
478    if ( m_pbSDCFlag            ) { xFree(m_pbSDCFlag);             m_pbSDCFlag             = NULL; }
479    if ( m_apSegmentDCOffset[0] ) { xFree(m_apSegmentDCOffset[0]);  m_apSegmentDCOffset[0]  = NULL; }
480    if ( m_apSegmentDCOffset[1] ) { xFree(m_apSegmentDCOffset[1]);  m_apSegmentDCOffset[1]  = NULL; }
481#endif   
482#if NH_3D_DBBP
483    if ( m_pbDBBPFlag         ) { xFree(m_pbDBBPFlag);          m_pbDBBPFlag        = NULL; }
484#endif
485
486  }
487
488  m_pcPic              = NULL;
489  m_pcSlice            = NULL;
490
491  m_pCtuAboveLeft      = NULL;
492  m_pCtuAboveRight     = NULL;
493  m_pCtuAbove          = NULL;
494  m_pCtuLeft           = NULL;
495
496
497  for(UInt i=0; i<NUM_REF_PIC_LIST_01; i++)
498  {
499    m_apcCUColocated[i]  = NULL;
500  }
501
502}
503
504Bool TComDataCU::CUIsFromSameTile            ( const TComDataCU *pCU /* Can be NULL */) const
505{
506  return pCU!=NULL &&
507         pCU->getSlice() != NULL &&
508         m_pcPic->getPicSym()->getTileIdxMap( pCU->getCtuRsAddr() ) == m_pcPic->getPicSym()->getTileIdxMap(getCtuRsAddr());
509}
510
511Bool TComDataCU::CUIsFromSameSliceAndTile    ( const TComDataCU *pCU /* Can be NULL */) const
512{
513  return pCU!=NULL &&
514         pCU->getSlice() != NULL &&
515         pCU->getSlice()->getSliceCurStartCtuTsAddr() == getSlice()->getSliceCurStartCtuTsAddr() &&
516         m_pcPic->getPicSym()->getTileIdxMap( pCU->getCtuRsAddr() ) == m_pcPic->getPicSym()->getTileIdxMap(getCtuRsAddr())
517         ;
518}
519
520Bool TComDataCU::CUIsFromSameSliceTileAndWavefrontRow( const TComDataCU *pCU /* Can be NULL */) const
521{
522  return CUIsFromSameSliceAndTile(pCU)
523         && (!getSlice()->getPPS()->getEntropyCodingSyncEnabledFlag() || getPic()->getCtu(getCtuRsAddr())->getCUPelY() == getPic()->getCtu(pCU->getCtuRsAddr())->getCUPelY());
524}
525
526Bool TComDataCU::isLastSubCUOfCtu(const UInt absPartIdx) const
527{
528  const TComSPS &sps=*(getSlice()->getSPS());
529
530  const UInt picWidth = sps.getPicWidthInLumaSamples();
531  const UInt picHeight = sps.getPicHeightInLumaSamples();
532  const UInt granularityWidth = sps.getMaxCUWidth();
533
534  const UInt cuPosX = getCUPelX() + g_auiRasterToPelX[ g_auiZscanToRaster[absPartIdx] ];
535  const UInt cuPosY = getCUPelY() + g_auiRasterToPelY[ g_auiZscanToRaster[absPartIdx] ];
536
537  return (((cuPosX+getWidth( absPartIdx))%granularityWidth==0||(cuPosX+getWidth( absPartIdx)==picWidth ))
538       && ((cuPosY+getHeight(absPartIdx))%granularityWidth==0||(cuPosY+getHeight(absPartIdx)==picHeight)));
539}
540
541// ====================================================================================================================
542// Public member functions
543// ====================================================================================================================
544
545// --------------------------------------------------------------------------------------------------------------------
546// Initialization
547// --------------------------------------------------------------------------------------------------------------------
548
549/**
550 Initialize top-level CU: create internal buffers and set initial values before encoding the CTU.
551 
552 \param  pcPic       picture (TComPic) class pointer
553 \param  ctuRsAddr   CTU address in raster scan order
554 */
555Void TComDataCU::initCtu( TComPic* pcPic, UInt ctuRsAddr )
556{
557
558  const UInt maxCUWidth = pcPic->getPicSym()->getSPS().getMaxCUWidth();
559  const UInt maxCUHeight= pcPic->getPicSym()->getSPS().getMaxCUHeight();
560  m_pcPic              = pcPic;
561  m_pcSlice            = pcPic->getSlice(pcPic->getCurrSliceIdx());
562  m_ctuRsAddr          = ctuRsAddr;
563  m_uiCUPelX           = ( ctuRsAddr % pcPic->getFrameWidthInCtus() ) * maxCUWidth;
564  m_uiCUPelY           = ( ctuRsAddr / pcPic->getFrameWidthInCtus() ) * maxCUHeight;
565  m_absZIdxInCtu       = 0;
566  m_dTotalCost         = MAX_DOUBLE;
567  m_uiTotalDistortion  = 0;
568  m_uiTotalBits        = 0;
569  m_uiTotalBins        = 0;
570  m_uiNumPartition     = pcPic->getNumPartitionsInCtu();
571
572  memset( m_skipFlag          , false,                      m_uiNumPartition * sizeof( *m_skipFlag ) );
573
574#if NH_3D_DIS
575    memset( m_bDISFlag        , false,                      m_uiNumPartition * sizeof( *m_bDISFlag ) );
576    memset( m_ucDISType       , false,                      m_uiNumPartition * sizeof( *m_ucDISType ) );
577#endif
578
579  memset( m_pePartSize        , NUMBER_OF_PART_SIZES,       m_uiNumPartition * sizeof( *m_pePartSize ) );
580  memset( m_pePredMode        , NUMBER_OF_PREDICTION_MODES, m_uiNumPartition * sizeof( *m_pePredMode ) );
581  memset( m_CUTransquantBypass, false,                      m_uiNumPartition * sizeof( *m_CUTransquantBypass) );
582  memset( m_puhDepth          , 0,                          m_uiNumPartition * sizeof( *m_puhDepth ) );
583  memset( m_puhTrIdx          , 0,                          m_uiNumPartition * sizeof( *m_puhTrIdx ) );
584  memset( m_puhWidth          , maxCUWidth,                 m_uiNumPartition * sizeof( *m_puhWidth ) );
585  memset( m_puhHeight         , maxCUHeight,                m_uiNumPartition * sizeof( *m_puhHeight ) );
586
587#if NH_3D_IC
588  memset( m_pbICFlag          , false,                      m_uiNumPartition * sizeof( *m_pbICFlag ) );
589#endif
590  for(UInt i=0; i<NUM_REF_PIC_LIST_01; i++)
591  {
592    const RefPicList rpl=RefPicList(i);
593    memset( m_apiMVPIdx[rpl]  , -1,                         m_uiNumPartition * sizeof( *m_apiMVPIdx[rpl] ) );
594    memset( m_apiMVPNum[rpl]  , -1,                         m_uiNumPartition * sizeof( *m_apiMVPNum[rpl] ) );
595  }
596  memset( m_phQP              , getSlice()->getSliceQp(),   m_uiNumPartition * sizeof( *m_phQP ) );
597  memset( m_ChromaQpAdj       , 0,                          m_uiNumPartition * sizeof( *m_ChromaQpAdj ) );
598  for(UInt comp=0; comp<MAX_NUM_COMPONENT; comp++)
599  {
600    memset( m_crossComponentPredictionAlpha[comp] , 0,                     m_uiNumPartition * sizeof( *m_crossComponentPredictionAlpha[comp] ) );
601    memset( m_puhTransformSkip[comp]              , 0,                     m_uiNumPartition * sizeof( *m_puhTransformSkip[comp]) );
602    memset( m_puhCbf[comp]                        , 0,                     m_uiNumPartition * sizeof( *m_puhCbf[comp] ) );
603    memset( m_explicitRdpcmMode[comp]             , NUMBER_OF_RDPCM_MODES, m_uiNumPartition * sizeof( *m_explicitRdpcmMode[comp] ) );
604  }
605  memset( m_pbMergeFlag       , false,                    m_uiNumPartition * sizeof( *m_pbMergeFlag ) );
606  memset( m_puhMergeIndex     , 0,                        m_uiNumPartition * sizeof( *m_puhMergeIndex ) );
607
608#if NH_3D_VSP
609  memset( m_piVSPFlag         , 0,                        m_uiNumPartition * sizeof( *m_piVSPFlag ) );
610#endif
611#if NH_3D_SPIVMP
612  memset( m_pbSPIVMPFlag      , 0,                     m_uiNumPartition * sizeof( *m_pbSPIVMPFlag ) );   
613#endif
614#if NH_3D_SDC_INTRA
615  memset( m_pbSDCFlag, false, m_uiNumPartition * sizeof( *m_pbSDCFlag ) );
616#endif
617#if NH_3D_DBBP
618  memset( m_pbDBBPFlag , false, m_uiNumPartition * sizeof( *m_pbDBBPFlag ));
619#endif
620
621  for (UInt ch=0; ch<MAX_NUM_CHANNEL_TYPE; ch++)
622  {
623    memset( m_puhIntraDir[ch] , ((ch==0) ? DC_IDX : 0),   m_uiNumPartition * sizeof( *(m_puhIntraDir[ch]) ) );
624  }
625
626#if NH_3D_ARP
627  memset( m_puhARPW      ,      0,        m_uiNumPartition * sizeof( *m_puhARPW )         );
628#endif
629
630
631#if NH_3D_DMM
632  for( Int i = 0; i < NUM_DMM; i++ )
633  {
634    memset( m_dmmDeltaDC[i][0], 0,                        m_uiNumPartition * sizeof( *m_dmmDeltaDC[i][0] ) );
635    memset( m_dmmDeltaDC[i][1], 0,                        m_uiNumPartition * sizeof( *m_dmmDeltaDC[i][1] ) );
636  }
637  memset( m_dmm1WedgeTabIdx,    0,                        m_uiNumPartition * sizeof( *m_dmm1WedgeTabIdx   ) );
638#endif
639#if NH_3D_SDC_INTRA
640    memset( m_pbSDCFlag,     false,                m_uiNumPartition * sizeof( *m_pbSDCFlag ) );
641    memset( m_apSegmentDCOffset[0],     0,                m_uiNumPartition * sizeof( *m_apSegmentDCOffset[0] ) );
642    memset( m_apSegmentDCOffset[1],     0,                m_uiNumPartition * sizeof( *m_apSegmentDCOffset[1] ) );
643#endif
644
645  memset( m_puhInterDir       , 0,                        m_uiNumPartition * sizeof( *m_puhInterDir ) );
646  memset( m_pbIPCMFlag        , false,                    m_uiNumPartition * sizeof( *m_pbIPCMFlag ) );
647
648  const UInt numCoeffY    = maxCUWidth*maxCUHeight;
649  for (UInt comp=0; comp<MAX_NUM_COMPONENT; comp++)
650  {
651    const UInt componentShift = m_pcPic->getComponentScaleX(ComponentID(comp)) + m_pcPic->getComponentScaleY(ComponentID(comp));
652    memset( m_pcTrCoeff[comp], 0, sizeof(TCoeff)* numCoeffY>>componentShift );
653#if ADAPTIVE_QP_SELECTION
654    memset( m_pcArlCoeff[comp], 0, sizeof(TCoeff)* numCoeffY>>componentShift );
655#endif
656  }
657
658  for(UInt i=0; i<NUM_REF_PIC_LIST_01; i++)
659  {
660    m_acCUMvField[i].clearMvField();
661  }
662
663  // Setting neighbor CU
664  m_pCtuLeft        = NULL;
665  m_pCtuAbove       = NULL;
666  m_pCtuAboveLeft   = NULL;
667  m_pCtuAboveRight  = NULL;
668
669
670  for(UInt i=0; i<NUM_REF_PIC_LIST_01; i++)
671  {
672    m_apcCUColocated[i]  = NULL;
673  }
674
675  UInt frameWidthInCtus = pcPic->getFrameWidthInCtus();
676  if ( m_ctuRsAddr % frameWidthInCtus )
677  {
678    m_pCtuLeft = pcPic->getCtu( m_ctuRsAddr - 1 );
679  }
680
681  if ( m_ctuRsAddr / frameWidthInCtus )
682  {
683    m_pCtuAbove = pcPic->getCtu( m_ctuRsAddr - frameWidthInCtus );
684  }
685
686  if ( m_pCtuLeft && m_pCtuAbove )
687  {
688    m_pCtuAboveLeft = pcPic->getCtu( m_ctuRsAddr - frameWidthInCtus - 1 );
689  }
690
691  if ( m_pCtuAbove && ( (m_ctuRsAddr%frameWidthInCtus) < (frameWidthInCtus-1) )  )
692  {
693    m_pCtuAboveRight = pcPic->getCtu( m_ctuRsAddr - frameWidthInCtus + 1 );
694  }
695
696  for(UInt i=0; i<NUM_REF_PIC_LIST_01; i++)
697  {
698    const RefPicList rpl=RefPicList(i);
699    if ( getSlice()->getNumRefIdx( rpl ) > 0 )
700    {
701      m_apcCUColocated[rpl] = getSlice()->getRefPic( rpl, 0)->getCtu( m_ctuRsAddr );
702    }
703  }
704}
705
706
707/** Initialize prediction data with enabling sub-CTU-level delta QP.
708*   - set CU width and CU height according to depth
709*   - set qp value according to input qp
710*   - set last-coded qp value according to input last-coded qp
711*
712* \param  uiDepth            depth of the current CU
713* \param  qp                 qp for the current CU
714* \param  bTransquantBypass  true for transquant bypass
715*/
716Void TComDataCU::initEstData( const UInt uiDepth, const Int qp, const Bool bTransquantBypass )
717{
718  m_dTotalCost         = MAX_DOUBLE;
719  m_uiTotalDistortion  = 0;
720  m_uiTotalBits        = 0;
721  m_uiTotalBins        = 0;
722
723  const UChar uhWidth  = getSlice()->getSPS()->getMaxCUWidth()  >> uiDepth;
724  const UChar uhHeight = getSlice()->getSPS()->getMaxCUHeight() >> uiDepth;
725
726  for (UInt ui = 0; ui < m_uiNumPartition; ui++)
727  {
728    for(UInt i=0; i<NUM_REF_PIC_LIST_01; i++)
729    {
730      const RefPicList rpl=RefPicList(i);
731      m_apiMVPIdx[rpl][ui]  = -1;
732      m_apiMVPNum[rpl][ui]  = -1;
733    }
734    m_puhDepth  [ui]    = uiDepth;
735    m_puhWidth  [ui]    = uhWidth;
736    m_puhHeight [ui]    = uhHeight;
737    m_puhTrIdx  [ui]    = 0;
738    for(UInt comp=0; comp<MAX_NUM_COMPONENT; comp++)
739    {
740      m_crossComponentPredictionAlpha[comp][ui] = 0;
741      m_puhTransformSkip             [comp][ui] = 0;
742      m_explicitRdpcmMode            [comp][ui] = NUMBER_OF_RDPCM_MODES;
743    }
744    m_skipFlag[ui]      = false;
745#if NH_3D_DIS
746    m_bDISFlag[ui]      = false;
747    m_ucDISType[ui]     = 0;
748#endif
749    m_pePartSize[ui]    = NUMBER_OF_PART_SIZES;
750    m_pePredMode[ui]    = NUMBER_OF_PREDICTION_MODES;
751    m_CUTransquantBypass[ui] = bTransquantBypass;
752    m_pbIPCMFlag[ui]    = 0;
753    m_phQP[ui]          = qp;
754    m_ChromaQpAdj[ui]   = 0;
755    m_pbMergeFlag[ui]   = 0;
756    m_puhMergeIndex[ui] = 0;
757#if NH_3D_VSP
758    m_piVSPFlag[ui]     = 0;
759#endif
760#if NH_3D_SPIVMP
761    m_pbSPIVMPFlag[ui] = 0;
762#endif
763
764    for (UInt ch=0; ch<MAX_NUM_CHANNEL_TYPE; ch++)
765    {
766      m_puhIntraDir[ch][ui] = ((ch==0) ? DC_IDX : 0);
767    }
768
769    m_puhInterDir[ui] = 0;
770    for (UInt comp=0; comp<MAX_NUM_COMPONENT; comp++)
771    {
772      m_puhCbf[comp][ui] = 0;
773    }
774#if NH_3D_ARP
775      m_puhARPW[ui] = 0;
776#endif
777#if NH_3D_IC
778      m_pbICFlag[ui]  = false;
779#endif
780
781
782#if NH_3D_DMM
783    for( Int i = 0; i < NUM_DMM; i++ )
784    {
785      m_dmmDeltaDC[i][0] [ui] = 0;
786      m_dmmDeltaDC[i][1] [ui] = 0;
787    }
788    m_dmm1WedgeTabIdx    [ui] = 0;
789#endif
790#if NH_3D_SDC_INTRA
791      m_pbSDCFlag           [ui] = false;
792      m_apSegmentDCOffset[0][ui] = 0;
793      m_apSegmentDCOffset[1][ui] = 0;
794#endif
795#if NH_3D_DBBP
796      m_pbDBBPFlag[ui] = false;
797#endif
798  }
799
800  for(UInt i=0; i<NUM_REF_PIC_LIST_01; i++)
801  {
802    m_acCUMvField[i].clearMvField();
803  }
804
805  const UInt numCoeffY = uhWidth*uhHeight;
806
807  for (UInt comp=0; comp<MAX_NUM_COMPONENT; comp++)
808  {
809    const ComponentID component = ComponentID(comp);
810    const UInt numCoeff = numCoeffY >> (getPic()->getComponentScaleX(component) + getPic()->getComponentScaleY(component));
811    memset( m_pcTrCoeff[comp],    0, numCoeff * sizeof( TCoeff ) );
812#if ADAPTIVE_QP_SELECTION
813    memset( m_pcArlCoeff[comp],   0, numCoeff * sizeof( TCoeff ) );
814#endif
815    memset( m_pcIPCMSample[comp], 0, numCoeff * sizeof( Pel) );
816  }
817}
818
819
820// initialize Sub partition
821Void TComDataCU::initSubCU( TComDataCU* pcCU, UInt uiPartUnitIdx, UInt uiDepth, Int qp )
822{
823  assert( uiPartUnitIdx<4 );
824
825  UInt uiPartOffset = ( pcCU->getTotalNumPart()>>2 )*uiPartUnitIdx;
826
827  m_pcPic              = pcCU->getPic();
828  m_pcSlice            = pcCU->getSlice();
829  m_ctuRsAddr          = pcCU->getCtuRsAddr();
830  m_absZIdxInCtu       = pcCU->getZorderIdxInCtu() + uiPartOffset;
831
832  const UChar uhWidth  = getSlice()->getSPS()->getMaxCUWidth()  >> uiDepth;
833  const UChar uhHeight = getSlice()->getSPS()->getMaxCUHeight() >> uiDepth;
834
835  m_uiCUPelX           = pcCU->getCUPelX() + ( uhWidth )*( uiPartUnitIdx &  1 );
836  m_uiCUPelY           = pcCU->getCUPelY() + ( uhHeight)*( uiPartUnitIdx >> 1 );
837
838  m_dTotalCost         = MAX_DOUBLE;
839  m_uiTotalDistortion  = 0;
840  m_uiTotalBits        = 0;
841  m_uiTotalBins        = 0;
842  m_uiNumPartition     = pcCU->getTotalNumPart() >> 2;
843
844  Int iSizeInUchar = sizeof( UChar  ) * m_uiNumPartition;
845  Int iSizeInBool  = sizeof( Bool   ) * m_uiNumPartition;
846  Int sizeInChar = sizeof( SChar  ) * m_uiNumPartition;
847
848  memset( m_phQP,              qp,  sizeInChar );
849  memset( m_pbMergeFlag,        0, iSizeInBool  );
850  memset( m_puhMergeIndex,      0, iSizeInUchar );
851#if NH_3D_VSP
852  memset( m_piVSPFlag,          0, sizeof( SChar ) * m_uiNumPartition );
853#endif
854#if NH_3D_SPIVMP
855  memset( m_pbSPIVMPFlag,       0, sizeof( Bool  ) * m_uiNumPartition );
856#endif
857
858  for (UInt ch=0; ch<MAX_NUM_CHANNEL_TYPE; ch++)
859  {
860    memset( m_puhIntraDir[ch],  ((ch==0) ? DC_IDX : 0), iSizeInUchar );
861  }
862
863  memset( m_puhInterDir,        0, iSizeInUchar );
864  memset( m_puhTrIdx,           0, iSizeInUchar );
865
866  for(UInt comp=0; comp<MAX_NUM_COMPONENT; comp++)
867  {
868    memset( m_crossComponentPredictionAlpha[comp], 0, iSizeInUchar );
869    memset( m_puhTransformSkip[comp],              0, iSizeInUchar );
870    memset( m_puhCbf[comp],                        0, iSizeInUchar );
871    memset( m_explicitRdpcmMode[comp],             NUMBER_OF_RDPCM_MODES, iSizeInUchar );
872  }
873
874  memset( m_puhDepth,     uiDepth, iSizeInUchar );
875  memset( m_puhWidth,          uhWidth,  iSizeInUchar );
876  memset( m_puhHeight,         uhHeight, iSizeInUchar );
877  memset( m_pbIPCMFlag,        0, iSizeInBool  );
878#if NH_3D_ARP
879  memset( m_puhARPW,           0, iSizeInUchar  );
880#endif
881#if NH_3D_IC
882  memset( m_pbICFlag,          0, iSizeInBool  );
883#endif
884#if NH_3D_DMM
885  for( Int i = 0; i < NUM_DMM; i++ )
886  {
887    memset( m_dmmDeltaDC[i][0], 0, sizeof(Pel ) * m_uiNumPartition );
888    memset( m_dmmDeltaDC[i][1], 0, sizeof(Pel ) * m_uiNumPartition );
889  }
890  memset( m_dmm1WedgeTabIdx,    0, sizeof(UInt) * m_uiNumPartition );
891#endif
892#if NH_3D_SDC_INTRA
893  memset( m_pbSDCFlag,            0, sizeof(Bool) * m_uiNumPartition  );
894  memset( m_apSegmentDCOffset[0], 0, sizeof(Pel) * m_uiNumPartition   );
895  memset( m_apSegmentDCOffset[1], 0, sizeof(Pel) * m_uiNumPartition   );
896#endif
897#if NH_3D_DBBP
898  memset( m_pbDBBPFlag,         0, sizeof(Bool) * m_uiNumPartition  );
899#endif
900
901  for (UInt ui = 0; ui < m_uiNumPartition; ui++)
902  {
903    m_skipFlag[ui]   = false;
904#if NH_3D_DIS
905    m_bDISFlag[ui]   = false;
906    m_ucDISType[ui]  = 0;
907#endif
908
909    m_pePartSize[ui] = NUMBER_OF_PART_SIZES;
910    m_pePredMode[ui] = NUMBER_OF_PREDICTION_MODES;
911    m_CUTransquantBypass[ui] = false;
912    m_ChromaQpAdj[ui] = 0;
913
914    for(UInt i=0; i<NUM_REF_PIC_LIST_01; i++)
915    {
916      const RefPicList rpl=RefPicList(i);
917      m_apiMVPIdx[rpl][ui] = -1;
918      m_apiMVPNum[rpl][ui] = -1;
919    }
920#if NH_3D_DIS
921      m_bDISFlag[ui]    = pcCU->getDISFlag(uiPartOffset+ui);
922      m_ucDISType[ui]   = pcCU->getDISType(uiPartOffset+ui);
923#endif
924#if NH_3D_VSP
925    m_piVSPFlag[ui] = pcCU->m_piVSPFlag[uiPartOffset+ui];
926    m_pDvInfo[ ui ] = pcCU->m_pDvInfo[uiPartOffset+ui];
927#endif
928#if NH_3D_SPIVMP
929    m_pbSPIVMPFlag[ui]=pcCU->m_pbSPIVMPFlag[uiPartOffset+ui];
930#endif
931#if NH_3D_ARP
932      m_puhARPW           [ui] = pcCU->getARPW( uiPartOffset+ui );
933#endif
934#if NH_3D_IC
935      m_pbICFlag          [ui] = pcCU->m_pbICFlag[uiPartOffset+ui];
936#endif
937#if NH_3D_DMM
938  for( Int i = 0; i < NUM_DMM; i++ )
939  {
940    m_dmmDeltaDC[i][0] [ui] = pcCU->m_dmmDeltaDC[i][0] [uiPartOffset+ui];
941    m_dmmDeltaDC[i][1] [ui] = pcCU->m_dmmDeltaDC[i][1] [uiPartOffset+ui];
942  }
943  m_dmm1WedgeTabIdx    [ui] = pcCU->m_dmm1WedgeTabIdx  [uiPartOffset+ui];
944#endif
945#if NH_3D_SDC_INTRA
946    m_pbSDCFlag           [ui] = pcCU->m_pbSDCFlag            [ uiPartOffset + ui ];
947    m_apSegmentDCOffset[0][ui] = pcCU->m_apSegmentDCOffset[0] [ uiPartOffset + ui ];
948    m_apSegmentDCOffset[1][ui] = pcCU->m_apSegmentDCOffset[1] [ uiPartOffset + ui ];
949#endif
950#if NH_3D_DBBP
951      m_pbDBBPFlag[ui]=pcCU->m_pbDBBPFlag[uiPartOffset+ui];
952#endif
953  }
954
955  const UInt numCoeffY    = uhWidth*uhHeight;
956  for (UInt ch=0; ch<MAX_NUM_COMPONENT; ch++)
957  {
958    const UInt componentShift = m_pcPic->getComponentScaleX(ComponentID(ch)) + m_pcPic->getComponentScaleY(ComponentID(ch));
959    memset( m_pcTrCoeff[ch],  0, sizeof(TCoeff)*(numCoeffY>>componentShift) );
960#if ADAPTIVE_QP_SELECTION
961    memset( m_pcArlCoeff[ch], 0, sizeof(TCoeff)*(numCoeffY>>componentShift) );
962#endif
963    memset( m_pcIPCMSample[ch], 0, sizeof(Pel)* (numCoeffY>>componentShift) );
964  }
965
966  for(UInt i=0; i<NUM_REF_PIC_LIST_01; i++)
967  {
968    m_acCUMvField[i].clearMvField();
969  }
970
971  m_pCtuLeft        = pcCU->getCtuLeft();
972  m_pCtuAbove       = pcCU->getCtuAbove();
973  m_pCtuAboveLeft   = pcCU->getCtuAboveLeft();
974  m_pCtuAboveRight  = pcCU->getCtuAboveRight();
975
976  for(UInt i=0; i<NUM_REF_PIC_LIST_01; i++)
977  {
978    m_apcCUColocated[i] = pcCU->getCUColocated(RefPicList(i));
979  }
980}
981
982Void TComDataCU::setOutsideCUPart( UInt uiAbsPartIdx, UInt uiDepth )
983{
984  const UInt     uiNumPartition = m_uiNumPartition >> (uiDepth << 1);
985  const UInt     uiSizeInUchar  = sizeof( UChar  ) * uiNumPartition;
986  const TComSPS &sps            = *(getSlice()->getSPS());
987  const UChar    uhWidth        = sps.getMaxCUWidth()  >> uiDepth;
988  const UChar    uhHeight       = sps.getMaxCUHeight() >> uiDepth;
989  memset( m_puhDepth    + uiAbsPartIdx,     uiDepth,  uiSizeInUchar );
990  memset( m_puhWidth    + uiAbsPartIdx,     uhWidth,  uiSizeInUchar );
991  memset( m_puhHeight   + uiAbsPartIdx,     uhHeight, uiSizeInUchar );
992}
993
994// --------------------------------------------------------------------------------------------------------------------
995// Copy
996// --------------------------------------------------------------------------------------------------------------------
997
998Void TComDataCU::copySubCU( TComDataCU* pcCU, UInt uiAbsPartIdx )
999{
1000  UInt uiPart = uiAbsPartIdx;
1001
1002  m_pcPic              = pcCU->getPic();
1003  m_pcSlice            = pcCU->getSlice();
1004  m_ctuRsAddr          = pcCU->getCtuRsAddr();
1005  m_absZIdxInCtu       = uiAbsPartIdx;
1006
1007  m_uiCUPelX           = pcCU->getCUPelX() + g_auiRasterToPelX[ g_auiZscanToRaster[uiAbsPartIdx] ];
1008  m_uiCUPelY           = pcCU->getCUPelY() + g_auiRasterToPelY[ g_auiZscanToRaster[uiAbsPartIdx] ];
1009
1010  m_skipFlag=pcCU->getSkipFlag()          + uiPart;
1011#if NH_3D_DIS
1012  m_bDISFlag     = pcCU->getDISFlag()     + uiPart;
1013  m_ucDISType    = pcCU->getDISType()     + uiPart;
1014#endif
1015
1016  m_phQP=pcCU->getQP()                    + uiPart;
1017  m_ChromaQpAdj = pcCU->getChromaQpAdj()  + uiPart;
1018  m_pePartSize = pcCU->getPartitionSize() + uiPart;
1019  m_pePredMode=pcCU->getPredictionMode()  + uiPart;
1020  m_CUTransquantBypass  = pcCU->getCUTransquantBypass()+uiPart;
1021#if NH_3D_NBDV
1022  m_pDvInfo             = pcCU->getDvInfo()           + uiPart;
1023#endif
1024
1025  m_pbMergeFlag         = pcCU->getMergeFlag()        + uiPart;
1026  m_puhMergeIndex       = pcCU->getMergeIndex()       + uiPart;
1027#if NH_3D_VSP
1028  m_piVSPFlag           = pcCU->getVSPFlag()          + uiPart;
1029#endif
1030#if NH_3D_SPIVMP
1031  m_pbSPIVMPFlag        = pcCU->getSPIVMPFlag()          + uiPart;
1032#endif
1033#if NH_3D_ARP
1034  m_puhARPW             = pcCU->getARPW()             + uiPart;
1035#endif
1036#if NH_3D_IC
1037  m_pbICFlag            = pcCU->getICFlag()           + uiPart;
1038#endif
1039
1040  for (UInt ch=0; ch<MAX_NUM_CHANNEL_TYPE; ch++)
1041  {
1042    m_puhIntraDir[ch]   = pcCU->getIntraDir(ChannelType(ch)) + uiPart;
1043  }
1044
1045  m_puhInterDir         = pcCU->getInterDir()         + uiPart;
1046  m_puhTrIdx            = pcCU->getTransformIdx()     + uiPart;
1047
1048  for(UInt comp=0; comp<MAX_NUM_COMPONENT; comp++)
1049  {
1050    m_crossComponentPredictionAlpha[comp] = pcCU->getCrossComponentPredictionAlpha(ComponentID(comp)) + uiPart;
1051    m_puhTransformSkip[comp]              = pcCU->getTransformSkip(ComponentID(comp))                 + uiPart;
1052    m_puhCbf[comp]                        = pcCU->getCbf(ComponentID(comp))                           + uiPart;
1053    m_explicitRdpcmMode[comp]             = pcCU->getExplicitRdpcmMode(ComponentID(comp))             + uiPart;
1054  }
1055#if NH_3D_DMM
1056  for( Int i = 0; i < NUM_DMM; i++ )
1057  {
1058    m_dmmDeltaDC[i][0] = pcCU->getDmmDeltaDC( (DmmID)i, 0 ) + uiPart;
1059    m_dmmDeltaDC[i][1] = pcCU->getDmmDeltaDC( (DmmID)i, 1 ) + uiPart;
1060  }
1061  m_dmm1WedgeTabIdx    = pcCU->getDmm1WedgeTabIdx()  + uiPart;
1062#endif
1063#if NH_3D_SDC_INTRA
1064  m_pbSDCFlag               = pcCU->getSDCFlag()              + uiPart;
1065  m_apSegmentDCOffset[0]    = pcCU->getSDCSegmentDCOffset(0)  + uiPart;
1066  m_apSegmentDCOffset[1]    = pcCU->getSDCSegmentDCOffset(1)  + uiPart;
1067#endif 
1068#if NH_3D_DBBP
1069  m_pbDBBPFlag              = pcCU->getDBBPFlag()         + uiPart;
1070#endif
1071
1072  m_puhDepth=pcCU->getDepth()                     + uiPart;
1073  m_puhWidth=pcCU->getWidth()                     + uiPart;
1074  m_puhHeight=pcCU->getHeight()                   + uiPart;
1075
1076  m_pbIPCMFlag         = pcCU->getIPCMFlag()        + uiPart;
1077
1078  m_pCtuAboveLeft      = pcCU->getCtuAboveLeft();
1079  m_pCtuAboveRight     = pcCU->getCtuAboveRight();
1080  m_pCtuAbove          = pcCU->getCtuAbove();
1081  m_pCtuLeft           = pcCU->getCtuLeft();
1082
1083  for(UInt i=0; i<NUM_REF_PIC_LIST_01; i++)
1084  {
1085    const RefPicList rpl=RefPicList(i);
1086    m_apcCUColocated[rpl] = pcCU->getCUColocated(rpl);
1087    m_apiMVPIdx[rpl]=pcCU->getMVPIdx(rpl)  + uiPart;
1088    m_apiMVPNum[rpl]=pcCU->getMVPNum(rpl)  + uiPart;
1089  }
1090
1091  for(UInt i=0; i<NUM_REF_PIC_LIST_01; i++)
1092  {
1093    const RefPicList rpl=RefPicList(i);
1094    m_acCUMvField[rpl].linkToWithOffset( pcCU->getCUMvField(rpl), uiPart );
1095  }
1096
1097  UInt uiMaxCuWidth=pcCU->getSlice()->getSPS()->getMaxCUWidth();
1098  UInt uiMaxCuHeight=pcCU->getSlice()->getSPS()->getMaxCUHeight();
1099
1100  UInt uiCoffOffset = uiMaxCuWidth*uiMaxCuHeight*uiAbsPartIdx/pcCU->getPic()->getNumPartitionsInCtu();
1101
1102  for (UInt ch=0; ch<MAX_NUM_COMPONENT; ch++)
1103  {
1104    const ComponentID component = ComponentID(ch);
1105    const UInt componentShift   = m_pcPic->getComponentScaleX(component) + m_pcPic->getComponentScaleY(component);
1106    const UInt offset           = uiCoffOffset >> componentShift;
1107    m_pcTrCoeff[ch] = pcCU->getCoeff(component) + offset;
1108#if ADAPTIVE_QP_SELECTION
1109    m_pcArlCoeff[ch] = pcCU->getArlCoeff(component) + offset;
1110#endif
1111    m_pcIPCMSample[ch] = pcCU->getPCMSample(component) + offset;
1112  }
1113}
1114
1115#if NH_3D_NBDV
1116Void TComDataCU::copyDVInfoFrom (TComDataCU* pcCU, UInt uiAbsPartIdx)
1117{
1118  m_pDvInfo            = pcCU->getDvInfo()                + uiAbsPartIdx;
1119}
1120#endif
1121
1122// Copy inter prediction info from the biggest CU
1123#if NH_3D_NBDV
1124Void TComDataCU::copyInterPredInfoFrom    ( TComDataCU* pcCU, UInt uiAbsPartIdx, RefPicList eRefPicList   , Bool bNBDV )
1125#else
1126Void TComDataCU::copyInterPredInfoFrom    ( TComDataCU* pcCU, UInt uiAbsPartIdx, RefPicList eRefPicList )
1127#endif
1128{
1129  m_pcPic              = pcCU->getPic();
1130  m_pcSlice            = pcCU->getSlice();
1131  m_ctuRsAddr          = pcCU->getCtuRsAddr();
1132  m_absZIdxInCtu       = uiAbsPartIdx;
1133
1134  Int iRastPartIdx     = g_auiZscanToRaster[uiAbsPartIdx];
1135  m_uiCUPelX           = pcCU->getCUPelX() + m_pcPic->getMinCUWidth ()*( iRastPartIdx % m_pcPic->getNumPartInCtuWidth() );
1136  m_uiCUPelY           = pcCU->getCUPelY() + m_pcPic->getMinCUHeight()*( iRastPartIdx / m_pcPic->getNumPartInCtuWidth() );
1137
1138  m_pCtuAboveLeft      = pcCU->getCtuAboveLeft();
1139  m_pCtuAboveRight     = pcCU->getCtuAboveRight();
1140  m_pCtuAbove          = pcCU->getCtuAbove();
1141  m_pCtuLeft           = pcCU->getCtuLeft();
1142
1143  for(UInt i=0; i<NUM_REF_PIC_LIST_01; i++)
1144  {
1145    m_apcCUColocated[i]  = pcCU->getCUColocated(RefPicList(i));
1146  }
1147
1148  m_skipFlag           = pcCU->getSkipFlag ()             + uiAbsPartIdx;
1149#if NH_3D_DIS
1150  m_bDISFlag           = pcCU->getDISFlag ()              + uiAbsPartIdx;
1151  m_ucDISType          = pcCU->getDISType()               + uiAbsPartIdx;
1152#endif
1153
1154  m_pePartSize         = pcCU->getPartitionSize ()        + uiAbsPartIdx;
1155#if NH_3D_NBDV
1156  if(bNBDV == true)
1157  {
1158    m_puhWidth           = pcCU->getWidth ()                + uiAbsPartIdx;
1159    m_puhHeight          = pcCU->getHeight()                + uiAbsPartIdx;
1160    m_puhDepth           = pcCU->getDepth ()                + uiAbsPartIdx;
1161  }
1162  else
1163  {
1164#endif
1165  m_pePredMode         = pcCU->getPredictionMode()        + uiAbsPartIdx;
1166  m_ChromaQpAdj        = pcCU->getChromaQpAdj()           + uiAbsPartIdx;
1167  m_CUTransquantBypass = pcCU->getCUTransquantBypass()    + uiAbsPartIdx;
1168  m_puhInterDir        = pcCU->getInterDir      ()        + uiAbsPartIdx;
1169
1170  m_puhDepth           = pcCU->getDepth ()                + uiAbsPartIdx;
1171  m_puhWidth           = pcCU->getWidth ()                + uiAbsPartIdx;
1172  m_puhHeight          = pcCU->getHeight()                + uiAbsPartIdx;
1173
1174  m_pbMergeFlag        = pcCU->getMergeFlag()             + uiAbsPartIdx;
1175  m_puhMergeIndex      = pcCU->getMergeIndex()            + uiAbsPartIdx;
1176#if NH_3D_VSP
1177  m_piVSPFlag          = pcCU->getVSPFlag()               + uiAbsPartIdx;
1178  m_pDvInfo            = pcCU->getDvInfo()                + uiAbsPartIdx;
1179#endif
1180#if NH_3D_SPIVMP
1181  m_pbSPIVMPFlag       = pcCU->getSPIVMPFlag()            + uiAbsPartIdx;
1182#endif
1183
1184  m_apiMVPIdx[eRefPicList] = pcCU->getMVPIdx(eRefPicList) + uiAbsPartIdx;
1185  m_apiMVPNum[eRefPicList] = pcCU->getMVPNum(eRefPicList) + uiAbsPartIdx;
1186#if NH_3D_ARP
1187  m_puhARPW            = pcCU->getARPW()                  + uiAbsPartIdx;
1188#endif   
1189#if NH_3D_DBBP
1190  m_pbDBBPFlag       = pcCU->getDBBPFlag()              + uiAbsPartIdx;
1191#endif
1192
1193  m_acCUMvField[ eRefPicList ].linkToWithOffset( pcCU->getCUMvField(eRefPicList), uiAbsPartIdx );
1194#if NH_3D_NBDV
1195  }
1196#endif
1197#if NH_3D_IC
1198  m_pbICFlag           = pcCU->getICFlag()                + uiAbsPartIdx;
1199#endif
1200
1201}
1202
1203// Copy small CU to bigger CU.
1204// One of quarter parts overwritten by predicted sub part.
1205Void TComDataCU::copyPartFrom( TComDataCU* pcCU, UInt uiPartUnitIdx, UInt uiDepth )
1206{
1207  assert( uiPartUnitIdx<4 );
1208
1209  m_dTotalCost         += pcCU->getTotalCost();
1210  m_uiTotalDistortion  += pcCU->getTotalDistortion();
1211  m_uiTotalBits        += pcCU->getTotalBits();
1212
1213  UInt uiOffset         = pcCU->getTotalNumPart()*uiPartUnitIdx;
1214  const UInt numValidComp=pcCU->getPic()->getNumberValidComponents();
1215  const UInt numValidChan=pcCU->getPic()->getChromaFormat()==CHROMA_400 ? 1:2;
1216
1217  UInt uiNumPartition = pcCU->getTotalNumPart();
1218  Int iSizeInUchar  = sizeof( UChar ) * uiNumPartition;
1219  Int iSizeInBool   = sizeof( Bool  ) * uiNumPartition;
1220
1221  Int sizeInChar  = sizeof( SChar ) * uiNumPartition;
1222  memcpy( m_skipFlag   + uiOffset, pcCU->getSkipFlag(),       sizeof( *m_skipFlag )   * uiNumPartition );
1223#if NH_3D_DIS
1224  memcpy( m_bDISFlag   + uiOffset, pcCU->getDISFlag(),        sizeof( *m_bDISFlag )   * uiNumPartition );
1225  memcpy( m_ucDISType  + uiOffset, pcCU->getDISType(),        sizeof( *m_ucDISType )  * uiNumPartition);
1226#endif
1227  memcpy( m_phQP       + uiOffset, pcCU->getQP(),             sizeInChar                        );
1228  memcpy( m_pePartSize + uiOffset, pcCU->getPartitionSize(),  sizeof( *m_pePartSize ) * uiNumPartition );
1229  memcpy( m_pePredMode + uiOffset, pcCU->getPredictionMode(), sizeof( *m_pePredMode ) * uiNumPartition );
1230  memcpy( m_ChromaQpAdj + uiOffset, pcCU->getChromaQpAdj(),   sizeof( *m_ChromaQpAdj ) * uiNumPartition );
1231  memcpy( m_CUTransquantBypass + uiOffset, pcCU->getCUTransquantBypass(), sizeof( *m_CUTransquantBypass ) * uiNumPartition );
1232  memcpy( m_pbMergeFlag         + uiOffset, pcCU->getMergeFlag(),         iSizeInBool  );
1233  memcpy( m_puhMergeIndex       + uiOffset, pcCU->getMergeIndex(),        iSizeInUchar );
1234#if NH_3D_VSP
1235  memcpy( m_piVSPFlag           + uiOffset, pcCU->getVSPFlag(),           sizeof( SChar ) * uiNumPartition );
1236  memcpy( m_pDvInfo             + uiOffset, pcCU->getDvInfo(),            sizeof( *m_pDvInfo ) * uiNumPartition );
1237#endif
1238#if NH_3D_SPIVMP  || NH_3D_DBBP
1239  memcpy( m_pbSPIVMPFlag        + uiOffset, pcCU->getSPIVMPFlag(),        sizeof( Bool ) * uiNumPartition );
1240#endif
1241
1242  for (UInt ch=0; ch<numValidChan; ch++)
1243  {
1244    memcpy( m_puhIntraDir[ch]   + uiOffset, pcCU->getIntraDir(ChannelType(ch)), iSizeInUchar );
1245  }
1246
1247  memcpy( m_puhInterDir         + uiOffset, pcCU->getInterDir(),          iSizeInUchar );
1248  memcpy( m_puhTrIdx            + uiOffset, pcCU->getTransformIdx(),      iSizeInUchar );
1249
1250  for(UInt comp=0; comp<numValidComp; comp++)
1251  {
1252    memcpy( m_crossComponentPredictionAlpha[comp] + uiOffset, pcCU->getCrossComponentPredictionAlpha(ComponentID(comp)), iSizeInUchar );
1253    memcpy( m_puhTransformSkip[comp]              + uiOffset, pcCU->getTransformSkip(ComponentID(comp))                , iSizeInUchar );
1254    memcpy( m_puhCbf[comp]                        + uiOffset, pcCU->getCbf(ComponentID(comp))                          , iSizeInUchar );
1255    memcpy( m_explicitRdpcmMode[comp]             + uiOffset, pcCU->getExplicitRdpcmMode(ComponentID(comp))            , iSizeInUchar );
1256  }
1257#if NH_3D_DMM
1258  for( Int i = 0; i < NUM_DMM; i++ )
1259  {
1260    memcpy( m_dmmDeltaDC[i][0] + uiOffset, pcCU->getDmmDeltaDC( (DmmID)i, 0 ), sizeof(Pel ) * uiNumPartition );
1261    memcpy( m_dmmDeltaDC[i][1] + uiOffset, pcCU->getDmmDeltaDC( (DmmID)i, 1 ), sizeof(Pel ) * uiNumPartition );
1262  }
1263  memcpy( m_dmm1WedgeTabIdx    + uiOffset, pcCU->getDmm1WedgeTabIdx(),         sizeof(UInt) * uiNumPartition );
1264#endif
1265#if NH_3D_SDC_INTRA
1266  memcpy( m_pbSDCFlag             + uiOffset, pcCU->getSDCFlag(), sizeof( *m_pbSDCFlag ) * uiNumPartition  );
1267  memcpy( m_apSegmentDCOffset[0]  + uiOffset, pcCU->getSDCSegmentDCOffset(0), sizeof( Pel ) * uiNumPartition);
1268  memcpy( m_apSegmentDCOffset[1]  + uiOffset, pcCU->getSDCSegmentDCOffset(1), sizeof( Pel ) * uiNumPartition);
1269#endif
1270#if NH_3D_DBBP
1271  memcpy( m_pbDBBPFlag          + uiOffset, pcCU->getDBBPFlag(),          iSizeInBool  );
1272#endif
1273#if NH_3D_ARP
1274  memcpy( m_puhARPW             + uiOffset, pcCU->getARPW(),              iSizeInUchar );
1275#endif
1276
1277  memcpy( m_puhDepth  + uiOffset, pcCU->getDepth(),  iSizeInUchar );
1278  memcpy( m_puhWidth  + uiOffset, pcCU->getWidth(),  iSizeInUchar );
1279  memcpy( m_puhHeight + uiOffset, pcCU->getHeight(), iSizeInUchar );
1280
1281  memcpy( m_pbIPCMFlag + uiOffset, pcCU->getIPCMFlag(), iSizeInBool );
1282
1283  m_pCtuAboveLeft      = pcCU->getCtuAboveLeft();
1284  m_pCtuAboveRight     = pcCU->getCtuAboveRight();
1285  m_pCtuAbove          = pcCU->getCtuAbove();
1286  m_pCtuLeft           = pcCU->getCtuLeft();
1287
1288  for(UInt i=0; i<NUM_REF_PIC_LIST_01; i++)
1289  {
1290    const RefPicList rpl=RefPicList(i);
1291    memcpy( m_apiMVPIdx[rpl] + uiOffset, pcCU->getMVPIdx(rpl), iSizeInUchar );
1292    memcpy( m_apiMVPNum[rpl] + uiOffset, pcCU->getMVPNum(rpl), iSizeInUchar );
1293    m_apcCUColocated[rpl] = pcCU->getCUColocated(rpl);
1294  }
1295
1296  for(UInt i=0; i<NUM_REF_PIC_LIST_01; i++)
1297  {
1298    const RefPicList rpl=RefPicList(i);
1299    m_acCUMvField[rpl].copyFrom( pcCU->getCUMvField( rpl ), pcCU->getTotalNumPart(), uiOffset );
1300  }
1301
1302  const UInt numCoeffY = (pcCU->getSlice()->getSPS()->getMaxCUWidth()*pcCU->getSlice()->getSPS()->getMaxCUHeight()) >> (uiDepth<<1);
1303  const UInt offsetY   = uiPartUnitIdx*numCoeffY;
1304  for (UInt ch=0; ch<numValidComp; ch++)
1305  {
1306    const ComponentID component = ComponentID(ch);
1307    const UInt componentShift   = m_pcPic->getComponentScaleX(component) + m_pcPic->getComponentScaleY(component);
1308    const UInt offset           = offsetY>>componentShift;
1309    memcpy( m_pcTrCoeff [ch] + offset, pcCU->getCoeff(component),    sizeof(TCoeff)*(numCoeffY>>componentShift) );
1310#if ADAPTIVE_QP_SELECTION
1311    memcpy( m_pcArlCoeff[ch] + offset, pcCU->getArlCoeff(component), sizeof(TCoeff)*(numCoeffY>>componentShift) );
1312#endif
1313    memcpy( m_pcIPCMSample[ch] + offset, pcCU->getPCMSample(component), sizeof(Pel)*(numCoeffY>>componentShift) );
1314  }
1315
1316#if NH_3D_IC
1317  memcpy( m_pbICFlag            + uiOffset, pcCU->getICFlag(),            iSizeInBool );
1318#endif
1319
1320  m_uiTotalBins += pcCU->getTotalBins();
1321}
1322
1323// Copy current predicted part to a CU in picture.
1324// It is used to predict for next part
1325Void TComDataCU::copyToPic( UChar uhDepth )
1326{
1327  TComDataCU* pCtu = m_pcPic->getCtu( m_ctuRsAddr );
1328  const UInt numValidComp=pCtu->getPic()->getNumberValidComponents();
1329  const UInt numValidChan=pCtu->getPic()->getChromaFormat()==CHROMA_400 ? 1:2;
1330
1331  pCtu->getTotalCost()       = m_dTotalCost;
1332  pCtu->getTotalDistortion() = m_uiTotalDistortion;
1333  pCtu->getTotalBits()       = m_uiTotalBits;
1334
1335  Int iSizeInUchar  = sizeof( UChar ) * m_uiNumPartition;
1336  Int iSizeInBool   = sizeof( Bool  ) * m_uiNumPartition;
1337  Int sizeInChar  = sizeof( SChar ) * m_uiNumPartition;
1338
1339  memcpy( pCtu->getSkipFlag() + m_absZIdxInCtu, m_skipFlag, sizeof( *m_skipFlag ) * m_uiNumPartition );
1340#if NH_3D_DIS
1341  memcpy( pCtu->getDISFlag()  + m_absZIdxInCtu, m_bDISFlag, sizeof( *m_bDISFlag )  * m_uiNumPartition );
1342  memcpy( pCtu->getDISType()  + m_absZIdxInCtu, m_ucDISType, sizeof( *m_ucDISType ) * m_uiNumPartition );
1343#endif
1344
1345  memcpy( pCtu->getQP() + m_absZIdxInCtu, m_phQP, sizeInChar  );
1346#if NH_3D_NBDV
1347  memcpy( pCtu->getDvInfo() + m_absZIdxInCtu, m_pDvInfo, sizeof(* m_pDvInfo) * m_uiNumPartition );
1348#endif
1349
1350  memcpy( pCtu->getPartitionSize()  + m_absZIdxInCtu, m_pePartSize, sizeof( *m_pePartSize ) * m_uiNumPartition );
1351  memcpy( pCtu->getPredictionMode() + m_absZIdxInCtu, m_pePredMode, sizeof( *m_pePredMode ) * m_uiNumPartition );
1352  memcpy( pCtu->getChromaQpAdj() + m_absZIdxInCtu, m_ChromaQpAdj, sizeof( *m_ChromaQpAdj ) * m_uiNumPartition );
1353  memcpy( pCtu->getCUTransquantBypass()+ m_absZIdxInCtu, m_CUTransquantBypass, sizeof( *m_CUTransquantBypass ) * m_uiNumPartition );
1354  memcpy( pCtu->getMergeFlag()         + m_absZIdxInCtu, m_pbMergeFlag,         iSizeInBool  );
1355  memcpy( pCtu->getMergeIndex()        + m_absZIdxInCtu, m_puhMergeIndex,       iSizeInUchar );
1356#if NH_3D_VSP
1357  memcpy( pCtu->getVSPFlag()           + m_absZIdxInCtu, m_piVSPFlag,           sizeof( SChar ) * m_uiNumPartition );
1358#endif
1359#if NH_3D_DBBP
1360  memcpy( pCtu->getDvInfo()            + m_absZIdxInCtu, m_pDvInfo,             sizeof( *m_pDvInfo ) * m_uiNumPartition );
1361#endif
1362#if NH_3D_SPIVMP
1363  memcpy( pCtu->getSPIVMPFlag()        + m_absZIdxInCtu, m_pbSPIVMPFlag,        sizeof( Bool ) * m_uiNumPartition );
1364#endif
1365
1366for (UInt ch=0; ch<numValidChan; ch++)
1367  {
1368    memcpy( pCtu->getIntraDir(ChannelType(ch)) + m_absZIdxInCtu, m_puhIntraDir[ch], iSizeInUchar);
1369  }
1370
1371  memcpy( pCtu->getInterDir()          + m_absZIdxInCtu, m_puhInterDir,         iSizeInUchar );
1372  memcpy( pCtu->getTransformIdx()      + m_absZIdxInCtu, m_puhTrIdx,            iSizeInUchar );
1373
1374  for(UInt comp=0; comp<numValidComp; comp++)
1375  {
1376    memcpy( pCtu->getCrossComponentPredictionAlpha(ComponentID(comp)) + m_absZIdxInCtu, m_crossComponentPredictionAlpha[comp], iSizeInUchar );
1377    memcpy( pCtu->getTransformSkip(ComponentID(comp))                 + m_absZIdxInCtu, m_puhTransformSkip[comp],              iSizeInUchar );
1378    memcpy( pCtu->getCbf(ComponentID(comp))                           + m_absZIdxInCtu, m_puhCbf[comp],                        iSizeInUchar );
1379    memcpy( pCtu->getExplicitRdpcmMode(ComponentID(comp))             + m_absZIdxInCtu, m_explicitRdpcmMode[comp],             iSizeInUchar );
1380  }
1381
1382#if NH_3D_DMM
1383  for( Int i = 0; i < NUM_DMM; i++ )
1384  {
1385    memcpy( pCtu->getDmmDeltaDC( (DmmID)i, 0 ) + m_absZIdxInCtu, m_dmmDeltaDC[i][0], sizeof(Pel ) * m_uiNumPartition );
1386    memcpy( pCtu->getDmmDeltaDC( (DmmID)i, 1 ) + m_absZIdxInCtu, m_dmmDeltaDC[i][1], sizeof(Pel ) * m_uiNumPartition );
1387  }
1388  memcpy( pCtu->getDmm1WedgeTabIdx()           + m_absZIdxInCtu, m_dmm1WedgeTabIdx,  sizeof(UInt) * m_uiNumPartition );
1389#endif
1390#if NH_3D_SDC_INTRA
1391  memcpy( pCtu->getSDCFlag()             + m_absZIdxInCtu, m_pbSDCFlag, sizeof(Bool) * m_uiNumPartition );
1392  memcpy( pCtu->getSDCSegmentDCOffset(0) + m_absZIdxInCtu, m_apSegmentDCOffset[0], sizeof( Pel ) * m_uiNumPartition);
1393  memcpy( pCtu->getSDCSegmentDCOffset(1) + m_absZIdxInCtu, m_apSegmentDCOffset[1], sizeof( Pel ) * m_uiNumPartition);
1394#endif
1395#if NH_3D_DBBP
1396  memcpy( pCtu->getDBBPFlag()          + m_absZIdxInCtu, m_pbDBBPFlag,          iSizeInBool  );
1397#endif
1398#if NH_3D_ARP
1399  memcpy( pCtu->getARPW()              + m_absZIdxInCtu, m_puhARPW,             iSizeInUchar );
1400#endif
1401
1402  memcpy( pCtu->getDepth()  + m_absZIdxInCtu, m_puhDepth,  iSizeInUchar );
1403  memcpy( pCtu->getWidth()  + m_absZIdxInCtu, m_puhWidth,  iSizeInUchar );
1404  memcpy( pCtu->getHeight() + m_absZIdxInCtu, m_puhHeight, iSizeInUchar );
1405
1406  for(UInt i=0; i<NUM_REF_PIC_LIST_01; i++)
1407  {
1408    const RefPicList rpl=RefPicList(i);
1409    memcpy( pCtu->getMVPIdx(rpl) + m_absZIdxInCtu, m_apiMVPIdx[rpl], iSizeInUchar );
1410    memcpy( pCtu->getMVPNum(rpl) + m_absZIdxInCtu, m_apiMVPNum[rpl], iSizeInUchar );
1411  }
1412
1413  for(UInt i=0; i<NUM_REF_PIC_LIST_01; i++)
1414  {
1415    const RefPicList rpl=RefPicList(i);
1416    m_acCUMvField[rpl].copyTo( pCtu->getCUMvField( rpl ), m_absZIdxInCtu );
1417  }
1418
1419  memcpy( pCtu->getIPCMFlag() + m_absZIdxInCtu, m_pbIPCMFlag,         iSizeInBool  );
1420
1421  const UInt numCoeffY    = (pCtu->getSlice()->getSPS()->getMaxCUWidth()*pCtu->getSlice()->getSPS()->getMaxCUHeight())>>(uhDepth<<1);
1422  const UInt offsetY      = m_absZIdxInCtu*m_pcPic->getMinCUWidth()*m_pcPic->getMinCUHeight();
1423  for (UInt comp=0; comp<numValidComp; comp++)
1424  {
1425    const ComponentID component = ComponentID(comp);
1426    const UInt componentShift   = m_pcPic->getComponentScaleX(component) + m_pcPic->getComponentScaleY(component);
1427    memcpy( pCtu->getCoeff(component)   + (offsetY>>componentShift), m_pcTrCoeff[component], sizeof(TCoeff)*(numCoeffY>>componentShift) );
1428#if ADAPTIVE_QP_SELECTION
1429    memcpy( pCtu->getArlCoeff(component) + (offsetY>>componentShift), m_pcArlCoeff[component], sizeof(TCoeff)*(numCoeffY>>componentShift) );
1430#endif
1431    memcpy( pCtu->getPCMSample(component) + (offsetY>>componentShift), m_pcIPCMSample[component], sizeof(Pel)*(numCoeffY>>componentShift) );
1432  }
1433
1434#if NH_3D_IC
1435  memcpy( pCtu->getICFlag() + m_absZIdxInCtu, m_pbICFlag, sizeof( *m_pbICFlag ) * m_uiNumPartition );
1436#endif
1437  pCtu->getTotalBins() = m_uiTotalBins;
1438}
1439#if H_3D_SPIVMP
1440  memcpy( rpcCU->getSPIVMPFlag()        + uiPartOffset, m_pbSPIVMPFlag,        sizeof(Bool) * uiQNumPart );
1441#endif
1442
1443
1444
1445// --------------------------------------------------------------------------------------------------------------------
1446// Other public functions
1447// --------------------------------------------------------------------------------------------------------------------
1448
1449const TComDataCU* TComDataCU::getPULeft( UInt& uiLPartUnitIdx,
1450                                   UInt uiCurrPartUnitIdx,
1451                                   Bool bEnforceSliceRestriction,
1452                                         Bool bEnforceTileRestriction ) const
1453{
1454  UInt uiAbsPartIdx       = g_auiZscanToRaster[uiCurrPartUnitIdx];
1455  UInt uiAbsZorderCUIdx   = g_auiZscanToRaster[m_absZIdxInCtu];
1456  const UInt numPartInCtuWidth = m_pcPic->getNumPartInCtuWidth();
1457
1458  if ( !RasterAddress::isZeroCol( uiAbsPartIdx, numPartInCtuWidth ) )
1459  {
1460    uiLPartUnitIdx = g_auiRasterToZscan[ uiAbsPartIdx - 1 ];
1461    if ( RasterAddress::isEqualCol( uiAbsPartIdx, uiAbsZorderCUIdx, numPartInCtuWidth ) )
1462    {
1463      return m_pcPic->getCtu( getCtuRsAddr() );
1464    }
1465    else
1466    {
1467      uiLPartUnitIdx -= m_absZIdxInCtu;
1468      return this;
1469    }
1470  }
1471
1472  uiLPartUnitIdx = g_auiRasterToZscan[ uiAbsPartIdx + numPartInCtuWidth - 1 ];
1473  if ( (bEnforceSliceRestriction && !CUIsFromSameSlice(m_pCtuLeft)) || (bEnforceTileRestriction && !CUIsFromSameTile(m_pCtuLeft)) )
1474  {
1475    return NULL;
1476  }
1477  return m_pCtuLeft;
1478}
1479
1480
1481const TComDataCU* TComDataCU::getPUAbove( UInt& uiAPartUnitIdx,
1482                                    UInt uiCurrPartUnitIdx,
1483                                    Bool bEnforceSliceRestriction,
1484                                    Bool planarAtCtuBoundary,
1485                                          Bool bEnforceTileRestriction ) const
1486{
1487  UInt uiAbsPartIdx       = g_auiZscanToRaster[uiCurrPartUnitIdx];
1488  UInt uiAbsZorderCUIdx   = g_auiZscanToRaster[m_absZIdxInCtu];
1489  const UInt numPartInCtuWidth = m_pcPic->getNumPartInCtuWidth();
1490
1491  if ( !RasterAddress::isZeroRow( uiAbsPartIdx, numPartInCtuWidth ) )
1492  {
1493    uiAPartUnitIdx = g_auiRasterToZscan[ uiAbsPartIdx - numPartInCtuWidth ];
1494    if ( RasterAddress::isEqualRow( uiAbsPartIdx, uiAbsZorderCUIdx, numPartInCtuWidth ) )
1495    {
1496      return m_pcPic->getCtu( getCtuRsAddr() );
1497    }
1498    else
1499    {
1500      uiAPartUnitIdx -= m_absZIdxInCtu;
1501      return this;
1502    }
1503  }
1504
1505  if(planarAtCtuBoundary)
1506  {
1507    return NULL;
1508  }
1509
1510  uiAPartUnitIdx = g_auiRasterToZscan[ uiAbsPartIdx + m_pcPic->getNumPartitionsInCtu() - numPartInCtuWidth ];
1511
1512  if ( (bEnforceSliceRestriction && !CUIsFromSameSlice(m_pCtuAbove)) || (bEnforceTileRestriction && !CUIsFromSameTile(m_pCtuAbove)) )
1513  {
1514    return NULL;
1515  }
1516  return m_pCtuAbove;
1517}
1518
1519const TComDataCU* TComDataCU::getPUAboveLeft( UInt& uiALPartUnitIdx, UInt uiCurrPartUnitIdx, Bool bEnforceSliceRestriction ) const
1520{
1521  UInt uiAbsPartIdx       = g_auiZscanToRaster[uiCurrPartUnitIdx];
1522  UInt uiAbsZorderCUIdx   = g_auiZscanToRaster[m_absZIdxInCtu];
1523  const UInt numPartInCtuWidth = m_pcPic->getNumPartInCtuWidth();
1524
1525  if ( !RasterAddress::isZeroCol( uiAbsPartIdx, numPartInCtuWidth ) )
1526  {
1527    if ( !RasterAddress::isZeroRow( uiAbsPartIdx, numPartInCtuWidth ) )
1528    {
1529      uiALPartUnitIdx = g_auiRasterToZscan[ uiAbsPartIdx - numPartInCtuWidth - 1 ];
1530      if ( RasterAddress::isEqualRowOrCol( uiAbsPartIdx, uiAbsZorderCUIdx, numPartInCtuWidth ) )
1531      {
1532        return m_pcPic->getCtu( getCtuRsAddr() );
1533      }
1534      else
1535      {
1536        uiALPartUnitIdx -= m_absZIdxInCtu;
1537        return this;
1538      }
1539    }
1540    uiALPartUnitIdx = g_auiRasterToZscan[ uiAbsPartIdx + getPic()->getNumPartitionsInCtu() - numPartInCtuWidth - 1 ];
1541    if ( bEnforceSliceRestriction && !CUIsFromSameSliceAndTile(m_pCtuAbove) )
1542    {
1543      return NULL;
1544    }
1545    return m_pCtuAbove;
1546  }
1547
1548  if ( !RasterAddress::isZeroRow( uiAbsPartIdx, numPartInCtuWidth ) )
1549  {
1550    uiALPartUnitIdx = g_auiRasterToZscan[ uiAbsPartIdx - 1 ];
1551    if ( bEnforceSliceRestriction && !CUIsFromSameSliceAndTile(m_pCtuLeft) )
1552    {
1553      return NULL;
1554    }
1555    return m_pCtuLeft;
1556  }
1557
1558  uiALPartUnitIdx = g_auiRasterToZscan[ m_pcPic->getNumPartitionsInCtu() - 1 ];
1559  if ( bEnforceSliceRestriction && !CUIsFromSameSliceAndTile(m_pCtuAboveLeft) )
1560  {
1561    return NULL;
1562  }
1563  return m_pCtuAboveLeft;
1564}
1565
1566const TComDataCU* TComDataCU::getPUBelowLeft(UInt& uiBLPartUnitIdx,  UInt uiCurrPartUnitIdx, UInt uiPartUnitOffset, Bool bEnforceSliceRestriction) const
1567{
1568  UInt uiAbsPartIdxLB     = g_auiZscanToRaster[uiCurrPartUnitIdx];
1569  const UInt numPartInCtuWidth = m_pcPic->getNumPartInCtuWidth();
1570  UInt uiAbsZorderCUIdxLB = g_auiZscanToRaster[ m_absZIdxInCtu ] + ((m_puhHeight[0] / m_pcPic->getMinCUHeight()) - 1)*numPartInCtuWidth;
1571
1572  if( ( m_pcPic->getCtu(m_ctuRsAddr)->getCUPelY() + g_auiRasterToPelY[uiAbsPartIdxLB] + (m_pcPic->getPicSym()->getMinCUHeight() * uiPartUnitOffset)) >= m_pcSlice->getSPS()->getPicHeightInLumaSamples())
1573  {
1574    uiBLPartUnitIdx = MAX_UINT;
1575    return NULL;
1576  }
1577
1578  if ( RasterAddress::lessThanRow( uiAbsPartIdxLB, m_pcPic->getNumPartInCtuHeight() - uiPartUnitOffset, numPartInCtuWidth ) )
1579  {
1580    if ( !RasterAddress::isZeroCol( uiAbsPartIdxLB, numPartInCtuWidth ) )
1581    {
1582      if ( uiCurrPartUnitIdx > g_auiRasterToZscan[ uiAbsPartIdxLB + uiPartUnitOffset * numPartInCtuWidth - 1 ] )
1583      {
1584        uiBLPartUnitIdx = g_auiRasterToZscan[ uiAbsPartIdxLB + uiPartUnitOffset * numPartInCtuWidth - 1 ];
1585        if ( RasterAddress::isEqualRowOrCol( uiAbsPartIdxLB, uiAbsZorderCUIdxLB, numPartInCtuWidth ) )
1586        {
1587          return m_pcPic->getCtu( getCtuRsAddr() );
1588        }
1589        else
1590        {
1591          uiBLPartUnitIdx -= m_absZIdxInCtu;
1592          return this;
1593        }
1594      }
1595      uiBLPartUnitIdx = MAX_UINT;
1596      return NULL;
1597    }
1598    uiBLPartUnitIdx = g_auiRasterToZscan[ uiAbsPartIdxLB + (1+uiPartUnitOffset) * numPartInCtuWidth - 1 ];
1599    if ( bEnforceSliceRestriction && !CUIsFromSameSliceAndTile(m_pCtuLeft) )
1600    {
1601      return NULL;
1602    }
1603    return m_pCtuLeft;
1604  }
1605
1606  uiBLPartUnitIdx = MAX_UINT;
1607  return NULL;
1608}
1609
1610const TComDataCU* TComDataCU::getPUAboveRight(UInt&  uiARPartUnitIdx, UInt uiCurrPartUnitIdx, UInt uiPartUnitOffset, Bool bEnforceSliceRestriction) const
1611{
1612  UInt uiAbsPartIdxRT     = g_auiZscanToRaster[uiCurrPartUnitIdx];
1613  UInt uiAbsZorderCUIdx   = g_auiZscanToRaster[ m_absZIdxInCtu ] + (m_puhWidth[0] / m_pcPic->getMinCUWidth()) - 1;
1614  const UInt numPartInCtuWidth = m_pcPic->getNumPartInCtuWidth();
1615
1616  if( ( m_pcPic->getCtu(m_ctuRsAddr)->getCUPelX() + g_auiRasterToPelX[uiAbsPartIdxRT] + (m_pcPic->getPicSym()->getMinCUHeight() * uiPartUnitOffset)) >= m_pcSlice->getSPS()->getPicWidthInLumaSamples() )
1617  {
1618    uiARPartUnitIdx = MAX_UINT;
1619    return NULL;
1620  }
1621
1622  if ( RasterAddress::lessThanCol( uiAbsPartIdxRT, numPartInCtuWidth - uiPartUnitOffset, numPartInCtuWidth ) )
1623  {
1624    if ( !RasterAddress::isZeroRow( uiAbsPartIdxRT, numPartInCtuWidth ) )
1625    {
1626      if ( uiCurrPartUnitIdx > g_auiRasterToZscan[ uiAbsPartIdxRT - numPartInCtuWidth + uiPartUnitOffset ] )
1627      {
1628        uiARPartUnitIdx = g_auiRasterToZscan[ uiAbsPartIdxRT - numPartInCtuWidth + uiPartUnitOffset ];
1629        if ( RasterAddress::isEqualRowOrCol( uiAbsPartIdxRT, uiAbsZorderCUIdx, numPartInCtuWidth ) )
1630        {
1631          return m_pcPic->getCtu( getCtuRsAddr() );
1632        }
1633        else
1634        {
1635          uiARPartUnitIdx -= m_absZIdxInCtu;
1636          return this;
1637        }
1638      }
1639      uiARPartUnitIdx = MAX_UINT;
1640      return NULL;
1641    }
1642
1643    uiARPartUnitIdx = g_auiRasterToZscan[ uiAbsPartIdxRT + m_pcPic->getNumPartitionsInCtu() - numPartInCtuWidth + uiPartUnitOffset ];
1644    if ( bEnforceSliceRestriction && !CUIsFromSameSliceAndTile(m_pCtuAbove) )
1645    {
1646      return NULL;
1647    }
1648    return m_pCtuAbove;
1649  }
1650
1651  if ( !RasterAddress::isZeroRow( uiAbsPartIdxRT, numPartInCtuWidth ) )
1652  {
1653    uiARPartUnitIdx = MAX_UINT;
1654    return NULL;
1655  }
1656
1657  uiARPartUnitIdx = g_auiRasterToZscan[ m_pcPic->getNumPartitionsInCtu() - numPartInCtuWidth + uiPartUnitOffset-1 ];
1658  if ( bEnforceSliceRestriction && !CUIsFromSameSliceAndTile(m_pCtuAboveRight) )
1659  {
1660    return NULL;
1661  }
1662  return m_pCtuAboveRight;
1663}
1664
1665/** Get left QpMinCu
1666*\param   uiLPartUnitIdx
1667*\param   uiCurrAbsIdxInCtu
1668*\returns TComDataCU*   point of TComDataCU of left QpMinCu
1669*/
1670const TComDataCU* TComDataCU::getQpMinCuLeft( UInt& uiLPartUnitIdx, UInt uiCurrAbsIdxInCtu ) const
1671{
1672  const UInt numPartInCtuWidth = m_pcPic->getNumPartInCtuWidth();
1673  const UInt maxCUDepth        = getSlice()->getSPS()->getMaxTotalCUDepth();
1674  const UInt maxCuDQPDepth     = getSlice()->getPPS()->getMaxCuDQPDepth();
1675  const UInt doubleDepthDifference = ((maxCUDepth - maxCuDQPDepth)<<1);
1676  UInt absZorderQpMinCUIdx = (uiCurrAbsIdxInCtu>>doubleDepthDifference)<<doubleDepthDifference;
1677  UInt absRorderQpMinCUIdx = g_auiZscanToRaster[absZorderQpMinCUIdx];
1678
1679  // check for left CTU boundary
1680  if ( RasterAddress::isZeroCol(absRorderQpMinCUIdx, numPartInCtuWidth) )
1681  {
1682    return NULL;
1683  }
1684
1685  // get index of left-CU relative to top-left corner of current quantization group
1686  uiLPartUnitIdx = g_auiRasterToZscan[absRorderQpMinCUIdx - 1];
1687
1688  // return pointer to current CTU
1689  return m_pcPic->getCtu( getCtuRsAddr() );
1690}
1691
1692/** Get Above QpMinCu
1693*\param   uiAPartUnitIdx
1694*\param   uiCurrAbsIdxInCtu
1695*\returns TComDataCU*   point of TComDataCU of above QpMinCu
1696*/
1697const TComDataCU* TComDataCU::getQpMinCuAbove( UInt& uiAPartUnitIdx, UInt uiCurrAbsIdxInCtu ) const
1698{
1699  const UInt numPartInCtuWidth = m_pcPic->getNumPartInCtuWidth();
1700  const UInt maxCUDepth        = getSlice()->getSPS()->getMaxTotalCUDepth();
1701  const UInt maxCuDQPDepth     = getSlice()->getPPS()->getMaxCuDQPDepth();
1702  const UInt doubleDepthDifference = ((maxCUDepth - maxCuDQPDepth)<<1);
1703  UInt absZorderQpMinCUIdx = (uiCurrAbsIdxInCtu>>doubleDepthDifference)<<doubleDepthDifference;
1704  UInt absRorderQpMinCUIdx = g_auiZscanToRaster[absZorderQpMinCUIdx];
1705
1706  // check for top CTU boundary
1707  if ( RasterAddress::isZeroRow( absRorderQpMinCUIdx, numPartInCtuWidth) )
1708  {
1709    return NULL;
1710  }
1711
1712  // get index of top-CU relative to top-left corner of current quantization group
1713  uiAPartUnitIdx = g_auiRasterToZscan[absRorderQpMinCUIdx - numPartInCtuWidth];
1714
1715  // return pointer to current CTU
1716  return m_pcPic->getCtu( getCtuRsAddr() );
1717}
1718
1719
1720
1721/** Get reference QP from left QpMinCu or latest coded QP
1722*\param   uiCurrAbsIdxInCtu
1723*\returns SChar   reference QP value
1724*/
1725SChar TComDataCU::getRefQP( UInt uiCurrAbsIdxInCtu ) const
1726{
1727  UInt lPartIdx = MAX_UINT;
1728  UInt aPartIdx = MAX_UINT;
1729  const TComDataCU* cULeft  = getQpMinCuLeft ( lPartIdx, m_absZIdxInCtu + uiCurrAbsIdxInCtu );
1730  const TComDataCU* cUAbove = getQpMinCuAbove( aPartIdx, m_absZIdxInCtu + uiCurrAbsIdxInCtu );
1731  return (((cULeft? cULeft->getQP( lPartIdx ): getLastCodedQP( uiCurrAbsIdxInCtu )) + (cUAbove? cUAbove->getQP( aPartIdx ): getLastCodedQP( uiCurrAbsIdxInCtu )) + 1) >> 1);
1732}
1733
1734Int TComDataCU::getLastValidPartIdx( Int iAbsPartIdx ) const
1735{
1736  Int iLastValidPartIdx = iAbsPartIdx-1;
1737  while ( iLastValidPartIdx >= 0
1738       && getPredictionMode( iLastValidPartIdx ) == NUMBER_OF_PREDICTION_MODES )
1739  {
1740    UInt uiDepth = getDepth( iLastValidPartIdx );
1741    iLastValidPartIdx -= m_uiNumPartition>>(uiDepth<<1);
1742  }
1743  return iLastValidPartIdx;
1744}
1745
1746SChar TComDataCU::getLastCodedQP( UInt uiAbsPartIdx ) const
1747{
1748  UInt uiQUPartIdxMask = ~((1<<((getSlice()->getSPS()->getMaxTotalCUDepth() - getSlice()->getPPS()->getMaxCuDQPDepth())<<1))-1);
1749  Int iLastValidPartIdx = getLastValidPartIdx( uiAbsPartIdx&uiQUPartIdxMask ); // A idx will be invalid if it is off the right or bottom edge of the picture.
1750  // If this CU is in the first CTU of the slice and there is no valid part before this one, use slice QP
1751  if ( getPic()->getPicSym()->getCtuTsToRsAddrMap(getSlice()->getSliceCurStartCtuTsAddr()) == getCtuRsAddr() && Int(getZorderIdxInCtu())+iLastValidPartIdx<0)
1752  {
1753    return getSlice()->getSliceQp();
1754  }
1755  else if ( iLastValidPartIdx >= 0 )
1756  {
1757    // If there is a valid part within the current Sub-CU, use it
1758    return getQP( iLastValidPartIdx );
1759  }
1760  else
1761  {
1762    if ( getZorderIdxInCtu() > 0 )
1763    {
1764      // If this wasn't the first sub-cu within the Ctu, explore the CTU itself.
1765      return getPic()->getCtu( getCtuRsAddr() )->getLastCodedQP( getZorderIdxInCtu() ); // TODO - remove this recursion
1766    }
1767    else if ( getPic()->getPicSym()->getCtuRsToTsAddrMap(getCtuRsAddr()) > 0
1768      && CUIsFromSameSliceTileAndWavefrontRow(getPic()->getCtu(getPic()->getPicSym()->getCtuTsToRsAddrMap(getPic()->getPicSym()->getCtuRsToTsAddrMap(getCtuRsAddr())-1))) )
1769    {
1770      // If this isn't the first Ctu (how can it be due to the first 'if'?), and the previous Ctu is from the same tile, examine the previous Ctu.
1771      return getPic()->getCtu( getPic()->getPicSym()->getCtuTsToRsAddrMap(getPic()->getPicSym()->getCtuRsToTsAddrMap(getCtuRsAddr())-1) )->getLastCodedQP( getPic()->getNumPartitionsInCtu() );  // TODO - remove this recursion
1772    }
1773    else
1774    {
1775      // No other options available - use the slice-level QP.
1776      return getSlice()->getSliceQp();
1777    }
1778  }
1779}
1780
1781
1782/** Check whether the CU is coded in lossless coding mode.
1783 * \param   absPartIdx
1784 * \returns true if the CU is coded in lossless coding mode; false if otherwise
1785 */
1786Bool TComDataCU::isLosslessCoded(UInt absPartIdx) const
1787{
1788  return (getSlice()->getPPS()->getTransquantBypassEnableFlag() && getCUTransquantBypass (absPartIdx));
1789}
1790
1791
1792/** Get allowed chroma intra modes
1793*   - fills uiModeList with chroma intra modes
1794*
1795*\param   [in]  uiAbsPartIdx
1796*\param   [out] uiModeList pointer to chroma intra modes array
1797*/
1798Void TComDataCU::getAllowedChromaDir( UInt uiAbsPartIdx, UInt uiModeList[NUM_CHROMA_MODE] ) const
1799{
1800  uiModeList[0] = PLANAR_IDX;
1801  uiModeList[1] = VER_IDX;
1802  uiModeList[2] = HOR_IDX;
1803  uiModeList[3] = DC_IDX;
1804  uiModeList[4] = DM_CHROMA_IDX;
1805  assert(4<NUM_CHROMA_MODE);
1806
1807  UInt uiLumaMode = getIntraDir( CHANNEL_TYPE_LUMA, uiAbsPartIdx );
1808
1809  for( Int i = 0; i < NUM_CHROMA_MODE - 1; i++ )
1810  {
1811    if( uiLumaMode == uiModeList[i] )
1812    {
1813      uiModeList[i] = 34; // VER+8 mode
1814      break;
1815    }
1816  }
1817}
1818
1819/** Get most probable intra modes
1820*\param   uiAbsPartIdx    partition index
1821*\param   uiIntraDirPred  pointer to the array for MPM storage
1822*\param   compID          colour component ID
1823*\param   piMode          it is set with MPM mode in case both MPM are equal. It is used to restrict RD search at encode side.
1824*\returns Number of MPM
1825*/
1826Void TComDataCU::getIntraDirPredictor( UInt uiAbsPartIdx, Int uiIntraDirPred[NUM_MOST_PROBABLE_MODES], const ComponentID compID, Int* piMode ) const
1827{
1828  UInt        LeftPartIdx  = MAX_UINT;
1829  UInt        AbovePartIdx = MAX_UINT;
1830  Int         iLeftIntraDir, iAboveIntraDir;
1831  const TComSPS *sps=getSlice()->getSPS();
1832  const UInt partsPerMinCU = 1<<(2*(sps->getMaxTotalCUDepth() - sps->getLog2DiffMaxMinCodingBlockSize()));
1833
1834  const ChannelType chType = toChannelType(compID);
1835  const ChromaFormat chForm = getPic()->getChromaFormat();
1836  // Get intra direction of left PU
1837  const TComDataCU *pcCULeft = getPULeft( LeftPartIdx, m_absZIdxInCtu + uiAbsPartIdx );
1838
1839  if (isChroma(compID))
1840  {
1841    LeftPartIdx = getChromasCorrespondingPULumaIdx(LeftPartIdx, chForm, partsPerMinCU);
1842  }
1843  iLeftIntraDir  = pcCULeft ? ( pcCULeft->isIntra( LeftPartIdx ) ? pcCULeft->getIntraDir( chType, LeftPartIdx ) : DC_IDX ) : DC_IDX;
1844#if NH_3D_DMM
1845  mapDmmToIntraDir( iLeftIntraDir );
1846#endif
1847
1848  // Get intra direction of above PU
1849  const TComDataCU *pcCUAbove = getPUAbove( AbovePartIdx, m_absZIdxInCtu + uiAbsPartIdx, true, true );
1850
1851  if (isChroma(compID))
1852  {
1853    AbovePartIdx = getChromasCorrespondingPULumaIdx(AbovePartIdx, chForm, partsPerMinCU);
1854  }
1855  iAboveIntraDir = pcCUAbove ? ( pcCUAbove->isIntra( AbovePartIdx ) ? pcCUAbove->getIntraDir( chType, AbovePartIdx ) : DC_IDX ) : DC_IDX;
1856#if NH_3D_DMM
1857  mapDmmToIntraDir( iAboveIntraDir );
1858#endif
1859
1860
1861  if (isChroma(chType))
1862  {
1863    if (iLeftIntraDir  == DM_CHROMA_IDX)
1864    {
1865      iLeftIntraDir  = pcCULeft-> getIntraDir( CHANNEL_TYPE_LUMA, LeftPartIdx  );
1866    }
1867    if (iAboveIntraDir == DM_CHROMA_IDX)
1868    {
1869      iAboveIntraDir = pcCUAbove->getIntraDir( CHANNEL_TYPE_LUMA, AbovePartIdx );
1870    }
1871  }
1872
1873  assert (2<NUM_MOST_PROBABLE_MODES);
1874  if(iLeftIntraDir == iAboveIntraDir)
1875  {
1876    if( piMode )
1877    {
1878      *piMode = 1;
1879    }
1880
1881    if (iLeftIntraDir > 1) // angular modes
1882    {
1883      uiIntraDirPred[0] = iLeftIntraDir;
1884      uiIntraDirPred[1] = ((iLeftIntraDir + 29) % 32) + 2;
1885      uiIntraDirPred[2] = ((iLeftIntraDir - 1 ) % 32) + 2;
1886    }
1887    else //non-angular
1888    {
1889      uiIntraDirPred[0] = PLANAR_IDX;
1890      uiIntraDirPred[1] = DC_IDX;
1891      uiIntraDirPred[2] = VER_IDX;
1892    }
1893  }
1894  else
1895  {
1896    if( piMode )
1897    {
1898      *piMode = 2;
1899    }
1900    uiIntraDirPred[0] = iLeftIntraDir;
1901    uiIntraDirPred[1] = iAboveIntraDir;
1902
1903    if (iLeftIntraDir && iAboveIntraDir ) //both modes are non-planar
1904    {
1905      uiIntraDirPred[2] = PLANAR_IDX;
1906    }
1907    else
1908    {
1909      uiIntraDirPred[2] =  (iLeftIntraDir+iAboveIntraDir)<2? VER_IDX : DC_IDX;
1910    }
1911  }
1912  for (UInt i=0; i<NUM_MOST_PROBABLE_MODES; i++)
1913  {
1914    assert(uiIntraDirPred[i] < 35);
1915  }
1916}
1917
1918UInt TComDataCU::getCtxSplitFlag( UInt uiAbsPartIdx, UInt uiDepth ) const
1919{
1920  const TComDataCU* pcTempCU;
1921  UInt        uiTempPartIdx;
1922  UInt        uiCtx;
1923  // Get left split flag
1924  pcTempCU = getPULeft( uiTempPartIdx, m_absZIdxInCtu + uiAbsPartIdx );
1925  uiCtx  = ( pcTempCU ) ? ( ( pcTempCU->getDepth( uiTempPartIdx ) > uiDepth ) ? 1 : 0 ) : 0;
1926
1927  // Get above split flag
1928  pcTempCU = getPUAbove( uiTempPartIdx, m_absZIdxInCtu + uiAbsPartIdx );
1929  uiCtx += ( pcTempCU ) ? ( ( pcTempCU->getDepth( uiTempPartIdx ) > uiDepth ) ? 1 : 0 ) : 0;
1930
1931  return uiCtx;
1932}
1933
1934UInt TComDataCU::getCtxQtCbf( TComTU &rTu, const ChannelType chType ) const
1935{
1936  const UInt transformDepth = rTu.GetTransformDepthRel();
1937
1938  if (isChroma(chType))
1939  {
1940    return transformDepth;
1941  }
1942  else
1943  {
1944    const UInt uiCtx = ( transformDepth == 0 ? 1 : 0 );
1945    return uiCtx;
1946  }
1947}
1948
1949UInt TComDataCU::getQuadtreeTULog2MinSizeInCU( UInt absPartIdx ) const
1950{
1951  UInt log2CbSize = g_aucConvertToBit[getWidth( absPartIdx )] + 2;
1952  PartSize  partSize  = getPartitionSize( absPartIdx );
1953  UInt quadtreeTUMaxDepth = isIntra( absPartIdx ) ? m_pcSlice->getSPS()->getQuadtreeTUMaxDepthIntra() : m_pcSlice->getSPS()->getQuadtreeTUMaxDepthInter();
1954  Int intraSplitFlag = ( isIntra( absPartIdx ) && partSize == SIZE_NxN ) ? 1 : 0;
1955  Int interSplitFlag = ((quadtreeTUMaxDepth == 1) && isInter( absPartIdx ) && (partSize != SIZE_2Nx2N) );
1956
1957  UInt log2MinTUSizeInCU = 0;
1958  if (log2CbSize < (m_pcSlice->getSPS()->getQuadtreeTULog2MinSize() + quadtreeTUMaxDepth - 1 + interSplitFlag + intraSplitFlag) )
1959  {
1960    // when fully making use of signaled TUMaxDepth + inter/intraSplitFlag, resulting luma TB size is < QuadtreeTULog2MinSize
1961    log2MinTUSizeInCU = m_pcSlice->getSPS()->getQuadtreeTULog2MinSize();
1962  }
1963  else
1964  {
1965    // when fully making use of signaled TUMaxDepth + inter/intraSplitFlag, resulting luma TB size is still >= QuadtreeTULog2MinSize
1966    log2MinTUSizeInCU = log2CbSize - ( quadtreeTUMaxDepth - 1 + interSplitFlag + intraSplitFlag); // stop when trafoDepth == hierarchy_depth = splitFlag
1967    if ( log2MinTUSizeInCU > m_pcSlice->getSPS()->getQuadtreeTULog2MaxSize())
1968    {
1969      // when fully making use of signaled TUMaxDepth + inter/intraSplitFlag, resulting luma TB size is still > QuadtreeTULog2MaxSize
1970      log2MinTUSizeInCU = m_pcSlice->getSPS()->getQuadtreeTULog2MaxSize();
1971    }
1972  }
1973  return log2MinTUSizeInCU;
1974}
1975
1976UInt TComDataCU::getCtxSkipFlag( UInt uiAbsPartIdx ) const
1977{
1978  const TComDataCU* pcTempCU;
1979  UInt        uiTempPartIdx;
1980  UInt        uiCtx = 0;
1981
1982  // Get BCBP of left PU
1983  pcTempCU = getPULeft( uiTempPartIdx, m_absZIdxInCtu + uiAbsPartIdx );
1984  uiCtx    = ( pcTempCU ) ? pcTempCU->isSkipped( uiTempPartIdx ) : 0;
1985
1986  // Get BCBP of above PU
1987  pcTempCU = getPUAbove( uiTempPartIdx, m_absZIdxInCtu + uiAbsPartIdx );
1988  uiCtx   += ( pcTempCU ) ? pcTempCU->isSkipped( uiTempPartIdx ) : 0;
1989
1990  return uiCtx;
1991}
1992#if NH_3D_ARP
1993UInt TComDataCU::getCTXARPWFlag( UInt uiAbsPartIdx )
1994{
1995  const TComDataCU* pcTempCU;
1996  UInt        uiTempPartIdx;
1997  UInt        uiCtx = 0;
1998
1999  pcTempCU = getPULeft( uiTempPartIdx, m_absZIdxInCtu + uiAbsPartIdx );
2000  uiCtx    = ( pcTempCU ) ? ((pcTempCU->getARPW( uiTempPartIdx )==0)?0:1) : 0;
2001  return uiCtx;
2002}
2003#endif
2004#if NH_3D_DBBP
2005Pel* TComDataCU::getVirtualDepthBlock(UInt uiAbsPartIdx, UInt uiWidth, UInt uiHeight, UInt& uiDepthStride)
2006{
2007  const TComSPS* sps = getSlice()->getSPS();
2008  UInt uiMaxCUWidth = sps->getMaxCUWidth();
2009  UInt uiMaxCUHeight = sps->getMaxCUHeight();
2010 
2011  // get coded and reconstructed depth view
2012  TComPicYuv* depthPicYuv = NULL;
2013  Pel* pDepthPels = NULL;
2014 
2015  // DBBP is a texture coding tool
2016  assert( !getSlice()->getIsDepth() );
2017 
2018#if H_3D_FCO
2019  TComPic* depthPic = getSlice()->getIvPic(true, getSlice()->getViewIndex() );
2020 
2021  if( depthPic && depthPic->getPicYuvRec() != NULL && depthPic->getIsDepth() )  // depth first
2022  {
2023    depthPicYuv = depthPic->getPicYuvRec();
2024    depthPicYuv->extendPicBorder();
2025   
2026    // get collocated depth block for current CU
2027    uiDepthStride = depthPicYuv->getStride();
2028    pDepthPels    = depthPicYuv->getLumaAddr( getAddr(), uiAbsPartIdx );
2029  }
2030  else  // texture first
2031#else
2032  {
2033    DisInfo DvInfo = getDvInfo(uiAbsPartIdx);
2034   
2035    TComPic* baseDepthPic = getSlice()->getIvPic (true, DvInfo.m_aVIdxCan);
2036   
2037    if( baseDepthPic == NULL || baseDepthPic->getPicYuvRec() == NULL )
2038    {
2039      return NULL;
2040    }
2041   
2042    depthPicYuv   = baseDepthPic->getPicYuvRec();
2043    depthPicYuv->extendPicBorder();
2044    uiDepthStride = depthPicYuv->getStride(COMPONENT_Y);
2045   
2046    Int iBlkX = ( getCtuRsAddr() % baseDepthPic->getFrameWidthInCtus() ) * uiMaxCUWidth  + g_auiRasterToPelX[ g_auiZscanToRaster[ getZorderIdxInCtu()+uiAbsPartIdx ] ];
2047    Int iBlkY = ( getCtuRsAddr() / baseDepthPic->getFrameWidthInCtus() ) * uiMaxCUHeight + g_auiRasterToPelY[ g_auiZscanToRaster[ getZorderIdxInCtu()+uiAbsPartIdx ] ];
2048   
2049    Int iPictureWidth  = depthPicYuv->getWidth(COMPONENT_Y);
2050    Int iPictureHeight = depthPicYuv->getHeight(COMPONENT_Y);
2051   
2052   
2053    Bool depthRefineFlag = false;
2054#if NH_3D_NBDV_REF
2055    depthRefineFlag = m_pcSlice->getDepthRefinementFlag();
2056#endif // NH_3D_NBDV_REF
2057   
2058    TComMv cDv = depthRefineFlag ? DvInfo.m_acDoNBDV : DvInfo.m_acNBDV;
2059    if( depthRefineFlag )
2060    {
2061      cDv.setVer(0);
2062    }
2063   
2064    Int depthPosX = Clip3(0,   iPictureWidth - 1,  iBlkX + ((cDv.getHor()+2)>>2));
2065    Int depthPosY = Clip3(0,   iPictureHeight - 1, iBlkY + ((cDv.getVer()+2)>>2));
2066   
2067    pDepthPels = depthPicYuv->getAddr(COMPONENT_Y) + depthPosX + depthPosY * uiDepthStride;
2068  }
2069#endif
2070 
2071  AOF( depthPicYuv != NULL );
2072  AOF( pDepthPels != NULL );
2073  AOF( uiDepthStride != 0 );
2074 
2075  return pDepthPels;
2076}
2077#endif
2078
2079#if NH_3D_DBBP
2080Void TComDataCU::setDBBPFlagSubParts ( Bool bDBBPFlag, UInt uiAbsPartIdx, UInt uiPartIdx, UInt uiDepth )
2081{
2082  setSubPart( bDBBPFlag, m_pbDBBPFlag, uiAbsPartIdx, uiDepth, uiPartIdx );
2083}
2084#endif
2085
2086
2087UInt TComDataCU::getCtxInterDir( UInt uiAbsPartIdx ) const
2088{
2089  return getDepth( uiAbsPartIdx );
2090}
2091
2092
2093UChar TComDataCU::getQtRootCbf( UInt uiIdx ) const
2094{
2095  const UInt numberValidComponents = getPic()->getNumberValidComponents();
2096  return getCbf( uiIdx, COMPONENT_Y, 0 )
2097          || ((numberValidComponents > COMPONENT_Cb) && getCbf( uiIdx, COMPONENT_Cb, 0 ))
2098          || ((numberValidComponents > COMPONENT_Cr) && getCbf( uiIdx, COMPONENT_Cr, 0 ));
2099}
2100
2101Void TComDataCU::setCbfSubParts( const UInt uiCbf[MAX_NUM_COMPONENT], UInt uiAbsPartIdx, UInt uiDepth )
2102{
2103  UInt uiCurrPartNumb = m_pcPic->getNumPartitionsInCtu() >> (uiDepth << 1);
2104  for(UInt comp=0; comp<MAX_NUM_COMPONENT; comp++)
2105  {
2106    memset( m_puhCbf[comp] + uiAbsPartIdx, uiCbf[comp], sizeof( UChar ) * uiCurrPartNumb );
2107  }
2108}
2109
2110Void TComDataCU::setCbfSubParts( UInt uiCbf, ComponentID compID, UInt uiAbsPartIdx, UInt uiDepth )
2111{
2112  UInt uiCurrPartNumb = m_pcPic->getNumPartitionsInCtu() >> (uiDepth << 1);
2113  memset( m_puhCbf[compID] + uiAbsPartIdx, uiCbf, sizeof( UChar ) * uiCurrPartNumb );
2114}
2115
2116/** Sets a coded block flag for all sub-partitions of a partition
2117 * \param uiCbf          The value of the coded block flag to be set
2118 * \param compID
2119 * \param uiAbsPartIdx
2120 * \param uiPartIdx
2121 * \param uiDepth
2122 */
2123Void TComDataCU::setCbfSubParts ( UInt uiCbf, ComponentID compID, UInt uiAbsPartIdx, UInt uiPartIdx, UInt uiDepth )
2124{
2125  setSubPart<UChar>( uiCbf, m_puhCbf[compID], uiAbsPartIdx, uiDepth, uiPartIdx );
2126}
2127
2128Void TComDataCU::setCbfPartRange ( UInt uiCbf, ComponentID compID, UInt uiAbsPartIdx, UInt uiCoveredPartIdxes )
2129{
2130  memset((m_puhCbf[compID] + uiAbsPartIdx), uiCbf, (sizeof(UChar) * uiCoveredPartIdxes));
2131}
2132
2133Void TComDataCU::bitwiseOrCbfPartRange( UInt uiCbf, ComponentID compID, UInt uiAbsPartIdx, UInt uiCoveredPartIdxes )
2134{
2135  const UInt stopAbsPartIdx = uiAbsPartIdx + uiCoveredPartIdxes;
2136
2137  for (UInt subPartIdx = uiAbsPartIdx; subPartIdx < stopAbsPartIdx; subPartIdx++)
2138  {
2139    m_puhCbf[compID][subPartIdx] |= uiCbf;
2140  }
2141}
2142
2143Void TComDataCU::setDepthSubParts( UInt uiDepth, UInt uiAbsPartIdx )
2144{
2145  UInt uiCurrPartNumb = m_pcPic->getNumPartitionsInCtu() >> (uiDepth << 1);
2146  memset( m_puhDepth + uiAbsPartIdx, uiDepth, sizeof(UChar)*uiCurrPartNumb );
2147}
2148
2149Bool TComDataCU::isFirstAbsZorderIdxInDepth (UInt uiAbsPartIdx, UInt uiDepth) const
2150{
2151  UInt uiPartNumb = m_pcPic->getNumPartitionsInCtu() >> (uiDepth << 1);
2152  return (((m_absZIdxInCtu + uiAbsPartIdx)% uiPartNumb) == 0);
2153}
2154
2155Void TComDataCU::setPartSizeSubParts( PartSize eMode, UInt uiAbsPartIdx, UInt uiDepth )
2156{
2157  assert( sizeof( *m_pePartSize) == 1 );
2158  memset( m_pePartSize + uiAbsPartIdx, eMode, m_pcPic->getNumPartitionsInCtu() >> ( 2 * uiDepth ) );
2159}
2160
2161Void TComDataCU::setCUTransquantBypassSubParts( Bool flag, UInt uiAbsPartIdx, UInt uiDepth )
2162{
2163  memset( m_CUTransquantBypass + uiAbsPartIdx, flag, m_pcPic->getNumPartitionsInCtu() >> ( 2 * uiDepth ) );
2164}
2165
2166Void TComDataCU::setSkipFlagSubParts( Bool skip, UInt absPartIdx, UInt depth )
2167{
2168  assert( sizeof( *m_skipFlag) == 1 );
2169  memset( m_skipFlag + absPartIdx, skip, m_pcPic->getNumPartitionsInCtu() >> ( 2 * depth ) );
2170}
2171
2172#if NH_3D_DIS
2173Void TComDataCU::setDISFlagSubParts( Bool bDIS, UInt uiAbsPartIdx, UInt uiDepth )
2174{
2175    assert( sizeof( *m_bDISFlag) == 1 );
2176    memset( m_bDISFlag + uiAbsPartIdx, bDIS, m_pcPic->getNumPartitionsInCtu() >> ( 2 * uiDepth ) );
2177}
2178
2179Void TComDataCU::setDISTypeSubParts(UChar ucDISType, UInt uiAbsPartIdx, UInt uiDepth )
2180{
2181  assert( sizeof( *m_ucDISType) == 1 );
2182  memset( m_ucDISType + uiAbsPartIdx, ucDISType, m_pcPic->getNumPartitionsInCtu() >> ( 2 * uiDepth ) );
2183}
2184#endif
2185
2186Void TComDataCU::setPredModeSubParts( PredMode eMode, UInt uiAbsPartIdx, UInt uiDepth )
2187{
2188  assert( sizeof( *m_pePredMode) == 1 );
2189  memset( m_pePredMode + uiAbsPartIdx, eMode, m_pcPic->getNumPartitionsInCtu() >> ( 2 * uiDepth ) );
2190}
2191
2192Void TComDataCU::setChromaQpAdjSubParts( UChar val, Int absPartIdx, Int depth )
2193{
2194  assert( sizeof(*m_ChromaQpAdj) == 1 );
2195  memset( m_ChromaQpAdj + absPartIdx, val, m_pcPic->getNumPartitionsInCtu() >> ( 2 * depth ) );
2196}
2197
2198Void TComDataCU::setQPSubCUs( Int qp, UInt absPartIdx, UInt depth, Bool &foundNonZeroCbf )
2199{
2200  UInt currPartNumb = m_pcPic->getNumPartitionsInCtu() >> (depth << 1);
2201  UInt currPartNumQ = currPartNumb >> 2;
2202  const UInt numValidComp = m_pcPic->getNumberValidComponents();
2203
2204  if(!foundNonZeroCbf)
2205  {
2206    if(getDepth(absPartIdx) > depth)
2207    {
2208      for ( UInt partUnitIdx = 0; partUnitIdx < 4; partUnitIdx++ )
2209      {
2210        setQPSubCUs( qp, absPartIdx+partUnitIdx*currPartNumQ, depth+1, foundNonZeroCbf );
2211      }
2212    }
2213    else
2214    {
2215      if(getCbf( absPartIdx, COMPONENT_Y ) || (numValidComp>COMPONENT_Cb && getCbf( absPartIdx, COMPONENT_Cb )) || (numValidComp>COMPONENT_Cr && getCbf( absPartIdx, COMPONENT_Cr) ) )
2216      {
2217        foundNonZeroCbf = true;
2218      }
2219      else
2220      {
2221        setQPSubParts(qp, absPartIdx, depth);
2222      }
2223    }
2224  }
2225}
2226
2227Void TComDataCU::setQPSubParts( Int qp, UInt uiAbsPartIdx, UInt uiDepth )
2228{
2229  const UInt numPart = m_pcPic->getNumPartitionsInCtu() >> (uiDepth << 1);
2230  memset(m_phQP+uiAbsPartIdx, qp, numPart);
2231}
2232
2233Void TComDataCU::setIntraDirSubParts( const ChannelType channelType, const UInt dir, const UInt absPartIdx, const UInt depth )
2234{
2235  UInt numPart = m_pcPic->getNumPartitionsInCtu() >> (depth << 1);
2236  memset( m_puhIntraDir[channelType] + absPartIdx, dir,sizeof(UChar)*numPart );
2237}
2238
2239template<typename T>
2240Void TComDataCU::setSubPart( T uiParameter, T* puhBaseCtu, UInt uiCUAddr, UInt uiCUDepth, UInt uiPUIdx )
2241{
2242  assert( sizeof(T) == 1 ); // Using memset() works only for types of size 1
2243
2244  UInt uiCurrPartNumQ = (m_pcPic->getNumPartitionsInCtu() >> (2 * uiCUDepth)) >> 2;
2245  switch ( m_pePartSize[ uiCUAddr ] )
2246  {
2247    case SIZE_2Nx2N:
2248      memset( puhBaseCtu + uiCUAddr, uiParameter, 4 * uiCurrPartNumQ );
2249      break;
2250    case SIZE_2NxN:
2251      memset( puhBaseCtu + uiCUAddr, uiParameter, 2 * uiCurrPartNumQ );
2252      break;
2253    case SIZE_Nx2N:
2254      memset( puhBaseCtu + uiCUAddr, uiParameter, uiCurrPartNumQ );
2255      memset( puhBaseCtu + uiCUAddr + 2 * uiCurrPartNumQ, uiParameter, uiCurrPartNumQ );
2256      break;
2257    case SIZE_NxN:
2258      memset( puhBaseCtu + uiCUAddr, uiParameter, uiCurrPartNumQ );
2259      break;
2260    case SIZE_2NxnU:
2261      if ( uiPUIdx == 0 )
2262      {
2263        memset( puhBaseCtu + uiCUAddr, uiParameter, (uiCurrPartNumQ >> 1) );
2264        memset( puhBaseCtu + uiCUAddr + uiCurrPartNumQ, uiParameter, (uiCurrPartNumQ >> 1) );
2265      }
2266      else if ( uiPUIdx == 1 )
2267      {
2268        memset( puhBaseCtu + uiCUAddr, uiParameter, (uiCurrPartNumQ >> 1) );
2269        memset( puhBaseCtu + uiCUAddr + uiCurrPartNumQ, uiParameter, ((uiCurrPartNumQ >> 1) + (uiCurrPartNumQ << 1)) );
2270      }
2271      else
2272      {
2273        assert(0);
2274      }
2275      break;
2276    case SIZE_2NxnD:
2277      if ( uiPUIdx == 0 )
2278      {
2279        memset( puhBaseCtu + uiCUAddr, uiParameter, ((uiCurrPartNumQ << 1) + (uiCurrPartNumQ >> 1)) );
2280        memset( puhBaseCtu + uiCUAddr + (uiCurrPartNumQ << 1) + uiCurrPartNumQ, uiParameter, (uiCurrPartNumQ >> 1) );
2281      }
2282      else if ( uiPUIdx == 1 )
2283      {
2284        memset( puhBaseCtu + uiCUAddr, uiParameter, (uiCurrPartNumQ >> 1) );
2285        memset( puhBaseCtu + uiCUAddr + uiCurrPartNumQ, uiParameter, (uiCurrPartNumQ >> 1) );
2286      }
2287      else
2288      {
2289        assert(0);
2290      }
2291      break;
2292    case SIZE_nLx2N:
2293      if ( uiPUIdx == 0 )
2294      {
2295        memset( puhBaseCtu + uiCUAddr, uiParameter, (uiCurrPartNumQ >> 2) );
2296        memset( puhBaseCtu + uiCUAddr + (uiCurrPartNumQ >> 1), uiParameter, (uiCurrPartNumQ >> 2) );
2297        memset( puhBaseCtu + uiCUAddr + (uiCurrPartNumQ << 1), uiParameter, (uiCurrPartNumQ >> 2) );
2298        memset( puhBaseCtu + uiCUAddr + (uiCurrPartNumQ << 1) + (uiCurrPartNumQ >> 1), uiParameter, (uiCurrPartNumQ >> 2) );
2299      }
2300      else if ( uiPUIdx == 1 )
2301      {
2302        memset( puhBaseCtu + uiCUAddr, uiParameter, (uiCurrPartNumQ >> 2) );
2303        memset( puhBaseCtu + uiCUAddr + (uiCurrPartNumQ >> 1), uiParameter, (uiCurrPartNumQ + (uiCurrPartNumQ >> 2)) );
2304        memset( puhBaseCtu + uiCUAddr + (uiCurrPartNumQ << 1), uiParameter, (uiCurrPartNumQ >> 2) );
2305        memset( puhBaseCtu + uiCUAddr + (uiCurrPartNumQ << 1) + (uiCurrPartNumQ >> 1), uiParameter, (uiCurrPartNumQ + (uiCurrPartNumQ >> 2)) );
2306      }
2307      else
2308      {
2309        assert(0);
2310      }
2311      break;
2312    case SIZE_nRx2N:
2313      if ( uiPUIdx == 0 )
2314      {
2315        memset( puhBaseCtu + uiCUAddr, uiParameter, (uiCurrPartNumQ + (uiCurrPartNumQ >> 2)) );
2316        memset( puhBaseCtu + uiCUAddr + uiCurrPartNumQ + (uiCurrPartNumQ >> 1), uiParameter, (uiCurrPartNumQ >> 2) );
2317        memset( puhBaseCtu + uiCUAddr + (uiCurrPartNumQ << 1), uiParameter, (uiCurrPartNumQ + (uiCurrPartNumQ >> 2)) );
2318        memset( puhBaseCtu + uiCUAddr + (uiCurrPartNumQ << 1) + uiCurrPartNumQ + (uiCurrPartNumQ >> 1), uiParameter, (uiCurrPartNumQ >> 2) );
2319      }
2320      else if ( uiPUIdx == 1 )
2321      {
2322        memset( puhBaseCtu + uiCUAddr, uiParameter, (uiCurrPartNumQ >> 2) );
2323        memset( puhBaseCtu + uiCUAddr + (uiCurrPartNumQ >> 1), uiParameter, (uiCurrPartNumQ >> 2) );
2324        memset( puhBaseCtu + uiCUAddr + (uiCurrPartNumQ << 1), uiParameter, (uiCurrPartNumQ >> 2) );
2325        memset( puhBaseCtu + uiCUAddr + (uiCurrPartNumQ << 1) + (uiCurrPartNumQ >> 1), uiParameter, (uiCurrPartNumQ >> 2) );
2326      }
2327      else
2328      {
2329        assert(0);
2330      }
2331      break;
2332    default:
2333      assert( 0 );
2334      break;
2335  }
2336}
2337
2338#if NH_3D_SDC_INTRA
2339Void TComDataCU::setSDCFlagSubParts ( Bool bSDCFlag, UInt absPartIdx, UInt depth )
2340{
2341  assert( sizeof( *m_pbSDCFlag) == 1 );
2342  memset( m_pbSDCFlag + absPartIdx, bSDCFlag, m_pcPic->getNumPartitionsInCtu() >> ( 2 * depth ) );
2343}
2344
2345Bool TComDataCU::getSDCAvailable( UInt uiAbsPartIdx )
2346{
2347  if( getSlice()->getIsDepth() && isIntra(uiAbsPartIdx) && getPartitionSize(uiAbsPartIdx) == SIZE_2Nx2N )
2348  {
2349    UInt lumaPredMode = getIntraDir( CHANNEL_TYPE_LUMA, uiAbsPartIdx );
2350    if( lumaPredMode < NUM_INTRA_MODE ) { return true; }
2351#if NH_3D_DMM
2352    if( isDmmMode( lumaPredMode )     ) { return true; }
2353#endif
2354  }
2355  return false;
2356}
2357#endif
2358
2359Void TComDataCU::setMergeFlagSubParts ( Bool bMergeFlag, UInt uiAbsPartIdx, UInt uiPartIdx, UInt uiDepth )
2360{
2361  setSubPart( bMergeFlag, m_pbMergeFlag, uiAbsPartIdx, uiDepth, uiPartIdx );
2362}
2363
2364Void TComDataCU::setMergeIndexSubParts ( UInt uiMergeIndex, UInt uiAbsPartIdx, UInt uiPartIdx, UInt uiDepth )
2365{
2366  setSubPart<UChar>( uiMergeIndex, m_puhMergeIndex, uiAbsPartIdx, uiDepth, uiPartIdx );
2367}
2368
2369#if NH_3D_SPIVMP
2370Void TComDataCU::setSPIVMPFlagSubParts( Bool bSPIVMPFlag, UInt uiAbsPartIdx, UInt uiPartIdx, UInt uiDepth )
2371{
2372  setSubPart<Bool>( bSPIVMPFlag, m_pbSPIVMPFlag, uiAbsPartIdx, uiDepth, uiPartIdx );
2373}
2374#endif
2375
2376#if NH_3D_VSP
2377Void TComDataCU::setVSPFlagSubParts( SChar iVSPFlag, UInt uiAbsPartIdx, UInt uiPartIdx, UInt uiDepth )
2378{
2379  setSubPart<SChar>( iVSPFlag, m_piVSPFlag, uiAbsPartIdx, uiDepth, uiPartIdx );
2380}
2381template<typename T>
2382Void TComDataCU::setSubPartT( T uiParameter, T* puhBaseLCU, UInt uiCUAddr, UInt uiCUDepth, UInt uiPUIdx )
2383{
2384  UInt uiCurrPartNumQ = (m_pcPic->getNumPartitionsInCtu() >> (2 * uiCUDepth)) >> 2;
2385  switch ( m_pePartSize[ uiCUAddr ] )
2386  {
2387  case SIZE_2Nx2N:
2388    for (UInt ui = 0; ui < 4 * uiCurrPartNumQ; ui++)
2389      puhBaseLCU[uiCUAddr + ui] = uiParameter;
2390
2391    break;
2392  case SIZE_2NxN:
2393    for (UInt ui = 0; ui < 2 * uiCurrPartNumQ; ui++)
2394      puhBaseLCU[uiCUAddr + ui] = uiParameter;
2395    break;
2396  case SIZE_Nx2N:
2397    for (UInt ui = 0; ui < uiCurrPartNumQ; ui++)
2398      puhBaseLCU[uiCUAddr + ui] = uiParameter;
2399    for (UInt ui = 0; ui < uiCurrPartNumQ; ui++)
2400      puhBaseLCU[uiCUAddr + 2 * uiCurrPartNumQ + ui] = uiParameter;
2401    break;
2402  case SIZE_NxN:
2403    for (UInt ui = 0; ui < uiCurrPartNumQ; ui++)
2404      puhBaseLCU[uiCUAddr + ui] = uiParameter;
2405    break;
2406  case SIZE_2NxnU:
2407    if ( uiPUIdx == 0 )
2408    {
2409      for (UInt ui = 0; ui < (uiCurrPartNumQ >> 1); ui++)
2410        puhBaseLCU[uiCUAddr + ui] = uiParameter;
2411      for (UInt ui = 0; ui < (uiCurrPartNumQ >> 1); ui++)
2412        puhBaseLCU[uiCUAddr + uiCurrPartNumQ + ui] = uiParameter;
2413
2414    }
2415    else if ( uiPUIdx == 1 )
2416    {
2417      for (UInt ui = 0; ui < (uiCurrPartNumQ >> 1); ui++)
2418        puhBaseLCU[uiCUAddr + ui] = uiParameter;
2419      for (UInt ui = 0; ui < (uiCurrPartNumQ >> 1) + (uiCurrPartNumQ << 1); ui++)
2420        puhBaseLCU[uiCUAddr + uiCurrPartNumQ + ui] = uiParameter;
2421
2422    }
2423    else
2424    {
2425      assert(0);
2426    }
2427    break;
2428  case SIZE_2NxnD:
2429    if ( uiPUIdx == 0 )
2430    {
2431      for (UInt ui = 0; ui < ((uiCurrPartNumQ << 1) + (uiCurrPartNumQ >> 1)); ui++)
2432        puhBaseLCU[uiCUAddr + ui] = uiParameter;
2433      for (UInt ui = 0; ui < (uiCurrPartNumQ >> 1); ui++)
2434        puhBaseLCU[uiCUAddr + (uiCurrPartNumQ << 1) + uiCurrPartNumQ + ui] = uiParameter;
2435
2436    }
2437    else if ( uiPUIdx == 1 )
2438    {
2439      for (UInt ui = 0; ui < (uiCurrPartNumQ >> 1); ui++)
2440        puhBaseLCU[uiCUAddr + ui] = uiParameter;
2441      for (UInt ui = 0; ui < (uiCurrPartNumQ >> 1); ui++)
2442        puhBaseLCU[uiCUAddr + uiCurrPartNumQ + ui] = uiParameter;
2443
2444    }
2445    else
2446    {
2447      assert(0);
2448    }
2449    break;
2450  case SIZE_nLx2N:
2451    if ( uiPUIdx == 0 )
2452    {
2453      for (UInt ui = 0; ui < (uiCurrPartNumQ >> 2); ui++)
2454        puhBaseLCU[uiCUAddr + ui] = uiParameter;
2455      for (UInt ui = 0; ui < (uiCurrPartNumQ >> 2); ui++)
2456        puhBaseLCU[uiCUAddr + (uiCurrPartNumQ >> 1) + ui] = uiParameter;
2457      for (UInt ui = 0; ui < (uiCurrPartNumQ >> 2); ui++)
2458        puhBaseLCU[uiCUAddr + (uiCurrPartNumQ << 1) + ui] = uiParameter;
2459      for (UInt ui = 0; ui < (uiCurrPartNumQ >> 2); ui++)
2460        puhBaseLCU[uiCUAddr + (uiCurrPartNumQ << 1) + (uiCurrPartNumQ >> 1) + ui] = uiParameter;
2461
2462    }
2463    else if ( uiPUIdx == 1 )
2464    {
2465      for (UInt ui = 0; ui < (uiCurrPartNumQ >> 2); ui++)
2466        puhBaseLCU[uiCUAddr + ui] = uiParameter;
2467      for (UInt ui = 0; ui < (uiCurrPartNumQ + (uiCurrPartNumQ >> 2)); ui++)
2468        puhBaseLCU[uiCUAddr + (uiCurrPartNumQ >> 1) + ui] = uiParameter;
2469      for (UInt ui = 0; ui < (uiCurrPartNumQ >> 2); ui++)
2470        puhBaseLCU[uiCUAddr + (uiCurrPartNumQ << 1) + ui] = uiParameter;
2471      for (UInt ui = 0; ui < (uiCurrPartNumQ + (uiCurrPartNumQ >> 2)); ui++)
2472        puhBaseLCU[uiCUAddr + (uiCurrPartNumQ << 1) + (uiCurrPartNumQ >> 1) + ui] = uiParameter;
2473
2474    }
2475    else
2476    {
2477      assert(0);
2478    }
2479    break;
2480  case SIZE_nRx2N:
2481    if ( uiPUIdx == 0 )
2482    {
2483      for (UInt ui = 0; ui < (uiCurrPartNumQ + (uiCurrPartNumQ >> 2)); ui++)
2484        puhBaseLCU[uiCUAddr + ui] = uiParameter;
2485      for (UInt ui = 0; ui < (uiCurrPartNumQ >> 2); ui++)
2486        puhBaseLCU[uiCUAddr + uiCurrPartNumQ + (uiCurrPartNumQ >> 1) + ui] = uiParameter;
2487      for (UInt ui = 0; ui < (uiCurrPartNumQ + (uiCurrPartNumQ >> 2)); ui++)
2488        puhBaseLCU[uiCUAddr + (uiCurrPartNumQ << 1) + ui] = uiParameter;
2489      for (UInt ui = 0; ui < (uiCurrPartNumQ >> 2); ui++)
2490        puhBaseLCU[uiCUAddr + (uiCurrPartNumQ << 1) + uiCurrPartNumQ + (uiCurrPartNumQ >> 1) + ui] = uiParameter;
2491
2492    }
2493    else if ( uiPUIdx == 1 )
2494    {
2495      for (UInt ui = 0; ui < (uiCurrPartNumQ >> 2); ui++)
2496        puhBaseLCU[uiCUAddr + ui] = uiParameter;
2497      for (UInt ui = 0; ui < (uiCurrPartNumQ >> 2); ui++)
2498        puhBaseLCU[uiCUAddr + (uiCurrPartNumQ >> 1) + ui] = uiParameter;
2499      for (UInt ui = 0; ui < (uiCurrPartNumQ >> 2); ui++)
2500        puhBaseLCU[uiCUAddr + (uiCurrPartNumQ << 1) + ui] = uiParameter;
2501      for (UInt ui = 0; ui < (uiCurrPartNumQ >> 2); ui++)
2502        puhBaseLCU[uiCUAddr + (uiCurrPartNumQ << 1) + (uiCurrPartNumQ >> 1) + ui] = uiParameter;
2503
2504    }
2505    else
2506    {
2507      assert(0);
2508    }
2509    break;
2510  default:
2511    assert( 0 );
2512  }
2513
2514}
2515#endif
2516
2517Void TComDataCU::setInterDirSubParts( UInt uiDir, UInt uiAbsPartIdx, UInt uiPartIdx, UInt uiDepth )
2518{
2519  setSubPart<UChar>( uiDir, m_puhInterDir, uiAbsPartIdx, uiDepth, uiPartIdx );
2520}
2521
2522Void TComDataCU::setMVPIdxSubParts( Int iMVPIdx, RefPicList eRefPicList, UInt uiAbsPartIdx, UInt uiPartIdx, UInt uiDepth )
2523{
2524  setSubPart<SChar>( iMVPIdx, m_apiMVPIdx[eRefPicList], uiAbsPartIdx, uiDepth, uiPartIdx );
2525}
2526
2527Void TComDataCU::setMVPNumSubParts( Int iMVPNum, RefPicList eRefPicList, UInt uiAbsPartIdx, UInt uiPartIdx, UInt uiDepth )
2528{
2529  setSubPart<SChar>( iMVPNum, m_apiMVPNum[eRefPicList], uiAbsPartIdx, uiDepth, uiPartIdx );
2530}
2531
2532
2533Void TComDataCU::setTrIdxSubParts( UInt uiTrIdx, UInt uiAbsPartIdx, UInt uiDepth )
2534{
2535  UInt uiCurrPartNumb = m_pcPic->getNumPartitionsInCtu() >> (uiDepth << 1);
2536
2537  memset( m_puhTrIdx + uiAbsPartIdx, uiTrIdx, sizeof(UChar)*uiCurrPartNumb );
2538}
2539
2540Void TComDataCU::setTransformSkipSubParts( const UInt useTransformSkip[MAX_NUM_COMPONENT], UInt uiAbsPartIdx, UInt uiDepth )
2541{
2542  UInt uiCurrPartNumb = m_pcPic->getNumPartitionsInCtu() >> (uiDepth << 1);
2543
2544  for(UInt i=0; i<MAX_NUM_COMPONENT; i++)
2545  {
2546    memset( m_puhTransformSkip[i] + uiAbsPartIdx, useTransformSkip[i], sizeof( UChar ) * uiCurrPartNumb );
2547  }
2548}
2549
2550Void TComDataCU::setTransformSkipSubParts( UInt useTransformSkip, ComponentID compID, UInt uiAbsPartIdx, UInt uiDepth)
2551{
2552  UInt uiCurrPartNumb = m_pcPic->getNumPartitionsInCtu() >> (uiDepth << 1);
2553
2554  memset( m_puhTransformSkip[compID] + uiAbsPartIdx, useTransformSkip, sizeof( UChar ) * uiCurrPartNumb );
2555}
2556
2557Void TComDataCU::setTransformSkipPartRange ( UInt useTransformSkip, ComponentID compID, UInt uiAbsPartIdx, UInt uiCoveredPartIdxes )
2558{
2559  memset((m_puhTransformSkip[compID] + uiAbsPartIdx), useTransformSkip, (sizeof(UChar) * uiCoveredPartIdxes));
2560}
2561
2562Void TComDataCU::setCrossComponentPredictionAlphaPartRange( SChar alphaValue, ComponentID compID, UInt uiAbsPartIdx, UInt uiCoveredPartIdxes )
2563{
2564  memset((m_crossComponentPredictionAlpha[compID] + uiAbsPartIdx), alphaValue, (sizeof(SChar) * uiCoveredPartIdxes));
2565}
2566
2567Void TComDataCU::setExplicitRdpcmModePartRange ( UInt rdpcmMode, ComponentID compID, UInt uiAbsPartIdx, UInt uiCoveredPartIdxes )
2568{
2569  memset((m_explicitRdpcmMode[compID] + uiAbsPartIdx), rdpcmMode, (sizeof(UChar) * uiCoveredPartIdxes));
2570}
2571
2572Void TComDataCU::setSizeSubParts( UInt uiWidth, UInt uiHeight, UInt uiAbsPartIdx, UInt uiDepth )
2573{
2574  UInt uiCurrPartNumb = m_pcPic->getNumPartitionsInCtu() >> (uiDepth << 1);
2575
2576  memset( m_puhWidth  + uiAbsPartIdx, uiWidth,  sizeof(UChar)*uiCurrPartNumb );
2577  memset( m_puhHeight + uiAbsPartIdx, uiHeight, sizeof(UChar)*uiCurrPartNumb );
2578}
2579
2580UChar TComDataCU::getNumPartitions(const UInt uiAbsPartIdx) const
2581{
2582  UChar iNumPart = 0;
2583
2584  switch ( m_pePartSize[uiAbsPartIdx] )
2585  {
2586    case SIZE_2Nx2N:    iNumPart = 1; break;
2587    case SIZE_2NxN:     iNumPart = 2; break;
2588    case SIZE_Nx2N:     iNumPart = 2; break;
2589    case SIZE_NxN:      iNumPart = 4; break;
2590    case SIZE_2NxnU:    iNumPart = 2; break;
2591    case SIZE_2NxnD:    iNumPart = 2; break;
2592    case SIZE_nLx2N:    iNumPart = 2; break;
2593    case SIZE_nRx2N:    iNumPart = 2; break;
2594    default:            assert (0);   break;
2595  }
2596
2597  return  iNumPart;
2598}
2599
2600// This is for use by a leaf/sub CU object only, with no additional AbsPartIdx
2601#if NH_3D_IC || NH_3D_VSP
2602Void TComDataCU::getPartIndexAndSize( UInt uiPartIdx, UInt& ruiPartAddr, Int& riWidth, Int& riHeight, UInt uiAbsPartIdx, Bool bLCU) const
2603{
2604  UInt uiNumPartition  = bLCU ? (getWidth(uiAbsPartIdx)*getHeight(uiAbsPartIdx) >> 4) : m_uiNumPartition;
2605  UInt  uiTmpAbsPartIdx  = bLCU ? uiAbsPartIdx : 0;
2606
2607  switch ( m_pePartSize[uiTmpAbsPartIdx] )
2608  {
2609  case SIZE_2NxN:
2610    riWidth = getWidth( uiTmpAbsPartIdx );      riHeight = getHeight( uiTmpAbsPartIdx ) >> 1; ruiPartAddr = ( uiPartIdx == 0 )? 0 : uiNumPartition >> 1;
2611    break;
2612  case SIZE_Nx2N:
2613    riWidth = getWidth( uiTmpAbsPartIdx ) >> 1; riHeight = getHeight( uiTmpAbsPartIdx );      ruiPartAddr = ( uiPartIdx == 0 )? 0 : uiNumPartition >> 2;
2614    break;
2615  case SIZE_NxN:
2616    riWidth = getWidth( uiTmpAbsPartIdx ) >> 1; riHeight = getHeight( uiTmpAbsPartIdx ) >> 1; ruiPartAddr = ( uiNumPartition >> 2 ) * uiPartIdx;
2617    break;
2618  case SIZE_2NxnU:
2619    riWidth     = getWidth( uiTmpAbsPartIdx );
2620    riHeight    = ( uiPartIdx == 0 ) ?  getHeight( uiTmpAbsPartIdx ) >> 2 : ( getHeight( uiTmpAbsPartIdx ) >> 2 ) + ( getHeight( uiTmpAbsPartIdx ) >> 1 );
2621    ruiPartAddr = ( uiPartIdx == 0 ) ? 0 : uiNumPartition >> 3;
2622    break;
2623  case SIZE_2NxnD:
2624    riWidth     = getWidth( uiTmpAbsPartIdx );
2625    riHeight    = ( uiPartIdx == 0 ) ?  ( getHeight( uiTmpAbsPartIdx ) >> 2 ) + ( getHeight( uiTmpAbsPartIdx ) >> 1 ) : getHeight( uiTmpAbsPartIdx ) >> 2;
2626    ruiPartAddr = ( uiPartIdx == 0 ) ? 0 : (uiNumPartition >> 1) + (uiNumPartition >> 3);
2627    break;
2628  case SIZE_nLx2N:
2629    riWidth     = ( uiPartIdx == 0 ) ? getWidth( uiTmpAbsPartIdx ) >> 2 : ( getWidth( uiTmpAbsPartIdx ) >> 2 ) + ( getWidth( uiTmpAbsPartIdx ) >> 1 );
2630    riHeight    = getHeight( uiTmpAbsPartIdx );
2631    ruiPartAddr = ( uiPartIdx == 0 ) ? 0 : uiNumPartition >> 4;
2632    break;
2633  case SIZE_nRx2N:
2634    riWidth     = ( uiPartIdx == 0 ) ? ( getWidth( uiTmpAbsPartIdx ) >> 2 ) + ( getWidth( uiTmpAbsPartIdx ) >> 1 ) : getWidth( uiTmpAbsPartIdx ) >> 2;
2635    riHeight    = getHeight( uiTmpAbsPartIdx );
2636    ruiPartAddr = ( uiPartIdx == 0 ) ? 0 : (uiNumPartition >> 2) + (uiNumPartition >> 4);
2637    break;
2638  default:
2639    assert ( m_pePartSize[uiTmpAbsPartIdx] == SIZE_2Nx2N ); 
2640    riWidth = getWidth( uiTmpAbsPartIdx );      riHeight = getHeight( uiTmpAbsPartIdx );      ruiPartAddr = 0;
2641    break;
2642  }
2643}
2644#else
2645
2646Void TComDataCU::getPartIndexAndSize( UInt uiPartIdx, UInt& ruiPartAddr, Int& riWidth, Int& riHeight )  const
2647{
2648  switch ( m_pePartSize[0] )
2649  {
2650    case SIZE_2NxN:
2651      riWidth = getWidth(0);      riHeight = getHeight(0) >> 1; ruiPartAddr = ( uiPartIdx == 0 )? 0 : m_uiNumPartition >> 1;
2652      break;
2653    case SIZE_Nx2N:
2654      riWidth = getWidth(0) >> 1; riHeight = getHeight(0);      ruiPartAddr = ( uiPartIdx == 0 )? 0 : m_uiNumPartition >> 2;
2655      break;
2656    case SIZE_NxN:
2657      riWidth = getWidth(0) >> 1; riHeight = getHeight(0) >> 1; ruiPartAddr = ( m_uiNumPartition >> 2 ) * uiPartIdx;
2658      break;
2659    case SIZE_2NxnU:
2660      riWidth     = getWidth(0);
2661      riHeight    = ( uiPartIdx == 0 ) ?  getHeight(0) >> 2 : ( getHeight(0) >> 2 ) + ( getHeight(0) >> 1 );
2662      ruiPartAddr = ( uiPartIdx == 0 ) ? 0 : m_uiNumPartition >> 3;
2663      break;
2664    case SIZE_2NxnD:
2665      riWidth     = getWidth(0);
2666      riHeight    = ( uiPartIdx == 0 ) ?  ( getHeight(0) >> 2 ) + ( getHeight(0) >> 1 ) : getHeight(0) >> 2;
2667      ruiPartAddr = ( uiPartIdx == 0 ) ? 0 : (m_uiNumPartition >> 1) + (m_uiNumPartition >> 3);
2668      break;
2669    case SIZE_nLx2N:
2670      riWidth     = ( uiPartIdx == 0 ) ? getWidth(0) >> 2 : ( getWidth(0) >> 2 ) + ( getWidth(0) >> 1 );
2671      riHeight    = getHeight(0);
2672      ruiPartAddr = ( uiPartIdx == 0 ) ? 0 : m_uiNumPartition >> 4;
2673      break;
2674    case SIZE_nRx2N:
2675      riWidth     = ( uiPartIdx == 0 ) ? ( getWidth(0) >> 2 ) + ( getWidth(0) >> 1 ) : getWidth(0) >> 2;
2676      riHeight    = getHeight(0);
2677      ruiPartAddr = ( uiPartIdx == 0 ) ? 0 : (m_uiNumPartition >> 2) + (m_uiNumPartition >> 4);
2678      break;
2679    default:
2680      assert ( m_pePartSize[0] == SIZE_2Nx2N );
2681      riWidth = getWidth(0);      riHeight = getHeight(0);      ruiPartAddr = 0;
2682      break;
2683  }
2684}
2685#endif
2686
2687// static member function
2688Void TComDataCU::getMvField ( const TComDataCU* pcCU, UInt uiAbsPartIdx, RefPicList eRefPicList, TComMvField& rcMvField )
2689{
2690  if ( pcCU == NULL )  // OUT OF BOUNDARY
2691  {
2692    TComMv  cZeroMv;
2693    rcMvField.setMvField( cZeroMv, NOT_VALID );
2694    return;
2695  }
2696
2697  const TComCUMvField*  pcCUMvField = pcCU->getCUMvField( eRefPicList );
2698  rcMvField.setMvField( pcCUMvField->getMv( uiAbsPartIdx ), pcCUMvField->getRefIdx( uiAbsPartIdx ) );
2699}
2700
2701Void TComDataCU::deriveLeftRightTopIdxGeneral ( UInt uiAbsPartIdx, UInt uiPartIdx, UInt& ruiPartIdxLT, UInt& ruiPartIdxRT ) const
2702{
2703  ruiPartIdxLT = m_absZIdxInCtu + uiAbsPartIdx;
2704  UInt uiPUWidth = 0;
2705
2706  switch ( m_pePartSize[uiAbsPartIdx] )
2707  {
2708    case SIZE_2Nx2N: uiPUWidth = m_puhWidth[uiAbsPartIdx];  break;
2709    case SIZE_2NxN:  uiPUWidth = m_puhWidth[uiAbsPartIdx];   break;
2710    case SIZE_Nx2N:  uiPUWidth = m_puhWidth[uiAbsPartIdx]  >> 1;  break;
2711    case SIZE_NxN:   uiPUWidth = m_puhWidth[uiAbsPartIdx]  >> 1; break;
2712    case SIZE_2NxnU:   uiPUWidth = m_puhWidth[uiAbsPartIdx]; break;
2713    case SIZE_2NxnD:   uiPUWidth = m_puhWidth[uiAbsPartIdx]; break;
2714    case SIZE_nLx2N:
2715      if ( uiPartIdx == 0 )
2716      {
2717        uiPUWidth = m_puhWidth[uiAbsPartIdx]  >> 2;
2718      }
2719      else if ( uiPartIdx == 1 )
2720      {
2721        uiPUWidth = (m_puhWidth[uiAbsPartIdx]  >> 1) + (m_puhWidth[uiAbsPartIdx]  >> 2);
2722      }
2723      else
2724      {
2725        assert(0);
2726      }
2727      break;
2728    case SIZE_nRx2N:
2729      if ( uiPartIdx == 0 )
2730      {
2731        uiPUWidth = (m_puhWidth[uiAbsPartIdx]  >> 1) + (m_puhWidth[uiAbsPartIdx]  >> 2);
2732      }
2733      else if ( uiPartIdx == 1 )
2734      {
2735        uiPUWidth = m_puhWidth[uiAbsPartIdx]  >> 2;
2736      }
2737      else
2738      {
2739        assert(0);
2740      }
2741      break;
2742    default:
2743      assert (0);
2744      break;
2745  }
2746
2747  ruiPartIdxRT = g_auiRasterToZscan [g_auiZscanToRaster[ ruiPartIdxLT ] + uiPUWidth / m_pcPic->getMinCUWidth() - 1 ];
2748}
2749
2750Void TComDataCU::deriveLeftBottomIdxGeneral( UInt uiAbsPartIdx, UInt uiPartIdx, UInt& ruiPartIdxLB ) const
2751{
2752  UInt uiPUHeight = 0;
2753  switch ( m_pePartSize[uiAbsPartIdx] )
2754  {
2755    case SIZE_2Nx2N: uiPUHeight = m_puhHeight[uiAbsPartIdx];    break;
2756    case SIZE_2NxN:  uiPUHeight = m_puhHeight[uiAbsPartIdx] >> 1;    break;
2757    case SIZE_Nx2N:  uiPUHeight = m_puhHeight[uiAbsPartIdx];  break;
2758    case SIZE_NxN:   uiPUHeight = m_puhHeight[uiAbsPartIdx] >> 1;    break;
2759    case SIZE_2NxnU:
2760      if ( uiPartIdx == 0 )
2761      {
2762        uiPUHeight = m_puhHeight[uiAbsPartIdx] >> 2;
2763      }
2764      else if ( uiPartIdx == 1 )
2765      {
2766        uiPUHeight = (m_puhHeight[uiAbsPartIdx] >> 1) + (m_puhHeight[uiAbsPartIdx] >> 2);
2767      }
2768      else
2769      {
2770        assert(0);
2771      }
2772      break;
2773    case SIZE_2NxnD:
2774      if ( uiPartIdx == 0 )
2775      {
2776        uiPUHeight = (m_puhHeight[uiAbsPartIdx] >> 1) + (m_puhHeight[uiAbsPartIdx] >> 2);
2777      }
2778      else if ( uiPartIdx == 1 )
2779      {
2780        uiPUHeight = m_puhHeight[uiAbsPartIdx] >> 2;
2781      }
2782      else
2783      {
2784        assert(0);
2785      }
2786      break;
2787    case SIZE_nLx2N: uiPUHeight = m_puhHeight[uiAbsPartIdx];  break;
2788    case SIZE_nRx2N: uiPUHeight = m_puhHeight[uiAbsPartIdx];  break;
2789    default:
2790      assert (0);
2791      break;
2792  }
2793
2794  ruiPartIdxLB      = g_auiRasterToZscan [g_auiZscanToRaster[ m_absZIdxInCtu + uiAbsPartIdx ] + ((uiPUHeight / m_pcPic->getMinCUHeight()) - 1)*m_pcPic->getNumPartInCtuWidth()];
2795}
2796
2797Void TComDataCU::deriveLeftRightTopIdx ( UInt uiPartIdx, UInt& ruiPartIdxLT, UInt& ruiPartIdxRT ) const
2798{
2799  ruiPartIdxLT = m_absZIdxInCtu;
2800  ruiPartIdxRT = g_auiRasterToZscan [g_auiZscanToRaster[ ruiPartIdxLT ] + m_puhWidth[0] / m_pcPic->getMinCUWidth() - 1 ];
2801
2802  switch ( m_pePartSize[0] )
2803  {
2804    case SIZE_2Nx2N:                                                                                                                                break;
2805    case SIZE_2NxN:
2806      ruiPartIdxLT += ( uiPartIdx == 0 )? 0 : m_uiNumPartition >> 1; ruiPartIdxRT += ( uiPartIdx == 0 )? 0 : m_uiNumPartition >> 1;
2807      break;
2808    case SIZE_Nx2N:
2809      ruiPartIdxLT += ( uiPartIdx == 0 )? 0 : m_uiNumPartition >> 2; ruiPartIdxRT -= ( uiPartIdx == 1 )? 0 : m_uiNumPartition >> 2;
2810      break;
2811    case SIZE_NxN:
2812      ruiPartIdxLT += ( m_uiNumPartition >> 2 ) * uiPartIdx;         ruiPartIdxRT +=  ( m_uiNumPartition >> 2 ) * ( uiPartIdx - 1 );
2813      break;
2814    case SIZE_2NxnU:
2815      ruiPartIdxLT += ( uiPartIdx == 0 )? 0 : m_uiNumPartition >> 3;
2816      ruiPartIdxRT += ( uiPartIdx == 0 )? 0 : m_uiNumPartition >> 3;
2817      break;
2818    case SIZE_2NxnD:
2819      ruiPartIdxLT += ( uiPartIdx == 0 )? 0 : ( m_uiNumPartition >> 1 ) + ( m_uiNumPartition >> 3 );
2820      ruiPartIdxRT += ( uiPartIdx == 0 )? 0 : ( m_uiNumPartition >> 1 ) + ( m_uiNumPartition >> 3 );
2821      break;
2822    case SIZE_nLx2N:
2823      ruiPartIdxLT += ( uiPartIdx == 0 )? 0 : m_uiNumPartition >> 4;
2824      ruiPartIdxRT -= ( uiPartIdx == 1 )? 0 : ( m_uiNumPartition >> 2 ) + ( m_uiNumPartition >> 4 );
2825      break;
2826    case SIZE_nRx2N:
2827      ruiPartIdxLT += ( uiPartIdx == 0 )? 0 : ( m_uiNumPartition >> 2 ) + ( m_uiNumPartition >> 4 );
2828      ruiPartIdxRT -= ( uiPartIdx == 1 )? 0 : m_uiNumPartition >> 4;
2829      break;
2830    default:
2831      assert (0);
2832      break;
2833  }
2834
2835}
2836
2837Void TComDataCU::deriveLeftBottomIdx( UInt  uiPartIdx,      UInt&      ruiPartIdxLB ) const
2838{
2839  ruiPartIdxLB      = g_auiRasterToZscan [g_auiZscanToRaster[ m_absZIdxInCtu ] + ( ((m_puhHeight[0] / m_pcPic->getMinCUHeight())>>1) - 1)*m_pcPic->getNumPartInCtuWidth()];
2840
2841  switch ( m_pePartSize[0] )
2842  {
2843    case SIZE_2Nx2N:
2844      ruiPartIdxLB += m_uiNumPartition >> 1;
2845      break;
2846    case SIZE_2NxN:
2847      ruiPartIdxLB += ( uiPartIdx == 0 )? 0 : m_uiNumPartition >> 1;
2848      break;
2849    case SIZE_Nx2N:
2850      ruiPartIdxLB += ( uiPartIdx == 0 )? m_uiNumPartition >> 1 : (m_uiNumPartition >> 2)*3;
2851      break;
2852    case SIZE_NxN:
2853      ruiPartIdxLB += ( m_uiNumPartition >> 2 ) * uiPartIdx;
2854      break;
2855    case SIZE_2NxnU:
2856      ruiPartIdxLB += ( uiPartIdx == 0 ) ? -((Int)m_uiNumPartition >> 3) : m_uiNumPartition >> 1;
2857      break;
2858    case SIZE_2NxnD:
2859      ruiPartIdxLB += ( uiPartIdx == 0 ) ? (m_uiNumPartition >> 2) + (m_uiNumPartition >> 3): m_uiNumPartition >> 1;
2860      break;
2861    case SIZE_nLx2N:
2862      ruiPartIdxLB += ( uiPartIdx == 0 ) ? m_uiNumPartition >> 1 : (m_uiNumPartition >> 1) + (m_uiNumPartition >> 4);
2863      break;
2864    case SIZE_nRx2N:
2865      ruiPartIdxLB += ( uiPartIdx == 0 ) ? m_uiNumPartition >> 1 : (m_uiNumPartition >> 1) + (m_uiNumPartition >> 2) + (m_uiNumPartition >> 4);
2866      break;
2867    default:
2868      assert (0);
2869      break;
2870  }
2871}
2872
2873/** Derive the partition index of neighbouring bottom right block
2874 * \param [in]  uiPartIdx     current partition index
2875 * \param [out] ruiPartIdxRB  partition index of neighbouring bottom right block
2876 */
2877Void TComDataCU::deriveRightBottomIdx( UInt uiPartIdx, UInt &ruiPartIdxRB ) const
2878{
2879  ruiPartIdxRB      = g_auiRasterToZscan [g_auiZscanToRaster[ m_absZIdxInCtu ] + ( ((m_puhHeight[0] / m_pcPic->getMinCUHeight())>>1) - 1)*m_pcPic->getNumPartInCtuWidth() +  m_puhWidth[0] / m_pcPic->getMinCUWidth() - 1];
2880
2881  switch ( m_pePartSize[0] )
2882  {
2883    case SIZE_2Nx2N:
2884      ruiPartIdxRB += m_uiNumPartition >> 1;
2885      break;
2886    case SIZE_2NxN:
2887      ruiPartIdxRB += ( uiPartIdx == 0 )? 0 : m_uiNumPartition >> 1;
2888      break;
2889    case SIZE_Nx2N:
2890      ruiPartIdxRB += ( uiPartIdx == 0 )? m_uiNumPartition >> 2 : (m_uiNumPartition >> 1);
2891      break;
2892    case SIZE_NxN:
2893      ruiPartIdxRB += ( m_uiNumPartition >> 2 ) * ( uiPartIdx - 1 );
2894      break;
2895    case SIZE_2NxnU:
2896      ruiPartIdxRB += ( uiPartIdx == 0 ) ? -((Int)m_uiNumPartition >> 3) : m_uiNumPartition >> 1;
2897      break;
2898    case SIZE_2NxnD:
2899      ruiPartIdxRB += ( uiPartIdx == 0 ) ? (m_uiNumPartition >> 2) + (m_uiNumPartition >> 3): m_uiNumPartition >> 1;
2900      break;
2901    case SIZE_nLx2N:
2902      ruiPartIdxRB += ( uiPartIdx == 0 ) ? (m_uiNumPartition >> 3) + (m_uiNumPartition >> 4): m_uiNumPartition >> 1;
2903      break;
2904    case SIZE_nRx2N:
2905      ruiPartIdxRB += ( uiPartIdx == 0 ) ? (m_uiNumPartition >> 2) + (m_uiNumPartition >> 3) + (m_uiNumPartition >> 4) : m_uiNumPartition >> 1;
2906      break;
2907    default:
2908      assert (0);
2909      break;
2910  }
2911}
2912
2913Bool TComDataCU::hasEqualMotion( UInt uiAbsPartIdx, const TComDataCU* pcCandCU, UInt uiCandAbsPartIdx ) const
2914{
2915  if ( getInterDir( uiAbsPartIdx ) != pcCandCU->getInterDir( uiCandAbsPartIdx ) )
2916  {
2917    return false;
2918  }
2919
2920  for ( UInt uiRefListIdx = 0; uiRefListIdx < 2; uiRefListIdx++ )
2921  {
2922    if ( getInterDir( uiAbsPartIdx ) & ( 1 << uiRefListIdx ) )
2923    {
2924      if ( getCUMvField( RefPicList( uiRefListIdx ) )->getMv( uiAbsPartIdx )     != pcCandCU->getCUMvField( RefPicList( uiRefListIdx ) )->getMv( uiCandAbsPartIdx ) ||
2925        getCUMvField( RefPicList( uiRefListIdx ) )->getRefIdx( uiAbsPartIdx ) != pcCandCU->getCUMvField( RefPicList( uiRefListIdx ) )->getRefIdx( uiCandAbsPartIdx ) )
2926      {
2927        return false;
2928      }
2929    }
2930  }
2931
2932  return true;
2933}
2934
2935#if NH_3D
2936Bool TComDataCU::hasEqualMotion( Int dirA, const TComMvField* mvFieldA, Int dirB, const TComMvField* mvFieldB )
2937{
2938  return  ( dirA == dirB  &&
2939    ( ( dirA & 1 ) == 0 || mvFieldA[0] == mvFieldB[0]  ) &&
2940    ( ( dirA & 2 ) == 0 || mvFieldA[1] == mvFieldB[1]  ) 
2941    );
2942}
2943#endif
2944
2945#if NH_3D_VSP
2946/** Add a VSP merging candidate
2947 * \Inputs
2948 * \param uiPUIdx: PU index within a CU
2949 * \param ucVspMergePos: Specify the VSP merge candidate position
2950 * \param mrgCandIdx: Target merge candidate index. At encoder, it is set equal to -1, such that the whole merge candidate list will be constructed.
2951 * \param pDinfo: The "disparity information" derived from neighboring blocks. Type 1 MV.
2952 * \param uiCount: The next position to add VSP merge candidate
2953 *
2954 * \Outputs
2955 * \param uiCount: The next position to add merge candidate. Will be updated if VSP is successfully added
2956 * \param abCandIsInter: abCandIsInter[iCount] tells that VSP candidate is an Inter candidate, if VSP is successfully added
2957 * \param pcMvFieldNeighbours:   Return combined motion information, then stored to a global buffer
2958 *                                    1) the "disparity vector". Type 1 MV. To be used to fetch a depth block.
2959 *                                    2) the ref index /list.    Type 2 reference picture pointer, typically for texture
2960 * \param puhInterDirNeighbours: Indicate the VSP prediction direction.
2961 * \param vspFlag: vspFlag[iCount] will be set (equal to 1), if VSP is successfully added. To be used to indicate the actual position of the VSP candidate
2962 *
2963 * \Return
2964 *   true:  if the VSP candidate is added at the target position
2965 *   false: otherwise
2966 */
2967inline Bool TComDataCU::xAddVspCand( Int mrgCandIdx, DisInfo* pDInfo, Int& iCount)
2968{
2969  if ( m_pcSlice->getViewIndex() == 0 || !m_pcSlice->getViewSynthesisPredFlag( ) || m_pcSlice->getIsDepth() || pDInfo->m_aVIdxCan == -1)
2970  {
2971    return false;
2972  }
2973
2974  Int refViewIdx = pDInfo->m_aVIdxCan;
2975  TComPic* picDepth = getSlice()->getIvPic( true, refViewIdx );
2976
2977  if( picDepth == NULL ) // No depth reference avail
2978  {
2979    // Is this allowed to happen? When not an assertion should be added here!
2980    return false;
2981  }
2982
2983  TComMvField mvVSP[2];
2984  UChar dirVSP;
2985  Bool  refViewAvailFlag = false;
2986  UChar predFlag[2]      = {0, 0};
2987
2988  for( Int iRefListIdX = 0; iRefListIdX < 2 && !refViewAvailFlag; iRefListIdX++ )
2989  {
2990    RefPicList eRefPicListX = RefPicList( iRefListIdX );
2991    for ( Int i = 0; i < m_pcSlice->getNumRefIdx(eRefPicListX) && !refViewAvailFlag; i++ )
2992    {
2993      Int viewIdxRefInListX = m_pcSlice->getRefPic(eRefPicListX, i)->getViewIndex();
2994      if ( viewIdxRefInListX == refViewIdx )
2995      {
2996        refViewAvailFlag      = true;
2997        predFlag[iRefListIdX] = 1;
2998        mvVSP[0+iRefListIdX].setMvField( pDInfo->m_acNBDV, i );
2999#if NH_3D_NBDV
3000        mvVSP[0+iRefListIdX].getMv().setIDVFlag (false);
3001#endif
3002      }
3003    }
3004  }
3005
3006  dirVSP = (predFlag[0] | (predFlag[1] << 1));
3007  m_mergCands[MRG_VSP].setCand( mvVSP, dirVSP, true
3008#if NH_3D_SPIVMP
3009    , false
3010#endif
3011    );
3012  if ( mrgCandIdx == iCount )
3013  {
3014    return true;
3015  }
3016
3017  iCount++;
3018
3019  return false;
3020}
3021#endif
3022
3023#if NH_3D_IV_MERGE
3024inline Bool TComDataCU::xAddIvMRGCand( Int mrgCandIdx, Int& iCount, Int* ivCandDir, TComMv* ivCandMv, Int* ivCandRefIdx )
3025{
3026  for(Int iLoop = 0; iLoop < 2; iLoop ++ ) 
3027  {
3028    /// iLoop = 0 --> IvMCShift
3029    /// iLoop = 1 --> IvDCShift  (Derived from IvDC)
3030    if(ivCandDir[iLoop + 2])
3031    {
3032      TComMvField tmpMV[2];
3033      UChar tmpDir = ivCandDir[iLoop + 2];
3034      if( ( ivCandDir[iLoop + 2] & 1 ) == 1 )
3035      {
3036        tmpMV[0].setMvField( ivCandMv[ (iLoop<<1) + 4 ], ivCandRefIdx[ (iLoop<<1) + 4 ] ); 
3037      }
3038      if( ( ivCandDir[iLoop + 2] & 2 ) == 2 )
3039      {
3040        tmpMV[1].setMvField( ivCandMv[ (iLoop<<1) + 5 ], ivCandRefIdx[ (iLoop<<1) + 5 ] );
3041      }
3042     
3043      // Prune IvMC vs. IvMcShift
3044      Bool bRemove = false;     
3045      if( !iLoop && ivCandDir[0] > 0)
3046      {
3047        if( hasEqualMotion(tmpDir, tmpMV, m_mergCands[MRG_IVMC].m_uDir, m_mergCands[MRG_IVMC].m_cMvField )) 
3048        {
3049            bRemove                         = true;
3050        }
3051      }
3052      if(!bRemove)
3053      {
3054#if NH_3D_NBDV
3055        if(iLoop) // For IvMcShift candidate
3056        {
3057          tmpMV[0].getMv().setIDVFlag (false);
3058          tmpMV[1].getMv().setIDVFlag (false);
3059        }
3060#endif
3061        m_mergCands[MRG_IVSHIFT].setCand(tmpMV, tmpDir, false, false);
3062        if( mrgCandIdx == iCount )
3063        {
3064          return true;
3065        }
3066        iCount++;
3067      }
3068      break;
3069    }
3070  }
3071  return false;
3072} 
3073
3074#endif
3075#if NH_3D_MLC
3076/** Construct a extended list of merging candidates
3077 * \param pcMvFieldNeighbours
3078 * \param puhInterDirNeighbours
3079 * \param vspFlag
3080 * \param pbSPIVMPFlag
3081 * \param numValidMergeCand
3082 */
3083Void TComDataCU::buildMCL(TComMvField* pcMvFieldNeighbours, UChar* puhInterDirNeighbours
3084#if NH_3D_VSP
3085  , Int* vspFlag
3086#endif
3087#if NH_3D_SPIVMP
3088  , Bool* pbSPIVMPFlag
3089#endif
3090  , Int& numValidMergeCand
3091  )
3092{
3093  if (!( getSlice()->getIsDepth() || getSlice()->getViewIndex()>0))
3094  {
3095    return;
3096  }
3097
3098
3099#if ENC_DEC_TRACE && H_MV_ENC_DEC_TRAC
3100  if ( g_traceMergeCandListConst ) 
3101  {
3102    for (Int i = 0; i<MRG_IVSHIFT+1; i++)
3103    {
3104      m_mergCands[i].print( i ); 
3105    }
3106  }
3107#endif
3108
3109
3110  Int iCount = 0;
3111  TComMv cZeroMv;
3112
3113  // init temporal list
3114  TComMvField extMergeCandList[MRG_MAX_NUM_CANDS_MEM << 1];
3115  UChar uhInterDirNeighboursExt[MRG_MAX_NUM_CANDS_MEM];
3116  for( UInt ui = 0; ui < getSlice()->getMaxNumMergeCand(); ++ui )
3117  {
3118    uhInterDirNeighboursExt[ui] = puhInterDirNeighbours[ui];
3119    extMergeCandList[ui<<1].setMvField(cZeroMv, NOT_VALID);
3120    extMergeCandList[(ui<<1)+1].setMvField(cZeroMv, NOT_VALID);
3121#if NH_3D_VSP
3122    vspFlag[ui] = 0;
3123#endif
3124  }
3125
3126  // insert MPI ... IvShift candidate to extMergeCandList
3127  for (Int i=0; i<=MRG_IVSHIFT; i++)
3128  {
3129    if (m_mergCands[i].m_bAvailable)
3130    {
3131      m_mergCands[i].getCand(iCount, extMergeCandList, uhInterDirNeighboursExt
3132#if NH_3D_VSP
3133        , vspFlag
3134#endif
3135#if NH_3D_SPIVMP
3136        , pbSPIVMPFlag
3137#endif
3138        );
3139      iCount++;
3140      if (iCount >= getSlice()->getMaxNumMergeCand())
3141        break;
3142    }
3143  }
3144
3145  Int iCountBase = m_numSpatialCands;
3146  // insert remaining base candidates to extMergeCandList
3147  while (iCount < getSlice()->getMaxNumMergeCand() && iCountBase < getSlice()->getMaxNumMergeCand())
3148  {
3149    uhInterDirNeighboursExt[iCount] = puhInterDirNeighbours[iCountBase];
3150    extMergeCandList[iCount<<1].setMvField(pcMvFieldNeighbours[iCountBase<<1].getMv(), pcMvFieldNeighbours[iCountBase<<1].getRefIdx());
3151    if ( getSlice()->isInterB() )
3152    {
3153      extMergeCandList[(iCount<<1)+1].setMvField(pcMvFieldNeighbours[(iCountBase<<1)+1].getMv(), pcMvFieldNeighbours[(iCountBase<<1)+1].getRefIdx());
3154    }
3155    iCountBase++;
3156    iCount++;
3157  }
3158
3159  for( UInt ui = 0; ui < getSlice()->getMaxNumMergeCand(); ui++ )
3160  {
3161    puhInterDirNeighbours[ui] = 0;
3162    pcMvFieldNeighbours[ui<<1].setMvField(cZeroMv, NOT_VALID);
3163    pcMvFieldNeighbours[(ui<<1)+1].setMvField(cZeroMv, NOT_VALID);
3164  }
3165
3166  // copy extMergeCandList to output
3167  for( UInt ui = 0; ui < getSlice()->getMaxNumMergeCand(); ui++ )
3168  {
3169    puhInterDirNeighbours[ui] = uhInterDirNeighboursExt[ui];
3170    pcMvFieldNeighbours[ui<<1].setMvField(extMergeCandList[ui<<1].getMv(), extMergeCandList[ui<<1].getRefIdx());
3171
3172    if ( getSlice()->isInterB() )
3173    {
3174      pcMvFieldNeighbours[(ui<<1)+1].setMvField(extMergeCandList[(ui<<1)+1].getMv(), extMergeCandList[(ui<<1)+1].getRefIdx());
3175    }
3176  }
3177
3178#if ENC_DEC_TRACE && H_MV_ENC_DEC_TRAC
3179  if ( g_traceMergeCandListConst )
3180  {
3181    std::cout << std::setfill(' ')                          << std::setw( 15 )
3182      <<  "Num"                                             << std::setw( 15 )
3183      <<  "Dir "                                            << std::setw( 15 )
3184      <<  "L0 RefIdx"                                       << std::setw( 15 )
3185      <<  "L0 Hor"                                          << std::setw( 15 )
3186      <<  "L0 Ver"                                          << std::setw( 15 )
3187      <<  "L1 RefIdx"                                       << std::setw( 15 )
3188      <<  "L1 Hor"                                          << std::setw( 15 )
3189      <<  "L1 Ver"                                          << std::setw( 15 )
3190      << std::endl; 
3191
3192    // copy extMergeCandList to output
3193    for( UInt ui = 0; ui < getSlice()->getMaxNumMergeCand(); ui++ )
3194    {
3195      UChar curDir        = puhInterDirNeighbours[ui];
3196      TComMvField& curf   = pcMvFieldNeighbours[ui<<1];
3197      TComMvField& curf2  = pcMvFieldNeighbours[(ui<<1)+1];
3198
3199      std::cout << std::setfill(' ')                         << std::setw( 15 )
3200        << ui                                                << std::setw( 15 )       
3201        << (UInt) curDir                                     << std::setw( 15 )   
3202        << ((curDir & 1) ? curf.getRefIdx()       : MIN_INT) << std::setw( 15 )
3203        << ((curDir & 1) ? curf.getMv().getHor()  : MIN_INT) << std::setw( 15 )
3204        << ((curDir & 1) ? curf.getMv().getVer()  : MIN_INT) << std::setw( 15 );
3205
3206      if ( getSlice()->isInterB() )
3207      {     
3208        std::cout << ((curDir & 2) ? curf2.getRefIdx() : MIN_INT) << std::setw( 15 )
3209          << ((curDir & 1) ? curf2.getMv().getHor()    : MIN_INT) << std::setw( 15 )
3210          << ((curDir & 1) ? curf2.getMv().getVer()    : MIN_INT) << std::setw( 15 );
3211      }
3212      std::cout << std::endl; 
3213    }
3214  }
3215#endif
3216  numValidMergeCand = iCount;
3217  assert(iCount == getSlice()->getMaxNumMergeCand());
3218}
3219
3220
3221
3222/** Derive 3D merge candidates
3223 * \param uiAbsPartIdx
3224 * \param uiPUIdx
3225 * \param pcMvFieldNeighbours
3226 * \param puhInterDirNeighbours
3227 * \param pcMvFieldSP
3228 * \param puhInterDirNeighbours
3229 * \param numValidMergeCand
3230 */
3231Void TComDataCU::xGetInterMergeCandidates( UInt uiAbsPartIdx, UInt uiPUIdx, TComMvField* pcMFieldNeighbours, UChar* puhInterDirNeighbours
3232#if NH_3D_SPIVMP
3233      , TComMvField* pcMvFieldSP, UChar* puhInterDirSP
3234#endif
3235      , Int& numValidMergeCand, Int mrgCandIdx
3236)
3237{
3238#if NH_3D_IV_MERGE
3239  TComMv cZeroMv;
3240  TComMvField tmpMV[2]; 
3241#endif
3242
3243  //////////////////////////////////
3244  //////// GET DISPARITIES  ////////
3245  //////////////////////////////////
3246#if NH_3D_IV_MERGE
3247  DisInfo cDisInfo = getDvInfo(uiAbsPartIdx);
3248  m_cDefaultDisInfo = cDisInfo;
3249#elif NH_3D_VSP
3250  // for xAddVspCand()
3251  DisInfo cDisInfo = getDvInfo(uiAbsPartIdx);
3252#endif
3253
3254  if (!( getSlice()->getIsDepth() || getSlice()->getViewIndex()>0))
3255  {
3256    return;
3257  }
3258  numValidMergeCand = getSlice()->getMaxNumMergeCand();
3259  //////////////////////////////////
3260  //////// DERIVE LOCATIONS ////////
3261  //////////////////////////////////
3262  // compute the location of the current PU
3263  Int xP, yP, nPSW, nPSH;
3264  this->getPartPosition(uiPUIdx, xP, yP, nPSW, nPSH);
3265
3266  Int iCount = 0;
3267  UInt uiPartIdxLT, uiPartIdxRT, uiPartIdxLB;
3268  deriveLeftRightTopIdxGeneral( uiAbsPartIdx, uiPUIdx, uiPartIdxLT, uiPartIdxRT );
3269  deriveLeftBottomIdxGeneral  ( uiAbsPartIdx, uiPUIdx, uiPartIdxLB );
3270#if NH_3D_TEXT_MERGE
3271  Bool bMPIFlag   = getSlice()->getMpiFlag(); 
3272  Int  tmpDir;
3273#endif
3274#if NH_3D_IV_MERGE || NH_3D_TEXT_MERGE
3275  Bool bIsDepth = getSlice()->getIsDepth();
3276#endif
3277
3278#if NH_3D_IC
3279  Bool bICFlag = getICFlag(uiAbsPartIdx);
3280#endif
3281#if NH_3D_ARP
3282  Bool bARPFlag = getARPW(uiAbsPartIdx) > 0;
3283#endif
3284#if NH_3D_DBBP
3285  Bool bDBBPFlag = getDBBPFlag(uiAbsPartIdx);
3286  assert(bDBBPFlag == getDBBPFlag(0)); 
3287#endif
3288
3289#if NH_3D_NBDV
3290  for(Int i = 0; i < MRG_MAX_NUM_CANDS_MEM; i++) 
3291  {
3292    pcMFieldNeighbours[i<<1    ].getMv().setIDVFlag (false);
3293    pcMFieldNeighbours[(i<<1)+1].getMv().setIDVFlag (false);
3294  }
3295#endif
3296  // init containers
3297  for (Int i = 0; i<MRG_IVSHIFT+1; i++)
3298    m_mergCands[i].init();
3299
3300  m_numSpatialCands = 0;
3301
3302  //////////////////////////////////
3303  ///////// GET VSP FLAGS //////////
3304  //////////////////////////////////
3305  //left
3306  UInt uiLeftPartIdx = 0;
3307  const TComDataCU* pcCULeft = 0;
3308  pcCULeft = getPULeft( uiLeftPartIdx, uiPartIdxLB ); 
3309
3310  if (getAvailableFlagA1())
3311  {
3312    m_mergCands[MRG_A1].setCand( &pcMFieldNeighbours[m_numSpatialCands<<1], puhInterDirNeighbours[m_numSpatialCands]
3313#if NH_3D_VSP
3314    , (pcCULeft->getVSPFlag(uiLeftPartIdx) != 0
3315#if NH_3D_IC
3316      && !bICFlag
3317#endif
3318#if NH_3D_ARP
3319      && !bARPFlag
3320#endif
3321#if NH_3D_DBBP
3322      && !bDBBPFlag
3323#endif
3324      )
3325#endif
3326#if NH_3D_SPIVMP
3327      , false
3328#endif
3329      ); 
3330    m_numSpatialCands++;
3331  }
3332
3333  // above
3334  if (getAvailableFlagB1())
3335  {
3336    m_mergCands[MRG_B1].setCand( &pcMFieldNeighbours[m_numSpatialCands<<1], puhInterDirNeighbours[m_numSpatialCands]
3337#if NH_3D_VSP
3338    , false
3339#endif
3340#if NH_3D_SPIVMP
3341      , false
3342#endif
3343      ); 
3344    m_numSpatialCands++;
3345  }
3346
3347  // above right
3348  if (getAvailableFlagB0())
3349  {
3350    m_mergCands[MRG_B0].setCand( &pcMFieldNeighbours[m_numSpatialCands<<1], puhInterDirNeighbours[m_numSpatialCands]
3351#if NH_3D_VSP
3352    , false
3353#endif
3354#if NH_3D_SPIVMP
3355      , false
3356#endif
3357      ); 
3358    m_numSpatialCands++;
3359  }
3360
3361  // left bottom
3362  if (getAvailableFlagA0())
3363  {
3364    m_mergCands[MRG_A0].setCand( &pcMFieldNeighbours[m_numSpatialCands<<1], puhInterDirNeighbours[m_numSpatialCands]
3365#if NH_3D_VSP
3366    , false
3367#endif
3368#if NH_3D_SPIVMP
3369      , false
3370#endif
3371      ); 
3372    m_numSpatialCands++;
3373  }
3374
3375  // above left
3376  if (getAvailableFlagB2())
3377  {
3378    m_mergCands[MRG_B2].setCand( &pcMFieldNeighbours[m_numSpatialCands<<1], puhInterDirNeighbours[m_numSpatialCands]
3379#if NH_3D_VSP
3380    , false
3381#endif
3382#if NH_3D_SPIVMP
3383      , false
3384#endif
3385      ); 
3386    m_numSpatialCands++;
3387  }
3388
3389
3390#if NH_3D_TEXT_MERGE
3391
3392  /////////////////////////////////////////////
3393  //////// TEXTURE MERGE CANDIDATE (T) ////////
3394  /////////////////////////////////////////////
3395
3396  bMPIFlag &= (nPSW + nPSH > 12);
3397  if( bMPIFlag)
3398  {
3399    tmpMV[0].setMvField( cZeroMv, NOT_VALID );
3400    tmpMV[1].setMvField( cZeroMv, NOT_VALID );
3401    tmpDir        =  0;
3402
3403    Bool bSPIVMPFlag = false;
3404
3405    TComPic * pcTexPic = m_pcSlice->getTexturePic();
3406#if H_3D_FCO
3407    if (pcTexPic && pcTexPic->getReconMark())
3408    {
3409#endif   
3410      TComPicYuv*   pcTexRec = pcTexPic->getPicYuvRec  ();
3411      UInt          uiPartAddr;
3412      Int           iWidth, iHeight;
3413      Int           iCurrPosX, iCurrPosY;
3414
3415      this->getPartIndexAndSize( uiPUIdx, uiPartAddr, iWidth, iHeight );
3416      pcTexRec->getTopLeftSamplePos( this->getCtuRsAddr(), this->getZorderIdxInCtu() + uiPartAddr, iCurrPosX, iCurrPosY );
3417
3418      Int iPUWidth, iPUHeight, iNumPart, iNumPartLine;
3419      this->getSPPara(iWidth, iHeight, iNumPart, iNumPartLine, iPUWidth, iPUHeight);
3420
3421      for (Int i=0; i<iNumPart; i++)
3422      {
3423        puhInterDirSP[i] = 0;
3424        pcMvFieldSP[2*i].getMv().set(0, 0);
3425        pcMvFieldSP[2*i+1].getMv().set(0, 0);
3426        pcMvFieldSP[2*i].setRefIdx(-1);
3427        pcMvFieldSP[2*i+1].setRefIdx(-1);
3428      }
3429
3430      Int         iTexCUAddr;
3431      Int         iTexAbsPartIdx;
3432      TComDataCU* pcTexCU;
3433      Int iPartition = 0;
3434      Int iInterDirSaved = 0;
3435      TComMvField cMvFieldSaved[2];
3436
3437      Int iOffsetX = iPUWidth/2;;
3438      Int iOffsetY = iPUHeight/2;
3439
3440      Int         iTexPosX, iTexPosY;
3441#if NH_3D_INTEGER_MV_DEPTH
3442      const TComMv cMvRounding( 1 << ( 2 - 1 ), 1 << ( 2 - 1 ) );
3443#endif
3444      Int         iCenterPosX = iCurrPosX + ( ( iWidth /  iPUWidth ) >> 1 )  * iPUWidth + ( iPUWidth >> 1 );
3445      Int         iCenterPosY = iCurrPosY + ( ( iHeight /  iPUHeight ) >> 1 )  * iPUHeight + (iPUHeight >> 1);
3446      Int         iTexCenterCUAddr, iTexCenterAbsPartIdx;
3447
3448      if(iWidth == iPUWidth && iHeight == iPUHeight)
3449      {
3450        iCenterPosX = iCurrPosX + (iWidth >> 1);
3451        iCenterPosY = iCurrPosY + (iHeight >> 1);
3452      }
3453
3454      // derivation of center motion parameters from the collocated texture CU
3455
3456      pcTexRec->getCUAddrAndPartIdx( iCenterPosX , iCenterPosY , iTexCenterCUAddr, iTexCenterAbsPartIdx );
3457      TComDataCU* pcDefaultCU    = pcTexPic->getCtu( iTexCenterCUAddr );
3458
3459      if( pcDefaultCU->getPredictionMode( iTexCenterAbsPartIdx ) != MODE_INTRA )
3460      {
3461        for( UInt uiCurrRefListId = 0; uiCurrRefListId < 2; uiCurrRefListId++ )
3462        {
3463          RefPicList  eCurrRefPicList = RefPicList( uiCurrRefListId );
3464
3465          TComMvField cDefaultMvField;
3466          pcDefaultCU->getMvField( pcDefaultCU, iTexCenterAbsPartIdx, eCurrRefPicList, cDefaultMvField );
3467          Int         iDefaultRefIdx     = cDefaultMvField.getRefIdx();
3468          if (iDefaultRefIdx >= 0)
3469          {
3470            Int iDefaultRefPOC = pcDefaultCU->getSlice()->getRefPOC(eCurrRefPicList, iDefaultRefIdx);
3471            for (Int iRefPicList = 0; iRefPicList < m_pcSlice->getNumRefIdx( eCurrRefPicList ); iRefPicList++)
3472            {
3473              if (iDefaultRefPOC == m_pcSlice->getRefPOC(eCurrRefPicList, iRefPicList))
3474              {
3475                bSPIVMPFlag = true;
3476#if NH_3D_INTEGER_MV_DEPTH
3477                TComMv cMv = cDefaultMvField.getMv() + cMvRounding;
3478                cMv >>= 2;
3479#else
3480                TComMv cMv = cDefaultMvField.getMv();
3481#endif
3482                cMvFieldSaved[eCurrRefPicList].setMvField(cMv, iRefPicList) ;
3483                break;
3484              }
3485            }
3486          }
3487        }
3488      }
3489      if ( bSPIVMPFlag == true )
3490      {   
3491        iInterDirSaved = (cMvFieldSaved[0].getRefIdx()!=-1 ? 1: 0) + (cMvFieldSaved[1].getRefIdx()!=-1 ? 2: 0);
3492        tmpDir = iInterDirSaved;
3493        tmpMV[0] = cMvFieldSaved[0];
3494        tmpMV[1] = cMvFieldSaved[1];
3495      }
3496
3497      if ( iInterDirSaved != 0 )
3498      {
3499        for (Int i=iCurrPosY; i < iCurrPosY + iHeight; i += iPUHeight)
3500        {
3501          for (Int j = iCurrPosX; j < iCurrPosX + iWidth; j += iPUWidth)
3502          {
3503            iTexPosX     = j + iOffsetX;
3504            iTexPosY     = i + iOffsetY; 
3505            pcTexRec->getCUAddrAndPartIdx( iTexPosX, iTexPosY, iTexCUAddr, iTexAbsPartIdx );
3506            pcTexCU  = pcTexPic->getCtu( iTexCUAddr );
3507
3508            if( pcTexCU && !pcTexCU->isIntra(iTexAbsPartIdx) )
3509            {
3510              for( UInt uiCurrRefListId = 0; uiCurrRefListId < 2; uiCurrRefListId++ )
3511              {
3512                RefPicList  eCurrRefPicList = RefPicList( uiCurrRefListId );
3513                TComMvField cTexMvField;
3514                pcTexCU->getMvField( pcTexCU, iTexAbsPartIdx, eCurrRefPicList, cTexMvField );
3515                Int iValidDepRef = getPic()->isTextRefValid( eCurrRefPicList, cTexMvField.getRefIdx() );
3516                if( (cTexMvField.getRefIdx()>=0) && ( iValidDepRef >= 0 ) )
3517                {
3518#if NH_3D_INTEGER_MV_DEPTH
3519                  TComMv cMv = cTexMvField.getMv() + cMvRounding;
3520                  cMv >>=2;         
3521#else
3522                  TComMv cMv = cTexMvField.getMv();
3523#endif         
3524                  pcMvFieldSP[2*iPartition + uiCurrRefListId].setMvField(cMv, iValidDepRef);
3525                }
3526              }
3527            }
3528            puhInterDirSP[iPartition] = (pcMvFieldSP[2*iPartition].getRefIdx()!=-1 ? 1: 0) + (pcMvFieldSP[2*iPartition+1].getRefIdx()!=-1 ? 2: 0);
3529            if (puhInterDirSP[iPartition] == 0)
3530            {
3531              if (iInterDirSaved != 0)
3532              {
3533                puhInterDirSP[iPartition] = iInterDirSaved;
3534                pcMvFieldSP[2*iPartition] = cMvFieldSaved[0];
3535                pcMvFieldSP[2*iPartition + 1] = cMvFieldSaved[1];
3536              }
3537            }
3538
3539            iPartition ++;
3540          }
3541        }
3542      }
3543#if H_3D_FCO
3544    }
3545#endif
3546    if( tmpDir != 0 )
3547    {
3548      Int iCnloop = 0;
3549      for(iCnloop = 0; iCnloop < 2; iCnloop ++)
3550      {
3551        if ( !m_mergCands[MRG_A1+iCnloop].m_bAvailable )  // pruning to A1, B1
3552        {
3553          continue;
3554        }
3555        if (hasEqualMotion( tmpDir, tmpMV, m_mergCands[MRG_A1+iCnloop].m_uDir, m_mergCands[MRG_A1+iCnloop].m_cMvField ) )
3556        {
3557          m_mergCands[MRG_A1+iCnloop].m_bAvailable = false;
3558          break;
3559        }     
3560      }
3561      m_mergCands[MRG_T].setCand( tmpMV, tmpDir, false, bSPIVMPFlag);
3562
3563      if ( mrgCandIdx == iCount )
3564      {
3565        return;
3566      }
3567      iCount ++;
3568    }
3569  }
3570#endif
3571
3572#if NH_3D_IV_MERGE
3573  /////////////////////////////////////////////////////////////////
3574  //////// DERIVE IvMC, IvMCShift,IvDCShift, IvDC  Candidates /////
3575  /////////////////////////////////////////////////////////////////
3576
3577  // { IvMCL0, IvMCL1, IvDCL0, IvDCL1, IvMCL0Shift, IvMCL1Shift, IvDCL0Shift, IvDCL1Shift }; 
3578  // An enumerator would be appropriate here!
3579  TComMv ivCandMv    [8];
3580  Int    ivCandRefIdx[8] = {-1, -1, -1, -1, -1, -1, -1, -1};
3581
3582  // { IvMC, IvDC, IvMCShift, IvDCShift }; 
3583  Int    ivCandDir   [4] = {0, 0, 0, 0};
3584
3585  Bool ivMvPredFlag   = getSlice()->getIvMvPredFlag();
3586
3587  ivMvPredFlag &= (nPSW + nPSH > 12);
3588  if ( ivMvPredFlag && cDisInfo.m_aVIdxCan!=-1)
3589  {
3590#if NH_3D_IC
3591    getInterViewMergeCands(uiPUIdx, ivCandRefIdx, ivCandMv, &cDisInfo, ivCandDir , bIsDepth, pcMvFieldSP, puhInterDirSP, bICFlag );
3592#else
3593    getInterViewMergeCands(uiPUIdx, ivCandRefIdx, ivCandMv, &cDisInfo, ivCandDir , bIsDepth, pcMvFieldSP, puhInterDirSP, false );
3594#endif
3595  } 
3596
3597  ///////////////////////////////////////////////
3598  //////// INTER VIEW MOTION COMP(IvMC) /////////
3599  ///////////////////////////////////////////////
3600  if( getSlice()->getIsDepth() )
3601  {
3602    ivCandDir[1] = ivCandDir[2] = ivCandDir[3] = 0;
3603  }
3604
3605  if( ivCandDir[0] )
3606  {
3607    tmpMV[0].setMvField( cZeroMv, NOT_VALID );
3608    tmpMV[1].setMvField( cZeroMv, NOT_VALID );
3609
3610    if( ( ivCandDir[0] & 1 ) == 1 )
3611    {
3612      tmpMV[0].setMvField( ivCandMv[ 0 ], ivCandRefIdx[ 0 ] );
3613    }
3614    if( ( ivCandDir[0] & 2 ) == 2 )
3615    {
3616      tmpMV[1].setMvField( ivCandMv[ 1 ], ivCandRefIdx[ 1 ] );
3617    }
3618
3619    Bool bRemoveSpa = false; //pruning
3620
3621    if (!bIsDepth)
3622    {
3623      for(Int i = 0; i < 2; i ++)
3624      {
3625        if ( !m_mergCands[MRG_A1 + i].m_bAvailable ) // pruning to A1, B1
3626        {
3627          continue;
3628        }
3629        if (hasEqualMotion(ivCandDir[0], tmpMV, m_mergCands[MRG_A1+i].m_uDir,  m_mergCands[MRG_A1+i].m_cMvField) )
3630        {
3631          m_mergCands[MRG_A1+i].m_bAvailable = false;
3632          break;
3633        }     
3634      }
3635    }
3636    else
3637    {
3638      if( hasEqualMotion( ivCandDir[0], tmpMV, m_mergCands[MRG_T].m_uDir, m_mergCands[MRG_T].m_cMvField ) )
3639      {
3640        bRemoveSpa                      = true;
3641      }
3642    }
3643    if (!bRemoveSpa)
3644    {
3645      Bool spiMvpFlag = false;
3646      if(!m_pcSlice->getIsDepth())
3647      {
3648        spiMvpFlag = true;
3649      }
3650#if NH_3D_DBBP
3651      spiMvpFlag &= !bDBBPFlag;
3652#endif
3653
3654      m_mergCands[MRG_IVMC].setCand( tmpMV, ivCandDir[0], false, spiMvpFlag);
3655
3656      if ( mrgCandIdx == iCount )
3657      {
3658        return;
3659      }
3660      iCount ++;
3661    }
3662  } 
3663
3664  // early termination
3665  if (iCount == getSlice()->getMaxNumMergeCand()) 
3666  {
3667    return;
3668  }
3669#endif
3670
3671  iCount += m_mergCands[MRG_A1].m_bAvailable + m_mergCands[MRG_B1].m_bAvailable;
3672
3673#if NH_3D_VSP
3674  /////////////////////////////////////////////////
3675  //////// VIEW SYNTHESIS PREDICTION (VSP) ////////
3676  /////////////////////////////////////////////////
3677  if (iCount<getSlice()->getMaxNumMergeCand())
3678  {
3679    if (
3680      (!getAvailableFlagA1() || !(pcCULeft->getVSPFlag(uiLeftPartIdx) != 0)) &&
3681#if NH_3D_IC
3682      !bICFlag &&
3683#endif
3684#if NH_3D_ARP
3685      !bARPFlag &&
3686#endif
3687#if NH_3D
3688      (nPSW + nPSH > 12) &&
3689#endif
3690#if NH_3D_DBBP
3691      !bDBBPFlag &&
3692#endif
3693      xAddVspCand( mrgCandIdx, &cDisInfo, iCount ) )
3694    {
3695      return;
3696    }
3697
3698    // early termination
3699    if (iCount == getSlice()->getMaxNumMergeCand())
3700    {
3701      return;
3702    }
3703  }
3704#endif
3705
3706  iCount += m_mergCands[MRG_B0].m_bAvailable;
3707
3708#if NH_3D_IV_MERGE
3709  /////////////////////////////////////////////
3710  //////// INTER VIEW DISP COMP (IvDC) ////////
3711  /////////////////////////////////////////////
3712  if( ivCandDir[1] && iCount < getSlice()->getMaxNumMergeCand() && !getSlice()->getIsDepth() )
3713  {
3714    assert(iCount < getSlice()->getMaxNumMergeCand());
3715
3716    tmpMV[0].setMvField( cZeroMv, NOT_VALID );
3717    tmpMV[1].setMvField( cZeroMv, NOT_VALID );
3718    if( ( ivCandDir[1] & 1 ) == 1 )
3719    {
3720      tmpMV[0].setMvField( ivCandMv[ 2 ], ivCandRefIdx[ 2 ] );
3721    }
3722    if( ( ivCandDir[1] & 2 ) == 2 )
3723    {
3724      tmpMV[1].setMvField( ivCandMv[ 3 ], ivCandRefIdx[ 3 ] );
3725    }
3726
3727    Bool bRemoveSpa = false; //pruning to A1, B1
3728    for(Int i = 0; i < 2; i ++)
3729    {
3730      if ( !m_mergCands[MRG_A1+i].m_bAvailable ) 
3731      {
3732        continue;
3733      }
3734      if ( hasEqualMotion(ivCandDir[1], tmpMV, m_mergCands[MRG_A1+i].m_uDir, m_mergCands[MRG_A1+i].m_cMvField) )
3735      {
3736        bRemoveSpa                      = true;
3737        break;
3738      }     
3739    }
3740    if(!bRemoveSpa)
3741    {
3742#if NH_3D_NBDV
3743      tmpMV[0].getMv().setIDVFlag (false);
3744      tmpMV[1].getMv().setIDVFlag (false);
3745#endif
3746      m_mergCands[MRG_IVDC].setCand( tmpMV, ivCandDir[1], false, false);
3747
3748      if ( mrgCandIdx == iCount )
3749        return;
3750      iCount ++;
3751
3752      // early termination
3753      if (iCount == getSlice()->getMaxNumMergeCand()) 
3754      {
3755        return;
3756      }
3757    }
3758  } 
3759#endif // H_3D_IV_MERGE
3760
3761  iCount += m_mergCands[MRG_A0].m_bAvailable + m_mergCands[MRG_B2].m_bAvailable;
3762
3763#if NH_3D_IV_MERGE
3764  ////////////////////////////////////////////////////
3765  //////// SHIFTED IV (IvMCShift + IvDCShift) ////////
3766  ////////////////////////////////////////////////////
3767  if(  ivMvPredFlag && iCount < getSlice()->getMaxNumMergeCand() && !getSlice()->getIsDepth() ) 
3768  {
3769    if(xAddIvMRGCand( mrgCandIdx,  iCount, ivCandDir, ivCandMv, ivCandRefIdx ) )
3770    {
3771      return;
3772    }
3773    //early termination
3774    if (iCount == getSlice()->getMaxNumMergeCand()) 
3775    {
3776      return;
3777    }
3778  }
3779#endif
3780}
3781#endif
3782
3783//! Construct a list of merging candidates
3784#if NH_3D
3785Void TComDataCU::getInterMergeCandidates( UInt uiAbsPartIdx, UInt uiPUIdx, TComMvField* pcMvFieldNeighbours, UChar* puhInterDirNeighbours, Int& numValidMergeCand, Int mrgCandIdx )
3786#else
3787Void TComDataCU::getInterMergeCandidates( UInt uiAbsPartIdx, UInt uiPUIdx, TComMvField* pcMvFieldNeighbours, UChar* puhInterDirNeighbours, Int& numValidMergeCand, Int mrgCandIdx ) const
3788#endif
3789{
3790  UInt uiAbsPartAddr = m_absZIdxInCtu + uiAbsPartIdx;
3791#if NH_3D_MLC
3792  Bool abCandIsInter[ MRG_MAX_NUM_CANDS_MEM ];
3793#else
3794  Bool abCandIsInter[ MRG_MAX_NUM_CANDS ];
3795#endif
3796  for( UInt ui = 0; ui < getSlice()->getMaxNumMergeCand(); ++ui )
3797  {
3798    abCandIsInter[ui] = false;
3799    pcMvFieldNeighbours[ ( ui << 1 )     ].setRefIdx(NOT_VALID);
3800    pcMvFieldNeighbours[ ( ui << 1 ) + 1 ].setRefIdx(NOT_VALID);
3801  }
3802  numValidMergeCand = getSlice()->getMaxNumMergeCand();
3803  // compute the location of the current PU
3804  Int xP, yP, nPSW, nPSH;
3805  this->getPartPosition(uiPUIdx, xP, yP, nPSW, nPSH);
3806
3807  Int iCount = 0;
3808
3809  UInt uiPartIdxLT, uiPartIdxRT, uiPartIdxLB;
3810  PartSize cCurPS = getPartitionSize( uiAbsPartIdx );
3811  deriveLeftRightTopIdxGeneral( uiAbsPartIdx, uiPUIdx, uiPartIdxLT, uiPartIdxRT );
3812  deriveLeftBottomIdxGeneral( uiAbsPartIdx, uiPUIdx, uiPartIdxLB );
3813
3814  //left
3815  UInt uiLeftPartIdx = 0;
3816  const TComDataCU *pcCULeft = getPULeft( uiLeftPartIdx, uiPartIdxLB );
3817
3818  Bool isAvailableA1 = pcCULeft &&
3819                       pcCULeft->isDiffMER(xP -1, yP+nPSH-1, xP, yP) &&
3820                       !( uiPUIdx == 1 && (cCurPS == SIZE_Nx2N || cCurPS == SIZE_nLx2N || cCurPS == SIZE_nRx2N) ) &&
3821                       pcCULeft->isInter( uiLeftPartIdx ) ;
3822
3823  if ( isAvailableA1 )
3824  {
3825#if NH_3D_MLC
3826    m_bAvailableFlagA1 = 1;
3827#endif
3828    abCandIsInter[iCount] = true;
3829    // get Inter Dir
3830    puhInterDirNeighbours[iCount] = pcCULeft->getInterDir( uiLeftPartIdx );
3831    // get Mv from Left
3832    TComDataCU::getMvField( pcCULeft, uiLeftPartIdx, REF_PIC_LIST_0, pcMvFieldNeighbours[iCount<<1] );
3833    if ( getSlice()->isInterB() )
3834    {
3835      TComDataCU::getMvField( pcCULeft, uiLeftPartIdx, REF_PIC_LIST_1, pcMvFieldNeighbours[(iCount<<1)+1] );
3836    }
3837    if ( mrgCandIdx == iCount )
3838    {
3839      return;
3840    }
3841    iCount ++;
3842  }
3843
3844  // early termination
3845  if (iCount == getSlice()->getMaxNumMergeCand())
3846  {
3847    return;
3848  }
3849  // above
3850  UInt uiAbovePartIdx = 0;
3851  const TComDataCU *pcCUAbove = getPUAbove( uiAbovePartIdx, uiPartIdxRT );
3852
3853  Bool isAvailableB1 = pcCUAbove &&
3854                       pcCUAbove->isDiffMER(xP+nPSW-1, yP-1, xP, yP) &&
3855                       !( uiPUIdx == 1 && (cCurPS == SIZE_2NxN || cCurPS == SIZE_2NxnU || cCurPS == SIZE_2NxnD) ) &&
3856                       pcCUAbove->isInter( uiAbovePartIdx );
3857
3858  if ( isAvailableB1 && (!isAvailableA1 || !pcCULeft->hasEqualMotion( uiLeftPartIdx, pcCUAbove, uiAbovePartIdx ) ) )
3859  {
3860#if NH_3D_MLC
3861    m_bAvailableFlagB1 = 1;
3862#endif
3863    abCandIsInter[iCount] = true;
3864    // get Inter Dir
3865    puhInterDirNeighbours[iCount] = pcCUAbove->getInterDir( uiAbovePartIdx );
3866    // get Mv from Left
3867    TComDataCU::getMvField( pcCUAbove, uiAbovePartIdx, REF_PIC_LIST_0, pcMvFieldNeighbours[iCount<<1] );
3868    if ( getSlice()->isInterB() )
3869    {
3870      TComDataCU::getMvField( pcCUAbove, uiAbovePartIdx, REF_PIC_LIST_1, pcMvFieldNeighbours[(iCount<<1)+1] );
3871    }
3872    if ( mrgCandIdx == iCount )
3873    {
3874      return;
3875    }
3876    iCount ++;
3877  }
3878  // early termination
3879  if (iCount == getSlice()->getMaxNumMergeCand())
3880  {
3881    return;
3882  }
3883
3884  // above right
3885  UInt uiAboveRightPartIdx = 0;
3886  const TComDataCU *pcCUAboveRight = getPUAboveRight( uiAboveRightPartIdx, uiPartIdxRT );
3887
3888  Bool isAvailableB0 = pcCUAboveRight &&
3889                       pcCUAboveRight->isDiffMER(xP+nPSW, yP-1, xP, yP) &&
3890                       pcCUAboveRight->isInter( uiAboveRightPartIdx );
3891
3892  if ( isAvailableB0 && ( !isAvailableB1 || !pcCUAbove->hasEqualMotion( uiAbovePartIdx, pcCUAboveRight, uiAboveRightPartIdx ) ) )
3893  {
3894#if NH_3D_MLC
3895    m_bAvailableFlagB0 = 1;
3896#endif
3897    abCandIsInter[iCount] = true;
3898    // get Inter Dir
3899    puhInterDirNeighbours[iCount] = pcCUAboveRight->getInterDir( uiAboveRightPartIdx );
3900    // get Mv from Left
3901    TComDataCU::getMvField( pcCUAboveRight, uiAboveRightPartIdx, REF_PIC_LIST_0, pcMvFieldNeighbours[iCount<<1] );
3902    if ( getSlice()->isInterB() )
3903    {
3904      TComDataCU::getMvField( pcCUAboveRight, uiAboveRightPartIdx, REF_PIC_LIST_1, pcMvFieldNeighbours[(iCount<<1)+1] );
3905    }
3906    if ( mrgCandIdx == iCount )
3907    {
3908      return;
3909    }
3910    iCount ++;
3911  }
3912  // early termination
3913  if (iCount == getSlice()->getMaxNumMergeCand())
3914  {
3915    return;
3916  }
3917
3918  //left bottom
3919  UInt uiLeftBottomPartIdx = 0;
3920  const TComDataCU *pcCULeftBottom = this->getPUBelowLeft( uiLeftBottomPartIdx, uiPartIdxLB );
3921
3922  Bool isAvailableA0 = pcCULeftBottom &&
3923                       pcCULeftBottom->isDiffMER(xP-1, yP+nPSH, xP, yP) &&
3924                       pcCULeftBottom->isInter( uiLeftBottomPartIdx ) ;
3925
3926  if ( isAvailableA0 && ( !isAvailableA1 || !pcCULeft->hasEqualMotion( uiLeftPartIdx, pcCULeftBottom, uiLeftBottomPartIdx ) ) )
3927  {
3928#if NH_3D_MLC
3929    m_bAvailableFlagA0 = 1;
3930#endif
3931    abCandIsInter[iCount] = true;
3932    // get Inter Dir
3933    puhInterDirNeighbours[iCount] = pcCULeftBottom->getInterDir( uiLeftBottomPartIdx );
3934    // get Mv from Left
3935    TComDataCU::getMvField( pcCULeftBottom, uiLeftBottomPartIdx, REF_PIC_LIST_0, pcMvFieldNeighbours[iCount<<1] );
3936    if ( getSlice()->isInterB() )
3937    {
3938      TComDataCU::getMvField( pcCULeftBottom, uiLeftBottomPartIdx, REF_PIC_LIST_1, pcMvFieldNeighbours[(iCount<<1)+1] );
3939    }
3940    if ( mrgCandIdx == iCount )
3941    {
3942      return;
3943    }
3944    iCount ++;
3945  }
3946  // early termination
3947  if (iCount == getSlice()->getMaxNumMergeCand())
3948  {
3949    return;
3950  }
3951
3952  // above left
3953  if( iCount < 4 )
3954  {
3955    UInt uiAboveLeftPartIdx = 0;
3956    const TComDataCU *pcCUAboveLeft = getPUAboveLeft( uiAboveLeftPartIdx, uiAbsPartAddr );
3957
3958    Bool isAvailableB2 = pcCUAboveLeft &&
3959                         pcCUAboveLeft->isDiffMER(xP-1, yP-1, xP, yP) &&
3960                         pcCUAboveLeft->isInter( uiAboveLeftPartIdx );
3961
3962    if ( isAvailableB2 && ( !isAvailableA1 || !pcCULeft->hasEqualMotion( uiLeftPartIdx, pcCUAboveLeft, uiAboveLeftPartIdx ) )
3963        && ( !isAvailableB1 || !pcCUAbove->hasEqualMotion( uiAbovePartIdx, pcCUAboveLeft, uiAboveLeftPartIdx ) ) )
3964    {
3965#if NH_3D_MLC
3966      m_bAvailableFlagB2 = 1;
3967#endif
3968      abCandIsInter[iCount] = true;
3969      // get Inter Dir
3970      puhInterDirNeighbours[iCount] = pcCUAboveLeft->getInterDir( uiAboveLeftPartIdx );
3971      // get Mv from Left
3972      TComDataCU::getMvField( pcCUAboveLeft, uiAboveLeftPartIdx, REF_PIC_LIST_0, pcMvFieldNeighbours[iCount<<1] );
3973      if ( getSlice()->isInterB() )
3974      {
3975        TComDataCU::getMvField( pcCUAboveLeft, uiAboveLeftPartIdx, REF_PIC_LIST_1, pcMvFieldNeighbours[(iCount<<1)+1] );
3976      }
3977      if ( mrgCandIdx == iCount )
3978      {
3979        return;
3980      }
3981      iCount ++;
3982    }
3983  }
3984  // early termination
3985  if (iCount == getSlice()->getMaxNumMergeCand())
3986  {
3987    return;
3988  }
3989
3990  if ( getSlice()->getEnableTMVPFlag() )
3991  {
3992    //>> MTK colocated-RightBottom
3993    UInt uiPartIdxRB;
3994
3995    deriveRightBottomIdx( uiPUIdx, uiPartIdxRB );
3996
3997    UInt uiAbsPartIdxTmp = g_auiZscanToRaster[uiPartIdxRB];
3998    const UInt numPartInCtuWidth  = m_pcPic->getNumPartInCtuWidth();
3999    const UInt numPartInCtuHeight = m_pcPic->getNumPartInCtuHeight();
4000
4001    TComMv cColMv;
4002    Int iRefIdx;
4003    Int ctuRsAddr = -1;
4004
4005    if (   ( ( m_pcPic->getCtu(m_ctuRsAddr)->getCUPelX() + g_auiRasterToPelX[uiAbsPartIdxTmp] + m_pcPic->getMinCUWidth () ) < m_pcSlice->getSPS()->getPicWidthInLumaSamples () )  // image boundary check
4006        && ( ( m_pcPic->getCtu(m_ctuRsAddr)->getCUPelY() + g_auiRasterToPelY[uiAbsPartIdxTmp] + m_pcPic->getMinCUHeight() ) < m_pcSlice->getSPS()->getPicHeightInLumaSamples() ) )
4007    {
4008      if ( ( uiAbsPartIdxTmp % numPartInCtuWidth < numPartInCtuWidth - 1 ) &&           // is not at the last column of CTU
4009        ( uiAbsPartIdxTmp / numPartInCtuWidth < numPartInCtuHeight - 1 ) )              // is not at the last row    of CTU
4010      {
4011        uiAbsPartAddr = g_auiRasterToZscan[ uiAbsPartIdxTmp + numPartInCtuWidth + 1 ];
4012        ctuRsAddr = getCtuRsAddr();
4013      }
4014      else if ( uiAbsPartIdxTmp % numPartInCtuWidth < numPartInCtuWidth - 1 )           // is not at the last column of CTU But is last row of CTU
4015      {
4016        uiAbsPartAddr = g_auiRasterToZscan[ (uiAbsPartIdxTmp + numPartInCtuWidth + 1) % m_pcPic->getNumPartitionsInCtu() ];
4017      }
4018      else if ( uiAbsPartIdxTmp / numPartInCtuWidth < numPartInCtuHeight - 1 )          // is not at the last row of CTU But is last column of CTU
4019      {
4020        uiAbsPartAddr = g_auiRasterToZscan[ uiAbsPartIdxTmp + 1 ];
4021        ctuRsAddr = getCtuRsAddr() + 1;
4022      }
4023      else //is the right bottom corner of CTU
4024      {
4025        uiAbsPartAddr = 0;
4026      }
4027    }
4028
4029    iRefIdx = 0;
4030
4031    Bool bExistMV = false;
4032    UInt uiPartIdxCenter;
4033    Int dir = 0;
4034    UInt uiArrayAddr = iCount;
4035    xDeriveCenterIdx( uiPUIdx, uiPartIdxCenter );
4036    bExistMV = ctuRsAddr >= 0 && xGetColMVP( REF_PIC_LIST_0, ctuRsAddr, uiAbsPartAddr, cColMv, iRefIdx );
4037    if( bExistMV == false )
4038    {
4039      bExistMV = xGetColMVP( REF_PIC_LIST_0, getCtuRsAddr(), uiPartIdxCenter,  cColMv, iRefIdx );
4040    }
4041    if( bExistMV )
4042    {
4043      dir |= 1;
4044      pcMvFieldNeighbours[ 2 * uiArrayAddr ].setMvField( cColMv, iRefIdx );
4045    }
4046
4047    if ( getSlice()->isInterB() )
4048    {
4049#if NH_3D_TMVP
4050      iRefIdx = 0;
4051#endif
4052      bExistMV = ctuRsAddr >= 0 && xGetColMVP( REF_PIC_LIST_1, ctuRsAddr, uiAbsPartAddr, cColMv, iRefIdx);
4053      if( bExistMV == false )
4054      {
4055        bExistMV = xGetColMVP( REF_PIC_LIST_1, getCtuRsAddr(), uiPartIdxCenter, cColMv, iRefIdx );
4056      }
4057      if( bExistMV )
4058      {
4059        dir |= 2;
4060        pcMvFieldNeighbours[ 2 * uiArrayAddr + 1 ].setMvField( cColMv, iRefIdx );
4061      }
4062    }
4063
4064    if (dir != 0)
4065    {
4066      puhInterDirNeighbours[uiArrayAddr] = dir;
4067      abCandIsInter[uiArrayAddr] = true;
4068#if NH_3D_NBDV
4069      pcMvFieldNeighbours[iCount<<1    ].getMv().setIDVFlag (false);
4070      pcMvFieldNeighbours[(iCount<<1)+1].getMv().setIDVFlag (false);
4071#endif
4072
4073      if ( mrgCandIdx == iCount )
4074      {
4075        return;
4076      }
4077      iCount++;
4078    }
4079  }
4080  // early termination
4081  if (iCount == getSlice()->getMaxNumMergeCand())
4082  {
4083    return;
4084  }
4085
4086  UInt uiArrayAddr = iCount;
4087  UInt uiCutoff = uiArrayAddr;
4088
4089#if NH_3D_MLC
4090  if ( getSlice()->isInterB() && iCount<5)
4091#else
4092  if ( getSlice()->isInterB() )
4093#endif
4094  {
4095    static const UInt NUM_PRIORITY_LIST=12;
4096    static const UInt uiPriorityList0[NUM_PRIORITY_LIST] = {0 , 1, 0, 2, 1, 2, 0, 3, 1, 3, 2, 3};
4097    static const UInt uiPriorityList1[NUM_PRIORITY_LIST] = {1 , 0, 2, 0, 2, 1, 3, 0, 3, 1, 3, 2};
4098
4099    for (Int idx=0; idx<uiCutoff*(uiCutoff-1) && uiArrayAddr!= getSlice()->getMaxNumMergeCand(); idx++)
4100    {
4101      assert(idx<NUM_PRIORITY_LIST);
4102      Int i = uiPriorityList0[idx];
4103      Int j = uiPriorityList1[idx];
4104      if (abCandIsInter[i] && abCandIsInter[j]&& (puhInterDirNeighbours[i]&0x1)&&(puhInterDirNeighbours[j]&0x2))
4105      {
4106        abCandIsInter[uiArrayAddr] = true;
4107        puhInterDirNeighbours[uiArrayAddr] = 3;
4108
4109        // get Mv from cand[i] and cand[j]
4110        pcMvFieldNeighbours[uiArrayAddr << 1].setMvField(pcMvFieldNeighbours[i<<1].getMv(), pcMvFieldNeighbours[i<<1].getRefIdx());
4111        pcMvFieldNeighbours[( uiArrayAddr << 1 ) + 1].setMvField(pcMvFieldNeighbours[(j<<1)+1].getMv(), pcMvFieldNeighbours[(j<<1)+1].getRefIdx());
4112
4113        Int iRefPOCL0 = m_pcSlice->getRefPOC( REF_PIC_LIST_0, pcMvFieldNeighbours[(uiArrayAddr<<1)].getRefIdx() );
4114        Int iRefPOCL1 = m_pcSlice->getRefPOC( REF_PIC_LIST_1, pcMvFieldNeighbours[(uiArrayAddr<<1)+1].getRefIdx() );
4115        if (iRefPOCL0 == iRefPOCL1 && pcMvFieldNeighbours[(uiArrayAddr<<1)].getMv() == pcMvFieldNeighbours[(uiArrayAddr<<1)+1].getMv())
4116        {
4117          abCandIsInter[uiArrayAddr] = false;
4118        }
4119        else
4120        {
4121          uiArrayAddr++;
4122        }
4123      }
4124    }
4125  }
4126  // early termination
4127  if (uiArrayAddr == getSlice()->getMaxNumMergeCand())
4128  {
4129    return;
4130  }
4131
4132  Int iNumRefIdx = (getSlice()->isInterB()) ? min(m_pcSlice->getNumRefIdx(REF_PIC_LIST_0), m_pcSlice->getNumRefIdx(REF_PIC_LIST_1)) : m_pcSlice->getNumRefIdx(REF_PIC_LIST_0);
4133
4134  Int r = 0;
4135  Int refcnt = 0;
4136  while (uiArrayAddr < getSlice()->getMaxNumMergeCand())
4137  {
4138    abCandIsInter[uiArrayAddr] = true;
4139    puhInterDirNeighbours[uiArrayAddr] = 1;
4140    pcMvFieldNeighbours[uiArrayAddr << 1].setMvField( TComMv(0, 0), r);
4141
4142    if ( getSlice()->isInterB() )
4143    {
4144      puhInterDirNeighbours[uiArrayAddr] = 3;
4145      pcMvFieldNeighbours[(uiArrayAddr << 1) + 1].setMvField(TComMv(0, 0), r);
4146    }
4147    uiArrayAddr++;
4148
4149    if ( refcnt == iNumRefIdx - 1 )
4150    {
4151      r = 0;
4152    }
4153    else
4154    {
4155      ++r;
4156      ++refcnt;
4157    }
4158  }
4159  numValidMergeCand = uiArrayAddr;
4160}
4161
4162/** Check whether the current PU and a spatial neighboring PU are in a same ME region.
4163 * \param xN, yN   location of the upper-left corner pixel of a neighboring PU
4164 * \param xP, yP   location of the upper-left corner pixel of the current PU
4165 */
4166Bool TComDataCU::isDiffMER(Int xN, Int yN, Int xP, Int yP) const
4167{
4168
4169  UInt plevel = this->getSlice()->getPPS()->getLog2ParallelMergeLevelMinus2() + 2;
4170  if ((xN>>plevel)!= (xP>>plevel))
4171  {
4172    return true;
4173  }
4174  if ((yN>>plevel)!= (yP>>plevel))
4175  {
4176    return true;
4177  }
4178  return false;
4179}
4180
4181/** Calculate the location of upper-left corner pixel and size of the current PU.
4182 * \param partIdx       PU index within a CU
4183 * \param xP, yP        location of the upper-left corner pixel of the current PU
4184 * \param nPSW, nPSH    size of the current PU
4185 */
4186Void TComDataCU::getPartPosition( UInt partIdx, Int& xP, Int& yP, Int& nPSW, Int& nPSH) const
4187{
4188  UInt col = m_uiCUPelX;
4189  UInt row = m_uiCUPelY;
4190
4191  switch ( m_pePartSize[0] )
4192  {
4193  case SIZE_2NxN:
4194    nPSW = getWidth(0);
4195    nPSH = getHeight(0) >> 1;
4196    xP   = col;
4197    yP   = (partIdx ==0)? row: row + nPSH;
4198    break;
4199  case SIZE_Nx2N:
4200    nPSW = getWidth(0) >> 1;
4201    nPSH = getHeight(0);
4202    xP   = (partIdx ==0)? col: col + nPSW;
4203    yP   = row;
4204    break;
4205  case SIZE_NxN:
4206    nPSW = getWidth(0) >> 1;
4207    nPSH = getHeight(0) >> 1;
4208    xP   = col + (partIdx&0x1)*nPSW;
4209    yP   = row + (partIdx>>1)*nPSH;
4210    break;
4211  case SIZE_2NxnU:
4212    nPSW = getWidth(0);
4213    nPSH = ( partIdx == 0 ) ?  getHeight(0) >> 2 : ( getHeight(0) >> 2 ) + ( getHeight(0) >> 1 );
4214    xP   = col;
4215    yP   = (partIdx ==0)? row: row + getHeight(0) - nPSH;
4216
4217    break;
4218  case SIZE_2NxnD:
4219    nPSW = getWidth(0);
4220    nPSH = ( partIdx == 0 ) ?  ( getHeight(0) >> 2 ) + ( getHeight(0) >> 1 ) : getHeight(0) >> 2;
4221    xP   = col;
4222    yP   = (partIdx ==0)? row: row + getHeight(0) - nPSH;
4223    break;
4224  case SIZE_nLx2N:
4225    nPSW = ( partIdx == 0 ) ? getWidth(0) >> 2 : ( getWidth(0) >> 2 ) + ( getWidth(0) >> 1 );
4226    nPSH = getHeight(0);
4227    xP   = (partIdx ==0)? col: col + getWidth(0) - nPSW;
4228    yP   = row;
4229    break;
4230  case SIZE_nRx2N:
4231    nPSW = ( partIdx == 0 ) ? ( getWidth(0) >> 2 ) + ( getWidth(0) >> 1 ) : getWidth(0) >> 2;
4232    nPSH = getHeight(0);
4233    xP   = (partIdx ==0)? col: col + getWidth(0) - nPSW;
4234    yP   = row;
4235    break;
4236  default:
4237    assert ( m_pePartSize[0] == SIZE_2Nx2N );
4238    nPSW = getWidth(0);
4239    nPSH = getHeight(0);
4240    xP   = col ;
4241    yP   = row ;
4242
4243    break;
4244  }
4245}
4246
4247/** Constructs a list of candidates for AMVP (See specification, section "Derivation process for motion vector predictor candidates")
4248 * \param uiPartIdx
4249 * \param uiPartAddr
4250 * \param eRefPicList
4251 * \param iRefIdx
4252 * \param pInfo
4253 */
4254Void TComDataCU::fillMvpCand ( const UInt partIdx, const UInt partAddr, const RefPicList eRefPicList, const Int refIdx, AMVPInfo* pInfo ) const
4255{
4256  pInfo->iN = 0;
4257  if (refIdx < 0)
4258  {
4259    return;
4260  }
4261
4262  //-- Get Spatial MV
4263  UInt partIdxLT, partIdxRT, partIdxLB;
4264  deriveLeftRightTopIdx( partIdx, partIdxLT, partIdxRT );
4265  deriveLeftBottomIdx( partIdx, partIdxLB );
4266
4267  Bool isScaledFlagLX = false; /// variable name from specification; true when the PUs below left or left are available (availableA0 || availableA1).
4268  {
4269    UInt idx;
4270    const TComDataCU* tmpCU = getPUBelowLeft(idx, partIdxLB);
4271    isScaledFlagLX = (tmpCU != NULL) && (tmpCU->isInter(idx));
4272    if (!isScaledFlagLX)
4273    {
4274      tmpCU = getPULeft(idx, partIdxLB);
4275      isScaledFlagLX = (tmpCU != NULL) && (tmpCU->isInter(idx));
4276    }
4277  }
4278
4279  // Left predictor search
4280  if (isScaledFlagLX)
4281  {
4282    Bool bAdded = xAddMVPCandUnscaled( *pInfo, eRefPicList, refIdx, partIdxLB, MD_BELOW_LEFT);
4283    if (!bAdded)
4284    {
4285      bAdded = xAddMVPCandUnscaled( *pInfo, eRefPicList, refIdx, partIdxLB, MD_LEFT );
4286      if(!bAdded)
4287      {
4288        bAdded = xAddMVPCandWithScaling( *pInfo, eRefPicList, refIdx, partIdxLB, MD_BELOW_LEFT);
4289        if (!bAdded)
4290        {
4291          xAddMVPCandWithScaling( *pInfo, eRefPicList, refIdx, partIdxLB, MD_LEFT );
4292        }
4293      }
4294    }
4295  }
4296
4297  // Above predictor search
4298  {
4299    Bool bAdded = xAddMVPCandUnscaled( *pInfo, eRefPicList, refIdx, partIdxRT, MD_ABOVE_RIGHT);
4300    if (!bAdded)
4301    {
4302      bAdded = xAddMVPCandUnscaled( *pInfo, eRefPicList, refIdx, partIdxRT, MD_ABOVE);
4303      if(!bAdded)
4304      {
4305        xAddMVPCandUnscaled( *pInfo, eRefPicList, refIdx, partIdxLT, MD_ABOVE_LEFT);
4306      }
4307    }
4308  }
4309
4310  if(!isScaledFlagLX)
4311  {
4312    Bool bAdded = xAddMVPCandWithScaling( *pInfo, eRefPicList, refIdx, partIdxRT, MD_ABOVE_RIGHT);
4313    if (!bAdded)
4314    {
4315      bAdded = xAddMVPCandWithScaling( *pInfo, eRefPicList, refIdx, partIdxRT, MD_ABOVE);
4316      if(!bAdded)
4317      {
4318        xAddMVPCandWithScaling( *pInfo, eRefPicList, refIdx, partIdxLT, MD_ABOVE_LEFT);
4319      }
4320    }
4321  }
4322
4323  if ( pInfo->iN == 2 )
4324  {
4325    if ( pInfo->m_acMvCand[ 0 ] == pInfo->m_acMvCand[ 1 ] )
4326    {
4327      pInfo->iN = 1;
4328    }
4329  }
4330
4331  if (pInfo->iN < AMVP_MAX_NUM_CANDS && getSlice()->getEnableTMVPFlag() )
4332  {
4333    // Get Temporal Motion Predictor
4334    const UInt numPartInCtuWidth  = m_pcPic->getNumPartInCtuWidth();
4335    const UInt numPartInCtuHeight = m_pcPic->getNumPartInCtuHeight();
4336#if NH_3D_TMVP
4337    Int refIdx_Col = refIdx;
4338#else
4339    const Int refIdx_Col = refIdx;
4340#endif
4341    TComMv cColMv;
4342    UInt partIdxRB;
4343    UInt absPartIdx;
4344
4345    deriveRightBottomIdx( partIdx, partIdxRB );
4346    UInt absPartAddr = m_absZIdxInCtu + partAddr;
4347
4348    //----  co-located RightBottom Temporal Predictor (H) ---//
4349    absPartIdx = g_auiZscanToRaster[partIdxRB];
4350    Int ctuRsAddr = -1;
4351    if (  ( ( m_pcPic->getCtu(m_ctuRsAddr)->getCUPelX() + g_auiRasterToPelX[absPartIdx] + m_pcPic->getMinCUWidth () ) < m_pcSlice->getSPS()->getPicWidthInLumaSamples () )  // image boundary check
4352      && ( ( m_pcPic->getCtu(m_ctuRsAddr)->getCUPelY() + g_auiRasterToPelY[absPartIdx] + m_pcPic->getMinCUHeight() ) < m_pcSlice->getSPS()->getPicHeightInLumaSamples() ) )
4353    {
4354      if ( ( absPartIdx % numPartInCtuWidth < numPartInCtuWidth - 1 ) &&  // is not at the last column of CTU
4355        ( absPartIdx / numPartInCtuWidth < numPartInCtuHeight - 1 ) )  // is not at the last row    of CTU
4356      {
4357        absPartAddr = g_auiRasterToZscan[ absPartIdx + numPartInCtuWidth + 1 ];
4358        ctuRsAddr = getCtuRsAddr();
4359      }
4360      else if ( absPartIdx % numPartInCtuWidth < numPartInCtuWidth - 1 )  // is not at the last column of CTU But is last row of CTU
4361      {
4362        absPartAddr = g_auiRasterToZscan[ (absPartIdx + numPartInCtuWidth + 1) % m_pcPic->getNumPartitionsInCtu() ];
4363      }
4364      else if ( absPartIdx / numPartInCtuWidth < numPartInCtuHeight - 1 ) // is not at the last row of CTU But is last column of CTU
4365      {
4366        absPartAddr = g_auiRasterToZscan[ absPartIdx + 1 ];
4367        ctuRsAddr = getCtuRsAddr() + 1;
4368      }
4369      else //is the right bottom corner of CTU
4370      {
4371        absPartAddr = 0;
4372      }
4373    }
4374#if NH_3D_TMVP
4375        if ( ctuRsAddr >= 0 && xGetColMVP( eRefPicList, ctuRsAddr, absPartAddr, cColMv, refIdx_Col  , 0 ) )
4376#else
4377    if ( ctuRsAddr >= 0 && xGetColMVP( eRefPicList, ctuRsAddr, absPartAddr, cColMv, refIdx_Col ) )
4378#endif
4379    {
4380      pInfo->m_acMvCand[pInfo->iN++] = cColMv;
4381    }
4382    else
4383    {
4384      UInt uiPartIdxCenter;
4385      xDeriveCenterIdx( partIdx, uiPartIdxCenter );
4386#if NH_3D_TMVP
4387      if (xGetColMVP( eRefPicList, getCtuRsAddr(), uiPartIdxCenter,  cColMv, refIdx_Col , 0 )) 
4388#else
4389      if (xGetColMVP( eRefPicList, getCtuRsAddr(), uiPartIdxCenter,  cColMv, refIdx_Col ))
4390#endif
4391      {
4392        pInfo->m_acMvCand[pInfo->iN++] = cColMv;
4393      }
4394    }
4395    //----  co-located RightBottom Temporal Predictor  ---//
4396  }
4397
4398  while (pInfo->iN < AMVP_MAX_NUM_CANDS)
4399  {
4400    pInfo->m_acMvCand[pInfo->iN].set(0,0);
4401    pInfo->iN++;
4402  }
4403  return ;
4404}
4405
4406
4407Bool TComDataCU::isBipredRestriction(UInt puIdx) const
4408{
4409  Int width = 0;
4410  Int height = 0;
4411  UInt partAddr;
4412
4413#if NH_3D_DBBP
4414  if( getDBBPFlag(0) )
4415  {
4416    return true;
4417  }
4418#endif
4419
4420  getPartIndexAndSize( puIdx, partAddr, width, height );
4421  if ( getWidth(0) == 8 && (width < 8 || height < 8) )
4422  {
4423    return true;
4424  }
4425  return false;
4426}
4427
4428
4429Void TComDataCU::clipMv    (TComMv&  rcMv) const
4430{
4431  const TComSPS &sps=*(m_pcSlice->getSPS());
4432  Int  iMvShift = 2;
4433#if NH_3D_INTEGER_MV_DEPTH
4434  if( getSlice()->getIsDepth() )
4435    iMvShift = 0;
4436#endif
4437
4438  Int iOffset = 8;
4439  Int iHorMax = ( sps.getPicWidthInLumaSamples() + iOffset - (Int)m_uiCUPelX - 1 ) << iMvShift;
4440  Int iHorMin = (      -(Int)sps.getMaxCUWidth() - iOffset - (Int)m_uiCUPelX + 1 ) << iMvShift;
4441
4442  Int iVerMax = ( sps.getPicHeightInLumaSamples() + iOffset - (Int)m_uiCUPelY - 1 ) << iMvShift;
4443  Int iVerMin = (      -(Int)sps.getMaxCUHeight() - iOffset - (Int)m_uiCUPelY + 1 ) << iMvShift;
4444
4445  rcMv.setHor( min (iHorMax, max (iHorMin, rcMv.getHor())) );
4446  rcMv.setVer( min (iVerMax, max (iVerMin, rcMv.getVer())) );
4447}
4448
4449#if NH_MV
4450Void TComDataCU::checkMvVertRest (TComMv&  rcMv,  RefPicList eRefPicList, int iRefIdx )
4451{
4452  if ( getSlice()->getSPS()->getInterViewMvVertConstraintFlag() )
4453  {
4454    if ( getSlice()->getRefPic( eRefPicList, iRefIdx )->getPOC() == getSlice()->getPOC() )
4455    {
4456        //When inter_view_mv_vert_constraint_flag is equal to 1,
4457        //the vertical component of the motion vectors used for inter-layer prediction
4458        //shall be equal to or less than 56 in units of luma samples
4459        assert ( rcMv.getVer() <= (56<<2) );
4460    }
4461  }
4462}
4463#endif
4464
4465UInt TComDataCU::getIntraSizeIdx(UInt uiAbsPartIdx) const
4466{
4467  UInt uiShift = ( m_pePartSize[uiAbsPartIdx]==SIZE_NxN ? 1 : 0 );
4468
4469  UChar uiWidth = m_puhWidth[uiAbsPartIdx]>>uiShift;
4470  UInt  uiCnt = 0;
4471  while( uiWidth )
4472  {
4473    uiCnt++;
4474    uiWidth>>=1;
4475  }
4476  uiCnt-=2;
4477  return uiCnt > 6 ? 6 : uiCnt;
4478}
4479
4480Void TComDataCU::clearCbf( UInt uiIdx, ComponentID compID, UInt uiNumParts )
4481{
4482  memset( &m_puhCbf[compID][uiIdx], 0, sizeof(UChar)*uiNumParts);
4483}
4484
4485/** Set a I_PCM flag for all sub-partitions of a partition.
4486 * \param bIpcmFlag I_PCM flag
4487 * \param uiAbsPartIdx patition index
4488 * \param uiDepth CU depth
4489 * \returns Void
4490 */
4491Void TComDataCU::setIPCMFlagSubParts  (Bool bIpcmFlag, UInt uiAbsPartIdx, UInt uiDepth)
4492{
4493  UInt uiCurrPartNumb = m_pcPic->getNumPartitionsInCtu() >> (uiDepth << 1);
4494
4495  memset(m_pbIPCMFlag + uiAbsPartIdx, bIpcmFlag, sizeof(Bool)*uiCurrPartNumb );
4496}
4497
4498/** Test whether the block at uiPartIdx is skipped.
4499 * \param uiPartIdx Partition index
4500 * \returns true if the current the block is skipped
4501 */
4502Bool TComDataCU::isSkipped( UInt uiPartIdx ) const
4503{
4504  return ( getSkipFlag( uiPartIdx ) );
4505}
4506
4507// ====================================================================================================================
4508// Protected member functions
4509// ====================================================================================================================
4510
4511Bool TComDataCU::xAddMVPCandUnscaled( AMVPInfo &info, const RefPicList eRefPicList, const Int iRefIdx, const UInt uiPartUnitIdx, const MVP_DIR eDir ) const
4512{
4513  const TComDataCU* neibCU = NULL;
4514  UInt neibPUPartIdx;
4515  switch( eDir )
4516  {
4517    case MD_LEFT:
4518    {
4519      neibCU = getPULeft(neibPUPartIdx, uiPartUnitIdx);
4520      break;
4521    }
4522    case MD_ABOVE:
4523    {
4524      neibCU = getPUAbove(neibPUPartIdx, uiPartUnitIdx);
4525      break;
4526    }
4527    case MD_ABOVE_RIGHT:
4528    {
4529      neibCU = getPUAboveRight(neibPUPartIdx, uiPartUnitIdx);
4530      break;
4531    }
4532    case MD_BELOW_LEFT:
4533    {
4534      neibCU = getPUBelowLeft(neibPUPartIdx, uiPartUnitIdx);
4535      break;
4536    }
4537    case MD_ABOVE_LEFT:
4538    {
4539      neibCU = getPUAboveLeft(neibPUPartIdx, uiPartUnitIdx);
4540      break;
4541    }
4542    default:
4543    {
4544      break;
4545    }
4546  }
4547
4548  if ( neibCU == NULL )
4549  {
4550    return false;
4551  }
4552
4553  const Int        currRefPOC     = m_pcSlice->getRefPic( eRefPicList, iRefIdx)->getPOC();
4554  const RefPicList eRefPicList2nd = (eRefPicList == REF_PIC_LIST_0) ? REF_PIC_LIST_1 : REF_PIC_LIST_0;
4555
4556  for(Int predictorSource=0; predictorSource<2; predictorSource++) // examine the indicated reference picture list, then if not available, examine the other list.
4557  {
4558    const RefPicList eRefPicListIndex = (predictorSource==0) ? eRefPicList : eRefPicList2nd;
4559    const Int        neibRefIdx       = neibCU->getCUMvField(eRefPicListIndex)->getRefIdx(neibPUPartIdx);
4560
4561    if ( neibRefIdx >= 0 && currRefPOC == neibCU->getSlice()->getRefPOC( eRefPicListIndex, neibRefIdx ))
4562    {
4563      info.m_acMvCand[info.iN++] = neibCU->getCUMvField(eRefPicListIndex)->getMv(neibPUPartIdx);
4564      return true;
4565    }
4566  }
4567  return false;
4568}
4569
4570/**
4571 * \param pInfo
4572 * \param eRefPicList
4573 * \param iRefIdx
4574 * \param uiPartUnitIdx
4575 * \param eDir
4576 * \returns Bool
4577 */
4578Bool TComDataCU::xAddMVPCandWithScaling( AMVPInfo &info, const RefPicList eRefPicList, const Int iRefIdx, const UInt uiPartUnitIdx, const MVP_DIR eDir ) const
4579{
4580  const TComDataCU* neibCU = NULL;
4581  UInt neibPUPartIdx;
4582  switch( eDir )
4583  {
4584  case MD_LEFT:
4585    {
4586      neibCU = getPULeft(neibPUPartIdx, uiPartUnitIdx);
4587      break;
4588    }
4589  case MD_ABOVE:
4590    {
4591      neibCU = getPUAbove(neibPUPartIdx, uiPartUnitIdx);
4592      break;
4593    }
4594  case MD_ABOVE_RIGHT:
4595    {
4596      neibCU = getPUAboveRight(neibPUPartIdx, uiPartUnitIdx);
4597      break;
4598    }
4599  case MD_BELOW_LEFT:
4600    {
4601      neibCU = getPUBelowLeft(neibPUPartIdx, uiPartUnitIdx);
4602      break;
4603    }
4604  case MD_ABOVE_LEFT:
4605    {
4606      neibCU = getPUAboveLeft(neibPUPartIdx, uiPartUnitIdx);
4607      break;
4608    }
4609  default:
4610    {
4611      break;
4612    }
4613  }
4614
4615  if ( neibCU == NULL )
4616  {
4617    return false;
4618  }
4619
4620  const RefPicList eRefPicList2nd = (eRefPicList == REF_PIC_LIST_0) ? REF_PIC_LIST_1 : REF_PIC_LIST_0;
4621
4622  const Int  currPOC            = m_pcSlice->getPOC();
4623  const Int  currRefPOC         = m_pcSlice->getRefPic( eRefPicList, iRefIdx)->getPOC();
4624  const Bool bIsCurrRefLongTerm = m_pcSlice->getRefPic( eRefPicList, iRefIdx)->getIsLongTerm();
4625  const Int  neibPOC            = currPOC;
4626
4627  for(Int predictorSource=0; predictorSource<2; predictorSource++) // examine the indicated reference picture list, then if not available, examine the other list.
4628  {
4629    const RefPicList eRefPicListIndex = (predictorSource==0) ? eRefPicList : eRefPicList2nd;
4630    const Int        neibRefIdx       = neibCU->getCUMvField(eRefPicListIndex)->getRefIdx(neibPUPartIdx);
4631    if( neibRefIdx >= 0)
4632    {
4633      const Bool bIsNeibRefLongTerm = neibCU->getSlice()->getRefPic( eRefPicListIndex, neibRefIdx )->getIsLongTerm();
4634
4635      if ( bIsCurrRefLongTerm == bIsNeibRefLongTerm )
4636      {
4637        const TComMv &cMvPred = neibCU->getCUMvField(eRefPicListIndex)->getMv(neibPUPartIdx);
4638        TComMv rcMv;
4639        if ( bIsCurrRefLongTerm /* || bIsNeibRefLongTerm*/ )
4640        {
4641          rcMv = cMvPred;
4642        }
4643        else
4644        {
4645          const Int neibRefPOC = neibCU->getSlice()->getRefPOC( eRefPicListIndex, neibRefIdx );
4646          const Int scale      = xGetDistScaleFactor( currPOC, currRefPOC, neibPOC, neibRefPOC );
4647          if ( scale == 4096 )
4648          {
4649            rcMv = cMvPred;
4650          }
4651          else
4652          {
4653            rcMv = cMvPred.scaleMv( scale );
4654          }
4655        }
4656
4657        info.m_acMvCand[info.iN++] = rcMv;
4658        return true;
4659      }
4660    }
4661  }
4662  return false;
4663}
4664
4665#if NH_3D_TMVP
4666Bool TComDataCU::xGetColMVP( const RefPicList eRefPicList, const Int ctuRsAddr, const Int partUnitIdx, TComMv& rcMv, Int& refIdx, Bool bMRG  ) const
4667#else
4668Bool TComDataCU::xGetColMVP( const RefPicList eRefPicList, const Int ctuRsAddr, const Int partUnitIdx, TComMv& rcMv, const Int refIdx ) const
4669#endif
4670{
4671  const UInt absPartAddr = partUnitIdx;
4672
4673  // use coldir.
4674  const TComPic    * const pColPic = getSlice()->getRefPic( RefPicList(getSlice()->isInterB() ? 1-getSlice()->getColFromL0Flag() : 0), getSlice()->getColRefIdx());
4675  const TComDataCU * const pColCtu = pColPic->getCtu( ctuRsAddr );
4676  if(pColCtu->getPic()==0 || pColCtu->getPartitionSize(partUnitIdx)==NUMBER_OF_PART_SIZES)
4677  {
4678    return false;
4679  }
4680
4681  if (!pColCtu->isInter(absPartAddr))
4682  {
4683    return false;
4684  }
4685
4686  RefPicList eColRefPicList = getSlice()->getCheckLDC() ? eRefPicList : RefPicList(getSlice()->getColFromL0Flag());
4687  Int iColRefIdx            = pColCtu->getCUMvField(RefPicList(eColRefPicList))->getRefIdx(absPartAddr);
4688
4689  if (iColRefIdx < 0 )
4690  {
4691    eColRefPicList = RefPicList(1 - eColRefPicList);
4692    iColRefIdx = pColCtu->getCUMvField(RefPicList(eColRefPicList))->getRefIdx(absPartAddr);
4693
4694    if (iColRefIdx < 0 )
4695    {
4696      return false;
4697    }
4698  }
4699
4700#if NH_3D_TMVP
4701  Bool bIsCurrRefLongTerm = m_pcSlice->getRefPic(eRefPicList, refIdx)->getIsLongTerm();
4702#else
4703  const Bool bIsCurrRefLongTerm = m_pcSlice->getRefPic(eRefPicList, refIdx)->getIsLongTerm();
4704#endif
4705  const Bool bIsColRefLongTerm  = pColCtu->getSlice()->getIsUsedAsLongTerm(eColRefPicList, iColRefIdx);
4706
4707  if ( bIsCurrRefLongTerm != bIsColRefLongTerm )
4708  {
4709#if NH_3D_TMVP
4710    Int iAlterRefIdx  = m_pcSlice->getAlterRefIdx(eRefPicList);
4711    if(bMRG && iAlterRefIdx > 0)
4712    {
4713      refIdx = iAlterRefIdx;
4714      bIsCurrRefLongTerm = m_pcSlice->getRefPic(eRefPicList, refIdx)->getIsLongTerm();
4715      assert(bIsCurrRefLongTerm == bIsColRefLongTerm);
4716    }
4717    else
4718    {
4719#endif
4720      return false;
4721#if NH_3D_TMVP
4722    }
4723#endif
4724  }
4725  // Scale the vector.
4726  const TComMv &cColMv = pColCtu->getCUMvField(eColRefPicList)->getMv(absPartAddr);
4727
4728#if NH_3D_TMVP
4729  if ( bIsCurrRefLongTerm || bIsColRefLongTerm )
4730#else
4731  if ( bIsCurrRefLongTerm /*|| bIsColRefLongTerm*/ )
4732#endif
4733  {
4734#if NH_3D_TMVP
4735    const Int iCurrViewId    = m_pcSlice->getViewId (); 
4736    const Int iCurrRefViewId = m_pcSlice->getRefPic(eRefPicList, refIdx)->getViewId (); 
4737    const Int iColViewId     = pColCtu->getSlice()->getViewId(); 
4738    const Int iColRefViewId  = pColCtu->getSlice()->getRefPic( eColRefPicList, pColCtu->getCUMvField(eColRefPicList)->getRefIdx(absPartAddr))->getViewId(); 
4739    Int scale = 4096;
4740    if ( iCurrRefViewId != iCurrViewId && iColViewId != iColRefViewId )
4741    {
4742      scale = xGetDistScaleFactor( iCurrViewId, iCurrRefViewId, iColViewId, iColRefViewId );
4743    }
4744    if ( bMRG && scale != 4096 && m_pcSlice->getIvMvScalingFlag( ) ) 
4745    {
4746      rcMv = cColMv.scaleMv( scale );
4747    }
4748    else
4749    {
4750#endif
4751      rcMv = cColMv;
4752#if NH_3D_TMVP
4753    }
4754#endif
4755  }
4756  else
4757  {
4758    const Int currPOC    = m_pcSlice->getPOC();
4759    const Int colPOC     = pColCtu->getSlice()->getPOC();
4760    const Int colRefPOC  = pColCtu->getSlice()->getRefPOC(eColRefPicList, iColRefIdx);
4761    const Int currRefPOC = m_pcSlice->getRefPic(eRefPicList, refIdx)->getPOC();
4762    const Int scale      = xGetDistScaleFactor(currPOC, currRefPOC, colPOC, colRefPOC);
4763    if ( scale == 4096 )
4764    {
4765      rcMv = cColMv;
4766    }
4767    else
4768    {
4769      rcMv = cColMv.scaleMv( scale );
4770    }
4771  }
4772
4773  return true;
4774}
4775
4776// Static member
4777Int TComDataCU::xGetDistScaleFactor(Int iCurrPOC, Int iCurrRefPOC, Int iColPOC, Int iColRefPOC)
4778{
4779  Int iDiffPocD = iColPOC - iColRefPOC;
4780  Int iDiffPocB = iCurrPOC - iCurrRefPOC;
4781
4782  if( iDiffPocD == iDiffPocB )
4783  {
4784    return 4096;
4785  }
4786  else
4787  {
4788    Int iTDB      = Clip3( -128, 127, iDiffPocB );
4789    Int iTDD      = Clip3( -128, 127, iDiffPocD );
4790    Int iX        = (0x4000 + abs(iTDD/2)) / iTDD;
4791    Int iScale    = Clip3( -4096, 4095, (iTDB * iX + 32) >> 6 );
4792    return iScale;
4793  }
4794}
4795
4796Void TComDataCU::xDeriveCenterIdx( UInt uiPartIdx, UInt& ruiPartIdxCenter ) const
4797{
4798  UInt uiPartAddr;
4799  Int  iPartWidth;
4800  Int  iPartHeight;
4801  getPartIndexAndSize( uiPartIdx, uiPartAddr, iPartWidth, iPartHeight);
4802
4803  ruiPartIdxCenter = m_absZIdxInCtu+uiPartAddr; // partition origin.
4804  ruiPartIdxCenter = g_auiRasterToZscan[ g_auiZscanToRaster[ ruiPartIdxCenter ]
4805                                        + ( iPartHeight/m_pcPic->getMinCUHeight()  )/2*m_pcPic->getNumPartInCtuWidth()
4806                                        + ( iPartWidth/m_pcPic->getMinCUWidth()  )/2];
4807}
4808
4809#if NH_3D
4810Void TComDataCU::compressMV(Int scale)
4811{
4812   Int scaleFactor = (4 / scale ) * AMVP_DECIMATION_FACTOR / m_unitSize;
4813#else
4814Void TComDataCU::compressMV()
4815{
4816  Int scaleFactor = 4 * AMVP_DECIMATION_FACTOR / m_unitSize;
4817#endif
4818  if (scaleFactor > 0)
4819  {
4820    for(UInt i=0; i<NUM_REF_PIC_LIST_01; i++)
4821    {
4822      m_acCUMvField[i].compress(m_pePredMode, scaleFactor);
4823    }
4824  }
4825}
4826#if NH_3D
4827Void TComDataCU::printMV( )
4828{ 
4829
4830  for(UInt i=0; i<NUM_REF_PIC_LIST_01; i++)
4831  {
4832    std::cout << "L" << i; 
4833    m_acCUMvField[i].print(m_pePredMode);
4834  }
4835
4836}
4837#endif
4838
4839UInt TComDataCU::getCoefScanIdx(const UInt uiAbsPartIdx, const UInt uiWidth, const UInt uiHeight, const ComponentID compID) const
4840{
4841  //------------------------------------------------
4842
4843  //this mechanism is available for intra only
4844
4845  if (!isIntra(uiAbsPartIdx))
4846  {
4847    return SCAN_DIAG;
4848  }
4849
4850  //------------------------------------------------
4851
4852  //check that MDCS can be used for this TU
4853
4854  const ChromaFormat format = getPic()->getChromaFormat();
4855
4856  const UInt maximumWidth  = MDCS_MAXIMUM_WIDTH  >> getComponentScaleX(compID, format);
4857  const UInt maximumHeight = MDCS_MAXIMUM_HEIGHT >> getComponentScaleY(compID, format);
4858
4859  if ((uiWidth > maximumWidth) || (uiHeight > maximumHeight))
4860  {
4861    return SCAN_DIAG;
4862  }
4863
4864  //------------------------------------------------
4865
4866  //otherwise, select the appropriate mode
4867
4868  UInt uiDirMode  = getIntraDir(toChannelType(compID), uiAbsPartIdx);
4869#if NH_3D_DMM
4870  mapDmmToIntraDir( uiDirMode );
4871#endif
4872
4873  if (uiDirMode==DM_CHROMA_IDX)
4874  {
4875    const TComSPS *sps=getSlice()->getSPS();
4876    const UInt partsPerMinCU = 1<<(2*(sps->getMaxTotalCUDepth() - sps->getLog2DiffMaxMinCodingBlockSize()));
4877    uiDirMode = getIntraDir(CHANNEL_TYPE_LUMA, getChromasCorrespondingPULumaIdx(uiAbsPartIdx, getPic()->getChromaFormat(), partsPerMinCU));
4878#if NH_3D_DMM
4879    mapDmmToIntraDir( uiDirMode );
4880#endif
4881  }
4882
4883  if (isChroma(compID) && (format == CHROMA_422))
4884  {
4885    uiDirMode = g_chroma422IntraAngleMappingTable[uiDirMode];
4886  }
4887
4888  //------------------
4889
4890  if      (abs((Int)uiDirMode - VER_IDX) <= MDCS_ANGLE_LIMIT)
4891  {
4892    return SCAN_HOR;
4893  }
4894  else if (abs((Int)uiDirMode - HOR_IDX) <= MDCS_ANGLE_LIMIT)
4895  {
4896    return SCAN_VER;
4897  }
4898  else
4899  {
4900    return SCAN_DIAG;
4901  }
4902}
4903
4904#if NH_3D_VSO
4905Void TComDataCU::getPosInPic( UInt uiAbsPartIndex, Int& riPosX, Int& riPosY ) const
4906{
4907  riPosX = g_auiRasterToPelX[g_auiZscanToRaster[uiAbsPartIndex]] + getCUPelX();
4908  riPosY = g_auiRasterToPelY[g_auiZscanToRaster[uiAbsPartIndex]] + getCUPelY(); 
4909}
4910#endif
4911
4912#if NH_3D_IV_MERGE
4913Void TComDataCU::getDispforDepth (UInt uiPartIdx, UInt uiPartAddr, DisInfo* pDisp)
4914{
4915  assert(getPartitionSize( uiPartAddr ) == SIZE_2Nx2N);
4916
4917  TComMv cMv; 
4918  if ( getSlice()->getDefaultRefViewIdxAvailableFlag() )
4919  {
4920    Int iViewIdx = getSlice()->getDefaultRefViewIdx();
4921    pDisp->m_aVIdxCan = iViewIdx;
4922    Int iDisp     = getSlice()->getDepthToDisparityB( iViewIdx )[ (Int64) (1 << ( getSlice()->getSPS()->getBitDepth(CHANNEL_TYPE_LUMA) - 1 )) ];
4923
4924    cMv.setHor(iDisp);
4925    cMv.setVer(0);
4926    pDisp->m_acNBDV = cMv;
4927    pDisp->m_aVIdxCan = iViewIdx;
4928  }
4929}
4930#endif
4931
4932#if NH_3D_DIS
4933Bool TComDataCU::getNeighDepth ( UInt uiPartIdx, UInt uiPartAddr, Pel* pNeighDepth, Int index )
4934{
4935  assert(uiPartIdx==0);
4936  const UInt uiPartIdxLT      = getZorderIdxInCtu() + uiPartAddr;
4937  const Int  iPartIdxStride   = getPic()->getNumPartInCtuWidth();
4938 
4939  UInt uiMidPart, uiPartNeighbor; 
4940  const TComDataCU* pcCUNeighbor;
4941  Bool bDepAvail = false;
4942  Pel *pDepth  = this->getPic()->getPicYuvRec()->getAddr(COMPONENT_Y);
4943  Int iDepStride =  this->getPic()->getPicYuvRec()->getStride(COMPONENT_Y);
4944
4945  Int xP, yP, nPSW, nPSH;
4946  this->getPartPosition( uiPartIdx, xP, yP, nPSW, nPSH );
4947
4948  switch( index )
4949  {
4950  case 0: // Mid Left
4951    uiMidPart = g_auiZscanToRaster[uiPartIdxLT] + (nPSH>>1) / this->getPic()->getMinCUHeight() * iPartIdxStride;
4952    pcCUNeighbor = this->getPULeft( uiPartNeighbor, g_auiRasterToZscan[uiMidPart] );
4953    if ( pcCUNeighbor )
4954    {
4955      if( !this->getSlice()->getPPS()->getConstrainedIntraPred() )
4956      {
4957        *pNeighDepth = pDepth[ (yP+(nPSH>>1)) * iDepStride + (xP-1) ];
4958        bDepAvail = true;
4959      }
4960      else if ( pcCUNeighbor->getPredictionMode( uiPartNeighbor ) == MODE_INTRA )
4961      {
4962        *pNeighDepth = pDepth[ (yP+(nPSH>>1)) * iDepStride + (xP-1) ];
4963        bDepAvail = true;
4964      }
4965    }
4966    break;
4967  case 1: // Mid Above
4968    uiMidPart = g_auiZscanToRaster[uiPartIdxLT] + (nPSW>>1) / this->getPic()->getMinCUWidth();
4969    pcCUNeighbor = this->getPUAbove( uiPartNeighbor, g_auiRasterToZscan[uiMidPart] );
4970    if( pcCUNeighbor )
4971    {
4972      if( !this->getSlice()->getPPS()->getConstrainedIntraPred() )
4973      {
4974        *pNeighDepth = pDepth[ (yP-1) * iDepStride + (xP + (nPSW>>1)) ];
4975        bDepAvail = true;
4976      }
4977      else if ( pcCUNeighbor->getPredictionMode( uiPartNeighbor ) == MODE_INTRA )
4978      {
4979        *pNeighDepth = pDepth[ (yP-1) * iDepStride + (xP + (nPSW>>1)) ];
4980        bDepAvail = true;
4981      }
4982    }
4983    break;
4984  default:
4985    break;
4986  }
4987
4988  return bDepAvail;
4989}
4990#endif
4991#if NH_3D_NBDV
4992//Notes from QC:
4993//TBD#1: DoNBDV related contributions are just partially integrated under the marco of NH_3D_NBDV_REF, remove this comment once DoNBDV and BVSP are done
4994//TBD#2: set of DvMCP values need to be done as part of inter-view motion prediction process. Remove this comment once merge related integration is done
4995//To be checked: Parallel Merge features for NBDV, related to DV_DERIVATION_PARALLEL_B0096 and LGE_IVMP_PARALLEL_MERGE_B0136 are not integrated. The need of these features due to the adoption of CU-based NBDV is not clear. We need confirmation on this, especially by proponents
4996Void TComDataCU::getDisMvpCandNBDV( DisInfo* pDInfo
4997#if NH_3D_NBDV_REF
4998, Bool bDepthRefine
4999#endif
5000)
5001{
5002  //// ******* Init variables ******* /////
5003  // Init disparity struct for results
5004  pDInfo->m_aVIdxCan = -1;
5005
5006  // Init struct for disparities from MCP neighboring blocks
5007  IDVInfo cIDVInfo;
5008  cIDVInfo.m_bFound = false; 
5009  UInt uiPartIdx = 0;
5010  UInt uiPartAddr = 0;
5011  for (UInt iCurDvMcpCand = 0; iCurDvMcpCand < IDV_CANDS; iCurDvMcpCand++)
5012  {
5013    for (UInt iList = 0; iList < 2; iList++)
5014    {
5015      cIDVInfo.m_acMvCand[iList][iCurDvMcpCand].setZero();
5016      cIDVInfo.m_aVIdxCan[iList][iCurDvMcpCand] = 0; 
5017      cIDVInfo.m_bAvailab[iList][iCurDvMcpCand] = false; 
5018    }
5019  }
5020#if NH_3D_NBDV_REF
5021  if( !m_pcSlice->getDepthRefinementFlag( ) )
5022  {
5023    bDepthRefine = false;
5024  }
5025#endif
5026  // Get Positions 
5027  PartSize eCUMode    = getPartitionSize( uiPartAddr );   
5028  assert(eCUMode == SIZE_2Nx2N);
5029  UInt uiPartIdxLT, uiPartIdxRT, uiPartIdxLB; 
5030
5031  deriveLeftRightTopIdxGeneral(uiPartAddr, uiPartIdx, uiPartIdxLT, uiPartIdxRT );
5032  deriveLeftBottomIdxGeneral  (uiPartAddr, uiPartIdx, uiPartIdxLB );
5033
5034  //// ******* Get disparity from temporal neighboring blocks ******* /////
5035  if ( getSlice()->getEnableTMVPFlag() )
5036  {
5037    TComMv cColMv;
5038    Int iTargetViewIdx = 0;
5039    Int iTStartViewIdx = 0;   
5040
5041    ///*** Derive center position ***
5042    UInt uiPartIdxCenter;
5043    Int  uiLCUIdx = getCtuRsAddr();
5044    xDeriveCenterIdx(uiPartIdx, uiPartIdxCenter );
5045
5046    ///*** Search temporal candidate pictures for disparity vector ***
5047    const Int iNumCandPics = getPic()->getNumDdvCandPics();
5048    for(Int curCandPic = 0; curCandPic < iNumCandPics; curCandPic++)
5049    {
5050      RefPicList eCurRefPicList   = REF_PIC_LIST_0 ;
5051      Int        curCandPicRefIdx = 0;
5052      if( curCandPic == 0 ) 
5053      { 
5054        eCurRefPicList   = RefPicList(getSlice()->isInterB() ? 1-getSlice()->getColFromL0Flag() : 0);
5055        curCandPicRefIdx = getSlice()->getColRefIdx();
5056      }
5057      else                 
5058      {
5059        eCurRefPicList   = getPic()->getRapRefList();
5060        curCandPicRefIdx = getPic()->getRapRefIdx();
5061      }
5062
5063      Bool bCheck = xGetColDisMV( curCandPic, eCurRefPicList, curCandPicRefIdx, uiLCUIdx,   uiPartIdxCenter,  cColMv, iTargetViewIdx, iTStartViewIdx );
5064
5065      if( bCheck )
5066      {
5067        pDInfo->m_acNBDV = cColMv;
5068        pDInfo->m_aVIdxCan  = iTargetViewIdx;
5069
5070#if NH_3D_NBDV_REF
5071        TComPic* picDepth = NULL;   
5072#if H_3D_FCO_VSP_DONBDV_E0163
5073        picDepth  = getSlice()->getIvPic(true, getSlice()->getViewIndex() );
5074        if ( picDepth->getPicYuvRec() != NULL  ) 
5075        {
5076          cColMv.setZero();
5077        }
5078        else // Go back with virtual depth
5079        {
5080          picDepth = getSlice()->getIvPic( true, iTargetViewIdx );
5081        }
5082
5083        assert(picDepth != NULL);
5084#else
5085        picDepth = getSlice()->getIvPic( true, iTargetViewIdx );
5086#endif
5087        if (picDepth && bDepthRefine)
5088        {
5089          estimateDVFromDM(iTargetViewIdx, uiPartIdx, picDepth, uiPartAddr, &cColMv );
5090        }
5091        pDInfo->m_acDoNBDV  = cColMv;
5092#endif //NH_3D_NBDV_REF
5093        return;
5094      }
5095    }
5096  } 
5097
5098  UInt uiIdx = 0;
5099  Bool        bCheckMcpDv = false;   
5100  const TComDataCU* pcTmpCU     = NULL;
5101
5102  //// ******* Get disparity from left block ******* /////
5103  pcTmpCU = getPULeft(uiIdx, uiPartIdxLB, true, false);
5104  bCheckMcpDv = true; 
5105  if ( xCheckSpatialNBDV( pcTmpCU, uiIdx, pDInfo, bCheckMcpDv, &cIDVInfo, DVFROM_LEFT
5106#if NH_3D_NBDV_REF
5107    , bDepthRefine
5108#endif
5109    ) )
5110    return;
5111
5112  //// ******* Get disparity from above block ******* /////
5113  pcTmpCU = getPUAbove(uiIdx, uiPartIdxRT, true, false, true);
5114  if(pcTmpCU != NULL )
5115  {
5116    bCheckMcpDv = ( ( getCtuRsAddr() - pcTmpCU->getCtuRsAddr() ) == 0);
5117    if ( xCheckSpatialNBDV( pcTmpCU, uiIdx, pDInfo, bCheckMcpDv, &cIDVInfo, DVFROM_ABOVE
5118#if NH_3D_NBDV_REF
5119      , bDepthRefine
5120#endif
5121      ) )
5122      return;
5123  }
5124
5125  //// ******* Search MCP blocks ******* /////
5126  if( cIDVInfo.m_bFound ) 
5127  {
5128    for( Int curPos = 0 ; curPos < IDV_CANDS ; curPos++ ) 
5129    {
5130      for(Int iList = 0; iList < (getSlice()->isInterB() ? 2: 1); iList ++)
5131      {
5132        if( cIDVInfo.m_bAvailab[iList][curPos] )
5133        {
5134          TComMv cDispVec = cIDVInfo.m_acMvCand[iList][ curPos ];
5135          pDInfo->m_acNBDV = cDispVec;
5136          pDInfo->m_aVIdxCan = cIDVInfo.m_aVIdxCan[iList][ curPos ];
5137#if NH_3D_NBDV_REF
5138#if H_3D_FCO_VSP_DONBDV_E0163
5139          TComPic* picDepth  = NULL;
5140
5141          picDepth  = getSlice()->getIvPic(true, getSlice()->getViewIndex() );
5142          if ( picDepth->getPicYuvRec() != NULL ) 
5143          {
5144            cDispVec.setZero();
5145          }
5146          else // Go back with virtual depth
5147          {
5148            picDepth = getSlice()->getIvPic( true, pDInfo->m_aVIdxCan );
5149          }
5150
5151          assert(picDepth != NULL);
5152#else
5153          TComPic* picDepth = getSlice()->getIvPic( true, pDInfo->m_aVIdxCan );
5154#endif
5155
5156          if (picDepth && bDepthRefine)
5157          {
5158            estimateDVFromDM (pDInfo->m_aVIdxCan, uiPartIdx, picDepth, uiPartAddr, &cDispVec);
5159          }
5160          pDInfo->m_acDoNBDV = cDispVec;
5161#endif
5162          return;
5163        }
5164      }
5165    }
5166  }
5167
5168  TComMv defaultDV(0, 0);
5169  pDInfo->m_acNBDV = defaultDV;
5170
5171  if (getSlice()->getDefaultRefViewIdxAvailableFlag())
5172  {
5173    pDInfo->m_aVIdxCan = getSlice()->getDefaultRefViewIdx();
5174
5175#if NH_3D_NBDV_REF
5176    TComPic* picDepth = NULL;
5177#if H_3D_FCO_VSP_DONBDV_E0163
5178    picDepth  = getSlice()->getIvPic(true, getSlice()->getViewIndex() );
5179    if ( picDepth->getPicYuvRec() != NULL ) 
5180    {
5181      defaultDV.setZero();
5182    }
5183    else // Go back with virtual depth
5184    {
5185      picDepth = getSlice()->getIvPic( true, getSlice()->getDefaultRefViewIdx());
5186    }
5187
5188    assert(picDepth != NULL);
5189#else
5190    picDepth = getSlice()->getIvPic( true, getSlice()->getDefaultRefViewIdx());
5191#endif
5192    if (picDepth && bDepthRefine)
5193    {
5194      estimateDVFromDM(getSlice()->getDefaultRefViewIdx(), uiPartIdx, picDepth, uiPartAddr, &defaultDV ); // from base view
5195    }
5196    pDInfo->m_acDoNBDV = defaultDV;
5197#endif
5198  }
5199}
5200
5201#if NH_3D_NBDV_REF
5202Pel TComDataCU::getMcpFromDM(TComPicYuv* pcBaseViewDepthPicYuv, TComMv* mv, Int iBlkX, Int iBlkY, Int iBlkWidth, Int iBlkHeight, Int* aiShiftLUT )
5203{
5204  Int iPictureWidth  = pcBaseViewDepthPicYuv->getWidth(COMPONENT_Y);
5205  Int iPictureHeight = pcBaseViewDepthPicYuv->getHeight(COMPONENT_Y);
5206
5207  Int depthStartPosX = Clip3(0,   iPictureWidth - 1,  iBlkX + ((mv->getHor()+2)>>2));
5208  Int depthStartPosY = Clip3(0,   iPictureHeight - 1, iBlkY + ((mv->getVer()+2)>>2));
5209  Int depthEndPosX   = Clip3(0,   iPictureWidth - 1,  iBlkX + iBlkWidth - 1 + ((mv->getHor()+2)>>2));
5210  Int depthEndPosY   = Clip3(0,   iPictureHeight - 1, iBlkY + iBlkHeight - 1 + ((mv->getVer()+2)>>2));
5211
5212  Pel* depthTL  = pcBaseViewDepthPicYuv->getAddr(COMPONENT_Y);
5213  Int depStride =  pcBaseViewDepthPicYuv->getStride(COMPONENT_Y);
5214
5215  Pel  maxDepthVal = 0;
5216  maxDepthVal = std::max( maxDepthVal, depthTL[ (depthStartPosY) * depStride + depthStartPosX ]);      // Left Top
5217  maxDepthVal = std::max( maxDepthVal, depthTL[ (depthEndPosY)   * depStride + depthStartPosX ]);      // Left Bottom
5218  maxDepthVal = std::max( maxDepthVal, depthTL[ (depthStartPosY) * depStride + depthEndPosX   ]);      // Right Top
5219  maxDepthVal = std::max( maxDepthVal, depthTL[ (depthEndPosY)   * depStride + depthEndPosX   ]);      // Right Bottom
5220
5221  return aiShiftLUT[ maxDepthVal ];
5222}
5223
5224Void TComDataCU::estimateDVFromDM(Int refViewIdx, UInt uiPartIdx, TComPic* picDepth, UInt uiPartAddr, TComMv* cMvPred )
5225{
5226  if (picDepth)
5227  {
5228    UInt uiAbsPartAddrCurrCU = m_absZIdxInCtu + uiPartAddr;
5229    Int iWidth, iHeight;
5230    getPartIndexAndSize( uiPartIdx, uiPartAddr, iWidth, iHeight ); // The modified value of uiPartAddr won't be used any more
5231
5232    TComPicYuv* pcBaseViewDepthPicYuv = picDepth->getPicYuvRec();
5233    const TComSPS   &sps =*(getSlice()->getSPS());
5234    Int iBlkX = ( getCtuRsAddr() % picDepth->getFrameWidthInCtus() ) * sps.getMaxCUWidth()  + g_auiRasterToPelX[ g_auiZscanToRaster[ uiAbsPartAddrCurrCU ] ];
5235    Int iBlkY = ( getCtuRsAddr() / picDepth->getFrameWidthInCtus() ) * sps.getMaxCUHeight() + g_auiRasterToPelY[ g_auiZscanToRaster[ uiAbsPartAddrCurrCU ] ];
5236
5237    Int* aiShiftLUT = getSlice()->getDepthToDisparityB(refViewIdx );
5238
5239    Pel iDisp = getMcpFromDM( pcBaseViewDepthPicYuv, cMvPred, iBlkX, iBlkY, iWidth, iHeight, aiShiftLUT );
5240    cMvPred->setHor( iDisp );
5241  }
5242}
5243#endif //NH_3D_NBDV_REF
5244
5245
5246Bool TComDataCU::xCheckSpatialNBDV( const TComDataCU* pcTmpCU, UInt uiIdx, DisInfo* pNbDvInfo, Bool bSearchForMvpDv, IDVInfo* paIDVInfo, UInt uiMvpDvPos
5247#if NH_3D_NBDV_REF
5248, Bool bDepthRefine
5249#endif
5250)
5251{
5252  if( pcTmpCU != NULL && !pcTmpCU->isIntra( uiIdx ) )
5253  {
5254    Bool bTmpIsSkipped = pcTmpCU->isSkipped( uiIdx );
5255    for(Int iList = 0; iList < (getSlice()->isInterB() ? 2: 1); iList ++)
5256    {
5257      RefPicList eRefPicList = RefPicList(iList);
5258      Int      refId = pcTmpCU->getCUMvField(eRefPicList)->getRefIdx(uiIdx) ;
5259      TComMv cMvPred = pcTmpCU->getCUMvField(eRefPicList)->getMv(uiIdx);
5260
5261      if( refId >= 0)
5262      {
5263        Int refViewIdx  = pcTmpCU->getSlice()->getRefPic(eRefPicList, refId)->getViewIndex();
5264        if (refViewIdx != m_pcSlice->getViewIndex()) 
5265        {
5266          pNbDvInfo->m_acNBDV = cMvPred;
5267          pNbDvInfo->m_aVIdxCan = refViewIdx;
5268#if NH_3D_NBDV_REF
5269          TComPic* picDepth = NULL;
5270          assert(getSlice()->getRefPic(eRefPicList, refId)->getPOC() == getSlice()->getPOC());           
5271#if H_3D_FCO_VSP_DONBDV_E0163
5272          picDepth  = getSlice()->getIvPic(true, getSlice()->getViewIndex() );
5273          if ( picDepth->getPicYuvRec() != NULL ) 
5274          {
5275            cMvPred.setZero();
5276          }
5277          else// Go back with virtual depth
5278          {
5279            picDepth = getSlice()->getIvPic (true, refViewIdx );
5280          }
5281          assert(picDepth != NULL);
5282#else
5283          picDepth   = getSlice()->getIvPic (true, refViewIdx );
5284#endif
5285          UInt uiPartIdx = 0;   //Notes from MTK: Please confirm that using 0 as partition index and partition address is correct for CU-level DoNBDV
5286          UInt uiPartAddr = 0;  //QC: confirmed
5287
5288          if (picDepth && bDepthRefine)
5289          {
5290            estimateDVFromDM(refViewIdx, uiPartIdx, picDepth, uiPartAddr, &cMvPred );
5291          }
5292          pNbDvInfo->m_acDoNBDV = cMvPred;
5293#endif
5294          return true;
5295        }
5296        else if ( bSearchForMvpDv && cMvPred.getIDVFlag() && bTmpIsSkipped )
5297        {
5298          assert( uiMvpDvPos < IDV_CANDS );
5299          paIDVInfo->m_acMvCand[iList][ uiMvpDvPos ] = TComMv( cMvPred.getIDVHor(), cMvPred.getIDVVer() );
5300          //Notes from QC: DvMCP is implemented in a way that doesnot carry the reference view identifier as NBDV. It only works for CTC and needs to be fixed to be aligned with other part of the NBDV design.
5301          paIDVInfo->m_aVIdxCan[iList][ uiMvpDvPos ] = cMvPred.getIDVVId();
5302          paIDVInfo->m_bAvailab[iList][ uiMvpDvPos ] = true;
5303          paIDVInfo->m_bFound                        = true; 
5304        }
5305      }
5306    }
5307  }
5308  return false; 
5309}
5310 
5311Void TComDataCU::xDeriveRightBottomNbIdx(Int &riLCUIdxRBNb, Int &riPartIdxRBNb )
5312{
5313  UInt uiPartIdx = 0;
5314  UInt uiNumPartInCUWidth = m_pcPic->getNumPartInCtuWidth(); 
5315  Int uiLCUIdx = getCtuRsAddr();
5316
5317  UInt uiPartIdxRB;
5318  deriveRightBottomIdx(uiPartIdx, uiPartIdxRB ); 
5319  UInt uiAbsPartIdxTmp = g_auiZscanToRaster[uiPartIdxRB];
5320
5321  if (( m_pcPic->getCtu(m_ctuRsAddr)->getCUPelX() + g_auiRasterToPelX[uiAbsPartIdxTmp] + m_pcPic->getMinCUWidth() )>= m_pcSlice->getSPS()->getPicWidthInLumaSamples() )
5322  {
5323    riLCUIdxRBNb  = -1;
5324    riPartIdxRBNb = -1;
5325  }
5326  else if(( m_pcPic->getCtu(m_ctuRsAddr)->getCUPelY() + g_auiRasterToPelY[uiAbsPartIdxTmp] + m_pcPic->getMinCUHeight() )>= m_pcSlice->getSPS()->getPicHeightInLumaSamples() )
5327  {
5328    riLCUIdxRBNb  = -1;
5329    riPartIdxRBNb = -1;
5330  }
5331  else
5332  {
5333    if ( ( uiAbsPartIdxTmp % uiNumPartInCUWidth < uiNumPartInCUWidth - 1 ) &&           // is not at the last column of LCU
5334      ( uiAbsPartIdxTmp / uiNumPartInCUWidth < m_pcPic->getNumPartInCtuHeight() - 1 ) ) // is not at the last row    of LCU
5335    {
5336      riPartIdxRBNb = g_auiRasterToZscan[ uiAbsPartIdxTmp + uiNumPartInCUWidth + 1 ];
5337      riLCUIdxRBNb  = uiLCUIdx; 
5338    }
5339    else if ( uiAbsPartIdxTmp % uiNumPartInCUWidth < uiNumPartInCUWidth - 1 )           // is not at the last column of LCU But is last row of LCU
5340    {
5341      riPartIdxRBNb = -1;
5342      riLCUIdxRBNb  = -1;
5343    }
5344    else if ( uiAbsPartIdxTmp / uiNumPartInCUWidth < m_pcPic->getNumPartInCtuHeight() - 1 ) // is not at the last row of LCU But is last column of LCU
5345    {
5346      riPartIdxRBNb = g_auiRasterToZscan[ uiAbsPartIdxTmp + 1 ];
5347      riLCUIdxRBNb = uiLCUIdx + 1;
5348    }
5349    else //is the right bottom corner of LCU                       
5350    {
5351      riPartIdxRBNb = -1;
5352      riLCUIdxRBNb  = -1;
5353    }
5354  }
5355}
5356
5357
5358Void TComDataCU::setDvInfoSubParts( DisInfo cDvInfo, UInt uiAbsPartIdx, UInt uiDepth )
5359{
5360#if NH_3D_VSP // bug fix
5361  UInt uiCurrPartNumb = m_pcPic->getNumPartitionsInCtu() >> (uiDepth << 1);
5362  assert(m_pcPic->getNumPartitionsInCtu() ==m_pcPic->getNumPartInCtuWidth()*m_pcPic->getNumPartInCtuHeight());
5363
5364#else
5365  UInt uiCurrPartNumb = m_pcPic->getNumPartInCtuWidth() >> (uiDepth << 1);
5366#endif
5367  for (UInt ui = 0; ui < uiCurrPartNumb; ui++ )
5368  {
5369    m_pDvInfo[uiAbsPartIdx + ui] = cDvInfo;
5370  }
5371}
5372#if NH_3D_VSP  || NH_3D_DBBP
5373Void TComDataCU::setDvInfoSubParts( DisInfo cDvInfo, UInt uiAbsPartIdx, UInt uiPUIdx, UInt uiDepth )
5374{
5375  setSubPartT<DisInfo>( cDvInfo, m_pDvInfo, uiAbsPartIdx, uiDepth, uiPUIdx );
5376}
5377#endif
5378
5379Bool TComDataCU::xGetColDisMV( Int currCandPic, RefPicList eRefPicList, Int refidx, Int uiCUAddr, Int uiPartUnitIdx, TComMv& rcMv , Int & iTargetViewIdx, Int & iStartViewIdx )
5380{
5381
5382  RefPicList  eColRefPicList = REF_PIC_LIST_0;
5383  Int iColViewIdx, iColRefViewIdx;
5384  TComPic *pColPic = getSlice()->getRefPic( eRefPicList, refidx);
5385  TComDataCU *pColCU = pColPic->getCtu( uiCUAddr );
5386  iColViewIdx = pColCU->getSlice()->getViewIndex();
5387  if (pColCU->getPic()==0||pColCU->getPartitionSize(uiPartUnitIdx)==NUMBER_OF_PART_SIZES||pColCU->isIntra(uiPartUnitIdx))
5388  {
5389    return false;
5390  }
5391  for (Int ilist = 0; ilist < (pColCU->getSlice()->isInterB()? 2:1); ilist++) 
5392  {
5393    if(pColCU->getSlice()->isInterB())
5394    {
5395      eColRefPicList = RefPicList(ilist);
5396    }
5397
5398    Int iColRefIdx = pColCU->getCUMvField(eColRefPicList)->getRefIdx(uiPartUnitIdx);
5399
5400    if (iColRefIdx < 0)
5401    {
5402      continue;
5403    }
5404
5405#if NH_3D_FIX_NBDV_COL
5406    // The picture pColCU->getSlice()->getRefPic(eColRefPicList, iColRefIdx) might not be in DPB anymore
5407    // So don't access it directly.
5408    iColRefViewIdx = pColCU->getSlice()->getVPS()->getViewOrderIdx( pColCU->getSlice()->getRefLayerId( eColRefPicList, iColRefIdx ) );       
5409#else
5410    iColRefViewIdx = pColCU->getSlice()->getRefPic(eColRefPicList, iColRefIdx)->getViewIndex();
5411#endif
5412
5413
5414    if ( iColViewIdx    == iColRefViewIdx ) // temporal vector
5415    {
5416      continue;
5417    }
5418    else 
5419    {
5420      if(getPic()->isTempIVRefValid(currCandPic, ilist,  iColRefIdx))
5421      {
5422        rcMv = pColCU->getCUMvField(eColRefPicList)->getMv(uiPartUnitIdx);
5423        rcMv.setIDVFlag(0);
5424        iTargetViewIdx  = iColRefViewIdx ;
5425        iStartViewIdx   = iColViewIdx   ;
5426        return true;   
5427      }
5428    }
5429  }
5430
5431  return false;
5432}
5433#endif
5434#if  NH_3D_FAST_TEXTURE_ENCODING
5435Void
5436TComDataCU::getIVNStatus       ( UInt uiPartIdx,  DisInfo* pDInfo, Bool& bIVFMerge, Int& iIVFMaxD)
5437{
5438  TComSlice*    pcSlice         = getSlice (); 
5439  Int iViewIndex = pDInfo->m_aVIdxCan;
5440  //--- get base CU/PU and check prediction mode ---
5441  TComPic*    pcBasePic   = pcSlice->getIvPic( false, iViewIndex );
5442  TComPicYuv* pcBaseRec   = pcBasePic->getPicYuvRec   ();
5443
5444  UInt          uiPartAddr;
5445  Int           iWidth;
5446  Int           iHeight;
5447  getPartIndexAndSize( uiPartIdx, uiPartAddr, iWidth, iHeight );
5448
5449  Int  iCurrPosX, iCurrPosY;
5450  pcBaseRec->getTopLeftSamplePos( this->getCtuRsAddr(), this->getZorderIdxInCtu() + uiPartAddr, iCurrPosX, iCurrPosY );
5451
5452  iCurrPosX  += ( ( iWidth  - 1 ) >> 1 );
5453  iCurrPosY  += ( ( iHeight - 1 ) >> 1 );
5454
5455  Bool depthRefineFlag = false; 
5456#if NH_3D_NBDV_REF
5457  depthRefineFlag = m_pcSlice->getDepthRefinementFlag( ); 
5458#endif // NH_3D_NBDV_REF
5459
5460  TComMv      cDv = depthRefineFlag ? pDInfo->m_acDoNBDV : pDInfo->m_acNBDV; 
5461  if( depthRefineFlag )
5462  {
5463    cDv.setVer(0);
5464  }
5465
5466  Int         iBasePosX   = Clip3( 0, pcBaseRec->getWidth (COMPONENT_Y) - 1, iCurrPosX + ( (cDv.getHor() + 2 ) >> 2 ) );
5467  Int         iBasePosY   = Clip3( 0, pcBaseRec->getHeight(COMPONENT_Y) - 1, iCurrPosY + ( (cDv.getVer() + 2 ) >> 2 )); 
5468  Int         iBaseLPosX   = Clip3( 0, pcBaseRec->getWidth (COMPONENT_Y) - 1, iCurrPosX - (iWidth >> 1) + ( (cDv.getHor() + 2 ) >> 2 ) );
5469  Int         iBaseLPosY   = Clip3( 0, pcBaseRec->getHeight(COMPONENT_Y) - 1, iCurrPosY + ( (cDv.getVer() + 2 ) >> 2 )); 
5470  Int         iBaseRPosX   = Clip3( 0, pcBaseRec->getWidth (COMPONENT_Y) - 1, iCurrPosX + (iWidth >> 1) + 1 + ( (cDv.getHor() + 2 ) >> 2 ) );
5471  Int         iBaseRPosY   = Clip3( 0, pcBaseRec->getHeight(COMPONENT_Y) - 1, iCurrPosY + ( (cDv.getVer() + 2 ) >> 2 )); 
5472  Int         iBaseUPosX   = Clip3( 0, pcBaseRec->getWidth (COMPONENT_Y) - 1, iCurrPosX + ( (cDv.getHor() + 2 ) >> 2 ) );
5473  Int         iBaseUPosY   = Clip3( 0, pcBaseRec->getHeight(COMPONENT_Y) - 1, iCurrPosY - (iHeight >> 1) + ( (cDv.getVer() + 2 ) >> 2 )); 
5474  Int         iBaseDPosX   = Clip3( 0, pcBaseRec->getWidth (COMPONENT_Y) - 1, iCurrPosX + ( (cDv.getHor() + 2 ) >> 2 ) );
5475  Int         iBaseDPosY   = Clip3( 0, pcBaseRec->getHeight(COMPONENT_Y) - 1, iCurrPosY + (iHeight >> 1) + 1 + ( (cDv.getVer() + 2 ) >> 2 )); 
5476
5477  Int         iBaseCUAddr;
5478  Int         iBaseAbsPartIdx;
5479  Int         iBaseLCUAddr;
5480  Int         iBaseLAbsPartIdx;
5481  Int         iBaseRCUAddr;
5482  Int         iBaseRAbsPartIdx;
5483  Int         iBaseUCUAddr;
5484  Int         iBaseUAbsPartIdx;
5485  Int         iBaseDCUAddr;
5486  Int         iBaseDAbsPartIdx;
5487  pcBaseRec->getCUAddrAndPartIdx( iBasePosX , iBasePosY , iBaseCUAddr, iBaseAbsPartIdx );
5488  pcBaseRec->getCUAddrAndPartIdx( iBaseLPosX , iBaseLPosY , iBaseLCUAddr, iBaseLAbsPartIdx );
5489  pcBaseRec->getCUAddrAndPartIdx( iBaseRPosX , iBaseRPosY , iBaseRCUAddr, iBaseRAbsPartIdx );
5490  pcBaseRec->getCUAddrAndPartIdx( iBaseUPosX , iBaseUPosY , iBaseUCUAddr, iBaseUAbsPartIdx );
5491  pcBaseRec->getCUAddrAndPartIdx( iBaseDPosX , iBaseDPosY , iBaseDCUAddr, iBaseDAbsPartIdx );
5492  TComDataCU* pcBaseCU     = pcBasePic->getCtu( iBaseCUAddr );
5493  TComDataCU* pcBaseLCU    = pcBasePic->getCtu( iBaseLCUAddr );
5494  TComDataCU* pcBaseRCU    = pcBasePic->getCtu( iBaseRCUAddr );
5495  TComDataCU* pcBaseUCU    = pcBasePic->getCtu( iBaseUCUAddr );
5496  TComDataCU* pcBaseDCU    = pcBasePic->getCtu( iBaseDCUAddr );
5497  bIVFMerge = pcBaseLCU->getMergeFlag( iBaseLAbsPartIdx ) && pcBaseCU->getMergeFlag( iBaseAbsPartIdx ) && pcBaseRCU->getMergeFlag( iBaseRAbsPartIdx ) && pcBaseUCU->getMergeFlag( iBaseUAbsPartIdx ) && pcBaseDCU->getMergeFlag( iBaseDAbsPartIdx );
5498  Int aiDepthL[5]; //depth level
5499  aiDepthL[0] = pcBaseCU->getDepth(iBaseAbsPartIdx);
5500  aiDepthL[1] = pcBaseLCU->getDepth(iBaseLAbsPartIdx);
5501  aiDepthL[2] = pcBaseRCU->getDepth(iBaseRAbsPartIdx);
5502  aiDepthL[3] = pcBaseUCU->getDepth(iBaseUAbsPartIdx);
5503  aiDepthL[4] = pcBaseDCU->getDepth(iBaseDAbsPartIdx);
5504  for (Int i = 0; i < 5; i++)
5505  {
5506    if (iIVFMaxD < aiDepthL[i])
5507      iIVFMaxD = aiDepthL[i];
5508  }
5509}
5510#endif
5511
5512#if NH_3D_SPIVMP
5513Void TComDataCU::getSPPara(Int iPUWidth, Int iPUHeight, Int& iNumSP, Int& iNumSPInOneLine, Int& iSPWidth, Int& iSPHeight)
5514{
5515  Int iSubPUSize = ( getSlice()->getIsDepth() ? getSlice()->getMpiSubPbSize() : getSlice()->getSubPbSize() );
5516
5517  iNumSPInOneLine = iPUWidth/iSubPUSize;
5518  Int iNumSPInOneColumn = iPUHeight/iSubPUSize;
5519  iNumSPInOneLine = (iPUHeight % iSubPUSize != 0 || iPUWidth % iSubPUSize != 0 ) ? 1 : iNumSPInOneLine;
5520  iNumSPInOneColumn = (iPUHeight % iSubPUSize != 0  || iPUWidth % iSubPUSize != 0 ) ? 1 : iNumSPInOneColumn;
5521  iNumSP = iNumSPInOneLine * iNumSPInOneColumn;
5522
5523  iSPWidth = iNumSPInOneLine == 1 ? iPUWidth: iSubPUSize; 
5524  iSPHeight = iNumSPInOneColumn == 1 ? iPUHeight: iSubPUSize; 
5525}
5526
5527Void TComDataCU::getSPAbsPartIdx(UInt uiBaseAbsPartIdx, Int iWidth, Int iHeight, Int iPartIdx, Int iNumPartLine, UInt& ruiPartAddr )
5528{
5529  uiBaseAbsPartIdx += m_absZIdxInCtu;
5530  Int iBasePelX = g_auiRasterToPelX[g_auiZscanToRaster[uiBaseAbsPartIdx]];
5531  Int iBasePelY = g_auiRasterToPelY[g_auiZscanToRaster[uiBaseAbsPartIdx]];
5532  Int iCurrPelX = iBasePelX + iPartIdx%iNumPartLine * iWidth;
5533  Int iCurrPelY = iBasePelY + iPartIdx/iNumPartLine * iHeight;
5534  Int iCurrRaster = iCurrPelY / getPic()->getMinCUHeight() * getPic()->getNumPartInCtuWidth() + iCurrPelX/getPic()->getMinCUWidth();
5535  ruiPartAddr = g_auiRasterToZscan[iCurrRaster];
5536  ruiPartAddr -= m_absZIdxInCtu; 
5537}
5538
5539Void TComDataCU::setInterDirSP( UInt uiDir, UInt uiAbsPartIdx, Int iWidth, Int iHeight )
5540{
5541  uiAbsPartIdx += getZorderIdxInCtu();
5542  Int iStartPelX = g_auiRasterToPelX[g_auiZscanToRaster[uiAbsPartIdx]];
5543  Int iStartPelY = g_auiRasterToPelY[g_auiZscanToRaster[uiAbsPartIdx]];
5544  Int iEndPelX = iStartPelX + iWidth;
5545  Int iEndPelY = iStartPelY + iHeight;
5546
5547  Int iCurrRaster, uiPartAddr;
5548
5549  for (Int i=iStartPelY; i<iEndPelY; i+=getPic()->getMinCUHeight())
5550  {
5551    for (Int j=iStartPelX; j < iEndPelX; j += getPic()->getMinCUWidth())
5552    {
5553      iCurrRaster = i / getPic()->getMinCUHeight() * getPic()->getNumPartInCtuWidth() + j/getPic()->getMinCUWidth();
5554      uiPartAddr = g_auiRasterToZscan[iCurrRaster];
5555      uiPartAddr -= getZorderIdxInCtu(); 
5556
5557      m_puhInterDir[uiPartAddr] = uiDir;
5558    }
5559  }
5560}
5561#endif
5562
5563#if NH_3D_IV_MERGE
5564Bool
5565TComDataCU::getInterViewMergeCands(UInt uiPartIdx, Int* paiPdmRefIdx, TComMv* pacPdmMv, DisInfo* pDInfo, Int* availableMcDc , Bool bIsDepth           
5566#if NH_3D_SPIVMP
5567, TComMvField* pcMvFieldSP, UChar* puhInterDirSP
5568#endif
5569, Bool bICFlag
5570)
5571{
5572  TComSlice*    pcSlice = getSlice (); 
5573  Int iViewIndex        = pDInfo->m_aVIdxCan;
5574
5575  //--- get base CU/PU and check prediction mode ---
5576  TComPic*    pcBasePic   = pcSlice->getIvPic( bIsDepth, iViewIndex );
5577  TComPicYuv* pcBaseRec   = pcBasePic->getPicYuvRec   ();
5578
5579  UInt          uiPartAddr;
5580  Int           iWidth;
5581  Int           iHeight;
5582  getPartIndexAndSize( uiPartIdx, uiPartAddr, iWidth, iHeight );
5583
5584  Int  iCurrPosX, iCurrPosY;
5585  pcBaseRec->getTopLeftSamplePos( getCtuRsAddr(), getZorderIdxInCtu() + uiPartAddr, iCurrPosX, iCurrPosY );
5586
5587#if !NH_3D_SPIVMP
5588  iCurrPosX  += ( iWidth  >> 1 );
5589  iCurrPosY  += ( iHeight >> 1 );
5590#endif
5591
5592  Bool depthRefineFlag = false; 
5593#if NH_3D_NBDV_REF
5594  depthRefineFlag = m_pcSlice->getDepthRefinementFlag( ); 
5595#endif // NH_3D_NBDV_REF
5596
5597  TComMv      cDv = depthRefineFlag ? pDInfo->m_acDoNBDV : pDInfo->m_acNBDV; 
5598  if( depthRefineFlag )
5599  {
5600    cDv.setVer(0);
5601  }
5602
5603  Bool abPdmAvailable[8] =  {false, false, false, false, false, false, false, false};
5604#if NH_3D_NBDV
5605  for( Int i = 0; i < 8; i++)
5606  {
5607    pacPdmMv[i].setIDVFlag   (false);
5608  }
5609#endif
5610
5611  if(!bICFlag)
5612  {
5613
5614#if NH_3D_SPIVMP
5615    ////////////////////////////////
5616    //////////sub-PU IvMC///////////
5617    ////////////////////////////////
5618    if(!m_pcSlice->getIsDepth())
5619    {
5620#if NH_3D_DBBP
5621      if (!getDBBPFlag(0))
5622#else
5623      if (1)
5624#endif
5625      {
5626        Int iNumSPInOneLine, iNumSP, iSPWidth, iSPHeight;
5627        getSPPara(iWidth, iHeight, iNumSP, iNumSPInOneLine, iSPWidth, iSPHeight);
5628
5629        for (Int i=0; i<iNumSP; i++)
5630        {
5631          puhInterDirSP[i] = 0;
5632          pcMvFieldSP[2*i].getMv().set(0, 0);
5633          pcMvFieldSP[2*i+1].getMv().set(0,0);
5634          pcMvFieldSP[2*i].setRefIdx(-1);
5635          pcMvFieldSP[2*i+1].setRefIdx(-1);
5636        }
5637
5638        Int         iBaseCUAddr;
5639        Int         iBaseAbsPartIdx;
5640        TComDataCU* pcBaseCU;
5641        Int iPartition = 0;
5642
5643        Int iDelX = iSPWidth/2;
5644        Int iDelY = iSPHeight/2;
5645
5646        Int         iCenterPosX = iCurrPosX + ( ( iWidth /  iSPWidth ) >> 1 )  * iSPWidth + ( iSPWidth >> 1 );
5647        Int         iCenterPosY = iCurrPosY + ( ( iHeight /  iSPHeight ) >> 1 )  * iSPHeight + (iSPHeight >> 1);
5648        Int         iRefCenterCUAddr, iRefCenterAbsPartIdx;
5649
5650        if(iWidth == iSPWidth && iHeight == iSPHeight)
5651        {
5652          iCenterPosX = iCurrPosX + (iWidth >> 1);
5653          iCenterPosY = iCurrPosY + (iHeight >> 1);
5654        }
5655
5656        Int iRefCenterPosX   = Clip3( 0, pcBaseRec->getWidth (COMPONENT_Y) - 1, iCenterPosX + ( (cDv.getHor() + 2 ) >> 2 ) );
5657        Int iRefCenterPosY   = Clip3( 0, pcBaseRec->getHeight(COMPONENT_Y) - 1, iCenterPosY + ( (cDv.getVer() + 2 ) >> 2 ) ); 
5658
5659        pcBaseRec->getCUAddrAndPartIdx( iRefCenterPosX , iRefCenterPosY , iRefCenterCUAddr, iRefCenterAbsPartIdx );
5660        TComDataCU* pcDefaultCU    = pcBasePic->getCtu( iRefCenterCUAddr );
5661        if(!( pcDefaultCU->getPredictionMode( iRefCenterAbsPartIdx ) == MODE_INTRA ))
5662        {
5663          for( UInt uiCurrRefListId = 0; uiCurrRefListId < 2; uiCurrRefListId++ )       
5664          {
5665            RefPicList  eCurrRefPicList = RefPicList( uiCurrRefListId );
5666            Bool stopLoop = false;
5667            for(Int iLoop = 0; iLoop < 2 && !stopLoop; ++iLoop)
5668            {
5669              RefPicList eDefaultRefPicList = (iLoop ==1)? RefPicList( 1 -  uiCurrRefListId ) : RefPicList( uiCurrRefListId );
5670              TComMvField cDefaultMvField;
5671              pcDefaultCU->getMvField( pcDefaultCU, iRefCenterAbsPartIdx, eDefaultRefPicList, cDefaultMvField );
5672              Int         iDefaultRefIdx     = cDefaultMvField.getRefIdx();
5673              if (iDefaultRefIdx >= 0)
5674              {
5675                Int iDefaultRefPOC = pcDefaultCU->getSlice()->getRefPOC(eDefaultRefPicList, iDefaultRefIdx);
5676                if (iDefaultRefPOC != pcSlice->getPOC())   
5677                {
5678                  for (Int iPdmRefIdx = 0; iPdmRefIdx < pcSlice->getNumRefIdx( eCurrRefPicList ); iPdmRefIdx++)
5679                  {
5680                    if (iDefaultRefPOC == pcSlice->getRefPOC(eCurrRefPicList, iPdmRefIdx))
5681                    {
5682                      abPdmAvailable[ uiCurrRefListId ] = true;
5683                      TComMv cMv(cDefaultMvField.getHor(), cDefaultMvField.getVer());
5684#if NH_3D_NBDV
5685#if NH_3D_IV_MERGE
5686                      if( !bIsDepth )
5687                      {
5688#endif
5689                        cMv.setIDVFlag   (true);
5690                        cMv.setIDVHor    (cDv.getHor());                 
5691                        cMv.setIDVVer    (cDv.getVer()); 
5692                        cMv.setIDVVId    (iViewIndex); 
5693#if NH_3D_IV_MERGE
5694                      }
5695#endif
5696#endif
5697                      paiPdmRefIdx  [ uiCurrRefListId ] = iPdmRefIdx;
5698                      pacPdmMv      [ uiCurrRefListId ] = cMv;
5699                      stopLoop = true;
5700                      break;
5701                    }
5702                  }
5703                }
5704              }
5705            }
5706          }
5707        }
5708        availableMcDc[0] = ( abPdmAvailable[0]? 1 : 0) + (abPdmAvailable[1]? 2 : 0);
5709
5710        if(availableMcDc[0])
5711        {
5712
5713          Int         iBasePosX, iBasePosY;
5714          for (Int i=iCurrPosY; i < iCurrPosY + iHeight; i += iSPHeight)
5715          {
5716            for (Int j = iCurrPosX; j < iCurrPosX + iWidth; j += iSPWidth)
5717            {
5718              iBasePosX   = Clip3( 0, pcBaseRec->getWidth (COMPONENT_Y) - 1, j + iDelX + ( (cDv.getHor() + 2 ) >> 2 ));
5719              iBasePosY   = Clip3( 0, pcBaseRec->getHeight(COMPONENT_Y) - 1, i + iDelY + ( (cDv.getVer() + 2 ) >> 2 )); 
5720
5721              pcBaseRec->getCUAddrAndPartIdx( iBasePosX , iBasePosY, iBaseCUAddr, iBaseAbsPartIdx );
5722              pcBaseCU    = pcBasePic->getCtu( iBaseCUAddr );
5723              if(!( pcBaseCU->getPredictionMode( iBaseAbsPartIdx ) == MODE_INTRA ))
5724              {
5725                for( UInt uiCurrRefListId = 0; uiCurrRefListId < 2; uiCurrRefListId++ )
5726                {
5727                  RefPicList  eCurrRefPicList = RefPicList( uiCurrRefListId );
5728                  Bool bLoopStop = false;
5729                  for(Int iLoop = 0; iLoop < 2 && !bLoopStop; ++iLoop)
5730                  {
5731                    RefPicList eBaseRefPicList = (iLoop ==1)? RefPicList( 1 -  uiCurrRefListId ) : RefPicList( uiCurrRefListId );
5732                    TComMvField cBaseMvField;
5733                    pcBaseCU->getMvField( pcBaseCU, iBaseAbsPartIdx, eBaseRefPicList, cBaseMvField );
5734                    Int         iBaseRefIdx     = cBaseMvField.getRefIdx();
5735                    if (iBaseRefIdx >= 0)
5736                    {
5737                      Int iBaseRefPOC = pcBaseCU->getSlice()->getRefPOC(eBaseRefPicList, iBaseRefIdx);
5738                      if (iBaseRefPOC != pcSlice->getPOC())   
5739                      {
5740                        for (Int iPdmRefIdx = 0; iPdmRefIdx < pcSlice->getNumRefIdx( eCurrRefPicList ); iPdmRefIdx++)
5741                        {
5742                          if (iBaseRefPOC == pcSlice->getRefPOC(eCurrRefPicList, iPdmRefIdx))
5743                          {
5744                            abPdmAvailable[ uiCurrRefListId ] = true;
5745                            TComMv cMv(cBaseMvField.getHor(), cBaseMvField.getVer());
5746
5747                            if( !bIsDepth )
5748                            {
5749                              cMv.setIDVFlag   (true);
5750                              cMv.setIDVHor    (cDv.getHor());                 
5751                              cMv.setIDVVer    (cDv.getVer()); 
5752                              cMv.setIDVVId    (iViewIndex); 
5753                            }
5754
5755                            bLoopStop = true;
5756
5757                            pcMvFieldSP[2*iPartition + uiCurrRefListId].setMvField(cMv, iPdmRefIdx);
5758                            break;
5759                          }
5760                        }
5761                      }
5762                    }
5763                  }
5764                }
5765              }
5766
5767              puhInterDirSP[iPartition] = (pcMvFieldSP[2*iPartition].getRefIdx()!=-1 ? 1: 0) + (pcMvFieldSP[2*iPartition+1].getRefIdx()!=-1 ? 2: 0);
5768              if (puhInterDirSP[iPartition] == 0)
5769              {
5770                puhInterDirSP[iPartition] = availableMcDc[0];
5771                pcMvFieldSP[2*iPartition].setMvField(pacPdmMv[0], paiPdmRefIdx[0]);
5772                pcMvFieldSP[2*iPartition + 1].setMvField(pacPdmMv[1], paiPdmRefIdx[1]);
5773
5774              }
5775              iPartition ++;
5776            }
5777          }
5778        }
5779      }
5780
5781      iCurrPosX  += ( iWidth  >> 1 );
5782      iCurrPosY  += ( iHeight >> 1 );
5783    }
5784#endif
5785
5786    ////////////////////////////////
5787    /////// IvMC + IvMCShift ///////
5788    ////////////////////////////////
5789
5790#if NH_3D_SPIVMP
5791    if(m_pcSlice->getIsDepth())
5792    {
5793      iCurrPosX  += ( iWidth  >> 1 );
5794      iCurrPosY  += ( iHeight >> 1 );
5795    }
5796#if NH_3D_DBBP
5797    for(Int iLoopCan = ( (m_pcSlice->getIsDepth() || getDBBPFlag(0)) ? 0 : 1 ); iLoopCan < ( 2 - m_pcSlice->getIsDepth() ); iLoopCan ++) 
5798#else
5799    for(Int iLoopCan = ( m_pcSlice->getIsDepth() ? 0 : 1 ); iLoopCan < ( 2 - m_pcSlice->getIsDepth() ); iLoopCan ++) 
5800#endif
5801#else
5802    for(Int iLoopCan = 0; iLoopCan < 2; iLoopCan ++)
5803#endif
5804    {
5805      // iLoopCan == 0 --> IvMC
5806      // iLoopCan == 1 --> IvMCShift
5807
5808      Int         iBaseCUAddr;
5809      Int         iBaseAbsPartIdx;
5810
5811      Int offsetW = (iLoopCan == 0) ? 0 : ( iWidth  * 2);
5812      Int offsetH = (iLoopCan == 0) ? 0 : ( iHeight * 2);
5813
5814      Int         iBasePosX   = Clip3( 0, pcBaseRec->getWidth (COMPONENT_Y) - 1, iCurrPosX + ( (cDv.getHor() + offsetW + 2 ) >> 2 ) );
5815      Int         iBasePosY   = Clip3( 0, pcBaseRec->getHeight(COMPONENT_Y) - 1, iCurrPosY + ( (cDv.getVer() + offsetH + 2 ) >> 2 ) ); 
5816      pcBaseRec->getCUAddrAndPartIdx( iBasePosX , iBasePosY , iBaseCUAddr, iBaseAbsPartIdx );
5817
5818      TComDataCU* pcBaseCU    = pcBasePic->getCtu( iBaseCUAddr );
5819      if(!( pcBaseCU->getPredictionMode( iBaseAbsPartIdx ) == MODE_INTRA ))
5820      {
5821        // Loop reference picture list of current slice (X in spec).
5822        for( UInt uiCurrRefListId = 0; uiCurrRefListId < 2; uiCurrRefListId++ )       
5823        {
5824          RefPicList  eCurrRefPicList = RefPicList( uiCurrRefListId );
5825
5826          Bool stopLoop = false;
5827          // Loop reference picture list of candidate slice (Y in spec)
5828          for(Int iLoop = 0; iLoop < 2 && !stopLoop; ++iLoop)
5829          {
5830            RefPicList eBaseRefPicList = (iLoop ==1)? RefPicList( 1 -  uiCurrRefListId ) : RefPicList( uiCurrRefListId );
5831            TComMvField cBaseMvField;
5832            pcBaseCU->getMvField( pcBaseCU, iBaseAbsPartIdx, eBaseRefPicList, cBaseMvField );
5833            Int         iBaseRefIdx     = cBaseMvField.getRefIdx();
5834            if (iBaseRefIdx >= 0)
5835            {
5836              Int iBaseRefPOC = pcBaseCU->getSlice()->getRefPOC(eBaseRefPicList, iBaseRefIdx);
5837              if (iBaseRefPOC != pcSlice->getPOC())   
5838              {
5839                for (Int iPdmRefIdx = 0; iPdmRefIdx < pcSlice->getNumRefIdx( eCurrRefPicList ); iPdmRefIdx++)
5840                {
5841                  if (iBaseRefPOC == pcSlice->getRefPOC(eCurrRefPicList, iPdmRefIdx))
5842                  {
5843                    abPdmAvailable[ (uiCurrRefListId + (iLoopCan<<2)) ] = true;
5844                    TComMv cMv(cBaseMvField.getHor(), cBaseMvField.getVer());
5845#if NH_3D_NBDV
5846#if NH_3D_IV_MERGE
5847                    if( !bIsDepth )
5848                    {
5849#endif
5850                      cMv.setIDVFlag   (true);
5851                      cMv.setIDVHor    (cDv.getHor());                 
5852                      cMv.setIDVVer    (cDv.getVer()); 
5853                      cMv.setIDVVId    (iViewIndex); 
5854#if NH_3D_IV_MERGE
5855                    }
5856#endif
5857#endif
5858                    paiPdmRefIdx  [ (uiCurrRefListId + (iLoopCan<<2)) ] = iPdmRefIdx;
5859                    pacPdmMv      [ (uiCurrRefListId + (iLoopCan<<2)) ] = cMv;
5860                    stopLoop = true;
5861                    break;
5862                  }
5863                }
5864              }
5865            }
5866          }
5867        }
5868      }
5869    }
5870#if NH_3D_SPIVMP
5871#if NH_3D_DBBP
5872    for(Int iLoopCan = ( (m_pcSlice->getIsDepth() || getDBBPFlag(0)) ? 0 : 1 ); iLoopCan < ( 2 - m_pcSlice->getIsDepth() ); iLoopCan ++)
5873#else
5874    for(Int iLoopCan = ( m_pcSlice->getIsDepth()  ? 0 : 1 ); iLoopCan < ( 2 - m_pcSlice->getIsDepth() ); iLoopCan ++)
5875#endif
5876#else
5877    for(Int iLoopCan = 0; iLoopCan < 2; iLoopCan ++)
5878#endif
5879    {
5880      availableMcDc[(iLoopCan << 1)] = ( abPdmAvailable[(iLoopCan<<2)] ? 1 : 0 ) + ( abPdmAvailable[1 + (iLoopCan<<2)] ? 2 : 0);
5881    }
5882
5883  }
5884
5885  ////////////////////////////////
5886  /////// IvDC + IvDCShift ///////
5887  ////////////////////////////////
5888
5889  if( !getSlice()->getIsDepth() )
5890  {
5891    for( Int iRefListId = 0; iRefListId < 2 ; iRefListId++ )
5892    {
5893      RefPicList  eRefPicListDMV       = RefPicList( iRefListId );
5894      Int         iNumRefPics       = pcSlice->getNumRefIdx( eRefPicListDMV );
5895      for( Int iPdmRefIdx = 0; iPdmRefIdx < iNumRefPics; iPdmRefIdx++ )
5896      {
5897        if(( pcSlice->getRefPOC( eRefPicListDMV, iPdmRefIdx ) == pcSlice->getPOC()) && (pcSlice->getRefPic( eRefPicListDMV, iPdmRefIdx )->getViewIndex() == pDInfo->m_aVIdxCan))
5898        {
5899          for(Int iLoopCan = 0; iLoopCan < 2; iLoopCan ++)
5900          {
5901            Int ioffsetDV = (iLoopCan == 0) ? 0 : 4;
5902            abPdmAvailable[ iRefListId + 2 + (iLoopCan<<2) ] = true;
5903            paiPdmRefIdx  [ iRefListId + 2 + (iLoopCan<<2) ] = iPdmRefIdx;
5904#if NH_3D_NBDV_REF
5905            TComMv cMv = depthRefineFlag ? pDInfo->m_acDoNBDV : pDInfo->m_acNBDV; 
5906#endif
5907            cMv.setHor( cMv.getHor() + ioffsetDV );
5908#if NH_3D_IV_MERGE
5909            if( bIsDepth )
5910            {
5911              cMv.setHor((cMv.getHor()+2)>>2); 
5912            }
5913#endif
5914            cMv.setVer( 0 );
5915            pacPdmMv      [iRefListId + 2 + (iLoopCan<<2)] = cMv;
5916          }
5917          break;
5918        }
5919      }
5920    }
5921    for(Int iLoopCan = 0; iLoopCan < 2; iLoopCan ++)
5922    {
5923      availableMcDc[1 + (iLoopCan << 1)] = ( abPdmAvailable[2 + (iLoopCan<<2)] ? 1 : 0 ) + ( abPdmAvailable[3 + (iLoopCan<<2)] ? 2 : 0 );
5924    }
5925  }
5926  return false;
5927}
5928#endif
5929#if NH_3D_ARP
5930Void TComDataCU::setARPWSubParts ( UChar w, UInt uiAbsPartIdx, UInt uiDepth )
5931{
5932  setSubPart<UChar>( w, m_puhARPW, uiAbsPartIdx, uiDepth, 0 );
5933}
5934#endif
5935
5936#if NH_3D_IC
5937Void TComDataCU::setICFlagSubParts( Bool bICFlag, UInt uiAbsPartIdx, UInt uiPartIdx, UInt uiDepth )
5938{
5939  memset( m_pbICFlag + uiAbsPartIdx, bICFlag, (m_pcPic->getNumPartitionsInCtu() >> ( 2 * uiDepth ))*sizeof(Bool) );
5940}
5941
5942Bool TComDataCU::isICFlagRequired( UInt uiAbsPartIdx )
5943{
5944  UInt uiPartAddr;
5945  UInt iNumbPart;
5946
5947  if( !( getPartitionSize( uiAbsPartIdx ) == SIZE_2Nx2N ) )
5948  {
5949    return false;
5950  }
5951
5952  if( getSlice()->getIcSkipParseFlag() )
5953  {
5954    if( getMergeFlag( uiAbsPartIdx ) && getMergeIndex( uiAbsPartIdx ) == 0 )
5955    {
5956      return false;
5957    }
5958  }
5959
5960  if( getMergeFlag( uiAbsPartIdx ) )
5961  {
5962    return true;
5963  }
5964
5965
5966  Int iWidth, iHeight;
5967
5968  iNumbPart = ( getPartitionSize( uiAbsPartIdx ) == SIZE_2Nx2N ? 1 : ( getPartitionSize( uiAbsPartIdx ) == SIZE_NxN ? 4 : 2 ) );
5969
5970  for(UInt i = 0; i < iNumbPart; i++)
5971  {
5972    getPartIndexAndSize( i, uiPartAddr, iWidth, iHeight, uiAbsPartIdx, true );
5973    uiPartAddr += uiAbsPartIdx;
5974
5975    for(UInt uiRefIdx = 0; uiRefIdx < 2; uiRefIdx++)
5976    {
5977      RefPicList eRefList = uiRefIdx ? REF_PIC_LIST_1 : REF_PIC_LIST_0;
5978      Int iBestRefIdx = getCUMvField(eRefList)->getRefIdx(uiPartAddr);
5979
5980      if( ( getInterDir( uiPartAddr ) & ( uiRefIdx+1 ) ) && iBestRefIdx >= 0 && getSlice()->getViewIndex() != getSlice()->getRefPic( eRefList, iBestRefIdx )->getViewIndex() )
5981      {
5982        return true;
5983      }
5984    }
5985  }
5986
5987  return false;
5988}
5989#endif
5990#if NH_3D_DMM
5991Void TComDataCU::setDmm1WedgeTabIdxSubParts( UInt tabIdx, UInt uiAbsPartIdx, UInt uiDepth )
5992{
5993  UInt uiCurrPartNumb = m_pcPic->getNumPartitionsInCtu() >> (uiDepth << 1);
5994  for( UInt ui = 0; ui < uiCurrPartNumb; ui++ ) { m_dmm1WedgeTabIdx[uiAbsPartIdx+ui] = tabIdx; }
5995}
5996#endif
5997
5998#if NH_3D_VSP
5999Void TComDataCU::setMvFieldPUForVSP( TComDataCU* pcCU, UInt partAddr, Int width, Int height, RefPicList eRefPicList, Int iRefIdx, Int &vspSize )
6000{
6001  // Get depth reference
6002  Int depthRefViewIdx = pcCU->getDvInfo(partAddr).m_aVIdxCan;
6003 
6004#if H_3D_FCO_VSP_DONBDV_E0163
6005  TComPic* pRefPicBaseDepth = 0;
6006  Bool     bIsCurrDepthCoded = false;
6007  pRefPicBaseDepth  = pcCU->getSlice()->getIvPic( true, pcCU->getSlice()->getViewIndex() );
6008  if ( pRefPicBaseDepth->getPicYuvRec() != NULL  ) 
6009  {
6010    bIsCurrDepthCoded = true;
6011  }
6012  else 
6013  {
6014    pRefPicBaseDepth = pcCU->getSlice()->getIvPic (true, depthRefViewIdx );
6015  }
6016#else
6017  TComPic* pRefPicBaseDepth = pcCU->getSlice()->getIvPic (true, depthRefViewIdx );
6018#endif
6019  assert(pRefPicBaseDepth != NULL);
6020  TComPicYuv* pcBaseViewDepthPicYuv = pRefPicBaseDepth->getPicYuvRec();
6021  assert(pcBaseViewDepthPicYuv != NULL);
6022  pcBaseViewDepthPicYuv->extendPicBorder();
6023
6024  // Get texture reference
6025  assert(iRefIdx >= 0);
6026  TComPic* pRefPicBaseTxt = pcCU->getSlice()->getRefPic( eRefPicList, iRefIdx );
6027  TComPicYuv* pcBaseViewTxtPicYuv = pRefPicBaseTxt->getPicYuvRec();
6028  assert(pcBaseViewTxtPicYuv != NULL);
6029
6030  // Initialize LUT according to the reference viewIdx
6031  Int txtRefViewIdx = pRefPicBaseTxt->getViewIndex();
6032  Int* pShiftLUT    = pcCU->getSlice()->getDepthToDisparityB( txtRefViewIdx );
6033  assert( txtRefViewIdx < pcCU->getSlice()->getViewIndex() );
6034
6035  // prepare Dv to access depth map or reference view
6036  TComMv cDv  = pcCU->getDvInfo(partAddr).m_acNBDV;
6037  pcCU->clipMv(cDv);
6038
6039#if H_3D_FCO_VSP_DONBDV_E0163
6040  if ( bIsCurrDepthCoded )
6041  {
6042      cDv.setZero();
6043  }
6044#endif
6045
6046  // fetch virtual depth map & convert depth to motion vector, which are stored in the motion memory
6047  xSetMvFieldForVSP( pcCU, pcBaseViewDepthPicYuv, &cDv, partAddr, width, height, pShiftLUT, eRefPicList, iRefIdx, pcCU->getSlice()->getIsDepth(), vspSize );
6048}
6049
6050Void TComDataCU::xSetMvFieldForVSP( TComDataCU *cu, TComPicYuv *picRefDepth, TComMv *dv, UInt partAddr, Int width, Int height, Int *shiftLUT, RefPicList refPicList, Int refIdx, Bool isDepth, Int &vspSize )
6051{
6052  TComCUMvField *cuMvField = cu->getCUMvField( refPicList );
6053  Int partAddrRasterSubPULine  = g_auiZscanToRaster[ partAddr ];
6054  Int numPartsLine    = cu->getPic()->getNumPartInCtuWidth();
6055
6056  Int nTxtPerMvInfoX = 4; // cu->getPic()->getMinCUWidth();
6057  Int nTxtPerMvInfoY = 4; // cu->getPic()->getMinCUHeight();
6058
6059  Int refDepStride = picRefDepth->getStride( COMPONENT_Y );
6060
6061  TComMv tmpMv(0, 0);
6062  tmpMv.setIDVFlag(false);
6063
6064  Int refDepOffset  = ( (dv->getHor()+2) >> 2 ) + ( (dv->getVer()+2) >> 2 ) * refDepStride;
6065  Pel *refDepth     = picRefDepth->getAddr( COMPONENT_Y, cu->getCtuRsAddr(), cu->getZorderIdxInCtu() + partAddr ) + refDepOffset;
6066
6067  if ((height % 8))
6068  {
6069    vspSize = 1; // 8x4
6070  }
6071  else if ((width % 8))
6072  {
6073    vspSize = 0; // 4x8
6074  }
6075  else
6076  {
6077    Bool ULvsBR, URvsBL;
6078    ULvsBR = refDepth[0]       < refDepth[refDepStride * (height-1) + width-1];
6079    URvsBL = refDepth[width-1] < refDepth[refDepStride * (height-1)];
6080    vspSize = ( ULvsBR ^ URvsBL ) ? 0 : 1;
6081  }
6082 
6083  Int subBlockW, subBlockH;
6084  if (vspSize)
6085  {
6086    subBlockW = 8;
6087    subBlockH = 4;
6088  }
6089  else
6090  {
6091    subBlockW = 4;
6092    subBlockH = 8;
6093  }
6094 
6095  Int numPartsInSubPUW = subBlockW / nTxtPerMvInfoX;
6096  Int numPartsInSubPUH = subBlockH / nTxtPerMvInfoY * numPartsLine;
6097
6098  for( Int y=0; y<height; y+=subBlockH, partAddrRasterSubPULine+=numPartsInSubPUH )
6099  {
6100    Pel *refDepthTmp[4];
6101    refDepthTmp[0] = refDepth + refDepStride * y;
6102    refDepthTmp[1] = refDepthTmp[0] + subBlockW - 1;
6103    refDepthTmp[2] = refDepthTmp[0] + refDepStride * (subBlockH - 1);
6104    refDepthTmp[3] = refDepthTmp[2] + subBlockW - 1;
6105
6106    Int partAddrRasterSubPU = partAddrRasterSubPULine;
6107    for( Int x=0; x<width; x+=subBlockW, partAddrRasterSubPU+=numPartsInSubPUW )
6108    {
6109      Pel  maxDepthVal;
6110      maxDepthVal = refDepthTmp[0][x];
6111      maxDepthVal = std::max( maxDepthVal, refDepthTmp[1][x]);
6112      maxDepthVal = std::max( maxDepthVal, refDepthTmp[2][x]);
6113      maxDepthVal = std::max( maxDepthVal, refDepthTmp[3][x]);
6114      tmpMv.setHor( (Short) shiftLUT[ maxDepthVal ] );
6115
6116      Int partAddrRasterPartLine = partAddrRasterSubPU;
6117      for( Int sY=0; sY<numPartsInSubPUH; sY+=numPartsLine, partAddrRasterPartLine += numPartsLine )
6118      {
6119        Int partAddrRasterPart = partAddrRasterPartLine;
6120        for( Int sX=0; sX<numPartsInSubPUW; sX+=1, partAddrRasterPart++ )
6121        {
6122          cuMvField->setMv    ( g_auiRasterToZscan[ partAddrRasterPart ], tmpMv );
6123          cuMvField->setRefIdx( g_auiRasterToZscan[ partAddrRasterPart ], refIdx );
6124        }
6125      }
6126    }
6127  }
6128
6129  vspSize = (vspSize<<2)+1;
6130
6131}
6132#endif
6133
6134//! \}
Note: See TracBrowser for help on using the repository browser.