diff options
author | Anthony Ramine <n.oxyde@gmail.com> | 2018-10-03 12:11:28 +0200 |
---|---|---|
committer | Anthony Ramine <n.oxyde@gmail.com> | 2018-10-05 00:35:39 +0200 |
commit | 62ea3c093a48362578b1f49d5a65270702015839 (patch) | |
tree | b1f4c4ce5ea3026126670cf725fdcaa652850395 /components/script/dom/canvasrenderingcontext2d.rs | |
parent | caa4d190af8bcd26df719e452b621952ae4dad0c (diff) | |
download | servo-62ea3c093a48362578b1f49d5a65270702015839.tar.gz servo-62ea3c093a48362578b1f49d5a65270702015839.zip |
Move canvas.putImageData checks to the DOM side
Diffstat (limited to 'components/script/dom/canvasrenderingcontext2d.rs')
-rw-r--r-- | components/script/dom/canvasrenderingcontext2d.rs | 71 |
1 files changed, 60 insertions, 11 deletions
diff --git a/components/script/dom/canvasrenderingcontext2d.rs b/components/script/dom/canvasrenderingcontext2d.rs index 2b364c3702d..3482c3d925a 100644 --- a/components/script/dom/canvasrenderingcontext2d.rs +++ b/components/script/dom/canvasrenderingcontext2d.rs @@ -1214,19 +1214,68 @@ impl CanvasRenderingContext2DMethods for CanvasRenderingContext2D { dirty_width: Finite<f64>, dirty_height: Finite<f64>, ) { - let data = imagedata.get_data_array(); - let offset = Vector2D::new(*dx, *dy); - let image_data_size = Size2D::new(imagedata.Width() as f64, imagedata.Height() as f64); + let imagedata_size = Size2D::new(imagedata.Width() as f64, imagedata.Height() as f64); + if imagedata_size.width <= 0. || imagedata_size.height <= 0. { + return; + } - let dirty_rect = Rect::new( - Point2D::new(*dirty_x, *dirty_y), - Size2D::new(*dirty_width, *dirty_height), - ); + let mut dirty_x = *dirty_x; + let mut dirty_y = *dirty_y; + let mut dirty_width = *dirty_width; + let mut dirty_height = *dirty_height; + + // Step 1. + // Done later. + + // Step 2. + // TODO: throw InvalidState if buffer is detached. + + // Step 3. + if dirty_width < 0. { + dirty_x += dirty_width; + dirty_width = -dirty_width; + } + if dirty_height < 0. { + dirty_y += dirty_height; + dirty_height = -dirty_height; + } + + // Step 4. + if dirty_x < 0. { + dirty_width += dirty_x; + dirty_x = 0.; + } + if dirty_y < 0. { + dirty_height += dirty_y; + dirty_y = 0.; + } + + // Step 5. + if dirty_x + dirty_width > imagedata_size.width { + dirty_width = imagedata_size.width - dirty_x; + } + if dirty_y + dirty_height > imagedata_size.height { + dirty_height = imagedata_size.height - dirty_y; + } + + // Step 6. + if dirty_width <= 0. || dirty_height <= 0. { + return; + } + + // FIXME(nox): There is no need to make a Vec<u8> of all the pixels + // if we didn't want to put the entire image. + let buffer = imagedata.get_data_array(); + + // Step 7. self.send_canvas_2d_msg(Canvas2dMsg::PutImageData( - data.into(), - offset, - image_data_size, - dirty_rect, + buffer.into(), + Vector2D::new(*dx, *dy), + imagedata_size, + Rect::new( + Point2D::new(dirty_x, dirty_y), + Size2D::new(dirty_width, dirty_height), + ), )); self.mark_as_dirty(); } |