Skip to content

DRAFT [dev-v5] Add FluentAutocomplete#4662

Draft
dvoituron wants to merge 43 commits intodev-v5from
users/dvoituron/dev-v5/autocomplete
Draft

DRAFT [dev-v5] Add FluentAutocomplete#4662
dvoituron wants to merge 43 commits intodev-v5from
users/dvoituron/dev-v5/autocomplete

Conversation

@dvoituron
Copy link
Copy Markdown
Collaborator

@dvoituron dvoituron commented Mar 31, 2026

[dev-v5] Add FluentAutocomplete

peek_1

TODO

  • Unit Tests
  • Multiple = false
  • Virtualize = true
  • HeaderContent
  • FooterContent
  • MaximumSelectedOptions, MaximumSelectedOptions
  • Items vs OnSearchAsync (?)

…ing and ensure at least one option is rendered
@github-actions
Copy link
Copy Markdown

github-actions bot commented Mar 31, 2026

Unit Tests

  • ❌[FAILED] Microsoft.FluentUI.AspNetCore.Components.Tests.Components.Base.InputBaseTests.InputBase_DefaultProperties(attributeName: "MessageState", attributeValue: Success, htmlAttribute: null, htmlValue: "color: var(--success);", extraCondition: "Add_MessageCondition_AlwaysTrue")
  • ❌[FAILED] Microsoft.FluentUI.AspNetCore.Components.Tests.Components.Base.InputBaseTests.InputBase_DefaultProperties(attributeName: "Required", attributeValue: True, htmlAttribute: "required", htmlValue: null, extraCondition: null)
  • ❌[FAILED] Microsoft.FluentUI.AspNetCore.Components.Tests.Components.Base.ComponentBaseTests.ComponentBase_DefaultProperties(blazor: "Padding='10px'", html: "style='padding: 10px;*'")
  • ❌[FAILED] Microsoft.FluentUI.AspNetCore.Components.Tests.Components.Base.InputBaseTests.InputBase_DefaultProperties(attributeName: "LabelPosition", attributeValue: Before, htmlAttribute: "label-position", htmlValue: "before", extraCondition: null)
  • ❌[FAILED] Microsoft.FluentUI.AspNetCore.Components.Tests.Components.Base.InputBaseTests.InputBase_DefaultProperties(attributeName: "AriaLabel", attributeValue: "my-aria-label", htmlAttribute: "aria-label", htmlValue: null, extraCondition: null)
  • ❌[FAILED] Microsoft.FluentUI.AspNetCore.Components.Tests.Components.Base.InputBaseTests.InputBase_DefaultProperties(attributeName: "LostFocus", attributeValue: "input", htmlAttribute: null, htmlValue: null, extraCondition: "Check_LostFocus")
  • ❌[FAILED] Microsoft.FluentUI.AspNetCore.Components.Tests.Components.Base.InputBaseTests.InputBase_DefaultProperties(attributeName: "Label", attributeValue: "my-label", htmlAttribute: null, htmlValue: null, extraCondition: null)
  • ❌[FAILED] Microsoft.FluentUI.AspNetCore.Components.Tests.Components.Base.ComponentBaseTests.ComponentBase_DefaultProperties(blazor: "Padding='my-padding'", html: "class='my-padding'")
  • ❌[FAILED] Microsoft.FluentUI.AspNetCore.Components.Tests.Components.Base.InputBaseTests.InputBase_DefaultProperties(attributeName: "Disabled", attributeValue: True, htmlAttribute: "disabled", htmlValue: null, extraCondition: null)
  • ❌[FAILED] Microsoft.FluentUI.AspNetCore.Components.Tests.Components.Base.InputBaseTests.InputBase_DefaultProperties(attributeName: "InputSlot", attributeValue: "input", htmlAttribute: null, htmlValue: "slot="input"", extraCondition: null)
  • ❌[FAILED] Microsoft.FluentUI.AspNetCore.Components.Tests.Components.Base.InputBaseTests.InputBase_DefaultProperties(attributeName: "LabelWidth", attributeValue: "150px", htmlAttribute: null, htmlValue: "width: 150px;", extraCondition: "Set_LabelPosition_Before")
  • ❌[FAILED] Microsoft.FluentUI.AspNetCore.Components.Tests.Components.Base.InputBaseTests.InputBase_DefaultProperties(attributeName: "Name", attributeValue: "my-name", htmlAttribute: "name", htmlValue: null, extraCondition: null)
  • ❌[FAILED] Microsoft.FluentUI.AspNetCore.Components.Tests.Components.Base.InputBaseTests.InputBase_DefaultProperties(attributeName: "ReadOnly", attributeValue: True, htmlAttribute: "readonly", htmlValue: null, extraCondition: null)
  • ❌[FAILED] Microsoft.FluentUI.AspNetCore.Components.Tests.Components.Base.ComponentBaseTests.ComponentBase_DefaultProperties(blazor: "Margin='10px'", html: "style='margin: 10px;*'")
  • ❌[FAILED] Microsoft.FluentUI.AspNetCore.Components.Tests.Components.Base.InputBaseTests.InputBase_DefaultProperties(attributeName: "Autofocus", attributeValue: True, htmlAttribute: "autofocus", htmlValue: null, extraCondition: null)
  • ❌[FAILED] Microsoft.FluentUI.AspNetCore.Components.Tests.Components.Base.ComponentBaseTests.ComponentBase_DefaultProperties(blazor: "Margin='my-margin'", html: "class='my-margin'")
  • ❌[FAILED] Microsoft.FluentUI.AspNetCore.Components.Tests.Components.Base.ComponentBaseTests.ComponentBase_TooltipInterface_CorrectRendering
  • ❌[FAILED] Microsoft.FluentUI.AspNetCore.Components.Tests.Components.Base.ComponentBaseTests.ComponentBase_DefaultProperties(blazor: "extra-attribute='My-Specific-Attribute'", html: "extra-attribute='My-Specific-Attribute'")
  • ❌[FAILED] Microsoft.FluentUI.AspNetCore.Components.Tests.Components.Base.ComponentBaseTests.ComponentBase_DefaultProperties(blazor: "Class='My-Specific-Item'", html: "class='My-Specific-Item'")
  • ❌[FAILED] Microsoft.FluentUI.AspNetCore.Components.Tests.Components.Base.ComponentBaseTests.ComponentBase_DefaultProperties(blazor: "Style='My-Specific-Style'", html: "style='My-Specific-Style'")
  • ❌[FAILED] Microsoft.FluentUI.AspNetCore.Components.Tests.Components.Base.ComponentBaseTests.ComponentBase_DefaultProperties(blazor: "Id='id='My-Specific-ID'", html: "id='My-Specific-ID'")
  • ❌[FAILED] Microsoft.FluentUI.AspNetCore.Components.Tests.Components.Base.InputBaseTests.InputBase_DefaultProperties(attributeName: "Message", attributeValue: "my-message", htmlAttribute: null, htmlValue: null, extraCondition: "Add_MessageCondition_AlwaysTrue")

Details on your Workflow / Core Tests page.

@MarvinKlein1508 MarvinKlein1508 self-requested a review April 1, 2026 07:29
@MarvinKlein1508
Copy link
Copy Markdown
Collaborator

MarvinKlein1508 commented Apr 1, 2026

I tried this code:

<div>Selected: <b>@string.Join("; ", Selected.Select(x => x.Name))</b></div>

<FluentAutocomplete TOption="MyUser"
                    TValue="int"
                    Width="100%"
                    Label="Name"
                    Placeholder="Name"
                    OptionText="(option) => option.Name"
                    OptionValue="(option) => option.UserId"
                    OptionSelectedComparer="CompareUser"
                    OnOptionsSearch="@OnSearchAsync"
                    @bind-SelectedItems="@Selected" />
@code
{
    IEnumerable<MyUser> Selected { get; set; } = [];

    Task OnSearchAsync(OptionsSearchEventArgs<MyUser> e)
    {
        e.Items =
        [
            new MyUser
            {
                UserId = 1,
                Name = "Marvin Klein"
            },
            new MyUser
            {
                UserId = 2,
                Name = "Denis Voituron"
            },
    ];

        return Task.CompletedTask;
    }

    public bool CompareUser(int checkItemId, int selectedItemId)
    {
        return checkItemId == selectedItemId;
    }

    public class MyUser
    {
        public int UserId { get; set; }
        public string Name { get; set; } = string.Empty;
    }
}

The behaviour of the component gets confused by this.

grafik

We should also add documentation to OptionSelectedComparer to show the user which parameter is the current checking item and which one is the value from the object the user selects. Also there is a breaking change from v4 as I can no longer pass in an IEqualityComparer<T>

@dvoituron
Copy link
Copy Markdown
Collaborator Author

@MarvinKlein1508 The OptionSelectedComparer is not yet used.
But do you think better to continue to use a IEqualityComparer and not a Func?
I prefer to continue to use this IEqualityComparer, so I need to create another PR to update all list components

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants