source: 3DVCSoftware/branches/HTM-3.0-Vidyo/source/Lib/TLibCommon/TComPattern.cpp @ 272

Last change on this file since 272 was 56, checked in by hschwarz, 13 years ago

updated trunk (move to HM6.1)

  • Property svn:eol-style set to native
File size: 29.8 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     TComPattern.cpp
35    \brief    neighbouring pixel access classes
36*/
37
38#include "TComPic.h"
39#include "TComPattern.h"
40#include "TComDataCU.h"
41
42//! \ingroup TLibCommon
43//! \{
44
45// ====================================================================================================================
46// Tables
47// ====================================================================================================================
48
49#if LOGI_INTRA_NAME_3MPM
50const UChar TComPattern::m_aucIntraFilter[5] =
51{
52  10, //4x4
53  7, //8x8
54  1, //16x16
55  0, //32x32
56  10, //64x64
57};
58#else
59const UChar TComPattern::m_aucIntraFilter[5][NUM_INTRA_MODE] =
60{
61  {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
62  }, //4x4
63  {1, 0, 0, 0, 1, 0, 0, 1, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
64  }, //8x8
65  {1, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 1, 1, 1, 1, 1, 1, 0, 0, 1, 1, 1, 0
66  }, //16x16
67  {1, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0
68  }, //32x32
69  {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
70  }, //64x64
71};
72#endif
73
74// ====================================================================================================================
75// Public member functions (TComPatternParam)
76// ====================================================================================================================
77
78/** \param  piTexture     pixel data
79 \param  iRoiWidth     pattern width
80 \param  iRoiHeight    pattern height
81 \param  iStride       buffer stride
82 \param  iOffsetLeft   neighbour offset (left)
83 \param  iOffsetRight  neighbour offset (right)
84 \param  iOffsetAbove  neighbour offset (above)
85 \param  iOffsetBottom neighbour offset (bottom)
86 */
87Void TComPatternParam::setPatternParamPel ( Pel* piTexture,
88                                           Int iRoiWidth,
89                                           Int iRoiHeight,
90                                           Int iStride,
91                                           Int iOffsetLeft,
92                                           Int iOffsetRight,
93                                           Int iOffsetAbove,
94                                           Int iOffsetBottom )
95{
96  m_piPatternOrigin = piTexture;
97  m_iROIWidth       = iRoiWidth;
98  m_iROIHeight      = iRoiHeight;
99  m_iPatternStride  = iStride;
100  m_iOffsetLeft     = iOffsetLeft;
101  m_iOffsetAbove    = iOffsetAbove;
102  m_iOffsetRight    = iOffsetRight;
103  m_iOffsetBottom   = iOffsetBottom;
104}
105
106/**
107 \param  pcCU          CU data structure
108 \param  iComp         component index (0=Y, 1=Cb, 2=Cr)
109 \param  iRoiWidth     pattern width
110 \param  iRoiHeight    pattern height
111 \param  iStride       buffer stride
112 \param  iOffsetLeft   neighbour offset (left)
113 \param  iOffsetRight  neighbour offset (right)
114 \param  iOffsetAbove  neighbour offset (above)
115 \param  iOffsetBottom neighbour offset (bottom)
116 \param  uiPartDepth   CU depth
117 \param  uiAbsPartIdx  part index
118 */
119Void TComPatternParam::setPatternParamCU( TComDataCU* pcCU,
120                                         UChar       iComp,
121                                         UChar       iRoiWidth,
122                                         UChar       iRoiHeight,
123                                         Int         iOffsetLeft,
124                                         Int         iOffsetRight,
125                                         Int         iOffsetAbove,
126                                         Int         iOffsetBottom,
127                                         UInt        uiPartDepth,
128                                         UInt        uiAbsPartIdx
129#if DEPTH_MAP_GENERATION
130                                         ,Bool        bPrdDepthMap
131#endif
132                                         )
133{
134  m_iOffsetLeft   = iOffsetLeft;
135  m_iOffsetRight  = iOffsetRight;
136  m_iOffsetAbove  = iOffsetAbove;
137  m_iOffsetBottom = iOffsetBottom;
138 
139  m_iROIWidth     = iRoiWidth;
140  m_iROIHeight    = iRoiHeight;
141 
142  UInt uiAbsZorderIdx = pcCU->getZorderIdxInCU() + uiAbsPartIdx;
143 
144#if DEPTH_MAP_GENERATION
145  TComPicYuv* pcPic = ( bPrdDepthMap ? pcCU->getPic()->getPredDepthMap() : pcCU->getPic()->getPicYuvRec() );
146#else
147  TComPicYuv* pcPic = pcCU->getPic()->getPicYuvRec();
148#endif
149
150  if ( iComp == 0 )
151  {
152#if DEPTH_MAP_GENERATION
153    m_iPatternStride  = ( bPrdDepthMap ? pcCU->getPic()->getPredDepthMap()->getStride() : pcCU->getPic()->getStride() );
154#else
155    m_iPatternStride  = pcCU->getPic()->getStride();
156#endif
157    m_piPatternOrigin = pcPic->getLumaAddr(pcCU->getAddr(), uiAbsZorderIdx) - m_iOffsetAbove * m_iPatternStride - m_iOffsetLeft;
158  }
159  else
160  {
161#if DEPTH_MAP_GENERATION
162    m_iPatternStride  = ( bPrdDepthMap ? pcCU->getPic()->getPredDepthMap()->getCStride() : pcCU->getPic()->getCStride() );
163#else
164    m_iPatternStride = pcCU->getPic()->getCStride();
165#endif
166    if ( iComp == 1 )
167    {
168      m_piPatternOrigin = pcPic->getCbAddr(pcCU->getAddr(), uiAbsZorderIdx) - m_iOffsetAbove * m_iPatternStride - m_iOffsetLeft;
169    }
170    else
171    {
172      m_piPatternOrigin = pcPic->getCrAddr(pcCU->getAddr(), uiAbsZorderIdx) - m_iOffsetAbove * m_iPatternStride - m_iOffsetLeft;
173    }
174  }
175}
176
177// ====================================================================================================================
178// Public member functions (TComPattern)
179// ====================================================================================================================
180
181Void TComPattern::initPattern ( Pel* piY,
182                               Pel* piCb,
183                               Pel* piCr,
184                               Int iRoiWidth,
185                               Int iRoiHeight,
186                               Int iStride,
187                               Int iOffsetLeft,
188                               Int iOffsetRight,
189                               Int iOffsetAbove,
190                               Int iOffsetBottom )
191{
192  m_cPatternY. setPatternParamPel( piY,  iRoiWidth,      iRoiHeight,      iStride,      iOffsetLeft,      iOffsetRight,      iOffsetAbove,      iOffsetBottom );
193  m_cPatternCb.setPatternParamPel( piCb, iRoiWidth >> 1, iRoiHeight >> 1, iStride >> 1, iOffsetLeft >> 1, iOffsetRight >> 1, iOffsetAbove >> 1, iOffsetBottom >> 1 );
194  m_cPatternCr.setPatternParamPel( piCr, iRoiWidth >> 1, iRoiHeight >> 1, iStride >> 1, iOffsetLeft >> 1, iOffsetRight >> 1, iOffsetAbove >> 1, iOffsetBottom >> 1 );
195 
196  return;
197}
198
199Void TComPattern::initPattern( TComDataCU* pcCU, UInt uiPartDepth, UInt uiAbsPartIdx
200#if DEPTH_MAP_GENERATION
201                              , Bool bPrdDepthMap
202#endif
203                              )
204{
205  Int   uiOffsetLeft  = 0;
206  Int   uiOffsetRight = 0;
207  Int   uiOffsetAbove = 0;
208 
209  TComPic* pcPic         = pcCU->getPic();
210  UChar uiWidth          = pcCU->getWidth (0)>>uiPartDepth;
211  UChar uiHeight         = pcCU->getHeight(0)>>uiPartDepth;
212 
213  UInt  uiAbsZorderIdx   = pcCU->getZorderIdxInCU() + uiAbsPartIdx;
214  UInt  uiCurrPicPelX    = pcCU->getCUPelX() + g_auiRasterToPelX[ g_auiZscanToRaster[uiAbsZorderIdx] ];
215  UInt  uiCurrPicPelY    = pcCU->getCUPelY() + g_auiRasterToPelY[ g_auiZscanToRaster[uiAbsZorderIdx] ];
216 
217  if( uiCurrPicPelX != 0 )
218  {
219    uiOffsetLeft = 1;
220  }
221 
222  if( uiCurrPicPelY != 0 )
223  {
224    UInt uiNumPartInWidth = ( uiWidth/pcPic->getMinCUWidth() );
225    uiOffsetAbove = 1;
226   
227    if( uiCurrPicPelX + uiWidth < pcCU->getSlice()->getSPS()->getPicWidthInLumaSamples() )
228    {
229      if( ( g_auiZscanToRaster[uiAbsZorderIdx] + uiNumPartInWidth ) % pcPic->getNumPartInWidth() ) // Not CU boundary
230      {
231        if( g_auiRasterToZscan[ (Int)g_auiZscanToRaster[uiAbsZorderIdx] - (Int)pcPic->getNumPartInWidth() + (Int)uiNumPartInWidth ] < uiAbsZorderIdx )
232        {
233          uiOffsetRight = 1;
234        }
235      }
236      else // if it is CU boundary
237      {
238        if( g_auiZscanToRaster[uiAbsZorderIdx] < pcPic->getNumPartInWidth() && (uiCurrPicPelX+uiWidth) < pcPic->getPicYuvRec()->getWidth() ) // first line
239        {
240          uiOffsetRight = 1;
241        }
242      }
243    }
244  }
245 
246#if DEPTH_MAP_GENERATION
247  m_cPatternY .setPatternParamCU( pcCU, 0, uiWidth,      uiHeight,      uiOffsetLeft, uiOffsetRight, uiOffsetAbove, 0, uiPartDepth, uiAbsPartIdx, bPrdDepthMap );
248  m_cPatternCb.setPatternParamCU( pcCU, 1, uiWidth >> 1, uiHeight >> 1, uiOffsetLeft, uiOffsetRight, uiOffsetAbove, 0, uiPartDepth, uiAbsPartIdx, bPrdDepthMap );
249  m_cPatternCr.setPatternParamCU( pcCU, 2, uiWidth >> 1, uiHeight >> 1, uiOffsetLeft, uiOffsetRight, uiOffsetAbove, 0, uiPartDepth, uiAbsPartIdx, bPrdDepthMap );
250#else
251  m_cPatternY .setPatternParamCU( pcCU, 0, uiWidth,      uiHeight,      uiOffsetLeft, uiOffsetRight, uiOffsetAbove, 0, uiPartDepth, uiAbsPartIdx );
252  m_cPatternCb.setPatternParamCU( pcCU, 1, uiWidth >> 1, uiHeight >> 1, uiOffsetLeft, uiOffsetRight, uiOffsetAbove, 0, uiPartDepth, uiAbsPartIdx );
253  m_cPatternCr.setPatternParamCU( pcCU, 2, uiWidth >> 1, uiHeight >> 1, uiOffsetLeft, uiOffsetRight, uiOffsetAbove, 0, uiPartDepth, uiAbsPartIdx );
254#endif
255}
256
257  Void TComPattern::initAdiPattern( TComDataCU* pcCU, UInt uiZorderIdxInPart, UInt uiPartDepth, Int* piAdiBuf, Int iOrgBufStride, Int iOrgBufHeight, Bool& bAbove, Bool& bLeft, Bool bLMmode
258#if DEPTH_MAP_GENERATION
259                                  , Bool bPrdDepthMap, UInt uiSubSampExpX, UInt uiSubSampExpY
260#endif
261    )
262{
263  Pel*  piRoiOrigin;
264  Int*  piAdiTemp;
265  UInt  uiCuWidth   = pcCU->getWidth(0) >> uiPartDepth;
266  UInt  uiCuHeight  = pcCU->getHeight(0)>> uiPartDepth;
267  UInt  uiCuWidth2  = uiCuWidth<<1;
268  UInt  uiCuHeight2 = uiCuHeight<<1;
269  UInt  uiWidth;
270  UInt  uiHeight;
271#if DEPTH_MAP_GENERATION
272  Int   iPicStride = ( bPrdDepthMap ? pcCU->getPic()->getPredDepthMap()->getStride() : pcCU->getPic()->getStride() );
273#else
274  Int   iPicStride = pcCU->getPic()->getStride();
275#endif
276  Int   iUnitSize = 0;
277  Int   iNumUnitsInCu = 0;
278  Int   iTotalUnits = 0;
279  Bool  bNeighborFlags[4 * MAX_NUM_SPU_W + 1];
280  Int   iNumIntraNeighbor = 0;
281 
282  UInt uiPartIdxLT, uiPartIdxRT, uiPartIdxLB;
283
284 
285  pcCU->deriveLeftRightTopIdxAdi( uiPartIdxLT, uiPartIdxRT, uiZorderIdxInPart, uiPartDepth );
286  pcCU->deriveLeftBottomIdxAdi  ( uiPartIdxLB,              uiZorderIdxInPart, uiPartDepth );
287 
288  iUnitSize      = g_uiMaxCUWidth >> g_uiMaxCUDepth;
289  iNumUnitsInCu  = uiCuWidth / iUnitSize;
290  iTotalUnits    = (iNumUnitsInCu << 2) + 1;
291
292  bNeighborFlags[iNumUnitsInCu*2] = isAboveLeftAvailable( pcCU, uiPartIdxLT );
293  iNumIntraNeighbor  += (Int)(bNeighborFlags[iNumUnitsInCu*2]);
294  iNumIntraNeighbor  += isAboveAvailable     ( pcCU, uiPartIdxLT, uiPartIdxRT, bNeighborFlags+(iNumUnitsInCu*2)+1 );
295  iNumIntraNeighbor  += isAboveRightAvailable( pcCU, uiPartIdxLT, uiPartIdxRT, bNeighborFlags+(iNumUnitsInCu*3)+1 );
296  iNumIntraNeighbor  += isLeftAvailable      ( pcCU, uiPartIdxLT, uiPartIdxLB, bNeighborFlags+(iNumUnitsInCu*2)-1 );
297  iNumIntraNeighbor  += isBelowLeftAvailable ( pcCU, uiPartIdxLT, uiPartIdxLB, bNeighborFlags+ iNumUnitsInCu   -1 );
298 
299  bAbove = true;
300  bLeft  = true;
301
302#if DEPTH_MAP_GENERATION
303  if ( bPrdDepthMap )
304  {
305    uiWidth  = ( uiCuWidth2  >> uiSubSampExpX ) + 1;
306    uiHeight = ( uiCuHeight2 >> uiSubSampExpY ) + 1;
307  }
308  else
309  {
310    uiWidth=uiCuWidth2+1;
311    uiHeight=uiCuHeight2+1;
312  }
313#else
314  uiWidth=uiCuWidth2+1;
315  uiHeight=uiCuHeight2+1;
316#endif
317 
318  if (((uiWidth<<2)>iOrgBufStride)||((uiHeight<<2)>iOrgBufHeight))
319  {
320    return;
321  }
322 
323  piRoiOrigin = pcCU->getPic()->getPicYuvRec()->getLumaAddr(pcCU->getAddr(), pcCU->getZorderIdxInCU()+uiZorderIdxInPart);
324  piAdiTemp   = piAdiBuf;
325
326#if DEPTH_MAP_GENERATION
327  if( bPrdDepthMap )
328  {
329    piRoiOrigin = pcCU->getPic()->getPredDepthMap()->getLumaAddr( pcCU->getAddr(), pcCU->getZorderIdxInCU() + uiZorderIdxInPart );
330  }
331#endif
332
333#if DEPTH_MAP_GENERATION
334  if ( bPrdDepthMap )
335    fillReferenceSamples ( pcCU, piRoiOrigin, piAdiTemp, bNeighborFlags, iNumIntraNeighbor, iUnitSize >> uiSubSampExpX, iNumUnitsInCu, iTotalUnits, uiCuWidth >> uiSubSampExpX, uiCuHeight >> uiSubSampExpY, uiWidth, uiHeight, iPicStride, bLMmode, bPrdDepthMap );
336  else
337    fillReferenceSamples ( pcCU, piRoiOrigin, piAdiTemp, bNeighborFlags, iNumIntraNeighbor, iUnitSize, iNumUnitsInCu, iTotalUnits, uiCuWidth, uiCuHeight, uiWidth, uiHeight, iPicStride, bLMmode, bPrdDepthMap );
338#else
339  fillReferenceSamples ( pcCU, piRoiOrigin, piAdiTemp, bNeighborFlags, iNumIntraNeighbor, iUnitSize, iNumUnitsInCu, iTotalUnits, uiCuWidth, uiCuHeight, uiWidth, uiHeight, iPicStride, bLMmode);
340#endif
341
342 
343  Int   i;
344  // generate filtered intra prediction samples
345  Int iBufSize = uiCuHeight2 + uiCuWidth2 + 1;  // left and left above border + above and above right border + top left corner = length of 3. filter buffer
346
347  UInt uiWH = uiWidth * uiHeight;               // number of elements in one buffer
348
349  Int* piFilteredBuf1 = piAdiBuf + uiWH;        // 1. filter buffer
350  Int* piFilteredBuf2 = piFilteredBuf1 + uiWH;  // 2. filter buffer
351  Int* piFilterBuf = piFilteredBuf2 + uiWH;     // buffer for 2. filtering (sequential)
352  Int* piFilterBufN = piFilterBuf + iBufSize;   // buffer for 1. filtering (sequential)
353
354  Int l = 0;
355  // left border from bottom to top
356  for (i = 0; i < uiCuHeight2; i++)
357  {
358    piFilterBuf[l++] = piAdiTemp[uiWidth * (uiCuHeight2 - i)];
359  }
360  // top left corner
361  piFilterBuf[l++] = piAdiTemp[0];
362  // above border from left to right
363  for (i=0; i < uiCuWidth2; i++)
364  {
365    piFilterBuf[l++] = piAdiTemp[1 + i];
366  }
367
368  // 1. filtering with [1 2 1]
369  piFilterBufN[0] = piFilterBuf[0];
370  piFilterBufN[iBufSize - 1] = piFilterBuf[iBufSize - 1];
371  for (i = 1; i < iBufSize - 1; i++)
372  {
373    piFilterBufN[i] = (piFilterBuf[i - 1] + 2 * piFilterBuf[i]+piFilterBuf[i + 1] + 2) >> 2;
374  }
375
376  // fill 1. filter buffer with filtered values
377  l=0;
378  for (i = 0; i < uiCuHeight2; i++)
379  {
380    piFilteredBuf1[uiWidth * (uiCuHeight2 - i)] = piFilterBufN[l++];
381  }
382  piFilteredBuf1[0] = piFilterBufN[l++];
383  for (i = 0; i < uiCuWidth2; i++)
384  {
385    piFilteredBuf1[1 + i] = piFilterBufN[l++];
386  }
387}
388
389Void TComPattern::initAdiPatternChroma( TComDataCU* pcCU, UInt uiZorderIdxInPart, UInt uiPartDepth, Int* piAdiBuf, Int iOrgBufStride, Int iOrgBufHeight, Bool& bAbove, Bool& bLeft )
390{
391  Pel*  piRoiOrigin;
392  Int*  piAdiTemp;
393  UInt  uiCuWidth  = pcCU->getWidth (0) >> uiPartDepth;
394  UInt  uiCuHeight = pcCU->getHeight(0) >> uiPartDepth;
395  UInt  uiWidth;
396  UInt  uiHeight;
397  Int   iPicStride = pcCU->getPic()->getCStride();
398
399  Int   iUnitSize = 0;
400  Int   iNumUnitsInCu = 0;
401  Int   iTotalUnits = 0;
402  Bool  bNeighborFlags[4 * MAX_NUM_SPU_W + 1];
403  Int   iNumIntraNeighbor = 0;
404 
405  UInt uiPartIdxLT, uiPartIdxRT, uiPartIdxLB;
406 
407  pcCU->deriveLeftRightTopIdxAdi( uiPartIdxLT, uiPartIdxRT, uiZorderIdxInPart, uiPartDepth );
408  pcCU->deriveLeftBottomIdxAdi  ( uiPartIdxLB,              uiZorderIdxInPart, uiPartDepth );
409 
410  iUnitSize      = (g_uiMaxCUWidth >> g_uiMaxCUDepth) >> 1; // for chroma
411  iNumUnitsInCu  = (uiCuWidth / iUnitSize) >> 1;            // for chroma
412  iTotalUnits    = (iNumUnitsInCu << 2) + 1;
413
414  bNeighborFlags[iNumUnitsInCu*2] = isAboveLeftAvailable( pcCU, uiPartIdxLT );
415  iNumIntraNeighbor  += (Int)(bNeighborFlags[iNumUnitsInCu*2]);
416  iNumIntraNeighbor  += isAboveAvailable     ( pcCU, uiPartIdxLT, uiPartIdxRT, bNeighborFlags+(iNumUnitsInCu*2)+1 );
417  iNumIntraNeighbor  += isAboveRightAvailable( pcCU, uiPartIdxLT, uiPartIdxRT, bNeighborFlags+(iNumUnitsInCu*3)+1 );
418  iNumIntraNeighbor  += isLeftAvailable      ( pcCU, uiPartIdxLT, uiPartIdxLB, bNeighborFlags+(iNumUnitsInCu*2)-1 );
419  iNumIntraNeighbor  += isBelowLeftAvailable ( pcCU, uiPartIdxLT, uiPartIdxLB, bNeighborFlags+ iNumUnitsInCu   -1 );
420 
421  bAbove = true;
422  bLeft  = true;
423 
424  uiCuWidth=uiCuWidth>>1;  // for chroma
425  uiCuHeight=uiCuHeight>>1;  // for chroma
426 
427  uiWidth=uiCuWidth*2+1;
428  uiHeight=uiCuHeight*2+1;
429 
430  if ((4*uiWidth>iOrgBufStride)||(4*uiHeight>iOrgBufHeight))
431  {
432    return;
433  }
434 
435  // get Cb pattern
436  piRoiOrigin = pcCU->getPic()->getPicYuvRec()->getCbAddr(pcCU->getAddr(), pcCU->getZorderIdxInCU()+uiZorderIdxInPart);
437  piAdiTemp   = piAdiBuf;
438
439#if DEPTH_MAP_GENERATION
440  fillReferenceSamples ( pcCU, piRoiOrigin, piAdiTemp, bNeighborFlags, iNumIntraNeighbor, iUnitSize, iNumUnitsInCu, iTotalUnits, uiCuWidth, uiCuHeight, uiWidth, uiHeight, iPicStride, false, false );
441#else
442  fillReferenceSamples ( pcCU, piRoiOrigin, piAdiTemp, bNeighborFlags, iNumIntraNeighbor, iUnitSize, iNumUnitsInCu, iTotalUnits, uiCuWidth, uiCuHeight, uiWidth, uiHeight, iPicStride);
443#endif
444 
445  // get Cr pattern
446  piRoiOrigin = pcCU->getPic()->getPicYuvRec()->getCrAddr(pcCU->getAddr(), pcCU->getZorderIdxInCU()+uiZorderIdxInPart);
447  piAdiTemp   = piAdiBuf+uiWidth*uiHeight;
448 
449#if DEPTH_MAP_GENERATION
450  fillReferenceSamples ( pcCU, piRoiOrigin, piAdiTemp, bNeighborFlags, iNumIntraNeighbor, iUnitSize, iNumUnitsInCu, iTotalUnits, uiCuWidth, uiCuHeight, uiWidth, uiHeight, iPicStride, false, false );
451#else
452  fillReferenceSamples ( pcCU, piRoiOrigin, piAdiTemp, bNeighborFlags, iNumIntraNeighbor, iUnitSize, iNumUnitsInCu, iTotalUnits, uiCuWidth, uiCuHeight, uiWidth, uiHeight, iPicStride);
453#endif
454
455}
456
457Void TComPattern::fillReferenceSamples( TComDataCU* pcCU, Pel* piRoiOrigin, Int* piAdiTemp, Bool* bNeighborFlags, Int iNumIntraNeighbor, Int iUnitSize, Int iNumUnitsInCu, Int iTotalUnits, UInt uiCuWidth, UInt uiCuHeight, UInt uiWidth, UInt uiHeight, Int iPicStride, Bool bLMmode
458#if DEPTH_MAP_GENERATION
459                                       , Bool bPrdDepthMap
460#endif
461                                       )
462{
463  Pel* piRoiTemp;
464  Int  i, j;
465#if DEPTH_MAP_GENERATION
466  Int  iDCValue = ( bPrdDepthMap ? PDM_UNDEFINED_DEPTH : ( 1<<( g_uiBitDepth + g_uiBitIncrement - 1) ) );
467#else
468  Int  iDCValue = ( 1<<( g_uiBitDepth + g_uiBitIncrement - 1) );
469#endif
470
471  if (iNumIntraNeighbor == 0)
472  {
473    // Fill border with DC value
474    for (i=0; i<uiWidth; i++)
475    {
476      piAdiTemp[i] = iDCValue;
477    }
478    for (i=1; i<uiHeight; i++)
479    {
480      piAdiTemp[i*uiWidth] = iDCValue;
481    }
482  }
483  else if (iNumIntraNeighbor == iTotalUnits)
484  {
485    // Fill top-left border with rec. samples
486    piRoiTemp = piRoiOrigin - iPicStride - 1;
487    piAdiTemp[0] = piRoiTemp[0];
488
489    // Fill left border with rec. samples
490    piRoiTemp = piRoiOrigin - 1;
491
492    if (bLMmode)
493    {
494      piRoiTemp --; // move to the second left column
495    }
496
497    for (i=0; i<uiCuHeight; i++)
498    {
499      piAdiTemp[(1+i)*uiWidth] = piRoiTemp[0];
500      piRoiTemp += iPicStride;
501    }
502
503    // Fill below left border with rec. samples
504    for (i=0; i<uiCuHeight; i++)
505    {
506      piAdiTemp[(1+uiCuHeight+i)*uiWidth] = piRoiTemp[0];
507      piRoiTemp += iPicStride;
508    }
509
510    // Fill top border with rec. samples
511    piRoiTemp = piRoiOrigin - iPicStride;
512    for (i=0; i<uiCuWidth; i++)
513    {
514      piAdiTemp[1+i] = piRoiTemp[i];
515    }
516   
517    // Fill top right border with rec. samples
518    piRoiTemp = piRoiOrigin - iPicStride + uiCuWidth;
519    for (i=0; i<uiCuWidth; i++)
520    {
521      piAdiTemp[1+uiCuWidth+i] = piRoiTemp[i];
522    }
523  }
524  else // reference samples are partially available
525  {
526    Int  iNumUnits2 = iNumUnitsInCu<<1;
527    Int  iTotalSamples = iTotalUnits*iUnitSize;
528    Pel  piAdiLine[5 * MAX_CU_SIZE];
529    Pel  *piAdiLineTemp; 
530    Bool *pbNeighborFlags;
531    Int  iNext, iCurr;
532    Pel  piRef = 0;
533
534    // Initialize
535    for (i=0; i<iTotalSamples; i++)
536    {
537      piAdiLine[i] = iDCValue;
538    }
539   
540    // Fill top-left sample
541    piRoiTemp = piRoiOrigin - iPicStride - 1;
542    piAdiLineTemp = piAdiLine + (iNumUnits2*iUnitSize);
543    pbNeighborFlags = bNeighborFlags + iNumUnits2;
544    if (*pbNeighborFlags)
545    {
546      piAdiLineTemp[0] = piRoiTemp[0];
547      for (i=1; i<iUnitSize; i++)
548      {
549        piAdiLineTemp[i] = piAdiLineTemp[0];
550      }
551    }
552
553    // Fill left & below-left samples
554    piRoiTemp += iPicStride;
555    if (bLMmode)
556    {
557      piRoiTemp --; // move the second left column
558    }
559    piAdiLineTemp--;
560    pbNeighborFlags--;
561    for (j=0; j<iNumUnits2; j++)
562    {
563      if (*pbNeighborFlags)
564      {
565        for (i=0; i<iUnitSize; i++)
566        {
567          piAdiLineTemp[-i] = piRoiTemp[i*iPicStride];
568        }
569      }
570      piRoiTemp += iUnitSize*iPicStride;
571      piAdiLineTemp -= iUnitSize;
572      pbNeighborFlags--;
573    }
574
575    // Fill above & above-right samples
576    piRoiTemp = piRoiOrigin - iPicStride;
577    piAdiLineTemp = piAdiLine + ((iNumUnits2+1)*iUnitSize);
578    pbNeighborFlags = bNeighborFlags + iNumUnits2 + 1;
579    for (j=0; j<iNumUnits2; j++)
580    {
581      if (*pbNeighborFlags)
582      {
583        for (i=0; i<iUnitSize; i++)
584        {
585          piAdiLineTemp[i] = piRoiTemp[i];
586        }
587      }
588      piRoiTemp += iUnitSize;
589      piAdiLineTemp += iUnitSize;
590      pbNeighborFlags++;
591    }
592
593    // Pad reference samples when necessary
594    iCurr = 0;
595    iNext = 1;
596    piAdiLineTemp = piAdiLine;
597    while (iCurr < iTotalUnits)
598    {
599      if (!bNeighborFlags[iCurr])
600      {
601        if(iCurr == 0)
602        {
603          while (iNext < iTotalUnits && !bNeighborFlags[iNext])
604          {
605            iNext++;
606          }
607          piRef = piAdiLine[iNext*iUnitSize];
608          // Pad unavailable samples with new value
609          while (iCurr < iNext)
610          {
611            for (i=0; i<iUnitSize; i++)
612            {
613              piAdiLineTemp[i] = piRef;
614            }
615            piAdiLineTemp += iUnitSize;
616            iCurr++;
617          }
618        }
619        else
620        {
621          piRef = piAdiLine[iCurr*iUnitSize-1];
622          for (i=0; i<iUnitSize; i++)
623          {
624            piAdiLineTemp[i] = piRef;
625          }
626          piAdiLineTemp += iUnitSize;
627          iCurr++;
628        }
629      }
630      else
631      {
632        piAdiLineTemp += iUnitSize;
633        iCurr++;
634      }
635    }
636
637    // Copy processed samples
638    piAdiLineTemp = piAdiLine + uiHeight + iUnitSize - 2;
639    for (i=0; i<uiWidth; i++)
640    {
641      piAdiTemp[i] = piAdiLineTemp[i];
642    }
643    piAdiLineTemp = piAdiLine + uiHeight - 1;
644    for (i=1; i<uiHeight; i++)
645    {
646      piAdiTemp[i*uiWidth] = piAdiLineTemp[-i];
647    }
648  }
649}
650
651Int* TComPattern::getAdiOrgBuf( Int iCuWidth, Int iCuHeight, Int* piAdiBuf)
652{
653  return piAdiBuf;
654}
655
656Int* TComPattern::getAdiCbBuf( Int iCuWidth, Int iCuHeight, Int* piAdiBuf)
657{
658  return piAdiBuf;
659}
660
661Int* TComPattern::getAdiCrBuf(Int iCuWidth,Int iCuHeight, Int* piAdiBuf)
662{
663  return piAdiBuf+(iCuWidth*2+1)*(iCuHeight*2+1);
664}
665
666/** Get pointer to reference samples for intra prediction
667 * \param uiDirMode   prediction mode index
668 * \param log2BlkSize size of block (2 = 4x4, 3 = 8x8, 4 = 16x16, 5 = 32x32, 6 = 64x64)
669 * \param piAdiBuf    pointer to unfiltered reference samples
670 * \return            pointer to (possibly filtered) reference samples
671 *
672 * The prediction mode index is used to determine whether a smoothed reference sample buffer is returned.
673 */
674Int* TComPattern::getPredictorPtr( UInt uiDirMode, UInt log2BlkSize, Int* piAdiBuf )
675{
676  Int* piSrc;
677  assert(log2BlkSize >= 2 && log2BlkSize < 7);
678#if HHI_DMM_WEDGE_INTRA || HHI_DMM_PRED_TEX
679  mapDMMtoIntraMode( uiDirMode );
680#endif
681#if LOGI_INTRA_NAME_3MPM
682  Int diff = min<Int>(abs((Int) uiDirMode - HOR_IDX), abs((Int)uiDirMode - VER_IDX));
683  UChar ucFiltIdx = diff > m_aucIntraFilter[log2BlkSize - 2] ? 1 : 0;
684  if (uiDirMode == DC_IDX || uiDirMode == LM_CHROMA_IDX)
685  {
686    ucFiltIdx = 0; //no smoothing for DC or LM chroma
687  }
688#else
689  UChar ucFiltIdx = m_aucIntraFilter[log2BlkSize - 2][uiDirMode];
690#endif
691
692  assert( ucFiltIdx <= 1 );
693
694  Int width  = 1 << log2BlkSize;
695  Int height = 1 << log2BlkSize;
696 
697  piSrc = getAdiOrgBuf( width, height, piAdiBuf );
698
699  if ( ucFiltIdx )
700  {
701    piSrc += (2 * width + 1) * (2 * height + 1);
702  }
703
704  return piSrc;
705}
706
707Bool TComPattern::isAboveLeftAvailable( TComDataCU* pcCU, UInt uiPartIdxLT )
708{
709  Bool bAboveLeftFlag;
710  UInt uiPartAboveLeft;
711  TComDataCU* pcCUAboveLeft = pcCU->getPUAboveLeft( uiPartAboveLeft, uiPartIdxLT, true, false );
712  if(pcCU->getSlice()->getPPS()->getConstrainedIntraPred())
713  {
714    bAboveLeftFlag = ( pcCUAboveLeft && pcCUAboveLeft->getPredictionMode( uiPartAboveLeft ) == MODE_INTRA );
715  }
716  else
717  {
718    bAboveLeftFlag = (pcCUAboveLeft ? true : false);
719  }
720  return bAboveLeftFlag;
721}
722
723Int TComPattern::isAboveAvailable( TComDataCU* pcCU, UInt uiPartIdxLT, UInt uiPartIdxRT, Bool *bValidFlags )
724{
725  const UInt uiRasterPartBegin = g_auiZscanToRaster[uiPartIdxLT];
726  const UInt uiRasterPartEnd = g_auiZscanToRaster[uiPartIdxRT]+1;
727  const UInt uiIdxStep = 1;
728  Bool *pbValidFlags = bValidFlags;
729  Int iNumIntra = 0;
730
731  for ( UInt uiRasterPart = uiRasterPartBegin; uiRasterPart < uiRasterPartEnd; uiRasterPart += uiIdxStep )
732  {
733    UInt uiPartAbove;
734    TComDataCU* pcCUAbove = pcCU->getPUAbove( uiPartAbove, g_auiRasterToZscan[uiRasterPart], true, false );
735    if(pcCU->getSlice()->getPPS()->getConstrainedIntraPred())
736    {
737      if ( pcCUAbove && pcCUAbove->getPredictionMode( uiPartAbove ) == MODE_INTRA )
738      {
739        iNumIntra++;
740        *pbValidFlags = true;
741      }
742      else
743      {
744        *pbValidFlags = false;
745      }
746    }
747    else
748    {
749      if (pcCUAbove)
750      {
751        iNumIntra++;
752        *pbValidFlags = true;
753      }
754      else
755      {
756        *pbValidFlags = false;
757      }
758    }
759    pbValidFlags++;
760  }
761  return iNumIntra;
762}
763
764Int TComPattern::isLeftAvailable( TComDataCU* pcCU, UInt uiPartIdxLT, UInt uiPartIdxLB, Bool *bValidFlags )
765{
766  const UInt uiRasterPartBegin = g_auiZscanToRaster[uiPartIdxLT];
767  const UInt uiRasterPartEnd = g_auiZscanToRaster[uiPartIdxLB]+1;
768  const UInt uiIdxStep = pcCU->getPic()->getNumPartInWidth();
769  Bool *pbValidFlags = bValidFlags;
770  Int iNumIntra = 0;
771
772  for ( UInt uiRasterPart = uiRasterPartBegin; uiRasterPart < uiRasterPartEnd; uiRasterPart += uiIdxStep )
773  {
774    UInt uiPartLeft;
775    TComDataCU* pcCULeft = pcCU->getPULeft( uiPartLeft, g_auiRasterToZscan[uiRasterPart], true, false );
776    if(pcCU->getSlice()->getPPS()->getConstrainedIntraPred())
777    {
778      if ( pcCULeft && pcCULeft->getPredictionMode( uiPartLeft ) == MODE_INTRA )
779      {
780        iNumIntra++;
781        *pbValidFlags = true;
782      }
783      else
784      {
785        *pbValidFlags = false;
786      }
787    }
788    else
789    {
790      if ( pcCULeft )
791      {
792        iNumIntra++;
793        *pbValidFlags = true;
794      }
795      else
796      {
797        *pbValidFlags = false;
798      }
799    }
800    pbValidFlags--; // opposite direction
801  }
802
803  return iNumIntra;
804}
805
806Int TComPattern::isAboveRightAvailable( TComDataCU* pcCU, UInt uiPartIdxLT, UInt uiPartIdxRT, Bool *bValidFlags )
807{
808  const UInt uiNumUnitsInPU = g_auiZscanToRaster[uiPartIdxRT] - g_auiZscanToRaster[uiPartIdxLT] + 1;
809  const UInt uiPuWidth = uiNumUnitsInPU * pcCU->getPic()->getMinCUWidth();
810  Bool *pbValidFlags = bValidFlags;
811  Int iNumIntra = 0;
812
813  for ( UInt uiOffset = 1; uiOffset <= uiNumUnitsInPU; uiOffset++ )
814  {
815    UInt uiPartAboveRight;
816    TComDataCU* pcCUAboveRight = pcCU->getPUAboveRightAdi( uiPartAboveRight, uiPuWidth, uiPartIdxRT, uiOffset, true, false );
817    if(pcCU->getSlice()->getPPS()->getConstrainedIntraPred())
818    {
819      if ( pcCUAboveRight && pcCUAboveRight->getPredictionMode( uiPartAboveRight ) == MODE_INTRA )
820      {
821        iNumIntra++;
822        *pbValidFlags = true;
823      }
824      else
825      {
826        *pbValidFlags = false;
827      }
828    }
829    else
830    {
831      if ( pcCUAboveRight )
832      {
833        iNumIntra++;
834        *pbValidFlags = true;
835      }
836      else
837      {
838        *pbValidFlags = false;
839      }
840    }
841    pbValidFlags++;
842  }
843
844  return iNumIntra;
845}
846
847Int TComPattern::isBelowLeftAvailable( TComDataCU* pcCU, UInt uiPartIdxLT, UInt uiPartIdxLB, Bool *bValidFlags )
848{
849  const UInt uiNumUnitsInPU = (g_auiZscanToRaster[uiPartIdxLB] - g_auiZscanToRaster[uiPartIdxLT]) / pcCU->getPic()->getNumPartInWidth() + 1;
850  const UInt uiPuHeight = uiNumUnitsInPU * pcCU->getPic()->getMinCUHeight();
851  Bool *pbValidFlags = bValidFlags;
852  Int iNumIntra = 0;
853
854  for ( UInt uiOffset = 1; uiOffset <= uiNumUnitsInPU; uiOffset++ )
855  {
856    UInt uiPartBelowLeft;
857    TComDataCU* pcCUBelowLeft = pcCU->getPUBelowLeftAdi( uiPartBelowLeft, uiPuHeight, uiPartIdxLB, uiOffset, true, false );
858    if(pcCU->getSlice()->getPPS()->getConstrainedIntraPred())
859    {
860      if ( pcCUBelowLeft && pcCUBelowLeft->getPredictionMode( uiPartBelowLeft ) == MODE_INTRA )
861      {
862        iNumIntra++;
863        *pbValidFlags = true;
864      }
865      else
866      {
867        *pbValidFlags = false;
868      }
869    }
870    else
871    {
872      if ( pcCUBelowLeft )
873      {
874        iNumIntra++;
875        *pbValidFlags = true;
876      }
877      else
878      {
879        *pbValidFlags = false;
880      }
881    }
882    pbValidFlags--; // opposite direction
883  }
884
885  return iNumIntra;
886}
887//! \}
Note: See TracBrowser for help on using the repository browser.