2013-06-07 2 views
0

Внутри моего приложения ASP.NET все страницы моего веб-контента получены из базового класса, который является производным от System.Web.UI.Page. Внутри этого базового класса мне нужно получить некоторые элементы управления, найденные в одном производном классе, SamplePage.aspx: BaseClass.cs. Это я добавить C# код ниже на странице нагрузки внутри SamplePage.aspx он находит ContentPlaceHolderControl,Доступ к элементам управления дочерними страницами с базовой страницы

<asp:ContentPlaceHolder ID="ContentPlaceHolder1" runat="server"> 
</asp:ContentPlaceHolder> /* defined in the master page */ 

/* inside SamplePage.aspx */ 
<ajaxtoolkit:tabcontainer runat="server" id="tabsmain" height="405px" Width="625px"> 
ContentPlaceHolder cph = (ContentPlaceHolder)this.Master.FindControl("ContentPlaceHolder1"); 
AjaxControlToolkit.TabContainer container = (AjaxControlToolkit.TabContainer)cph.FindControl("tabsmain"); 

а если добавить его в базовом классе я получаю эту ошибку:

Content controls have to be top-level controls in a content page or a nested master page that references a master page.

Есть Я могу получить ContentPlaceHolder внутри моего базового класса тоже? И как я могу получить к нему доступ?

+0

Там нет необходимости для тегов заголовков. Пожалуйста, прочитайте http://meta.stackexchange.com/q/19190/147072 для получения дополнительной информации. – Patrick

ответ

0

Вот полный пример кода, как вы можете получить доступ к ContentPlaceHolder:

Первый мастер-код (Site1.master):

<%@ Master Language="C#" AutoEventWireup="true" CodeBehind="Site1.master.cs" Inherits="WebTesterInherit.Site1" %> 

<!DOCTYPE html> 

<html xmlns="http://www.w3.org/1999/xhtml"> 
<head runat="server"> 
    <title></title> 
    <asp:ContentPlaceHolder ID="head" runat="server"> 
    </asp:ContentPlaceHolder> 
</head> 
<body> 
    <form id="form1" runat="server"> 
    <div> 
     <asp:ContentPlaceHolder ID="ContentPlaceHolder1" runat="server"> 

     </asp:ContentPlaceHolder> 
    </div> 
    </form> 
</body> 
</html> 

Теперь пользовательский класс, который наследует от страницы:

public class MyPage: System.Web.UI.Page 
{ 

    public System.Web.UI.WebControls.ContentPlaceHolder GetMyContentPlaceHolder() 
    { 
     System.Web.UI.WebControls.ContentPlaceHolder holder = null; 
     Site1 site = this.Master as Site1; 
     if (site != null) 
     { 
      holder = site.FindControl("ContentPlaceHolder1") as System.Web.UI.WebControls.ContentPlaceHolder; 
     } 
     return holder; 
    } 
} 

И, наконец, страница, которая наследуется от MyPage (Default.aspx):

<%@ Page Title="" Language="C#" MasterPageFile="~/Site1.Master" AutoEventWireup="true" CodeBehind="Default.aspx.cs" Inherits="WebTesterInherit.Default" %> 
<asp:Content ID="Content1" ContentPlaceHolderID="head" runat="server"> 
</asp:Content> 
<asp:Content ID="Content2" ContentPlaceHolderID="ContentPlaceHolder1" runat="server"> 
    <asp:Button ID="btnTest" runat="server" Text="Test" OnClick="btnTest_Click"/><br /> 
    <asp:Label ID="lblMessage" runat="server" Text=""></asp:Label> 
</asp:Content> 

Код для Default.aspx:

public partial class Default : MyPage 
{ 
    protected void Page_Load(object sender, EventArgs e) 
    { 

    } 

    protected void btnTest_Click(object sender, EventArgs e) 
    { 
     try 
     { 
      System.Web.UI.WebControls.ContentPlaceHolder holder = base.GetMyContentPlaceHolder(); 
      lblMessage.Text = string.Format("Holder contains {0} control(s).", holder.Controls.Count); 
     } 
     catch (Exception ex) 
     { 
      lblMessage.Text = string.Format("Error: {0}", ex.Message); 
     } 
    } 
} 
0

Я проверил, и вы можете найти управление вложенным в ContentPlaceHolder от базового класса OnLoad метода.

Конечно, это может быть сделано ... но помнить, что некоторые страницы могут иметь различные управления в ихнем CPH. Вы уверены, что находитесь в контексте страницы, на которой есть tabsmain?

Я думаю, что если вам нужно делать такие вещи, у вас есть проблема с дизайном. Смешение главной страницы и вниз FindControl (базовый класс -> производный класс) просто не кажется правильным.

0

Универсальный "поиск по идентификатору и типа" метод:

protected T GetControlOfType<T>(Control root, string id) where T : Control { 
    var stack = new Stack<Control>(); 
    stack.Push(root); 
    while (stack.Count > 0) { 
     var control = stack.Pop(); 
     var typedControl = control as T; 
     if (typedControl != null && string.Compare(id, typedControl.ID, StringComparison.Ordinal) == 0) { 
     return typedControl; 
     } 
     foreach (Control child in control.Controls) { 
     stack.Push(child); 
     } 
    } 
    return default(T); 
    } 

Использование:

var control = GetControlOfType<MyControl>(Page, "MyControlServerID"); 
Смежные вопросы