import { Button, Popover, Input, InputNumber } from 'ant-design-vue'; import classNames from 'ant-design-vue/es/_util/classNames'; import type { PropType } from 'vue'; import { defineComponent, toRefs, computed, ref, watch } from 'vue'; import { debounce } from 'lodash'; import ColorPanel from './ColorPanel'; import ColorPreview from './ColorPreview'; import type { MutableTheme } from './interface'; import { useInjectLocaleContext } from './locale'; import isColor from './utils/isColor'; import makeStyle from './utils/makeStyle'; const useStyle = makeStyle('TokenInput', token => ({ '.previewer-token-input': { [`${token.rootCls}-input-group-addon, ${token.rootCls}-input-number-group-addon`]: { border: '0 !important', color: `rgba(0, 0, 0, 0.25) !important`, fontSize: `${token.fontSizeSM}px !important`, padding: '0 !important', backgroundColor: 'transparent !important', '&:first-child': { paddingInlineStart: 0, }, '&:last-child': { paddingInlineEnd: 0, }, }, [`${token.rootCls}-input-group-wrapper, ${token.rootCls}-input-number-group-wrapper`]: { padding: 0, height: 24, width: '100%', input: { fontSize: token.fontSizeSM, lineHeight: token.lineHeightSM, padding: `2px ${token.paddingXS}px`, height: 24, }, }, [`${token.rootCls}-input-group-wrapper ${token.rootCls}-input, ${token.rootCls}-input-number-group-wrapper ${token.rootCls}-input-number`]: { background: 'white', borderRadius: `${token.borderRadiusLG}px !important`, whiteSpace: 'nowrap', textOverflow: 'ellipsis', }, '&&-light': { [`${token.rootCls}-input-group-addon, ${token.rootCls}-input-number-group-addon`]: { backgroundColor: token.colorBgContainer, }, [`${token.rootCls}-input-group-wrapper ${token.rootCls}-input, ${token.rootCls}-input-number-group-wrapper ${token.rootCls}-input-number-input`]: { background: token.colorFillAlter, }, }, '&&-readonly': { input: { cursor: 'text', color: token.colorText, }, }, }, })); export type TokenInputProps = { theme?: MutableTheme; value?: string | number; onChange?: (value: string | number) => void; light?: boolean; readonly?: boolean; onReset?: () => void; canReset?: boolean; hideTheme?: boolean; }; const TokenInput = defineComponent({ name: 'TokenInput', inheritAttrs: false, props: { theme: { type: Object as PropType }, value: { type: [String, Number] }, onChange: { type: Function as PropType<(value: string | number) => void> }, light: { type: Boolean }, readonly: { type: Boolean }, onReset: { type: Function as PropType<() => void> }, canReset: { type: Boolean }, hideTheme: { type: Boolean }, }, setup(props, { attrs }) { const { value, theme, light, readonly, canReset: customCanReset, hideTheme } = toRefs(props); const valueRef = ref(value.value || ''); const tokenValue = ref(value.value || ''); const canReset = computed(() => customCanReset.value ?? valueRef.value !== tokenValue.value); const locale = useInjectLocaleContext(); const [wrapSSR, hashId] = useStyle(); watch( value, val => { if (val !== undefined) { tokenValue.value = val; } }, { immediate: true }, ); const debouncedOnChange = debounce((newValue: number | string) => { props.onChange?.(newValue); }, 500); const handleTokenChange = (newValue: number | string) => { if (!readonly.value) { tokenValue.value = newValue; debouncedOnChange(newValue); } }; const handleReset = () => { if (props.onReset) { props.onReset(); } else { handleTokenChange(valueRef.value); } }; return () => { const addonAfter = !readonly.value && ( {canReset.value || hideTheme.value ? ( ) : ( {theme.value?.name} )} ); let inputNode; if (typeof valueRef.value === 'string' && isColor(valueRef.value)) { inputNode = ( ( { handleTokenChange(v); }} /> ), }} > } onChange={e => { handleTokenChange(e.target.value); }} /> ); } else if (typeof valueRef.value === 'number') { inputNode = ( { handleTokenChange(Number(newValue)); }} /> ); } else { inputNode = ( { handleTokenChange( typeof value.value === 'number' ? Number(e.target.value) : e.target.value, ); }} /> ); } return wrapSSR(
{inputNode}
, ); }; }, }); export default TokenInput;