Chromium Code Reviews| OLD | NEW | 
|---|---|
| 1 /* | 1 /* | 
| 2 * Copyright (C) 2006, 2007, 2008, 2010 Apple Inc. All rights reserved. | 2 * Copyright (C) 2006, 2007, 2008, 2010 Apple Inc. All rights reserved. | 
| 3 * Copyright (C) 2007 Alp Toker <alp@atoker.com> | 3 * Copyright (C) 2007 Alp Toker <alp@atoker.com> | 
| 4 * Copyright (C) 2013 Google Inc. All rights reserved. | 4 * Copyright (C) 2013 Google Inc. All rights reserved. | 
| 5 * | 5 * | 
| 6 * Redistribution and use in source and binary forms, with or without | 6 * Redistribution and use in source and binary forms, with or without | 
| 7 * modification, are permitted provided that the following conditions | 7 * modification, are permitted provided that the following conditions | 
| 8 * are met: | 8 * are met: | 
| 9 * 1. Redistributions of source code must retain the above copyright | 9 * 1. Redistributions of source code must retain the above copyright | 
| 10 * notice, this list of conditions and the following disclaimer. | 10 * notice, this list of conditions and the following disclaimer. | 
| (...skipping 35 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 46 : m_radial(false) | 46 : m_radial(false) | 
| 47 , m_p0(p0) | 47 , m_p0(p0) | 
| 48 , m_p1(p1) | 48 , m_p1(p1) | 
| 49 , m_r0(0) | 49 , m_r0(0) | 
| 50 , m_r1(0) | 50 , m_r1(0) | 
| 51 , m_aspectRatio(1) | 51 , m_aspectRatio(1) | 
| 52 , m_stopsSorted(false) | 52 , m_stopsSorted(false) | 
| 53 , m_spreadMethod(SpreadMethodPad) | 53 , m_spreadMethod(SpreadMethodPad) | 
| 54 , m_cachedHash(0) | 54 , m_cachedHash(0) | 
| 55 , m_drawInPMColorSpace(false) | 55 , m_drawInPMColorSpace(false) | 
| 56 , m_gradient(0) | |
| 57 { | 56 { | 
| 58 } | 57 } | 
| 59 | 58 | 
| 60 Gradient::Gradient(const FloatPoint& p0, float r0, const FloatPoint& p1, float r 1, float aspectRatio) | 59 Gradient::Gradient(const FloatPoint& p0, float r0, const FloatPoint& p1, float r 1, float aspectRatio) | 
| 61 : m_radial(true) | 60 : m_radial(true) | 
| 62 , m_p0(p0) | 61 , m_p0(p0) | 
| 63 , m_p1(p1) | 62 , m_p1(p1) | 
| 64 , m_r0(r0) | 63 , m_r0(r0) | 
| 65 , m_r1(r1) | 64 , m_r1(r1) | 
| 66 , m_aspectRatio(aspectRatio) | 65 , m_aspectRatio(aspectRatio) | 
| 67 , m_stopsSorted(false) | 66 , m_stopsSorted(false) | 
| 68 , m_spreadMethod(SpreadMethodPad) | 67 , m_spreadMethod(SpreadMethodPad) | 
| 69 , m_cachedHash(0) | 68 , m_cachedHash(0) | 
| 70 , m_drawInPMColorSpace(false) | 69 , m_drawInPMColorSpace(false) | 
| 71 , m_gradient(0) | |
| 72 { | 70 { | 
| 73 } | 71 } | 
| 74 | 72 | 
| 75 Gradient::~Gradient() | 73 Gradient::~Gradient() | 
| 76 { | 74 { | 
| 77 destroyShader(); | |
| 78 } | |
| 79 | |
| 80 void Gradient::destroyShader() | |
| 81 { | |
| 82 SkSafeUnref(m_gradient); | |
| 83 m_gradient = 0; | |
| 84 } | 75 } | 
| 85 | 76 | 
| 86 void Gradient::adjustParametersForTiledDrawing(IntSize& size, FloatRect& srcRect ) | 77 void Gradient::adjustParametersForTiledDrawing(IntSize& size, FloatRect& srcRect ) | 
| 87 { | 78 { | 
| 88 if (m_radial) | 79 if (m_radial) | 
| 89 return; | 80 return; | 
| 90 | 81 | 
| 91 if (srcRect.isEmpty()) | 82 if (srcRect.isEmpty()) | 
| 92 return; | 83 return; | 
| 93 | 84 | 
| (...skipping 14 matching lines...) Expand all Loading... | |
| 108 void Gradient::addColorStop(float value, const Color& color) | 99 void Gradient::addColorStop(float value, const Color& color) | 
| 109 { | 100 { | 
| 110 float r; | 101 float r; | 
| 111 float g; | 102 float g; | 
| 112 float b; | 103 float b; | 
| 113 float a; | 104 float a; | 
| 114 color.getRGBA(r, g, b, a); | 105 color.getRGBA(r, g, b, a); | 
| 115 m_stops.append(ColorStop(value, r, g, b, a)); | 106 m_stops.append(ColorStop(value, r, g, b, a)); | 
| 116 | 107 | 
| 117 m_stopsSorted = false; | 108 m_stopsSorted = false; | 
| 118 destroyShader(); | 109 m_gradient.clear(); | 
| 119 | 110 | 
| 120 invalidateHash(); | 111 invalidateHash(); | 
| 121 } | 112 } | 
| 122 | 113 | 
| 123 void Gradient::addColorStop(const Gradient::ColorStop& stop) | 114 void Gradient::addColorStop(const Gradient::ColorStop& stop) | 
| 124 { | 115 { | 
| 125 m_stops.append(stop); | 116 m_stops.append(stop); | 
| 126 | 117 | 
| 127 m_stopsSorted = false; | 118 m_stopsSorted = false; | 
| 128 destroyShader(); | 119 m_gradient.clear(); | 
| 129 | 120 | 
| 130 invalidateHash(); | 121 invalidateHash(); | 
| 131 } | 122 } | 
| 132 | 123 | 
| 133 static inline bool compareStops(const Gradient::ColorStop& a, const Gradient::Co lorStop& b) | 124 static inline bool compareStops(const Gradient::ColorStop& a, const Gradient::Co lorStop& b) | 
| 134 { | 125 { | 
| 135 return a.stop < b.stop; | 126 return a.stop < b.stop; | 
| 136 } | 127 } | 
| 137 | 128 | 
| 138 void Gradient::sortStopsIfNecessary() | 129 void Gradient::sortStopsIfNecessary() | 
| (...skipping 17 matching lines...) Expand all Loading... | |
| 156 if (m_stops[i].alpha < 1) | 147 if (m_stops[i].alpha < 1) | 
| 157 return true; | 148 return true; | 
| 158 } | 149 } | 
| 159 | 150 | 
| 160 return false; | 151 return false; | 
| 161 } | 152 } | 
| 162 | 153 | 
| 163 void Gradient::setSpreadMethod(GradientSpreadMethod spreadMethod) | 154 void Gradient::setSpreadMethod(GradientSpreadMethod spreadMethod) | 
| 164 { | 155 { | 
| 165 // FIXME: Should it become necessary, allow calls to this method after m_gra dient has been set. | 156 // FIXME: Should it become necessary, allow calls to this method after m_gra dient has been set. | 
| 166 ASSERT(m_gradient == 0); | 157 ASSERT(!m_gradient); | 
| 167 | 158 | 
| 168 if (m_spreadMethod == spreadMethod) | 159 if (m_spreadMethod == spreadMethod) | 
| 169 return; | 160 return; | 
| 170 | 161 | 
| 171 m_spreadMethod = spreadMethod; | 162 m_spreadMethod = spreadMethod; | 
| 172 | 163 | 
| 173 invalidateHash(); | 164 invalidateHash(); | 
| 174 } | 165 } | 
| 175 | 166 | 
| 176 void Gradient::setDrawsInPMColorSpace(bool drawInPMColorSpace) | 167 void Gradient::setDrawsInPMColorSpace(bool drawInPMColorSpace) | 
| 177 { | 168 { | 
| 178 if (drawInPMColorSpace == m_drawInPMColorSpace) | 169 if (drawInPMColorSpace == m_drawInPMColorSpace) | 
| 179 return; | 170 return; | 
| 180 | 171 | 
| 181 m_drawInPMColorSpace = drawInPMColorSpace; | 172 m_drawInPMColorSpace = drawInPMColorSpace; | 
| 182 | 173 m_gradient.clear(); | 
| 183 if (m_gradient) | |
| 184 destroyShader(); | |
| 185 | 174 | 
| 186 invalidateHash(); | 175 invalidateHash(); | 
| 187 } | 176 } | 
| 188 | 177 | 
| 189 void Gradient::setGradientSpaceTransform(const AffineTransform& gradientSpaceTra nsformation) | 178 void Gradient::setGradientSpaceTransform(const AffineTransform& gradientSpaceTra nsformation) | 
| 190 { | 179 { | 
| 191 if (m_gradientSpaceTransformation == gradientSpaceTransformation) | 180 if (m_gradientSpaceTransformation == gradientSpaceTransformation) | 
| 192 return; | 181 return; | 
| 193 | 182 | 
| 194 m_gradientSpaceTransformation = gradientSpaceTransformation; | 183 m_gradientSpaceTransformation = gradientSpaceTransformation; | 
| (...skipping 105 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 300 // comparison. | 289 // comparison. | 
| 301 if (count < 1 || (--stop)->stop < 1.0) { | 290 if (count < 1 || (--stop)->stop < 1.0) { | 
| 302 pos[start + count] = WebCoreFloatToSkScalar(1.0); | 291 pos[start + count] = WebCoreFloatToSkScalar(1.0); | 
| 303 colors[start + count] = colors[start + count - 1]; | 292 colors[start + count] = colors[start + count - 1]; | 
| 304 } | 293 } | 
| 305 } | 294 } | 
| 306 | 295 | 
| 307 SkShader* Gradient::shader() | 296 SkShader* Gradient::shader() | 
| 308 { | 297 { | 
| 309 if (m_gradient) | 298 if (m_gradient) | 
| 310 return m_gradient; | 299 return m_gradient.get(); | 
| 311 | 300 | 
| 312 sortStopsIfNecessary(); | 301 sortStopsIfNecessary(); | 
| 313 ASSERT(m_stopsSorted); | 302 ASSERT(m_stopsSorted); | 
| 314 | 303 | 
| 315 size_t countUsed = totalStopsNeeded(m_stops.data(), m_stops.size()); | 304 size_t countUsed = totalStopsNeeded(m_stops.data(), m_stops.size()); | 
| 316 ASSERT(countUsed >= 2); | 305 ASSERT(countUsed >= 2); | 
| 317 ASSERT(countUsed >= m_stops.size()); | 306 ASSERT(countUsed >= m_stops.size()); | 
| 318 | 307 | 
| 319 // FIXME: Why is all this manual pointer math needed?! | 308 // FIXME: Why is all this manual pointer math needed?! | 
| 320 SkAutoMalloc storage(countUsed * (sizeof(SkColor) + sizeof(SkScalar))); | 309 SkAutoMalloc storage(countUsed * (sizeof(SkColor) + sizeof(SkScalar))); | 
| (...skipping 12 matching lines...) Expand all Loading... | |
| 333 break; | 322 break; | 
| 334 case SpreadMethodPad: | 323 case SpreadMethodPad: | 
| 335 tile = SkShader::kClamp_TileMode; | 324 tile = SkShader::kClamp_TileMode; | 
| 336 break; | 325 break; | 
| 337 } | 326 } | 
| 338 | 327 | 
| 339 uint32_t shouldDrawInPMColorSpace = m_drawInPMColorSpace ? SkGradientShader: :kInterpolateColorsInPremul_Flag : 0; | 328 uint32_t shouldDrawInPMColorSpace = m_drawInPMColorSpace ? SkGradientShader: :kInterpolateColorsInPremul_Flag : 0; | 
| 340 if (m_radial) { | 329 if (m_radial) { | 
| 341 // Since the two-point radial gradient is slower than the plain radial, | 330 // Since the two-point radial gradient is slower than the plain radial, | 
| 342 // only use it if we have to. | 331 // only use it if we have to. | 
| 343 if (m_p0 == m_p1 && m_r0 <= 0.0f) | 332 if (m_p0 == m_p1 && m_r0 <= 0.0f) { | 
| 344 m_gradient = SkGradientShader::CreateRadial(m_p1, m_r1, colors, pos, static_cast<int>(countUsed), tile, 0, shouldDrawInPMColorSpace); | 333 m_gradient = adoptRef(SkGradientShader::CreateRadial(m_p1, m_r1, col ors, pos, static_cast<int>(countUsed), tile, 0, shouldDrawInPMColorSpace)); | 
| 
 
Stephen Chennney
2013/07/08 13:55:11
In Blink, a "Create..." method would return a Pass
 
jbroman
2013/07/08 13:59:19
Correct; these methods are defined in Skia, which
 
 | |
| 345 else { | 334 } else { | 
| 346 // The radii we give to Skia must be positive. If we're given a | 335 // The radii we give to Skia must be positive. If we're given a | 
| 347 // negative radius, ask for zero instead. | 336 // negative radius, ask for zero instead. | 
| 348 SkScalar radius0 = m_r0 >= 0.0f ? WebCoreFloatToSkScalar(m_r0) : 0; | 337 SkScalar radius0 = m_r0 >= 0.0f ? WebCoreFloatToSkScalar(m_r0) : 0; | 
| 349 SkScalar radius1 = m_r1 >= 0.0f ? WebCoreFloatToSkScalar(m_r1) : 0; | 338 SkScalar radius1 = m_r1 >= 0.0f ? WebCoreFloatToSkScalar(m_r1) : 0; | 
| 350 m_gradient = SkGradientShader::CreateTwoPointConical(m_p0, radius0, m_p1, radius1, colors, pos, static_cast<int>(countUsed), tile, 0, shouldDrawInPM ColorSpace); | 339 m_gradient = adoptRef(SkGradientShader::CreateTwoPointConical(m_p0, radius0, m_p1, radius1, colors, pos, static_cast<int>(countUsed), tile, 0, shoul dDrawInPMColorSpace)); | 
| 351 } | 340 } | 
| 352 | 341 | 
| 353 if (aspectRatio() != 1) { | 342 if (aspectRatio() != 1) { | 
| 354 // CSS3 elliptical gradients: apply the elliptical scaling at the | 343 // CSS3 elliptical gradients: apply the elliptical scaling at the | 
| 355 // gradient center point. | 344 // gradient center point. | 
| 356 m_gradientSpaceTransformation.translate(m_p0.x(), m_p0.y()); | 345 m_gradientSpaceTransformation.translate(m_p0.x(), m_p0.y()); | 
| 357 m_gradientSpaceTransformation.scale(1, 1 / aspectRatio()); | 346 m_gradientSpaceTransformation.scale(1, 1 / aspectRatio()); | 
| 358 m_gradientSpaceTransformation.translate(-m_p0.x(), -m_p0.y()); | 347 m_gradientSpaceTransformation.translate(-m_p0.x(), -m_p0.y()); | 
| 359 ASSERT(m_p0 == m_p1); | 348 ASSERT(m_p0 == m_p1); | 
| 360 } | 349 } | 
| 361 } else { | 350 } else { | 
| 362 SkPoint pts[2] = { m_p0, m_p1 }; | 351 SkPoint pts[2] = { m_p0, m_p1 }; | 
| 363 m_gradient = SkGradientShader::CreateLinear(pts, colors, pos, static_cas t<int>(countUsed), tile, 0, shouldDrawInPMColorSpace); | 352 m_gradient = adoptRef(SkGradientShader::CreateLinear(pts, colors, pos, s tatic_cast<int>(countUsed), tile, 0, shouldDrawInPMColorSpace)); | 
| 364 } | 353 } | 
| 365 | 354 | 
| 366 if (!m_gradient) | 355 if (!m_gradient) { | 
| 367 // use last color, since our "geometry" was degenerate (e.g. radius==0) | 356 // use last color, since our "geometry" was degenerate (e.g. radius==0) | 
| 368 m_gradient = new SkColorShader(colors[countUsed - 1]); | 357 m_gradient = adoptRef(new SkColorShader(colors[countUsed - 1])); | 
| 369 else | 358 } else { | 
| 370 m_gradient->setLocalMatrix(m_gradientSpaceTransformation); | 359 m_gradient->setLocalMatrix(m_gradientSpaceTransformation); | 
| 371 return m_gradient; | 360 } | 
| 361 return m_gradient.get(); | |
| 372 } | 362 } | 
| 373 | 363 | 
| 374 } //namespace | 364 } //namespace | 
| OLD | NEW |