Вот моя реализация с использованием Numeral.js:
Vue.filter('formatNumber', function (value) {
return numeral(value).format('0,0.[000]')
})
Vue.component('input-number', {
template: '\
<div>\
<label v-if="label">{{ label }}</label>\
<input\
ref="input"\
v-bind:value="displayValue(value)"\
v-on:input="updateValue($event.target.value)"\
v-on:focus="selectAll"\
>\
</div>\
',
props: {
value: {
},
label: {
}
},
methods: {
updateValue: function (inputValue) {
var valToSend = inputValue
var numVal = numeral(valToSend).value()
if (isNaN(numVal)) {
valToSend = this.value.toString()
numVal = numeral(valToSend).value()
}
var formattedVal = numeral(numVal).format('0,0.[000]')
this.$refs.input.value = formattedVal + (valToSend.endsWith('.') ? '.' : '')
this.$emit('input', numeral(formattedVal).value())
},
displayValue: function (inputValue) {
return numeral(inputValue).format('0,0.[000]')
},
selectAll: function (event) {
// Workaround for Safari bug
// http://coderhelper.com/questions/1269722/selecting-text-on-focus-using-jquery-not-working-in-safari-and-chrome
setTimeout(function () {
event.target.select()
}, 0)
}
}
})
var app = new Vue({
el: '#app',
data: {
pricePerGram: '160000',
weightInGrams: '1.5',
},
computed: {
totalPrice: function () {
return (this.pricePerGram * this.weightInGrams)
},
toatlWithVat: function () {
return (this.totalPrice *1.09)
}
}
})
<script src="https://cdn.jsdelivr.net/npm/vue@2.5.16/dist/vue.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/numeral.js/2.0.6/numeral.min.js"></script>
<div id="app">
<input-number v-model="pricePerGram" label="Price per gram:"></input-number><br />
<input-number v-model="weightInGrams" label="Weight in grams:"></input-number><br />
<div><label>Total price: </label><span dir="ltr">{{totalPrice | formatNumber}}</span></div><br />
<div><label>Total + Vat: </label><span dir="ltr">{{toatlWithVat | formatNumber}}</span></div><br />
</div>
Правильно ли я делаю? Есть ли лучший способ реализовать только числовой ввод?
Я хочу это улучшить. Использование Numeral.js не является обязательным. Это просто библиотека, которую я нашел.
несколько вещей, касающихся текущей реализации:
-
Поддерживает разделитель тысяч (по мере ввода).
-
Поддерживает десятичную точку с 3 цифрами (Я хотел бы улучшить это и принять неограниченное количество десятичных цифр. это из-за этого формата
0,0.[000]
. Я не смог найти формат, принимающий неограниченное количество десятичных цифр с Numeral.js) -
допускаются только цифры, запятая и точка (символы не допускаются).
Я также могу использовать регулярное выражение вместо Numeral.js. Может ли это быть улучшением?
Ваш код выглядит действительно чистым и многообещающим. Я могу заменить «toLocaleString» регулярным выражением, но я думаю, что ваш подход чище, чем мой. Спасибо тебе, друг.