首页 文章

HTML5输入类型=数字更改步骤行为

提问于
浏览
25

如果我使用type =“number”的输入字段,其中step =“100” . 我不希望奇数无效 . 我只想增加或减少值为1000 .

<input type="number" min="100" max="999999" step="100" />

如果用户输入值“199”并提交,则他/她得到一个错误,因为该值不能被100分割 . 但我想要的步长值是控制微调器的行为,例如,如果用户点击我希望值199变为200并且如果他/她点击它我希望它变为100.或者理想情况下我希望值增加或减少值为100 .

我该怎么做呢?我尝试使用无效事件(使用jQuery 1.7.2),如下所示:

$( "[type='number']" ).bind( 'invalid', function( e ) {
    var el = $( this ),
      val = el.val( ),
      min = el.attr( 'min' ),
      max = el.attr( 'max' );

    if ( val >= min && val <= max ) {
        return false;
    }
} );

但这导致表单未提交 .

PS . :这是Fedora 16上的Google Chrome 20.0.1132.57 .

8 回答

  • 1

    我认为你不能, step 和验证是closely tied together . 在将来,您可以覆盖stepUp() and stepDown() functions以获取您描述的行为,但我还没有研究过这是否是这些事情的预期用例 . 我建议在WHATWG mailing list上发帖,具体询问这些功能并描述你的用例 .

    出于当前的实际目的,您是否尝试过设置 step=1 并绑定到 click 事件来捕获?我可以看到'll probably be an issue with distinguishing between '向下'点击',但这可能是可以克服的 . 然而,可能更容易使用 text 输入,适当地设置 pattern 属性并实现自己的微调器 .

  • 0

    好吧,首先感谢你提出这个非常有趣的问题 . 通过搜索问题的解决方案,我学到了很多关于HTML5验证的知识 .

    我的研究让我发现HTML5表单验证API有一个interesting set of properties是只读的,但对于你想要的东西非常有用 .

    我对你的问题的处理方法是首先将 novalidate 属性添加到表单元素,这样我就可以控制何时触发验证,然后读取附加到输入的 validity 对象,这样我就可以准确地知道哪些验证错误,以及如果唯一的错误是 stepMismatch (这是触发数字无效的原因,如199),我可以绕过所有的验证过程 . 否则,我可以使用reportValidity()方法显示正常的HTML验证行为 .

    这是我提出的代码,我希望能做到你想要的:

    var form = document.querySelector("form")       // Get the form
    var input = document.querySelector("#myInput")  // Get the input to validate
    
    form.addEventListener("submit", function(e) {
    	e.preventDefault()  // Catch the submit
      // Do the magic
      if(onlyStepMatters(input.validity)){
      	form.submit()
      }else {
      	form.reportValidity()
      }
    })
    
    function onlyStepMatters(validityState) {
      return !(
        validityState.badInput || validityState.customError || validityState. patternMismatch || validityState.rangeOverflow || validityState.rangeUnderflow || validityState.tooLong || validityState.tooShort || validityState.typeMismatch || validityState.valueMissing
        )
        
      /* This is what the object looks like, notice I just skipped the stepMismatch */
      /*
      {
        badInput,
        customError,
        patternMismatch,
        rangeOverflow,
        rangeUnderflow,
        stepMismatch,
        tooLong,
        tooShort,
        typeMismatch,
        valid,
        valueMissing,
      }
      */
    }
    
    <form novalidate>
    <input type="number" id="myInput" min="0" max="1000" step = "100" placeholder="Enter a number" required/>
    <button type="submit">Send</button> 
    </form>
    

    我很确定这个代码可以重构并基于相同的逻辑变得更简洁,但我没有足够的时间来考虑它 .

    任何建设性的评论将不胜感激 .

    希望这可以帮助 .

  • 0

    只有步骤但您可以使用范围并为滑块添加标记

    喜欢

    <input type='range' min ='0' max='50' step='1' name='slide' list="settings" onchange="updateTextInput(this.value);">
    <datalist id="settings">
    <option>15</option>
    <option>20</option>
    <option>26</option>
    <option>36</option>
    <option>50</option>
    </dataList>
    

    然后使用javascript检查near值并设置它

    <script type="text/javascript">
    function updateTextInput(val) {
    if(val>1)
          document.getElementById('textInput').value=15;
    if(val>15)
          document.getElementById('textInput').value=20; 
    if(val>20)
          document.getElementById('textInput').value=26; 
    //...
        }
      </script>
    
  • 3

    这是实现你所要求的所需代码,我试图避免重新计算和改变标准行为,因此这应该对任何其他约束设置(必需,模式,范围......)是透明的 .

    我只在Firefox和Chrome上测试过,但我相信它应该适用于任何最近的浏览器 .

    <!DOCTYPE html>
    <html lang="en">
    <head>
    <meta charset="utf-8">
    <title>Disable validity constrains</title>
    <!-- avoid highlight due to constrains -->
    <style>#qty { box-shadow: unset; }</style>
    </head>
    <body>
    <form>
            <input id="qty" name="num" type="number" min="100" max="1000" step="100">
            <input type="submit">
    </form>
    <script>
    (function() {
            var el = document.getElementById('qty');
            el && el.addEventListener('invalid', function(event) {
                    if ('validity' in el) {
                            for (var state in el.validity) {
                                    if (state == 'stepMismatch') { continue; }
                                    if (el.validity[state]) { return true; }
                            }
                            event.preventDefault();
                            el.form.submit();
                    }
            }, true);
    })();
    </script>
    </body>
    </html>
    
  • 0

    在"change" event round to nearest valid value 内 .

    $( "[type='number']" ).change(function () {
       var value = $(this).val());
       var newValue = Math.round(value/100)*100
       if (newValue < 100) {
          newValue = 100;
       }
       if (newValue > 999999) {
          newValue = 999999;
       }
       if (newValue === value ) {
          return;
       }
       $(this).val(newValue)
    })
    
  • 0

    尝试使用change()函数...

    <form>
        <input type="number" id="number" min="100" max="999999" step="100" />
    </form>
    
    $(document).ready(function(){
        $("#number").change(function(a){
            if ($(this).val() % 100 === 0) {
                /* Do something when the number is even */ 
                console.log("EVEN");
            } else {
                /* Or when it's odd (isn't dividable by 100), do ... whatever */ 
                console.log("ODD");
            }
        })
    });
    

    我正在使用bootstrap测试它,就像你想要的例子,当用户点击时该值将变为200(从199),当用户点击时该值将变为100

    要改变可分割:

    if ($(this).val() % 100 === 0) { //Change 100 with what ever you want
    
  • 0

    我一直在玩你的代码,尝试实现这个目标:

    理想情况下,我希望值增加或减少值为100

    ...并以一些脚本结束:

    • 通过键盘或鼠标检测步长增加或减少,

    • 使用 remainder 变量存储计算结果: value % 100

    • 修改 step 参数和 inputvalue

    • 在键盘或鼠标事件结束时添加 remainder 变量,并将 step 参数重置回 1 (需要能够提交) .

    在此工作代码段中,尝试使用箭头(在键盘上或使用鼠标)修改输入值,从不可除以100的数字开始:

    var remainder = false;
    var stepbefore;
    
    $("[type='number']").bind('keydown mousedown', function() {
      // If keyboard Up or Down arrow keys or mouse left button on the arrows
      if (event.keyCode == 38 || event.keyCode == 40 || event.button === 0) {
        // If there is already a change running, exit the function
        if (remainder !== false) return;
    
        var myStep = this.getAttribute("stepcustom"); // Get my "stepcustom" attribute
        remainder = this.value % myStep;
        this.value = Math.floor(this.value / myStep) * myStep;
        stepbefore = this.step;
        this.step = myStep;
      }
    });
    
    $("[type='number']").bind('keyup mouseup', function() {
      if (remainder !== false) {
        this.value = +(this.value) + remainder;
        this.step = stepbefore;
        remainder = false;
      }
    });
    
    <script src="https://ajax.googleapis.com/ajax/libs/jquery/1.7.2/jquery.min.js"></script>
    <form>
      <input type="number" min="100" max="999999" step="1" stepcustom="100" />
      <input type="submit" />
    </form>
    

    希望能帮助到你 .

  • 5

    这是一个简单的javascript函数,可以帮助你
    其中prev_num是全局变量
    这适用于 incrementdecrement 两者

    var perv_num=0;
    function ax(z)
    {
    
         let def;
         let mul=10;
         let valu;
         let valucopy=parseInt(z.value);
         let  frst;
         valucopy=((valucopy+100)%100);
    
    
             if (parseInt( z.value)<100) 
             {
                      document.getElementById("myNumber").value="";
                      document.getElementById("myNumber").value=100;
             }
             else if(parseInt( z.value)<perv_num)
            {
                      def=parseInt( z.value.length);
                      mul=Math.pow(mul,def-1);
                      frst=(parseInt(z.value[0])*mul);
                      document.getElementById("myNumber").value="";
                      document.getElementById("myNumber").value=frst;
             }
             else if(valucopy  ==0)
             {
                      document.getElementById("myNumber").value="";
                     document.getElementById("myNumber").value=parseInt(z.value)+100;
              }
              else{
                      def=parseInt( z.value.length);
                      mul=Math.pow(mul,def-1);
                      frst=(parseInt(z.value[0])*mul);
                      valu=Math.abs( parseInt(z.value)-frst);
                      valu=100-valu;
                      var number=(parseInt(z.value)+valu);
                      document.getElementById("myNumber").value="";
                      document.getElementById("myNumber").value= number;
                  }
                  perv_num=parseInt( z.value);
    }
    

    和HTML一样

    <input type="number" id="myNumber" onchange="ax(this)">
    

    小提琴是https://jsfiddle.net/ecpy5gr0/1

相关问题