Sat, 03 Jan 2015 20:18:00 +0100
Conditionally enable double key logic according to:
private browsing mode or privacy.thirdparty.isolate preference and
implement in GetCookieStringCommon and FindCookie where it counts...
With some reservations of how to convince FindCookie users to test
condition and pass a nullptr when disabling double key logic.
michael@0 | 1 | # HG changeset patch |
michael@0 | 2 | # User Matt Woodrow <mwoodrow@mozilla.com> |
michael@0 | 3 | # Date 1339988782 -43200 |
michael@0 | 4 | # Node ID 1e9dae659ee6c992f719fd4136efbcc5410ded37 |
michael@0 | 5 | # Parent 946750f6d95febd199fb7b748e9d2c48fd01c8a6 |
michael@0 | 6 | [mq]: skia-windows-gradients |
michael@0 | 7 | |
michael@0 | 8 | diff --git a/gfx/skia/src/effects/SkGradientShader.cpp b/gfx/skia/src/effects/SkGradientShader.cpp |
michael@0 | 9 | --- a/gfx/skia/src/effects/SkGradientShader.cpp |
michael@0 | 10 | +++ b/gfx/skia/src/effects/SkGradientShader.cpp |
michael@0 | 11 | @@ -847,16 +847,19 @@ bool Linear_Gradient::setContext(const S |
michael@0 | 12 | fFlags |= SkShader::kConstInY32_Flag; |
michael@0 | 13 | if ((fFlags & SkShader::kHasSpan16_Flag) && !paint.isDither()) { |
michael@0 | 14 | // only claim this if we do have a 16bit mode (i.e. none of our |
michael@0 | 15 | // colors have alpha), and if we are not dithering (which obviously |
michael@0 | 16 | // is not const in Y). |
michael@0 | 17 | fFlags |= SkShader::kConstInY16_Flag; |
michael@0 | 18 | } |
michael@0 | 19 | } |
michael@0 | 20 | + if (fStart == fEnd) { |
michael@0 | 21 | + fFlags &= ~kOpaqueAlpha_Flag; |
michael@0 | 22 | + } |
michael@0 | 23 | return true; |
michael@0 | 24 | } |
michael@0 | 25 | |
michael@0 | 26 | #define NO_CHECK_ITER \ |
michael@0 | 27 | do { \ |
michael@0 | 28 | unsigned fi = fx >> Gradient_Shader::kCache32Shift; \ |
michael@0 | 29 | SkASSERT(fi <= 0xFF); \ |
michael@0 | 30 | fx += dx; \ |
michael@0 | 31 | @@ -976,16 +979,21 @@ void Linear_Gradient::shadeSpan(int x, i |
michael@0 | 32 | TileProc proc = fTileProc; |
michael@0 | 33 | const SkPMColor* SK_RESTRICT cache = this->getCache32(); |
michael@0 | 34 | #ifdef USE_DITHER_32BIT_GRADIENT |
michael@0 | 35 | int toggle = ((x ^ y) & 1) * kDitherStride32; |
michael@0 | 36 | #else |
michael@0 | 37 | int toggle = 0; |
michael@0 | 38 | #endif |
michael@0 | 39 | |
michael@0 | 40 | + if (fStart == fEnd) { |
michael@0 | 41 | + sk_bzero(dstC, count * sizeof(*dstC)); |
michael@0 | 42 | + return; |
michael@0 | 43 | + } |
michael@0 | 44 | + |
michael@0 | 45 | if (fDstToIndexClass != kPerspective_MatrixClass) { |
michael@0 | 46 | dstProc(fDstToIndex, SkIntToScalar(x) + SK_ScalarHalf, |
michael@0 | 47 | SkIntToScalar(y) + SK_ScalarHalf, &srcPt); |
michael@0 | 48 | SkFixed dx, fx = SkScalarToFixed(srcPt.fX); |
michael@0 | 49 | |
michael@0 | 50 | if (fDstToIndexClass == kFixedStepInX_MatrixClass) { |
michael@0 | 51 | SkFixed dxStorage[1]; |
michael@0 | 52 | (void)fDstToIndex.fixedStepInX(SkIntToScalar(y), dxStorage, NULL); |
michael@0 | 53 | @@ -1169,16 +1177,21 @@ void Linear_Gradient::shadeSpan16(int x, |
michael@0 | 54 | SkASSERT(count > 0); |
michael@0 | 55 | |
michael@0 | 56 | SkPoint srcPt; |
michael@0 | 57 | SkMatrix::MapXYProc dstProc = fDstToIndexProc; |
michael@0 | 58 | TileProc proc = fTileProc; |
michael@0 | 59 | const uint16_t* SK_RESTRICT cache = this->getCache16(); |
michael@0 | 60 | int toggle = ((x ^ y) & 1) * kDitherStride16; |
michael@0 | 61 | |
michael@0 | 62 | + if (fStart == fEnd) { |
michael@0 | 63 | + sk_bzero(dstC, count * sizeof(*dstC)); |
michael@0 | 64 | + return; |
michael@0 | 65 | + } |
michael@0 | 66 | + |
michael@0 | 67 | if (fDstToIndexClass != kPerspective_MatrixClass) { |
michael@0 | 68 | dstProc(fDstToIndex, SkIntToScalar(x) + SK_ScalarHalf, |
michael@0 | 69 | SkIntToScalar(y) + SK_ScalarHalf, &srcPt); |
michael@0 | 70 | SkFixed dx, fx = SkScalarToFixed(srcPt.fX); |
michael@0 | 71 | |
michael@0 | 72 | if (fDstToIndexClass == kFixedStepInX_MatrixClass) { |
michael@0 | 73 | SkFixed dxStorage[1]; |
michael@0 | 74 | (void)fDstToIndex.fixedStepInX(SkIntToScalar(y), dxStorage, NULL); |
michael@0 | 75 | @@ -1739,21 +1752,25 @@ void Radial_Gradient::shadeSpan(int x, i |
michael@0 | 76 | possible circles on which the point may fall. Solving for t yields |
michael@0 | 77 | the gradient value to use. |
michael@0 | 78 | |
michael@0 | 79 | If a<0, the start circle is entirely contained in the |
michael@0 | 80 | end circle, and one of the roots will be <0 or >1 (off the line |
michael@0 | 81 | segment). If a>0, the start circle falls at least partially |
michael@0 | 82 | outside the end circle (or vice versa), and the gradient |
michael@0 | 83 | defines a "tube" where a point may be on one circle (on the |
michael@0 | 84 | - inside of the tube) or the other (outside of the tube). We choose |
michael@0 | 85 | - one arbitrarily. |
michael@0 | 86 | + inside of the tube) or the other (outside of the tube). We choose |
michael@0 | 87 | + the one with the highest t value, as long as the radius that it |
michael@0 | 88 | + corresponds to is >=0. In the case where neither root has a positive |
michael@0 | 89 | + radius, we don't draw anything. |
michael@0 | 90 | |
michael@0 | 91 | + XXXmattwoodrow: I've removed this for now since it breaks |
michael@0 | 92 | + down when Dr == 0. Is there something else we can do instead? |
michael@0 | 93 | In order to keep the math to within the limits of fixed point, |
michael@0 | 94 | - we divide the entire quadratic by Dr^2, and replace |
michael@0 | 95 | + we divide the entire quadratic by Dr, and replace |
michael@0 | 96 | (x - Sx)/Dr with x' and (y - Sy)/Dr with y', giving |
michael@0 | 97 | |
michael@0 | 98 | [Dx^2 / Dr^2 + Dy^2 / Dr^2 - 1)] * t^2 |
michael@0 | 99 | + 2 * [x' * Dx / Dr + y' * Dy / Dr - Sr / Dr] * t |
michael@0 | 100 | + [x'^2 + y'^2 - Sr^2/Dr^2] = 0 |
michael@0 | 101 | |
michael@0 | 102 | (x' and y' are computed by appending the subtract and scale to the |
michael@0 | 103 | fDstToIndex matrix in the constructor). |
michael@0 | 104 | @@ -1763,99 +1780,122 @@ void Radial_Gradient::shadeSpan(int x, i |
michael@0 | 105 | x' and y', if x and y are linear in the span, 'B' can be computed |
michael@0 | 106 | incrementally with a simple delta (db below). If it is not (e.g., |
michael@0 | 107 | a perspective projection), it must be computed in the loop. |
michael@0 | 108 | |
michael@0 | 109 | */ |
michael@0 | 110 | |
michael@0 | 111 | namespace { |
michael@0 | 112 | |
michael@0 | 113 | -inline SkFixed two_point_radial(SkScalar b, SkScalar fx, SkScalar fy, |
michael@0 | 114 | - SkScalar sr2d2, SkScalar foura, |
michael@0 | 115 | - SkScalar oneOverTwoA, bool posRoot) { |
michael@0 | 116 | +inline bool two_point_radial(SkScalar b, SkScalar fx, SkScalar fy, |
michael@0 | 117 | + SkScalar sr2d2, SkScalar foura, |
michael@0 | 118 | + SkScalar oneOverTwoA, SkScalar diffRadius, |
michael@0 | 119 | + SkScalar startRadius, SkFixed& t) { |
michael@0 | 120 | SkScalar c = SkScalarSquare(fx) + SkScalarSquare(fy) - sr2d2; |
michael@0 | 121 | if (0 == foura) { |
michael@0 | 122 | - return SkScalarToFixed(SkScalarDiv(-c, b)); |
michael@0 | 123 | + SkScalar result = SkScalarDiv(-c, b); |
michael@0 | 124 | + if (result * diffRadius + startRadius >= 0) { |
michael@0 | 125 | + t = SkScalarToFixed(result); |
michael@0 | 126 | + return true; |
michael@0 | 127 | + } |
michael@0 | 128 | + return false; |
michael@0 | 129 | } |
michael@0 | 130 | |
michael@0 | 131 | SkScalar discrim = SkScalarSquare(b) - SkScalarMul(foura, c); |
michael@0 | 132 | if (discrim < 0) { |
michael@0 | 133 | - discrim = -discrim; |
michael@0 | 134 | + return false; |
michael@0 | 135 | } |
michael@0 | 136 | SkScalar rootDiscrim = SkScalarSqrt(discrim); |
michael@0 | 137 | - SkScalar result; |
michael@0 | 138 | - if (posRoot) { |
michael@0 | 139 | - result = SkScalarMul(-b + rootDiscrim, oneOverTwoA); |
michael@0 | 140 | - } else { |
michael@0 | 141 | - result = SkScalarMul(-b - rootDiscrim, oneOverTwoA); |
michael@0 | 142 | + |
michael@0 | 143 | + // Make sure the results corresponds to a positive radius. |
michael@0 | 144 | + SkScalar result = SkScalarMul(-b + rootDiscrim, oneOverTwoA); |
michael@0 | 145 | + if (result * diffRadius + startRadius >= 0) { |
michael@0 | 146 | + t = SkScalarToFixed(result); |
michael@0 | 147 | + return true; |
michael@0 | 148 | } |
michael@0 | 149 | - return SkScalarToFixed(result); |
michael@0 | 150 | + result = SkScalarMul(-b - rootDiscrim, oneOverTwoA); |
michael@0 | 151 | + if (result * diffRadius + startRadius >= 0) { |
michael@0 | 152 | + t = SkScalarToFixed(result); |
michael@0 | 153 | + return true; |
michael@0 | 154 | + } |
michael@0 | 155 | + |
michael@0 | 156 | + return false; |
michael@0 | 157 | } |
michael@0 | 158 | |
michael@0 | 159 | typedef void (* TwoPointRadialShadeProc)(SkScalar fx, SkScalar dx, |
michael@0 | 160 | SkScalar fy, SkScalar dy, |
michael@0 | 161 | SkScalar b, SkScalar db, |
michael@0 | 162 | - SkScalar fSr2D2, SkScalar foura, SkScalar fOneOverTwoA, bool posRoot, |
michael@0 | 163 | + SkScalar fSr2D2, SkScalar foura, SkScalar fOneOverTwoA, |
michael@0 | 164 | + SkScalar fDiffRadius, SkScalar fRadius1, |
michael@0 | 165 | SkPMColor* SK_RESTRICT dstC, const SkPMColor* SK_RESTRICT cache, |
michael@0 | 166 | int count); |
michael@0 | 167 | |
michael@0 | 168 | void shadeSpan_twopoint_clamp(SkScalar fx, SkScalar dx, |
michael@0 | 169 | SkScalar fy, SkScalar dy, |
michael@0 | 170 | SkScalar b, SkScalar db, |
michael@0 | 171 | - SkScalar fSr2D2, SkScalar foura, SkScalar fOneOverTwoA, bool posRoot, |
michael@0 | 172 | + SkScalar fSr2D2, SkScalar foura, SkScalar fOneOverTwoA, |
michael@0 | 173 | + SkScalar fDiffRadius, SkScalar fRadius1, |
michael@0 | 174 | SkPMColor* SK_RESTRICT dstC, const SkPMColor* SK_RESTRICT cache, |
michael@0 | 175 | int count) { |
michael@0 | 176 | for (; count > 0; --count) { |
michael@0 | 177 | - SkFixed t = two_point_radial(b, fx, fy, fSr2D2, foura, |
michael@0 | 178 | - fOneOverTwoA, posRoot); |
michael@0 | 179 | - |
michael@0 | 180 | - if (t < 0) { |
michael@0 | 181 | + SkFixed t; |
michael@0 | 182 | + if (!two_point_radial(b, fx, fy, fSr2D2, foura, fOneOverTwoA, fDiffRadius, fRadius1, t)) { |
michael@0 | 183 | + *(dstC++) = 0; |
michael@0 | 184 | + } else if (t < 0) { |
michael@0 | 185 | *dstC++ = cache[-1]; |
michael@0 | 186 | } else if (t > 0xFFFF) { |
michael@0 | 187 | *dstC++ = cache[Gradient_Shader::kCache32Count * 2]; |
michael@0 | 188 | } else { |
michael@0 | 189 | SkASSERT(t <= 0xFFFF); |
michael@0 | 190 | *dstC++ = cache[t >> Gradient_Shader::kCache32Shift]; |
michael@0 | 191 | } |
michael@0 | 192 | |
michael@0 | 193 | fx += dx; |
michael@0 | 194 | fy += dy; |
michael@0 | 195 | b += db; |
michael@0 | 196 | } |
michael@0 | 197 | } |
michael@0 | 198 | void shadeSpan_twopoint_mirror(SkScalar fx, SkScalar dx, |
michael@0 | 199 | SkScalar fy, SkScalar dy, |
michael@0 | 200 | SkScalar b, SkScalar db, |
michael@0 | 201 | - SkScalar fSr2D2, SkScalar foura, SkScalar fOneOverTwoA, bool posRoot, |
michael@0 | 202 | + SkScalar fSr2D2, SkScalar foura, SkScalar fOneOverTwoA, |
michael@0 | 203 | + SkScalar fDiffRadius, SkScalar fRadius1, |
michael@0 | 204 | SkPMColor* SK_RESTRICT dstC, const SkPMColor* SK_RESTRICT cache, |
michael@0 | 205 | int count) { |
michael@0 | 206 | for (; count > 0; --count) { |
michael@0 | 207 | - SkFixed t = two_point_radial(b, fx, fy, fSr2D2, foura, |
michael@0 | 208 | - fOneOverTwoA, posRoot); |
michael@0 | 209 | - SkFixed index = mirror_tileproc(t); |
michael@0 | 210 | - SkASSERT(index <= 0xFFFF); |
michael@0 | 211 | - *dstC++ = cache[index >> Gradient_Shader::kCache32Shift]; |
michael@0 | 212 | + SkFixed t; |
michael@0 | 213 | + if (!two_point_radial(b, fx, fy, fSr2D2, foura, fOneOverTwoA, fDiffRadius, fRadius1, t)) { |
michael@0 | 214 | + *(dstC++) = 0; |
michael@0 | 215 | + } else { |
michael@0 | 216 | + SkFixed index = mirror_tileproc(t); |
michael@0 | 217 | + SkASSERT(index <= 0xFFFF); |
michael@0 | 218 | + *dstC++ = cache[index >> (16 - Gradient_Shader::kCache32Shift)]; |
michael@0 | 219 | + } |
michael@0 | 220 | fx += dx; |
michael@0 | 221 | fy += dy; |
michael@0 | 222 | b += db; |
michael@0 | 223 | } |
michael@0 | 224 | } |
michael@0 | 225 | |
michael@0 | 226 | void shadeSpan_twopoint_repeat(SkScalar fx, SkScalar dx, |
michael@0 | 227 | SkScalar fy, SkScalar dy, |
michael@0 | 228 | SkScalar b, SkScalar db, |
michael@0 | 229 | - SkScalar fSr2D2, SkScalar foura, SkScalar fOneOverTwoA, bool posRoot, |
michael@0 | 230 | + SkScalar fSr2D2, SkScalar foura, SkScalar fOneOverTwoA, |
michael@0 | 231 | + SkScalar fDiffRadius, SkScalar fRadius1, |
michael@0 | 232 | SkPMColor* SK_RESTRICT dstC, const SkPMColor* SK_RESTRICT cache, |
michael@0 | 233 | int count) { |
michael@0 | 234 | for (; count > 0; --count) { |
michael@0 | 235 | - SkFixed t = two_point_radial(b, fx, fy, fSr2D2, foura, |
michael@0 | 236 | - fOneOverTwoA, posRoot); |
michael@0 | 237 | - SkFixed index = repeat_tileproc(t); |
michael@0 | 238 | - SkASSERT(index <= 0xFFFF); |
michael@0 | 239 | - *dstC++ = cache[index >> Gradient_Shader::kCache32Shift]; |
michael@0 | 240 | + SkFixed t; |
michael@0 | 241 | + if (!two_point_radial(b, fx, fy, fSr2D2, foura, fOneOverTwoA, fDiffRadius, fRadius1, t)) { |
michael@0 | 242 | + *(dstC++) = 0; |
michael@0 | 243 | + } else { |
michael@0 | 244 | + SkFixed index = repeat_tileproc(t); |
michael@0 | 245 | + SkASSERT(index <= 0xFFFF); |
michael@0 | 246 | + *dstC++ = cache[index >> (16 - Gradient_Shader::kCache32Shift)]; |
michael@0 | 247 | + } |
michael@0 | 248 | fx += dx; |
michael@0 | 249 | fy += dy; |
michael@0 | 250 | b += db; |
michael@0 | 251 | } |
michael@0 | 252 | } |
michael@0 | 253 | |
michael@0 | 254 | |
michael@0 | 255 | |
michael@0 | 256 | @@ -1935,17 +1975,16 @@ public: |
michael@0 | 257 | sk_bzero(dstC, count * sizeof(*dstC)); |
michael@0 | 258 | return; |
michael@0 | 259 | } |
michael@0 | 260 | SkMatrix::MapXYProc dstProc = fDstToIndexProc; |
michael@0 | 261 | TileProc proc = fTileProc; |
michael@0 | 262 | const SkPMColor* SK_RESTRICT cache = this->getCache32(); |
michael@0 | 263 | |
michael@0 | 264 | SkScalar foura = fA * 4; |
michael@0 | 265 | - bool posRoot = fDiffRadius < 0; |
michael@0 | 266 | if (fDstToIndexClass != kPerspective_MatrixClass) { |
michael@0 | 267 | SkPoint srcPt; |
michael@0 | 268 | dstProc(fDstToIndex, SkIntToScalar(x) + SK_ScalarHalf, |
michael@0 | 269 | SkIntToScalar(y) + SK_ScalarHalf, &srcPt); |
michael@0 | 270 | SkScalar dx, fx = srcPt.fX; |
michael@0 | 271 | SkScalar dy, fy = srcPt.fY; |
michael@0 | 272 | |
michael@0 | 273 | if (fDstToIndexClass == kFixedStepInX_MatrixClass) { |
michael@0 | 274 | @@ -1954,60 +1993,69 @@ public: |
michael@0 | 275 | dx = SkFixedToScalar(fixedX); |
michael@0 | 276 | dy = SkFixedToScalar(fixedY); |
michael@0 | 277 | } else { |
michael@0 | 278 | SkASSERT(fDstToIndexClass == kLinear_MatrixClass); |
michael@0 | 279 | dx = fDstToIndex.getScaleX(); |
michael@0 | 280 | dy = fDstToIndex.getSkewY(); |
michael@0 | 281 | } |
michael@0 | 282 | SkScalar b = (SkScalarMul(fDiff.fX, fx) + |
michael@0 | 283 | - SkScalarMul(fDiff.fY, fy) - fStartRadius) * 2; |
michael@0 | 284 | + SkScalarMul(fDiff.fY, fy) - fStartRadius * fDiffRadius) * 2; |
michael@0 | 285 | SkScalar db = (SkScalarMul(fDiff.fX, dx) + |
michael@0 | 286 | SkScalarMul(fDiff.fY, dy)) * 2; |
michael@0 | 287 | |
michael@0 | 288 | TwoPointRadialShadeProc shadeProc = shadeSpan_twopoint_repeat; |
michael@0 | 289 | if (proc == clamp_tileproc) { |
michael@0 | 290 | shadeProc = shadeSpan_twopoint_clamp; |
michael@0 | 291 | } else if (proc == mirror_tileproc) { |
michael@0 | 292 | shadeProc = shadeSpan_twopoint_mirror; |
michael@0 | 293 | } else { |
michael@0 | 294 | SkASSERT(proc == repeat_tileproc); |
michael@0 | 295 | } |
michael@0 | 296 | (*shadeProc)(fx, dx, fy, dy, b, db, |
michael@0 | 297 | - fSr2D2, foura, fOneOverTwoA, posRoot, |
michael@0 | 298 | + fSr2D2, foura, fOneOverTwoA, fDiffRadius, fRadius1, |
michael@0 | 299 | dstC, cache, count); |
michael@0 | 300 | } else { // perspective case |
michael@0 | 301 | SkScalar dstX = SkIntToScalar(x); |
michael@0 | 302 | SkScalar dstY = SkIntToScalar(y); |
michael@0 | 303 | for (; count > 0; --count) { |
michael@0 | 304 | SkPoint srcPt; |
michael@0 | 305 | dstProc(fDstToIndex, dstX, dstY, &srcPt); |
michael@0 | 306 | SkScalar fx = srcPt.fX; |
michael@0 | 307 | SkScalar fy = srcPt.fY; |
michael@0 | 308 | SkScalar b = (SkScalarMul(fDiff.fX, fx) + |
michael@0 | 309 | SkScalarMul(fDiff.fY, fy) - fStartRadius) * 2; |
michael@0 | 310 | - SkFixed t = two_point_radial(b, fx, fy, fSr2D2, foura, |
michael@0 | 311 | - fOneOverTwoA, posRoot); |
michael@0 | 312 | - SkFixed index = proc(t); |
michael@0 | 313 | - SkASSERT(index <= 0xFFFF); |
michael@0 | 314 | - *dstC++ = cache[index >> Gradient_Shader::kCache32Shift]; |
michael@0 | 315 | + SkFixed t; |
michael@0 | 316 | + if (!two_point_radial(b, fx, fy, fSr2D2, foura, fOneOverTwoA, fDiffRadius, fRadius1, t)) { |
michael@0 | 317 | + *(dstC++) = 0; |
michael@0 | 318 | + } else { |
michael@0 | 319 | + SkFixed index = proc(t); |
michael@0 | 320 | + SkASSERT(index <= 0xFFFF); |
michael@0 | 321 | + *dstC++ = cache[index >> (16 - kCache32Bits)]; |
michael@0 | 322 | + } |
michael@0 | 323 | dstX += SK_Scalar1; |
michael@0 | 324 | } |
michael@0 | 325 | } |
michael@0 | 326 | } |
michael@0 | 327 | |
michael@0 | 328 | virtual bool setContext(const SkBitmap& device, |
michael@0 | 329 | const SkPaint& paint, |
michael@0 | 330 | const SkMatrix& matrix) SK_OVERRIDE { |
michael@0 | 331 | if (!this->INHERITED::setContext(device, paint, matrix)) { |
michael@0 | 332 | return false; |
michael@0 | 333 | } |
michael@0 | 334 | |
michael@0 | 335 | // we don't have a span16 proc |
michael@0 | 336 | fFlags &= ~kHasSpan16_Flag; |
michael@0 | 337 | + |
michael@0 | 338 | + // If we might end up wanting to draw nothing as part of the gradient |
michael@0 | 339 | + // then we should mark ourselves as not being opaque. |
michael@0 | 340 | + if (fA >= 0 || (fDiffRadius == 0 && fCenter1 == fCenter2)) { |
michael@0 | 341 | + fFlags &= ~kOpaqueAlpha_Flag; |
michael@0 | 342 | + } |
michael@0 | 343 | return true; |
michael@0 | 344 | } |
michael@0 | 345 | |
michael@0 | 346 | SK_DECLARE_PUBLIC_FLATTENABLE_DESERIALIZATION_PROCS(Two_Point_Radial_Gradient) |
michael@0 | 347 | |
michael@0 | 348 | protected: |
michael@0 | 349 | Two_Point_Radial_Gradient(SkFlattenableReadBuffer& buffer) |
michael@0 | 350 | : INHERITED(buffer), |
michael@0 | 351 | @@ -2033,26 +2081,22 @@ private: |
michael@0 | 352 | const SkScalar fRadius1; |
michael@0 | 353 | const SkScalar fRadius2; |
michael@0 | 354 | SkPoint fDiff; |
michael@0 | 355 | SkScalar fStartRadius, fDiffRadius, fSr2D2, fA, fOneOverTwoA; |
michael@0 | 356 | |
michael@0 | 357 | void init() { |
michael@0 | 358 | fDiff = fCenter1 - fCenter2; |
michael@0 | 359 | fDiffRadius = fRadius2 - fRadius1; |
michael@0 | 360 | - SkScalar inv = SkScalarInvert(fDiffRadius); |
michael@0 | 361 | - fDiff.fX = SkScalarMul(fDiff.fX, inv); |
michael@0 | 362 | - fDiff.fY = SkScalarMul(fDiff.fY, inv); |
michael@0 | 363 | - fStartRadius = SkScalarMul(fRadius1, inv); |
michael@0 | 364 | + fStartRadius = fRadius1; |
michael@0 | 365 | fSr2D2 = SkScalarSquare(fStartRadius); |
michael@0 | 366 | - fA = SkScalarSquare(fDiff.fX) + SkScalarSquare(fDiff.fY) - SK_Scalar1; |
michael@0 | 367 | + fA = SkScalarSquare(fDiff.fX) + SkScalarSquare(fDiff.fY) - SkScalarSquare(fDiffRadius); |
michael@0 | 368 | fOneOverTwoA = fA ? SkScalarInvert(fA * 2) : 0; |
michael@0 | 369 | |
michael@0 | 370 | fPtsToUnit.setTranslate(-fCenter1.fX, -fCenter1.fY); |
michael@0 | 371 | - fPtsToUnit.postScale(inv, inv); |
michael@0 | 372 | } |
michael@0 | 373 | }; |
michael@0 | 374 | |
michael@0 | 375 | /////////////////////////////////////////////////////////////////////////////// |
michael@0 | 376 | |
michael@0 | 377 | class Sweep_Gradient : public Gradient_Shader { |
michael@0 | 378 | public: |
michael@0 | 379 | Sweep_Gradient(SkScalar cx, SkScalar cy, const SkColor colors[], |
michael@0 | 380 | @@ -2488,16 +2532,20 @@ SkShader* SkGradientShader::CreateTwoPoi |
michael@0 | 381 | int colorCount, |
michael@0 | 382 | SkShader::TileMode mode, |
michael@0 | 383 | SkUnitMapper* mapper) { |
michael@0 | 384 | if (startRadius < 0 || endRadius < 0 || NULL == colors || colorCount < 1) { |
michael@0 | 385 | return NULL; |
michael@0 | 386 | } |
michael@0 | 387 | EXPAND_1_COLOR(colorCount); |
michael@0 | 388 | |
michael@0 | 389 | + if (start == end && startRadius == 0) { |
michael@0 | 390 | + return CreateRadial(start, endRadius, colors, pos, colorCount, mode, mapper); |
michael@0 | 391 | + } |
michael@0 | 392 | + |
michael@0 | 393 | return SkNEW_ARGS(Two_Point_Radial_Gradient, |
michael@0 | 394 | (start, startRadius, end, endRadius, colors, pos, |
michael@0 | 395 | colorCount, mode, mapper)); |
michael@0 | 396 | } |
michael@0 | 397 | |
michael@0 | 398 | SkShader* SkGradientShader::CreateSweep(SkScalar cx, SkScalar cy, |
michael@0 | 399 | const SkColor colors[], |
michael@0 | 400 | const SkScalar pos[], |