- let data = [
- 'eggnog ice cream',
- 'double choc muffins',
- 'salted caramel truffles',
- 'honey crepes',
- 'caramel pecan brownies',
- 'festive gingerbread',
- 'salted caramel macarons',
- 'chocolate lava cakes',
- 'mini apple pies',
- 'lemon cupcakes',
- 'baba au rhum',
- 'ricciarelli'
- ];
- let n = data.length;
- let base = 'https://assets.codepen.io/2017/ex_1_bg_';
body(style=`--n: ${n}; --k: -1; --exp: 0`)
style
- for(let i = 0; i < n; i++)
- let c = data[i];
| .i:nth-child(#{i + 1}) {
| --idx: #{i};
| --img: url('#{base}#{c.split(' ').join('_')}.jpg')
| }
header
h1 the yummy planet
nav#top
- for(let i = 0; i < n; i++)
- let c = data[i];
a.i(href=`#${c.split(' ').join('-')}` aria-label=c)
span(aria-hidden='true') #{c}
main
- for(let i = 0; i < n; i++)
- let c = data[i];
article.i(id=`${c.split(' ').join('-')}`)
h2 #{data[i]} recipe
- let p = Math.round(3*(1 + Math.random()));
- for(let j = 0; j < p; j++)
p(style=`width: ${10 + Math.round(90*Math.random())}%`)
a.b(href='#top') back
View Compiled
$html-s: 1.25;
$head-p: Min(.5rem, 5vmin);
$head-s: clamp(1em, 8vw, 2em);
$head-l: 2;
$te: .3s;
$dt: .05s;
$ts: .8s;
$tr: .7s;
@property --dt0 {
syntax: '<time>';
initial-value: 0s;
inherits: true
}
@property --dt1 {
syntax: '<time>';
initial-value: 0s;
inherits: true
}
* { margin: 0; padding: 0; list-style: none; color: inherit; font: inherit }
html {
font: var(--html-s, 1.25em)/ 1.5 ubuntu, trebuchet ms, sans-serif;
@media (max-width: 360px) { --html-s: 1em }
@media (max-width: 240px) { --html-s: .75em }
}
body, header, main { display: grid }
body {
--not-exp: calc(1 - var(--exp));
--i: var(--narr, 1);
--not-i: calc(1 - var(--i));
--head-h: calc(#{$head-l}*#{$head-s} + 2*#{$head-p});
overflow-x: hidden;
overflow-y: var(--narr, scroll);
min-height: 100vh;
background: #262626;
scrollbar-width: thin;
scrollbar-color: drimgrey rgba(#000, .1);
&::-webkit-scrollbar {
z-index: 3;
width: 8px;
background: rgba(#000, .1)
}
&::-webkit-scrollbar-track {
background: rgba(#000, .1)
}
&::-webkit-scrollbar-thumb {
background: dimgrey;
}
@media (min-width: 740px),
(orientation: landscape) { --narr: 0 }
}
header, main, article { grid-area: 1/ 1 }
header {
z-index: 2;
pointer-events: none
}
h1, a { pointer-events: auto }
h1 {
box-sizing: border-box;
position: fixed;
z-index: 2;
padding: $head-p;
width: calc(var(--i)*100vh + var(--not-i)*100%);
transform-origin: 0 0;
transform:
rotate(calc(var(--i)*-90deg))
translatex(calc(var(--i)*-100%));
color: gainsboro;
background: dimgray;
font-family: z003, segoe script, cursive;
font-size: $head-s;
line-height: $head-l;
}
nav, main {
margin: calc(var(--not-i)*var(--head-h)) 0 0 calc(var(--i)*var(--head-h))
}
nav {
display: flex;
flex-direction: var(--narr, column);
max-width: 100%;
}
.i {
--abs: Max(var(--k) - var(--idx), var(--idx) - var(--k));
--not-sel: Min(1, var(--abs));
--sel: calc(1 - var(--not-sel));
}
a.i {
flex: 1;
place-content: center;
overflow: hidden;
min-width: calc(var(--not-i)*(var(--not-sel)*2em + var(--sel)*15em));
min-height: calc(var(--i)*(var(--not-sel)*2em + var(--sel)*15em));
transform:
translate(calc(var(--i)*var(--exp)*-100%),
calc(var(--not-i)*var(--exp)*-100%));
background:
linear-gradient(-45deg,
transparent calc(50% - 1.5em),
rgba(#000, var(--sel)) 0 calc(50% + 1.5em),
transparent 0),
var(--img) 50%/cover;
background-blend-mode: color;
text-decoration: none;
filter: Saturate(var(--sel));
--dt0: calc(var(--abs)*#{$dt});
transition:
min-width $te ease-out calc(var(--not-sel)*#{$te}),
min-height $te ease-out calc(var(--not-sel)*#{$te}),
transform $ts ease-in-out calc(var(--dt0) + var(--not-exp)*#{$tr}),
filter $te ease-out;
pointer-events: auto
}
span {
position: absolute;
top: 50%; left: 50%;
width: 25em;
transform:
translate(-50%, -50%)
rotate(-45deg);
opacity: var(--sel);
background: rgba(#000, .1);
color: #fff;
font-weight: 700;
line-height: 3;
text-align: center;
text-shadow: 1px 1px #000;
text-transform: uppercase;
white-space: nowrap;
transition: opacity $te ease-out;
pointer-events: none
}
main {
--max: Max(var(--k), var(--n) - var(--k) - 1);
overflow: hidden;
}
article {
z-index: var(--sel);
margin: 5vmin;
padding: 5vmin;
border-radius: 7px;
transform:
perspective(75em)
rotatey(calc(var(--not-exp)*90deg));
opacity: var(--sel);
background: var(--img) 50%/ cover silver;
background-blend-mode: screen;
--dt1: calc(var(--max)*#{$dt});
transition:
transform $tr calc(var(--exp)*(var(--dt1) + #{$ts}))
cubic-bezier(var(--not-exp), 0, var(--not-exp), 1)
}
p {
margin: .5em 0;
min-height: 2em;
background: dimgrey;
}
.b {
display: inline-block;
padding: 0 .375em;
border-radius: 5px;
background: crimson;
color: whitesmoke;
text-decoration: none;
&::before {
display: inline-block;
margin-right: .25em;
content: '«'
}
}
View Compiled
const _BODY = document.body,
_NAVI = document.querySelector('nav'),
_MAIN = document.querySelector('main'),
S = _BODY.style;
let k = -1;
function select(e) {
const _t = e.target;
if(_t.tagName.toLowerCase() === 'a' &&
_t.classList.contains('i')) {
let newk = +getComputedStyle(_t).getPropertyValue('--idx');
if(newk !== k) S.setProperty('--k', k = newk)
}
}
function remove(e) {
const _t = e.target;
if(_t.tagName.toLowerCase() === 'a' &&
_t.classList.contains('i'))
S.setProperty('--k', k = -1)
}
_NAVI.addEventListener('focusin', select);
_NAVI.addEventListener('mouseover', select);
_NAVI.addEventListener('blur', remove);
_NAVI.addEventListener('mouseout', remove);
_BODY.addEventListener('click', e => {
let _t = e.target;
if(_t.classList.contains('i')) {
_MAIN.style.setProperty('--k', k);
S.setProperty('--exp', 1)
}
if(_t.classList.contains('b')) {
S.setProperty('--exp', 0);
_BODY.style.setProperty('--k', k = +_MAIN.style.getPropertyValue('--k'));
}
});
View Compiled
This Pen doesn't use any external CSS resources.
This Pen doesn't use any external JavaScript resources.