1
2/*
3 * Copyright 2011 Google Inc.
4 *
5 * Use of this source code is governed by a BSD-style license that can be
6 * found in the LICENSE file.
7 */
8
9#include "SkMathPriv.h"
10
11#define SCALE_FILTER_NAME       MAKENAME(_filter_DX_shaderproc)
12
13// Can't be static in the general case because some of these implementations
14// will be defined and referenced in different object files.
15void SCALE_FILTER_NAME(const SkBitmapProcState& s, int x, int y,
16                       DSTTYPE* SK_RESTRICT colors, int count);
17
18void SCALE_FILTER_NAME(const SkBitmapProcState& s, int x, int y,
19                       DSTTYPE* SK_RESTRICT colors, int count) {
20    SkASSERT((s.fInvType & ~(SkMatrix::kTranslate_Mask |
21                             SkMatrix::kScale_Mask)) == 0);
22    SkASSERT(s.fInvKy == 0);
23    SkASSERT(count > 0 && colors != NULL);
24    SkASSERT(s.fFilterLevel != SkPaint::kNone_FilterLevel);
25    SkDEBUGCODE(CHECKSTATE(s);)
26
27    const unsigned maxX = s.fBitmap->width() - 1;
28    const SkFixed oneX = s.fFilterOneX;
29    const SkFixed dx = s.fInvSx;
30    SkFixed fx;
31    const SRCTYPE* SK_RESTRICT row0;
32    const SRCTYPE* SK_RESTRICT row1;
33    unsigned subY;
34
35    {
36        SkPoint pt;
37        s.fInvProc(s.fInvMatrix, SkIntToScalar(x) + SK_ScalarHalf,
38                   SkIntToScalar(y) + SK_ScalarHalf, &pt);
39        SkFixed fy = SkScalarToFixed(pt.fY) - (s.fFilterOneY >> 1);
40        const unsigned maxY = s.fBitmap->height() - 1;
41        // compute our two Y values up front
42        subY = TILEY_LOW_BITS(fy, maxY);
43        int y0 = TILEY_PROCF(fy, maxY);
44        int y1 = TILEY_PROCF((fy + s.fFilterOneY), maxY);
45
46        const char* SK_RESTRICT srcAddr = (const char*)s.fBitmap->getPixels();
47        size_t rb = s.fBitmap->rowBytes();
48        row0 = (const SRCTYPE*)(srcAddr + y0 * rb);
49        row1 = (const SRCTYPE*)(srcAddr + y1 * rb);
50        // now initialize fx
51        fx = SkScalarToFixed(pt.fX) - (oneX >> 1);
52    }
53
54#ifdef PREAMBLE
55    PREAMBLE(s);
56#endif
57
58    do {
59        unsigned subX = TILEX_LOW_BITS(fx, maxX);
60        unsigned x0 = TILEX_PROCF(fx, maxX);
61        unsigned x1 = TILEX_PROCF((fx + oneX), maxX);
62
63        FILTER_PROC(subX, subY,
64                    SRC_TO_FILTER(row0[x0]),
65                    SRC_TO_FILTER(row0[x1]),
66                    SRC_TO_FILTER(row1[x0]),
67                    SRC_TO_FILTER(row1[x1]),
68                    colors);
69        colors += 1;
70
71        fx += dx;
72    } while (--count != 0);
73
74#ifdef POSTAMBLE
75    POSTAMBLE(s);
76#endif
77}
78
79///////////////////////////////////////////////////////////////////////////////
80
81#undef TILEX_PROCF
82#undef TILEY_PROCF
83#undef TILEX_LOW_BITS
84#undef TILEY_LOW_BITS
85#undef MAKENAME
86#undef SRCTYPE
87#undef DSTTYPE
88#undef CHECKSTATE
89#undef SRC_TO_FILTER
90#undef FILTER_TO_DST
91#undef PREAMBLE
92#undef POSTAMBLE
93
94#undef SCALE_FILTER_NAME
95