summaryrefslogtreecommitdiffstats
path: root/Source/WebCore/css/CSSGradientValue.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'Source/WebCore/css/CSSGradientValue.cpp')
-rw-r--r--Source/WebCore/css/CSSGradientValue.cpp48
1 files changed, 32 insertions, 16 deletions
diff --git a/Source/WebCore/css/CSSGradientValue.cpp b/Source/WebCore/css/CSSGradientValue.cpp
index b6b9ebe..ede76da 100644
--- a/Source/WebCore/css/CSSGradientValue.cpp
+++ b/Source/WebCore/css/CSSGradientValue.cpp
@@ -41,27 +41,28 @@ using namespace std;
namespace WebCore {
-Image* CSSGradientValue::image(RenderObject* renderer, const IntSize& size)
+PassRefPtr<Image> CSSGradientValue::image(RenderObject* renderer, const IntSize& size)
{
- if (!m_clients.contains(renderer))
- return 0;
-
- // Need to look up our size. Create a string of width*height to use as a hash key.
- // FIXME: hashing based only on size is not sufficient. Color stops may use context-sensitive units (like em)
- // that should force the color stop positions to be recomputed.
- Image* result = getImage(renderer, size);
- if (result)
- return result;
-
if (size.isEmpty())
return 0;
+ bool cacheable = isCacheable();
+ if (cacheable) {
+ if (!m_clients.contains(renderer))
+ return 0;
+
+ // Need to look up our size. Create a string of width*height to use as a hash key.
+ Image* result = getImage(renderer, size);
+ if (result)
+ return result;
+ }
+
// We need to create an image.
RefPtr<Image> newImage = GeneratedImage::create(createGradient(renderer, size), size);
- result = newImage.get();
- putImage(size, newImage.release());
+ if (cacheable)
+ putImage(size, newImage);
- return result;
+ return newImage.release();
}
// Should only ever be called for deprecated gradients.
@@ -280,7 +281,7 @@ void CSSGradientValue::addStops(Gradient* gradient, RenderObject* renderer, Rend
float lastOffset = stops[stops.size() - 1].offset;
if (lastOffset < maxExtent) {
float currOffset = lastOffset;
- size_t srcStopOrdinal = 0;
+ size_t srcStopOrdinal = originalFirstStopIndex;
while (true) {
GradientStop newStop = stops[srcStopOrdinal];
@@ -289,7 +290,7 @@ void CSSGradientValue::addStops(Gradient* gradient, RenderObject* renderer, Rend
if (currOffset > maxExtent)
break;
if (srcStopOrdinal < originalNumStops - 1)
- currOffset += stops[originalFirstStopIndex + srcStopOrdinal + 1].offset - stops[originalFirstStopIndex + srcStopOrdinal].offset;
+ currOffset += stops[srcStopOrdinal + 1].offset - stops[srcStopOrdinal].offset;
srcStopOrdinal = (srcStopOrdinal + 1) % originalNumStops;
}
}
@@ -406,6 +407,21 @@ FloatPoint CSSGradientValue::computeEndPoint(CSSPrimitiveValue* first, CSSPrimit
return result;
}
+bool CSSGradientValue::isCacheable() const
+{
+ for (size_t i = 0; i < m_stops.size(); ++i) {
+ const CSSGradientColorStop& stop = m_stops[i];
+ if (!stop.m_position)
+ continue;
+
+ unsigned short unitType = stop.m_position->primitiveType();
+ if (unitType == CSSPrimitiveValue::CSS_EMS || unitType == CSSPrimitiveValue::CSS_EXS || unitType == CSSPrimitiveValue::CSS_REMS)
+ return false;
+ }
+
+ return true;
+}
+
String CSSLinearGradientValue::cssText() const
{
String result;