如何在用户使用 JavaScript 单击它时重置 input type=number 元素

How to reset an input type=number element when the user clicks it using JavaScript

我正在尝试使用 <input type="number" ...> 列表选项 创建一个显示一组预定义的数字输入字段'favorite' 个值,但仍允许用户输入其他值。

到目前为止,这是我所拥有的:

<label>
  Zoom(%)
  <input type="number"
         min="50" step="50" value="100"
         list="favorites"
         title="Please enter or choose a zoom value." />
  <datalist id="favorites">
    <option value="100" />
    <option value="150" />
    <option value="200" />
    <option value="250" />
    <option value="300" />
  </datalist>
</label>

问题:

有两个问题:

  1. 在第一次selecting/entering一个值并退出该字段后,下一次该字段获得焦点时,下拉列表仅显示一些与当前输入值匹配的选项,并且
  2. 必须清除输入元素并单击两次才能显示完整的选项列表。

目标:

每次显示下拉列表时,如何获取要显示的完整选项列表?

我尝试向输入元素添加内联 onclick="this.value = '';" 代码段,以便在每次用户单击输入元素时重置输入元素,但有时这似乎有效,它并不总是有效,即使在同一个浏览器中,所以这不是跨浏览器问题。

有没有一种方法可以像重置表单一样重置输入元素,而无需实际使用封闭的表单元素?

我在使用表单时遇到的问题是,当我使用表单元素来包含输入字段并重置父表单时,我无法嵌套表单以仅隔离一个输入元素并重置父表单重置所有我不想要的输入元素。

这是一个 CodePen 示例,展示了我的测试用例和其他示例。 CodePen 示例中的最后一个示例显示了输入类型数字的替代,但没有列表属性。这将列表功能与输入元素分开,以便在用户按下输入元素旁边的向下三角形列表按钮之前,不会显示下拉列表。在列表实际显示之前,列表中的选项是过滤器,其中包含用户可能在输入字段中键入的任何内容,并支持部分匹配。输入字段的 initial/default 值未用作过滤器,因此整个列表会显示,直到在字段中输入内容或单击清除按钮后。

这里是一个结合了数字输入和下拉列表的示例,以实现比使用带有数据列表选项的数字输入更好的解决方案。

div {
  display: inline-block;
  vertical-align: top;
  padding-right: 10px;
}

span.h {
  font-weight: 900;
  font-size: x-large;
}

button.blacktriangledown {
  position: relative;
  top: -1px;
  margin-left: -5px;
  padding: 0;
  height: 21px;
  width: 20px;
  outline: none;
}
button.blacktriangledown > div {
  position: relative;
  top: -7px;
  left: -3px;
  font-size: 26px;
}

button.times {
  outline: none;
  padding: 0;
  height: 20px;
  width: 20px;
}
button.times > div {
  position: relative;
  top: -8px;
  font-size: 26px;
}

datalist {
  display: none;
  position: absolute;
  top: 20px;
  left: 0px;
  border: thin solid black;
  background-color: white;
  cursor: pointer;
}

datalist > option:hover {
  border: thin solid black;
  background-color: lightskyblue;
}
<div>
  <p>
    <span class="h">Input-7</span><br />
    <b><u>with</u> an inline reset inline code segment and list and clear buttons</b>
  </p>
  <label>
    Zoom(%)
    <div style="position: relative;">
      <input type="number" id="input7" min="50" step="50" filter="" value="100"
             datalist="favorites7"
             title="Please enter or choose a zoom value."
             oninput="this.setAttribute( 'filter', this.value );" />
      <button class="blacktriangledown" onclick="listButton( this );">
        <div>&blacktriangledown;</div>
      </button>
      <button class="times" onclick="clearButton( this );">
        <div>&times;</div>
      </button>
      <script>
        function listButton( This ) {
          var input   = This.parentElement.querySelector( 'input' );
          var filter  = input.getAttribute( 'filter' );
          var value   = input.value;
          var list    = This.parentElement.querySelector( 'datalist' );
          var options = list.options;

          var option;

          for( var i = 0, l = options.length; i < l; ++i ) {

            option                       = options[ i ];

            option.style.backgroundColor = ( ( option.value === value )
                                             ? 'lightblue'
                                             : 'inherit' );

            if( filter !== '' )
              option.hidden = ( option.value.indexOf( filter ) === -1 );

          }

          list.style.display = ( ( list.style.display === 'inline' )
                                 ? 'none'
                                 : 'inline' );

        }

        function clearButton( This ) {
          var input   = This.parentElement.querySelector( 'input' );
          var list    = This.parentElement.querySelector( 'datalist' );
          var options = list.options;

          list.style.display = 'none';

          for( var i = 0, l = options.length; i < l; ++i )
            options[ i ].hidden = false;

          input.setAttribute( 'filter', '' );

          input.value = input.defaultValue;
          input.focus();
        }
      </script>
      <datalist id="favorites7">
        <option value="50">50%&nbsp;(half-size)</option>
        <option value="100">100%&nbsp;(full-size)</option>
        <option value="150">150%</option>
        <option value="200">200%</option>
        <option value="250">250%</option>
        <option value="300">300%</option>
      </datalist>
      <script>
        ( function() {
            var lists   = document.querySelectorAll( 'datalist' );
            var list    = lists[ lists.length - 1 ];
            var options = list.options;

            list.value          =
            list.selectedOption = null;
            list.selectedIndex  = -1;
            list.length         = list.length;

            for( var i = 0, l = options.length; i < l; ++i ) {

              options[ i ].index = i;
              options[ i ]
              .addEventListener( 'click',
                                 function() {
                                   var list            = this.parentElement;

                                   list.style.display  = 'none';
                                   list.value          = this.value;
                                   list.selectedOption = this;
                                   list.selectedIndex  = this.index;

                                   list.parentElement
                                       .querySelector( 'input' )
                                       .value          = this.value ;

                                 } );

            }

          } )();
      </script>
    </div>
  </label><br />
  <span id="span7"></span>
</div>