C# 未选中复选框时,不会触发 asp:checkbox 的 OnCheckedChanged 事件处理程序

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/1404528/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-06 16:08:49  来源:igfitidea点击:

OnCheckedChanged event handler of asp:checkbox does not fire when checkbox is unchecked

c#asp.netc#-2.0

提问by Jason

I have a repeater, in each ItemTemplate of the repeater is an asp:checkbox with an OnCheckedChanged event handler set. The checkboxes have the AutoPostBack property set to true. When any of the checkboxes is checked, the event handler fires. When any is unchecked, the event handler does not fire.

我有一个转发器,在转发器的每个 ItemTemplate 中都是一个 asp:checkbox,其中设置了一个 OnCheckedChanged 事件处理程序。复选框的 AutoPostBack 属性设置为 true。当任何复选框被选中时,事件处理程序将触发。当 any 未选中时,事件处理程序不会触发。

Any idea why the event does not fire, and how I mgiht make it fire? Thanks.

知道为什么事件没有触发,以及我如何让它触发?谢谢。

Simplified repeater code:

简化中继器代码:

<asp:Repeater ID="rptLinkedItems" runat="server">            
    <ItemTemplate>      
    <asp:CheckBox ID="chkLinked" runat="server" 
     Checked="false" OnCheckedChanged="chkLinked_CheckedChanged" />
    </ItemTemplate>    
</asp:Repeater>

The collection is bound to the repeater as follows:

集合绑定到转发器如下:

protected override void OnPreRenderComplete(EventArgs e)
{
    if (!Page.IsPostBack)
    {
        m_linkedItems = GetLinkedItems();
        rptLinkedItems.DataSource = GetLinkableItems();
        rptLinkedItems.ItemDataBound += new RepeaterItemEventHandler
               (rptLinkedItems_ItemDataBound);
        rptLinkedItems.DataBind();
    }

    base.OnPreRenderComplete(e);
}

The OnItemDataBound event handler is as follows:

OnItemDataBound 事件处理程序如下:

private void rptLinkedItems_ItemDataBound(Object sender, RepeaterItemEventArgs args)
{
    if (args.Item.ItemType == ListItemType.Item || args.Item.ItemType == ListItemType.AlternatingItem)
    {
        CategoryItem item = args.Item.DataItem as CategoryItem;

        Literal litItemName = args.Item.FindControl("litItemName") as Literal;
        CheckBox chkLinked = args.Item.FindControl("chkLinked") as CheckBox;

        litItemName.Text = item.Text;

        chkLinked.Checked = IsItemLinked(item);
        chkLinked.AutoPostBack = true;
        chkLinked.InputAttributes.Add("Value", item.Id.ToString());
    }
}

The OnCheckedChanged event handler is as follows:

OnCheckedChanged 事件处理程序如下:

protected void chkLinked_CheckedChanged(Object sender, EventArgs args)
{
    CheckBox linkedItem = sender as CheckBox;
    Boolean itemState = linkedItem.Checked;
    Int32 itemId = Int32.Parse(linkedItem.InputAttributes["Value"].ToString());
    DataAccessLayer.UpdateLinkedItem(m_linkingItem, Utilities.GetCategoryItemFromId(itemId), itemState);
}

P.S. If someone can also tell me why markdown doesn't work correctly for me...

PS如果有人也能告诉我为什么降价对我来说不能正常工作......

采纳答案by Rabid

This is because the control hierarchy (and the check boxes in particular) don't exist when ASP.NET executes the Control eventsportion of the ASP.NET page life cycle, as you had created them in the later PreRenderstages. Please see ASP.NET Page Life Cycle Overviewfor more detailed overview of the event sequence.

这是因为当 ASP.NET 执行Control eventsASP.NET 页面生命周期的一部分时,控件层次结构(尤其是复选框)不存在,因为您在后面的PreRender阶段创建了它们。有关事件序列的更详细概述,请参阅ASP.NET 页面生命周期概述

I would err on the side of caution for @bleeeah's advice, for you're assigning a value to CheckBox.Checkedinside rptLinkedItems_ItemDataBound, which would also cause the event handler to execute:

对于@bleeeah 的建议,我会谨慎行事,因为您正在为CheckBox.Checkedinside分配一个值rptLinkedItems_ItemDataBound,这也会导致事件处理程序执行:


chkLinked.Checked = IsItemLinked(item);

Instead, move:

相反,移动:


if (!Page.IsPostBack)
   {
      m_linkedItems = GetLinkedItems();
      rptLinkedItems.DataSource = GetLinkableItems();
      rptLinkedItems.ItemDataBound += new RepeaterItemEventHandler
          (rptLinkedItems_ItemDataBound);
      rptLinkedItems.DataBind();
   }

Into the Page.Loadevent handler.

进入Page.Load事件处理程序。

回答by bleeeah

Try re-subscribing to the CheckChanged event in your OnItemDataBound event ,

尝试重新订阅 OnItemDataBound 事件中的 CheckChanged 事件,

chkLinked.CheckedChanged += new EventHandler(chkLinked_CheckedChanged);

回答by Jan Jongboom

Subscribe to the CheckChanged event in your Page_Init.

在您的 Page_Init 中订阅 CheckChanged 事件。

回答by tommy

Try usingAutoPostBack="true"like this:

尝试使用AutoPostBack="true"这样的:

<asp:CheckBox ID="chkLinked" runat="server" Checked="false"
    OnCheckedChanged="chkLinked_CheckedChanged" AutoPostBack="true"/>

回答by Shaahin

You have to define eventhandler for checklist out of repeater item command, then inside the repeater item command, go through checklist items and get checked items.

您必须在转发器项目命令中为清单定义事件处理程序,然后在转发器项目命令中,通过清单项目并获取已检查项目。

In the .aspx page you can use Ajax and updatepanel to fire eventhandler, but keep in mind you have to define scriptmanage outside of repeater.

在 .aspx 页面中,您可以使用 Ajax 和 updatepanel 来触发 eventhandler,但请记住,您必须在转发器之外定义 scriptmanage。

// checklisk checkedchange eventhandler

// checklisk checkedchange 事件处理程序

protected void chkLinked_CheckedChanged(Object sender, EventArgs args)
        {
        }

and item repeater command item: // iterate checklist items and detect checked

和项目转发器命令项目://迭代清单项目并检测已检查

    protected void Repeater1_ItemCommand(object sender, RepeaterCommandEventArgs e)
    {
        CheckBoxList cbl = (CheckBoxList)e.Item.FindControl("CheckBoxList1");
        cbl.SelectedIndexChanged += new EventHandler(chkLinked_CheckedChanged);

        string name = "";
        for (int i = 0; i < cbl.Items.Count; i++)
        {
            if (cbl.Items[i].Selected)
            {
                name += cbl.Items[i].Text.Split(',')[0] + ",";
            }
        }
    }

回答by Vikash Kumar

Use AutoPostBack="true"like this:

AutoPostBack="true"像这样使用:

<asp:CheckBox ID="chkLinked" runat="server" AutoPostBack="true"
    Checked="false" OnCheckedChanged="chkLinked_CheckedChanged" />