将表单序列化为javascript对象的特例

时间:2010-12-03 08:13:54

标签: javascript jquery serialization

基于this question$.fn.serializeObject()函数构建,我希望能够在我的表单名称中支持“点符号”,如下所示:

<form>
    <input name="Property.Items[0].Text" value="item 1" />
    <input name="Property.Items[0].Value" value="1" />
    <input name="Property.Items[1].Text" value="item 2" />
    <input name="Property.Items[1].Value" value="2" />
</form>

鉴于$('form').serializeArray()产生以下内容:

[{"name":"Property.Items[0].Text","value":"item 1"},
 {"name":"Property.Items[0].Value","value":"1"},
 {"name":"Property.Items[1].Text","value":"item 2"},
 {"name":"Property.Items[1].Value","value":"2"}]

我怎样才能在下面达到预期的结果:

{Property: {Items: [{Text: 'item 1', Value: '1'},
                    {Text: 'item 2', Value: '2'}]} }

任何帮助将不胜感激。

编辑: 具体而言,所需的代码将被添加到serializeObject扩展名中,这样除了它现在的工作方式之外,它还将支持上述约定。这是现有的方便方法。

$.fn.serializeObject = function() {
    var o = {};
    var a = this.serializeArray();
    $.each(a, function() {
        if (o[this.name]) {
            if (!o[this.name].push) {
                o[this.name] = [o[this.name]];
            }
            o[this.name].push(this.value || '');
        } else {
            o[this.name] = this.value || '';
        }
    });
    return o;
};

编辑2: 提供答案,这是我目前的实施:

$.fn.serializeObject = function() {
  var o = {};
  var a = this.serializeArray();
  var regArray = /^([^\[\]]+)\[(\d+)\]$/;

  $.each(a, function(i) {
      var name = this.name;
      var value = this.value;

      // let's also allow for "dot notation" in the input names
      var props = name.split('.');
      var position = o;
      while (props.length) {
          var key = props.shift();
          var matches;
          if (matches = regArray.exec(key)) {
              var p = matches[1];
              var n = matches[2];
              if (!position[p]) position[p] = [];
              if (!position[p][n]) position[p][n] = {};
              position = position[p][n];
          } else {
              if (!props.length) {
                  if (!position[key]) position[key] = value || '';
                  else if (position[key]) {
                      if (!position[key].push) position[key] = [position[key]];
                      position[key].push(value || '');
                  }
              } else {
                  if (!position[key]) position[key] = {};
                  position = position[key];
              }
          }
      }
  });
  return o;
};

您可以在行动here

中看到它

1 个答案:

答案 0 :(得分:4)

这个解决方案有点静态。但它应该做的伎俩:

var serialized = $.fn.serializeObject(),
            properties = {},
            property = [],
            position = {},
            key = '',
            n = 0,
            matchName = '',
            i = 0;

        for (i = 0; i < serialized.length; i += 1) {
            property = serialized[i].name.split('.');
            position = properties;
            while (property.length) {
                key = property.shift();
                if (key.match(/\[\d+\]/) && key.match(/\[\d+\]/).join().match(/\d+/g) ) {
                    matchName = key.match(/\w+/)[0]
                    n = parseInt(key.match(/\[\d+\]/).join().match(/\d+/g), 10);
                    if (!position[matchName]) {
                        position[matchName] = [];
                    }

                    if (!position[matchName][n]) {
                        position[matchName][n] = {}
                    }

                    position = position[matchName][n]
                } else {
                    if (!property.length) {
                        position[key] = serialized[i].value
                    } else {
                        if (!position[key]) {
                            position[key] = {};
                        }
                        position = position[key]
                    }
                }

            }
        }

        console.log(properties);