Программное указание эталонной страницы (VB)
Проверяет настройку страницы master содержимого программным способом с помощью обработчика событий PreInit.
Введение
С момента первого примера в статье Создание макета Site-Wide с помощью главных страниц все страницы содержимого ссылаются на свою master страницу декларативно с помощью атрибута MasterPageFile
в директиве @Page
. Например, следующая @Page
директива связывает страницу содержимого со страницей Site.master
master :
<%@ Page Language="C#" MasterPageFile="~/Site.master"... %>
КлассPage
в System.Web.UI
пространстве имен содержит MasterPageFile
свойство , которое возвращает путь к странице master содержимого. Именно это свойство задается директивой @Page
. Это свойство также можно использовать для программного задания страницы master содержимого. Этот подход полезен, если вы хотите динамически назначить страницу master на основе внешних факторов, таких как пользователь, посещающий страницу.
В этом руководстве мы добавим вторую страницу master на наш веб-сайт и динамически решаем, какую страницу master использовать во время выполнения.
Шаг 1. Обзор жизненного цикла страницы
Всякий раз, когда на веб-сервер поступает запрос на страницу ASP.NET, которая является страницей содержимого, подсистема ASP.NET должна объединить элементы управления контентом страницы в соответствующие элементы управления ContentPlaceHolder master страницы. Это слияние создает единую иерархию элементов управления, которая затем может перейти к стандартному жизненному циклу страницы.
На рисунке 1 показан этот слияние. Шаг 1 на рис. 1 показывает начальное содержимое и master иерархии элементов управления страницы. В конце этапа PreInit элементы управления контентом на странице добавляются в соответствующие элементы ContentPlaceHolders на странице master (шаг 2). После этого слияния страница master служит корнем иерархии плавленного элемента управления. Затем эта плавленная иерархия элементов управления добавляется на страницу для создания завершенной иерархии элементов управления (шаг 3). Результатом является то, что иерархия элементов управления страницы включает в себя иерархию слитых элементов управления.
Рис. 01. Иерархии элементов управления главной страницы и страницы содержимого объединяются вместе на этапе PreInit (Щелкните для просмотра полноразмерного изображения)
Шаг 2. ЗаданиеMasterPageFile
свойства из кода
То, что master страница участвует в этом слиянии, зависит от значения Page
свойства объектаMasterPageFile
. Задание атрибута MasterPageFile
в директиве @Page
имеет чистый эффект от назначения Page
свойства на MasterPageFile
этапе инициализации, который является самым первым этапом жизненного цикла страницы. Можно также задать это свойство программным способом. Однако необходимо, чтобы это свойство было задано до слияния на рис. 1.
В начале этапа Page
PreInit объект вызывает событиеPreInit
и вызывает егоOnPreInit
метод . Чтобы задать страницу master программным способом, можно либо создать обработчик событий для PreInit
события, либо переопределить OnPreInit
метод . Давайте рассмотрим оба метода.
Начните с открытия Default.aspx.vb
файла класса кода программной части для домашней страницы нашего сайта. Добавьте обработчик событий для события страницы, PreInit
введя следующий код:
Protected Sub Page_PreInit(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.PreInit
End Sub
Здесь можно задать MasterPageFile
свойство . Обновите код таким образом, чтобы он присваивал значение "~/Site. master" в MasterPageFile
свойство .
Protected Sub Page_PreInit(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.PreInit
Me.MasterPageFile = "~/Site.master"
End Sub
Если вы задали точку останова и начали с отладки, вы увидите, что при каждом Default.aspx
посещении страницы или при отправке обратной передачи на эту страницу Page_PreInit
обработчик событий выполняется и MasterPageFile
свойство назначается "~/Site.master".
Кроме того, можно переопределить Page
метод класса OnPreInit
и задать в нем MasterPageFile
свойство . В этом примере давайте задали не страницу master на определенной странице, а из BasePage
. Помните, что мы создали пользовательский класс базовой страницы (BasePage
) еще в руководстве Указание заголовка, метатегов и других заголовков HTML в главной странице . В настоящее BasePage
время переопределяет Page
метод класса OnLoadComplete
, где он задает свойство страницы Title
на основе данных карты сайта. Давайте также BasePage
переопределим метод для программного OnPreInit
указания страницы master.
Protected Overrides Sub OnPreInit(ByVal e As System.EventArgs)
Me.MasterPageFile = "~/Site.master"
MyBase.OnPreInit(e)
End Sub
Так как все страницы содержимого являются производными от BasePage
, теперь всем страницам master назначается программным способом. На этом этапе PreInit
обработчик событий в Default.aspx.vb
не является лишним. Вы можете удалить его.
Как насчет директивы@Page
?
Что может быть немного запутанным, так это то, что свойства страниц содержимого MasterPageFile
теперь задаются в двух местах: программно в BasePage
методе класса OnPreInit
, а также с помощью MasterPageFile
атрибута в директиве каждой страницы содержимого @Page
.
Первым этапом жизненного цикла страницы является этап инициализации. На этом этапе свойству Page
объекта MasterPageFile
присваивается значение атрибута MasterPageFile
в директиве @Page
(если оно указано). Этап PreInit следует за этапом инициализации, и именно здесь мы программно задаем Page
свойство объекта MasterPageFile
, тем самым перезаписав значение, присвоенное директивой @Page
. Так как мы задаем Page
свойство объекта MasterPageFile
программным способом, мы можем удалить MasterPageFile
атрибут из @Page
директивы, не влияя на взаимодействие с конечным пользователем. Чтобы убедиться в этом, удалите MasterPageFile
атрибут из директивы @Page
в , Default.aspx
а затем перейдите на страницу через браузер. Как и следовало ожидать, выходные данные будут теми же, что и до удаления атрибута.
MasterPageFile
То, задано ли свойство с помощью @Page
директивы или программным способом, не имеет значения для взаимодействия с конечным пользователем. MasterPageFile
Однако атрибут в директиве @Page
используется Visual Studio во время разработки для создания представления WYSIWYG в Designer. Если вернуться к Default.aspx
в Visual Studio и перейти к Designer появится сообщение "Ошибка главной страницы: на странице есть элементы управления, требующие ссылки на главную страницу, но ни одна из них не указана" (см. рис. 2).
Короче говоря, необходимо оставить MasterPageFile
атрибут в директиве , @Page
чтобы воспользоваться широкими возможностями разработки в Visual Studio.
@Page для отображения представления конструктора" />
Рис. 02. Visual Studio использует @Page
атрибут директивы для отрисовки представления конструктора MasterPageFile
(щелкните для просмотра полноразмерного изображения)
Шаг 3. Создание альтернативной главной страницы
Так как страница master страницы содержимого может быть задана программным способом во время выполнения, можно динамически загружать определенную страницу master на основе некоторых внешних критериев. Эта функция может быть полезна в ситуациях, когда макет сайта должен меняться в зависимости от пользователя. Например, веб-приложение подсистемы блога может позволить пользователям выбирать макет для своего блога, где каждый макет связан с другой страницей master. Во время выполнения, когда посетитель просматривает блог пользователя, веб-приложению потребуется определить макет блога и динамически связать соответствующую страницу master со страницей содержимого.
Давайте рассмотрим, как динамически загружать страницу master во время выполнения на основе некоторых внешних критериев. Наш веб-сайт в настоящее время содержит только одну страницу master (Site.master
). Нам нужна еще одна страница master, чтобы проиллюстрировать выбор страницы master во время выполнения. Этот шаг посвящен созданию и настройке новой страницы master. В шаге 4 рассматривается определение master страницы для использования во время выполнения.
Создайте новую страницу master в корневой папке с именем Alternate.master
. Кроме того, добавьте новую таблицу стилей на веб-сайт с именем AlternateStyles.css
.
Рис. 03. Добавление другой главной страницы и CSS-файла на веб-сайт (щелкните для просмотра полноразмерного изображения)
Я разработал страницу Alternate.master
master, чтобы заголовок отображался в верхней части страницы, по центру и на военно-морском фоне. Я распределил левый столбец и переместил его содержимое под MainContent
элементом управления ContentPlaceHolder, который теперь охватывает всю ширину страницы. Кроме того, я префиксировал список неупорядоченных уроков и заменил его горизонтальным списком выше MainContent
. Кроме того, я обновил шрифты и цвета, используемые на странице master (и, в своюихе, и, в свою 2018 году, на страницах содержимого). На рисунке 4 показано Default.aspx
использование страницы Alternate.master
master.
Примечание
ASP.NET включает возможность определения тем. Тема — это коллекция изображений, CSS-файлов и параметров свойств веб-элемента управления, связанных со стилем, которые можно применить к странице во время выполнения. Темы — это путь, если макеты вашего сайта отличаются только отображаемыми изображениями и правилами CSS. Если макеты отличаются более существенно, например с использованием разных веб-элементов управления или с радикально отличающимся макетом, вам потребуется использовать отдельные master страницы. Дополнительные сведения о темах см. в разделе Дополнительное чтение в конце этого руководства.
Рис. 04. Наши страницы содержимого теперь могут использовать новый внешний вид (щелкните для просмотра полноразмерного изображения)
При слиянии разметки страниц master и содержимого MasterPage
класс проверяет, ссылается ли каждый элемент управления Контентом на странице содержимого на ContentPlaceHolder на странице master. Исключение возникает при обнаружении элемента управления контентом, который ссылается на несуществующий ContentPlaceHolder. Иными словами, крайне важно, чтобы страница master, назначаемая странице содержимого, была contentPlaceHolder для каждого элемента управления контентом на странице содержимого.
Страница Site.master
master содержит четыре элемента управления ContentPlaceHolder:
head
MainContent
QuickLoginUI
LeftColumnContent
Некоторые страницы содержимого на нашем веб-сайте содержат только один или два элемента управления контентом; другие включают элемент управления Контент для каждого из доступных ContentPlaceHolders. Если наша новая страница master (Alternate.master
) может быть назначена тем страницам содержимого, которые имеют элементы управления контентом для всех ContentPlaceHolders в Site.master
, важно также включать те же элементы управления ContentPlaceHolder, что Alternate.master
и Site.master
.
Alternate.master
Чтобы страница master выглядела аналогично моей (см. рис. 4), начните с определения стилей страницы master в таблице стилейAlternateStyles.css
. Добавьте следующие правила в AlternateStyles.css
:
body
{
font-family: Comic Sans MS, Arial;
font-size: medium;
margin: 0px;
}
#topContent
{
text-align: center;
background-color: Navy;
color: White;
font-size: x-large;
text-decoration: none;
font-weight: bold;
padding: 10px;
height: 50px;
}
#topContent a
{
text-decoration: none;
color: White;
}
#navContent
{
font-size: small;
text-align: center;
}
#footerContent
{
padding: 10px;
font-size: 90%;
text-align: center;
border-top: solid 1px black;
}
#mainContent
{
text-align: left;
padding: 10px;
}
Затем добавьте следующую декларативную разметку в Alternate.master
. Как видите, Alternate.master
содержит четыре элемента управления ContentPlaceHolder с теми же ID
значениями, что и элементы управления ContentPlaceHolder в Site.master
. Кроме того, он включает в себя элемент управления ScriptManager, который необходим для тех страниц на нашем веб-сайте, которые используют платформу ASP.NET AJAX.
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head id="Head1" runat="server">
<title>Untitled Page</title>
<asp:ContentPlaceHolder id="head" runat="server">
</asp:ContentPlaceHolder>
<link href="AlternateStyles.css" rel="stylesheet" type="text/css"/>
</head>
<body>
<form id="form1" runat="server">
<asp:ScriptManager ID="MyManager" runat="server">
</asp:ScriptManager>
<div id="topContent">
<asp:HyperLink ID="lnkHome" runat="server" NavigateUrl="~/Default.aspx"
Text="Master Pages Tutorials" />
</div>
<div id="navContent">
<asp:ListView ID="LessonsList" runat="server"
DataSourceID="LessonsDataSource">
<LayoutTemplate>
<asp:PlaceHolder runat="server" ID="itemPlaceholder" />
</LayoutTemplate>
<ItemTemplate>
<asp:HyperLink runat="server" ID="lnkLesson"
NavigateUrl='<%# Eval("Url") %>'
Text='<%# Eval("Title") %>' />
</ItemTemplate>
<ItemSeparatorTemplate> | </ItemSeparatorTemplate>
</asp:ListView>
<asp:SiteMapDataSource ID="LessonsDataSource" runat="server"
ShowStartingNode="false" />
</div>
<div id="mainContent">
<asp:ContentPlaceHolder id="MainContent" runat="server">
</asp:ContentPlaceHolder>
</div>
<div id="footerContent">
<p>
<asp:Label ID="DateDisplay" runat="server"></asp:Label>
</p>
<asp:ContentPlaceHolder ID="QuickLoginUI" runat="server">
</asp:ContentPlaceHolder>
<asp:ContentPlaceHolder ID="LeftColumnContent" runat="server">
</asp:ContentPlaceHolder>
</div>
</form>
</body>
</html>
Тестирование новой главной страницы
Чтобы протестировать этот новый master странице обновите BasePage
метод классаOnPreInit
, MasterPageFile
чтобы присвоить свойству значение"~/Alternate.maser"
, а затем перейдите на веб-сайт. Каждая страница должна работать без ошибок, за исключением двух: ~/Admin/AddProduct.aspx
и ~/Admin/Products.aspx
. Добавление продукта в DetailsView в ~/Admin/AddProduct.aspx
приводит к получению NullReferenceException
из строки кода, которая пытается задать свойство страницы GridMessageText
master. При посещении ~/Admin/Products.aspx
InvalidCastException
возникает при загрузке страницы сообщение: "Не удается привести объект типа "ASP.alternate_master" к типу "ASP.site_master".
Эти ошибки возникают из-за того Site.master
, что класс кода программной части содержит открытые события, свойства и методы, которые не определены в Alternate.master
. Часть разметки этих двух страниц имеет директиву@MasterType
, которая ссылается на Site.master
master страницу.
<%@ MasterType VirtualPath="~/Site.master" %>
Кроме того, обработчик событий DetailsView ItemInserted
в ~/Admin/AddProduct.aspx
содержит код, который приводит свойство слабо типизированного Page.Master
к объекту типа Site
. Директива @MasterType
(используется таким образом) и приведение в обработчике ItemInserted
событий тесно связаны ~/Admin/AddProduct.aspx
страницы и ~/Admin/Products.aspx
со страницей Site.master
master.
Чтобы разорвать эту тесную связь, мы можем получить Site.master
и Alternate.master
наследовать от общего базового класса, который содержит определения для открытых членов. После этого можно обновить директиву для @MasterType
ссылки на этот общий базовый тип.
Создание настраиваемого класса базовой главной страницы
Добавьте новый файл класса в папку с App_Code
именем BaseMasterPage.vb
и наследуйте его от System.Web.UI.MasterPage
. Нам нужно определить RefreshRecentProductsGrid
метод и GridMessageText
свойство в BaseMasterPage
, но мы не можем просто переместить их оттудаSite.master
, так как эти элементы работают с веб-элементами управления, характерными для Site.master
страницы master (RecentProducts
GridView и GridMessage
Label).
Нам нужно настроить BaseMasterPage
таким образом, чтобы эти члены были определены там, но на самом деле реализуются производными классами BaseMasterPage
(Site.master
и Alternate.master
). Этот тип наследования возможен, помечая класс как MustInherit
и его члены как MustOverride
. Короче говоря, при добавлении этих ключевых слов в класс и два его члена объявляется, что BaseMasterPage
не реализованы RefreshRecentProductsGrid
и GridMessageText
, но что его производные классы будут.
Кроме того, необходимо определить PricesDoubled
событие в BaseMasterPage
и предоставить средства для создания события с помощью производных классов. Шаблон, используемый в платформа .NET Framework для упрощения этого поведения, заключается в создании открытого события в базовом классе и добавлен защищенный переопределенный метод с именем OnEventName
. Производные классы могут вызывать этот метод для вызова события или переопределять его для выполнения кода непосредственно перед или после возникновения события.
Обновите BaseMasterPage
класс таким образом, чтобы он содержал следующий код:
Public MustInherit Class BaseMasterPage
Inherits System.Web.UI.MasterPage
Public Event PricesDoubled As EventHandler
Protected Overridable Sub OnPricesDoubled(ByVal e As EventArgs)
RaiseEvent PricesDoubled(Me, e)
End Sub
Public MustOverride Sub RefreshRecentProductsGrid()
Public MustOverride Property GridMessageText() As String
End Class
Затем перейдите к классу Site.master
кода программной части и наследуйте его от BaseMasterPage
. Так как BaseMasterPage
содержит элементы, помеченные MustOverride
, необходимо переопределить эти члены здесь в Site.master
. Overrides
Добавьте ключевое слово в определения метода и свойства. Кроме того, обновите код, который вызывает PricesDoubled
событие в DoublePrice
обработчике Click
событий Button, вызвав метод базового класса OnPricesDoubled
.
После этих изменений Site.master
класс кода программной части должен содержать следующий код:
Partial Class Site
Inherits BaseMasterPage
Protected Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load
DateDisplay.Text = DateTime.Now.ToString("dddd, MMMM dd")
End Sub
Public Overrides Sub RefreshRecentProductsGrid()
RecentProducts.DataBind()
End Sub
Public Overrides Property GridMessageText() As String
Get
Return GridMessage.Text
End Get
Set(ByVal Value As String)
GridMessage.Text = Value
End Set
End Property
Protected Sub DoublePrice_Click(ByVal sender As Object, ByVal e As System.EventArgs) Handles DoublePrice.Click
' Double the prices
DoublePricesDataSource.Update()
' Refresh RecentProducts
RecentProducts.DataBind()
' Raise the PricesDoubled event
MyBase.OnPricesDoubled(EventArgs.Empty)
End Sub
End Class
Кроме того, необходимо обновить Alternate.master
класс кода программной части, чтобы он был производным от BaseMasterPage
двух MustOverride
членов и переопределен. Но поскольку Alternate.master
не содержит GridView, в котором перечислены последние продукты, и метки, отображающей сообщение после добавления нового продукта в базу данных, эти методы не должны ничего делать.
Partial Class Alternate
Inherits BaseMasterPage
Public Overrides Property GridMessageText() As String
Get
Return String.Empty
End Get
Set(ByVal value As String)
' Do nothing
End Set
End Property
Public Overrides Sub RefreshRecentProductsGrid()
' Do nothing
End Sub
End Class
Ссылка на класс базовой главной страницы
Теперь, когда мы завершили работу с классом BaseMasterPage
и расширили его две страницы master, наш последний шаг — обновить ~/Admin/AddProduct.aspx
страницы и , ~/Admin/Products.aspx
чтобы они ссылались на этот распространенный тип. Начните с изменения директивы на @MasterType
обеих страницах с:
<%@ MasterType VirtualPath="~/Site.master" %>
В:
<%@ MasterType TypeName="BaseMasterPage" %>
Вместо ссылки на путь к файлу @MasterType
свойство теперь ссылается на базовый тип (BaseMasterPage
). Следовательно, строго типизированное Master
свойство, используемое в классах кода программной части обеих страниц, теперь имеет тип BaseMasterPage
(а не тип Site
). С этим изменением на месте вернитесь к ~/Admin/Products.aspx
. Ранее это приводило к ошибке приведения, так как страница настроена для использования Alternate.master
master страницы, но директива @MasterType
ссылалась на Site.master
файл. Но теперь страница отображается без ошибок. Это связано с тем Alternate.master
, что master страницу можно привести к объекту типа BaseMasterPage
(так как он расширяет его).
Существует одно небольшое изменение, которое необходимо внести в ~/Admin/AddProduct.aspx
. Обработчик событий элемента управления ItemInserted
DetailsView использует как строго типизированное Master
, так и слабо типизированное Page.Master
свойство. Мы исправили строго типизированную ссылку при обновлении @MasterType
директивы, но нам по-прежнему нужно обновить слабо типизированную ссылку. Замените следующую строку кода:
Dim myMasterPage As Site = CType(Page.Master, Site)
С помощью следующего, который приводит Page.Master
к базовому типу:
Dim myMasterPage As BaseMasterPage = CType(Page.Master, BaseMasterPage)
Шаг 4. Определение главной страницы для привязки к страницам содержимого
В настоящее время наш BasePage
класс задает свойства всех страниц MasterPageFile
содержимого как жестко закодированное значение на этапе PreInit жизненного цикла страницы. Мы можем обновить этот код, чтобы на странице master учитывались некоторые внешние факторы. Возможно, загрузка страницы master зависит от предпочтений текущего пользователя, выполнившего вход. В этом случае нам потребуется написать код в методе OnPreInit
в BasePage
, который ищет параметры страницы master текущего пользователя.
Давайте создадим веб-страницу, которая позволяет пользователю выбрать, какую master страницу использовать ( Site.master
или Alternate.master
) и сохранить этот вариант в переменной сеанса. Начните с создания новой веб-страницы в корневом каталоге с именем ChooseMasterPage.aspx
. При создании этой страницы (или любых других страниц содержимого в настоящее время) ее не нужно привязывать к master странице, так как master страница задается программным способом в BasePage
. Однако если не привязать новую страницу к master странице, декларативная разметка новой страницы по умолчанию будет содержать веб-форму и другое содержимое, предоставляемое master страницей. Вам потребуется вручную заменить эту разметку соответствующими элементами управления контентом. По этой причине мне проще привязать новую страницу ASP.NET к master странице.
Примечание
Так как Site.master
и Alternate.master
имеют одинаковый набор элементов управления ContentPlaceHolder, не имеет значения, какую master страницу вы выбираете при создании новой страницы содержимого. Для обеспечения согласованности я бы предложил использовать .Site.master
Рис. 05. Добавление новой страницы содержимого на веб-сайт (щелкните для просмотра полноразмерного изображения)
Обновите файл, Web.sitemap
чтобы включить запись для этого урока. Добавьте следующую разметку под элементом для урока <siteMapNode>
"Главные страницы" и ASP.NET AJAX:
<siteMapNode url="~/ChooseMasterPage.aspx" title="Choose a Master Page" />
Перед добавлением содержимого на страницу ChooseMasterPage.aspx
обновите класс кода программной части страницы, чтобы он был производным от BasePage
(а не System.Web.UI.Page
). Затем добавьте элемент управления DropDownList на страницу, задайте для его ID
свойства MasterPageChoice
значение и добавьте два Элемента ListItems со значениями Text
"~/Site.master" и "~/Alternate.master".
Добавьте на страницу элемент управления Button Web и задайте для его ID
свойств SaveLayout
и Text
значение и "Сохранить вариант макета" соответственно. На этом этапе декларативная разметка страницы должна выглядеть примерно так:
<p>
Your layout choice:
<asp:DropDownList ID="MasterPageChoice" runat="server">
<asp:ListItem>~/Site.master</asp:ListItem>
<asp:ListItem>~/Alternate.master</asp:ListItem>
</asp:DropDownList>
</p>
<p>
<asp:Button ID="SaveLayout" runat="server" Text="Save Layout Choice" />
</p>
При первом посещении страницы необходимо отобразить выбранный пользователем master выбор страницы. Создайте Page_Load
обработчик событий и добавьте следующий код:
Protected Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load
If Not Page.IsPostBack Then
If Session("MyMasterPage") IsNot Nothing Then
Dim li As ListItem = MasterPageChoice.Items.FindByText(Session("MyMasterPage").ToString())
If li IsNot Nothing Then
li.Selected = True
End If
End If
End If
End Sub
Приведенный выше код выполняется только при первом посещении страницы (а не при последующих обратных операциях). Сначала проверяется, существует ли переменная MyMasterPage
Session. Если это так, он пытается найти соответствующий ListItem в MasterPageChoice
DropDownList. Если найден соответствующий Объект ListItem, его Selected
свойству True
присваивается значение .
Нам также нужен код, который сохраняет выбор пользователя в переменной MyMasterPage
Session. Создайте обработчик событий для SaveLayout
события Button Click
и добавьте следующий код:
Protected Sub SaveLayout_Click(ByVal sender As Object, ByVal e As System.EventArgs) Handles SaveLayout.Click
Session("MyMasterPage") = MasterPageChoice.SelectedValue
Response.Redirect("ChooseMasterPage.aspx")
End Sub
Примечание
К тому времени, когда Click
обработчик событий будет выполняться при обратной отправке, страница master уже была выбрана. Таким образом, выбор раскрывающегося списка пользователя не будет действовать до следующего посещения страницы. Заставляет Response.Redirect
браузер повторно запрашивать ChooseMasterPage.aspx
.
ChooseMasterPage.aspx
После завершения страницы наша конечная задача — BasePage
назначить MasterPageFile
свойство на основе значения переменной MyMasterPage
Session. Если переменная Session не задана, по умолчанию имеет BasePage
значение Site.master
.
Protected Overrides Sub OnPreInit(ByVal e As System.EventArgs)
SetMasterPageFile()
MyBase.OnPreInit(e)
End Sub
Protected Overridable Sub SetMasterPageFile()
Me.MasterPageFile = GetMasterPageFileFromSession()
End Sub
Protected Function GetMasterPageFileFromSession() As String
If Session("MyMasterPage") Is Nothing Then
Return "~/Site.master"
Else
Return Session("MyMasterPage").ToString()
End If
End Function
Примечание
Я переместил код, который назначает Page
свойство объекта MasterPageFile
из обработчика OnPreInit
событий и в два отдельных метода. Этот первый метод, SetMasterPageFile
, присваивает MasterPageFile
свойство значению, возвращаемого вторым методом . GetMasterPageFileFromSession
Я помечал SetMasterPageFile
метод Overridable
, чтобы будущие классы, расширяющие BasePage
его, при необходимости могли переопределить его для реализации пользовательской логики. Пример переопределения BasePage
SetMasterPageFile
свойства мы рассмотрим в следующем руководстве.
После этого кода перейдите на страницу ChooseMasterPage.aspx
. Изначально выбрана Site.master
страница master (см. рис. 6), но пользователь может выбрать другую страницу master из раскрывающегося списка.
Рис. 06. Страница содержимого отображается с помощью главной Site.master
страницы (щелкните для просмотра полноразмерного изображения)
Рис. 07. Страницы содержимого теперь отображаются с помощью главной Alternate.master
страницы (щелкните для просмотра полноразмерного изображения)
Сводка
При посещении страницы содержимого ее элементы управления контентом сливаются с элементами управления ContentPlaceHolder master страницы. Страница master страницы содержимого обозначается свойством Page
класса MasterPageFile
, которое назначается атрибуту @Page
директивы MasterPageFile
на этапе инициализации. Как показано в этом руководстве, мы можем присвоить значение свойству MasterPageFile
до завершения этапа PreInit. Возможность программно указать страницу master открывает возможности для более сложных сценариев, таких как динамическая привязка страницы содержимого к странице master на основе внешних факторов.
Счастливое программирование!
Дополнительные материалы
Дополнительные сведения по темам, рассматриваемым в этом руководстве, см. в следующих ресурсах:
- Схема жизненного цикла страницы ASP.NET
- Обзор жизненного цикла страницы ASP.NET
- Общие сведения о темах и обложках ASP.NET
- Эталонные страницы: советы, рекомендации и ловушки
- Темы в ASP.NET
Об авторе
Скотт Митчелл(Scott Mitchell), автор нескольких книг ASP/ASP.NET и основатель 4GuysFromRolla.com, работает с веб-технологиями Майкрософт с 1998 года. Скотт работает независимым консультантом, тренером и писателем. Его последняя книга Sams Teach Yourself ASP.NET 3,5 в 24 часа. Скотт может быть доступен в mitchell@4GuysFromRolla.com или через его блог по адресу http://ScottOnWriting.NET.
Особая благодарность
Эта серия учебников была рассмотрена многими полезными рецензентами. Ведущим рецензентом этого руководства был Сухи Банерджи. Хотите просмотреть предстоящие статьи MSDN? Если да, бросить мне строку на mitchell@4GuysFromRolla.com