jQuery - serializeArray()没有获取checked复选框的值

时间:2014-06-21 04:07:42

标签: javascript jquery html checkbox

我在一个表格中有一个复选框,作为一个标志。

为了做到这一点,我添加了一个隐藏的输入元素,这样如果未选中复选框,仍会保存某些内容

<form action="">
    ...
        <input type="hidden" name="foo" value="no" />
        <input type="checkbox" name="foo" value="yes">
    ...
</form>

我遇到的问题是,当我

  1. 选中复选框
  2. 然后在表单
  3. 上运行jQuery.serializeArray()

    为foo元素设置的值为“no”

    Object { name="foo", value="no"}
    

    不应该serializeArray()模拟浏览器行为吗?如果是这样,如果选中复选框,它是否应该返回“是”?

    我正在使用jQuery v1.10.2

6 个答案:

答案 0 :(得分:3)

简而言之:不可以。在检查 的情况下,serializeArray方法仅返回复选框。因此,只要它未被检查,它就会忽略它。 但是,如果您检查了它,它将直接返回您输入的值。

http://api.jquery.com/serializearray/查看演示。

答案 1 :(得分:3)

在具有多个同名输入的表单上使用serializeArray会为每个元素返回多个对象(如果选中)。这意味着以下HTML将返回以下对象。所以有问题的数据就在那里并且可用。因此,我假设您正在尝试将数据操作为1个对象,或者您将其发布到服务器,该服务器仅考虑来自第一个值的数据那把钥匙。您只需要确保任何checkbox元素优先。

返回对象:

[
    {
        name:"foo",
        value:"no"
    },
    {
        name:"foo2",
        value:"no"
    },
    {
        name:"foo2",
        value:"yes"
    }
] 

HTML:

<form>
    <input type="hidden" name="foo" value="no" />
    <input type="checkbox" name="foo" value="yes" />

    <input type="hidden" name="foo2" value="no" />
    <input type="checkbox" name="foo2" value="yes" checked />
</form>

JS:

console.log($('form').serializeArray());

DEMO

您可以执行此操作的另一种方法是删除隐藏字段,在提交表单之前,请检查每个未选中的复选框,并检查serializeArray中是否有任何具有相同名称的数据。如果不只是将其作为off添加到其中。

$('#submit').on('click', function(){
    var arr = $('form').serializeArray(),
        names = (function(){
            var n = [],
                l = arr.length - 1;
            for(; l>=0; l--){
                n.push(arr[l].name);
            }

            return n;
        })();

    $('input[type="checkbox"]:not(:checked)').each(function(){
        if($.inArray(this.name, names) === -1){
            arr.push({name: this.name, value: 'off'});
        }
    });

    console.log(arr);
});

DEMO

答案 2 :(得分:0)

对多个字段使用相同的名称充其量是有问题的,并且前端系统或后端系统没有标准化的方式来处理它。

使用相同名称的唯一原因是,如果您尝试传递某种默认值,就像下面的情况一样,您在做一个简单的是/否。

要模拟浏览器,您需要的是serialize方法,而不是serializeArray

我将表单添加到页面 - 从我的控制台:

JSON.stringify(f.serializeArray());
"[{"name":"foo","value":"no"}]"

没有选中标记

JSON.stringify(f.serialize());
""foo=no""

<强>对勾

JSON.stringify(f.serialize());
""foo=yes&foo=no""

如果您的后端系统感到困惑并且输入错误的值,请反转您的复选标记和隐藏元素的顺序。

答案 3 :(得分:0)

事实:jQuery serializeArray()不包含未选中的复选框,可能我们 DO 需要将其发送到服务器(尽管对于收音机来说没有问题)。

解决方案:创建一个新的序列化

//1. `sel` any collection of `form` and/or `input`, `select`, `textarea` 
//2. we assign value `1` if not exists to radios and checkboxes
// so that the server will receive `1` instead of `on` when checked
//3. we assign empty value to unchecked checkboxes 
function serialize(sel) {
   var arr,
       tmp,
       i,
       $nodes = $(sel);

   // 1. collect form controls
   $nodes = $nodes.map(function(ndx){
      var $n = $(this);

      if($n.is('form'))
         return $n.find('input, select, textarea').get();
      return this;
    });

   // 2. replace empty values of <input>s of type=["checkbox"|"radio"] with 1 
   // or, we end up with "on" when checked
   $nodes.each(function(ndx, el){
      if ((el.nodeName.toUpperCase() == 'INPUT') && ((el.type.toUpperCase() == 'CHECKBOX') || (el.type.toUpperCase() == 'RADIO'))){
         if((el.value === undefined) || (el.value == ''))
            el.value = 1;
      }
   });

   // 3. produce array of objects: {name: "field attribute name", value: "actual field value"}
   arr = $nodes.serializeArray();
   tmp = [];
   for(i = 0; i < arr.length; i++)
      tmp.push(arr[i].name);

   // 4. include unchecked checkboxes
    $nodes.filter('input[type="checkbox"]:not(:checked)').each(function(){
      if(tmp.indexOf(this.name) < 0){
         arr.push({name: this.name, value: ''});
      }
    });

   return arr;
}

我们将空字符串分配给未选中的复选框的原因是,选中的复选框会将其值提交到在html中设置的服务器,并且可以为零!

因此,空值表示未选中复选框。

答案 4 :(得分:0)

<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.0.3/jquery.min.js"></script>

<form url="http://application.localdev/api/v1/register" method="post" id="formReg" accept-charset="utf-8">
    <input type="email" placeholder="email" name="email"><br>
    <input type="text" placeholder="firstname" name="firstname"><br>
    <input type="text" placeholder="lastname" name="lastname"><br>
    <input type="number" placeholder="zip_code" name="zip_code"><br>
    <input type="checkbox" name="general" value="true"> general<br>
    <input type="checkbox" name="marketing" value="true"> marketing<br>
    <input type="checkbox" name="survey" value="true"> survey<br>
    <button type="submit">save</button>
</form>

<script>
    $(document).ready(function() {
        $('#formReg').on('submit', function(e){
            // validation code here
                        
            e.preventDefault();


                            
            var values = {};
            $.each($('#formReg').serializeArray(), function(i, field) {
                values[field.name] = field.value;
            });

            $('input[type="checkbox"]:not(:checked)').each(function(){
                if($.inArray(this.name, values) === -1){
                    values[this.name] = $(this).prop('checked')
                }
            });

            console.log(values)
        });
    });
</script>

答案 5 :(得分:0)

serializeArray 不会返回未选中的复选框。我试试这个而不是 serializeArray:

$('input, select, textarea').each(
   function(index){  
       var input = $(this);
       alert('Type: ' + input.attr('type') + 'Name: ' + input.attr('name') + 
       'Value: ' + input.val());
   }
);