source: SHVCSoftware/trunk/source/Lib/TLibCommon/TComPicSym.cpp @ 548

Last change on this file since 548 was 540, checked in by seregin, 11 years ago

merge SHM-4.1-dev branch

  • Property svn:eol-style set to native
File size: 15.9 KB
Line 
1/* The copyright in this software is being made available under the BSD
2 * License, included below. This software may be subject to other third party
3 * and contributor rights, including patent rights, and no such rights are
4 * granted under this license. 
5 *
6 * Copyright (c) 2010-2013, ITU/ISO/IEC
7 * All rights reserved.
8 *
9 * Redistribution and use in source and binary forms, with or without
10 * modification, are permitted provided that the following conditions are met:
11 *
12 *  * Redistributions of source code must retain the above copyright notice,
13 *    this list of conditions and the following disclaimer.
14 *  * Redistributions in binary form must reproduce the above copyright notice,
15 *    this list of conditions and the following disclaimer in the documentation
16 *    and/or other materials provided with the distribution.
17 *  * Neither the name of the ITU/ISO/IEC nor the names of its contributors may
18 *    be used to endorse or promote products derived from this software without
19 *    specific prior written permission.
20 *
21 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
22 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
23 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
24 * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS
25 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
26 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
27 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
28 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
29 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
30 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
31 * THE POSSIBILITY OF SUCH DAMAGE.
32 */
33
34/** \file     TComPicSym.cpp
35    \brief    picture symbol class
36*/
37
38#include "TComPicSym.h"
39#include "TComSampleAdaptiveOffset.h"
40
41//! \ingroup TLibCommon
42//! \{
43
44// ====================================================================================================================
45// Constructor / destructor / create / destroy
46// ====================================================================================================================
47
48TComPicSym::TComPicSym()
49:m_uiWidthInCU(0)
50,m_uiHeightInCU(0)
51,m_uiMaxCUWidth(0)
52,m_uiMaxCUHeight(0)
53,m_uiMinCUWidth(0)
54,m_uiMinCUHeight(0)
55,m_uhTotalDepth(0)
56,m_uiNumPartitions(0)
57,m_uiNumPartInWidth(0)
58,m_uiNumPartInHeight(0)
59,m_uiNumCUsInFrame(0)
60,m_apcTComSlice(NULL)
61,m_uiNumAllocatedSlice (0)
62,m_apcTComDataCU (NULL)
63,m_iNumColumnsMinus1 (0)
64,m_iNumRowsMinus1(0)
65,m_apcTComTile(NULL)
66,m_puiCUOrderMap(0)
67,m_puiTileIdxMap(NULL)
68,m_puiInverseCUOrderMap(NULL)
69#if HM_CLEANUP_SAO
70,m_saoBlkParams(NULL)
71#endif
72{};
73
74
75Void TComPicSym::create  ( Int iPicWidth, Int iPicHeight, UInt uiMaxWidth, UInt uiMaxHeight, UInt uiMaxDepth )
76{
77  UInt i;
78
79  m_uhTotalDepth      = uiMaxDepth;
80  m_uiNumPartitions   = 1<<(m_uhTotalDepth<<1);
81 
82  m_uiMaxCUWidth      = uiMaxWidth;
83  m_uiMaxCUHeight     = uiMaxHeight;
84 
85  m_uiMinCUWidth      = uiMaxWidth  >> m_uhTotalDepth;
86  m_uiMinCUHeight     = uiMaxHeight >> m_uhTotalDepth;
87 
88  m_uiNumPartInWidth  = m_uiMaxCUWidth  / m_uiMinCUWidth;
89  m_uiNumPartInHeight = m_uiMaxCUHeight / m_uiMinCUHeight;
90 
91  m_uiWidthInCU       = ( iPicWidth %m_uiMaxCUWidth  ) ? iPicWidth /m_uiMaxCUWidth  + 1 : iPicWidth /m_uiMaxCUWidth;
92  m_uiHeightInCU      = ( iPicHeight%m_uiMaxCUHeight ) ? iPicHeight/m_uiMaxCUHeight + 1 : iPicHeight/m_uiMaxCUHeight;
93 
94  m_uiNumCUsInFrame   = m_uiWidthInCU * m_uiHeightInCU;
95  m_apcTComDataCU     = new TComDataCU*[m_uiNumCUsInFrame];
96 
97  if (m_uiNumAllocatedSlice>0)
98  {
99    for ( i=0; i<m_uiNumAllocatedSlice ; i++ )
100    {
101      delete m_apcTComSlice[i];
102    }
103    delete [] m_apcTComSlice;
104  }
105  m_apcTComSlice      = new TComSlice*[m_uiNumCUsInFrame*m_uiNumPartitions]; 
106  m_apcTComSlice[0]   = new TComSlice;
107  m_uiNumAllocatedSlice = 1;
108  for ( i=0; i<m_uiNumCUsInFrame ; i++ )
109  {
110    m_apcTComDataCU[i] = new TComDataCU;
111    m_apcTComDataCU[i]->create( m_uiNumPartitions, m_uiMaxCUWidth, m_uiMaxCUHeight, false, m_uiMaxCUWidth >> m_uhTotalDepth
112#if ADAPTIVE_QP_SELECTION
113      , true
114#endif     
115      );
116  }
117
118  m_puiCUOrderMap = new UInt[m_uiNumCUsInFrame+1];
119  m_puiTileIdxMap = new UInt[m_uiNumCUsInFrame];
120#if N0383_IL_CONSTRAINED_TILE_SETS_SEI
121  m_piTileSetIdxMap = new Int[m_uiNumCUsInFrame];
122  m_pucTileSetType = new UChar[m_uiNumCUsInFrame];
123  m_pbSkippedTileSetFlag = new Bool[m_uiNumCUsInFrame];
124#endif
125  m_puiInverseCUOrderMap = new UInt[m_uiNumCUsInFrame+1];
126
127  for( i=0; i<m_uiNumCUsInFrame; i++ )
128  {
129    m_puiCUOrderMap[i] = i;
130    m_puiInverseCUOrderMap[i] = i;
131  }
132
133#if HM_CLEANUP_SAO
134  m_saoBlkParams = new SAOBlkParam[m_uiNumCUsInFrame];
135#else
136  m_saoParam = NULL;
137#endif
138}
139
140Void TComPicSym::destroy()
141{
142  if (m_uiNumAllocatedSlice>0)
143  {
144    for (Int i = 0; i<m_uiNumAllocatedSlice ; i++ )
145    {
146      delete m_apcTComSlice[i];
147    }
148    delete [] m_apcTComSlice;
149  }
150  m_apcTComSlice = NULL;
151 
152  for (Int i = 0; i < m_uiNumCUsInFrame; i++)
153  {
154    m_apcTComDataCU[i]->destroy();
155    delete m_apcTComDataCU[i];
156    m_apcTComDataCU[i] = NULL;
157  }
158  delete [] m_apcTComDataCU;
159  m_apcTComDataCU = NULL;
160
161#if SVC_EXTENSION
162  if( m_apcTComTile )
163  {
164#endif
165  for(Int i = 0; i < (m_iNumColumnsMinus1+1)*(m_iNumRowsMinus1+1); i++ )
166  {
167    delete m_apcTComTile[i];
168  }
169  delete [] m_apcTComTile;
170#if SVC_EXTENSION
171  }
172#endif
173
174  m_apcTComTile = NULL;
175
176  delete [] m_puiCUOrderMap;
177  m_puiCUOrderMap = NULL;
178
179  delete [] m_puiTileIdxMap;
180  m_puiTileIdxMap = NULL;
181#if N0383_IL_CONSTRAINED_TILE_SETS_SEI
182  delete [] m_piTileSetIdxMap;
183  m_piTileSetIdxMap = NULL;
184  delete [] m_pucTileSetType;
185  m_pucTileSetType = NULL;
186  delete [] m_pbSkippedTileSetFlag;
187  m_pbSkippedTileSetFlag = NULL;
188#endif
189
190  delete [] m_puiInverseCUOrderMap;
191  m_puiInverseCUOrderMap = NULL;
192 
193#if HM_CLEANUP_SAO
194  if(m_saoBlkParams)
195  {
196    delete[] m_saoBlkParams; m_saoBlkParams = NULL;
197  }
198#else
199  if (m_saoParam)
200  {
201    TComSampleAdaptiveOffset::freeSaoParam(m_saoParam);
202    delete m_saoParam;
203    m_saoParam = NULL;
204  }
205#endif
206}
207
208Void TComPicSym::allocateNewSlice()
209{
210  m_apcTComSlice[m_uiNumAllocatedSlice ++] = new TComSlice;
211  if (m_uiNumAllocatedSlice>=2)
212  {
213    m_apcTComSlice[m_uiNumAllocatedSlice-1]->copySliceInfo( m_apcTComSlice[m_uiNumAllocatedSlice-2] );
214#if SVC_EXTENSION
215    m_apcTComSlice[m_uiNumAllocatedSlice-1]->initSlice( m_apcTComSlice[m_uiNumAllocatedSlice-1]->getLayerId() );
216#else
217    m_apcTComSlice[m_uiNumAllocatedSlice-1]->initSlice();
218#endif
219  }
220}
221
222Void TComPicSym::clearSliceBuffer()
223{
224  UInt i;
225  for (i = 1; i < m_uiNumAllocatedSlice; i++)
226  {
227    delete m_apcTComSlice[i];
228  }
229  m_uiNumAllocatedSlice = 1;
230}
231
232UInt TComPicSym::getPicSCUEncOrder( UInt SCUAddr )
233{ 
234  return getInverseCUOrderMap(SCUAddr/m_uiNumPartitions)*m_uiNumPartitions + SCUAddr%m_uiNumPartitions; 
235}
236
237UInt TComPicSym::getPicSCUAddr( UInt SCUEncOrder )
238{
239  return getCUOrderMap(SCUEncOrder/m_uiNumPartitions)*m_uiNumPartitions + SCUEncOrder%m_uiNumPartitions;
240}
241
242Void TComPicSym::xCreateTComTileArray()
243{
244  m_apcTComTile = new TComTile*[(m_iNumColumnsMinus1+1)*(m_iNumRowsMinus1+1)];
245  for( UInt i=0; i<(m_iNumColumnsMinus1+1)*(m_iNumRowsMinus1+1); i++ )
246  {
247    m_apcTComTile[i] = new TComTile;
248  }
249}
250
251Void TComPicSym::xInitTiles()
252{
253  UInt  uiTileIdx;
254  UInt  uiColumnIdx = 0;
255  UInt  uiRowIdx = 0;
256  UInt  uiRightEdgePosInCU;
257  UInt  uiBottomEdgePosInCU;
258  Int   i, j;
259
260  //initialize each tile of the current picture
261  for( uiRowIdx=0; uiRowIdx < m_iNumRowsMinus1+1; uiRowIdx++ )
262  {
263    for( uiColumnIdx=0; uiColumnIdx < m_iNumColumnsMinus1+1; uiColumnIdx++ )
264    {
265      uiTileIdx = uiRowIdx * (m_iNumColumnsMinus1+1) + uiColumnIdx;
266
267      //initialize the RightEdgePosInCU for each tile
268      uiRightEdgePosInCU = 0;
269      for( i=0; i <= uiColumnIdx; i++ )
270      {
271        uiRightEdgePosInCU += this->getTComTile(uiRowIdx * (m_iNumColumnsMinus1+1) + i)->getTileWidth();
272      }
273      this->getTComTile(uiTileIdx)->setRightEdgePosInCU(uiRightEdgePosInCU-1);
274
275      //initialize the BottomEdgePosInCU for each tile
276      uiBottomEdgePosInCU = 0;
277      for( i=0; i <= uiRowIdx; i++ )
278      {
279        uiBottomEdgePosInCU += this->getTComTile(i * (m_iNumColumnsMinus1+1) + uiColumnIdx)->getTileHeight();
280      }
281      this->getTComTile(uiTileIdx)->setBottomEdgePosInCU(uiBottomEdgePosInCU-1);
282
283      //initialize the FirstCUAddr for each tile
284      this->getTComTile(uiTileIdx)->setFirstCUAddr( (this->getTComTile(uiTileIdx)->getBottomEdgePosInCU() - this->getTComTile(uiTileIdx)->getTileHeight() +1)*m_uiWidthInCU + 
285        this->getTComTile(uiTileIdx)->getRightEdgePosInCU() - this->getTComTile(uiTileIdx)->getTileWidth() + 1);
286    }
287  }
288
289  //initialize the TileIdxMap
290  for( i=0; i<m_uiNumCUsInFrame; i++)
291  {
292    for(j=0; j < m_iNumColumnsMinus1+1; j++)
293    {
294      if(i % m_uiWidthInCU <= this->getTComTile(j)->getRightEdgePosInCU())
295      {
296        uiColumnIdx = j;
297        j = m_iNumColumnsMinus1+1;
298      }
299    }
300    for(j=0; j < m_iNumRowsMinus1+1; j++)
301    {
302      if(i/m_uiWidthInCU <= this->getTComTile(j*(m_iNumColumnsMinus1 + 1))->getBottomEdgePosInCU())
303      {
304        uiRowIdx = j;
305        j = m_iNumRowsMinus1 + 1;
306      }
307    }
308    m_puiTileIdxMap[i] = uiRowIdx * (m_iNumColumnsMinus1 + 1) + uiColumnIdx;
309  }
310
311}
312
313UInt TComPicSym::xCalculateNxtCUAddr( UInt uiCurrCUAddr )
314{
315  UInt  uiNxtCUAddr;
316  UInt  uiTileIdx;
317 
318  //get the tile index for the current LCU
319  uiTileIdx = this->getTileIdxMap(uiCurrCUAddr);
320
321  //get the raster scan address for the next LCU
322  if( uiCurrCUAddr % m_uiWidthInCU == this->getTComTile(uiTileIdx)->getRightEdgePosInCU() && uiCurrCUAddr / m_uiWidthInCU == this->getTComTile(uiTileIdx)->getBottomEdgePosInCU() )
323  //the current LCU is the last LCU of the tile
324  {
325    if(uiTileIdx == (m_iNumColumnsMinus1+1)*(m_iNumRowsMinus1+1)-1)
326    {
327      uiNxtCUAddr = m_uiNumCUsInFrame;
328    }
329    else
330    {
331      uiNxtCUAddr = this->getTComTile(uiTileIdx+1)->getFirstCUAddr();
332    }
333  } 
334  else //the current LCU is not the last LCU of the tile
335  {
336    if( uiCurrCUAddr % m_uiWidthInCU == this->getTComTile(uiTileIdx)->getRightEdgePosInCU() )  //the current LCU is on the rightmost edge of the tile
337    {
338      uiNxtCUAddr = uiCurrCUAddr + m_uiWidthInCU - this->getTComTile(uiTileIdx)->getTileWidth() + 1;
339    }
340    else
341    {
342      uiNxtCUAddr = uiCurrCUAddr + 1;
343    }
344  }
345
346  return uiNxtCUAddr;
347}
348
349
350#if HM_CLEANUP_SAO
351Void TComPicSym::deriveLoopFilterBoundaryAvailibility(Int ctu,
352                                                      Bool& isLeftAvail,
353                                                      Bool& isRightAvail,
354                                                      Bool& isAboveAvail,
355                                                      Bool& isBelowAvail,
356                                                      Bool& isAboveLeftAvail,
357                                                      Bool& isAboveRightAvail,
358                                                      Bool& isBelowLeftAvail,
359                                                      Bool& isBelowRightAvail
360                                                      )
361{
362
363  isLeftAvail      = (ctu % m_uiWidthInCU != 0);
364  isRightAvail     = (ctu % m_uiWidthInCU != m_uiWidthInCU-1);
365  isAboveAvail     = (ctu >= m_uiWidthInCU );
366  isBelowAvail     = (ctu <  m_uiNumCUsInFrame - m_uiWidthInCU);
367  isAboveLeftAvail = (isAboveAvail && isLeftAvail);
368  isAboveRightAvail= (isAboveAvail && isRightAvail);
369  isBelowLeftAvail = (isBelowAvail && isLeftAvail);
370  isBelowRightAvail= (isBelowAvail && isRightAvail);
371
372  Bool isLoopFiltAcrossTilePPS = getCU(ctu)->getSlice()->getPPS()->getLoopFilterAcrossTilesEnabledFlag();
373
374  {
375    TComDataCU* ctuCurr  = getCU(ctu);
376    TComDataCU* ctuLeft  = isLeftAvail ?getCU(ctu-1):NULL;
377    TComDataCU* ctuRight = isRightAvail?getCU(ctu+1):NULL;
378    TComDataCU* ctuAbove = isAboveAvail?getCU(ctu-m_uiWidthInCU):NULL;
379    TComDataCU* ctuBelow = isBelowAvail?getCU(ctu+m_uiWidthInCU):NULL;
380    TComDataCU* ctuAboveLeft  = isAboveLeftAvail ? getCU(ctu-m_uiWidthInCU-1):NULL;
381    TComDataCU* ctuAboveRigtht= isAboveRightAvail? getCU(ctu-m_uiWidthInCU+1):NULL;
382    TComDataCU* ctuBelowLeft  = isBelowLeftAvail ? getCU(ctu+m_uiWidthInCU-1):NULL;
383    TComDataCU* ctuBelowRight = isBelowRightAvail? getCU(ctu+m_uiWidthInCU+1):NULL;
384
385    {
386      //left
387      if(ctuLeft != NULL)
388      {
389        isLeftAvail = (ctuCurr->getSlice()->getSliceCurStartCUAddr() != ctuLeft->getSlice()->getSliceCurStartCUAddr())?ctuCurr->getSlice()->getLFCrossSliceBoundaryFlag():true;
390      }
391      //above
392      if(ctuAbove != NULL)
393      {
394        isAboveAvail = (ctuCurr->getSlice()->getSliceCurStartCUAddr() != ctuAbove->getSlice()->getSliceCurStartCUAddr())?ctuCurr->getSlice()->getLFCrossSliceBoundaryFlag():true;
395      }
396      //right
397      if(ctuRight != NULL)
398      {
399        isRightAvail = (ctuCurr->getSlice()->getSliceCurStartCUAddr() != ctuRight->getSlice()->getSliceCurStartCUAddr())?ctuRight->getSlice()->getLFCrossSliceBoundaryFlag():true;
400      }
401      //below
402      if(ctuBelow != NULL)
403      {
404        isBelowAvail = (ctuCurr->getSlice()->getSliceCurStartCUAddr() != ctuBelow->getSlice()->getSliceCurStartCUAddr())?ctuBelow->getSlice()->getLFCrossSliceBoundaryFlag():true;
405      }
406      //above-left
407      if(ctuAboveLeft != NULL)
408      {
409        isAboveLeftAvail = (ctuCurr->getSlice()->getSliceCurStartCUAddr() != ctuAboveLeft->getSlice()->getSliceCurStartCUAddr())?ctuCurr->getSlice()->getLFCrossSliceBoundaryFlag():true;
410      }
411      //below-right
412      if(ctuBelowRight != NULL)
413      {
414        isBelowRightAvail = (ctuCurr->getSlice()->getSliceCurStartCUAddr() != ctuBelowRight->getSlice()->getSliceCurStartCUAddr())?ctuBelowRight->getSlice()->getLFCrossSliceBoundaryFlag():true;
415      }
416
417
418      //above-right
419      if(ctuAboveRigtht != NULL)
420      {
421        Int curSliceStartTS  = getCUOrderMap(ctuCurr->getSlice()->getSliceCurStartCUAddr()/m_uiNumPartitions);
422        Int aboveRigthtSliceStartTS = getCUOrderMap(ctuAboveRigtht->getSlice()->getSliceCurStartCUAddr()/m_uiNumPartitions);
423
424        isAboveRightAvail = (curSliceStartTS == aboveRigthtSliceStartTS)?(true):
425          (
426          (curSliceStartTS > aboveRigthtSliceStartTS)?(ctuCurr->getSlice()->getLFCrossSliceBoundaryFlag())
427          :(ctuAboveRigtht->getSlice()->getLFCrossSliceBoundaryFlag())
428          );         
429      }
430      //below-left
431      if(ctuBelowLeft != NULL)
432      {
433        Int curSliceStartTS       = getCUOrderMap(ctuCurr->getSlice()->getSliceCurStartCUAddr()/m_uiNumPartitions);
434        Int belowLeftSliceStartTS = getCUOrderMap(ctuBelowLeft->getSlice()->getSliceCurStartCUAddr()/m_uiNumPartitions);
435
436        isBelowLeftAvail = (curSliceStartTS == belowLeftSliceStartTS)?(true):
437          (
438          (curSliceStartTS > belowLeftSliceStartTS)?(ctuCurr->getSlice()->getLFCrossSliceBoundaryFlag())
439          :(ctuBelowLeft->getSlice()->getLFCrossSliceBoundaryFlag())
440          );
441      }       
442    }
443
444    if(!isLoopFiltAcrossTilePPS)
445    {     
446      isLeftAvail      = (!isLeftAvail      ) ?false:(getTileIdxMap( ctuLeft->getAddr()         ) == getTileIdxMap( ctu ));
447      isAboveAvail     = (!isAboveAvail     ) ?false:(getTileIdxMap( ctuAbove->getAddr()        ) == getTileIdxMap( ctu ));
448      isRightAvail     = (!isRightAvail     ) ?false:(getTileIdxMap( ctuRight->getAddr()        ) == getTileIdxMap( ctu ));
449      isBelowAvail     = (!isBelowAvail     ) ?false:(getTileIdxMap( ctuBelow->getAddr()        ) == getTileIdxMap( ctu ));
450      isAboveLeftAvail = (!isAboveLeftAvail ) ?false:(getTileIdxMap( ctuAboveLeft->getAddr()    ) == getTileIdxMap( ctu ));
451      isAboveRightAvail= (!isAboveRightAvail) ?false:(getTileIdxMap( ctuAboveRigtht->getAddr()  ) == getTileIdxMap( ctu ));
452      isBelowLeftAvail = (!isBelowLeftAvail ) ?false:(getTileIdxMap( ctuBelowLeft->getAddr()    ) == getTileIdxMap( ctu ));
453      isBelowRightAvail= (!isBelowRightAvail) ?false:(getTileIdxMap( ctuBelowRight->getAddr()   ) == getTileIdxMap( ctu ));
454    }
455  }
456
457}
458#else
459Void TComPicSym::allocSaoParam(TComSampleAdaptiveOffset *sao)
460{
461  m_saoParam = new SAOParam;
462  sao->allocSaoParam(m_saoParam);
463}
464#endif
465
466TComTile::TComTile()
467{
468}
469
470TComTile::~TComTile()
471{
472}
473//! \}
Note: See TracBrowser for help on using the repository browser.