<script setup lang="ts">
import { useAttrs, getCurrentInstance, computed, watch } from 'vue'
import { usePropBind, LABEL_KEY, MIN_KEY, MAX_KEY, NUMBER_MAX, NUMBER_MIN } from './common'
import GdFormItem from './GdFormItem.vue';
const $t: any = getCurrentInstance()?.appContext.config.globalProperties.$t

const props = withDefaults(defineProps<{
  label: string,
  rules?: [],
  min?: number,
  max?: number
}>(), { label: '' })
const emit = defineEmits<{
  (e: 'change', val: any): void
}>();

const { propValue, handleChange } = usePropBind()
const attrs = <any>useAttrs()

const handleInput = (val: string) => {
  if (!val || isNaN(Number(val))) {
    emit('change', undefined)
    return handleChange(undefined)
  }
  val = val.trim()
  const value = Number(val).toFixed(attrs.precision || 0)
  let result = value
  const min = attrs.min !== undefined ? attrs.min : NUMBER_MIN
  const max = attrs.max !== undefined ? attrs.max : NUMBER_MAX
  if (result < min) {
    result = min
  } else if (result > max) {
    result = max
  }
  const currentPrecision = val.split('.')[1]?.length || 0
  result = Number(result).toFixed(attrs.precision ? Math.min(currentPrecision, attrs.precision) : 0)
  handleChange(result)
  emit('change', result)
};

const handleBlur = () => {
  const result = propValue.value ? Number(propValue.value).toFixed(attrs.precision || 0) : ''
  handleChange(result)
  emit('change', result)
}

const rules = computed(() => {
  const res: any = props.rules || []
  const { min, max } = props
  if (min !== undefined) {
    res.push({
      validator(rule: any, value: any, callback: any) {
        if (min && Number(value) < Number(min)) {
          callback(`${$t('check_min')?.replace(LABEL_KEY, props.label).replace(MIN_KEY, min)}`)
        } else {
          callback()
        }
      }
    })
  }
  if (max !== undefined) {
    res.push({
      validator(rule: any, value: any, callback: any) {
        if (max && Number(value) > Number(max)) {
          callback(`${$t('check_max')?.replace(LABEL_KEY, props.label).replace(MAX_KEY, max)}`)
        } else {
          callback()
        }
      }
    })
  }
  return res
})
</script>

<template>
  <GdFormItem :label="props.label" :rules="rules">
    <p class="viewer-content" v-if="attrs.viewerMode">{{ propValue }}</p>
    <el-input key="input-number" type="number" v-else :model-value="propValue"
      :placeholder="`${$t('placeholder_prefix_input')?.replace(LABEL_KEY, label)}`" class="gd-input-number" clearable
      v-bind="attrs" @input="handleInput" @blur="handleBlur" />
  </GdFormItem>
</template>

<style lang="scss">
.gd-form .gd-input-number.el-input-number {
  width: 100%;

  .el-input__inner {
    text-align: left;
  }

}

.gd-form .gd-input-number input::-webkit-outer-spin-button,
.gd-form .gd-input-number input::-webkit-inner-spin-button {
  -webkit-appearance: none;
}

/* 火狐浏览器 */
.gd-form .gd-input-number input[type="number"] {
  -moz-appearance: textfield;
}
</style>