source: 3DVCSoftware/trunk/source/Lib/TLibCommon/TComYuv.cpp @ 1313

Last change on this file since 1313 was 1313, checked in by tech, 9 years ago

Merged 14.1-update-dev1@1312.

  • Property svn:eol-style set to native
File size: 21.4 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-2015, 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     TComYuv.cpp
35    \brief    general YUV buffer class
36    \todo     this should be merged with TComPicYuv
37*/
38
39#include <stdlib.h>
40#include <memory.h>
41#include <assert.h>
42#include <math.h>
43
44#include "CommonDef.h"
45#include "TComYuv.h"
46#include "TComInterpolationFilter.h"
47
48//! \ingroup TLibCommon
49//! \{
50
51TComYuv::TComYuv()
52{
53  for(Int comp=0; comp<MAX_NUM_COMPONENT; comp++)
54  {
55    m_apiBuf[comp] = NULL;
56  }
57}
58
59TComYuv::~TComYuv()
60{
61}
62
63Void TComYuv::create( UInt iWidth, UInt iHeight, ChromaFormat chromaFormatIDC )
64{
65  // set width and height
66  m_iWidth   = iWidth;
67  m_iHeight  = iHeight;
68  m_chromaFormatIDC = chromaFormatIDC;
69
70  for(Int comp=0; comp<MAX_NUM_COMPONENT; comp++)
71  {
72    // memory allocation
73    m_apiBuf[comp]  = (Pel*)xMalloc( Pel, getWidth(ComponentID(comp))*getHeight(ComponentID(comp)) );
74  }
75}
76
77Void TComYuv::destroy()
78{
79  // memory free
80  for(Int comp=0; comp<MAX_NUM_COMPONENT; comp++)
81  {
82    if (m_apiBuf[comp]!=NULL)
83    {
84      xFree( m_apiBuf[comp] );
85      m_apiBuf[comp] = NULL;
86    }
87  }
88}
89
90Void TComYuv::clear()
91{
92  for(Int comp=0; comp<MAX_NUM_COMPONENT; comp++)
93  {
94    if (m_apiBuf[comp]!=NULL)
95    {
96      ::memset( m_apiBuf[comp], 0, ( getWidth(ComponentID(comp)) * getHeight(ComponentID(comp))  )*sizeof(Pel) );
97    }
98  }
99}
100
101
102
103
104Void TComYuv::copyToPicYuv   ( TComPicYuv* pcPicYuvDst, const UInt ctuRsAddr, const UInt uiAbsZorderIdx, const UInt uiPartDepth, const UInt uiPartIdx ) const
105{
106  for(Int comp=0; comp<getNumberValidComponents(); comp++)
107  {
108    copyToPicComponent  ( ComponentID(comp), pcPicYuvDst, ctuRsAddr, uiAbsZorderIdx, uiPartDepth, uiPartIdx );
109  }
110}
111
112Void TComYuv::copyToPicComponent  ( const ComponentID compID, TComPicYuv* pcPicYuvDst, const UInt ctuRsAddr, const UInt uiAbsZorderIdx, const UInt uiPartDepth, const UInt uiPartIdx ) const
113{
114  const Int iWidth  = getWidth(compID) >>uiPartDepth;
115  const Int iHeight = getHeight(compID)>>uiPartDepth;
116
117  const Pel* pSrc     = getAddr(compID, uiPartIdx, iWidth);
118        Pel* pDst     = pcPicYuvDst->getAddr ( compID, ctuRsAddr, uiAbsZorderIdx );
119
120  const UInt  iSrcStride  = getStride(compID);
121  const UInt  iDstStride  = pcPicYuvDst->getStride(compID);
122
123  for ( Int y = iHeight; y != 0; y-- )
124  {
125    ::memcpy( pDst, pSrc, sizeof(Pel)*iWidth);
126#if ENC_DEC_TRACE && H_MV_ENC_DEC_TRAC
127    if ( g_traceCopyBack && compID == COMPONENT_Y)
128    { 
129      std::stringstream strStr; 
130      for ( Int x = 0; x < iWidth; x++)
131      {     
132        strStr << pSrc[ x ] << " " ; 
133      }
134      printStrIndent( true, strStr.str() );
135    }
136#endif
137    pDst += iDstStride;
138    pSrc += iSrcStride;
139  }
140}
141
142
143
144
145Void TComYuv::copyFromPicYuv   ( const TComPicYuv* pcPicYuvSrc, const UInt ctuRsAddr, const UInt uiAbsZorderIdx )
146{
147  for(Int comp=0; comp<getNumberValidComponents(); comp++)
148  {
149    copyFromPicComponent  ( ComponentID(comp), pcPicYuvSrc, ctuRsAddr, uiAbsZorderIdx );
150  }
151}
152
153Void TComYuv::copyFromPicComponent  ( const ComponentID compID, const TComPicYuv* pcPicYuvSrc, const UInt ctuRsAddr, const UInt uiAbsZorderIdx )
154{
155        Pel* pDst     = getAddr(compID);
156  const Pel* pSrc     = pcPicYuvSrc->getAddr ( compID, ctuRsAddr, uiAbsZorderIdx );
157
158  const UInt iDstStride  = getStride(compID);
159  const UInt iSrcStride  = pcPicYuvSrc->getStride(compID);
160  const Int  iWidth=getWidth(compID);
161  const Int  iHeight=getHeight(compID);
162
163  for (Int y = iHeight; y != 0; y-- )
164  {
165    ::memcpy( pDst, pSrc, sizeof(Pel)*iWidth);
166    pDst += iDstStride;
167    pSrc += iSrcStride;
168  }
169}
170
171
172
173
174Void TComYuv::copyToPartYuv( TComYuv* pcYuvDst, const UInt uiDstPartIdx ) const
175{
176  for(Int comp=0; comp<getNumberValidComponents(); comp++)
177  {
178    copyToPartComponent  ( ComponentID(comp), pcYuvDst, uiDstPartIdx );
179  }
180}
181
182Void TComYuv::copyToPartComponent( const ComponentID compID, TComYuv* pcYuvDst, const UInt uiDstPartIdx ) const
183{
184  const Pel* pSrc     = getAddr(compID);
185        Pel* pDst     = pcYuvDst->getAddr( compID, uiDstPartIdx );
186
187  const UInt iSrcStride  = getStride(compID);
188  const UInt iDstStride  = pcYuvDst->getStride(compID);
189  const Int  iWidth=getWidth(compID);
190  const Int  iHeight=getHeight(compID);
191
192  for (Int y = iHeight; y != 0; y-- )
193  {
194    ::memcpy( pDst, pSrc, sizeof(Pel)*iWidth);
195    pDst += iDstStride;
196    pSrc += iSrcStride;
197  }
198}
199
200
201
202
203Void TComYuv::copyPartToYuv( TComYuv* pcYuvDst, const UInt uiSrcPartIdx ) const
204{
205  for(Int comp=0; comp<getNumberValidComponents(); comp++)
206  {
207    copyPartToComponent  ( ComponentID(comp), pcYuvDst, uiSrcPartIdx );
208  }
209}
210
211Void TComYuv::copyPartToComponent( const ComponentID compID, TComYuv* pcYuvDst, const UInt uiSrcPartIdx ) const
212{
213  const Pel* pSrc     = getAddr(compID, uiSrcPartIdx);
214        Pel* pDst     = pcYuvDst->getAddr(compID, 0 );
215
216  const UInt  iSrcStride  = getStride(compID);
217  const UInt  iDstStride  = pcYuvDst->getStride(compID);
218
219  const UInt uiHeight = pcYuvDst->getHeight(compID);
220  const UInt uiWidth = pcYuvDst->getWidth(compID);
221
222  for ( UInt y = uiHeight; y != 0; y-- )
223  {
224    ::memcpy( pDst, pSrc, sizeof(Pel)*uiWidth);
225    pDst += iDstStride;
226    pSrc += iSrcStride;
227  }
228}
229
230
231
232
233Void TComYuv::copyPartToPartYuv   ( TComYuv* pcYuvDst, const UInt uiPartIdx, const UInt iWidth, const UInt iHeight ) const
234{
235  for(Int comp=0; comp<getNumberValidComponents(); comp++)
236  {
237    copyPartToPartComponent   (ComponentID(comp), pcYuvDst, uiPartIdx, iWidth>>getComponentScaleX(ComponentID(comp)), iHeight>>getComponentScaleY(ComponentID(comp)) );
238  }
239}
240
241Void TComYuv::copyPartToPartComponent  ( const ComponentID compID, TComYuv* pcYuvDst, const UInt uiPartIdx, const UInt iWidthComponent, const UInt iHeightComponent ) const
242{
243  const Pel* pSrc =           getAddr(compID, uiPartIdx);
244        Pel* pDst = pcYuvDst->getAddr(compID, uiPartIdx);
245  if( pSrc == pDst )
246  {
247    //th not a good idea
248    //th best would be to fix the caller
249    return ;
250  }
251
252  const UInt  iSrcStride = getStride(compID);
253  const UInt  iDstStride = pcYuvDst->getStride(compID);
254  for ( UInt y = iHeightComponent; y != 0; y-- )
255  {
256    ::memcpy( pDst, pSrc, iWidthComponent * sizeof(Pel) );
257    pSrc += iSrcStride;
258    pDst += iDstStride;
259  }
260}
261
262
263
264
265Void TComYuv::copyPartToPartComponentMxN  ( const ComponentID compID, TComYuv* pcYuvDst, const TComRectangle &rect) const
266{
267  const Pel* pSrc =           getAddrPix( compID, rect.x0, rect.y0 );
268        Pel* pDst = pcYuvDst->getAddrPix( compID, rect.x0, rect.y0 );
269  if( pSrc == pDst )
270  {
271    //th not a good idea
272    //th best would be to fix the caller
273    return ;
274  }
275
276  const UInt  iSrcStride = getStride(compID);
277  const UInt  iDstStride = pcYuvDst->getStride(compID);
278  const UInt uiHeightComponent=rect.height;
279  const UInt uiWidthComponent=rect.width;
280  for ( UInt y = uiHeightComponent; y != 0; y-- )
281  {
282    ::memcpy( pDst, pSrc, uiWidthComponent * sizeof( Pel ) );
283    pSrc += iSrcStride;
284    pDst += iDstStride;
285  }
286}
287
288
289
290
291Void TComYuv::addClip( const TComYuv* pcYuvSrc0, const TComYuv* pcYuvSrc1, const UInt uiTrUnitIdx, const UInt uiPartSize, const BitDepths &clipBitDepths )
292{
293  for(Int comp=0; comp<getNumberValidComponents(); comp++)
294  {
295    const ComponentID compID=ComponentID(comp);
296    const Int uiPartWidth =uiPartSize>>getComponentScaleX(compID);
297    const Int uiPartHeight=uiPartSize>>getComponentScaleY(compID);
298
299    const Pel* pSrc0 = pcYuvSrc0->getAddr(compID, uiTrUnitIdx, uiPartWidth );
300    const Pel* pSrc1 = pcYuvSrc1->getAddr(compID, uiTrUnitIdx, uiPartWidth );
301          Pel* pDst  = getAddr(compID, uiTrUnitIdx, uiPartWidth );
302
303    const UInt iSrc0Stride = pcYuvSrc0->getStride(compID);
304    const UInt iSrc1Stride = pcYuvSrc1->getStride(compID);
305    const UInt iDstStride  = getStride(compID);
306    const Int clipbd = clipBitDepths.recon[toChannelType(compID)];
307#if O0043_BEST_EFFORT_DECODING
308    const Int bitDepthDelta = clipBitDepths.stream[toChannelType(compID)] - clipbd;
309#endif
310
311    for ( Int y = uiPartHeight-1; y >= 0; y-- )
312    {
313      for ( Int x = uiPartWidth-1; x >= 0; x-- )
314      {
315#if O0043_BEST_EFFORT_DECODING
316        pDst[x] = Pel(ClipBD<Int>( Int(pSrc0[x]) + rightShiftEvenRounding<Pel>(pSrc1[x], bitDepthDelta), clipbd));
317#else
318        pDst[x] = Pel(ClipBD<Int>( Int(pSrc0[x]) + Int(pSrc1[x]), clipbd));
319#endif
320      }
321      pSrc0 += iSrc0Stride;
322      pSrc1 += iSrc1Stride;
323      pDst  += iDstStride;
324    }
325  }
326}
327
328
329
330
331Void TComYuv::subtract( const TComYuv* pcYuvSrc0, const TComYuv* pcYuvSrc1, const UInt uiTrUnitIdx, const UInt uiPartSize )
332{
333  for(Int comp=0; comp<getNumberValidComponents(); comp++)
334  {
335    const ComponentID compID=ComponentID(comp);
336    const Int uiPartWidth =uiPartSize>>getComponentScaleX(compID);
337    const Int uiPartHeight=uiPartSize>>getComponentScaleY(compID);
338
339    const Pel* pSrc0 = pcYuvSrc0->getAddr( compID, uiTrUnitIdx, uiPartWidth );
340    const Pel* pSrc1 = pcYuvSrc1->getAddr( compID, uiTrUnitIdx, uiPartWidth );
341          Pel* pDst  = getAddr( compID, uiTrUnitIdx, uiPartWidth );
342
343    const Int  iSrc0Stride = pcYuvSrc0->getStride(compID);
344    const Int  iSrc1Stride = pcYuvSrc1->getStride(compID);
345    const Int  iDstStride  = getStride(compID);
346
347    for (Int y = uiPartHeight-1; y >= 0; y-- )
348    {
349      for (Int x = uiPartWidth-1; x >= 0; x-- )
350      {
351        pDst[x] = pSrc0[x] - pSrc1[x];
352      }
353      pSrc0 += iSrc0Stride;
354      pSrc1 += iSrc1Stride;
355      pDst  += iDstStride;
356    }
357  }
358}
359
360
361
362
363Void TComYuv::addAvg( const TComYuv* pcYuvSrc0, const TComYuv* pcYuvSrc1, const UInt iPartUnitIdx, const UInt uiWidth, const UInt uiHeight, const BitDepths &clipBitDepths )
364{
365  for(Int comp=0; comp<getNumberValidComponents(); comp++)
366  {
367    const ComponentID compID=ComponentID(comp);
368    const Pel* pSrc0  = pcYuvSrc0->getAddr( compID, iPartUnitIdx );
369    const Pel* pSrc1  = pcYuvSrc1->getAddr( compID, iPartUnitIdx );
370    Pel* pDst   = getAddr( compID, iPartUnitIdx );
371
372    const UInt  iSrc0Stride = pcYuvSrc0->getStride(compID);
373    const UInt  iSrc1Stride = pcYuvSrc1->getStride(compID);
374    const UInt  iDstStride  = getStride(compID);
375    const Int   clipbd      = clipBitDepths.recon[toChannelType(compID)];
376    const Int   shiftNum    = std::max<Int>(2, (IF_INTERNAL_PREC - clipbd)) + 1;
377    const Int   offset      = ( 1 << ( shiftNum - 1 ) ) + 2 * IF_INTERNAL_OFFS;
378
379    const Int   iWidth      = uiWidth  >> getComponentScaleX(compID);
380    const Int   iHeight     = uiHeight >> getComponentScaleY(compID);
381
382    if (iWidth&1)
383    {
384      assert(0);
385      exit(-1);
386    }
387    else if (iWidth&2)
388    {
389      for ( Int y = 0; y < iHeight; y++ )
390      {
391        for (Int x=0 ; x < iWidth; x+=2 )
392        {
393          pDst[ x + 0 ] = ClipBD( rightShift(( pSrc0[ x + 0 ] + pSrc1[ x + 0 ] + offset ), shiftNum), clipbd );
394          pDst[ x + 1 ] = ClipBD( rightShift(( pSrc0[ x + 1 ] + pSrc1[ x + 1 ] + offset ), shiftNum), clipbd );
395        }
396        pSrc0 += iSrc0Stride;
397        pSrc1 += iSrc1Stride;
398        pDst  += iDstStride;
399      }
400    }
401    else
402    {
403      for ( Int y = 0; y < iHeight; y++ )
404      {
405        for (Int x=0 ; x < iWidth; x+=4 )
406        {
407          pDst[ x + 0 ] = ClipBD( rightShift(( pSrc0[ x + 0 ] + pSrc1[ x + 0 ] + offset ), shiftNum), clipbd );
408          pDst[ x + 1 ] = ClipBD( rightShift(( pSrc0[ x + 1 ] + pSrc1[ x + 1 ] + offset ), shiftNum), clipbd );
409          pDst[ x + 2 ] = ClipBD( rightShift(( pSrc0[ x + 2 ] + pSrc1[ x + 2 ] + offset ), shiftNum), clipbd );
410          pDst[ x + 3 ] = ClipBD( rightShift(( pSrc0[ x + 3 ] + pSrc1[ x + 3 ] + offset ), shiftNum), clipbd );
411        }
412        pSrc0 += iSrc0Stride;
413        pSrc1 += iSrc1Stride;
414        pDst  += iDstStride;
415      }
416    }
417  }
418}
419
420Void TComYuv::removeHighFreq( const TComYuv* pcYuvSrc,
421                              const UInt uiPartIdx,
422                              const UInt uiWidth,
423                              const UInt uiHeight,
424                              const Int bitDepths[MAX_NUM_CHANNEL_TYPE],
425                              const Bool bClipToBitDepths
426                              )
427{
428  for(Int comp=0; comp<getNumberValidComponents(); comp++)
429  {
430    const ComponentID compID=ComponentID(comp);
431    const Pel* pSrc  = pcYuvSrc->getAddr(compID, uiPartIdx);
432    Pel* pDst  = getAddr(compID, uiPartIdx);
433
434    const Int iSrcStride = pcYuvSrc->getStride(compID);
435    const Int iDstStride = getStride(compID);
436    const Int iWidth  = uiWidth >>getComponentScaleX(compID);
437    const Int iHeight = uiHeight>>getComponentScaleY(compID);
438    if (bClipToBitDepths)
439    {
440      const Int clipBd=bitDepths[toChannelType(compID)];
441      for ( Int y = iHeight-1; y >= 0; y-- )
442      {
443        for ( Int x = iWidth-1; x >= 0; x-- )
444        {
445          pDst[x ] = ClipBD((2 * pDst[x]) - pSrc[x], clipBd);
446        }
447        pSrc += iSrcStride;
448        pDst += iDstStride;
449      }
450    }
451    else
452    {
453      for ( Int y = iHeight-1; y >= 0; y-- )
454      {
455        for ( Int x = iWidth-1; x >= 0; x-- )
456        {
457          pDst[x ] = (2 * pDst[x]) - pSrc[x];
458        }
459        pSrc += iSrcStride;
460        pDst += iDstStride;
461      }
462    }
463  }
464}
465
466#if NH_3D_VSO
467Void TComYuv::addClipPartLuma( Int bitDepth, TComYuv* pcYuvSrc0, TComYuv* pcYuvSrc1, UInt uiTrUnitIdx, UInt uiPartSize )
468{
469  Int x, y;
470
471  Pel* pSrc0 = pcYuvSrc0->getAddr( COMPONENT_Y, uiTrUnitIdx);
472  Pel* pSrc1 = pcYuvSrc1->getAddr( COMPONENT_Y, uiTrUnitIdx);
473  Pel* pDst  =            getAddr( COMPONENT_Y, uiTrUnitIdx);
474
475  UInt iSrc0Stride = pcYuvSrc0->getStride( COMPONENT_Y );
476  UInt iSrc1Stride = pcYuvSrc1->getStride( COMPONENT_Y );
477  UInt iDstStride  =            getStride( COMPONENT_Y );
478  for ( y = uiPartSize-1; y >= 0; y-- )
479  {
480    for ( x = uiPartSize-1; x >= 0; x-- )
481    {
482      pDst[x] = ClipBD( pSrc0[x] + pSrc1[x], bitDepth );     
483    }
484    pSrc0 += iSrc0Stride;
485    pSrc1 += iSrc1Stride;
486    pDst  += iDstStride;
487  }
488}
489
490#if NH_3D_ARP
491Void TComYuv::addARP( TComYuv* pcYuvSrc0, TComYuv* pcYuvSrc1, UInt uiAbsPartIdx, UInt uiWidth, UInt uiHeight, Bool bClip, const BitDepths &clipBitDepths )
492{
493  addARPLuma   ( pcYuvSrc0, pcYuvSrc1, uiAbsPartIdx, uiWidth   , uiHeight    , bClip , clipBitDepths);
494  addARPChroma ( pcYuvSrc0, pcYuvSrc1, uiAbsPartIdx, uiWidth>>1, uiHeight>>1 , bClip , clipBitDepths);
495}
496
497Void TComYuv::addARPLuma( TComYuv* pcYuvSrc0, TComYuv* pcYuvSrc1, UInt uiAbsPartIdx, UInt uiWidth, UInt uiHeight, Bool bClip, const BitDepths &clipBitDepths )
498{
499  Int x, y;
500
501  Pel* pSrc0 = pcYuvSrc0->getAddr( COMPONENT_Y, uiAbsPartIdx );
502  Pel* pSrc1 = pcYuvSrc1->getAddr( COMPONENT_Y, uiAbsPartIdx );
503  Pel* pDst  = getAddr( COMPONENT_Y, uiAbsPartIdx );
504
505  UInt iSrc0Stride = pcYuvSrc0->getStride(COMPONENT_Y);
506  UInt iSrc1Stride = pcYuvSrc1->getStride(COMPONENT_Y);
507  UInt iDstStride  = getStride(COMPONENT_Y);
508  const Int clipbd = clipBitDepths.recon[CHANNEL_TYPE_LUMA];
509  Int iIFshift = IF_INTERNAL_PREC - clipbd;
510  Int iOffSet  = ( 1 << ( iIFshift - 1 ) ) + IF_INTERNAL_OFFS;
511  for ( y = uiHeight-1; y >= 0; y-- )
512  {
513    for ( x = uiWidth-1; x >= 0; x-- )
514    {
515      pDst[x] = pSrc0[x] + pSrc1[x];
516      if( bClip )
517      {
518        pDst[x] = Pel(ClipBD<Int>(Int( ( pDst[x] + iOffSet ) >> iIFshift ), clipbd));
519      }
520    }
521    pSrc0 += iSrc0Stride;
522    pSrc1 += iSrc1Stride;
523    pDst  += iDstStride;
524  }
525}
526
527Void TComYuv::addARPChroma( TComYuv* pcYuvSrc0, TComYuv* pcYuvSrc1, UInt uiAbsPartIdx, UInt uiWidth, UInt uiHeight, Bool bClip, const BitDepths &clipBitDepths )
528{
529  Int x, y;
530
531  Pel* pSrcU0 = pcYuvSrc0->getAddr( COMPONENT_Cb, uiAbsPartIdx );
532  Pel* pSrcU1 = pcYuvSrc1->getAddr( COMPONENT_Cb, uiAbsPartIdx );
533  Pel* pSrcV0 = pcYuvSrc0->getAddr( COMPONENT_Cr, uiAbsPartIdx );
534  Pel* pSrcV1 = pcYuvSrc1->getAddr( COMPONENT_Cr, uiAbsPartIdx );
535  Pel* pDstU = getAddr( COMPONENT_Cb, uiAbsPartIdx );
536  Pel* pDstV = getAddr( COMPONENT_Cr, uiAbsPartIdx );
537
538  UInt  iSrc0StrideCb = pcYuvSrc0->getStride(COMPONENT_Cb);
539  UInt  iSrc1StrideCb = pcYuvSrc1->getStride(COMPONENT_Cb);
540  UInt  iDstStrideCb  = getStride(COMPONENT_Cb);
541
542  UInt  iSrc0StrideCr = pcYuvSrc0->getStride(COMPONENT_Cr);
543  UInt  iSrc1StrideCr = pcYuvSrc1->getStride(COMPONENT_Cr);
544  UInt  iDstStrideCr  = getStride(COMPONENT_Cr);
545
546  const Int clipbd = clipBitDepths.recon[CHANNEL_TYPE_CHROMA];
547  Int iIFshift = IF_INTERNAL_PREC - clipbd;
548  Int iOffSet  = ( 1 << ( iIFshift - 1 ) ) + IF_INTERNAL_OFFS;
549
550  for ( y = uiHeight-1; y >= 0; y-- )
551  {
552    for ( x = uiWidth-1; x >= 0; x-- )
553    {
554      pDstU[x] = pSrcU0[x] + pSrcU1[x];
555      pDstV[x] = pSrcV0[x] + pSrcV1[x];
556      if( bClip )
557      {
558        pDstU[x] = Pel(ClipBD<Int>( Int( ( pDstU[x] + iOffSet ) >> iIFshift ), clipbd));
559        pDstV[x] = Pel(ClipBD<Int>( Int( ( pDstV[x] + iOffSet ) >> iIFshift ), clipbd));
560      }
561    }
562
563    pSrcU0 += iSrc0StrideCb;
564    pSrcU1 += iSrc1StrideCb;
565    pSrcV0 += iSrc0StrideCr;
566    pSrcV1 += iSrc1StrideCr;
567    pDstU  += iDstStrideCb;
568    pDstV  += iDstStrideCr;
569  }
570}
571
572Void TComYuv::subtractARP( TComYuv* pcYuvSrc0, TComYuv* pcYuvSrc1, UInt uiAbsPartIdx, UInt uiWidth , UInt uiHeight )
573{
574  subtractARPLuma  ( pcYuvSrc0, pcYuvSrc1,  uiAbsPartIdx, uiWidth    , uiHeight    );
575
576  if (uiWidth > 8 && pcYuvSrc1->getNumberValidComponents() > 1)
577  {
578    subtractARPChroma( pcYuvSrc0, pcYuvSrc1,  uiAbsPartIdx, uiWidth>>1 , uiHeight>>1 );
579}
580}
581
582Void TComYuv::subtractARPLuma( TComYuv* pcYuvSrc0, TComYuv* pcYuvSrc1, UInt uiAbsPartIdx, UInt uiWidth , UInt uiHeight )
583{
584  Int x, y;
585
586  Pel* pSrc0 = pcYuvSrc0->getAddr(COMPONENT_Y, uiAbsPartIdx );
587  Pel* pSrc1 = pcYuvSrc1->getAddr(COMPONENT_Y, uiAbsPartIdx );
588  Pel* pDst  = getAddr           (COMPONENT_Y, uiAbsPartIdx );
589
590  Int  iSrc0Stride = pcYuvSrc0->getStride(COMPONENT_Y);
591  Int  iSrc1Stride = pcYuvSrc1->getStride(COMPONENT_Y);
592  Int  iDstStride  = getStride(COMPONENT_Y);
593  for ( y = uiHeight-1; y >= 0; y-- )
594  {
595    for ( x = uiWidth-1; x >= 0; x-- )
596    {
597      pDst[x] = pSrc0[x] - pSrc1[x];
598    }
599    pSrc0 += iSrc0Stride;
600    pSrc1 += iSrc1Stride;
601    pDst  += iDstStride;
602  }
603}
604
605Void TComYuv::subtractARPChroma( TComYuv* pcYuvSrc0, TComYuv* pcYuvSrc1, UInt uiAbsPartIdx, UInt uiWidth , UInt uiHeight )
606{
607  Int x, y;
608
609  Pel* pSrcU0 = pcYuvSrc0->getAddr(COMPONENT_Cb, uiAbsPartIdx );
610  Pel* pSrcU1 = pcYuvSrc1->getAddr(COMPONENT_Cb, uiAbsPartIdx );
611  Pel* pSrcV0 = pcYuvSrc0->getAddr(COMPONENT_Cr, uiAbsPartIdx );
612  Pel* pSrcV1 = pcYuvSrc1->getAddr(COMPONENT_Cr, uiAbsPartIdx );
613  Pel* pDstU  = getAddr(COMPONENT_Cb, uiAbsPartIdx );
614  Pel* pDstV  = getAddr(COMPONENT_Cr, uiAbsPartIdx );
615
616  Int  iSrc0Stride = pcYuvSrc0->getStride(COMPONENT_Cb);
617  Int  iSrc1Stride = pcYuvSrc1->getStride(COMPONENT_Cb);
618  Int  iDstStride  = getStride( COMPONENT_Cb );
619  for ( y = uiHeight-1; y >= 0; y-- )
620  {
621    for ( x = uiWidth-1; x >= 0; x-- )
622    {
623      pDstU[x] = pSrcU0[x] - pSrcU1[x];
624      pDstV[x] = pSrcV0[x] - pSrcV1[x];
625    }
626    pSrcU0 += iSrc0Stride;
627    pSrcU1 += iSrc1Stride;
628    pSrcV0 += iSrc0Stride;
629    pSrcV1 += iSrc1Stride;
630    pDstU  += iDstStride;
631    pDstV  += iDstStride;
632  }
633}
634
635Void TComYuv::multiplyARP( UInt uiAbsPartIdx , UInt uiWidth , UInt uiHeight , UChar dW )
636{
637  multiplyARPLuma( uiAbsPartIdx , uiWidth , uiHeight , dW );
638
639  if ( uiWidth > 8 && getNumberValidComponents() > 1 )
640  {
641    multiplyARPChroma( uiAbsPartIdx , uiWidth >> 1 , uiHeight >> 1 , dW );
642}
643}
644
645Void TComYuv::xxMultiplyLine( Pel* pSrcDst , UInt uiWidth , UChar dW )
646{
647  assert( dW == 2 );
648  for( UInt x = 0 ; x < uiWidth ; x++ )
649    pSrcDst[x] =  pSrcDst[x] >> 1;
650}
651
652Void TComYuv::multiplyARPLuma( UInt uiAbsPartIdx , UInt uiWidth , UInt uiHeight , UChar dW )
653{
654  Pel* pDst  = getAddr(COMPONENT_Y, uiAbsPartIdx );
655  Int  iDstStride  = getStride(COMPONENT_Y);
656  for ( Int y = uiHeight-1; y >= 0; y-- )
657  {
658    xxMultiplyLine( pDst , uiWidth , dW );
659    pDst  += iDstStride;
660  }
661}
662
663Void TComYuv::multiplyARPChroma( UInt uiAbsPartIdx , UInt uiWidth , UInt uiHeight , UChar dW )
664{
665  Pel* pDstU  = getAddr( COMPONENT_Cb, uiAbsPartIdx );
666  Pel* pDstV  = getAddr( COMPONENT_Cr, uiAbsPartIdx );
667
668  Int  iDstStride  = getStride( COMPONENT_Cb );
669  for ( Int y = uiHeight-1; y >= 0; y-- )
670  {
671    xxMultiplyLine( pDstU , uiWidth , dW );
672    xxMultiplyLine( pDstV , uiWidth , dW );
673    pDstU  += iDstStride;
674    pDstV  += iDstStride;
675  }
676}
677#endif
678#endif
679
680//! \}
Note: See TracBrowser for help on using the repository browser.