Condividi tramite


Impostazione della pagina master a livello di codice (VB)

di Scott Mitchell

Esamina l'impostazione della pagina master della pagina del contenuto a livello di codice tramite il gestore eventi PreInit.

Introduzione

Poiché l'esempio inaugurale in Creazione di un layout a livello di sito tramite pagine master, tutte le pagine del contenuto hanno fatto riferimento dichiarativo alla relativa pagina master tramite l'attributo MasterPageFile nella @Page direttiva . Ad esempio, la direttiva seguente @Page collega la pagina del contenuto alla pagina Site.mastermaster :

<%@ Page Language="C#" MasterPageFile="~/Site.master"... %>

La classe nello spazio dei System.Web.UI nomi include una MasterPageFile proprietà che restituisce il percorso alla pagina master della pagina del contenuto. Si tratta di questa proprietà impostata dalla @Page direttiva .Page Questa proprietà può essere utilizzata anche per specificare a livello di codice la pagina master della pagina del contenuto. Questo approccio è utile se si vuole assegnare dinamicamente la pagina master in base a fattori esterni, ad esempio l'utente che visita la pagina.

In questa esercitazione viene aggiunta una seconda pagina master al sito Web e si decide in modo dinamico quale pagina master usare in fase di esecuzione.

Passaggio 1: Esaminare il ciclo di vita della pagina

Ogni volta che una richiesta arriva al server Web per una pagina ASP.NET che è una pagina di contenuto, il motore di ASP.NET deve unire i controlli Contenuto della pagina nei controlli ContentPlaceHolder corrispondenti della pagina master. Questa fusione crea una singola gerarchia di controlli che può quindi procedere nel ciclo di vita tipico della pagina.

La figura 1 illustra questa fusione. Il passaggio 1 nella figura 1 mostra le gerarchie iniziali di contenuto e controllo pagina master. Alla fine finale della fase PreInit i controlli Contenuto nella pagina vengono aggiunti ai ContentPlaceHolders corrispondenti nella pagina master (passaggio 2). Dopo questa fusione, la pagina master funge da radice della gerarchia dei controlli fusi. Questa gerarchia di controlli fusi viene quindi aggiunta alla pagina per produrre la gerarchia dei controlli finali (passaggio 3). Il risultato netto è che la gerarchia di controllo della pagina include la gerarchia dei controlli fusi.

Le gerarchie di controllo della pagina master e della pagina contenuto vengono unite insieme durante la fase preinit

Figura 01: Le gerarchie di controllo della pagina master e della pagina del contenuto vengono unite insieme durante la fase PreInit (fare clic per visualizzare l'immagine a dimensione intera)

Passaggio 2: Impostazione dellaMasterPageFileproprietà dal codice

Il contenuto della pagina master in questa fusione dipende dal valore della Page proprietà dell'oggetto MasterPageFile . L'impostazione dell'attributo nella @Page direttiva ha l'effetto MasterPageFile netto dell'assegnazione Pagedella proprietà della MasterPageFile proprietà durante la fase di inizializzazione, che è la prima fase del ciclo di vita della pagina. In alternativa, è possibile impostare questa proprietà a livello di codice. Tuttavia, è fondamentale che questa proprietà venga impostata prima che venga eseguita la fusione nella figura 1.

All'inizio della fase PreInit l'oggetto genera l'evento PagePreInit e chiama il relativo OnPreInit metodo. Per impostare la pagina master a livello di codice, è possibile creare un gestore eventi per l'evento o eseguire l'override PreInit del OnPreInit metodo . Di seguito vengono esaminati entrambi gli approcci.

Per iniziare, aprire Default.aspx.vb, il file di classe code-behind per la home page del sito. Aggiungere un gestore eventi per l'evento della PreInit pagina digitando il codice seguente:

Protected Sub Page_PreInit(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.PreInit 
End Sub

Da qui è possibile impostare la MasterPageFile proprietà . Aggiornare il codice in modo che assegni il valore "~/Site.master" alla MasterPageFile proprietà .

Protected Sub Page_PreInit(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.PreInit 
 Me.MasterPageFile = "~/Site.master"
End Sub

Se si imposta un punto di interruzione e si inizia con il debug, si noterà che ogni volta che la Default.aspx pagina viene visitata o ogni volta che è presente un postback a questa pagina, il Page_PreInit gestore eventi viene eseguito e la MasterPageFile proprietà viene assegnata a "~/Site.master".

In alternativa, è possibile eseguire l'override del Page metodo della OnPreInit classe e impostare la MasterPageFile proprietà. Per questo esempio, non impostiamo la pagina master in una determinata pagina, ma piuttosto da BasePage. Tenere presente che è stata creata una classe di pagina di base personalizzata (BasePage) nell'esercitazione Specifica del titolo, dei meta tag e di altre intestazioni HTML nell'esercitazione sulla pagina master. Attualmente BasePage esegue l'override del Page metodo della OnLoadComplete classe, in cui imposta la proprietà della Title pagina in base ai dati della mappa del sito. Si aggiornerà BasePage per eseguire anche l'override del OnPreInit metodo per specificare la pagina master a livello di codice.

Protected Overrides Sub OnPreInit(ByVal e As System.EventArgs)
 Me.MasterPageFile = "~/Site.master" 
 MyBase.OnPreInit(e)
End Sub

Poiché tutte le pagine di contenuto derivano da BasePage, tutte hanno ora la relativa pagina master assegnata a livello di codice. A questo punto il PreInit gestore eventi in Default.aspx.vb è superfluo. È possibile rimuoverlo.

Che ne dici della@Pagedirettiva?

Ciò che può essere poco chiaro è che le proprietà delle pagine del MasterPageFile contenuto vengono ora specificate in due posizioni: a livello di codice nel BasePage metodo della OnPreInit classe e tramite l'attributo MasterPageFile nella direttiva di ogni pagina del @Page contenuto.

La prima fase del ciclo di vita della pagina è la fase di inizializzazione. Durante questa fase alla Page proprietà dell'oggetto MasterPageFile viene assegnato il valore dell'attributo MasterPageFile nella @Page direttiva (se specificato). La fase PreInit segue la fase di inizializzazione ed è qui che impostiamo a livello di codice la Page proprietà dell'oggetto MasterPageFile , sovrascrivendo così il valore assegnato dalla @Page direttiva. Poiché si imposta la Page proprietà dell'oggetto a livello di MasterPageFile codice, è possibile rimuovere l'attributo MasterPageFile dalla @Page direttiva senza influire sull'esperienza dell'utente finale. Per convincersi di questo, procedere e rimuovere l'attributo MasterPageFile dalla @Page direttiva in Default.aspx e quindi visitare la pagina tramite un browser. Come previsto, l'output è uguale a quello precedente alla rimozione dell'attributo.

Se la MasterPageFile proprietà viene impostata tramite la @Page direttiva o a livello di codice è inconsequential all'esperienza dell'utente finale. Tuttavia, l'attributo MasterPageFile nella direttiva viene usato da Visual Studio durante la @Page fase di progettazione per produrre la visualizzazione WYSIWYG nella finestra di progettazione. Se si torna a Default.aspx in Visual Studio e si passa alla finestra di progettazione verrà visualizzato il messaggio "Errore pagina master: la pagina contiene controlli che richiedono un riferimento alla pagina master, ma non è specificato nessuno" (vedere la figura 2).

In breve, è necessario lasciare l'attributo MasterPageFile nella @Page direttiva per godere di un'esperienza di progettazione avanzata in Visual Studio.

Visual Studio usa la classe <span= Attributo MasterPageFile della direttiva @Page per eseguire il rendering della visualizzazione struttura" />

Figura 02: Visual Studio usa l'attributo @Page della MasterPageFile direttiva per eseguire il rendering della visualizzazione struttura (fare clic per visualizzare l'immagine a dimensione intera)

Passaggio 3: Creazione di una pagina master alternativa

Poiché la pagina master di una pagina del contenuto può essere impostata a livello di codice in fase di esecuzione, è possibile caricare dinamicamente una determinata pagina master in base ad alcuni criteri esterni. Questa funzionalità può essere utile nelle situazioni in cui il layout del sito deve variare in base all'utente. Ad esempio, un'applicazione Web del motore di blog può consentire agli utenti di scegliere un layout per il blog, in cui ogni layout è associato a una pagina master diversa. In fase di esecuzione, quando un visitatore visualizza il blog di un utente, l'applicazione Web dovrà determinare il layout del blog e associare dinamicamente la pagina master corrispondente alla pagina del contenuto.

Si esaminerà ora come caricare dinamicamente una pagina master in fase di esecuzione in base ad alcuni criteri esterni. Il nostro sito web contiene attualmente solo una pagina master (Site.master). È necessaria un'altra pagina master per illustrare la scelta di una pagina master in fase di esecuzione. Questo passaggio è incentrato sulla creazione e la configurazione della nuova pagina master. Il passaggio 4 esamina la determinazione della pagina master da usare in fase di esecuzione.

Creare una nuova pagina master nella cartella radice denominata Alternate.master. Aggiungere anche un nuovo foglio di stile al sito Web denominato AlternateStyles.css.

Aggiungere un'altra pagina master e un altro file CSS al sito Web

Figura 03: Aggiungere un'altra pagina master e un altro file CSS al sito Web (fare clic per visualizzare l'immagine a dimensione intera)

Ho progettato la Alternate.master pagina master per visualizzare il titolo nella parte superiore della pagina, centrato e su uno sfondo navy. Ho erogato la colonna sinistra e spostato il contenuto sotto il MainContent controllo ContentPlaceHolder, che ora si estende sull'intera larghezza della pagina. Inoltre, ho nixed nixed Lessons list e sostituito con un elenco orizzontale sopra MainContent. Ho anche aggiornato i tipi di carattere e i colori usati dalla pagina master (e, per estensione, le relative pagine di contenuto). La figura 4 mostra quando Default.aspx si usa la Alternate.master pagina master.

Nota

ASP.NET include la possibilità di definire i temi. Un tema è una raccolta di immagini, file CSS e impostazioni delle proprietà del controllo Web correlate allo stile che possono essere applicate a una pagina in fase di esecuzione. I temi sono il modo per procedere se i layout del sito differiscono solo nelle immagini visualizzate e nelle relative regole CSS. Se i layout differiscono in modo più sostanziale, ad esempio usando controlli Web diversi o con un layout radicalmente diverso, sarà necessario usare pagine master separate. Per altre informazioni sui temi, vedere la sezione Altre informazioni sulla lettura alla fine di questa esercitazione.

Le pagine di contenuto possono ora usare un nuovo aspetto

Figura 04: Le pagine di contenuto possono ora usare un nuovo aspetto (fare clic per visualizzare un'immagine a dimensione intera)

Quando il markup delle pagine master e del contenuto viene fuso, la MasterPage classe verifica che ogni controllo Contenuto nella pagina del contenuto faccia riferimento a contentPlaceHolder nella pagina master. Viene generata un'eccezione se viene trovato un controllo Content che fa riferimento a un ContentPlaceHolder inesistente. In altre parole, è fondamentale che la pagina master assegnata alla pagina del contenuto abbia un ContentPlaceHolder per ogni controllo Contenuto nella pagina contenuto.

La Site.master pagina master include quattro controlli ContentPlaceHolder:

  • head
  • MainContent
  • QuickLoginUI
  • LeftColumnContent

Alcune delle pagine di contenuto nel nostro sito web includono solo uno o due controlli Contenuto; altri includono un controllo Contenuto per ognuno dei ContentPlaceHolders disponibili. Se la nuova pagina master (Alternate.master) può essere assegnata a tali pagine di contenuto con controlli Contenuto per tutti i ContentPlaceHolders in Site.master , è essenziale includere Alternate.master anche gli stessi controlli ContentPlaceHolder di Site.master.

Per ottenere l'aspetto Alternate.master della pagina master simile al mio (vedere la figura 4), iniziare definendo gli stili della pagina master nel AlternateStyles.css foglio di stile. Aggiungere le regole seguenti in 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;
}

Aggiungere quindi il markup dichiarativo seguente a Alternate.master. Come si può notare, Alternate.master contiene quattro controlli ContentPlaceHolder con gli stessi ID valori dei controlli ContentPlaceHolder in Site.master. Inoltre, include un controllo ScriptManager, che è necessario per tali pagine nel nostro sito Web che usano il framework 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>

Test della nuova pagina master

Per testare questa nuova pagina master, aggiornare il BasePage metodo della OnPreInit classe in modo che alla MasterPageFile proprietà venga assegnato il valore "~/Alternate.maser" e quindi visitare il sito Web. Ogni pagina deve funzionare senza errori, ad eccezione di due: ~/Admin/AddProduct.aspx e ~/Admin/Products.aspx. L'aggiunta di un prodotto a DetailsView in ~/Admin/AddProduct.aspx restituisce un NullReferenceException oggetto dalla riga di codice che tenta di impostare la proprietà della GridMessageText pagina master. Quando si visita ~/Admin/Products.aspx un oggetto InvalidCastException viene generato al caricamento della pagina con il messaggio : "Impossibile eseguire il cast dell'oggetto di tipo "ASP.alternate_master" per digitare "ASP.site_master".

Questi errori si verificano perché la Site.master classe code-behind include eventi, proprietà e metodi pubblici non definiti in Alternate.master. La parte di markup di queste due pagine ha una @MasterType direttiva che fa riferimento alla Site.master pagina master.

<%@ MasterType VirtualPath="~/Site.master" %>

Inoltre, il gestore eventi di ItemInserted DetailsView in ~/Admin/AddProduct.aspx include il codice che esegue il cast della proprietà di Page.Master tipo libero a un oggetto di tipo Site. La @MasterType direttiva (usata in questo modo) e il cast nel ItemInserted gestore eventi associa strettamente le ~/Admin/AddProduct.aspx pagine e ~/Admin/Products.aspx alla Site.master pagina master.

Per interrompere questo accoppiamento stretto, è possibile avere Site.master e Alternate.master derivare da una classe base comune che contiene definizioni per i membri pubblici. In seguito, è possibile aggiornare la @MasterType direttiva per fare riferimento a questo tipo di base comune.

Creazione di una classe di pagina master di base personalizzata

Aggiungere un nuovo file di classe alla App_Code cartella denominata BaseMasterPage.vb e derivarlo da System.Web.UI.MasterPage. È necessario definire il RefreshRecentProductsGrid metodo e la GridMessageText proprietà in BaseMasterPage, ma non è possibile spostarli da Site.master perché questi membri funzionano con i controlli Web specifici della Site.master pagina master ( RecentProducts GridView e GridMessage Label).

Ciò che è necessario fare è configurare BaseMasterPage in modo che questi membri siano definiti in tale posizione, ma vengono effettivamente implementati dalle BaseMasterPageclassi derivate (Site.master e Alternate.master). Questo tipo di ereditarietà è possibile contrassegnando la classe come MustInherit e i relativi membri come MustOverride. In breve, l'aggiunta di queste parole chiave alla classe e i suoi due membri annuncia che BaseMasterPage non ha implementato RefreshRecentProductsGrid e GridMessageText, ma che le classi derivate lo faranno.

È anche necessario definire l'evento PricesDoubled in BaseMasterPage e fornire un mezzo dalle classi derivate per generare l'evento. Il modello usato in .NET Framework per facilitare questo comportamento consiste nel creare un evento pubblico nella classe di base e aggiungere un metodo protetto e sottoponibile a override denominato OnEventName. Le classi derivate possono quindi chiamare questo metodo per generare l'evento o eseguirne l'override per eseguire il codice immediatamente prima o dopo la generazione dell'evento.

Aggiornare la BaseMasterPage classe in modo che contenga il codice seguente:

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

Passare quindi alla Site.master classe code-behind e fare in modo che derivi da BaseMasterPage. Poiché BaseMasterPage contiene membri contrassegnati MustOverride come è necessario eseguire l'override di tali membri qui in Site.master. Aggiungere la Overrides parola chiave alle definizioni di metodo e proprietà. Aggiornare anche il codice che genera l'evento PricesDoubled nel DoublePrice gestore eventi del Click pulsante con una chiamata al metodo della classe di OnPricesDoubled base.

Dopo queste modifiche, la Site.master classe code-behind deve contenere il codice seguente:

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

È anche necessario aggiornare Alternate.masterla classe code-behind per derivare ed BaseMasterPage eseguire l'override dei due MustOverride membri. Tuttavia, poiché Alternate.master non contiene un controllo GridView che elenca i prodotti più recenti né un'etichetta che visualizza un messaggio dopo l'aggiunta di un nuovo prodotto al database, questi metodi non devono eseguire alcuna operazione.

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

Riferimento alla classe di pagina master di base

Dopo aver completato la BaseMasterPage classe e aver esteso le due pagine master, il passaggio finale consiste nell'aggiornare le ~/Admin/AddProduct.aspx pagine e ~/Admin/Products.aspx per fare riferimento a questo tipo comune. Iniziare modificando la direttiva in entrambe le @MasterType pagine da:

<%@ MasterType VirtualPath="~/Site.master" %>

Con:

<%@ MasterType TypeName="BaseMasterPage" %>

Anziché fare riferimento a un percorso di file, la @MasterType proprietà fa ora riferimento al tipo di base (BaseMasterPage). Di conseguenza, la proprietà fortemente tipizzata Master usata nelle classi code-behind di entrambe le pagine è ora di tipo (anziché di tipo SiteBaseMasterPage ). Con questa modifica sul posto rivedere ~/Admin/Products.aspx. In precedenza, si è verificato un errore di cast perché la pagina è configurata per l'uso della Alternate.master pagina master, ma la @MasterType direttiva ha fatto riferimento al Site.master file. Ma ora viene eseguito il rendering della pagina senza errori. Ciò è dovuto al fatto che è possibile eseguire il cast della Alternate.master pagina master a un oggetto di tipo BaseMasterPage (dal momento che lo estende).

C'è una piccola modifica che deve essere apportata in ~/Admin/AddProduct.aspx. Il gestore eventi del ItemInserted controllo DetailsView usa sia la proprietà fortemente tipizzata Master che la proprietà di tipo Page.Master libero. È stato corretto il riferimento fortemente tipizzato quando è stata aggiornata la @MasterType direttiva, ma è comunque necessario aggiornare il riferimento con tipizzato libero. Sostituire la riga di codice seguente:

Dim myMasterPage As Site = CType(Page.Master, Site)

Con il comando seguente, che esegue il cast Page.Master al tipo di base:

Dim myMasterPage As BaseMasterPage = CType(Page.Master, BaseMasterPage)

Passaggio 4: Determinazione della pagina master da associare alle pagine del contenuto

La BasePage classe imposta attualmente tutte le proprietà delle pagine di MasterPageFile contenuto su un valore hardcoded nella fase PreInit del ciclo di vita della pagina. È possibile aggiornare questo codice per basare la pagina master su un fattore esterno. La pagina master da caricare dipende forse dalle preferenze dell'utente attualmente connesso. In questo caso, è necessario scrivere codice nel OnPreInit metodo in BasePage che cerca le preferenze della pagina master dell'utente attualmente in visita.

Si creerà una pagina Web che consente all'utente di scegliere la pagina master da usare Site.master oppure Alternate.master e salvare questa scelta in una variabile di sessione. Per iniziare, creare una nuova pagina Web nella directory radice denominata ChooseMasterPage.aspx. Quando si crea questa pagina (o qualsiasi altra pagina di contenuto) non è necessario associarla a una pagina master perché la pagina master è impostata a livello di codice in BasePage. Tuttavia, se non si associa la nuova pagina a una pagina master, il markup dichiarativo predefinito della nuova pagina contiene un Web Form e altri contenuti forniti dalla pagina master. Dovrai sostituire manualmente questo markup con i controlli Contenuto appropriati. Per questo motivo, trovo più facile associare la nuova pagina ASP.NET a una pagina master.

Nota

Poiché Site.master e Alternate.master hanno lo stesso set di controlli ContentPlaceHolder, non è importante quale pagina master si sceglie durante la creazione della nuova pagina di contenuto. Per coerenza, è consigliabile usare Site.master.

Aggiungere una nuova pagina contenuto al sito Web

Figura 05: Aggiungere una nuova pagina contenuto al sito Web (fare clic per visualizzare l'immagine a dimensione intera)

Aggiornare il Web.sitemap file in modo da includere una voce per questa lezione. Aggiungere il markup seguente sotto per <siteMapNode> le pagine master e ASP.NET lezione AJAX:

<siteMapNode url="~/ChooseMasterPage.aspx" title="Choose a Master Page" />

Prima di aggiungere contenuto alla ChooseMasterPage.aspx pagina, è necessario un attimo per aggiornare la classe code-behind della pagina in modo che derivi da (anziché System.Web.UI.Page).BasePage Aggiungere quindi un controllo DropDownList alla pagina, impostarne la ID proprietà su MasterPageChoicee aggiungere due elementi ListItem con i Text valori di "~/Site.master" e "~/Alternate.master".

Aggiungere un controllo Web Button alla pagina e impostarne ID le proprietà e Text rispettivamente su SaveLayout e "Save Layout Choice". A questo punto il markup dichiarativo della pagina dovrebbe essere simile al seguente:

<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>

Quando la pagina viene visitata per la prima volta, è necessario visualizzare la scelta della pagina master attualmente selezionata dall'utente. Creare un Page_Load gestore eventi e aggiungere il codice seguente:

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

Il codice precedente viene eseguito solo nella prima pagina visita (e non nei postback successivi). Controlla prima di tutto se la variabile MyMasterPage Session esiste. In caso affermativo, tenta di trovare l'oggetto ListItem corrispondente nell'elenco MasterPageChoice a discesa. Se viene trovato un oggetto ListItem corrispondente, la relativa Selected proprietà viene impostata su True.

È necessario anche il codice che salva la scelta dell'utente nella MyMasterPage variabile Session. Creare un gestore eventi per l'evento SaveLayout button Click e aggiungere il codice seguente:

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

Nota

Al momento dell'esecuzione del Click gestore eventi al postback, la pagina master è già stata selezionata. Pertanto, la selezione dell'elenco a discesa dell'utente non sarà attiva fino alla visita della pagina successiva. Forza Response.Redirect il browser a richiedere ChooseMasterPage.aspxnuovamente .

Al termine della pagina, l'attività ChooseMasterPage.aspx finale consiste nell'assegnare BasePage la MasterPageFile proprietà in base al valore della MyMasterPage variabile Session. Se la variabile Session non è impostata per BasePage impostazione predefinita su 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

Nota

Il codice che assegna la Page proprietà dell'oggetto MasterPageFile al gestore eventi OnPreInit è stato spostato in due metodi separati. Questo primo metodo, SetMasterPageFile, assegna la MasterPageFile proprietà al valore restituito dal secondo metodo, GetMasterPageFileFromSession. Il metodo Overridable è stato contrassegnato SetMasterPageFile in modo che le classi future che si estendono BasePage possano eseguire facoltativamente l'override per implementare la logica personalizzata, se necessario. Nell'esercitazione successiva verrà illustrato un esempio di override BasePagedella proprietà di SetMasterPageFile .

Con questo codice sul posto, visitare la ChooseMasterPage.aspx pagina. Inizialmente, la Site.master pagina master è selezionata (vedere la figura 6), ma l'utente può selezionare una pagina master diversa dall'elenco a discesa.

Le pagine contenuto vengono visualizzate tramite la pagina master Site.master

Figura 06: Le pagine del contenuto vengono visualizzate utilizzando la pagina master (fare clic per visualizzare l'immagine Site.mastera dimensione intera)

Le pagine del contenuto vengono ora visualizzate tramite la pagina master Alternate.master

Figura 07: Le pagine del contenuto sono ora visualizzate usando la pagina master (fare clic per visualizzare l'immagine Alternate.mastera dimensione intera)

Riepilogo

Quando viene visitata una pagina di contenuto, i controlli Contenuto vengono fusi con i controlli ContentPlaceHolder della pagina master. La pagina master della pagina del contenuto è indicata dalla Page proprietà della MasterPageFile classe, assegnata all'attributo della direttiva durante la @Page fase di MasterPageFile inizializzazione. Come illustrato in questa esercitazione, è possibile assegnare un valore alla proprietà purché MasterPageFile lo si verifichi prima della fine della fase PreInit. La possibilità di specificare a livello di codice la pagina master apre la porta per scenari più avanzati, ad esempio l'associazione dinamica di una pagina di contenuto a una pagina master in base a fattori esterni.

Buon programmatori!

Altre informazioni

Per altre informazioni sugli argomenti illustrati in questa esercitazione, vedere le risorse seguenti:

Informazioni sull'autore

Scott Mitchell, autore di più libri ASP/ASP.NET e fondatore di 4GuysFromRolla.com, ha lavorato con le tecnologie Web Microsoft dal 1998. Scott lavora come consulente indipendente, formatore e scrittore. Il suo ultimo libro è Sams Teach Yourself ASP.NET 3.5 in 24 ore. Scott può essere raggiunto all'indirizzo mitchell@4GuysFromRolla.com o tramite il suo blog all'indirizzo http://ScottOnWriting.NET.

Grazie speciale a

Questa serie di esercitazioni è stata esaminata da molti revisori utili. Il revisore principale per questa esercitazione era Suchi Banerjee. Si è interessati a esaminare i prossimi articoli MSDN? In tal caso, lasciami una riga in mitchell@4GuysFromRolla.com