使用自动回发从模板化复选框选择中确定网格行

发布于 2024-09-30 16:15:42 字数 325 浏览 1 评论 0原文

我有一个数据绑定网格,其中包含一个作为复选框的模板化字段列。当用户选中该复选框时,它将自动回发并更新该行以指示该框的选中状态。

我的第一次尝试是简单地使用 OnCheckedChanged 方法,但是当调用该方法时,我无法知道复选框来自哪一行。因此,我不知道要更新哪一行。

任何人都可以建议一种方法来确定触发 oncheckedchanged 事件的复选框来自哪一行?或者你能建议一个更好的方法来实现我需要做的事情吗?

我无法将复选框绑定到数据列,因为我不希望在选择模式下禁用该复选框,并且不希望要求用户进入编辑模式来更改值。我还需要所有行都是可编辑的。因此,最好的路线似乎是在模板列中。

I have a databound grid with a templated field column that is a checkbox. When the user checks the checkbox, it will autopostback and update the row to indicate the box's check state.

My first attempt was to simply use the OnCheckedChanged method, but when this gets called, I have no way to know which row the checkbox came from. Thus, I don't know which row to update.

Can anyone suggest a method to determine which row the checkbox that fired the oncheckedchanged event came from? Or can you suggest a better way to achieve what I need to do?

I cannot bind the checkbox to the data column because I do not want the checkbox disabled in select mode, and do not wish to require the user to enter edit mode to change the value. I also need all rows to be editable. So, the best route seems to be in a templated column.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

黑寡妇 2024-10-07 16:15:42

您可以通过迭代行来找到选中的复选框。

Protected Sub MyCheckBoxCheckedChanged(ByVal sender As Object, ByVal e As EventArgs)
    For Each row As GridViewRow In GridView1.Rows
        Dim cb As CheckBox = DirectCast(row.FindControl("MyCheckBoxID"), CheckBox)
        If sender Is cb AndAlso cb.Checked Then
            'Do something ...'
            Exit For
        End If
    Next
End Sub

这并不像看起来那么低效(当网格的 PageSize 不太高时)。

您还可以通过 Checkbox.Parent.Parent 获取 GridViewRow:

  Protected Sub MyCheckBoxCheckedChanged(ByVal sender As Object, ByVal e As EventArgs)
        Dim cb As CheckBox = DirectCast(sender, CheckBox)
        Dim row As GridViewRow = DirectCast(cb.Parent.Parent, GridViewRow)
        row.BackColor = DirectCast(IIf(cb.Checked, Color.Red, Color.White), Color)
  End Sub

这比选项 1 更快,但如果您将来将 Checkbox 嵌套在 Table 中,那么如果不进行调整,这将不再有效。

我通常更喜欢选项 1,因为在事件处理程序中,多一毫秒或少一毫秒并不重要。


Update: getting the GridViewRow via NamingContainer is another(in my opinion the best) option:

Dim row As GridViewRow = DirectCast(cb.NamingContainer, GridViewRow)

当您将复选框嵌套在其他控件(例如表格)中时,这甚至仍然有效。

You could find the checked Checkbox by iterating over the rows.

Protected Sub MyCheckBoxCheckedChanged(ByVal sender As Object, ByVal e As EventArgs)
    For Each row As GridViewRow In GridView1.Rows
        Dim cb As CheckBox = DirectCast(row.FindControl("MyCheckBoxID"), CheckBox)
        If sender Is cb AndAlso cb.Checked Then
            'Do something ...'
            Exit For
        End If
    Next
End Sub

This isn't as inefficient as it looks like(when the Grid's PageSize is not too high).

You can also get the GridViewRow via Checkbox.Parent.Parent:

  Protected Sub MyCheckBoxCheckedChanged(ByVal sender As Object, ByVal e As EventArgs)
        Dim cb As CheckBox = DirectCast(sender, CheckBox)
        Dim row As GridViewRow = DirectCast(cb.Parent.Parent, GridViewRow)
        row.BackColor = DirectCast(IIf(cb.Checked, Color.Red, Color.White), Color)
  End Sub

This is faster as option 1 but if you f.e. would nest the Checkbox in a Table in the future, this wouldn't work anymore without adjustment.

I would normally prefer option 1, because in an event-handler one millisecond more or less doesn't matter.


Update: getting the GridViewRow via NamingContainer is another(in my opinion the best) option:

Dim row As GridViewRow = DirectCast(cb.NamingContainer, GridViewRow)

This even still works when you nest the Checkbox inside other Controls like a Table.

只是我以为 2024-10-07 16:15:42

我认为没有办法在不处理 RowEditingRowUpdatingRowCancelingEdit 事件的情况下执行此操作。

或者,我建议将 CommandField 添加到 GridView,如下所示:

<asp:CommandField ShowSelectButton="true" />

您需要处理 GridView.SelectedIndexChanging,再次如下所示:

    void GridView_SelectedIndexChanging(object sender, GridViewSelectEventArgs e)
    {
        GridView.SelectedIndex = e.NewSelectedIndex;
    }

一旦您进入SelectedIndexChanging,您可以使用 GridView.Rows[e.NewSelectedIndex].FindControl("id") 来获取您需要的控件 - 假设此功能对您仍然至关重要。

编辑:我刚刚阅读了您的更新,但我不完全确定您想要在这里实现什么目标。听起来您对 CommandField 很熟悉。当您选中此必须独立完成的复选框时,您希望您的网站做什么?

编辑 2: 您还可以将 object sender 转换为 CheckBox,并使用 查找适当的 GridRow .Parent(),但这对我来说一直感觉非常hacky。

编辑 3:我发誓,我最终将停止编辑此内容。

我从未尝试过此操作,但您可以获取对 CheckBox.ClientID 的引用并尝试遍历 GridView 中的每一行,然后调用 GridViewRow.FindControl(CheckBox.ClientID) 。不过,我真的不知道这是否有效。

I don't think there's a way to do this as stated without handling the RowEditing, RowUpdating, and RowCancelingEdit events.

Alternatively, I'd suggest adding a CommandField to the GridView, like so:

<asp:CommandField ShowSelectButton="true" />

You'll need to handle the GridView.SelectedIndexChanging, again like so:

    void GridView_SelectedIndexChanging(object sender, GridViewSelectEventArgs e)
    {
        GridView.SelectedIndex = e.NewSelectedIndex;
    }

Once you're in SelectedIndexChanging, you can use GridView.Rows[e.NewSelectedIndex].FindControl("id") to get the control you need -- assuming this funcitonality is still critical to you.

Edit: I just read your update, and I'm not entirely sure what you're trying to achieve here. It sounds like you're familiar with the CommandField. What do you want your website to do when you check this checkbox that has to be done independently the row states?

Edit 2: You could also cast object sender to your CheckBox, and find the appropriate GridRow using .Parent(), but this has always felt extremely hacky to me.

Edit 3: I swear, I'm going to stop editing this eventually.

I've never tried this, but you could get a reference to CheckBox.ClientID and try going through each row in the GridView, and calling GridViewRow.FindControl(CheckBox.ClientID). I really have no idea if this will work, though.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文