4 #include "swf_matrix.h"
7 swf_matrix_parse(bitstream_t *bs, swf_matrix_t *matrix) {
9 bitstream_align(bs); // The MATRIX record must be byte aligned.
10 matrix->has_scale = bitstream_getbit(bs);
11 if (matrix->has_scale) {
12 int scale_bits = bitstream_getbits(bs, 5);
13 matrix->scale_bits = scale_bits;
14 matrix->scale_x = bitstream_getbits_signed(bs, scale_bits);
15 matrix->scale_y = bitstream_getbits_signed(bs, scale_bits);
17 matrix->scale_x = SWF_TWIPS; // XXX
18 matrix->scale_y = SWF_TWIPS; // XXX
20 matrix->has_rotate = bitstream_getbit(bs);
21 if (matrix->has_rotate) {
22 int rotate_bits = bitstream_getbits(bs, 5);
23 matrix->rotate_bits = rotate_bits;
24 matrix->rotate_skew0 = bitstream_getbits_signed(bs, rotate_bits);
25 matrix->rotate_skew1 = bitstream_getbits_signed(bs, rotate_bits);
27 matrix->rotate_skew0 = 0;
28 matrix->rotate_skew1 = 0;
30 translate_bits = bitstream_getbits(bs, 5);
31 matrix->translate_bits = translate_bits;
32 matrix->translate_x = bitstream_getbits_signed(bs, translate_bits);
33 matrix->translate_y = bitstream_getbits_signed(bs, translate_bits);
38 swf_matrix_build(bitstream_t *bs, swf_matrix_t *matrix) {
41 bitstream_align(bs); // The MATRIX record must be byte aligned.
42 bitstream_putbit(bs, matrix->has_scale);
43 if (matrix->has_scale) {
45 log2_x = bitstream_need_bits_signed(matrix->scale_x);
46 log2_y = bitstream_need_bits_signed(matrix->scale_y);
47 scale_bits = (log2_x > log2_y)? log2_x: log2_y;
48 bitstream_putbits(bs, scale_bits, 5);
49 bitstream_putbits_signed(bs, matrix->scale_x, scale_bits);
50 bitstream_putbits_signed(bs, matrix->scale_y, scale_bits);
52 if ((matrix->rotate_skew0 == 0) && (matrix->rotate_skew1 == 0)) {
53 matrix->has_rotate = 0;
55 bitstream_putbit(bs, matrix->has_rotate);
56 if (matrix->has_rotate) {
58 float log2_skew0, log2_skew1;
59 log2_skew0 = bitstream_need_bits_signed(matrix->rotate_skew0);
60 log2_skew1 = bitstream_need_bits_signed(matrix->rotate_skew1);
61 rotate_bits = (log2_skew0 > log2_skew1)? log2_skew0: log2_skew1;
62 bitstream_putbits(bs, rotate_bits, 5);
63 bitstream_putbits_signed(bs, matrix->rotate_skew0, rotate_bits);
64 bitstream_putbits_signed(bs, matrix->rotate_skew1, rotate_bits);
66 if ((matrix->translate_x == 0) && (matrix->translate_y == 0)) {
68 bitstream_putbits(bs, translate_bits, 5);
70 log2_x = bitstream_need_bits_signed(matrix->translate_x);
71 log2_y = bitstream_need_bits_signed(matrix->translate_y);
72 translate_bits = (log2_x > log2_y)? log2_x: log2_y;
73 bitstream_putbits(bs, translate_bits, 5);
74 bitstream_putbits_signed(bs, matrix->translate_x, translate_bits);
75 bitstream_putbits_signed(bs, matrix->translate_y, translate_bits);
81 swf_matrix_print(swf_matrix_t *matrix, int indent_depth) {
82 print_indent(indent_depth);
83 if (matrix->has_scale) {
84 printf("scale=(%.3f,%.3f):bits=%u ",
85 matrix->scale_x / 65536.0 / SWF_TWIPS,
86 matrix->scale_y / 65536.0 / SWF_TWIPS,
89 printf("(has_scale=no) ");
91 if (matrix->has_rotate) {
92 printf("rotate=(%.3f,%.3f)bits=%u\n",
93 matrix->rotate_skew0 / 65536.0 / SWF_TWIPS,
94 matrix->rotate_skew1 / 65536.0 / SWF_TWIPS,
97 printf("(has_rotate=no)\n");
99 print_indent(indent_depth);
100 printf("translate=(%.2f,%.2f):bits=%u\n",
101 (float) matrix->translate_x / SWF_TWIPS,
102 (float) matrix->translate_y / SWF_TWIPS,
103 matrix->translate_bits);
108 swf_matrix_apply_factor(swf_matrix_t *matrix,
109 double scale_x, double scale_y,
111 signed int trans_x, signed int trans_y) {
112 if (matrix->has_scale == 0) {
113 matrix->has_scale = 1;
114 matrix->scale_x = 20 * 65536;
115 matrix->scale_y = 20 * 65536;
117 matrix->scale_x *= scale_x;
118 matrix->scale_y *= scale_y;
119 if ((rotate_rad != 0)) {
120 double rot_sin, rot_cos;
122 if (matrix->has_rotate == 0) {
123 matrix->has_rotate = 1;
124 matrix->rotate_skew0 = 0;
125 matrix->rotate_skew1 = 0;
127 rot_cos = cos(rotate_rad);
128 rot_sin = sin(rotate_rad);
129 sx = rot_cos * matrix->scale_x - rot_sin * matrix->rotate_skew0;
130 s0 = rot_sin * matrix->scale_x + rot_cos * matrix->rotate_skew0;
131 s1 = rot_cos * matrix->rotate_skew1 - rot_sin * matrix->scale_y;
132 sy = rot_sin * matrix->rotate_skew1 + rot_cos * matrix->scale_y;
133 matrix->scale_x = sx;
134 matrix->scale_y = sy;
135 matrix->rotate_skew0 = s0;
136 matrix->rotate_skew1 = s1;
138 matrix->translate_x += 20 * trans_x;
139 matrix->translate_y += 20 * trans_y;