You are currently browsing the category archive for the 'development' category.
So thanks to the iPhone 2.0 software release, I can now blog directly from my iPhone.
The photo below is of my oldest daughter and I walking on the beach at Camp Pendleton, CA over the fourth of July weekend.
Wow. So after making a new post to my blog on my iPhone, then seeing it on the computer, I must say, this little iPhone App is a must have!!
5 of 5 *’s
I made the most interesting discovery today at work! Par for the course, Microsoft has left little to be desired from the documentation on MasterPages and actually leveraging their fullest potential. Today, I believe I have stumbled upon a small sieve into the potential power MasterPages have.
First I want to explain a few details, an example of sorts in the form of a scenario:
Suppose you have a web project and on the main page you want to display multiple areas of content, not necessarily related to one another. Say you have a header, body and footer – each containing dynamic content pertinent to their own function. In ASP.NET 1.1, it would be easy to just create user controls and place a single line of code for each element in the code and include an @ directive for each user control. Or for an even older example, use includes in classic ASP. Now, ASP.NET 2.0 comes along and introduces MasterPages and ContentPlaceHolders! Such a simple and effective solution one would think!!
Because of the way our brains have wrapped around includes in classic ASP and user controls in 1.1, we think that somehow 2.0 renders from the MasterPage down to the pages themselves – thus rendering every page. But this doesn’t work. For if you were to actually try to add more than one ContentPlaceHolder into the MasterPage and render different .aspx pages within, you’d quickly discover that not all the ContentPlaceHolders render on the page when you browse out to them. *scratches head* Hmm… So, you’ll need to set each of the 3 ContentPlaceHolder’s in each rendered page (in this case, default.aspx) in the form of <asp:Content> tags. When I first saw this example, I thought – but that’s NOT what I wanted it to do! That’s not how I expected it to code out as. I figured the MasterPage should serve out this content. After all, it’s the MasterPage that has the ContentPlaceHolders! It just didn’t seem right to me.
Then it hit me: What actually happens is that the page renders from the bottom up: The page that is called, such as in “http://localhost/default.aspx”, default.aspx is called and rendered, rendering each of the <asp:Content> tags which have attributes telling us where in what MasterPage they should be rendered in. Then, the MasterPage that is attributed in the Page directive of default.aspx is called and rendered.
Basically, the page (default.aspx) could be nothing more than a “staging area” as we might call it in the military. It would tell the server what MasterPage it belongs to and it would tell the MasterPage what ContentPlaceHolders to render in it’s code. This is where 1.1 collides with 2.0:
MasterPage.Master has the following:
- cphHeader as ContentPlaceHolder control
- cphBody as ContentPlaceHolder control
- cphFooter as ContentPlaceHolder control
<body>
<form id="form1" runat="server">
<div>
<asp:contentplaceholder id="cphHeader" runat="server">
</asp:contentplaceholder>
<asp:contentplaceholder id="cphBody" runat="server">
</asp:contentplaceholder>
<asp:contentplaceholder id="cphFooter" runat="server">
</asp:contentplaceholder>
</div>
</form>
</body>
Default.aspx has the following:
- In the @Page directive, assign the MasterPage to which default.aspx belongs to
- Each of the <asp:Content> tags assigned to their respective ContentPlaceHolder
- To cut to the chase, the <asp:Content> tags have User Controls in them which helps you manage your code more fluidly
<%@ Page Language="C#" MasterPageFile="~/MasterPage.master" AutoEventWireup="true" CodeFile="Default.aspx.cs" Inherits="_Default" Title="Untitled Page" %>
<asp:Content ID="Content1" ContentPlaceHolderID="cphHeader" Runat="Server">
<ctrl:Header ID="ctrlHeader" runat="server" />
</asp:Content>
<asp:Content ID="Content2" ContentPlaceHolderID="cphBody" Runat="Server">
<ctrl:Body ID="ctrlBody" runat="server" />
</asp:Content>
<asp:Content ID="Content3" ContentPlaceHolderID="cphFooter" Runat="Server">
<ctrl:Footer ID="ctrlFooter" runat="server" />
</asp:Content>
web.config has the following:
- Look to <system.web><pages><controls> node and add the User Control tags for global use of the Controls
<system.web>
<pages>
<controls>
<add tagPrefix="ctrl" tagName="Header" src="~/Controls/ctrlHeader.ascx" />
<add tagPrefix="ctrl" tagName="Body" src="~/Controls/ctrlBody.ascx" />
<add tagPrefix="ctrl" tagName="Footer" src="~/Controls/ctrlFooter.ascx" />
<add tagPrefix="asp" namespace="System.Web.UI" assembly="System.Web.Extensions, Version=1.0.61025.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35"/>
<add namespace="AjaxControlToolkit" assembly="AjaxControlToolkit" tagPrefix="ajaxToolkit"/>
</controls>
</pages>
</system.web>
Then, each of the User Controls files have their own unique html which when rendered, is completed as one long string of code, just like with classic ASP’s Includes and ASP.NET 1.1’s User Controls.
<%@ Control Language="C#" AutoEventWireup="true" CodeFile="ctrlBody.ascx.cs" Inherits="Controls_ctrlBody" %>
<div>This is the Body in a UserControl.</div>
What’s really great about this approach is that you can still programmatically call the user controls based on condition or whatever all in your codebehind! In the default.aspx file, if I didn’t want to see one of the User Controls, I can simply hide it’s visibility. The possibilites are endless!
public partial class _Default : System.Web.UI.Page
{
protected void Page_Load(object sender, EventArgs e)
{
if (1 > 0)
ctrlBody.Visible = false;
}
}
Since 1 is always greater than 0 (duh!), the output would look like this:
Mathematicians don’t answer questions by working them out on paper the way schoolchildren are taught to. They do more in their heads: they try to understand a problem space well enough that they can walk around it the way you can walk around the memory of the house you grew up in. At its best programming is the same.
AAA has reported that the majority of people have taken this week off as a holiday. Unfortunately, I was only able to take off Wednesday – but blessing as it was, I was still able to take a day off this week! Not to mention that I telecommute tomorrow and Monday, so, even though I’m working at home, I’ll still be able to work in my PJ’s if I wanted to! LOL – I’m glad we don’t have teleconferencing at our office. What a scary thought, eh?











fresh comments