Closed husseinshaib1 closed 1 year ago
@husseinshaib1 Hello, I am unable to reproduce the issue on latest version with code similar to yours. Can you provide more details? If it's called repeatedly, the app would just straight crash or be completely unresponsive.
ReadData
should be called on most key strokes which is what is happening.
Here's the code I used to test:
<Blazorise.Components.Autocomplete TItem="DataPointDto"
TValue="string"
Data="@Temp"
TextField="@(( item ) => item.DisplayKey)"
ValueField="@(( item ) => item.Key)"
Placeholder="Search..."
SelectionMode="AutocompleteSelectionMode.Checkbox"
ReadData="@OnHandleReadData"
@bind-SelectedValues="multipleSelectionData"
@bind-SelectedTexts="multipleSelectionTexts">
</Blazorise.Components.Autocomplete>
@code {
public class DataPointDto
{
public string Key { get; set; }
public string DisplayKey { get; set; }
}
public List<DataPointDto> Temp = new List<DataPointDto>();
public List<DataPointDto> DataPoints = new List<DataPointDto>();
private Random random = new();
List<string> multipleSelectionData;
List<string> multipleSelectionTexts;
protected override async Task OnInitializedAsync()
{
DataPoints = new List<DataPointDto>();
DataPoints.Add( new DataPointDto() { Key = "1", DisplayKey = "dsadsa 1" } );
DataPoints.Add( new DataPointDto() { Key = "2", DisplayKey = "dsagfdhfgdsa 1" } );
DataPoints.Add( new DataPointDto() { Key = "3", DisplayKey = "gfhgf 1" } );
DataPoints.Add( new DataPointDto() { Key = "4", DisplayKey = "dsafdfdgdfdsa 1" } );
await base.OnInitializedAsync();
}
private void OnHandleReadData( AutocompleteReadDataEventArgs autocompleteReadDataEventArgs )
{
Console.WriteLine( "OnHandleReadData" );
if ( !autocompleteReadDataEventArgs.CancellationToken.IsCancellationRequested )
{
Task.Delay( random.Next( 100 ) );
if ( !autocompleteReadDataEventArgs.CancellationToken.IsCancellationRequested )
{
Temp = DataPoints.Take( 2 ).ToList();
}
}
}
}
Hello @husseinshaib1, thank you for your submission. The issue was labeled "Status: Repro Missing", as you have not provided a way to reproduce the issue quickly. Most problems already solve themselves when isolated, but we would like you to provide us with a reproducible code to make it easier to investigate a possible bug.
I tried again the issue is still there with the same code, but what I noticed is that when I open the developer tool and place a break point on the read data handler in the code behind it works. however when I run without opening the developer tool and placing the breakpoint on the handler function the issue occurs. I know this is very weird and makes no sense but this is what I noticed!
Please provide a repro I must be missing something on my tests.
here is the packages I am using in my demo project.
@using Blazorise
@using Blazorise.Components;
<Blazorise.Components.Autocomplete TItem="DataPointDto"
TValue="string"
Data="@Temp"
TextField="@(( item ) => item.DisplayKey)"
ValueField="@(( item ) => item.Key)"
Placeholder="Search..."
SelectionMode="AutocompleteSelectionMode.Checkbox"
ReadData="@OnHandleReadData"
@bind-SelectedValues="multipleSelectionData"
@bind-SelectedTexts="multipleSelectionTexts">
</Blazorise.Components.Autocomplete>
this is the blazor code followed by the code behind
using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;
using Microsoft.AspNetCore.Components;
using System.Net.Http;
using System.Net.Http.Json;
using Microsoft.AspNetCore.Components.Forms;
using Microsoft.AspNetCore.Components.Routing;
using Microsoft.AspNetCore.Components.Web;
using Microsoft.AspNetCore.Components.Web.Virtualization;
using Microsoft.AspNetCore.Components.WebAssembly.Http;
using Microsoft.JSInterop;
using BlazorApp1;
using BlazorApp1.Shared;
using Blazorise;
using Blazorise.Components;
namespace BlazorApp1.Pages
{
public partial class Counter
{
public class DataPointDto
{
public string Key { get; set; }
public string DisplayKey { get; set; }
}
public List<DataPointDto> Temp = new List<DataPointDto>();
public List<DataPointDto> DataPoints = new List<DataPointDto>();
private Random random = new();
List<string> multipleSelectionData;
List<string> multipleSelectionTexts;
protected override async Task OnInitializedAsync()
{
DataPoints = new List<DataPointDto>();
DataPoints.Add(new DataPointDto() { Key = "1", DisplayKey = "dsadsa 1" });
DataPoints.Add(new DataPointDto() { Key = "2", DisplayKey = "dsagfdhfgdsa 1" });
DataPoints.Add(new DataPointDto() { Key = "3", DisplayKey = "gfhgf 1" });
DataPoints.Add(new DataPointDto() { Key = "4", DisplayKey = "dsafdfdgdfdsa 1" });
await base.OnInitializedAsync();
}
private void OnHandleReadData(AutocompleteReadDataEventArgs autocompleteReadDataEventArgs)
{
Console.WriteLine("OnHandleReadData");
if (!autocompleteReadDataEventArgs.CancellationToken.IsCancellationRequested)
{
Task.Delay(random.Next(100));
if (!autocompleteReadDataEventArgs.CancellationToken.IsCancellationRequested)
{
Temp = DataPoints.Take(2).ToList();
}
}
}
}
}
this is the whole code I have. just to explain once again the issue by steps:
OnHandleReadData
functionAs I said before, if you type inside the textbox with developer tools open the breakpoint will be hit only once.
hope this will help, I have nothing more to elaborate or explain
@husseinshaib1 Ahh now you're giving me more precise info on what you're doing. :)
This seems to be a combination of debugging and when you press F5 the window refocus on the browser and retriggers ReadData
. I don't think this is an example of real world usage of Autocomplete
. Debugging on WASM has some quirkness sometimes because under the curtains the browser is syncing/sending dotnet debugging info to visual studio.
If you take off the breakpoint and just take a look at the Developer tools you can keep track of how many times it is being called and when due to the
Console.WriteLine( "OnHandleReadData" );
and it seems normal to me.
Again, if the behaviour you mentioned was happening on regular usage, the Autocomplete
would most likely make the page unresponsive or crash if it kept calling ReadData
continously.
I understand that the debugging behavior might not be the best, but I would say that's just a quirky of wasm debugging. Just let me know if you're ok with this response, or if you still feel like there's something quite not right.
this is true, the issue is now clarified. It is just debugging issue. I have another question, is there a way to do lazy loading from api. when I read the docs I found that lazy loading only loads data incrementally on UI not getting back to the API every time to get more data. If this possible please let me know
So load data on demand, but from an UI perspective? Virtualization
?
Check https://blazorise.com/docs/extensions/autocomplete Virtualize example.
Or https://bootstrapdemo.blazorise.com/tests/autocomplete at the bottom, Virtualize examples
Is that what you're looking for?
in the virtualization section the code is as below:
<Autocomplete TItem="Country"
TValue="string"
Data="@Countries"
TextField="@(( item ) => item.Name)"
ValueField="@((item) => item.Iso)"
@bind-SelectedValue="selectedSearchValue"
Placeholder="Search..."
Virtualize>
<NotFoundContent> Sorry... @context was not found! :( </NotFoundContent>
</Autocomplete>
@code {
[Inject]
public CountryData CountryData { get; set; }
public IEnumerable<Country> Countries;
protected override async Task OnInitializedAsync()
{
Countries = await CountryData.GetDataAsync();
await base.OnInitializedAsync();
}
public string selectedSearchValue { get; set; }
}
in this code what is being done is as follows: 1- get data on initialization 2-the control will load data by chunks on UI without going back each time to API
what I need is: 1-get data from api on first load(for ex, 10 items) 2- when user scrolls down in the drop down list I should hit the api again and say hey I need the next 10 items and so on
Is this feasible?
in the virtualization section the code is as below:
<Autocomplete TItem="Country" TValue="string" Data="@Countries" TextField="@(( item ) => item.Name)" ValueField="@((item) => item.Iso)" @bind-SelectedValue="selectedSearchValue" Placeholder="Search..." Virtualize> <NotFoundContent> Sorry... @context was not found! :( </NotFoundContent> </Autocomplete> @code { [Inject] public CountryData CountryData { get; set; } public IEnumerable<Country> Countries; protected override async Task OnInitializedAsync() { Countries = await CountryData.GetDataAsync(); await base.OnInitializedAsync(); } public string selectedSearchValue { get; set; } }
in this code what is being done is as follows: 1- get data on initialization 2-the control will load data by chunks on UI without going back each time to API
what I need is: 1-get data from api on first load(for ex, 10 items) 2- when user scrolls down in the drop down list I should hit the api again and say hey I need the next 10 items and so on
Is this feasible?
ReadData code should work by enabling Virtualize. You will find arguments you can use with the Virtualize offset, example taken off the demo page source code:
private async Task HandleVirtualizeReadData( AutocompleteReadDataEventArgs autocompleteReadDataEventArgs )
{
if ( !autocompleteReadDataEventArgs.CancellationToken.IsCancellationRequested )
{
IEnumerable<Country> response = ( await GetDataFromExternalSource( autocompleteReadDataEventArgs.SearchValue, autocompleteReadDataEventArgs.VirtualizeOffset, autocompleteReadDataEventArgs.VirtualizeCount ) );
if ( !autocompleteReadDataEventArgs.CancellationToken.IsCancellationRequested )
{
VirtualizeReadDataCountries = response;
VirtualizeTotalReadDataCountries = await GetTotalFromExternalSource( autocompleteReadDataEventArgs.SearchValue );
}
}
}
Thank you bro for the help I think this is what I need.
Going ahead and closing the issue. We have a discord channel if you want to join for more recurrent questions, https://discord.io/blazorise
Hello guys, I am trying to use AutoComplete control with read data in order to load data after user search from the api because I have lot of data to retrieve.
and here is the code behind:
the problem is when I enter any character inside the AutoComplete the event
OnHandleReadData
is called infinitely. This will cause overhead on the Api.Any suggestions please?