Quantcast
Channel: Active questions tagged blazor - Stack Overflow
Viewing all articles
Browse latest Browse all 4839

How to dynamically build parent and child components with rendertreebuilder?

$
0
0

I need help with dynamically building/generating multistep component with rendertreebuilder.

I have a two components: MultistepComponent (parent) and MultiStepNavigation (child). I also have a component builder class to build these components.

Rendering components does not work, I get an error:

Object reference not set to an instance of an object.

That is because the MultiStepComponent property in MultiStepNavigation is empty. Using a component in razor page does not give this error.

I will be posting a lot of code, but you don't have to read every detail. I just want to give all the information.

MultiStepComponent.razor

<CascadingValue Value="this"><div id="@Id"><ul class="nav nav-pills nav-justified">            @foreach (var step in Steps)            {<li id="step-@(StepsIndex(step) + 1)" class="nav-item"><a class="nav-link @((ActiveStep == step) ? "active" : "")" href="javascript: void(0)"                       @onclick="@(e=> SetActive(step))">@step.Name</a></li>            }</ul><div id="container-fluid"><div class="navigatingBtns"><button class="btn btn-primary btn-lg" type="button"                        disabled="@(ActiveStepIndex == 0)" @onclick="GoBack">                    Previous</button><button class="btn btn-primary btn-lg"                        type="@(IsLastStep ? "submit" : "button")" @onclick="GoNext">                    @(IsLastStep ? "Submit" : "Next")</button></div>            @ChildContent</div></div></CascadingValue>

MultiStepComponent.razor.cs

public partial class MultiStepComponent {         protected internal List<MultiStepNavigation> Steps = new List<MultiStepNavigation>();        [Parameter]        public string Id { get; set; }        [Parameter]        public RenderFragment? ChildContent { get; set; }        [Parameter]        public MultiStepNavigation? ActiveStep { get; set; }        [Parameter]        public int ActiveStepIndex { get; set; }        public bool IsLastStep { get; set; }        protected internal void GoBack()        {            if (ActiveStepIndex > 0)            {                SetActive(Steps[ActiveStepIndex - 1]);            }        }        protected internal void GoNext()        {            if (ActiveStepIndex < Steps.Count - 1)            {                SetActive(Steps[(Steps.IndexOf(ActiveStep) + 1)]);            }        }        protected internal void SetActive(MultiStepNavigation step)        {            ActiveStepIndex = StepsIndex(step);            if (ActiveStepIndex == Steps.Count - 1)            {                IsLastStep = true;            }            else            {                IsLastStep = false;            }        }        public int StepsIndex(MultiStepNavigation step) => StepsIndexInternal(step);        protected int StepsIndexInternal(MultiStepNavigation step)        {            return Steps.IndexOf(step);        }        protected internal void AddStep(MultiStepNavigation step)        {            Steps.Add(step);        }        protected override void OnAfterRender(bool firstRender)        {            if (firstRender)            {                SetActive(Steps[0]);                StateHasChanged();            }        }    }

MultiStepNavigation.razor

@if (MultiStepComponent.ActiveStep == this) { <div id="step-@(MultiStepComponent.StepsIndex(this) + 1)">        @ChildContent</div>}

MultiStepNavigation.razor.cs

public partial class MultiStepNavigation    {        [CascadingParameter]        protected internal MultiStepComponent MultiStepComponent { get; set; }        [Parameter]        public RenderFragment ChildContent { get; set; } = default!;        [Parameter]        public string Name { get; set; } = "";        protected override void OnInitialized()        {            if(MultiStepComponent != null)            {                MultiStepComponent.AddStep(this);            }        }    }

code to build componnts:

renderFragment = b =>            {                b.OpenComponent<MultiStepComponent>(0);                b.AddAttribute(1, "id", "MultiStepContainer");                b.OpenComponent<MultiStepNavigation>(2);                b.AddAttribute(3, "Name", "First Step");                b.CloseComponent();                b.CloseComponent();            };

Making a component on razor page myself does not give an error. It looks like this:

<MultiStepComponent Id="MultiStepContainer"><MultiStepNavigation Name="First Step"></MultiStepNavigation>    </MultiStepComponent>

What did I do wrong??


Viewing all articles
Browse latest Browse all 4839

Trending Articles



<script src="https://jsc.adskeeper.com/r/s/rssing.com.1596347.js" async> </script>