You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Update Panel内DropDownList的SelectedIndexChanged事件无法触发问题

ASP.NET 3.5 DetailsView中DropDownList SelectedIndexChanged事件不触发问题

我正在使用ASP.NET 3.5(Visual Studio 2008,VB)开发项目,在DetailsView控件中借助UpdatePanel实现多控件的显隐交互逻辑:

  • 单选按钮rblAttemptType有“Phone Call”和“Letter”两个选项,选择“Phone Call”时,显示通话时间文本框并启用单选按钮rblSuccess;选择“Letter”时隐藏该文本框并禁用rblSuccess,同时将其选中项设为“N/A”。
  • 单选按钮rblSuccess有“N/A”“No”“Yes”三个选项,选择“No”时显示下拉列表ddlrncType,该下拉列表包含“no answer”“left voicemail”“Other”等选项,选择“Other”时需显示用于填写详情的文本框txrncOther。

目前前两步的SelectedIndexChanged事件均正常触发,但ddlrncType已设置AutoPostBack="True",其绑定的SelectedIndexChanged事件却始终无法触发。我尝试新增一个仅包含该下拉列表和txrncOther的UpdatePanel,并将ddlrncType设为异步回发触发器,问题仍未解决。

相关代码片段

ASPX页面代码

<asp:DetailsView ID="dvAppointment" runat="server" AutoGenerateRows="False" DataKeyNames="aID"
            Visible="False" Caption="Appointment Details" BorderColor="#189AA1" BorderStyle="Solid"
            BorderWidth="1px">
            <RowStyle BackColor="White" BorderStyle="None" Font-Names="Verdana,Arial,Helvetica"
                Font-Size="11px" Font-Strikeout="False" />
            <FieldHeaderStyle BackColor="#449c77" CssClass="white" Font-Bold="True" Width="15%"
                BorderColor="#189AA1" BorderStyle="Solid" BorderWidth="1px" />
            <Fields>
            <asp:BoundField DataField="aID" HeaderText="aID" Visible="False" ReadOnly="True" />
                <asp:TemplateField HeaderText="Attempt Type" SortExpression="AttemptType" HeaderStyle-VerticalAlign="Middle">
                    <ItemTemplate>
                        <asp:Label ID="lblAttemptType" runat="server" Text='<%# Eval("AttemptTypeDetails") %>'></asp:Label>&nbsp;&nbsp;
                        <br />
                        <asp:Label ID="lblAttemptMessage" runat="server" Text='<%# ContactAttemptMessage()%>'
                            HtmlEncode="False" CssClass="FireBrick9" HtmlEncodeFormatString="False" />
                    </ItemTemplate>
                    <InsertItemTemplate>
                        <asp:Label ID="lblAttemptMessage" runat="server" Text='<%# ContactAttemptMessage()%>'
                            HtmlEncode="False" CssClass="FireBrick9" HtmlEncodeFormatString="False" />
                        <asp:RadioButtonList ID="rblAttemptType" runat="server" RepeatDirection="Horizontal"
                            AutoPostBack="true" OnSelectedIndexChanged="rblAttemptTypeChanged" CssClass="Text9B">
                            <asp:ListItem Value="1">Phone call</asp:ListItem>
                            <asp:ListItem Value="2">Letter</asp:ListItem>
                        </asp:RadioButtonList>
                    </InsertItemTemplate>
                    <HeaderStyle VerticalAlign="Middle"></HeaderStyle>
                </asp:TemplateField>
        <asp:TemplateField HeaderText="Attempt Date" SortExpression="AttemptDate">
                    <ItemTemplate>
                        <asp:Label ID="lblAttemptDateWithTime" runat="server" Text='<%# AttemptDateDetails() %>'></asp:Label>&nbsp;&nbsp;
                    </ItemTemplate>
                    <InsertItemTemplate>
                        <asp:TextBox ID="txAttemptDate" runat="server" AutoCompleteType="Disabled" AutoPostBack="False"></asp:TextBox>
                        <asp:CalendarExtender ID="CalendarExtenderAttemptDate" runat="server" TodaysDateFormat="mm/dd/yyyy"
                            TargetControlID="txAttemptDate">
                        </asp:CalendarExtender> &nbsp;
                     <asp:UpdatePanel ID="UpdatePanelforAttempt" runat="server" UpdateMode="Conditional">
                            <ContentTemplate>
                                <asp:Label ID="AttemptTimeLabel" runat="server" Text="Time of phone attempt (hh:mm AM/PM): "
                                    Visible="False"></asp:Label>
                                <asp:TextBox ID="txAttemptTime" runat="server" ToolTip="Time should be in format XX:XX AM/PM"
                                    Visible="False"></asp:TextBox>
                                <asp:MaskedEditExtender ID="txAttemptTimeTime_MaskedEditExtender" runat="server"
                                 CultureAMPMPlaceholder="" CultureCurrencySymbolPlaceholder="" CultureDateFormat=""
                                    CultureDatePlaceholder="" CultureDecimalPlaceholder="" CultureThousandsPlaceholder=""
                                    CultureTimePlaceholder="" Enabled="True" TargetControlID="txAttemptTime" Mask="99:99 LL"
                                 ClearMaskOnLostFocus="False" MaskType="Number">
                                </asp:MaskedEditExtender>
                                <asp:Label ID="LabelSuccess" runat="server" Text="<br /><br />Was the attempt successful?"
                                 CssClass="Text8B" ></asp:Label>
                                <asp:RadioButtonList ID="rblSuccess" runat="server" OnSelectedIndexChanged="rblSuccessChanged"
                                    RepeatDirection="Horizontal" AutoPostBack="True" 
                                     Enabled='<%# IIF(Eval("AttemptType")=1,"true","false") %>'>
                                    <asp:ListItem Value="2">Yes</asp:ListItem>
                                    <asp:ListItem Value="1">No</asp:ListItem>
                                    <asp:ListItem Value="0" Selected="True">N/A</asp:ListItem>
                                </asp:RadioButtonList>
                                        <asp:Label ID="lblNoContactReason" runat="server" Text="<br />Please clarify the contact attempt result:"
                                            Visible="False" CssClass="smTextItalic"></asp:Label>&nbsp;
                                        <asp:DropDownList ID="ddlrncType" runat="server" DataSourceID="sdsrncTypes" DataValueField="rncTypeID"
                                            DataTextField="rncType" Visible="false" AutoPostBack="True" OnSelectedIndexChanged="ddlrncTypeChanged">
                                        </asp:DropDownList>
                                        <asp:Label ID="lblSpecify" runat="server" Text="<br /><br />Please Explain:<br />"
                                            CssClass="smTextbold" Visible="False"></asp:Label>&nbsp;
                                        <asp:TextBox ID="txrncOther" runat="server" Visible="false" ToolTip="Specific result (350 characters allowed)"
                                            TextMode="MultiLine" CssClass="MultiLineInsert" Width="35%" />
                            </ContentTemplate>
                        </asp:UpdatePanel>
                    </InsertItemTemplate>
                </asp:TemplateField>
        </Fields>
            <HeaderStyle BackColor="#449C77" BorderColor="#189AA1" BorderStyle="Solid" BorderWidth="1px" />
            <InsertRowStyle Width="80%" BackColor="White" Font-Names="Verdana,Ariel,Helvetica"
                Font-Size="11px" />
            <EditRowStyle Width="77%" BackColor="White" Font-Names="Verdana,Ariel,Helvetica"
                Font-Size="11px" />
            <AlternatingRowStyle BackColor="#CFCFCF" Font-Names="Verdana,Ariel,Helvetica" Font-Size="11px" />
        </asp:DetailsView>

VB后台代码

Protected Sub rblAttemptTypeChanged(ByVal sender As Object, ByVal e As System.EventArgs)
    Dim iAttemptTimeLabel As Label = DirectCast(dvAppointment.FindControl("AttemptTimeLabel"), Label)
    Dim itxAttemptTime As TextBox = DirectCast(dvAppointment.FindControl("txAttemptTime"), TextBox)
    Dim irblSuccess As RadioButtonList = DirectCast(dvAppointment.FindControl("rblSuccess"), RadioButtonList)
    Dim iUpdatePanelforAttempt As UpdatePanel = DirectCast(dvAppointment.FindControl("UpdatePanelforAttempt"), UpdatePanel)
    Dim AttemptType As Integer = 0
    If Not sender.selectedValue = String.Empty Then
        AttemptType = CInt(sender.selectedValue)
        ViewState("AttemptType") = CInt(sender.selectedValue)
        If AttemptType = 1 Then     'Phone
            If Not iAttemptTimeLabel Is Nothing Then
                iAttemptTimeLabel.Visible = True
            End If
            If Not itxAttemptTime Is Nothing Then
                itxAttemptTime.Visible = True
            End If
            If Not irblSuccess Is Nothing Then
                irblSuccess.Enabled = True
                irblSuccess.ClearSelection()
            End If
        ElseIf AttemptType = 2 Then     'Letter
            If Not iAttemptTimeLabel Is Nothing Then
                iAttemptTimeLabel.Visible = False
            End If
            If Not itxAttemptTime Is Nothing Then
                itxAttemptTime.Visible = False
            End If
            If Not irblSuccess Is Nothing Then
                irblSuccess.Enabled = False
                irblSuccess.SelectedIndex = 2
            End If
        End If
        If Not iUpdatePanelforAttempt Is Nothing Then
            iUpdatePanelforAttempt.Update()
        End If
    End If     
End Sub

Protected Sub rblSuccessChanged(ByVal sender As Object, ByVal e As System.EventArgs)
    Dim iddlrncType As DropDownList = DirectCast(dvAppointment.FindControl("ddlrncType"), DropDownList)
    Dim itxrncOther As TextBox = DirectCast(dvAppointment.FindControl("txrncOther"), TextBox)
    Dim ilblNoContactReason As Label = DirectCast(dvAppointment.FindControl("lblNoContactReason"), Label)
    Dim iUpdatePanelforAttempt As UpdatePanel = DirectCast(dvAppointment.FindControl("UpdatePanelforAttempt"), UpdatePanel)
    Dim Success as Integer = -1
    If Not sender.selectedValue = String.Empty Then
        Success = CInt(sender.selectedValue)
        If Success = 1 Then
            If Not iddlrncType Is Nothing Then
                iddlrncType.Visible = True
            End If
            If Not ilblNoContactReason Is Nothing Then
                ilblNoContactReason.Visible = True
            End If
        Else    
            If Not iddlrncType Is Nothing Then
                iddlrncType.Visible = False
            End If
            If Not ilblNoContactReason Is Nothing Then
                ilblNoContactReason.Visible = False
            End If
        End If 
        If Not iUpdatePanelforAttempt Is Nothing Then
            iUpdatePanelforAttempt.Update()
        End If
    End If   
End Sub

Protected Sub ddlrncTypeChanged(ByVal sender As Object, ByVal e As System.EventArgs)
    Dim ilblSpecify As Label = CType(dvAppointment.FindControl("lblSpecify"), Label)
    Dim itxrncOther As TextBox = CType(dvAppointment.FindControl("txrncOther"), TextBox)
    Dim iUpdatePanelforAttempt As UpdatePanel = DirectCast(dvAppointment.FindControl("UpdatePanelforAttempt"), UpdatePanel)
    Dim rncTypeID as Integer = 0
    If Not sender.selectedValue = String.Empty AndAlso IsNumeric(sender.selectedvalue) Then
        rncTypeID = CInt(sender.selectedValue)
        If rncTypeID = 5 Then
            If Not itxrncOther Is Nothing Then
                itxrncOther.Visible = True
                itxrncOther.Focus()
                If Not ilblSpecify Is Nothing Then
                    ilblSpecify.Visible = True
                End If
            End If
        Else
            If Not itxrncOther Is Nothing Then
                itxrncOther.Visible = False
                If Not ilblSpecify Is Nothing Then
                    ilblSpecify.Visible = False
                End If
            End If
        End If
        If Not iUpdatePanelforAttempt Is Nothing Then
            iUpdatePanelforAttempt.Update()
        End If
    End If
End Sub

解决方案

1. 修正控件查找逻辑

DetailsView处于Insert模式时,模板内的控件不能直接通过dvAppointment.FindControl获取,需要先定位到Insert行再查找控件。修改所有事件中的控件查找代码,以rblSuccessChanged为例:

Protected Sub rblSuccessChanged(ByVal sender As Object, ByVal e As System.EventArgs)
    ' 获取Insert模式下的行
    Dim insertRow As DetailsViewRow = dvAppointment.Rows(dvAppointment.Rows.Count - 1)
    Dim iddlrncType As DropDownList = DirectCast(insertRow.FindControl("ddlrncType"), DropDownList)
    Dim itxrncOther As TextBox = DirectCast(insertRow.FindControl("txrncOther"), TextBox)
    Dim ilblNoContactReason As Label = DirectCast(insertRow.FindControl("lblNoContactReason"), Label)
    Dim iUpdatePanelforAttempt As UpdatePanel = DirectCast(insertRow.FindControl("UpdatePanelforAttempt"), UpdatePanel)
    ' 剩余逻辑保持不变
End Sub

同理,rblAttemptTypeChanged和ddlrncTypeChanged事件中的控件查找都需要做相同修改。

2. 配置UpdatePanel触发器

在UpdatePanel中显式添加所有需要触发异步回发的控件触发器,确保事件能被正确捕获:

<asp:UpdatePanel ID="UpdatePanelforAttempt" runat="server" UpdateMode="Conditional">
    <ContentTemplate>
        <!-- 原有内容 -->
    </ContentTemplate>
    <Triggers>
        <asp:AsyncPostBackTrigger ControlID="rblAttemptType" EventName="SelectedIndexChanged" />
        <asp:AsyncPostBackTrigger ControlID="rblSuccess" EventName="SelectedIndexChanged" />
        <asp:AsyncPostBackTrigger ControlID="ddlrncType" EventName="SelectedIndexChanged" />
    </Triggers>
</asp:UpdatePanel>

如果模板内控件ID无法被触发器识别,可以在后台代码的Page_Load事件中动态添加触发器:

Protected Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load
    If Not IsPostBack Then
        Dim updatePanel As UpdatePanel = DirectCast(dvAppointment.Rows(dvAppointment.Rows.Count - 1).FindControl("UpdatePanelforAttempt"), UpdatePanel)
        Dim ddl As DropDownList = DirectCast(dvAppointment.Rows(dvAppointment.Rows.Count - 1).FindControl("ddlrncType"), DropDownList)
        updatePanel.Triggers.Add(New AsyncPostBackTrigger() With {.ControlID = ddl.UniqueID, .EventName = "SelectedIndexChanged"})
    End If
End Sub

3. 确保控件状态正确

在显示ddlrncType时,确保控件的Enabled属性为True,并且如果是首次显示,重新绑定数据源(如果依赖动态数据源):

If Success = 1 Then
    If Not iddlrncType Is Nothing Then
        iddlrncType.Visible = True
        iddlrncType.Enabled = True
        ' 若数据源未提前绑定,添加此行
        ' iddlrncType.DataBind()
    End If
    ' 剩余逻辑保持不变
End If

4. 检查ViewState设置

确保UpdatePanel和ddlrncType的EnableViewState属性为True,避免异步回发时控件状态丢失:

<asp:UpdatePanel ID="UpdatePanelforAttempt" runat="server" UpdateMode="Conditional" EnableViewState="True">
    <!-- 内容 -->
</asp:UpdatePanel>

<asp:DropDownList ID="ddlrncType" runat="server" EnableViewState="True" ...>
</asp:DropDownList>

内容的提问来源于stack exchange,提问作者Dave Starns

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.11 19:55:17