如何在没有jQuery的情况下序列化表单?

15

出于多种原因(首要原因为学习JavaScript),我需要在没有jQuery的情况下将表单序列化,并使用ajax将生成的序列化数据结构发送到php页面。 序列化的数据必须是JSON格式。

我该如何做呢?

--编辑--

这是我的表单样式:http://jsfiddle.net/XGD4X/


如果您不反对使用json2.js,您可以使用它,或者另外获取并学习它的序列化方式,并从该源代码中学习。 - Mark Schultheiss
你是否不愿意使用任何库? - Dave Hogan
3
更好的学习方式是查看jQuery源代码。http://james.padolsey.com/jquery/#v=git&fn=serialize - codef0rmer
1
@F.Calderan 这是我的代码:http://jsfiddle.net/XGD4X/ - Andrea Rastelli
在这种情况下,你不能只获取存在于表单标签中的所有元素,并将它们放入一个数组中,然后将其转换为 JSON 吗?这是你尝试做的吗? - codef0rmer
显示剩余6条评论
2个回答

2

我正在解决类似的问题,我认为在使用框架之前学习如何编程是值得的。我使用一个数据对象(BP.reading)来保存信息,例如血压读数。然后使用JSON.stringify(dataObj)即可完成工作。

这里是“保存”按钮单击的处理程序,它是数据对象上的一个方法。请注意,我使用表单而不是表格来输入数据,但是相同的思路应该适用。

update: function () {
            var arr = document.getElementById("BP_input_form").firstChild.elements,
                request = JDK.makeAjaxPost();  // simple cross-browser httpxmlrequest with post headings preset

            // gather the data and store in this data obj
            this.name = arr[0].value.trim();
            ...
            this.systolic = arr[3].value;
            this.diastolic = arr[4].value;

            // still testing so just put server message on page
            request.callback = function (text) {
                msgDiv.innerHTML += 'server said ' + text;
            };
            // 
            request.call("BP_update_server.php", JSON.stringify(this));
        }

我在我的程序中使用对象来发送、接收、显示和输入相同类型的数据,因此我已经准备好了对象。如果您想要更快速的解决方案,可以使用一个空对象并向其中添加数据。如果数据是一组相同类型的数据,则只需使用数组即可。然而,使用对象在服务器端具有有用的名称。以下是一个更通用的版本,尽管未经测试,但已通过jslint。

function postUsingJSON() {
    // collect elements that hold data on the page, here I have an array
    var elms = document.getElementById('parent_id').elements,
        // create a post request object
        // JDK is a namespace I use for helper function I intend to use in other
        //  programs or that i use over and over
        // makeAjaxPost returns a request object with post header prefilled
        req = JDK.makeAjaxPost(),
        // create object to hold the data, or use one you have already
        dataObj = {},   // empty object or use array dataArray = []
        n = elms.length - 1;     // last field in form

    // next add the data to the object, trim whitespace
    // use meaningful names here to make it easy on the server side
    dataObj.dataFromField0 = elms[0].value.trim();  // dataArray[0] =
    //        ....
    dataObj.dataFromFieldn = elms[n].value;

    // define a callback method on post to use the server response
    req.callback = function (text) {
        // ...
    };

    // JDK.makeAjaxPost.call(ULR, data)
    req.call('handle_post_on_server.php', JSON.stringify(dataObj));
}

祝你好运。


据我所知,JSON主要是对象字面量JavaScript语法,stringify方法只是剥离对象的方法(出于安全考虑),只留下数据。对于一个简单的程序,您可以声明一个空对象,将数据添加到其中,进行字符串化并发布。如果对您的数据有意义,可以使用Array,或者只使用对象。早餐后,我会调整我的帖子,展示更通用的解决方案。您是否也有兴趣看到我的makeAjaxPost()函数? - Jeff
关于你的makeAjaxPost函数...嗯...我一直很感兴趣。 现在我正在使用你的建议进行一些测试。谢谢你的时间:D。 - Andrea Rastelli
花费时间是值得的,因为它澄清了我的思路。最好从这里开始看看你能做到什么程度。明天我会添加我的JDK模块的一部分,之后我会整理文档。 - Jeff
我再次查看了你的代码,有一些问题。请将表中的每一行视为一个数据对象,例如{name:'widget',numA:'15',numB:'87'},您会将此对象称为产品吗?还是有更好的名称?这些数字字段之间有什么区别?接下来,请考虑这些对象的列表,例如{list:anArrayofProducts [ ... ]},您会如何命名此列表?您是否考虑过为每个对象使用单独的标记,创建“产品”的表单,将其添加到“列表”中,并使用表格显示“列表”? - Jeff
嗯,这是我的领域功能:第一个字段是产品名称;第二个字段是产品数量的滑块(仅适用于Chrome);第三个字段是产品精确数量的数字字段(我知道,它看起来像是重复输入,但在我的理解中,第二个数字输入是为了细化而第一个是为了大步增量)。我的对象数组(基于您的示例)是表格中每一行的容器。 - Andrea Rastelli
显示剩余3条评论

1
CoffeeScript实现返回GET查询字符串:
serialize = (form) ->
  enabled = [].filter.call form.elements, (node) -> not node.disabled
  pairs = [].map.call enabled, (node) ->
    encoded = [node.name, node.value].map(encodeURIComponent)
    encoded.join '='
  pairs.join '&'

或者,如果您更喜欢键值对映射:

serialize = (form) ->
  data = {}
  for node in form.elements when not node.disabled and node.name
    data[node.name] = node.value
  data

我没有查看jQuery的实现,因此无法保证100%的兼容性。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接