C# ASP.NET CheckBox_OnCheckedChanged未按预期触发

本文关键字:OnCheckedChanged ASP NET CheckBox | 更新日期: 2023-09-27 18:35:20

我有一个问题,Checkbox_OnCheckedChangedDropdownlist_OnSelectedIndexChanged事件都没有触发我的代码中的相关函数。

这两个控件都绑定到GridView中的值。在从 UI 引发的第一个OnCheckedChangedOnSelectedIndexChanged事件中,代码后面的函数会毫无错误地触发,但是如果我刷新我的UpdatePanel,例如通过更改GridView内数据的日期范围并因此加载或多或少的记录,不再调用 OnCheckedChangedOnSelectedIndexChanged 函数, 但是发生了PostBack

我相信这些函数没有被调用,而是调用了重新绑定GridView的函数:

 private void report_DateChanged(object sender, EventArgs e)
 {
        // Bind GridView here..
 }

但是我无法弄清楚为什么会发生这种情况。

我有一个母版页:

namespace ReportingSystemV2.Reporting
{
public partial class Reporting : System.Web.UI.MasterPage
{
    protected void Page_Load(object sender, EventArgs e)
    {
        // Attach to DateChanged Event on DateChange UserControl to Function
        DateRangeSelect.dateChanged += new DateRangeSelect.dateChangedEventHandler(dtRgSel_dateChanged);
    }
    // Declare an event for the content pages
    public event EventHandler reportDateChanged;
    // Called on a date change event
    protected void dtRgSel_dateChanged(object sender, DateChangedEventArgs e)
    {
        // Raise the event for content pages
        if (reportDateChanged != null)
            reportDateChanged(this, EventArgs.Empty);
    }
}

MasterPage有一个用于选择我的日期范围的Control

我的控件ascx代码的主要代码部分是:

<%--UpdatePanel to trigger datechange--%>
<asp:UpdatePanel runat="server" ID="UpdatePanelDateChanged" OnLoad="UpdatePanelDateChanged_Load" >
</asp:UpdatePanel>
<%--When the date changes in javascript a postback is called in the updatepanel--%>
__doPostBack('<%=UpdatePanelDateChanged.ClientID %>', null);

此控件的主要代码隐藏部分是:

// Declare a delegate
public delegate void dateChangedEventHandler(object sender, DateChangedEventArgs e);
// Declare an event for any pages that have the control
public event dateChangedEventHandler dateChanged;
protected virtual void OnDateChanged(DateChangedEventArgs e)
{
    dateChangedEventHandler handler = dateChanged;
    // Raise the event
    if (handler != null)
        handler(this, e);
}
protected void UpdatePanelDateChanged_Load(object sender, EventArgs e)
{
   // Trigger the controls public event
   OnDateChanged(new DateChangedEventArgs(DateTime.Parse(dates[0]), DateTime.Parse(dates[1])));
}

在我的内容页面中,我aspx代码是:

<%@ Page Title="Downtime" Language="C#" MasterPageFile="~/Reporting/Reporting.Master" AutoEventWireup="true" CodeBehind="GensetDowntime.aspx.cs" Inherits="ReportingSystemV2.Reporting.GensetDowntime" %>
<%@ MasterType VirtualPath="~/Reporting/Reporting.Master" %>
<asp:Content ID="Content1" ContentPlaceHolderID="ReportingSubContent" runat="server">
<div class="container-fluid">
    <asp:UpdatePanel ID="updPanelDowntime" runat="server">
        <ContentTemplate>
            <div class="row">
                <div id="downtimeDiv" runat="server">
                    <asp:GridView ID="gridDowntime" runat="server" AutoGenerateColumns="False" GridLines="None" CssClass="table table-striped table-condensed"
                        OnRowDataBound="gridDowntime_RowDataBound"
                        OnSelectedIndexChanged="gridDowntime_SelectedIndexChanged"
                        DataKeyNames="ID,ID_Location,iddown,idup,dtdown,dtup,isexempt" EmptyDataText="No exempts in the selected period.">
                        <Columns>
                            <asp:TemplateField>
                                <ItemTemplate>
                            <asp:TemplateField HeaderText="Exempt?">
                                <ItemTemplate>
                                    <asp:DropDownList ID="ddlDowntimeExempt" AutoPostBack="true" runat="server"
                                        OnSelectedIndexChanged="ddlDowntimeExempt_SelectedIndexChanged">
                                        <asp:ListItem Value="-1">Unverified</asp:ListItem>
                                        <asp:ListItem Value="1">Yes</asp:ListItem>
                                        <asp:ListItem Value="0">No</asp:ListItem>
                                    </asp:DropDownList>
                                    <asp:Label ID="lblDowntimeExempt" runat="server" Text='<%#DataBinder.Eval(Container.DataItem,"isexempt")%>' Visible="false"></asp:Label>
                                </ItemTemplate>
                            </asp:TemplateField>
                            <asp:TemplateField HeaderText="Exclude?">
                                <ItemTemplate>
                                    <asp:CheckBox ID="chkDowntimeExclude" runat="server" Checked='<%#Convert.ToBoolean(Eval("ISEXCLUDED")) %>' OnCheckedChanged="chkDowntimeExclude_CheckedChanged" AutoPostBack="true"/>
                                </ItemTemplate>
                            </asp:TemplateField>
                            <asp:CommandField ShowSelectButton="True" SelectText="Details" />
                        </Columns>
                    </asp:GridView>
                </div>
            </div>
        </ContentTemplate>
    </asp:UpdatePanel>
</div>
</asp:Content>

最后,我的内容页面代码是:

    protected void Page_PreInit(object sender, EventArgs e)
    {
        // Attach to UserControl Event on the MasterPage
        Master.reportDateChanged += new EventHandler(report_DateChanged);
    }
    // If the user changes the date lets update the table
    private void report_DateChanged(object sender, EventArgs e)
    {
        // Bind the gridview
    }
    // Function to be called when the ddl selectedindex is changed, only called on initial page load
    protected void ddlDowntimeExempt_SelectedIndexChanged(object sender, EventArgs e)
    {
        // Applies the values selected in the exempt DDL to the database value
    }
    // function to be called when the checkbox checked state is change, again only called on the initial page loading - not after a postback
    protected void chkDowntimeExclude_CheckedChanged(object sender, EventArgs e)
    {
        // When the Exclude checkbox is changed, update the Db
    }

上面的代码显示了使用 javascript 在UpdatePaneltrigger PostBackcontroltriggers Control中的公共事件。MasterPage有一个附加到Control事件的函数,这个MasterPage函数更新一些值并触发一个可由我的ContentPage访问的新事件。ContentPage将一个函数附加到此MasterPage事件,当DateRange更改时,它将加载GridView的数据并将其绑定。

C# ASP.NET CheckBox_OnCheckedChanged未按预期触发

母版页在"子"页的控件开头附加额外的名称。最有可能的是,您希望下拉列表有一个名称,但它会有一个不同的更长的名称,例如ctrl1 $something$dropdown。

使用 Chrome 或开发工具中的检查功能检查 IDA,首先确认这是您的问题。

我认为您缺少异步回发触发器。当更新面板部分回发时,它会发回整个页面,执行处理,然后仅返回更改的部分。可能在这个过程中,发生了轻微的ID更改,然后错过了注册。触发report_DateChanged很可能是因为它是页面上实现IPostBackEventHandler的第一个控件(因为复选框和下拉列表上的回发不再起作用)

若要解决此问题,请将应执行异步回发的每个控件显式添加到更新面板的触发器。 像这样:

protected void gridDowntime_RowDataBound(object sender, GridViewRowEventArgs e)  
{  
    DropDownList ddl = e.Row.FindControl("ddlDowntimeExempt") as DropDownList;  
    CheckBox cb = e.Row.FindControl("chkDowntimeExclude") as CheckBox;  
    ScriptManager.GetCurrent(this).RegisterAsyncPostBackControl(ddl);  
    ScriptManager.GetCurrent(this).RegisterAsyncPostBackControl(cb);  
}  
问题

解决了,通过修改我DateRangeControl中的代码,UpdatePanel不再在所有PostBacks上触发,只有那些在我的Javascript中被__doPostBack('<%=UpdatePanelDateChanged.ClientID %>', null);调用的那些

protected void UpdatePanelDateChanged_Load(object sender, EventArgs e)
{
    if (Request["__EVENTTARGET"] == UpdatePanelDateChanged.ClientID)
    {
        //Trigger Event
        OnDateChanged(new DateChangedEventArgs(DateTime.Parse(dates[0]), DateTime.Parse(dates[1])));
    }
}

解决方案参考:http://encosia.com/are-you-making-these-3-common-aspnet-ajax-mistakes/