[svg] Rename gradient units type to object bounding box units

It turns out that "userSpaceOnUse | objectBoundingBox" can be specified
as the unit type for multiple elements, such as clips, masks, filters
etc. and is not specific to gradients.

The full list:
https://www.w3.org/TR/SVG11/coords.html#ObjectBoundingBoxUnits

Bug: skia:10842
Change-Id: I995d588862fb43b9f130f0455d7af8de47046af4
Reviewed-on: https://skia-review.googlesource.com/c/skia/+/330616
Reviewed-by: Florin Malita <fmalita@chromium.org>
Commit-Queue: Tyler Denniston <tdenniston@google.com>
This commit is contained in:
Tyler Denniston 2020-10-29 16:29:22 -04:00 committed by Skia Commit-Bot
parent d5e6368fff
commit 30e327e19e
9 changed files with 37 additions and 28 deletions

View File

@ -29,7 +29,7 @@ public:
bool parseIRI(SkSVGStringType*);
bool parseSpreadMethod(SkSVGSpreadMethod*);
bool parseStopColor(SkSVGStopColor*);
bool parseGradientUnits(SkSVGGradientUnits*);
bool parseObjectBoundingBoxUnits(SkSVGObjectBoundingBoxUnits*);
bool parseVisibility(SkSVGVisibility*);
bool parseDashArray(SkSVGDashArray*);
bool parsePreserveAspectRatio(SkSVGPreserveAspectRatio*);

View File

@ -23,7 +23,7 @@ public:
void setHref(const SkSVGStringType&);
void setGradientTransform(const SkSVGTransformType&);
void setSpreadMethod(const SkSVGSpreadMethod&);
void setGradientUnits(const SkSVGGradientUnits&);
void setGradientUnits(const SkSVGObjectBoundingBoxUnits&);
protected:
explicit SkSVGGradient(SkSVGTag t) : INHERITED(t) {}
@ -36,7 +36,8 @@ protected:
const SkColor*, const SkScalar*, int count,
SkTileMode, const SkMatrix& localMatrix) const = 0;
SkSVGGradientUnits fGradientUnits = SkSVGGradientUnits(SkSVGGradientUnits::Type::kObjectBoundingBox);
SkSVGObjectBoundingBoxUnits fGradientUnits =
SkSVGObjectBoundingBoxUnits(SkSVGObjectBoundingBoxUnits::Type::kObjectBoundingBox);
private:
using StopPositionArray = SkSTArray<2, SkScalar, true>;

View File

@ -308,20 +308,22 @@ private:
SkSVGColorType fColor;
};
class SkSVGGradientUnits {
class SkSVGObjectBoundingBoxUnits {
public:
enum class Type {
kUserSpaceOnUse,
kObjectBoundingBox,
};
SkSVGGradientUnits() : fType(Type::kUserSpaceOnUse) {}
explicit SkSVGGradientUnits(Type t) : fType(t) {}
SkSVGObjectBoundingBoxUnits() : fType(Type::kUserSpaceOnUse) {}
explicit SkSVGObjectBoundingBoxUnits(Type t) : fType(t) {}
bool operator==(const SkSVGGradientUnits& other) const {
bool operator==(const SkSVGObjectBoundingBoxUnits& other) const {
return fType == other.fType;
}
bool operator!=(const SkSVGGradientUnits& other) const { return !(*this == other); }
bool operator!=(const SkSVGObjectBoundingBoxUnits& other) const {
return !(*this == other);
}
Type type() const { return fType; }

View File

@ -26,11 +26,11 @@ public:
kFontSize,
kFontStyle,
kFontWeight,
kGradientUnits,
kLength,
kLineCap,
kLineJoin,
kNumber,
kObjectBoundingBoxUnits,
kPaint,
kPath,
kPoints,
@ -98,8 +98,6 @@ using SkSVGStringValue = SkSVGWrapperValue<SkSVGStringType , SkSVGValue:
using SkSVGSpreadMethodValue = SkSVGWrapperValue<SkSVGSpreadMethod ,
SkSVGValue::Type::kSpreadMethod>;
using SkSVGStopColorValue = SkSVGWrapperValue<SkSVGStopColor , SkSVGValue::Type::kStopColor >;
using SkSVGGradientUnitsValue= SkSVGWrapperValue<SkSVGGradientUnits,
SkSVGValue::Type::kGradientUnits>;
using SkSVGVisibilityValue = SkSVGWrapperValue<SkSVGVisibility , SkSVGValue::Type::kVisibility>;
using SkSVGDashArrayValue = SkSVGWrapperValue<SkSVGDashArray , SkSVGValue::Type::kDashArray >;
@ -109,7 +107,10 @@ using SkSVGFontStyleValue = SkSVGWrapperValue<SkSVGFontStyle , SkSVGValue:
using SkSVGFontWeightValue = SkSVGWrapperValue<SkSVGFontWeight , SkSVGValue::Type::kFontWeight>;
using SkSVGTextAnchorValue = SkSVGWrapperValue<SkSVGTextAnchor , SkSVGValue::Type::kTextAnchor>;
using SkSVGPreserveAspectRatioValue = SkSVGWrapperValue<SkSVGPreserveAspectRatio,
SkSVGValue::Type::kPreserveAspectRatio>;
using SkSVGPreserveAspectRatioValue = SkSVGWrapperValue<SkSVGPreserveAspectRatio,
SkSVGValue::Type::kPreserveAspectRatio>;
using SkSVGObjectBoundingBoxUnitsValue = SkSVGWrapperValue<SkSVGObjectBoundingBoxUnits,
SkSVGValue::Type::kObjectBoundingBoxUnits>;
#endif // SkSVGValue_DEFINED

View File

@ -597,14 +597,17 @@ bool SkSVGAttributeParser::parseStopColor(SkSVGStopColor* stopColor) {
return parsedValue && this->parseEOSToken();
}
// https://www.w3.org/TR/SVG11/pservers.html#LinearGradientElementGradientUnitsAttribute
bool SkSVGAttributeParser::parseGradientUnits(SkSVGGradientUnits* gradientUnits) {
// https://www.w3.org/TR/SVG11/coords.html#ObjectBoundingBoxUnits
bool SkSVGAttributeParser::parseObjectBoundingBoxUnits(
SkSVGObjectBoundingBoxUnits* objectBoundingBoxUnits) {
bool parsedValue = false;
if (this->parseExpectedStringToken("userSpaceOnUse")) {
*gradientUnits = SkSVGGradientUnits(SkSVGGradientUnits::Type::kUserSpaceOnUse);
*objectBoundingBoxUnits =
SkSVGObjectBoundingBoxUnits(SkSVGObjectBoundingBoxUnits::Type::kUserSpaceOnUse);
parsedValue = true;
} else if (this->parseExpectedStringToken("objectBoundingBox")) {
*gradientUnits = SkSVGGradientUnits(SkSVGGradientUnits::Type::kObjectBoundingBox);
*objectBoundingBoxUnits =
SkSVGObjectBoundingBoxUnits(SkSVGObjectBoundingBoxUnits::Type::kObjectBoundingBox);
parsedValue = true;
}
return parsedValue && this->parseEOSToken();

View File

@ -200,15 +200,16 @@ bool SetStopColorAttribute(const sk_sp<SkSVGNode>& node, SkSVGAttribute attr,
return true;
}
bool SetGradientUnitsAttribute(const sk_sp<SkSVGNode>& node, SkSVGAttribute attr,
const char* stringValue) {
SkSVGGradientUnits gradientUnits;
bool SetObjectBoundingBoxUnitsAttribute(const sk_sp<SkSVGNode>& node,
SkSVGAttribute attr,
const char* stringValue) {
SkSVGObjectBoundingBoxUnits objectBoundingBoxUnits;
SkSVGAttributeParser parser(stringValue);
if (!parser.parseGradientUnits(&gradientUnits)) {
if (!parser.parseObjectBoundingBoxUnits(&objectBoundingBoxUnits)) {
return false;
}
node->setAttribute(attr, SkSVGGradientUnitsValue(gradientUnits));
node->setAttribute(attr, SkSVGObjectBoundingBoxUnitsValue(objectBoundingBoxUnits));
return true;
}
@ -428,7 +429,8 @@ SortedDictionaryEntry<AttrParseInfo> gAttributeParseInfo[] = {
{ "fx" , { SkSVGAttribute::kFx , SetLengthAttribute }},
{ "fy" , { SkSVGAttribute::kFy , SetLengthAttribute }},
{ "gradientTransform" , { SkSVGAttribute::kGradientTransform, SetTransformAttribute }},
{ "gradientUnits" , { SkSVGAttribute::kGradientUnits , SetGradientUnitsAttribute}},
{ "gradientUnits" , { SkSVGAttribute::kGradientUnits ,
SetObjectBoundingBoxUnitsAttribute }},
{ "height" , { SkSVGAttribute::kHeight , SetLengthAttribute }},
{ "offset" , { SkSVGAttribute::kOffset , SetLengthAttribute }},
{ "opacity" , { SkSVGAttribute::kOpacity , SetNumberAttribute }},

View File

@ -23,7 +23,7 @@ void SkSVGGradient::setSpreadMethod(const SkSVGSpreadMethod& spread) {
fSpreadMethod = spread;
}
void SkSVGGradient::setGradientUnits(const SkSVGGradientUnits& gradientUnits) {
void SkSVGGradient::setGradientUnits(const SkSVGObjectBoundingBoxUnits& gradientUnits) {
fGradientUnits = gradientUnits;
}
@ -45,7 +45,7 @@ void SkSVGGradient::onSetAttribute(SkSVGAttribute attr, const SkSVGValue& v) {
}
break;
case SkSVGAttribute::kGradientUnits:
if (const auto* gradientUnits = v.as<SkSVGGradientUnitsValue>()) {
if (const auto* gradientUnits = v.as<SkSVGObjectBoundingBoxUnitsValue>()) {
this->setGradientUnits(*gradientUnits);
}
break;
@ -127,7 +127,7 @@ bool SkSVGGradient::onAsPaint(const SkSVGRenderContext& ctx, SkPaint* paint) con
const auto tileMode = static_cast<SkTileMode>(fSpreadMethod.type());
SkMatrix localMatrix = SkMatrix::I();
if (fGradientUnits.type() == SkSVGGradientUnits::Type::kObjectBoundingBox) {
if (fGradientUnits.type() == SkSVGObjectBoundingBoxUnits::Type::kObjectBoundingBox) {
SkASSERT(ctx.node());
const SkRect objBounds = ctx.node()->objectBoundingBox(ctx);
localMatrix.preTranslate(objBounds.fLeft, objBounds.fTop);

View File

@ -60,7 +60,7 @@ sk_sp<SkShader> SkSVGLinearGradient::onMakeShader(const SkSVGRenderContext& ctx,
int count, SkTileMode tm,
const SkMatrix& localMatrix) const {
const SkSVGLengthContext lctx =
fGradientUnits.type() == SkSVGGradientUnits::Type::kObjectBoundingBox
fGradientUnits.type() == SkSVGObjectBoundingBoxUnits::Type::kObjectBoundingBox
? SkSVGLengthContext({1, 1})
: ctx.lengthContext();

View File

@ -69,7 +69,7 @@ sk_sp<SkShader> SkSVGRadialGradient::onMakeShader(const SkSVGRenderContext& ctx,
int count, SkTileMode tm,
const SkMatrix& m) const {
const SkSVGLengthContext lctx =
fGradientUnits.type() == SkSVGGradientUnits::Type::kObjectBoundingBox
fGradientUnits.type() == SkSVGObjectBoundingBoxUnits::Type::kObjectBoundingBox
? SkSVGLengthContext({1, 1})
: ctx.lengthContext();