@extclp/vexip-ui
Version:
A Vue 3 UI library, Highly customizability, full TypeScript, performance pretty good
1 lines • 14.8 kB
Source Map (JSON)
{"version":3,"file":"textarea.vue2.mjs","sources":["../../../components/textarea/textarea.vue"],"sourcesContent":["<script setup lang=\"ts\">\r\nimport { Icon } from '@/components/icon'\r\nimport { useFieldStore } from '@/components/form'\r\n\r\nimport { computed, ref, toRef, watch } from 'vue'\r\n\r\nimport {\r\n createIconProp,\r\n createStateProp,\r\n emitEvent,\r\n useIcons,\r\n useLocale,\r\n useNameHelper,\r\n useProps,\r\n} from '@vexip-ui/config'\r\nimport { debounce, isNull, throttle, toNumber } from '@vexip-ui/utils'\r\nimport { textareaProps } from './props'\r\n\r\ndefineOptions({ name: 'Textarea' })\r\n\r\nconst { idFor, state, labelId, disabled, loading, validateField, getFieldValue, setFieldValue } =\r\n useFieldStore<string>(() => textarea.value?.focus())\r\n\r\nconst _props = defineProps(textareaProps)\r\nconst props = useProps('textarea', _props, {\r\n state: createStateProp(state),\r\n locale: null,\r\n value: {\r\n default: () => getFieldValue(),\r\n static: true,\r\n },\r\n placeholder: null,\r\n rows: 2,\r\n noResize: false,\r\n autofocus: false,\r\n spellcheck: false,\r\n autocomplete: false,\r\n readonly: false,\r\n disabled: () => disabled.value,\r\n debounce: false,\r\n delay: null,\r\n maxLength: 0,\r\n hideCount: false,\r\n loading: () => loading.value,\r\n loadingIcon: createIconProp(),\r\n loadingLock: false,\r\n loadingEffect: null,\r\n sync: false,\r\n controlClass: null,\r\n controlAttrs: null,\r\n name: {\r\n default: '',\r\n static: true,\r\n },\r\n})\r\n\r\nconst emit = defineEmits(['update:value'])\r\n\r\nconst nh = useNameHelper('textarea')\r\nconst locale = useLocale('input', toRef(props, 'locale'))\r\nconst icons = useIcons()\r\n\r\nconst focused = ref(false)\r\nconst currentValue = ref(props.value)\r\nconst currentLength = ref(props.value ? props.value.length : 0)\r\nconst composing = ref(false)\r\n\r\nconst textarea = ref<HTMLTextAreaElement>()\r\n\r\nlet lastValue = props.value\r\n\r\nconst isReadonly = computed(() => {\r\n return (props.loading && props.loadingLock) || props.readonly\r\n})\r\nconst className = computed(() => {\r\n return {\r\n [nh.b()]: true,\r\n [nh.ns('input-vars')]: true,\r\n [nh.bs('vars')]: true,\r\n [nh.bm('inherit')]: props.inherit,\r\n [nh.bm('focused')]: focused.value,\r\n [nh.bm('disabled')]: props.disabled,\r\n [nh.bm('readonly')]: isReadonly.value,\r\n [nh.bm('loading')]: props.loading,\r\n [nh.bm('no-resize')]: props.noResize,\r\n [nh.bm(props.state)]: props.state !== 'default',\r\n }\r\n})\r\nconst autoComplete = computed(() => {\r\n return typeof props.autocomplete === 'boolean'\r\n ? props.autocomplete\r\n ? 'on'\r\n : 'off'\r\n : props.autocomplete\r\n})\r\n\r\nwatch(\r\n () => props.value,\r\n value => {\r\n currentValue.value = value\r\n lastValue = value\r\n limitValueLength()\r\n },\r\n)\r\n\r\ndefineExpose({\r\n idFor,\r\n currentValue,\r\n currentLength,\r\n composing,\r\n isReadonly,\r\n textarea,\r\n copyValue,\r\n focus: (options?: FocusOptions) => textarea.value?.focus(options),\r\n blur: () => textarea.value?.blur(),\r\n})\r\n\r\nfunction handleFocus(event: FocusEvent) {\r\n focused.value = true\r\n emitEvent(props.onFocus, event)\r\n}\r\n\r\nfunction handleBlur(event: FocusEvent) {\r\n focused.value = false\r\n emitEvent(props.onBlur, event)\r\n}\r\n\r\nfunction handleChange(event: Event) {\r\n const type = event.type as 'change' | 'input'\r\n\r\n if (composing.value) {\r\n if (type === 'input') return\r\n\r\n composing.value = false\r\n }\r\n\r\n currentValue.value = (event.target as HTMLTextAreaElement).value\r\n limitValueLength()\r\n\r\n if (type === 'change') {\r\n if (lastValue === currentValue.value) return\r\n\r\n lastValue = currentValue.value\r\n\r\n if (!props.sync) {\r\n emit('update:value', currentValue.value)\r\n setFieldValue(currentValue.value)\r\n }\r\n\r\n emitEvent(props.onChange, currentValue.value)\r\n\r\n if (!props.sync) {\r\n validateField()\r\n }\r\n } else {\r\n if (props.sync) {\r\n emit('update:value', currentValue.value)\r\n setFieldValue(currentValue.value)\r\n }\r\n\r\n emitEvent(props.onInput, currentValue.value)\r\n\r\n if (props.sync) {\r\n validateField()\r\n }\r\n }\r\n}\r\n\r\nfunction handleEnter() {\r\n emitEvent(props.onEnter)\r\n}\r\n\r\nfunction handleKeyDown(event: KeyboardEvent) {\r\n emitEvent(props.onKeyDown, event)\r\n}\r\n\r\nfunction handleKeyPress(event: KeyboardEvent) {\r\n emitEvent(props.onKeyPress, event)\r\n}\r\n\r\nfunction handleKeyUp(event: KeyboardEvent) {\r\n emitEvent(props.onKeyUp, event)\r\n}\r\n\r\nfunction limitValueLength() {\r\n let value = currentValue.value\r\n\r\n if (isNull(value)) {\r\n currentLength.value = 0\r\n\r\n return\r\n }\r\n\r\n const maxLength = props.maxLength\r\n\r\n if (maxLength && value.length > maxLength) {\r\n value = value.slice(0, maxLength)\r\n }\r\n\r\n currentLength.value = value.length\r\n currentValue.value = value\r\n}\r\n\r\nfunction copyValue() {\r\n const textarea = document.createElement('textarea')\r\n\r\n textarea.style.height = '0'\r\n textarea.setAttribute('readonly', 'readonly')\r\n textarea.value = currentValue.value\r\n document.body.appendChild(textarea)\r\n textarea.select()\r\n\r\n const isSuccess = document.execCommand('copy')\r\n\r\n document.body.removeChild(textarea)\r\n\r\n return isSuccess\r\n}\r\n\r\nconst delay = toNumber(props.delay)\r\nconst handleInput = props.debounce\r\n ? debounce(handleChange, delay || 100)\r\n : throttle(handleChange, delay || 16)\r\n\r\nfunction handleCompositionStart(event: CompositionEvent) {\r\n composing.value = true\r\n emitEvent(props.onCompositionStart, event)\r\n}\r\n\r\nfunction handleCompositionEnd(event: CompositionEvent) {\r\n if (composing.value) {\r\n composing.value = false\r\n\r\n if (textarea.value) {\r\n textarea.value.dispatchEvent(new Event('input'))\r\n }\r\n }\r\n\r\n emitEvent(props.onCompositionStart, event)\r\n}\r\n</script>\r\n\r\n<template>\r\n <div :id=\"idFor\" :class=\"className\" @click=\"textarea?.focus()\">\r\n <textarea\r\n v-bind=\"props.controlAttrs\"\r\n ref=\"textarea\"\r\n :class=\"[nh.be('control'), props.controlAttrs?.class, props.controlClass]\"\r\n :value=\"currentValue\"\r\n :rows=\"props.rows\"\r\n :autofocus=\"props.autofocus\"\r\n :autocomplete=\"autoComplete\"\r\n :spellcheck=\"props.spellcheck\"\r\n :disabled=\"props.disabled\"\r\n :readonly=\"isReadonly\"\r\n :placeholder=\"props.placeholder ?? locale.placeholder\"\r\n :maxlength=\"props.maxLength > 0 ? props.maxLength : undefined\"\r\n :name=\"props.name || props.controlAttrs?.name\"\r\n :aria-labelledby=\"labelId\"\r\n @blur=\"handleBlur\"\r\n @focus=\"handleFocus\"\r\n @keyup.enter=\"handleEnter\"\r\n @keyup=\"handleKeyUp\"\r\n @keypress=\"handleKeyPress\"\r\n @keydown=\"handleKeyDown\"\r\n @input=\"handleInput\"\r\n @change=\"handleChange\"\r\n @compositionstart=\"handleCompositionStart\"\r\n @compositionend=\"handleCompositionEnd\"\r\n ></textarea>\r\n <div :class=\"nh.be('extra')\">\r\n <Transition :name=\"nh.ns('fade')\" appear>\r\n <div v-if=\"props.loading\" :class=\"nh.be('loading')\">\r\n <Icon\r\n v-bind=\"icons.loading\"\r\n :effect=\"props.loadingEffect || icons.loading.effect\"\r\n :icon=\"props.loadingIcon || icons.loading.icon\"\r\n label=\"loading\"\r\n ></Icon>\r\n </div>\r\n </Transition>\r\n <div v-if=\"props.maxLength > 0 && !props.hideCount\" :class=\"nh.be('count')\">\r\n <slot name=\"count\" :value=\"currentValue\">\r\n {{ props.maxLength === Infinity ? currentLength : `${currentLength}/${props.maxLength}` }}\r\n </slot>\r\n </div>\r\n </div>\r\n </div>\r\n</template>\r\n"],"names":["idFor","state","labelId","disabled","loading","validateField","getFieldValue","setFieldValue","useFieldStore","_a","textarea","props","useProps","__props","createStateProp","createIconProp","emit","__emit","nh","useNameHelper","locale","useLocale","toRef","icons","useIcons","focused","ref","currentValue","currentLength","composing","lastValue","isReadonly","computed","className","autoComplete","watch","value","limitValueLength","__expose","copyValue","options","handleFocus","event","emitEvent","handleBlur","handleChange","type","handleEnter","handleKeyDown","handleKeyPress","handleKeyUp","isNull","maxLength","isSuccess","delay","toNumber","handleInput","debounce","throttle","handleCompositionStart","handleCompositionEnd","_createElementBlock","_unref","_cache","$event","_createElementVNode","_mergeProps","args","_normalizeClass","_createVNode","_Transition","Icon","_renderSlot","_ctx"],"mappings":"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"}