Skip to content

Commit

Permalink
Handle overlapping gradient stops for linear gradients
Browse files Browse the repository at this point in the history
From `addColorStop(offset, color)`s spec:
If multiple stops are added at the same offset on a gradient, they must
be placed in the order added, with the first one closest to the start of
the gradient, and each subsequent one infinitesimally further along
towards the end point (in effect causing all but the first and last stop
added at each point to be ignored)

https://www.w3.org/html/test/results/2dcontext/annotated-spec/canvas.html#testrefs.2d.gradient.interpolate.overlapu
  • Loading branch information
pylbrecht committed Dec 17, 2019
1 parent 04e9523 commit 1cdcbb2
Showing 1 changed file with 10 additions and 3 deletions.
13 changes: 10 additions & 3 deletions components/canvas/raqote_backend.rs
Original file line number Diff line number Diff line change
Expand Up @@ -243,15 +243,19 @@ impl GenericDrawTarget for raqote::DrawTarget {
dt.get_data_mut().copy_from_slice(s);
raqote::DrawTarget::copy_surface(self, &dt, source.to_box2d(), destination);
}
// TODO(pylbrecht)
// unused code?
fn create_gradient_stops(
&self,
gradient_stops: Vec<GradientStop>,
_extend_mode: ExtendMode,
) -> GradientStops {
let stops = gradient_stops
let mut stops = gradient_stops
.into_iter()
.map(|item| item.as_raqote().clone())
.collect();
.collect::<Vec<raqote::GradientStop>>();
// https://www.w3.org/html/test/results/2dcontext/annotated-spec/canvas.html#testrefs.2d.gradient.interpolate.overlap
stops.sort_by(|a, b| a.position.partial_cmp(&b.position).unwrap());
GradientStops::Raqote(stops)
}
fn create_path_builder(&self) -> Box<dyn GenericPathBuilder> {
Expand Down Expand Up @@ -730,7 +734,10 @@ impl<'a> ToRaqoteSource<'a> for FillOrStrokeStyle {
rgba.blue,
))),
LinearGradient(style) => {
let stops = style.stops.into_iter().map(|s| s.to_raqote()).collect();
let mut stops: Vec<raqote::GradientStop> =
style.stops.into_iter().map(|s| s.to_raqote()).collect();
// https://www.w3.org/html/test/results/2dcontext/annotated-spec/canvas.html#testrefs.2d.gradient.interpolate.overlap
stops.sort_by(|a, b| a.position.partial_cmp(&b.position).unwrap());
let mut gradient = raqote::Gradient { stops };
let start = Point2D::new(style.x0 as f32, style.y0 as f32);
let end = Point2D::new(style.x1 as f32, style.y1 as f32);
Expand Down

0 comments on commit 1cdcbb2

Please sign in to comment.