-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathdemo.html
More file actions
118 lines (96 loc) · 4.08 KB
/
demo.html
File metadata and controls
118 lines (96 loc) · 4.08 KB
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
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Confetti!</title>
</head>
<body>
<div id="confetti-button" class="button" onclick="spawnConfetti(); setRandomFavicon()">
Confetti!
</div>
<style>
body {
-webkit-tap-highlight-color: transparent;
user-select: none; /* For modern browsers */
-webkit-user-select: none; /* For Safari */
-moz-user-select: none; /* For Firefox */
-ms-user-select: none; /* For Internet Explorer */
cursor: default;
font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, "Helvetica Neue", Arial, sans-serif;
font-weight: 500;
display: flex;
align-items: center;
justify-content: center;
height: 100vh;
overflow: hidden;
}
.button {
display: flex;
align-items: center;
width: fit-content;
height: fit-content;
padding: .3rem .4rem;
margin: 0 0 .3rem 0;
background-color: rgb(200, 200, 200);
border: 2px solid rgb(215, 215, 215);
border-radius: .6rem;
box-shadow: 0 .3rem 0 rgb(180, 180, 180);
transition: transform .05s, box-shadow .05s;
} .button:hover {
cursor: pointer;
} .button:active {
box-shadow: none;
transform: translate(0, 6px);
} .button.touch-held {
box-shadow: none;
transform: translate(0, 6px);
}
</style>
<script src="/confetti.js" type="module"></script>
<script>
// Copying :active CSS on mobile
document.querySelectorAll('div', 'svg').forEach(el => {
el.addEventListener('touchstart', () => {
el.classList.add('touch-held')
})
el.addEventListener('touchend', () => {
el.classList.remove('touch-held')
})
el.addEventListener('touchcancel', () => {
el.classList.remove('touch-held')
})
})
function getRandomColor() { // Returns a random confetti color
const colors = ["#f44a4a", "#fb8f23", "#fee440", "#7aff60", "#00f5d4", "#00bbf9", "#9b5de5", "#f15bb5"] // Array of colors
return colors[Math.floor(Math.random() * colors.length)] // Pick a random color
}
function setRandomFavicon() {
const shapes = [
`<rect x="5" y="0" width="6" height="16" fill="{{color}}" transform="rotate(${Math.floor(Math.random() * 361)}, 9, 9), scale(.9)"/>`, // Rectangle
`<path d="M0,12 Q4,4 8,12 Q12,20 16,12" stroke="{{color}}" stroke-width="5" fill="none" transform="rotate(${Math.floor(Math.random() * 361)}, 9, 9), scale(.8)"/>`, // Squigly line
`<circle cx="9" cy="9" r="5.5" fill="{{color}}" transform="rotate(${Math.floor(Math.random() * 361)}, 9, 9)"/>`, // Circle
`<polygon points="9,2.072 17,15.928 1,15.928" fill="{{color}}" transform="rotate(${Math.floor(Math.random() * 361)}, 9, 9), scale(.8)" />` // Triangle
]
const shape = shapes[Math.floor(Math.random() * shapes.length)]
const color = getRandomColor()
const svg = `
<svg xmlns="http://www.w3.org/2000/svg" width="18" height="18" viewBox="0 0 18 18">
${shape.replaceAll("{{color}}", color)}
</svg>
`
const svgBlob = new Blob([svg], { type: "image/svg+xml" })
const url = URL.createObjectURL(svgBlob)
let favicon = document.querySelector("link[rel~='icon']")
if (!favicon) {
favicon = document.createElement("link")
favicon.rel = "icon"
document.head.appendChild(favicon)
}
favicon.href = url
}
// Run it once on load
setRandomFavicon()
</script>
</body>
</html>