ASP.NET Core中的视图组件介绍

admin
admin
2022-03-08
分享:

ASP.NET Core中的视图组件介绍-非常好用

导航:

在本视频中,我们将通过示例讨论ASP.NET Core中的View Components。

除了页面特定的内容外,我们还希望在应用程序的多个页面上显示以下学生人数统计摘要。

由于我们要在几页上显示“学生人数统计摘要”,因此创建可重用的组件很有意义。

我们不想做的是在每个页面上都包含代码。这种方法重复了代码。

我们也不能使用分部视图,因为分部视图,只能显示一些简单的数据,而不能让它去访问数据源,并且进行逻辑处理。

当然他能不能做,答案是可以的,但是在我们的基础课程中说了,视图尽可能的少包含逻辑,不要作复杂运算,这样会减低性能。

毕竟视图文件,它取决于从父视图或 Razor Pages传递的数据。我们不想在每页上都包含用于查询数据的代码。

我们提到的统计数据的业务需求,会产生很多的代码重复。我们需要可以独立查询数据并进行渲染的东西。 所以View Component是一个完美的选择。

创建视图组件文件夹

在项目根目录中,创建“ViewComponents ”文件夹。 我们将所有视图组件放置在此文件夹中。添加一个名称为-HeadCountViewComponent.cs的新类文件。复制并粘贴以下代码。


using Microsoft.AspNetCore.Mvc;
using YoYoMooc.StudentManagement.Services;

namespace StudentManagement.RazorPage.ViewComponents
{
    public class HeadCountViewComponent : ViewComponent
    {
        private readonly IStudentRepository studentRepository;

        public HeadCountViewComponent(IStudentRepository studentRepository)
        {
            this.studentRepository = studentRepository;
        }

        public IViewComponentResult Invoke()
        {
            var result = studentRepository.StudentCountByMajorEnum();
            return View(result);
        }
    }
}

视图组件类分析

  1. 视图组件类名称以后缀ViewComponent结尾
  2. 它继承自ViewComponent基类
  3. 它支持依赖项注入,就像 Razor Pages或MVC控制器一样
  4. 视图组件不会直接响应HTTP请求。它通常由 Razor Pages,布局视图或MVC视图调用和使用。
  5. 当视图组件被调用时,它调用Invoke方法。
  6. Inovke()方法返回IViewComponentResult。
  7. 如果要异步调用视图组件,请使用InvokeAsync()方法。
  8. 视图组件遵循MVC设计模式。它通过调用View方法来初始化模型并将其传递给视图。
  9. 尽管它遵循MVC方法,但它既可以在MVC项目中也可以在 Razor Pages项目中使用。

组件视图发现规则

ASP.NET Core 中的视图组件会按照以下规则进行视图组件的查找

Razor pages 项目的查找规则

  • /Pages/Shared/Components/{视图组件名称}/{视图名称}

MVC 项目的查找规则

  • /Views//Components/{视图组件名称}/{视图名称}
  • /Views/Shared/Components/{视图组件名称}/{视图名称}

创建视图组件视图文件

  • 在“ Shared”文件夹中,创建“Components”文件夹。
  • 在“ Components”文件夹中,创建一个与“视图组件”同名的文件夹。我们的视图组件名称为HeadCountViewComponent。因此,创建一个名为HeadCount的文件夹。不需要后缀ViewComponent
  • 在此文件夹中创建一个名称为Default.cshtml的文件

此时,文件夹结构应如下所示。

将以下代码复制并粘贴到Default.cshtml


@model IEnumerable<MajorHeadCount>

<h3>学生人数汇总</h3>

<table class="table table-bordered">
    <thead class="thead-light">
        <tr>
            <th>专业</th>
            <th>合计人数</th>
        </tr>
    </thead>
    <tbody>
        @foreach (var item in Model)
        {
            <tr>
                <td>@item.Major</td>
                <td>@item.Count</td>
            </tr>
        }
    </tbody>
</table>

渲染视图组件

使用Component.InvokeAsync调用视图组件。我们要从“详细信息” Razor Pages渲染它。因此,在Details.cshtml页面上包含以下代码。


@await Component.InvokeAsync("HeadCount")

配套的类文件

模型项目中的 MajorHeadCount.cs


namespace YoYoMooc.StudentManagement.Models
{

    public class MajorHeadCount
    {
        public MajorEnum Major { get; set; }
        public int Count { get; set; }
    }
}

模型项目中的IStudentRepository.cs

namespace YoYoMooc.StudentManagement.Services
{
    public interface IStudentRepository
    {
        // 其他方法
        IEnumerable<MajorHeadCount> StudentCountByMajorEnum();

    }
}

模型项目中的MockStudentRepository.cs


namespace YoYoMooc.StudentManagement.Services
{
    public class MockStudentRepository : IStudentRepository
    {
        private List<Student> _studentList;

        public MockStudentRepository()
        {
             _studentList = new List<Student>()
            {
                 new Student() { Id = 1, Name = "张三", Major = MajorEnum.ComputerScience, Email = "Tony-zhang@52abp.com" },
            new Student() { Id = 2, Name = "李四", Major = MajorEnum.ElectronicCommerce, Email = "lisi@52abp.com" },
            new Student() { Id = 3, Name = "王二麻子", Major = MajorEnum.Mathematics, Email = "wang@52abp.com" },
            };
        }

     public IEnumerable<MajorHeadCount> StudentCountByMajorEnum()
        {
         var dtos= _studentList.GroupBy(e => e.Major)
                                 .Select(g => new MajorHeadCount()
                                 {
                                     Major = g.Key.Value,
                                     Count = g.Count()
                                 }).ToList();

            return dtos;
        }
}