2009-03-04 10 views
2

LabelとTextBoxを含む単純化されたコンポジットコントロールにテンプレートを追加しようとしています。私は、テキストボックスとラベルのプロパティを持つtemplateContainerクラスを持っているASP.NETテンプレート複合コントロールを使用するにはどうすればよいですか?

<test:FormItem ID="fi" runat="server" Title="MyTitle" Text="My Text!"> 
    <TestTemplate> 
     <i> 
      <%# Container.Title) %></i> 
     <br /> 
     <%# Container.Text %> 
    </TestTemplate> 
</test:FormItem> 

:私はこのような何かを見て、私のマークをアップします。私はCreateChildControlsの(から呼び出されているCreateControlHierarchy()メソッドを持ってメインのFormItemクラスで

public class TemplateContainer : WebControl, INamingContainer 
{ 

    public TextBox Text { get { return m_item.Text; } } 
    public Label Title { get { return m_item.Title; } } 

    private FormItem m_item; 

    public TemplateContainer(FormItem item) 
    { 
     m_item = item; 
    } 

} 

):私が欲しいもの

protected virtual void CreateControlHierarchy() 
    { 

     m_itemTemplateContainer = new TemplateContainer(this); 
     TestTemplate.InstantiateIn(m_itemTemplateContainer); 

     Controls.Add(m_itemTemplateContainer); 

    } 

は、実際のコントロールをレンダリングするテンプレートです。代わりに、コントロールのToString()を呼び出して、System.Web.UI.WebControls.LabelとSystem.Web.UI.WebControls.TextBoxを表示しています。テンプレートをToString()を呼び出すのではなく、そのコレクションにコントロールを追加する方法はありますか?

注:テキストボックスとラベルを、同じことを行うコンテナのコントロールコレクションに追加しようとしました。

答えて

1

だから私はいくつかのことを試して、OKの解決策を考え出しました。

最初に、データバインディング式でメソッドを使用して、コンテナのControlコレクション内でテキストボックスまたはラベルがどこに移動するかを追跡しようとしました。ただし、CompiledTemplateBuilder(.Net内部ではマークアップで指定されたITテンプレート用に内部的に構築されています)は、両方のバインディング式の前と後にすべてのマークアップを1つのDataBoundLiteralコントロールに入れ、メソッドの呼び出し時にControlコレクションが既に構築されています。

複合コントロール内のコントロールのプレースホルダーとして機能する新しいWebControlを作成することができました。これには1つのプロパティControlがあり、設定されると、コントロールコレクションにコントロールが追加されます。

public class FormItemPlaceHolder : WebControl, INamingContainer 
{ 
    public WebControl Control 
    { 
     get 
     { 
      if(Controls.Count == 0) 
       return null; 
      return Controls[0] as WebControl; 
     } 
     set 
     { 
      if (Controls.Count != 0) 
       Controls.Clear(); 
      Controls.Add(value); 
     } 
    } 

} 

次に、このタイプのコントロールを作成し、そのコントロールのプロパティをコンテナの正しいプロパティにバインドします。

<test:FormItem ID="fi" runat="server" Title="MyTitle" Text="My Text!"> 
    <TestTemplate> 
     <i> 
     <test:FormItemPlaceHolder ID="ph" runat="server" 
      Control='<%# Container.Title %>' /> 
     </i> 
     <br /> 
     <test:FormItemPlaceHolder ID="ph2" runat="server" 
      Control='<%# Container.Text %>' /> 
    </TestTemplate> 
</test:FormItem> 

誰かがより良い解決策を持っていますか?

0

コンテナはコントロールを定義するものではなく、データのみを定義する必要があります。

データの実際のコントロールを定義し、その値をコンテナから割り当てる必要があります。

など。

public class TemplateContainer : UserControl 
{ 
    public string Text { get { return m_text; } } 
    public string Title { get { return m_title; } } 

    private string m_text; 
    private string m_title; 
    private FormItem m_item; 

    public TemplateContainer(FormItem item) 
    { 
     m_item = item; 
    } 

} 

とマークアップで:

<test:FormItem ID="fi" runat="server" Title="MyTitle" Text="My Text!"> 
     <TestTemplate> 
      <i><asp:Label runat="server" Text='<%# Container.Title) %>' /></i> 
      <br /> 
      <asp:TextBox runat="server" Text='<%# Container.Text %>' /> 
    </TestTemplate> 
</test:FormItem> 

あなたは、なぜあなたがテンプレートを使用している、マークアップに追加するコントロールを必要としない、複合コントロールを作成しようとしている場合は?それがスタイリングのためのものであれば、独自のスタイルオブジェクトを作成する方が効果的でしょうか?

+0

コンポジットコントロール(コントロールのコントロール)を作成し、ユーザーがコントロールの周りにマークアップを追加できるようにします。注:私はUserControlを作成したくありません。私はコンポジットコントロールのコントロール用のカスタムロジックを持っており、アプリケーション間で使用したいと思っています。 – rmw

+0

ユーザーは、実際のコントロール自体を移動できなければならないのでしょうか、それともその前後にマークアップを置くことができなければなりませんか? – codemonkeh

関連する問題