source: 3DVCSoftware/branches/HTM-6.0-dev0/source/Lib/TLibCommon/TComInterpolationFilter.cpp @ 312

Last change on this file since 312 was 56, checked in by hschwarz, 12 years ago

updated trunk (move to HM6.1)

File size: 13.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-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/**
35 * \file
36 * \brief Implementation of TComInterpolationFilter class
37 */
38
39// ====================================================================================================================
40// Includes
41// ====================================================================================================================
42
43#include "TComRom.h"
44#include "TComInterpolationFilter.h"
45#include <assert.h>
46
47
48//! \ingroup TLibCommon
49//! \{
50
51// ====================================================================================================================
52// Tables
53// ====================================================================================================================
54
55const Short TComInterpolationFilter::m_lumaFilter[4][NTAPS_LUMA] =
56{
57  {  0, 0,   0, 64,  0,   0, 0,  0 },
58  { -1, 4, -10, 58, 17,  -5, 1,  0 },
59  { -1, 4, -11, 40, 40, -11, 4, -1 },
60  {  0, 1,  -5, 17, 58, -10, 4, -1 }
61};
62
63const Short TComInterpolationFilter::m_chromaFilter[8][NTAPS_CHROMA] =
64{
65  {  0, 64,  0,  0 },
66  { -2, 58, 10, -2 },
67  { -4, 54, 16, -2 },
68  { -6, 46, 28, -4 },
69  { -4, 36, 36, -4 },
70  { -4, 28, 46, -6 },
71  { -2, 16, 54, -4 },
72  { -2, 10, 58, -2 }
73};
74
75// ====================================================================================================================
76// Private member functions
77// ====================================================================================================================
78
79/**
80 * \brief Apply unit FIR filter to a block of samples
81 *
82 * \param src        Pointer to source samples
83 * \param srcStride  Stride of source samples
84 * \param dst        Pointer to destination samples
85 * \param dstStride  Stride of destination samples
86 * \param width      Width of block
87 * \param height     Height of block
88 * \param isFirst    Flag indicating whether it is the first filtering operation
89 * \param isLast     Flag indicating whether it is the last filtering operation
90 */
91Void TComInterpolationFilter::filterCopy(const Pel *src, Int srcStride, Short *dst, Int dstStride, Int width, Int height, Bool isFirst, Bool isLast)
92{
93  Int row, col;
94 
95  if ( isFirst == isLast )
96  {
97    for (row = 0; row < height; row++)
98    {
99      for (col = 0; col < width; col++)
100      {
101        dst[col] = src[col];
102      }
103     
104      src += srcStride;
105      dst += dstStride;
106    }             
107  }
108  else if ( isFirst )
109  {
110    Int shift = IF_INTERNAL_PREC - ( g_uiBitDepth + g_uiBitIncrement );
111   
112    for (row = 0; row < height; row++)
113    {
114      for (col = 0; col < width; col++)
115      {
116        Short val = src[col] << shift;
117        dst[col] = val - (Short)IF_INTERNAL_OFFS;
118      }
119     
120      src += srcStride;
121      dst += dstStride;
122    }         
123  }
124  else
125  {
126    Int shift = IF_INTERNAL_PREC - ( g_uiBitDepth + g_uiBitIncrement );
127    Short offset = IF_INTERNAL_OFFS + (1 << (shift - 1));
128    Short maxVal = g_uiIBDI_MAX;
129    Short minVal = 0;
130    for (row = 0; row < height; row++)
131    {
132      for (col = 0; col < width; col++)
133      {
134        Short val = src[ col ];
135        val = ( val + offset ) >> shift;
136        if (val < minVal) val = minVal;
137        if (val > maxVal) val = maxVal;
138        dst[col] = val;
139      }
140     
141      src += srcStride;
142      dst += dstStride;
143    }             
144  }
145}
146
147/**
148 * \brief Apply FIR filter to a block of samples
149 *
150 * \tparam N          Number of taps
151 * \tparam isVertical Flag indicating filtering along vertical direction
152 * \tparam isFirst    Flag indicating whether it is the first filtering operation
153 * \tparam isLast     Flag indicating whether it is the last filtering operation
154 * \param  src        Pointer to source samples
155 * \param  srcStride  Stride of source samples
156 * \param  dst        Pointer to destination samples
157 * \param  dstStride  Stride of destination samples
158 * \param  width      Width of block
159 * \param  height     Height of block
160 * \param  coeff      Pointer to filter taps
161 */
162template<int N, bool isVertical, bool isFirst, bool isLast>
163Void TComInterpolationFilter::filter(Short const *src, Int srcStride, Short *dst, Int dstStride, Int width, Int height, Short const *coeff)
164{
165  Int row, col;
166 
167  Short c[8];
168  c[0] = coeff[0];
169  c[1] = coeff[1];
170  if ( N >= 4 )
171  {
172    c[2] = coeff[2];
173    c[3] = coeff[3];
174  }
175  if ( N >= 6 )
176  {
177    c[4] = coeff[4];
178    c[5] = coeff[5];
179  }
180  if ( N == 8 )
181  {
182    c[6] = coeff[6];
183    c[7] = coeff[7];
184  }
185 
186  Int cStride = ( isVertical ) ? srcStride : 1;
187  src -= ( N/2 - 1 ) * cStride;
188
189  Int offset;
190  Short maxVal;
191  Int headRoom = IF_INTERNAL_PREC - (g_uiBitDepth + g_uiBitIncrement);
192  Int shift = IF_FILTER_PREC;
193  if ( isLast )
194  {
195    shift += (isFirst) ? 0 : headRoom;
196    offset = 1 << (shift - 1);
197    offset += (isFirst) ? 0 : IF_INTERNAL_OFFS << IF_FILTER_PREC;
198    maxVal = g_uiIBDI_MAX;
199  }
200  else
201  {
202    shift -= (isFirst) ? headRoom : 0;
203    offset = (isFirst) ? -IF_INTERNAL_OFFS << shift : 0;
204    maxVal = 0;
205  }
206 
207  for (row = 0; row < height; row++)
208  {
209    for (col = 0; col < width; col++)
210    {
211      Int sum;
212     
213      sum  = src[ col + 0 * cStride] * c[0];
214      sum += src[ col + 1 * cStride] * c[1];
215      if ( N >= 4 )
216      {
217        sum += src[ col + 2 * cStride] * c[2];
218        sum += src[ col + 3 * cStride] * c[3];
219      }
220      if ( N >= 6 )
221      {
222        sum += src[ col + 4 * cStride] * c[4];
223        sum += src[ col + 5 * cStride] * c[5];
224      }
225      if ( N == 8 )
226      {
227        sum += src[ col + 6 * cStride] * c[6];
228        sum += src[ col + 7 * cStride] * c[7];       
229      }
230     
231      Short val = ( sum + offset ) >> shift;
232      if ( isLast )
233      {
234        val = ( val < 0 ) ? 0 : val;
235        val = ( val > maxVal ) ? maxVal : val;       
236      }
237      dst[col] = val;
238    }
239   
240    src += srcStride;
241    dst += dstStride;
242  }   
243}
244
245/**
246 * \brief Filter a block of samples (horizontal)
247 *
248 * \tparam N          Number of taps
249 * \param  src        Pointer to source samples
250 * \param  srcStride  Stride of source samples
251 * \param  dst        Pointer to destination samples
252 * \param  dstStride  Stride of destination samples
253 * \param  width      Width of block
254 * \param  height     Height of block
255 * \param  isLast     Flag indicating whether it is the last filtering operation
256 * \param  coeff      Pointer to filter taps
257 */
258template<int N>
259Void TComInterpolationFilter::filterHor(Pel *src, Int srcStride, Short *dst, Int dstStride, Int width, Int height, Bool isLast, Short const *coeff)
260{
261  if ( isLast )
262  {
263    filter<N, false, true, true>(src, srcStride, dst, dstStride, width, height, coeff);
264  }
265  else
266  {
267    filter<N, false, true, false>(src, srcStride, dst, dstStride, width, height, coeff);
268  }
269}
270
271/**
272 * \brief Filter a block of samples (vertical)
273 *
274 * \tparam N          Number of taps
275 * \param  src        Pointer to source samples
276 * \param  srcStride  Stride of source samples
277 * \param  dst        Pointer to destination samples
278 * \param  dstStride  Stride of destination samples
279 * \param  width      Width of block
280 * \param  height     Height of block
281 * \param  isFirst    Flag indicating whether it is the first filtering operation
282 * \param  isLast     Flag indicating whether it is the last filtering operation
283 * \param  coeff      Pointer to filter taps
284 */
285template<int N>
286Void TComInterpolationFilter::filterVer(Pel *src, Int srcStride, Short *dst, Int dstStride, Int width, Int height, Bool isFirst, Bool isLast, Short const *coeff)
287{
288  if ( isFirst && isLast )
289  {
290    filter<N, true, true, true>(src, srcStride, dst, dstStride, width, height, coeff);
291  }
292  else if ( isFirst && !isLast )
293  {
294    filter<N, true, true, false>(src, srcStride, dst, dstStride, width, height, coeff);
295  }
296  else if ( !isFirst && isLast )
297  {
298    filter<N, true, false, true>(src, srcStride, dst, dstStride, width, height, coeff);
299  }
300  else
301  {
302    filter<N, true, false, false>(src, srcStride, dst, dstStride, width, height, coeff);   
303  }     
304}
305
306// ====================================================================================================================
307// Public member functions
308// ====================================================================================================================
309
310/**
311 * \brief Filter a block of luma samples (horizontal)
312 *
313 * \param  src        Pointer to source samples
314 * \param  srcStride  Stride of source samples
315 * \param  dst        Pointer to destination samples
316 * \param  dstStride  Stride of destination samples
317 * \param  width      Width of block
318 * \param  height     Height of block
319 * \param  frac       Fractional sample offset
320 * \param  isLast     Flag indicating whether it is the last filtering operation
321 */
322Void TComInterpolationFilter::filterHorLuma(Pel *src, Int srcStride, Short *dst, Int dstStride, Int width, Int height, Int frac, Bool isLast )
323{
324  assert(frac >= 0 && frac < 4);
325 
326  if ( frac == 0 )
327  {
328    filterCopy( src, srcStride, dst, dstStride, width, height, true, isLast );
329  }
330  else
331  {
332    filterHor<NTAPS_LUMA>(src, srcStride, dst, dstStride, width, height, isLast, m_lumaFilter[frac]);
333  }
334}
335
336/**
337 * \brief Filter a block of luma samples (vertical)
338 *
339 * \param  src        Pointer to source samples
340 * \param  srcStride  Stride of source samples
341 * \param  dst        Pointer to destination samples
342 * \param  dstStride  Stride of destination samples
343 * \param  width      Width of block
344 * \param  height     Height of block
345 * \param  frac       Fractional sample offset
346 * \param  isFirst    Flag indicating whether it is the first filtering operation
347 * \param  isLast     Flag indicating whether it is the last filtering operation
348 */
349Void TComInterpolationFilter::filterVerLuma(Pel *src, Int srcStride, Short *dst, Int dstStride, Int width, Int height, Int frac, Bool isFirst, Bool isLast )
350{
351  assert(frac >= 0 && frac < 4);
352 
353  if ( frac == 0 )
354  {
355    filterCopy( src, srcStride, dst, dstStride, width, height, isFirst, isLast );
356  }
357  else
358  {
359    filterVer<NTAPS_LUMA>(src, srcStride, dst, dstStride, width, height, isFirst, isLast, m_lumaFilter[frac]);   
360  }
361}
362
363/**
364 * \brief Filter a block of chroma samples (horizontal)
365 *
366 * \param  src        Pointer to source samples
367 * \param  srcStride  Stride of source samples
368 * \param  dst        Pointer to destination samples
369 * \param  dstStride  Stride of destination samples
370 * \param  width      Width of block
371 * \param  height     Height of block
372 * \param  frac       Fractional sample offset
373 * \param  isLast     Flag indicating whether it is the last filtering operation
374 */
375Void TComInterpolationFilter::filterHorChroma(Pel *src, Int srcStride, Short *dst, Int dstStride, Int width, Int height, Int frac, Bool isLast )
376{
377  assert(frac >= 0 && frac < 8);
378 
379  if ( frac == 0 )
380  {
381    filterCopy( src, srcStride, dst, dstStride, width, height, true, isLast );
382  }
383  else
384  {
385    filterHor<NTAPS_CHROMA>(src, srcStride, dst, dstStride, width, height, isLast, m_chromaFilter[frac]);
386  }
387}
388
389/**
390 * \brief Filter a block of chroma samples (vertical)
391 *
392 * \param  src        Pointer to source samples
393 * \param  srcStride  Stride of source samples
394 * \param  dst        Pointer to destination samples
395 * \param  dstStride  Stride of destination samples
396 * \param  width      Width of block
397 * \param  height     Height of block
398 * \param  frac       Fractional sample offset
399 * \param  isFirst    Flag indicating whether it is the first filtering operation
400 * \param  isLast     Flag indicating whether it is the last filtering operation
401 */
402Void TComInterpolationFilter::filterVerChroma(Pel *src, Int srcStride, Short *dst, Int dstStride, Int width, Int height, Int frac, Bool isFirst, Bool isLast )
403{
404  assert(frac >= 0 && frac < 8);
405 
406  if ( frac == 0 )
407  {
408    filterCopy( src, srcStride, dst, dstStride, width, height, isFirst, isLast );
409  }
410  else
411  {
412    filterVer<NTAPS_CHROMA>(src, srcStride, dst, dstStride, width, height, isFirst, isLast, m_chromaFilter[frac]);   
413  }
414}
415
416//! \}
Note: See TracBrowser for help on using the repository browser.