Вложенные компоненты. Параметры компонентов

Последнее обновление: 29.11.2023

Компоненты могут содержать другие компоненты. Работа приложения Blazor начинается с выполнения главного компонента, который, в свою очередь, содержит остальные компоненты. В прошлой теме был рассмотрен добавление и рендеринг главного компонента приложения. Однако добавление дочерних компонентов отличается - для добавления дочернего компонента используется тег, назначение которого совпадает с названием компонента. Например, определим в проекте для неглавных компонентов папку Components. И добавим в нее новый компонент - Home.razor:

Вложенные компоненты Razor в Blazor в C#

Определим в компоненте Home.razor:

<h2>@header</h2>

@code{
    string header = "Главная страница";
}

Вызовем этот компонент в главном компоненте App.razor:

@page "/"

<!DOCTYPE html>
<html>
<head>
    <title>METANIT.COM</title>
    <meta charset="utf-8" />
</head>
<body>
    <h1>@header</h1>
    <Home />
</body>
</html>
@code {
    string header = "Приложение Blazor";
}

Для добавления компонента Home определяем его как обычный html-элемент:

<Home />

Вместо сокращенной записи можно явным образом определить открывающий и закрывающий теги элемента:

<Home></Home>

Таким образом, компонент App в данном случае является родительским и содержит дочерний компонент Home.

Вложенные компоненты Razor в приложении Blazor на C#

Параметры компонентов

Компоненты существуют независимо друг от друга. Переменные и методы одного компонента применяются только в рамках этого компонента. Например, в примеры выше оба компонента определяли свою собственную переменную header. Тем не менее существует возможность передачи данных из родительского компонента в дочерний. Эту возможность предоставляют параметры компонента - публичные свойства компонента, к которым применяется атрибут Parameter. Например, изменим компонент Home.razor:

<h2>@Title</h2>

@code {
    [Parameter]
    public string Title { get; set; } = "Default Title";
}

Теперь компонент содержит одно свойство Title, к которому применяется атрибут [Parameter], поэтому это свойство можно назвать параметром компонента. Через это свойства компонент может получить извне некоторые данные.

Следует учитывать, что подобные свойства-параметры должны представлять автосвойства, у которых блоки set и get не содержат никакой логики.

Далее изменим вызов компонента Home в родительском компоненте App:

@page "/"
<!DOCTYPE html>
<html>
<head>
    <title>METANIT.COM</title>
    <meta charset="utf-8" />
</head>
<body>
    <h1>Hello Blazor</h1>
    <Home Title="Home Page" />
    <Home Title="@someTitle" />
    <Home />
</body>
</html>

@code {
    string someTitle = "Main Page";
}

Здесь определяется три вложенных компонента Home. Через атрибуты, названия которых совпадают с названиями параметров компонента, можно передать этим параметрам некоторые данные. Причем можно передать параметру компонента значение некоторого выражения, например, переменной, как в случае со вторым вызовом Home. Если не передать значения, то свойства компонента получат значения по умолчанию.

Параметры компонентов Razor в Blazor

Причем можно передавать более сложное содержимое, нежели простые строки. Например, пусть Home.razor принимает список строк:

<h2>Количество пользователей: @Count</h2>
<ul>
    @foreach(var user in Users)
    {
        <li>@user</li>
    }
</ul>

@code{

    [Parameter]
    public List<string> Users { get; set; } = new();

    [Parameter]
    public int Count { get; set; }
}

Теперь компонент получает список и выводит его в коде html. Передадим этот список в родительском компоненте App:

@page "/"
<h1>Приложение Blazor</h1>
<Home Count="@users.Count" Users="@users"></Home>

@code{
    List<string> users = new List<string> { "Tom", "Bob", "Sam", "Mike" };
}
Передача данных из компонента в компонент в Blazor

Обязательные параметры

По умолчанию если свойствам-параметрам не передано значение, то они получают значение по умолчанию. Но иногда требуется, чтобы параметрам-свойствам извне обязательно передавалось некоторое значение. В этом случае можно использовать атрибут [EditorRequired]:

<h2>@Title</h2>

@code {
    [Parameter]
    [EditorRequired]
    public string Title { get; set; } = "";
}

В этом случае, если не передать значение параметру Title, ошибки не произойдет. Однако на уровне статического анализатора кода в Visual Studio мы получим предупреждение, что значение необходимо передать:

Атрибут EditorRequired и установка параметров компонентов Blazor

Передача множественных значений

Если надо передать несколько различных значений, то мы можем для всех этих значений определить соответствующие свойства-параметра. Например, код Home.razor:

<ul>
    <li>Name: @Name</li>
    <li>Age: @Age</li>
    <li>IsMarried: @IsMarried</li>
</ul>

@code {
    [Parameter]
    public string Name { get; set; } = "";
    [Parameter]
    public int Age { get; set; }
    [Parameter]
    public bool IsMarried { get; set; }
}

И в компоненте App мы можем передать этим свойствам какие-нибудь значения:

@page "/"
<Home Name="Tom" Age="38" IsMarried="false" />
Передача данных в компонент Blazor через кортеж

В качестве альтернативы можно сгруппировать все значения через кортеж. Так, изменим компонент Home следуюшим образом:

<ul>
    <li>Name: @Data?.Item1</li>
    <li>Age: @Data?.Item2</li>
    <li>IsMarried: @Data?.Item3</li>
</ul>

@code {
    [Parameter]
    public Tuple<string, int, bool>? Data { get; set; }
}

А в компоненте App передать значения в Home:

@page "/"
<Home Data="@data" />

@code {
    Tuple<string, int, bool> data = new("Tom", 38, false);
}

Передача содержимого из родительского в дочерний компонент

С помощью свойства ChildContent в дочерний компонент можно передать из родительского некоторое содержимое. Например, изменим компонент Home.razor следующим образом:

<h2>@Title</h2>
<div>@ChildContent</div>
<hr />
<div>Условный футер</div>

@code{
    [Parameter]
    public string Title { get; set; } = "";

    [Parameter]
    public RenderFragment? ChildContent { get; set; }
}

Согласно условностям свойство должно называться именно ChildContent, и оно должно представлять тип RenderFragment. В остальном оно используется аналогично другим свойствам. Например, его содержимое можно вывести на веб-страницу где-нибудь в разметке компонента.

Теперь изменим родительский компонент App:

@page "/"
<h1>Приложение Blazor</h1>
<Home Title="Главная страница">
    Случайное содержимое дочернего компонента
</Home>

Все то, что передается между открывающим и закрывающим тегами <Home> и </Home> и будет представлять свойство ChildContent дочернего компонента

ChildContent и RenderFragment в Blazor и C#

Передаваемое содержимое может быть и более сложным, нежели простая строка. Например, можно передать код html. Так, изменим родительский компонент App.razor:

@page "/"
<h1>Приложение Blazor</h1>
<Home Title="Главная страница">
    <div>
        <h3>Отрывок</h3>
        <p>Высокой страсти не имея</p>
        <p>Для кода жизни не щадить,</p>
        <p>Не мог он джаву от сишарпа</p>
        <p>Как мы ни бились, отличить.</p>
    </div>
</Home>
ChildContent и RenderFragment в компонентах Blazor
Помощь сайту
Юмани:
410011174743222
Перевод на карту
Номер карты:
4048415020898850