Compatibility with Vue 3
See original GitHub issueYesterday the final version Vue 3 was launched. But vue-currency-input
is not compatible.
So I had to write some code in one personal project that redefines the plugin, component, and directive to be allowed to be used with Vue 3.
Plugin
In the old version, the $ci
is defined in Vue.prototype.$ci
. The new version we should define this in instance.config.globalProperties.$ci
to inject the $ci
variables in the instance and make this available globally. And use the redefined directive and component too.
The new plugin was defined in this way:
import {parse, getValue, setValue} from 'vue-currency-input'
import component from './component'
import directive from './directive'
export default {
install(instance, globalOptions) {
instance.directive('currency', directive)
instance.component('currency-input', component)
instance.config.globalProperties.$ci = {
parse,
getValue,
setValue,
globalOptions,
}
},
}
Directive
In the old version, the directive hooks are bind
and componentUpdated
. In the new version, the directive hooks were renamed to beforeMount
and updated
. So we can only rename these hooks and everything will work properly, or just wrap the old directive functions in the new directive like this:
import { CurrencyDirective } from 'vue-currency-input'
export default {
beforeMount () {
CurrencyDirective.bind(...arguments)
},
updated () {
CurrencyDirective.componentUpdated(...arguments)
}
}
Component
The component requires most of the changes.
In the old version, the h
function is injected in the render
function as the first param. In the new version, we should import the h
function from the vue
package, using import { h } from 'vue'
. The way that the events are defined is different too. And we don’t have the directive property anymore.
return h('input', {
onChange: () => {
this.$emit('change', getValue(this.$el))
},
onInput: () => {
const numberValue = getValue(this.$el)
if (this.modelValue !== numberValue) {
this.$emit('update:modelValue', numberValue)
}
}
})
We doesn’t have the directives
property, so we have to initialize the NumberInput
in the mounted
hook, like:
this.$el.$ci = new NumberInput(this.$el, this.options, {
onChange: () => {},
onInput: () => {}
})
And as the props and events for v-model
was changed. We should use the modelValue
instead value
, and emit 'update:modelValue'
instead 'input'
.
The final version of the file is this:
import {
getValue, setValue, CurrencyInput
} from 'vue-currency-input'
import { NumberInput } from 'vue-currency-input/src/numberInput'
import { h } from 'vue'
import directive from './directive'
export default {
extends: CurrencyInput,
render() {
return h('input', {
onChange: () => {
this.$emit('change', getValue(this.$el))
},
onInput: () => {
const numberValue = getValue(this.$el)
if (this.modelValue !== numberValue) {
this.$emit('update:modelValue', numberValue)
}
}
})
},
directives: {
currency: directive
},
props: {
modelValue: {
type: Number,
default: null
}
},
mounted() {
this.$el.$ci = new NumberInput(this.$el, this.options, {
onChange: () => {},
onInput: () => {}
})
this.setValue(this.modelValue)
},
methods: {
setValue(value) {
if (!this?.$el?.$ci) return;
setValue(this, value)
}
}
}
Final Words
I think making the project compatible with Vue 3 is important, but we have these breaking changes. It would be great if we could have the Vue 3 compatible version of this library.
I hope that what I showed here helps us to have the compatible version, or helps anyone who wants to use this library with Vue 3.
Issue Analytics
- State:
- Created 3 years ago
- Reactions:5
- Comments:37 (16 by maintainers)
Top GitHub Comments
Hi @maxmaccari, thank you for summing up 👍
I have also followed the progress of Vue 3 with great interest and just want to let everyone know that I’m currently working on a compatible version. A beta version will be released shortly.
I just published a pre-release 2.0.0-beta.0 compatible with Vue 3 🎉
Any feedback is appreciated.