diff --git a/knowledge-base/combobox-auto-select-on-blur.md b/knowledge-base/combobox-auto-select-on-blur.md new file mode 100644 index 0000000000..d8742793b2 --- /dev/null +++ b/knowledge-base/combobox-auto-select-on-blur.md @@ -0,0 +1,185 @@ +--- +title: How to Automatically Select Preselected Item on Blur +description: Learn how to configure the Telerik ComboBox for Blazor to automatically select the first matching item when the input loses focus. +type: how-to +page_title: How to Automatically Select Preselected Item on Blur +slug: combobox-kb-autoselect-on-blur +tags: telerik, blazor, combobox, blur, auto-select +res_type: kb +--- + +## Environment + + + + + + + + +
ProductComboBox for Blazor
+ +## Description + +The article asnwers to the following question: + +* How to configure the ComboBox to automatically select the first matching item when the input loses focus (e.g., when the user tabs away or clicks outside)? +* How to auto-select a ComboBox item based on user input when focus is lost? +* Can the ComboBox select a suggested item on blur without pressing Enter? +* How to set the ComboBox value when the user leaves the input field? + +## Solution +To automatically select the first matching item in the ComboBox when the input loses focus, use a combination of the ComboBox [`OnRead` event](slug:components/combobox/events#onread) and JavaScript interop. The provided example demonstrates how to: + +1. Use the `OnRead` event to filter data and store the first matching item. +2. Attach a JavaScript event handler to detect when the user blurs the ComboBox input. +3. Invoke a .NET method from JavaScript to set the ComboBox value to the first matching item when focus is lost. +4. Update the ComboBox selection programmatically and refresh the UI. + +>caption Auto-select the first matching item on blur + +````RAZOR +@using Telerik.DataSource.Extensions + +@implements IDisposable + +@inject IJSRuntime js + +

ComboBoxFirstItem: @ComboBoxFirstItem?.Text

+ +

Selected value: @ComboBoxValue

+ + + + + + +
+
+ + +@* Move JavaScript to a separate JS file *@ + + +@code { + private DotNetObjectReference<__Main>? DotNetRef { get; set; } + + private List ComboBoxData { get; set; } = new(); + private int ComboBoxValue { get; set; } + private ListItem? ComboBoxFirstItem { get; set; } + + [JSInvokable("OnComboBoxTab")] + public void OnComboBoxTab(string newStringValue) + { + if (ComboBoxFirstItem is not null && ComboBoxFirstItem.Text.Contains(newStringValue)) + { + ComboBoxValue = ComboBoxFirstItem.Id; + ComboBoxFirstItem = default; + + StateHasChanged(); + } + } + + private void ComboBoxValueChanged(int newValue) + { + ComboBoxValue = newValue; + ComboBoxFirstItem = default; + } + + private async Task OnComboBoxRead(ReadEventArgs args) + { + var result = await ComboBoxData.ToDataSourceResultAsync(args.Request); + + args.Data = result.Data; + args.Total = result.Total; + + if (args.Request.Filters.Count > 0) + { + ComboBoxFirstItem = args.Data.Cast().First(); + } + else + { + ComboBoxFirstItem = default; + } + } + + protected override async Task OnAfterRenderAsync(bool firstRender) + { + if (firstRender) + { + await Task.Delay(1); // ensure HTML is ready + await js.InvokeVoidAsync("saveDotNetRef", DotNetRef); + await js.InvokeVoidAsync("attachComboKeyDown", "#combo-1"); + } + + await base.OnAfterRenderAsync(firstRender); + } + + protected override void OnInitialized() + { + DotNetRef = DotNetObjectReference.Create(this); + + for (int i = 1; i <= 24; i++) + { + ComboBoxData.Add(new ListItem() + { + Id = i, + Text = $"Item {i}" + }); + } + } + + public void Dispose() + { + DotNetRef?.Dispose(); + _ = js.InvokeVoidAsync("detachComboKeyDown", "#combo-1"); + } + + public class ListItem + { + public int Id { get; set; } + public string Text { get; set; } = string.Empty; + } +} +```` +## See Also + +- [ComboBox Events](slug:components/combobox/events) \ No newline at end of file