C# 在面板列表中动态创建的DropDownList不允许进行事件处理

C# 在面板列表中动态创建的DropDownList不允许进行事件处理,c#,asp.net,event-handling,drop-down-menu,C#,Asp.net,Event Handling,Drop Down Menu,我正在尝试创建一个UI,它创建可以动态填充的行 我现在可以将一个面板添加到我的列表中,该面板包含一个DropDownList并具有一个关联的删除按钮 移除按钮有一个OnClick事件绑定,允许我移除该特定面板 尝试将SelectedIndexChanged事件处理程序绑定到DropDownList时出现问题,但实际情况并非如此 我怀疑这与每次回发后我如何重新创建控件有关 我不是要求或期待一个简单的“在代码中添加或更改此项”。我真的想了解我的错误所在,抱歉问了这么多!: protected voi

我正在尝试创建一个UI,它创建可以动态填充的行

我现在可以将一个面板添加到我的列表中,该面板包含一个DropDownList并具有一个关联的删除按钮

移除按钮有一个OnClick事件绑定,允许我移除该特定面板

尝试将SelectedIndexChanged事件处理程序绑定到DropDownList时出现问题,但实际情况并非如此

我怀疑这与每次回发后我如何重新创建控件有关

我不是要求或期待一个简单的“在代码中添加或更改此项”。我真的想了解我的错误所在,抱歉问了这么多!:

protected void Page_Load(object sender, EventArgs e)
{
    //Showing this for the the poster that asked.
    if (!IsPostBack)
    {
        GetClustersFromDB(user);
        BindGrid();
        BindState();            
    }
    if (Session["persistControls"] != null)
    {
        persistControls = (List<Panel>)Session["persistControls"];
        int count = 0;

        foreach (Panel dynamicControl in persistControls)
        {
            DropDownList list = new DropDownList();
            list.ID = "list" + count;
            list.SelectedIndexChanged += new EventHandler(list_SelectedIndexChanged);
            list.AutoPostBack = true;
            list.Items.Add(new ListItem("", "0"));
            list.Items.Add(new ListItem("Title", "1"));

            dynamicControl.ID = "panel" + count;

            Button btnRemove = new Button();
            btnRemove.Click += new EventHandler(btnDelete_Click);
            btnRemove.Text = "Remove";
            btnRemove.CommandArgument = count.ToString();             

            myPlaceholder.Controls.Add(dynamicControl);
            myPlaceholder.Controls.Add(btnRemove);
            count++;
        }
    }
}

protected void btnAdd_Click(object sender, EventArgs e)
{
    try
    {
        DropDownList list = new DropDownList();
        list.SelectedIndexChanged += new EventHandler(list_SelectedIndexChanged);
        list.AutoPostBack = true;
        list.Items.Add(new ListItem("", "0"));
        list.Items.Add(new ListItem("Title", "1"));

        Panel panelContainer = new Panel();
        panelContainer.ID = "panel" + persistControls.Count;

        panelContainer.Controls.Add(list);

        Button btnRemove = new Button();
        btnRemove.Click += new EventHandler(btnDelete_Click);
        btnRemove.Text = "Remove";
        btnRemove.CommandArgument = persistControls.Count.ToString();
        myPlaceholder.Controls.Add(panelContainer); // Pushes the Panel to the page.
        persistControls.Add(panelContainer);// Adds our Panel to the Control list

        myPlaceholder.Controls.Add(btnRemove); // Pushes our Button to the page.
        Session["persistControls"] = persistControls; // put it in the session
    }
    catch
    {
        throw;
    }
}

protected void btnDelete_Click(object sender, EventArgs e)
{
    try
    {
        int deleteThisOne = int.Parse(((Button)sender).CommandArgument);
        persistControls.Remove(persistControls[deleteThisOne]);
        Session["persistControls"] = persistControls;          
        Response.Redirect(Request.Url.ToString());
    }
    catch
    {
        throw;
    }
}

protected void list_SelectedIndexChanged(object sender, EventArgs e)
{
    throw new NotImplementedException();
}

//aspx File Snippets
<asp:Button ID="btnAdd" runat="server" Text="Add Control" onclick="btnAdd_Click" />
<asp:Button ID="btnClear" runat="server" Text="Reset" onclick="btnClear_Click"/>
<asp:PlaceHolder ID="myPlaceholder" runat="server"></asp:PlaceHolder>
受保护的无效页面加载(对象发送方,事件参数e)
{
//在询问的海报上显示这一点。
如果(!IsPostBack)
{
GetClustersFromDB(用户);
BindGrid();
BindState();
}
if(会话[“persistControls”]!=null)
{
persistControls=(列表)会话[“persistControls”];
整数计数=0;
foreach(持久化控件中的面板dynamicControl)
{
DropDownList list=新的DropDownList();
list.ID=“list”+计数;
list.SelectedIndexChanged+=新事件处理程序(list\u SelectedIndexChanged);
list.AutoPostBack=true;
添加(新的ListItem(“,”0”);
添加(新列表项(“标题”、“1”));
dynamicControl.ID=“panel”+计数;
按钮btnRemove=新按钮();
btnRemove.Click+=新建事件处理程序(btnDelete\u Click);
btnRemove.Text=“删除”;
btnRemove.CommandArgument=count.ToString();
myPlaceholder.Controls.Add(dynamicControl);
myPlaceholder.Controls.Add(btnRemove);
计数++;
}
}
}
受保护的无效btnAdd_单击(对象发送者,事件参数e)
{
尝试
{
DropDownList list=新的DropDownList();
list.SelectedIndexChanged+=新事件处理程序(list\u SelectedIndexChanged);
list.AutoPostBack=true;
添加(新的ListItem(“,”0”);
添加(新列表项(“标题”、“1”));
Panel panelContainer=新面板();
panelContainer.ID=“panel”+persistControls.Count;
panelContainer.Controls.Add(列表);
按钮btnRemove=新按钮();
btnRemove.Click+=新建事件处理程序(btnDelete\u Click);
btnRemove.Text=“删除”;
btnRemove.CommandArgument=persistControls.Count.ToString();
myPlaceholder.Controls.Add(panelContainer);//将面板推到页面上。
persistControls.Add(panelContainer);//将我们的面板添加到控件列表中
myPlaceholder.Controls.Add(btnRemove);//将我们的按钮按到页面上。
会话[“persistControls”]=persistControls;//将其放入会话中
}
抓住
{
投掷;
}
}
受保护的无效BTN删除\单击(对象发送者,事件参数e)
{
尝试
{
int deleteThisOne=int.Parse((按钮)sender.CommandArgument);
persistControls.Remove(persistControls[deleteThisOne]);
会话[“persistControls”]=persistControls;
Response.Redirect(Request.Url.ToString());
}
抓住
{
投掷;
}
}
受保护的无效列表\u SelectedIndexChanged(对象发送方,事件参数e)
{
抛出新的NotImplementedException();
}
//aspx文件片段

像这样维护控件真是一件痛苦的事。您可以尝试另一种方法:

  • 创建一个(小)类,封装要在每个面板中显示的数据
  • 在会话中维护这些对象的
    列表

  • 使用
    是必读的。

    我认为这行不通。如果在PageLoad事件中创建DropDownList,viewstate将永远不会绑定到它,也永远不会看到用户选择的选项


    您应该在NIT上创建控件,然后当回发发生时,ViewState数据将绑定到控件,您将能够访问它。

    列表\u SelectedIndexChanged处理程序方法在哪里?嗨,Alex,它与cs代码的其余部分..asp.cs文件位于同一位置。我在函数上设置了断点,但在调试过程中始终无法触发它。**在最初的帖子中添加了代码,但没有意识到我可以编辑。谢谢你,格雷厄姆!只是为了澄清。。。每个“行”都将根据左侧控件的选择进行填充。理想情况下,我将把每个面板的内容作为参数传递给存储过程,然后绑定其中的数据。在您看来,这是解决我的问题的更好的设计方法吗?好的,当您在“添加”单击上发回时,您可以检查控件的值,并基于这些值填充列表对象。希望这是有意义的,我不太确定我是否理解你的页面布局。这是一个很好的说法,我只是重新阅读了我发布的内容,听起来很奇怪。我们的想法是,我们有三个按钮(添加行、清除行和搜索)。当我们点击添加行,一个面板被创建包含一个DropDownList,从该DropDownList我会选择一个选项,然后创建另一个控件。。。最终为复杂的select语句提供UI组件。清除行只是清除我的控制会话。搜索将通过每个控件的事件处理来传递我在面板中填充的控件“行”中的信息。我之所以获得此答案,主要是因为您向我指出了优秀的资源,