source: SHVCSoftware/branches/SHM-1.0-dev/source/Lib/TLibCommon/TComPic.cpp @ 1165

Last change on this file since 1165 was 34, checked in by seregin, 12 years ago

Merge with trunk

File size: 23.1 KB
Line 
1/* The copyright in this software is being made available under the BSD
2 * License, included below. This software may be subject to other third party
3 * and contributor rights, including patent rights, and no such rights are
4 * granted under this license. 
5 *
6 * Copyright (c) 2010-2012, 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     TComPic.cpp
35    \brief    picture class
36*/
37
38#include "TComPic.h"
39#include "SEI.h"
40
41//! \ingroup TLibCommon
42//! \{
43
44// ====================================================================================================================
45// Constructor / destructor / create / destroy
46// ====================================================================================================================
47
48TComPic::TComPic()
49: m_uiTLayer                              (0)
50, m_bUsedByCurr                           (false)
51, m_bIsLongTerm                           (false)
52, m_bIsUsedAsLongTerm                     (false)
53, m_apcPicSym                             (NULL)
54, m_pcPicYuvPred                          (NULL)
55, m_pcPicYuvResi                          (NULL)
56, m_bReconstructed                        (false)
57, m_bNeededForOutput                      (false)
58, m_uiCurrSliceIdx                        (0)
59, m_pSliceSUMap                           (NULL)
60, m_pbValidSlice                          (NULL)
61, m_sliceGranularityForNDBFilter          (0)
62, m_bIndependentSliceBoundaryForNDBFilter (false)
63, m_bIndependentTileBoundaryForNDBFilter  (false)
64, m_pNDBFilterYuvTmp                      (NULL)
65, m_bCheckLTMSB                           (false)
66, m_SEIs                                  (NULL)
67#if SVC_EXTENSION
68, m_bSpatialEnhLayer( false )
69, m_pcFullPelBaseRec( NULL )
70#if REF_IDX_ME_AROUND_ZEROMV || REF_IDX_ME_ZEROMV || ENCODER_FAST_MODE || REF_IDX_MFM
71, m_bIsILR                                (false)
72#endif
73
74#endif
75{
76  m_apcPicYuv[0]      = NULL;
77  m_apcPicYuv[1]      = NULL;
78}
79
80TComPic::~TComPic()
81{
82}
83
84#if SVC_UPSAMPLING
85Void TComPic::create( Int iWidth, Int iHeight, UInt uiMaxWidth, UInt uiMaxHeight, UInt uiMaxDepth, TComSPS* pcSps,  Bool bIsVirtual )
86{
87  m_apcPicSym     = new TComPicSym;  m_apcPicSym   ->create( iWidth, iHeight, uiMaxWidth, uiMaxHeight, uiMaxDepth );
88  if (!bIsVirtual)
89  {
90    m_apcPicYuv[0]  = new TComPicYuv;  m_apcPicYuv[0]->create( iWidth, iHeight, uiMaxWidth, uiMaxHeight, uiMaxDepth, pcSps );
91  }
92  m_apcPicYuv[1]  = new TComPicYuv;  m_apcPicYuv[1]->create( iWidth, iHeight, uiMaxWidth, uiMaxHeight, uiMaxDepth, pcSps );
93 
94  if (m_bSpatialEnhLayer)
95  {
96    m_pcFullPelBaseRec = new TComPicYuv;  m_pcFullPelBaseRec->create( iWidth, iHeight, uiMaxWidth, uiMaxHeight, uiMaxDepth, pcSps );
97  }
98
99  /* there are no SEI messages associated with this picture initially */
100  m_SEIs = NULL;
101  m_bUsedByCurr = false;
102  return;
103}
104#if REF_IDX_FRAMEWORK
105Void TComPic::createWithOutYuv( Int iWidth, Int iHeight, UInt uiMaxWidth, UInt uiMaxHeight, UInt uiMaxDepth, TComSPS* pcSps,  Bool bIsVirtual)
106{
107  m_apcPicSym     = new TComPicSym;  m_apcPicSym   ->create( iWidth, iHeight, uiMaxWidth, uiMaxHeight, uiMaxDepth );
108  if (!bIsVirtual)
109  {
110    m_apcPicYuv[0]  = new TComPicYuv;  m_apcPicYuv[0]->create( iWidth, iHeight, uiMaxWidth, uiMaxHeight, uiMaxDepth, pcSps );
111  }
112  m_apcPicYuv[1]  = NULL;
113 
114#if SVC_UPSAMPLING
115  if (m_bSpatialEnhLayer)
116  {
117    m_pcFullPelBaseRec = new TComPicYuv;  m_pcFullPelBaseRec->create( iWidth, iHeight, uiMaxWidth, uiMaxHeight, uiMaxDepth, pcSps );
118  }
119#endif
120
121  /* there are no SEI messages associated with this picture initially */
122  m_SEIs = NULL;
123  m_bUsedByCurr = false;
124  return;
125}
126#endif
127#else
128
129Void TComPic::create( Int iWidth, Int iHeight, UInt uiMaxWidth, UInt uiMaxHeight, UInt uiMaxDepth, Bool bIsVirtual )
130{
131  m_apcPicSym     = new TComPicSym;  m_apcPicSym   ->create( iWidth, iHeight, uiMaxWidth, uiMaxHeight, uiMaxDepth );
132  if (!bIsVirtual)
133  {
134    m_apcPicYuv[0]  = new TComPicYuv;  m_apcPicYuv[0]->create( iWidth, iHeight, uiMaxWidth, uiMaxHeight, uiMaxDepth );
135  }
136  m_apcPicYuv[1]  = new TComPicYuv;  m_apcPicYuv[1]->create( iWidth, iHeight, uiMaxWidth, uiMaxHeight, uiMaxDepth );
137 
138  /* there are no SEI messages associated with this picture initially */
139  m_SEIs = NULL;
140  m_bUsedByCurr = false;
141  return;
142}
143#endif
144
145Void TComPic::destroy()
146{
147  if (m_apcPicSym)
148  {
149    m_apcPicSym->destroy();
150    delete m_apcPicSym;
151    m_apcPicSym = NULL;
152  }
153 
154  if (m_apcPicYuv[0])
155  {
156    m_apcPicYuv[0]->destroy();
157    delete m_apcPicYuv[0];
158    m_apcPicYuv[0]  = NULL;
159  }
160 
161  if (m_apcPicYuv[1])
162  {
163    m_apcPicYuv[1]->destroy();
164    delete m_apcPicYuv[1];
165    m_apcPicYuv[1]  = NULL;
166  }
167 
168#if SVC_EXTENSION && SVC_UPSAMPLING
169  if (m_bSpatialEnhLayer)
170  {
171    m_pcFullPelBaseRec->destroy();
172    delete m_pcFullPelBaseRec;    m_pcFullPelBaseRec  = NULL;
173  }
174#endif
175
176  delete m_SEIs;
177}
178
179Void TComPic::compressMotion()
180{
181  TComPicSym* pPicSym = getPicSym(); 
182  for ( UInt uiCUAddr = 0; uiCUAddr < pPicSym->getFrameHeightInCU()*pPicSym->getFrameWidthInCU(); uiCUAddr++ )
183  {
184    TComDataCU* pcCU = pPicSym->getCU(uiCUAddr);
185    pcCU->compressMV(); 
186  } 
187}
188
189/** Create non-deblocked filter information
190 * \param pSliceStartAddress array for storing slice start addresses
191 * \param numSlices number of slices in picture
192 * \param sliceGranularityDepth slice granularity
193 * \param bNDBFilterCrossSliceBoundary cross-slice-boundary in-loop filtering; true for "cross".
194 * \param numTiles number of tiles in picture
195 * \param bNDBFilterCrossTileBoundary cross-tile-boundary in-loop filtering; true for "cross".
196 */
197Void TComPic::createNonDBFilterInfo(std::vector<Int> sliceStartAddress, Int sliceGranularityDepth
198                                    ,std::vector<Bool>* LFCrossSliceBoundary
199                                    ,Int numTiles
200                                    ,Bool bNDBFilterCrossTileBoundary)
201{
202  UInt maxNumSUInLCU = getNumPartInCU();
203  UInt numLCUInPic   = getNumCUsInFrame();
204  UInt picWidth      = getSlice(0)->getSPS()->getPicWidthInLumaSamples();
205  UInt picHeight     = getSlice(0)->getSPS()->getPicHeightInLumaSamples();
206  Int  numLCUsInPicWidth = getFrameWidthInCU();
207  Int  numLCUsInPicHeight= getFrameHeightInCU();
208  UInt maxNumSUInLCUWidth = getNumPartInWidth();
209  UInt maxNumSUInLCUHeight= getNumPartInHeight();
210  Int  numSlices = (Int) sliceStartAddress.size() - 1;
211  m_bIndependentSliceBoundaryForNDBFilter = false;
212  if(numSlices > 1)
213  {
214    for(Int s=0; s< numSlices; s++)
215    {
216      if((*LFCrossSliceBoundary)[s] == false)
217      {
218        m_bIndependentSliceBoundaryForNDBFilter = true;
219      }
220    }
221  }
222  m_sliceGranularityForNDBFilter = sliceGranularityDepth;
223  m_bIndependentTileBoundaryForNDBFilter  = (bNDBFilterCrossTileBoundary)?(false) :((numTiles > 1)?(true):(false));
224
225  m_pbValidSlice = new Bool[numSlices];
226  for(Int s=0; s< numSlices; s++)
227  {
228    m_pbValidSlice[s] = true;
229  }
230  m_pSliceSUMap = new Int[maxNumSUInLCU * numLCUInPic];
231
232  //initialization
233  for(UInt i=0; i< (maxNumSUInLCU * numLCUInPic); i++ )
234  {
235    m_pSliceSUMap[i] = -1;
236  }
237  for( UInt CUAddr = 0; CUAddr < numLCUInPic ; CUAddr++ )
238  {
239    TComDataCU* pcCU = getCU( CUAddr );
240    pcCU->setSliceSUMap(m_pSliceSUMap + (CUAddr* maxNumSUInLCU)); 
241    pcCU->getNDBFilterBlocks()->clear();
242  }
243  m_vSliceCUDataLink.clear();
244
245  m_vSliceCUDataLink.resize(numSlices);
246
247  UInt startAddr, endAddr, firstCUInStartLCU, startLCU, endLCU, lastCUInEndLCU, uiAddr;
248  UInt LPelX, TPelY, LCUX, LCUY;
249  UInt currSU;
250  UInt startSU, endSU;
251
252  for(Int s=0; s< numSlices; s++)
253  {
254    //1st step: decide the real start address
255    startAddr = sliceStartAddress[s];
256    endAddr   = sliceStartAddress[s+1] -1;
257
258    startLCU            = startAddr / maxNumSUInLCU;
259    firstCUInStartLCU   = startAddr % maxNumSUInLCU;
260
261    endLCU              = endAddr   / maxNumSUInLCU;
262    lastCUInEndLCU      = endAddr   % maxNumSUInLCU;   
263
264    uiAddr = m_apcPicSym->getCUOrderMap(startLCU);
265
266    LCUX      = getCU(uiAddr)->getCUPelX();
267    LCUY      = getCU(uiAddr)->getCUPelY();
268    LPelX     = LCUX + g_auiRasterToPelX[ g_auiZscanToRaster[firstCUInStartLCU] ];
269    TPelY     = LCUY + g_auiRasterToPelY[ g_auiZscanToRaster[firstCUInStartLCU] ];
270    currSU    = firstCUInStartLCU;
271
272    Bool bMoveToNextLCU = false;
273    Bool bSliceInOneLCU = (startLCU == endLCU);
274
275    while(!( LPelX < picWidth ) || !( TPelY < picHeight ))
276    {
277      currSU ++;
278
279      if(bSliceInOneLCU)
280      {
281        if(currSU > lastCUInEndLCU)
282        {
283          m_pbValidSlice[s] = false;
284          break;
285        }
286      }
287
288      if(currSU >= maxNumSUInLCU )
289      {
290        bMoveToNextLCU = true;
291        break;
292      }
293
294      LPelX = LCUX + g_auiRasterToPelX[ g_auiZscanToRaster[currSU] ];
295      TPelY = LCUY + g_auiRasterToPelY[ g_auiZscanToRaster[currSU] ];
296
297    }
298
299
300    if(!m_pbValidSlice[s])
301    {
302      continue;
303    }
304
305    if(currSU != firstCUInStartLCU)
306    {
307      if(!bMoveToNextLCU)
308      {
309        firstCUInStartLCU = currSU;
310      }
311      else
312      {
313        startLCU++;
314        firstCUInStartLCU = 0;
315        assert( startLCU < getNumCUsInFrame());
316      }
317      assert(startLCU*maxNumSUInLCU + firstCUInStartLCU < endAddr);
318    }
319
320
321    //2nd step: assign NonDBFilterInfo to each processing block
322    for(UInt i= startLCU; i <= endLCU; i++)
323    {
324      startSU = (i == startLCU)?(firstCUInStartLCU):(0);
325      endSU   = (i == endLCU  )?(lastCUInEndLCU   ):(maxNumSUInLCU -1);
326
327      uiAddr = m_apcPicSym->getCUOrderMap(i);
328      Int iTileID= m_apcPicSym->getTileIdxMap(uiAddr);
329
330      TComDataCU* pcCU = getCU(uiAddr);
331      m_vSliceCUDataLink[s].push_back(pcCU);
332
333      createNonDBFilterInfoLCU(iTileID, s, pcCU, startSU, endSU, m_sliceGranularityForNDBFilter, picWidth, picHeight);
334    }
335  }
336
337  //step 3: border availability
338  for(Int s=0; s< numSlices; s++)
339  {
340    if(!m_pbValidSlice[s])
341    {
342      continue;
343    }
344
345    for(Int i=0; i< m_vSliceCUDataLink[s].size(); i++)
346    {
347      TComDataCU* pcCU = m_vSliceCUDataLink[s][i];
348      uiAddr = pcCU->getAddr();
349
350      if(pcCU->getPic()==0)
351      {
352        continue;
353      }
354      Int iTileID= m_apcPicSym->getTileIdxMap(uiAddr);
355      Bool bTopTileBoundary = false, bDownTileBoundary= false, bLeftTileBoundary= false, bRightTileBoundary= false;
356
357      if(m_bIndependentTileBoundaryForNDBFilter)
358      {
359        //left
360        if( uiAddr % numLCUsInPicWidth != 0)
361        {
362          bLeftTileBoundary = ( m_apcPicSym->getTileIdxMap(uiAddr -1) != iTileID )?true:false;
363        }
364        //right
365        if( (uiAddr % numLCUsInPicWidth) != (numLCUsInPicWidth -1) )
366        {
367          bRightTileBoundary = ( m_apcPicSym->getTileIdxMap(uiAddr +1) != iTileID)?true:false;
368        }
369        //top
370        if( uiAddr >= numLCUsInPicWidth)
371        {
372          bTopTileBoundary = (m_apcPicSym->getTileIdxMap(uiAddr - numLCUsInPicWidth) !=  iTileID )?true:false;
373        }
374        //down
375        if( uiAddr + numLCUsInPicWidth < numLCUInPic )
376        {
377          bDownTileBoundary = (m_apcPicSym->getTileIdxMap(uiAddr + numLCUsInPicWidth) != iTileID)?true:false;
378        }
379
380      }
381
382      pcCU->setNDBFilterBlockBorderAvailability(numLCUsInPicWidth, numLCUsInPicHeight, maxNumSUInLCUWidth, maxNumSUInLCUHeight,picWidth, picHeight
383        , *LFCrossSliceBoundary
384        ,bTopTileBoundary, bDownTileBoundary, bLeftTileBoundary, bRightTileBoundary
385        ,m_bIndependentTileBoundaryForNDBFilter);
386
387    }
388
389  }
390
391  if( m_bIndependentSliceBoundaryForNDBFilter || m_bIndependentTileBoundaryForNDBFilter)
392  {
393    m_pNDBFilterYuvTmp = new TComPicYuv();
394    m_pNDBFilterYuvTmp->create(picWidth, picHeight, g_uiMaxCUWidth, g_uiMaxCUHeight, g_uiMaxCUDepth);
395  }
396
397}
398
399/** Create non-deblocked filter information for LCU
400 * \param tileID tile index
401 * \param sliceID slice index
402 * \param pcCU CU data pointer
403 * \param startSU start SU index in LCU
404 * \param endSU end SU index in LCU
405 * \param sliceGranularyDepth slice granularity
406 * \param picWidth picture width
407 * \param picHeight picture height
408 */
409Void TComPic::createNonDBFilterInfoLCU(Int tileID, Int sliceID, TComDataCU* pcCU, UInt startSU, UInt endSU, Int sliceGranularyDepth, UInt picWidth, UInt picHeight)
410{
411  UInt LCUX          = pcCU->getCUPelX();
412  UInt LCUY          = pcCU->getCUPelY();
413  Int* pCUSliceMap    = pcCU->getSliceSUMap();
414  UInt maxNumSUInLCU = getNumPartInCU();
415  UInt maxNumSUInSGU = maxNumSUInLCU >> (sliceGranularyDepth << 1);
416  UInt maxNumSUInLCUWidth = getNumPartInWidth();
417  UInt LPelX, TPelY;
418  UInt currSU;
419
420
421  //get the number of valid NBFilterBLock
422  currSU   = startSU;
423  while(currSU <= endSU)
424  {
425    LPelX = LCUX + g_auiRasterToPelX[ g_auiZscanToRaster[currSU] ];
426    TPelY = LCUY + g_auiRasterToPelY[ g_auiZscanToRaster[currSU] ];
427
428    while(!( LPelX < picWidth ) || !( TPelY < picHeight ))
429    {
430      currSU += maxNumSUInSGU;
431      if(currSU >= maxNumSUInLCU || currSU > endSU)
432      {
433        break;
434      }
435      LPelX = LCUX + g_auiRasterToPelX[ g_auiZscanToRaster[currSU] ];
436      TPelY = LCUY + g_auiRasterToPelY[ g_auiZscanToRaster[currSU] ];
437    }
438
439    if(currSU >= maxNumSUInLCU || currSU > endSU)
440    {
441      break;
442    }
443
444    NDBFBlockInfo NDBFBlock;
445
446    NDBFBlock.tileID  = tileID;
447    NDBFBlock.sliceID = sliceID;
448    NDBFBlock.posY    = TPelY;
449    NDBFBlock.posX    = LPelX;
450    NDBFBlock.startSU = currSU;
451
452    UInt uiLastValidSU  = currSU;
453    UInt uiIdx, uiLPelX_su, uiTPelY_su;
454    for(uiIdx = currSU; uiIdx < currSU + maxNumSUInSGU; uiIdx++)
455    {
456      if(uiIdx > endSU)
457      {
458        break;       
459      }
460      uiLPelX_su   = LCUX + g_auiRasterToPelX[ g_auiZscanToRaster[uiIdx] ];
461      uiTPelY_su   = LCUY + g_auiRasterToPelY[ g_auiZscanToRaster[uiIdx] ];
462      if( !(uiLPelX_su < picWidth ) || !( uiTPelY_su < picHeight ))
463      {
464        continue;
465      }
466      pCUSliceMap[uiIdx] = sliceID;
467      uiLastValidSU = uiIdx;
468    }
469    NDBFBlock.endSU = uiLastValidSU;
470
471    UInt rTLSU = g_auiZscanToRaster[ NDBFBlock.startSU ];
472    UInt rBRSU = g_auiZscanToRaster[ NDBFBlock.endSU   ];
473    NDBFBlock.widthSU  = (rBRSU % maxNumSUInLCUWidth) - (rTLSU % maxNumSUInLCUWidth)+ 1;
474    NDBFBlock.heightSU = (UInt)(rBRSU / maxNumSUInLCUWidth) - (UInt)(rTLSU / maxNumSUInLCUWidth)+ 1;
475    NDBFBlock.width    = NDBFBlock.widthSU  * getMinCUWidth();
476    NDBFBlock.height   = NDBFBlock.heightSU * getMinCUHeight();
477
478    pcCU->getNDBFilterBlocks()->push_back(NDBFBlock);
479
480    currSU += maxNumSUInSGU;
481  }
482
483}
484
485/** destroy non-deblocked filter information for LCU
486 */
487Void TComPic::destroyNonDBFilterInfo()
488{
489  if(m_pbValidSlice != NULL)
490  {
491    delete[] m_pbValidSlice;
492    m_pbValidSlice = NULL;
493  }
494
495  if(m_pSliceSUMap != NULL)
496  {
497    delete[] m_pSliceSUMap;
498    m_pSliceSUMap = NULL;
499  }
500  for( UInt CUAddr = 0; CUAddr < getNumCUsInFrame() ; CUAddr++ )
501  {
502    TComDataCU* pcCU = getCU( CUAddr );
503    pcCU->getNDBFilterBlocks()->clear();
504  }
505
506  if( m_bIndependentSliceBoundaryForNDBFilter || m_bIndependentTileBoundaryForNDBFilter)
507  {
508    m_pNDBFilterYuvTmp->destroy();
509    delete m_pNDBFilterYuvTmp;
510    m_pNDBFilterYuvTmp = NULL;
511  }
512
513}
514
515#if REF_IDX_FRAMEWORK
516Void copyOnetoOnePicture(    // SVC_NONCOLL
517                  Pel *in,       
518                  Pel *out,     
519                  Int nCols,
520                  Int nRows, 
521                  Int fullRowWidth)
522{
523  Int rX;
524
525  for (rX = 0; rX < nRows; rX++)       
526  {
527    memcpy( out, in, sizeof(Pel) * nCols );
528    in = in + fullRowWidth;
529    out = out + fullRowWidth;
530  }
531}
532
533Void TComPic:: copyUpsampledPictureYuv(TComPicYuv*   pcPicYuvIn, TComPicYuv*   pcPicYuvOut)
534{
535  Int upsampledRowWidthLuma = pcPicYuvOut->getStride(); // 2 * pcPicYuvOut->getLumaMargin() + pcPicYuvOut->getWidth();
536  Int upsampledRowWidthCroma = pcPicYuvOut->getCStride(); //2 * pcPicYuvOut->getChromaMargin() + (pcPicYuvOut->getWidth()>>1);
537
538  copyOnetoOnePicture(
539    pcPicYuvIn->getLumaAddr(),       
540    pcPicYuvOut->getLumaAddr(),     
541    pcPicYuvOut->getWidth(), 
542    pcPicYuvOut->getHeight(),
543    upsampledRowWidthLuma);
544  copyOnetoOnePicture(
545    pcPicYuvIn->getCrAddr(),       
546    pcPicYuvOut->getCrAddr(),     
547    pcPicYuvOut->getWidth()>>1, 
548    pcPicYuvOut->getHeight()>>1,
549    upsampledRowWidthCroma);
550  copyOnetoOnePicture(
551    pcPicYuvIn->getCbAddr(),       
552    pcPicYuvOut->getCbAddr(),     
553    pcPicYuvOut->getWidth()>>1, 
554    pcPicYuvOut->getHeight()>>1,
555    upsampledRowWidthCroma);
556}
557
558#if REF_IDX_MFM
559Void TComPic::deriveUnitIdxBase( UInt uiUpsamplePelX, UInt uiUpsamplePelY, UInt ratio, UInt& uiBaseCUAddr, UInt& uiBaseAbsPartIdx )
560{
561  //pixel in the base layer
562
563  UInt uiPelX       = (uiUpsamplePelX<<1)/ratio;
564  UInt uiPelY       = (uiUpsamplePelY<<1)/ratio;
565  UInt uiBaseWidth  = getPicYuvRec()->getWidth();
566  UInt uiBaseHeight = getPicYuvRec()->getHeight();
567
568  UInt uiWidthInCU       = ( uiBaseWidth % g_uiMaxCUWidth  ) ? uiBaseWidth /g_uiMaxCUWidth  + 1 : uiBaseWidth /g_uiMaxCUWidth;
569  UInt uiHeightInCU      = ( uiBaseHeight% g_uiMaxCUHeight ) ? uiBaseHeight/ g_uiMaxCUHeight + 1 : uiBaseHeight/ g_uiMaxCUHeight;
570
571  uiPelX     = (UInt)Clip3<UInt>(0, uiWidthInCU * g_uiMaxCUWidth - 1, uiPelX);
572  uiPelY     = (UInt)Clip3<UInt>(0, uiHeightInCU * g_uiMaxCUHeight - 1, uiPelY);
573 
574  uiBaseCUAddr = uiPelY / g_uiMaxCUHeight * uiWidthInCU + uiPelX / g_uiMaxCUWidth;
575
576  UInt uiWidthMinPU = g_uiMaxCUWidth / (1<<g_uiMaxCUDepth);
577  UInt uiHeightMinPU = g_uiMaxCUHeight/(1<<g_uiMaxCUDepth);
578 
579  UInt uiAbsPelX = uiPelX - (uiPelX / g_uiMaxCUWidth) * g_uiMaxCUWidth;
580  UInt uiAbsPelY = uiPelY - (uiPelY / g_uiMaxCUHeight) * g_uiMaxCUHeight;
581
582  UInt RasterIdx = uiAbsPelY / uiHeightMinPU * (g_uiMaxCUWidth/uiWidthMinPU) + uiAbsPelX / uiWidthMinPU;
583  uiBaseAbsPartIdx = g_auiRasterToZscan[RasterIdx];
584
585  return;
586}
587
588Void TComPic::copyUpsampledMvField(TComPic* pcPicBase)
589{
590  Int iBWidth   = pcPicBase->getPicYuvRec()->getWidth () - pcPicBase->getPicYuvRec()->getPicCropLeftOffset() - pcPicBase->getPicYuvRec()->getPicCropRightOffset();
591  Int iBHeight  = pcPicBase->getPicYuvRec()->getHeight() - pcPicBase->getPicYuvRec()->getPicCropTopOffset() - pcPicBase->getPicYuvRec()->getPicCropBottomOffset();
592
593  Int iEWidth   = getPicYuvRec()->getWidth() -  getPicYuvRec()->getPicCropLeftOffset() - getPicYuvRec()->getPicCropRightOffset();
594  Int iEHeight  = getPicYuvRec()->getHeight() - getPicYuvRec()->getPicCropTopOffset() -  getPicYuvRec()->getPicCropBottomOffset();
595 
596  UInt upSampleRatio = 0;
597  if(iEWidth == iBWidth && iEHeight == iBHeight)
598  {
599    upSampleRatio = 2;
600  }
601  else if(2*iEWidth == 3*iBWidth && 2*iEHeight == 3*iBHeight)
602  {
603    upSampleRatio = 3;
604  }
605  else if(iEWidth == 2*iBWidth && iEHeight == 2*iBHeight)
606  {
607    upSampleRatio = 4;
608  }
609  else
610  {
611    assert(0);
612  }
613
614  for(UInt cuIdx = 0; cuIdx < getPicSym()->getNumberOfCUsInFrame(); cuIdx++)  //each LCU
615  {
616    UInt uiNumPartitions   = 1<<(g_uiMaxCUDepth<<1);
617
618    TComDataCU*             pcCUDes = getCU(cuIdx);
619
620    UInt uiWidthMinPU      = g_uiMaxCUWidth/(1<<g_uiMaxCUDepth);
621    UInt uiHeightMinPU     = g_uiMaxCUHeight/(1<<g_uiMaxCUDepth);
622    Int unitNum = max (1, (Int)((16/uiWidthMinPU)*(16/uiHeightMinPU)) ); 
623
624    for(UInt uiAbsPartIdx = 0; uiAbsPartIdx < uiNumPartitions; uiAbsPartIdx+=unitNum )  //each 16x16 unit
625    {
626      //pixel position of each unit in up-sampled layer
627      UInt  uiPelX = pcCUDes->getCUPelX() + g_auiRasterToPelX[ g_auiZscanToRaster[uiAbsPartIdx] ];
628      UInt  uiPelY = pcCUDes->getCUPelY() + g_auiRasterToPelY[ g_auiZscanToRaster[uiAbsPartIdx] ];
629      UInt uiBaseCUAddr, uiBaseAbsPartIdx;
630         pcPicBase->deriveUnitIdxBase(uiPelX + 8, uiPelY + 8, upSampleRatio, uiBaseCUAddr, uiBaseAbsPartIdx);
631      if( (pcPicBase->getCU(uiBaseCUAddr)->getPredictionMode(uiBaseAbsPartIdx) != MODE_NONE) && (pcPicBase->getCU(uiBaseCUAddr)->getPredictionMode(uiBaseAbsPartIdx) != MODE_INTRA) )  //base layer unit not skip and invalid mode
632      {
633        for(UInt list = 0; list < 2; list++)  //each list
634        { 
635          TComMv cMv = pcPicBase->getCU(uiBaseCUAddr)->getCUMvField((RefPicList)list)->getMv(uiBaseAbsPartIdx);
636          Int refIdx = pcPicBase->getCU(uiBaseCUAddr)->getCUMvField((RefPicList)list)->getRefIdx(uiBaseAbsPartIdx);
637
638          Int Hor =  ((Int)upSampleRatio * cMv.getHor())/2 ;
639          Int Ver =  ((Int)upSampleRatio * cMv.getVer())/2 ;
640
641          TComMv cScaledMv(Hor, Ver);
642          TComMvField sMvField;
643          sMvField.setMvField(cScaledMv, refIdx);
644
645          pcCUDes->getCUMvField((RefPicList)list)->setMvField(sMvField, uiAbsPartIdx);
646          pcCUDes->setPredictionMode(uiAbsPartIdx, MODE_INTER);
647        }
648      }
649      else
650      {
651        TComMvField zeroMvField;  //zero MV and invalid reference index
652        pcCUDes->getCUMvField(REF_PIC_LIST_0)->setMvField(zeroMvField, uiAbsPartIdx);
653        pcCUDes->getCUMvField(REF_PIC_LIST_1)->setMvField(zeroMvField, uiAbsPartIdx);
654        pcCUDes->setPredictionMode(uiAbsPartIdx, MODE_INTRA);
655      }
656
657      for(UInt i = 1; i < unitNum; i++ ) 
658      {
659        pcCUDes->getCUMvField(REF_PIC_LIST_0)->setMvField(pcCUDes->getCUMvField(REF_PIC_LIST_0)->getMv(uiAbsPartIdx), pcCUDes->getCUMvField(REF_PIC_LIST_0)->getRefIdx(uiAbsPartIdx), uiAbsPartIdx + i);
660        pcCUDes->getCUMvField(REF_PIC_LIST_1)->setMvField(pcCUDes->getCUMvField(REF_PIC_LIST_1)->getMv(uiAbsPartIdx), pcCUDes->getCUMvField(REF_PIC_LIST_1)->getRefIdx(uiAbsPartIdx), uiAbsPartIdx + i);
661        pcCUDes->setPredictionMode(uiAbsPartIdx+i, pcCUDes->getPredictionMode(uiAbsPartIdx))  ;
662      }
663    }
664      memset( pcCUDes->getPartitionSize(), SIZE_2Nx2N, sizeof(char)*uiNumPartitions);
665  }
666}
667#endif
668
669#endif
670
671//! \}
Note: See TracBrowser for help on using the repository browser.