Mercurial > MadButterfly
annotate src/coord.c @ 775:caa2fdb5f220
Add mode line
author | Thinker K.F. Li <thinker@codemud.net> |
---|---|
date | Sun, 29 Aug 2010 23:58:43 +0800 |
parents | a545f126d2bf |
children | 8e9481bf1cc0 |
rev | line source |
---|---|
2 | 1 /*! \brief Implement coordination tranform mechanism. |
2 * \file | |
3 * This file implements coordination transforming for containers. | |
4 */ | |
1 | 5 #include <stdio.h> |
6 #include <string.h> | |
31
da770188a44d
resize font size for changige of coord.
Thinker K.F. Li <thinker@branda.to>
parents:
17
diff
changeset
|
7 #include <math.h> |
186
530bb7728546
Move header files to $(top_srcdir)/include/ and prefixed with 'mb_'.
Thinker K.F. Li <thinker@branda.to>
parents:
185
diff
changeset
|
8 #include "mb_types.h" |
1 | 9 |
12 | 10 |
11 #define ASSERT(x) | |
12 | |
3
164162781a7a
Test cairo with Xlib surface
Thinker K.F. Li <thinker@branda.to>
parents:
2
diff
changeset
|
13 /* To keep possibility of changing type of aix */ |
2 | 14 #define MUL(a, b) ((a) * (b)) |
15 #define ADD(a, b) ((a) + (b)) | |
16 #define DIV(a, b) ((a) / (b)) | |
17 #define SUB(a, b) ((a) - (b)) | |
18 | |
19 static void mul_matrix(co_aix *m1, co_aix *m2, co_aix *dst) { | |
20 dst[0] = ADD(MUL(m1[0], m2[0]), MUL(m1[1], m2[3])); | |
21 dst[1] = ADD(MUL(m1[0], m2[1]), MUL(m1[1], m2[4])); | |
22 dst[2] = ADD(ADD(MUL(m1[0], m2[2]), MUL(m1[1], m2[5])), m1[2]); | |
23 dst[3] = ADD(MUL(m1[3], m2[0]), MUL(m1[4], m2[3])); | |
24 dst[4] = ADD(MUL(m1[3], m2[1]), MUL(m1[4], m2[4])); | |
25 dst[5] = ADD(ADD(MUL(m1[3], m2[2]), MUL(m1[4], m2[5])), m1[5]); | |
1 | 26 } |
27 | |
314
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
28 void matrix_mul(co_aix *m1, co_aix *m2, co_aix *dst) { |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
29 co_aix *_dst = dst; |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
30 co_aix fake_dst[6]; |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
31 |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
32 if(m1 == dst || m2 == dst) |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
33 _dst = fake_dst; |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
34 |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
35 mul_matrix(m1, m2, _dst); |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
36 |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
37 if(m1 == dst || m2 == dst) { |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
38 dst[0] = fake_dst[0]; |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
39 dst[1] = fake_dst[1]; |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
40 dst[2] = fake_dst[2]; |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
41 dst[3] = fake_dst[3]; |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
42 dst[4] = fake_dst[4]; |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
43 dst[5] = fake_dst[5]; |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
44 } |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
45 } |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
46 |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
47 void matrix_trans_pos(co_aix *matrix, co_aix *x, co_aix *y) { |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
48 co_aix nx, ny; |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
49 |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
50 nx = ADD(ADD(MUL(matrix[0], *x), |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
51 MUL(matrix[1], *y)), |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
52 matrix[2]); |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
53 ny = ADD(ADD(MUL(matrix[3], *x), |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
54 MUL(matrix[4], *y)), |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
55 matrix[5]); |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
56 *x = nx; |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
57 *y = ny; |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
58 } |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
59 |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
60 /*! \brief Compute aggregated transform matrix. |
2 | 61 * |
62 * Base on parent's aggregated matrix if it is existed, or use transform | |
63 * matrix as aggregated matrix. | |
64 */ | |
1 | 65 static void compute_transform_function(coord_t *visit) { |
533
b51ae415f459
Use coord_is_root() to indicate the root coord
Thinker K.F. Li <thinker@branda.to>
parents:
314
diff
changeset
|
66 if(!coord_is_root(visit)) |
1 | 67 mul_matrix(visit->parent->aggr_matrix, |
68 visit->matrix, visit->aggr_matrix); | |
69 else | |
70 memcpy(visit->aggr_matrix, visit->matrix, sizeof(visit->matrix)); | |
71 } | |
72 | |
16
e17e12b112c4
A simple animation using rdman_redraw_changed().
Thinker K.F. Li <thinker@branda.to>
parents:
15
diff
changeset
|
73 void compute_aggr_of_coord(coord_t *coord) { |
e17e12b112c4
A simple animation using rdman_redraw_changed().
Thinker K.F. Li <thinker@branda.to>
parents:
15
diff
changeset
|
74 compute_transform_function(coord); |
e17e12b112c4
A simple animation using rdman_redraw_changed().
Thinker K.F. Li <thinker@branda.to>
parents:
15
diff
changeset
|
75 } |
e17e12b112c4
A simple animation using rdman_redraw_changed().
Thinker K.F. Li <thinker@branda.to>
parents:
15
diff
changeset
|
76 |
314
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
77 /*! \brief Compute aggregated transform matrix for cached coord. |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
78 * |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
79 * \sa \ref img_cache |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
80 */ |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
81 static void compute_transform_function_cached(coord_t *visit) { |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
82 co_aix *p_matrix; |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
83 co_aix cache_p_matrix[6]; |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
84 co_aix cache_scale_x, cache_scale_y; |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
85 |
533
b51ae415f459
Use coord_is_root() to indicate the root coord
Thinker K.F. Li <thinker@branda.to>
parents:
314
diff
changeset
|
86 if(!coord_is_root(visit)) { |
314
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
87 p_matrix = coord_get_aggr_matrix(visit->parent); |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
88 cache_scale_x = |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
89 sqrtf(p_matrix[0] * p_matrix[0] + p_matrix[3] * p_matrix[3]); |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
90 cache_scale_y = |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
91 sqrtf(p_matrix[1] * p_matrix[1] + p_matrix[4] * p_matrix[4]); |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
92 cache_p_matrix[0] = cache_scale_x; |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
93 cache_p_matrix[1] = 0; |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
94 cache_p_matrix[2] = 0; |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
95 cache_p_matrix[3] = 0; |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
96 cache_p_matrix[4] = cache_scale_y; |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
97 cache_p_matrix[5] = 0; |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
98 mul_matrix(cache_p_matrix, visit->matrix, visit->aggr_matrix); |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
99 } else { |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
100 memcpy(visit->aggr_matrix, visit->matrix, sizeof(visit->matrix)); |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
101 } |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
102 } |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
103 |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
104 void compute_aggr_of_cached_coord(coord_t *coord) { |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
105 compute_transform_function_cached(coord); |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
106 } |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
107 |
535
a545f126d2bf
pcached_area replaces owner_mems_area
Thinker K.F. Li <thinker@branda.to>
parents:
533
diff
changeset
|
108 void |
a545f126d2bf
pcached_area replaces owner_mems_area
Thinker K.F. Li <thinker@branda.to>
parents:
533
diff
changeset
|
109 compute_aggr(coord_t *coord) { |
a545f126d2bf
pcached_area replaces owner_mems_area
Thinker K.F. Li <thinker@branda.to>
parents:
533
diff
changeset
|
110 if(coord->flags & COF_OWN_CANVAS) |
a545f126d2bf
pcached_area replaces owner_mems_area
Thinker K.F. Li <thinker@branda.to>
parents:
533
diff
changeset
|
111 compute_transform_function_cached(coord); |
a545f126d2bf
pcached_area replaces owner_mems_area
Thinker K.F. Li <thinker@branda.to>
parents:
533
diff
changeset
|
112 else |
a545f126d2bf
pcached_area replaces owner_mems_area
Thinker K.F. Li <thinker@branda.to>
parents:
533
diff
changeset
|
113 compute_transform_function(coord); |
a545f126d2bf
pcached_area replaces owner_mems_area
Thinker K.F. Li <thinker@branda.to>
parents:
533
diff
changeset
|
114 } |
a545f126d2bf
pcached_area replaces owner_mems_area
Thinker K.F. Li <thinker@branda.to>
parents:
533
diff
changeset
|
115 |
314
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
116 void compute_reverse(co_aix *orig, co_aix *reverse) { |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
117 co_aix working[6]; |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
118 co_aix factor; |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
119 |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
120 #define VEC_MAC(src, factor, dst) \ |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
121 do { \ |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
122 (dst)[0] += (src)[0] * (factor); \ |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
123 (dst)[1] += (src)[1] * (factor); \ |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
124 (dst)[2] += (src)[2] * (factor); \ |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
125 } while(0) |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
126 |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
127 reverse[0] = 1; |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
128 reverse[1] = 0; |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
129 reverse[2] = 0; |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
130 reverse[3] = 0; |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
131 reverse[4] = 1; |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
132 reverse[5] = 0; |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
133 |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
134 memcpy(working, orig, sizeof(co_aix) * 6); |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
135 |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
136 factor = -working[3] / working[0]; |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
137 VEC_MAC(working, factor, working + 3); |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
138 VEC_MAC(reverse, factor, reverse + 3); |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
139 |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
140 factor = -working[1] / working[4]; |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
141 VEC_MAC(working + 3, factor, working); |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
142 VEC_MAC(reverse + 3, factor, reverse); |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
143 |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
144 reverse[2] = -working[2]; |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
145 reverse[5] = -working[5]; |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
146 |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
147 reverse[0] /= working[0]; |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
148 reverse[1] /= working[0]; |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
149 reverse[2] /= working[0]; |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
150 reverse[3] /= working[4]; |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
151 reverse[4] /= working[4]; |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
152 reverse[5] /= working[4]; |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
153 } |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
154 |
1 | 155 /*! \brief Update aggregate matrices of elements under a sub-tree. |
156 * | |
157 * A subtree is specified by the root of it. All elements in the subtree | |
158 * are effected by that changes of matrix of the subtree root. | |
314
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
159 * |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
160 * \todo Remove update_aggr_matrix() since it is out of date and |
6c350fc92ae3
Cache rednering result is now workable.
Thinker K.F. Li <thinker@branda.to>
parents:
224
diff
changeset
|
161 * no one use it. |
1 | 162 */ |
163 void update_aggr_matrix(coord_t *start) { | |
164 coord_t *visit, *child, *next; | |
165 | |
166 compute_transform_function(start); | |
167 | |
168 visit = start; | |
169 while(visit) { | |
12 | 170 child = STAILQ_HEAD(visit->children); |
1 | 171 while(child) { |
172 compute_transform_function(child); | |
12 | 173 child = STAILQ_NEXT(coord_t, sibling, child); |
1 | 174 } |
175 | |
12 | 176 if(STAILQ_HEAD(visit->children)) |
177 visit = STAILQ_HEAD(visit->children); | |
178 else if(STAILQ_NEXT(coord_t, sibling, visit)) | |
179 visit = STAILQ_NEXT(coord_t, sibling, visit); | |
1 | 180 else { |
181 next = NULL; | |
182 while(visit->parent && visit->parent != start) { | |
183 visit = visit->parent; | |
12 | 184 if(STAILQ_NEXT(coord_t, sibling, visit)) { |
185 next = STAILQ_NEXT(coord_t, sibling, visit); | |
1 | 186 break; |
187 } | |
188 } | |
189 visit = next; | |
190 } | |
191 } | |
192 } | |
193 | |
12 | 194 /*! \brief Initialize a coord object. |
195 * | |
196 * The object is cleared and matrix was initialized to ID. | |
197 * The object is be a children of specified parent. | |
198 */ | |
1 | 199 void coord_init(coord_t *co, coord_t *parent) { |
200 memset(co, 0, sizeof(coord_t)); | |
201 if(parent) { | |
12 | 202 /* insert at tail of children list. */ |
1 | 203 co->parent = parent; |
12 | 204 STAILQ_INS_TAIL(parent->children, coord_t, sibling, co); |
1 | 205 } |
224
29e1b2bffe4c
X backend only sent EVT_MOUSE_MOVE_RAW to MadButterfly.
Thinker K.F. Li <thinker@branda.to>
parents:
196
diff
changeset
|
206 mb_obj_init(co, MBO_COORD); |
1 | 207 co->matrix[0] = 1; |
208 co->matrix[4] = 1; | |
17
41f0907b27ac
Unittest for rdman_redraw_changed().
Thinker K.F. Li <thinker@branda.to>
parents:
16
diff
changeset
|
209 co->aggr_matrix[0] = 1; |
41f0907b27ac
Unittest for rdman_redraw_changed().
Thinker K.F. Li <thinker@branda.to>
parents:
16
diff
changeset
|
210 co->aggr_matrix[4] = 1; |
15
c2ce186a5c37
X_main uses rdman_redraw_all()
Thinker K.F. Li <thinker@branda.to>
parents:
13
diff
changeset
|
211 co->cur_area = &co->areas[0]; |
c2ce186a5c37
X_main uses rdman_redraw_all()
Thinker K.F. Li <thinker@branda.to>
parents:
13
diff
changeset
|
212 co->last_area = &co->areas[1]; |
1 | 213 } |
214 | |
2 | 215 void coord_trans_pos(coord_t *co, co_aix *x, co_aix *y) { |
216 co_aix nx, ny; | |
217 | |
218 nx = ADD(ADD(MUL(co->aggr_matrix[0], *x), | |
219 MUL(co->aggr_matrix[1], *y)), | |
220 co->aggr_matrix[2]); | |
221 ny = ADD(ADD(MUL(co->aggr_matrix[3], *x), | |
222 MUL(co->aggr_matrix[4], *y)), | |
223 co->aggr_matrix[5]); | |
224 *x = nx; | |
225 *y = ny; | |
226 } | |
227 | |
31
da770188a44d
resize font size for changige of coord.
Thinker K.F. Li <thinker@branda.to>
parents:
17
diff
changeset
|
228 co_aix coord_trans_size(coord_t *co, co_aix sz) { |
da770188a44d
resize font size for changige of coord.
Thinker K.F. Li <thinker@branda.to>
parents:
17
diff
changeset
|
229 co_aix x, y; |
da770188a44d
resize font size for changige of coord.
Thinker K.F. Li <thinker@branda.to>
parents:
17
diff
changeset
|
230 |
da770188a44d
resize font size for changige of coord.
Thinker K.F. Li <thinker@branda.to>
parents:
17
diff
changeset
|
231 x = MUL(co->aggr_matrix[0], sz); |
da770188a44d
resize font size for changige of coord.
Thinker K.F. Li <thinker@branda.to>
parents:
17
diff
changeset
|
232 y = MUL(co->aggr_matrix[3], sz); |
da770188a44d
resize font size for changige of coord.
Thinker K.F. Li <thinker@branda.to>
parents:
17
diff
changeset
|
233 |
da770188a44d
resize font size for changige of coord.
Thinker K.F. Li <thinker@branda.to>
parents:
17
diff
changeset
|
234 return sqrt(x * x + y * y); |
da770188a44d
resize font size for changige of coord.
Thinker K.F. Li <thinker@branda.to>
parents:
17
diff
changeset
|
235 } |
da770188a44d
resize font size for changige of coord.
Thinker K.F. Li <thinker@branda.to>
parents:
17
diff
changeset
|
236 |
151
d11aa8fc06c7
Fix bug of tanks do not show at right places.
Thinker K.F. Li <thinker@branda.to>
parents:
140
diff
changeset
|
237 /*! |
d11aa8fc06c7
Fix bug of tanks do not show at right places.
Thinker K.F. Li <thinker@branda.to>
parents:
140
diff
changeset
|
238 * \note Coords, marked with COF_SKIP_TRIVAL (for temporary), and |
d11aa8fc06c7
Fix bug of tanks do not show at right places.
Thinker K.F. Li <thinker@branda.to>
parents:
140
diff
changeset
|
239 * descendants of them will not be trivaled and the flag with be removed |
d11aa8fc06c7
Fix bug of tanks do not show at right places.
Thinker K.F. Li <thinker@branda.to>
parents:
140
diff
changeset
|
240 * after skipping them. |
d11aa8fc06c7
Fix bug of tanks do not show at right places.
Thinker K.F. Li <thinker@branda.to>
parents:
140
diff
changeset
|
241 */ |
13 | 242 coord_t *preorder_coord_subtree(coord_t *root, coord_t *last) { |
151
d11aa8fc06c7
Fix bug of tanks do not show at right places.
Thinker K.F. Li <thinker@branda.to>
parents:
140
diff
changeset
|
243 coord_t *next = NULL; |
12 | 244 |
138
9f4fc9ecfd1f
Make shapes and coords drawed in post-order of tree.
Thinker K.F. Li <thinker@branda.to>
parents:
31
diff
changeset
|
245 ASSERT(last != NULL); |
12 | 246 |
151
d11aa8fc06c7
Fix bug of tanks do not show at right places.
Thinker K.F. Li <thinker@branda.to>
parents:
140
diff
changeset
|
247 if((!(last->flags & COF_SKIP_TRIVAL)) && |
d11aa8fc06c7
Fix bug of tanks do not show at right places.
Thinker K.F. Li <thinker@branda.to>
parents:
140
diff
changeset
|
248 STAILQ_HEAD(last->children)) { |
12 | 249 next = STAILQ_HEAD(last->children); |
151
d11aa8fc06c7
Fix bug of tanks do not show at right places.
Thinker K.F. Li <thinker@branda.to>
parents:
140
diff
changeset
|
250 if(!(next->flags & COF_SKIP_TRIVAL)) |
d11aa8fc06c7
Fix bug of tanks do not show at right places.
Thinker K.F. Li <thinker@branda.to>
parents:
140
diff
changeset
|
251 return next; |
d11aa8fc06c7
Fix bug of tanks do not show at right places.
Thinker K.F. Li <thinker@branda.to>
parents:
140
diff
changeset
|
252 } else { |
12 | 253 next = last; |
151
d11aa8fc06c7
Fix bug of tanks do not show at right places.
Thinker K.F. Li <thinker@branda.to>
parents:
140
diff
changeset
|
254 } |
d11aa8fc06c7
Fix bug of tanks do not show at right places.
Thinker K.F. Li <thinker@branda.to>
parents:
140
diff
changeset
|
255 |
d11aa8fc06c7
Fix bug of tanks do not show at right places.
Thinker K.F. Li <thinker@branda.to>
parents:
140
diff
changeset
|
256 do { |
d11aa8fc06c7
Fix bug of tanks do not show at right places.
Thinker K.F. Li <thinker@branda.to>
parents:
140
diff
changeset
|
257 next->flags &= ~COF_SKIP_TRIVAL; |
13 | 258 while(next != root && STAILQ_NEXT(coord_t, sibling, next) == NULL) |
12 | 259 next = next->parent; |
13 | 260 if(next == root) |
151
d11aa8fc06c7
Fix bug of tanks do not show at right places.
Thinker K.F. Li <thinker@branda.to>
parents:
140
diff
changeset
|
261 return NULL; |
d11aa8fc06c7
Fix bug of tanks do not show at right places.
Thinker K.F. Li <thinker@branda.to>
parents:
140
diff
changeset
|
262 next = STAILQ_NEXT(coord_t, sibling, next); |
d11aa8fc06c7
Fix bug of tanks do not show at right places.
Thinker K.F. Li <thinker@branda.to>
parents:
140
diff
changeset
|
263 } while(next->flags & COF_SKIP_TRIVAL); |
12 | 264 |
265 return next; | |
266 } | |
267 | |
138
9f4fc9ecfd1f
Make shapes and coords drawed in post-order of tree.
Thinker K.F. Li <thinker@branda.to>
parents:
31
diff
changeset
|
268 coord_t *postorder_coord_subtree(coord_t *root, coord_t *last) { |
9f4fc9ecfd1f
Make shapes and coords drawed in post-order of tree.
Thinker K.F. Li <thinker@branda.to>
parents:
31
diff
changeset
|
269 coord_t *next; |
9f4fc9ecfd1f
Make shapes and coords drawed in post-order of tree.
Thinker K.F. Li <thinker@branda.to>
parents:
31
diff
changeset
|
270 |
9f4fc9ecfd1f
Make shapes and coords drawed in post-order of tree.
Thinker K.F. Li <thinker@branda.to>
parents:
31
diff
changeset
|
271 if(root == last) |
9f4fc9ecfd1f
Make shapes and coords drawed in post-order of tree.
Thinker K.F. Li <thinker@branda.to>
parents:
31
diff
changeset
|
272 return NULL; |
9f4fc9ecfd1f
Make shapes and coords drawed in post-order of tree.
Thinker K.F. Li <thinker@branda.to>
parents:
31
diff
changeset
|
273 |
9f4fc9ecfd1f
Make shapes and coords drawed in post-order of tree.
Thinker K.F. Li <thinker@branda.to>
parents:
31
diff
changeset
|
274 if(last == NULL) { |
9f4fc9ecfd1f
Make shapes and coords drawed in post-order of tree.
Thinker K.F. Li <thinker@branda.to>
parents:
31
diff
changeset
|
275 /* Go most left leaf. */ |
9f4fc9ecfd1f
Make shapes and coords drawed in post-order of tree.
Thinker K.F. Li <thinker@branda.to>
parents:
31
diff
changeset
|
276 next = root; |
9f4fc9ecfd1f
Make shapes and coords drawed in post-order of tree.
Thinker K.F. Li <thinker@branda.to>
parents:
31
diff
changeset
|
277 while(STAILQ_HEAD(next->children)) |
9f4fc9ecfd1f
Make shapes and coords drawed in post-order of tree.
Thinker K.F. Li <thinker@branda.to>
parents:
31
diff
changeset
|
278 next = STAILQ_HEAD(next->children); |
9f4fc9ecfd1f
Make shapes and coords drawed in post-order of tree.
Thinker K.F. Li <thinker@branda.to>
parents:
31
diff
changeset
|
279 return next; |
9f4fc9ecfd1f
Make shapes and coords drawed in post-order of tree.
Thinker K.F. Li <thinker@branda.to>
parents:
31
diff
changeset
|
280 } |
9f4fc9ecfd1f
Make shapes and coords drawed in post-order of tree.
Thinker K.F. Li <thinker@branda.to>
parents:
31
diff
changeset
|
281 |
9f4fc9ecfd1f
Make shapes and coords drawed in post-order of tree.
Thinker K.F. Li <thinker@branda.to>
parents:
31
diff
changeset
|
282 next = last; |
9f4fc9ecfd1f
Make shapes and coords drawed in post-order of tree.
Thinker K.F. Li <thinker@branda.to>
parents:
31
diff
changeset
|
283 if(STAILQ_NEXT(coord_t, sibling, next) == NULL) /* most right */ |
9f4fc9ecfd1f
Make shapes and coords drawed in post-order of tree.
Thinker K.F. Li <thinker@branda.to>
parents:
31
diff
changeset
|
284 return next->parent; |
9f4fc9ecfd1f
Make shapes and coords drawed in post-order of tree.
Thinker K.F. Li <thinker@branda.to>
parents:
31
diff
changeset
|
285 |
9f4fc9ecfd1f
Make shapes and coords drawed in post-order of tree.
Thinker K.F. Li <thinker@branda.to>
parents:
31
diff
changeset
|
286 /* Go most left leaf of right sibling sub-tree. */ |
9f4fc9ecfd1f
Make shapes and coords drawed in post-order of tree.
Thinker K.F. Li <thinker@branda.to>
parents:
31
diff
changeset
|
287 next = STAILQ_NEXT(coord_t, sibling, next); |
9f4fc9ecfd1f
Make shapes and coords drawed in post-order of tree.
Thinker K.F. Li <thinker@branda.to>
parents:
31
diff
changeset
|
288 while(STAILQ_HEAD(next->children)) |
9f4fc9ecfd1f
Make shapes and coords drawed in post-order of tree.
Thinker K.F. Li <thinker@branda.to>
parents:
31
diff
changeset
|
289 next = STAILQ_HEAD(next->children); |
9f4fc9ecfd1f
Make shapes and coords drawed in post-order of tree.
Thinker K.F. Li <thinker@branda.to>
parents:
31
diff
changeset
|
290 |
9f4fc9ecfd1f
Make shapes and coords drawed in post-order of tree.
Thinker K.F. Li <thinker@branda.to>
parents:
31
diff
changeset
|
291 return next; |
9f4fc9ecfd1f
Make shapes and coords drawed in post-order of tree.
Thinker K.F. Li <thinker@branda.to>
parents:
31
diff
changeset
|
292 } |
9f4fc9ecfd1f
Make shapes and coords drawed in post-order of tree.
Thinker K.F. Li <thinker@branda.to>
parents:
31
diff
changeset
|
293 |
1 | 294 #ifdef UNITTEST |
295 | |
296 #include <CUnit/Basic.h> | |
297 | |
298 void test_update_aggr_matrix(void) { | |
299 coord_t elms[6]; | |
2 | 300 co_aix x, y; |
1 | 301 |
302 coord_init(elms, NULL); | |
303 coord_init(elms + 1, elms); | |
304 coord_init(elms + 2, elms); | |
305 coord_init(elms + 3, elms + 1); | |
306 coord_init(elms + 4, elms + 1); | |
307 coord_init(elms + 5, elms + 2); | |
308 | |
309 /* | 2 -1 0 | | |
310 * | 0 1 0 | | |
311 * | 0 0 1 | | |
312 */ | |
313 elms[0].matrix[0] = 2; | |
314 elms[0].matrix[1] = -1; | |
315 | |
316 /* | 1 3 0 | | |
317 * | 5 1 0 | | |
318 * | 0 0 1 | | |
319 */ | |
320 elms[1].matrix[1] = 3; | |
321 elms[1].matrix[3] = 5; | |
322 | |
323 update_aggr_matrix(elms); | |
324 | |
325 /* | -3 5 0 | | |
326 * | 5 1 0 | | |
327 * | 0 0 1 | | |
328 */ | |
329 CU_ASSERT(elms[3].aggr_matrix[0] == -3); | |
330 CU_ASSERT(elms[3].aggr_matrix[1] == 5); | |
331 CU_ASSERT(elms[3].aggr_matrix[2] == 0); | |
332 CU_ASSERT(elms[3].aggr_matrix[3] == 5); | |
333 CU_ASSERT(elms[3].aggr_matrix[4] == 1); | |
334 CU_ASSERT(elms[3].aggr_matrix[5] == 0); | |
335 | |
336 CU_ASSERT(elms[4].aggr_matrix[0] == -3); | |
337 CU_ASSERT(elms[4].aggr_matrix[1] == 5); | |
338 CU_ASSERT(elms[4].aggr_matrix[2] == 0); | |
339 CU_ASSERT(elms[4].aggr_matrix[3] == 5); | |
340 CU_ASSERT(elms[4].aggr_matrix[4] == 1); | |
341 CU_ASSERT(elms[4].aggr_matrix[5] == 0); | |
342 | |
343 CU_ASSERT(elms[5].aggr_matrix[0] == 2); | |
344 CU_ASSERT(elms[5].aggr_matrix[1] == -1); | |
345 CU_ASSERT(elms[5].aggr_matrix[2] == 0); | |
346 CU_ASSERT(elms[5].aggr_matrix[3] == 0); | |
347 CU_ASSERT(elms[5].aggr_matrix[4] == 1); | |
348 CU_ASSERT(elms[5].aggr_matrix[5] == 0); | |
2 | 349 |
350 x = 50; | |
351 y = 99; | |
352 coord_trans_pos(elms + 5, &x, &y); | |
353 CU_ASSERT(x == 1); | |
354 CU_ASSERT(y == 99); | |
1 | 355 } |
356 | |
13 | 357 void test_preorder_coord_subtree(void) { |
12 | 358 coord_t elms[6]; |
359 coord_t *last; | |
360 | |
361 coord_init(elms, NULL); | |
362 coord_init(elms + 1, elms); | |
363 coord_init(elms + 2, elms); | |
364 coord_init(elms + 3, elms + 1); | |
365 coord_init(elms + 4, elms + 1); | |
366 coord_init(elms + 5, elms + 2); | |
367 | |
368 last = elms; | |
13 | 369 last = preorder_coord_subtree(elms, last); |
12 | 370 CU_ASSERT(last == elms + 1); |
13 | 371 last = preorder_coord_subtree(elms, last); |
12 | 372 CU_ASSERT(last == elms + 3); |
13 | 373 last = preorder_coord_subtree(elms, last); |
12 | 374 CU_ASSERT(last == elms + 4); |
13 | 375 last = preorder_coord_subtree(elms, last); |
12 | 376 CU_ASSERT(last == elms + 2); |
13 | 377 last = preorder_coord_subtree(elms, last); |
12 | 378 CU_ASSERT(last == elms + 5); |
13 | 379 last = preorder_coord_subtree(elms, last); |
12 | 380 CU_ASSERT(last == NULL); |
381 } | |
382 | |
1 | 383 CU_pSuite get_coord_suite(void) { |
384 CU_pSuite suite; | |
385 | |
386 suite = CU_add_suite("Suite_coord", NULL, NULL); | |
387 CU_ADD_TEST(suite, test_update_aggr_matrix); | |
13 | 388 CU_ADD_TEST(suite, test_preorder_coord_subtree); |
1 | 389 |
390 return suite; | |
391 } | |
392 | |
393 #endif |