Forms are used to obtain data from a user. They comprise one or more inputs, each one designed to gather data of a particular type. In a typical server-side web application, the form also includes a control for submitting the form values for processing by application logic on the server. When this control is clicked, the raw form data is sent to the server using a GET
or POST
HTTP request with a content type of x-www-form-urlencoded
.
Single page applications work a little differently. In this model, it is more usual to serialise the values of the form fields to JSON and send that to the server for processing. Some SPA frameworks (including Blazor) provide a data binding mechanism that enables you to bind properties of a model to individual form fields, and then to serialise the model to JSON to be passed to a server-side API for processing.
In Blazor applications, while you can use standard HTML to render form controls, the EditForm component is the recommended tool for building forms. Each EditForm component acts as a parent component to any number of input validation components and optionally, validation message components. The EditForm is dependent on an EditContext, an object that holds information about the current state of the data editing process, such as which fields have been modified and the current validation state of the form together with any validation messages. This feature, built-in validation management, is one of the primary reasons for favouring the EditForm over standard HTML for constructing a form in a Blazor application.
The EditForm itself has a number of properties which are detailed in the following table.
Table 1. EditForm properties
Property | Description |
---|---|
AdditionalAttributes |
This is used for getting or setting a collection of additional attributes that will be applied to the rendered form element. |
ChildContent |
Specifies any content to be rendered inside the EditForm. |
EditContext |
Specifies the edit context explicitly. If using this parameter, do not also supply Model , since the model value will be taken from the Model property. |
Model |
Specifies the top-level model object for the form. An edit context will automatically be constructed for this model. If using this parameter, do not also supply a value for EditContext . |
OnInvalidSubmit |
A callback that is invoked when the form is submitted and the EditContext is determined to be invalid. |
OnSubmit |
A callback that will be invoked when the form is submitted. If using this parameter, you are responsible for triggering any validation manually, e.g., by calling Validate() . |
OnValidSubmit |
A callback that will be invoked when the form is submitted and the EditContext is determined to be valid. |
The data in the form is represented by the Model
property. This is passed to the EditForm when it is declared:
<EditForm Model="Person">
Internally, the EditForm wraps the specified model in an EditContext
which, as already described, keeps track of the state of the data editing process. Alternatively, we can construct the EditContext
explicitly, passing in the model and then assign that to the EditContext
parameter of the EditForm:
<EditForm EditContext="context">
@code{
var context = new EditContext(new Person());
}
EditContext or Model?
This raises the question of when to directly pass a model to the form, and when to explicitly construct an EditContext
wrapper for the model and pass that in. Most often, you will pass a model directly to the form. You would only construct an instance of an EditContext when you want to access properties, methods, or more likely, events of the EditContext
, which you might do if you want to take control over some aspect of validation, for example.
Input Validation Components
Blazor includes a number of different input validation components that render as standard HTML form controls, each one designed to cater for a different type of data. The built-in input validation components are detailed below in table 2.
Table 2. The standard Blazor input validation components
Component | HTML | UI |
---|---|---|
InputCheckbox |
<input type="checkbox"> |
|
InputDate<TValue> |
<input type="date"> |
|
InputFile |
<input type="file"> |
|
InputNumber<TValue> |
<input type="number"> |
|
InputRadio<TValue> |
<input type="radio"> |
|
InputSelect<TValue> |
<select> |
|
InputText |
<input> |
|
InputTextArea |
<textarea></textarea> |
In addition, Blazor provides an InputRadioGroup<TValue>
, which houses a group of child InputRadio<TValue>
components so that they share the same name
attribute. This is used when you want to present the user with a mutually exclusive selection and a select element is not appropriate. For example, you ,might use this if you want to offer the user the option to select either a morning or an afternoon appointment.
Input validation components derive from InputBase<TValue>
, which exposes a number of properties and methods, the most commonly used of which are detailed in table 3.
Table 3. Properties and methods of InputBase<TValue>
Property/Method | Description |
---|---|
Value |
Gets or sets the value of the input |
ValueChanged |
Gets or sets a callback that updates the bound value |
DisplayName |
Gets or sets the display name for this field. |
FieldIdentifier |
Gets the FieldIdentifier for the bound value |
CurrentValue |
Gets or sets the current value of the input and notifies the EditContext if the value has changed |
CssClass |
Gets a string consisting of an HTML class attribute and "valid" or "invalid" combined with "modified" if appropriate to indicate the status of the field |