Using VS 2008, I have a Repeater control:
Even better: this subclass adds an EmptyDataTemplate property. In your markup, put in an element just as you would an element. By default this will hide the header and footer if there's no data; you can change this with the HeaderVisibleWhenEmpty and FooterVisibleWhenEmpty properties in markup.
public class RepeaterWithEmptyDataTemplate : Repeater
{
public virtual ITemplate EmptyDataTemplate { get; set; }
protected virtual bool DefaultHeaderVisibleWhenEmpty
{
get { return false; }
}
protected virtual bool DefaultFooterVisibleWhenEmpty
{
get { return false; }
}
public bool HeaderVisibleWhenEmpty
{
get { return ViewState["hve"] == null ? DefaultHeaderVisibleWhenEmpty : (bool) ViewState["hve"]; }
set { ViewState["hve"] = value; }
}
public bool FooterVisibleWhenEmpty
{
get { return ViewState["fve"] == null ? DefaultFooterVisibleWhenEmpty : (bool) ViewState["fve"]; }
set { ViewState["fve"] = value; }
}
protected override void OnDataBinding(EventArgs e)
{
base.OnDataBinding(e);
if (Items.Count == 0 && EmptyDataTemplate != null)
{
var emptyPlaceHolder = new PlaceHolder {ID = "empty", Visible = true};
EmptyDataTemplate.InstantiateIn(emptyPlaceHolder);
//figure out where to put placeholder
RepeaterItem footer =
Controls.OfType().FirstOrDefault(i => i.ItemType == ListItemType.Footer);
if (footer == null)
{
//add to end if no footer
Controls.Add(emptyPlaceHolder);
}
else
{
Controls.AddAt(Controls.IndexOf(footer), emptyPlaceHolder);
}
//hide header and footer according to properties.
foreach (RepeaterItem x in Controls.OfType())
{
switch (x.ItemType)
{
case ListItemType.Header:
x.Visible = HeaderVisibleWhenEmpty;
break;
case ListItemType.Footer:
x.Visible = FooterVisibleWhenEmpty;
break;
}
}
}
}
}
Sample in markup:
blah blah blah
Hey, no data!
Please note that the DataBind method must be called, or the emptydatatemplate won't be displayed.