source: 3DVCSoftware/branches/HTM-5.1-dev0/source/Lib/TLibCommon/TComDepthMapGenerator.cpp @ 1206

Last change on this file since 1206 was 293, checked in by tech, 12 years ago

Renamed macros related to IVMP and created list of 6.1 macros to be removed.

  • Property svn:eol-style set to native
File size: 80.5 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-2011, 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 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
35
36/** \file     TComDepthMapGenerator.cpp
37    \brief    depth map generator class
38*/
39
40
41
42#include "CommonDef.h"
43#include "TComDepthMapGenerator.h"
44
45
46#if DEPTH_MAP_GENERATION
47
48TComDepthMapGenerator::TComDepthMapGenerator()
49{
50  m_bCreated            = false;
51  m_bInit               = false;
52  m_bDecoder            = false;
53  m_pcPrediction        = 0;
54  m_pcSPSAccess         = 0;
55  m_pcAUPicAccess       = 0;
56  m_uiMaxDepth          = 0;
57  m_uiOrgDepthBitDepth  = 0;
58  m_uiSubSampExpX       = 0;
59  m_uiSubSampExpY       = 0;
60  m_ppcYuv              = 0;
61  m_ppcCU               = 0;
62}
63
64TComDepthMapGenerator::~TComDepthMapGenerator()
65{
66  destroy ();
67  uninit  ();
68}
69
70Void
71TComDepthMapGenerator::create( Bool bDecoder, UInt uiPicWidth, UInt uiPicHeight, UInt uiMaxCUDepth, UInt uiMaxCUWidth, UInt uiMaxCUHeight, UInt uiOrgBitDepth, UInt uiSubSampExpX, UInt uiSubSampExpY )
72{
73  destroy();
74  m_bDecoder            = bDecoder;
75  m_uiMaxDepth          = uiMaxCUDepth;
76  m_uiOrgDepthBitDepth  = uiOrgBitDepth;
77  m_uiSubSampExpX       = uiSubSampExpX;
78  m_uiSubSampExpY       = uiSubSampExpY;
79#if !H3D_NBDV
80  m_ppcYuv              = new TComYuv*    [ m_uiMaxDepth ];
81  m_ppcCU               = new TComDataCU* [ m_uiMaxDepth ];
82  for( UInt uiDepth = 0; uiDepth < m_uiMaxDepth; uiDepth++ )
83  {
84    UInt  uiNumPart = 1 << ( ( m_uiMaxDepth - uiDepth ) << 1 );
85    UInt  uiWidth   = uiMaxCUWidth  >> uiDepth;
86    UInt  uiHeight  = uiMaxCUHeight >> uiDepth;
87
88    m_ppcYuv[ uiDepth ] = new TComYuv;    m_ppcYuv[ uiDepth ]->create( uiWidth >> m_uiSubSampExpX, uiHeight >> m_uiSubSampExpY );
89    m_ppcCU [ uiDepth ] = new TComDataCU; m_ppcCU [ uiDepth ]->create( uiNumPart, uiWidth, uiHeight, true, uiMaxCUWidth >> (uiMaxCUDepth - 1) );
90  }
91  m_cTmpPic.create( uiPicWidth >> m_uiSubSampExpX, uiPicHeight >> m_uiSubSampExpY, uiMaxCUWidth >> m_uiSubSampExpX, uiMaxCUHeight >> m_uiSubSampExpY, uiMaxCUDepth );
92  xSetChroma( &m_cTmpPic, ( 1 << uiOrgBitDepth ) >> 1 );
93#endif //!H3D_NBDV
94  m_bCreated    = true;
95}
96
97Void
98TComDepthMapGenerator::destroy()
99{
100  if( m_bCreated )
101  {
102    m_bCreated    = false;
103#if !H3D_NBDV
104    for( UInt uiDepth = 0; uiDepth < m_uiMaxDepth; uiDepth++ )
105    {
106      if( m_ppcYuv[ uiDepth ] )
107      {
108        m_ppcYuv[ uiDepth ]->destroy(); delete m_ppcYuv[ uiDepth ]; m_ppcYuv[ uiDepth ] = 0;
109      }
110      if( m_ppcCU [ uiDepth ] )
111      {
112        m_ppcCU [ uiDepth ]->destroy(); delete m_ppcCU [ uiDepth ]; m_ppcCU [ uiDepth ] = 0;
113      }
114    }
115    delete [] m_ppcYuv; m_ppcYuv = 0;
116    delete [] m_ppcCU;  m_ppcCU  = 0;
117    m_cTmpPic.destroy();
118#endif //!H3D_NBDV
119    m_uiMaxDepth          = 0;
120    m_uiOrgDepthBitDepth  = 0;
121    m_uiSubSampExpX       = 0;
122    m_uiSubSampExpY       = 0;
123    m_bDecoder            = false;
124  }
125}
126
127#if VIDYO_VPS_INTEGRATION
128Void
129TComDepthMapGenerator::init( TComPrediction* pcPrediction, TComVPSAccess* pcVPSAccess, TComSPSAccess* pcSPSAccess, TComAUPicAccess* pcAUPicAccess )
130#else
131Void
132TComDepthMapGenerator::init( TComPrediction* pcPrediction, TComSPSAccess* pcSPSAccess, TComAUPicAccess* pcAUPicAccess )
133#endif
134{
135  AOF( pcPrediction  );
136  AOF( pcSPSAccess   );
137  AOF( pcAUPicAccess );
138  uninit();
139  m_pcPrediction  = pcPrediction;
140#if VIDYO_VPS_INTEGRATION
141  m_pcVPSAccess   = pcVPSAccess;
142#endif
143  m_pcSPSAccess   = pcSPSAccess;
144  m_pcAUPicAccess = pcAUPicAccess;
145  m_bInit         = true;
146}
147
148Void
149TComDepthMapGenerator::uninit()
150{
151  if( m_bInit )
152  {
153    m_bInit         = false;
154    m_pcPrediction  = 0;
155    m_pcSPSAccess   = 0;
156    m_pcAUPicAccess = 0;
157  }
158}
159
160Void 
161TComDepthMapGenerator::initViewComponent( TComPic* pcPic )
162{
163  AOF  ( m_bCreated && m_bInit );
164  AOF  ( pcPic );
165  AOT  ( pcPic->getSPS()->getViewId() && !pcPic->getSPS()->isDepth() && pcPic->getPOC() && pcPic->getSPS()->getPredDepthMapGeneration() != m_pcSPSAccess->getPdm() );
166  m_bPDMAvailable = false;
167  m_uiCurrViewId  = pcPic->getSPS()->getViewId();
168#if PDM_REMOVE_DEPENDENCE
169  pcPic->setStoredPDMforV2(0);
170#endif
171  // update SPS list and AU pic list and set depth map generator in SPS
172#if VIDYO_VPS_INTEGRATION
173  m_pcVPSAccess  ->addVPS( pcPic->getVPS() );
174#endif
175  m_pcSPSAccess  ->addSPS( pcPic->getSPS() );
176  m_pcAUPicAccess->addPic( pcPic );
177  pcPic->getSPS()->setDepthMapGenerator( this );
178
179  // check whether we have depth data or don't use pred depth prediction
180  ROFVS( pcPic->getSPS()->getViewId() );
181  ROTVS( pcPic->getSPS()->isDepth  () );
182  ROFVS( m_pcSPSAccess->getPdm     () );
183
184  // set basic SPS parameters
185  const Int iDisparityDir = 1; // 1 or -1, depending on the usage of disparity vectors
186  TComSPS*  pcSPS         = pcPic->getSPS                 ();
187  Int       iVOI          = pcSPS->getViewOrderIdx        ();
188  UInt      uiPdmPrec     = pcSPS->getPdmPrecision        ();
189  UInt      uiCamPrec     = pcSPS->getCamParPrecision     ();
190  Bool      bInSlice      = pcSPS->hasCamParInSliceHeader ();
191  Int       iScaleVOI01   = ( 1 << ( uiPdmPrec + PDM_INTER_CALC_SHIFT + PDM_VIRT_DEPTH_PRECISION - 2 ) );
192
193  // check availability of base views and set base id list
194  std::vector<Int>  aiAbsDeltaVOI;
195  for( UInt uiBaseId = 0; uiBaseId < m_uiCurrViewId; uiBaseId++ )
196  {
197    TComSPS*  pcBaseSPS     = m_pcSPSAccess  ->getSPS( uiBaseId );
198    TComPic*  pcBasePic     = m_pcAUPicAccess->getPic( uiBaseId );
199    AOF( pcBaseSPS != 0 && pcBasePic != 0 );
200    Int       iDeltaVOI     = iVOI - pcBaseSPS->getViewOrderIdx();
201    Int       iAbsDeltaVOI  = ( iDeltaVOI < 0 ? -iDeltaVOI : iDeltaVOI ); 
202    AOT( iAbsDeltaVOI == 0 );
203    aiAbsDeltaVOI.push_back( iAbsDeltaVOI );
204  }
205  m_auiBaseIdList.clear();
206  while( (UInt)m_auiBaseIdList.size() < m_uiCurrViewId )
207  {
208    Int       iMinAbsDelta  = MAX_INT;
209    UInt      uiNextBaseId  = MAX_VIEW_NUM;
210    for( UInt uiBaseId = 0; uiBaseId < m_uiCurrViewId; uiBaseId++ )
211    {
212      if( aiAbsDeltaVOI[ uiBaseId ] > 0 && aiAbsDeltaVOI[ uiBaseId ] <= iMinAbsDelta )
213      {
214        iMinAbsDelta  = aiAbsDeltaVOI[ uiBaseId ];
215        uiNextBaseId  = uiBaseId;
216      }
217    }
218    m_auiBaseIdList.push_back( uiNextBaseId );
219    aiAbsDeltaVOI[ uiNextBaseId ] = 0;
220  }
221
222  // check availability of prediction depth map
223  if( m_uiCurrViewId )
224  {
225#if PDM_REMOVE_DEPENDENCE
226    UInt      uiBaseVId   = m_auiBaseIdList[0];
227#else
228    Bool      bCheckVId1  = ( m_uiCurrViewId > 1 && m_auiBaseIdList[0] == 0 );
229    UInt      uiBaseVId   = ( bCheckVId1 ? 1 : m_auiBaseIdList[0] );
230#endif
231    TComPic*  pcBasePic   = m_pcAUPicAccess->getPic( uiBaseVId );
232    SliceType eSliceType  = pcBasePic->getCurrSlice()->getSliceType();
233    Bool      bNoRAPdm    = ( pcPic->getSPS()->getPredDepthMapGeneration() == 1 );
234    m_bPDMAvailable       = ( eSliceType != I_SLICE || !bNoRAPdm );
235  }
236
237  // update disparity depth conversion parameters
238  for( UInt uiBaseId = 0; uiBaseId < m_uiCurrViewId; uiBaseId++ )
239  {
240    TComSPS*  pcBaseSPS   = m_pcSPSAccess->getSPS( uiBaseId );
241    Int       iBaseVOI    = pcBaseSPS->getViewOrderIdx();
242
243    // disparity -> virtual depth
244    Int       iVNominator = ( 1 << PDM_LOG4_SCALE_DENOMINATOR ) + pcSPS->getPdmScaleNomDelta()[ uiBaseId ];
245    Int       iVDiv       = iVOI - iBaseVOI;
246    Int       iVAdd       = ( iVDiv > 0 ? iVDiv / 2 : -iVDiv / 2 );
247    Int       iVScalePred = ( iScaleVOI01 + iVAdd ) / iVDiv;
248    Int       iVShift     = PDM_INTER_CALC_SHIFT;
249    Int       iVScale     = Int( ( (Int64)iVNominator * (Int64)iVScalePred + (Int64)( ( 1 << PDM_LOG4_SCALE_DENOMINATOR ) >> 1 ) ) >> PDM_LOG4_SCALE_DENOMINATOR );
250    Int       iVOffset    = pcSPS->getPdmOffset()[ uiBaseId ] << PDM_OFFSET_SHIFT;
251    m_aaiConvParsDisparity2VirtDepth[ uiBaseId ][ 0 ] = iDisparityDir * iVScale;
252    m_aaiConvParsDisparity2VirtDepth[ uiBaseId ][ 1 ] = iDisparityDir * iVOffset + ( ( 1 << iVShift ) >> 1 );
253    m_aaiConvParsDisparity2VirtDepth[ uiBaseId ][ 2 ] = iVShift;
254
255    // virtual depth -> disparity
256    Int       iVInvAdd    = ( iVScale > 0 ? iVScale / 2 : -iVScale / 2 );
257    Int       iVInvScale  = Int( ( ( Int64(  1        ) << ( iVShift << 1 ) ) + iVInvAdd ) / Int64( iVScale ) );
258    Int       iVInvOffset = Int( ( ( Int64( -iVOffset ) <<   iVShift        ) + iVInvAdd ) / Int64( iVScale ) );
259    m_aaiConvParsVirtDepth2Disparity[ uiBaseId ][ 0 ] = iDisparityDir * iVInvScale;
260    m_aaiConvParsVirtDepth2Disparity[ uiBaseId ][ 1 ] = iDisparityDir * iVInvOffset + ( ( 1 << iVShift ) >> 1 );
261    m_aaiConvParsVirtDepth2Disparity[ uiBaseId ][ 2 ] = iVShift;
262
263    // coded depth -> virtual depth
264    Int       iCScale     = ( bInSlice ? pcPic->getCurrSlice()->getCodedScale () : pcSPS->getCodedScale () )[ uiBaseId ];
265    Int       iCOffset    = ( bInSlice ? pcPic->getCurrSlice()->getCodedOffset() : pcSPS->getCodedOffset() )[ uiBaseId ] << m_uiOrgDepthBitDepth;
266    Int       iCShift     = m_uiOrgDepthBitDepth + uiCamPrec + 1 - 2;
267    Int       iCVShift    = PDM_INTER_CALC_SHIFT;
268    Int       iTmpShift   = iVShift + iCShift - iCVShift; AOF( iTmpShift >= 0 )
269    Int       iCVScale    = Int( ( Int64( iVScale ) * Int64( iCScale  ) + Int64( ( 1 << iTmpShift ) >> 1 ) ) >> iTmpShift );
270    Int       iCVOffset   = Int( ( Int64( iVScale ) * Int64( iCOffset ) + Int64( ( 1 << iTmpShift ) >> 1 ) ) >> iTmpShift );
271    iTmpShift             = iVShift - iCVShift;           AOF( iTmpShift >= 0 )
272    iCVOffset            +=      ( iVOffset                             +      ( ( 1 << iTmpShift ) >> 1 ) ) >> iTmpShift;
273    m_aaiConvParsOrigDepth2VirtDepth[ uiBaseId ][ 0 ] = iCVScale;
274    m_aaiConvParsOrigDepth2VirtDepth[ uiBaseId ][ 1 ] = iCVOffset + ( ( 1 << iCVShift ) >> 1 );
275    m_aaiConvParsOrigDepth2VirtDepth[ uiBaseId ][ 2 ] = iCVShift;
276
277    // virtual depth -> coded depth
278    Int       iCVAdd      = ( iCVScale > 0 ? iCVScale / 2 : -iCVScale / 2 );
279    Int       iCVInvScale = Int( ( ( Int64(  1         ) << ( iCVShift << 1 ) ) + iCVAdd ) / Int64( iCVScale ) );
280    Int       iCVInvOffset= Int( ( ( Int64( -iCVOffset ) <<   iCVShift        ) + iCVAdd ) / Int64( iCVScale ) );
281    m_aaiConvParsVirtDepth2OrigDepth[ uiBaseId ][ 0 ] = iCVInvScale;
282    m_aaiConvParsVirtDepth2OrigDepth[ uiBaseId ][ 1 ] = iCVInvOffset + ( ( 1 << iCVShift ) >> 1 );
283    m_aaiConvParsVirtDepth2OrigDepth[ uiBaseId ][ 2 ] = iCVShift;
284  }
285
286  if( m_uiCurrViewId > 0 )
287  {
288    UInt      uiBaseId    = 0;
289    UInt      uiBaseVOI   = 0; // per definition
290    Int       iVNominator = ( 1 << PDM_LOG4_SCALE_DENOMINATOR ) + pcSPS->getPdmScaleNomDelta()[ uiBaseId ];
291    Int       iVDiv       = iVOI - uiBaseVOI;
292    Int       iVAdd       = ( iVDiv > 0 ? iVDiv / 2 : -iVDiv / 2 );
293    Int       iVScalePred = ( iScaleVOI01 + iVAdd ) / iVDiv;
294    Int       iVShift     = PDM_INTER_CALC_SHIFT;
295    Int       iVScale     = Int( ( (Int64)iVNominator * (Int64)iVScalePred + (Int64)( ( 1 << PDM_LOG4_SCALE_DENOMINATOR ) >> 1 ) ) >> PDM_LOG4_SCALE_DENOMINATOR );
296    Int       iVOffset    = pcSPS->getPdmOffset()[ uiBaseId ] << PDM_OFFSET_SHIFT;
297
298    // coded depth -> virtual depth (current view)
299    Int       iCScale     = ( bInSlice ? pcPic->getCurrSlice()->getInvCodedScale () : pcSPS->getInvCodedScale () )[ uiBaseId ];
300    Int       iCOffset    = ( bInSlice ? pcPic->getCurrSlice()->getInvCodedOffset() : pcSPS->getInvCodedOffset() )[ uiBaseId ] << m_uiOrgDepthBitDepth;
301    Int       iCShift     = m_uiOrgDepthBitDepth + uiCamPrec + 1 - 2;
302    Int       iCVShift    = PDM_INTER_CALC_SHIFT;
303    Int       iTmpShift   = iVShift + iCShift - iCVShift; AOF( iTmpShift >= 0 )
304    Int       iCVScale    = Int( ( Int64( -iVScale ) * Int64( iCScale  ) + Int64( ( 1 << iTmpShift ) >> 1 ) ) >> iTmpShift );
305    Int       iCVOffset   = Int( ( Int64( -iVScale ) * Int64( iCOffset ) + Int64( ( 1 << iTmpShift ) >> 1 ) ) >> iTmpShift );
306    iTmpShift             = iVShift - iCVShift;           AOF( iTmpShift >= 0 )
307    iCVOffset            +=      ( iVOffset                             +      ( ( 1 << iTmpShift ) >> 1 ) ) >> iTmpShift;
308    m_aaiConvParsOrigDepth2VirtDepth[ m_uiCurrViewId ][ 0 ] = iCVScale;
309    m_aaiConvParsOrigDepth2VirtDepth[ m_uiCurrViewId ][ 1 ] = iCVOffset + ( ( 1 << iCVShift ) >> 1 );
310    m_aaiConvParsOrigDepth2VirtDepth[ m_uiCurrViewId ][ 2 ] = iCVShift;
311
312    // virtual depth -> coded depth
313    Int       iCVAdd      = ( iCVScale > 0 ? iCVScale / 2 : -iCVScale / 2 );
314    Int       iCVInvScale = Int( ( ( Int64(  1         ) << ( iCVShift << 1 ) ) + iCVAdd ) / Int64( iCVScale ) );
315    Int       iCVInvOffset= Int( ( ( Int64( -iCVOffset ) <<   iCVShift        ) + iCVAdd ) / Int64( iCVScale ) );
316    m_aaiConvParsVirtDepth2OrigDepth[ m_uiCurrViewId ][ 0 ] = iCVInvScale;
317    m_aaiConvParsVirtDepth2OrigDepth[ m_uiCurrViewId ][ 1 ] = iCVInvOffset + ( ( 1 << iCVShift ) >> 1 );
318    m_aaiConvParsVirtDepth2OrigDepth[ m_uiCurrViewId ][ 2 ] = iCVShift;
319  }
320  else if( pcPic->getPOC() == 0 )
321  { // set dummy values
322    m_aaiConvParsOrigDepth2VirtDepth[ m_uiCurrViewId ][ 0 ] = 0;
323    m_aaiConvParsOrigDepth2VirtDepth[ m_uiCurrViewId ][ 1 ] = 0;
324    m_aaiConvParsOrigDepth2VirtDepth[ m_uiCurrViewId ][ 2 ] = 0;
325    m_aaiConvParsVirtDepth2OrigDepth[ m_uiCurrViewId ][ 0 ] = 0;
326    m_aaiConvParsVirtDepth2OrigDepth[ m_uiCurrViewId ][ 1 ] = 0;
327    m_aaiConvParsVirtDepth2OrigDepth[ m_uiCurrViewId ][ 2 ] = 0;
328  }
329
330
331#if 0 // print out for debugging
332  if( m_uiCurrViewId )
333  {
334    printf( "\n\ninit slice of view %d (VOI=%2d):\n===============================\n", m_uiCurrViewId, iVOI );
335    {
336      printf( "\n  disparity -> virtual depth:\n" );
337      for( UInt uiBaseId = 0; uiBaseId < m_uiCurrViewId; uiBaseId++ )
338      {
339        Int*    pP = m_aaiConvParsDisparity2VirtDepth[ uiBaseId ];
340        Double  dF = 1.0 / Double( 1 << pP[ 2 ] );
341        Double  dA = dF  * Double( pP[ 0 ] );
342        Double  dB = dF  * Double( pP[ 1 ] - ( ( 1 << pP[ 2 ] ) >> 1 ) );
343        printf( "    BId=%d:    a = %10.4lf    b = %10.4lf\n", uiBaseId, dA, dB );
344      }
345      printf( "\n  virtual depth -> disparity:\n" );
346      for( UInt uiBaseId = 0; uiBaseId < m_uiCurrViewId; uiBaseId++ )
347      {
348        Int*    pP = m_aaiConvParsVirtDepth2Disparity[ uiBaseId ];
349        Double  dF = 1.0 / Double( 1 << pP[ 2 ] );
350        Double  dA = dF  * Double( pP[ 0 ] );
351        Double  dB = dF  * Double( pP[ 1 ] - ( ( 1 << pP[ 2 ] ) >> 1 ) );
352        printf( "    BId=%d:    a = %10.4lf    b = %10.4lf\n", uiBaseId, dA, dB );
353      }
354      printf( "\n  original depth -> virtual depth:\n" );
355      for( UInt uiBaseId = 0; uiBaseId <= m_uiCurrViewId; uiBaseId++ )
356      {
357        Int*    pP = m_aaiConvParsOrigDepth2VirtDepth[ uiBaseId ];
358        Double  dF = 1.0 / Double( 1 << pP[ 2 ] );
359        Double  dA = dF  * Double( pP[ 0 ] );
360        Double  dB = dF  * Double( pP[ 1 ] - ( ( 1 << pP[ 2 ] ) >> 1 ) );
361        printf( "    VId=%d:    a = %10.4lf    b = %10.4lf\n", uiBaseId, dA, dB );
362      }
363      printf( "\n  virtual depth -> original depth:\n" );
364      for( UInt uiBaseId = 0; uiBaseId <= m_uiCurrViewId; uiBaseId++ )
365      {
366        Int*    pP = m_aaiConvParsVirtDepth2OrigDepth[ uiBaseId ];
367        Double  dF = 1.0 / Double( 1 << pP[ 2 ] );
368        Double  dA = dF  * Double( pP[ 0 ] );
369        Double  dB = dF  * Double( pP[ 1 ] - ( ( 1 << pP[ 2 ] ) >> 1 ) );
370        printf( "    VId=%d:    a = %10.4lf    b = %10.4lf\n", uiBaseId, dA, dB );
371      }
372      printf( "\n" );
373    }
374  }
375#endif
376}
377
378#if !H3D_NBDV
379Bool
380TComDepthMapGenerator::predictDepthMap( TComPic* pcPic )
381{
382  AOF  ( m_bCreated && m_bInit );
383  AOF  ( pcPic );
384  ROTRS( pcPic->getSPS()->isDepth(),  true );
385  ROFRS( m_pcSPSAccess->getPdm(),     true );
386  AOF  ( pcPic->getPredDepthMap() );
387  AOF  ( pcPic->getSPS()->getViewId() == m_uiCurrViewId );
388
389#if PDM_OUTPUT_PRED_DEPTH_MAP
390  Char acFilenameBase[1024];
391  ::sprintf( acFilenameBase, "PDM_%s_Prd", ( m_bDecoder ? "Dec" : "Enc" ) );
392#endif
393
394  Bool bUndefined = true;
395  if( m_uiCurrViewId )
396  {
397    AOF( m_auiBaseIdList.size() );
398    UInt        uiBaseId    = m_auiBaseIdList[ 0 ];
399    TComPic*    pcBasePic   = m_pcAUPicAccess->getPic( uiBaseId );
400    AOF( pcBasePic );
401
402    if( m_uiCurrViewId == 1 )
403    {
404      if( pcBasePic->getPOC() == 0 )
405      {
406        pcBasePic->removePrdDepthMapBuffer();
407        pcBasePic->addPrdDepthMapBuffer( PDM_SUB_SAMP_EXP_X(m_pcSPSAccess->getPdm()), PDM_SUB_SAMP_EXP_Y(m_pcSPSAccess->getPdm()) );
408        xClearDepthMap( pcBasePic );
409#if PDM_REMOVE_DEPENDENCE
410        xClearDepthMap( pcBasePic, PDM_UNDEFINED_DEPTH, 1 );
411#endif
412      }
413#if PDM_OUTPUT_PRED_DEPTH_MAP
414      dumpDepthMap( pcBasePic, acFilenameBase );
415#endif
416    }
417
418    Bool  bLoadDepth  = ( m_pcSPSAccess->getPdm() == 2 );
419    if( m_pcSPSAccess->getPdm() > 2 )
420    {
421      bLoadDepth = ( pcBasePic->getCurrSlice()->getSliceType() == I_SLICE );
422    }
423
424    if( bLoadDepth)
425    { // load coded depth of base view
426      TComPic*  pcBaseDepth = m_pcAUPicAccess->getPic( uiBaseId, true );
427      AOF( pcBaseDepth );
428      AOF( pcBaseDepth->getPicYuvRec() );
429      AOF( pcBaseDepth->getPicYuvRec()->getWidth () == pcBasePic->getPredDepthMap()->getWidth () );
430      AOF( pcBaseDepth->getPicYuvRec()->getHeight() == pcBasePic->getPredDepthMap()->getHeight() );
431      Int       iWidth      = pcBasePic  ->getPredDepthMap()->getWidth    ();
432      Int       iHeight     = pcBasePic  ->getPredDepthMap()->getHeight   ();
433      Int       iDesStride  = pcBasePic  ->getPredDepthMap()->getStride   ();
434      Int       iSrcStride  = pcBaseDepth->getPicYuvRec   ()->getStride   ();
435      Pel*      pDesSamples = pcBasePic  ->getPredDepthMap()->getLumaAddr ( 0 );
436      Pel*      pSrcSamples = pcBaseDepth->getPicYuvRec   ()->getLumaAddr ( 0 );
437      for( Int iY = 0; iY < iHeight; iY++, pSrcSamples += iSrcStride, pDesSamples += iDesStride )
438      {
439        for( Int iX = 0; iX < iWidth; iX++ )
440        {
441          pDesSamples[ iX ] = xGetVirtDepthFromOrigDepth( uiBaseId, pSrcSamples[ iX ] );
442        }
443      }
444    }
445
446    // convert depth of base view to current view
447    bUndefined = xConvertDepthMapRef2Curr( pcPic, pcBasePic );
448
449#if PDM_OUTPUT_PRED_DEPTH_MAP
450    dumpDepthMap( pcPic, acFilenameBase );
451#endif
452  }
453  else
454  {
455    xClearDepthMap( pcPic );
456#if PDM_REMOVE_DEPENDENCE
457    xClearDepthMap( pcPic, PDM_UNDEFINED_DEPTH, 1 );
458#endif
459  }
460  return bUndefined;
461}
462
463
464Void
465TComDepthMapGenerator::updateDepthMap( TComPic* pcPic )
466{
467  AOF  ( m_bCreated && m_bInit );
468  AOF  ( pcPic );
469  ROTVS( pcPic->getSPS()->isDepth() );
470  ROFVS( m_pcSPSAccess->getPdm() == 1 || m_pcSPSAccess->getPdm() == 3 );
471  AOF  ( pcPic->getPredDepthMap() );
472  AOF  ( pcPic->getSPS()->getViewId() == m_uiCurrViewId );
473
474#if PDM_OUTPUT_PRED_DEPTH_MAP
475  Char acFilenameBase[1024];
476  ::sprintf( acFilenameBase, "PDM_%s_Upd", ( m_bDecoder ? "Dec" : "Enc" ) );
477#endif
478
479  // predict depth map using current coding symbols
480#if PDM_REMOVE_DEPENDENCE
481  pcPic->setStoredPDMforV2(0);
482  xPredictDepthMap( pcPic );
483  if(m_uiCurrViewId==0)
484  {
485    pcPic->setStoredPDMforV2(1);
486    xPredictDepthMap( pcPic );
487    pcPic->setStoredPDMforV2(0);
488  }
489#else
490  xPredictDepthMap( pcPic );
491#if PDM_OUTPUT_PRED_DEPTH_MAP
492  if( m_uiCurrViewId )
493  {
494    dumpDepthMap( pcPic, acFilenameBase );
495  }
496#endif
497#endif
498
499  // generate base depth map
500  if( m_uiCurrViewId == 1 )
501  {
502    TComPic* pcBasePic = m_pcAUPicAccess->getPic( 0 );
503    AOF( pcBasePic );
504    xConvertDepthMapCurr2Ref( pcBasePic, pcPic );
505#if PDM_OUTPUT_PRED_DEPTH_MAP
506    dumpDepthMap( pcBasePic, acFilenameBase );
507#endif
508  }
509#if PDM_REMOVE_DEPENDENCE
510  if( m_uiCurrViewId == 2 )
511  {
512    TComPic* pcBasePic = m_pcAUPicAccess->getPic( 0 );
513    AOF( pcBasePic );
514    xConvertDepthMapCurr2Ref( pcBasePic, pcPic );
515#if PDM_OUTPUT_PRED_DEPTH_MAP
516    dumpDepthMap( pcBasePic, acFilenameBase );
517#endif
518  }
519#endif
520}
521
522
523Void
524TComDepthMapGenerator::dumpDepthMap( TComPic* pcPic, char* pFilenameBase )
525{
526  AOF( m_bCreated && m_bInit );
527  AOF( pcPic );
528  AOF( pFilenameBase );
529  AOF( m_uiOrgDepthBitDepth == 8 + g_uiBitIncrement );
530  AOF( pcPic->getSPS()->getViewId() <= m_uiCurrViewId );
531
532  // convert to output format
533  Int         iMax        = ( 1 << m_uiOrgDepthBitDepth ) - 1;
534  UInt        uiViewId    = pcPic->getSPS()->getViewId();
535  TComPicYuv* pcPicYuv    = pcPic->getPredDepthMap();
536  Int         iWidth      = pcPicYuv->getWidth    ();
537  Int         iHeight     = pcPicYuv->getHeight   ();
538  Int         iSrcStride  = pcPicYuv->getStride   ();
539  Int         iDstStride  = m_cTmpPic.getStride   ();
540#if PDM_REMOVE_DEPENDENCE
541  if(pcPic->getStoredPDMforV2())
542     pcPicYuv    = pcPic->getPredDepthMapTemp();
543#endif
544  Pel*        pSrcSamples = pcPicYuv->getLumaAddr ( 0 );
545  Pel*        pDstSamples = m_cTmpPic.getLumaAddr ( 0 );
546  Int         iMidOrgDpth = ( 1 << m_uiOrgDepthBitDepth ) >> 1;
547  AOF( m_cTmpPic.getWidth () == iWidth  );
548  AOF( m_cTmpPic.getHeight() == iHeight );
549  for( Int iY = 0; iY < iHeight; iY++, pSrcSamples += iSrcStride, pDstSamples += iDstStride )
550  {
551    for( Int iX = 0; iX < iWidth; iX++ )
552    {
553      Int iOrgDepth     = ( pSrcSamples[ iX ] != PDM_UNDEFINED_DEPTH ? xGetOrigDepthFromVirtDepth( uiViewId, pSrcSamples[ iX ] ) : iMidOrgDpth );
554      pDstSamples[ iX ] = Max( 0, Min( iMax, iOrgDepth ) );
555    }
556  }
557
558  // output
559  Char  acFilename[1024];
560  ::sprintf     ( acFilename, "%s_V%d.yuv", pFilenameBase, uiViewId );
561  m_cTmpPic.dump( acFilename, ( pcPic->getPOC() != 0 )  );
562}
563
564#endif //!H3D_NBDV
565
566#if H3D_IVMP
567Void 
568TComDepthMapGenerator::covertOrgDepthMap( TComPic* pcPic )
569{
570  AOF  ( m_bCreated && m_bInit   );
571  AOF  ( pcPic );
572  ROFVS( pcPic->getOrgDepthMap() );
573  AOF  ( pcPic->getViewId() );
574
575  UInt  uiBaseId = pcPic->getViewId();
576  Int   iWidth   = pcPic->getOrgDepthMap()->getWidth    ();
577  Int   iHeight  = pcPic->getOrgDepthMap()->getHeight   ();
578  Int   iStride  = pcPic->getOrgDepthMap()->getStride   ();
579  Pel*  pSamples = pcPic->getOrgDepthMap()->getLumaAddr ( 0 );
580  for( Int iY = 0; iY < iHeight; iY++, pSamples += iStride )
581  {
582    for( Int iX = 0; iX < iWidth; iX++ )
583    {
584      pSamples[ iX ] = xGetVirtDepthFromOrigDepth( uiBaseId, pSamples[ iX ] );
585    }
586  }
587}
588#endif
589
590Int
591TComDepthMapGenerator::getDisparity( TComPic* pcPic, Int iPosX, Int iPosY, UInt uiRefViewId )
592{
593  AOF( pcPic );
594  AOF( pcPic->getPredDepthMap() );
595  AOF( iPosX >= 0 && iPosX < pcPic->getPredDepthMap()->getWidth () );
596  AOF( iPosY >= 0 && iPosY < pcPic->getPredDepthMap()->getHeight() );
597  Pel*   piPdmMap    = pcPic->getPredDepthMap()->getLumaAddr( 0 );
598  Int    iStride     = pcPic->getPredDepthMap()->getStride  ();
599  Int    iPrdDepth   = piPdmMap[ iPosX + iPosY * iStride ];
600  Int    iDisparity  = xGetDisparityFromVirtDepth( uiRefViewId, iPrdDepth );
601  return iDisparity;
602}
603
604
605
606#if H3D_IVMP
607#if QC_AMVP_MRG_UNIFY_IVCAN_C0051
608Bool
609TComDepthMapGenerator::getPdmCandidate(TComDataCU* pcCU, UInt uiPartIdx, RefPicList eRefPicList, Int iRefIdx, Int* paiPdmRefIdx, TComMv* pacPdmMv, DisInfo* pDInfo, Int* iPdm, Bool bMerge )
610{
611  AOF  ( m_bCreated && m_bInit );
612  TComSlice*    pcSlice     = pcCU->getSlice ();
613  TComSPS*      pcSPS       = pcSlice->getSPS();
614  AOF  ( pcSPS->getViewId() == m_uiCurrViewId );
615
616  TComPic*      pcRefPic    = pcSlice->getRefPic( eRefPicList, iRefIdx );
617  UInt          uiRefViewId = pcRefPic->getSPS()->getViewId();
618  Bool          bInterview  = ( uiRefViewId < m_uiCurrViewId );
619  Bool          bPdmIView   = ( ( pcSPS->getMultiviewMvPredMode() & PDM_USE_FOR_IVIEW ) == PDM_USE_FOR_IVIEW );
620  Bool          bPdmInter   = ( ( pcSPS->getMultiviewMvPredMode() & PDM_USE_FOR_INTER ) == PDM_USE_FOR_INTER );
621  Bool          bPdmMerge   = ( ( pcSPS->getMultiviewMvPredMode() & PDM_USE_FOR_MERGE ) == PDM_USE_FOR_MERGE );
622  if(!bMerge)
623  {
624    ROTRS( ( bInterview && !bMerge ) && !bPdmIView, false );
625    ROTRS( (!bInterview && !bMerge ) && !bPdmInter, false );
626    ROTRS(                  bMerge   && !bPdmMerge, false );
627  }
628  else
629    ROTRS( !bPdmMerge, 0 );
630
631
632  Bool abPdmAvailable[4] = {false, false, false, false};
633
634  Int iValid = 0;
635  Int iViewId = 0;
636  for( UInt uiBId = 0; uiBId < m_uiCurrViewId && iValid==0; uiBId++ )
637  {
638#if MTK_C0138_FIXED
639    UInt        uiBaseId    = uiBId;
640#else
641    UInt        uiBaseId    = m_auiBaseIdList[ uiBId ];
642#endif
643    TComPic*    pcBasePic   = m_pcAUPicAccess->getPic( uiBaseId );
644    for( Int iRefListId = 0; iRefListId < 2 && iValid==0; iRefListId++ )
645    {
646      RefPicList  eRefPicListTest = RefPicList( iRefListId );
647      Int         iNumRefPics = pcSlice->getNumRefIdx( eRefPicListTest ) ;
648      for( Int iRefIndex = 0; iRefIndex < iNumRefPics; iRefIndex++ )
649      { 
650        if(pcBasePic->getPOC() == pcSlice->getRefPic( eRefPicListTest, iRefIndex )->getPOC() 
651          && pcBasePic->getViewId() == pcSlice->getRefPic( eRefPicListTest, iRefIndex )->getViewId())
652        {
653          iValid=1;
654          iViewId = uiBaseId;
655          break;
656        }
657      }
658    }
659  }
660  if (iValid == 0)
661    return false;
662
663  //--- get base CU/PU and check prediction mode ---
664  TComPic*    pcBasePic   = m_pcAUPicAccess->getPic( iViewId );
665  TComPicYuv* pcBaseRec   = pcBasePic->getPicYuvRec   ();
666  if(bMerge || !bInterview)
667  {
668#if H3D_NBDV
669    Int  iCurrPosX, iCurrPosY;
670    UInt          uiPartAddr;
671    Int           iWidth;
672    Int           iHeight;
673
674    pcCU->getPartIndexAndSize( uiPartIdx, uiPartAddr, iWidth, iHeight );
675    pcBaseRec->getTopLeftSamplePos( pcCU->getAddr(), pcCU->getZorderIdxInCU() + uiPartAddr, iCurrPosX, iCurrPosY );
676    iCurrPosX  += ( ( iWidth  - 1 ) >> 1 );
677    iCurrPosY  += ( ( iHeight - 1 ) >> 1 );
678
679    Int         iBasePosX   = Clip3( 0, pcBaseRec->getWidth () - 1, iCurrPosX + ( (pDInfo->m_acMvCand[0].getHor() + 2 ) >> 2 ) );
680    Int         iBasePosY   = Clip3( 0, pcBaseRec->getHeight() - 1, iCurrPosY + ( (pDInfo->m_acMvCand[0].getVer() + 2 ) >> 2 )); 
681    Int         iBaseCUAddr;
682    Int         iBaseAbsPartIdx;
683    pcBaseRec->getCUAddrAndPartIdx( iBasePosX , iBasePosY , iBaseCUAddr, iBaseAbsPartIdx );
684#else //H3D_NBDV
685    Int  iPrdDepth, iCurrPosX, iCurrPosY;
686    Bool bAvailable  = xGetPredDepth( pcCU, uiPartIdx, iPrdDepth, &iCurrPosX, &iCurrPosY );
687    AOF( bAvailable );
688    TComPicYuv* pcBasePdm   = pcBasePic->getPredDepthMap();
689    Int         iDisparity  = xGetDisparityFromVirtDepth( iViewId, iPrdDepth );
690    Int         iShiftX     = m_uiSubSampExpX + 2;
691    Int         iAddX       = ( 1 << iShiftX ) >> 1;
692    Int         iBasePosX   = Clip3( 0, pcBasePdm->getWidth () - 1, iCurrPosX + ( ( iDisparity + iAddX ) >> iShiftX ) );
693    Int         iBasePosY   = Clip3( 0, pcBasePdm->getHeight() - 1, iCurrPosY                               );
694    Int         iBaseCUAddr;
695    Int         iBaseAbsPartIdx;
696    pcBaseRec->getCUAddrAndPartIdx( iBasePosX<< m_uiSubSampExpX , iBasePosY<< m_uiSubSampExpY , iBaseCUAddr, iBaseAbsPartIdx );
697#endif // H3D_NBDV
698    TComDataCU* pcBaseCU    = pcBasePic->getCU( iBaseCUAddr );
699    if( pcBaseCU->getPredictionMode( iBaseAbsPartIdx ) == MODE_INTER || pcBaseCU->getPredictionMode( iBaseAbsPartIdx ) == MODE_SKIP )
700    {
701      for( UInt uiCurrRefListId = 0; uiCurrRefListId < 2; uiCurrRefListId++ )
702      {
703        RefPicList  eCurrRefPicList = RefPicList( uiCurrRefListId );
704        if(!bMerge && eCurrRefPicList != eRefPicList)
705          continue;
706        Bool bLoop_stop = false;
707        for(Int iLoop = 0; iLoop < 2 && !bLoop_stop; ++iLoop)
708        {
709          RefPicList eBaseRefPicList = (iLoop ==1)? RefPicList( 1 -  uiCurrRefListId ) : RefPicList( uiCurrRefListId );
710          TComMvField cBaseMvField;
711          pcBaseCU->getMvField( pcBaseCU, iBaseAbsPartIdx, eBaseRefPicList, cBaseMvField );
712          Int         iBaseRefIdx     = cBaseMvField.getRefIdx();
713          if (iBaseRefIdx >= 0)
714          {
715            Int iBaseRefPOC = pcBaseCU->getSlice()->getRefPOC(eBaseRefPicList, iBaseRefIdx);
716            if (iBaseRefPOC != pcSlice->getPOC())   
717            {
718              for (Int iPdmRefIdx = (bMerge?0: iRefIdx); iPdmRefIdx < (bMerge? pcSlice->getNumRefIdx( eCurrRefPicList ): (iRefIdx+1)); iPdmRefIdx++)
719              {
720                if (iBaseRefPOC == pcSlice->getRefPOC(eCurrRefPicList, iPdmRefIdx))
721                {
722                  abPdmAvailable[ uiCurrRefListId ] = true;
723                  TComMv cMv(cBaseMvField.getHor(), cBaseMvField.getVer());
724#if H3D_NBDV
725                  if( bMerge )
726                  {
727                    cMv.m_bDvMcp = true;
728                    cMv.m_iDvMcpDispX = pDInfo->m_acMvCand[0].getHor();
729                  }
730#endif
731                  pcCU->clipMv( cMv );
732                  if(bMerge)
733                  {
734                    paiPdmRefIdx  [ uiCurrRefListId ] = iPdmRefIdx;
735                    pacPdmMv      [ uiCurrRefListId ] = cMv;
736                    bLoop_stop = true;
737                    break;
738                  }else
739                  {
740                    pacPdmMv  [0] = cMv;
741                    return true;
742                  }
743                }
744              }
745            }
746          }
747        }
748      }
749    }
750    if( bMerge )
751      iPdm[0] = ( abPdmAvailable[0] ? 1 : 0 ) + ( abPdmAvailable[1] ? 2 : 0 );
752  }
753  if(bMerge || bInterview)
754  {
755    for( Int iRefListId = 0; iRefListId < 2 ; iRefListId++ )
756    {
757      RefPicList  eRefPicListDMV       = RefPicList( iRefListId );
758      Int         iNumRefPics       = pcSlice->getNumRefIdx( eRefPicListDMV );
759      for( Int iPdmRefIdx = (bMerge ? 0: iRefIdx); iPdmRefIdx < (bMerge ? iNumRefPics: (iRefIdx+1) ); iPdmRefIdx++ )
760      {
761        if( pcSlice->getRefPOC( eRefPicListDMV, iPdmRefIdx ) == pcSlice->getPOC())
762        {
763          abPdmAvailable[ iRefListId+2 ] = true;
764          paiPdmRefIdx  [ iRefListId+2 ] = iPdmRefIdx;
765#if H3D_NBDV
766          TComMv cMv = pDInfo->m_acMvCand[0]; 
767          cMv.setVer(0);
768#else
769          TComMv cMv(iDisparity, 0);
770#endif
771          pcCU->clipMv( cMv );
772          pacPdmMv      [ iRefListId + 2] = cMv;
773          if(bMerge)
774            break;
775          else
776          {
777            pacPdmMv [0] = cMv;
778            return true;
779          }
780        }
781      }
782    }
783    iPdm[1] = ( abPdmAvailable[2] ? 1 : 0 ) + ( abPdmAvailable[3] ? 2 : 0 );
784  }
785  return false;
786}
787#else // QC_AMVP_MRG_UNIFY_IVCAN_C0051
788#if H3D_NBDV
789Int
790TComDepthMapGenerator::getPdmMergeCandidate( TComDataCU* pcCU, UInt uiPartIdx, Int* paiPdmRefIdx, TComMv* pacPdmMv, DisInfo* pDInfo, Int* iPdm )
791#else
792Int
793TComDepthMapGenerator::getPdmMergeCandidate( TComDataCU* pcCU, UInt uiPartIdx, Int* paiPdmRefIdx, TComMv* pacPdmMv )
794#endif
795{
796  AOF  ( m_bCreated && m_bInit );
797
798#if !H3D_NBDV
799  ROFRS( m_bPDMAvailable, 0 );
800#endif
801
802  TComSlice*    pcSlice     = pcCU->getSlice ();
803  TComSPS*      pcSPS       = pcSlice->getSPS();
804  AOF  ( pcSPS->getViewId() == m_uiCurrViewId );
805  Bool          bPdmMerge   = ( ( pcSPS->getMultiviewMvPredMode() & PDM_USE_FOR_MERGE ) == PDM_USE_FOR_MERGE );
806  ROTRS( !bPdmMerge, 0 );
807
808  Bool abPdmAvailable[4] = {false, false, false, false};
809
810  Int iValid = 0;
811  Int iViewId = 0;
812  for( UInt uiBId = 0; uiBId < m_uiCurrViewId && iValid==0; uiBId++ )
813  {
814    UInt        uiBaseId    = m_auiBaseIdList[ uiBId ];
815    TComPic*    pcBasePic   = m_pcAUPicAccess->getPic( uiBaseId );
816    for( Int iRefListId = 0; iRefListId < 2 && iValid==0; iRefListId++ )
817    {
818      RefPicList  eRefPicListTest = RefPicList( iRefListId );
819      Int         iNumRefPics = pcSlice->getNumRefIdx( eRefPicListTest ) ;
820      for( Int iRefIndex = 0; iRefIndex < iNumRefPics; iRefIndex++ )
821      { 
822        if(pcBasePic->getPOC() == pcSlice->getRefPic( eRefPicListTest, iRefIndex )->getPOC() 
823          && pcBasePic->getViewId() == pcSlice->getRefPic( eRefPicListTest, iRefIndex )->getViewId())
824        {
825          iValid=1;
826          iViewId = uiBaseId;
827          break;
828        }
829      }
830    }
831  }
832  if (iValid == 0)
833    return 0;
834
835  //--- get base CU/PU and check prediction mode ---
836  TComPic*    pcBasePic   = m_pcAUPicAccess->getPic( iViewId );
837  TComPicYuv* pcBaseRec   = pcBasePic->getPicYuvRec   ();
838
839#if H3D_NBDV
840  Int  iCurrPosX, iCurrPosY;
841  UInt          uiPartAddr;
842  Int           iWidth;
843  Int           iHeight;
844
845  pcCU->getPartIndexAndSize( uiPartIdx, uiPartAddr, iWidth, iHeight );
846  pcBaseRec->getTopLeftSamplePos( pcCU->getAddr(), pcCU->getZorderIdxInCU() + uiPartAddr, iCurrPosX, iCurrPosY );
847  iCurrPosX  += ( ( iWidth  - 1 ) >> 1 );
848  iCurrPosY  += ( ( iHeight - 1 ) >> 1 );
849
850  Int         iBasePosX   = Clip3( 0, pcBaseRec->getWidth () - 1, iCurrPosX + ( (pDInfo->m_acMvCand[0].getHor() + 2 ) >> 2 ) );
851  Int         iBasePosY   = Clip3( 0, pcBaseRec->getHeight() - 1, iCurrPosY + ( (pDInfo->m_acMvCand[0].getVer() + 2 ) >> 2 )); 
852  Int         iBaseCUAddr;
853  Int         iBaseAbsPartIdx;
854  pcBaseRec->getCUAddrAndPartIdx( iBasePosX , iBasePosY , iBaseCUAddr, iBaseAbsPartIdx );
855#else
856  Int  iPrdDepth, iCurrPosX, iCurrPosY;
857  Bool bAvailable  = xGetPredDepth( pcCU, uiPartIdx, iPrdDepth, &iCurrPosX, &iCurrPosY );
858  AOF( bAvailable );
859  TComPicYuv* pcBasePdm   = pcBasePic->getPredDepthMap();
860  Int         iDisparity  = xGetDisparityFromVirtDepth( iViewId, iPrdDepth );
861  Int         iShiftX     = m_uiSubSampExpX + 2;
862  Int         iAddX       = ( 1 << iShiftX ) >> 1;
863  Int         iBasePosX   = Clip3( 0, pcBasePdm->getWidth () - 1, iCurrPosX + ( ( iDisparity + iAddX ) >> iShiftX ) );
864  Int         iBasePosY   = Clip3( 0, pcBasePdm->getHeight() - 1, iCurrPosY                               );
865  Int         iBaseCUAddr;
866  Int         iBaseAbsPartIdx;
867  pcBaseRec->getCUAddrAndPartIdx( iBasePosX<< m_uiSubSampExpX , iBasePosY<< m_uiSubSampExpY , iBaseCUAddr, iBaseAbsPartIdx );
868#endif
869
870  TComDataCU* pcBaseCU    = pcBasePic->getCU( iBaseCUAddr );
871
872  if( pcBaseCU->getPredictionMode( iBaseAbsPartIdx ) == MODE_INTER || pcBaseCU->getPredictionMode( iBaseAbsPartIdx ) == MODE_SKIP )
873  {
874    for( UInt uiBaseRefListId = 0; uiBaseRefListId < 2; uiBaseRefListId++ )
875    {
876      RefPicList  eBaseRefPicList = RefPicList( uiBaseRefListId );
877      TComMvField cBaseMvField;
878      pcBaseCU->getMvField( pcBaseCU, iBaseAbsPartIdx, eBaseRefPicList, cBaseMvField );
879      Int         iBaseRefIdx     = cBaseMvField.getRefIdx();
880
881      if (iBaseRefIdx >= 0)
882      {
883        Int iBaseRefPOC = pcBaseCU->getSlice()->getRefPOC(eBaseRefPicList, iBaseRefIdx);
884        if (iBaseRefPOC != pcSlice->getPOC())   
885        {
886          for (Int iPdmRefIdx = 0; iPdmRefIdx < pcSlice->getNumRefIdx( eBaseRefPicList ); iPdmRefIdx++)
887          {
888            if (iBaseRefPOC == pcSlice->getRefPOC(eBaseRefPicList, iPdmRefIdx))
889            {
890              abPdmAvailable[ uiBaseRefListId ] = true;
891              paiPdmRefIdx  [ uiBaseRefListId ] = iPdmRefIdx;
892              TComMv cMv(cBaseMvField.getHor(), cBaseMvField.getVer());
893#if H3D_NBDV
894              cMv.m_bDvMcp = true;
895              cMv.m_iDvMcpDispX = pDInfo->m_acMvCand[0].getHor();
896#if MTK_RELEASE_DV_CONSTRAINT_C0129
897              cMv.m_iDvMcpDispY = pDInfo->m_acMvCand[0].getVer();
898#endif
899#endif //H3D_NBDV
900              pcCU->clipMv( cMv );
901              pacPdmMv      [ uiBaseRefListId ] = cMv;
902              break;
903            }
904          }
905        }
906      }
907    }
908  }
909  Int iPdmInterDir = ( abPdmAvailable[0] ? 1 : 0 ) + ( abPdmAvailable[1] ? 2 : 0 );
910
911  iPdm[0] = iPdmInterDir;
912    for( Int iRefListId = 0; iRefListId < 2 ; iRefListId++ )
913    {
914      RefPicList  eRefPicList       = RefPicList( iRefListId );
915      Int         iNumRefPics       = pcSlice->getNumRefIdx( eRefPicList );
916      for( Int iPdmRefIdx = 0; iPdmRefIdx < iNumRefPics; iPdmRefIdx++ )
917      {
918        if( pcSlice->getRefPOC( eRefPicList, iPdmRefIdx ) == pcSlice->getPOC())
919        {
920          abPdmAvailable[ iRefListId+2 ] = true;
921          paiPdmRefIdx  [ iRefListId+2 ] = iPdmRefIdx;
922#if H3D_NBDV
923          TComMv cMv = pDInfo->m_acMvCand[0]; 
924          cMv.setVer(0);
925#else
926          TComMv cMv(iDisparity, 0);
927#endif
928          pcCU->clipMv( cMv );
929          pacPdmMv      [ iRefListId + 2] = cMv;
930          break;
931        }
932      }
933    }
934    iPdmInterDir = ( abPdmAvailable[2] ? 1 : 0 ) + ( abPdmAvailable[3] ? 2 : 0 ) ;
935    iPdm[1] = iPdmInterDir;
936
937  return iPdmInterDir;
938}
939
940#if H3D_NBDV
941Bool
942TComDepthMapGenerator::getDisCanPdmMvPred    ( TComDataCU*   pcCU, UInt uiPartIdx, RefPicList eRefPicList, Int iRefIdx, TComMv& rcMv, DisInfo* pDInfo, Bool bMerge )
943{
944  rcMv.m_bDvMcp = false;
945  AOF  ( m_bCreated && m_bInit );
946  AOF  ( iRefIdx >= 0 );
947  AOF  ( pcCU );
948  TComSlice*    pcSlice     = pcCU->getSlice ();
949  TComSPS*      pcSPS       = pcSlice->getSPS();
950  AOF  ( pcSPS->getViewId() == m_uiCurrViewId );
951  TComPic*      pcRefPic    = pcSlice->getRefPic( eRefPicList, iRefIdx );
952  UInt          uiRefViewId = pcRefPic->getSPS()->getViewId();
953  Int           iRefPoc     = pcRefPic->getPOC();
954  Bool          bInterview  = ( uiRefViewId < m_uiCurrViewId );
955  AOT(  bInterview && iRefPoc != pcSlice->getPOC() );
956  AOT( !bInterview && iRefPoc == pcSlice->getPOC() );
957  Bool          bPdmIView   = ( ( pcSPS->getMultiviewMvPredMode() & PDM_USE_FOR_IVIEW ) == PDM_USE_FOR_IVIEW );
958  Bool          bPdmInter   = ( ( pcSPS->getMultiviewMvPredMode() & PDM_USE_FOR_INTER ) == PDM_USE_FOR_INTER );
959  Bool          bPdmMerge   = ( ( pcSPS->getMultiviewMvPredMode() & PDM_USE_FOR_MERGE ) == PDM_USE_FOR_MERGE );
960  ROTRS( ( bInterview && !bMerge ) && !bPdmIView, false );
961  ROTRS( (!bInterview && !bMerge ) && !bPdmInter, false );
962  ROTRS(                  bMerge   && !bPdmMerge, false );
963  Int  iCurrPosX, iCurrPosY;
964  TComMv cDisMv;
965
966  if( bInterview )
967  {
968    rcMv = pDInfo->m_acMvCand[0]; 
969    rcMv.setVer(0);
970    return      true;
971  }
972  for( UInt uiBId = 0; uiBId < m_uiCurrViewId; uiBId++ )
973  {
974    UInt        uiBaseId    = uiBId; 
975
976    if (m_uiCurrViewId >1 && uiBaseId ==1 ) 
977      continue;
978
979    TComPic*    pcBasePic   = m_pcAUPicAccess->getPic( uiBaseId );
980    TComPicYuv* pcBaseRec   = pcBasePic->getPicYuvRec   ();
981    UInt          uiPartAddr;
982    Int           iWidth;
983    Int           iHeight;
984
985    pcCU->getPartIndexAndSize( uiPartIdx, uiPartAddr, iWidth, iHeight );
986    pcBaseRec->getTopLeftSamplePos( pcCU->getAddr(), pcCU->getZorderIdxInCU() + uiPartAddr, iCurrPosX, iCurrPosY );
987    iCurrPosX  += ( ( iWidth  - 1 ) >> 1 );
988    iCurrPosY  += ( ( iHeight - 1 ) >> 1 );
989    Int         iBasePosX   = Clip3( 0, pcBaseRec->getWidth () - 1, iCurrPosX + ( (pDInfo->m_acMvCand[0].getHor() + 2 ) >> 2 ) );
990    Int         iBasePosY   = Clip3( 0, pcBaseRec->getHeight() - 1, iCurrPosY + ( (pDInfo->m_acMvCand[0].getVer() + 2 ) >> 2 )); 
991    Int         iBaseCUAddr;
992    Int         iBaseAbsPartIdx;
993    pcBaseRec->getCUAddrAndPartIdx( iBasePosX , iBasePosY , iBaseCUAddr, iBaseAbsPartIdx );
994    TComDataCU* pcBaseCU    = pcBasePic->getCU( iBaseCUAddr );
995    if( pcBaseCU->getPredictionMode( iBaseAbsPartIdx ) != MODE_INTER && pcBaseCU->getPredictionMode( iBaseAbsPartIdx ) != MODE_SKIP )
996    {
997      continue;
998    }
999    for( UInt uiBaseRefListId = 0; uiBaseRefListId < 2; uiBaseRefListId++ )
1000    {
1001      RefPicList  eBaseRefPicList = RefPicList( uiBaseRefListId );
1002      TComMvField cBaseMvField;
1003      pcBaseCU->getMvField( pcBaseCU, iBaseAbsPartIdx, eBaseRefPicList, cBaseMvField );
1004      Int         iBaseRefIdx     = cBaseMvField.getRefIdx();
1005      Int         iBaseRefPoc     = ( iBaseRefIdx >= 0 ? pcBaseCU->getSlice()->getRefPic( eBaseRefPicList, iBaseRefIdx )->getPOC() : -(1<<30) );
1006      if( iBaseRefIdx >= 0 && iBaseRefPoc == iRefPoc )
1007      {
1008        rcMv.set( cBaseMvField.getHor(), cBaseMvField.getVer() );
1009        // save disparity vector when a merge candidate for IVMP is set as DV-MCP
1010        if( bMerge ) 
1011        {
1012          rcMv.m_bDvMcp = true;
1013          rcMv.m_iDvMcpDispX = pDInfo->m_acMvCand[0].getHor(); 
1014#if MTK_RELEASE_DV_CONSTRAINT_C0129
1015          rcMv.m_iDvMcpDispY = pDInfo->m_acMvCand[0].getVer();
1016#endif
1017        }
1018        else { // AMVP ?
1019          rcMv.m_bDvMcp = false;
1020        }
1021        return true;
1022      }
1023    }
1024  }
1025  return false;
1026}
1027#else // H3D_NBDV
1028Bool 
1029TComDepthMapGenerator::getPdmMvPred( TComDataCU* pcCU, UInt uiPartIdx, RefPicList eRefPicList, Int iRefIdx, TComMv& rcMv, Bool bMerge )
1030{
1031  AOF  ( m_bCreated && m_bInit );
1032  AOF  ( iRefIdx >= 0 );
1033  AOF  ( pcCU );
1034  ROFRS( m_bPDMAvailable, false );
1035
1036  TComSlice*    pcSlice     = pcCU->getSlice ();
1037  TComPic*      pcPic       = pcCU->getPic   ();
1038  TComSPS*      pcSPS       = pcSlice->getSPS();
1039  AOF  ( pcPic->getPredDepthMap() );
1040  AOF  ( pcSPS->getViewId() == m_uiCurrViewId );
1041 
1042  TComPic*      pcRefPic    = pcSlice->getRefPic( eRefPicList, iRefIdx );
1043  UInt          uiRefViewId = pcRefPic->getSPS()->getViewId();
1044  Int           iRefPoc     = pcRefPic->getPOC();
1045  Bool          bInterview  = ( uiRefViewId < m_uiCurrViewId );
1046  AOT(  bInterview && iRefPoc != pcSlice->getPOC() );
1047  AOT( !bInterview && iRefPoc == pcSlice->getPOC() );
1048
1049  Bool          bPdmIView   = ( ( pcSPS->getMultiviewMvPredMode() & PDM_USE_FOR_IVIEW ) == PDM_USE_FOR_IVIEW );
1050  Bool          bPdmInter   = ( ( pcSPS->getMultiviewMvPredMode() & PDM_USE_FOR_INTER ) == PDM_USE_FOR_INTER );
1051  Bool          bPdmMerge   = ( ( pcSPS->getMultiviewMvPredMode() & PDM_USE_FOR_MERGE ) == PDM_USE_FOR_MERGE );
1052  ROTRS( ( bInterview && !bMerge ) && !bPdmIView, false );
1053  ROTRS( (!bInterview && !bMerge ) && !bPdmInter, false );
1054  ROTRS(                  bMerge   && !bPdmMerge, false );
1055
1056  //===== get predicted depth for middle position of current PU ===== 
1057  Int  iPrdDepth, iCurrPosX, iCurrPosY;
1058  Bool bAvailable  = xGetPredDepth( pcCU, uiPartIdx, iPrdDepth, &iCurrPosX, &iCurrPosY );
1059  AOF( bAvailable );
1060 
1061  //===== inter-view motion vector prediction =====
1062  if( bInterview )
1063  {
1064    Int         iDisparity  = xGetDisparityFromVirtDepth( uiRefViewId, iPrdDepth );
1065    rcMv.set  ( iDisparity, 0 );
1066    return      true;
1067  }
1068 
1069  //===== inter motion vector prediction =====
1070  for( UInt uiBId = 0; uiBId < m_uiCurrViewId; uiBId++ )
1071  {
1072    //--- get base CU/PU and check prediction mode ---
1073    UInt        uiBaseId    = m_auiBaseIdList[ uiBId ];
1074#if PDM_REMOVE_DEPENDENCE
1075    if( uiBaseId != 0)
1076      continue;
1077#endif
1078    TComPic*    pcBasePic   = m_pcAUPicAccess->getPic( uiBaseId );
1079    TComPicYuv* pcBasePdm   = pcBasePic->getPredDepthMap();
1080    TComPicYuv* pcBaseRec   = pcBasePic->getPicYuvRec   ();
1081    Int         iDisparity  = xGetDisparityFromVirtDepth( uiBaseId, iPrdDepth );
1082    Int         iShiftX     = m_uiSubSampExpX + 2;
1083    Int         iAddX       = ( 1 << iShiftX ) >> 1;
1084    Int         iBasePosX   = Clip3( 0, pcBasePdm->getWidth () - 1, iCurrPosX + ( ( iDisparity + iAddX ) >> iShiftX ) );
1085    Int         iBasePosY   = Clip3( 0, pcBasePdm->getHeight() - 1, iCurrPosY                               );
1086    Int         iBaseCUAddr;
1087    Int         iBaseAbsPartIdx;
1088    pcBaseRec->getCUAddrAndPartIdx( iBasePosX << m_uiSubSampExpX, iBasePosY << m_uiSubSampExpY, iBaseCUAddr, iBaseAbsPartIdx );
1089    TComDataCU* pcBaseCU    = pcBasePic->getCU( iBaseCUAddr );
1090    if( pcBaseCU->getPredictionMode( iBaseAbsPartIdx ) != MODE_INTER && pcBaseCU->getPredictionMode( iBaseAbsPartIdx ) != MODE_SKIP )
1091    {
1092      continue;
1093    }
1094
1095    for( UInt uiBaseRefListId = 0; uiBaseRefListId < 2; uiBaseRefListId++ )
1096    {
1097      RefPicList  eBaseRefPicList = RefPicList( uiBaseRefListId );
1098      TComMvField cBaseMvField;
1099      pcBaseCU->getMvField( pcBaseCU, iBaseAbsPartIdx, eBaseRefPicList, cBaseMvField );
1100      Int         iBaseRefIdx     = cBaseMvField.getRefIdx();
1101      Int         iBaseRefPoc     = ( iBaseRefIdx >= 0 ? pcBaseCU->getSlice()->getRefPic( eBaseRefPicList, iBaseRefIdx )->getPOC() : -(1<<30) );
1102      if( iBaseRefIdx >= 0 && iBaseRefPoc == iRefPoc )
1103      {
1104        rcMv.set( cBaseMvField.getHor(), cBaseMvField.getVer() );
1105        return true;
1106      }
1107    }
1108  }
1109  return false;
1110}
1111#endif // H3D_NBDV
1112#endif // QC_AMVP_MRG_UNIFY_IVCAN_C0051
1113
1114
1115Bool  // first version
1116TComDepthMapGenerator::getIViewOrgDepthMvPred( TComDataCU* pcCU, UInt uiPartIdx, RefPicList eRefPicList, Int iRefIdx, TComMv& rcMv )
1117{
1118  AOF  ( m_bCreated && m_bInit );
1119  AOF  ( iRefIdx >= 0 );
1120  AOF  ( pcCU );
1121
1122  TComSlice*    pcSlice     = pcCU->getSlice ();
1123  TComPic*      pcPic       = pcCU->getPic   ();
1124  TComSPS*      pcSPS       = pcSlice->getSPS();
1125  AOF  ( pcSPS->getViewId() == m_uiCurrViewId );
1126  ROFRS( pcPic->getOrgDepthMap(),      false );
1127 
1128  TComPic*      pcRefPic    = pcSlice->getRefPic( eRefPicList, iRefIdx );
1129  UInt          uiRefViewId = pcRefPic->getSPS()->getViewId();
1130  Int           iRefPoc     = pcRefPic->getPOC();
1131  ROFRS( uiRefViewId < m_uiCurrViewId, false );
1132  AOF  ( iRefPoc    == pcSlice->getPOC() );
1133
1134  //===== get predicted depth for middle position of current PU (first version) ===== 
1135  UInt          uiPartAddr;
1136  Int           iWidth;
1137  Int           iHeight;
1138  pcCU->getPartIndexAndSize( uiPartIdx, uiPartAddr, iWidth, iHeight );
1139  TComPicYuv*   pcOrgDepthMap  = pcPic->getOrgDepthMap();
1140  Pel*          piOrgDepthMap  = pcOrgDepthMap->getLumaAddr ( 0 );
1141  Int           iCurrStride    = pcOrgDepthMap->getStride   ();
1142  Int           iCurrPosX;
1143  Int           iCurrPosY;
1144  pcOrgDepthMap->getTopLeftSamplePos( pcCU->getAddr(), pcCU->getZorderIdxInCU() + uiPartAddr, iCurrPosX, iCurrPosY );
1145  iCurrPosX                    += ( iWidth  - 1 ) >> 1;
1146  iCurrPosY                    += ( iHeight - 1 ) >> 1;
1147  Int           iPrdDepth       = piOrgDepthMap[ iCurrPosX + iCurrPosY * iCurrStride ];
1148 
1149  //===== get disparity vector =====
1150  Int           iDisparity      = xGetDisparityFromVirtDepth( uiRefViewId, iPrdDepth );
1151  rcMv.set    ( iDisparity, 0 );
1152  return        true;
1153}
1154#endif //  H3D_IVMP
1155
1156
1157
1158
1159
1160#if !H3D_NBDV
1161/*=======================================================*
1162 *=====                                             =====*
1163 *=====     p i c t u r e   o p e r a t i o n s     =====*
1164 *=====                                             =====*
1165 *=======================================================*/
1166
1167Bool
1168TComDepthMapGenerator::xConvertDepthMapCurr2Ref( TComPic* pcRef, TComPic* pcCur )
1169{
1170  AOF( pcCur->getSPS()->getViewId() == m_uiCurrViewId );
1171  AOF( pcCur->getSPS()->getViewId()  > pcRef->getSPS()->getViewId() );
1172  AOF( pcCur->getPredDepthMap() );
1173  AOF( pcRef->getPredDepthMap() );
1174  AOF( pcRef->getPredDepthMap()->getWidth () == pcCur->getPredDepthMap()->getWidth () );
1175  AOF( pcRef->getPredDepthMap()->getHeight() == pcCur->getPredDepthMap()->getHeight() );
1176#if PDM_REMOVE_DEPENDENCE
1177  if( pcCur->getViewId() == 1)
1178    xClearDepthMap( pcRef );
1179  else if (pcCur->getViewId() == 2)
1180    xClearDepthMap( pcRef, PDM_UNDEFINED_DEPTH, 1 );
1181#else
1182  xClearDepthMap( pcRef );
1183#endif
1184  TComPicYuv* pcCurDepthMap =  pcCur->getPredDepthMap    ();
1185  TComPicYuv* pcRefDepthMap =  pcRef->getPredDepthMap    ();
1186  Int         iWidth        =  pcCurDepthMap->getWidth   ();
1187  Int         iHeight       =  pcCurDepthMap->getHeight  ();
1188  Int         iCurStride    =  pcCurDepthMap->getStride  ();
1189  Int         iRefStride    =  pcRefDepthMap->getStride  ();
1190  Pel*        pCurSamples   =  pcCurDepthMap->getLumaAddr( 0 );
1191  Pel*        pRefSamples   =  pcRefDepthMap->getLumaAddr( 0 );
1192  Int         iRefViewIdx   =  pcRef->getViewId();
1193#if PDM_REMOVE_DEPENDENCE
1194  if( pcCur->getViewId() == 2)
1195  {
1196    pcRefDepthMap =  pcRef->getPredDepthMapTemp();
1197    pRefSamples   =  pcRefDepthMap->getLumaAddr( 0 );
1198  }
1199#endif
1200  Int         iShiftX       = m_uiSubSampExpX + 2;
1201  Int         iAddX         = ( 1 << iShiftX ) >> 1;
1202  for( Int iY = 0; iY < iHeight; iY++, pCurSamples += iCurStride, pRefSamples += iRefStride )
1203  {
1204    for( Int iXCur = 0; iXCur < iWidth; iXCur++ )
1205    {
1206      Int iDepth = pCurSamples[ iXCur ];
1207      Int iDisp  = xGetDisparityFromVirtDepth( iRefViewIdx, iDepth );
1208      Int iXRef  = iXCur + ( ( iDisp + iAddX ) >> iShiftX );
1209      if( iXRef >= 0 && iXRef < iWidth && iDepth > pRefSamples[ iXRef ] )
1210      {
1211        pRefSamples[ iXRef ] = iDepth;
1212      }
1213    }
1214  }
1215  Bool    bUndefined = xFillDepthMapHoles( pcRef );
1216  pcRefDepthMap->setBorderExtension( false );
1217  pcRefDepthMap->extendPicBorder   ();
1218  return  bUndefined;
1219}
1220
1221
1222Bool
1223TComDepthMapGenerator::xConvertDepthMapRef2Curr( TComPic* pcCur, TComPic* pcRef )
1224{
1225  AOF( pcCur->getSPS()->getViewId() == m_uiCurrViewId );
1226  AOF( pcCur->getSPS()->getViewId()  > pcRef->getSPS()->getViewId() );
1227  AOF( pcCur->getPredDepthMap() );
1228#if PDM_REMOVE_DEPENDENCE
1229  if(pcCur->getViewId() == 1)
1230  {
1231    AOF( pcRef->getPredDepthMap() );
1232  }else
1233  {
1234    AOF( pcRef->getPredDepthMapTemp() );
1235  }
1236#else
1237  AOF( pcRef->getPredDepthMap() );
1238#endif
1239  AOF( pcRef->getPredDepthMap()->getWidth () == pcCur->getPredDepthMap()->getWidth () );
1240  AOF( pcRef->getPredDepthMap()->getHeight() == pcCur->getPredDepthMap()->getHeight() );
1241
1242  xClearDepthMap( pcCur );
1243  TComPicYuv* pcRefDepthMap =  pcRef->getPredDepthMap    ();
1244#if PDM_REMOVE_DEPENDENCE
1245  if(pcCur->getViewId() == 2)
1246    pcRefDepthMap =  pcRef->getPredDepthMapTemp        ();
1247#endif
1248  TComPicYuv* pcCurDepthMap =  pcCur->getPredDepthMap    ();
1249  Int         iWidth        =  pcRefDepthMap->getWidth   ();
1250  Int         iHeight       =  pcRefDepthMap->getHeight  ();
1251  Int         iRefStride    =  pcRefDepthMap->getStride  ();
1252  Int         iCurStride    =  pcCurDepthMap->getStride  ();
1253  Pel*        pRefSamples   =  pcRefDepthMap->getLumaAddr( 0 );
1254  Pel*        pCurSamples   =  pcCurDepthMap->getLumaAddr( 0 );
1255  Int         iRefViewIdx   =  pcRef->getViewId();
1256  Int         iShiftX       = m_uiSubSampExpX + 2;
1257  Int         iAddX         = ( 1 << iShiftX ) >> 1;
1258  for( Int iY = 0; iY < iHeight; iY++, pRefSamples += iRefStride, pCurSamples += iCurStride )
1259  {
1260    for( Int iXRef = 0; iXRef < iWidth; iXRef++ )
1261    {
1262      Int iDepth = pRefSamples[ iXRef ];
1263      Int iDisp  = xGetDisparityFromVirtDepth( iRefViewIdx, iDepth );
1264      Int iXCur  = iXRef - ( ( iDisp + iAddX ) >> iShiftX );
1265      if( iXCur >= 0 && iXCur < iWidth && iDepth > pCurSamples[ iXCur ] )
1266      {
1267        pCurSamples[ iXCur ] = iDepth;
1268      }
1269    }
1270  }
1271  Bool    bUndefined = xFillDepthMapHoles( pcCur );
1272  pcCurDepthMap->setBorderExtension( false );
1273  pcCurDepthMap->extendPicBorder   ();
1274  return  bUndefined;
1275}
1276
1277
1278Bool
1279TComDepthMapGenerator::xPredictDepthMap( TComPic* pcPic )
1280{
1281  for( UInt uiCUAddr = 0; uiCUAddr < pcPic->getPicSym()->getNumberOfCUsInFrame(); uiCUAddr++ )
1282  {
1283    TComDataCU* pcCU = pcPic->getCU( uiCUAddr );
1284    xPredictCUDepthMap( pcCU, 0, 0 );
1285  }
1286  Bool    bUndefined = xFillDepthMapHoles( pcPic );
1287#if PDM_REMOVE_DEPENDENCE
1288  if(pcPic->getStoredPDMforV2() == 1){
1289  pcPic->getPredDepthMapTemp()->setBorderExtension( false );
1290  pcPic->getPredDepthMapTemp()->extendPicBorder   ();
1291  }else{
1292#endif
1293  pcPic->getPredDepthMap()->setBorderExtension( false );
1294  pcPic->getPredDepthMap()->extendPicBorder   ();
1295#if PDM_REMOVE_DEPENDENCE
1296  }
1297#endif
1298  return  bUndefined;
1299}
1300
1301
1302Bool
1303TComDepthMapGenerator::xFillDepthMapHoles( TComPic* pcPic )
1304{
1305  Bool        bUndefined  = false;     
1306  TComPicYuv* pcDepthMap  = pcPic->getPredDepthMap  ();
1307#if PDM_REMOVE_DEPENDENCE
1308  if(pcPic->getViewId()==0 && pcPic->getStoredPDMforV2()==1)
1309    pcDepthMap  = pcPic->getPredDepthMapTemp  ();
1310#endif
1311  Int         iWidth      = pcDepthMap->getWidth    ();
1312  Int         iHeight     = pcDepthMap->getHeight   ();
1313  Int         iStride     = pcDepthMap->getStride   ();
1314  Pel*        pDMSamples  = pcDepthMap->getLumaAddr ( 0 );
1315  // horizontal
1316  for( Int iY = 0; iY < iHeight && !bUndefined; iY++, pDMSamples += iStride )
1317  {
1318    for( Int iX = 0; iX < iWidth; iX++ )
1319    {
1320      if( pDMSamples[ iX ] == PDM_UNDEFINED_DEPTH )
1321      {
1322        Int  iE;
1323        for( iE = iX + 1; iE < iWidth; iE++ )
1324        {
1325          if( pDMSamples[ iE ] != PDM_UNDEFINED_DEPTH )
1326          {
1327            break;
1328          }
1329        }
1330        if( iX > 0 || iE < iWidth )
1331        {
1332          Int iDepth;
1333          if     ( iX > 0 && iE < iWidth )  iDepth  = ( pDMSamples[ iX-1 ] < pDMSamples[ iE ] ? pDMSamples[ iX-1 ] : pDMSamples[ iE ] ); 
1334          else if( iX > 0 )                 iDepth  =   pDMSamples[ iX-1 ]; 
1335          else /*( iE < iWidth )*/          iDepth  =   pDMSamples[ iE   ]; 
1336          for( Int iZ = iX; iZ < iE; iZ++ )
1337          {
1338            pDMSamples[ iZ ] = iDepth;
1339          }
1340        }
1341        else
1342        {
1343          bUndefined = true;
1344          break;
1345        }
1346        iX = iE - 1;
1347      }
1348    }
1349  }
1350 
1351  if( bUndefined && m_uiCurrViewId )
1352  {
1353    pDMSamples          = pcDepthMap->getLumaAddr( 0 );
1354    Int  iMiddleOrgDpth = ( 1 << m_uiOrgDepthBitDepth ) >> 1;
1355    Int  iMiddleDepth   = xGetVirtDepthFromOrigDepth( m_uiCurrViewId, iMiddleOrgDpth );
1356    for( Int iY = 0; iY < iHeight; iY++, pDMSamples += iStride )
1357    {
1358      for( Int iX = 0; iX < iWidth; iX++ )
1359      {
1360        pDMSamples[ iX ] = iMiddleDepth;
1361       }
1362    }
1363  }
1364  return bUndefined;
1365}
1366
1367
1368Void
1369TComDepthMapGenerator::xClearDepthMap( TComPic* pcPic, Int iVal
1370#if PDM_REMOVE_DEPENDENCE
1371,
1372Int forFirstNonBaseView
1373#endif
1374)
1375{
1376  TComPicYuv* pcDepthMap  = pcPic->getPredDepthMap  ();
1377  Int         iWidth      = pcDepthMap->getWidth    ();
1378  Int         iHeight     = pcDepthMap->getHeight   ();
1379  Int         iStride     = pcDepthMap->getStride   ();
1380  Pel*        pDMSamples  = pcDepthMap->getLumaAddr ( 0 );
1381#if PDM_REMOVE_DEPENDENCE
1382  if( forFirstNonBaseView == 1)
1383  {
1384    pcDepthMap  = pcPic->getPredDepthMapTemp  ();
1385    pDMSamples  = pcDepthMap->getLumaAddr ( 0 );
1386  }
1387#endif
1388  for( Int iY = 0; iY < iHeight; iY++, pDMSamples += iStride )
1389  {
1390    for( Int iX = 0; iX < iWidth; iX++ )
1391    {
1392      pDMSamples[ iX ] = iVal;
1393    }
1394  }
1395  pcDepthMap->setBorderExtension( false );
1396  pcDepthMap->extendPicBorder   ();
1397}
1398
1399Void 
1400TComDepthMapGenerator::xSetChroma( TComPicYuv* pcPic, Int iVal )
1401{
1402  Int   iWidth      = pcPic->getWidth   () >> 1;
1403  Int   iHeight     = pcPic->getHeight  () >> 1;
1404  Int   iStride     = pcPic->getCStride ();
1405  Pel*  pCbSamples  = pcPic->getCbAddr  ( 0 );
1406  Pel*  pCrSamples  = pcPic->getCrAddr  ( 0 );
1407  for( Int iY = 0; iY < iHeight; iY++, pCbSamples += iStride, pCrSamples += iStride )
1408  {
1409    for( Int iX = 0; iX < iWidth; iX++ )
1410    {
1411      pCbSamples[ iX ] = pCrSamples[ iX ] = iVal;
1412    }
1413  }
1414}
1415
1416
1417
1418
1419
1420
1421
1422/*===============================================*
1423 *=====                                     =====*
1424 *=====     C U   p r e d i c t i o n s     =====*
1425 *=====                                     =====*
1426 *===============================================*/
1427
1428Void
1429TComDepthMapGenerator::xPredictCUDepthMap( TComDataCU* pcCU, UInt uiDepth, UInt uiAbsPartIdx )
1430{
1431  UInt  uiLPelX   = pcCU->getCUPelX() + g_auiRasterToPelX[ g_auiZscanToRaster[ uiAbsPartIdx ] ];
1432  UInt  uiTPelY   = pcCU->getCUPelY() + g_auiRasterToPelY[ g_auiZscanToRaster[ uiAbsPartIdx ] ];
1433  UInt  uiRPelX   = uiLPelX           + ( g_uiMaxCUWidth  >> uiDepth ) - 1;
1434  UInt  uiBPelY   = uiTPelY           + ( g_uiMaxCUHeight >> uiDepth ) - 1;
1435  Bool  bBoundary = ( uiRPelX >= pcCU->getSlice()->getSPS()->getPicWidthInLumaSamples() || uiBPelY >= pcCU->getSlice()->getSPS()->getPicHeightInLumaSamples() );
1436  Bool  bSplit    = ( ( uiDepth < pcCU->getDepth( uiAbsPartIdx ) && uiDepth < ( g_uiMaxCUDepth - g_uiAddCUDepth ) ) || bBoundary );
1437  if(   bSplit )
1438  {
1439    UInt uiQNumParts = ( pcCU->getPic()->getNumPartInCU() >> ( uiDepth << 1 ) ) >> 2;
1440    for ( UInt uiPartUnitIdx = 0; uiPartUnitIdx < 4; uiPartUnitIdx++, uiAbsPartIdx += uiQNumParts )
1441    {
1442      uiLPelX       = pcCU->getCUPelX() + g_auiRasterToPelX[ g_auiZscanToRaster[ uiAbsPartIdx ] ];
1443      uiTPelY       = pcCU->getCUPelY() + g_auiRasterToPelY[ g_auiZscanToRaster[ uiAbsPartIdx ] ];
1444      Bool  bInside = ( uiLPelX < pcCU->getSlice()->getSPS()->getPicWidthInLumaSamples() && uiTPelY < pcCU->getSlice()->getSPS()->getPicHeightInLumaSamples() );
1445      if(   bInside )
1446      {
1447        xPredictCUDepthMap( pcCU, uiDepth + 1, uiAbsPartIdx );
1448      }
1449    }
1450    return;
1451  }
1452
1453  //--- set sub-CU and sub-depth-map ---
1454  TComDataCU* pcSubCU   = m_ppcCU [ uiDepth ];
1455  TComYuv*    pcSubDM   = m_ppcYuv[ uiDepth ];
1456  TComPicYuv* pcPicDM   = pcCU->getPic()->getPredDepthMap();
1457#if PDM_REMOVE_DEPENDENCE
1458  if( pcCU->getPic()->getStoredPDMforV2() == 1)
1459    pcPicDM   = pcCU->getPic()->getPredDepthMapTemp();
1460#endif
1461  UInt        uiCUAddr  = pcCU->getAddr();
1462  pcSubCU->copySubCU( pcCU, uiAbsPartIdx, uiDepth );
1463
1464  //--- update depth map ---
1465  switch( pcSubCU->getPredictionMode( 0 ) )
1466  {
1467  case MODE_INTRA:
1468    xIntraPredictCUDepthMap( pcSubCU, pcSubDM );
1469    break;
1470  case MODE_SKIP:
1471  case MODE_INTER:
1472    xInterPredictCUDepthMap( pcSubCU, pcSubDM );
1473    break;
1474  default:
1475    AOT( true );
1476    break;
1477  }
1478
1479  //--- copy sub-depth-map ---
1480  pcSubDM->copyToPicYuv( pcPicDM, uiCUAddr, uiAbsPartIdx );
1481}
1482
1483
1484Void
1485TComDepthMapGenerator::xIntraPredictCUDepthMap( TComDataCU* pcCU, TComYuv* pcCUDepthMap )
1486{
1487  UInt  uiInitTrDepth = ( pcCU->getPartitionSize( 0 ) == SIZE_2Nx2N ? 0 : 1 );
1488  UInt  uiNumPart     =   pcCU->getNumPartInter ();
1489  UInt  uiNumQParts   =   pcCU->getTotalNumPart () >> 2;
1490  for( UInt uiPU = 0; uiPU < uiNumPart; uiPU++ )
1491  {
1492    xIntraPredictBlkDepthMap( pcCU, pcCUDepthMap, uiPU * uiNumQParts, uiInitTrDepth );
1493  }
1494}
1495
1496
1497Void
1498TComDepthMapGenerator::xInterPredictCUDepthMap( TComDataCU* pcCU, TComYuv* pcCUDepthMap )
1499{
1500  for( UInt uiPartIdx = 0; uiPartIdx < pcCU->getNumPartInter(); uiPartIdx++ )
1501  {
1502    xInterPredictPUDepthMap( pcCU, pcCUDepthMap, uiPartIdx );
1503  }
1504}
1505
1506
1507
1508
1509
1510
1511
1512/*=====================================================================*
1513 *=====                                                           =====*
1514 *=====     P U -   a n d   B l o c k   p r e d i c t i o n s     =====*
1515 *=====                                                           =====*
1516 *=====================================================================*/
1517
1518Void
1519TComDepthMapGenerator::xIntraPredictBlkDepthMap( TComDataCU* pcCU, TComYuv* pcCUDepthMap, UInt uiAbsPartIdx, UInt uiTrDepth )
1520{
1521  UInt uiFullDepth  = pcCU->getDepth( 0 ) + uiTrDepth;
1522  UInt uiTrMode     = pcCU->getTransformIdx( uiAbsPartIdx );
1523  if( uiTrMode == uiTrDepth )
1524  {
1525    UInt  uiWidth         = pcCU->getWidth ( 0 ) >> ( uiTrDepth + m_uiSubSampExpX );
1526    UInt  uiHeight        = pcCU->getHeight( 0 ) >> ( uiTrDepth + m_uiSubSampExpY );
1527    UInt  uiStride        = pcCUDepthMap->getStride  ();
1528    UInt  uiBlkX          = g_auiRasterToPelX[ g_auiZscanToRaster[ uiAbsPartIdx ] ] >> m_uiSubSampExpX;
1529    UInt  uiBlkY          = g_auiRasterToPelY[ g_auiZscanToRaster[ uiAbsPartIdx ] ] >> m_uiSubSampExpY;
1530    Pel*  pDepthMap       = pcCUDepthMap->getLumaAddr() + uiBlkY * pcCUDepthMap->getStride() + uiBlkX;
1531    UInt  uiLumaPredMode  = pcCU->getLumaIntraDir    ( uiAbsPartIdx );
1532    Bool  bAboveAvail     = false;
1533    Bool  bLeftAvail      = false;
1534    pcCU->getPattern()->initPattern   ( pcCU, uiTrDepth, uiAbsPartIdx, true );
1535    pcCU->getPattern()->initAdiPattern( pcCU, uiAbsPartIdx, uiTrDepth, 
1536                                        m_pcPrediction->getPredicBuf       (),
1537                                        m_pcPrediction->getPredicBufWidth  (),
1538                                        m_pcPrediction->getPredicBufHeight (),
1539                                        bAboveAvail, bLeftAvail, false, true, m_uiSubSampExpX, m_uiSubSampExpY );
1540    m_pcPrediction->predIntraDepthAng ( pcCU->getPattern(), uiLumaPredMode, pDepthMap, uiStride, uiWidth, uiHeight ); // could be replaced with directional intra prediction
1541                                                                                                                      // using "predIntraLumaAng", but note:
1542                                                                                                                      //  - need to take care of neighbours with undefined depth
1543                                                                                                                      //  - special case for wedgelet mode (if available in normal views)
1544    // copy to picture array (for next intra prediction block)
1545    UInt  uiZOrderIdx     = pcCU->getZorderIdxInCU() + uiAbsPartIdx;
1546    Pel*  pPicDepthMap    = pcCU->getPic()->getPredDepthMap()->getLumaAddr( pcCU->getAddr(), uiZOrderIdx );
1547#if PDM_REMOVE_DEPENDENCE
1548    if(pcCU->getPic()->getStoredPDMforV2()==1)
1549      pPicDepthMap    = pcCU->getPic()->getPredDepthMapTemp()->getLumaAddr( pcCU->getAddr(), uiZOrderIdx );
1550#endif
1551    Int   iPicStride      = pcCU->getPic()->getPredDepthMap()->getStride  ();
1552    for( UInt uiY = 0; uiY < uiHeight; uiY++, pDepthMap += uiStride, pPicDepthMap += iPicStride )
1553    {
1554      for( UInt uiX = 0; uiX < uiWidth; uiX++ )
1555      {
1556        pPicDepthMap[ uiX ] = pDepthMap[ uiX ];
1557      }
1558    }
1559  }
1560  else
1561  {
1562    UInt uiNumQPart  = pcCU->getPic()->getNumPartInCU() >> ( ( uiFullDepth + 1 ) << 1 );
1563    for( UInt uiPart = 0; uiPart < 4; uiPart++ )
1564    {
1565      xIntraPredictBlkDepthMap( pcCU, pcCUDepthMap, uiAbsPartIdx + uiPart * uiNumQPart, uiTrDepth + 1 );
1566    }
1567  }
1568}
1569
1570
1571Void 
1572TComDepthMapGenerator::xInterPredictPUDepthMap( TComDataCU* pcCU, TComYuv* pcCUDepthMap, UInt uiPartIdx )
1573{
1574  if ( pcCU->getSlice()->getSPS()->getViewId() )
1575  {
1576    AOF( m_uiCurrViewId == pcCU->getSlice()->getSPS()->getViewId() );
1577    // check for interview prediction
1578    Int             iWidth;
1579    Int             iHeight;
1580    UInt            uiAbsPartIdx;
1581    pcCU->getPartIndexAndSize( uiPartIdx, uiAbsPartIdx, iWidth, iHeight );
1582    TComCUMvField*  aiCurrMvField[2]  = { pcCU->getCUMvField( REF_PIC_LIST_0 ),        pcCU->getCUMvField( REF_PIC_LIST_1 )        };
1583    Int             aiCurrRefIdx [2]  = { aiCurrMvField[0]->getRefIdx( uiAbsPartIdx ), aiCurrMvField[1]->getRefIdx( uiAbsPartIdx ) };
1584    Bool            abCurrIntView[2]  = { aiCurrRefIdx[0] >= 0 && pcCU->getSlice()->getRefPic( REF_PIC_LIST_0, aiCurrRefIdx[0] )->getSPS()->getViewId() != m_uiCurrViewId,
1585                                          aiCurrRefIdx[1] >= 0 && pcCU->getSlice()->getRefPic( REF_PIC_LIST_1, aiCurrRefIdx[1] )->getSPS()->getViewId() != m_uiCurrViewId };
1586    Bool            bUsesInterViewPrd = ( abCurrIntView[0] || abCurrIntView[1] );
1587    if( bUsesInterViewPrd )
1588    {
1589      xIViewPUDepthMapUpdate  ( pcCU, pcCUDepthMap, uiPartIdx );
1590    }
1591    else
1592    { 
1593#if PDM_NO_INTER_UPDATE
1594      xInterPUDepthMapPrediction( pcCU, pcCUDepthMap, uiPartIdx );
1595#else
1596      xInterPUDepthMapUpdate  ( pcCU, pcCUDepthMap, uiPartIdx );
1597#endif
1598    }
1599  }
1600  else
1601  {
1602    xInterPUDepthMapPrediction( pcCU, pcCUDepthMap, uiPartIdx );
1603  }
1604}
1605
1606
1607Void 
1608TComDepthMapGenerator::xIViewPUDepthMapUpdate( TComDataCU* pcCU, TComYuv* pcCUDepthMap, UInt uiPartIdx )
1609{
1610  // get width, height, and part address
1611  Int   iWidth;
1612  Int   iHeight;
1613  UInt  uiAbsPartIdx;
1614  pcCU->getPartIndexAndSize( uiPartIdx, uiAbsPartIdx, iWidth, iHeight );
1615  iWidth  >>= m_uiSubSampExpX;
1616  iHeight >>= m_uiSubSampExpY;
1617
1618  // get depth values
1619  Int   iDepthValue   = PDM_UNDEFINED_DEPTH;
1620  Int   aiPrdDepth[2] = { PDM_UNDEFINED_DEPTH, PDM_UNDEFINED_DEPTH };
1621  for( Int iRefListId = 0; iRefListId < 2; iRefListId++ )
1622  {
1623    RefPicList      eRefPicList = RefPicList( iRefListId );
1624    TComCUMvField*  pcCUMvField = pcCU->getCUMvField( eRefPicList );
1625    Int             iRefIdx     = pcCUMvField->getRefIdx( uiAbsPartIdx );
1626    UInt            uiBaseId    = ( iRefIdx >= 0 ? pcCU->getSlice()->getRefPic( eRefPicList, iRefIdx )->getSPS()->getViewId() : MAX_VIEW_NUM ); 
1627    Bool            bInterview  = ( iRefIdx >= 0 && uiBaseId < m_uiCurrViewId );
1628    if( bInterview )
1629    {
1630      Int           iMvX        = pcCUMvField->getMv( uiAbsPartIdx ).getHor();
1631      aiPrdDepth[ iRefListId ]  = xGetVirtDepthFromDisparity( uiBaseId, iMvX );
1632    }
1633  }
1634  if( aiPrdDepth[ 0 ] != PDM_UNDEFINED_DEPTH && aiPrdDepth[ 1 ] != PDM_UNDEFINED_DEPTH )
1635  {
1636    iDepthValue = ( aiPrdDepth[ 0 ] + aiPrdDepth[ 1 ] + 1 ) >> 1;
1637  }
1638  else
1639  {
1640    iDepthValue = ( aiPrdDepth[ 0 ] != PDM_UNDEFINED_DEPTH ? aiPrdDepth[ 0 ] : aiPrdDepth[ 1 ] );
1641    AOT( iDepthValue == PDM_UNDEFINED_DEPTH );
1642  }
1643  iDepthValue   = Max( 0, Min( PDM_MAX_ABS_VIRT_DEPTH, iDepthValue ) );
1644
1645  // set depth map for PU
1646  UInt  uiBlkX      = g_auiRasterToPelX[ g_auiZscanToRaster[ uiAbsPartIdx ] ] >> m_uiSubSampExpX;
1647  UInt  uiBlkY      = g_auiRasterToPelY[ g_auiZscanToRaster[ uiAbsPartIdx ] ] >> m_uiSubSampExpY;
1648  Pel*  pDMSamples  = pcCUDepthMap->getLumaAddr() + uiBlkY * pcCUDepthMap->getStride() + uiBlkX;
1649  Int   iStride     = pcCUDepthMap->getStride  ();
1650  for( Int iY = 0; iY < iHeight; iY++, pDMSamples += iStride )
1651  {
1652    for( Int iX = 0; iX < iWidth; iX++)
1653    {
1654      pDMSamples[ iX ] = (Pel)iDepthValue;
1655    }
1656  }
1657}
1658
1659
1660Void
1661TComDepthMapGenerator::xInterPUDepthMapUpdate( TComDataCU* pcCU, TComYuv* pcCUDepthMap, UInt uiPartIdx )
1662{
1663  const Int       iMaxAbsDeltaMvY   = 8 << 2;
1664
1665  //===== determine block parameters for current access unit and current view =====
1666  Int             iWidth;
1667  Int             iHeight;
1668  UInt            uiAbsPartIdx;
1669  pcCU->getPartIndexAndSize ( uiPartIdx, uiAbsPartIdx, iWidth, iHeight );
1670  UInt            uiCurrViewId      = pcCU->getSlice()->getSPS()->getViewId(); 
1671  Int             iNum4x4BlksY      = iHeight >> 2;
1672  Int             iNum4x4BlksX      = iWidth  >> 2;
1673  iWidth  >>= m_uiSubSampExpX;
1674  iHeight >>= m_uiSubSampExpY;
1675
1676  TComPicYuv*     pcCurrDepthMap    = pcCU->getPic()->getPredDepthMap();
1677  Pel*            piCurrDepthMap    = pcCurrDepthMap->getLumaAddr();
1678  Int             iCurrStride       = pcCurrDepthMap->getStride();
1679  TComCUMvField*  aiCurrMvField[2]  = { pcCU->getCUMvField( REF_PIC_LIST_0 ),        pcCU->getCUMvField( REF_PIC_LIST_1 )        };
1680  Int             aiCurrRefIdx [2]  = { aiCurrMvField[0]->getRefIdx( uiAbsPartIdx ), aiCurrMvField[1]->getRefIdx( uiAbsPartIdx ) };
1681  Int             iMinCurrListId    = ( aiCurrRefIdx [0] < 0 ? 1 : 0 );
1682  Int             iMaxCurrListId    = ( aiCurrRefIdx [1] < 0 ? 0 : 1 );
1683  Int             iCurrPUPosX;
1684  Int             iCurrPUPosY;
1685  pcCurrDepthMap->getTopLeftSamplePos( pcCU->getAddr(), pcCU->getZorderIdxInCU() + uiAbsPartIdx, iCurrPUPosX, iCurrPUPosY );
1686  AOT( uiCurrViewId    != m_uiCurrViewId );
1687  AOT( iMinCurrListId  >  iMaxCurrListId );
1688  AOT( aiCurrRefIdx[0] >= 0 && pcCU->getSlice()->getRefPic( REF_PIC_LIST_0, aiCurrRefIdx[0] )->getSPS()->getViewId() != uiCurrViewId );
1689  AOT( aiCurrRefIdx[1] >= 0 && pcCU->getSlice()->getRefPic( REF_PIC_LIST_1, aiCurrRefIdx[1] )->getSPS()->getViewId() != uiCurrViewId );
1690
1691  //===== determine parameters for current access unit and base view =====
1692  AOF( m_auiBaseIdList.size() );
1693  UInt            uiBaseId          = m_auiBaseIdList[ 0 ];
1694  TComPic*        pcBasePic         = m_pcAUPicAccess->getPic( uiBaseId );
1695  AOF( pcBasePic );
1696  TComPicYuv*     pcBaseDepthMap    = pcBasePic->getPredDepthMap();
1697  TComPicYuv*     pcBaseRecPic      = pcBasePic->getPicYuvRec   ();
1698  Pel*            piBaseDepthMap    = pcBaseDepthMap->getLumaAddr();
1699  Int             iBaseStride       = pcBaseDepthMap->getStride();
1700  Int             iShiftX           = m_uiSubSampExpX + 2;
1701  Int             iShiftY           = m_uiSubSampExpY + 2;
1702  Int             iAddX             = ( 1 << iShiftX ) >> 1;
1703  Int             iAddY             = ( 1 << iShiftY ) >> 1;
1704
1705  //===== initialize 4x4 block arrays =====
1706  for( Int i4x4BlkY = 0; i4x4BlkY < iNum4x4BlksY; i4x4BlkY++ )
1707  {
1708    for( Int i4x4BlkX = 0; i4x4BlkX < iNum4x4BlksX; i4x4BlkX++ )
1709    {
1710      m_aabDepthSet[ i4x4BlkY ][ i4x4BlkX ] = false;
1711      m_aai4x4Depth[ i4x4BlkY ][ i4x4BlkX ] = PDM_UNDEFINED_DEPTH;
1712    }
1713  }
1714  Int iNum4x4Set = 0;
1715
1716  //===== determine depth based on 4x4 blocks =====
1717  for( Int i4x4BlkY = 0; i4x4BlkY < iNum4x4BlksY; i4x4BlkY++ )
1718  {
1719    for( Int i4x4BlkX = 0; i4x4BlkX < iNum4x4BlksX; i4x4BlkX++ )
1720    {
1721      // position parameters
1722      Int               iCurrBlkPosX        = iCurrPUPosX + ( ( i4x4BlkX << 2 ) >> m_uiSubSampExpX );
1723      Int               iCurrBlkPosY        = iCurrPUPosY + ( ( i4x4BlkY << 2 ) >> m_uiSubSampExpY );
1724      Int               iCurrSamplePosX     = iCurrBlkPosX + ( 1 >> m_uiSubSampExpX );
1725      Int               iCurrSamplePosY     = iCurrBlkPosY + ( 1 >> m_uiSubSampExpY );
1726      Int               iCurrPredDepth      = piCurrDepthMap[ iCurrSamplePosY * iCurrStride + iCurrSamplePosX ];
1727      Int               iCurrPredDisp       = xGetDisparityFromVirtDepth( uiBaseId, iCurrPredDepth );
1728      Int               iBaseSamplePosX     = iCurrSamplePosX + ( ( iCurrPredDisp + iAddX ) >> iShiftX );
1729      Int               iBaseSamplePosY     = iCurrSamplePosY;
1730      iBaseSamplePosX                       = Clip3( 0, pcBaseDepthMap->getWidth () - 1, iBaseSamplePosX );
1731      iBaseSamplePosY                       = Clip3( 0, pcBaseDepthMap->getHeight() - 1, iBaseSamplePosY );
1732
1733      // check for occlusion
1734      if( piBaseDepthMap[ iBaseSamplePosY * iBaseStride + iBaseSamplePosX ] != iCurrPredDepth )
1735      {
1736        continue;
1737      }
1738
1739      // determine base motion data and check prediction mode
1740      Int               iBaseCUAddr;
1741      Int               iBaseAbsPartIdx;
1742      pcBaseRecPic->getCUAddrAndPartIdx( iBaseSamplePosX << m_uiSubSampExpX, iBaseSamplePosY << m_uiSubSampExpY, iBaseCUAddr, iBaseAbsPartIdx );
1743      TComDataCU*       pcBaseCU            = pcBasePic->getCU( iBaseCUAddr );
1744      if( pcBaseCU->getPredictionMode( iBaseAbsPartIdx ) != MODE_INTER && pcBaseCU->getPredictionMode( iBaseAbsPartIdx ) != MODE_SKIP )
1745      {
1746        continue;
1747      }
1748
1749      // check whether base was inter-view predicted
1750      TComCUMvField*    aiBaseMvField[2]    = { pcBaseCU->getCUMvField( REF_PIC_LIST_0 ),       pcBaseCU->getCUMvField( REF_PIC_LIST_1 )       };
1751      Int               aiBaseRefIdx [2]    = { aiBaseMvField[0]->getRefIdx( iBaseAbsPartIdx ), aiBaseMvField[1]->getRefIdx( iBaseAbsPartIdx ) };
1752      Bool              abBaseIntView[2]    = { aiBaseRefIdx[0] >= 0 && pcBaseCU->getSlice()->getRefPic( REF_PIC_LIST_0, aiBaseRefIdx[0] )->getSPS()->getViewId() != uiBaseId,
1753                                                aiBaseRefIdx[1] >= 0 && pcBaseCU->getSlice()->getRefPic( REF_PIC_LIST_1, aiBaseRefIdx[1] )->getSPS()->getViewId() != uiBaseId };
1754      if( abBaseIntView[0] || abBaseIntView[1] )
1755      { // current depth is reliable
1756        m_aai4x4Depth[i4x4BlkY][i4x4BlkX]   = iCurrPredDepth;
1757        m_aabDepthSet[i4x4BlkY][i4x4BlkX]   = true;
1758        iNum4x4Set++;
1759        continue;
1760      }
1761     
1762      // determine depth candidates using an approximate 4-point relationship (if appropriate)
1763      std::vector<Int>  aiDepthCand;
1764      Int               iMinBaseListId      = ( aiBaseRefIdx [0] < 0 ? 1 : 0 );
1765      Int               iMaxBaseListId      = ( aiBaseRefIdx [1] < 0 ? 0 : 1 );
1766      AOT( iMinBaseListId > iMaxBaseListId );
1767      for( Int iCurrRefListId  = iMinCurrListId; iCurrRefListId <= iMaxCurrListId; iCurrRefListId++ )
1768      {
1769        RefPicList      eCurrRefPicList     = RefPicList( iCurrRefListId );
1770        Int             iCurrRefPoc         = pcCU->getSlice()->getRefPOC( eCurrRefPicList, aiCurrRefIdx[ iCurrRefListId ] );
1771        TComPic*        pcCurrRefPic        = pcCU->getSlice()->getRefPic( eCurrRefPicList, aiCurrRefIdx[ iCurrRefListId ] );
1772        TComPicYuv*     pcCurrRefDMap       = pcCurrRefPic->getPredDepthMap();
1773        Pel*            piCurrRefDMap       = pcCurrRefDMap->getLumaAddr();
1774        Int             iCurrRefStride      = pcCurrRefDMap->getStride();
1775        TComMv          rcCurrMv            = aiCurrMvField[ iCurrRefListId ]->getMv( uiAbsPartIdx );
1776        Int             iCurrRefSamplePosX  = iCurrSamplePosX + ( ( rcCurrMv.getHor() + iAddX ) >> iShiftX );
1777        Int             iCurrRefSamplePosY  = iCurrSamplePosY + ( ( rcCurrMv.getVer() + iAddY ) >> iShiftY );
1778        Int             iCurrRefSamplePosXC = Clip3( 0, pcCurrRefDMap->getWidth () - 1, iCurrRefSamplePosX );
1779        Int             iCurrRefSamplePosYC = Clip3( 0, pcCurrRefDMap->getHeight() - 1, iCurrRefSamplePosY );
1780        Int             iCurrRefDepth       = piCurrRefDMap[ iCurrRefSamplePosYC * iCurrRefStride + iCurrRefSamplePosXC ];
1781
1782        for( Int iBaseRefListId = iMinBaseListId; iBaseRefListId <= iMaxBaseListId; iBaseRefListId++ )
1783        {
1784          RefPicList    eBaseRefPicList     = RefPicList( iBaseRefListId );
1785          Int           iBaseRefPoc         = pcBaseCU->getSlice()->getRefPOC( eBaseRefPicList, aiBaseRefIdx[ iBaseRefListId ] );
1786
1787          if( iCurrRefPoc == iBaseRefPoc )
1788          {
1789            // location and depth for path currView/currAU -> currView/refAU -> baseView/refAU
1790            Int         iCurrRefDisp        = xGetDisparityFromVirtDepth( uiBaseId, iCurrRefDepth );
1791            Int         iBaseRefSamplePosX  = iCurrRefSamplePosX + ( ( iCurrRefDisp + iAddX ) >> iShiftX );
1792            Int         iBaseRefSamplePosY  = iCurrRefSamplePosY;
1793            TComPic*    pcBaseRefPic        = pcBaseCU->getSlice()->getRefPic( eBaseRefPicList, aiBaseRefIdx[ iBaseRefListId ] );
1794            TComPicYuv* pcBaseRefDMap       = pcBaseRefPic->getPredDepthMap();
1795            Pel*        piBaseRefDMap       = pcBaseRefDMap->getLumaAddr();
1796            Int         iBaseRefStride      = pcBaseRefDMap->getStride();
1797            iBaseRefSamplePosX              = Clip3( 0, pcBaseRefDMap->getWidth () - 1, iBaseRefSamplePosX );
1798            iBaseRefSamplePosY              = Clip3( 0, pcBaseRefDMap->getHeight() - 1, iBaseRefSamplePosY );
1799            Int         iBaseRefDepth       = piBaseRefDMap[ iBaseRefSamplePosY * iBaseRefStride + iBaseRefSamplePosX ];
1800
1801            // location and depth for path currView/currAU ->baseView/currAU -> baseView/refAU
1802            TComMv     rcBaseMv            = aiBaseMvField[ iBaseRefListId ]->getMv( iBaseAbsPartIdx );
1803            Int         iAbsDeltaMvY        = ( rcBaseMv.getAbsVer() > rcCurrMv.getVer() ? rcBaseMv.getAbsVer() - rcCurrMv.getVer() : rcCurrMv.getVer() - rcBaseMv.getAbsVer() );
1804
1805            // check reliability (occlusion in reference access unit / vertical motion vector difference)
1806            if( iBaseRefDepth != iCurrRefDepth || iAbsDeltaMvY > iMaxAbsDeltaMvY )
1807            {
1808              continue;
1809            }
1810
1811            // determine new depth
1812            Int         iCurrCandDisp       = iCurrRefDisp + rcCurrMv.getHor() - rcBaseMv.getHor();
1813            Int         iCurrCandDepth      = xGetVirtDepthFromDisparity( uiBaseId, iCurrCandDisp );
1814            aiDepthCand.push_back( iCurrCandDepth );
1815          } // iCurrRefPoc == iBaseRefPoc
1816        } // iBaseRefListId
1817      } // iCurrRefListId
1818     
1819      // set depth for 4x4 block
1820      if( aiDepthCand.size() )
1821      { // get depth with minimum change (probably most reliable)
1822        Int             iMinAbsDepthChange  = (1<<30);
1823        Int             iDepthForMinChange  = (1<<30);
1824        for( UInt uiCandId = 0; uiCandId < (UInt)aiDepthCand.size(); uiCandId++ )
1825        {
1826          Int           iAbsDeltaDepth      = ( aiDepthCand[uiCandId] > iCurrPredDepth ? aiDepthCand[uiCandId] > iCurrPredDepth : iCurrPredDepth - aiDepthCand[uiCandId] );
1827          if( iAbsDeltaDepth < iMinAbsDepthChange )
1828          {
1829            iMinAbsDepthChange              = iAbsDeltaDepth;
1830            iDepthForMinChange              = aiDepthCand[uiCandId];
1831          }
1832        }
1833        m_aai4x4Depth[i4x4BlkY][i4x4BlkX]   = Min( Max( 0, iDepthForMinChange ), PDM_MAX_ABS_VIRT_DEPTH );
1834        m_aabDepthSet[i4x4BlkY][i4x4BlkX]   = true;
1835        iNum4x4Set++;
1836      }
1837    } // i4x4BlkX
1838  } // i4x4BlkY
1839
1840  //===== fall back (take original depth for 4x4 blocks) ====
1841  if( iNum4x4Set < Max( 1, ( iNum4x4BlksY * iNum4x4BlksX ) >> 2 ) )
1842  {
1843    iNum4x4Set = 0;
1844    for( Int i4x4BlkY = 0; i4x4BlkY < iNum4x4BlksY; i4x4BlkY++ )
1845    {
1846      for( Int i4x4BlkX = 0; i4x4BlkX < iNum4x4BlksX; i4x4BlkX++ )
1847      {
1848        Int             iCurrSamplePosX     = iCurrPUPosX + ( ( ( i4x4BlkX << 2 ) + 1 ) >> m_uiSubSampExpX );
1849        Int             iCurrSamplePosY     = iCurrPUPosY + ( ( ( i4x4BlkY << 2 ) + 1 ) >> m_uiSubSampExpY );
1850        m_aai4x4Depth[i4x4BlkY][i4x4BlkX]   = piCurrDepthMap[ iCurrSamplePosY * iCurrStride + iCurrSamplePosX ];
1851        m_aabDepthSet[i4x4BlkY][i4x4BlkX]   = true;
1852        iNum4x4Set++;
1853      }
1854    }
1855  }
1856
1857#if PDM_ONE_DEPTH_PER_PU
1858  //===== set average in 4x4 depth array =====
1859  Int   iSum        = 0;
1860  for( Int i4x4BlkY = 0; i4x4BlkY < iNum4x4BlksY; i4x4BlkY++ )
1861  {
1862    for( Int i4x4BlkX = 0; i4x4BlkX < iNum4x4BlksX; i4x4BlkX++ )
1863    {
1864      if( m_aabDepthSet[ i4x4BlkY ][ i4x4BlkX ] )
1865      {
1866        iSum += m_aai4x4Depth[ i4x4BlkY ][ i4x4BlkX ];
1867      }
1868    }
1869  }
1870  Int   iDepth      = ( iSum + ( iNum4x4Set >> 1 ) ) / iNum4x4Set;
1871  iNum4x4Set        = iNum4x4BlksY * iNum4x4BlksX;
1872  for( Int i4x4BlkY = 0; i4x4BlkY < iNum4x4BlksY; i4x4BlkY++ )
1873  {
1874    for( Int i4x4BlkX = 0; i4x4BlkX < iNum4x4BlksX; i4x4BlkX++ )
1875    {
1876      m_aai4x4Depth[ i4x4BlkY ][ i4x4BlkX ] = iDepth;
1877      m_aabDepthSet[ i4x4BlkY ][ i4x4BlkX ] = true;
1878    }
1879  }
1880#endif
1881 
1882  //===== complete depth arrays =====
1883  while( iNum4x4BlksY * iNum4x4BlksX - iNum4x4Set )
1884  {
1885    for( Int i4x4BlkY = 0; i4x4BlkY < iNum4x4BlksY; i4x4BlkY++ )
1886    {
1887      for( Int i4x4BlkX = 0; i4x4BlkX < iNum4x4BlksX; i4x4BlkX++ )
1888      {
1889        if( !m_aabDepthSet[ i4x4BlkY ][ i4x4BlkX ] )
1890        { // could also use minimum of neighbours (occlusions)
1891          Int iNumNeighbours  = 0;
1892          Int iSumNeighbours  = 0;
1893          if( i4x4BlkY > 0              && m_aabDepthSet[ i4x4BlkY-1 ][ i4x4BlkX   ] ) { iSumNeighbours += m_aai4x4Depth[ i4x4BlkY-1 ][ i4x4BlkX   ]; iNumNeighbours++; }
1894          if( i4x4BlkY < iNum4x4BlksY-1 && m_aabDepthSet[ i4x4BlkY+1 ][ i4x4BlkX   ] ) { iSumNeighbours += m_aai4x4Depth[ i4x4BlkY+1 ][ i4x4BlkX   ]; iNumNeighbours++; }
1895          if( i4x4BlkX > 0              && m_aabDepthSet[ i4x4BlkY   ][ i4x4BlkX-1 ] ) { iSumNeighbours += m_aai4x4Depth[ i4x4BlkY   ][ i4x4BlkX-1 ]; iNumNeighbours++; }
1896          if( i4x4BlkX < iNum4x4BlksX-1 && m_aabDepthSet[ i4x4BlkY   ][ i4x4BlkX+1 ] ) { iSumNeighbours += m_aai4x4Depth[ i4x4BlkY   ][ i4x4BlkX+1 ]; iNumNeighbours++; }
1897          if( iNumNeighbours )
1898          {
1899            m_aai4x4Depth[ i4x4BlkY ][ i4x4BlkX ] = ( iSumNeighbours + ( iNumNeighbours >> 1 ) ) / iNumNeighbours;
1900            m_aabDepthSet[ i4x4BlkY ][ i4x4BlkX ] = true;
1901            iNum4x4Set++;
1902          }
1903        }
1904      }
1905    }
1906  }
1907
1908  //===== set depth values =====
1909  UInt uiBlkX     = g_auiRasterToPelX[ g_auiZscanToRaster[ uiAbsPartIdx ] ] >> m_uiSubSampExpX;
1910  UInt uiBlkY     = g_auiRasterToPelY[ g_auiZscanToRaster[ uiAbsPartIdx ] ] >> m_uiSubSampExpY;
1911  Pel* piDepthMap = pcCUDepthMap->getLumaAddr() + uiBlkY * pcCUDepthMap->getStride() + uiBlkX;
1912  Int  iCUStride  = pcCUDepthMap->getStride  ();
1913  for( Int iRow = 0; iRow < iHeight; iRow++, piDepthMap += iCUStride )
1914  {
1915    for( Int iCol = 0; iCol < iWidth; iCol++ )
1916    {
1917      piDepthMap[ iCol ] = m_aai4x4Depth[ (iRow << m_uiSubSampExpY) >> 2  ][ (iCol << m_uiSubSampExpX) >> 2 ];
1918    }
1919  }
1920}
1921
1922
1923Void
1924TComDepthMapGenerator::xInterPUDepthMapPrediction( TComDataCU* pcCU, TComYuv* pcCUDepthMap, UInt uiPartIdx )
1925{
1926  m_pcPrediction->motionCompensation( pcCU, pcCUDepthMap, REF_PIC_LIST_X, (Int)uiPartIdx, true, m_uiSubSampExpX, m_uiSubSampExpY ); 
1927}
1928
1929
1930Bool
1931TComDepthMapGenerator::xGetPredDepth( TComDataCU* pcCU, UInt uiPartIdx, Int& riPrdDepth, Int* piPosX, Int* piPosY )
1932{
1933  AOF  ( m_bCreated && m_bInit );
1934  AOF  ( pcCU );
1935  ROFRS( m_bPDMAvailable, false );
1936
1937  TComSlice*    pcSlice     = pcCU->getSlice ();
1938  TComPic*      pcPic       = pcCU->getPic   ();
1939  TComSPS*      pcSPS       = pcSlice->getSPS();
1940  AOF  ( pcPic->getPredDepthMap() );
1941  AOF  ( pcSPS->getViewId() == m_uiCurrViewId );
1942 
1943  //===== get predicted depth and disprity for middle position of current PU ===== 
1944  UInt          uiPartAddr;
1945  Int           iWidth;
1946  Int           iHeight;
1947  pcCU->getPartIndexAndSize( uiPartIdx, uiPartAddr, iWidth, iHeight );
1948  TComPicYuv*   pcPredDepthMap  = pcPic->getPredDepthMap();
1949  Pel*          piPredDepthMap  = pcPredDepthMap->getLumaAddr ( 0 );
1950  Int           iCurrStride     = pcPredDepthMap->getStride   ();
1951  Int           iCurrPosX;
1952  Int           iCurrPosY;
1953  pcPredDepthMap->getTopLeftSamplePos( pcCU->getAddr(), pcCU->getZorderIdxInCU() + uiPartAddr, iCurrPosX, iCurrPosY );
1954#if H3D_IVMP // max disparity within PU
1955  Int DiWidth  = iCurrPosX+(iWidth  >> m_uiSubSampExpX);
1956  Int DiHeight = iCurrPosY+(iHeight >> m_uiSubSampExpY);
1957  Int maxDepth = MIN_INT;
1958
1959  for(Int y=iCurrPosY; y<DiHeight ;y++)
1960  {
1961    for(Int x=iCurrPosX; x<DiWidth; x++)
1962    {
1963      if(piPredDepthMap[ x + y * iCurrStride ] > maxDepth)
1964      {
1965        maxDepth = piPredDepthMap[ x + y * iCurrStride ];
1966      }
1967    }
1968  }
1969  iCurrPosX  += ( ( iWidth  >> m_uiSubSampExpX ) - 1 ) >> 1;
1970  iCurrPosY  += ( ( iHeight >> m_uiSubSampExpY ) - 1 ) >> 1;
1971  riPrdDepth  = maxDepth;
1972#else
1973  iCurrPosX  += ( ( iWidth  >> m_uiSubSampExpX ) - 1 ) >> 1;
1974  iCurrPosY  += ( ( iHeight >> m_uiSubSampExpY ) - 1 ) >> 1;
1975  riPrdDepth  = piPredDepthMap[ iCurrPosX + iCurrPosY * iCurrStride ];
1976#endif
1977  if( piPosX )
1978  {
1979    *piPosX   = iCurrPosX;
1980  }
1981  if( piPosY )
1982  {
1983    *piPosY   = iCurrPosY;
1984  }
1985  return        true;
1986}
1987#endif // H3D_NBDV
1988
1989#endif // DEPTH_MAP_GENERATION
1990
Note: See TracBrowser for help on using the repository browser.