重置表单无效值

时间:2019-04-10 07:32:48

标签: javascript html forms

这是示例表格:

var form = document.querySelector('form');

function detectChange() {
  var inputs = form.querySelectorAll('input');
  for (var input of inputs) {
    if (input.value != input.defaultValue) {
      return true;
    }
  }
}

form.querySelector('button').addEventListener('click', function() {
  if (detectChange() && confirm('Are you sure you want to reset?')) {
    form.reset();
  }
});
<form>
  <input type="number">
  <input type="number" value="7">
  <button type="button">Reset</button>
</form>

我希望即使用户输入非数字值,重置按钮也可以工作。

8 个答案:

答案 0 :(得分:9)

如果您查看input DOM对象,则badInput对象下有一个属性validity,其值为boolean。对于数字输入或空白字段,其为false。但是,对于非数值,它是true,可以有趣地用于您的情况。

注意:仅在firefoxsafari上进行过测试

input
|  +-- ...
|  +-- validity
|  |   +-- badInput
|  |   +-- ...
|  +-- ...

使用此知识,您可以修改函数以检查badInput以最小的调整来实现所需的功能。

// non-empty and non default
if ((input.value && input.value != input.defaultValue) || input.validity.badInput)

var form = document.querySelector('form');

function detectChange() {
  var inputs = form.querySelectorAll('input');
  for (var input of inputs) {
    if ((input.value && input.value != input.defaultValue) || input.validity.badInput) {
      return true;
    }
  }
}

form.querySelector('button').addEventListener('click', function() {
  if (detectChange() && confirm('Are you sure you want to reset?')) {
    form.reset();
  }
});
<form>
  <input type="number">
  <input type="number" value="11">
  <button type="button">Reset</button>
</form>

更新:

更新以涵盖:

  

具有非空默认值的输入

答案 1 :(得分:3)

接近目标的一种替代方法是使用一组:invalid:valid等标准pseudo-classes。另外请注意,我们将使用一些数组方法和功能,例如Array.some()Spread Syntax

var form = document.querySelector('form');

function detectChange()
{
    var invalids = form.querySelectorAll('input:invalid');
    var valids = form.querySelectorAll('input:valid');
    return (invalids.length > 0) || [...valids].some(i => i.defaultValue !== i.value);
}

form.querySelector('button').addEventListener('click', function()
{
    if (detectChange() && confirm('Are you sure you want to reset?'))
        form.reset();
});
<form>
  <input type="number">
  <input type="number">
  <input type="number" value="7">
  <button type="button">Reset</button>
</form>

如果您可以在placeholders上使用inputs,那么另一种可能的解决方案是使用 CSS伪类 :placeholder-shown。但是,请检查browser's support以确保它符合您的需求。请注意,这是实验,并且不推荐用于生产。然后,您可以使用下一个selector

input:not(:placeholder-shown)

获取未显示placeholder的所有输入,即所有非空输入,并重新实现代码,如下所示:

var form = document.querySelector('form');

function detectChange()
{
    var inputs = form.querySelectorAll(
        'input:not([value]):not(:placeholder-shown), input[value]'
    );
    return [...inputs].some(i => !i.defaultValue || i.defaultValue !== i.value);
}

form.querySelector('button').addEventListener('click', function()
{
    if (detectChange() && confirm('Are you sure you want to reset?'))
        form.reset();
});
<form>
  <input type="number" placeholder="Insert a number">
  <input type="number" placeholder="Insert a number">
  <input type="number" value="7" placeholder="Insert a number">
  <button type="button">Reset</button>
</form>

答案 2 :(得分:1)

更改此:

<button type="button">Reset</button>

TO

<input type="reset" value="Reset"/>

答案 3 :(得分:0)

在输入字段上循环并手动设置值=“”;

var form = document.querySelector('form');

function detectChange() {
  var inputs = form.querySelectorAll('input');
  for (var input of inputs) {
    input.value = "";
  }
}

form.querySelector('button').addEventListener('click', function() {
  if (confirm('Are you sure you want to reset?')) {
    detectChange(); 
  }
});
<form>
  <input type="number">
  <input type="number">
  <button type="button">Reset</button>
</form>

答案 4 :(得分:0)

只需为输入元素的onkeydownonpaste设置一个事件侦听器:

const inputs = document.querySelectorAll('input[type=number]')
inputs.forEach((el) => el.onkeydown = el.onpaste = (event) => event.target.dataset.receivedEntry = 1)

然后在 detectChange 中检查input.dataset.receivedEntry

function detectChange () {
  const inputs = form.querySelectorAll('input');
  for (var input of inputs) {
    if (input.dataset.receivedEntry) {
      return true;
    }
  }
}

答案 5 :(得分:0)

只需使用button type="reset",然后在form上附加一个事件侦听器即可监听reset事件。

代码的主要问题是detectChange()函数永远不会对无效输入起作用,因为如果您要求输入值,浏览器将始终为任何非数字输入返回空字符串。这是根据规范。选中https://stackoverflow.com/a/18853513/3744304

最初在@naga中提出了解决此问题的方法-elixir-jar的答案。编辑我的答案a)使其成为可行的答案,b)以简洁的ES6方式将其全部组合。

const form = document.querySelector('form');

form.addEventListener('reset', (event) => {
  if (detectChange() && !confirm('Are you sure you want to reset?')) {
    event.preventDefault();
  }
});

function detectChange() { 
  return [...form.querySelectorAll('input')].some(el => el.validity.badInput || el.value !== el.defaultValue); 
};
<form>
  <input type="number" value="87">
  <input type="number">
  <button type="reset">Reset</button>
</form>

答案 6 :(得分:-1)

var form = document.querySelector('form');
var btn = form.querySelector('button');
var inputs = form.querySelectorAll('input');
btn.disabled = true;
btn.addEventListener('click', function() {
  if (confirm('Are you sure you want to reset?')) {
    form.reset();
    btn.disabled = true;
  }
});

for (var input of inputs) {
  input.addEventListener('keypress', detectSpace)
  input.addEventListener('input', handleChange);
}

function handleChange(e) {
  var disabled = true;
  for (var input of inputs) {
    input.value = input.value.trim()
    if (input.value) {
      disabled = false
    }
  }
  btn.disabled = disabled
}

function detectSpace(e) {
  if (e.keyCode == 32) {
    e.preventDefault();
    return false
  }
}
<form>
  <input type="number">
  <input type="number">
  <button type="button">Reset</button>
</form>

这行得通吗?它通过修剪input type="number"中的值来防止用户粘贴到数字中。

detectSpace之所以存在,是因为在Firefox中,按空格键将删除该数字,因为该数字无效。

答案 7 :(得分:-1)

<form>
  <input type="number">
  <input type="number">
  <button type="button" onclick="resetData()">Reset</button>
</form>


function resetData(){
    var y = document.querySelectorAll('input,textarea');
        for (var i= 0; i < y.length; i++) {
        var id =y[i].id;
        if(y[i].value !=''&&y[i].value!= 'undefined'){
        document.getElementById(id).value="";
        }
        } 
}