1 /* ADG - Automatic Drawing Generation
2 * Copyright (C) 2007-2021 Nicola Fontana <ntd at entidi.it>
4 * This library is free software; you can redistribute it and/or
5 * modify it under the terms of the GNU Lesser General Public
6 * License as published by the Free Software Foundation; either
7 * version 2 of the License, or (at your option) any later version.
9 * This library is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12 * Lesser General Public License for more details.
14 * You should have received a copy of the GNU Lesser General Public
15 * License along with this library; if not, write to the
16 * Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
17 * Boston, MA 02110-1301, USA.
27 _cpml_behavior_browsing(void)
30 CpmlPrimitive primitive
, primitive_copy
;
32 cpml_segment_from_cairo(&segment
, (cairo_path_t
*) adg_test_path());
34 cpml_primitive_from_segment(&primitive
, &segment
);
35 adg_assert_isapprox((primitive
.org
)->point
.x
, 0);
36 adg_assert_isapprox((primitive
.org
)->point
.y
, 1);
37 g_assert_cmpint((primitive
.data
)->header
.type
, ==, CPML_LINE
);
38 g_assert_true(cpml_primitive_next(&primitive
));
39 adg_assert_isapprox((primitive
.org
)->point
.x
, 3);
40 adg_assert_isapprox((primitive
.org
)->point
.y
, 1);
41 g_assert_cmpint((primitive
.data
)->header
.type
, ==, CPML_ARC
);
42 g_assert_true(cpml_primitive_next(&primitive
));
43 adg_assert_isapprox((primitive
.org
)->point
.x
, 6);
44 adg_assert_isapprox((primitive
.org
)->point
.y
, 7);
45 g_assert_cmpint((primitive
.data
)->header
.type
, ==, CPML_CURVE
);
46 g_assert_true(cpml_primitive_next(&primitive
));
47 adg_assert_isapprox((primitive
.org
)->point
.x
, -2);
48 adg_assert_isapprox((primitive
.org
)->point
.y
, 2);
49 g_assert_cmpint((primitive
.data
)->header
.type
, ==, CPML_CLOSE
);
50 g_assert_false(cpml_primitive_next(&primitive
));
52 cpml_primitive_reset(&primitive
);
53 g_assert_true(cpml_primitive_next(&primitive
));
54 cpml_primitive_reset(&primitive
);
55 cpml_primitive_reset(&primitive
);
56 g_assert_true(cpml_primitive_next(&primitive
));
57 g_assert_true(cpml_primitive_next(&primitive
));
58 g_assert_true(cpml_primitive_next(&primitive
));
59 g_assert_false(cpml_primitive_next(&primitive
));
61 cpml_primitive_copy(&primitive_copy
, &primitive
);
62 g_assert_false(cpml_primitive_next(&primitive_copy
));
63 cpml_primitive_reset(&primitive
);
64 g_assert_false(cpml_primitive_next(&primitive_copy
));
65 cpml_primitive_reset(&primitive_copy
);
66 g_assert_true(cpml_primitive_next(&primitive_copy
));
70 _cpml_sanity_type(gint i
)
74 cpml_primitive_type(NULL
);
77 g_test_trap_assert_failed();
83 _cpml_sanity_from_segment(gint i
)
85 CpmlPrimitive primitive
;
88 cpml_segment_from_cairo(&segment
, (cairo_path_t
*) adg_test_path());
92 cpml_primitive_from_segment(NULL
, &segment
);
95 cpml_primitive_from_segment(&primitive
, NULL
);
98 g_test_trap_assert_failed();
104 _cpml_sanity_copy(gint i
)
106 CpmlPrimitive primitive
;
109 cpml_segment_from_cairo(&segment
, (cairo_path_t
*) adg_test_path());
110 cpml_primitive_from_segment(&primitive
, &segment
);
114 cpml_primitive_copy(NULL
, &primitive
);
117 cpml_primitive_copy(&primitive
, NULL
);
120 g_test_trap_assert_failed();
126 _cpml_sanity_copy_data(gint i
)
128 CpmlPrimitive primitive
;
131 cpml_segment_from_cairo(&segment
, (cairo_path_t
*) adg_test_path());
132 cpml_primitive_from_segment(&primitive
, &segment
);
136 cpml_primitive_copy_data(NULL
, &primitive
);
139 cpml_primitive_copy_data(&primitive
, NULL
);
142 g_test_trap_assert_failed();
148 _cpml_sanity_get_n_points(gint i
)
152 cpml_primitive_get_n_points(NULL
);
155 g_test_trap_assert_failed();
161 _cpml_sanity_get_length(gint i
)
165 cpml_primitive_get_length(NULL
);
168 g_test_trap_assert_failed();
174 _cpml_sanity_put_extents(gint i
)
177 CpmlPrimitive primitive
;
180 cpml_segment_from_cairo(&segment
, (cairo_path_t
*) adg_test_path());
181 cpml_primitive_from_segment(&primitive
, &segment
);
185 cpml_primitive_put_extents(NULL
, &extents
);
188 cpml_primitive_put_extents(&primitive
, NULL
);
191 g_test_trap_assert_failed();
197 _cpml_sanity_put_pair_at(gint i
)
200 CpmlPrimitive primitive
;
203 cpml_segment_from_cairo(&segment
, (cairo_path_t
*) adg_test_path());
204 cpml_primitive_from_segment(&primitive
, &segment
);
208 cpml_primitive_put_pair_at(NULL
, 1, &pair
);
211 cpml_primitive_put_pair_at(&primitive
, 1, NULL
);
214 g_test_trap_assert_failed();
220 _cpml_sanity_put_vector_at(gint i
)
223 CpmlPrimitive primitive
;
226 cpml_segment_from_cairo(&segment
, (cairo_path_t
*) adg_test_path());
227 cpml_primitive_from_segment(&primitive
, &segment
);
231 cpml_primitive_put_vector_at(NULL
, 1, &vector
);
234 cpml_primitive_put_vector_at(&primitive
, 1, NULL
);
237 g_test_trap_assert_failed();
243 _cpml_sanity_get_closest_pos(gint i
)
246 CpmlPrimitive primitive
;
247 CpmlPair pair
= { 1, 1 };
249 cpml_segment_from_cairo(&segment
, (cairo_path_t
*) adg_test_path());
250 cpml_primitive_from_segment(&primitive
, &segment
);
254 cpml_primitive_get_closest_pos(NULL
, &pair
);
257 cpml_primitive_get_closest_pos(&primitive
, NULL
);
260 g_test_trap_assert_failed();
266 _cpml_sanity_set_point(gint i
)
269 CpmlPrimitive primitive
;
270 CpmlPair pair
= { 1, 1 };
272 cpml_segment_from_cairo(&segment
, (cairo_path_t
*) adg_test_path());
273 cpml_primitive_from_segment(&primitive
, &segment
);
277 cpml_primitive_set_point(NULL
, 1, &pair
);
280 cpml_primitive_set_point(&primitive
, 1, NULL
);
283 g_test_trap_assert_failed();
289 _cpml_sanity_put_point(gint i
)
292 CpmlPrimitive primitive
;
295 cpml_segment_from_cairo(&segment
, (cairo_path_t
*) adg_test_path());
296 cpml_primitive_from_segment(&primitive
, &segment
);
300 cpml_primitive_put_point(NULL
, 0, &pair
);
303 cpml_primitive_put_point(&primitive
, 0, NULL
);
306 g_test_trap_assert_failed();
312 _cpml_sanity_put_intersections(gint i
)
315 CpmlPrimitive primitive1
, primitive2
;
318 /* Set primitive1 to 1.1 and primitive 2 to 2.2,
319 * so there is an intersection point in (1, 1) */
320 cpml_segment_from_cairo(&segment
, (cairo_path_t
*) adg_test_path());
321 cpml_primitive_from_segment(&primitive1
, &segment
);
323 cpml_segment_next(&segment
);
324 cpml_primitive_from_segment(&primitive2
, &segment
);
325 cpml_primitive_next(&primitive2
);
329 cpml_primitive_put_intersections(NULL
, &primitive2
, 2, &pair
);
332 cpml_primitive_put_intersections(&primitive1
, NULL
, 2, &pair
);
335 cpml_primitive_put_intersections(&primitive1
, &primitive2
, 2, NULL
);
338 g_test_trap_assert_failed();
344 _cpml_sanity_put_intersections_with_segment(gint i
)
346 CpmlPrimitive primitive
;
350 /* Set primitive 1.1 and segment to 2
351 * so there is an intersection point in (1,1) */
352 cpml_segment_from_cairo(&segment
, (cairo_path_t
*) adg_test_path());
353 cpml_primitive_from_segment(&primitive
, &segment
);
355 cpml_segment_next(&segment
);
359 cpml_primitive_put_intersections_with_segment(NULL
, &segment
, 2, &pair
);
362 cpml_primitive_put_intersections_with_segment(&primitive
, NULL
, 2, &pair
);
365 cpml_primitive_put_intersections_with_segment(&primitive
, &segment
, 2, NULL
);
368 g_test_trap_assert_failed();
374 _cpml_sanity_join(gint i
)
377 CpmlPrimitive primitive
;
379 cpml_segment_from_cairo(&segment
, (cairo_path_t
*) adg_test_path());
380 cpml_primitive_from_segment(&primitive
, &segment
);
384 cpml_primitive_join(NULL
, &primitive
);
387 cpml_primitive_join(&primitive
, NULL
);
390 g_test_trap_assert_failed();
396 _cpml_sanity_offset(gint i
)
400 cpml_primitive_offset(NULL
, 1);
403 g_test_trap_assert_failed();
409 _cpml_sanity_dump(gint i
)
413 cpml_segment_dump(NULL
);
416 g_test_trap_assert_failed();
422 _cpml_sanity_to_cairo(gint i
)
425 CpmlPrimitive primitive
;
427 cpml_segment_from_cairo(&segment
, (cairo_path_t
*) adg_test_path());
428 cpml_primitive_from_segment(&primitive
, &segment
);
432 cpml_primitive_to_cairo(NULL
, adg_test_cairo_context());
435 cpml_primitive_to_cairo(&primitive
, NULL
);
438 g_test_trap_assert_failed();
444 _cpml_method_type(void)
447 CpmlPrimitive primitive
;
449 g_assert_true(cpml_segment_from_cairo(&segment
, (cairo_path_t
*) adg_test_path()));
451 cpml_primitive_from_segment(&primitive
, &segment
);
452 g_assert_cmpint(cpml_primitive_type(&primitive
), ==, CPML_LINE
);
454 cpml_primitive_next(&primitive
);
455 g_assert_cmpint(cpml_primitive_type(&primitive
), ==, CPML_ARC
);
457 cpml_primitive_next(&primitive
);
458 g_assert_cmpint(cpml_primitive_type(&primitive
), ==, CPML_CURVE
);
460 cpml_primitive_next(&primitive
);
461 g_assert_cmpint(cpml_primitive_type(&primitive
), ==, CPML_CLOSE
);
465 _cpml_method_from_segment(void)
468 CpmlPrimitive primitive
;
470 g_assert_true(cpml_segment_from_cairo(&segment
, (cairo_path_t
*) adg_test_path()));
472 cpml_primitive_from_segment(&primitive
, &segment
);
473 g_assert_nonnull(primitive
.segment
);
474 g_assert_nonnull(primitive
.org
);
475 g_assert_nonnull(primitive
.data
);
479 _cpml_method_copy(void)
482 CpmlPrimitive original
;
483 CpmlPrimitive primitive
= { NULL
, NULL
, NULL
};
485 cpml_segment_from_cairo(&segment
, (cairo_path_t
*) adg_test_path());
486 cpml_primitive_from_segment(&original
, &segment
);
488 g_assert_false(original
.segment
== primitive
.segment
);
489 g_assert_false(original
.org
== primitive
.org
);
490 g_assert_false(original
.data
== primitive
.data
);
492 cpml_primitive_copy(&primitive
, &original
);
494 g_assert_true(original
.segment
== primitive
.segment
);
495 g_assert_true(original
.org
== primitive
.org
);
496 g_assert_true(original
.data
== primitive
.data
);
500 _cpml_method_copy_data(void)
503 CpmlPrimitive original
, *primitive
;
506 cpml_segment_from_cairo(&segment
, (cairo_path_t
*) adg_test_path());
507 cpml_primitive_from_segment(&original
, &segment
);
509 /* Check incompatible primitives are not copied */
510 primitive
= cpml_primitive_deep_dup(&original
);
511 ++primitive
->data
[0].header
.length
;
512 g_assert_cmpint(cpml_primitive_copy_data(primitive
, &original
), ==, 0);
513 --primitive
->data
[0].header
.length
;
514 ++primitive
->data
[0].header
.type
;
515 g_assert_cmpint(cpml_primitive_copy_data(primitive
, &original
), ==, 0);
516 --primitive
->data
[0].header
.type
;
519 primitive
= cpml_primitive_deep_dup(&original
);
520 ++primitive
->org
->point
.x
;
521 ++primitive
->org
->point
.y
;
522 for (n
= 1; n
< primitive
->data
[0].header
.length
; ++n
) {
523 ++primitive
->data
[n
].point
.x
;
524 ++primitive
->data
[n
].point
.y
;
526 g_assert_cmpfloat(primitive
->org
->point
.x
, !=, original
.org
->point
.x
);
527 g_assert_cmpfloat(primitive
->org
->point
.y
, !=, original
.org
->point
.y
);
528 for (n
= 1; n
< primitive
->data
[0].header
.length
; ++n
) {
529 g_assert_cmpfloat(primitive
->data
[n
].point
.x
, !=, original
.data
[n
].point
.x
);
530 g_assert_cmpfloat(primitive
->data
[n
].point
.y
, !=, original
.data
[n
].point
.y
);
532 g_assert_cmpint(cpml_primitive_copy_data(primitive
, &original
), ==, 1);
533 adg_assert_isapprox(primitive
->org
->point
.x
, original
.org
->point
.x
);
534 adg_assert_isapprox(primitive
->org
->point
.y
, original
.org
->point
.y
);
535 for (n
= 1; n
< primitive
->data
[0].header
.length
; ++n
) {
536 adg_assert_isapprox(primitive
->data
[n
].point
.x
, original
.data
[n
].point
.x
);
537 adg_assert_isapprox(primitive
->data
[n
].point
.y
, original
.data
[n
].point
.y
);
540 } while (cpml_primitive_next(&original
));
544 _cpml_method_type_get_n_points(void)
548 n_points
= cpml_primitive_type_get_n_points(CPML_MOVE
);
549 g_assert_cmpuint(n_points
, ==, 0);
551 n_points
= cpml_primitive_type_get_n_points(CPML_LINE
);
552 g_assert_cmpuint(n_points
, ==, 2);
554 n_points
= cpml_primitive_type_get_n_points(CPML_ARC
);
555 g_assert_cmpuint(n_points
, ==, 3);
557 n_points
= cpml_primitive_type_get_n_points(CPML_CURVE
);
558 g_assert_cmpuint(n_points
, ==, 4);
560 n_points
= cpml_primitive_type_get_n_points(CPML_CLOSE
);
561 g_assert_cmpuint(n_points
, ==, 2);
565 _cpml_method_get_n_points(void)
568 CpmlPrimitive primitive
;
571 cpml_segment_from_cairo(&segment
, (cairo_path_t
*) adg_test_path());
574 cpml_primitive_from_segment(&primitive
, &segment
);
575 n_points
= cpml_primitive_get_n_points(&primitive
);
576 g_assert_cmpuint(n_points
, ==, 2);
579 cpml_primitive_next(&primitive
);
580 n_points
= cpml_primitive_get_n_points(&primitive
);
581 g_assert_cmpuint(n_points
, ==, 3);
584 cpml_primitive_next(&primitive
);
585 n_points
= cpml_primitive_get_n_points(&primitive
);
586 g_assert_cmpuint(n_points
, ==, 4);
588 /* Close: although the end point is not needed, the CPML API
589 * returns 2 points to treat this primitive as a CPML_LINE */
590 cpml_primitive_next(&primitive
);
591 n_points
= cpml_primitive_get_n_points(&primitive
);
592 g_assert_cmpuint(n_points
, ==, 2);
596 _cpml_method_get_length(void)
599 CpmlPrimitive primitive
;
601 cpml_segment_from_cairo(&segment
, (cairo_path_t
*) adg_test_path());
602 cpml_segment_next(&segment
);
603 cpml_primitive_from_segment(&primitive
, &segment
);
605 adg_assert_isapprox(cpml_primitive_get_length(&primitive
), 1);
607 cpml_primitive_next(&primitive
);
608 adg_assert_isapprox(cpml_primitive_get_length(&primitive
), 2);
612 _cpml_method_put_extents(void)
615 CpmlPrimitive primitive
;
618 cpml_segment_from_cairo(&segment
, (cairo_path_t
*) adg_test_path());
621 cpml_primitive_from_segment(&primitive
, &segment
);
622 cpml_primitive_put_extents(&primitive
, &extents
);
623 g_assert_true(extents
.is_defined
);
624 adg_assert_isapprox(extents
.org
.x
, 0);
625 adg_assert_isapprox(extents
.org
.y
, 1);
626 adg_assert_isapprox(extents
.size
.x
, 3);
627 adg_assert_isapprox(extents
.size
.y
, 0);
629 /* Arc: the extents are computed precisely... let's ensure
630 * at least all the 3 points are included */
631 cpml_primitive_next(&primitive
);
632 cpml_primitive_put_extents(&primitive
, &extents
);
633 g_assert_true(extents
.is_defined
);
634 g_assert_cmpfloat(extents
.org
.x
, <=, 3);
635 g_assert_cmpfloat(extents
.org
.y
, <=, 1);
636 g_assert_cmpfloat(extents
.size
.x
, >=, 3);
637 g_assert_cmpfloat(extents
.size
.y
, >=, 6);
639 /* Curve: actually the extents are computed by using the
640 * convex hull (hence the exact coordinates of the points) */
641 cpml_primitive_next(&primitive
);
642 cpml_primitive_put_extents(&primitive
, &extents
);
643 g_assert_true(extents
.is_defined
);
644 adg_assert_isapprox(extents
.org
.x
, -2);
645 adg_assert_isapprox(extents
.org
.y
, 2);
646 adg_assert_isapprox(extents
.size
.x
, 12);
647 adg_assert_isapprox(extents
.size
.y
, 9);
650 cpml_primitive_next(&primitive
);
651 cpml_primitive_put_extents(&primitive
, &extents
);
652 g_assert_true(extents
.is_defined
);
653 adg_assert_isapprox(extents
.org
.x
, -2);
654 adg_assert_isapprox(extents
.org
.y
, 1);
655 adg_assert_isapprox(extents
.size
.x
, 2);
656 adg_assert_isapprox(extents
.size
.y
, 1);
660 _cpml_method_put_pair_at(void)
663 CpmlPrimitive primitive
;
666 cpml_segment_from_cairo(&segment
, (cairo_path_t
*) adg_test_path());
669 cpml_primitive_from_segment(&primitive
, &segment
);
670 cpml_primitive_put_pair_at(&primitive
, 0, &pair
);
671 adg_assert_isapprox(pair
.x
, 0);
672 adg_assert_isapprox(pair
.y
, 1);
673 cpml_primitive_put_pair_at(&primitive
, 1, &pair
);
674 adg_assert_isapprox(pair
.x
, 3);
675 adg_assert_isapprox(pair
.y
, 1);
676 cpml_primitive_put_pair_at(&primitive
, 0.5, &pair
);
677 adg_assert_isapprox(pair
.x
, 1.5);
678 adg_assert_isapprox(pair
.y
, 1);
681 cpml_primitive_next(&primitive
);
682 cpml_primitive_put_pair_at(&primitive
, 0, &pair
);
683 adg_assert_isapprox(pair
.x
, 3);
684 adg_assert_isapprox(pair
.y
, 1);
685 cpml_primitive_put_pair_at(&primitive
, 1, &pair
);
686 adg_assert_isapprox(pair
.x
, 6);
687 adg_assert_isapprox(pair
.y
, 7);
688 cpml_primitive_put_pair_at(&primitive
, 0.5, &pair
);
689 adg_assert_isapprox(pair
.x
, 3.669);
690 adg_assert_isapprox(pair
.y
, 4.415);
693 cpml_primitive_next(&primitive
);
694 /* TODO: not yet implemented
695 * cpml_primitive_put_pair_at(&primitive, 0, &pair);
696 * adg_assert_isapprox(pair.x, 6);
697 * adg_assert_isapprox(pair.y, 7);
698 * cpml_primitive_put_pair_at(&primitive, 1, &pair);
699 * adg_assert_isapprox(pair.x, -2);
700 * adg_assert_isapprox(pair.y, 2);
701 * cpml_primitive_put_pair_at(&primitive, 0.5, &pair);
702 * adg_assert_isapprox(pair.x, 1);
703 * adg_assert_isapprox(pair.y, 1); */
706 cpml_primitive_next(&primitive
);
707 cpml_primitive_put_pair_at(&primitive
, 0, &pair
);
708 adg_assert_isapprox(pair
.x
, -2);
709 adg_assert_isapprox(pair
.y
, 2);
710 cpml_primitive_put_pair_at(&primitive
, 1, &pair
);
711 adg_assert_isapprox(pair
.x
, 0);
712 adg_assert_isapprox(pair
.y
, 1);
713 cpml_primitive_put_pair_at(&primitive
, 0.5, &pair
);
714 adg_assert_isapprox(pair
.x
, -1);
715 adg_assert_isapprox(pair
.y
, 1.5);
719 _cpml_method_put_vector_at(void)
722 CpmlPrimitive primitive
;
725 cpml_segment_from_cairo(&segment
, (cairo_path_t
*) adg_test_path());
728 cpml_primitive_from_segment(&primitive
, &segment
);
729 cpml_primitive_put_vector_at(&primitive
, 0, &vector
);
730 adg_assert_isapprox(vector
.x
, 3);
731 adg_assert_isapprox(vector
.y
, 0);
732 cpml_primitive_put_vector_at(&primitive
, 1, &vector
);
733 adg_assert_isapprox(vector
.x
, 3);
734 adg_assert_isapprox(vector
.y
, 0);
735 cpml_primitive_put_vector_at(&primitive
, 0.5, &vector
);
736 adg_assert_isapprox(vector
.x
, 3);
737 adg_assert_isapprox(vector
.y
, 0);
740 cpml_primitive_next(&primitive
);
741 cpml_primitive_put_vector_at(&primitive
, 0, &vector
);
742 adg_assert_isapprox(vector
.x
, -0.077);
743 adg_assert_isapprox(vector
.y
, 0.997);
744 cpml_primitive_put_vector_at(&primitive
, 1, &vector
);
745 adg_assert_isapprox(vector
.x
, 0.844);
746 adg_assert_isapprox(vector
.y
, 0.537);
747 cpml_primitive_put_vector_at(&primitive
, 0.5, &vector
);
748 adg_assert_isapprox(vector
.x
, 0.447);
749 adg_assert_isapprox(vector
.y
, 0.894);
752 cpml_primitive_next(&primitive
);
753 /* TODO: not yet implemented
754 * cpml_primitive_put_vector_at(&primitive, 0, &vector);
755 * adg_assert_isapprox(vector.x, 6);
756 * adg_assert_isapprox(vector.y, 7);
757 * cpml_primitive_put_vector_at(&primitive, 1, &vector);
758 * adg_assert_isapprox(vector.x, -2);
759 * adg_assert_isapprox(vector.y, 2);
760 * cpml_primitive_put_vector_at(&primitive, 0.5, &vector);
761 * adg_assert_isapprox(vector.x, 1);
762 * adg_assert_isapprox(vector.y, 1); */
765 cpml_primitive_next(&primitive
);
766 cpml_primitive_put_vector_at(&primitive
, 0, &vector
);
767 adg_assert_isapprox(vector
.x
, 2);
768 adg_assert_isapprox(vector
.y
, -1);
769 cpml_primitive_put_vector_at(&primitive
, 1, &vector
);
770 adg_assert_isapprox(vector
.x
, 2);
771 adg_assert_isapprox(vector
.y
, -1);
772 cpml_primitive_put_vector_at(&primitive
, 0.5, &vector
);
773 adg_assert_isapprox(vector
.x
, 2);
774 adg_assert_isapprox(vector
.y
, -1);
778 _cpml_method_get_closest_pos(void)
781 CpmlPrimitive primitive
;
784 cpml_segment_from_cairo(&segment
, (cairo_path_t
*) adg_test_path());
785 cpml_primitive_from_segment(&primitive
, &segment
);
788 pair
.x
= 0; pair
.y
= 1;
789 adg_assert_isapprox(cpml_primitive_get_closest_pos(&primitive
, &pair
), 0);
790 pair
.x
= 3; pair
.y
= 1;
791 adg_assert_isapprox(cpml_primitive_get_closest_pos(&primitive
, &pair
), 1);
792 pair
.x
= -1; pair
.y
= -1;
793 adg_assert_isapprox(cpml_primitive_get_closest_pos(&primitive
, &pair
), 0);
794 pair
.x
= 4; pair
.y
= 2;
795 adg_assert_isapprox(cpml_primitive_get_closest_pos(&primitive
, &pair
), 1);
796 pair
.x
= 1.5; pair
.y
= 0;
797 adg_assert_isapprox(cpml_primitive_get_closest_pos(&primitive
, &pair
), 0.5);
800 cpml_primitive_next(&primitive
);
801 /* TODO: not yet implemented
802 * pair.x = 3; pair.y = 1;
803 * adg_assert_isapprox(cpml_primitive_get_closest_pos(&primitive, &pair), 0);
804 * pair.x = 6; pair.y = 7;
805 * adg_assert_isapprox(cpml_primitive_get_closest_pos(&primitive, &pair), 1);
806 * pair.x = 0; pair.y = 0;
807 * adg_assert_isapprox(cpml_primitive_get_closest_pos(&primitive, &pair), 0);
808 * pair.x = 10; pair.y = 10;
809 * adg_assert_isapprox(cpml_primitive_get_closest_pos(&primitive, &pair), 1);
813 cpml_primitive_next(&primitive
);
814 /* TODO: not yet implemented
815 * pair.x = 6; pair.y = 7;
816 * adg_assert_isapprox(cpml_primitive_get_closest_pos(&primitive, &pair), 0);
817 * pair.x = -2; pair.y = 2;
818 * adg_assert_isapprox(cpml_primitive_get_closest_pos(&primitive, &pair), 1);
819 * pair.x = 10; pair.y = 10;
820 * adg_assert_isapprox(cpml_primitive_get_closest_pos(&primitive, &pair), 0);
821 * pair.x = 0; pair.y = 0;
822 * adg_assert_isapprox(cpml_primitive_get_closest_pos(&primitive, &pair), 1);
826 cpml_primitive_next(&primitive
);
827 pair
.x
= -2; pair
.y
= 2;
828 adg_assert_isapprox(cpml_primitive_get_closest_pos(&primitive
, &pair
), 0);
829 pair
.x
= 0; pair
.y
= 1;
830 adg_assert_isapprox(cpml_primitive_get_closest_pos(&primitive
, &pair
), 1);
831 pair
.x
= -3; pair
.y
= 3;
832 adg_assert_isapprox(cpml_primitive_get_closest_pos(&primitive
, &pair
), 0);
833 pair
.x
= 1; pair
.y
= 0;
834 adg_assert_isapprox(cpml_primitive_get_closest_pos(&primitive
, &pair
), 1);
835 pair
.x
= -1; pair
.y
= 1.5;
836 adg_assert_isapprox(cpml_primitive_get_closest_pos(&primitive
, &pair
), 0.5);
840 _cpml_method_set_point(void)
843 CpmlSegment original
, *segment
;
844 CpmlPrimitive primitive
;
845 CpmlPair pair
, pair2
;
848 /* Work on a copy to not modify the original path data */
849 cpml_segment_from_cairo(&original
, (cairo_path_t
*) adg_test_path());
850 data_size
= original
.num_data
* sizeof(cairo_path_data_t
);
851 segment
= cpml_segment_deep_dup(&original
);
854 cpml_primitive_from_segment(&primitive
, segment
);
856 equality
= memcmp(original
.data
, segment
->data
, data_size
);
857 g_assert_cmpint(equality
, ==, 0);
858 cpml_primitive_put_point(&primitive
, 0, &pair
);
860 cpml_primitive_set_point(&primitive
, 0, &pair
);
861 equality
= memcmp(original
.data
, segment
->data
, data_size
);
862 g_assert_cmpint(equality
, !=, 0);
864 cpml_primitive_set_point(&primitive
, 0, &pair
);
865 equality
= memcmp(original
.data
, segment
->data
, data_size
);
866 g_assert_cmpint(equality
, ==, 0);
867 cpml_primitive_put_point(&primitive
, 1, &pair
);
869 cpml_primitive_set_point(&primitive
, 1, &pair
);
870 equality
= memcmp(original
.data
, segment
->data
, data_size
);
871 g_assert_cmpint(equality
, !=, 0);
872 /* On a CPML_LINE primitives, -1 and 1 indices are equals */
873 cpml_primitive_put_point(&primitive
, -1, &pair2
);
874 adg_assert_isapprox(pair
.x
, pair2
.x
);
875 adg_assert_isapprox(pair
.y
, pair2
.y
);
876 memcpy(segment
->data
, original
.data
, data_size
);
877 equality
= memcmp(original
.data
, segment
->data
, data_size
);
878 g_assert_cmpint(equality
, ==, 0);
879 cpml_primitive_put_point(&primitive
, 2, &pair
);
882 /* This should be a NOP without segfaults */
883 cpml_primitive_set_point(&primitive
, 2, &pair
);
884 equality
= memcmp(original
.data
, segment
->data
, data_size
);
885 g_assert_cmpint(equality
, ==, 0);
887 /* From now on, memcpy() is assumed to force equality (as already
888 * proved by the previous assertions) and pair2 is used as a
889 * different-from-everything pair, that is setting pair2 on any
890 * point will break the equality between segment->data and
897 cpml_primitive_next(&primitive
);
899 cpml_primitive_set_point(&primitive
, 0, &pair2
);
900 equality
= memcmp(original
.data
, segment
->data
, data_size
);
901 g_assert_cmpint(equality
, !=, 0);
902 memcpy(segment
->data
, original
.data
, data_size
);
903 cpml_primitive_set_point(&primitive
, 1, &pair2
);
904 equality
= memcmp(original
.data
, segment
->data
, data_size
);
905 g_assert_cmpint(equality
, !=, 0);
906 memcpy(segment
->data
, original
.data
, data_size
);
907 cpml_primitive_set_point(&primitive
, 2, &pair2
);
908 equality
= memcmp(original
.data
, segment
->data
, data_size
);
909 g_assert_cmpint(equality
, !=, 0);
910 memcpy(segment
->data
, original
.data
, data_size
);
911 cpml_primitive_set_point(&primitive
, 3, &pair2
);
912 equality
= memcmp(original
.data
, segment
->data
, data_size
);
913 g_assert_cmpint(equality
, ==, 0);
916 cpml_primitive_next(&primitive
);
918 cpml_primitive_set_point(&primitive
, 0, &pair2
);
919 equality
= memcmp(original
.data
, segment
->data
, data_size
);
920 g_assert_cmpint(equality
, !=, 0);
921 memcpy(segment
->data
, original
.data
, data_size
);
922 cpml_primitive_set_point(&primitive
, 1, &pair2
);
923 equality
= memcmp(original
.data
, segment
->data
, data_size
);
924 g_assert_cmpint(equality
, !=, 0);
925 memcpy(segment
->data
, original
.data
, data_size
);
926 cpml_primitive_set_point(&primitive
, 2, &pair2
);
927 equality
= memcmp(original
.data
, segment
->data
, data_size
);
928 g_assert_cmpint(equality
, !=, 0);
929 memcpy(segment
->data
, original
.data
, data_size
);
930 cpml_primitive_set_point(&primitive
, 3, &pair2
);
931 equality
= memcmp(original
.data
, segment
->data
, data_size
);
932 g_assert_cmpint(equality
, !=, 0);
933 memcpy(segment
->data
, original
.data
, data_size
);
934 cpml_primitive_set_point(&primitive
, 4, &pair2
);
935 equality
= memcmp(original
.data
, segment
->data
, data_size
);
936 g_assert_cmpint(equality
, ==, 0);
939 cpml_primitive_next(&primitive
);
941 cpml_primitive_set_point(&primitive
, 0, &pair2
);
942 equality
= memcmp(original
.data
, segment
->data
, data_size
);
943 g_assert_cmpint(equality
, !=, 0);
944 memcpy(segment
->data
, original
.data
, data_size
);
945 cpml_primitive_set_point(&primitive
, 1, &pair2
);
946 equality
= memcmp(original
.data
, segment
->data
, data_size
);
947 g_assert_cmpint(equality
, !=, 0);
948 memcpy(segment
->data
, original
.data
, data_size
);
949 cpml_primitive_set_point(&primitive
, 2, &pair2
);
950 equality
= memcmp(original
.data
, segment
->data
, data_size
);
951 g_assert_cmpint(equality
, ==, 0);
957 _cpml_method_put_point(void)
960 CpmlPrimitive primitive
;
963 cpml_segment_from_cairo(&segment
, (cairo_path_t
*) adg_test_path());
966 cpml_primitive_from_segment(&primitive
, &segment
);
968 cpml_primitive_put_point(&primitive
, 0, &pair
);
969 adg_assert_isapprox(pair
.x
, 0);
970 adg_assert_isapprox(pair
.y
, 1);
971 cpml_primitive_put_point(&primitive
, 1, &pair
);
972 adg_assert_isapprox(pair
.x
, 3);
973 adg_assert_isapprox(pair
.y
, 1);
974 cpml_primitive_put_point(&primitive
, 2, &pair
);
975 adg_assert_isapprox(pair
.x
, 3);
976 adg_assert_isapprox(pair
.y
, 1);
977 /* The negative indices are checked only against CPML_LINE */
978 cpml_primitive_put_point(&primitive
, -1, &pair
);
979 adg_assert_isapprox(pair
.x
, 3);
980 adg_assert_isapprox(pair
.y
, 1);
981 cpml_primitive_put_point(&primitive
, -2, &pair
);
982 adg_assert_isapprox(pair
.x
, 0);
983 adg_assert_isapprox(pair
.y
, 1);
984 cpml_primitive_put_point(&primitive
, -3, &pair
);
985 adg_assert_isapprox(pair
.x
, 0);
986 adg_assert_isapprox(pair
.y
, 1);
989 cpml_primitive_next(&primitive
);
991 cpml_primitive_put_point(&primitive
, 0, &pair
);
992 adg_assert_isapprox(pair
.x
, 3);
993 adg_assert_isapprox(pair
.y
, 1);
994 cpml_primitive_put_point(&primitive
, 1, &pair
);
995 adg_assert_isapprox(pair
.x
, 4);
996 adg_assert_isapprox(pair
.y
, 5);
997 cpml_primitive_put_point(&primitive
, 2, &pair
);
998 adg_assert_isapprox(pair
.x
, 6);
999 adg_assert_isapprox(pair
.y
, 7);
1000 cpml_primitive_put_point(&primitive
, 3, &pair
);
1001 adg_assert_isapprox(pair
.x
, 6);
1002 adg_assert_isapprox(pair
.y
, 7);
1005 cpml_primitive_next(&primitive
);
1007 cpml_primitive_put_point(&primitive
, 0, &pair
);
1008 adg_assert_isapprox(pair
.x
, 6);
1009 adg_assert_isapprox(pair
.y
, 7);
1010 cpml_primitive_put_point(&primitive
, 1, &pair
);
1011 adg_assert_isapprox(pair
.x
, 8);
1012 adg_assert_isapprox(pair
.y
, 9);
1013 cpml_primitive_put_point(&primitive
, 2, &pair
);
1014 adg_assert_isapprox(pair
.x
, 10);
1015 adg_assert_isapprox(pair
.y
, 11);
1016 cpml_primitive_put_point(&primitive
, 3, &pair
);
1017 adg_assert_isapprox(pair
.x
, -2);
1018 adg_assert_isapprox(pair
.y
, 2);
1019 cpml_primitive_put_point(&primitive
, 4, &pair
);
1020 adg_assert_isapprox(pair
.x
, -2);
1021 adg_assert_isapprox(pair
.y
, 2);
1024 cpml_primitive_next(&primitive
);
1026 cpml_primitive_put_point(&primitive
, 0, &pair
);
1027 adg_assert_isapprox(pair
.x
, -2);
1028 adg_assert_isapprox(pair
.y
, 2);
1029 cpml_primitive_put_point(&primitive
, 1, &pair
);
1030 adg_assert_isapprox(pair
.x
, 0);
1031 adg_assert_isapprox(pair
.y
, 1);
1032 cpml_primitive_put_point(&primitive
, 2, &pair
);
1033 adg_assert_isapprox(pair
.x
, 0);
1034 adg_assert_isapprox(pair
.y
, 1);
1038 _cpml_method_put_intersections(void)
1040 CpmlSegment segment
;
1041 CpmlPrimitive primitive1
, primitive2
;
1044 /* Set primitive1 to 1.1 (first segment, first primitive) */
1045 cpml_segment_from_cairo(&segment
, (cairo_path_t
*) adg_test_path());
1046 cpml_primitive_from_segment(&primitive1
, &segment
);
1048 /* Set primitive2 to 2.1 (second segment, first primitive) */
1049 cpml_segment_next(&segment
);
1050 cpml_primitive_from_segment(&primitive2
, &segment
);
1052 /* primitive1 (1.1) does not intersect primitive2 (2.1) */
1053 g_assert_cmpuint(cpml_primitive_put_intersections(&primitive1
, &primitive2
, 2, pair
), ==, 0);
1055 cpml_primitive_next(&primitive2
);
1057 /* primitive1 (1.1) intersects primitive2 (2.2) in (1, 1) */
1058 g_assert_cmpuint(cpml_primitive_put_intersections(&primitive1
, &primitive2
, 2, pair
), ==, 1);
1059 adg_assert_isapprox(pair
[0].x
, 1);
1060 adg_assert_isapprox(pair
[0].y
, 1);
1061 g_assert_cmpint(cpml_primitive_is_inside(&primitive1
, pair
), ==, 1);
1062 g_assert_cmpint(cpml_primitive_is_inside(&primitive2
, pair
), ==, 1);
1064 /* Check the intersection is not returned when not requested */
1065 g_assert_cmpuint(cpml_primitive_put_intersections(&primitive1
, &primitive2
, 0, pair
), ==, 0);
1067 cpml_primitive_next(&primitive1
);
1069 /* primitive1 (1.2) does not intersect primitive2 (2.2) */
1070 // TODO: g_assert_cmpuint(cpml_primitive_put_intersections(&primitive1, &primitive2, 2, pair), ==, 0);
1072 cpml_primitive_next(&primitive1
);
1074 /* primitive1 (1.3) does not intersect primitive2 (2.2) */
1075 g_assert_cmpuint(cpml_primitive_put_intersections(&primitive1
, &primitive2
, 2, pair
), ==, 0);
1077 cpml_primitive_next(&primitive1
);
1079 /* primitive1 (1.4) intersects primitive2 (2.2), but outside their boundaries */
1080 g_assert_cmpuint(cpml_primitive_put_intersections(&primitive1
, &primitive2
, 2, pair
), ==, 1);
1081 adg_assert_isapprox(pair
[0].x
, 1);
1082 adg_assert_isapprox(pair
[0].y
, -1);
1083 g_assert_cmpint(cpml_primitive_is_inside(&primitive1
, pair
), ==, 0);
1084 g_assert_cmpint(cpml_primitive_is_inside(&primitive2
, pair
), ==, 0);
1088 _cpml_method_put_intersections_circle_line(void)
1093 /* Line (-4, 4) .. (4, 4) */
1094 cairo_path_data_t line_data
[] = {
1095 { .header
= { CPML_MOVE
, 2 }},
1096 { .point
= { -4, 4 }},
1098 { .header
= { CPML_LINE
, 2 }},
1099 { .point
= { 4, 4 }}
1101 CpmlPrimitive line
= {
1107 /* Arc PI .. -PI of radius 3 in (0, 0) */
1108 cairo_path_data_t arc_data
[] = {
1109 { .header
= { CPML_MOVE
, 2 }},
1110 { .point
= { 0, 3 }},
1112 { .header
= { CPML_ARC
, 3 }},
1113 { .point
= { 3, 0 }},
1114 { .point
= { 0, -3 }}
1116 CpmlPrimitive arc
= {
1122 /* Intersection between arc and line (-4, 4) .. (4, 4) */
1123 g_assert_cmpuint(cpml_primitive_put_intersections(&arc
, &line
, 2, pair
), ==, 0);
1124 g_assert_cmpuint(cpml_primitive_put_intersections(&line
, &arc
, 2, pair
), ==, 0);
1126 /* Intersection between arc and line (-4, 0) .. (4, 0) */
1127 line_data
[1].point
.y
= line_data
[3].point
.y
= 0;
1129 g_assert_cmpuint(cpml_primitive_put_intersections(&arc
, &line
, 2, pair
), ==, 2);
1130 adg_assert_isapprox(pair
[0].x
, 3);
1131 adg_assert_isapprox(pair
[0].y
, 0);
1132 adg_assert_isapprox(pair
[1].x
, -3);
1133 adg_assert_isapprox(pair
[1].y
, 0);
1135 g_assert_cmpuint(cpml_primitive_put_intersections(&line
, &arc
, 2, pair
), ==, 2);
1136 adg_assert_isapprox(pair
[0].x
, 3);
1137 adg_assert_isapprox(pair
[0].y
, 0);
1138 adg_assert_isapprox(pair
[1].x
, -3);
1139 adg_assert_isapprox(pair
[1].y
, 0);
1141 /* Intersection between arc and line (4, 1) .. (4, 1) */
1142 line_data
[1].point
.y
= line_data
[3].point
.y
= 1;
1144 g_assert_cmpuint(cpml_primitive_put_intersections(&line
, &arc
, 2, pair
), ==, 2);
1145 adg_assert_isapprox(pair
[0].x
, 2.82842712);
1146 adg_assert_isapprox(pair
[0].y
, 1);
1147 adg_assert_isapprox(pair
[1].x
, -2.82842712);
1148 adg_assert_isapprox(pair
[1].y
, 1);
1150 /* Intersection between arc and line (0, -4) .. (0, 4) */
1151 line_data
[1].point
.y
= -4;
1152 line_data
[3].point
.y
= 4;
1153 line_data
[1].point
.x
= line_data
[3].point
.x
= 0;
1155 g_assert_cmpuint(cpml_primitive_put_intersections(&arc
, &line
, 2, pair
), ==, 2);
1156 adg_assert_isapprox(pair
[0].x
, 0);
1157 adg_assert_isapprox(pair
[0].y
, 3);
1158 adg_assert_isapprox(pair
[1].x
, 0);
1159 adg_assert_isapprox(pair
[1].y
, -3);
1161 /* Intersection between arc and line (1, -4) .. (1, 4) */
1162 line_data
[1].point
.x
= line_data
[3].point
.x
= 1;
1164 g_assert_cmpuint(cpml_primitive_put_intersections(&line
, &arc
, 2, pair
), ==, 2);
1165 adg_assert_isapprox(pair
[0].x
, 1);
1166 adg_assert_isapprox(pair
[0].y
, 2.82842712);
1167 adg_assert_isapprox(pair
[1].x
, 1);
1168 adg_assert_isapprox(pair
[1].y
, -2.82842712);
1170 /* Intersection between arc and line (-3, -4) .. (-3, 4) */
1171 line_data
[1].point
.x
= line_data
[3].point
.x
= -3;
1173 g_assert_cmpuint(cpml_primitive_put_intersections(&arc
, &line
, 2, pair
), ==, 1);
1174 adg_assert_isapprox(pair
[0].x
, -3);
1175 adg_assert_isapprox(pair
[0].y
, 0);
1177 /* Intersection between arc and line (3, -4) .. (3, 4) */
1178 line_data
[1].point
.x
= line_data
[3].point
.x
= 3;
1180 g_assert_cmpuint(cpml_primitive_put_intersections(&line
, &arc
, 2, pair
), ==, 1);
1181 adg_assert_isapprox(pair
[0].x
, 3);
1182 adg_assert_isapprox(pair
[0].y
, 0);
1184 /* Intersection between arc and line (-4, -3) .. (4, -3) */
1185 line_data
[1].point
.x
= -4;
1186 line_data
[3].point
.x
= 4;
1187 line_data
[1].point
.y
= line_data
[3].point
.y
= -3;
1189 g_assert_cmpuint(cpml_primitive_put_intersections(&arc
, &line
, 2, pair
), ==, 1);
1190 adg_assert_isapprox(pair
[0].x
, 0);
1191 adg_assert_isapprox(pair
[0].y
, -3);
1193 /* Intersection between arc and line (-4, 3) .. (4, 3) */
1194 line_data
[1].point
.y
= line_data
[3].point
.y
= 3;
1196 g_assert_cmpuint(cpml_primitive_put_intersections(&arc
, &line
, 2, pair
), ==, 1);
1197 adg_assert_isapprox(pair
[0].x
, 0);
1198 adg_assert_isapprox(pair
[0].y
, 3);
1200 /* Intersection between arc and line (-4, 1) .. (3, 3) */
1201 line_data
[1].point
.x
= -4;
1202 line_data
[1].point
.y
= -1;
1203 line_data
[3].point
.x
= line_data
[3].point
.y
= 3;
1205 g_assert_cmpuint(cpml_primitive_put_intersections(&arc
, &line
, 2, pair
), ==, 2);
1206 adg_assert_isapprox(pair
[0].x
, 1.86384016);
1207 adg_assert_isapprox(pair
[0].y
, 2.3507658);
1208 adg_assert_isapprox(pair
[1].x
, -2.97153247);
1209 adg_assert_isapprox(pair
[1].y
, -0.412304266);
1211 /* Translate the original primitives by (+10, +20) and check that the
1212 * intersections translate of the same amount too */
1213 line_data
[1].point
.x
+= 10;
1214 line_data
[3].point
.x
+= 10;
1215 arc_data
[1].point
.x
+= 10;
1216 arc_data
[3].point
.x
+= 10;
1217 arc_data
[4].point
.x
+= 10;
1218 line_data
[1].point
.y
+= 20;
1219 line_data
[3].point
.y
+= 20;
1220 arc_data
[1].point
.y
+= 20;
1221 arc_data
[3].point
.y
+= 20;
1222 arc_data
[4].point
.y
+= 20;
1224 g_assert_cmpuint(cpml_primitive_put_intersections(&arc
, &line
, 2, pair
), ==, 2);
1225 adg_assert_isapprox(pair
[0].x
, 11.86384016);
1226 adg_assert_isapprox(pair
[0].y
, 22.3507658);
1227 adg_assert_isapprox(pair
[1].x
, 7.02846753);
1228 adg_assert_isapprox(pair
[1].y
, 19.587695734);
1232 _cpml_method_put_intersections_with_segment(void)
1234 CpmlSegment segment1
, segment2
;
1235 CpmlPrimitive primitive
;
1238 /* Initialize segment1 and segment2 */
1239 cpml_segment_from_cairo(&segment1
, (cairo_path_t
*) adg_test_path());
1240 cpml_segment_from_cairo(&segment2
, (cairo_path_t
*) adg_test_path());
1241 cpml_segment_next(&segment2
);
1243 /* primitive 1 segment1 intersects segment2 in (1, 1) */
1244 cpml_primitive_from_segment(&primitive
, &segment1
);
1245 g_assert_cmpuint(cpml_primitive_put_intersections_with_segment(&primitive
, &segment2
, 4, pair
), ==, 1);
1246 adg_assert_isapprox(pair
[0].x
, 1);
1247 adg_assert_isapprox(pair
[0].y
, 1);
1249 /* primitive 2 segment1 does not intersect segment2 */
1250 cpml_primitive_next(&primitive
);
1251 g_assert_cmpuint(cpml_primitive_put_intersections_with_segment(&primitive
, &segment2
, 4, pair
), ==, 0);
1253 /* primitive 1 segment2 does not intersect segment1 */
1254 cpml_primitive_from_segment(&primitive
, &segment2
);
1255 g_assert_cmpuint(cpml_primitive_put_intersections_with_segment(&primitive
, &segment1
, 4, pair
), ==, 0);
1257 /* primitive 2 segment2 intersects segment1 in (1, 1) */
1258 cpml_primitive_next(&primitive
);
1259 g_assert_cmpuint(cpml_primitive_put_intersections_with_segment(&primitive
, &segment1
, 4, pair
), ==, 1);
1260 adg_assert_isapprox(pair
[0].x
, 1);
1261 adg_assert_isapprox(pair
[0].y
, 1);
1265 _cpml_method_offset(void)
1267 CpmlSegment original
, *segment
;
1268 CpmlPrimitive primitive
, line
, curve
;
1269 CpmlPrimitive
*backup
;
1271 /* Work on a copy to avoid modifying the original cairo path */
1272 cpml_segment_from_cairo(&original
, (cairo_path_t
*) adg_test_path());
1273 segment
= cpml_segment_deep_dup(&original
);
1274 cpml_primitive_from_segment(&primitive
, segment
);
1276 /* Offsetting and de-offsetting can introduce rounding errors
1277 * so we use adg_assert_isapprox instead of g_assert_cmpfloat */
1280 cpml_primitive_copy(&line
, &primitive
);
1281 cpml_primitive_offset(&primitive
, 1);
1282 adg_assert_isapprox((primitive
.org
)->point
.x
, 0);
1283 adg_assert_isapprox((primitive
.org
)->point
.y
, 2);
1284 adg_assert_isapprox(primitive
.data
[1].point
.x
, 3);
1285 adg_assert_isapprox(primitive
.data
[1].point
.y
, 2);
1286 cpml_primitive_offset(&primitive
, -1);
1287 adg_assert_isapprox((primitive
.org
)->point
.x
, 0);
1288 adg_assert_isapprox((primitive
.org
)->point
.y
, 1);
1289 adg_assert_isapprox(primitive
.data
[1].point
.x
, 3);
1290 adg_assert_isapprox(primitive
.data
[1].point
.y
, 1);
1293 cpml_primitive_next(&primitive
);
1294 cpml_primitive_offset(&primitive
, 1);
1295 adg_assert_isapprox((primitive
.org
)->point
.x
, 2.003);
1296 adg_assert_isapprox((primitive
.org
)->point
.y
, 0.923);
1297 adg_assert_isapprox(primitive
.data
[1].point
.x
, 3.156);
1298 adg_assert_isapprox(primitive
.data
[1].point
.y
, 5.537);
1299 adg_assert_isapprox(primitive
.data
[2].point
.x
, 5.463);
1300 adg_assert_isapprox(primitive
.data
[2].point
.y
, 7.844);
1301 cpml_primitive_offset(&primitive
, -1);
1302 adg_assert_isapprox((primitive
.org
)->point
.x
, 3);
1303 adg_assert_isapprox((primitive
.org
)->point
.y
, 1);
1304 adg_assert_isapprox(primitive
.data
[1].point
.x
, 4);
1305 adg_assert_isapprox(primitive
.data
[1].point
.y
, 5);
1306 adg_assert_isapprox(primitive
.data
[2].point
.x
, 6);
1307 adg_assert_isapprox(primitive
.data
[2].point
.y
, 7);
1310 cpml_primitive_next(&primitive
);
1311 cpml_primitive_copy(&curve
, &primitive
);
1312 /* The offset algorithm for curves is an approximation, so
1313 * offsetting +1 and -1 does not return the original curve.
1314 * Keeping a backup around to restore the original data.
1316 backup
= cpml_primitive_deep_dup(&curve
);
1317 /* Testing different algorithms */
1318 cpml_curve_offset_algorithm(CPML_CURVE_OFFSET_ALGORITHM_GEOMETRICAL
);
1319 cpml_primitive_offset(&primitive
, 1);
1320 adg_assert_isapprox((primitive
.org
)->point
.x
, 5.293);
1321 adg_assert_isapprox((primitive
.org
)->point
.y
, 7.707);
1322 adg_assert_isapprox(primitive
.data
[1].point
.x
, 7.889);
1323 adg_assert_isapprox(primitive
.data
[1].point
.y
, 8.515);
1324 adg_assert_isapprox(primitive
.data
[2].point
.x
, 11.196);
1325 adg_assert_isapprox(primitive
.data
[2].point
.y
, 9.007);
1326 adg_assert_isapprox(primitive
.data
[3].point
.x
, -1.4);
1327 adg_assert_isapprox(primitive
.data
[3].point
.y
, 1.2);
1328 cpml_primitive_copy_data(&primitive
, backup
);
1329 cpml_curve_offset_algorithm(CPML_CURVE_OFFSET_ALGORITHM_BAIOCA
);
1330 cpml_primitive_offset(&primitive
, 1);
1331 adg_assert_isapprox((primitive
.org
)->point
.x
, 5.293);
1332 adg_assert_isapprox((primitive
.org
)->point
.y
, 7.707);
1333 adg_assert_isapprox(primitive
.data
[1].point
.x
, 6.901);
1334 adg_assert_isapprox(primitive
.data
[1].point
.y
, 9.315);
1335 adg_assert_isapprox(primitive
.data
[2].point
.x
, 10.806);
1336 adg_assert_isapprox(primitive
.data
[2].point
.y
, 10.355);
1337 adg_assert_isapprox(primitive
.data
[3].point
.x
, -1.4);
1338 adg_assert_isapprox(primitive
.data
[3].point
.y
, 1.2);
1339 cpml_primitive_copy_data(&primitive
, backup
);
1340 cpml_curve_offset_algorithm(CPML_CURVE_OFFSET_ALGORITHM_HANDCRAFT
);
1341 cpml_primitive_offset(&primitive
, 1);
1342 adg_assert_isapprox((primitive
.org
)->point
.x
, 5.293);
1343 adg_assert_isapprox((primitive
.org
)->point
.y
, 7.707);
1344 adg_assert_isapprox(primitive
.data
[1].point
.x
, -5.758);
1345 adg_assert_isapprox(primitive
.data
[1].point
.y
, -3.344);
1346 adg_assert_isapprox(primitive
.data
[2].point
.x
, 24.987);
1347 adg_assert_isapprox(primitive
.data
[2].point
.y
, 20.99);
1348 adg_assert_isapprox(primitive
.data
[3].point
.x
, -1.4);
1349 adg_assert_isapprox(primitive
.data
[3].point
.y
, 1.2);
1350 cpml_primitive_copy_data(&primitive
, backup
);
1353 cpml_curve_offset_algorithm(CPML_CURVE_OFFSET_ALGORITHM_DEFAULT
);
1355 /* Close: this primitive does not own data points but should
1356 * modify the points of the previous and next primitives */
1357 cpml_primitive_next(&primitive
);
1358 cpml_primitive_offset(&primitive
, 1);
1359 adg_assert_isapprox((curve
.org
)->point
.x
, 6);
1360 adg_assert_isapprox((curve
.org
)->point
.y
, 7);
1361 adg_assert_isapprox(curve
.data
[3].point
.x
, -1.553);
1362 adg_assert_isapprox(curve
.data
[3].point
.y
, 2.894);
1363 adg_assert_isapprox((line
.org
)->point
.x
, 0.447);
1364 adg_assert_isapprox((line
.org
)->point
.y
, 1.894);
1365 adg_assert_isapprox(line
.data
[1].point
.x
, 3);
1366 adg_assert_isapprox(line
.data
[1].point
.y
, 1);
1367 cpml_primitive_offset(&primitive
, -1);
1368 adg_assert_isapprox((curve
.org
)->point
.x
, 6);
1369 adg_assert_isapprox((curve
.org
)->point
.y
, 7);
1370 adg_assert_isapprox(curve
.data
[3].point
.x
, -2);
1371 adg_assert_isapprox(curve
.data
[3].point
.y
, 2);
1372 adg_assert_isapprox((line
.org
)->point
.x
, 0);
1373 adg_assert_isapprox((line
.org
)->point
.y
, 1);
1374 adg_assert_isapprox(line
.data
[1].point
.x
, 3);
1375 adg_assert_isapprox(line
.data
[1].point
.y
, 1);
1381 _cpml_method_join(void)
1383 cairo_path_data_t path_data
[] = {
1384 { .header
= { CPML_MOVE
, 2 }},
1385 { .point
= { 0, 0 }},
1387 { .header
= { CPML_LINE
, 2 }},
1388 { .point
= { 2, 0 }},
1390 { .header
= { CPML_LINE
, 2 }},
1391 { .point
= { 2, 2 }},
1393 { .header
= { CPML_LINE
, 2 }},
1394 { .point
= { 1, 2 }},
1396 { .header
= { CPML_LINE
, 2 }},
1397 { .point
= { 1, -2 }}
1399 cairo_path_t path
= {
1400 CAIRO_STATUS_SUCCESS
,
1402 G_N_ELEMENTS(path_data
)
1404 CpmlSegment segment
;
1405 CpmlPrimitive primitive1
, primitive2
;
1407 cpml_segment_from_cairo(&segment
, &path
);
1409 cpml_primitive_from_segment(&primitive1
, &segment
);
1410 cpml_primitive_copy(&primitive2
, &primitive1
);
1411 cpml_primitive_next(&primitive2
);
1413 /* primitive1 and primitive2 are already joint */
1414 g_assert_cmpint(cpml_primitive_join(&primitive1
, &primitive2
), ==, 1);
1415 adg_assert_isapprox((primitive2
.org
)->point
.x
, 2);
1416 adg_assert_isapprox((primitive2
.org
)->point
.y
, 0);
1418 cpml_primitive_next(&primitive2
);
1419 /* Now primitive1 and primitive2 are divergent,
1420 * hence cannot be joined */
1421 g_assert_cmpint(cpml_primitive_join(&primitive1
, &primitive2
), ==, 0);
1423 cpml_primitive_next(&primitive2
);
1424 g_assert_cmpint(cpml_primitive_join(&primitive1
, &primitive2
), ==, 1);
1425 adg_assert_isapprox((primitive2
.org
)->point
.x
, 1);
1426 adg_assert_isapprox((primitive2
.org
)->point
.y
, 0);
1430 _cpml_method_to_cairo(void)
1433 CpmlSegment segment
;
1434 CpmlPrimitive primitive
;
1435 int length
, last_length
;
1437 cr
= adg_test_cairo_context();
1438 cpml_segment_from_cairo(&segment
, (cairo_path_t
*) adg_test_path());
1439 cpml_primitive_from_segment(&primitive
, &segment
);
1441 g_assert_cmpint(adg_test_cairo_num_data(cr
), ==, 0);
1445 last_length
= length
;
1446 cpml_primitive_to_cairo(&primitive
, cr
);
1447 length
= adg_test_cairo_num_data(cr
);
1448 g_assert_cmpint(length
, >, last_length
);
1449 } while (cpml_primitive_next(&primitive
));
1455 _cpml_method_dump(gint i
)
1457 CpmlSegment segment
;
1458 CpmlPrimitive primitive
;
1462 cpml_segment_from_cairo(&segment
, (cairo_path_t
*) adg_test_path());
1463 cpml_primitive_from_segment(&primitive
, &segment
);
1464 cpml_primitive_dump(&primitive
, 1);
1466 cpml_primitive_next(&primitive
);
1467 cpml_primitive_dump(&primitive
, 1);
1470 g_test_trap_assert_passed();
1471 g_test_trap_assert_stderr_unmatched("?");
1472 g_test_trap_assert_stdout("*NULL*");
1473 g_test_trap_assert_stdout("*move*");
1474 g_test_trap_assert_stdout("*line*");
1480 main(int argc
, char *argv
[])
1482 adg_test_init(&argc
, &argv
);
1484 g_test_add_func("/cpml/primitive/behavior/browsing", _cpml_behavior_browsing
);
1486 adg_test_add_traps("/cpml/primitive/sanity/type", _cpml_sanity_type
, 1);
1487 adg_test_add_traps("/cpml/primitive/sanity/from-segment", _cpml_sanity_from_segment
, 2);
1488 adg_test_add_traps("/cpml/primitive/sanity/copy", _cpml_sanity_copy
, 2);
1489 adg_test_add_traps("/cpml/primitive/sanity/copy-data", _cpml_sanity_copy_data
, 2);
1490 adg_test_add_traps("/cpml/primitive/sanity/get-n-points", _cpml_sanity_get_n_points
, 1);
1491 adg_test_add_traps("/cpml/primitive/sanity/get-length", _cpml_sanity_get_length
, 1);
1492 adg_test_add_traps("/cpml/primitive/sanity/put-extents", _cpml_sanity_put_extents
, 2);
1493 adg_test_add_traps("/cpml/primitive/sanity/put-pair-at", _cpml_sanity_put_pair_at
, 2);
1494 adg_test_add_traps("/cpml/primitive/sanity/put-vector-at", _cpml_sanity_put_vector_at
, 2);
1495 adg_test_add_traps("/cpml/primitive/sanity/get-closest-pos", _cpml_sanity_get_closest_pos
, 2);
1496 adg_test_add_traps("/cpml/primitive/sanity/set-point", _cpml_sanity_set_point
, 2);
1497 adg_test_add_traps("/cpml/primitive/sanity/put-point", _cpml_sanity_put_point
, 2);
1498 adg_test_add_traps("/cpml/primitive/sanity/put-intersections", _cpml_sanity_put_intersections
, 3);
1499 adg_test_add_traps("/cpml/primitive/sanity/put-intersections-with-segment", _cpml_sanity_put_intersections_with_segment
, 3);
1500 adg_test_add_traps("/cpml/primitive/sanity/offset", _cpml_sanity_offset
, 1);
1501 adg_test_add_traps("/cpml/primitive/sanity/join", _cpml_sanity_join
, 2);
1502 adg_test_add_traps("/cpml/primitive/sanity/to-cairo", _cpml_sanity_to_cairo
, 2);
1503 adg_test_add_traps("/cpml/primitive/sanity/dump", _cpml_sanity_dump
, 1);
1505 g_test_add_func("/cpml/primitive/method/type", _cpml_method_type
);
1506 g_test_add_func("/cpml/primitive/method/from-segment", _cpml_method_from_segment
);
1507 g_test_add_func("/cpml/primitive/method/copy", _cpml_method_copy
);
1508 g_test_add_func("/cpml/primitive/method/copy-data", _cpml_method_copy_data
);
1509 g_test_add_func("/cpml/primitive/method/type-get-n-points", _cpml_method_type_get_n_points
);
1510 g_test_add_func("/cpml/primitive/method/get-n-points", _cpml_method_get_n_points
);
1511 g_test_add_func("/cpml/primitive/method/get-length", _cpml_method_get_length
);
1512 g_test_add_func("/cpml/primitive/method/put-extents", _cpml_method_put_extents
);
1513 g_test_add_func("/cpml/primitive/method/put-pair-at", _cpml_method_put_pair_at
);
1514 g_test_add_func("/cpml/primitive/method/put-vector-at", _cpml_method_put_vector_at
);
1515 g_test_add_func("/cpml/primitive/method/get-closest-pos", _cpml_method_get_closest_pos
);
1516 g_test_add_func("/cpml/primitive/method/set-point", _cpml_method_set_point
);
1517 g_test_add_func("/cpml/primitive/method/put-point", _cpml_method_put_point
);
1518 g_test_add_func("/cpml/primitive/method/put-intersections", _cpml_method_put_intersections
);
1519 g_test_add_func("/cpml/primitive/method/put-intersections/circle-line", _cpml_method_put_intersections_circle_line
);
1520 g_test_add_func("/cpml/primitive/method/put-intersections-with-segment", _cpml_method_put_intersections_with_segment
);
1521 g_test_add_func("/cpml/primitive/method/offset", _cpml_method_offset
);
1522 g_test_add_func("/cpml/primitive/method/join", _cpml_method_join
);
1523 g_test_add_func("/cpml/primitive/method/to-cairo", _cpml_method_to_cairo
);
1524 adg_test_add_traps("/cpml/primitive/method/dump", _cpml_method_dump
, 1);
1526 return g_test_run();