【问题标题】:How can I clone a fieldset without keeping the rules of the fields?如何在不保留字段规则的情况下克隆字段集?
【发布时间】:2014-12-12 17:53:04
【问题描述】:

我克隆了我的字段集,它运行良好。我完美地清除了所有字段值。我遇到的唯一问题是,如果在添加新字段集之前提交已被点击,并且如果您没有点击提交,则不遵循规则。我真正想要的是能够删除所有规则并重新设置它,或者以它们正常工作的方式保持规则。我试图删除规则,但它不起作用()。我尝试添加新规则,它可以工作,但每次添加部分时,每个字段都会多出 1 条规则。请注意,每次添加新字段集时,我的 ID 和名称都会更改。

这是我的 html @Sparky:

            <!------  Fiedlset company information starts here     ------>


                <fieldset class="clonableId" id="location1">

                    <table>

                        <tr class="align_error">

                            <td>

                                <p><label id="lblOwner1" for="propertyOwner1" class="required" >Property Owner</label></p>

                            </td>

                            <td>

                                <p><input type="text" name="propertyOwner1" id="propertyOwner1" /></p>

                            </td>

                        </tr>

                    </table>

                    <p><label><strong>Excavation Address (Rural Areas Province DIrections)</strong></label></p>

                    <table>

                        <tr class="align_error">

                            <td>

                                <p><label id="lblexcavAddress1" for="excavAddress1" class="required" >Address</label> &nbsp; &nbsp;</p>

                            </td>

                            <td>

                                <p><input class="address" type="text" name="excavAddress1" id="excavAddress1" /></p>

                            </td>

                            <td>

                                <p><label id="lblexcavCity1" for="excavCity1" class="required" >City</label></p>

                            </td>

                            <td>

                                <p><input type="text" name="excavCity1" id="excavCity1" /></p>

                            </td>

                            <td><p><label id="lblexcavProv1" for="excavProv1" class="required" >Province</label></p>

                            </td>

                            <td><p>

                                <select id="excavProv1" name="excavProv1" >

                                    <option></option>

                                    <option>AB</option>

                                    <option>BC</option>

                                    <option>MB</option>

                                    <option>NB</option> 

                                    <option>NF</option>

                                    <option>NW</option>

                                    <option>NS</option>

                                    <option>NU</option>

                                    <option>ON</option>

                                    <option>PE</option>

                                    <option>QU</option>

                                    <option>SK</option>

                                    <option>YK</option>

                                </select>

                            </p></td>

                            <td><p><label id="lblzipCode1" for="excavPostCod1" class="required" >Postal Code</label></p></td>

                            <td>
                                <p><input type="text" name="excavPostCod1" id="excavPostCod1" class="lilfield55" onchange="postCod()" /></p>
                            </td>

                        </tr>

                    </table>


                </fieldset>

                <div id="newLoc">

                    <input type="button" id="addSection" value="Add new Location"> <input type="button" id="btnDel" value="remove Location above">

                </div>

                <div>

                    <input class="buttons" type="button" value="Print" onClick="window.print()" /><input id="submit_btn" class="buttons" type="submit" value="Submit" />

                </div>
                <div>

                    <button class="remove-rule">remove rule</button>

                </div>
            <!------  Fieldset Hearing conservation program ends here     ------>

        </form>

查看我的 Jquery,我们将不胜感激:

$(document).ready(function(){

        $("#excavationform").validate({

                rules: 
                    {
                    compName: {
                        required: true
                    },
                    compCity: {
                        required: true,
                    },                              
                    compAddress: {
                        required: true
                    },
                    compPROV: {
                        required: true
                    },
                    compPostCod:{
                        required:true
                    }
                },

                messages: {
                        compName: "Enter the company name.",
                        compAddress: "Enter the company's address",
                        compCity: "Enter the company city",
                        compPROV: "Enter the company province",
                        compPostCod:{
                                postalcode: "Enter a valid postal code in the format A1A 1A1 (including the space).",
                                required: "A valid postal code is required"
                        }
                }

        });

        nameFields("#compName");

        nameFields("#compAddress");

        nameFields("#compCity");

        filterInvalidHHTPPostChar("#compAddress");

        filterInvalidHHTPPostChar("#compPostCod");

        makeCaps("#compPostCod");


//////////////////////////////////////////////////////////////////////////////


//////////////////////////////////////////////////////////////////////////////////////////////////////////////

});

$(function () {
    $("form").on("click","#addSection",function (e) {
        e.preventDefault();
        var num     = $('.clonableId').length, // how many "duplicatable" input fields we currently have
            newNum  = new Number(num + 1),      // the numeric ID of the new input field being added
            newElem = $('#location' + num).clone(true).attr('id', 'location' + newNum).fadeIn('slow'); // create the new element via clone(), and manipulate it's ID using newNum value
    // manipulate the name/id values of the input inside the new element

        // Property Owner - Input
        newElem.find('#lblOwner' + num).attr('id', 'lblOwner'+ newNum).attr('for', 'propertyOwner'+ newNum);
        newElem.find('#propertyOwner' + num).attr('id', 'propertyOwner'+ newNum).attr('name', 'propertyOwner'+ newNum).val('');

        // Excavation Address - Input
        newElem.find('#lblexcavAddress' + num).attr('id', 'lblexcavAddress' + newNum).attr('for', 'excavAddress' + newNum);
        newElem.find('#excavAddress' + num).attr('id', 'excavAddress' + newNum).attr('name', 'excavAddress' + newNum).val('');

        // Excavation City - Input
        newElem.find('#lblexcavCity' + num).attr('id', 'lblexcavCity' + newNum).attr('for', 'excavCity' + newNum);
        newElem.find('#excavCity' + num).attr('id', 'excavCity' + newNum).attr('name', 'excavCity' + newNum).val('');

        // Excavation Province - Input
        newElem.find('#lblexcavProv' + num).attr('id', 'lblexcavProv' + newNum).attr('for', 'excavProv' + newNum);
        newElem.find('#excavProv' + num).attr('id', 'excavProv' + newNum).attr('name', 'excavProv' + newNum).val('');

        // Excavation Postal Code - Input
        newElem.find('#lblzipCode' + num).attr('id', 'lblzipCode' + newNum).attr('for', 'excavPostCod' + newNum);
        newElem.find('#excavPostCod' + num).attr('id', 'excavPostCod' + newNum).attr('name', 'excavPostCod' + newNum).val('');

    // insert the new element after the last "duplicatable" input field
        $('#location' + num).after(newElem);

    // Allow the datepicker: we delete it first then we re-create it
        $('#location' + newNum).on('focus','.dateChooser', function(){
            $(this).removeClass('hasDatepicker').datepicker();
        });

    // focus on the first input of the new section
        $('#propertyOwner' + newNum).focus();

    ///////////////////////////////////////////////////////Add rules


    //////////////////////////////////////////////////Control on the new section

        nameFields("#propertyOwner" + newNum);

        nameFields("#excavAddress" + newNum);

        nameFields("#excavCity" + newNum);

        numberFields("#MBrfNumber" + newNum);

        nameFields("#supervisorName" + newNum);

        fieldLength("#propertyOwner" + newNum, 70);

        fieldLength("#excavAddress" + newNum, 70);

        fieldLength("#excavCity" + newNum, 35);

        fieldLength("#excavPostCod" + newNum, 7);

        fieldLength("#startDate" + newNum, 10);

        fieldLength("#endDate" + newNum, 10);

        fieldLength("#MBrfNumber" + newNum, 10);

        fieldLength("#supervisorName" + newNum , 70);

        /////////////////////////////////////////Dates
    // enable the "remove" button
        $('#btnDel').attr('disabled', false);

    });

    $('#btnDel').click(function () {
    // confirmation
        if (confirm("Are you sure you wish to remove this section? This cannot be undone."))
            {
                var num = $('.clonableId').length;
                // how many "duplicatable" input fields we currently have
                $('#location' + num).slideUp('slow', function () {$(this).remove();
                // if only one element remains, disable the "remove" button
                    if (num -1 === 1)
                $('#btnDel').attr('disabled', true);
                // enable the "add" button
                $('#addSection').attr('disabled', false).prop('value', "add section");});
            }
        return false;
             // remove the last element

    // enable the "add" button
        $('#addSection').attr('disabled', false);
    });

});

【问题讨论】:

  • 您使用的是.clone(true),现在试试.clone()。顺便说一句,您应该阅读相关文档api.jquery.com/clone 我不确定这与您的问题有关,您的代码很难理解
  • 感谢您回复 A. Wolff。我之前尝试过 .clone() 但没有成功。我什至尝试强制执行 .clone(false)。是的,代码很难理解,我想更具体一点,但只有添加部分很重要。
  • 这毫无意义。如果克隆的字段包含不同的name 属性,那么它们将没有由您的.validate() 方法分配给它们的任何规则。我们需要查看正在克隆的相关 HTML。
  • 好的 @Sparky,我愿意向您展示我的代码,但不公开,所以如果您想给我发一封电子邮件,以便我们解决,因为这是给客户的表格。跨度>
  • 对不起,我是来帮助 Stack Overflow 的,不提供免费的私人咨询。您必须向我们展示足够的代码来重现该问题,否则这是徒劳的练习。此外,表单的 HTML 标记不可能有任何私有或专有的内容……只需将其剥离到相关部分并更改名称即可。见:stackoverflow.com/help/mcve

标签: jquery jquery-validate clone


【解决方案1】:

在几个地方你有class="required",如果这是在你的输入元素内部,是问题所在。但是,您的 &lt;label&gt; 元素中有这个 class,因此我们可以排除这种情况。

jQuery Validate 在每个输入上都需要唯一的 name 属性,因此即使您不小心重复了名称,jQuery Validate 也只会在每个元素的第一个实例上工作,而不是在克隆上工作......如果元素确实如此调用.validate()时不存在,完全可以排除.validate()方法的原因。

在调用.validate()之后,对动态创建的元素声明规则的唯一方式如下...

  1. 使用the .rules('add') method(虽然你为什么要添加你说你不想要的规则,我在你的代码中没有看到)

  2. 使用内联 HTML 5 验证属性,例如 required="required"。 (我在你的代码中没有看到这些)

  3. 使用内联 class 声明,例如 class="required"。 (同样,您只对 &lt;label&gt; 元素执行此操作)

换句话说,我在您的代码中绝对看不到任何会导致任何验证规则延续到您动态创建或克隆的元素中的内容。要么您忽略了向我们展示代码导致问题或您对所看到的内容有误。

使用浏览器的开发人员工具检查 DOM,并验证克隆的标记是否符合您的预期,并且您没有上面 #2 和 #3 中描述的任何属性或类。


如果您尝试过 .rules('remove') 并且失败了,as per documentation,此方法 "...仅操作通过 rules-option 或 rules('add')" 指定的规则。换句话说,您只能使用.rules('remove') 删除由.validate().rules('add') 方法设置的规则。

请记住,.rules('remove') 只能附加到代表单个输入元素的选择器...

$('#singleInput').rules('remove');     // <- ONE input

否则,如果您的选择器以一组元素为目标,则需要将其包装在 jQuery .each()...

$('.groupOfInputs').each(function() {  // <- multiple inputs
    $(this).rules('remove');
});

编辑

根据 cmets 中发布的 jsFiddle,您可以看到实际情况。

您没有遇到从原始部分克隆规则的问题,而且您的问题确实与规则完全无关。问题是您正在克隆错误消息本身......错误消息仅适用于原始元素集。你真的需要重新考虑你的整个方法,因为我什至不明白在这里克隆任何东西的好处。

由于您已经竭尽全力重命名所有内容,只需使用 jQuery 为每个部分编写所有新标记,而不是盲目地克隆包含动态内容(例如您甚至不需要/不需要的错误消息)的内容。换句话说,只需创建具有新名称的新表单元素,而从其他地方创建、克隆或复制任何动态内容。你的代码实际上会变得很简单,因为当它被正确创建时,你不需要做太多的 DOM 操作。

【讨论】:

  • 非常感谢您的回复,我也不能t see wheres 从所有这些毫无意义的验证中,但您可以查看我的jsfiddle。请先点击提交并添加一个新位置,然后填写第一部分。
  • @Pasoum,您需要重新考虑整个克隆方法。问题不在于规则被克隆。根本问题是您正在克隆实际的错误消息!
  • 我同意@Sparky 的解释,因为这是唯一有意义的原因。那么你知道克隆部分的任何其他方法(仅限字段)
  • @Pasoum,不要克隆。使用 jQuery 方法编写新的标记。 .append().insert() 等方法。查看我的编辑。
  • 听起来不错,我会这样做并随时通知您。非常感谢您的关注!!!
猜你喜欢
  • 2012-10-09
  • 1970-01-01
  • 1970-01-01
  • 2015-08-13
  • 1970-01-01
  • 2021-10-28
  • 2021-01-11
  • 2019-05-29
  • 1970-01-01
相关资源
最近更新 更多