The link below shows a listview composite control in its most basic form however I can't seem to extend this to what I'm trying to do.
How to define listview templates in code
My listview has 1 tablerow with 2 fields. The first field contains 1 element whilst the second field contains 2 elements as shown below.
<asp:ListView ID="lstArticle" runat="server">
<LayoutTemplate>
<table id="itemPlaceholder" runat="server">
</table>
</LayoutTemplate>
<ItemTemplate>
<div class="ctrlArticleList_rptStandardItem">
<table width="100%">
<tr>
<td valign="top" class="ctrlArticleList_firstColumnWidth">
<a href="<%# GetURL(Container.DataItem) %>">
<%# GetImage(Container.DataItem)%>
</a>
</td>
<td valign="top">
<span class="ctrlArticleList_title">
<a href="<%# GetURL(Container.DataItem) %>">
<%# DataBinder.Eval(Container.DataItem, "Title") %>
</a>
</span>
<span class="ctrlArticleList_date">
<%# convertToShortDate(DataBinder.Eval(Container.DataItem, "ActiveDate"))%>
</span>
<div class="ctrlArticleList_standFirst">
<%# DataBinder.Eval(Container.DataItem, "StandFirst")%>
</div>
</td>
</tr>
</table>
</div>
</ItemTemplate>
So to convert this I have to use the InstantiateIn method of the ITemplate for the layouttemplate and the ItemTemplate. Data is bound to the itemtemplate using the DataBinding event.
My question at the moment is how do I setup the ItemTemplate class and bind the values from the above ListView ItemTemplate. This is what I've managed so far:
private class LayoutTemplate : ITemplate
{
public void InstantiateIn(Control container)
{
var table = new HtmlGenericControl("table") { ID = "itemPlaceholder" };
container.Controls.Add(table);
}
}
private class ItemTemplate : ITemplate
{
public void InstantiateIn(Control container)
{
var tableRow = new HtmlGenericControl("tr");
//first field in row
var tableFieldImage = new HtmlGenericControl("td");
var imageLink = new HtmlGenericControl("a");
imageLink.ID = "imageLink";
tableRow.Controls.Add(imageLink);
// second field in row
var tableFieldTitle = new HtmlGenericControl("td");
var title = new HtmlGenericControl("a");
tableFieldTitle.Controls.Add(title);
tableRow.Controls.Add(tableFieldTitle);
//Bind the data with the controls
tableRow.DataBinding += BindData;
//add the controls to the container
container.Controls.Add(tableRow);
}
public void BindData(object sender, EventArgs e)
{
var container = (HtmlGenericControl)sender;
var dataItem = ((ListViewDataItem)container.NamingContainer).DataItem;
container.Controls.Add(new Literal() { Text = dataItem.ToString() });
}
One of the functions in the code behind used in the ListView just for an example is:
public string GetURL(object objArticle)
{
ArticleItem arti开发者_高级运维cleItem = (ArticleItem)objArticle;
Article article = new Article(Guid.Empty, articleItem.ContentVersionID);
return GetArticleURL(article);
}
Summary
What do I need to do to convert the following into a composite control:
GetURL(Container.DataItem) GetImage(Container.DataItem)
GetURL(Container.DataItem) DataBinder.Eval(Container.DataItem, "Title")
convertToShortDate(DataBinder.Eval(Container.DataItem, "ActiveDate"))
DataBinder.Eval(Container.DataItem, "StandFirst")
In your control, you don't need to generate the <%# binding; rather, you can just get the bound URL on the server and assign it to a link, create a HyperLink and do:
var link = new HyperLink();
link.NavigateUrl = GetUrl(dataItem);
link.ImageUrl = GetImage(dataItem);
Where the dataItem is the data item for the specific row, which you get within the item template binddata method, right?
Am I off base?
HTH.
精彩评论