Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(159)

Side by Side Diff: src/gpu/GrBlend.h

Issue 1124373002: Implement Porter Duff XP with a blend table (Closed) Base URL: https://skia.googlesource.com/skia.git@master
Patch Set: add coverage at runtime Created 5 years, 7 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 1
2 /* 2 /*
3 * Copyright 2013 Google Inc. 3 * Copyright 2013 Google Inc.
4 * 4 *
5 * Use of this source code is governed by a BSD-style license that can be 5 * Use of this source code is governed by a BSD-style license that can be
6 * found in the LICENSE file. 6 * found in the LICENSE file.
7 */ 7 */
8 8
9 #include "GrTypes.h" 9 #include "GrTypes.h"
10 #include "GrColor.h" 10 #include "SkTLogic.h"
11 #include "GrXferProcessor.h" 11 #include "GrXferProcessor.h"
12 12
13 #ifndef GrBlend_DEFINED 13 #ifndef GrBlend_DEFINED
14 #define GrBlend_DEFINED 14 #define GrBlend_DEFINED
15 15
16 static inline bool GrBlendCoeffRefsSrc(GrBlendCoeff coeff) { 16 inline bool GrBlendCoeffRefsSrc(GrBlendCoeff coeff) {
17 switch (coeff) { 17 switch (coeff) {
18 case kSC_GrBlendCoeff: 18 case kSC_GrBlendCoeff:
19 case kISC_GrBlendCoeff: 19 case kISC_GrBlendCoeff:
20 case kSA_GrBlendCoeff: 20 case kSA_GrBlendCoeff:
21 case kISA_GrBlendCoeff: 21 case kISA_GrBlendCoeff:
22 return true; 22 return true;
23 default: 23 default:
24 return false; 24 return false;
25 } 25 }
26 } 26 }
27 27
28 static inline bool GrBlendCoeffRefsDst(GrBlendCoeff coeff) { 28 template<GrBlendCoeff Coeff>
29 struct GrTBlendCoeffRefsSrc : SkTBool<kSC_GrBlendCoeff == Coeff ||
30 kISC_GrBlendCoeff == Coeff ||
31 kSA_GrBlendCoeff == Coeff ||
32 kISA_GrBlendCoeff == Coeff> {};
33
34 #define GR_BLEND_COEFF_REFS_SRC(COEFF) \
35 GrTBlendCoeffRefsSrc<COEFF>::value
36
37
38 inline bool GrBlendCoeffRefsDst(GrBlendCoeff coeff) {
29 switch (coeff) { 39 switch (coeff) {
30 case kDC_GrBlendCoeff: 40 case kDC_GrBlendCoeff:
31 case kIDC_GrBlendCoeff: 41 case kIDC_GrBlendCoeff:
32 case kDA_GrBlendCoeff: 42 case kDA_GrBlendCoeff:
33 case kIDA_GrBlendCoeff: 43 case kIDA_GrBlendCoeff:
34 return true; 44 return true;
35 default: 45 default:
36 return false; 46 return false;
37 } 47 }
38 } 48 }
39 49
40 GrColor GrSimplifyBlend(GrBlendCoeff* srcCoeff, 50 template<GrBlendCoeff Coeff>
41 GrBlendCoeff* dstCoeff, 51 struct GrTBlendCoeffRefsDst : SkTBool<kDC_GrBlendCoeff == Coeff ||
42 GrColor srcColor, uint32_t srcCompFlags, 52 kIDC_GrBlendCoeff == Coeff ||
43 GrColor dstColor, uint32_t dstCompFlags, 53 kDA_GrBlendCoeff == Coeff ||
44 GrColor constantColor); 54 kIDA_GrBlendCoeff == Coeff> {};
55
56 #define GR_BLEND_COEFF_REFS_DST(COEFF) \
57 GrTBlendCoeffRefsDst<COEFF>::value
58
59
60 inline bool GrBlendCoeffRefsBlendColor(GrBlendCoeff coeff) {
61 switch (coeff) {
62 case kConstC_GrBlendCoeff:
63 case kIConstC_GrBlendCoeff:
64 case kConstA_GrBlendCoeff:
65 case kIConstA_GrBlendCoeff:
66 return true;
67 default:
68 return false;
69 }
70 }
71
72 template<GrBlendCoeff Coeff>
73 struct GrTBlendCoeffRefsBlendColor : SkTBool<kConstC_GrBlendCoeff == Coeff ||
74 kIConstC_GrBlendCoeff == Coeff ||
75 kConstA_GrBlendCoeff == Coeff ||
76 kIConstA_GrBlendCoeff == Coeff> {};
77
78 #define GR_BLEND_COEFF_REFS_BLEND_COLOR(COEFF) \
79 GrTBlendCoeffRefsBlendColor<COEFF>::value
80
81
82 inline bool GrBlendCoeffRefsSrc2(GrBlendCoeff coeff) {
83 switch (coeff) {
84 case kS2C_GrBlendCoeff:
85 case kIS2C_GrBlendCoeff:
86 case kS2A_GrBlendCoeff:
87 case kIS2A_GrBlendCoeff:
88 return true;
89 default:
90 return false;
91 }
92 }
93
egdaniel 2015/05/21 19:35:39 General cleanup thought...do we need both the inli
Chris Dalton 2015/05/21 23:14:49 Done.
94 template<GrBlendCoeff Coeff>
95 struct GrTBlendCoeffRefsSrc2 : SkTBool<kS2C_GrBlendCoeff == Coeff ||
96 kIS2C_GrBlendCoeff == Coeff ||
97 kS2A_GrBlendCoeff == Coeff ||
98 kIS2A_GrBlendCoeff == Coeff> {};
99
100 #define GR_BLEND_COEFF_REFS_SRC2(COEFF) \
101 GrTBlendCoeffRefsSrc2<COEFF>::value
102
103
104 inline bool GrBlendCoeffsUseSrcColor(GrBlendCoeff srcCoeff, GrBlendCoeff dstCoef f) {
105 return kZero_GrBlendCoeff != srcCoeff || GrBlendCoeffRefsSrc(dstCoeff);
106 }
107
108 template<GrBlendCoeff SrcCoeff, GrBlendCoeff DstCoeff>
109 struct GrTBlendCoeffsUseSrcColor : SkTBool<kZero_GrBlendCoeff != SrcCoeff ||
110 GR_BLEND_COEFF_REFS_SRC(DstCoeff)> {} ;
111
112 #define GR_BLEND_COEFFS_USE_SRC_COLOR(SRC_COEFF, DST_COEFF) \
113 GrTBlendCoeffsUseSrcColor<SRC_COEFF, DST_COEFF>::value
114
115
116 inline bool GrBlendCoeffsUseDstColor(GrBlendCoeff srcCoeff, GrBlendCoeff dstCoef f) {
117 return GrBlendCoeffRefsDst(srcCoeff) || kZero_GrBlendCoeff != dstCoeff;
118 }
119
120 template<GrBlendCoeff SrcCoeff, GrBlendCoeff DstCoeff>
121 struct GrTBlendCoeffsUseDstColor : SkTBool<GR_BLEND_COEFF_REFS_DST(SrcCoeff) ||
122 kZero_GrBlendCoeff != DstCoeff> {};
123
124 #define GR_BLEND_COEFFS_USE_DST_COLOR(SRC_COEFF, DST_COEFF) \
125 GrTBlendCoeffsUseDstColor<SRC_COEFF, DST_COEFF>::value
126
127
128 inline bool GrBlendEquationIsAdvanced(GrBlendEquation equation) {
129 return equation >= kFirstAdvancedGrBlendEquation;
130 }
131
132 template<GrBlendEquation Equation>
133 struct GrTBlendEquationIsAdvanced : SkTBool<Equation >= kFirstAdvancedGrBlendEqu ation> {};
134
135 #define GR_BLEND_EQUATION_IS_ADVANCED(EQUATION) \
136 GrTBlendEquationIsAdvanced<EQUATION>::value
137
138
139 inline bool GrBlendModifiesDst(GrBlendEquation equation,
140 GrBlendCoeff srcCoeff, GrBlendCoeff dstCoeff) {
141 if (kAdd_GrBlendEquation != equation && kReverseSubtract_GrBlendEquation != equation) {
142 return true;
143 }
144 return kZero_GrBlendCoeff != srcCoeff || kOne_GrBlendCoeff != dstCoeff;
145 }
146
147 template<GrBlendEquation BlendEquation, GrBlendCoeff SrcCoeff, GrBlendCoeff DstC oeff>
148 struct GrTBlendModifiesDst : SkTBool<(kAdd_GrBlendEquation != BlendEquation &&
149 kReverseSubtract_GrBlendEquation != BlendE quation) ||
150 kZero_GrBlendCoeff != SrcCoeff ||
151 kOne_GrBlendCoeff != DstCoeff> {};
152
153 #define GR_BLEND_MODIFIES_DST(EQUATION, SRC_COEFF, DST_COEFF) \
154 GrTBlendModifiesDst<EQUATION, SRC_COEFF, DST_COEFF>::value
155
156
157 inline bool GrBlendCanTweakAlphaForCoverage(GrBlendEquation equation,
158 GrBlendCoeff srcCoeff, GrBlendCoeff dstCoeff) {
159 if (GrBlendEquationIsAdvanced(equation)) {
160 return true; // See GrCustomXfermode.cpp for an explanation on why this works.
161 }
162 if (kSubtract_GrBlendEquation == equation) {
163 return false;
164 }
165
166 SkASSERT(kAdd_GrBlendEquation == equation || kReverseSubtract_GrBlendEquatio n == equation);
167
168 /*
169 The blend equation at this point with f=coverage is:
170
171 D' = f * (S * srcCoeff + D * dstCoeff) + (1-f) * D
172 = f * S * srcCoeff + D * (f * dstCoeff + (1 - f))
173
174 (Let srcCoeff be negative for reverse subtract.) We can tweak alpha for cove rage when the
175 following relationship holds:
176
177 (f*S) * srcCoeff' + D * dstCoeff' == f * S * srcCoeff + D * (f * dstCoeff + (1 - f))
178
179 (Where srcCoeff' and dstCoeff' have any reference to S pre-multiplied by f.)
180
181 It's easy to see this works for the src term as long as srcCoeff' == srcCoef f (meaning srcCoeff
182 does not reference S). For the dst term, the test can be rewritten as follow s:
183
184 D * dstCoeff' == D * (1 - f * (1 - dstCoeff))
185
186 By inspection we can see this will work as long as dstCoeff has a 1, and any other term in
187 dstCoeff references S.
188 */
189
190 if (GrBlendCoeffRefsSrc(srcCoeff)) {
191 return false;
192 }
193
194 switch (dstCoeff) {
195 case kOne_GrBlendCoeff:
196 case kISC_GrBlendCoeff:
197 case kISA_GrBlendCoeff:
198 return true;
199 default:
200 return false;
201 }
202 }
203
204 template<GrBlendEquation Equation, GrBlendCoeff SrcCoeff, GrBlendCoeff DstCoeff>
205 struct GrTBlendCanTweakAlphaForCoverage : SkTBool<GR_BLEND_EQUATION_IS_ADVANCED( Equation) ||
206 ((kAdd_GrBlendEquation == Equa tion ||
207 kReverseSubtract_GrBlendEqua tion == Equation) &&
208 !GR_BLEND_COEFF_REFS_SRC(SrcC oeff) &&
209 (kOne_GrBlendCoeff == DstCoef f ||
210 kISC_GrBlendCoeff == DstCoef f ||
211 kISA_GrBlendCoeff == DstCoef f))> {};
212
213 #define GR_BLEND_CAN_TWEAK_ALPHA_FOR_COVERAGE(EQUATION, SRC_COEFF, DST_COEFF) \
214 GrTBlendCanTweakAlphaForCoverage<EQUATION, SRC_COEFF, DST_COEFF>::value
45 215
46 #endif 216 #endif
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698