2

I have a custom control which is basically a Gridview and its first column is a TemplateField with a checkbox in the header and a checkbox for each of the rows. Clicking on the header checkbox should call some javascript to toggle each of the checkboxes in every row on display... it's a common requirement as we know.

My problem is (I'll go into more detail later) that when I have 2 of these controls on the same page, and I click the checkbox that selects all the chkboxes, the page calls the wrong bit of javascript (which only appears once on the rendered html page) and checks all the checkboxes on the wrong grid !

Here's my code:

<asp:TemplateField>
    <HeaderTemplate>
        <input type="checkbox" ID="chkSelectAll" onclick="SelectAllCheckboxes(this)"/>
    </HeaderTemplate>
    <ItemTemplate>
        <asp:CheckBox runat="server" ID="chkSelected"></asp:CheckBox>
    </ItemTemplate>
</asp:TemplateField>

Javascript:

<script>
    function SelectAllCheckboxes(chk) {
        $('#<%=gridPublishers.ClientID%>').find("input:checkbox").each(function () 
            {
                if (this != chk) { this.checked = chk.checked; }
            });
        }
 </script>

So, the parent page has 2 of these controls on it. The first grid shows All the publishers and the other shows the publishers that have been selected from the first...

<h2>Selected Publishers</h2>
<cac:GridPublishers id="GridSelectedPublishers" runat="server" CssClass="GridSelectedPublishers" BindSource="DynamicFromSession" ShowMultiSelectCol="true" ShowFilterControls="false" NoRecordsMessage="No Publishers have been selected yet." />
<br /><br />
<h2>All Publishers</h2>
<cac:GridPublishers id="GridPublishers" runat="server" ShowMultiSelectCol="true" CssClass="GridPublishers"  />

As I said earlier, the javascript only appears once on the rendered html page (and I understand why) but how can I get each instance of the custom control calling it's own javascript (or an alternative method) so that it only toggles its own checkboxes ??

...

I've also tried adding 2 javascript events and on grid bind trying to find the master checkbox and assign it the correct JS function, but I've searched each cell of the header row, and col 0 (where the control should be) holds 0 controls.

...

I've also tried adding a hidden button that on page load, I can assign it the correct javascript function (that will affect the correct gridview) and then the master checkbox fires the hidden button onClientClick event, but as the page reloads, it gets confused and fires the click event twice and from both grids apparently !

Please help !!

4

3 回答 3

1

所以我猜你意识到这行代码导致了在错误的数据网格中选择复选框的根本问题:

#<%=gridPublishers.ClientID%>').find

它总是会选择 gridPublishers,而不是 GridSelectedPublishers。

所以这是要修复的区域。你需要做的是让这个函数更抽象一点:

<input type="checkbox" ID="chkSelectAll" onclick="SelectAllCheckboxes(this)"/>

onclick 事件传递“this”,但这只是对复选框的引用,没有太大帮助。

我建议你试着把它做成这样:

<input type="checkbox" ID="chkSelectAll" onclick="SelectAllCheckboxes(this,'GridSelectedPublishers')"/>

然后使用 javascript 函数中的第二个参数来获取正确的数据网格。

您现在的问题是如何在其中获取第二个参数....您可能可以为此考虑自己的解决方案,但我很想将该复选框设置为 ASP 复选框,并在数据网格渲染期间找到它和使用 Attribute.Add 为其分配 onClick

有道理?

于 2013-10-02T09:39:32.730 回答
1

我已经将“ben_the_builder's”的答案标记为正确,因为它让我走上了正确的道路。

当我绑定我的网格时,我调用这个函数:

private void Register_CheckAllControl_JScript()
    {
        // THIS IS A WORKAROUND FOR WHEN TWO OF THE SAME CUSTOM CONTROL LIVE ON THE SAME PAGE, EACH CONTROL'S JAVASCRIPT MUST SPECIFY THE ID OF THE CONTROL TO AFFECT

        if (gridPublishers.HeaderRow != null)
        { 
            CheckBox chkAll = gridPublishers.HeaderRow.FindControl("chkSelectAll") as CheckBox;

            if (chkAll != null)
            {
                if (this.BindSource == Enumerators.BindSource.DynamicFromSession)
                {
                    chkAll.Attributes.Add("onclick", "SelectAllCheckboxes(this,'GridSelectedPublishers');");
                }
                else
                {
                    chkAll.Attributes.Add("onclick", "SelectAllCheckboxes(this,'GridPublishers');");
                }
            }
        }
    }

要从后面的代码访问“主”复选框 - 它必须是一个 ASP 控件。迭代标题单元格集合时无法识别输入控件。

我的 Javascript 需要稍微调整才能使 ID 正确。我传递的控件名称必须是它在父页面上给出的名称,该名称属于三层最终 html 输出名称的中间(参见示例,它会有意义......)

我的 Javascript 现在看起来像这样:

<script>
        function SelectAllCheckboxes(chk, ctrlName) {
            //if ctrlName = "

            $("#MainContent_" + ctrlName + "_gridPublishers").find("input:checkbox").each(function () {
                if (this != chk) { this.checked = chk.checked; }
            });
        }
    </script>
于 2013-10-02T16:04:52.067 回答
0

你想使用参数。无需将 #<%=gridPublishers.ClientID%> 硬编码到您的 javascript 函数中,而是使用传递给函数的 this 参数来确定包含复选框的网格视图的名称,然后检查该网格视图内的所有内容。

于 2013-10-01T21:08:50.027 回答