<template>
  <div
    v-show="!isHidden"
    class="form-group"
    :class="[
      columnSize,
      {
        'has-icon': faIcon,
        'has-feedback': hasFeedback,
        'has-success': hasSuccess,
        'has-error': hasError,
      },
    ]"
  >
    <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>
    <input
      :ref="id"
      :id="id"
      type="text"
      class="form-control flatpickr-input"
      :class="{ active: isOnFocus }"
      :required="isRequired"
      @focus="onFocus"
      @blur="onBlur"
      :disabled="!isEnabled"
    />
    <span v-if="faIcon" class="form-control-feedback" :class="faIcon"></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-datepicker",
  data() {
    return {
      isOnFocus: false,
      isValid: null,
      inputValue: null,
      dateInstance: null,
      valueFormat: null,
    };
  },
  props: {
    id: {
      type: String,
      default: null,
    },
    label: {
      type: String,
      default: null,
    },
    value: {
      type: [Date, Number, String],
      default: null,
    },
    info: {
      type: String,
      default: null,
    },
    icon: {
      type: String,
      default: null,
    },
    tooltip: {
      type: String,
      default: null,
    },
    help: {
      type: String,
      default: null,
    },
    validation: {
      type: String,
      default: null,
    },
    column_size: {
      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,
    },
    date_format: {
      type: String,
      default: "j M Y H:i",
    },
    date_default: {
      type: String,
      default: "now",
    },
    date_enable_time: {
      type: [Boolean, String],
      default: true,
    },
  },
  watch: {
    value: {
      immediate: true,
      handler(newValue, oldValue) {
        // console.log("new value", newValue);
        if (newValue) {
          if (newValue !== oldValue) {
            // assess if value is a string, number or a date
            if (Object.prototype.toString.call(newValue) === "[object Date]") {
              this.valueFormat = "date";
            } else if (typeof newValue == "number") {
              this.valueFormat = "number";
            } else if (typeof newValue == "string") {
              this.valueFormat = "string";
            }
            this.inputValue = this.parseValue(newValue);
            if (this.dateInstance) {
              this.dateInstance.setDate(this.inputValue, false);
            }
          }
        }
      },
    },
  },
  mounted() {
    this.inputValue = this.parseValue(this.value);
    let self = this;
    /* eslint-disable */
    this.$nextTick(() => {
      // setup flatpicker
      self.dateInstance = flatpickr(self.$el.getElementsByTagName("input")[0], {
        dateFormat: self.date_format,
        enableTime: self.date_enable_time,
        defaultDate: self.inputValue,
        time_24hr: true,
        onChange: function (selectedDates, dateStr, instance) {
          self.inputValue = new Date(instance.selectedDates[0]);
          if (this.valueFormat === "number") {
            self.$emit("input", self.inputValue.getTime());
          } else if (this.valueFormat === "string") {
            self.$emit("input", self.inputValue.toISOString());
          } else {
            self.$emit("input", self.inputValue);
          }
          // self.isOnFocus = false;
          // self.dateInstance.close();
        },
      });
    });
    /* eslint-enable */
    this.isValid = str2bool(this.is_valid, null);
  },
  updated() {
    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);
    },
    dateEnableTime() {
      return str2bool(this.date_enable_time, 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;
    },
    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: {
    parseValue(value) {
      // try parse value into a date
      const defaultDateValue = (() => {
        if (this.date_default == "now") {
          return new Date();
        }
        return null;
      })();
      if (value) {
        let date = new Date(value);
        if (isNaN(date)) {
          // date is invalid
          return defaultDateValue;
        } else {
          console.log("valid date ");
          return date;
        }
      } else {
        return defaultDateValue;
      }
    },
    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>

