1 :
2 : /*
3 : * Copyright 2006 The Android Open Source Project
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 :
10 : #ifndef SkColorFilter_DEFINED
11 : #define SkColorFilter_DEFINED
12 :
13 : #include "SkColor.h"
14 : #include "SkFlattenable.h"
15 : #include "SkXfermode.h"
16 :
17 0 : class SK_API SkColorFilter : public SkFlattenable {
18 : public:
19 : /**
20 : * If the filter can be represented by a source color plus Mode, this
21 : * returns true, and sets (if not NULL) the color and mode appropriately.
22 : * If not, this returns false and ignores the parameters.
23 : */
24 : virtual bool asColorMode(SkColor* color, SkXfermode::Mode* mode);
25 :
26 : /**
27 : * If the filter can be represented by a 5x4 matrix, this
28 : * returns true, and sets the matrix appropriately.
29 : * If not, this returns false and ignores the parameter.
30 : */
31 : virtual bool asColorMatrix(SkScalar matrix[20]);
32 :
33 : /**
34 : * If the filter can be represented by per-component table, return true,
35 : * and if table is not null, copy the bitmap containing the table into it.
36 : *
37 : * The table bitmap will be in SkBitmap::kA8_Config. Each row corresponding
38 : * to each component in ARGB order. e.g. row[0] == alpha, row[1] == red,
39 : * etc. To transform a color, you (logically) perform the following:
40 : *
41 : * a' = *table.getAddr8(a, 0);
42 : * r' = *table.getAddr8(r, 1);
43 : * g' = *table.getAddr8(g, 2);
44 : * b' = *table.getAddr8(b, 3);
45 : *
46 : * The original component value is the horizontal index for a given row,
47 : * and the stored value at that index is the new value for that component.
48 : */
49 : virtual bool asComponentTable(SkBitmap* table);
50 :
51 : /** Called with a scanline of colors, as if there was a shader installed.
52 : The implementation writes out its filtered version into result[].
53 : Note: shader and result may be the same buffer.
54 : @param src array of colors, possibly generated by a shader
55 : @param count the number of entries in the src[] and result[] arrays
56 : @param result written by the filter
57 : */
58 : virtual void filterSpan(const SkPMColor src[], int count,
59 : SkPMColor result[]) = 0;
60 : /** Called with a scanline of colors, as if there was a shader installed.
61 : The implementation writes out its filtered version into result[].
62 : Note: shader and result may be the same buffer.
63 : @param src array of colors, possibly generated by a shader
64 : @param count the number of entries in the src[] and result[] arrays
65 : @param result written by the filter
66 : */
67 : virtual void filterSpan16(const uint16_t shader[], int count,
68 : uint16_t result[]);
69 :
70 : enum Flags {
71 : /** If set the filter methods will not change the alpha channel of the
72 : colors.
73 : */
74 : kAlphaUnchanged_Flag = 0x01,
75 : /** If set, this subclass implements filterSpan16(). If this flag is
76 : set, then kAlphaUnchanged_Flag must also be set.
77 : */
78 : kHasFilter16_Flag = 0x02
79 : };
80 :
81 : /** Returns the flags for this filter. Override in subclasses to return
82 : custom flags.
83 : */
84 0 : virtual uint32_t getFlags() { return 0; }
85 :
86 : /**
87 : * Apply this colorfilter to the specified SkColor. This routine handles
88 : * converting to SkPMColor, calling the filter, and then converting back
89 : * to SkColor. This method is not virtual, but will call filterSpan()
90 : * which is virtual.
91 : */
92 : SkColor filterColor(SkColor);
93 :
94 :
95 : /** Create a colorfilter that uses the specified color and mode.
96 : If the Mode is DST, this function will return NULL (since that
97 : mode will have no effect on the result).
98 : @param c The source color used with the specified mode
99 : @param mode The xfermode mode that is applied to each color in
100 : the colorfilter's filterSpan[16,32] methods
101 : @return colorfilter object that applies the src color and mode,
102 : or NULL if the mode will have no effect.
103 : */
104 : static SkColorFilter* CreateModeFilter(SkColor c, SkXfermode::Mode mode);
105 :
106 : /** Create a colorfilter that calls through to the specified procs to
107 : filter the colors. The SkXfermodeProc parameter must be non-null, but
108 : the SkXfermodeProc16 is optional, and may be null.
109 : */
110 : static SkColorFilter* CreateProcFilter(SkColor srcColor,
111 : SkXfermodeProc proc,
112 : SkXfermodeProc16 proc16 = NULL);
113 :
114 : /** Create a colorfilter that multiplies the RGB channels by one color, and
115 : then adds a second color, pinning the result for each component to
116 : [0..255]. The alpha components of the mul and add arguments
117 : are ignored.
118 : */
119 : static SkColorFilter* CreateLightingFilter(SkColor mul, SkColor add);
120 :
121 : SK_DECLARE_FLATTENABLE_REGISTRAR()
122 : protected:
123 0 : SkColorFilter() {}
124 : SkColorFilter(SkFlattenableReadBuffer& rb) : INHERITED(rb) {}
125 :
126 : private:
127 : typedef SkFlattenable INHERITED;
128 : };
129 :
130 : #include "SkShader.h"
131 :
132 : class SkFilterShader : public SkShader {
133 : public:
134 : SkFilterShader(SkShader* shader, SkColorFilter* filter);
135 : virtual ~SkFilterShader();
136 :
137 : // override
138 : virtual uint32_t getFlags();
139 : virtual bool setContext(const SkBitmap& device, const SkPaint& paint,
140 : const SkMatrix& matrix);
141 : virtual void shadeSpan(int x, int y, SkPMColor result[], int count);
142 : virtual void shadeSpan16(int x, int y, uint16_t result[], int count);
143 : virtual void beginSession();
144 : virtual void endSession();
145 :
146 : protected:
147 : SkFilterShader(SkFlattenableReadBuffer& );
148 : virtual void flatten(SkFlattenableWriteBuffer& ) SK_OVERRIDE;
149 0 : virtual Factory getFactory() SK_OVERRIDE { return CreateProc; }
150 : private:
151 0 : static SkFlattenable* CreateProc(SkFlattenableReadBuffer& buffer) {
152 0 : return SkNEW_ARGS(SkFilterShader, (buffer)); }
153 : SkShader* fShader;
154 : SkColorFilter* fFilter;
155 :
156 : typedef SkShader INHERITED;
157 : };
158 :
159 : #endif
|