1 /**
2  * @file vg_lite_matrix.c
3  *
4  */
5 
6 /*********************
7  *      INCLUDES
8  *********************/
9 
10 #include "../../lv_conf_internal.h"
11 
12 #if LV_USE_DRAW_VG_LITE && LV_USE_VG_LITE_THORVG
13 
14 #include <math.h>
15 #include <string.h>
16 #include "vg_lite.h"
17 
18 /*********************
19  *      DEFINES
20  *********************/
21 
22 #define VG_SW_BLIT_PRECISION_OPT 1
23 
24 /**********************
25  *      TYPEDEFS
26  **********************/
27 
28 /**********************
29  *  STATIC PROTOTYPES
30  **********************/
31 
32 /**********************
33  *  STATIC VARIABLES
34  **********************/
35 
36 /**********************
37  *      MACROS
38  **********************/
39 
40 /**********************
41  *   GLOBAL FUNCTIONS
42  **********************/
43 
vg_lite_identity(vg_lite_matrix_t * matrix)44 vg_lite_error_t vg_lite_identity(vg_lite_matrix_t * matrix)
45 {
46     /* Set identify matrix. */
47     matrix->m[0][0] = 1.0f;
48     matrix->m[0][1] = 0.0f;
49     matrix->m[0][2] = 0.0f;
50     matrix->m[1][0] = 0.0f;
51     matrix->m[1][1] = 1.0f;
52     matrix->m[1][2] = 0.0f;
53     matrix->m[2][0] = 0.0f;
54     matrix->m[2][1] = 0.0f;
55     matrix->m[2][2] = 1.0f;
56 
57 #if VG_SW_BLIT_PRECISION_OPT
58     matrix->scaleX = 1.0f;
59     matrix->scaleY = 1.0f;
60     matrix->angle   = 0.0f;
61 #endif /* VG_SW_BLIT_PRECISION_OPT */
62 
63     return VG_LITE_SUCCESS;
64 }
65 
multiply(vg_lite_matrix_t * matrix,vg_lite_matrix_t * mult)66 static void multiply(vg_lite_matrix_t * matrix, vg_lite_matrix_t * mult)
67 {
68     vg_lite_matrix_t temp;
69     int row, column;
70 
71     /* Process all rows. */
72     for(row = 0; row < 3; row++) {
73         /* Process all columns. */
74         for(column = 0; column < 3; column++) {
75             /* Compute matrix entry. */
76             temp.m[row][column] = (matrix->m[row][0] * mult->m[0][column])
77                                   + (matrix->m[row][1] * mult->m[1][column])
78                                   + (matrix->m[row][2] * mult->m[2][column]);
79         }
80     }
81 
82     /* Copy temporary matrix into result. */
83 #if VG_SW_BLIT_PRECISION_OPT
84     memcpy(matrix, &temp, sizeof(vg_lite_float_t) * 9);
85 #else
86     memcpy(matrix, &temp, sizeof(temp));
87 #endif /* VG_SW_BLIT_PRECISION_OPT */
88 }
89 
vg_lite_translate(vg_lite_float_t x,vg_lite_float_t y,vg_lite_matrix_t * matrix)90 vg_lite_error_t vg_lite_translate(vg_lite_float_t x, vg_lite_float_t y, vg_lite_matrix_t * matrix)
91 {
92     /* Set translation matrix. */
93     vg_lite_matrix_t t = { { {1.0f, 0.0f, x},
94             {0.0f, 1.0f, y},
95             {0.0f, 0.0f, 1.0f},
96         },
97         0.0f, 0.0f, 0.0f
98     };
99 
100     /* Multiply with current matrix. */
101     multiply(matrix, &t);
102 
103     return VG_LITE_SUCCESS;
104 }
105 
vg_lite_scale(vg_lite_float_t scale_x,vg_lite_float_t scale_y,vg_lite_matrix_t * matrix)106 vg_lite_error_t vg_lite_scale(vg_lite_float_t scale_x, vg_lite_float_t scale_y, vg_lite_matrix_t * matrix)
107 {
108     /* Set scale matrix. */
109     vg_lite_matrix_t s = { { {scale_x, 0.0f, 0.0f},
110             {0.0f, scale_y, 0.0f},
111             {0.0f, 0.0f, 1.0f},
112         },
113         0.0f, 0.0f, 0.0f
114     };
115 
116     /* Multiply with current matrix. */
117     multiply(matrix, &s);
118 
119 #if VG_SW_BLIT_PRECISION_OPT
120     matrix->scaleX = matrix->scaleX * scale_x;
121     matrix->scaleY = matrix->scaleY * scale_y;
122 #endif /* VG_SW_BLIT_PRECISION_OPT */
123 
124     return VG_LITE_SUCCESS;
125 }
126 
vg_lite_rotate(vg_lite_float_t degrees,vg_lite_matrix_t * matrix)127 vg_lite_error_t vg_lite_rotate(vg_lite_float_t degrees, vg_lite_matrix_t * matrix)
128 {
129     /* Convert degrees into radians. */
130     vg_lite_float_t angle = (degrees / 180.0f) * 3.141592654f;
131 
132     /* Compute cosine and sine values. */
133     vg_lite_float_t cos_angle = cosf(angle);
134     vg_lite_float_t sin_angle = sinf(angle);
135 
136     /* Set rotation matrix. */
137     vg_lite_matrix_t r = { { {cos_angle, -sin_angle, 0.0f},
138             {sin_angle, cos_angle, 0.0f},
139             {0.0f, 0.0f, 1.0f},
140         },
141         0.0f, 0.0f, 0.0f
142     };
143 
144     /* Multiply with current matrix. */
145     multiply(matrix, &r);
146 
147 #if VG_SW_BLIT_PRECISION_OPT
148     matrix->angle = matrix->angle + degrees;
149     if(matrix->angle >= 360) {
150         vg_lite_uint32_t count = (vg_lite_uint32_t)matrix->angle / 360;
151         matrix->angle = matrix->angle - count * 360;
152     }
153 #endif /* VG_SW_BLIT_PRECISION_OPT */
154 
155     return VG_LITE_SUCCESS;
156 }
157 
158 /**********************
159  *   STATIC FUNCTIONS
160  **********************/
161 
162 #endif /*LV_USE_VG_LITE_THORVG*/
163