Содержание
Как правило, компонент представления наследуется от ViewComponent
, инициализирует модель и передает ее в представление, вызвав один из перегруженных методов View()
класса ViewComponent
. Именно эти методы генерирует объект ViewComponentResult
.
Метод View() класса ViewComponent
В базовом классе компонента представлений ViewComponent
опрелены следующие перегруженные версии метода View():
View() |
Возвращает результат, который будет отображать частичное представление с именем Default . |
View(string? viewName) |
Возвращает результат, который будет отображать частичное представление с именем viewName . |
View<TModel>(TModel? model) |
Возвращает результат, который будет отображать частичное представление с именем Default . При этом, в представление передается модель model
|
View<TModel>(string? viewName, TModel? model) |
Возвращает результат, который будет отображать частичное представление с именем viewName . При этом, в представление передается модель model |
Первое, на что необходимо обратить внимание — это то, что, если в метод View()
не передается имя представления, то ASP.NET Core MVC использует некое частичное представление по умолчанию с именем Default
. Как мы знаем, такого представления по умолчанию в пустом проекте ASP.NET Core MVC нет и, следовательно, его необходимо будет создать.
Второй момент — как производится поиск частичного представления. Опять же, по умолчанию, поиск необходимого частичного представления осуществляется по следующим путям:
- /Views/{Имя контроллера}/Components/{Имя компонента представления}/{Имя представления}
- /Views/Shared/Components/{Имя компонента представления}/{Имя представления}
- /Pages/Shared/Components/{Имя компонента представления}/{Имя представления}
- /Area/{Имя области}/Views/Shared/Components/{View Component Name}/{View Component Name}/{View Name}
Сами разработчики Microsoft дают следующую рекомендацию по размещению частичного представления Default.cshtml: использовать путь Views/Shared/Components/{View Component Name}/{View Name}.
Например, если наш компонент называется DayInfo
, то рекомендуемый путь будет таким: Views/Shared/Components/DayInfo/Default.cshtml
С теорией немного разобрались, теперь перейдем к практике.
Использование метода View()
В качестве примера, разработаем небольшой компонент, представляющий меню навигации. Создадим новый пустой проект ASP.NET Core MVC, добавим в него папку Components и в этой папке создадим файл с именем Menu.cs
:
Содержимое файла будет следующим:
using Microsoft.AspNetCore.Mvc; namespace AspMvcComponents.Components { public class MenuItem { public string Name { get; set; } public string Link { get; set; } } public class Menu: ViewComponent { public IViewComponentResult Invoke(List<MenuItem> items) { return View(items); } } }
Всё, что делает наш компонент — это принимает список компонентов меню и передает их в представление, используя для этого метод View()
. При этом, использоваться будет частичное представление с именем Default.cshtml
. Теперь создадим частичное представление Default.cshtml. Расположим этот файл в папке Views/Shared/Components/Menu/Default.cshtml:
Содержимое представления:
@using AspMvcComponents.Components @model IEnumerable<MenuItem> <ul> @foreach (var item in Model) { <li><a href="@item.Link">@item.Name</a></li> } </ul>
В представлении используется модель нашего меню, а данные мы получим из компонента. Теперь зарегистрируем наш компонент в качестве tag-хэлпера и разместим его в любом другом представлении (или в нескольких, если потребуется). Например, воспользуемся представлением Index.cshtml:
@addTagHelper *, AspMvcComponents @using AspMvcComponents.Components @{ ViewData["Title"] = "Home Page"; } <vc:menu items="@(new() { new MenuItem() { Name="Главная", Link = "/"}, new MenuItem() { Name="Privacy", Link = "/home/privacy"} })"> </vc:menu>
В качестве параметров, мы передали в компонент список пунктов меню. Теперь запустим приложение и получим следующий результат:
В этом простом примере прослеживаются преимущества компонентов представлений — сам компонент может считывать данные, например, из базы данных и передавать их в частичное представление, которое будет отвечать за рендеринг HTML-кода и, при этом, сам компонент мы можем многократно использовать в различных представлениях нашего приложения.
Если необходимо использовать для рендеринга другое частичное представление, имя которого отличается от Default.cshtml, мы можем также разместить его в папке для частичных представлений компонента и использовать в коде компонента, например, так:
public IViewComponentResult Invoke(List<MenuItem> items) { return View("menu", items); }
здесь «menu» — это имя частичного представления для компонента.
Настройка пути поиска представления
Иногда бывает не совсем удобно держать код компонента в одной папке, а частичное представление для этого компонента — в другой. ASP.NET Core MVC позволяет настраивать пути поиска частичных представлений компонентов. Например, настроим путь поиска таким образом, чтобы частичное представление находилось в той же папке, что и код компонента. Для этого перейдем в файл Program.cs и добавим настройки для сервиса:
builder.Services.AddControllersWithViews().AddRazorOptions(options => { options.ViewLocationFormats.Add("/{0}.cshtml"); });
Здесь заполнитель {0}
будет соответствовать пути Components/{View Component Name}/{View Name}
. Чтобы использовать этот путь поиска, изменим немного структуру нашего проекта, а именно — создадим для нашего компонента и его представления отдельную папку в папке Components. Должна получиться вот такая структура проекта:
Теперь можно снова запустить проект и убедиться, что частичное представление берется по пути /Components/Menu/Default.cshtml:
Итого
Компоненты представлений могут передавать данные в частичные представления, используя методы View()
родительского компонента ViewComponent
. Частичное представление компонента должно располагаться по одному из путей по умолчанию или же путь можно настроить, используя настройки сервисов в приложении.