/*
Copyright (c) 2018 Uber Technologies, Inc.

This source code is licensed under the MIT license found in the
LICENSE file in the root directory of this source tree.
*/
import { styled } from '../styles/index.js';

function build(breakpoints) {
  var styles = {};
  var mediaQueries = Object.keys(breakpoints).map(function (size) {
    return "@media screen and (min-width: ".concat(breakpoints[size], "px)");
  });
  return {
    apply: function apply(_ref) {
      var property = _ref.property,
          _ref$transform = _ref.transform,
          transform = _ref$transform === void 0 ? function (x) {
        return x;
      } : _ref$transform,
          value = _ref.value;

      if (value === null || value === undefined) {
        return;
      }

      if (Array.isArray(value)) {
        value.forEach(function (v, index) {
          // Do not create a media query for the smallest breakpoint.
          if (index === 0) {
            styles[property] = transform(v);
            return;
          }

          var mediaQuery = mediaQueries[index - 1];

          if (!styles[mediaQuery]) {
            styles[mediaQuery] = {};
          }

          styles[mediaQuery][property] = transform(v);
        });
      } else {
        styles[property] = transform(value);
      }
    },
    value: function value() {
      return styles;
    }
  };
}

export var StyledBlock = styled('div', function (props) {
  var _props$$theme = props.$theme,
      breakpoints = _props$$theme.breakpoints,
      colors = _props$$theme.colors,
      typography = _props$$theme.typography,
      sizing = _props$$theme.sizing;

  var get = function get(obj, key) {
    return obj[key];
  };

  var getScale = function getScale(size) {
    return sizing[size] || size;
  };

  var styles = build(breakpoints);
  styles.apply({
    property: 'color',
    value: get(props, '$color'),
    transform: function transform(color) {
      return colors[color] || color;
    }
  });
  styles.apply({
    property: 'fontFamily',
    value: get(props, '$font'),
    transform: function transform(font) {
      return typography[font].fontFamily;
    }
  });
  styles.apply({
    property: 'fontWeight',
    value: get(props, '$font'),
    transform: function transform(font) {
      return typography[font].fontWeight;
    }
  });
  styles.apply({
    property: 'fontSize',
    value: get(props, '$font'),
    transform: function transform(font) {
      return typography[font].fontSize;
    }
  });
  styles.apply({
    property: 'lineHeight',
    value: get(props, '$font'),
    transform: function transform(font) {
      return typography[font].lineHeight;
    }
  });
  styles.apply({
    property: 'alignContent',
    value: get(props, '$alignContent')
  });
  styles.apply({
    property: 'alignItems',
    value: get(props, '$alignItems')
  });
  styles.apply({
    property: 'alignSelf',
    value: get(props, '$alignSelf')
  });
  styles.apply({
    property: 'display',
    value: get(props, '$display')
  });
  styles.apply({
    property: 'flex',
    value: get(props, '$flex')
  });
  styles.apply({
    property: 'flexDirection',
    value: get(props, '$flexDirection')
  });
  styles.apply({
    property: 'grid',
    value: get(props, '$grid')
  });
  styles.apply({
    property: 'gridArea',
    value: get(props, '$gridArea')
  });
  styles.apply({
    property: 'gridAutoColumns',
    value: get(props, '$gridAutoColumns')
  });
  styles.apply({
    property: 'gridAutoFlow',
    value: get(props, '$gridAutoFlow')
  });
  styles.apply({
    property: 'gridAutoRows',
    value: get(props, '$gridAutoRows')
  });
  styles.apply({
    property: 'gridColumn',
    value: get(props, '$gridColumn')
  });
  styles.apply({
    property: 'gridColumnEnd',
    value: get(props, '$gridColumnEnd')
  });
  styles.apply({
    property: 'gridColumnGap',
    value: get(props, '$gridColumnGap'),
    transform: getScale
  });
  styles.apply({
    property: 'gridColumnStart',
    value: get(props, '$gridColumnStart')
  });
  styles.apply({
    property: 'gridGap',
    value: get(props, '$gridGap'),
    transform: getScale
  });
  styles.apply({
    property: 'gridRow',
    value: get(props, '$gridRow')
  });
  styles.apply({
    property: 'gridRowStart',
    value: get(props, '$gridRowStart')
  });
  styles.apply({
    property: 'gridRowEnd',
    value: get(props, '$gridRowEnd')
  });
  styles.apply({
    property: 'gridTemplate',
    value: get(props, '$gridTemplate')
  });
  styles.apply({
    property: 'gridTemplateAreas',
    value: get(props, '$gridTemplateAreas')
  });
  styles.apply({
    property: 'gridTemplateColumns',
    value: get(props, '$gridTemplateColumns')
  });
  styles.apply({
    property: 'gridTemplateRows',
    value: get(props, '$gridTemplateRows')
  });
  styles.apply({
    property: 'justifyContent',
    value: get(props, '$justifyContent')
  });
  styles.apply({
    property: 'justifyItems',
    value: get(props, '$justifyItems')
  });
  styles.apply({
    property: 'justifySelf',
    value: get(props, '$justifySelf')
  });
  styles.apply({
    property: 'position',
    value: get(props, '$position')
  });
  styles.apply({
    property: 'width',
    value: get(props, '$width')
  });
  styles.apply({
    property: 'minWidth',
    value: get(props, '$minWidth')
  });
  styles.apply({
    property: 'maxWidth',
    value: get(props, '$maxWidth')
  });
  styles.apply({
    property: 'height',
    value: get(props, '$height')
  });
  styles.apply({
    property: 'minHeight',
    value: get(props, '$minHeight')
  });
  styles.apply({
    property: 'maxHeight',
    value: get(props, '$maxHeight')
  });
  styles.apply({
    property: 'overflowX',
    value: get(props, '$overflow'),
    transform: function transform(overflow) {
      if (overflow === 'scrollX') {
        return 'scroll';
      }

      return null;
    }
  });
  styles.apply({
    property: 'overflowY',
    value: get(props, '$overflow'),
    transform: function transform(overflow) {
      if (overflow === 'scrollY') {
        return 'scroll';
      }

      return null;
    }
  });
  styles.apply({
    property: 'overflow',
    value: get(props, '$overflow'),
    transform: function transform(overflow) {
      if (overflow !== 'scrollX' && overflow !== 'scrollY') {
        return overflow;
      }

      return null;
    }
  });
  styles.apply({
    property: 'margin',
    value: get(props, '$margin'),
    transform: getScale
  });
  styles.apply({
    property: 'marginTop',
    value: get(props, '$marginTop'),
    transform: getScale
  });
  styles.apply({
    property: 'marginRight',
    value: get(props, '$marginRight'),
    transform: getScale
  });
  styles.apply({
    property: 'marginBottom',
    value: get(props, '$marginBottom'),
    transform: getScale
  });
  styles.apply({
    property: 'marginLeft',
    value: get(props, '$marginLeft'),
    transform: getScale
  });
  styles.apply({
    property: 'padding',
    value: get(props, '$padding'),
    transform: getScale
  });
  styles.apply({
    property: 'paddingTop',
    value: get(props, '$paddingTop'),
    transform: getScale
  });
  styles.apply({
    property: 'paddingRight',
    value: get(props, '$paddingRight'),
    transform: getScale
  });
  styles.apply({
    property: 'paddingBottom',
    value: get(props, '$paddingBottom'),
    transform: getScale
  });
  styles.apply({
    property: 'paddingLeft',
    value: get(props, '$paddingLeft'),
    transform: getScale
  });
  styles.apply({
    property: 'placeContent',
    value: get(props, '$placeContent')
  });
  styles.apply({
    property: 'placeItems',
    value: get(props, '$placeItems')
  });
  styles.apply({
    property: 'placeSelf',
    value: get(props, '$placeSelf')
  });
  styles.apply({
    property: 'flexWrap',
    value: get(props, '$flexWrap'),
    transform: function transform() {
      return 'wrap';
    }
  });
  styles.apply({
    property: 'top',
    value: get(props, '$top')
  });
  styles.apply({
    property: 'right',
    value: get(props, '$right')
  });
  styles.apply({
    property: 'left',
    value: get(props, '$left')
  });
  styles.apply({
    property: 'bottom',
    value: get(props, '$bottom')
  });
  return styles.value();
});
StyledBlock.displayName = "StyledBlock";