使用jQuery获取表单输入字段?


412

我有一个包含许多输入字段的表单。

当我使用jQuery捕获Submit form事件时,是否可以在关联数组中获取该表单的所有输入字段?


23
这是一个好问题;实际上,我发现jQuery没有一个功能可以做到这一点真的很奇怪。有一些函数可以两种不同的格式获取表单数据,但不是最方便的一种脚本编写方法 ……(如果在表单元素上调用,也许.val()应该返回这样的数组?)
Luke Maurer

Answers:


524
$('#myForm').submit(function() {
    // get all the inputs into an array.
    var $inputs = $('#myForm :input');

    // not sure if you wanted this, but I thought I'd add it.
    // get an associative array of just the values.
    var values = {};
    $inputs.each(function() {
        values[this.name] = $(this).val();
    });

});

感谢Simon_Weaver的技巧,这是您可以使用的另一种方法serializeArray

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

请注意,此代码段将对<select multiple>元素失败。

看来新的HTML 5表单输入serializeArray在jQuery 1.3版中不起作用。适用于1.4+版本


1
在较新版本的jQuery中,Simon_Weaver的答案更强大,更容易。
MightyE 2010年

1
@MightyE和@Simon_Weaver-是的,这是一种更可靠的方法,但它并不能完全满足OP的要求。serializeArray返回具有属性name和的对象的数组value。更好的解决方案可能是将serializeArray的输出处理为所需的任何格式。
尼克

1
我认为serializeArray()完全可以满足您的要求,并且代码少得多。
slacy 2011年

1
对于第一种选择,<select>元素呢?我试过了,var $inputs = $('#new-ticket :input, :select');但是不行。有谁知道这样做的正确方法,因为我认为我做的不正确。
内森

2
@Nathan,您应该使用$("#new-ticket :input, #new-ticket :select"),甚至更好,$(":input, :select", "#new-ticket")
nickf

252

在这个问题上晚了聚会,但是这甚至更容易:

$('#myForm').submit(function() {
    // Get all the forms elements and their values in one step
    var values = $(this).serialize();

});

8
这确实是最好的答案。它甚至保留输入字段可能具有的任何数组格式。我不认为nickf的答案实际上可以使您的数据结构完整,例如,如果它是使用Zend_Form形成的,那么您将使用field [something]和field [something_else]作为输入的名称……至少从语义
上讲

43
根据jQuery API文档,.serialize()api.jquery.com/serialize)将表单的所有元素放在单个字符串中,准备添加到查询字符串中的URL,本质上是模仿GET表单请求。这将无法完成尼克的答案。
Christopher Parker'3

这是最好的答案!
丹尼尔·亨特

5
值得知道的:.serialize()仅适用于表单元素。因此$('form select').serialize()将序列化的数据仅用于选择。
抗毒剂2012年

3
不要重复$('#myForm')使用$(this)。
Jimothy 2014年


15

有时,我发现一次获得一个更有用。为此,这是:

var input_name = "firstname";
var input = $("#form_id :input[name='"+input_name+"']"); 

附加[0].value于此即$(...)[0].value;直接给了我输入值,谢谢!
保罗·科马·拉米雷斯

12
$('#myForm').bind('submit', function () {
  var elements = this.elements;
});

elements变量将包含表单中的所有输入,选择,文本区域和字段集。


9

这是另一种解决方案,通过这种方式,您可以获取有关表单的所有数据,并将其用于服务器端调用或其他操作中。

$('.form').on('submit', function( e )){ 
   var form = $( this ), // this will resolve to the form submitted
       action = form.attr( 'action' ),
         type = form.attr( 'method' ),
         data = {};

     // Make sure you use the 'name' field on the inputs you want to grab. 
   form.find( '[name]' ).each( function( i , v ){
      var input = $( this ), // resolves to current input element.
          name = input.attr( 'name' ),
          value = input.val();
      data[name] = value;
   });

  // Code which makes use of 'data'.

 e.preventDefault();
}

然后可以将其与ajax调用一起使用:

function sendRequest(action, type, data) {
       $.ajax({
            url: action,
           type: type,
           data: data
       })
       .done(function( returnedHtml ) {
           $( "#responseDiv" ).append( returnedHtml );
       })
       .fail(function() {
           $( "#responseDiv" ).append( "This failed" );
       });
}

希望这对你们任何人都有用:)


5

发生了类似的问题,但略有扭曲,我想我应该把它排除在外。我有一个获取表单的回调函数,所以我已经有一个表单对象,不能轻易更改$('form:input')。相反,我想出了:

    var dataValues = {};
    form.find('input').each(
        function(unusedIndex, child) {
            dataValues[child.name] = child.value;
        });

它的情况类似但不完全相同,但是我发现此线程非常有用,并以为我会在最后把它塞进去,并希望其他人觉得它有用。


4

关联的?不是没有一些工作,但是您可以使用通用选择器:

var items = new Array();

$('#form_id:input').each(function (el) {
    items[el.name] = el;
});

实际上,Lance的答案使POST值的关联数组保持不变,并占用了多达一行代码。
msumme 2010年

为什么项目是数组?您正在像使用普通对象一样使用它。这里不需要阵列
Jonathan MoralesVélez15年

3
@JonathanMoralesVélez2008年的Oli不再置评。2015同意你的观点。
奥利2015年

4

jQuery的serializeArray不包含禁用字段,因此,如果您也需要这些字段,请尝试:

var data = {};
$('form.my-form').find('input, textarea, select').each(function(i, field) {
    data[field.name] = field.value;
});


4

不要忘记复选框和单选按钮-

var inputs = $("#myForm :input");
var obj = $.map(inputs, function(n, i) {
  var o = {};
  if (n.type == "radio" || n.type == "checkbox")
    o[n.id] = $(n).attr("checked");
  else
    o[n.id] = $(n).val();
  return o;
});
return obj

3

此代码段将 代替名称,电子邮件输入您的表单字段名称

$(document).ready(function(){
  $("#form_id").submit(function(event){
    event.preventDefault();
    var name = $("input[name='name']",this).val();
    var email = $("input[name='email']",this).val();
  });
});

3

似乎很奇怪,没有人赞成或提出一种简洁的解决方案来获取列表数据。几乎没有任何形式将成为一维对象。

当然,此解决方案的缺点是必须在[0]索引处访问您的单例对象。但是,IMO比使用十二行制图解决方案之一更好。

var formData = $('#formId').serializeArray().reduce(function (obj, item) {
    if (obj[item.name] == null) {
        obj[item.name] = [];
    } 
    obj[item.name].push(item.value);
    return obj;
}, {});

2

我遇到了同样的问题,并以不同的方式解决了它。

var arr = new Array();
$(':input').each(function() {
 arr.push($(this).val());
});
arr;

它返回所有输入字段的值。您可以将更$(':input')改为更具体。


2

nickf提供的解决方案相同,但考虑到数组输入名称,例如

<input type="text" name="array[]" />

values = {};
$("#something :input").each(function() {
  if (this.name.search(/\[\]/) > 0) //search for [] in name
  {
    if (typeof values[this.name] != "undefined") {
      values[this.name] = values[this.name].concat([$(this).val()])
    } else {
      values[this.name] = [$(this).val()];
    }
  } else {
    values[this.name] = $(this).val();
  }
});

1

如果您需要从输入中获取多个值,并且使用[]来定义具有多个值的输入,则可以使用以下方法:

$('#contentform').find('input, textarea, select').each(function(x, field) {
    if (field.name) {
        if (field.name.indexOf('[]')>0) {
            if (!$.isArray(data[field.name])) {
               data[field.name]=new Array();
            }
            data[field.name].push(field.value);
        } else {
            data[field.name]=field.value;
        }
    }                   
});

1

Lance RushingSimon_Weaver的答案启发,这是我最喜欢的解决方案。

$('#myForm').submit( function( event ) {
    var values = $(this).serializeArray();
    // In my case, I need to fetch these data before custom actions
    event.preventDefault();
});

输出是对象数组,例如

[{name: "start-time", value: "11:01"}, {name: "end-time", value: "11:11"}]

使用下面的代码,

var inputs = {};
$.each(values, function(k, v){
    inputs[v.name]= v.value;
});

它的最终输出将是

{"start-time":"11:01", "end-time":"11:01"}

1

我在没有每个循环的情况下使用此代码:

$('.subscribe-form').submit(function(e){
    var arr=$(this).serializeArray();
    var values={};
    for(i in arr){values[arr[i]['name']]=arr[i]['value']}
    console.log(values);
    return false;
});

1

我希望这是最有用的,也是最简单的一种。

 $("#form").submit(function (e) { 
    e.preventDefault();
    input_values =  $(this).serializeArray();
  });

奇怪的是,这不适用于最新版本的jquery 3.4.1
relipse

0

当我需要使用所有表单字段进行ajax调用时,我会遇到:input选择器返回所有复选框(无论是否已选中)的问题。我添加了一个新的选择器来获取可提交的表单元素:

$.extend($.expr[':'],{
    submitable: function(a){
        if($(a).is(':checkbox:not(:checked)'))
        {
            return false;
        }
        else if($(a).is(':input'))
        {
            return true;
        }
        else
        {
            return false;
        }
    }
});

用法:

$('#form_id :submitable');

我还没有使用多个选择框对其进行测试,但是它可以以标准提交的方式获取所有表单字段。

在自定义OpenCart网站上的产品选项时,包括复选框和文本字段以及标准选择框类型时,我使用了此选项。


0

serialize()是最好的方法。@克里斯托弗·帕克(Christopher Parker)说,尼克(Nickf)的答案更胜一筹,但是并没有考虑到表格可能包含文本区域和选择菜单。最好使用serialize()然后根据需要进行操作。来自serialize()的数据可以在Ajax发布或get中使用,因此在那里没有问题。


0

希望这对某人有帮助。:)

// This html:
// <form id="someCoolForm">
// <input type="text" class="form-control" name="username" value="...." />
// 
// <input type="text" class="form-control" name="profile.first_name" value="...." />
// <input type="text" class="form-control" name="profile.last_name" value="...." />
// 
// <input type="text" class="form-control" name="emails[]" value="..." />
// <input type="text" class="form-control" name="emails[]" value=".." />
// <input type="text" class="form-control" name="emails[]" value="." />
// </form>
// 
// With this js:
// 
// var form1 = parseForm($('#someCoolForm'));
// console.log(form1);
// 
// Will output something like:
// {
// username: "test2"
// emails:
//   0: ".@....com"
//   1: "...@........com"
// profile: Object
//   first_name: "..."
//   last_name: "..."
// }
// 
// So, function below:

var parseForm = function (form) {

    var formdata = form.serializeArray();

    var data = {};

    _.each(formdata, function (element) {

        var value = _.values(element);

        // Parsing field arrays.
        if (value[0].indexOf('[]') > 0) {
            var key = value[0].replace('[]', '');

            if (!data[key])
                data[key] = [];

            data[value[0].replace('[]', '')].push(value[1]);
        } else

        // Parsing nested objects.
        if (value[0].indexOf('.') > 0) {

            var parent = value[0].substring(0, value[0].indexOf("."));
            var child = value[0].substring(value[0].lastIndexOf(".") + 1);

            if (!data[parent])
                data[parent] = {};

            data[parent][child] = value[1];
        } else {
            data[value[0]] = value[1];
        }
    });

    return data;
};

0

所有答案都是好的,但是在该函数中是否有您要忽略的字段?轻松,给字段一个属性,例如ignore_this:

<input type="text" name="some_name" ignore_this>

并在您的序列化功能中:

if(!$(name).prop('ignorar')){
   do_your_thing;
}

这就是您忽略某些字段的方式。


1
由于它不能回答原始问题,因此它更像是评论,而不是答案。
Wai Ha Lee

也许是因为他已经有了很多答案?这是对他收到的答案的补充。
Marcelo Rocha

如果必须填写输入,我将使用类似于强制性的类名称来实现此目的。然后我可以检查$('.mandatory');!$('.mandatory');
lharby

更改ignore_thisdata-ignore-this="true"而不是创建您自己的不验证w3c的属性
-zanderwar


0

对于多个选择元素(<select multiple="multiple">),我修改了@Jason Norwood-Young的解决方案以使其正常运行。

答案(如发布的那样)仅从选择的第一个元素中获取值,而不是所有元素。它也没有初始化或返回data,前者抛出JavaScript错误。

这是新版本:

function _get_values(form) {
  let data = {};
  $(form).find('input, textarea, select').each(function(x, field) {
    if (field.name) {
      if (field.name.indexOf('[]') > 0) {
        if (!$.isArray(data[field.name])) {
          data[field.name] = new Array();
        }
        for (let i = 0; i < field.selectedOptions.length; i++) {
          data[field.name].push(field.selectedOptions[i].value);
        }

      } else {
        data[field.name] = field.value;
      }
    }

  });
  return data
}

用法:

_get_values($('#form'))

注意:您只需要确保name所选内容[]的末尾已附加了该内容,例如:

<select name="favorite_colors[]" multiple="multiple">
  <option value="red">Red</option>
  <option value="green">Green</option>
  <option value="blue">Blue</option>
</select>

-1
$("#form-id").submit(function (e) { 
  e.preventDefault();
  inputs={};
  input_serialized =  $(this).serializeArray();
  input_serialized.forEach(field => {
    inputs[field.name] = field.value;
  })
  console.log(inputs)
});
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.