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

GridView内嵌动态项的DropDownList回发时SelectedIndexChanged不触发问题

问题根因

  1. GridView同时绑定了DataSourceID声明式数据源和手动调用DataBind(),双重绑定导致控件状态加载混乱。
  2. DropDownList动态选项生成时机错误,且回发时重复清空选项,覆盖了ViewState加载的用户选中值,导致回发事件无法匹配触发。
  3. 手动添加ListItem后多余调用DataBind(),扰乱控件状态。

修正步骤

1. 调整ASCX代码

删除GridView的DataSourceID属性,完全使用手动绑定控制数据加载:

<asp:GridView ID="MyGV" runat="server" AutoGenerateColumns="False" Width="100%" OnRowDataBound="MyGV_OnRowDataBound">
    <Columns>                                    
        <asp:TemplateField >
             <ItemTemplate>
                   <asp:DropDownList runat="server" ID="SectionDD" AppendDataBoundItems="True" AutoPostBack="True" OnSelectedIndexChanged="SectionDD_OnSelectedIndexChanged" >
                   </asp:DropDownList>
             </ItemTemplate>
        </asp:TemplateField>
    </Columns>
</asp:GridView>

2. 修正后置代码逻辑

protected void Page_Init(object sender,EventArgs e)
{                                                                 
    // 所有请求都在Page_Init阶段绑定GridView,保证控件树在ViewState加载前生成完成
    MyGV.DataBind();
}

protected void SectionDD_OnSelectedIndexChanged(object sender, EventArgs e)
{
    // 此处可正常获取选中值执行业务逻辑
    DropDownList sectionDd = sender as DropDownList;
    string selectedVal = sectionDd.SelectedValue;
}

protected void MyGV_OnRowDataBound(object sender, GridViewRowEventArgs e)
{
    using (EntitiesModel dbContext = new EntitiesModel())
    {
        // 从数据库获取二维数组array                
        if (e.Row.RowType == DataControlRowType.DataRow)
        {
            DropDownList sectionDd = (DropDownList)e.Row.FindControl("SectionDD");
            // 仅首次加载时生成选项,回发时不再重复生成覆盖状态
            if(!Page.IsPostBack)
            {
                sectionDd.Items.Clear();
                if (array.Length == 3)
                {
                    if(array[0][2].ToDecimal() > 0) sectionDd.Items.Add(new ListItem(array[0][0], array[0][1]));
                    if(array[1][2].ToDecimal() > 0) sectionDd.Items.Add(new ListItem(array[1][0], array[1][1]));
                    if(array[2][2].ToDecimal() > 0) sectionDd.Items.Add(new ListItem(array[2][0], array[2][1]));
                }
                else if (array.Length == 2)
                {
                    if (array[0][2].ToDecimal() > 0) sectionDd.Items.Add(new ListItem(array[0][0], array[0][1]));
                    if (array[1][2].ToDecimal() > 0) sectionDd.Items.Add(new ListItem(array[1][0], array[1][1]));
                }
                else if (array.Length == 1)
                {
                    if (array[0][2].ToDecimal() > 0) sectionDd.Items.Add(new ListItem(array[0][0], array[0][1]));
                }
            }
        }                    
    }
}

private void SaveToDB()
{
    // 保存数据到数据库逻辑
    // 保存完成后需要刷新数据时再手动调用一次绑定即可
    MyGV.DataBind();
}

关键逻辑说明

  • Page_Init阶段绑定GridView是为了保证控件树结构在ViewState加载前和上一次渲染完全一致,ViewState才能正确把用户选中值加载到DropDownList,触发对应的选中变更事件。
  • 回发时不再清空重新生成DropDownList选项,避免覆盖ViewState加载的用户操作状态,解决选中值自动恢复初始值的问题。
  • 去掉DropDownList多余的DataBind调用,手动添加ListItem不需要执行该方法,避免扰乱控件状态。

内容的提问来源于stack exchange,提问作者Darren Wood

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.10.16 01:54:03