javascript 设置所有类型的输入值,并给出它们的名称属性-值对

qjp7pelc  于 2023-05-05  发布在  Java
关注(0)|答案(2)|浏览(89)

假设表单中有一个未知的输入类型列表,所以它可能是许多类型的混合(radio,select,texts等),当页面刷新时,我从后端获得一个表示输入名称及其值的键值对象,是否可以在不知道类型的情况下轻松设置它们的值,或者在某些情况下,仅仅知道输入名称和值是不够的?
例如,形式:

<form id="myform">
    <input type="text" name="text1" />
    <input type="radio" name="radio1" />
    <input type="radio" name="radio2" />
    <select name="select1">
       <option value="1">1</option>
       <option value="2">2</option>
       <option value="3">3</option>
    </select> 
</form>

然后是来自后端的数据对象:

{
    "text1": "foo",
    "radio1": "bar",
    "radio2": "hello",
    "select1": "world"    
}

那这是我做的剧本

function setInputs(inputs) {
    let inputElement;
    for (const [key, value] of Object.entries(inputs)) {        
        inputElement = document.querySelector(`#myform [name='${key}']`);
        inputElement.value = value;
    }
}

但是它会设置所有可能设置的输入吗?当然,有些输入是不可能的,比如type="file",但是我的setInputs()函数会设置什么是可能的吗?或者我需要涵盖更多的用例,而我所做的还不够?

vktxenjb

vktxenjb1#

复选框字段

复选框有两种状态,我们应该关注:truefalse。如果服务器收到一个复选框[name]: value,则意味着它是true。使用.checked属性将复选框设置为选中状态(参见示例A)。

示例A

const data = {
  chx: "TEST"
};
const checkbox = document.forms[0].elements["chx"];
checkbox.checked = true;
<form>
  <input name="chx" type="checkbox" value="TEST">
</form>

单选按钮组

单选按钮的典型布局是一组两个或多个--每个都有一个特定的值。单选按钮组具有特定行为,其中用户只能选中所述组的一个单选按钮。为了确保这种行为,组中的每个单选按钮共享相同的[name](参见示例B)。
如果只有一个值要选中或取消选中,请使用复选框。
除了复选框之外,直接赋值给.value属性也可以。

示例B

/**
 * Set a given form's values derived from a given object 
 * by matching object key to a field's name attribute.
 * @param {Object} data - An object literal.
 * @param {number|string} form - A reference to a form by
 *        an index number or the form's #id or [name].
 *        @default is index number 0.
 */
function setVal(data, form = 0) {
  // Reference the <form>
  const main = document.forms[form];
  // Reference all form fields
  const fields = main.elements;
  // Get an array of all field [name]s
  const names = Array.from(fields).map(f => f.name);
  // Convert {Object} data into an array of key/value pairs
  const keyVal = Object.entries(data);
  
  // For each key/value pairs...
  keyVal.forEach(([key, val]) => {
    //... if the names array matches key...
    if (names.includes(key)) {
      //... and if the field is a checkbox...
      if (fields[key].type === "checkbox") {
        //... check the checkbox...
        fields[key].checked = true;
        //... otherwise...
      } else {
        //... assign the value of field to the value object
        fields[key].value = val;
      }
    }
  });
}

const data = {
  txt: "test",
  num: 7,
  area: `  test
  multiline
  data`,
  sel: "4",
  chx: "X",
  rad: "B"
};

setVal(data);
<form id="test">
  <fieldset>
    <legend>Direct Values</legend>
    <input name="txt" type="text"><br>
    <input name="num" type="number"><br>
    <textarea name="area" rows="3"></textarea><br>
    <select name="sel">
      <option value="1">I</option>
      <option value="2">II</option>
      <option value="3">III</option>
      <option value="4">IV</option>
    </select>
  </fieldset>
  <fieldset>
    <legend>Checked Values</legend>
    <input name="chx" type="checkbox" value="X"> X<br>
    <input name="rad" type="radio" value="A"> A
    <input name="rad" type="radio" value="B"> B
    <input name="rad" type="radio" value="C"> C
    <input name="rad" type="radio" value="D"> D
  </fieldset>
</form>
lxkprmvk

lxkprmvk2#

这对于某些输入类型是可以的,但不是所有输入类型。而不是在这行代码中分配value

inputElement.value = value;

我会调用一个函数来执行适当的操作:

function setInputs(inputs) {
    let inputElement;
    for (const [key, value] of Object.entries(inputs)) {        
        inputElement = document.querySelector(`#myform [name='${key}']`);
        assingInputValue(inputElement, value);
    }
}

function assingInputValue(inputElement, value) {
  switch (inputElement.type) {
    case 'text':
    case 'textarea':
    case 'number':
    case 'search':
      inputElement.value = value;
    break;
    case 'radio':
    case 'checkbox':
      // probably better to separate this to another function
      if (value === 'true' || value === true) {
         inputElement.setAttribute('checked', '');
      } else {
         inputElement.removeAttribute('checked');
      }
    break;
    case 'password':
      // WARNING: It is not safe to transfer passwords back to user in plain text.
    break;
    // others...
  }
}

相关问题