Dynamically add HyperLink in GridView

2020-04-18 05:46发布

问题:

I have two types of code: 1st:

               <Columns>
                <asp:TemplateField>
                    <ItemTemplate>
                        <asp:HyperLink runat="server" Text="Скачать объект" NavigateUrl='<%#"objects/" + Eval("Идентификатор") %>'></asp:HyperLink>
                    </ItemTemplate>    
                </asp:TemplateField>
               </Columns>

works normal. But TemplateField showed everytime.

2nd

            TemplateField templField = new TemplateField();
            HyperLink hypLink = new HyperLink();
            hypLink.NavigateUrl = "<%#\"objects/\" + Eval(\"Идентификатор\") %>";
            hypLink.Text = "Скачать объект";
            templField.InsertItemTemplate = (ITemplate)hypLink;
            tableResults.Columns.Add(templField);

dosn't work with error: Unable to cast object of type 'System.Web.UI.WebControls.HyperLink' to type 'System.Web.UI.ITemplate'. Why in 1st time HyperLink added, in 2nd time didn't?

回答1:

This might help to get started:

protected void Page_Load(object sender, EventArgs e)
{
    if (!IsPostBack)
    { 
        var hyperlinkField = new TemplateField();
        hyperlinkField.ItemTemplate = new HyperlinkColumn();
        tableResults.Columns.Add(linkField);
    }
}


class HyperlinkColumn : ITemplate
{
    public void InstantiateIn(System.Web.UI.Control container)
    {
        HyperLink hypLink = new HyperLink()
        container.Controls.Add(link);
    }
}

Note that you cannot set the NavigateUrl or Text from within InstantiateIn. There you only create the control. You would databind it in RowDataBound according to the row's DataItem.

But:

Although you can dynamically add fields to a data-bound control, it is strongly recommended that fields be statically declared and then shown or hidden, as appropriate. Statically declaring all your fields reduces the size of the view state for the parent data-bound control.

http://msdn.microsoft.com/en-us/library/system.web.ui.webcontrols.templatefield.templatefield.aspx



回答2:

templField.InsertItemTemplate expects an ITemplate object where as hyperlink does not extends this interface.

In your first declarative example, hyperlink is a host of ItemTemplate which extend this interface ITemplate.