Bug 1217643 part 3: Represent parsed CSS -webkit-gradient(radial, ...) expressions internally as parsed versions of more modern syntax. r=heycam

This commit is contained in:
Daniel Holbert 2015-11-20 14:46:11 -08:00
parent 4d4cb99346
commit c471ba59f3
2 changed files with 35 additions and 6 deletions

View File

@ -6,7 +6,7 @@ default-preferences pref(layout.css.prefixes.webkit,true)
# (These just ensure that our approximate/do-something rendering does not
# change unexpectedly.)
fuzzy-if(cocoaWidget,3,3369) == webkit-gradient-approx-linear-1.html webkit-gradient-approx-linear-1-ref.html # bug 1225372
fails == webkit-gradient-approx-radial-1.html webkit-gradient-approx-radial-1-ref.html
== webkit-gradient-approx-radial-1.html webkit-gradient-approx-radial-1-ref.html
# Tests for -webkit-gradient(linear, ...)
== webkit-gradient-linear-1a.html webkit-gradient-linear-1-ref.html
@ -16,6 +16,6 @@ fails == webkit-gradient-approx-radial-1.html webkit-gradient-approx-radial-1-re
== webkit-gradient-linear-2.html webkit-gradient-linear-2-ref.html
# Tests for -webkit-gradient(radial, ...)
fails == webkit-gradient-radial-1a.html webkit-gradient-radial-1-ref.html
fails == webkit-gradient-radial-1b.html webkit-gradient-radial-1-ref.html
fails == webkit-gradient-radial-2.html webkit-gradient-radial-2-ref.html
== webkit-gradient-radial-1a.html webkit-gradient-radial-1-ref.html
== webkit-gradient-radial-1b.html webkit-gradient-radial-1-ref.html
== webkit-gradient-radial-2.html webkit-gradient-radial-2-ref.html

View File

@ -10384,9 +10384,38 @@ CSSParserImpl::FinalizeRadialWebkitGradient(nsCSSValueGradient* aGradient,
{
MOZ_ASSERT(aGradient->mIsRadial, "passed-in gradient must be radial");
aGradient->mBgPos = aFirstCenter;
// NOTE: -webkit-gradient(radial, ...) has *two arbitrary circles*, with the
// gradient stretching between the circles' edges. In contrast, the standard
// syntax (and hence our data structures) can only represent *one* circle,
// with the gradient going from its center to its edge. To bridge this gap
// in expressiveness, we'll just see which of our two circles is smaller, and
// we'll treat that circle as if it were zero-sized and located at the center
// of the larger circle. Then, we'll be able to use the same data structures
// that we use for the standard radial-gradient syntax.
if (aSecondRadius >= aFirstRadius) {
// Second circle is larger.
aGradient->mBgPos = aSecondCenter;
aGradient->mIsExplicitSize = true;
aGradient->GetRadiusX().SetFloatValue(aSecondRadius, eCSSUnit_Pixel);
return;
}
// XXXdholbert Do further positioning/sizing here.
// First circle is larger, so we'll have it be the outer circle.
aGradient->mBgPos = aFirstCenter;
aGradient->mIsExplicitSize = true;
aGradient->GetRadiusX().SetFloatValue(aFirstRadius, eCSSUnit_Pixel);
// For this to work properly (with the earlier color stops attached to the
// first circle), we need to also reverse the color-stop list, so that
// e.g. the author's "from" color is attached to the outer edge (the first
// circle), rather than attached to the center (the collapsed second circle).
std::reverse(aGradient->mStops.begin(), aGradient->mStops.end());
// And now invert the stop locations:
for (nsCSSValueGradientStop& colorStop : aGradient->mStops) {
float origLocation = colorStop.mLocation.GetPercentValue();
colorStop.mLocation.SetPercentValue(1.0f - origLocation);
}
}
bool