Comment puis-je limiter les entrées possibles dans un élément «nombre» HTML5?

359

Pour l' <input type="number">élément, maxlengthne fonctionne pas. Comment puis-je restreindre le maxlengthpour cet élément numérique?

Prasad
la source
5
Pour les personnes à la recherche d'une meilleure solution, celle-ci est la meilleure: stackoverflow.com/questions/9361193/…
Ünsal Korkmaz
4
L'attribut max ne fonctionne pas dans le navigateur Chrome dans la tablette Android.
Forever
4
@ ÜnsalKorkmaz: cette solution a l'inconvénient de ne pas faire apparaître le clavier numérique sur les appareils Android
Le

Réponses:

340

Et vous pouvez ajouter un maxattribut qui spécifiera le plus grand nombre possible que vous pourrez insérer

<input type="number" max="999" />

si vous ajoutez à la fois une maxet une minvaleur, vous pouvez spécifier la plage de valeurs autorisées:

<input type="number" min="1" max="999" />

Ce qui précède n'empêchera toujours pas un utilisateur d'entrer manuellement une valeur en dehors de la plage spécifiée. Au lieu de cela, il affichera une fenêtre contextuelle lui disant d'entrer une valeur dans cette plage lors de la soumission du formulaire, comme indiqué dans cette capture d'écran:

entrez la description de l'image ici

Cyclonecode
la source
4
Krister, cela a fonctionné. Aussi, comme @Andy l'a dit, j'ai utilisé l'entrée pour découper les nombres supplémentaires. Référence mathiasbynens.be/notes/oninput
Prasad
7
@Prasad - Si la réponse d'Andy est correcte, sélectionnez-la, au lieu de la réponse la plus votée.
Moshe
81
C'est correct, mais il convient de noter qu'Andy déclare que cela n'empêche pas de taper un numéro plus long. Ce n'est donc pas vraiment l'équivalent de maxlength dans un champ de texte.
DA.
9
Si vous entrez simplement un flotteur de précision supérieure, cela se cassera. Par exemple, 3.1415926 contourne ce problème car il est inférieur à 999 et supérieur à 1.
0112
44
Je ne sais pas pourquoi cela est si voté et accepté si cela ne fonctionne tout simplement pas! Cela n'affecte que les contrôles "spinner", et ne fait rien pour empêcher l'utilisateur de taper un nombre long.
Codemonkey
115

Vous pouvez spécifier les attributs minet max, qui autoriseront la saisie uniquement dans une plage spécifique.

<!-- equivalent to maxlength=4 -->
<input type="number" min="-9999" max="9999">

Cependant, cela ne fonctionne que pour les boutons de commande du spinner. Bien que l'utilisateur puisse être en mesure de taper un nombre supérieur à celui autorisé max, le formulaire ne sera pas soumis.

Message de validation de Chrome pour les nombres supérieurs au maximum
Capture d'écran tirée de Chrome 15

Vous pouvez utiliser l' oninputévénement HTML5 en JavaScript pour limiter le nombre de caractères:

myInput.oninput = function () {
    if (this.value.length > 4) {
        this.value = this.value.slice(0,4); 
    }
}
Andy E
la source
11
Un problème possible avec cette approche JavaScript: il pourrait ne pas fonctionner comme prévu si le point d'insertion n'est pas à la fin de la valeur. Par exemple, si vous entrez la valeur "1234" dans le champ de saisie, puis déplacez le point d'insertion au début de la valeur et tapez "5", vous vous retrouvez avec la valeur "5123". Ceci est différent d'un champ d'entrée type = "texte" d'une longueur maximale de 4, où le navigateur ne vous permet pas de taper un 5ème caractère dans le champ "complet", et la valeur reste "1234".
Jon Schneider
@Andy, Évidemment, la question est à la recherche d'une façon de faire non JS maxlength.............
Pacerier
4
@Pacerier: quelque chose dans ma réponse impliquait-il que je pensais autrement? Comme vous pouvez le voir, j'ai proposé la solution la plus proche possible qui peut être obtenue en utilisant uniquement HTML, ainsi qu'une suggestion supplémentaire qui utilise JavaScript là où l'OP aurait pu vouloir empêcher l'utilisateur de taper plus de caractères que ce qui est autorisé.
Andy E
84

Si vous recherchez un Web mobile solution dans laquelle vous souhaitez que votre utilisateur voit un pavé numérique plutôt qu'un clavier de texte intégral. Utilisez type = "tel". Cela fonctionnera avec maxlength qui vous évite de créer du javascript supplémentaire.

Max et Min permettront toujours à l'utilisateur de taper des nombres supérieurs à max et min, ce qui n'est pas optimal.

Duane
la source
3
Super trouvaille, cela a fonctionné comme un charme, bravo pour ne pas avoir à créer le javascript supplémentaire.
Diego
9
J'ai trouvé que ce n'est pas la meilleure solution pour la saisie numérique car une entrée "tel" permet des symboles supplémentaires, et elle affiche des lettres à côté de chaque chiffre. Le clavier purement numérique semble beaucoup plus propre.
hawkharris
@hawkharris Vous avez raison, tapez = "nombre" est l'interface utilisateur plus propre. Il est plus facile de taper accidentellement un mauvais caractère. Une validation supplémentaire est donc nécessaire pour garantir que l'utilisateur n'entre pas de mauvaises données. Mais considérez également que l'utilisateur peut tout aussi bien saisir toutes les décimales avec un clavier numérique. De plus, cela ne résout pas la question ci-dessus sans JavaScript supplémentaire.
Duane
1
Merci, je travaille sur l'application mobile du cadre ionique et cela a résolu mon problème
Ahmed
1
si utilisé avec pattern = "[0-9] *" les symboles supplémentaires seront désactivés
apereira
71

Vous pouvez combiner tout cela comme ceci:

<input name="myinput_drs"
oninput="maxLengthCheck(this)"
type = "number"
maxlength = "3"
min = "1"
max = "999" />

<script>
  // This is an old version, for a more recent version look at
  // https://jsfiddle.net/DRSDavidSoft/zb4ft1qq/2/
  function maxLengthCheck(object)
  {
    if (object.value.length > object.maxLength)
      object.value = object.value.slice(0, object.maxLength)
  }
</script>


Mise à jour:
vous souhaiterez peut-être également empêcher la saisie de caractères non numériques, car ce object.lengthserait une chaîne vide pour les entrées numériques, et donc sa longueur serait 0. Ainsi, la maxLengthCheckfonction ne fonctionnera pas.

Solution:
voir ceci ou cela pour des exemples.

Démo - Voir la version complète du code ici:
http://jsfiddle.net/DRSDavidSoft/zb4ft1qq/1/

Mise à jour 2: voici le code de mise à jour: https://jsfiddle.net/DRSDavidSoft/zb4ft1qq/2/

Mise à jour 3: Veuillez noter que permettre à plus d'un point décimal d'être entré peut perturber la valeur numérique.

David Refoua
la source
C'est une bonne solution, mais je trouve que object.value.length renvoie 0 s'il y a des valeurs non numériques entrées.
Andrew
1
@AndrewSpear C'est parce que object.value serait une chaîne vide si vous entrez des valeurs non numériques dans les entrées avec un type de "nombre" défini. Consultez la documentation. Veuillez également lire ma mise à jour afin de résoudre ce problème.
David Refoua
Cela ne fonctionne toujours pas si vous entrez plus d'un point décimal, comme 111..1111. N'utilisez pas ce code pour la sécurité, car un code malveillant peut toujours être transmis.
PieBie
@PieBie Dude, ce code existe depuis plus de 3 ans. Utilisez jQuery à la place.
David Refoua
1
oui, je le sais, mais les débutants peuvent toujours le copier-coller.
PieBie
26

c'est très simple, avec du javascript, vous pouvez simuler un maxlength, vérifiez-le:

//maxlength="2"
<input type="number" onKeyDown="if(this.value.length==2) return false;" />
Maycow Moura
la source
12
Avec votre solution, vous ne pouvez pas utiliser le retour arrière une fois que vous avez atteint 2 caractères. mais il me manque peu de chose pour une solution fonctionnelle
Christophe Debove
12
Au lieu de onKeyDown, vous devez utiliser onKeyPress.
Rupesh Arora
1
ne fonctionnera pas si vous mettez en surbrillance le texte et appuyez sur un caractère (c'est-à-dire pour remplacer le contenu de l'entrée)
Arijoon
valider ceci s'il ne s'agit pas des clés suivantes stackoverflow.com/a/2353562/1534925
Akshay
3
le problème keydownest que vous ne pouvez pas utiliser le retour arrière au maximum de caractères. le problème keypressest que vous pouvez copier + coller au-delà du nombre maximum de caractères.
Stavm
23

Ou si votre valeur maximale est par exemple 99 et minimum 0, vous pouvez l'ajouter à l'élément d'entrée (votre valeur sera réécrite par votre valeur maximale, etc.)

<input type="number" min="0" max="99" 
   onKeyUp="if(this.value>99){this.value='99';}else if(this.value<0){this.value='0';}"
id="yourid">

Ensuite (si vous voulez), vous pouvez vérifier si l'entrée est vraiment un nombre

Richard
la source
... Génial, mais tu n'as plus besoin de min et max mec. (juste en disant)
xoxel
2
@xoxel vous faites si vous voulez que le message d'avertissement s'affiche toujours
DNKROZ
C'est vraiment bien ... Merci
Vincy Oommen
pour des raisons de généralisation je feraisonKeyUp="if(this.value>this.max)this.value=this.max;if(this.value<this.min)this.value=this.min;"
oriadam
18

Vous pouvez le spécifier sous forme de texte, mais ajouter un motif, qui ne correspond qu'aux nombres:

<input type="text" pattern="\d*" maxlength="2">

Il fonctionne parfaitement et également sur mobile (testé sur iOS 8 et Android) sort le clavier numérique.

Chris Panayotoff
la source
L'attribut pattern n'est pas pris en charge dans IE9 et les versions antérieures, et il est partiellement pris en charge dans Safari: caniuse.com/#feat=input-pattern
diazdeteran
Oui, merci pour le pointage, mais nous avons abandonné le support IE9 (en supprimant la moutarde), et je le préfère aux méthodes JS. Dépend du projet.
Chris Panayotoff
2
Un utilisateur n'est pas empêché d'entrer des caractères non numériques avec cela. Ils peuvent entrer 2 caractères quelconques. La patternseule cause la mise en évidence de la validation.
brt
testé sur Android 9 (Nokia 8) mais j'obtiens le clavier normal :( des idées?
oriadam
14

//For Angular I have attached following snippet.
<div ng-app="">
  <form>
    Enter number: <input type="number" ng-model="number" onKeyPress="if(this.value.length==7) return false;" min="0">
  </form>
  <h1>You entered: {{number}}</h1>
</div>

Si vous utilisez l'événement "onkeypress", vous n'aurez aucune limitation utilisateur en tant que telle lors du développement (testez-le à l'unité). Et si vous avez des exigences qui ne permettent pas à l'utilisateur d'entrer après une limite particulière, jetez un œil à ce code et essayez une fois.

Prasad Shinde
la source
1
Les problèmes que je vois ici sont: 1. remplacer par sélectionner le texte et le type ne fonctionne pas si l'entrée a atteint 7 chiffres 2. augmenter l'entrée de 1 lorsque le débordement "boarder" frappe fonctionne -> 9999999 et cliquez sur le haut bouton. Brise la limitation
Edub
J'ai essayé avec une version javascript simple. Si vous le souhaitez, vous pouvez voir à l'aide de l'extrait de code Run. En tant que tel, je n'ai trouvé aucune limitation.
Prasad Shinde
1
N'a pas non plus trouvé de limites. Il s'arrête à 7 chiffres. J'utilise cette solution pour mon code.
Claudio
Il y a une limitation. Lorsque vous atteignez la limite, sélectionnez tout et souhaitez les remplacer, cela ne fonctionne pas. Le remplacement ne fonctionne pour moi que lorsque j'écrase la valeur avec la valeur cur avant de retourner false.
Insomnia88
@ Insomnia88, @ edub et si nous écrivons la fonction et vérifions les conditions nécessaires ...
Prasad Shinde
12

Une autre option consiste simplement à ajouter un écouteur pour tout ce qui a l'attribut maxlength et à y ajouter la valeur de tranche. En supposant que l'utilisateur ne souhaite pas utiliser de fonction dans chaque événement lié à l'entrée. Voici un extrait de code. Ignorez le code CSS et HTML, le JavaScript est ce qui compte.

// Reusable Function to Enforce MaxLength
function enforce_maxlength(event) {
  var t = event.target;
  if (t.hasAttribute('maxlength')) {
    t.value = t.value.slice(0, t.getAttribute('maxlength'));
  }
}

// Global Listener for anything with an maxlength attribute.
// I put the listener on the body, put it on whatever.
document.body.addEventListener('input', enforce_maxlength);
label { margin: 10px; font-size: 16px; display: block }
input { margin: 0 10px 10px; padding: 5px; font-size: 24px; width: 100px }
span { margin: 0 10px 10px; display: block; font-size: 12px; color: #666 }
<label for="test_input">Text Input</label>
<input id="test_input" type="text" maxlength="5"/>
<span>set to 5 maxlength</span>

<br>

<label for="test_input">Number Input</label>
<input id="test_input" type="number" min="0" max="99" maxlength="2"/>
<span>set to 2 maxlength, min 0 and max 99</span>

Boutons Brandon
la source
10

La longueur maximale ne fonctionnera pas avec <input type="number"la meilleure façon que je sache est d'utiliser l' oninputévénement pour limiter la longueur maximale. Veuillez consulter le code ci-dessous pour une implémentation simple.

<input name="somename"
    oninput="javascript: if (this.value.length > this.maxLength) this.value = this.value.slice(0, this.maxLength);"
    type = "number"
    maxlength = "6"
 />
Neha Jain
la source
A fonctionné comme un charme!
SiboVG
9

Supposons que vous vouliez que la valeur maximale autorisée soit de 1 000 - soit tapée soit avec la double flèche.

Vous limitez les valeurs de spinner en utilisant: type="number" min="0" max="1000"

et restreindre ce qui est tapé par le clavier avec javascript: onkeyup="if(parseInt(this.value)>1000){ this.value =1000; return false; }"

<input type="number" min="0" max="1000" onkeyup="if(parseInt(this.value)>1000){ this.value =1000; return false; }">
Stnfordly
la source
8

Comme indiqué par d'autres, min / max n'est pas la même chose que maxlength car les gens peuvent toujours entrer un flottant qui serait plus grand que la longueur de chaîne maximale que vous vouliez. Pour vraiment émuler l'attribut maxlength, vous pouvez faire quelque chose comme ça dans un pincement (cela équivaut à maxlength = "16"):

<input type="number" oninput="if(value.length>16)value=value.slice(0,16)">
thdoan
la source
slice supprimera les caractères à l'insu de l'utilisateur final lorsqu'il est inséré entre les deux. tandis que max-length se bloquera.
Pradeep Kumar Prabaharan
@PradeepKumarPrabaharan maxlengthn'est pas pris en charge par les entrées de nombre. Dans mon exemple, value.slice(0,16)ne démarre que si la valeur d'entrée dépasse 16 caractères.
thdoan
oui maxlength n'est pas pris en charge pour les entrées de nombre .. ce code est gud mais ce code ne correspond pas exactement à la propriété de maxlength ..
Pradeep Kumar Prabaharan
@TobiasGaertner type="number"s'en charge :).
thdoan
@ 10basetom ... selon le navigateur ... par exemple, dans FF, vous pouvez toujours entrer des caractères et ils ne s'arrêteront pas après la limite - mais liée à l'idée du numéro de type, c'est une solution acceptable.
Tobias Gaertner
6

La réponse de Maycow Moura était un bon début. Cependant, sa solution signifie que lorsque vous entrez le deuxième chiffre, toute modification du champ s'arrête. Vous ne pouvez donc pas modifier les valeurs ni supprimer aucun caractère.

Le code suivant s'arrête à 2, mais permet de continuer l'édition;

//MaxLength 2
onKeyDown="if(this.value.length==2) this.value = this.value.slice(0, - 1);"
Tim Wright
la source
2
Nan. Essayez de coller une valeur.
Qwertiy
6

J'ai eu ce problème avant et je l'ai résolu en utilisant une combinaison de type de numéro html5 et de jQuery.

<input maxlength="2" min="0" max="59" name="minutes" value="0" type="number"/>

scénario:

$("input[name='minutes']").on('keyup keypress blur change', function(e) {
    //return false if not 0-9
    if (e.which != 8 && e.which != 0 && (e.which < 48 || e.which > 57)) {
       return false;
    }else{
        //limit length but allow backspace so that you can still delete the numbers.
        if( $(this).val().length >= parseInt($(this).attr('maxlength')) && (e.which != 8 && e.which != 0)){
            return false;
        }
    }
});

Je ne sais pas si les événements sont un peu exagérés mais cela a résolu mon problème. JSfiddle

incliner vers le bas
la source
Vous pouvez facilement coller des caractères.
Jessica
4

Entrée HTML

 <input class="minutesInput" type="number" min="10" max="120" value="" />

jQuery

 $(".minutesInput").on('keyup keypress blur change', function(e) {

    if($(this).val() > 120){
      $(this).val('120');
      return false;
    }

  });
Hector
la source
4

un moyen simple de définir la longueur maximale pour les entrées numériques est:

<input type="number" onkeypress="return this.value.length < 4;" oninput="if(this.value.length>=4) { this.value = this.value.slice(0,4); }" />
HexboY
la source
ne fonctionne pas sur Android Chrome. onkeypress a quelques problèmes avec cela.
Aakash Thakur
3

Comme avec type="number", vous spécifiez une propriété maxau lieu de maxlength, qui est le nombre maximum possible. Donc, avec 4 chiffres, maxdevrait être 9999, 5 chiffres99999 et ainsi de suite.

De plus, si vous voulez vous assurer qu'il s'agit d'un nombre positif, vous pouvez définir min="0"un nombre positif.

Jan Dragsbaek
la source
3

Pouah. C'est comme si quelqu'un avait abandonné à mi-chemin de sa mise en œuvre et pensait que personne ne le remarquerait.

Pour une raison quelconque, les réponses ci-dessus n'utilisent pas les attributs minet max. Cette jQuery le termine:

    $('input[type="number"]').on('input change keyup paste', function () {
      if (this.min) this.value = Math.max(parseInt(this.min), parseInt(this.value) || 0);
      if (this.max) this.value = Math.min(parseInt(this.max), parseInt(this.value) || 0);
    });

Il fonctionnerait probablement aussi comme une fonction nommée "oninput" sans jQuery si l'un de ces types "jQuery-is-the-devil".

Michael Cole
la source
il ne répond pas correctement à la question, mais a voté car il a résolu mon problème :)
TrOnNe
2

Comme je l' ai appris que vous ne pouvez pas utiliser l' une onkeydown, onkeypressou des onkeyupévénements pour une solution complète incluant les navigateurs mobiles. Au fait, il onkeypressest obsolète et n'est plus présent dans Chrome / Opera pour Android (voir: UI Events W3C Working Draft, 04 août 2016 ).

J'ai trouvé une solution en utilisant l' oninputévénement uniquement. Vous devrez peut-être effectuer une vérification supplémentaire des nombres, comme un signe négatif / positif ou des séparateurs décimaux et mille, etc., mais pour commencer, les éléments suivants devraient suffire:

function checkMaxLength(event) {
	// Prepare to restore the previous value.
	if (this.oldValue === undefined) {
		this.oldValue = this.defaultValue;
	}

	if (this.value.length > this.maxLength) {
		// Set back to the previous value.
		this.value = oldVal;
	}
	else {
		// Store the previous value.
		this.oldValue = this.value;
		
		// Make additional checks for +/- or ./, etc.
		// Also consider to combine 'maxlength'
		// with 'min' and 'max' to prevent wrong submits.
	}
}

Je recommanderais également de combiner maxlengthavecmin et maxd'éviter les mauvaises soumissions comme indiqué ci-dessus à plusieurs reprises.

markus s
la source
2
<input type="number" onchange="this.value=Math.max(Math.min(this.value, 100), -100);" />

ou si vous ne voulez rien saisir

<input type="number" onchange="this.value=this.value ? Math.max(Math.min(this.value,100),-100) : null" />
j4r3k
la source
1

Vous pouvez également essayer ceci pour la saisie numérique avec restriction de longueur

<input type="tel" maxlength="3" />
shinobi
la source
@tiltdown Sry pour mistype. Correction de la réponse.
shinobi
1

Je sais qu'il y a déjà une réponse, mais si vous voulez que votre entrée se comporte exactement comme l' maxlengthattribut ou aussi près que possible, utilisez le code suivant:

(function($) {
 methods = {
    /*
     * addMax will take the applied element and add a javascript behavior
     * that will set the max length
     */
    addMax: function() {
        // set variables
        var
            maxlAttr = $(this).attr("maxlength"),
            maxAttR = $(this).attr("max"),
            x = 0,
            max = "";

        // If the element has maxlength apply the code.
        if (typeof maxlAttr !== typeof undefined && maxlAttr !== false) {

            // create a max equivelant
            if (typeof maxlAttr !== typeof undefined && maxlAttr !== false){
                while (x < maxlAttr) {
                    max += "9";
                    x++;
                }
              maxAttR = max;
            }

            // Permissible Keys that can be used while the input has reached maxlength
            var keys = [
                8, // backspace
                9, // tab
                13, // enter
                46, // delete
                37, 39, 38, 40 // arrow keys<^>v
            ]

            // Apply changes to element
            $(this)
                .attr("max", maxAttR) //add existing max or new max
                .keydown(function(event) {
                    // restrict key press on length reached unless key being used is in keys array or there is highlighted text
                    if ($(this).val().length == maxlAttr && $.inArray(event.which, keys) == -1 && methods.isTextSelected() == false) return false;
                });;
        }
    },
    /*
     * isTextSelected returns true if there is a selection on the page. 
     * This is so that if the user selects text and then presses a number
     * it will behave as normal by replacing the selection with the value
     * of the key pressed.
     */
    isTextSelected: function() {
       // set text variable
        text = "";
        if (window.getSelection) {
            text = window.getSelection().toString();
        } else if (document.selection && document.selection.type != "Control") {
            text = document.selection.createRange().text;
        }
        return (text.length > 0);
    }
};

$.maxlengthNumber = function(){
     // Get all number inputs that have maxlength
     methods.addMax.call($("input[type=number]"));
 }

})($)

// Apply it:
$.maxlengthNumber();
Philll_t
la source
@Phill_t vous pouvez peut-être m'éclairer? J'ai utilisé votre code et il fonctionne bien en principe MAIS "$ (this) .attr (" maxlength ")" fournit toujours 2. ET pourquoi serait-il préférable d'utiliser "$ (this) .attr (" maxlength ")" si cela fonctionnait au lieu de simplement "this.maxlength" que j'ai testé et fonctionnait comme prévu et est plus court et à mon humble avis plus clair à lire? Ai-je manqué quelque chose?
Markus s
Que voulez-vous dire par "livre 2"?
Philll_t
Phill_t mes excuses. "this.maxLength" ne fonctionne que dans le cadre de la fonction keydown. Dans la fonction "addMax" "ceci" est le document plutôt que l'élément attendu et a donc des valeurs d'attribut différentes. Comment pourrais-je accéder à la saisie du numéro à la place? Le code ci-dessus fonctionne-t-il vraiment de votre côté? J'ai testé avec Chrome / Opera / Vivaldi, Firefox, Edge, IE et Safari et j'ai eu les mêmes résultats pour chaque navigateur. D'accord, dans Edge maxlegth = "1" et maxlength = "2" où en effet travailler mais "$ (this) .attr (" maxlength ")" n'augmente pas plus pour un nombre plus élevé !!? @anybody: Des suggestions?
Markus s
Comme je l'ai dit, il s'agit toujours de deux parce qu'il est appelé sur le document plutôt que sur l'élément en question comme je l'ai découvert lorsque je le déboguais. Au fait, vous voudrez peut-être également regarder ma solution que j'ai trouvée après avoir étudié la vôtre: stackoverflow.com/a/41871960/1312012
markus s
0

Les attributs les plus pertinents à utiliser seraient minet max.

Marcel
la source
0

Cela pourrait aider quelqu'un.

Avec un peu de javascript, vous pouvez rechercher toutes les entrées locales datetime, rechercher si l'année que l'utilisateur essaie d'entrer, plus de 100 ans à l'avenir:

$('input[type=datetime-local]').each(function( index ) {

    $(this).change(function() {
      var today = new Date();
      var date = new Date(this.value);
      var yearFuture = new Date();
      yearFuture.setFullYear(yearFuture.getFullYear()+100);

      if(date.getFullYear() > yearFuture.getFullYear()) {

        this.value = today.getFullYear() + this.value.slice(4);
      }
    })
  });
Simon Berton
la source