-
Notifications
You must be signed in to change notification settings - Fork 0
/
animation.js
94 lines (85 loc) · 3.1 KB
/
animation.js
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
(function (pm) {
const frames = [];
const styles = {};
function getAnimationName(path) {
const name = `move-path-${path.direction}-${path.steps.join('-')}`;
if (!styles[name]) {
generateFrameStyle(name, path);
}
return name;
}
function generateFrameStyle(name, path) {
const style = document.createElement("style");
style.type = 'text/css';
style.innerHTML = generateFrameContent(name, path);
document.head.appendChild(style);
styles[name] = style;
}
function generateFrameContent(name, path) {
const length = getLength(path);
let horizontal = path.direction === 'left' || path.direction === 'right';
let x = 0, y = 0, step = 0;
let content = `@keyframes ${name} {\n`;
content += ` 0% { transform: translate(${x}px, ${y}px) }\n`;
for (let i = 0; i < path.steps.length; i++) {
const s = path.steps[i];
step += Math.abs(s);
if (horizontal) {
x += s * (pm.TILE_SIZE + pm.TILE_SPACING);
} else {
y += s * (pm.TILE_SIZE + pm.TILE_SPACING);
}
horizontal = !horizontal;
const stepPercent = Math.floor(step / length * 100, 2);
content += ` ${stepPercent}% { transform: translate(${x}px, ${y}px) }\n`;
}
content += "}\n";
return content;
}
function getLength(path) {
return path.steps.reduce((a, b) => a + Math.abs(b), 0);
}
function getAnimationDuration(path) {
return getLength(path) * 0.05 + 's';
}
function getFrame(row, col) {
if (!frames[row]) {
frames[row] = [];
}
const r = frames[row];
if (!r[col]) {
r[col] = generateFrame(row, col);
}
return `move-path-${row}-${col}`;
}
function offset(col) {
return col * (pm.TILE_SIZE + pm.TILE_SPACING);
}
function generateFrame(row, col) {
const style = document.createElement("style");
style.type = 'text/css';
let name = `move-path-${row}-${col}`;
if (row === 0) {
style.innerHTML = `@keyframes ${name} {
0% { transform: translateX(0); }
100% { transform: translateX(${(offset(col))}px); }
}`;
} else if (col === 0) {
style.innerHTML = `@keyframes ${name} {
0% { transform: translateY(0); }
100% { transform: translateY(${offset(row)}px); }
}`;
} else {
style.innerHTML = `@keyframes ${name} {
0% { transform: translate(0, 0); }
50% { transform: translate(${(offset(col))}px, 0); }
100% { transform: translate(${(offset(col))}px, ${offset(row)}px); }
}`;
}
document.head.appendChild(style);
return name;
}
pm.getFrame = getFrame;
pm.getAnimationName = getAnimationName;
pm.getAnimationDuration = getAnimationDuration;
}).call(null,window.__pm = window.__pm || {});