Access a content control in C# when using Master Pages
Asked Answered
C

5

6

Good day everyone,

I am building a page in ASP.NET, and using Master Pages in the process.

I have a Content Place Holder name "cphBody" in my Master Page, which will contain the body of each Page for which that Master Page is the Master Page.

In the ASP.NET Web page, I have a Content tag (referencing "cphBody") which also contains some controls (buttons, Infragistics controls, etc.), and I want to access these controls in the CodeBehind file. However, I can't do that directly (this.myControl ...), since they are nested in the Content tag.

I found a workaround with the FindControl method.

ContentPlaceHolder contentPlaceHolder = (ContentPlaceHolder) Master.FindControl("cphBody");
ControlType myControl = (ControlType) contentPlaceHolder.FindControl("ControlName");

That works just fine. However, I am suspecting that it's not a very good design. Do you guys know a more elegant way to do so?

Thank you!

Guillaume Gervais.

Creedon answered 29/6, 2009 at 20:44 Comment(3)
Are you trying to access the controls from the content page's codebehind, or the master page's code behind?Ludewig
The Content page's CodeBehind.Creedon
That's odd. You should be able to directly access your controls from your content page's code-behind, unless they're being dynamically created and added.Maul
O
4

Rick Strahl has a good explanation (and sample code) here - http://www.west-wind.com/Weblog/posts/5127.aspx

Overstreet answered 29/6, 2009 at 21:2 Comment(2)
Thank you! That's basically what I did, so it validates my method for me!Creedon
I really dislike FindControl it's normally only needed when you can't expose a strong typed property and you need to dig through the pre-rendered output.Mow
M
7

I try and avoid FindControl unless there is no alternative, and there's usually a neater way.

How about including the path to your master page at the top of your child page

<%@ MasterType VirtualPath="~/MasterPages/PublicUI.Master" %>

Which will allow you to directly call code from your master page code behind.

Then from your master page code behind you could make a property return your control, or make a method on the master page get your control etc.

public Label SomethingLabel
{
    get { return lblSomething; }
}
//or
public string SomethingText
{
    get { return lblSomething.Text; }
    set { lblSomething.Text = value; }
}

Refers to a label on the master page

<asp:Label ID="lblSomething" runat="server" />

Usage:

Master.SomethingLabel.Text = "some text";
//or
Master.SomethingText = "some text";
Mow answered 30/6, 2009 at 2:44 Comment(2)
What about the other way around? I have a GridView in my content page and I want to be able to update that from my MasterPage.Drypoint
I would raise an event with the event data you need from the master page and subscribe to it with your page. Master.SomeEvent += SomeHandler;Mow
O
4

Rick Strahl has a good explanation (and sample code) here - http://www.west-wind.com/Weblog/posts/5127.aspx

Overstreet answered 29/6, 2009 at 21:2 Comment(2)
Thank you! That's basically what I did, so it validates my method for me!Creedon
I really dislike FindControl it's normally only needed when you can't expose a strong typed property and you need to dig through the pre-rendered output.Mow
S
3

Nothing to do different. Just write this code on child page to access the master page label control.

Label lblMessage = new Label();
lblMessage = (Label)Master.FindControl("lblTest");
lblMessage.Text = DropDownList1.SelectedItem.Text;
Spinode answered 6/7, 2012 at 9:32 Comment(0)
U
1

I use this code for acess to files recursively:

    /// <summary>
    /// Recursively iterate through the controls collection to find the child controls of the given control
    /// including controls inside child controls. Return all the IDs of controls of the given type 
    /// </summary>
    /// <param name="control"></param>
    /// <param name="controlType"></param>
    /// <returns></returns>
    public static List<string> GetChildControlsId(Control control, Type controlType)
    {
        List<string> FoundControlsIds = new List<string>();
        GetChildControlsIdRecursive(FoundControlsIds, control, controlType);

        // return the result as a generic list of Controls
        return FoundControlsIds;
    }

    public static List<string> GetChildControlsIdRecursive(List<string> foundControlsIds, Control control, Type controlType)
    {
        foreach (Control c in control.Controls)
        {
            if (controlType == null || controlType.IsAssignableFrom(c.GetType()))
            {
                // check if the control is already in the collection
                String FoundControl = foundControlsIds.Find(delegate(string ctrlId) { return ctrlId == c.ID; });

                if (String.IsNullOrEmpty(FoundControl))
                {
                    // add this control and all its nested controls
                    foundControlsIds.Add(c.ID);
                }
            }

            if (c.HasControls())
            {
                GetChildControlsIdRecursive(foundControlsIds, c, controlType);
            }
        }
Ulphiah answered 29/6, 2009 at 20:59 Comment(0)
S
1

Hi just thought i'd share my solution, found this works for accessing a 'Control' that is inside an < asp:Panel> which is on a 'ContentPage', but from C# code-behind of the 'MasterPage'. Hope it helps some.

  1. add an < asp:Panel> with an ID="PanelWithLabel" and runat="server" to your ContentPage.

  2. inside the Panel, add an < asp:Label> control with ID="MyLabel".

  3. write (or copy / paste the below) a function in your MasterPage Code-behind as follows: (this accesses the label control, inside the Panel, which are both on the ContentPage, from the Master page code-behind and changes its text to be that of a TextBox on the Master page :)

    protected void onButton1_click(object sender, EventArgs e)
    {
    // find a Panel on Content Page and access its controls (Labels, TextBoxes, etc.) from my master page code behind //
    System.Web.UI.WebControls.Panel pnl1;
    pnl1 = (System.Web.UI.WebControls.Panel)MainContent.FindControl("PanelWithLabel");
    if (pnl1 != null)
     {
        System.Web.UI.WebControls.Label lbl = (System.Web.UI.WebControls.Label)pnl1.FindControl("MyLabel");
        lbl.Text = MyMasterPageTextBox.Text;
     }
    }
    
Spalla answered 7/11, 2013 at 21:51 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.