Diff
Modified: trunk/Source/WebCore/ChangeLog (262107 => 262108)
--- trunk/Source/WebCore/ChangeLog 2020-05-24 15:34:44 UTC (rev 262107)
+++ trunk/Source/WebCore/ChangeLog 2020-05-24 15:53:19 UTC (rev 262108)
@@ -1,3 +1,173 @@
+2020-05-24 Sam Weinig <[email protected]>
+
+ Extended Color Cleanup: Stop allowing direct access to the underlying SimpleColor (it is almost always incorrect with respect to extended colors)
+ https://bugs.webkit.org/show_bug.cgi?id=212184
+
+ Reviewed by Dean Jackson.
+
+ - Makes Color::rgb() private, removing a class of extended color bugs from users
+ of the Color class. To get the equivilent functionality, users of the class must
+ now use toSRGBASimpleColorLossy() which does actually does the conversion to sRGB
+ if necessary and makes it clear to the caller that precision is being lost.
+ - Removes Color::red()/green()/blue() entirely. They were just calling down to
+ Color::rgb(), and going forward, it won't make sense to think about rgb components
+ of Colors in general, since some extended color spaces don't deal in them (e.g. Lab)
+ Color::alpha() was kept (and fixed to work even with ExtendedColor) since all
+ ExtendedColors do need to have alpha.
+
+ * accessibility/AccessibilityNodeObject.cpp:
+ (WebCore::AccessibilityNodeObject::colorValue const):
+ Use toSRGBASimpleColorLossy() to get access to color components.
+
+ * accessibility/atk/WebKitAccessibleInterfaceText.cpp:
+ (getAttributeSetForAccessibilityObject):
+ Use toSRGBASimpleColorLossy() to get access to color components.
+
+ * accessibility/isolatedtree/AXIsolatedObject.cpp:
+ (WebCore::AXIsolatedObject::colorValue const):
+ Use toSRGBASimpleColorLossy() to get access to color components.
+
+ * css/DeprecatedCSSOMRGBColor.h:
+ Use toSRGBASimpleColorLossy() to get access to color components.
+
+ * page/CaptionUserPreferencesMediaAF.cpp:
+ (WebCore::CaptionUserPreferencesMediaAF::captionsWindowCSS const):
+ (WebCore::CaptionUserPreferencesMediaAF::captionsBackgroundCSS const):
+ (WebCore::CaptionUserPreferencesMediaAF::captionsTextColor const):
+ User Color::colorWithAlpha() to avoid the need to muck with components directly.
+
+ * platform/graphics/Color.cpp:
+ (WebCore::differenceSquared):
+ Use rgb() directly, which is ok, since this is explicitly checking isExtended().
+ This code is still wrong (there is a FIXME) as it assumes the two colors are in
+ the same color space.
+
+ (WebCore::Color::Color):
+ Add constructor which takes an ExtendedColor to allow functions like
+ Color::invertedColorWithAlpha to delegate their functionality to ExtendedColor.
+
+ (WebCore::Color::light const):
+ Use new SimpleColor::colorWithAlpha() to avoid hardcoding constants here.
+
+ (WebCore::Color::blend const):
+ (WebCore::Color::blendWithWhite const):
+ Use toSRGBASimpleColorLossy() to get access to color components. These
+ are still not ideal implementations, as they don't preserve extended colors
+ as well as they could, but now they don't return bogus values for extended
+ colors. Minor cleanup bringing constants and lambda inside the function they
+ are used in.
+
+ (WebCore::Color::colorWithAlpha const):
+ (WebCore::Color::colorWithAlphaUsingAlternativeRounding const):
+ Minor cleanups to use a more consistent style and make use of the new
+ SimpleColor::colorWithAlpha.
+
+ (WebCore::Color::invertedColorWithAlpha const):
+ Added. Used to avoid direct component usage in line box code.
+
+ (WebCore::Color::semanticColor const):
+ Added. Hopefully temporary. Used by RenderThemeIOS.mm to convert
+ a Color from a map into a Color with the semantic bit set. This
+ should not be necessary as every color in the map should already
+ have it set, but to avoid uncessary possible behavior changes this
+ preserves that functionality until it can be researched further.
+ Fixing coders to preserve the semantic bit may be required to
+ elliminate the need.
+
+ (WebCore::Color::colorSpaceAndComponents const):
+ Use rgb() rather than the individual components which have been removed.
+
+ * platform/graphics/Color.h:
+ (WebCore::SimpleColor::alphaComponentAsFloat const):
+ Added. Needed by DeprecatedCSSOMRGBColor and useful to Color.
+
+ (WebCore::SimpleColor::colorWithAlpha const):
+ Useful to simplify Color::colorWithAlpha implementations and
+ in Color::dark().
+
+ (WebCore::SimpleColor::get const):
+ Added tuple interface to SimpleColor to support structure bindings.
+ NOTE: Unlike the storage of SimpleColor (ARGB), this produces the
+ bindings in the more familiar [r,g,b,a] to match FloatComponents.
+
+ (WebCore::Color::alpha const):
+ Made work with ExtendedColor as well.
+
+ (WebCore::Color::red const): Deleted.
+ (WebCore::Color::green const): Deleted.
+ (WebCore::Color::blue const): Deleted.
+ Removed.
+
+ (CGColorRef cachedCGColor):
+ (int differenceSquared):
+ Made friends so they could use Color::rgb().
+
+ (WebCore::Color::rgb const):
+ Made private.
+
+ * platform/graphics/ExtendedColor.cpp:
+ (WebCore::ExtendedColor::invertedColorWithAlpha const):
+ * platform/graphics/ExtendedColor.h:
+ Added invertedColorWithAlpha to allow inversion to be encapsulated.
+ When future color spaces are added, we may need to choose per-colorspace
+ algorithms for this instead of the trivial one used today.
+
+ * platform/graphics/ca/cocoa/PlatformCAAnimationCocoa.mm:
+ (WebCore::PlatformCAAnimationCocoa::setFromValue):
+ (WebCore::PlatformCAAnimationCocoa::setToValue):
+ (WebCore::PlatformCAAnimationCocoa::setValues):
+ Use toSRGBASimpleColorLossy() to get access to color components.
+
+ * platform/graphics/ca/win/PlatformCAAnimationWin.cpp:
+ (PlatformCAAnimationWin::setFromValue):
+ (PlatformCAAnimationWin::setToValue):
+ (PlatformCAAnimationWin::setValues):
+ Use toSRGBASimpleColorLossy() to get access to color components.
+
+ * platform/graphics/cairo/CairoOperations.cpp:
+ (WebCore::Cairo::drawFocusRing):
+ Use Color::colorWithAlpha() to avoid needing access to components.
+
+ * platform/graphics/cpu/arm/filters/FELightingNEON.h:
+ (WebCore::FELighting::platformApplyNeon):
+ Use toSRGBASimpleColorLossy() to get access to color components.
+
+ * platform/graphics/texmap/TextureMapperGL.cpp:
+ (WebCore::TextureMapperGL::clearColor):
+ Use toSRGBASimpleColorLossy() to get access to color components.
+
+ * platform/graphics/win/Direct2DOperations.cpp:
+ (WebCore::Direct2D::drawGlyphs):
+ Use colorWithAlphaMultipliedBy() to avoid needing access to components.
+
+ * platform/graphics/win/FontCGWin.cpp:
+ (WebCore::FontCascade::drawGlyphs):
+ Use colorWithAlphaMultipliedBy() to avoid needing access to components.
+
+ * platform/graphics/win/FontCascadeDirect2D.cpp:
+ (WebCore::FontCascade::drawGlyphs):
+ Use colorWithAlphaMultipliedBy() to avoid needing access to components.
+
+ * rendering/EllipsisBox.cpp:
+ (WebCore::EllipsisBox::paintSelection):
+ Use invertedColorWithAlpha() to avoid needing access to components.
+
+ * rendering/InlineTextBox.cpp:
+ (WebCore::InlineTextBox::resolveStyleForMarkedText):
+ Use invertedColorWithAlpha() to avoid needing access to components.
+
+ * rendering/RenderBoxModelObject.cpp:
+ (WebCore::RenderBoxModelObject::paintBoxShadow):
+ Use opaqueColor() to avoid needing access to components.
+
+ * rendering/RenderThemeIOS.mm:
+ (WebCore::RenderThemeIOS::systemColor const):
+ Use opaqueColor() to avoid needing access to components.
+
+ * svg/properties/SVGAnimationAdditiveValueFunctionImpl.h:
+ (WebCore::SVGAnimationColorFunction::animate):
+ Use toSRGBASimpleColorLossy() to get access to color components.
+
2020-05-24 Zalan Bujtas <[email protected]>
[LFC][TFC] Take sections into account when computing collapsed border.
Modified: trunk/Source/WebCore/accessibility/AccessibilityNodeObject.cpp (262107 => 262108)
--- trunk/Source/WebCore/accessibility/AccessibilityNodeObject.cpp 2020-05-24 15:34:44 UTC (rev 262107)
+++ trunk/Source/WebCore/accessibility/AccessibilityNodeObject.cpp 2020-05-24 15:53:19 UTC (rev 262108)
@@ -1962,10 +1962,10 @@
if (!is<HTMLInputElement>(node()))
return;
- auto color = downcast<HTMLInputElement>(*node()).valueAsColor();
- r = color.red();
- g = color.green();
- b = color.blue();
+ auto color = downcast<HTMLInputElement>(*node()).valueAsColor().toSRGBASimpleColorLossy();
+ r = color.redComponent();
+ g = color.greenComponent();
+ b = color.blueComponent();
#endif
}
Modified: trunk/Source/WebCore/accessibility/atk/WebKitAccessibleInterfaceText.cpp (262107 => 262108)
--- trunk/Source/WebCore/accessibility/atk/WebKitAccessibleInterfaceText.cpp 2020-05-24 15:34:44 UTC (rev 262107)
+++ trunk/Source/WebCore/accessibility/atk/WebKitAccessibleInterfaceText.cpp 2020-05-24 15:53:19 UTC (rev 262108)
@@ -92,13 +92,15 @@
Color bgColor = style->visitedDependentColor(CSSPropertyBackgroundColor);
if (bgColor.isValid()) {
- buffer.reset(g_strdup_printf("%i,%i,%i", bgColor.red(), bgColor.green(), bgColor.blue()));
+ auto [r, g, b, a] = bgColor.toSRGBASimpleColorLossy();
+ buffer.reset(g_strdup_printf("%i,%i,%i", r, g, b));
result = addToAtkAttributeSet(result, atk_text_attribute_get_name(ATK_TEXT_ATTR_BG_COLOR), buffer.get());
}
Color fgColor = style->visitedDependentColor(CSSPropertyColor);
if (fgColor.isValid()) {
- buffer.reset(g_strdup_printf("%i,%i,%i", fgColor.red(), fgColor.green(), fgColor.blue()));
+ auto [r, g, b, a] = fgColor.toSRGBASimpleColorLossy();
+ buffer.reset(g_strdup_printf("%i,%i,%i", r, g, b));
result = addToAtkAttributeSet(result, atk_text_attribute_get_name(ATK_TEXT_ATTR_FG_COLOR), buffer.get());
}
Modified: trunk/Source/WebCore/accessibility/isolatedtree/AXIsolatedObject.cpp (262107 => 262108)
--- trunk/Source/WebCore/accessibility/isolatedtree/AXIsolatedObject.cpp 2020-05-24 15:34:44 UTC (rev 262107)
+++ trunk/Source/WebCore/accessibility/isolatedtree/AXIsolatedObject.cpp 2020-05-24 15:53:19 UTC (rev 262108)
@@ -698,10 +698,10 @@
void AXIsolatedObject::colorValue(int& r, int& g, int& b) const
{
- auto color = colorAttributeValue(AXPropertyName::ColorValue);
- r = color.red();
- g = color.green();
- b = color.blue();
+ auto color = colorAttributeValue(AXPropertyName::ColorValue).toSRGBASimpleColorLossy();
+ r = color.redComponent();
+ g = color.greenComponent();
+ b = color.blueComponent();
}
AXCoreObject* AXIsolatedObject::accessibilityHitTest(const IntPoint& point) const
Modified: trunk/Source/WebCore/css/DeprecatedCSSOMRGBColor.h (262107 => 262108)
--- trunk/Source/WebCore/css/DeprecatedCSSOMRGBColor.h 2020-05-24 15:34:44 UTC (rev 262107)
+++ trunk/Source/WebCore/css/DeprecatedCSSOMRGBColor.h 2020-05-24 15:53:19 UTC (rev 262108)
@@ -37,7 +37,7 @@
DeprecatedCSSOMPrimitiveValue& blue() { return m_blue; }
DeprecatedCSSOMPrimitiveValue& alpha() { return m_alpha; }
- Color color() const { return m_color; }
+ SimpleColor color() const { return m_color; }
private:
template<typename NumberType> static Ref<DeprecatedCSSOMPrimitiveValue> createWrapper(CSSStyleDeclaration& owner, NumberType number)
@@ -46,15 +46,15 @@
}
DeprecatedCSSOMRGBColor(CSSStyleDeclaration& owner, const Color& color)
- : m_color(color)
- , m_red(createWrapper(owner, color.red()))
- , m_green(createWrapper(owner, color.green()))
- , m_blue(createWrapper(owner, color.blue()))
- , m_alpha(createWrapper(owner, color.alphaAsFloat()))
+ : m_color(color.toSRGBASimpleColorLossy())
+ , m_red(createWrapper(owner, m_color.redComponent()))
+ , m_green(createWrapper(owner, m_color.greenComponent()))
+ , m_blue(createWrapper(owner, m_color.blueComponent()))
+ , m_alpha(createWrapper(owner, m_color.alphaComponentAsFloat()))
{
}
- Color m_color;
+ SimpleColor m_color;
Ref<DeprecatedCSSOMPrimitiveValue> m_red;
Ref<DeprecatedCSSOMPrimitiveValue> m_green;
Ref<DeprecatedCSSOMPrimitiveValue> m_blue;
Modified: trunk/Source/WebCore/page/CaptionUserPreferencesMediaAF.cpp (262107 => 262108)
--- trunk/Source/WebCore/page/CaptionUserPreferencesMediaAF.cpp 2020-05-24 15:34:44 UTC (rev 262107)
+++ trunk/Source/WebCore/page/CaptionUserPreferencesMediaAF.cpp 2020-05-24 15:53:19 UTC (rev 262108)
@@ -276,7 +276,7 @@
CGFloat opacity = MACaptionAppearanceGetWindowOpacity(kMACaptionAppearanceDomainUser, &behavior);
if (!important)
important = behavior == kMACaptionAppearanceBehaviorUseValue;
- String windowStyle = colorPropertyCSS(CSSPropertyBackgroundColor, Color(windowColor.red(), windowColor.green(), windowColor.blue(), static_cast<int>(opacity * 255)), important);
+ String windowStyle = colorPropertyCSS(CSSPropertyBackgroundColor, windowColor.colorWithAlpha(opacity), important);
if (!opacity)
return windowStyle;
@@ -301,7 +301,7 @@
CGFloat opacity = MACaptionAppearanceGetBackgroundOpacity(kMACaptionAppearanceDomainUser, &behavior);
if (!important)
important = behavior == kMACaptionAppearanceBehaviorUseValue;
- return colorPropertyCSS(CSSPropertyBackgroundColor, Color(backgroundColor.red(), backgroundColor.green(), backgroundColor.blue(), static_cast<int>(opacity * 255)), important);
+ return colorPropertyCSS(CSSPropertyBackgroundColor, backgroundColor.colorWithAlpha(opacity), important);
}
Color CaptionUserPreferencesMediaAF::captionsTextColor(bool& important) const
@@ -317,7 +317,7 @@
CGFloat opacity = MACaptionAppearanceGetForegroundOpacity(kMACaptionAppearanceDomainUser, &behavior);
if (!important)
important = behavior == kMACaptionAppearanceBehaviorUseValue;
- return Color(textColor.red(), textColor.green(), textColor.blue(), static_cast<int>(opacity * 255));
+ return textColor.colorWithAlpha(opacity);
}
String CaptionUserPreferencesMediaAF::captionsTextColorCSS() const
Modified: trunk/Source/WebCore/platform/graphics/Color.cpp (262107 => 262108)
--- trunk/Source/WebCore/platform/graphics/Color.cpp 2020-05-24 15:34:44 UTC (rev 262107)
+++ trunk/Source/WebCore/platform/graphics/Color.cpp 2020-05-24 15:53:19 UTC (rev 262108)
@@ -180,12 +180,12 @@
// FIXME: This should probably return a floating point number, but many of the call
// sites have picked comparison values based on feel. We'd need to break out
// our logarithm tables to change them :)
- int c1Red = c1.isExtended() ? c1.asExtended().red() * 255 : c1.red();
- int c1Green = c1.isExtended() ? c1.asExtended().green() * 255 : c1.green();
- int c1Blue = c1.isExtended() ? c1.asExtended().blue() * 255 : c1.blue();
- int c2Red = c2.isExtended() ? c2.asExtended().red() * 255 : c2.red();
- int c2Green = c2.isExtended() ? c2.asExtended().green() * 255 : c2.green();
- int c2Blue = c2.isExtended() ? c2.asExtended().blue() * 255 : c2.blue();
+ int c1Red = c1.isExtended() ? c1.asExtended().red() * 255 : c1.rgb().redComponent();
+ int c1Green = c1.isExtended() ? c1.asExtended().green() * 255 : c1.rgb().greenComponent();
+ int c1Blue = c1.isExtended() ? c1.asExtended().blue() * 255 : c1.rgb().blueComponent();
+ int c2Red = c2.isExtended() ? c2.asExtended().red() * 255 : c2.rgb().redComponent();
+ int c2Green = c2.isExtended() ? c2.asExtended().green() * 255 : c2.rgb().greenComponent();
+ int c2Blue = c2.isExtended() ? c2.asExtended().blue() * 255 : c2.rgb().blueComponent();
int dR = c1Red - c2Red;
int dG = c1Green - c2Green;
int dB = c1Blue - c2Blue;
@@ -250,12 +250,16 @@
}
Color::Color(float c1, float c2, float c3, float alpha, ColorSpace colorSpace)
+ : Color(ExtendedColor::create(c1, c2, c3, alpha, colorSpace))
{
+}
+
+Color::Color(Ref<ExtendedColor>&& extendedColor)
+{
// Zero the union, just in case a 32-bit system only assigns the
// top 32 bits when copying the extendedColor pointer below.
m_colorData.rgbaAndFlags = 0;
- auto extendedColorRef = ExtendedColor::create(c1, c2, c3, alpha, colorSpace);
- m_colorData.extendedColor = &extendedColorRef.leakRef();
+ m_colorData.extendedColor = &extendedColor.leakRef();
ASSERT(isExtended());
}
@@ -363,17 +367,17 @@
float v = std::max({ r, g, b });
- if (v == 0.0f) {
- // Lightened black with alpha.
- return Color(0x54, 0x54, 0x54, alpha());
- }
+ if (v == 0.0f)
+ return lightenedBlack.colorWithAlpha(alpha());
float multiplier = std::min(1.0f, v + 0.33f) / v;
- return Color(static_cast<int>(multiplier * r * scaleFactor),
- static_cast<int>(multiplier * g * scaleFactor),
- static_cast<int>(multiplier * b * scaleFactor),
- alpha());
+ return {
+ static_cast<int>(multiplier * r * scaleFactor),
+ static_cast<int>(multiplier * g * scaleFactor),
+ static_cast<int>(multiplier * b * scaleFactor),
+ alpha()
+ };
}
Color Color::dark() const
@@ -389,10 +393,12 @@
float v = std::max({ r, g, b });
float multiplier = std::max(0.0f, (v - 0.33f) / v);
- return Color(static_cast<int>(multiplier * r * scaleFactor),
- static_cast<int>(multiplier * g * scaleFactor),
- static_cast<int>(multiplier * b * scaleFactor),
- alpha());
+ return {
+ static_cast<int>(multiplier * r * scaleFactor),
+ static_cast<int>(multiplier * g * scaleFactor),
+ static_cast<int>(multiplier * b * scaleFactor),
+ alpha()
+ };
}
bool Color::isDark() const
@@ -409,19 +415,6 @@
return WebCore::lightness(toSRGBAComponentsLossy());
}
-static int blendComponent(int c, int a)
-{
- // We use white.
- float alpha = a / 255.0f;
- int whiteBlend = 255 - a;
- c -= whiteBlend;
- return static_cast<int>(c / alpha);
-}
-
-const int cStartAlpha = 153; // 60%
-const int cEndAlpha = 204; // 80%;
-const int cAlphaIncrement = 17; // Increments in between.
-
Color Color::blend(const Color& source) const
{
if (!isVisible() || source.isOpaque())
@@ -430,37 +423,55 @@
if (!source.alpha())
return *this;
- int d = 255 * (alpha() + source.alpha()) - alpha() * source.alpha();
- int a = d / 255;
- int r = (red() * alpha() * (255 - source.alpha()) + 255 * source.alpha() * source.red()) / d;
- int g = (green() * alpha() * (255 - source.alpha()) + 255 * source.alpha() * source.green()) / d;
- int b = (blue() * alpha() * (255 - source.alpha()) + 255 * source.alpha() * source.blue()) / d;
- return Color(r, g, b, a);
+ auto [selfR, selfG, selfB, selfA] = toSRGBASimpleColorLossy();
+ auto [sourceR, sourceG, sourceB, sourceA] = source.toSRGBASimpleColorLossy();
+
+ int d = 0xFF * (selfA + sourceA) - selfA * sourceA;
+ int a = d / 0xFF;
+ int r = (selfR * selfA * (0xFF - sourceA) + 0xFF * sourceA * sourceR) / d;
+ int g = (selfG * selfA * (0xFF - sourceA) + 0xFF * sourceA * sourceG) / d;
+ int b = (selfB * selfA * (0xFF - sourceA) + 0xFF * sourceA * sourceB) / d;
+
+ return makeRGBA(r, g, b, a);
}
Color Color::blendWithWhite() const
{
+ constexpr int startAlpha = 153; // 60%
+ constexpr int endAlpha = 204; // 80%;
+ constexpr int alphaIncrement = 17;
+
+ auto blendComponent = [](int c, int a) -> int {
+ float alpha = a / 255.0f;
+ int whiteBlend = 255 - a;
+ c -= whiteBlend;
+ return static_cast<int>(c / alpha);
+ };
+
// If the color contains alpha already, we leave it alone.
if (!isOpaque())
return *this;
- Color newColor;
- for (int alpha = cStartAlpha; alpha <= cEndAlpha; alpha += cAlphaIncrement) {
+ auto [existingR, existingG, existingB, existingAlpha] = toSRGBASimpleColorLossy();
+
+ Color result;
+ for (int alpha = startAlpha; alpha <= endAlpha; alpha += alphaIncrement) {
// We have a solid color. Convert to an equivalent color that looks the same when blended with white
// at the current alpha. Try using less transparency if the numbers end up being negative.
- int r = blendComponent(red(), alpha);
- int g = blendComponent(green(), alpha);
- int b = blendComponent(blue(), alpha);
+ int r = blendComponent(existingR, alpha);
+ int g = blendComponent(existingG, alpha);
+ int b = blendComponent(existingB, alpha);
- newColor = Color(r, g, b, alpha);
+ result = makeRGBA(r, g, b, alpha);
if (r >= 0 && g >= 0 && b >= 0)
break;
}
+ // FIXME: Why is preserving the semantic bit desired and/or correct here?
if (isSemantic())
- newColor.setIsSemantic();
- return newColor;
+ result.setIsSemantic();
+ return result;
}
Color Color::colorWithAlphaMultipliedBy(float amount) const
@@ -477,13 +488,15 @@
Color Color::colorWithAlpha(float alpha) const
{
- if (isExtended())
- return Color { m_colorData.extendedColor->red(), m_colorData.extendedColor->green(), m_colorData.extendedColor->blue(), alpha, m_colorData.extendedColor->colorSpace() };
+ if (isExtended()) {
+ auto& extendedColor = asExtended();
+ return Color { extendedColor.red(), extendedColor.green(), extendedColor.blue(), alpha, extendedColor.colorSpace() };
+ }
// FIXME: This is where this function differs from colorWithAlphaUsingAlternativeRounding.
- int newAlpha = alpha * 255;
+ uint8_t newAlpha = alpha * 0xFF;
- Color result = { red(), green(), blue(), newAlpha };
+ Color result = rgb().colorWithAlpha(newAlpha);
if (isSemantic())
result.setIsSemantic();
return result;
@@ -491,15 +504,37 @@
Color Color::colorWithAlphaUsingAlternativeRounding(float alpha) const
{
- if (isExtended())
- return Color { m_colorData.extendedColor->red(), m_colorData.extendedColor->green(), m_colorData.extendedColor->blue(), alpha, m_colorData.extendedColor->colorSpace() };
+ if (isExtended()) {
+ auto& extendedColor = asExtended();
+ return Color { extendedColor.red(), extendedColor.green(), extendedColor.blue(), alpha, extendedColor.colorSpace() };
+ }
- Color result = SimpleColor { (rgb().value() & 0x00FFFFFF) | colorFloatToRGBAByte(alpha) << 24 };
+ // FIXME: This is where this function differs from colorWithAlphaUsing.
+ uint8_t newAlpha = colorFloatToRGBAByte(alpha);
+
+ Color result = rgb().colorWithAlpha(newAlpha);
if (isSemantic())
result.setIsSemantic();
return result;
}
+Color Color::invertedColorWithAlpha(float alpha) const
+{
+ if (isExtended())
+ return Color { asExtended().invertedColorWithAlpha(alpha) };
+
+ auto [r, g, b, existingAlpha] = rgb();
+ return { 0xFF - r, 0xFF - g, 0xFF - b, colorFloatToRGBAByte(alpha) };
+}
+
+Color Color::semanticColor() const
+{
+ if (isSemantic())
+ return *this;
+
+ return { toSRGBASimpleColorLossy(), Semantic };
+}
+
std::pair<ColorSpace, FloatComponents> Color::colorSpaceAndComponents() const
{
if (isExtended()) {
@@ -507,7 +542,8 @@
return { extendedColor.colorSpace(), extendedColor.channels() };
}
- return { ColorSpace::SRGB, FloatComponents { red() / 255.0f, green() / 255.0f, blue() / 255.0f, alpha() / 255.0f } };
+ auto [r, g, b, a] = rgb();
+ return { ColorSpace::SRGB, FloatComponents { r / 255.0f, g / 255.0f, b / 255.0f, a / 255.0f } };
}
SimpleColor Color::toSRGBASimpleColorLossy() const
Modified: trunk/Source/WebCore/platform/graphics/Color.h (262107 => 262108)
--- trunk/Source/WebCore/platform/graphics/Color.h 2020-05-24 15:34:44 UTC (rev 262107)
+++ trunk/Source/WebCore/platform/graphics/Color.h 2020-05-24 15:53:19 UTC (rev 262108)
@@ -69,6 +69,8 @@
constexpr uint8_t blueComponent() const { return m_value; }
constexpr uint8_t alphaComponent() const { return m_value >> 24; }
+ constexpr float alphaComponentAsFloat() const { return static_cast<float>(alphaComponent()) / 0xFF; }
+
constexpr bool isOpaque() const { return alphaComponent() == 0xFF; }
constexpr bool isVisible() const { return alphaComponent(); }
@@ -76,6 +78,22 @@
String serializationForCSS() const;
String serializationForRenderTreeAsText() const;
+ constexpr SimpleColor colorWithAlpha(uint8_t alpha) const { return { (m_value & 0x00FFFFFF) | alpha << 24 }; }
+
+ template<std::size_t N>
+ constexpr uint8_t get() const
+ {
+ static_assert(N < 4);
+ if constexpr (!N)
+ return redComponent();
+ else if constexpr (N == 1)
+ return greenComponent();
+ else if constexpr (N == 2)
+ return blueComponent();
+ else if constexpr (N == 3)
+ return alphaComponent();
+ }
+
private:
uint32_t m_value { 0 };
};
@@ -171,6 +189,7 @@
// FIXME: If the colorSpace is sRGB and the values can all be
// converted exactly to integers, we should make a normal Color.
WEBCORE_EXPORT Color(float, float, float, float, ColorSpace);
+ WEBCORE_EXPORT Color(Ref<ExtendedColor>&&);
WEBCORE_EXPORT Color(const Color&);
WEBCORE_EXPORT Color(Color&&);
@@ -195,15 +214,9 @@
bool isOpaque() const { return isExtended() ? asExtended().alpha() == 1.0 : rgb().isOpaque(); }
bool isVisible() const { return isExtended() ? asExtended().alpha() > 0.0 : rgb().isVisible(); }
- int red() const { return rgb().redComponent(); }
- int green() const { return rgb().greenComponent(); }
- int blue() const { return rgb().blueComponent(); }
- int alpha() const { return rgb().alphaComponent(); }
+ int alpha() const { return isExtended() ? asExtended().alpha() * 255 : rgb().alphaComponent(); }
+ float alphaAsFloat() const { return isExtended() ? asExtended().alpha() : rgb().alphaComponentAsFloat(); }
- float alphaAsFloat() const { return isExtended() ? asExtended().alpha() : static_cast<float>(rgb().alphaComponent()) / 0xFF; }
-
- RGBA32 rgb() const;
-
unsigned hash() const;
WEBCORE_EXPORT std::pair<ColorSpace, FloatComponents> colorSpaceAndComponents() const;
@@ -225,6 +238,8 @@
Color blend(const Color&) const;
Color blendWithWhite() const;
+ Color invertedColorWithAlpha(float alpha) const;
+
Color colorWithAlphaMultipliedBy(float) const;
Color colorWithAlpha(float) const;
@@ -235,6 +250,7 @@
WEBCORE_EXPORT Color colorWithAlphaUsingAlternativeRounding(float) const;
Color opaqueColor() const { return colorWithAlpha(1.0f); }
+ Color semanticColor() const;
// True if the color originated from a CSS semantic color name.
bool isSemantic() const { return !isExtended() && (m_colorData.rgbaAndFlags & isSemanticRBGAColorBit); }
@@ -247,6 +263,7 @@
#if USE(CG)
WEBCORE_EXPORT Color(CGColorRef);
WEBCORE_EXPORT Color(CGColorRef, SemanticTag);
+ friend WEBCORE_EXPORT CGColorRef cachedCGColor(const Color&);
#endif
#if PLATFORM(WIN)
@@ -288,6 +305,8 @@
friend bool operator==(const Color& a, const Color& b);
friend bool equalIgnoringSemanticColor(const Color& a, const Color& b);
+ friend int differenceSquared(const Color&, const Color&);
+
static bool isBlackColor(const Color&);
static bool isWhiteColor(const Color&);
@@ -295,6 +314,7 @@
template<class Decoder> static Optional<Color> decode(Decoder&);
private:
+ RGBA32 rgb() const;
void setRGB(int r, int g, int b) { setRGB(makeRGB(r, g, b)); }
void setRGB(RGBA32);
void setIsSemantic() { m_colorData.rgbaAndFlags |= isSemanticRBGAColorBit; }
@@ -530,3 +550,17 @@
template<> struct DefaultHash<WebCore::Color>;
template<> struct HashTraits<WebCore::Color>;
}
+
+namespace std {
+
+template<>
+class tuple_size<WebCore::SimpleColor> : public std::integral_constant<std::size_t, 4> {
+};
+
+template<std::size_t N>
+class tuple_element<N, WebCore::SimpleColor> {
+public:
+ using type = uint8_t;
+};
+
+}
Modified: trunk/Source/WebCore/platform/graphics/ExtendedColor.cpp (262107 => 262108)
--- trunk/Source/WebCore/platform/graphics/ExtendedColor.cpp 2020-05-24 15:34:44 UTC (rev 262107)
+++ trunk/Source/WebCore/platform/graphics/ExtendedColor.cpp 2020-05-24 15:53:19 UTC (rev 262108)
@@ -63,4 +63,10 @@
return makeString("color(", colorSpace, ' ', red(), ' ', green(), ' ', blue(), " / ", alpha(), ')');
}
+Ref<ExtendedColor> ExtendedColor::invertedColorWithAlpha(float alpha) const
+{
+ auto [c1, c2, c3, existingAlpha] = channels();
+ return ExtendedColor::create(1.0f - c1, 1.0f - c2, 1.0f - c3, alpha, colorSpace());
}
+
+}
Modified: trunk/Source/WebCore/platform/graphics/ExtendedColor.h (262107 => 262108)
--- trunk/Source/WebCore/platform/graphics/ExtendedColor.h 2020-05-24 15:34:44 UTC (rev 262107)
+++ trunk/Source/WebCore/platform/graphics/ExtendedColor.h 2020-05-24 15:53:19 UTC (rev 262108)
@@ -63,6 +63,8 @@
WEBCORE_EXPORT String cssText() const;
+ Ref<ExtendedColor> invertedColorWithAlpha(float) const;
+
private:
ExtendedColor(float c1, float c2, float c3, float alpha, ColorSpace colorSpace)
: m_channels(c1, c2, c3, alpha)
Modified: trunk/Source/WebCore/platform/graphics/avfoundation/InbandTextTrackPrivateAVF.cpp (262107 => 262108)
--- trunk/Source/WebCore/platform/graphics/avfoundation/InbandTextTrackPrivateAVF.cpp 2020-05-24 15:34:44 UTC (rev 262107)
+++ trunk/Source/WebCore/platform/graphics/avfoundation/InbandTextTrackPrivateAVF.cpp 2020-05-24 15:53:19 UTC (rev 262108)
@@ -64,16 +64,16 @@
disconnect();
}
-static bool makeRGBA32FromARGBCFArray(CFArrayRef colorArray, RGBA32& color)
+static Optional<SimpleColor> makeRGBA32FromARGBCFArray(CFArrayRef colorArray)
{
if (CFArrayGetCount(colorArray) < 4)
- return false;
+ return WTF::nullopt;
float componentArray[4];
for (int i = 0; i < 4; i++) {
CFNumberRef value = static_cast<CFNumberRef>(CFArrayGetValueAtIndex(colorArray, i));
if (CFGetTypeID(value) != CFNumberGetTypeID())
- return false;
+ return WTF::nullopt;
float component;
CFNumberGetValue(value, kCFNumberFloatType, &component);
@@ -80,8 +80,7 @@
componentArray[i] = component;
}
- color = makeRGBA32FromFloats(componentArray[1], componentArray[2], componentArray[3], componentArray[0]);
- return true;
+ return makeRGBA32FromFloats(componentArray[1], componentArray[2], componentArray[3], componentArray[0]);
}
Ref<InbandGenericCue> InbandTextTrackPrivateAVF::processCueAttributes(CFAttributedStringRef attributedString)
@@ -268,10 +267,10 @@
if (CFGetTypeID(arrayValue) != CFArrayGetTypeID())
continue;
- RGBA32 color;
- if (!makeRGBA32FromARGBCFArray(arrayValue, color))
+ auto color = makeRGBA32FromARGBCFArray(arrayValue);
+ if (!color)
continue;
- cueData->setForegroundColor(color);
+ cueData->setForegroundColor(*color);
continue;
}
@@ -280,10 +279,10 @@
if (CFGetTypeID(arrayValue) != CFArrayGetTypeID())
continue;
- RGBA32 color;
- if (!makeRGBA32FromARGBCFArray(arrayValue, color))
+ auto color = makeRGBA32FromARGBCFArray(arrayValue);
+ if (!color)
continue;
- cueData->setBackgroundColor(color);
+ cueData->setBackgroundColor(*color);
continue;
}
@@ -292,10 +291,10 @@
if (CFGetTypeID(arrayValue) != CFArrayGetTypeID())
continue;
- RGBA32 color;
- if (!makeRGBA32FromARGBCFArray(arrayValue, color))
+ auto color = makeRGBA32FromARGBCFArray(arrayValue);
+ if (!color)
continue;
- cueData->setHighlightColor(color);
+ cueData->setHighlightColor(*color);
continue;
}
}
Modified: trunk/Source/WebCore/platform/graphics/ca/cocoa/PlatformCAAnimationCocoa.mm (262107 => 262108)
--- trunk/Source/WebCore/platform/graphics/ca/cocoa/PlatformCAAnimationCocoa.mm 2020-05-24 15:34:44 UTC (rev 262107)
+++ trunk/Source/WebCore/platform/graphics/ca/cocoa/PlatformCAAnimationCocoa.mm 2020-05-24 15:53:19 UTC (rev 262108)
@@ -396,7 +396,8 @@
{
if (!isBasicAnimation())
return;
- [static_cast<CABasicAnimation*>(m_animation.get()) setFromValue:@[@(value.red()), @(value.green()), @(value.blue()), @(value.alpha())]];
+ auto [r, g, b, a] = value.toSRGBASimpleColorLossy();
+ [static_cast<CABasicAnimation*>(m_animation.get()) setFromValue:@[@(r), @(g), @(b), @(a)]];
}
void PlatformCAAnimationCocoa::setFromValue(const FilterOperation* operation, int internalFilterPropertyIndex)
@@ -438,7 +439,8 @@
{
if (!isBasicAnimation())
return;
- [static_cast<CABasicAnimation*>(m_animation.get()) setToValue:@[@(value.red()), @(value.green()), @(value.blue()), @(value.alpha())]];
+ auto [r, g, b, a] = value.toSRGBASimpleColorLossy();
+ [static_cast<CABasicAnimation*>(m_animation.get()) setToValue:@[@(r), @(g), @(b), @(a)]];
}
void PlatformCAAnimationCocoa::setToValue(const FilterOperation* operation, int internalFilterPropertyIndex)
@@ -494,7 +496,8 @@
return;
[static_cast<CAKeyframeAnimation*>(m_animation.get()) setValues:createNSArray(value, [] (auto& color) {
- return @[@(color.red()), @(color.green()), @(color.blue()), @(color.alpha())];
+ auto [r, g, b, a] = color.toSRGBASimpleColorLossy();
+ return @[@(r), @(g), @(b), @(a)];
}).get()];
}
Modified: trunk/Source/WebCore/platform/graphics/ca/win/PlatformCAAnimationWin.cpp (262107 => 262108)
--- trunk/Source/WebCore/platform/graphics/ca/win/PlatformCAAnimationWin.cpp 2020-05-24 15:34:44 UTC (rev 262107)
+++ trunk/Source/WebCore/platform/graphics/ca/win/PlatformCAAnimationWin.cpp 2020-05-24 15:53:19 UTC (rev 262108)
@@ -367,7 +367,8 @@
if (animationType() != Basic)
return;
- CGFloat a[4] = { value.red(), value.green(), value.blue(), value.alpha() };
+ auto simpleColor = value.toSRGBASimpleColorLossy();
+ CGFloat a[4] = { simpleColor.redComponent(), simpleColor.greenComponent(), simpleColor.blueComponent(), simpleColor.alphaComponent() };
RetainPtr<CACFVectorRef> v = adoptCF(CACFVectorCreate(4, a));
CACFAnimationSetFromValue(m_animation.get(), v.get());
}
@@ -418,7 +419,8 @@
if (animationType() != Basic)
return;
- CGFloat a[4] = { value.red(), value.green(), value.blue(), value.alpha() };
+ auto simpleColor = value.toSRGBASimpleColorLossy();
+ CGFloat a[4] = { simpleColor.redComponent(), simpleColor.greenComponent(), simpleColor.blueComponent(), simpleColor.alphaComponent() };
RetainPtr<CACFVectorRef> v = adoptCF(CACFVectorCreate(4, a));
CACFAnimationSetToValue(m_animation.get(), v.get());
}
@@ -487,7 +489,8 @@
RetainPtr<CFMutableArrayRef> array = adoptCF(CFArrayCreateMutable(0, value.size(), &kCFTypeArrayCallBacks));
for (size_t i = 0; i < value.size(); ++i) {
- CGFloat a[4] = { value[i].red(), value[i].green(), value[i].blue(), value[i].alpha() };
+ auto simpleColor = value[i].toSRGBASimpleColorLossy();
+ CGFloat a[4] = { simpleColor.redComponent(), simpleColor.greenComponent(), simpleColor.blueComponent(), simpleColor.alphaComponent() };
RetainPtr<CACFVectorRef> v = adoptCF(CACFVectorCreate(4, a));
CFArrayAppendValue(array.get(), v.get());
}
Modified: trunk/Source/WebCore/platform/graphics/cairo/CairoOperations.cpp (262107 => 262108)
--- trunk/Source/WebCore/platform/graphics/cairo/CairoOperations.cpp 2020-05-24 15:34:44 UTC (rev 262107)
+++ trunk/Source/WebCore/platform/graphics/cairo/CairoOperations.cpp 2020-05-24 15:53:19 UTC (rev 262108)
@@ -78,7 +78,7 @@
} else {
// Solid color source
if (globalAlpha < 1)
- setSourceRGBAFromColor(cr, color.colorWithAlphaUsingAlternativeRounding(color.alpha() / 255.f * globalAlpha));
+ setSourceRGBAFromColor(cr, color.colorWithAlphaMultipliedByUsingAlternativeRounding(globalAlpha));
else
setSourceRGBAFromColor(cr, color);
}
@@ -1121,7 +1121,7 @@
// so as to be consistent with how we draw rectangular focus rings.
// Force the alpha to 50%. This matches what the Mac does with outline rings.
- Color ringColor = makeRGBA(color.red(), color.green(), color.blue(), 127);
+ Color ringColor = color.colorWithAlpha(.5);
cairo_t* cr = platformContext.cr();
cairo_save(cr);
Modified: trunk/Source/WebCore/platform/graphics/cpu/arm/filters/FELightingNEON.h (262107 => 262108)
--- trunk/Source/WebCore/platform/graphics/cpu/arm/filters/FELightingNEON.h 2020-05-24 15:34:44 UTC (rev 262107)
+++ trunk/Source/WebCore/platform/graphics/cpu/arm/filters/FELightingNEON.h 2020-05-24 15:53:19 UTC (rev 262108)
@@ -111,9 +111,11 @@
// Set light source arguments.
floatArguments.constOne = 1;
- floatArguments.colorRed = m_lightingColor.red();
- floatArguments.colorGreen = m_lightingColor.green();
- floatArguments.colorBlue = m_lightingColor.blue();
+ auto simpleColor = m_lightingColor.toSRGBASimpleColorLossy();
+
+ floatArguments.colorRed = simpleColor.redComponent();
+ floatArguments.colorGreen = simpleColor.greenComponent();
+ floatArguments.colorBlue = simpleColor.blueComponent();
floatArguments.padding4 = 0;
if (m_lightSource->type() == LS_POINT) {
Modified: trunk/Source/WebCore/platform/graphics/texmap/TextureMapperGL.cpp (262107 => 262108)
--- trunk/Source/WebCore/platform/graphics/texmap/TextureMapperGL.cpp 2020-05-24 15:34:44 UTC (rev 262107)
+++ trunk/Source/WebCore/platform/graphics/texmap/TextureMapperGL.cpp 2020-05-24 15:53:19 UTC (rev 262108)
@@ -686,7 +686,8 @@
void TextureMapperGL::clearColor(const Color& color)
{
- glClearColor(color.red() / 255.0f, color.green() / 255.0f, color.blue() / 255.0f, color.alpha() / 255.0f);
+ auto [r, g, b, a] = color.toSRGBAComponentsLossy();
+ glClearColor(r, g, b, a);
glClear(GL_COLOR_BUFFER_BIT);
}
Modified: trunk/Source/WebCore/platform/graphics/win/Direct2DOperations.cpp (262107 => 262108)
--- trunk/Source/WebCore/platform/graphics/win/Direct2DOperations.cpp 2020-05-24 15:34:44 UTC (rev 262107)
+++ trunk/Source/WebCore/platform/graphics/win/Direct2DOperations.cpp 2020-05-24 15:53:19 UTC (rev 262108)
@@ -780,7 +780,7 @@
// Paint simple shadows ourselves instead of relying on CG shadows, to avoid losing subpixel antialiasing.
graphicsContext.clearShadow();
Color fillColor = graphicsContext.fillColor();
- Color shadowFillColor(shadowColor.red(), shadowColor.green(), shadowColor.blue(), shadowColor.alpha() * fillColor.alpha() / 255);
+ Color shadowFillColor = shadowColor.colorWithAlphaMultipliedBy(fillColor.alphaAsFloat());
float shadowTextX = point.x() + shadowOffset.width();
// If shadows are ignoring transforms, then we haven't applied the Y coordinate flip yet, so down is negative.
float shadowTextY = point.y() + shadowOffset.height() * (graphicsContext.shadowsIgnoreTransforms() ? -1 : 1);
Modified: trunk/Source/WebCore/platform/graphics/win/FontCGWin.cpp (262107 => 262108)
--- trunk/Source/WebCore/platform/graphics/win/FontCGWin.cpp 2020-05-24 15:34:44 UTC (rev 262107)
+++ trunk/Source/WebCore/platform/graphics/win/FontCGWin.cpp 2020-05-24 15:53:19 UTC (rev 262108)
@@ -186,7 +186,7 @@
// Paint simple shadows ourselves instead of relying on CG shadows, to avoid losing subpixel antialiasing.
graphicsContext.clearShadow();
Color fillColor = graphicsContext.fillColor();
- Color shadowFillColor(shadowColor.red(), shadowColor.green(), shadowColor.blue(), shadowColor.alpha() * fillColor.alpha() / 255);
+ Color shadowFillColor = shadowColor.colorWithAlphaMultipliedBy(fillColor.alphaAsFloat());
graphicsContext.setFillColor(shadowFillColor);
float shadowTextX = point.x() + shadowOffset.width();
// If shadows are ignoring transforms, then we haven't applied the Y coordinate flip yet, so down is negative.
Modified: trunk/Source/WebCore/platform/graphics/win/FontCascadeDirect2D.cpp (262107 => 262108)
--- trunk/Source/WebCore/platform/graphics/win/FontCascadeDirect2D.cpp 2020-05-24 15:34:44 UTC (rev 262107)
+++ trunk/Source/WebCore/platform/graphics/win/FontCascadeDirect2D.cpp 2020-05-24 15:53:19 UTC (rev 262108)
@@ -121,7 +121,7 @@
// Paint simple shadows ourselves instead of relying on CG shadows, to avoid losing subpixel antialiasing.
graphicsContext.clearShadow();
Color fillColor = graphicsContext.fillColor();
- Color shadowFillColor(shadowColor.red(), shadowColor.green(), shadowColor.blue(), shadowColor.alpha() * fillColor.alpha() / 255);
+ Color shadowFillColor = shadowColor.colorWithAlphaMultipliedBy(fillColor.alphaAsFloat());
float shadowTextX = point.x() + shadowOffset.width();
// If shadows are ignoring transforms, then we haven't applied the Y coordinate flip yet, so down is negative.
float shadowTextY = point.y() + shadowOffset.height() * (graphicsContext.shadowsIgnoreTransforms() ? -1 : 1);
Modified: trunk/Source/WebCore/rendering/EllipsisBox.cpp (262107 => 262108)
--- trunk/Source/WebCore/rendering/EllipsisBox.cpp 2020-05-24 15:34:44 UTC (rev 262107)
+++ trunk/Source/WebCore/rendering/EllipsisBox.cpp 2020-05-24 15:53:19 UTC (rev 262108)
@@ -134,7 +134,7 @@
// If the text color ends up being the same as the selection background, invert the selection
// background.
if (textColor == c)
- c = Color(0xff - c.red(), 0xff - c.green(), 0xff - c.blue());
+ c = c.invertedColorWithAlpha(1.0);
const RootInlineBox& rootBox = root();
GraphicsContextStateSaver stateSaver(context);
Modified: trunk/Source/WebCore/rendering/InlineTextBox.cpp (262107 => 262108)
--- trunk/Source/WebCore/rendering/InlineTextBox.cpp 2020-05-24 15:34:44 UTC (rev 262107)
+++ trunk/Source/WebCore/rendering/InlineTextBox.cpp 2020-05-24 15:53:19 UTC (rev 262108)
@@ -854,7 +854,7 @@
Color selectionBackgroundColor = renderer().selectionBackgroundColor();
style.backgroundColor = selectionBackgroundColor;
if (selectionBackgroundColor.isValid() && selectionBackgroundColor.alpha() && style.textStyles.fillColor == selectionBackgroundColor)
- style.backgroundColor = { 0xff - selectionBackgroundColor.red(), 0xff - selectionBackgroundColor.green(), 0xff - selectionBackgroundColor.blue() };
+ style.backgroundColor = selectionBackgroundColor.invertedColorWithAlpha(1.0);
break;
}
case MarkedText::TextMatch: {
Modified: trunk/Source/WebCore/rendering/RenderBoxModelObject.cpp (262107 => 262108)
--- trunk/Source/WebCore/rendering/RenderBoxModelObject.cpp 2020-05-24 15:34:44 UTC (rev 262107)
+++ trunk/Source/WebCore/rendering/RenderBoxModelObject.cpp 2020-05-24 15:53:19 UTC (rev 262108)
@@ -2495,7 +2495,7 @@
continue;
}
- Color fillColor(shadowColor.red(), shadowColor.green(), shadowColor.blue(), 255);
+ Color fillColor = shadowColor.opaqueColor();
auto shadowCastingRect = areaCastingShadowInHole(borderRect.rect(), shadowPaintingExtent, shadowSpread, shadowOffset);
auto pixelSnappedOuterRect = snapRectToDevicePixels(shadowCastingRect, deviceScaleFactor);
Modified: trunk/Source/WebCore/rendering/RenderThemeIOS.mm (262107 => 262108)
--- trunk/Source/WebCore/rendering/RenderThemeIOS.mm 2020-05-24 15:34:44 UTC (rev 262107)
+++ trunk/Source/WebCore/rendering/RenderThemeIOS.mm 2020-05-24 15:53:19 UTC (rev 262108)
@@ -1554,7 +1554,7 @@
auto it = globalCSSValueToSystemColorMap().find(CSSValueKey { cssValueID, useDarkAppearance, useElevatedUserInterfaceLevel });
if (it == globalCSSValueToSystemColorMap().end())
return RenderTheme::systemColor(cssValueID, options);
- return Color(it->value.rgb(), Color::Semantic);
+ return it->value.semanticColor();
}
auto color = systemColorFromCSSValueID(cssValueID, useDarkAppearance, useElevatedUserInterfaceLevel);
if (color)
Modified: trunk/Source/WebCore/svg/properties/SVGAnimationAdditiveValueFunctionImpl.h (262107 => 262108)
--- trunk/Source/WebCore/svg/properties/SVGAnimationAdditiveValueFunctionImpl.h 2020-05-24 15:34:44 UTC (rev 262107)
+++ trunk/Source/WebCore/svg/properties/SVGAnimationAdditiveValueFunctionImpl.h 2020-05-24 15:53:19 UTC (rev 262108)
@@ -81,12 +81,15 @@
void animate(SVGElement*, float progress, unsigned repeatCount, Color& animated)
{
- Color from = m_animationMode == AnimationMode::To ? animated : m_from;
+ auto simpleAnimated = animated.toSRGBASimpleColorLossy();
+ auto simpleFrom = m_animationMode == AnimationMode::To ? simpleAnimated : m_from.toSRGBASimpleColorLossy();
+ auto simpleTo = m_to.toSRGBASimpleColorLossy();
+ auto simpleToAtEndOfDuration = toAtEndOfDuration().toSRGBASimpleColorLossy();
- float red = Base::animate(progress, repeatCount, from.red(), m_to.red(), toAtEndOfDuration().red(), animated.red());
- float green = Base::animate(progress, repeatCount, from.green(), m_to.green(), toAtEndOfDuration().green(), animated.green());
- float blue = Base::animate(progress, repeatCount, from.blue(), m_to.blue(), toAtEndOfDuration().blue(), animated.blue());
- float alpha = Base::animate(progress, repeatCount, from.alpha(), m_to.alpha(), toAtEndOfDuration().alpha(), animated.alpha());
+ float red = Base::animate(progress, repeatCount, simpleFrom.redComponent(), simpleTo.redComponent(), simpleToAtEndOfDuration.redComponent(), simpleAnimated.redComponent());
+ float green = Base::animate(progress, repeatCount, simpleFrom.greenComponent(), simpleTo.greenComponent(), simpleToAtEndOfDuration.greenComponent(), simpleAnimated.greenComponent());
+ float blue = Base::animate(progress, repeatCount, simpleFrom.blueComponent(), simpleTo.blueComponent(), simpleToAtEndOfDuration.blueComponent(), simpleAnimated.blueComponent());
+ float alpha = Base::animate(progress, repeatCount, simpleFrom.alphaComponent(), simpleTo.alphaComponent(), simpleToAtEndOfDuration.alphaComponent(), simpleAnimated.alphaComponent());
animated = { roundAndClampColorChannel(red), roundAndClampColorChannel(green), roundAndClampColorChannel(blue), roundAndClampColorChannel(alpha) };
}
@@ -99,9 +102,14 @@
Color toColor = CSSParser::parseColor(to.stripWhiteSpace());
if (!toColor.isValid())
return { };
- float red = fromColor.red() - toColor.red();
- float green = fromColor.green() - toColor.green();
- float blue = fromColor.blue() - toColor.blue();
+
+ auto simpleFrom = fromColor.toSRGBASimpleColorLossy();
+ auto simpleTo = toColor.toSRGBASimpleColorLossy();
+
+ float red = simpleFrom.redComponent() - simpleTo.redComponent();
+ float green = simpleFrom.greenComponent() - simpleTo.greenComponent();
+ float blue = simpleFrom.blueComponent() - simpleTo.blueComponent();
+
return std::hypot(red, green, blue);
}
@@ -108,11 +116,14 @@
private:
void addFromAndToValues(SVGElement*) override
{
+ auto simpleFrom = m_from.toSRGBASimpleColorLossy();
+ auto simpleTo = m_to.toSRGBASimpleColorLossy();
+
// Ignores any alpha and sets alpha on result to 100% opaque.
m_to = {
- roundAndClampColorChannel(m_to.red() + m_from.red()),
- roundAndClampColorChannel(m_to.green() + m_from.green()),
- roundAndClampColorChannel(m_to.blue() + m_from.blue())
+ roundAndClampColorChannel(simpleTo.redComponent() + simpleFrom.redComponent()),
+ roundAndClampColorChannel(simpleTo.greenComponent() + simpleFrom.greenComponent()),
+ roundAndClampColorChannel(simpleTo.blueComponent() + simpleFrom.blueComponent())
};
}
Modified: trunk/Source/WebKit/ChangeLog (262107 => 262108)
--- trunk/Source/WebKit/ChangeLog 2020-05-24 15:34:44 UTC (rev 262107)
+++ trunk/Source/WebKit/ChangeLog 2020-05-24 15:53:19 UTC (rev 262108)
@@ -1,3 +1,14 @@
+2020-05-24 Sam Weinig <[email protected]>
+
+ Extended Color Cleanup: Stop allowing direct access to the underlying SimpleColor (it is almost always incorrect with respect to extended colors)
+ https://bugs.webkit.org/show_bug.cgi?id=212184
+
+ Reviewed by Dean Jackson.
+
+ * WebProcess/WebPage/RemoteLayerTree/PlatformCAAnimationRemote.mm:
+ (WebKit::animationValueFromKeyframeValue):
+ Use toSRGBASimpleColorLossy() to get access to color components.
+
2020-05-24 Carlos Garcia Campos <[email protected]>
Unreviewed. Remove unused file since r261570
Modified: trunk/Source/WebKit/WebProcess/WebPage/RemoteLayerTree/PlatformCAAnimationRemote.mm (262107 => 262108)
--- trunk/Source/WebKit/WebProcess/WebPage/RemoteLayerTree/PlatformCAAnimationRemote.mm 2020-05-24 15:34:44 UTC (rev 262107)
+++ trunk/Source/WebKit/WebProcess/WebPage/RemoteLayerTree/PlatformCAAnimationRemote.mm 2020-05-24 15:53:19 UTC (rev 262108)
@@ -693,8 +693,8 @@
return @(keyframeValue.numberValue());
case PlatformCAAnimationRemote::KeyframeValue::ColorKeyType: {
- Color color = keyframeValue.colorValue();
- return @[ @(color.red()), @(color.green()), @(color.blue()), @(color.alpha()) ];
+ auto [r, g, b, a] = keyframeValue.colorValue().toSRGBASimpleColorLossy();
+ return @[ @(r), @(g), @(b), @(a) ];
}
case PlatformCAAnimationRemote::KeyframeValue::PointKeyType: {
Modified: trunk/Tools/ChangeLog (262107 => 262108)
--- trunk/Tools/ChangeLog 2020-05-24 15:34:44 UTC (rev 262107)
+++ trunk/Tools/ChangeLog 2020-05-24 15:53:19 UTC (rev 262108)
@@ -1,3 +1,14 @@
+2020-05-24 Sam Weinig <[email protected]>
+
+ Extended Color Cleanup: Stop allowing direct access to the underlying SimpleColor (it is almost always incorrect with respect to extended colors)
+ https://bugs.webkit.org/show_bug.cgi?id=212184
+
+ Reviewed by Dean Jackson.
+
+ * TestWebKitAPI/Tests/WebCore/ColorTests.cpp:
+ (TestWebKitAPI::TEST):
+ Use toSRGBASimpleColorLossy() to get access to color components.
+
2020-05-22 Alex Christensen <[email protected]>
Make download resume workaround forgiving of changes in CFNetwork
Modified: trunk/Tools/TestWebKitAPI/Tests/WebCore/ColorTests.cpp (262107 => 262108)
--- trunk/Tools/TestWebKitAPI/Tests/WebCore/ColorTests.cpp 2020-05-24 15:34:44 UTC (rev 262107)
+++ trunk/Tools/TestWebKitAPI/Tests/WebCore/ColorTests.cpp 2020-05-24 15:53:19 UTC (rev 262108)
@@ -182,26 +182,29 @@
validColor = Color(1, 2, 3, 4);
EXPECT_TRUE(validColor.isValid());
EXPECT_FALSE(validColor.isExtended());
- EXPECT_EQ(validColor.red(), 1);
- EXPECT_EQ(validColor.green(), 2);
- EXPECT_EQ(validColor.blue(), 3);
- EXPECT_EQ(validColor.alpha(), 4);
+ auto simpleValidColor = validColor.toSRGBASimpleColorLossy();
+ EXPECT_EQ(simpleValidColor.redComponent(), 1);
+ EXPECT_EQ(simpleValidColor.greenComponent(), 2);
+ EXPECT_EQ(simpleValidColor.blueComponent(), 3);
+ EXPECT_EQ(simpleValidColor.alphaComponent(), 4);
Color yetAnotherValidColor(WTFMove(validColor));
EXPECT_TRUE(yetAnotherValidColor.isValid());
EXPECT_FALSE(yetAnotherValidColor.isExtended());
- EXPECT_EQ(yetAnotherValidColor.red(), 1);
- EXPECT_EQ(yetAnotherValidColor.green(), 2);
- EXPECT_EQ(yetAnotherValidColor.blue(), 3);
- EXPECT_EQ(yetAnotherValidColor.alpha(), 4);
+ auto simpleYetAnotherValidColor = yetAnotherValidColor.toSRGBASimpleColorLossy();
+ EXPECT_EQ(simpleYetAnotherValidColor.redComponent(), 1);
+ EXPECT_EQ(simpleYetAnotherValidColor.greenComponent(), 2);
+ EXPECT_EQ(simpleYetAnotherValidColor.blueComponent(), 3);
+ EXPECT_EQ(simpleYetAnotherValidColor.alphaComponent(), 4);
otherValidColor = WTFMove(yetAnotherValidColor);
EXPECT_TRUE(otherValidColor.isValid());
EXPECT_FALSE(otherValidColor.isExtended());
- EXPECT_EQ(otherValidColor.red(), 1);
- EXPECT_EQ(otherValidColor.green(), 2);
- EXPECT_EQ(otherValidColor.blue(), 3);
- EXPECT_EQ(otherValidColor.alpha(), 4);
+ auto simpleOtherValidColor = otherValidColor.toSRGBASimpleColorLossy();
+ EXPECT_EQ(simpleOtherValidColor.redComponent(), 1);
+ EXPECT_EQ(simpleOtherValidColor.greenComponent(), 2);
+ EXPECT_EQ(simpleOtherValidColor.blueComponent(), 3);
+ EXPECT_EQ(simpleOtherValidColor.alphaComponent(), 4);
}
} // namespace TestWebKitAPI