Search code examples
asp.net-mvcrazorblazorrazor-pagesblazor-webassembly

BuildRenderTree is not called in a razor page that inherits of my custom component


I have the following files:

BaseComponent.cs:

using Microsoft.AspNetCore.Components;
using Microsoft.AspNetCore.Components.Rendering;

namespace Test.Pages;

[Route("/basepage")]

public class BasePage :ComponentBase
{
    protected override void BuildRenderTree(RenderTreeBuilder builder)
    {
        base.BuildRenderTree(builder);
        var seq = 0;
        builder.OpenElement(seq, "h3");
        builder.AddContent(++seq, "BuildRenderTree of BasePage.cs");
        builder.CloseElement();
    }
}

CustomNonRazorPage.cs:

using Microsoft.AspNetCore.Components;
using Microsoft.AspNetCore.Components.Rendering;

namespace Xcition.Client.Pages;

[Route("/customnonrazorpage")]
public class CustomNonRazorPage : BasePage
{
    protected override void BuildRenderTree(RenderTreeBuilder builder)
    {
        base.BuildRenderTree(builder);
        var seq = 0;
        builder.OpenElement(seq, "h3");
        builder.AddContent(++seq, "BuildRenderTree of CustomNonRazorPage.cs");
        builder.CloseElement();
    }
}

CustomPage.razor:

@inherits BasePage
@page "/custompage"

<h3>CustomPage.razor</h3>

I call the following relative URI in the browser:

  • /basepage: returns a page with BuildRenderTree of BasePage.cs OK, it calls its own BuildRenderTree method
  • /customnonrazorpage: returns a page with BuildRenderTree of BasePage.cs and BuildRenderTree of CustomNonRazorPage.cs OK, it calls the BuildRenderTree method of BasePage
  • /custompage: returns a page with CustomPage.razor Unexpected value because it doesn't call the BuildRenderTree method of BasePage

May be I'm doing something wrong because I'm a beginner in Blazor.

I would like to create my custom base component that surrounds with an another component the body of a child razor component that inherits of my custom base component (something like the Layouts do).

I try to explain it better with an example:

  • FinalComponent.razor that inherits from BaseComponent and with a body like "My final content".

  • BaseComponent.cs that implements in BuildRenderTree the code that surrounds [Parameter] RenderFragment body with the OtherComponent

  • OtherComponent.razor that contains <div>@Body</div>

I would like to get the final result like this:

<div><h3>My final content</h3></div>

The target is to be able to decide by code in the BaseComponent what is the the class that I would use for the OtherComponent without need to know it from the FinalComponent.


Solution

  • It is possible, essentially in the same way as in your CustomNonRazorPage

    @inherits BasePage
    @page "/custompage"
    
    @{ base.BuildRenderTree(__builder); }
    
    <h3>CustomPage.razor</h3>
    

    but besides being ugly that __builder is a hack, no warranties.