mirror of
https://github.com/penpot/penpot.git
synced 2025-06-06 07:31:36 +02:00
♻️ Refactor how rebuild_tiles works
This commit is contained in:
parent
fef342b489
commit
caf13eb774
8 changed files with 63 additions and 15 deletions
|
@ -7,7 +7,7 @@ license-file = "../LICENSE"
|
|||
description = "Wasm-based canvas renderer for Penpot"
|
||||
|
||||
[features]
|
||||
default = ["profile"]
|
||||
default = []
|
||||
profile = ["profile-macros", "profile-raf"]
|
||||
profile-macros = []
|
||||
profile-raf = []
|
||||
|
|
|
@ -24,7 +24,7 @@ EMSDK_QUIET=1 . /usr/local/emsdk/emsdk_env.sh;
|
|||
|
||||
export EM_CACHE="/tmp/emsdk_cache";
|
||||
|
||||
_CARGO_PARAMS="";
|
||||
_CARGO_PARAMS="${@:2}";
|
||||
|
||||
if [ "$_BUILD_MODE" = "release" ]; then
|
||||
_CARGO_PARAMS="--release $_CARGO_PARAMS"
|
||||
|
|
|
@ -1 +0,0 @@
|
|||
pub const DEBUG_VISIBLE: u32 = 0x01;
|
|
@ -1,10 +1,10 @@
|
|||
use skia_safe as skia;
|
||||
|
||||
mod debug;
|
||||
#[cfg(target_arch = "wasm32")]
|
||||
mod emscripten;
|
||||
mod math;
|
||||
mod mem;
|
||||
mod options;
|
||||
mod performance;
|
||||
mod render;
|
||||
mod shapes;
|
||||
|
@ -140,7 +140,11 @@ pub extern "C" fn set_view(zoom: f32, x: f32, y: f32) {
|
|||
render_state.viewbox.set_all(zoom, x, y);
|
||||
if zoom_changed {
|
||||
with_state!(state, {
|
||||
if state.render_state.options.is_profile_rebuild_tiles() {
|
||||
state.rebuild_tiles();
|
||||
} else {
|
||||
state.rebuild_tiles_shallow();
|
||||
}
|
||||
});
|
||||
}
|
||||
});
|
||||
|
|
2
render-wasm/src/options.rs
Normal file
2
render-wasm/src/options.rs
Normal file
|
@ -0,0 +1,2 @@
|
|||
pub const DEBUG_VISIBLE: u32 = 0x01;
|
||||
pub const PROFILE_REBUILD_TILES: u32 = 0x02;
|
|
@ -4,8 +4,6 @@ use crate::uuid::Uuid;
|
|||
use std::collections::{HashMap, HashSet, VecDeque};
|
||||
|
||||
use crate::performance;
|
||||
#[cfg(target_arch = "wasm32")]
|
||||
use crate::run_script;
|
||||
use crate::view::Viewbox;
|
||||
use crate::wapi;
|
||||
|
||||
|
@ -154,7 +152,7 @@ impl RenderState {
|
|||
}
|
||||
|
||||
pub fn set_debug_flags(&mut self, debug: u32) {
|
||||
self.options.debug_flags = debug;
|
||||
self.options.flags = debug;
|
||||
}
|
||||
|
||||
pub fn set_dpr(&mut self, dpr: f32) {
|
||||
|
@ -640,6 +638,12 @@ impl RenderState {
|
|||
.to_string(),
|
||||
)?;
|
||||
|
||||
// If the shape is not in the tile set, then we update
|
||||
// it.
|
||||
if let None = self.tiles.get_tiles_of(node_id) {
|
||||
self.update_tile_for(element);
|
||||
}
|
||||
|
||||
if visited_children {
|
||||
if !visited_mask {
|
||||
match element.shape_type {
|
||||
|
@ -810,13 +814,13 @@ impl RenderState {
|
|||
Ok(())
|
||||
}
|
||||
|
||||
pub fn get_tiles_for_rect(&mut self, shape: &Shape) -> (i32, i32, i32, i32) {
|
||||
pub fn get_tiles_for_shape(&mut self, shape: &Shape) -> (i32, i32, i32, i32) {
|
||||
let tile_size = tiles::get_tile_size(self.viewbox);
|
||||
tiles::get_tiles_for_rect(shape.extrect(), tile_size)
|
||||
}
|
||||
|
||||
pub fn update_tile_for(&mut self, shape: &Shape) {
|
||||
let (rsx, rsy, rex, rey) = self.get_tiles_for_rect(shape);
|
||||
let (rsx, rsy, rex, rey) = self.get_tiles_for_shape(shape);
|
||||
let new_tiles: HashSet<(i32, i32)> = (rsx..=rex)
|
||||
.flat_map(|x| (rsy..=rey).map(move |y| (x, y)))
|
||||
.collect();
|
||||
|
@ -840,6 +844,36 @@ impl RenderState {
|
|||
}
|
||||
}
|
||||
|
||||
pub fn rebuild_tiles_shallow(
|
||||
&mut self,
|
||||
tree: &mut HashMap<Uuid, Shape>,
|
||||
modifiers: &HashMap<Uuid, Matrix>,
|
||||
structure: &HashMap<Uuid, Vec<StructureEntry>>,
|
||||
) {
|
||||
performance::begin_measure!("rebuild_tiles_shallow");
|
||||
self.tiles.invalidate();
|
||||
self.surfaces.remove_cached_tiles();
|
||||
let mut nodes = vec![Uuid::nil()];
|
||||
while let Some(shape_id) = nodes.pop() {
|
||||
if let Some(shape) = tree.get(&shape_id) {
|
||||
let mut shape = shape.clone();
|
||||
if shape_id != Uuid::nil() {
|
||||
if let Some(modifier) = modifiers.get(&shape_id) {
|
||||
shape.apply_transform(modifier);
|
||||
}
|
||||
self.update_tile_for(&shape);
|
||||
} else {
|
||||
// We only need to rebuild tiles from the first level.
|
||||
let children = modified_children_ids(&shape, structure.get(&shape.id));
|
||||
for child_id in children.iter() {
|
||||
nodes.push(*child_id);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
performance::end_measure!("rebuild_tiles_shallow");
|
||||
}
|
||||
|
||||
pub fn rebuild_tiles(
|
||||
&mut self,
|
||||
tree: &mut HashMap<Uuid, Shape>,
|
||||
|
|
|
@ -1,15 +1,15 @@
|
|||
use crate::debug;
|
||||
use crate::options;
|
||||
|
||||
#[derive(Debug, Copy, Clone, PartialEq)]
|
||||
pub struct RenderOptions {
|
||||
pub debug_flags: u32,
|
||||
pub flags: u32,
|
||||
pub dpr: Option<f32>,
|
||||
}
|
||||
|
||||
impl Default for RenderOptions {
|
||||
fn default() -> Self {
|
||||
Self {
|
||||
debug_flags: 0x00,
|
||||
flags: 0x00,
|
||||
dpr: None,
|
||||
}
|
||||
}
|
||||
|
@ -17,7 +17,11 @@ impl Default for RenderOptions {
|
|||
|
||||
impl RenderOptions {
|
||||
pub fn is_debug_visible(&self) -> bool {
|
||||
self.debug_flags & debug::DEBUG_VISIBLE == debug::DEBUG_VISIBLE
|
||||
self.flags & options::DEBUG_VISIBLE == options::DEBUG_VISIBLE
|
||||
}
|
||||
|
||||
pub fn is_profile_rebuild_tiles(&self) -> bool {
|
||||
self.flags & options::PROFILE_REBUILD_TILES == options::PROFILE_REBUILD_TILES
|
||||
}
|
||||
|
||||
pub fn dpr(&self) -> f32 {
|
||||
|
|
|
@ -73,7 +73,7 @@ impl<'a> State<'a> {
|
|||
pub fn delete_shape(&mut self, id: Uuid) {
|
||||
// We don't really do a self.shapes.remove so that redo/undo keep working
|
||||
if let Some(shape) = self.shapes.get(&id) {
|
||||
let (rsx, rsy, rex, rey) = self.render_state.get_tiles_for_rect(&shape);
|
||||
let (rsx, rsy, rex, rey) = self.render_state.get_tiles_for_shape(&shape);
|
||||
for x in rsx..=rex {
|
||||
for y in rsy..=rey {
|
||||
let tile = (x, y);
|
||||
|
@ -118,6 +118,11 @@ impl<'a> State<'a> {
|
|||
}
|
||||
}
|
||||
|
||||
pub fn rebuild_tiles_shallow(&mut self) {
|
||||
self.render_state
|
||||
.rebuild_tiles_shallow(&mut self.shapes, &self.modifiers, &self.structure);
|
||||
}
|
||||
|
||||
pub fn rebuild_tiles(&mut self) {
|
||||
self.render_state
|
||||
.rebuild_tiles(&mut self.shapes, &self.modifiers, &self.structure);
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue