动态添加命令按钮到GridView

时间:2011-01-19 15:58:20

标签: c# asp.net

我在尝试向网格添加按钮时遇到问题。我的GridView首先在PageLoad事件中加载了数据。

然后我在每行的第一个单元格中获取数据,并创建一个链接到URL的按钮。要获取URL,我必须使用第一个单元格中的数据作为参数运行查询。我最初是在RowDataBound事件中执行此操作,但是对每一行执行该查询都会让它变得非常慢。

所以我决定添加一个按钮,只有在你点击按钮时才能检索URL。

这是我的GridView:

<asp:GridView ID="gvResults" runat="server"
    OnRowDataBound="gvResults_RowDataBound"
    OnRowCommand="gvResults_RowCommand">               
</asp:GridView>    

我的代码:

protected void gvResults_RowDataBound(object sender, GridViewRowEventArgs e)
{
    if (e.Row.DataItem != null)
    {
        LinkButton lb = new LinkButton();
        lb.CommandArgument = e.Row.Cells[0].Text;
        lb.CommandName = "NumClick";
        lb.Text = e.Row.Cells[0].Text;

        e.Row.Cells[0].Controls.Add((Control)lb);
    }
}


protected void gvResults_RowCommand(object sender, CommandEventArgs e)
{
    switch (e.CommandName.ToLower())
    {
        case "numclick":
            string url = GetUrl(e.CommandArgument.ToString());
            Response.Redirect(url);
            break;
        default:
            break;
    }
}

网格生成正常,按钮会添加到每行的网格中。但是当我点击它时,RowCommand事件不会触发,页面只会刷新。

有谁知道这是什么问题?

3 个答案:

答案 0 :(得分:3)

为什么要使用动态按钮?您可以轻松地将链接按钮直接放入gridview的标记中(只要您不介意使用模板字段),就不需要处理RowDataBound事件。

您的标记看起来如下所示:

<Columns>
    <asp:TemplateField HeaderText="SomeHeaderText">
            <ItemTemplate>
                <asp:LinkButton ID="lnkBtn" runat="server" CommandName="NumClick" CommandArgument= '<%# (string)Eval("dbValue") %>'  Text='<%# (string)Eval("dbValue") %>'></asp:LinkButton>
            </ItemTemplate>
        </asp:TemplateField>        
    <asp:BoundField></asp:BoundField>
    <asp:BoundField></asp:BoundField>
    <asp:BoundField></asp:BoundField>
</Columns>

向RowCommand事件添加断点,并确保可以命中断点。

问题可能出在其他地方。

另外,请确保您没有在回发上进行数据绑定。

答案 1 :(得分:1)

您的代码遇到了大麻烦。我很难解释你的大错是什么,但我可以很容易地告诉你如何解决。

问题是你在RowDataBound事件中生成一个新按钮,绝对是最糟糕的选择。该按钮被呈现,因为在页面呈现后该事件之后存在,但在数据绑定之前不存在。如果每次加载页面时绑定数据(即使在回发期间),按钮仍然会被渲染,因为您生成了一个新按钮。

但由于数据绑定之前按钮不存在,因此无法引发事件。您必须将标记中的按钮声明为GridView的模板,然后使用新的LinkButton()访问它,而不是使用e.Row.Cells[0].FindControl("buttonId")并设置其文本。然后,您必须设置其标记,以便激活自己的 Command事件(而不是RowCommand)并按照您的使用处理它(不要忘记设置{{ 1}}在数据绑定期间)

[编辑]我也犯了一个错误:数据绑定控件内部的控件在数据绑定之前也不会存在。但它们不是使用CommandArgument(通过数据绑定控制的私有方法)而是使用new Control()进行初始化。这是动态加载控件时必须修复的第一件事!!

答案 2 :(得分:0)

因为控件是在数据绑定上动态添加的,并且您必须为每个回发数据绑定gridview,所以每次“被点击”的控件都是不同的。事件不会触发,因为在它需要触发时它不存在,就像在页面的最后一次迭代中那样。

我注意到你没有任何逻辑确定按钮是否应该在那里,它总是进入单元格[0]。

您应该将此按钮放入TemplateItem中,以使其正确存在。如果您需要在代码隐藏中执行此操作,则可能更适合在RowCreated事件中执行此操作。