<nav class="nav" data-nav id="nav">
  <ul class="nav__items">
    <li class="nav__item">
      <a href="/" data-item>Services</a>
    </li>
    <li class="nav__item">
      <a href="/" data-item>Cases</a>
    </li>
    <li class="nav__item">
      <a href="/" data-item>Careers</a>
    </li>
    <li class="nav__item">
      <a href="/" data-item>Contact</a>
    </li>
  </ul>
</nav>

<a class="toggle" href="#" data-toggle>Navigation</a>
*,
*:before,
*:after {
  margin: 0;
  padding: 0;
  box-sizing: border-box;
}

html, 
body {
  width: 100%;
  height: 100%;
}

body {
  font-family: sans-serif;
  background-color: #fffeca;
}

.nav {
  position: fixed;
  top: 0;
  left: 0;
  width: 100%;
  height: 100%;
  background-color: #ffe400;
  
  transform: translateX(-100%);
}

.nav__items {
  padding: 20px;
  list-style: none;
}

.nav__item {
  display: flex;
  justify-content: center;
  overflow: hidden;
}

.nav__item a {
  display: block;
  padding-top: 10px;
  padding-bottom: 10px;
  
  font-size: 1.6rem;
  color: #00f;
  text-decoration: none;
  
  transform-origin: 100% 50%;
  will-change: transform;
}

.toggle {
  position: fixed;
  right: 20px;
  bottom: 20px;
  width: 40px;
  height: 40px;
  
  background-color: #00f;
  overflow: hidden;
  text-indent: 60px;
}
View Compiled
const nav = document.querySelector('[data-nav]')
const items = [...nav.querySelectorAll('[data-item]')]
const toggle = document.querySelector('[data-toggle]')

const reducedMotion = window.matchMedia('(prefers-reduced-motion: reduce)').matches

const duration = reducedMotion ? .01 : 400
const stagger = reducedMotion ? 0 : 50
const easing = 'cubic-bezier(.17,.67,.35,.98)'
let initial
let totalDuration = duration

const animations = []

animations.push(
  nav.animate({
    transform: ['translateX(-100%)', 'translateX(0%)'],
    offset: 0
  }, {
    duration,
    fill: 'both',
    easing
  })
)

items.forEach((item, index) => {
  animations.push(
    item.animate({
      transform: ['translateY(150%) rotate(-15deg)', 'translateY(0%) rotate(0deg)'],
      offset: 0
    },{
      duration,
      delay: duration * .5 + index * stagger,
      fill: 'both',
      easing
    })
 )
})

animations.forEach(animation => animation.pause())

function handleToggle(event) {
  event.preventDefault()

  if(!initial) {
    animations.forEach(item => item.play())
    initial = true
  } else {
    animations.forEach(item => item.reverse())
  }
}

toggle.addEventListener('click', handleToggle)
View Compiled
Run Pen

External CSS

This Pen doesn't use any external CSS resources.

External JavaScript

This Pen doesn't use any external JavaScript resources.