<template>
    <div class="input range">
        <div ref="rangeRef" class="range-content" :class="{ animation: mode === modeEmun.default }" :style="{ '--percentage': percenStyle }" @click="rangeClickHandler">
            <div ref="locusRef" class="range-locus">
                <span class="range-slide" @click.stop @mousedown="slideDownHandler">
                    <span v-if="rangeTips" class="tips">{{ modelValue }}%</span>
                </span>
            </div>
        </div>
        <div v-if="rangeInput">
            <UItext v-if="inch" :model-value="inch" class="range-text" style="pointer-events: none" />
            <UInumber v-else :model-value="modelValue" :min="min" :max="max" :step="step" :ctrl="false" right class="range-text" @update:model-value="inputUpdateHandler" />
        </div>
    </div>
</template>

<script setup lang="ts">
import { computed, defineProps, nextTick, onMounted, ref } from 'vue'
import UInumber from '../number/number.vue'
import UItext from '../text/text.vue'
import { rangProps } from './range'

const props = defineProps(rangProps)
const emit = defineEmits(['update:modelValue'])
const getValue = (value: number) => {
    const calcStep = Math.ceil(1 / props.step)
    const calcValue = Math.round(value * calcStep)
    const calcMin = Number(props.min) * calcStep
    const calcMax = Number(props.max) * calcStep

    const newVal = calcValue >= calcMax ? calcMax : calcValue <= calcMin ? calcMin : calcValue - (calcValue % (calcStep * props.step))

    return newVal / calcStep
}

const percen = computed({
    get() {
        return (Number(props.modelValue) - Number(props.min)) / (Number(props.max) - Number(props.min))
    },
    set(val) {
        const len = Number(props.max) - Number(props.min)
        let num
        if (props.limit > 0 && Number(props.min) + len * val > props.limit) {
            num = getValue(props.limit)
        } else {
            num = getValue(Number(props.min) + len * val)
        }

        emit('update:modelValue', num)
    },
})

const percenStyle = computed(() => `${percen.value * 100}%`)

const inputUpdateHandler = val => {
    let num
    if (props.limit > 0 && val > props.limit) {
        num = getValue(props.limit)
    } else {
        num = getValue(val)
    }
    emit('update:modelValue', num)
}

const modeEmun = {
    slide: 0,
    default: 1,
}
const mode = ref(modeEmun.default)
const locusWidth = ref(0)
const locusRef = ref(null)
const rangeWidth = ref(0)
const rangeRef = ref(null)
onMounted(() => {
    nextTick(() => {
        locusWidth.value = locusRef.value.offsetWidth
        rangeWidth.value = rangeRef.value.offsetWidth
    })
})

const rangeClickHandler = ev => {
    percen.value = ev.offsetX / rangeWidth.value
    console.log(ev.offsetX, rangeWidth.value)
    //首次点击，获取limit的值
    const t = setTimeout(() => {
        const len = Number(props.max) - Number(props.min)
        if (props.limit > 0 && Number(props.min) + len * percen.value > props.limit) {
            percen.value = (props.limit - Number(props.min)) / len
        } else {
            // percen.value = ev.offsetX / rangeWidth.value
        }
        clearTimeout(t)
    }, 0)
}

const parent = document.documentElement
const player = document.querySelector('.player[name="main"]')
const slideDownHandler = ev => {
    ev.preventDefault()
    const moveStartX = ev.clientX
    const startPercen = percen.value
    mode.value = modeEmun.slide
    const moveHandler = ev => {
        ev.preventDefault()
        const moveX = ev.clientX - moveStartX

        const readyPercen = startPercen + moveX / locusWidth.value

        percen.value = readyPercen < 0 ? 0 : readyPercen > 1 ? 1 : readyPercen
    }

    const upHandler = _ => {
        mode.value = modeEmun.default
        parent.removeEventListener('mousemove', moveHandler, false)
        parent.removeEventListener('mouseup', upHandler, false)
        player && player.removeEventListener('mouseup', upHandler, false)
    }
    parent.addEventListener('mousemove', moveHandler, false)
    parent.addEventListener('mouseup', upHandler, false)
    player && player.addEventListener('mouseup', upHandler, false)
}
</script>
