ASP.NET模板化用户控件“Container”关键字

时间:2011-02-01 02:05:37

标签: asp.net user-controls

我正在使用模板化用户控件。在控件的最终标记中, Container 关键字正在访问数据。我正在自由地使用“关键字”这个词,因为我不明白这是一个关键字,还是容器词的来源。以下是我的书中的一个例子。

//Address User Control markup
<%@ Control Language="C#" AutoEventWireup="true"
CodeFile="AddressUcTemplated.ascx.cs" Inherits="AddressUcTemplated" %>
<asp:PlaceHolder runat="server"
ID="PlaceHolderAddressTemplate">
</asp:PlaceHolder>

-

//Address User Control code-behind
public partial class AddressUcTemplated :
System.Web.UI.UserControl
{
protected void Page_Init(object sender, EventArgs e)
{
//clear the controls from the placeholder
PlaceHolderAddressTemplate.Controls.Clear();
if (LayoutTemplate == null)
{
PlaceHolderAddressTemplate.Controls.Add(
new LiteralControl("No template defined."));
}
else
{
AddressUcContainer container = new
AddressUcContainer(this.Address);
this.LayoutTemplate.InstantiateIn(container);
//add the controls to the placeholder
PlaceHolderAddressTemplate.Controls.Add(container);
}
}
[PersistenceMode(PersistenceMode.InnerProperty)]
[TemplateContainer(typeof(AddressUcContainer))]
public ITemplate LayoutTemplate { get; set; }
public Address Address { get; set; }
}

-

//Naming Container Class
    public class AddressUcContainer : Control, INamingContainer
    {
    public AddressUcContainer(Address address)
    {
    this.Address = address;
    }
    public Address Address { get; set; }
    }

-

     //Page using the user control; the Container keyword is confusing me in the below //statement
...
<%@ Register src="AddressUcTemplated.ascx" tagname="AddressUcTemplated"
tagprefix="uc1" %>
        <uc1:AddressUcTemplated ID="AddressUcTemplated1"
        runat="server" AddressType="Home">
        <LayoutTemplate>
        <h1>Edit Home Address</h1>
        <table>
        <tr>
        <td>Address Line 1:</td>
        <td>
        <asp:TextBox ID="TextBoxAddress" runat="server"
        Text="<%#Container.Address.AddressLine1%>"></asp:TextBox>
        ...

1 个答案:

答案 0 :(得分:0)

我的示例代码如下:

<asp:Repeater runat="server">
    <ItemTemplate><%# Container.DataItem %></ItemTemplate>
</asp:Repeater>

Intellisense声明Container是类型为RepeaterItem字段/变量。变量部分告诉我这是一些特殊的解析,因为它很可能是一个属性,如果它是公共的东西。

无论如何,我的代码被解析为以下数据绑定代码:

public void __DataBind__control4(object sender, EventArgs e) {
    var target = (DataBoundLiteralControl)sender;
    var Container = (RepeaterItem)target.BindingContainer;
    target.SetDataBoundString(0, Convert.ToString(Container.DataItem, CultureInfo.CurrentCulture));
}

<%# ... %>是一个DataBoundLiteralControl,Container是暴露给intellisense的变量。这也表明有一个target变量,显示在intellisense中,但编译没有任何问题。请注意,这也允许您访问生成的类中的所有私有内容,例如__fileDependencies

<%# target %>有效,而<%# dummy %>没有。在它的同时,<%# __DataBind__control4(null, null) %>创建了两个编译错误,1)“'System.Convert.ToString(object,System.IFormatProvider)'的最佳重载方法匹配'有一些无效的参数”和2)“参数1:无法从'void'转换为'object'“。

这看起来像<%# ... %>放置在Convert.ToString(..., CultureInfo.CurrentCulture)之间的任何内容的简单情况。它可能更高级,涉及不同的ControlBuilders,TemplateParsers和一盎司魔法,但我认为我的抽象运作得很好,可以理解这一点。