summaryrefslogtreecommitdiff
path: root/graphics.c
blob: 97b07df2a102b41ce1e867bb392347e6f14e8aec (plain) (blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
/* gcc -std=c99 *.c -lm && ./a.out | mpv --no-correct-pts --container-fps-override=30 -
 * gcc -std=c99 *.c -lm && ./a.out | ffmpeg -r 30 -i - output.mp4
 */

#include "Animation.h"
#include "AnimationObject.h"
#include "AnimationMove.h"
#include "AnimationInterpolate.h"
#include <math.h>

double
pointDistance(i32 rowA, i32 colA, i32 rowB, i32 colB) {
	return sqrt(pow(rowA - rowB, 2) + pow(colA - colB, 2));
}

void
HorSegmentByPoints(
	i32 rowA, i32 colA, i32 rowB, i32 colB,
	struct AO_HorSegment* segment,
	struct AM_Spin* rotate,
	struct AM_Linear* translate)
{
	segment->left = 0;
	segment->right = pointDistance(rowA, colA, rowB, colB);

	rotate->theta = atan2(rowB - rowA, colB - colA);

	translate->startRow = rowA;
	translate->startCol = colA;

	rotate->callback = AO_HorSegment;
	rotate->priv = segment;
	translate->callback = AM_Spin;
	translate->priv = rotate;
}

int
main() {
	const u32 FPS = 60;
	Animation anim = Animation_new(512, 512, FPS * 5);

	struct AO_Square background = {
		.width = anim.width, .height = anim.height,
		.color = 0xFFF0F0F0,
	};
	Animation_pushEvent(&anim, 0, anim.frameCount, AO_Square, &background);

	/* Root node */
	struct AO_Circle rootNode_ = {
		.radius = 60, .color = 0xFFFF0000,
	};
	struct AM_Linear rootNode_linear = {
		.callback = AO_Circle, .priv = &rootNode_,

		.startRow = anim.height / 4, .startCol = anim.width / 2,
	};

	struct AM_Linear rootNode = rootNode_linear;

	/* Child node */
	struct AO_Circle childNode_ = {
		.radius = 60, .color = 0xFF00FF00,
	};

	struct AM_Linear childNode_left = {
		.callback = AO_Circle, .priv = &childNode_,

		.startRow = anim.height * 3 / 4, .startCol = anim.width / 4,
	};
	struct AM_Linear childNode_right = {
		.callback = AO_Circle, .priv = &childNode_,

		.startRow = anim.height * 3 / 4, .startCol = anim.width * 3 / 4,
	};

	struct AM_Linear childNode = childNode_right;

	/* Root Node --- Child Node */
	struct AO_HorSegment link_ = {
		.color = 0xFFFF00FF, .width = 10,
	};

	struct AM_Spin link_spin_left = {};
	struct AM_Linear link_translate_left = {};
	HorSegmentByPoints(
		rootNode_linear.startRow, rootNode_linear.startCol,
		childNode_left.startRow, childNode_left.startCol,
		&link_, &link_spin_left, &link_translate_left);

	struct AM_Spin link_spin_right = {};
	struct AM_Linear link_translate_right = {};
	HorSegmentByPoints(
		rootNode_linear.startRow, rootNode_linear.startCol,
		childNode_right.startRow, childNode_right.startCol,
		&link_, &link_spin_right, &link_translate_right);

	struct AM_Spin link_spin = link_spin_right;
	struct AM_Linear link_translate = link_translate_right;
	link_translate.priv = &link_spin;

	Animation_pushEvent(&anim, 0, anim.frameCount, AM_Linear, &link_translate);
	Animation_pushEvent(&anim, 0, anim.frameCount, AM_Linear, &rootNode);
	Animation_pushEvent(&anim, 0, anim.frameCount, AM_Linear, &childNode);

	/* Movement */

	struct AM_Linear temp1;
	struct A_Interpolate childNode_moveToLeft = {
		.initialValueTemp = &temp1, .initialValueTempSize = sizeof(temp1),

		.interpolate = AM_LinearInterpolate,
		.value = &childNode, .goalValue = &childNode_left,
	};
	struct AM_Spin temp11;
	struct A_Interpolate segment_spin_moveToLeft = {
		.initialValueTemp = &temp11, .initialValueTempSize = sizeof(temp11),

		.interpolate = AM_SpinInterpolate,
		.value = &link_spin, .goalValue = &link_spin_left,
	};
	struct AM_Linear temp12;
	struct A_Interpolate segment_translate_moveToLeft = {
		.initialValueTemp = &temp12, .initialValueTempSize = sizeof(temp12),

		.interpolate = AM_LinearInterpolate,
		.value = &link_translate, .goalValue = &link_translate_left,
	};

	struct AM_Linear temp2;
	struct A_Interpolate childNode_moveToRight = {
		.initialValueTemp = &temp2, .initialValueTempSize = sizeof(temp2),

		.interpolate = AM_LinearInterpolate,
		.value = &childNode, .goalValue = &childNode_right,
	};
	struct AM_Spin temp21;
	struct A_Interpolate segment_spin_moveToRight = {
		.initialValueTemp = &temp21, .initialValueTempSize = sizeof(temp21),

		.interpolate = AM_SpinInterpolate,
		.value = &link_spin, .goalValue = &link_spin_right,
	};
	struct AM_Linear temp22;
	struct A_Interpolate segment_translate_moveToRight = {
		.initialValueTemp = &temp22, .initialValueTempSize = sizeof(temp22),

		.interpolate = AM_LinearInterpolate,
		.value = &link_translate, .goalValue = &link_translate_right,
	};

	/* Move child node from right to left */

	childNode_moveToLeft.startFrame = segment_spin_moveToLeft.startFrame = segment_translate_moveToLeft.startFrame
		= anim.frameCount / 3 - FPS;
	childNode_moveToLeft.endFrame = segment_spin_moveToLeft.endFrame = segment_translate_moveToLeft.endFrame
		= anim.frameCount / 3;
	Animation_pushEvent(&anim, childNode_moveToLeft.startFrame, childNode_moveToLeft.endFrame, A_Interpolate, &childNode_moveToLeft);
	Animation_pushEvent(&anim, childNode_moveToLeft.startFrame, childNode_moveToLeft.endFrame, A_Interpolate, &segment_spin_moveToLeft);
	Animation_pushEvent(&anim, childNode_moveToLeft.startFrame, childNode_moveToLeft.endFrame, A_Interpolate, &segment_translate_moveToLeft);

	/* Move child node from left to right */

	childNode_moveToRight.startFrame = segment_spin_moveToRight.startFrame = segment_translate_moveToRight.startFrame
		= anim.frameCount * 2 / 3 - FPS;
	childNode_moveToRight.endFrame = segment_spin_moveToRight.endFrame = segment_translate_moveToRight.endFrame
		= anim.frameCount * 2 / 3;
	Animation_pushEvent(&anim, childNode_moveToRight.startFrame, childNode_moveToRight.endFrame, A_Interpolate, &childNode_moveToRight);
	Animation_pushEvent(&anim, childNode_moveToRight.startFrame, childNode_moveToRight.endFrame, A_Interpolate, &segment_spin_moveToRight);
	Animation_pushEvent(&anim, childNode_moveToRight.startFrame, childNode_moveToRight.endFrame, A_Interpolate, &segment_translate_moveToRight);

	Animation_render(&anim);

	Animation_delete(&anim);

	return 0;
}