diff --git a/src/directive.ts b/src/directive.ts index 526471a..d977f80 100644 --- a/src/directive.ts +++ b/src/directive.ts @@ -5,6 +5,16 @@ type MaskaDirective = Directive const masks = new WeakMap() +const checkValue = (input: HTMLInputElement): void => { + const value = input.dataset.maskaValue + if ( + (value == null && input.value !== '') || + (value != null && value !== input.value) + ) { + input.dispatchEvent(new CustomEvent('input')) + } +} + export const vMaska: MaskaDirective = (el, binding) => { const input = el instanceof HTMLInputElement ? el : el.querySelector('input') const opts = { ...(binding.arg as MaskInputOptions) } ?? {} @@ -13,6 +23,8 @@ export const vMaska: MaskaDirective = (el, binding) => { const existed = masks.get(input) if (existed != null) { + checkValue(input) + if (!existed.needUpdate(input, opts)) { return } @@ -38,10 +50,8 @@ export const vMaska: MaskaDirective = (el, binding) => { masks.set(input, new MaskInput(input, opts)) - // check initial value for v-model + // timeout to process initial v-model value setTimeout(() => { - if (input.value !== '') { - input.dispatchEvent(new InputEvent('input')) - } + checkValue(input) }) } diff --git a/src/mask-input.ts b/src/mask-input.ts index a78c4f0..cbb5aa5 100644 --- a/src/mask-input.ts +++ b/src/mask-input.ts @@ -145,6 +145,7 @@ export class MaskInput { } input.value = value + input.dataset.maskaValue = value const detail = { masked: mask.masked(value), diff --git a/test/components/ChangeValue.vue b/test/components/ChangeValue.vue new file mode 100644 index 0000000..c2700c5 --- /dev/null +++ b/test/components/ChangeValue.vue @@ -0,0 +1,11 @@ + + + diff --git a/test/directive.test.ts b/test/directive.test.ts index 6f638f8..d022363 100644 --- a/test/directive.test.ts +++ b/test/directive.test.ts @@ -6,6 +6,7 @@ import BindInitial from './components/BindInitial.vue' import BindMasked from './components/BindMasked.vue' import BindUnmasked from './components/BindUnmasked.vue' import Callbacks from './components/Callbacks.vue' +import ChangeValue from './components/ChangeValue.vue' import Completed from './components/Completed.vue' import Config from './components/Config.vue' import Custom from './components/Custom.vue' @@ -137,6 +138,19 @@ test('custom component', async () => { expect(wrapper.get('div').element.textContent).toBe('1-2') }) +test('change value', async () => { + const wrapper = mount(ChangeValue) + const input = wrapper.get('input') + + await new Promise((r) => setTimeout(r)) + + expect(input.element.value).toBe('1-2') + + await wrapper.get('button').trigger('click') + + expect(input.element.value).toBe('3-4') +}) + test('multiple inputs', async () => { const wrapper = mount(Multiple) const input = wrapper.get('#input1')