{"version":3,"file":"color-palette.vue.mjs","sources":["../../../components/color-picker/color-palette.vue"],"sourcesContent":["<template>\r\n  <div\r\n    ref=\"wrapper\"\r\n    :class=\"nh.be('palette')\"\r\n    tabindex=\"-1\"\r\n    role=\"group\"\r\n    :style=\"{\r\n      backgroundColor: `hsl(${hue}, 100%, 50%)`\r\n    }\"\r\n  >\r\n    <div :class=\"nh.be('saturation')\" role=\"none\"></div>\r\n    <div :class=\"nh.be('value')\" role=\"none\"></div>\r\n    <div\r\n      :class=\"nh.be('palette-handler')\"\r\n      :style=\"{\r\n        top: `${currentTop}%`,\r\n        left: `${currentLeft}%`\r\n      }\"\r\n    >\r\n      <div :class=\"nh.be('palette-pointer')\"></div>\r\n    </div>\r\n  </div>\r\n</template>\r\n\r\n<script lang=\"ts\">\r\nimport { defineComponent, ref, watch } from 'vue'\r\n\r\nimport { useNameHelper } from '@vexip-ui/config'\r\nimport { useModifier, useMoving } from '@vexip-ui/hooks'\r\nimport { boundRange, toFixed } from '@vexip-ui/utils'\r\n\r\nexport default defineComponent({\r\n  name: 'ColorPalette',\r\n  props: {\r\n    hue: {\r\n      type: Number,\r\n      default: 0,\r\n      validator: (value: number) => {\r\n        return value >= 0 && value <= 360\r\n      },\r\n    },\r\n    value: {\r\n      type: Number,\r\n      default: 1,\r\n      validator: (value: number) => {\r\n        return value >= 0 && value <= 1\r\n      },\r\n    },\r\n    saturation: {\r\n      type: Number,\r\n      default: 0,\r\n      validator: (value: number) => {\r\n        return value >= 0 && value <= 1\r\n      },\r\n    },\r\n  },\r\n  emits: ['edit-start', 'edit-end', 'change'],\r\n  setup(props, { emit }) {\r\n    const currentTop = ref((1 - props.value) * 100)\r\n    const currentLeft = ref(props.saturation * 100)\r\n\r\n    let prevTop = currentTop.value\r\n    let prevLeft = currentLeft.value\r\n    let widthLimit: number\r\n    let heightLimit: number\r\n    let topStartAt: number\r\n    let leftStartAt: number\r\n\r\n    const { target: wrapper } = useModifier({\r\n      passive: false,\r\n      onKeyDown: (event, modifier) => {\r\n        if (modifier.up || modifier.down || modifier.left || modifier.right) {\r\n          event.preventDefault()\r\n\r\n          const step = event.ctrlKey ? 10 : event.altKey ? 0.5 : 2\r\n          const sign = modifier.up || modifier.left ? -1 : 1\r\n          const delta = step * sign\r\n\r\n          if (modifier.up || modifier.down) {\r\n            currentTop.value += delta\r\n          } else {\r\n            currentLeft.value += delta\r\n          }\r\n\r\n          verifyPosition()\r\n          prevTop = currentTop.value\r\n          prevLeft = currentLeft.value\r\n          handleChange()\r\n        }\r\n      },\r\n    })\r\n\r\n    const { moving: editing } = useMoving({\r\n      target: wrapper,\r\n      onStart: (state, event) => {\r\n        if (!wrapper.value || event.button > 0) {\r\n          return false\r\n        }\r\n\r\n        const rect = wrapper.value.getBoundingClientRect()\r\n        const { top, left, width, height } = rect\r\n\r\n        widthLimit = width\r\n        heightLimit = height\r\n\r\n        currentTop.value = ((topStartAt = state.clientY - top) / height) * 100\r\n        currentLeft.value = ((leftStartAt = state.clientX - left) / width) * 100\r\n\r\n        verifyPosition()\r\n        emit('edit-start')\r\n\r\n        let changed = false\r\n\r\n        if (Math.abs(currentTop.value - prevTop) >= 0.01) {\r\n          prevTop = currentTop.value\r\n          changed = true\r\n        }\r\n\r\n        if (Math.abs(currentLeft.value - prevLeft) >= 0.01) {\r\n          prevLeft = currentLeft.value\r\n          changed = true\r\n        }\r\n\r\n        changed && handleChange()\r\n      },\r\n      onMove: state => {\r\n        currentTop.value = ((topStartAt + state.deltaY) / heightLimit) * 100\r\n        currentLeft.value = ((leftStartAt + state.deltaX) / widthLimit) * 100\r\n\r\n        verifyPosition()\r\n        handleChange()\r\n      },\r\n      onEnd: () => {\r\n        emit('edit-end')\r\n      },\r\n    })\r\n\r\n    watch(\r\n      () => props.value,\r\n      value => {\r\n        currentTop.value = (1 - value) * 100\r\n        verifyPosition()\r\n      },\r\n      { immediate: true },\r\n    )\r\n    watch(\r\n      () => props.saturation,\r\n      value => {\r\n        currentLeft.value = value * 100\r\n        verifyPosition()\r\n      },\r\n      { immediate: true },\r\n    )\r\n\r\n    function verifyPosition() {\r\n      currentTop.value = toFixed(boundRange(currentTop.value, 0, 100), 3)\r\n      currentLeft.value = toFixed(boundRange(currentLeft.value, 0, 100), 3)\r\n    }\r\n\r\n    function handleChange() {\r\n      emit('change', {\r\n        h: props.hue,\r\n        s: currentLeft.value / 100,\r\n        v: toFixed(1 - currentTop.value / 100, 3),\r\n      })\r\n    }\r\n\r\n    return {\r\n      nh: useNameHelper('color-picker'),\r\n      currentTop,\r\n      currentLeft,\r\n      editing,\r\n\r\n      wrapper,\r\n\r\n      // handleMouseDown\r\n    }\r\n  },\r\n})\r\n</script>\r\n"],"names":["_createElementBlock","_normalizeClass","_ctx","_normalizeStyle","_createElementVNode"],"mappings":";;;;cACEA,EAoBM,OAAA;AAAA,IAnBJ,KAAI;AAAA,IACH,OAAKC,EAAEC,EAAA,GAAG,GAAE,SAAA,CAAA;AAAA,IACb,UAAS;AAAA,IACT,MAAK;AAAA,IACJ,OAAKC,EAAA;AAAA,MAAA,iBAAA,OAAmCD,EAAG,GAAA;AAAA,IAAA,CAAA;AAAA;IAI5CE,EAAoD,OAAA;AAAA,MAA9C,OAAKH,EAAEC,EAAA,GAAG,GAAE,YAAA,CAAA;AAAA,MAAgB,MAAK;AAAA,IAAA,GAAA,MAAA,CAAA;AAAA,IACvCE,EAA+C,OAAA;AAAA,MAAzC,OAAKH,EAAEC,EAAA,GAAG,GAAE,OAAA,CAAA;AAAA,MAAW,MAAK;AAAA,IAAA,GAAA,MAAA,CAAA;AAAA,IAClCE,EAQM,OAAA;AAAA,MAPH,OAAKH,EAAEC,EAAA,GAAG,GAAE,iBAAA,CAAA;AAAA,MACZ,OAAKC,EAAA;AAAA,QAAA,KAAA,GAAqBD,EAAU,UAAA;AAAA,QAAA,MAAA,GAAuBA,EAAW,WAAA;AAAA,MAAA,CAAA;AAAA;MAKvEE,EAA6C,OAAA;AAAA,QAAvC,OAAKH,EAAEC,EAAA,GAAG,GAAE,iBAAA,CAAA;AAAA,MAAA,GAAA,MAAA,CAAA;AAAA;;;;"}