
<script>
import ColorPropMixin from '../../../mixins/color-prop-mixin';
import SizePropMixin from '../../../mixins/size-prop-mixin';
import feather from 'feather-icons';

export default {
  name: 'EbIcon',
  mixins: [ColorPropMixin, SizePropMixin],
  props: {
    type: {
      type: String,
      required: true
    },
    tag: {
      type: String,
      default: 'i'
    },
    family: {
      validator: prop => typeof prop === 'string' || prop === null,
      default: null
    },
    animation: {
      type: String,
      default: undefined
    },
    animationSpeed: {
      type: String,
      default: undefined
    },
    fill: {
      type: String,
      default: 'none'
    },
    stroke: {
      type: String,
      default: 'currentColor'
    },
    strokeLinecap: {
      type: String,
      default: 'round'
    },
    strokeLinejoin: {
      type: String,
      default: 'round'
    },
    strokeWidth: {
      type: [Number, String],
      default: 2
    }
  },
  render(createElement) {
    const { animation, animationSpeed, size, type, family } = this;
    const icon = family === null ? feather.icons[type] : null;
    return createElement(
      this.tag,
      {
        attrs: this.buildIconAttrs(icon),
        class: this.buildIconClass(icon),
        on: this.$listeners
      },
      [
        icon
          ? createElement('svg', {
              attrs: {
                ...icon.attrs,
                fill: this.fill,
                height: size,
                stroke: this.stroke,
                'stroke-linecap': this.strokeLinecap,
                'stroke-linejoin': this.strokeLinejoin,
                'stroke-width': this.strokeWidth,
                width: size
              },
              class: [icon.attrs.class, 'eb-icon__content'],
              domProps: {
                innerHTML: icon.contents
              }
            })
          : ''
      ]
    );
  },
  computed: {
    iconPath() {
      return this.type;
    },
    iconClass() {
      return this.fontAwesomeIcons ? 'fa' : this.family;
    },
    useColor() {
      return this.hasColor ? `color: ${this.color}` : false;
    },
    useSize() {
      return this.size === null
        ? ''
        : `font-size: ${!isNaN(this.size) ? this.size + 'px' : this.size};`;
    },
    fontAwesomeIcons() {
      return (
        this.family === 'fab' ||
        this.family === 'fas' ||
        this.family === 'far' ||
        this.family === 'fa'
      );
    }
  },
  methods: {
    buildIconAttrs(icon) {
      return icon !== null
        ? {
            'data-name': this.type,
            'data-tags': icon ? icon.tags : '',
            'data-type': this.type
          }
        : {
            style: `${this.useSize} ${this.useColor}`
          };
    },
    buildIconClass(icon) {
      return icon !== null
        ? {
            'eb-icon': true,
            [`eb-icon--${this.type}`]: this.type,
            [`eb-icon--${this.animation}`]: this.animation,
            [`eb-icon--${this.animationSpeed}`]: this.animationSpeed
          }
        : {
            'eb-icon': true,
            [`${this.family}`]: true,
            [`${this.iconClass}-${this.type}`]: true,
            [`eb-icon--${this.animation}`]: this.animation,
            [`eb-icon--${this.animationSpeed}`]: this.animationSpeed
          };
    }
  }
};
</script>

<style lang="scss" scoped>
@keyframes eb-icon--spin {
  from {
    transform: rotate(0);
  }
  to {
    transform: rotate(360deg);
  }
}
.eb-icon {
  display: inline-flex;
  overflow: hidden;
  &--spin {
    animation: eb-icon--spin 2s linear infinite;
  }
  &--pulse {
    animation: eb-icon--spin 2s infinite steps(8);
  }
  &--slow {
    animation-duration: 3s;
  }
  &--fast {
    animation-duration: 1s;
  }
  &__content {
    display: inline-block;
    height: inherit;
    width: inherit;
  }
}
</style>

