Realtime Searchable list in blazor

Hi, in the project I'm working on, we have a drop down list that has 7000+ entries that it has to select from.

When we try to use the filterable dropdown control, it try's to load all the entries in that are in the collection, before it allows the filtered set to show in the list below it.

This causes a very noticeable delay (Note at this point we already have the data loaded from the backend into a list in the page, so the delay is NOT caused by the data being loaded from the rest api we are using), before the users of the application can begin to type anything into the search field (Several seconds in some cases)

In our previous version before we used radzen, we solved this problem using the html datalist template, a text box and an update on every key press that dynamically replaced all entries in the data list, something similar to the following code:

 <input class="form-control @_validationClass"
       id="@myId"
       list="listFor@(myId)"
       @onchange="@((args) => _selectedCustomer = args.Value.ToString())"
       placeholder="@ChooseText" />
<datalist id="listFor@(myId)">
    @foreach (var customer in CustomerList)
    {
        <option value="@($"{customer.CustomerText}")" />
    }
</datalist>

I've tried to replicate this using the radzen controls, as follows:

<RadzenTextBox Name="@myId" @oninput=@((cust) => textBoxChanged(cust.Value.ToString())) />
  <datalist style="border: 2px solid red;" id="listFor@(myId)">
    @foreach (var item in DisplayList)
    {
      <option value="@($"{item.Text}")" />    }
  </datalist>

@code {

  [Parameter] public List<DropDownListStringEntry> DataList { get; set; } = new List<DropDownListStringEntry>();

  private List<DropDownListStringEntry> DisplayList = new List<DropDownListStringEntry>();

  private string myId = RandomStringUtils.RandomAlphanumeric(10);

  private void textBoxChanged(string selectedCustomer)
  {
    if(string.IsNullOrEmpty(selectedCustomer))
    {
      DisplayList = new List<DropDownListStringEntry>();
      return;
    }

    DisplayList = DataList.Where(I => I.Text.Contains(selectedCustomer)).Take(5).ToList();
  }

But I notice that RadzenTextBox does not make available the "list" attribute to allow me to attach the datalist html element to the input so I can dynamically show the users the top 5 results and allow them to click them and select them into the input box.

We can't use the drop down search as it's too slow (Unless there is a way to speed it up).

We have brought an enterprise subscription to the radzen components, in anticipation of asking for help, but my email keeps getting rejected saying my address is listed as a spammers address.

Thanks for any ideas/assistance that you can provide.

Hi @shawty,

Indeed the RadzenTextBox does not apply HTML attributes to the input element that it renders - as all Radzen Blazor components it applies them to the outermost HTML element. I recommend you use the regular input element and apply the Radzen CSS class so it looks the same. We are doing something similar here: radzen-blazor/RadzenBlazorDemos/Shared/MainLayout.razor at master ยท radzenhq/radzen-blazor ยท GitHub

Alternatively you can try using the RadzenAutoComplete or RadzenDropDownDataGrid components which provide either built-in filtering or paging.

We don't have a purchase associated with the email address of your forum account. Did you use a different email address to make the purchase? You can share this with a forum direct message.

Purchase is not under my email, I'm working as a contractor to the company who bought the licence. How do I do a direct message?

I have replied via direct message.. disregard my last reply.

In the meantime, I'll take a look on the Github link you have provided.

This is actually wrong. The RadzenTextBox renders nothing but an input element so all custom attributes should apply to it. So specifying the list attribute should render:

<RadzenTextBox Name="@myId" 
     list="listFor@(myId)" 
     @oninput=@((cust) => textBoxChanged(cust.Value.ToString())) />

Thanks Korchev, I will try then anyway.

I (Possibly wrongly) assumed that when intellisense did not show the attribute, and it wasn't mentioned in the documentation, that it was not supported.

Sorry for the delay in responding (Friday night is time to knock of early and let your hair down... so to speak)

I'll let you know how I get on.

Just tried this morning, and this is what I get:

It appears the razor generator doesn't allow it some how, I'll try the second approach of a normal text box but applying the Radzen styling classes.

Cheers
Shawty

Yes, for some reason Blazor does not allow such expression for component properties (but allows them for HTML attributes). You can use string interpolation instead:

list=@($"listFor{myId}")

Hi Korchev,

Yes that works.. I should have realized that was the problem myself to be fair :slight_smile:

now however, I cant seem to get the "onchange" handler to fire, the way I have it set up is the same as I have in other controls, and it's not just the "not firing on each key" it's not firing on pressing return or tabbing away either... (Very Puzzled)

And ignore that last reply... because as is always the case, as soon as you explain an issue to someone, the solution comes to you!!

I will share my full solution, soon, once I tidy the code up a little.

Here is the full and now working implementation of a type ahead list that can handle 1000's of entries easily without slowing down. (In my case over 7000!)

Once the data is loaded into the parent page, the control is assigned that data via the use of the "DataList" attribute.

When the text is typed into the text box, the only data that is given to the list to display are the first 5 matches (From the linq select query at line 40)

This is significantly faster than the default implementation of the Radzen drop down which tries to load all the data in one go.

Regards
Shawty

Hey @shawty,

The DropDownDataGrid will use exactly Linq to query and filter data as you type + you have sorting:
https://blazor.radzen.com/dropdown-datagrid

The DropDown as well can benefit from Linq using LoadData event. Check the third DropDown in this demo:

1 Like

I tried the dropdown data grid initially enchev, but it lacked the ability for me to click on an entry in the list, and have the entry accepted as the final string in the input field.

Likewise, using the Load data event on the drop down turned out to still be too slow for the volume of data I was handling in this case.

With Korchev's help however, the solution I have arrived at now works perfectly.