<template>
  <div
    v-show="!isHidden"
    class="form-group"
    :class="[
      columnSize,
      {
        'has-icon': faIcon,
        'has-feedback': hasFeedback,
        'has-success': hasSuccess,
        'has-error': hasError,
        'has-password-toggle': hasPasswordToggle,
      },
    ]"
  >
    <label class="control-label" :for="id">
      {{ label }}
      <span class="info">{{ info }}</span>
      <span v-if="isRequired" class="required-marker"></span>
      <span
        v-if="tooltip"
        class="tooltip-info"
        data-toggle="tooltip"
        :title="tooltip"
      ></span>
    </label>
    <slot></slot>
    <input
      v-if="type !== 'textarea'"
      :ref="id"
      :type="type"
      :id="id"
      class="form-control"
      :placeholder="placeholder"
      :maxLength="max_length"
      :pattern="pattern"
      :required="isRequired"
      @input="onInput"
      @focus="onFocus"
      @blur="onBlur"
      :disabled="!isEnabled"
      :value="inputValue"
    />
    <textarea
      v-else
      :ref="id"
      :type="type"
      :id="id"
      class="form-control"
      :placeholder="placeholder"
      :maxLength="max_length"
      :pattern="pattern"
      :required="isRequired"
      rows="3"
      @input="onInput"
      @focus="onFocus"
      @blur="onBlur"
      :disabled="!isEnabled"
      :value="inputValue"
    ></textarea>
    <span v-if="faIcon" class="form-control-feedback" :class="faIcon"></span>
    <span v-if="type === 'password'" class="password-toggle"></span>
    <div
      v-if="validationText && hasError"
      class="help-block"
      data-validation-error
    >
      {{ validationText }}
    </div>
    <p v-if="help && !validationText" :id="id + 'Help'" class="help-block">
      {{ help }}
    </p>
  </div>
</template>

<script>
import { str2bool } from "../../util";
export default {
  name: "bc-input",
  props: {
    id: {
      type: String,
      default: null,
    },
    label: {
      type: String,
      default: null,
    },
    value: {
      type: String,
      default: null,
    },
    placeholder: {
      type: String,
      default: null,
    },
    info: {
      type: String,
      default: null,
    },
    icon: {
      type: String,
      default: null,
    },
    tooltip: {
      type: String,
      default: null,
    },
    pattern: {
      type: String,
      default: null,
    },
    type: {
      type: String,
      default: "text", // text, password, textarea, number, email
    },
    help: {
      type: String,
      default: null,
    },
    validation: {
      type: String,
      default: null,
    },
    column_size: {
      type: Number,
      default: null,
    },
    max_length: {
      type: Number,
      default: null,
    },
    is_enabled: {
      type: [Boolean, String],
      default: true,
    },
    is_hidden: {
      type: [Boolean, String],
      default: false,
    },
    is_required: {
      type: [Boolean, String],
      default: false,
    },
    is_valid: {
      type: [Boolean, String],
      default: null,
    },
  },
  data() {
    return {
      isOnFocus: false,
      isValid: null,
      inputValue: null,
    };
  },
  watch: {
    value: {
      immediate: true,
      handler(newValue) {
        this.inputValue = newValue;
      },
    },
  },
  mounted() {
    if (this.value) {
      this.inputValue = this.value;
    }
    this.isValid = str2bool(this.is_valid, null);
  },
  updated() {
    if (this.value) {
      this.inputValue = this.value;
    }
    this.isValid = str2bool(this.is_valid, null);
  },
  computed: {
    isRequired() {
      return str2bool(this.is_required);
    },
    isHidden() {
      return str2bool(this.is_hidden, false);
    },
    isEnabled() {
      return str2bool(this.is_enabled, true);
    },
    hasFeedback() {
      if (this.isValid == null) {
        return false;
      } else {
        return !this.isOnFocus;
      }
    },
    hasError() {
      return !this.isOnFocus && this.isValid === false && this.hasFeedback;
    },
    hasSuccess() {
      return !this.isOnFocus && this.isValid === true && this.hasFeedback;
    },
    hasPasswordToggle() {
      if (this.type === "password") {
        return true;
      }
      return false;
    },
    columnSize() {
      if (this.column_size) {
        return `col-xs-${this.column_size}`;
      }
      return "";
    },
    faIcon() {
      if (this.icon) {
        return `fa-${this.icon}`;
      }
      return false;
    },
    validationText() {
      if (this.validation) {
        if (!this.isOnFocus) {
          return this.validation;
        }
      }
      return false;
    },
  },
  methods: {
    onInput(event) {
      let value = event.target.value;
      this.inputValue = value;
      this.$emit("input", this.inputValue);
    },
    onFocus() {
      this.isOnFocus = true;
    },
    onBlur() {
      // mute validation error if the value is now filled
      if (!this.isValid && this.value) {
        this.isValid = true;
      }
      this.isOnFocus = false;
    },
  },
};
</script>

