diff src/coord.c @ 2:31402929c587

Transform position
author Thinker K.F. Li <thinker@branda.to>
date Wed, 23 Jul 2008 16:07:37 +0800
parents b5c0162ccf69
children 164162781a7a
line wrap: on
line diff
--- a/src/coord.c	Wed Jul 23 13:57:33 2008 +0800
+++ b/src/coord.c	Wed Jul 23 16:07:37 2008 +0800
@@ -1,23 +1,46 @@
+/*! \brief Implement coordination tranform mechanism.
+ * \file
+ * This file implements coordination transforming for containers.
+ */
 #include <stdio.h>
 #include <string.h>
 
+typedef float co_aix;
+/*! \brief A coordination system.
+ *
+ * It have a transform function defined by matrix to transform
+ * coordination from source space to target space.
+ * Source space is where the contained is drawed, and target space
+ * is where the coordination of parent container of the element
+ * represented by this coord object.
+ */
 typedef struct coord {
     int seq;
-    float matrix[6];
-    float aggr_matrix[6];
+    co_aix matrix[6];
+    co_aix aggr_matrix[6];
     struct coord *parent;
     struct coord *children, *sibling;
 } coord_t;
 
-static void mul_matrix(float *m1, float *m2, float *dst) {
-    dst[0] = m1[0] * m2[0] + m1[1] * m2[3];
-    dst[1] = m1[0] * m2[1] + m1[1] * m2[4];
-    dst[2] = m1[0] * m2[2] + m1[1] * m2[5] + m1[2];
-    dst[3] = m1[3] * m2[0] + m1[4] * m2[3];
-    dst[4] = m1[3] * m2[1] + m1[4] * m2[4];
-    dst[5] = m1[3] * m2[2] + m1[4] * m2[5] + m1[5];
+#define MUL(a, b) ((a) * (b))
+#define ADD(a, b) ((a) + (b))
+#define DIV(a, b) ((a) / (b))
+#define SUB(a, b) ((a) - (b))
+
+static void mul_matrix(co_aix *m1, co_aix *m2, co_aix *dst) {
+    dst[0] = ADD(MUL(m1[0], m2[0]), MUL(m1[1], m2[3]));
+    dst[1] = ADD(MUL(m1[0], m2[1]), MUL(m1[1], m2[4]));
+    dst[2] = ADD(ADD(MUL(m1[0], m2[2]), MUL(m1[1], m2[5])), m1[2]);
+    dst[3] = ADD(MUL(m1[3], m2[0]), MUL(m1[4], m2[3]));
+    dst[4] = ADD(MUL(m1[3], m2[1]), MUL(m1[4], m2[4]));
+    dst[5] = ADD(ADD(MUL(m1[3], m2[2]), MUL(m1[4], m2[5])), m1[5]);
 }
 
+/*! \brief Compute agrregated transform function.
+ *
+ * Base on parent's aggregated matrix if it is existed, or use transform
+ * matrix as aggregated matrix. 
+ */
 static void compute_transform_function(coord_t *visit) {
     if(visit->parent)
 	mul_matrix(visit->parent->aggr_matrix,
@@ -73,12 +96,26 @@
     co->matrix[4] = 1;
 }
 
+void coord_trans_pos(coord_t *co, co_aix *x, co_aix *y) {
+    co_aix nx, ny;
+
+    nx = ADD(ADD(MUL(co->aggr_matrix[0], *x),
+		 MUL(co->aggr_matrix[1], *y)),
+	     co->aggr_matrix[2]);
+    ny = ADD(ADD(MUL(co->aggr_matrix[3], *x),
+		 MUL(co->aggr_matrix[4], *y)),
+	     co->aggr_matrix[5]);
+    *x = nx;
+    *y = ny;
+}
+
 #ifdef UNITTEST
 
 #include <CUnit/Basic.h>
 
 void test_update_aggr_matrix(void) {
     coord_t elms[6];
+    co_aix x, y;
 
     coord_init(elms, NULL);
     coord_init(elms + 1, elms);
@@ -127,6 +164,12 @@
     CU_ASSERT(elms[5].aggr_matrix[3] == 0);
     CU_ASSERT(elms[5].aggr_matrix[4] == 1);
     CU_ASSERT(elms[5].aggr_matrix[5] == 0);
+
+    x = 50;
+    y = 99;
+    coord_trans_pos(elms + 5, &x, &y);
+    CU_ASSERT(x == 1);
+    CU_ASSERT(y == 99);
 }
 
 CU_pSuite get_coord_suite(void) {