source: SHVCSoftware/branches/SHM-dev/source/Lib/TLibCommon/TComPattern.cpp @ 1256

Last change on this file since 1256 was 1246, checked in by seregin, 10 years ago

port rev 4240

  • Property svn:eol-style set to native
File size: 24.2 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-2014, 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     TComPattern.cpp
35    \brief    neighbouring pixel access classes
36*/
37
38#include "TComPic.h"
39#include "TComPattern.h"
40#include "TComDataCU.h"
41#include "TComTU.h"
42#include "Debug.h"
43#include "TComPrediction.h"
44
45//! \ingroup TLibCommon
46//! \{
47
48// Forward declarations
49
50/// padding of unavailable reference samples for intra prediction
51#if O0043_BEST_EFFORT_DECODING
52Void fillReferenceSamples( const Int bitDepth, const Int bitDepthDelta, TComDataCU* pcCU, const Pel* piRoiOrigin, Pel* piAdiTemp, const Bool* bNeighborFlags,
53#else
54Void fillReferenceSamples( const Int bitDepth, TComDataCU* pcCU, const Pel* piRoiOrigin, Pel* piAdiTemp, const Bool* bNeighborFlags,
55#endif
56                           const Int iNumIntraNeighbor, const Int unitWidth, const Int unitHeight, const Int iAboveUnits, const Int iLeftUnits,
57                           const UInt uiCuWidth, const UInt uiCuHeight, const UInt uiWidth, const UInt uiHeight, const Int iPicStride,
58                           const ChannelType chType, const ChromaFormat chFmt );
59
60/// constrained intra prediction
61Bool  isAboveLeftAvailable  ( TComDataCU* pcCU, UInt uiPartIdxLT );
62Int   isAboveAvailable      ( TComDataCU* pcCU, UInt uiPartIdxLT, UInt uiPartIdxRT, Bool* bValidFlags );
63Int   isLeftAvailable       ( TComDataCU* pcCU, UInt uiPartIdxLT, UInt uiPartIdxLB, Bool* bValidFlags );
64Int   isAboveRightAvailable ( TComDataCU* pcCU, UInt uiPartIdxLT, UInt uiPartIdxRT, Bool* bValidFlags );
65Int   isBelowLeftAvailable  ( TComDataCU* pcCU, UInt uiPartIdxLT, UInt uiPartIdxLB, Bool* bValidFlags );
66
67
68// ====================================================================================================================
69// Public member functions (TComPatternParam)
70// ====================================================================================================================
71
72/** \param  piTexture     pixel data
73 \param  iRoiWidth     pattern width
74 \param  iRoiHeight    pattern height
75 \param  iStride       buffer stride
76 \param  iOffsetLeft   neighbour offset (left)
77 \param  iOffsetRight  neighbour offset (right)
78 \param  iOffsetAbove  neighbour offset (above)
79 \param  iOffsetBottom neighbour offset (bottom)
80 */
81Void TComPatternParam::setPatternParamPel ( Pel* piTexture,
82                                           Int iRoiWidth,
83                                           Int iRoiHeight,
84                                           Int iStride
85                                           )
86{
87  m_piROIOrigin    = piTexture;
88  m_iROIWidth       = iRoiWidth;
89  m_iROIHeight      = iRoiHeight;
90  m_iPatternStride  = iStride;
91}
92
93// ====================================================================================================================
94// Public member functions (TComPattern)
95// ====================================================================================================================
96
97Void TComPattern::initPattern (Pel* piY,
98                               Int iRoiWidth,
99                               Int iRoiHeight,
100                               Int iStride)
101{
102  m_cPatternY. setPatternParamPel( piY,  iRoiWidth, iRoiHeight, iStride);
103}
104
105
106// TODO: move this function to TComPrediction.cpp.
107Void TComPrediction::initAdiPatternChType( TComTU &rTu, Bool& bAbove, Bool& bLeft, const ComponentID compID, const Bool bFilterRefSamples DEBUG_STRING_FN_DECLARE(sDebug))
108{
109  const ChannelType chType    = toChannelType(compID);
110
111  TComDataCU *pcCU=rTu.getCU();
112  const UInt uiZorderIdxInPart=rTu.GetAbsPartIdxTU();
113  const UInt uiTuWidth        = rTu.getRect(compID).width;
114  const UInt uiTuHeight       = rTu.getRect(compID).height;
115  const UInt uiTuWidth2       = uiTuWidth  << 1;
116  const UInt uiTuHeight2      = uiTuHeight << 1;
117
118  const Int  iBaseUnitSize    = g_uiMaxCUWidth >> g_uiMaxCUDepth;
119  const Int  iUnitWidth       = iBaseUnitSize  >> pcCU->getPic()->getPicYuvRec()->getComponentScaleX(compID);
120  const Int  iUnitHeight      = iBaseUnitSize  >> pcCU->getPic()->getPicYuvRec()->getComponentScaleY(compID);
121  const Int  iTUWidthInUnits  = uiTuWidth  / iUnitWidth;
122  const Int  iTUHeightInUnits = uiTuHeight / iUnitHeight;
123  const Int  iAboveUnits      = iTUWidthInUnits  << 1;
124  const Int  iLeftUnits       = iTUHeightInUnits << 1;
125
126  assert(iTUHeightInUnits > 0 && iTUWidthInUnits > 0);
127
128  const Int  iPartIdxStride   = pcCU->getPic()->getNumPartInCtuWidth();
129  const UInt uiPartIdxLT      = pcCU->getZorderIdxInCtu() + uiZorderIdxInPart;
130  const UInt uiPartIdxRT      = g_auiRasterToZscan[ g_auiZscanToRaster[ uiPartIdxLT ] +   iTUWidthInUnits  - 1                   ];
131  const UInt uiPartIdxLB      = g_auiRasterToZscan[ g_auiZscanToRaster[ uiPartIdxLT ] + ((iTUHeightInUnits - 1) * iPartIdxStride)];
132
133  Int   iPicStride = pcCU->getPic()->getStride(compID);
134  Bool  bNeighborFlags[4 * MAX_NUM_SPU_W + 1];
135  Int   iNumIntraNeighbor = 0;
136
137  bNeighborFlags[iLeftUnits] = isAboveLeftAvailable( pcCU, uiPartIdxLT );
138  iNumIntraNeighbor += bNeighborFlags[iLeftUnits] ? 1 : 0;
139  iNumIntraNeighbor  += isAboveAvailable     ( pcCU, uiPartIdxLT, uiPartIdxRT, (bNeighborFlags + iLeftUnits + 1)                    );
140  iNumIntraNeighbor  += isAboveRightAvailable( pcCU, uiPartIdxLT, uiPartIdxRT, (bNeighborFlags + iLeftUnits + 1 + iTUWidthInUnits ) );
141  iNumIntraNeighbor  += isLeftAvailable      ( pcCU, uiPartIdxLT, uiPartIdxLB, (bNeighborFlags + iLeftUnits - 1)                    );
142  iNumIntraNeighbor  += isBelowLeftAvailable ( pcCU, uiPartIdxLT, uiPartIdxLB, (bNeighborFlags + iLeftUnits - 1 - iTUHeightInUnits) );
143
144  bAbove = true;
145  bLeft  = true;
146
147  const ChromaFormat chFmt       = rTu.GetChromaFormat();
148  const UInt         uiROIWidth  = uiTuWidth2+1;
149  const UInt         uiROIHeight = uiTuHeight2+1;
150
151  assert(uiROIWidth*uiROIHeight <= m_iYuvExtSize);
152
153#ifdef DEBUG_STRING
154  std::stringstream ss(stringstream::out);
155#endif
156
157  {
158    Pel *piAdiTemp   = m_piYuvExt[compID][PRED_BUF_UNFILTERED];
159    Pel *piRoiOrigin = pcCU->getPic()->getPicYuvRec()->getAddr(compID, pcCU->getCtuRsAddr(), pcCU->getZorderIdxInCtu()+uiZorderIdxInPart);
160#if O0043_BEST_EFFORT_DECODING
161    fillReferenceSamples (g_bitDepthInStream[chType], g_bitDepthInStream[chType] - g_bitDepth[chType], pcCU, piRoiOrigin, piAdiTemp, bNeighborFlags, iNumIntraNeighbor,  iUnitWidth, iUnitHeight, iAboveUnits, iLeftUnits,
162#else
163    fillReferenceSamples (g_bitDepth[chType], pcCU, piRoiOrigin, piAdiTemp, bNeighborFlags, iNumIntraNeighbor,  iUnitWidth, iUnitHeight, iAboveUnits, iLeftUnits,
164#endif
165                          uiTuWidth, uiTuHeight, uiROIWidth, uiROIHeight, iPicStride, toChannelType(compID), chFmt);
166
167
168#ifdef DEBUG_STRING
169    if (DebugOptionList::DebugString_Pred.getInt()&DebugStringGetPredModeMask(MODE_INTRA))
170    {
171      ss << "###: generating Ref Samples for channel " << compID << " and " << rTu.getRect(compID).width << " x " << rTu.getRect(compID).height << "\n";
172      for (UInt y=0; y<uiROIHeight; y++)
173      {
174        ss << "###: - ";
175        for (UInt x=0; x<uiROIWidth; x++)
176        {
177          if (x==0 || y==0)
178          {
179            ss << piAdiTemp[y*uiROIWidth + x] << ", ";
180//          if (x%16==15) ss << "\nPart size: ~ ";
181          }
182        }
183        ss << "\n";
184      }
185    }
186#endif
187
188    if (bFilterRefSamples)
189    {
190      // generate filtered intra prediction samples
191
192            Int          stride    = uiROIWidth;
193      const Pel         *piSrcPtr  = piAdiTemp                             + (stride * uiTuHeight2); // bottom left
194            Pel         *piDestPtr = m_piYuvExt[compID][PRED_BUF_FILTERED] + (stride * uiTuHeight2); // bottom left
195
196      //------------------------------------------------
197
198      Bool useStrongIntraSmoothing = isLuma(chType) && pcCU->getSlice()->getSPS()->getUseStrongIntraSmoothing();
199
200      const Pel bottomLeft = piAdiTemp[stride * uiTuHeight2];
201      const Pel topLeft    = piAdiTemp[0];
202      const Pel topRight   = piAdiTemp[uiTuWidth2];
203
204      if (useStrongIntraSmoothing)
205      {
206#if O0043_BEST_EFFORT_DECODING
207        const Int  threshold     = 1 << (g_bitDepthInStream[chType] - 5);
208#else
209        const Int  threshold     = 1 << (g_bitDepth[chType] - 5);
210#endif
211        const Bool bilinearLeft  = abs((bottomLeft + topLeft ) - (2 * piAdiTemp[stride * uiTuHeight])) < threshold; //difference between the
212        const Bool bilinearAbove = abs((topLeft    + topRight) - (2 * piAdiTemp[         uiTuWidth ])) < threshold; //ends and the middle
213        if ((uiTuWidth < 32) || (!bilinearLeft) || (!bilinearAbove))
214        {
215          useStrongIntraSmoothing = false;
216        }
217      }
218
219      *piDestPtr = *piSrcPtr; // bottom left is not filtered
220      piDestPtr -= stride;
221      piSrcPtr  -= stride;
222
223      //------------------------------------------------
224
225      //left column (bottom to top)
226
227      if (useStrongIntraSmoothing)
228      {
229        const Int shift = g_aucConvertToBit[uiTuHeight] + 3; //log2(uiTuHeight2)
230
231        for(UInt i=1; i<uiTuHeight2; i++, piDestPtr-=stride)
232        {
233          *piDestPtr = (((uiTuHeight2 - i) * bottomLeft) + (i * topLeft) + uiTuHeight) >> shift;
234        }
235
236        piSrcPtr -= stride * (uiTuHeight2 - 1);
237      }
238      else
239      {
240        for(UInt i=1; i<uiTuHeight2; i++, piDestPtr-=stride, piSrcPtr-=stride)
241        {
242          *piDestPtr = ( piSrcPtr[stride] + 2*piSrcPtr[0] + piSrcPtr[-stride] + 2 ) >> 2;
243        }
244      }
245
246      //------------------------------------------------
247
248      //top-left
249
250      if (useStrongIntraSmoothing)
251      {
252        *piDestPtr = piSrcPtr[0];
253      }
254      else
255      {
256        *piDestPtr = ( piSrcPtr[stride] + 2*piSrcPtr[0] + piSrcPtr[1] + 2 ) >> 2;
257      }
258      piDestPtr += 1;
259      piSrcPtr  += 1;
260
261      //------------------------------------------------
262
263      //top row (left-to-right)
264
265      if (useStrongIntraSmoothing)
266      {
267        const Int shift = g_aucConvertToBit[uiTuWidth] + 3; //log2(uiTuWidth2)
268
269        for(UInt i=1; i<uiTuWidth2; i++, piDestPtr++)
270        {
271          *piDestPtr = (((uiTuWidth2 - i) * topLeft) + (i * topRight) + uiTuWidth) >> shift;
272        }
273
274        piSrcPtr += uiTuWidth2 - 1;
275      }
276      else
277      {
278        for(UInt i=1; i<uiTuWidth2; i++, piDestPtr++, piSrcPtr++)
279        {
280          *piDestPtr = ( piSrcPtr[1] + 2*piSrcPtr[0] + piSrcPtr[-1] + 2 ) >> 2;
281        }
282      }
283
284      //------------------------------------------------
285
286      *piDestPtr=*piSrcPtr; // far right is not filtered
287
288#ifdef DEBUG_STRING
289    if (DebugOptionList::DebugString_Pred.getInt()&DebugStringGetPredModeMask(MODE_INTRA))
290    {
291      ss << "###: filtered result for channel " << compID <<"\n";
292      for (UInt y=0; y<uiROIHeight; y++)
293      {
294        ss << "###: - ";
295        for (UInt x=0; x<uiROIWidth; x++)
296        {
297          if (x==0 || y==0)
298          {
299            ss << m_piYuvExt[compID][PRED_BUF_FILTERED][y*uiROIWidth + x] << ", ";
300//          if (x%16==15) ss << "\nPart size: ~ ";
301          }
302        }
303        ss << "\n";
304      }
305    }
306#endif
307
308
309    }
310  }
311  DEBUG_STRING_APPEND(sDebug, ss.str())
312}
313
314#if O0043_BEST_EFFORT_DECODING
315Void fillReferenceSamples( const Int bitDepth, const Int bitDepthDelta, TComDataCU* pcCU, const Pel* piRoiOrigin, Pel* piAdiTemp, const Bool* bNeighborFlags,
316#else
317Void fillReferenceSamples( const Int bitDepth, TComDataCU* pcCU, const Pel* piRoiOrigin, Pel* piAdiTemp, const Bool* bNeighborFlags,
318#endif
319                           const Int iNumIntraNeighbor, const Int unitWidth, const Int unitHeight, const Int iAboveUnits, const Int iLeftUnits,
320                           const UInt uiCuWidth, const UInt uiCuHeight, const UInt uiWidth, const UInt uiHeight, const Int iPicStride,
321                           const ChannelType chType, const ChromaFormat chFmt )
322{
323  const Pel* piRoiTemp;
324  Int  i, j;
325  Int  iDCValue = 1 << (bitDepth - 1);
326  const Int iTotalUnits = iAboveUnits + iLeftUnits + 1; //+1 for top-left
327
328  if (iNumIntraNeighbor == 0)
329  {
330    // Fill border with DC value
331    for (i=0; i<uiWidth; i++)
332    {
333      piAdiTemp[i] = iDCValue;
334    }
335    for (i=1; i<uiHeight; i++)
336    {
337      piAdiTemp[i*uiWidth] = iDCValue;
338    }
339  }
340  else if (iNumIntraNeighbor == iTotalUnits)
341  {
342    // Fill top-left border and top and top right with rec. samples
343    piRoiTemp = piRoiOrigin - iPicStride - 1;
344
345    for (i=0; i<uiWidth; i++)
346    {
347#if O0043_BEST_EFFORT_DECODING
348      piAdiTemp[i] = piRoiTemp[i] << bitDepthDelta;
349#else
350      piAdiTemp[i] = piRoiTemp[i];
351#endif
352    }
353
354    // Fill left and below left border with rec. samples
355    piRoiTemp = piRoiOrigin - 1;
356
357    for (i=1; i<uiHeight; i++)
358    {
359#if O0043_BEST_EFFORT_DECODING
360      piAdiTemp[i*uiWidth] = (*(piRoiTemp)) << bitDepthDelta;
361#else
362      piAdiTemp[i*uiWidth] = *(piRoiTemp);
363#endif
364      piRoiTemp += iPicStride;
365    }
366  }
367  else // reference samples are partially available
368  {
369    // all above units have "unitWidth" samples each, all left/below-left units have "unitHeight" samples each
370    const Int  iTotalSamples = (iLeftUnits * unitHeight) + ((iAboveUnits + 1) * unitWidth);
371    Pel  piAdiLine[5 * MAX_CU_SIZE];
372    Pel  *piAdiLineTemp;
373    const Bool *pbNeighborFlags;
374
375
376    // Initialize
377    for (i=0; i<iTotalSamples; i++)
378    {
379      piAdiLine[i] = iDCValue;
380    }
381
382    // Fill top-left sample
383    piRoiTemp = piRoiOrigin - iPicStride - 1;
384    piAdiLineTemp = piAdiLine + (iLeftUnits * unitHeight);
385    pbNeighborFlags = bNeighborFlags + iLeftUnits;
386    if (*pbNeighborFlags)
387    {
388#if O0043_BEST_EFFORT_DECODING
389      Pel topLeftVal=piRoiTemp[0] << bitDepthDelta;
390#else
391      Pel topLeftVal=piRoiTemp[0];
392#endif
393      for (i=0; i<unitWidth; i++)
394      {
395        piAdiLineTemp[i] = topLeftVal;
396      }
397    }
398
399    // Fill left & below-left samples (downwards)
400    piRoiTemp += iPicStride;
401    piAdiLineTemp--;
402    pbNeighborFlags--;
403
404    for (j=0; j<iLeftUnits; j++)
405    {
406      if (*pbNeighborFlags)
407      {
408        for (i=0; i<unitHeight; i++)
409        {
410#if O0043_BEST_EFFORT_DECODING
411          piAdiLineTemp[-i] = piRoiTemp[i*iPicStride] << bitDepthDelta;
412#else
413          piAdiLineTemp[-i] = piRoiTemp[i*iPicStride];
414#endif
415        }
416      }
417      piRoiTemp += unitHeight*iPicStride;
418      piAdiLineTemp -= unitHeight;
419      pbNeighborFlags--;
420    }
421
422    // Fill above & above-right samples (left-to-right) (each unit has "unitWidth" samples)
423    piRoiTemp = piRoiOrigin - iPicStride;
424    // offset line buffer by iNumUints2*unitHeight (for left/below-left) + unitWidth (for above-left)
425    piAdiLineTemp = piAdiLine + (iLeftUnits * unitHeight) + unitWidth;
426    pbNeighborFlags = bNeighborFlags + iLeftUnits + 1;
427    for (j=0; j<iAboveUnits; j++)
428    {
429      if (*pbNeighborFlags)
430      {
431        for (i=0; i<unitWidth; i++)
432        {
433#if O0043_BEST_EFFORT_DECODING
434          piAdiLineTemp[i] = piRoiTemp[i] << bitDepthDelta;
435#else
436          piAdiLineTemp[i] = piRoiTemp[i];
437#endif
438        }
439      }
440      piRoiTemp += unitWidth;
441      piAdiLineTemp += unitWidth;
442      pbNeighborFlags++;
443    }
444
445    // Pad reference samples when necessary
446    Int iCurrJnit = 0;
447    Pel  *piAdiLineCur   = piAdiLine;
448    const UInt piAdiLineTopRowOffset = iLeftUnits * (unitHeight - unitWidth);
449
450    if (!bNeighborFlags[0])
451    {
452      // very bottom unit of bottom-left; at least one unit will be valid.
453      {
454        Int   iNext = 1;
455        while (iNext < iTotalUnits && !bNeighborFlags[iNext])
456        {
457          iNext++;
458        }
459        Pel *piAdiLineNext = piAdiLine + ((iNext < iLeftUnits) ? (iNext * unitHeight) : (piAdiLineTopRowOffset + (iNext * unitWidth)));
460        const Pel refSample = *piAdiLineNext;
461        // Pad unavailable samples with new value
462        Int iNextOrTop = std::min<Int>(iNext, iLeftUnits);
463        // fill left column
464        while (iCurrJnit < iNextOrTop)
465        {
466          for (i=0; i<unitHeight; i++)
467          {
468            piAdiLineCur[i] = refSample;
469          }
470          piAdiLineCur += unitHeight;
471          iCurrJnit++;
472        }
473        // fill top row
474        while (iCurrJnit < iNext)
475        {
476          for (i=0; i<unitWidth; i++)
477          {
478            piAdiLineCur[i] = refSample;
479          }
480          piAdiLineCur += unitWidth;
481          iCurrJnit++;
482        }
483      }
484    }
485
486    // pad all other reference samples.
487    while (iCurrJnit < iTotalUnits)
488    {
489      if (!bNeighborFlags[iCurrJnit]) // samples not available
490      {
491        {
492          const Int numSamplesInCurrUnit = (iCurrJnit >= iLeftUnits) ? unitWidth : unitHeight;
493          const Pel refSample = *(piAdiLineCur-1);
494          for (i=0; i<numSamplesInCurrUnit; i++)
495          {
496            piAdiLineCur[i] = refSample;
497          }
498          piAdiLineCur += numSamplesInCurrUnit;
499          iCurrJnit++;
500        }
501      }
502      else
503      {
504        piAdiLineCur += (iCurrJnit >= iLeftUnits) ? unitWidth : unitHeight;
505        iCurrJnit++;
506      }
507    }
508
509    // Copy processed samples
510
511    piAdiLineTemp = piAdiLine + uiHeight + unitWidth - 2;
512    // top left, top and top right samples
513    for (i=0; i<uiWidth; i++)
514    {
515      piAdiTemp[i] = piAdiLineTemp[i];
516    }
517
518    piAdiLineTemp = piAdiLine + uiHeight - 1;
519    for (i=1; i<uiHeight; i++)
520    {
521      piAdiTemp[i*uiWidth] = piAdiLineTemp[-i];
522    }
523  }
524}
525
526/** Get pointer to reference samples for intra prediction
527 * \param uiDirMode   prediction mode index
528 * \param log2BlkSize size of block (2 = 4x4, 3 = 8x8, 4 = 16x16, 5 = 32x32, 6 = 64x64)
529 * \param piAdiBuf    pointer to unfiltered reference samples
530 * \return            pointer to (possibly filtered) reference samples
531 *
532 * The prediction mode index is used to determine whether a smoothed reference sample buffer is returned.
533 */
534
535Bool TComPrediction::filteringIntraReferenceSamples(const ComponentID compID, UInt uiDirMode, UInt uiTuChWidth, UInt uiTuChHeight, const ChromaFormat chFmt, const Bool intraReferenceSmoothingDisabled)
536{
537  Bool bFilter;
538
539  if (!filterIntraReferenceSamples(toChannelType(compID), chFmt, intraReferenceSmoothingDisabled))
540  {
541    bFilter=false;
542  }
543  else
544  {
545    assert(uiTuChWidth>=4 && uiTuChHeight>=4 && uiTuChWidth<128 && uiTuChHeight<128);
546
547    if (uiDirMode == DC_IDX)
548    {
549      bFilter=false; //no smoothing for DC or LM chroma
550    }
551    else
552    {
553      Int diff = min<Int>(abs((Int) uiDirMode - HOR_IDX), abs((Int)uiDirMode - VER_IDX));
554      UInt sizeIndex=g_aucConvertToBit[uiTuChWidth];
555      assert(sizeIndex < MAX_INTRA_FILTER_DEPTHS);
556      bFilter = diff > m_aucIntraFilter[toChannelType(compID)][sizeIndex];
557    }
558  }
559  return bFilter;
560}
561
562Bool isAboveLeftAvailable( TComDataCU* pcCU, UInt uiPartIdxLT )
563{
564  Bool bAboveLeftFlag;
565  UInt uiPartAboveLeft;
566  TComDataCU* pcCUAboveLeft = pcCU->getPUAboveLeft( uiPartAboveLeft, uiPartIdxLT );
567  if(pcCU->getSlice()->getPPS()->getConstrainedIntraPred())
568  {
569    bAboveLeftFlag = ( pcCUAboveLeft && pcCUAboveLeft->isIntra( uiPartAboveLeft ) );
570  }
571  else
572  {
573    bAboveLeftFlag = (pcCUAboveLeft ? true : false);
574  }
575  return bAboveLeftFlag;
576}
577
578Int isAboveAvailable( TComDataCU* pcCU, UInt uiPartIdxLT, UInt uiPartIdxRT, Bool *bValidFlags )
579{
580  const UInt uiRasterPartBegin = g_auiZscanToRaster[uiPartIdxLT];
581  const UInt uiRasterPartEnd = g_auiZscanToRaster[uiPartIdxRT]+1;
582  const UInt uiIdxStep = 1;
583  Bool *pbValidFlags = bValidFlags;
584  Int iNumIntra = 0;
585
586  for ( UInt uiRasterPart = uiRasterPartBegin; uiRasterPart < uiRasterPartEnd; uiRasterPart += uiIdxStep )
587  {
588    UInt uiPartAbove;
589    TComDataCU* pcCUAbove = pcCU->getPUAbove( uiPartAbove, g_auiRasterToZscan[uiRasterPart] );
590    if(pcCU->getSlice()->getPPS()->getConstrainedIntraPred())
591    {
592      if ( pcCUAbove && pcCUAbove->isIntra( uiPartAbove ) )
593      {
594        iNumIntra++;
595        *pbValidFlags = true;
596      }
597      else
598      {
599        *pbValidFlags = false;
600      }
601    }
602    else
603    {
604      if (pcCUAbove)
605      {
606        iNumIntra++;
607        *pbValidFlags = true;
608      }
609      else
610      {
611        *pbValidFlags = false;
612      }
613    }
614    pbValidFlags++;
615  }
616  return iNumIntra;
617}
618
619Int isLeftAvailable( TComDataCU* pcCU, UInt uiPartIdxLT, UInt uiPartIdxLB, Bool *bValidFlags )
620{
621  const UInt uiRasterPartBegin = g_auiZscanToRaster[uiPartIdxLT];
622  const UInt uiRasterPartEnd = g_auiZscanToRaster[uiPartIdxLB]+1;
623  const UInt uiIdxStep = pcCU->getPic()->getNumPartInCtuWidth();
624  Bool *pbValidFlags = bValidFlags;
625  Int iNumIntra = 0;
626
627  for ( UInt uiRasterPart = uiRasterPartBegin; uiRasterPart < uiRasterPartEnd; uiRasterPart += uiIdxStep )
628  {
629    UInt uiPartLeft;
630    TComDataCU* pcCULeft = pcCU->getPULeft( uiPartLeft, g_auiRasterToZscan[uiRasterPart] );
631    if(pcCU->getSlice()->getPPS()->getConstrainedIntraPred())
632    {
633      if ( pcCULeft && pcCULeft->isIntra( uiPartLeft ) )
634      {
635        iNumIntra++;
636        *pbValidFlags = true;
637      }
638      else
639      {
640        *pbValidFlags = false;
641      }
642    }
643    else
644    {
645      if ( pcCULeft )
646      {
647        iNumIntra++;
648        *pbValidFlags = true;
649      }
650      else
651      {
652        *pbValidFlags = false;
653      }
654    }
655    pbValidFlags--; // opposite direction
656  }
657
658  return iNumIntra;
659}
660
661Int isAboveRightAvailable( TComDataCU* pcCU, UInt uiPartIdxLT, UInt uiPartIdxRT, Bool *bValidFlags )
662{
663  const UInt uiNumUnitsInPU = g_auiZscanToRaster[uiPartIdxRT] - g_auiZscanToRaster[uiPartIdxLT] + 1;
664  Bool *pbValidFlags = bValidFlags;
665  Int iNumIntra = 0;
666
667  for ( UInt uiOffset = 1; uiOffset <= uiNumUnitsInPU; uiOffset++ )
668  {
669    UInt uiPartAboveRight;
670    TComDataCU* pcCUAboveRight = pcCU->getPUAboveRightAdi( uiPartAboveRight, uiPartIdxRT, uiOffset );
671    if(pcCU->getSlice()->getPPS()->getConstrainedIntraPred())
672    {
673      if ( pcCUAboveRight && pcCUAboveRight->isIntra( uiPartAboveRight ) )
674      {
675        iNumIntra++;
676        *pbValidFlags = true;
677      }
678      else
679      {
680        *pbValidFlags = false;
681      }
682    }
683    else
684    {
685      if ( pcCUAboveRight )
686      {
687        iNumIntra++;
688        *pbValidFlags = true;
689      }
690      else
691      {
692        *pbValidFlags = false;
693      }
694    }
695    pbValidFlags++;
696  }
697
698  return iNumIntra;
699}
700
701Int isBelowLeftAvailable( TComDataCU* pcCU, UInt uiPartIdxLT, UInt uiPartIdxLB, Bool *bValidFlags )
702{
703  const UInt uiNumUnitsInPU = (g_auiZscanToRaster[uiPartIdxLB] - g_auiZscanToRaster[uiPartIdxLT]) / pcCU->getPic()->getNumPartInCtuWidth() + 1;
704  Bool *pbValidFlags = bValidFlags;
705  Int iNumIntra = 0;
706
707  for ( UInt uiOffset = 1; uiOffset <= uiNumUnitsInPU; uiOffset++ )
708  {
709    UInt uiPartBelowLeft;
710    TComDataCU* pcCUBelowLeft = pcCU->getPUBelowLeftAdi( uiPartBelowLeft, uiPartIdxLB, uiOffset );
711    if(pcCU->getSlice()->getPPS()->getConstrainedIntraPred())
712    {
713      if ( pcCUBelowLeft && pcCUBelowLeft->isIntra( uiPartBelowLeft ) )
714      {
715        iNumIntra++;
716        *pbValidFlags = true;
717      }
718      else
719      {
720        *pbValidFlags = false;
721      }
722    }
723    else
724    {
725      if ( pcCUBelowLeft )
726      {
727        iNumIntra++;
728        *pbValidFlags = true;
729      }
730      else
731      {
732        *pbValidFlags = false;
733      }
734    }
735    pbValidFlags--; // opposite direction
736  }
737
738  return iNumIntra;
739}
740//! \}
Note: See TracBrowser for help on using the repository browser.