/* Standalone 3D Ball Loader
   Based on the original Uiverse.io animation by Mahmoud-walid.
*/

:root {
  --loader-ball-size: 60px;
  --loader-duration: 1.2s;
  --loader-bg: #ffffff;
  --loader-line: #333333;
  --loader-ball-light: #ff8c16;
  --loader-ball-dark: #b35100;
}

/* Full-screen loader */
.loader {
  position: fixed;
  inset: 0;
  z-index: 99999;
  display: grid;
  place-items: center;
  overflow: hidden;
  background: var(--loader-bg);
  opacity: 1;
  visibility: visible;
  transition:
    opacity 400ms ease,
    visibility 400ms ease;
}

/* Added by loader.js when loading is complete */
.loader.is-hidden {
  opacity: 0;
  visibility: hidden;
  pointer-events: none;
}

/* Animation scene */
.loader__scene {
  position: relative;
  width: 150px;
  height: 170px;
  display: flex;
  align-items: center;
  justify-content: center;
  perspective: 500px;
}

/* Ball */
@keyframes rotateBall {
  0% {
    transform: rotateY(0deg) rotateX(0deg) rotateZ(0deg);
  }

  50% {
    transform: rotateY(360deg) rotateX(360deg) rotateZ(0deg);
  }

  100% {
    transform: rotateY(720deg) rotateX(720deg) rotateZ(360deg);
  }
}

@keyframes bounceBall {
  0% {
    transform: translateY(-70px) scale(1, 1);
  }

  15% {
    transform: translateY(-56px) scale(1, 1);
  }

  45% {
    transform: translateY(70px) scale(1, 1);
  }

  50% {
    transform: translateY(73.5px) scale(1, 0.92);
  }

  55% {
    transform: translateY(70px) scale(1, 0.95);
  }

  85% {
    transform: translateY(-56px) scale(1, 1);
  }

  95%,
  100% {
    transform: translateY(-70px) scale(1, 1);
  }
}

.ball {
  position: relative;
  z-index: 2;
  width: var(--loader-ball-size);
  height: var(--loader-ball-size);
  border-radius: 50%;
  transform-style: preserve-3d;
  animation:
    bounceBall var(--loader-duration)
    cubic-bezier(0.42, 0, 0.58, 1)
    infinite;
  will-change: transform;
}

.ball::before {
  position: absolute;
  inset: -3px -6px;
  width: calc(100% + 6px);
  height: calc(100% + 6px);
  content: "";
  border: 2px solid var(--loader-line);
  border-radius: 50%;
  background:
    radial-gradient(
      circle at 36px 20px,
      var(--loader-ball-light),
      var(--loader-ball-dark)
    );
  transform: translateZ(1px);
}

/* Rotating internal lines */
.ball .inner {
  position: absolute;
  width: 100%;
  height: 100%;
  border-radius: 50%;
  transform-style: preserve-3d;
  animation: rotateBall 25s linear infinite;
  will-change: transform;
}

.ball .line::before,
.ball .line::after {
  position: absolute;
  width: 99%;
  height: 99%;
  content: "";
  border: 2px solid var(--loader-line);
  border-radius: 50%;
}

.ball .line::before {
  transform: rotate3d(0, 0, 0, 0);
}

.ball .line::after {
  transform: rotate3d(1, 0, 0, 90deg);
}

.ball .line--two::before {
  transform: rotate3d(0, 0, 0, 2deg);
}

.ball .line--two::after {
  transform: rotate3d(1, 0, 0, 88deg);
}

.ball .oval::before,
.ball .oval::after {
  position: absolute;
  width: 99%;
  height: 99%;
  content: "";
  border-top: 4px solid var(--loader-line);
  border-radius: 50%;
}

.ball .oval::before {
  transform: rotate3d(1, 0, 0, 45deg) translate3d(0, 0, 6px);
}

.ball .oval::after {
  transform: rotate3d(1, 0, 0, -45deg) translate3d(0, 0, -6px);
}

.ball .oval--two::before {
  transform: rotate3d(1, 0, 0, 135deg) translate3d(0, 0, -6px);
}

.ball .oval--two::after {
  transform: rotate3d(1, 0, 0, -135deg) translate3d(0, 0, 6px);
}

/* Shadow */
@keyframes bounceShadow {
  0% {
    opacity: 0.6;
    filter: blur(3px);
    transform: translateY(73px) scale(0.5, 0.5);
  }

  45%,
  55% {
    opacity: 0.9;
    filter: blur(1px);
    transform: translateY(73px) scale(1, 1);
  }

  100% {
    opacity: 0.6;
    filter: blur(3px);
    transform: translateY(73px) scale(0.5, 0.5);
  }
}

.shadow {
  position: absolute;
  z-index: 1;
  width: 54px;
  height: 6px;
  border-radius: 50%;
  background: #000;
  transform: translateY(73px);
  animation:
    bounceShadow var(--loader-duration)
    cubic-bezier(0.42, 0, 0.58, 1)
    infinite;
  will-change: transform, opacity, filter;
}

/* Reduced motion accessibility */
@media (prefers-reduced-motion: reduce) {
  .ball,
  .ball .inner,
  .shadow {
    animation: none;
  }

  .ball {
    transform: translateY(0);
  }

  .shadow {
    transform: translateY(73px);
    opacity: 0.7;
    filter: blur(2px);
  }
}

/* Small screens */
@media (max-width: 480px) {
  .loader__scene {
    transform: scale(0.9);
  }
}
