servo/pathfinder

Image::new is very slow

colorhook opened this issue · 5 comments

let start = std::time::Instant::now();
pixels.hash(&mut pixels_hasher);
let delta = std::time::Instant::now() - start;
println!("image pixels.hash cost: {}ms", delta.as_micros() as f32 / 1000.0);

In release version:

output:  image pixels.hash cost: 20.289ms
s3bk commented

That should probably be precomputed…

Follow the BitmapData definition in Web Standard, I maintain the pixels by TypeArray in Javascript.
I create Pattern by Vec dynamically each frame and call draw_subimage to draw Image.

I cannot precompute and cache the Image because the TypeArray would be changed in JavaScript

in CanvasRenderingContext2D put_image_data method, Image::new called also:

pub fn put_image_data<L>(&mut self, image_data: ImageData, dest_location: L)
                             where L: CanvasImageDestLocation {
    let origin = dest_location.origin();
    let size = dest_location.size().unwrap_or(image_data.size.to_f32());
    let pattern = Pattern::from_image(image_data.into_image());
    let paint_id = self.canvas.scene.push_paint(&Paint::from_pattern(pattern));
    let draw_path = DrawPath::new(Outline::from_rect(RectF::new(origin, size)), paint_id);
    self.canvas.scene.push_draw_path(draw_path);
}
s3bk commented

Creating an Image from data is expensive, there is nothing one can do about it apart from not doing it.
In the best case the image encoding matches the texture and the trans-coding can be skipped, but that is not implemented yet.

I use caching layer to avoid .drawImage() performance issues, thanks!