2008-09-18 50 views
9

我正在寫一個複合控件,它包含一個listview來顯示一個項目表。通常在Asp.NET中使用ListView時,我會在代碼轉發中定義模板。如何定義代碼中的列表視圖模板

<asp:ListView runat="server" ID="ArticleList"> 
    <LayoutTemplate> 
     <div class="ContentContainer"> 
      <div runat="server" id="itemPlaceholder" /> 
     </div> 
    </LayoutTemplate> 
    <ItemTemplate> 
     <div> 
      <div><%# Eval("Content") %></div> 
     </div> 
    </ItemTemplate> 
    </asp:ListView> 

我以爲這是類似:

ListView view = new ListView(); 
view.LayoutTemplate = ..... 
view.ItemTemplate = ..... 

// when do I call these? 
view.DataSource = myDataSource; 
view.DataBind(); 

更新: 我通過實現了Itemplate界面創建2個模板:

private class LayoutTemplate : ITemplate 
{ 
    public void InstantiateIn(Control container) 
    { 
     var outer = new HtmlGenericControl("div"); 
     var inner = new HtmlGenericControl("div") { ID = "itemPlaceholder" }; 
     table.Rows.Add(row); 

     container.Controls.Add(table); 
    } 
} 

private class ItemTemplate : ITemplate 
{ 
    public void InstantiateIn(Control container) 
    { 
     var inner = new HtmlGenericControl("div"); 

     container.Controls.Add(inner); 
    } 
} 

,我可以用它們添加:

dataList.LayoutTemplate = new LayoutTemplate(); 
dataList.ItemTemplate = new ItemTemplate(); 

但後來我卡住了,因爲container.DataItem爲null。

回答

9

關鍵是要訂閱在ItemTemplate的itemplaceholder的數據綁定事件。

完整的解決方案:

public class FibonacciControl : CompositeControl 
{ 
    public FibonacciControl() 
    { 
     // .... 
    } 

    protected override void CreateChildControls() 
    { 
     base.CreateChildControls(); 

     ListView view = new ListView(); 

     view.LayoutTemplate = new LayoutTemplate(); 
     view.ItemTemplate = new ItemTemplate(); 

     view.DataSource = FibonacciSequence(); 
     view.DataBind(); 

     this.Controls.Add(view); 
    } 

    private IEnumerable<int> FibonacciSequence() 
    { 

     int i1 = 0; 
     int i2 = 1; 

     for (int i = 0; i < Iterations; i++) 
     { 
      yield return i1 + i2; 
      int temp = i1 + i2; 
      i1 = i2; 
      i2 = temp; 
     } 
     yield break; 
    } 

    public int Iterations { get; set; } 

    private class LayoutTemplate : ITemplate 
    { 

     public void InstantiateIn(Control container) 
     { 
      var ol = new HtmlGenericControl("ol"); 
      var li = new HtmlGenericControl("li") { ID = "itemPlaceholder" }; 
      ol.Controls.Add(li); 

      container.Controls.Add(ol); 
     } 
    } 

    private class ItemTemplate : ITemplate 
    { 
     public void InstantiateIn(Control container) 
     { 
      var li = new HtmlGenericControl("li"); 

      li.DataBinding += DataBinding; 
      container.Controls.Add(li); 
     } 

     public void DataBinding(object sender, EventArgs e) 
     { 
      var container = (HtmlGenericControl)sender; 
      var dataItem = ((ListViewDataItem)container.NamingContainer).DataItem; 

      container.Controls.Add(new Literal(){Text = dataItem.ToString() }); 
     } 
    } 
} 
2

這個鏈接可以得到一些幫助嗎? Using Templated Controls Programmatically

在設計時生成模板(爲了將它們保存在aspx文件中)有點棘手,但DataBinding會自動工作。

+0

看起來可能。 – 2008-09-18 15:51:59

-1

設置像一個類:

public delegate void InstantiateTemplateDelegate(Control container); 

public class GenericTemplateImplementation : ITemplate 
{ 
    private InstantiateTemplateDelegate instantiateTemplate; 

    public void InstantiateIn(Control container) 
    { 
     this.instantiateTemplate(container); 
    } 

    public GenericTemplateImplementation(InstantiateTemplateDelegate instantiateTemplate) 
    { 
     this.instantiateTemplate = instantiateTemplate; 
    } 
} 

然後執行以下操作:

view.LayoutTemplate = new GenericTemplateImplementation(p => 
       { 
        p.Controls.Add(new Label { Text = "Foo" }); 
       }); 
0

大廈Sonteks這裏的例子是,創建一個包含然後使用數據綁定綁定元素模板的例子。

public partial class View : PortalModuleBase 
{ 
    protected void Page_Load(object sender, EventArgs e) 
    { 

    } 

    #region MasterListView_ItemDataBound 
    public void MasterListView_ItemDataBound(object sender, ListViewItemEventArgs e) 
    { 
     ListViewItem objListViewItem = (ListViewItem)e.Item; 
     ListViewDataItem objListViewDataItem = objListViewItem as ListViewDataItem; 

     if (objListViewDataItem != null) 
     { 
      Tab objTab = (Tab)objListViewDataItem.DataItem; 
      IEnumerable<Tab> Tabs = CustomData(objTab.TabID); 

      Label TabIDLabel = (Label)objListViewItem.FindControl("TabIDLabel"); 
      Label TabNameLabel = (Label)objListViewItem.FindControl("TabNameLabel"); 

      TabIDLabel.Text = objTab.TabID.ToString(); 
      TabNameLabel.Text = objTab.TabName; 

      AddListView(objTab.TabName, objListViewItem, Tabs); 
     } 
    } 
    #endregion 

    #region CustomData 
    static IEnumerable<Tab> CustomData(int? ParentID) 
    { 
     TabAdminDataContext objTabAdminDataContext = new TabAdminDataContext(); 

     var myCustomData = from Tabs in objTabAdminDataContext.Tabs 
          where Tabs.ParentId == ParentID 
          select Tabs; 

     return myCustomData.AsEnumerable(); 
    } 
    #endregion 

    #region AddListView 
    private void AddListView(string CurrentTabName, Control container, IEnumerable<Tab> ChildTabs) 
    { 
     // The Tab has Children so add a ListView 
     if (ChildTabs.Count() > 0) 
     { 
      ListView ChildListView = new ListView(); 
      ChildListView.ID = "ChildListView"; 
      ChildListView.ItemCommand += ListView_ItemCommand; 
      ChildListView.EnableViewState = true; 
      ChildListView.LayoutTemplate = new MyLayoutTemplate(); 
      ChildListView.ItemTemplate = new MyItemTemplate(); 
      ChildListView.DataSource = ChildTabs; 
      ChildListView.DataBind(); 

      // Put the ListView in a Panel 
      var oTR = new HtmlGenericControl("tr") { ID = "ChildListViewTR" }; 
      var oTD = new HtmlGenericControl("td") { ID = "ChildListViewTD" }; 

      Panel objPanel = new Panel(); 
      objPanel.ID = "ListViewPanel"; 
      objPanel.ToolTip = CurrentTabName; 
      objPanel.Controls.Add(ChildListView); 

      oTD.Controls.Add(objPanel); 
      oTR.Controls.Add(oTD); 
      container.Controls.Add(oTR); 
     } 
    } 
    #endregion 

    #region ListView_ItemCommand 
    protected void ListView_ItemCommand(object sender, ListViewCommandEventArgs e) 
    { 
     LinkButton objButton = (LinkButton)sender; 
     Label1.Text = objButton.Text; 
     MasterListView.DataBind(); 
    } 
    #endregion 

    #region MyLayoutTemplate 
    public class MyLayoutTemplate : ITemplate 
    { 
     public void InstantiateIn(Control container) 
     { 
      var oTR = new HtmlGenericControl("tr") { ID = "itemPlaceholder" }; 
      container.Controls.Add(oTR); 
     } 
    } 
    #endregion 

    #region ItemTemplate 
    public class MyItemTemplate : ITemplate 
    { 
     public void InstantiateIn(Control container) 
     { 
      var oTR = new HtmlGenericControl("tr"); 

      var oTD1 = new HtmlGenericControl("td"); 
      LinkButton TabIDLinkButton = new LinkButton(); 
      TabIDLinkButton.ID = "TabIDLinkButton"; 
      oTD1.Controls.Add(TabIDLinkButton); 
      oTR.Controls.Add(oTD1); 

      var oTD2 = new HtmlGenericControl("td"); 
      Label TabNameLabel = new Label(); 
      TabNameLabel.ID = "TabNameLabel"; 
      oTD2.Controls.Add(TabNameLabel); 
      oTR.Controls.Add(oTD2); 

      oTR.DataBinding += DataBinding; 
      container.Controls.Add(oTR); 
     } 

     public void DataBinding(object sender, EventArgs e) 
     { 
      var container = (HtmlGenericControl)sender; 
      var dataItem = ((ListViewDataItem)container.NamingContainer).DataItem; 
      Tab objTab = (Tab)dataItem; 

      LinkButton TabIDLinkButton = (LinkButton)container.FindControl("TabIDLinkButton"); 
      Label TabNameLabel = (Label)container.FindControl("TabNameLabel"); 

      TabIDLinkButton.Text = "+" + objTab.TabID.ToString(); 
      TabNameLabel.Text = objTab.TabName; 

      IEnumerable<Tab> ChildTabs = View.CustomData(objTab.TabID); 

      View objView = new View(); 
      objView.AddListView(objTab.TabName, container, ChildTabs); 
     } 

    } 
    #endregion 

}