acme
Foundational cross-platform layer of the ca2 framework
Loading...
Searching...
No Matches
_function.h
1// Created by camilo on 2022-11-08 16:01 <3ThomasBorregaardSorensen!!
2#pragma once
3template < prototype_rectangle RECTANGLE_TYPE >
4RECTANGLE_TYPE & clear(RECTANGLE_TYPE & rectangle);
5
6
7//template < prototype_rectangle RECTANGLE_TYPE >
8//constexpr auto width(RECTANGLE_TYPE & rectangle);
9
10//template < prototype_rectangle RECTANGLE_TYPE >
11//constexpr auto height(RECTANGLE_TYPE & rectangle);
12
13//template < typename W, typename H >
14//constexpr H area(W w, H h);
15
16//template < prototype_rectangle RECTANGLE_TYPE >
17//constexpr auto area(RECTANGLE_TYPE & rectangle);
18
19//template < prototype_rectangle RECTANGLE_TYPE >
20//bool is_null(const RECTANGLE_TYPE & rectangle);
21
22//template < prototype_rectangle RECTANGLE_TYPE >
23//constexpr auto is_empty(RECTANGLE_TYPE & rectangle);
24
25//template < prototype_rectangle RECTANGLE_TYPE >
26//constexpr auto is_set(RECTANGLE_TYPE & rectangle);
27
28//template < prototype_size SIZE_TYPE >
29//bool is_null(const SIZE_TYPE & size);
30
31//template < prototype_point POINT_TYPE >
32//bool is_null(const POINT_TYPE & point);
33
34//template < prototype_rectangle RECTANGLE_TYPE, typename X >
35//inline RECTANGLE_TYPE & x_offset(RECTANGLE_TYPE & rectangle, X x);
36
37//template < prototype_rectangle RECTANGLE_TYPE, typename Y >
38//inline RECTANGLE_TYPE & y_offset(RECTANGLE_TYPE & rectangle, Y y);
39
40//template < prototype_rectangle RECTANGLE_TYPE, typename X >
41//inline RECTANGLE_TYPE & x_subtract(RECTANGLE_TYPE & rectangle, X x);
42
43//template < prototype_rectangle RECTANGLE_TYPE, typename Y >
44//inline RECTANGLE_TYPE & y_subtract(RECTANGLE_TYPE & rectangle, Y y);
45
46//template < typename RECTANGLE_TYPE, typename X, typename Y >
47//inline RECTANGLE_TYPE & offset(RECTANGLE_TYPE & rectangle, X x, Y y);
48
49//template < typename RECTANGLE_TYPE, typename X, typename Y >
50//inline RECTANGLE_TYPE & subtract(RECTANGLE_TYPE & rectangle, X x, Y y);
51
52//template < typename RECTANGLE_TYPE, prototype_point POINT_TYPE >
53//inline RECTANGLE_TYPE & offset(RECTANGLE_TYPE & rectangle, const POINT_TYPE & point);
54
55//template < prototype_rectangle RECTANGLE_TYPE, prototype_point POINT_TYPE >
56//inline RECTANGLE_TYPE & subtract(RECTANGLE_TYPE & rectangle, const POINT_TYPE & point);
57
58//template < prototype_rectangle RECTANGLE1, prototype_rectangle RECTANGLE2 >
59//inline RECTANGLE1 & subtract(RECTANGLE1 & rectangle, const RECTANGLE2 & rectangle2);
60
61//template < prototype_rectangle RECTANGLE_TYPE, prototype_point POINT >
62//inline RECTANGLE_TYPE & subtract(RECTANGLE_TYPE & rectangle, const POINT & point) { return subtract(rectangle, point); }
63
64
65//template < prototype_point POINT, typename X, typename Y >
66//inline POINT & offset(POINT & point, X x, Y y);
67
68//template < prototype_point POINT, prototype_point POINT2 >
69//inline POINT & offset(POINT & point, const POINT2 & point2);
70
71//template < prototype_point POINT, prototype_point POINT2 >
72//inline POINT & add(POINT & point, const POINT2 & point2);
73
74//template < prototype_point POINT_TYPE, typename X, typename Y >
75//inline POINT_TYPE & subtract(POINT_TYPE & point, X x, Y y);
76
77//template < prototype_point POINT_TYPE, prototype_point POINT_TYPE2 >
78//inline POINT_TYPE & subtract(POINT_TYPE & point, const POINT_TYPE2 & point2);
79
80//template < prototype_rectangle RECTANGLE_TYPE, prototype_point POINT_TYPE >
81//inline RECTANGLE_TYPE & add(RECTANGLE_TYPE & rectangle, const POINT_TYPE & point);
82
83//template < prototype_rectangle RECTANGLE_TYPE, prototype_rectangle RECT_TYPE1, prototype_rectangle RECT_TYPE2 >
84//bool x_intersect(RECTANGLE_TYPE & rectangle, const RECT_TYPE1 & rect1, const RECT_TYPE2 & rect2);
85
86//template < prototype_rectangle RECT_TYPE1, prototype_rectangle RECT_TYPE2 >
87//bool x_intersects(const RECT_TYPE1 & rect1, const RECT_TYPE2 & rect2);
88
89//template < prototype_rectangle RECTANGLE_TYPE, prototype_rectangle RECT_TYPE1, prototype_rectangle RECT_TYPE2 >
90//bool y_intersect(RECTANGLE_TYPE & rectangle, const RECT_TYPE1 & rect1, const RECT_TYPE2 & rect2);
91
92//template < prototype_rectangle RECT_TYPE1, prototype_rectangle RECT_TYPE2 >
93//bool y_intersects(const RECT_TYPE1 & rect1, const RECT_TYPE2 & rect2);
94
95//template < prototype_rectangle RECTANGLE_TYPE, prototype_rectangle RECT_TYPE1, prototype_rectangle RECT_TYPE2 >
96//bool intersect(RECTANGLE_TYPE & rectangle, const RECT_TYPE1 & rect1, const RECT_TYPE2 & rect2);
97
98//template < prototype_rectangle RECT_TYPE1, prototype_rectangle RECT_TYPE2 >
99//bool intersects(const RECT_TYPE1 & rect1, const RECT_TYPE2 & rect2);
100
101//template < prototype_rectangle RECTANGLE_TYPE, prototype_rectangle RECT_TYPE1, prototype_rectangle RECT_TYPE2 >
102//bool x_null_intersect(RECTANGLE_TYPE & rectangle, const RECT_TYPE1 & rect1, const RECT_TYPE2 & rect2);
103
104//template < prototype_rectangle RECTANGLE_TYPE, prototype_rectangle RECT_TYPE1, prototype_rectangle RECT_TYPE2 >
105//bool y_null_intersect(RECTANGLE_TYPE & rectangle, const RECT_TYPE1 & rect1, const RECT_TYPE2 & rect2);
106
107//template < prototype_rectangle RECTANGLE_TYPE, prototype_rectangle RECT_TYPE1, prototype_rectangle RECT_TYPE2 >
108//bool null_intersect(RECTANGLE_TYPE & rectangle, const RECT_TYPE1 & rect1, const RECT_TYPE2 & rect2);
109//
110//template < prototype_rectangle RECTANGLE_TYPE, prototype_rectangle RECT_TYPE1, prototype_rectangle RECT_TYPE2 >
111//bool x_left_null_intersect(RECTANGLE_TYPE & rectangle, const RECT_TYPE1 & rect1, const RECT_TYPE2 & rect2);
112//
113//template < prototype_rectangle RECTANGLE_TYPE, prototype_rectangle RECT_TYPE1, prototype_rectangle RECT_TYPE2 >
114//bool y_top_null_intersect(RECTANGLE_TYPE & rectangle, const RECT_TYPE1 & rect1, const RECT_TYPE2 & rect2);
115//
116//template < prototype_rectangle RECTANGLE_TYPE, prototype_rectangle RECT_TYPE1, prototype_rectangle RECT_TYPE2 >
117//bool top_left_null_intersect(RECTANGLE_TYPE & rectangle, const RECT_TYPE1 & rect1, const RECT_TYPE2 & rect2);
118
119//template < prototype_rectangle RECTANGLE_TYPE, prototype_rectangle RECT_TYPE1, prototype_rectangle RECT_TYPE2 >
120//RECTANGLE_TYPE & unite(RECTANGLE_TYPE & rectangle, const RECT_TYPE1 & rect1, const RECT_TYPE2 & rect2);
121
122
123//template < prototype_rectangle RECT_TYPE1, prototype_rectangle RECT_TYPE2 >
124//RECT_TYPE1 & unite(RECT_TYPE1 & rect1, const RECT_TYPE2 & rect2);
125
126
127//template < typename X, typename Y >
128//auto get_dimension(enum_orientation eorientation, X x, Y y);
129
130
131//template < typename X, typename Y >
132//auto get_normal_dimension(enum_orientation eorientation, X x, Y y);
133//
134//
135//template < prototype_rectangle RECTANGLE1, prototype_rectangle RECTANGLE2 >
136//bool is_equal(const RECTANGLE1 & rectangle1, const RECTANGLE2 & rectangle2, ::f32 epsilon = 0.0001);
137//
138//template < prototype_point POINT1, prototype_point POINT2 >
139//bool is_equal(const POINT1 & point1, const POINT2 & point2, ::f32 epsilon = 0.0001);
140
141//template < prototype_size SIZE_TYPE1, prototype_size SIZE_TYPE2 >
142//bool is_equal(const SIZE_TYPE1 & size1, const SIZE_TYPE2 & size2, ::f32 epsilon = 0.0001);
143//
144//template < prototype_rectangle RECTANGLE_TYPE, prototype_number L, prototype_number T, prototype_number R, prototype_number B >
145//RECTANGLE_TYPE & assign(RECTANGLE_TYPE & rectangle, L l, T t, R r, B b);
146//
147//
148//template < prototype_rectangle RECTANGLE, prototype_number L, prototype_number T, prototype_number W, prototype_number H >
149//RECTANGLE & set_dimension(RECTANGLE & rectangle, L l, T t, W w, H h);
150
151//template < prototype_rectangle RECTANGLE, typename L, typename T, typename W, typename H >
152//inline auto _001SetRectDim(RECTANGLE &r, L l, T t, W w, H h) { return set_dim(p, l, t, w, h); }
153//template < typename L, typename T, typename W, typename H >
154//inline auto _001SetRectDim(::i64_rectangle * p, L l, T t, W w, H h) { return set_rect_dim(p, l, t, w, h); }
155//template < typename L, typename T, typename W, typename H >
156//inline auto _001SetRectDim(::f32_rectangle * p, L l, T t, W w, H h) { return set_rect_dim(p, l, t, w, h); }
157//template < typename L, typename T, typename W, typename H >
158//inline auto _001SetRectDim(::f64_rectangle * p, L l, T t, W w, H h) { return set_rect_dim(p, l, t, w, h); }
159
160
161//template < prototype_rectangle RECTANGLE, prototype_point POINT, prototype_size SIZE >
162//RECTANGLE & set_bottom_right(RECTANGLE & rectangle, const SIZE & size);
163//
164//template < prototype_rectangle RECTANGLE, prototype_point POINT, prototype_size SIZE >
165//RECTANGLE & assign(RECTANGLE & rectangle, const POINT & point, const SIZE & size);
166
167
168//template < prototype_rectangle RECTANGLE_TYPE >
169//RECTANGLE_TYPE & null(RECTANGLE_TYPE & rectangle);
170//
171//
172//template < prototype_rectangle RECTANGLE, prototype_number X >
173//inline bool contains_x(const RECTANGLE & rectangle, X x);
174//
175//
176//template < prototype_rectangle RECTANGLE, prototype_number Y >
177//inline bool contains_y(const RECTANGLE & rectangle, Y y);
178//
179//template < typename RECTANGLE, prototype_number X, prototype_number Y >
180//inline bool contains(const RECTANGLE & rectangle, X x, Y y);
181//
182//template < prototype_rectangle RECTANGLE_TYPE, prototype_number L, prototype_number T, prototype_number R, prototype_number B >
183//inline RECTANGLE_TYPE & inflate(RECTANGLE_TYPE & rectangle, L l, T t, R r, B b);
184//
185//template < prototype_rectangle RECTANGLE_TYPE, prototype_rectangle RECT_TYPE2 >
186//inline RECTANGLE_TYPE & inflate(RECTANGLE_TYPE & rectangle, const RECT_TYPE2 & rect2);
187//
188
189//template < prototype_rectangle RECTANGLE_TYPE, prototype_rectangle RECT_TYPE2 >
190//inline RECTANGLE_TYPE & multiply_inline(RECTANGLE_TYPE & rectangle, const RECT_TYPE2 & rect2);
191//
192//
193//template < prototype_rectangle RECTANGLE_TYPE, prototype_number L, prototype_number T, prototype_number R, prototype_number B >
194//inline RECTANGLE_TYPE & deflate(RECTANGLE_TYPE & rectangle, L l, T t, R r, B b);
195//
196//template < typename RECTANGLE_TYPE, prototype_rectangle RECT_TYPE2 >
197//inline RECTANGLE_TYPE & deflate(RECTANGLE_TYPE & rectangle, const RECT_TYPE2 & rect2);
198//
199//
200//template < prototype_rectangle RECTANGLE_TYPE, prototype_number X, prototype_number Y >
201//inline RECTANGLE_TYPE & inflate(RECTANGLE_TYPE & rectangle, X x, Y y);
202//
203//template < prototype_rectangle RECTANGLE_TYPE, prototype_number X, prototype_number Y >
204//inline RECTANGLE_TYPE & deflate(RECTANGLE_TYPE & rectangle, X x, Y y);
205//
206//
207//template < prototype_rectangle RECTANGLE_TYPE, prototype_number UNIT >
208//inline RECTANGLE_TYPE & inflate(RECTANGLE_TYPE & rectangle, UNIT u);
209//
210//
211//template < prototype_rectangle RECTANGLE_TYPE, prototype_number UNIT >
212//inline RECTANGLE_TYPE & deflate(RECTANGLE_TYPE & rectangle, UNIT u);
213//
214//
215//template < prototype_rectangle RECTANGLE_TYPE >
216//inline RECTANGLE_TYPE & swap_left_right(RECTANGLE_TYPE & rectangle);
217//
218//
219//template < prototype_point POINT1, prototype_point POINT2 >
220//inline bool polygon_contains_winding(const POINT1 * ppPolygon, ::i32 iCount, const POINT2 & point);
221//
222//template < prototype_point POINT1, prototype_point POINT2 >
223//inline bool polygon_contains_alternate(const POINT1 * ppPolygon, ::i32 iCount, const POINT2 & point, bool bUseHoles, ::f32 epsilon = 0.00001f);
224//
225//template < prototype_point POINT, prototype_point POINT2 >
226//inline POINT & operator -= (POINT & point, const POINT2 & pointOffset);
227//
228//template < prototype_point POINT, prototype_point POINT2 >
229//inline POINT & operator += (POINT & point, const POINT2 & pointOffset);
230//
231//template < prototype_rectangle RECTANGLE, prototype_point POINT >
232//inline RECTANGLE & operator -= (RECTANGLE & rectangle, const POINT & point);
233//
234//template < prototype_rectangle RECTANGLE, prototype_point POINT >
235//inline RECTANGLE & operator += (RECTANGLE & rectangle, const POINT & point);
236//
237//
238//CLASS_DECL_ACME ::f64 d_distance(const i32_point& point1, const i32_point& point2);
239
240
241template < prototype_point POINT1, prototype_point POINT2 >
242::f64 f64_distance(const POINT1 & point1, const POINT2 & point2)
243{
244
245 return sqrt((point2.x - point1.x) * (point2.x - point1.x) + (point2.y - point1.y) * (point2.y - point1.y));
246
247}
248
249
250template < typename X, typename Y >
251inline auto get_dimension(enum_orientation eorientation, X x, Y y)
252{
253
254 if (eorientation == e_orientation_horizontal)
255 {
256
257 return x;
258
259 }
260 else if (eorientation == e_orientation_vertical)
261 {
262
263 return y;
264
265 }
266 else
267 {
268
269 throw ::exception(error_bad_argument, "invalid orientation");
270
271 }
272
273}
274
275
276template < typename X, typename Y, typename Z >
277inline auto get_dimension(enum_orientation eorientation, X x, Y y, Z z)
278{
279
280 if (eorientation == e_orientation_horizontal)
281 {
282
283 return x;
284
285 }
286 else if (eorientation == e_orientation_vertical)
287 {
288
289 return y;
290
291 }
292 else if (eorientation == e_orientation_z)
293 {
294
295 return z;
296
297 }
298 else
299 {
300
301 throw ::exception(error_bad_argument, "invalid orientation (2)");
302
303 }
304
305}
306
307
308template < typename X, typename Y, typename Z, typename W >
309inline auto get_dimension(enum_orientation eorientation, X x, Y y, Z z, W w)
310{
311
312 if (eorientation == e_orientation_horizontal)
313 {
314
315 return x;
316
317 }
318 else if (eorientation == e_orientation_vertical)
319 {
320
321 return y;
322
323 }
324 else if (eorientation == e_orientation_z)
325 {
326
327 return z;
328
329 }
330 else if (eorientation == e_orientation_w)
331 {
332
333 return w;
334
335 }
336 else
337 {
338
339 throw ::exception(error_bad_argument, "invalid orientation (3)");
340
341 }
342
343}
344
345
346template < typename X, typename Y >
347inline auto get_normal_dimension2(enum_orientation eorientation, X x, Y y)
348{
349
350 if (eorientation == e_orientation_horizontal)
351 {
352
353 return y;
354
355 }
356 else if (eorientation == e_orientation_vertical)
357 {
358
359 return x;
360
361 }
362 else
363 {
364
365 throw ::exception(error_bad_argument, "invalid orientation (4)");
366
367 }
368
369}
370
371
372
373
374//template < prototype_rectangle RECTANGLE, prototype_rectangle RECTANGLE1, prototype_rectangle RECTANGLE2 >
375//RECTANGLE & unite(RECTANGLE1 & rectangle, const RECTANGLE1 & rectangle1, const RECTANGLE2 & rectangle2)
376//{
377//
378// if (is_empty(rectangle1))
379// {
380//
381// if (is_empty(rectangle2))
382// {
383//
384// null(rectangle);
385//
386// }
387// else
388// {
389//
390// copy(rectangle, rectangle2);
391//
392// }
393//
394// }
395// else if (is_empty(rectangle2))
396// {
397//
398// copy(rectangle, rectangle1);
399//
400// }
401// else
402// {
403//
404// copy(rectangle, rectangle1);
405//
406// rectangle2.expand_bounding_box(rectangle.top_left(), rectangle.bottom_right());
407//
408// }
409//
410// return rectangle;
411//
412//}
413
414
415template < prototype_rectangle RECTANGLE1, prototype_rectangle RECTANGLE2 >
416RECTANGLE1 & unite(RECTANGLE1 & rectangle1, const RECTANGLE2 & rectangle2)
417{
418
419 if (is_empty(rectangle1))
420 {
421
422 if (is_empty(rectangle2))
423 {
424
425 null(rectangle1);
426
427 }
428 else
429 {
430
431 copy(rectangle1, rectangle2);
432
433 }
434
435 }
436 else if (is_set(rectangle2))
437 {
438
439 rectangle2.expand_bounding_box(rectangle1.top_left(), rectangle1.bottom_right());
440
441 }
442
443 return rectangle1;
444
445}
446
447
448
449
450template < prototype_rectangle RECTANGLE_TYPE >
451constexpr auto width(RECTANGLE_TYPE & rectangle) { return rectangle.right - rectangle.left; }
452
453
454template < prototype_rectangle RECTANGLE_TYPE >
455constexpr auto height(RECTANGLE_TYPE & rectangle) { return rectangle.bottom - rectangle.top; }
456
457
458template < typename W, typename H >
459constexpr H area(W w, H h) { return (w <= (W)0 || h <= (H)0) ? 0 : (H)(w * h); }
460
461
462template < prototype_rectangle RECTANGLE_TYPE >
463constexpr auto area(RECTANGLE_TYPE & rectangle) { return area(width(rectangle), height(rectangle)); }
464
465
466template < prototype_rectangle RECTANGLE_TYPE >
467bool is_null(const RECTANGLE_TYPE & rectangle)
468{
469
470 return rectangle.left == (decltype(rectangle.left))0
471 && rectangle.top == (decltype(rectangle.top))0
472 && rectangle.right == (decltype(rectangle.right))0
473 && rectangle.bottom == (decltype(rectangle.bottom))0;
474
475}
476
477
478template < prototype_rectangle RECTANGLE_TYPE >
479constexpr auto is_empty(RECTANGLE_TYPE & rectangle) { return ::is_null(rectangle) || rectangle.right <= rectangle.left || rectangle.bottom <= rectangle.top; }
480
481
482template < prototype_rectangle RECTANGLE_TYPE >
483constexpr auto is_set(RECTANGLE_TYPE & rectangle) { return !::is_empty(rectangle); }
484
485
486template < prototype_size SIZE_TYPE >
487bool is_null(const SIZE_TYPE & size)
488{
489
490 return size.cx == (typename SIZE_TYPE::UNIT_TYPE)0
491 && size.cy == (typename SIZE_TYPE::UNIT_TYPE)0;
492
493}
494
495
496template < prototype_point POINT_TYPE >
497bool is_null(const POINT_TYPE & point)
498{
499
500 return point.x == (typename POINT_TYPE::UNIT_TYPE)0 && point.y == (typename POINT_TYPE::UNIT_TYPE)0;
501
502}
503
504
505
506
507
508template < prototype_rectangle RECTANGLE_TYPE, typename X >
509inline RECTANGLE_TYPE & x_offset(RECTANGLE_TYPE & rectangle, X x)
510{
511
512 rectangle.left = (decay<typename RECTANGLE_TYPE::UNIT_TYPE>)(rectangle.left + x);
513
514 rectangle.right = (decay<typename RECTANGLE_TYPE::UNIT_TYPE>)(rectangle.right + x);
515
516 return rectangle;
517
518}
519
520
521template < prototype_rectangle RECTANGLE_TYPE, typename Y >
522inline RECTANGLE_TYPE & y_offset(RECTANGLE_TYPE & rectangle, Y y)
523{
524
525 rectangle.top = (decay<typename RECTANGLE_TYPE::UNIT_TYPE>)(rectangle.top + y);
526
527 rectangle.bottom = (decay<typename RECTANGLE_TYPE::UNIT_TYPE>)(rectangle.bottom + y);
528
529 return rectangle;
530
531}
532
533
534
535template < prototype_rectangle RECTANGLE_TYPE, prototype_number X >
536inline RECTANGLE_TYPE & x_subtract(RECTANGLE_TYPE & rectangle, X x)
537{
538
539 rectangle.left = (::decay<typename RECTANGLE_TYPE::UNIT_TYPE>)(rectangle.left - x);
540
541 rectangle.right = (::decay<typename RECTANGLE_TYPE::UNIT_TYPE>)(rectangle.right - x);
542
543 return rectangle;
544
545}
546
547
548template < prototype_rectangle RECTANGLE_TYPE, prototype_number Y >
549inline RECTANGLE_TYPE & y_subtract(RECTANGLE_TYPE & rectangle, Y y)
550{
551
552 rectangle.top = (::decay<typename RECTANGLE_TYPE::UNIT_TYPE>)(rectangle.top - y);
553
554 rectangle.bottom = (::decay<typename RECTANGLE_TYPE::UNIT_TYPE>)(rectangle.bottom - y);
555
556 return rectangle;
557
558}
559
560
561template < prototype_rectangle RECTANGLE_TYPE, prototype_number X, prototype_number Y >
562inline RECTANGLE_TYPE & offset(RECTANGLE_TYPE & rectangle, X x, Y y)
563{
564
565 x_offset(rectangle, x);
566
567 y_offset(rectangle, y);
568
569 return rectangle;
570
571}
572
573
574template < prototype_rectangle RECTANGLE_TYPE, prototype_number X, prototype_number Y >
575inline RECTANGLE_TYPE & subtract(RECTANGLE_TYPE & rectangle, X x, Y y)
576{
577
578 x_subtract(rectangle, x);
579
580 y_subtract(rectangle, y);
581
582 return rectangle;
583
584}
585
586
587template < prototype_rectangle RECTANGLE_TYPE, prototype_point POINT_TYPE >
588inline RECTANGLE_TYPE & offset(RECTANGLE_TYPE & rectangle, const POINT_TYPE & point)
589{
590
591 return offset(rectangle, point.x, point.y);
592
593}
594
595
596template < prototype_rectangle RECTANGLE_TYPE, prototype_point POINT_TYPE >
597inline RECTANGLE_TYPE & subtract(RECTANGLE_TYPE & rectangle, const POINT_TYPE & point)
598{
599
600 return subtract(rectangle, point.x, point.y);
601
602}
603
604
605template < prototype_rectangle RECTANGLE1, prototype_rectangle RECTANGLE2 >
606inline RECTANGLE1 & subtract(RECTANGLE1 & rectangle, const RECTANGLE2 & rectangle2)
607{
608
609 rectangle.left = (decay<typename RECTANGLE1::UNIT_TYPE>)(rectangle.left - rectangle2.left);
610 rectangle.top = (decay<typename RECTANGLE1::UNIT_TYPE>)(rectangle.top - rectangle2.top);
611 rectangle.right = (decay<typename RECTANGLE1::UNIT_TYPE>)(rectangle.right - rectangle2.right);
612 rectangle.bottom = (decay<typename RECTANGLE1::UNIT_TYPE>)(rectangle.bottom - rectangle2.bottom);
613
614 return rectangle;
615
616}
617
618
619template < prototype_rectangle RECTANGLE, prototype_rectangle RECTANGLE1, prototype_rectangle RECTANGLE2 >
620inline RECTANGLE & subtract(RECTANGLE & rectangle, const RECTANGLE1 & rectangle1, const RECTANGLE2 & rectangle2)
621{
622
623 rectangle.left = (decay<typename RECTANGLE::UNIT_TYPE>)(rectangle1.left - rectangle2.left);
624 rectangle.top = (decay<typename RECTANGLE::UNIT_TYPE>)(rectangle1.top - rectangle2.top);
625 rectangle.right = (decay<typename RECTANGLE::UNIT_TYPE>)(rectangle1.right - rectangle2.right);
626 rectangle.bottom = (decay<typename RECTANGLE::UNIT_TYPE>)(rectangle1.bottom - rectangle2.bottom);
627
628 return rectangle;
629
630}
631
632
633//template < prototype_rectangle RECTANGLE_TYPE, prototype_point POINT >
634//inline RECTANGLE_TYPE & subtract(RECTANGLE_TYPE & rectangle, const POINT & point) { return subtract(rectangle, point); }
635
636
637template < prototype_sequence2 SEQUENCE, prototype_number X, prototype_number Y >
638inline SEQUENCE & offset(SEQUENCE & sequence, X x, Y y)
640{
641
642 sequence.x = (const decay<typename SEQUENCE::UNIT_TYPE>&)(sequence.x + x);
643 sequence.y = (const decay<typename SEQUENCE::UNIT_TYPE>&)(sequence.y + y);
644
645 return sequence;
646
647}
648
649
650template < prototype_sequence2 SEQUENCEA, prototype_sequence SEQUENCEB >
651inline SEQUENCEA & offset(SEQUENCEA & sequencea, const SEQUENCEB & sequenceb)
653{
654
655 return offset(sequencea, sequenceb.x, sequenceb.y);
656
657}
658
659
660template < prototype_sequence2 SEQUENCEA, prototype_sequence SEQUENCEB >
661inline SEQUENCEA & add(SEQUENCEA & sequencea, const SEQUENCEB & sequenceb)
663{
664
665 return offset(sequencea, sequenceb);
666
667}
668
669
670template < prototype_sequence2 SEQUENCE, typename X, typename Y >
671inline SEQUENCE & subtract(SEQUENCE & sequence, X x, Y y)
673{
674
675 sequence.x = (const decay<typename SEQUENCE::UNIT_TYPE>&)(sequence.x - x);
676 sequence.y = (const decay<typename SEQUENCE::UNIT_TYPE>&)(sequence.y - y);
677
678 return sequence;
679
680}
681
682
683template < prototype_sequence2 SEQUENCEA, prototype_sequence2 SEQUENCEB >
684inline SEQUENCEA & subtract(SEQUENCEA & sequence, const SEQUENCEB & sequenceb)
686{
687
688 return subtract(sequence, sequenceb.x, sequenceb.y);
689
690}
691
692
693template < prototype_rectangle RECTANGLE_TYPE, prototype_point POINT_TYPE >
694inline RECTANGLE_TYPE & add(RECTANGLE_TYPE & rectangle, const POINT_TYPE & point)
695{
696
697 return offset(rectangle, point);
698
699}
700
701
702template < prototype_rectangle RECTANGLE_TYPE, prototype_rectangle RECT_TYPE1, prototype_rectangle RECT_TYPE2 >
703bool x_intersect(RECTANGLE_TYPE & rectangle, const RECT_TYPE1 & rect1, const RECT_TYPE2 & rect2)
704{
705
706 auto left = maximum(rect1.left, rect2.left);
707
708 auto right = minimum(rect1.right, rect2.right);
709
710 bool bIntersect = right > left;
711
712 if (!bIntersect)
713 {
714
715 rectangle.left = 0;
716
717 rectangle.right = 0;
718
719 }
720 else
721 {
722 //if (::is_set(rectangle))
723 //{
724
725 rectangle.left = left;
726
727 rectangle.right = right;
728
729 }
730
731 return bIntersect;
732
733}
734
735
736template < prototype_rectangle RECT_TYPE1, prototype_rectangle RECT_TYPE2 >
737bool x_intersects(const RECT_TYPE1 & rect1, const RECT_TYPE2 & rect2)
738{
739
740
741 return rect1.left < rect2.right && rect1.right > rect2.left;
742
743 //auto left = maximum(rect1.left, rect2.left);
744
745 //auto right = minimum(rect1.right, rect2.right);
746
747 //return right > left;
748
749}
750
751
752template < prototype_rectangle RECTANGLE_TYPE, prototype_rectangle RECT_TYPE1, prototype_rectangle RECT_TYPE2 >
753bool y_intersect(RECTANGLE_TYPE & rectangle, const RECT_TYPE1 & rect1, const RECT_TYPE2 & rect2)
754{
755
756 auto top = maximum(rect1.top, rect2.top);
757
758 auto bottom = minimum(rect1.bottom, rect2.bottom);
759
760 bool bIntersect = bottom > top;
761
762 if (!bIntersect)
763 {
764
765 rectangle.top =0;
766
767 rectangle.bottom = 0;
768
769 }
770 else
771 {
772 //if (::is_set(rectangle))
773 //{
774
775 rectangle.top = top;
776
777 rectangle.bottom = bottom;
778
779 }
780
781 return bIntersect;
782
783}
784
785
786template < prototype_rectangle RECT_TYPE1, prototype_rectangle RECT_TYPE2 >
787bool y_intersects(const RECT_TYPE1 & rect1, const RECT_TYPE2 & rect2)
788{
789
790 //auto top = maximum(rect1.top, rect2.top);
791
792 //auto bottom = minimum(rect1.bottom, rect2.bottom);
793
794 //return bottom > top;
795
796 return rect1.top < rect2.bottom && rect1.bottom > rect2.top;
797
798}
799
800
801template < prototype_rectangle RECTANGLE_TYPE, prototype_rectangle RECT_TYPE1, prototype_rectangle RECT_TYPE2 >
802bool intersect(RECTANGLE_TYPE & rectangle, const RECT_TYPE1 & rect1, const RECT_TYPE2 & rect2)
803{
804
805 if (x_intersect(rectangle, rect1, rect2) && y_intersect(rectangle, rect1, rect2))
806 {
807
808 return true;
809
810 }
811
812 //if (::is_set(rectangle))
813 //{
814
815 clear(rectangle);
816
817 //}
818
819 return false;
820
821}
822
823
824template < prototype_rectangle RECT_TYPE1, prototype_rectangle RECT_TYPE2 >
825bool intersects(const RECT_TYPE1 & rect1, const RECT_TYPE2 & rect2)
826{
827
828 return x_intersects(rect1, rect2) && y_intersects(rect1, rect2);
829
830}
831
832
833template < prototype_rectangle RECTANGLE_TYPE, prototype_rectangle RECT_TYPE1, prototype_rectangle RECT_TYPE2 >
834bool x_null_intersect(RECTANGLE_TYPE & rectangle, const RECT_TYPE1 & rect1, const RECT_TYPE2 & rect2)
835{
836
837 auto left = maximum(rect1.left, rect2.left);
838
839 auto right = minimum(rect1.right, rect2.right);
840
841 bool bIntersect = right >= left;
842
843 if (!bIntersect)
844 {
845
846 left = 0; right = 0;
847
848 }
849
850 //if (::is_set(rectangle))
851 //{
852
853 rectangle.left = left;
854
855 rectangle.right = right;
856
857 //}
858
859 return bIntersect;
860
861}
862
863
864template < prototype_rectangle RECTANGLE_TYPE, prototype_rectangle RECT_TYPE1, prototype_rectangle RECT_TYPE2 >
865bool y_null_intersect(RECTANGLE_TYPE & rectangle, const RECT_TYPE1 & rect1, const RECT_TYPE2 & rect2)
866{
867
868 auto top = maximum(rect1.top, rect2.top);
869
870 auto bottom = minimum(rect1.bottom, rect2.bottom);
871
872 bool bIntersect = bottom >= top;
873
874 if (!bIntersect)
875 {
876
877 top = 0; bottom = 0;
878
879 }
880
881 //if (::is_set(rectangle))
882 //{
883
884 rectangle.top = top;
885
886 rectangle.bottom = bottom;
887
888 //}
889
890 return bIntersect;
891
892}
893
894
895template < prototype_rectangle RECTANGLE_TYPE, prototype_rectangle RECT_TYPE1, prototype_rectangle RECT_TYPE2 >
896bool null_intersect(RECTANGLE_TYPE & rectangle, const RECT_TYPE1 & rect1, const RECT_TYPE2 & rect2)
897{
898
899 if (x_null_intersect(rectangle, rect1, rect2) && y_null_intersect(rectangle, rect1, rect2))
900 {
901
902 return true;
903
904 }
905
906 //if (::is_set(rectangle))
907 //{
908
909 ::clear(rectangle);
910
911 //}
912
913 return false;
914
915}
916
917
918template < prototype_rectangle RECTANGLE_TYPE, prototype_rectangle RECT_TYPE1, prototype_rectangle RECT_TYPE2 >
919bool x_left_null_intersect(RECTANGLE_TYPE & rectangle, const RECT_TYPE1 & rect1, const RECT_TYPE2 & rect2)
920{
921
922 rectangle.left = maximum(rect1.left, rect2.left);
923
924 rectangle.right = minimum(rect1.right, rect2.right);
925
926 return rectangle.right > rectangle.left || (rectangle.right == rectangle.left && rect1.left == rect2.left);
927
928}
929
930
931template < prototype_rectangle RECTANGLE_TYPE, prototype_rectangle RECT_TYPE1, prototype_rectangle RECT_TYPE2 >
932bool y_top_null_intersect(RECTANGLE_TYPE & rectangle, const RECT_TYPE1 & rect1, const RECT_TYPE2 & rect2)
933{
934
935 rectangle.top = maximum(rect1.top, rect2.top);
936
937 rectangle.bottom = minimum(rect1.bottom, rect2.bottom);
938
939 return rectangle.top < rectangle.bottom || (rectangle.top == rectangle.bottom && rect1.top == rect2.top);
940
941}
942
943
944template < prototype_rectangle RECTANGLE_TYPE, prototype_rectangle RECT_TYPE1, prototype_rectangle RECT_TYPE2 >
945bool top_left_null_intersect(RECTANGLE_TYPE & rectangle, const RECT_TYPE1 & rect1, const RECT_TYPE2 & rect2)
946{
947
948 if (x_left_null_intersect(rectangle, rect1, rect2) && y_top_null_intersect(rectangle, rect1, rect2))
949 {
950
951 return true;
952
953 }
954 else
955 {
956
957 clear(rectangle);
958
959 return false;
960
961 }
962
963}
964
965
966template < prototype_rectangle RECTANGLE1, prototype_rectangle RECTANGLE2 >
967bool is_equal(const RECTANGLE1 & rectangle1, const RECTANGLE2 & rectangle2, largest_number < ::decay<typename RECTANGLE1::UNIT_TYPE>, ::decay<typename RECTANGLE2::UNIT_TYPE > > epsilon = default_epsilon < ::largest_number < ::decay < typename RECTANGLE1::UNIT_TYPE >, ::decay<typename RECTANGLE2::UNIT_TYPE > >>())
968{
969
970 return is_equal(rectangle1.left, rectangle2.left, epsilon)
971 && is_equal(rectangle1.top, rectangle2.top, epsilon)
972 && is_equal(rectangle1.right, rectangle2.right, epsilon)
973 && is_equal(rectangle1.bottom, rectangle2.bottom, epsilon);
974
975}
976
977
978template < prototype_point POINT1, prototype_point POINT2 >
979bool is_equal(const POINT1 & point1, const POINT2 & point2, largest_number < ::decay<typename POINT1::UNIT_TYPE>, ::decay<typename POINT2::UNIT_TYPE> > epsilon = default_epsilon<largest_number < ::decay<typename POINT1::UNIT_TYPE>, ::decay<typename POINT2::UNIT_TYPE> >>())
980{
981
982 return is_equal(point1.x, point2.x, epsilon) && is_equal(point1.y, point2.y, epsilon);
983
984}
985
986
987template < prototype_size SIZE1, prototype_size SIZE2 >
988bool is_equal(const SIZE1 & size1, const SIZE2 & size2, largest_number < ::decay<typename SIZE1::UNIT_TYPE>, ::decay<typename SIZE2::UNIT_TYPE> > epsilon = default_epsilon<largest_number < ::decay<typename SIZE1::UNIT_TYPE>, ::decay<typename SIZE2::UNIT_TYPE > >>())
989{
990
991 return is_equal(size1.cx, size2.cx, epsilon) && is_equal(size1.cy, size2.cy, epsilon);
992
993}
994
995
996template < prototype_rectangle RECTANGLE_TYPE, prototype_number L, prototype_number T, prototype_number R, prototype_number B >
997RECTANGLE_TYPE & assign(RECTANGLE_TYPE & rectangle, L l, T t, R r, B b)
998{
999
1000 rectangle.left = (typename RECTANGLE_TYPE::UNIT_TYPE)l;
1001 rectangle.top = (typename RECTANGLE_TYPE::UNIT_TYPE)t;
1002 rectangle.right = (typename RECTANGLE_TYPE::UNIT_TYPE)r;
1003 rectangle.bottom = (typename RECTANGLE_TYPE::UNIT_TYPE)b;
1004
1005 return rectangle;
1006
1007}
1008
1009
1010template < prototype_rectangle RECTANGLE, prototype_number L, prototype_number T, prototype_number W, prototype_number H >
1011RECTANGLE & set_dimension(RECTANGLE & rectangle, L l, T t, W w, H h)
1012{
1013
1014 rectangle.left = (typename RECTANGLE::UNIT_TYPE)l;
1015 rectangle.top = (typename RECTANGLE::UNIT_TYPE)t;
1016 rectangle.right = (typename RECTANGLE::UNIT_TYPE)(l + w);
1017 rectangle.bottom = (typename RECTANGLE::UNIT_TYPE)(t + h);
1018
1019 return rectangle;
1020
1021}
1022
1023//template < prototype_rectangle RECTANGLE, typename L, typename T, typename W, typename H >
1024//inline auto _001SetRectDim(RECTANGLE &r, L l, T t, W w, H h) { return set_dim(p, l, t, w, h); }
1025//template < typename L, typename T, typename W, typename H >
1026//inline auto _001SetRectDim(::i64_rectangle * p, L l, T t, W w, H h) { return set_rect_dim(p, l, t, w, h); }
1027//template < typename L, typename T, typename W, typename H >
1028//inline auto _001SetRectDim(::f32_rectangle * p, L l, T t, W w, H h) { return set_rect_dim(p, l, t, w, h); }
1029//template < typename L, typename T, typename W, typename H >
1030//inline auto _001SetRectDim(::f64_rectangle * p, L l, T t, W w, H h) { return set_rect_dim(p, l, t, w, h); }
1031
1032
1033template < prototype_rectangle RECTANGLE, prototype_point POINT, prototype_size SIZE >
1034RECTANGLE & set_bottom_right(RECTANGLE & rectangle, const SIZE & size)
1035{
1036
1037 rectangle.right = (typename RECTANGLE::UNIT_TYPE)(rectangle.left + size.cx);
1038 rectangle.bottom = (typename RECTANGLE::UNIT_TYPE)(rectangle.top + size.cy);
1039
1040 return rectangle;
1041
1042}
1043
1044
1045template < prototype_rectangle RECTANGLE, prototype_point POINT, prototype_size SIZE >
1046RECTANGLE & assign(RECTANGLE & rectangle, const POINT & point, const SIZE & size)
1047{
1048
1049 rectangle.left = (typename RECTANGLE::UNIT_TYPE)point.x;
1050 rectangle.top = (typename RECTANGLE::UNIT_TYPE)point.y;
1051 rectangle.right = (typename RECTANGLE::UNIT_TYPE)(point.x + size.cx);
1052 rectangle.bottom = (typename RECTANGLE::UNIT_TYPE)(point.y + size.cy);
1053
1054 return rectangle;
1055
1056}
1057
1058
1059template < prototype_rectangle RECTANGLE_TYPE >
1060RECTANGLE_TYPE & clear(RECTANGLE_TYPE & rectangle)
1061{
1062
1063 return ::assign(rectangle, 0, 0, 0, 0);
1064
1065}
1066
1067
1068
1069template < prototype_rectangle RECTANGLE, prototype_number X >
1070inline bool contains_x(const RECTANGLE & rectangle, X x)
1071{
1072
1073 return x >= rectangle.left && x <= rectangle.right;
1074
1075}
1076
1077
1078template < prototype_rectangle RECTANGLE, prototype_number Y >
1079inline bool contains_y(const RECTANGLE & rectangle, Y y)
1080{
1081
1082 return y >= rectangle.top && y <= rectangle.bottom;
1083
1084}
1085
1086
1087template < typename RECTANGLE, prototype_number X, prototype_number Y >
1088inline bool contains(const RECTANGLE & rectangle, X x, Y y)
1089{
1090
1091 return contains_x(rectangle, x) && contains_y(rectangle, y);
1092
1093}
1094
1095
1096template < prototype_rectangle RECTANGLE_TYPE, prototype_number L, prototype_number T, prototype_number R, prototype_number B >
1097inline RECTANGLE_TYPE & inflate(RECTANGLE_TYPE & rectangle, L l, T t, R r, B b)
1098{
1099
1100 rectangle.left = (typename RECTANGLE_TYPE::UNIT_TYPE)(rectangle.left - l);
1101 rectangle.top = (typename RECTANGLE_TYPE::UNIT_TYPE)(rectangle.top - t);
1102 rectangle.right = (typename RECTANGLE_TYPE::UNIT_TYPE)(rectangle.right + r);
1103 rectangle.bottom = (typename RECTANGLE_TYPE::UNIT_TYPE)(rectangle.bottom + b);
1104
1105 return rectangle;
1106
1107}
1108
1109
1110template < prototype_rectangle RECTANGLE_TYPE, prototype_rectangle RECT_TYPE2 >
1111inline RECTANGLE_TYPE & inflate(RECTANGLE_TYPE & rectangle, const RECT_TYPE2 & rect2)
1112{
1113
1114 return inflate(rectangle, rect2.left, rect2.top, rect2.right, rect2.bottom);
1115
1116}
1117
1118
1119template < prototype_rectangle RECTANGLE_TYPE, prototype_rectangle RECT_TYPE2 >
1120inline RECTANGLE_TYPE & multiply_inline(RECTANGLE_TYPE & rectangle, const RECT_TYPE2 & rect2)
1121{
1122
1123 rectangle.left *= rect2.left;
1124 rectangle.top *= rect2.top;
1125 rectangle.right *= rect2.right;
1126 rectangle.bottom *= rect2.bottom;
1127
1128 return rectangle;
1129
1130}
1131
1132
1133template < prototype_rectangle RECTANGLE_TYPE, prototype_number L, prototype_number T, prototype_number R, prototype_number B >
1134inline RECTANGLE_TYPE & deflate(RECTANGLE_TYPE & rectangle, L l, T t, R r, B b)
1135{
1136
1137 rectangle.left = (typename RECTANGLE_TYPE::UNIT_TYPE)(rectangle.left + l);
1138 rectangle.top = (typename RECTANGLE_TYPE::UNIT_TYPE)(rectangle.top + t);
1139 rectangle.right = (typename RECTANGLE_TYPE::UNIT_TYPE)(rectangle.right - r);
1140 rectangle.bottom = (typename RECTANGLE_TYPE::UNIT_TYPE)(rectangle.bottom - b);
1141
1142 return rectangle;
1143
1144}
1145
1146
1147template < typename RECTANGLE_TYPE, prototype_rectangle RECT_TYPE2 >
1148inline RECTANGLE_TYPE & deflate(RECTANGLE_TYPE & rectangle, const RECT_TYPE2 & rect2)
1149{
1150
1151 return deflate(rectangle, rect2.left, rect2.top, rect2.right, rect2.bottom);
1152
1153}
1154
1155
1156template < prototype_rectangle RECTANGLE_TYPE, prototype_number X, prototype_number Y >
1157inline RECTANGLE_TYPE & inflate(RECTANGLE_TYPE & rectangle, X x, Y y)
1158{
1159
1160 return inflate(rectangle, x, y, x, y);
1161
1162}
1163
1164template < prototype_rectangle RECTANGLE_TYPE, prototype_number X, prototype_number Y >
1165inline RECTANGLE_TYPE & deflate(RECTANGLE_TYPE & rectangle, X x, Y y)
1166{
1167
1168 return deflate(rectangle, x, y, x, y);
1169
1170}
1171
1172
1173template < prototype_rectangle RECTANGLE_TYPE, prototype_number UNIT >
1174inline RECTANGLE_TYPE & inflate(RECTANGLE_TYPE & rectangle, UNIT u)
1175{
1176
1177 return inflate(rectangle, u, u);
1178
1179}
1180
1181
1182template < prototype_rectangle RECTANGLE_TYPE, prototype_number UNIT >
1183inline RECTANGLE_TYPE & deflate(RECTANGLE_TYPE & rectangle, UNIT u)
1184{
1185
1186 return deflate(rectangle, u, u);
1187
1188}
1189
1190
1191template < prototype_rectangle RECTANGLE_TYPE >
1192inline RECTANGLE_TYPE & swap_left_right(RECTANGLE_TYPE & rectangle) { __swap(rectangle.left, rectangle.right); return rectangle; }
1193
1194
1195template < prototype_point POINT1, prototype_point POINT2 >
1196inline bool polygon_contains_winding(const POINT1 * ppPolygon, ::i32 iCount, const POINT2 & point)
1197{
1198
1199 ::i32 i, j = iCount - 1;
1200
1201 auto x = point.x;
1202
1203 auto y = point.y;
1204
1205 bool oddNodes = false;
1206
1207 for (i = 0; i < iCount; i++)
1208 {
1209
1210 if (((ppPolygon[i].y < y && ppPolygon[j].y >= y) || (ppPolygon[j].y < y && ppPolygon[i].y >= y)) && (ppPolygon[i].x <= x || ppPolygon[j].x <= x))
1211 {
1212
1213 oddNodes ^= (ppPolygon[i].x + (y - ppPolygon[i].y) / (ppPolygon[j].y - ppPolygon[i].y) * (ppPolygon[j].x - ppPolygon[i].x) < x);
1214
1215 }
1216
1217 j = i;
1218
1219 }
1220
1221 return oddNodes;
1222
1223}
1224
1225
1226
1227// there are degenerated cases for this ray-casting method for even odd rule (use holes)
1228//https://stackoverflow.com/questions/217578/how-can-i-determine-whether-a-2d-point-is-within-a-polygon
1229
1230
1231/* intersection function */
1232template < prototype_point POINT1, prototype_point POINT2 >
1233inline bool polygon_contains_alternate(const POINT1 * ppPolygon, ::i32 iCount, const POINT2 & point, const bool use_holes, largest_number < ::decay<typename POINT1::UNIT_TYPE>, ::decay<typename POINT2::UNIT_TYPE>> epsilon = default_epsilon<largest_number < ::decay < typename POINT1::UNIT_TYPE >, ::decay < typename POINT2::UNIT_TYPE > > > ())
1234{
1235
1236 using UNIT_TYPE = largest_number < ::decay <typename POINT1::UNIT_TYPE >, ::decay<typename POINT2::UNIT_TYPE > >;
1237
1238 /* we do the angle rule, define that all added angles should be about zero or (2 * PI) */
1239 UNIT_TYPE angletot{};
1240 //::f32 fp1[2], fp2[2];
1241 //::u32 i;
1242 //const ::f32 * p1, * p2;
1243
1244 auto * p1 = &ppPolygon[iCount - 1];
1245
1246 const POINT1 * p2 = nullptr;
1247
1248 /* first vector */
1249 POINT1 fp1 = *p1 - point;
1250
1251 for (::i32 i = 0; i < iCount; i++)
1252 {
1253
1254 p2 = &ppPolygon[i];
1255
1256 /* second vector */
1257 POINT1 fp2 = *p2 - point;
1258
1259 /* dot and angle and cross */
1260 angletot += fp1.angle(fp2);
1261
1262 /* circulate */
1263 fp1 = fp2;
1264
1265 p1 = p2;
1266
1267 }
1268
1269 angletot = (UNIT_TYPE) fabs(angletot);
1270
1271 if (use_holes)
1272 {
1273
1274 auto nested = (UNIT_TYPE) (floor((::f64) (angletot / (UNIT_TYPE)(MATH_PI * 2.0)) + (::f64) epsilon));
1275
1276 angletot -= nested * (UNIT_TYPE)(MATH_PI * 2.0);
1277
1278 return (angletot > 4.0f) != ((::i32)nested % 2);
1279
1280 }
1281 else
1282 {
1283
1284 return (angletot > 4.0f);
1285
1286 }
1287
1288}
1289
1290
1291/* math lib */
1292
1293//static ::f32 dot_v2v2(const ::f32 a[2], const ::f32 b[2])
1294//{
1295// return a[0] * b[0] + a[1] * b[1];
1296//}
1297
1298
1299//static void copy_v2_v2(::f32 r[2], const ::f32 a[2])
1300//{
1301// r[0] = a[0];
1302// r[1] = a[1];
1303//}
1304
1305//template < prototype_point POINT, prototype_point POINT2 >
1306//inline POINT & operator -= (POINT & point, const POINT2 & pointOffset) { ::subtract(point, pointOffset); return point; }
1307//
1308//template < prototype_point POINT, prototype_point POINT2 >
1309//inline POINT & operator += (POINT & point, const POINT2 & pointOffset) { ::add(point, pointOffset); return point; }
1310//
1311//template < prototype_rectangle RECTANGLE, prototype_point POINT >
1312//inline RECTANGLE & operator -= (RECTANGLE & rectangle, const POINT & point) { ::subtract(rectangle, point); return rectangle; }
1313//
1314//template < prototype_rectangle RECTANGLE, prototype_point POINT >
1315//inline RECTANGLE & operator += (RECTANGLE & rectangle, const POINT & point) { ::add(rectangle, point); return rectangle; }
1316
1317
1318
1319
1320
1321
1322template < typename RECT1, typename RECT2 >
1323inline void expand_rect(RECT1& rectangle, const RECT2& r)
1324{
1325
1326 if (::is_null(rectangle))
1327 {
1328
1329 copy(rectangle, r);
1330
1331 }
1332 else
1333 {
1334
1335 rectangle.left = minimum((typename RECT1::UNIT_TYPE)rectangle.left, (typename RECT1::UNIT_TYPE)r.left);
1336 rectangle.right = maximum((typename RECT1::UNIT_TYPE)rectangle.right, (typename RECT1::UNIT_TYPE)r.right);
1337 rectangle.top = minimum((typename RECT1::UNIT_TYPE)rectangle.top, (typename RECT1::UNIT_TYPE)r.top);
1338 rectangle.bottom = maximum((typename RECT1::UNIT_TYPE)rectangle.bottom, (typename RECT1::UNIT_TYPE)r.bottom);
1339
1340 }
1341
1342}
1343
1344
1345template < typename RECT1, typename RECT2 >
1346inline void collapse_rect(RECT1& rectangle, const RECT2& r)
1347{
1348
1349 if (::is_null(rectangle))
1350 {
1351
1352 copy(rectangle, r);
1353
1354 }
1355 else
1356 {
1357
1358 rectangle.left = maximum((typename RECT1::UNIT_TYPE)rectangle.left, (typename RECT1::UNIT_TYPE)r.left);
1359 rectangle.right = minimum((typename RECT1::UNIT_TYPE)rectangle.right, (typename RECT1::UNIT_TYPE)r.right);
1360 rectangle.top = maximum((typename RECT1::UNIT_TYPE)rectangle.top, (typename RECT1::UNIT_TYPE)r.top);
1361 rectangle.bottom = minimum((typename RECT1::UNIT_TYPE)rectangle.bottom, (typename RECT1::UNIT_TYPE)r.bottom);
1362
1363 if (::width(rectangle) == 0 || height(rectangle) == 0)
1364 {
1365
1366 ::clear(rectangle);
1367
1368 }
1369
1370 }
1371
1372}
1373
1374
1375template < prototype_point POINT >
1376inline constexpr auto __horz(const POINT& point) { return point.x; }
1377template < prototype_point POINT >
1378inline constexpr auto __vert(const POINT& point) { return point.y; }
1379template < prototype_size SIZE >
1380inline constexpr auto __horz(const SIZE& size) { return size.cx; }
1381template < prototype_size SIZE >
1382inline constexpr auto __vert(const SIZE& size) { return size.cy; }
1383
1384
1385template < prototype_rectangle RECTANGLE >
1386inline auto & top_left(const RECTANGLE & rectangle) { return *(typename RECTANGLE::POINT_TYPE*)&rectangle; }
1387template < prototype_rectangle RECTANGLE >
1388inline auto & bottom_right(const RECTANGLE& rectangle) { return *(typename RECTANGLE::POINT_TYPE*)&rectangle.right; }
1389
1390
1391//inline i64_point& top_left(const i64_rectangle& rectangle) { return *(i64_point*)&rectangle; }
1392//inline i64_point& bottom_right(const i64_rectangle& rectangle) { return *(i64_point*)&rectangle.right; }
1393
1394
1395//inline ::f32_point& top_left(const ::f32_rectangle& rectangle) { return *(::f32_point*)&rectangle; }
1396//inline ::f32_point& bottom_right(const ::f32_rectangle& rectangle) { return *(::f32_point*)&rectangle.right; }
1397
1398
1399//inline ::f64_point& top_left(const ::f64_rectangle& rectangle) { return *(::f64_point*)&rectangle; }
1400//inline ::f64_point& bottom_right(const ::f64_rectangle& rectangle) { return *(::f64_point*)&rectangle.right; }
1401
1402
1403//inline i32_point & top_left(const ::i32_rectangle &rectangle) { return *(i32_point *)&rectangle; }
1404//inline i32_point & bottom_right(const ::i32_rectangle &rectangle) { return *(i32_point *)&rectangle.right; }
1405//inline i32_point & top_left(const ::i32_rectangle &rectangle) { return top_left(&rectangle); }
1406//inline i32_point & bottom_right(const ::i32_rectangle &rectangle) { return bottom_right(&rectangle); }
1407
1408
1409//inline i64_point & top_left(const ::i64_rectangle & rectangle) { return *(i64_point *)&rectangle; }
1410//inline i64_point & bottom_right(const ::i64_rectangle & rectangle) { return *(i64_point *)&rectangle.right; }
1411//inline i64_point & top_left(const ::i64_rectangle & rectangle) { return top_left(&rectangle); }
1412//inline i64_point & bottom_right(const ::i64_rectangle & rectangle) { return bottom_right(&rectangle); }
1413
1414
1415//inline ::f64_point & top_left(const ::f64_rectangle & rectangle) { return *(::f64_point *)&rectangle; }
1416//inline ::f64_point & bottom_right(const ::f64_rectangle & rectangle) { return *(::f64_point *)&rectangle.right; }
1417//inline ::f64_point & top_left(const ::f64_rectangle & rectangle) { return top_left(&rectangle); }
1418//inline ::f64_point & bottom_right(const ::f64_rectangle & rectangle) { return bottom_right(&rectangle); }
1419
1420
1421
1422
1423//template < typename BASE_TYPE, typename POINT_BASE_TYPE, typename RECTANGLE_BASE_TYPE >
1424//inline size_type < BASE_TYPE, POINT_BASE_TYPE, RECTANGLE_BASE_TYPE >::size_type(const POINT_TYPE & point) noexcept : size_type((size_type&)i32_point) {}
1425//
1426//
1427//template < typename BASE_TYPE, typename POINT_BASE_TYPE, typename RECTANGLE_BASE_TYPE >
1428//inline size_type < BASE_TYPE, POINT_BASE_TYPE, RECTANGLE_BASE_TYPE >::size_type(const RECTANGLE_TYPE & rectangle) noexcept : size_type(rectangle.width(), rectangle.height()) {}
1429
1430//
1431//template < typename UNIT_TYPE >
1432//inline UNIT_TYPE __conv(const ::scoped_string & scopedstr)
1433//{
1434//
1435// return (UNIT_TYPE)str;
1436//
1437//}
1438//
1439//
1440//template < >
1441//inline ::i32 __conv<::i32>(const ::scoped_string & scopedstr)
1442//{
1443//
1444// return (::i32) ::atoi(str);
1445//
1446//}
1447//
1448//
1449//template < >
1450//inline ::i64 __conv<::i64>(const ::scoped_string & scopedstr)
1451//{
1452//
1453// return (::i32) ::atoi(str);
1454//
1455//}
1456//
1457//
1458//template < >
1459//inline ::f64 __conv<::f64>(const ::scoped_string & scopedstr)
1460//{
1461//
1462// return (::i32) ::atoi(str);
1463//
1464//}
1465//
1466//
1467//template < typename TYPE >
1468//inline string __xmlpri()
1469//{
1470//
1471// return "%";
1472//
1473//}
1474//
1475//
1476//template < >
1477//inline string __xmlpri<::i32>()
1478//{
1479//
1480// return "%" PRId32;
1481//
1482//}
1483//
1484//
1485//template < >
1486//inline string __xmlpri<::i64>()
1487//{
1488//
1489// return "%" PRId64;
1490//
1491//}
1492//
1493//
1494//template < >
1495//inline string __xmlpri<::f64>()
1496//{
1497//
1498// return "%f";
1499//
1500//}
1501//
1502//
1503//
1504
1505
1506
1507
1508
1509namespace geometry
1510{
1511
1513 //
1514 // Function Name: deflate
1515 //
1516 // Purpose:
1517 // Change rectangle dimension using its dimensions and the specified
1518 // rates. For example, the dLeftRate machine the left position of the
1519 // rectangle. If 0.0, it remains the same as the original left.
1520 // If 1.0, it turns as the original right. If 0.4, it will be 40%
1521 // of the width from left to right.
1522 //
1523 // Output:
1524 // -1 if the creation of the ::user::impact failed.
1525 // 0 if the creation of the ::user::impact succeeded.
1526 //
1527 // Author:
1528 // Vanessa Testoni
1529 //
1530 //
1532 template < prototype_rectangle RECTANGLE >
1533 inline void deflate(RECTANGLE& rectangle, ::f64 dLeftRate, ::f64 dRightRate, ::f64 dTopRate, ::f64 dBottomRate)
1534 {
1535
1536 rectangle.left = range_rate(rectangle.left, rectangle.right, dLeftRate);
1537
1538 rectangle.right = range_rate(rectangle.right, rectangle.left, dRightRate);
1539
1540 rectangle.top = range_rate(rectangle.top, rectangle.bottom, dTopRate);
1541
1542 rectangle.bottom = range_rate(rectangle.bottom, rectangle.top, dBottomRate);
1543
1544 }
1545
1546
1547} // namespace geometry
1548
1549
1550//template < prototype_point POINT >
1551//inline ::string as_string(const POINT & point)
1552//{
1553//
1554// return as_string(point.x) + ", " + as_string(point.y);
1555//
1556//}
1557//
1558//
1559//template < prototype_size SIZE >
1560//inline ::string as_string(const SIZE & size)
1561//{
1562//
1563// return as_string(size.cx) + ", " + as_string(size.cy);
1564//
1565//}
Definition _initial_concepts.h:38