/*
  @function get-breakpoint-directions

  Sorts through breakpoints SASS map,
  generates a full SASS map containing all the breakpoint
  variations we'll require

  Parameters:
  none
*/
@function get-breakpoint-directions() {
  $_bps: ();
  @each $k, $bp in $breakpoints {
    $_bps: map-merge($_bps, ($k: $bp));
    $start: map-get($bp, start);
    $end: map-get($bp, end);

    @if $end != null and $start != null {
      $down-key: unquote($k + '-');
      $_bps: map-merge($_bps, ($down-key: (
        start: null,
        end: $end
      )));
    }

    @if $start != null and $end != null {
      $up-key: unquote($k) + '+';
      $_bps: map-merge($_bps, ($up-key: (
        start: $start,
        end: null
      )));
    }
  }

  @return $_bps;
}

$breakpoints-with-directions: get-breakpoint-directions();

/*
  @mixin breakpoint

  Inserts a media query

  Parameters:
  $name - name of breakpoint, choose from:

  xsmall, small, medium, large, xlarge, xxlarge  - *just* that breakpoint
  small-, medium-, large-, xlarge-, xxlarge-  - that breakpoint *and* below
  xsmall+, small+, medium+, large+, xlarge+  - that breakpoint *and* up

  NB: the we're mobile up, so the minus values should be avoided..

  $option - ie11, hover - to make an IE11 CSS with a breakpoint or to target browsers with mouse cursors

  ```scss
  @include breakpoint('medium+') {
    // styles to be given to browsers at `medium` and above
  }
  @include breakpoint(null,'hover') {
    // styles to be given to devices with mouse pointers
  }
  @include breakpoint(null,'ie11') {
    // styles to be given to be given to IE11
  }
  @include breakpoint('medium+','hover') {
    // styles to be given to browsers at `medium` and above that have mouse pointers
  }
  @include breakpoint('medium+','ie11') {
    // styles to be given to ie11 at `medium` and above
  }
  ```
*/

@mixin breakpoint($name, $option:'') {
  $points: map-get($breakpoints-with-directions, $name);
  @if ($name and $points) {
    $media: get-media($points);
    $start: map-get($media, 'start');
    $end: map-get($media, 'end');
    $str: 'screen and (';
    @if($start != null) {
      $str: $str + 'min-width: ' + ($start * 1px);
    }
    @if($start != null and $end != null) {
      $str: $str + ') and ('
    }
    @if($end != null) {
      $str: $str + 'max-width: ' + ($end * 1px);
    }
    $str: $str + ')';
    @if($option == 'hover') {
      $str1: $str + ' and (-moz-touch-enabled: 0), ';
      $str2: $str + ' and (pointer: fine)';
      $str: $str1 + $str2;
    }
    @if($option == 'ie11') {
      $str1: $str + ' and (-ms-high-contrast: none), ';
      $str2: $str + ' and (-ms-high-contrast: active)';
      $str: $str1 + $str2;
    }
    @media #{$str} {
      @content;
    }
  } @else if ($option == 'hover') {
    @media (-moz-touch-enabled: 0), (pointer: fine) {
      @content;
    }
  } @else if ($option == 'ie11') {
    @media screen and (-ms-high-contrast: none), screen and (-ms-high-contrast: active) {
      @content;
    }
  } @else {
    @warn "Unknown breakpoint `#{$name}` in $breakpoints.";
  }
}


/*
  @function get-media

  Returns start and stop points of a given media query

  Parameters:
  $bp - the breakpoint you want the stop and stop points of
*/

@function get-media($bp) {
  $start: null;
  $end: null;

  $bp-start: map-get($bp, 'start');
  $bp-end: map-get($bp, 'end');
  @if($bp-start != null and ($start == null or $bp-start < $start)) {
    $start: $bp-start;
  }
  @if($bp-end != null and ($end == null or $bp-end > $end)) {
    $end: $bp-end;
  }

  @return (
    start: $start,
    end: $end
  );
}
