Component Communication
Real UIs are many components working together. Choosing the right communication pattern keeps them simple and predictable.
On this page · 5 min · Intermediate
On this page
- Learning objectives
- Explanation
- Code example
- Step by step
- Real-world use
- Common mistakes
- Best practices
- Remember this
- Practice exercise
- Mini quiz
- Related topics
- My notes
- Reading time
- 5 min
- Difficulty
- Intermediate
- Updated
- Oct 29, 2026
Interview questions
Learning objectives#
- Send data down with parameters
- Send events up with EventCallback
- Share values with cascading parameters
- Coordinate siblings with a state service
Explanation#
Parent → child: parameters.
Child → parent: an EventCallback<T> parameter. The child calls InvokeAsync(value); the parent handles it and re-renders automatically.
Ancestor → many descendants: <CascadingValue Value="theme"> and [CascadingParameter] in descendants.
Unrelated components (header cart badge and product page): a scoped state service with an OnChange event both subscribe to.
Code example: A rating child notifying its parent#
@for (var i = 1; i <= 5; i++)
{
var star = i;
<button type="button" aria-label="@($"{star} stars")" @onclick="() => Select(star)">
@(star <= Value ? "★" : "☆")
</button>
}
@code {
[Parameter] public int Value { get; set; }
[Parameter] public EventCallback<int> ValueChanged { get; set; }
private Task Select(int stars) => ValueChanged.InvokeAsync(stars);
}
@* Parent: two-way binding works because of Value + ValueChanged *@
@* <StarRating @bind-Value="review.Stars" /> <p>You chose @review.Stars stars</p> *@
Clicking the fourth star shows ★★★★☆ and the parent text updates to “You chose 4 stars”.
This example is illustrative. Copy or download it and run it in your own environment; the expected output is shown above.
Step-by-step explanation#
- Value comes down from the parent.
- Clicking calls ValueChanged.InvokeAsync with the new rating.
- Value + ValueChanged lets the parent use @bind-Value.
- The local copy star avoids capturing the loop variable i.
Real-world use case#
Reusable inputs (ratings, date pickers, quantity selectors) that work with @bind-Value like built-in inputs.
Common mistakes#
EventCallback re-renders the parent automatically and supports async.
Every change re-renders all subscribers. Use IsFixed="true" for values that never change.
Best practices#
- Parameters down, EventCallback up
- Implement Value/ValueChanged for bindable components
- Use state services for distant components
- Unsubscribe from service events in Dispose
Remember this#
Down: [Parameter]. Up: EventCallback.
Value + ValueChanged = @bind-Value support.
Siblings: shared scoped service with OnChange.
Practice exercise#
Your task: Write a CartState service that raises OnChange when an item is added.
Show solution
public class CartState
{
public List<string> Items { get; } = [];
public event Action? OnChange;
public void Add(string item) { Items.Add(item); OnChange?.Invoke(); }
}
Mini quiz#
Which type should a child use to notify its parent?
Want more? Practise all Blazor MCQs · Blazor interview questions
My notes#
Saved in this browser.