Входной текст фильтра принимает только число и точку vue.js

#vue.js

#vue.js

Вопрос:

У меня есть текстовое поле, и я хочу принимать только цифры и точку «.» при использовании VueJS. Кто-нибудь может помочь с кодом? Я новичок в Vue.

Комментарии:

1. Я знаю, что это старый вопрос, но он был лучшим в результатах Google. Итак, вот решение для пользователей с подобной проблемой. Я думаю, что все решения здесь сложны. Самое простое, что можно сделать, это добавить событие @input и заменить все не цифры и точки. this.message.replace(/[^0-9.]/g,''); . Вот пример для демонстрации .

2. @KalimahApps — допускает несколько точек = проблема.

3. Серьезно, не читайте дальше, делайте то, что предлагает @Kalimah. Я включил его через 15 секунд

4. @Kalimah Мне очень нравится ваше решение. Это то, что я сделал в первую очередь, но проблема в том, что у меня есть несколько текстовых полей, которые принимают только числа. Как я могу это сделать без повторения кода? Я создал одну функцию, которая работала для всех полей, используя событие using event.target.value = event.target.value.replace(/[^0-9]/g, ""); on «@input», но когда я добавил v-model (потому что мне это нужно по другой причине), теперь она не работает… Пожалуйста, помогите. Заранее спасибо!

5. @VasilijeBursac Вы можете использовать этот codepen .

Ответ №1:

Вы можете написать метод Vue, и этот метод может быть вызван при событии нажатия клавиши. Проверьте эту скрипку.

Обновить:

добавление исходного кода:

HTML

 <div id="demo">
  <input v-model="message" @keypress="isNumber($event)">
</div>
  

Vue.js

 var data = {
  message: 1234.34
}

var demo = new Vue({
  el: '#demo',
  data: data,
  methods: {
    isNumber: function(evt) {
      evt = (evt) ? evt : window.event;
      var charCode = (evt.which) ? evt.which : evt.keyCode;
      if ((charCode > 31 amp;amp; (charCode < 48 || charCode > 57)) amp;amp; charCode !== 46) {
        evt.preventDefault();;
      } else {
        return true;
      }
    }
  }
});
  

Комментарии:

1. Чтобы не допустить изменения периода charCode !== 46 на charCode === 46

2. На самом деле привязка должна быть v-on:keypress="isNumber($event)"

3. Я попробовал в вашей скрипке js, и я могу ввести более 1 периода. Это должно быть только 1. Как это сделать?

4. Как этот дескриптор вставить?

5. Это не обрабатывает вставку случайной строки.

Ответ №2:

Вы должны изменить свой ввод на type="number" , чтобы более точно отражать ваше поведение. Затем вы можете использовать встроенный Vue.js директива v-model.number .

Использование:

 <input type="number" v-model.number="data.myNumberData"/>
  

Комментарии:

1. В некоторых браузерах есть onScroll for type=number , которые увеличивают / уменьшают значения.

2. Использование type=number не всегда является хорошим решением для числового ввода, поскольку браузер будет по-разному оформлять поле ввода и добавлять кнопки увеличения / уменьшения.

3. этот ответ работает, но только один символ (E) позволяет вводить. почему какая-либо причина?

4. @SudhirKGupta Научные обозначения, такие как 1.2e-1, что равно 0.12

5. Это по-прежнему допускает записи с несколькими десятичными точками, например 1.2.3.4.5

Ответ №3:

Это было мое решение. Большинство ответов здесь устарели. Кроме того, входные значения всегда возвращают строку, даже если вы вводите число. Поэтому из-за этого некоторые из решений здесь не сработали для меня.

В моем случае мне не нужна была десятичная точка, но я добавил ее в массив для целей этого потока.

 <b-form-input v-model.number="quantity" @keypress="isNumber($event)" type="number"></b-form-input>
  
 isNumber (evt: KeyboardEvent): void {
    const keysAllowed: string[] = ['0', '1', '2', '3', '4', '5', '6', '7', '8', '9', '.'];
    const keyPressed: string = evt.key;
    
    if (!keysAllowed.includes(keyPressed)) {
           evt.preventDefault()
    }
}
  

Комментарии:

1. Однако мой любимый ответ написан на машинописном языке.

2. это должно быть основным ответом. в большинстве остальных ответов используется event.keyCode , который удален

3. Я замечаю Backspace , что клавиши и Arrows клавиши не могут быть введены таким образом

4. С недавнего времени вы также можете обнаруживать такие ключи, как Backspace и Delete , просто добавив их в этот список. event.key поддерживает это отлично.

5. Привет! Это довольно хорошее решение, но как насчет копирования-вставки?

Ответ №4:

Короткий и понятный.

HTML

  <input @keypress="onlyNumber" type="text">
  

VUE JS

 onlyNumber ($event) {
   //console.log($event.keyCode); //keyCodes value
   let keyCode = ($event.keyCode ? $event.keyCode : $event.which);
   if ((keyCode < 48 || keyCode > 57) amp;amp; keyCode !== 46) { // 46 is dot
      $event.preventDefault();
   }
}
  

Комментарии:

1. Таким образом, нажатие клавиши «Backspace» также не допускается. Что, если я хочу удалить предыдущий номер и добавить другой?

2. Вы можете проверить код ключа, используя этот код console.log($event.keyCode); //Значение keyCodes

3. Как ограничить ввод только одной точкой?

4. код ключа устарел

Ответ №5:

Простой способ сделать это в одной строке:

 IsNumber(event) {
  if (!/d/.test(event.key) amp;amp; event.key !== '.') return event.preventDefault();
}
  

Комментарии:

1. Я не знаю о производительности (из-за регулярного выражения), но это должно быть единственным ответом, если вы проверяете числа….

2. Для меня работает if (!/^[0-9] $/.test(event.key) || event.key === '.') return event.preventDefault();

3. allowDecimalChars(event: KeyboardEvent) { if (/[^.0-9]/.test(event.key)) { event.preventDefault() } }

Ответ №6:

Вот лучший способ обработать конкретный заданный вопрос (только числа и «точки»), установив v-restrict.number.decimal, используя следующую директиву. В нем также был некоторый бонусный код для поддержки только букв или буквенно-цифровых символов. Вы также могли бы разрешить только «точки», хотя я не знаю, почему вы это делаете. Это не позволит дополнительным символам «проскальзывать» при быстром наборе текста. Он также поддерживает копирование / вставку, удаление и некоторые другие ключи, которые пользователи ожидают от ввода:

 Vue.directive('restrict', {
  bind (el, binding) {
    el.addEventListener('keydown', (e) => {
      // delete, backpsace, tab, escape, enter,
      let special = [46, 8, 9, 27, 13]
      if (binding.modifiers['decimal']) {
        // decimal(numpad), period
        special.push(110, 190)
      }
      // special from above
      if (special.indexOf(e.keyCode) !== -1 ||
        // Ctrl A
        (e.keyCode === 65 amp;amp; e.ctrlKey === true) ||
        // Ctrl C
        (e.keyCode === 67 amp;amp; e.ctrlKey === true) ||
        // Ctrl X
        (e.keyCode === 88 amp;amp; e.ctrlKey === true) ||
        // home, end, left, right
        (e.keyCode >= 35 amp;amp; e.keyCode <= 39)) {
        return // allow
      }
      if ((binding.modifiers['alpha']) amp;amp;
        // a-z/A-Z
        (e.keyCode >= 65 amp;amp; e.keyCode <= 90)) {
        return // allow
      }
      if ((binding.modifiers['number']) amp;amp;
        // number keys without shift
        ((!e.shiftKey amp;amp; (e.keyCode >= 48 amp;amp; e.keyCode <= 57)) ||
        // numpad number keys
        (e.keyCode >= 96 amp;amp; e.keyCode <= 105))) {
        return // allow
      }
      // otherwise stop the keystroke
      e.preventDefault() // prevent
    }) // end addEventListener
  } // end bind
}) // end directive
  

Для использования:

 <!-- number and decimal -->
<input
  v-model="test"
  v-ep-restrict.number.decimal
  ...
/>

<!-- alphanumeric (no decimal) -->
<input
  v-model="test2"
  v-ep-restrict.alpha.number
  ...
/>

<!-- alpha only -->
<input
  v-model="test3"
  v-ep-restrict.alpha
  ...
/>
  

Это может быть изменено, чтобы служить основой практически для любого сценария, и хороший список ключевых кодов находится здесь

Комментарии:

1. Мне нравится этот ответ, но можно ли его обновить, чтобы учесть, что код ключа устарел?

Ответ №7:

Я решил проблему, подобную вашей, с помощью vue.js фильтры. Сначала я создал фильтр — скажем, в filters.js файл

 export const JustDigits = () => {
  Vue.directive('digitsonly', (el, binding) => {
    if (/[d.] /i.test(el.value)) {
      console.log('ok');
    } else {
      let newValue = el.value.replace(/[a-zA-Z] /ig, '');
      el.value = newValue;
      console.log('should fix', newValue);
      binding.value = el.value;
    }
  });
};
  

Затем в компоненте, где требуется эта функциональность, я сделал:

 import {
  JustDigits
} from './filters';

JustDigits();
  

И тогда вы сможете использовать эту директиву в шаблоне:

  <input  v-model="myModel"
         v-digitsonly
         type="text"  
         maxlength="4"  class="form-control" id="myModel" name="my_model" />
  

Пожалуйста, обратите внимание, что мое регулярное выражение может отличаться от того, что вам нужно, не стесняйтесь изменять его, а также эту строку кода let newValue = el.value.replace(/[a-zA-Z] /ig, ''); , которая удаляет символы из строки. Я опубликовал это только для того, чтобы показать вам одно из возможных решений vue.js обеспечивает решение подобной задачи.

Комментарии:

1. если вы вводите более одной буквы, вторая иногда проходит.

2. Вы можете избежать быстрого ввода дополнительных символов, хотя и обернув значение примерно за полсекунды (импортируя из Lodash или unserscore), прежде чем проверять его

Ответ №8:

Основываясь на предыдущих решениях, чтобы предотвратить множественные десятичные позиции, также передайте v-модель функции:

<input v-model="message" v-on:keypress="isNumber($event, message)">

и измените метод isNumber следующим образом:

 isNumber(event, message) {
  if (!/d/.test(event.key) amp;amp;  
    (event.key !== "." || /./.test(message))  
  )  
    return event.preventDefault();  
}
  

Чтобы ограничить количество цифр после десятичной дроби, добавьте следующую строку в метод isNumber:

  if (/.d{2}/.test(message)) return event.preventDefault();
  

d{2} Ограничивает ввод двух цифр. Измените это на d{1} , чтобы ограничить до единицы.

Как указано в других ответах, это не препятствует вставке нечисловых данных.

Ответ №9:

Мне нужно было, чтобы мой ввод разрешал только цифры, поэтому никаких e символов, плюс, минус или . . Vue кажется странным и не запускается повторно @onkeypress для таких символов, как dot .

Вот мое решение этой проблемы:

 <input
  onkeypress="return event.key === 'Enter'
    || (Number(event.key) >= 0
    amp;amp; Number(event.key) <= 9"
  type="number"
>
  

Я беру только цифры, ограничивая от 0 до 9, но также я хочу включить отправку формы при вводе, что было бы исключено при вышеуказанном подходе — таким образом, ввод.

Комментарии:

1. В условии отсутствует скобка, но работает отлично! : пальцы вверх:

2. onkeypress устарел в Firefox

Ответ №10:

Вы можете справиться с этим с помощью простого html

 <input type="number">
  

и в вашем app.css

 /* Chrome, Safari, Edge, Opera */
input::-webkit-outer-spin-button,
input::-webkit-inner-spin-button {
  -webkit-appearance: none;
  margin: 0;
}

/* this is for Firefox */
input[type=number] {
  -moz-appearance: textfield;
}
  

Код стиля удалит уродливые стрелки из вашего поля ввода номера, и да, он принимает точки

Ответ №11:

ответ @Kalimah не сработал для меня, но мне понравилась идея использования регулярных выражений. В моем случае мне нужно было отфильтровать любой нецифровой символ, включая точки. Приведенный ниже код работал для меня, Vue 2.6.

 <input type="text" v-model="variable" @input="cleanVariable" />
  
 methods: {
    cleanVariable(event) {
        this.variable = event.target.value.replace(/[^0-9]/g, "");
}
  

Ответ №12:

 <v-text-field class='reqField' label="NUMBER" @keypress="isNumber($event)"></v-text-field>
methods: {
    isNumber: function(evt) {
        evt = (evt) ? evt : window.event;
        var charCode = (evt.which) ? evt.which : evt.keyCode;
        if (charCode > 31 amp;amp; (charCode < 48 || charCode > 57) amp;amp; (charCode != 9)) {
            evt.preventDefault();
        } else {
            return true;
        }
        `enter code here`
    },
}
  

Комментарии:

1. Пожалуйста, объясните свой ответ

Ответ №13:

Почему бы не использовать внешнюю библиотеку масок, такую как vue-the-mask или cleave.js ?

Например, с помощью vue-the-mask вы можете легко использовать их директиву следующим образом:

 <input type="text" name="some-name" id="some-id" v-model="some.value" v-mask="'##.##.##.##.###'">
  

Комментарии:

1. vue-the-mask качается

2. Почему бы и нет? Потому что вы всегда хотите минимизировать внешние библиотеки.

Ответ №14:

Вы можете использовать эту библиотеку https://www.npmjs.com/package/vue-input-only-number

 import onlyInt, { onlyFloat } from 'vue-input-only-number';

Vue.use(onlyInt);
Vue.use(onlyFloat);

<input type="text" v-int>
<input type="text" v-float>
  

Ответ №15:

Просто оцените, равно ли значение nan, и теперь вы можете предотвратить дефолт

 <input @keypress="isNumber">

isNumber (val) {
  if (isNaN(Number(val.key))) {
    return val.preventDefault();
  }
}
  

Комментарии:

1. Это было бы отличным ответом, если бы он также не отключал delete enter клавиши и.

Ответ №16:

Я не могу найти идеального решения, так как некоторые работают для ввода, но не для копирования и вставки, некоторые наоборот. Это решение работает для меня. Он предотвращает отрицательные числа, ввод «e», копирование и вставку текста «e».

Я использую mixin, чтобы меня можно было повторно использовать где угодно.

 const numberOnlyMixin = {
    directives: {
    numericOnly: {
        bind(el, binding, vnode) {

        // console.log(el, binding);

        // this two prevent from copyamp;paste non-number text, including "e".
        // need to have both together to take effect.
        el.type = 'number';
        el.addEventListener('input', (e) => {
            // console.log('input', e);
            // console.log(el.validity);
            return el.validity.valid || (el.value = '');
        });

        // this prevents from typing non-number text, including "e".
        el.addEventListener('keypress', (e) => {
            let charCode = (e.which) ? e.which : e.keyCode;
            if ((charCode > 31 amp;amp; (charCode < 48 || charCode > 57)) amp;amp; charCode !== 46) {
            e.preventDefault();
            } else {
            return true;
            }
        });
        }
    }
    },
};

export {numberOnlyMixin}
  

В вашем компоненте добавьте к своему вводу.

 <input v-model="myData" v-numericOnly />
  

Комментарии:

1. ПОТЕНЦИАЛЬНАЯ УТЕЧКА ПАМЯТИ! Готово ли это решение к производству? Я думаю, вам нужно отвязать прослушиватели событий, когда элемент покидает DOM.

2. Я считаю, что создание директивы является правильным подходом, хотя эта реализация сложнее, чем должна быть. Если вы обеспокоены утечками памяти, вы можете удалить прослушиватель в unbind событии директивы. Однако JavaScript, похоже, позаботится об этом автоматически.

Ответ №17:

Существует input событие, которое является более мощным / гибким, чем keypress , keydown или change которое реагирует на любой тип изменения: тип программы или пользователя, например, нажатия клавиш или события вставки.

 // Initial input state
let prevValue = ''
let prevSelectionStart = 0

function allowNumbersOnly(event) {
  const input = event.target
  let value = event.target.value

  // Check if value is number
  let isValid =  value ==  value

  if (isValid) {
    // preserve input state
    prevValue = value
    prevSelectionStart = input.selectionStart
  } else {
    // restore previous valid input state.
    // we have to fire one more Input event in  order to reset cursor position.
    var resetEvent = new InputEvent('input')
    input.value = prevValue
    input.selectionStart = prevSelectionStart
    input.selectionEnd = prevSelectionStart
    input.dispatchEvent(resetEvent)
  }
}  
 <input type="text" oninput="allowNumbersOnly(event)">  

Ответ №18:

Проблема с type="number" and min="1" заключается в том, что он позволяет вводить или вставлять - знак, e знак и знак.

Проблема в Math.abs(value) том, что он заменяет весь введенный номер на 0 , чего мы не хотим, и это очень расстраивает.

Очень e.keyCode нечитаемый и устаревший.

Метод чистого HTML в этом случае не работает, вам нужно использовать JavaScript.

Удалите type="number" и сделайте это:

 function inputNumberAbs() {
  var input = document.getElementsByTagName("input")[0];
  var val = input.value;
  val = val.replace(/^0 |[^d.]/g, '');
  input.value = val;
}  
 <input oninput="inputNumberAbs()">  

Объяснение регулярных выражений:

^0 удаляет все 0 с начала

| ИЛИ оператор

[^d]. удалите все, что является ^ (НЕ) a d (ЧИСЛО) или a . (ТОЧКА)

Это не позволяет пользователю вводить или вставлять какие-либо из не определенных символов, например e, -, , , и все другие символы, которые не являются числами.

Если вам не нужны десятичные числа, просто удалите . из регулярного выражения.

Ответ №19:

Вы можете использовать в нем тип числа:

 <input type="number" class="yourCssClass" placeholder="someText" id="someId" />
  

а затем добавьте CSS, необходимый для удаления вращателей вверх / вниз:

 /* Chrome, Safari, Edge, Opera */
  input::-webkit-outer-spin-button,
  input::-webkit-inner-spin-button {
    -webkit-appearance: none;
    margin: 0;
  }

  /* Firefox */
  input[type=number] {
    -moz-appearance: textfield;
  }
  

Комментарии:

1. Этого ответа недостаточно. Он не обрабатывается e в браузерах на основе Chromium. Кроме того, браузеры, такие как Firefox, не блокируют нечисловые символы, когда вводится тип number . Вы можете проверить это с помощью документации MDN во время запуска Firefox: developer.mozilla.org/en-US/docs/Web/HTML/Element/input/number