Skip to content

Instantly share code, notes, and snippets.

@dmirtyisme
Created January 17, 2017 17:07
Show Gist options
  • Save dmirtyisme/026bc8d511c0badf9c82753f9d3dcf9a to your computer and use it in GitHub Desktop.
Save dmirtyisme/026bc8d511c0badf9c82753f9d3dcf9a to your computer and use it in GitHub Desktop.
Gooey Overlay ver2
<div class="p-summary">
<div class="p-summary__wrap">
<h1 class="p-summary__title">Stage 1</h1>
</div>
</div>
<svg width="100%" height="100%" viewBox="0 0 100 100" preserveAspectRatio="none">
<path class="path01" id="path01" d=""></path>
<path class="path02" id="path02" d=""></path>
</svg>
const ease = {
cubicInOut: (t) => {
return t < 0.5
? 4.0 * t * t * t
: 0.5 * Math.pow(2.0 * t - 2.0, 3.0) + 1.0;
},
circularInOut: (t) => {
return (t < 0.5)
? 0.5 * (1.0 - Math.sqrt(1.0 - 4.0 * t * t))
: 0.5 * (Math.sqrt((3.0 - 2.0 * t) * (2.0 * t - 1.0)) + 1.0);
}
}
class GooeyOverlay {
constructor(path1, path2) {
this.path1 = path1;
this.path2 = path2;
this.duration = 700;
this.delay = 400;
this.timeStart = Date.now();
this.direction = true;
}
open() {
this.direction = true;
this.timeStart = Date.now();
this.renderLoop();
}
close() {
this.direction = false;
this.timeStart = Date.now();
this.renderLoop();
}
updatePathOpen(time) {
const p = [
100 - ease.cubicInOut(Math.min(Math.max(time - 100, 0) / this.duration, 1)) * 100,
100 - ease.cubicInOut(Math.min(Math.max(time - 200, 0) / this.duration, 1)) * 100,
100 - ease.cubicInOut(Math.min(Math.max(time - 0, 0) / this.duration, 1)) * 100,
100 - ease.cubicInOut(Math.min(Math.max(time - 50, 0) / this.duration, 1)) * 100,
100 - ease.cubicInOut(Math.min(Math.max(time - 200, 0) / this.duration, 1)) * 100,
100 - ease.cubicInOut(Math.min(Math.max(time - 300, 0) / this.duration, 1)) * 100,
100 - ease.cubicInOut(Math.min(Math.max(time - 250, 0) / this.duration, 1)) * 100,
100 - ease.cubicInOut(Math.min(Math.max(time - 200, 0) / this.duration, 1)) * 100,
100 - ease.cubicInOut(Math.min(Math.max(time - 150, 0) / this.duration, 1)) * 100,
100 - ease.cubicInOut(Math.min(Math.max(time - 250, 0) / this.duration, 1)) * 100,
100 - ease.cubicInOut(Math.min(Math.max(time - 100, 0) / this.duration, 1)) * 100,
];
return `
M ${p[0]} 0 C ${p[0]} 5
${p[1]} 5 ${p[1]} 10 C ${p[1]} 15
${p[2]} 15 ${p[2]} 20 C ${p[2]} 25
${p[3]} 25 ${p[3]} 30 C ${p[3]} 35
${p[4]} 35 ${p[4]} 40 C ${p[4]} 45
${p[5]} 45 ${p[5]} 50 C ${p[5]} 55
${p[6]} 55 ${p[6]} 60 C ${p[6]} 65
${p[7]} 65 ${p[7]} 70 C ${p[7]} 75
${p[8]} 75 ${p[8]} 80 C ${p[8]} 85
${p[9]} 85 ${p[9]} 90 C ${p[9]} 95
${p[10]} 95 ${p[10]} 100
H 100
V 0
`;
}
updatePathClose(time) {
const p = [
100 - ease.cubicInOut(Math.min(Math.max(time - 100, 0) / this.duration, 1)) * 100,
100 - ease.cubicInOut(Math.min(Math.max(time - 200, 0) / this.duration, 1)) * 100,
100 - ease.cubicInOut(Math.min(Math.max(time - 0, 0) / this.duration, 1)) * 100,
100 - ease.cubicInOut(Math.min(Math.max(time - 50, 0) / this.duration, 1)) * 100,
100 - ease.cubicInOut(Math.min(Math.max(time - 200, 0) / this.duration, 1)) * 100,
100 - ease.cubicInOut(Math.min(Math.max(time - 300, 0) / this.duration, 1)) * 100,
100 - ease.cubicInOut(Math.min(Math.max(time - 250, 0) / this.duration, 1)) * 100,
100 - ease.cubicInOut(Math.min(Math.max(time - 200, 0) / this.duration, 1)) * 100,
100 - ease.cubicInOut(Math.min(Math.max(time - 150, 0) / this.duration, 1)) * 100,
100 - ease.cubicInOut(Math.min(Math.max(time - 250, 0) / this.duration, 1)) * 100,
100 - ease.cubicInOut(Math.min(Math.max(time - 100, 0) / this.duration, 1)) * 100,
];
return `
M 0 0
H ${p[0]} C ${p[0]} 5
${p[1]} 5 ${p[1]} 10 C ${p[1]} 15
${p[2]} 15 ${p[2]} 20 C ${p[2]} 25
${p[3]} 25 ${p[3]} 30 C ${p[3]} 35
${p[4]} 35 ${p[4]} 40 C ${p[4]} 45
${p[5]} 45 ${p[5]} 50 C ${p[5]} 55
${p[6]} 55 ${p[6]} 60 C ${p[6]} 65
${p[7]} 65 ${p[7]} 70 C ${p[7]} 75
${p[8]} 75 ${p[8]} 80 C ${p[8]} 85
${p[9]} 85 ${p[9]} 90 C ${p[9]} 95
${p[10]} 95 ${p[10]} 100
H 0
V 0
`;
}
render() {
if (this.direction) {
this.path1.setAttribute('d', this.updatePathOpen(Date.now() - this.timeStart));
this.path2.setAttribute('d', this.updatePathOpen(Date.now() - (this.timeStart + this.delay)));
} else {
this.path1.setAttribute('d', this.updatePathClose(Date.now() - (this.timeStart + this.delay)));
this.path2.setAttribute('d', this.updatePathClose(Date.now() - this.timeStart));
}
}
renderLoop() {
this.render();
if (Date.now() - this.timeStart >= this.duration + this.delay + 6000) {
if (!this.direction) {
this.open();
} else {
this.close();
}
} else {
requestAnimationFrame(() => {
this.renderLoop();
});
}
}
}
const path1 = document.getElementById('path01');
const path2 = document.getElementById('path02');
const gooeyOverlay = new GooeyOverlay(path1, path2);
gooeyOverlay.close();
@import url('https://fonts.googleapis.com/css?family=Baloo+Thambi');
html {
height: 100%;
}
body {
min-height: 100%;
overflow: hidden;
background-color: #FBA829;
}
svg {
position: absolute;
top: 0; right: 0; bottom: 0; left: 0;
z-index: 10;
path {
&.path01 {
fill: #222;
}
&.path02 {
fill: #111;
}
}
}
.p-summary {
position: absolute;
top: 0; right: 0; bottom: 0; left: 0;
display: flex;
align-items: center;
justify-content: center;
&__title {
text-align: center;
color: #111;
font-size: 10vw;
font-weight: 400;
font-family: 'Baloo Thambi', cursive;
letter-spacing: 0.1em;
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment