Delen via


Indeling in ASP.NET Core

Door Steve Smith en Dave Brock

Pagina's en schermweergaven delen vaak visuele en programmatische elementen. Dit artikel laat zien hoe je dat doet:

  • Gebruik algemene indelingen.
  • Deel instructies.
  • Voer algemene code uit voordat u pagina's of weergaven weergeeft.

In dit document worden indelingen besproken voor de twee verschillende benaderingen voor ASP.NET Core MVC: Razor Pagina's en controllers met weergaven. Voor dit onderwerp zijn de verschillen minimaal:

  • Razor Pagina's bevinden zich in de map Pagina's .
  • Controllers met weergaven maken gebruik van een map Weergaven voor weergaven.

Wat is een indeling?

De meeste web-apps hebben een algemene indeling die de gebruiker een consistente ervaring biedt wanneer ze van pagina naar pagina navigeren. De indeling bevat doorgaans algemene elementen van de gebruikersinterface, zoals de koptekst van de app, navigatie of menu-elementen en voettekst.

Voorbeeld van pagina-indeling

Algemene HTML-structuren, zoals scripts en opmaakmodellen, worden ook vaak gebruikt door veel pagina's in een app. Al deze gedeelde elementen kunnen worden gedefinieerd in een indelingsbestand , waarnaar vervolgens kan worden verwezen door elke weergave die in de app wordt gebruikt. Lay-outs verminderen dubbele code in weergaven.

Standaard heeft de standaardindeling voor een ASP.NET Core-app de naam _Layout.cshtml. De indelingsbestanden voor nieuwe ASP.NET Core-projecten die met de sjablonen zijn gemaakt, zijn:

  • Razor Bladzijden: Pages/Shared/_Layout.cshtml

    Paginamap in Solution Explorer

  • Controller met weergaven: Views/Shared/_Layout.cshtml

    Weergaven-map in Solution Explorer

De indeling definieert een sjabloon op het hoogste niveau voor weergaven in de app. Voor apps is geen indeling vereist. Apps kunnen meer dan één indeling definiëren, met verschillende weergaven die verschillende indelingen opgeven.

De volgende code toont het lay-outbestand voor een project dat met behulp van een sjabloon is gemaakt, met een controller en views.

<!DOCTYPE html>
<html>
<head>
    <meta charset="utf-8" />
    <meta name="viewport" content="width=device-width, initial-scale=1.0" />
    <title>@ViewData["Title"] - WebApplication1</title>

    <environment include="Development">
        <link rel="stylesheet" href="~/lib/bootstrap/dist/css/bootstrap.css" />
        <link rel="stylesheet" href="~/css/site.css" />
    </environment>
    <environment exclude="Development">
        <link rel="stylesheet" href="https://ajax.aspnetcdn.com/ajax/bootstrap/3.3.7/css/bootstrap.min.css"
              asp-fallback-href="~/lib/bootstrap/dist/css/bootstrap.min.css"
              asp-fallback-test-class="sr-only" asp-fallback-test-property="position" asp-fallback-test-value="absolute" />
        <link rel="stylesheet" href="~/css/site.min.css" asp-append-version="true" />
    </environment>
</head>
<body>
    <nav class="navbar navbar-inverse navbar-fixed-top">
        <div class="container">
            <div class="navbar-header">
                <button type="button" class="navbar-toggle" data-toggle="collapse" data-target=".navbar-collapse">
                    <span class="sr-only">Toggle navigation</span>
                    <span class="icon-bar"></span>
                    <span class="icon-bar"></span>
                    <span class="icon-bar"></span>
                </button>
                <a asp-page="/Index" class="navbar-brand">WebApplication1</a>
            </div>
            <div class="navbar-collapse collapse">
                <ul class="nav navbar-nav">
                    <li><a asp-page="/Index">Home</a></li>
                    <li><a asp-page="/About">About</a></li>
                    <li><a asp-page="/Contact">Contact</a></li>
                </ul>
            </div>
        </div>
    </nav>

    <partial name="_CookieConsentPartial" />

    <div class="container body-content">
        @RenderBody()
        <hr />
        <footer>
            <p>&copy; 2018 - WebApplication1</p>
        </footer>
    </div>

    <environment include="Development">
        <script src="~/lib/jquery/dist/jquery.js"></script>
        <script src="~/lib/bootstrap/dist/js/bootstrap.js"></script>
        <script src="~/js/site.js" asp-append-version="true"></script>
    </environment>
    <environment exclude="Development">
        <script src="https://ajax.aspnetcdn.com/ajax/jquery/jquery-3.3.1.min.js"
                asp-fallback-src="~/lib/jquery/dist/jquery.min.js"
                asp-fallback-test="window.jQuery"
                crossorigin="anonymous"
                integrity="sha384-tsQFqpEReu7ZLhBV2VZlAu7zcOV+rXbYlF2cqB8txI/8aZajjp4Bqd+V6D5IgvKT">
        </script>
        <script src="https://ajax.aspnetcdn.com/ajax/bootstrap/3.3.7/bootstrap.min.js"
                asp-fallback-src="~/lib/bootstrap/dist/js/bootstrap.min.js"
                asp-fallback-test="window.jQuery && window.jQuery.fn && window.jQuery.fn.modal"
                crossorigin="anonymous"
                integrity="sha384-Tc5IQib027qvyjSMfHjOMaLkfuWVxZxUPnCJA7l2mCWNIpG9mGCD8wGNIcPD7Txa">
        </script>
        <script src="~/js/site.min.js" asp-append-version="true"></script>
    </environment>

    @RenderSection("Scripts", required: false)
</body>
</html>

Een indeling opgeven

Razor weergaven hebben een Layout eigenschap. Afzonderlijke weergaven geven een indeling op door deze eigenschap in te stellen:

@{
    Layout = "_Layout";
}

De opgegeven indeling kan een volledig pad (bijvoorbeeld /Pages/Shared/_Layout.cshtml of /Views/Shared/_Layout.cshtml) of een gedeeltelijke naam (bijvoorbeeld: _Layout) gebruiken. Wanneer er een gedeeltelijke naam wordt opgegeven, zoekt de Razor weergave-engine naar het indelingsbestand met behulp van het standaarddetectieproces. De map waarin de handlermethode (of controller) bestaat, wordt eerst doorzocht, gevolgd door de gedeelde map. Dit detectieproces is identiek aan het proces dat wordt gebruikt om gedeeltelijke weergaven te detecteren.

Standaard moet elke indeling RenderBody aanroepen. Waar de aanroep naartoe RenderBody wordt geplaatst, wordt de inhoud van de weergave weergegeven.

Afdelingen

Een indeling kan desgewenst verwijzen naar een of meer secties door aan te roepen RenderSection. Secties bieden een manier om te ordenen waar bepaalde pagina-elementen moeten worden geplaatst. Elke aanroep naar RenderSection kan specificeren of deze sectie vereist of optioneel is.

<script type="text/javascript" src="~/scripts/global.js"></script>

@RenderSection("Scripts", required: false)

Als er geen vereiste sectie wordt gevonden, wordt er een uitzondering gegenereerd. In afzonderlijke weergaven wordt de inhoud opgegeven die in een sectie moet worden weergegeven met behulp van de @sectionRazor syntaxis. Als een pagina of weergave een sectie definieert, moet deze worden weergegeven (of er treedt een fout op).

Een voorbeelddefinitie @section in Razor de Pagina's-weergave:

@section Scripts {
     <script type="text/javascript" src="~/scripts/main.js"></script>
}

In de voorgaande code scripts/main.js wordt deze toegevoegd aan de scripts sectie op een pagina of weergave. Voor andere pagina's of weergaven in dezelfde app is dit script mogelijk niet vereist en wordt er geen sectie met scripts gedefinieerd.

De volgende markering maakt gebruik van de Partiële Tag Helper om _ValidationScriptsPartial.cshtml weer te geven.

@section Scripts {
    <partial name="_ValidationScriptsPartial" />
}

De voorgaande markeringen zijn gegenereerd door scaffolding Identity.

Secties die zijn gedefinieerd in een pagina of weergave, zijn alleen beschikbaar op de directe indelingspagina. Er kan niet naar worden verwezen vanuit partials, weergavecomponenten of andere delen van het weergavesysteem.

Secties negeren

Standaard moeten de hoofdtekst en alle secties op een inhoudspagina allemaal worden weergegeven door de indelingspagina. De Razor weergave-engine dwingt dit af door bij te houden of de hoofdtekst en elke sectie zijn weergegeven.

Als u de weergave-engine wilt instrueren om de hoofdtekst of secties te negeren, roept u de IgnoreBody en IgnoreSection methoden aan.

De hoofdtekst en elke sectie op een Razor pagina moeten worden weergegeven of genegeerd.

Gedeelde richtlijnen importeren

Weergaven en pagina's kunnen Razor directieven gebruiken om naamruimten te importeren en afhankelijkheidsinjectie te gebruiken. Richtlijnen die door veel weergaven worden gedeeld, kunnen worden opgegeven in een gemeenschappelijk _ViewImports.cshtml bestand. Het _ViewImports bestand ondersteunt de volgende instructies:

  • @addTagHelper
  • @removeTagHelper
  • @tagHelperPrefix
  • @using
  • @model
  • @inherits
  • @inject
  • @namespace

Het bestand biedt geen ondersteuning voor andere Razor functies, zoals functies en sectiedefinities.

Een voorbeeldbestand _ViewImports.cshtml :

@using WebApplication1
@using WebApplication1.Models
@using WebApplication1.Models.AccountViewModels
@using WebApplication1.Models.ManageViewModels
@using Microsoft.AspNetCore.Identity
@addTagHelper *, Microsoft.AspNetCore.Mvc.TagHelpers

Het _ViewImports.cshtml bestand voor een ASP.NET Core MVC-app wordt meestal in de map Pagina's (of weergaven) geplaatst. Een _ViewImports.cshtml bestand kan in elke map worden geplaatst. In dat geval wordt het alleen toegepast op pagina's of weergaven in die map en de bijbehorende submappen. _ViewImports bestanden worden verwerkt vanaf het hoofdniveau en vervolgens voor elke map die leidt tot de locatie van de pagina of weergave zelf. _ViewImports instellingen die zijn opgegeven op het hoofdniveau, kunnen worden overschreven op mapniveau.

Stel bijvoorbeeld:

  • Het hoofdniveaubestand _ViewImports.cshtml bevat @model MyModel1 en @addTagHelper *, MyTagHelper1.
  • Een submapbestand _ViewImports.cshtml bevat @model MyModel2 en @addTagHelper *, MyTagHelper2.

Pagina's en weergaven in de submap hebben toegang tot zowel Tag Helpers als het MyModel2 model.

Als er meerdere _ViewImports.cshtml bestanden in de bestandshiërarchie worden gevonden, is het gecombineerde gedrag van de instructies:

  • @addTagHelper, : @removeTagHelperalle uitgevoerd, in volgorde
  • @tagHelperPrefix: het dichtstbijzijnde zicht vervangt alle andere
  • @model: het dichtstbijzijnde exemplaar van de weergave overschrijft alle andere
  • @inherits: het element het dichtst bij het zicht overschrijdt alle anderen
  • @using: alle zijn inbegrepen; duplicaten worden genegeerd
  • @inject: voor elke eigenschap overschrijft degene die het dichtst bij de weergave ligt alle andere met dezelfde eigenschapsnaam

Code uitvoeren vóór elke weergave

Code die moet worden uitgevoerd voordat elke weergave of pagina in het _ViewStart.cshtml bestand moet worden geplaatst. Volgens de conventie bevindt het _ViewStart.cshtml bestand zich in de map Pagina's (of Weergaven). De instructies die in _ViewStart.cshtml worden vermeld, worden uitgevoerd vóór elke volledige weergave (geen indelingen en geen gedeeltelijke weergaven). Net als ViewImports.cshtml is _ViewStart.cshtml hiërarchisch. Als een _ViewStart.cshtml bestand is gedefinieerd in de map weergave of pagina's, wordt het uitgevoerd nadat het bestand is gedefinieerd in de hoofdmap van de map Pagina's (of weergaven) (indien van toepassing).

Een voorbeeldbestand _ViewStart.cshtml :

@{
    Layout = "_Layout";
}

In het bovenstaande bestand wordt aangegeven dat alle weergaven gebruikmaken van de _Layout.cshtml indeling.

_ViewStart.cshtml en _ViewImports.cshtml worden meestal niet in de map /Pages/Shared (of /Views/Shared) geplaatst. De versies op app-niveau van deze bestanden moeten rechtstreeks in de map /Pages (of /Views) worden geplaatst.