Dia 68/2019 - Anime.js

Desafio #92daysofcode que fiz no final de 2019. Nesse artigo temos o dia 68, mostrando o uso do Anime.js.

Pré-visualização

Código

Começamos com a estrutura do HTML.

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
<!DOCTYPE html>
<html lang="pt-br">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta http-equiv="X-UA-Compatible" content="ie=edge">
<title>Day 68</title>
<style>
*, *:before, *:after { -webkit-box-sizing: border-box; -moz-box-sizing: border-box; box-sizing:border-box; }
html { -webkit-box-sizing:border-box; -moz-box-sizing:border-box; box-sizing:border-box; font-size: 62.5%; }
* { margin: 0; padding: 0; list-style: none; outline: none; }
body { background: #000; color: #fff; font-family: Arial, Helvetica, sans-serif; }

.container { margin: 60px auto; max-width: 992px; text-align: center; width: 100%; }

.item { cursor: pointer; fill: none; stroke: #ccc; stroke-width: 14; stroke-linecap: round; stroke-linejoin: round; }
.active { stroke: #feffca; stroke-width: 10; stroke-linecap: round; stroke-linejoin: round; }
</style>
</head>
<body>
<svg xmlns="http://www.w3.org/2000/svg" width="600" height="600">
<path fill="#333" d="M445.3,121.9v346.9h-84.4V324H229.4v144.7h-83.9V121.9h83.9v134.4h131.5V121.9H445.3z"/>
<path class="item" d="M148.3 133.1c-5.5 0-10-4.5-10-10s4.5-10 10-10 10 4.5 10 10-4.5 10-10 10zm0-10z" id="item_0"/>
<path class="item" d="M227.6 133.1c-5.5 0-10-4.5-10-10s4.5-10 10-10 10 4.5 10 10-4.5 10-10 10zm0-10z" id="item_1"/>
<path class="item" d="M227.6 262.9c-5.5 0-10-4.5-10-10s4.5-10 10-10 10 4.5 10 10-4.5 10-10 10zm0-10z" id="item_2"/>
<path class="item" d="M360.4 267.9c-5.5 0-10-4.5-10-10s4.5-10 10-10 10 4.5 10 10-4.5 10-10 10zm0-10z" id="item_3"/>
<path class="item" d="M363.4 134.1c-5.5 0-10-4.5-10-10s4.5-10 10-10 10 4.5 10 10-4.5 10-10 10zm0-10z" id="item_4"/>
<path class="item" d="M444 134.1c-5.5 0-10-4.5-10-10s4.5-10 10-10 10 4.5 10 10-4.5 10-10 10zm0-10z" id="item_5"/>
<path class="item" d="M444 299c-5.5 0-10-4.5-10-10s4.5-10 10-10 10 4.5 10 10-4.5 10-10 10zm0-10z" id="item_6"/>
<path class="item" d="M444 478.7c-5.5 0-10-4.5-10-10s4.5-10 10-10 10 4.5 10 10-4.5 10-10 10zm0-10z" id="item_7"/>
<path class="item" d="M363.4 478.7c-5.5 0-10-4.5-10-10s4.5-10 10-10 10 4.5 10 10-4.5 10-10 10zm0-10z" id="item_8"/>
<path class="item" d="M361.4 334.7c-5.5 0-10-4.5-10-10s4.5-10 10-10 10 4.5 10 10-4.5 10-10 10zm0-10z" id="item_9"/>
<path class="item" d="M229.6 334.7c-5.5 0-10-4.5-10-10s4.5-10 10-10 10 4.5 10 10-4.5 10-10 10zm0-10z" id="item_10"/>
<path class="item" d="M227.6 478.7c-5.5 0-10-4.5-10-10s4.5-10 10-10 10 4.5 10 10-4.5 10-10 10zm0-10z" id="item_11"/>
<path class="item" d="M146.3 478.7c-5.5 0-10-4.5-10-10s4.5-10 10-10 10 4.5 10 10-4.5 10-10 10zm0-10z" id="item_12"/>
<path class="item" d="M146.3 299c-5.5 0-10-4.5-10-10s4.5-10 10-10 10 4.5 10 10-4.5 10-10 10zm0-10z" id="item_13"/>
<path class="active" d="M148.3 133.1c-5.5 0-10-4.5-10-10s4.5-10 10-10 10 4.5 10 10-4.5 10-10 10zm0-10z" data-active="item_0"/>
</svg>
</div>
<script src="./node_modules/animejs/lib/anime.min.js"></script>
<script src="./day.js"></script>
</body>
</html>
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
const items = document.querySelectorAll(".item");
const on = items => {
[...items].forEach(item => {
item.addEventListener("click", itemOnClick.bind(this, item))
});
}
const off = items => {
[...items].forEach((item) => {
item.removeEventListener("click", itemOnClick.bind(this, item))
});
}
const paths = [
{ d: "M148.3 133.1c-5.5 0-10-4.5-10-10s4.5-10 10-10 10 4.5 10 10-4.5 10-10 10zm0-10z", id: "item_0"},
{ d: "M227.6 133.1c-5.5 0-10-4.5-10-10s4.5-10 10-10 10 4.5 10 10-4.5 10-10 10zm0-10z", id: "item_1"},
{ d: "M227.6 262.9c-5.5 0-10-4.5-10-10s4.5-10 10-10 10 4.5 10 10-4.5 10-10 10zm0-10z", id: "item_2"},
{ d: "M360.4 267.9c-5.5 0-10-4.5-10-10s4.5-10 10-10 10 4.5 10 10-4.5 10-10 10zm0-10z", id: "item_3"},
{ d: "M363.4 134.1c-5.5 0-10-4.5-10-10s4.5-10 10-10 10 4.5 10 10-4.5 10-10 10zm0-10z", id: "item_4"},
{ d: "M444 134.1c-5.5 0-10-4.5-10-10s4.5-10 10-10 10 4.5 10 10-4.5 10-10 10zm0-10z", id: "item_5"},
{ d: "M444 299c-5.5 0-10-4.5-10-10s4.5-10 10-10 10 4.5 10 10-4.5 10-10 10zm0-10z", id: "item_6"},
{ d: "M444 478.7c-5.5 0-10-4.5-10-10s4.5-10 10-10 10 4.5 10 10-4.5 10-10 10zm0-10z", id: "item_7"},
{ d: "M363.4 478.7c-5.5 0-10-4.5-10-10s4.5-10 10-10 10 4.5 10 10-4.5 10-10 10zm0-10z", id: "item_8"},
{ d: "M361.4 334.7c-5.5 0-10-4.5-10-10s4.5-10 10-10 10 4.5 10 10-4.5 10-10 10zm0-10z", id: "item_9"},
{ d: "M229.6 334.7c-5.5 0-10-4.5-10-10s4.5-10 10-10 10 4.5 10 10-4.5 10-10 10zm0-10z", id: "item_10"},
{ d: "M227.6 478.7c-5.5 0-10-4.5-10-10s4.5-10 10-10 10 4.5 10 10-4.5 10-10 10zm0-10z", id: "item_11"},
{ d: "M146.3 478.7c-5.5 0-10-4.5-10-10s4.5-10 10-10 10 4.5 10 10-4.5 10-10 10zm0-10z", id: "item_12"},
{ d: "M146.3 299c-5.5 0-10-4.5-10-10s4.5-10 10-10 10 4.5 10 10-4.5 10-10 10zm0-10z", id: "item_13"}
];

const checkSelectedItemDirection = item => {
const activeItem = document.querySelector(".active");
const previousActiveItem = activeItem.getAttribute("data-active");
const previousActiveItemNumber = +previousActiveItem.split("_")[1];

const selectedItem = item.getAttribute("id");
const selectedItemNumber = +selectedItem.split("_")[1];

const itemObj = {
selItem: selectedItemNumber,
preItem: previousActiveItemNumber,
dir: selectedItemNumber <= previousActiveItemNumber ? "-" : "+"
};

activeItem.setAttribute('data-active', selectedItem);

return itemObj;
}

const animeTimeline = loopPaths => {
if (loopPaths && loopPaths.length) {
var timeline = anime.timeline();
timeline.add({
targets: ".active",
d: {
value: loopPaths[0]["d"],
duration: 1000,
easing: "easeInOutQuad"
},
complete: () => {
document.querySelector(".active").getAttribute("data-active", loopPaths[0]["id"]);
loopPaths.shift();
animeTimeline(loopPaths);
}
});
} else {
on(items);
}
}

const itemOnClick = item => {
off(items);

const itemObj = checkSelectedItemDirection(item);
let loopPaths = [];

switch (itemObj.dir) {
case '-':
loopPaths = paths.slice(itemObj.selItem, itemObj.preItem).reverse();
animeTimeline(loopPaths);
break;
case '+':
loopPaths = paths.slice(itemObj.preItem + 1, itemObj.selItem + 1);
animeTimeline(loopPaths);
break;
default:
break;
}
}

on(items);

Conclusão

A postagem original pode ser vista no meu Instagram e o código está acessível no meu Github.

Relacionados

Ao fechar este aviso ou continuar navegando no site Nerd Calistênico, você aceita o uso de cookies.

Este site usa cookies para assegurar a melhor experiência para os nossos usuários. Consulte nossa política de privacidade.

Uma nova versão está disponível. Clique aqui para atualizar.