Skip to content

Commit

Permalink
Add benchmark infrastructure
Browse files Browse the repository at this point in the history
  • Loading branch information
TrueDoctor committed Sep 14, 2024
1 parent ec71948 commit 06e00c6
Show file tree
Hide file tree
Showing 4 changed files with 125 additions and 16 deletions.
12 changes: 12 additions & 0 deletions libraries/path-bool/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -24,3 +24,15 @@ glob = "0.3"
svg = "0.13"
resvg = "0.28"
image = "0.24"

# Required dependencies
criterion = { version = "0.5", features = ["html_reports"]}

# Benchmarks
[[bench]]
name = "painted_dreams"
harness = false

[[bench]]
name = "path_segment_intersection"
harness = false
90 changes: 90 additions & 0 deletions libraries/path-bool/benches/painted_dreams.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,90 @@
use criterion::{black_box, criterion_group, criterion_main, Criterion};
use path_bool::*;

pub fn criterion_benchmark(c: &mut Criterion) {
let path_a = path_from_path_data("M0,340C161.737914,383.575765 107.564182,490.730587 273,476 C419,463 481.741198,514.692273 481.333333,768 C481.333333,768 -0,768 -0,768 C-0,768 0,340 0,340 Z ");
let path_b = path_from_path_data(
"M458.370270,572.165771C428.525848,486.720093 368.618805,467.485992 273,476 C107.564178,490.730591 161.737915,383.575775 0,340 C0,340 0,689 0,689 C56,700 106.513901,779.342590 188,694.666687 C306.607422,571.416260 372.033966,552.205139 458.370270,572.165771 Z",
);
c.bench_function("painted_dreams_diff", |b| {
b.iter(|| path_boolean(black_box(&path_a), FillRule::NonZero, black_box(&path_b), FillRule::NonZero, PathBooleanOperation::Difference))
});
}

criterion_group!(benches, criterion_benchmark);
criterion_main!(benches);

/*
[libraries/path-bool/src/intersection_path_segment.rs:84:2] seg0 = Cubic(
DVec2(
458.37027,
572.165771,
),
DVec2(
428.525848,
486.720093,
),
DVec2(
368.618805,
467.485992,
),
DVec2(
273.0,
476.0,
),
)
[libraries/path-bool/src/intersection_path_segment.rs:84:2] seg1 = Cubic(
DVec2(
273.0,
476.0,
),
DVec2(
419.0,
463.0,
),
DVec2(
481.741198,
514.692273,
),
DVec2(
481.333333,
768.0,
),
)
[libraries/path-bool/src/intersection_path_segment.rs:84:2] seg0 = Cubic(
DVec2(
273.0,
476.0,
),
DVec2(
107.564178,
490.730591,
),
DVec2(
161.737915,
383.575775,
),
DVec2(
0.0,
340.0,
),
)
[libraries/path-bool/src/intersection_path_segment.rs:84:2] seg1 = Cubic(
DVec2(
0.0,
340.0,
),
DVec2(
161.737914,
383.575765,
),
DVec2(
107.564182,
490.730587,
),
DVec2(
273.0,
476.0,
),
)
*/
37 changes: 23 additions & 14 deletions libraries/path-bool/src/intersection_path_segment.rs
Original file line number Diff line number Diff line change
Expand Up @@ -58,7 +58,7 @@ fn intersection_segments_overlap(seg0: &IntersectionSegment, seg1: &Intersection
}

pub fn segments_equal(seg0: &PathSegment, seg1: &PathSegment, point_epsilon: f64) -> bool {
let equal = match (*seg0, *seg1) {
match (*seg0, *seg1) {
(PathSegment::Line(start0, end0), PathSegment::Line(start1, end1)) => vectors_equal(start0, start1, point_epsilon) && vectors_equal(end0, end1, point_epsilon),
(PathSegment::Cubic(p00, p01, p02, p03), PathSegment::Cubic(p10, p11, p12, p13)) => {
vectors_equal(p00, p10, point_epsilon) && vectors_equal(p01, p11, point_epsilon) && vectors_equal(p02, p12, point_epsilon) && vectors_equal(p03, p13, point_epsilon)
Expand All @@ -76,16 +76,12 @@ pub fn segments_equal(seg0: &PathSegment, seg1: &PathSegment, point_epsilon: f64
vectors_equal(p01, p11, point_epsilon)
}
_ => false,
};
let start = sample_path_segment_at(seg0, 0.);
let end = sample_path_segment_at(seg0, 1.);
if (start.abs_diff_eq((1418., 0.).into(), 0.01) || end.abs_diff_eq((1418., 0.).into(), 0.01)) && (start.abs_diff_eq((969., 0.).into(), 0.01) || end.abs_diff_eq((969., 0.).into(), 0.01)) {
eprintln!("equal: {}, {:?}, {:?}", equal, seg0, seg1);
}
equal
}

pub fn path_segment_intersection(seg0: &PathSegment, seg1: &PathSegment, endpoints: bool, eps: &Epsilons) -> Vec<[f64; 2]> {
eprintln!("intersecting:");
dbg!(seg0, seg1);
// dbg!(&seg0, &seg1, endpoints);
if let (PathSegment::Line(start0, end0), PathSegment::Line(start1, end1)) = (seg0, seg1) {
if let Some(st) = line_segment_intersection([*start0, *end0], [*start1, *end1], eps.param) {
Expand All @@ -112,20 +108,23 @@ pub fn path_segment_intersection(seg0: &PathSegment, seg1: &PathSegment, endpoin
bounding_box: path_segment_bounding_box(seg1),
},
)];
let mut next_pairs = Vec::new();

let mut params = Vec::new();
let mut subdivided0 = Vec::new();
let mut subdivided1 = Vec::new();

while !pairs.is_empty() {
let mut next_pairs = Vec::new();
next_pairs.clear();

for (seg0, seg1) in pairs {
for (seg0, seg1) in pairs.iter() {
if segments_equal(&seg0.seg, &seg1.seg, eps.point) {
// TODO: move this outside of this loop?
continue; // TODO: what to do?
}

let is_linear0 = bounding_box_max_extent(&seg0.bounding_box) <= eps.linear;
let is_linear1 = bounding_box_max_extent(&seg1.bounding_box) <= eps.linear;
let is_linear0 = bounding_box_max_extent(&seg0.bounding_box) <= eps.linear || (seg1.end_param - seg1.start_param).abs() < eps.param;
let is_linear1 = bounding_box_max_extent(&seg1.bounding_box) <= eps.linear || (seg1.end_param - seg1.start_param).abs() < eps.param;

if is_linear0 && is_linear1 {
let line_segment0 = path_segment_to_line_segment(&seg0.seg);
Expand All @@ -134,8 +133,18 @@ pub fn path_segment_intersection(seg0: &PathSegment, seg1: &PathSegment, endpoin
params.push([lerp(seg0.start_param, seg0.end_param, st.0), lerp(seg1.start_param, seg1.end_param, st.1)]);
}
} else {
let subdivided0 = if is_linear0 { vec![seg0] } else { subdivide_intersection_segment(&seg0).to_vec() };
let subdivided1 = if is_linear1 { vec![seg1] } else { subdivide_intersection_segment(&seg1).to_vec() };
subdivided0.clear();
subdivided1.clear();
if is_linear0 {
subdivided0.push(seg0.clone())
} else {
subdivided0.extend_from_slice(&subdivide_intersection_segment(seg0))
};
if is_linear1 {
subdivided1.push(seg1.clone())
} else {
subdivided1.extend_from_slice(&subdivide_intersection_segment(seg1))
};

for seg0 in &subdivided0 {
for seg1 in &subdivided1 {
Expand All @@ -147,7 +156,7 @@ pub fn path_segment_intersection(seg0: &PathSegment, seg1: &PathSegment, endpoin
}
}

pairs = next_pairs;
std::mem::swap(&mut pairs, &mut next_pairs);
}

if !endpoints {
Expand Down
2 changes: 0 additions & 2 deletions libraries/path-bool/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -147,11 +147,9 @@ mod test {
#[test]
fn painted_dreams_2() {
let a = path_from_path_data("M0,340C161.737914,383.575765 107.564182,490.730587 273,476 C419,463 481.741198,514.692273 481.333333,768 C481.333333,768 -0,768 -0,768 C-0,768 0,340 0,340 Z ");
dbg!(&a);
let b = path_from_path_data(
"M458.370270,572.165771C428.525848,486.720093 368.618805,467.485992 273,476 C107.564178,490.730591 161.737915,383.575775 0,340 C0,340 0,689 0,689 C56,700 106.513901,779.342590 188,694.666687 C306.607422,571.416260 372.033966,552.205139 458.370270,572.165771 Z",
);
dbg!(&b);

let result = path_boolean(&a, FillRule::NonZero, &b, FillRule::NonZero, PathBooleanOperation::Difference).unwrap();

Expand Down

0 comments on commit 06e00c6

Please sign in to comment.