In the last lesson, the Kladde’s pages moved to Blazor, but every page is still a single block of HTML. In this lesson you break them down into components: small building blocks with one job that get values from outside and look the same everywhere. It’s the same principle as with methods and classes in K1: Whatever appears twice or is understandable on its own gets a name.
In the end, the pages have three building blocks: a page header PageHeader, the list ContactList and a contact’s row ContactCard. Each
brings its own stylesheet, and the look stays as it was.
Building a component
Every .razor file is a component, even one without @page. The page header is the first building block: a heading with a frame around
it. In the Kladde, create src/Kladde.Web/Components/Shared/PageHeader.razor:
<div class="page-header">
<h1>@Title</h1>
</div>
@code {
[Parameter]
public string Title { get; set; } = string.Empty;
}
A parameter is a public property with the attribute [Parameter]. Whoever uses the component sets it like an HTML attribute. So that
the name PageHeader is known everywhere, add the folder’s namespace to Components/_Imports.razor:
@using Kladde.Web.Components.Shared
Then the home page writes, instead of <h1>Kladde</h1>:
<PageHeader Title="Kladde" />
Components begin with an uppercase letter, HTML elements with a lowercase one. That’s how the compiler knows what’s meant. A typo like
<Pageheader> is therefore not an error but an unknown HTML element; the compiler warns with RZ10012, and because warnings are errors in
the Kladde, the build fails.
What goes in an attribute
For a parameter of type string, the value is text. With @, you give a C# expression instead:
<PageHeader Title="Contacts" />
<PageHeader Title="@pageTitle" />
<PageHeader Title="@($"Contacts ({count})")" />
For all other types, the value is always C#, even without @. So Contacts="contacts" passes the field contacts, not the text
“contacts”. You may write the @ all the same, and many people do for clarity.
Required parameters
A page header without a title is a mistake. The compiler should find this mistake, not only someone who looks at the page. That’s what
[EditorRequired] is for:
@code {
[Parameter, EditorRequired]
public string Title { get; set; } = string.Empty;
}
If Title is missing where the component is used, the Razor compiler reports the warning RZ2012. In the Kladde, warnings are errors, so
the build stops:
Contacts.razor(8,1): error RZ2012: Component 'PageHeader' expects a value for the parameter 'Title', but a value may not have been provided.
The initial value string.Empty is still necessary, because nullable is on, and the compiler doesn’t know that Blazor sets the parameter.