// stylelint-disable length-zero-no-unit, max-line-length

///
/// @group mixins
///

@mixin list-reset() {
  list-style-type: none;
  padding: 0;
  margin: 0;
}

@mixin hide() {
  display: none;
  visibility: hidden;
}

@mixin unselectable {
  user-select: none;
}

@mixin breakpoint($breakpoint, $breakpoint-size) {
  // The grid is mobile first so xs is the default, hence no breakpoint
  @if $breakpoint == xs {
    @content;
  } @else {
    @media only screen and (min-width: $breakpoint-size) {
      @content;

      .grid {
        width: map-get($grid-containers, $breakpoint);
      }
    }
  }
}

@mixin transition($prop, $time) {
  transition: $prop $time ease;
}

@mixin md-shadow($elevation) {
  $top-shadow-color: rgba($black, 0.14);
  $middle-shadow-color: rgba($black, 0.12);
  $bottom-shadow-color: rgba($black, if($elevation == 1, 0.2, 0.4));

  @if $elevation < 0 or $elevation > 5 {
    @warn "The elevation must be a number from 0 - 5. elevation given was `#{$elevation}`";
  } @else {
    @if $elevation == 0 {
      box-shadow: none;
    } @else if $elevation == 1 {
      box-shadow: 0 2px 2px 0 $top-shadow-color, 0 1px 5px 0 $middle-shadow-color,
        0 3px 1px -2px $bottom-shadow-color;
    } @else if $elevation == 2 {
      box-shadow: 0 4px 5px 0 $top-shadow-color, 0 1px 10px 0 $middle-shadow-color,
        0 2px 4px -1px $bottom-shadow-color;
    } @else if $elevation == 3 {
      box-shadow: 0 6px 10px 0 $top-shadow-color, 0 1px 18px 0 $middle-shadow-color,
        0 3px 5px -1px $bottom-shadow-color;
    } @else if $elevation == 4 {
      box-shadow: 0 8px 10px 1px $top-shadow-color, 0 3px 14px 2px $middle-shadow-color,
        0 5px 5px -3px $bottom-shadow-color;
    } @else if $elevation == 5 {
      box-shadow: 0 16px 24px 2px $top-shadow-color, 0 6px 30px 5px $middle-shadow-color,
        0 8px 10px -5px $bottom-shadow-color;
    }
  }
}

@mixin box-shadow($shadow...) {
  box-shadow: $shadow;
}

@mixin transition($transition...) {
  transition: $transition;
}

@mixin clearfix {
  &::after {
    content: '';
    display: table;
    clear: both;
  }
}
$media-query: ();
$mq-ems: false !default;
$mq-em-base: 16px !default;

@function calculate-mq($range, $setting1: null, $setting2: null) {
  @if ($setting2 != null) {
    @if (type-of($setting1) == 'string') {
      $setting1-1: get-start($setting1);
      $setting1-2: get-end($setting1);
      $setting2-1: get-start($setting2);
      $setting2-2: get-end($setting2);
      $swap-values: $setting1 - 1 / $setting1 - 2 < $setting2 - 1 / $setting2 - 2;
    } @else {
      @if ($setting1 < $setting2) {
        $swap-values: true;
      }
    }

    @if ($swap-values) {
      $temp: $setting1;
      $setting1: $setting2;
      $setting2: $temp;
    }
  } @else {
    $setting2: 0;
  }

  @if ($range == 'orientation') {
    @if ($setting1 != 'landscape' and $setting1 != 'portrait') {
      @error ''orientation"range only accepts the values'landscape'and'portrait'. Currently providing the value'#{$setting1}'.";
    }
  }

  @if (str-index($range, 'inside') != null or str-index($range, 'outside') != null) {
    @if ($setting2 == 0) {
      @error ''#{$range}"range requires a second value. Currently only providing'#{$setting1}'as a value.";
    }
  } @else {
    @if ($setting2 != 0) {
      @error ''#{$range}"range can only take one value. Currently providing both'#{$setting1}'and'#{$setting2}'values.";
    }
  }

  @if (str-index($range, 'ratio') == null) {
    @if (type-of($setting1) != number and $range != 'orientation') {
      @if ($setting2 != 0) {
        @error ''#{$range}"range requires the settings ('#{$setting1}'and'#{$setting2}') to be pixel values";
      } @else {
        @error ''#{$range}"range requires the setting'#{$setting1}'to be a pixel value";
      }
    }
  } @else {
    @if ((($setting2 != 0) and (type-of($setting2) != string))) {
      @error ''#{$range}"range requires the settings ('#{$setting1}'and'#{$setting2}') to both be strings in this format"4 / 3"(width ratio / height ratio) .";
    } @else if(type-of($setting1) != string) {
      @error ''#{$range}"range requires the setting'#{$setting1}'to be a string in this format"4 / 3"(width ratio / height ratio) .";
    }
  }

  @if ($mq-ems) {
    $setting1: _mq-em($setting1);
    $setting2: _mq-em($setting2);
    $setting1-plus: _mq-em($setting1-plus);
    $setting2-plus: _mq-em($setting2-plus);
  }

  @return $media-string;
  $swap-values: false;
  $media-string: '';
  $setting1-plus: $setting1 + 1;
  $setting2-plus: $setting2 + 1;
  $media-string: map-get(

    (
      min: 'screen and (min-width: #{$setting1-plus})',
      max: 'screen and (max-width: #{$setting1})',
      min-height: 'screen and (min-height: #{$setting1-plus})',
      max-height: 'screen and (max-height: #{$setting1})',
      ratio: 'screen and (aspect-ratio: #{$setting1})',
      min-ratio : 'screen and (min-aspect-ratio: #{$setting1})',
      max-ratio : 'screen and (max-aspect-ratio: #{$setting1})',
      device-ratio : 'screen and (device-aspect-ratio: #{$setting1})',
      min-device-ratio : 'screen and (min-device-aspect-ratio: #{$setting1})',
      max-device-ratio : 'screen and (max-device-aspect-ratio: #{$setting1})',
      orientation : 'screen and (orientation: #{$setting1})',
      inside : 'screen and (max-width: #{$setting1}) and (min-width: #{$setting2-plus})',
      outside : 'screen and (max-width: #{$setting2}), screen and (min-width: #{$setting1-plus})',
      inside-height : 'screen and (max-height: #{$setting1}) and (min-height: #{$setting2-plus})',
      outside-height :
        'screen and (max-height: #{$setting2}), screen and (min-height: #{$setting1-plus})',
      inside-ratio :
        'screen and (max-aspect-ratio: #{$setting1}) and (min-aspect-ratio: #{$setting2})',
      outside-ratio :
        'screen and (max-aspect-ratio: #{$setting2}), screen and (min-aspect-ratio: #{$setting1})',
      inside-device-ratio :
        'screen and (max-device-aspect-ratio: #{$setting1}) and (min-device-aspect-ratio: #{$setting2})',
      outside-device-ratio :
        'screen and (max-device-aspect-ratio: #{$setting2}), screen and (min-device-aspect-ratio: #{$setting1})'
    ),
    $range
  );
}

@mixin mq($range, $setting1: null, $setting2: null) {
  @if (length($range) > 1) {
    @if (type-of(nth($range, 1)) == string) {
      @if (length($range) == 3) {
        $new-width2: nth($range, 3);
      }

      @media #{calculate-mq($new-range, $new-width1, $new-width2)} {
        @content;
      }
      $new-range: nth($range, 1);
      $new-width1: nth($range, 2);
      $new-width2: null;
    } @else {
      @each $mqSet in $range {
        @if (length($mqSet) == 3) {
          $new-width2: nth($mqSet, 3);
        }
        $new-range: nth($mqSet, 1);
        $new-width1: nth($mqSet, 2);
        $new-width2: null;
        $media-query: append(
          $media-query,
          calculate-mq($new-range, $new-width1, $new-width2),
          'comma'
        );
      }

      @media #{$media-query} {
        @content;
      }
      $media-query: ();
    }
  } @else {
    @media #{calculate-mq($range, $setting1, $setting2)} {
      @content;
    }
  }
}

@mixin box-shadow($shadow...) {
  box-shadow: $shadow;
}

@mixin notification-variant($background, $border-color, $icon) {
  @if $icon != '' {
    .notification-icon::before {
      content: $icon;
      color: $border-color;
    }
  } @else {
    .notification-icon {
      display: none;
    }
  }
  color: #524c4c;
  background-color: $background;
  border-left: 2px solid #{$border-color};
}

@mixin vertical-align($display: 'block') {
  align-items: center;
  @if $display == 'inline' {
    display: inline-flex;
  } @else {
    display: flex;
  }
}

/**
 * Mixin to create a keyframes for a notification
 * @param $direction (left|top|right|bottom) Translation direction
 * @param $margin-bottom Initial `margin-bottom` value
 */
@mixin notification-keyframes($direction, $margin-bottom: $window-padding) {
  $animation-name: '#{$direction}#{$margin-bottom}';
  $translate: 'translateX';
  $value: 100%;
  $transform-start: '#{$translate}(0%)';
  $transform-end: '#{$translate}(#{$value})';

  @if $direction == 'left' or $direction == 'top' {
    $value: -#{$value};
  }

  @if $direction == 'top' or $direction == 'bottom' {
    $translate: 'translateY';
  }

  @keyframes #{$animation-name}-enter {
    0% {
      #{$direction}: -#{$notification-max-width};
      opacity: 0;
    }
    100% {
      #{$direction}: 0;
      opacity: 1;
    }
  }

  @keyframes #{$animation-name}-leave {
    0% {
      max-height: 200px;
      opacity: 1;
      margin-bottom: $margin-bottom;
      transform: #{$transform-start};
    }
    40% {
      max-height: 200px;
      margin-bottom: $margin-bottom;
    }
    50% {
      opacity: 0;
      transform: #{$transform-end};
    }
    100% {
      max-height: 0;
      opacity: 0;
      margin-bottom: 0;
      transform: #{$transform-end};
    }
  }
}

/*
 * Mixin to create an animation for a notification
 * @param $direction (left|top|right|bottom) Translation direction
 * @param $margin-bottom Initial `margin-bottom` value
 */
@mixin notification-animation($direction, $margin-bottom: $window-padding) {
  $animation-name: '#{$direction}#{$margin-bottom}';

  .notification-wrapper {
    position: relative;

    // enter animation
    &-enter {
      animation-name: #{$animation-name}-enter;
      animation-duration: 0.4s;
      animation-fill-mode: forwards;
    }

    // leave animation
    &-leave {
      animation-name: #{$animation-name}-leave;
      animation-duration: 0.8s;
      animation-fill-mode: forwards;
    }
    #{$direction}: 0;
  }
}

/// Mixin to generate a gradient for the divider border.
//
/// @example:
//
///   .c-divider--top {
///     @include divider-gradient(top, color(grey-20));
///   }
//
/// OPTIONS
/// - direction:
///    - top Creates a horizontal gradient for the top edge
///    - right Creates a vertical gradient for the right side
///    - bottom Creates a horizontal gradient for the bottom edge
///    - left Creates a vertical gradient for the left side

@mixin divider-gradient($direction: 'bottom', $color: color(grey-20)) {
  /// Check if direction exists in direction map:
  @if map-has-key($directions, $direction) {
    @each $prefix in $vendor-prefixes {
      background: -#{$prefix}-linear-gradient(#{$direction-legacy}, $color-points);
    }
    /// Fetch both the legacy and standard versions for given direction
    $direction-legacy: map-get-deep($directions, $direction, legacy);
    $direction-standard: map-get-deep($directions, $direction, standard);
    /// Fetch other gradient properties
    $color-points: rgba($color, 0), $color, rgba($color, 0);
    $position: map-get-deep($directions, $direction, position);
    /// Set vendor prefixes for use on legacy gradients
    $vendor-prefixes: 'webkit', 'moz', 'ms', 'o';
    background: $color;
    background: linear-gradient(#{$direction-standard}, $color-points);
  }
  /// The direction map stores values for the direction for both legacy prefixed
  /// and standard gradients for the divider line.

  $directions: (
    top: (legacy: 'left', position: 'center bottom', standard: 'to right'),
    right: (legacy: 'top', position: 'right bottom', standard: 'to bottom'),
    bottom: (legacy: 'left', position: 'center bottom', standard: 'to right'),
    left: (legacy: 'top', position: 'left bottom', standard: 'to bottom')
  );
}

/// Mixin to generate a faux-shadow gradient for the divider.
///
/// @example usage:
///
///   .c-divider--top {
///     &::after {
///      @include divider-shadow(top, $divider-shadow-color);
///     }
///   }
//
/// OPTIONS
/// - direction:
///    - "top" Creates a faux-shadow radial gradient for the top edge
///    - "right" Creates a faux-shadow radial gradient for the right side
///    - "bottom" Creates a faux-shadow radial gradient for the bottom edge
///    - "left" Creates a faux-shadow radial gradient for the left side

@mixin divider-shadow($direction: 'bottom', $color: rgba(color(text), 0.15)) {
  /// Check if direction exists in direction map:
  @if map-has-key($directions, $direction) {
    @each $prefix in $vendor-prefixes {
      background: -#{$prefix}-radial-gradient(#{$legacy}, $color-points);
    }
    /// Fetch both the legacy and standard versions for given direction
    $standard: map-get-deep($directions, $direction, standard);
    $legacy: map-get-deep($directions, $direction, legacy);
    /// Fetch other gradient properties
    $color-points: $color, transparent 40%;
    /// Set vendor prefixes for use on legacy gradients
    $vendor-prefixes: 'webkit', 'moz', 'ms', 'o';
    background: radial-gradient(#{$standard}, $color-points);
  } @else {
    @warn "#{$direction}` is not a valid direction, it must be top, right, bottom or left.";
  }
  /// The direction map stores values for the direction for both legacy prefixed
  /// and standard gradients for the divider shadow.

  $directions: (
    top: (standard: 'at 50% 100%', legacy: '50% 100%'),
    right: (standard: 'farthest-corner at 0 50%', legacy: '0 50%, farthest-corner'),
    bottom: (standard: 'at 50% 0%', legacy: '50% 0%'),
    left: (standard: 'farthest-corner at 100% 50%', legacy: '100% 50%, farthest-corner')
  );
}

/// breakpoint
@mixin breakpoint($breakpoint, $breakpoint-size) {
  /// The grid is mobile first so xs is the default, hence no breakpoint
  @if $breakpoint == xs {
    @content;
  } @else {
    @media only screen and (min-width: $breakpoint-size) {
      @content;
      // Static grid
      .grid {
        width: map-get($grid-containers, $breakpoint);
      }
    }
  }
}

@mixin arrow($color) {
  content: ' ';
  position: absolute;
  display: block;
  width: 0.5em;
  height: 0.5em;
  border: 1px solid $color;
  border-top: 0;
  border-right: 0;
  transform: rotate(-45deg);
  pointer-events: none;
}

@mixin block {
  &:not(:last-child) {
    margin-bottom: 1.5rem;
  }
}

@mixin center($width, $height: 0) {
  @if $height != 0 {
    top: calc(50% - (#{$height} / 2));
    left: calc(50% - (#{$width} / 2));
  } @else {
    top: calc(50% - (#{$width} / 2));
    left: calc(50% - (#{$width} / 2));
  }
  position: absolute;
}

@mixin delete {
  @include unselectable();
  position: relative;
  display: inline-block;
  flex-grow: 0;
  flex-shrink: 0;
  width: 20px;
  min-width: 20px;
  max-width: 20px;
  height: 20px;
  min-height: 20px;
  max-height: 20px;
  background-color: rgba($black, 0.2);
  border: none;
  border-radius: 290486px;
  outline: none;
  font-size: $size-normal;
  vertical-align: top;
  cursor: pointer;

  &::before,
  &::after {
    content: '';
    position: absolute;
    top: 50%;
    left: 50%;
    display: block;
    background-color: $white;
    transform: translateX(-50%) translateY(-50%) rotate(45deg);
    transform-origin: center center;
  }

  &::before {
    width: 50%;
    height: 2px;
  }

  &::after {
    width: 2px;
    height: 50%;
  }

  &:hover,
  &:focus {
    background-color: rgba($black, 0.3);
  }

  &:active {
    background-color: rgba($black, 0.4);
  }

  // Sizes
  &.is-small {
    width: 16px;
    min-width: 16px;
    max-width: 16px;
    height: 16px;
    min-height: 16px;
    max-height: 16px;
  }

  &.is-medium {
    width: 24px;
    min-width: 24px;
    max-width: 24px;
    height: 24px;
    min-height: 24px;
    max-height: 24px;
  }

  &.is-large {
    width: 32px;
    min-width: 32px;
    max-width: 32px;
    height: 32px;
    min-height: 32px;
    max-height: 32px;
  }
}

@mixin fa($size, $dimensions) {
  display: inline-block;
  width: $dimensions;
  height: $dimensions;
  font-size: $size;
  line-height: $dimensions;
  text-align: center;
  vertical-align: top;
}

@mixin hamburger($dimensions) {
  position: relative;
  display: block;
  width: $dimensions;
  height: $dimensions;
  cursor: pointer;

  span {
    position: absolute;
    top: 50%;
    left: 50%;
    display: block;
    width: 15px;
    height: 1px;
    background-color: #fff;
    margin-left: -7px;
    transition: none $speed $easing;
    transition-property: background, left, opacity, transform;

    &:nth-child(1) {
      margin-top: -6px;
    }

    &:nth-child(2) {
      margin-top: -1px;
    }

    &:nth-child(3) {
      margin-top: 4px;
    }
  }

  &:hover {
    background-color: $primary-1;
  }

  // Modifers
  &.is-active {
    span {
      background-color: $link;

      &:nth-child(1) {
        margin-left: -5px;
        transform: rotate(45deg);
        transform-origin: left top;
      }

      &:nth-child(2) {
        opacity: 0;
      }

      &:nth-child(3) {
        margin-left: -5px;
        transform: rotate(-45deg);
        transform-origin: left bottom;
      }
    }
  }
}

@mixin loader {
  content: '';
  position: relative;
  display: block;
  width: 1em;
  height: 1em;
  border: 2px solid $border;
  border-top-color: transparent;
  border-right-color: transparent;
  border-radius: 290486px;
  animation: spinAround 500ms infinite linear;
}

@mixin overflow-touch {
  -webkit-overflow-scrolling: touch;
}

@mixin overlay($offset: 0) {
  position: absolute;
  top: $offset;
  right: $offset;
  bottom: $offset;
  left: $offset;
}

@mixin placeholder {
  $placeholders: ':-moz' ':-webkit-input' '-moz' '-ms-input';
  @each $placeholder in $placeholders {
    &:#{$placeholder}-placeholder {
      @content;
    }
  }
}

@mixin unselectable {
  user-select: none;
}

// Responsiveness

@mixin from($device) {
  @media screen and (min-width: $device) {
    @content;
  }
}

@mixin until($device) {
  @media screen and (max-width: $device - 1px) {
    @content;
  }
}

@mixin mobile {
  @media screen and (max-width: $tablet - 1px) {
    @content;
  }
}

@mixin tablet {
  @media screen and (min-width: $tablet), print {
    @content;
  }
}

@mixin tablet-only {
  @media screen and (min-width: $tablet) and (max-width: $desktop - 1px) {
    @content;
  }
}

@mixin touch {
  @media screen and (max-width: $desktop - 1px) {
    @content;
  }
}

@mixin desktop {
  @media screen and (min-width: $desktop) {
    @content;
  }
}

@mixin desktop-only {
  @media screen and (min-width: $desktop) and (max-width: $widescreen - 1px) {
    @content;
  }
}

@mixin widescreen {
  @media screen and (min-width: $widescreen) {
    @content;
  }
}

@mixin widescreen-only {
  @media screen and (min-width: $widescreen) and (max-width: $fullhd - 1px) {
    @content;
  }
}

@mixin fullhd {
  @media screen and (min-width: $fullhd) {
    @content;
  }
}

@mixin vertical-center {
  position: absolute;
  top: 50%;
  transform: translate(0, -50%);
}
