【问题标题】:Using jQuery to store the state of a complicated form使用jQuery存储复杂表单的状态
【发布时间】:2011-03-26 20:18:59
【问题描述】:

我有一个相当复杂的表格,里面有很多由用户填写的“步骤”。一些步骤(将它们视为表单段)具有默认选项,但在单击“输入自定义值”时,它们会显示一组隐藏的字段,用户可以在其中输入信息。这是一个示例

<div id="#s1_normal">
<input type="radio" name="mode" value="a"> Mode A
<input type="radio" name="mode" value="b"> Mode B
Choose one of the above for applying average coefficient 
values of "a" or "b" to 100% of your product or
<a href="#" onclick="toggleCustom('s1');">enter custom values</a>
</div>

<div id="#s1_custom">
%a: <input type="text" name="perc_a"> coeff. a <input type="text" name="coeff_a">
%b: <input type="text" name="perc_b"> coeff. b <input type="text" name="coeff_b">
Enter custom values above or 
<a href="#" onclick="toggleCustom('s1');">choose average values</a>

有几个这样的段,例如,#s1 .. #s7。这是我的任务。我想让用户保存表单的状态。因此,一旦用户填写了整个表单,为某些部分选择了平均默认值,并为其他部分输入了自定义值,用户就可以单击一个按钮并保存整个状态以供以后解冻。我在想,如果我可以将状态保存在可以序列化的对象中,我可以将其保存在 db 表或其他一些持久存储中。

用户可以稍后返回并重新构建整个之前的会话。

我该怎么做?有 getAttributes 插件http://plugins.jquery.com/project/getAttributes,还有 jQuery 序列化方法,但我一辈子都无法开始。请把我推向正确的方向。

【问题讨论】:

    标签: jquery forms session-state


    【解决方案1】:

    这里有几个函数可以帮助完成这个过程。 formToString 将表单序列化为字符串,stringToForm 则相反:

    function formToString(filledForm) {
        formObject = new Object
        filledForm.find("input, select, textarea").each(function() {
            if (this.id) {
                elem = $(this);
                if (elem.attr("type") == 'checkbox' || elem.attr("type") == 'radio') {
                    formObject[this.id] = elem.attr("checked");
                } else {
                    formObject[this.id] = elem.val();
                }
            }
        });
        formString = JSON.stringify(formObject);
        return formString;
    }
    function stringToForm(formString, unfilledForm) {
        formObject = JSON.parse(formString);
        unfilledForm.find("input, select, textarea").each(function() {
            if (this.id) {
                id = this.id;
                elem = $(this); 
                if (elem.attr("type") == "checkbox" || elem.attr("type") == "radio" ) {
                    elem.attr("checked", formObject[id]);
                } else {
                    elem.val(formObject[id]);
                }
            }
        });
    }
    

    用法:

    // Convert form to string
    var formString = formToString($("#myForm"));
    // Save string somewhere, e.g. localStorage
    // ...
    
    // Restore form from string
    stringToForm(formString, $("#myForm"));
    

    【讨论】:

    • 这太有用了!只是给不知道怎么调用函数的人注意一下,我是这样使用的:sessionStorage.setItem("formdata",formToString(jQuery("#form")));,然后调用它:var storedform = sessionStorage.getItem("formdata"); stringToForm(storedform,jQuery("#form"));
    • $j(this) 表达式是错字吗?我在使用这个脚本时遇到 JavaScript 错误,并假设它应该是 $(this),对吧?
    • 这不是一个错字,但我从答案中删除了它,因为只有 $ 是访问 jquery 的默认方式。请参阅learn.jquery.com/using-jquery-core/… 了解更多信息
    • 你忘了textarea
    • 应该使用 formObject[this.id] = elem.prop("checked");让它工作。 (jQuery 2.2.0)
    【解决方案2】:

    我会先使用dumbFormState jQuery plugin

    该插件实际上会在您键入时自动保存内容等。所以当它们回来时,它已经再次填写,您不需要服务器端来做。

    在那之后,我将创建更多的 jQuery 以在dumbFormState 插件之后加载,然后显示/隐藏已填写的区域。如果您在有人填写表单之前调用它也没问题,因为它将是空白的,并且您的逻辑不应该显示/隐藏空白的东西。

    【讨论】:

      【解决方案3】:

      我猜你正在寻找.serialize(),它序列化了form data。为此,您的 input 元素必须在 form tag 内,并且它们都必须具有 name 属性。

      var form1data = $('#form1').serialize();
      
      alert(form1data);
      

      【讨论】:

      • 感谢您的建议。正如我在问题中指出的那样,我知道 serialize 方法,但是,对我来说,这似乎只是解决方案的一部分。要恢复表单,我必须读取存储的序列化数据,然后将表单重建回状态,包括其所有自定义条目。也就是说,如果隐藏段未被隐藏以输入自定义值,我想带上它背部。我该怎么做呢?
      • @punkish:我不知道 jQuery 核心中有一些 deserialize() 方法。因此,您要么必须编写自己的自定义解析器,要么寻找插件。
      • @punkish 这是我的formstate plugin - serialize() 的替代方法和缺失的 unserialize() 可用于对象而不是字符串;我想要一个只处理表单状态的轻量级插件,而不是字符串表示或存储方法。它以合理的方式处理收音机、复选框等。
      【解决方案4】:

      您可能只想将非默认数据放入 json 中,然后通过 post 请求将其发送到服务器以进行保存。

      因此,一旦该人返回该页面,您会自动查看他们是否保存了某些内容,您可以询问他们是否要使用它或从保存的数据中填充表单。

      保存默认值是对带宽的浪费,因为无论如何您都不会改变它加载时的形式。

      更新:

      要将其保存为 JSON,我认为将其构建成一个长字符串就很容易了,因为格式很简单,因此您只需将所有内容作为单个字符串发送。

      您可能还想保存他们所在的阶段,或者在他们进入每个阶段时自动保存,这可能是一个更好的选择,以防他们的计算机崩溃,他们不必从头开始重新开始,但您可能希望通过复选框启用它,以打开自动保存。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 2012-02-19
        • 2020-07-06
        • 1970-01-01
        • 1970-01-01
        • 2017-04-29
        • 1970-01-01
        • 2010-09-17
        相关资源
        最近更新 更多