Understanding the Layout.master File

The layout.Master file is an ASP.NET MasterPage and is the template for all pages in the content management system. Any markup that needs to be on every page in the site should be in the layout.Master file. The layout.Master also provides the pockets where content features are loaded. The layout.Master file in the included skins inherits from the mojoPortal layout class which keeps track of what content is on the page and facilitates automatic adjustment from 1 to 3 columns for  the main layout. For more details see How The Main Column Layout Works.

Inside the layout.Master file there are some required tags that are used to render content from the database and a few optional mojoPortal specific tags that can be used, but other than that, you can add any html markup that you want to appear on every page. You can position the required tags within the layout.Master any way you wish. However most of the style and layout is really determined by the CSS. You will find there are very few differences among the layout.Master files for included skins.

If you are new to ASP.NET and are confused about what all those non html tags are in layout.master, this forum thread should help.

Required elements of a mojoPortal layout.Master file

The site cannot function without these elements. In addition to these, the skin must also have the standard required html elements html head (which should have id="Head1" runat="server"), and body elements with both opening and closing tags. It is also highly advisable to have a DOCTYPE element. Here is a layout.Master file with the bare minimum required elements.

<%@ Master Language="C#" AutoEventWireup="true" CodeBehind="~/App_MasterPages/layout.Master.cs" Inherits="mojoPortal.Web.layout" %>
<!DOCTYPE html>
<html>
	<head id="Head1" runat="server">
		<title></title>
	</head>
	<body class="pagebody">
		<form id="frmMain" runat="server">
			<asp:SiteMapDataSource ID="SiteMapData" runat="server" ShowStartingNode="false" />
			<asp:SiteMapDataSource ID="ChildPageSiteMapData" runat="server" ShowStartingNode="false" />
			<asp:ScriptManager ID="ScriptManager1" EnablePageMethods="true" runat="server" />

			<portal:SiteMenu id="SiteMenu1" runat="server" UseTreeView="false" HideMenuOnSiteMap="false" Direction="Horizontal" ></portal:SiteMenu>

			<asp:Panel id="divLeft" runat="server" cssclass="leftside" visible="True" SkinID="pnlPlain">
				<asp:contentplaceholder ID="leftContent" runat="server"></asp:contentplaceholder>
			</asp:Panel>

			<asp:Panel id="divCenter" runat="server" visible="True" cssclass="center-rightandleftmargins" SkinID="pnlPlain">
				<asp:ContentPlaceHolder ID="mainContent" runat="server"></asp:ContentPlaceHolder>
			</asp:Panel>

			<asp:Panel id="divRight" runat="server" visible="True" cssclass="rightside" SkinID="pnlPlain">
				<asp:contentplaceholder ID="rightContent" runat="server"></asp:contentplaceholder>
			</asp:Panel>
			<asp:ContentPlaceHolder ID="pageEditContent" runat="server"></asp:ContentPlaceHolder>
		</form>
	</body>
</html>

However, if you strip it down that far not all the features will work. While the above is the minimum required to prevent errors, for all features to work as designed it is recommended to keep most of what you see in layout.Master files in included skins, and only remove things judiciously once you know what they are for and are sure you don't want them. I recommend when you want to create a new skin, copy an existing skin thathas the closest layout to what you want to achieve and modify it from there.

SiteMapDataSource - is required to populate the menu

ScriptManager - is required as part of the Microsoft AJAX framework.

LoginLink - displays the Login Link if the user is not logged in, it is hidden when the user is logged in.

LogoutLink - displays the Logout link, it is hidden when the user is not logged in

contentplaceholder id=pageEditContent - for users in a role which allows editing content, this is where the edit icons (add page, edit page properties, edit page content) will be dislayed

SiteMenu - this is the main menu for the site. The most important setting is Direction which can be Horizontal or Vertical. TopLevelOnly should normally be set to false unless you are also using the PageMenu, see optional elements below. If set to true the SiteMenu will only display top level menu items.

Panel id=divLeft - this is the container for content that comes from the content management system and is placed in the left column. The content actually renders in the contentplaceholder within this panel, but the Panel itself is used for positioning and/or showing or hiding the left content using css.

Panel id=divCenter - this is the container for content that comes from the content management system and is placed in the center column. The content actually renders in the contentplaceholder within this panel, but the Panel itself is used for positioning and/or showing or hiding the left content using css.

Panel id=divRight - this is the container for content that comes from the content management system and is placed in the right column. The content actually renders in the contentplaceholder within this panel, but the Panel itself is used for positioning and/or showing or hiding the left content using css.

See the css documentation for more info on these css classes.

Recommended Elements of a mojoPortal layout.Master file

Below is a layout.Master file with all the recommended elements.

<%@ Master Language="C#" AutoEventWireup="true" CodeBehind="~/App_MasterPages/layout.Master.cs" Inherits="mojoPortal.Web.layout" %>
<!DOCTYPE html>
<html>
	<head id="Head1" runat="server">
		<title></title>
		<portal:StyleSheetCombiner id="StyleSheetCombiner" runat="server" JQueryUIThemeName="trontastic" UseIconsForAdminLinks="false" />
		<portal:IEStyleIncludes id="IEStyleIncludes1" runat="server" IncludeHtml5Script="true" />
		<portal:MetaContent id="MetaContent" runat="server" />
		<portal:Favicon id="Favicon1" runat="server" />
		<portal:ScriptLoader id="ScriptLoader1" runat="server" />
	</head>
	<body class="pagebody" id="Body" runat="server">
		<portal:AnalyticsAsyncTopScript ID="analyticsTop" runat="server" />
		<form id="frmMain" runat="server">
			<asp:SiteMapDataSource ID="SiteMapData" runat="server" ShowStartingNode="false" />
			<asp:SiteMapDataSource ID="PageMapDataSource" runat="server" ShowStartingNode="false" />
			<asp:SiteMapDataSource ID="ChildPageSiteMapData" runat="server" ShowStartingNode="false" />
			<asp:ScriptManager ID="ScriptManager1" EnablePageMethods="true" runat="server" />

			<div id="wrapwebsite">
				<div class="topnav">
					<portal:SkipLink id="SkipLink1" runat="server" />
					<ul>
						<portal:WelcomeMessage id="WelcomeMessage" runat="server" RenderAsListItem="true" ListItemCSS="firstnav" />
						<portal:HomeLink id="HomeLink" runat="server" RenderAsListItem="true" />
						<portal:SiteMapLink id="SiteMapLink2" runat="server" CssClass="sitelink" RenderAsListItem="true" />
						<portal:MyPageLink id="MyPageLink1" runat="server" RenderAsListItem="true" />
						<portal:UserProfileLink id="UserProfileLink" runat="server" RenderAsListItem="true" />
						<portal:MailboxLink id="MailboxLink1" runat="server" RenderAsListItem="true" />
						<portal:MemberListLink id="MemberListLink" runat="server" RenderAsListItem="true" />
						<portal:SearchInput id="SearchInput1" LinkOnly="True" RenderAsListItem="true" runat="server" />
						<portal:RegisterLink id="RegisterLink" runat="server" RenderAsListItem="true" />
						<portal:LoginLink id="LoginLink" runat="server" RenderAsListItem="true" />
						<portal:LogoutLink id="LogoutLink" runat="server" RenderAsListItem="true" />
					</ul>
				</div>

				<div id="wrapheader">
					<portal:SiteTitle id="SiteTitle" runat="server"></portal:SiteTitle>
				</div>

				<portal:SiteMenu id="SiteMenu1" runat="server" EnableTheming="false" UseTreeView="false" HideMenuOnSiteMap="false" Direction="Horizontal" TopLevelOnly="true" />

				<div id="wrapcenter">
					<asp:Panel id="divLeft" runat="server" cssclass="leftside" visible="True" SkinID="pnlPlain">
						<portal:PageMenu id="PageMenu1" runat="server" UseTreeView="true" TreeViewShowExpandCollapse="true" />
						<a id="startcontent"></a>
						<asp:contentplaceholder ID="leftContent" runat="server"></asp:contentplaceholder>
					</asp:Panel>

					<asp:Panel id="divCenter" runat="server" visible="True" cssclass="center-rightandleftmargins" SkinID="pnlPlain">
						<portal:Breadcrumbs id="Breadcrumbs" runat="server"></portal:Breadcrumbs>
						<portal:ChildPageMenu id="ChildPageMenu" runat="server" CssClass="txtnormal"></portal:ChildPageMenu>
						<asp:ContentPlaceHolder ID="mainContent" runat="server"></asp:ContentPlaceHolder>
					</asp:Panel>

					<asp:Panel id="divRight" runat="server" visible="True" cssclass="rightside" SkinID="pnlPlain">
						<asp:contentplaceholder ID="rightContent" runat="server"></asp:contentplaceholder>
					</asp:Panel>
				</div>

				<div id="wrapfooter">
					<portal:SiteMapLink id="SiteMapLink1" runat="server" CssClass="sitemaplink" /> |
					<portal:CopyrightLabel ID="cl1" runat="server" ShowYear="true" BeginYear="2008" /> |
					<portal:mojoPortalLink id="lnkmojoportal" runat="server" UseImage="false" /> |
					<a title="Visit the web site of the designer" href="https://i7media.com">design by i7MEDIA</a>
				</div>
			</div>

			<script type="text/javascript">
				$(document).ready(function() {
					$('span.downarr a').click(function() {
						$('#toolbar').fadeOut();
						$('#toolbarbut').fadeIn('slow');
					});
					$('span.showbar a').click(function() {
						$('#toolbar').fadeIn();
						$('#toolbarbut').fadeOut('slow');
					});
					$('span.downarr a, span.showbar a').click(function() {
						return false;
					});
				});
			</script>

			<portal:AutoHidePanel ID="ah1" runat="server">
				<div id="toolbarbut">
					<span class="showbar"><a href="#">Show Bar</a></span>
				</div>
				<div id="toolbar">
					<div class="toolbarright">
						<span class="downarr"><a href="#"></a></span>
						<portal:AdminMenuLink id="lnkAdminMenu" runat="server" />
						<portal:FileManagerLink id="lnkFileManager" runat="server" />
						<portal:NewPageLink id="lnkNewPage" runat="server" />
						<portal:PageEditFeaturesLink id="lnkPageContent" runat="server" />
						<portal:PageEditSettingsLink id="lnkPageSettings" runat="server" />
						<asp:ContentPlaceHolder ID="pageEditContent" runat="server"></asp:ContentPlaceHolder>
					</div>
				</div>
			</portal:AutoHidePanel>
			<portal:AnalyticsAsyncBottomScript ID="analyticsBottom" runat="server" />
			<portal:Woopra ID="woopra11" runat="server" />
		</form>
	</body>
</html>

The displayed text for many of the links in layout.master can be changed by adding OverrideText="My Text" to the portal declaration. For instance, to change the "Sign In" link to instead read "Log In", the portal declaration would look like:

<portal:LoginLink ID="LoginLink" runat="server" RenderAsListItem="true" OverrideText="Log In" />

StylesheetCombiner - this control gets the correct stylesheet url for the current skin, it should be in the head section.

MetaContent - this should also be in the head section. MetaContent can be defined for a site in the Site Settings admin section. Individual pages can also override the site setting in Page Settings.

Favicon - this gets the icon link that points to favicon.ico in the skin folder. Modern browsers display this at the left of the url.

WelcomeMessage - this is the indicator of who you are signed into the site as.

HomeLink - is just a link to the home page of the site, useful to have this on every page

SiteMapLink - this is a link to the Site Map page. Note that you can have more than one SiteMap link. I usually have one at the top and bottom of the page.

MyPageLink - if the MyPage feature is enabled in Site Settings this link to the My Page feature will be displayed.

UserProfileLink - is hidden if the user is not logged in.

MailboxLink - this will be a link to the private message system mailbox (not yet implemented coming at some point)

MemberlistLink - if the Web.config setting AllowAnonymousUsersToViewMemberList is true this link will be displayed all the time, if not it will be displayed only for users who are logged in.

RegisterLink - is only displayed to users who are not logged in. If Site Settings is configured not to allow new users to register then this link is not displayed.

SearchInput - If LinkOnly is true this will just be a link to the Search page, if false this will be a search input textbox and a button.

SiteLogo - corresponds to a logo that you pick from Site Settings and is also a link to the home page. It is possible to remove this and just make your own image link using markup.

SiteTitle - corresponds to the Title of the site as entered in Site Settings, it also links to the home page.

SkipLink - is an accessibility feature, it should be placed near the title. A hidden link is placed there that can jump past the menu to the start of the page content. For more info on Skip Links see here.

Breadcrumbs - if Show Breadcrumbs is enabled in Page Settings, breadcrumbs are displayed. Breadcrumbs are an indicator of where you are in the site. This page uses breadcrumbs.

ChildPageMenu - if Show Child Page menu is enabled in Page Settings a menu of pages beneath the current page is shown. This is useful for pages that are just a parent to other pages but have no content themselves.

SkinPreview - is used for the Printable View link which uses the printerfriendly skin.

Beware of Errors! If you remove required elements or add something incorrect that causes an error, the error will be logged and the page will fall back to using the layout.master file from App_MasterPages. Be aware of this, if you make edits and it does not work you should check the log and fix the error.