Как получить необработанное значение поля <input type = «number»>?


117

Как я могу получить «реальное» значение <input type="number">поля?


У меня есть inputкоробка, и я использую новый тип ввода HTML5 number:

<input id="edQuantity" type="number">

В основном это поддерживается в Chrome 29:

введите описание изображения здесь

Что мне теперь нужно, так это возможность читать «сырое» значение, введенное пользователем в поле ввода. Если пользователь ввел номер:

введите описание изображения здесь

тогда edQuantity.value = 4и все хорошо.

Но если пользователь вводит недопустимый текст, я хочу покрасить поле ввода красным цветом:

введите описание изображения здесь

К сожалению, для type="number"поля ввода, если значение в текстовом поле не является числом, valueвозвращается пустая строка:

edQuantity.value = "" (String);

(как минимум в Chrome 29)

Как я могу получить "сырое" значение элемента <input type="number">управления?

Я попытался просмотреть список других свойств поля ввода Chrome:

введите описание изображения здесь

я не видел ничего похожего на фактический ввод.

Я также не мог найти способ узнать, «пусто» ли поле или нет. Возможно, я мог предположить:

value          isEmpty        Conclusion
=============  =============  ================
"4"            false          valid number
""             true           empty box; not a problem
""             false          invalid text; color it red

Примечание . Все, что находится после горизонтальной линейки, можно игнорировать; это просто наполнитель для обоснования вопроса. Также: не путайте пример с вопросом. Люди могли бы ответить на этот вопрос , по причинам , другие , чем окрашивать коробки красных (один пример: преобразование текста "four"в латинском "4"символ во время мероприятия ONBLUR)

Как я могу получить "сырое" значение элемента <input type="number">управления?

Бонусное чтение


2
«Настоящее» значение числового поля ввода должно быть числом. Если вы хотите разрешить ввод, отличный от числовых значений, то numberэто не тот тип ввода, который вы ищете; используйте обычный textввод.
— robertc

7
@robertc Chrome - это агент, позволяющий вводить кроме чисел; мне просто нужно знать, что они ввели не цифры.
— Ian Boyd

1
Проверьте поле в validityсостоянии - я бы ожидать , typeMismatchно я не проверял сам.
— robertc

2
@ int32_t Прочтите шестую строчку вниз (т.е. «Но если пользователь войдет ...» )
— Ян Бойд

6
Мой вариант использования ... У меня есть два числовых поля: широта и долгота. Я хотел бы определить, вставляет ли кто-то в "lat, lon" и правильно ли обрабатывает. В настоящее время это невозможно с type = "number". поскольку "lat, lon" недействителен ... нет способа получить "сырое" значение для выполнения регулярного выражения. Другой вариант использования: отображение ошибки клиента: « blahневерный номер».
— Брэд Кент

Ответы:


55

Согласно WHATWG , вы не сможете получить значение, если это не допустимый числовой ввод. Алгоритм очистки числового поля ввода говорит, что браузер должен установить значение в пустую строку, если ввод не является допустимым числом с плавающей запятой.

Алгоритм значения санитарного выглядят следующим образом : Если значение элемента не является допустимым число с плавающей точкой , а затем установить его в пустую строку вместо.

Указывая type ( <input type="number">), вы просите браузер сделать за вас некоторую работу. Если, с другой стороны, вы хотите иметь возможность захватывать нечисловой ввод и что-то делать с ним, вам придется полагаться на старое проверенное и достоверное поле ввода текста и самостоятельно анализировать содержимое.

W3 имеет те же характеристики и добавляет:

Пользовательские агенты не должны позволять пользователю устанавливать значение непустой строки, которая не является допустимым числом с плавающей запятой.


6
Было бы полезно, если бы пользовательские агенты не разрешали пользователю устанавливать значение в непустую строку, которая не является допустимым числом с плавающей запятой. Но если whatwg говорит, что это невозможно; тогда это ответ. Обходной путь для моей текущей потребности добавлен ниже.
— Ян Бойд

57
Указывая type ( <input type="number">), вы просите браузер сделать за вас некоторую работу. Лично я просто просил мобильные браузеры отображать цифровую клавиатуру и получил подтверждение как неприятную дополнительную вещь. Большинство этих проблем проистекает из того факта, что typeатрибут определяет как правила проверки, так и правила о том, какой механизм ввода отображать, но вполне возможно захотеть показать цифровую клавиатуру мобильным пользователям, не желая также, чтобы проверка номера применялась к пользователям настольных компьютеров. HTML 5.1 в конечном итоге решит эту проблему с помощью inputmodeатрибута.
— Марк Эмери

4
но когда браузер делает недостаточно, я хотел бы иметь возможность завершить его. например, удаление пробелов во вводе, определение десятичной точки ...
— njzk2

1
Кроме того, в разных языках, например во французском, есть 2 слова для числа. один для чисел в качестве идентификаторов, таких как номера кредитных карт, и один для подсчета чисел, таких как числа с плавающей запятой.
— njzk2

1
@MotiKorets не работает для ввода чисел с плавающей запятой, поскольку iPhone не помещает десятичную точку на клавиатуре. К сожалению, на данный момент разработчики сильно облажались, обеспечивая хороший UX для ввода с плавающей запятой ...
— Энди

50

Это не дает ответа на вопрос, но полезный обходной путь - проверить

edQuantity.validity.valid

Объект ValidityStateобъекта дает подсказку о том, что ввел пользователь. Рассмотрим type="number"вход с a minи maxустановите

<input type="number" min="1" max="10">

Мы всегда хотим использовать .validity.valid.

Другие свойства предоставляют только бонусную информацию:

User's Input  .value  .valid | .badInput  .rangeUnderflow  .rangeOverflow
============  ======  ====== | =========  ===============  ==============
""            ""      true   | false      false            false  ;valid because field not marked required
"1"           "1"     true   | false      false            false  
"10"          "10"    true   | false      false            false
"0"           "0"     false  | false      true             false  ;invalid because below min
"11"          "11"    false  | false      false            true   ;invalid because above max
"q"           ""      false  | true       false            false  ;invalid because not number
"³"           ""      false  | true       false            false  ;superscript digit 3
"٣"           ""      false  | true       false            false  ;arabic digit 3
"₃"           ""      false  | true       false            false  ;subscript digit 3

Перед использованием убедитесь, что браузер поддерживает проверку HTML5:

function ValidateElementAsNumber(element)
{
   //Public Domain: no attribution required.
   if ((element.validity) && (!element.validity.valid))
   {
      //if html5 validation says it's bad: it's bad
      return false;
   }

   //Fallback to browsers that don't yet support html5 input validation
   //Or we maybe want to perform additional validations
   var value = StrToInt(element.value);
   if (value != null)
      return true;
   else
      return false;
}

бонус

У Спадли есть полезный ответ, который он удалил:

Просто используйте :invalidдля этого селектор CSS .

input[type=number]:invalid {
    background-color: #FFCCCC;
}

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

Поддержка браузером <input type='number'>примерно такая же :invalid, так что проблем нет.

Подробнее читайте :invalid здесь .


Не работает в Opera. Он говорит, что действительно, даже если вы вводите строку.
— Берги

Opera поддерживает .validityсвойство, но не обрабатывает его правильно .valid?!
— Ian Boyd

Да, но когда ввод числа недопустим ? Он просто действует так, как если бы ввод был пуст. A typeMismatchможет иметь смысл, но это только для типов электронной почты или URL…
— Берги

@Bergi В таблице выше приведены примеры, когда числовые значения могут быть недопустимыми: «q», «11» (тогда максимальное значение равно 10), «0» (когда минимальное значение равно 1), «» (тогда элемент равен required)
— Ян Boyd

1
@Bergi .badInputдобавлен 20.11.2012 . Но никто не должен смотреть, badInputверен ли ввод; они должны смотреть .valid. Возможно (и правильно), .badInputчто он будет ложным, но все равно будет иметь недопустимый ввод. .validопределяется как отсутствие каких-либо ошибок проверки (например, несоответствия, переполнения, потери значимости), из которых .badInputтолько один вид ошибок. Обратите внимание на диаграмму выше, где указано значение .badInputfalse, но ввод все еще недействителен.
— Ян Бойд

11
input.focus();
document.execCommand("SelectAll");
var displayValue = window.getSelection().toString();


Не работает в firefox: bugzilla.mozilla.org/show_bug.cgi?id=85686 (обратите внимание, что эта ошибка была зарегистрирована в 2001 году !!)
— Брэд Кент,

Firefox, как всегда, правильный. Это не должно работать и является ошибкой
— vsync

4

Отслеживайте все нажатые клавиши на основе их кодов клавиш

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

http://unixpapa.com/js/key.html

Выберите ввод и получите выделение в виде строки

document.querySelector('input').addEventListener('input', onInput);

function onInput(){
  this.select(); 
  console.log( window.getSelection().toString() )
}
<input type='number'>

Все кредиты на: int32_t


Это решение было испробовано в другом месте, но оно не работает . Особенно , когда пользователи прессы Delete, Backspace, Ctrl+X, Ctrl+V, Right-click-cut, Right-click-paste.
— Ян Бойд,

Я согласен с вами, в основном то, что спросил OP, невозможно. Однако оба упомянутых мною взлома (и я не отрицаю, что это взломы) в некоторой степени работают. Может быть, они могут быть кому-то полезны, в каком-то случае?
— Sandstrom

как ни странно, выбор работает. Какие ограничения у этого метода?
— njzk2

Ограничения: текст выделяется визуально. Если пользователь что-то
— напечатает,

Отредактировано живой демонстрацией, которая показывает, насколько плох этот метод
— vsync
Используя наш сайт, вы подтверждаете, что прочитали и поняли нашу Политику в отношении файлов cookie и Политику конфиденциальности.
Licensed under cc by-sa 3.0 with attribution required.