如何将表单的所有元素转换为JavaScript对象?
我希望有某种方法从表单自动构建JavaScript对象,而不必遍历每个元素。我不希望使用$('#formid').serialize();返回的字符串;,我也不希望$('#formid').serializeArray()返回映射;
如何将表单的所有元素转换为JavaScript对象?
我希望有某种方法从表单自动构建JavaScript对象,而不必遍历每个元素。我不希望使用$('#formid').serialize();返回的字符串;,我也不希望$('#formid').serializeArray()返回映射;
当前回答
使用maček的解决方案,我对其进行了修改,使其与ASP.NET MVC在同一表单上处理嵌套/复杂对象的方式一致。您所要做的就是将验证部分修改为:
"validate": /^[a-zA-Z][a-zA-Z0-9_]*((?:\[(?:\d*|[a-zA-Z0-9_]+)\])*(?:\.)[a-zA-Z][a-zA-Z0-9_]*)*$/,
这将匹配并正确映射具有以下名称的元素:
<input type="text" name="zooName" />
And
<input type="text" name="zooAnimals[0].name" />
其他回答
将任何东西变成对象(未经单元测试)
<script type="text/javascript">
string = {};
string.repeat = function(string, count)
{
return new Array(count+1).join(string);
}
string.count = function(string)
{
var count = 0;
for (var i=1; i<arguments.length; i++)
{
var results = string.match(new RegExp(arguments[i], 'g'));
count += results ? results.length : 0;
}
return count;
}
array = {};
array.merge = function(arr1, arr2)
{
for (var i in arr2)
{
if (arr1[i] && typeof arr1[i] == 'object' && typeof arr2[i] == 'object')
arr1[i] = array.merge(arr1[i], arr2[i]);
else
arr1[i] = arr2[i]
}
return arr1;
}
array.print = function(obj)
{
var arr = [];
$.each(obj, function(key, val) {
var next = key + ": ";
next += $.isPlainObject(val) ? array.print(val) : val;
arr.push( next );
});
return "{ " + arr.join(", ") + " }";
}
node = {};
node.objectify = function(node, params)
{
if (!params)
params = {};
if (!params.selector)
params.selector = "*";
if (!params.key)
params.key = "name";
if (!params.value)
params.value = "value";
var o = {};
var indexes = {};
$(node).find(params.selector+"["+params.key+"]").each(function()
{
var name = $(this).attr(params.key),
value = $(this).attr(params.value);
var obj = $.parseJSON("{"+name.replace(/([^\[]*)/, function()
{
return '"'+arguments[1]+'"';
}).replace(/\[(.*?)\]/gi, function()
{
if (arguments[1].length == 0)
{
var index = arguments[3].substring(0, arguments[2]);
indexes[index] = indexes[index] !== undefined ? indexes[index]+1 : 0;
return ':{"'+indexes[index]+'"';
}
else
return ':{"'+escape(arguments[1])+'"';
})+':"'+value.replace(/[\\"]/gi, function()
{
return "\\"+arguments[0];
})+'"'+string.repeat('}', string.count(name, ']'))+"}");
o = array.merge(o, obj);
});
return o;
}
</script>
测试输出:
$(document).ready(function()
{
console.log(array.print(node.objectify($("form"), {})));
console.log(array.print(node.objectify($("form"), {selector: "select"})));
});
on
<form>
<input name='input[a]' type='text' value='text'/>
<select name='input[b]'>
<option>select</option>
</select>
<input name='otherinput[c][a]' value='a'/>
<input name='otherinput[c][]' value='b'/>
<input name='otherinput[d][b]' value='c'/>
<input name='otherinput[c][]' value='d'/>
<input type='hidden' name='anotherinput' value='hidden'/>
<input type='hidden' name='anotherinput' value='1'/>
<input type='submit' value='submit'/>
</form>
将产生:
{ input: { a: text, b: select }, otherinput: { c: { a: a, 0: b, 1: d }, d: { b: c } }, anotherinput: 1 }
{ input: { b: select } }
这和你想要的完全一样
仅执行以下代码一次
$.fn.serializeObject = function(){
let d={};
$(this).serializeArray().forEach(r=>d[r.name]=r.value);
return d;
}
现在您可以多次执行以下行
let formObj = $('#myForm').serializeObject();
// will return like {id:"1", username:"abc"}
这里最简单。我用一个简单的字符串替换了一个正则表达式,到目前为止,它们就像一个符咒。我不是正则表达式专家,但我打赌您甚至可以填充非常复杂的对象。
var values = $(this).serialize(),
attributes = {};
values.replace(/([^&]+)=([^&]*)/g, function (match, name, value) {
attributes[name] = value;
});
这会把一切都考虑在内
函数formToObject(表单){let data=新FormData(表单);let queryString=新URLSearchParams(data).toString();var obj={};var params=queryString.split(“&”);对于(var i=0;i<params.length;i++){var param=params[i].split(“=”);var key=param[0].replace(“[]”,“”);var key=密钥.替换(“%5B%5 D”,“”);var值=参数[1];if(obj[key]==未定义){obj[key]=值;}else if(数组的obj[key]实例){obj[key].push(值);}其他{obj[key]=[obj[key],值];}}控制台日志(obj)返回obj;}<!DOCTYPE html><html><head><title>表单示例</title></head><body style=“height:800px;溢出:滚动”><form id=“test”onchange=“formToObject(this)”><div><h3>水果</h3><input type=“checkbox”name=“fruit”value=“apple”id=“apple“><label for=“apple”>Apfel</label><input-type=“checkbox”name=“fruit”value=“banana”id=“banana“><label for=“banana”>Banane</label><input type=“checkbox”name=“fruit”value=“cherry”id=“cherr”><label for=“cherry”>Kirsche</label><input type=“checkbox”name=“fruit”value=“葡萄”id=“葡萄”><label for=“葡萄”>Traube</label><input type=“checkbox”name=“fruit”value=“pear”id=“pear“><label for=“pear”>Birne</label></div><div><h3>多个选项</h3><select multiple name=“manyOptions[]”><option value=“选项1”>选项1</option><option value=“option 2”>选项2</option><option value=“选项3”>选项3</option></选择></div><div><h3>检查选项</h3><input type=“radio”name=“onceOption”value=“Option 1”>选项1<br><input type=“radio”name=“onceOption”value=“Option 2”>选项2<br><input type=“radio”name=“onceOption”value=“Option 3”>选项3<br></div></form></body></html>
这里有一种非jQuery方法:
var getFormData = function(form) {
//Ignore the submit button
var elements = Array.prototype.filter.call(form.elements, function(element) {
var type = element.getAttribute('type');
return !type || type.toLowerCase() !== 'submit';
});
您可以这样使用:
function() {
var getFormData = function(form) {
//Ignore the submit button
var elements = Array.prototype.filter.call(form.elements, function(element) {
var type = element.getAttribute('type');
return !type || type.toLowerCase() !== 'submit';
});
//Make an object out of the form data: {name: value}
var data = elements.reduce(function(data, element) {
data[element.name] = element.value;
return data;
}, {});
return data;
};
var post = function(action, data, callback) {
var request = new XMLHttpRequest();
request.onload = callback;
request.open('post', action);
request.setRequestHeader("Content-Type", "application/json;charset=UTF-8");
request.send(JSON.stringify(data), true);
request.send();
};
var submit = function(e) {
e.preventDefault();
var form = e.target;
var action = form.action;
var data = getFormData(form);
//change the third argument in order to do something
//more intersting with the response than just print it
post(action, data, console.log.bind(console));
}
//change formName below
document.formName.onsubmit = submit;
})();