'Blazor - Telerik loader container

I am creating a webapp using Blazor. I want to add loader to all my pages where the dataload takes more than 5 seconds. I want to use my custom loader gif image. Is there anyway to achieve it using telerikloader? If not what is the best possible solution for this.



Solution 1:[1]

If you don't want to persevere with the Telerik control then page loaders come in all shapes and sizes. They aren't difficult to code.

Here's the simplest:

SimplePageLoader

@if (this.IsLoaded)
{
    @ChildContent
}
else
{
    <h4>Loading......</h4>
}

@code {
    [Parameter, EditorRequired] public bool IsLoaded { get; set; }
    [Parameter] public RenderFragment? ChildContent { get; set; }
}

As you want a timer then it gets a little more complex:

PageLoader.razor

@using System.Timers
@implements IDisposable

@if (this.ShowLoader)
{
    <h3>It's Sloooooow custom image</h3>
}
else
{
    @this.ChildContent
}

@code {
    private System.Timers.Timer _timer = new System.Timers.Timer();
    private bool ShowLoader;
    private bool _isLoaded = false;

    [Parameter, EditorRequired] public bool IsLoaded { get; set; }
    [Parameter] public int Timeout { get; set; } = 5000;
    [Parameter] public RenderFragment? ChildContent { get; set; }

    protected override void OnInitialized()
    {
        if (this.Timeout > 0)
        {
            // set up the timer
            _timer.Interval = this.Timeout;
            _timer.AutoReset = false;
            _timer.Elapsed += this.TimerElapsed;
        }
        else
        {
            _isLoaded = this.IsLoaded;
            this.ShowLoader = !this.IsLoaded;
        }
    }

    protected override void OnParametersSet()
    {
        // loaded and state has changed to loaded
        if (IsLoaded && IsLoaded != _isLoaded)
        {
            _isLoaded = this.IsLoaded;
            ShowLoader = false;
            _timer.Stop();
        }

        // Not Loaded and state has changed from loaded
        if (!IsLoaded && IsLoaded != _isLoaded)
        {
            _isLoaded = this.IsLoaded;
            ShowLoader = false;
            // set the timer going if we have a timeout
            // if not just set ShowLoader now
            if (this.Timeout > 0)
                _timer.Start();
            else
                ShowLoader = true;
        }

        // All else - do nothing
    }

    private void TimerElapsed(object? sender, ElapsedEventArgs e)
    {
        this.ShowLoader = true;
        this.InvokeAsync(StateHasChanged);
    }

    public void Dispose()
        => _timer.Elapsed -= this.TimerElapsed;
}

Demo Page:

@page "/"

<PageTitle>Index</PageTitle>

<PageLoader IsLoaded=this.IsLoaded Timeout=2000>
<h1>Hello, world!</h1>
</PageLoader>

<PageLoader IsLoaded=this.IsLoaded Timeout=0>
<h1>Hello, world! - Timeout at 0</h1>
</PageLoader>

<SimplePageLoader IsLoaded=this.IsLoaded>
    Simple Page Loader
</SimplePageLoader>

<div class="p-3">
    <button class="btn btn-primary" @onclick=OnClick>Load a slow compoinent</button>
</div>
Welcome to your new app.

@code {
    private bool IsLoaded = true;

    protected override async Task OnInitializedAsync()
    {
        this.IsLoaded = false;
        await Task.Delay(3000);
        this.IsLoaded = true;
    }

    private async Task OnClick()
    {
        IsLoaded = false;
        await Task.Delay(10000);
        IsLoaded = true;
    }
}

A Question - In your scenario, what do you display before the 5 seconds has elapsed on initial load?

Sources

This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.

Source: Stack Overflow

Solution Source
Solution 1