Blazorise Validations Issue with Validation Containing Dynamic DropDown Element

Created on 9 Apr 2020  路  9Comments  路  Source: stsrki/Blazorise

In my client side wasm application, I have a form which contains a dropdown selection field which is dynamically generated using data received from an API call.

When calling the contactValidations.ValidateAll() method in my .razor code an issue appears to be occurring. I cannot see any particular error being generated in the console or client side chrome devtools debugger, but the chrome tools is failing at the ValidateAll() call and it breaks out of the debugger at this point.

I can verify form a process of elimination it seems to be the dynamic dropdown causing this as if I remove the dropdown field the code works just fine.

I have the following code;

```cshtml




First Name


Please enter a First Name for the Contact!



        @* REDUCED FOR BREVITY *@ 

        <Field IsHorizontal="false" ColumnSize="ColumnSize.Is12.OnDesktop">
            <Validation Validator="@ValidationRule.IsNotEmpty">
                <FieldLabel>Contact Type</FieldLabel>
                <Dropdown @ref="contactTypeDropDown">
                    <DropdownToggle Color="Color.Primary">
                        @contactTypeDropDownText
                    </DropdownToggle>
                    <DropdownMenu>
                        @if (contactTypes != null)
                        {
                            foreach (var type in contactTypes)
                            {
                                <DropdownItem Clicked="@(() => SetContactType(type))" Value="@type.Id">@type.Name</DropdownItem>
                                <DropdownDivider />
                            }
                        }
                    </DropdownMenu>
                </Dropdown>
            </Validation>
        </Field>
    </Fields>
</Validations>

where the data for the dropdown is 

   ```cs
 protected override async Task OnInitializedAsync()
    {
        await Refresh();
    }

    private async Task Refresh()
    {
        var response = await Http.GetAsync<ContactTypeOutputModel[]>("ContactTypes/all");

        if (response.HasError)
        {
            await NotificationService.AddNotificationAsync(
                  new Notification
                  {
                      Level = NotificationLevel.Error,
                      Text = response.Error
                  });
        }

        contactTypes = response.Result;
    }

The validations are then declared in the .razor

private Validations contactValidations = new Validations();

My contactTypes are simply;

private ContactTypeOutputModel[] contactTypes;

Finally I trigger the validateAll() call from a 'Add Button' click which triggers the method;

```cs
public async Task SubmitClick()
{
var isValid = contactValidations.ValidateAll();

   logger.LogDebug($"{contactValidations.ValidateAll()}");

   if(contactValidation.ValidateAll())
   {
      //removed for brevity
   }
}

```

Interestingly the isValid variable is showing as false in scope window of the Chrome tools debugger, however, I dont get pas the logger call (or the if statment if I remove the logger call).

Also the form does update to show the validations on all the above the dropdown.

I have also tried calling a bespoke Validator method call i.e.

<Validation Validator="@MyValidation">

I assume the issue is that a dropdown cannot be validated? what would the work around be here please?

My project is has the following versions;

Blazor.Client Project
Microsoft.AspNetCore.Components 3.1.3
Microsoft.AspNetCore.Blazor 3.1.0-preview3.19555.2
Blazorise.Bootstrap 0.8.8.4

Blazor.Server Project (API)
Microsoft.AspNetCore.Blazor.Server 3.1.0-preview3.19555.2

Question

Most helpful comment

Guys, I completely forgot that I already implemented this feature in one of previews for v0,9. The event is called SearchChanged and is raised whenever the text is changed.

I think this event should cover it all. It should go live in a day or two.

All 9 comments

Thank you for very detailed report! The reason why validation is failing is that Dropdown has no support for validation.

Generally dropdown is best to use as an additional menus with just a few items to choose from. Have you tried with Select component instead?. It should be better for your scenario I think.

@stsrki Thanks for the reply. Yes I did think this could be possibly why, after further testing.

The issue I have is that there is potentially a lot of data to chosen from here (between 40 and 50 elements).

I have been looking at possibly using a restricted Autocomplete from a predetermined list to help with searching.

Is it possible to utilize the validation (as its I assume a TextEdit??) around the autocomplete to ensure someone completes this element?

Or do you have any other suggestions?

Yeah, when used on Autocomplete the validation will pick up TextEdit. While not ideal it should still work. You want something to be selected, and it's perfectly fine to check for TextEdit empty or not empty.

@stsrki I wonder if you could suggest a solution for my situation please.

I am now using the Autocomplete text input to filter the result set and it is working well.

However, we also have the requirement to detect if the text doesn't match any item in the enum array and if not show an add button to add it to the array.

Can you suggest whether this would be possible? As the OnSelectedValueChanged method is only fired when a valid result is selected.

Is it possible to detect for example OnFocusOut type of events?

i guess it can be done. But by your description it sounds like you need OnTextChanged event...

@mfitconsultants I have a similar usecase. I'd prefer some parameter to keep the textedit from clearing if filtered data is empty.

@JRC86 Could you not override the SelectValueChanged event, set the @ref to be a private variable and then in the SelectValueChanged method set the Autocomplete.Placeholder to be the select value?

@stsrki I looked at handling the OnTextChanged event but it doesn't seem to exist?

@stsrki one possible solution would be to have another eventcallback, ontextchanged that is invoked at the bottom of HandleTextChanged depending on if it has a delegate.

[Parameter] public EventCallback<object> OnTextChanged { get; set; }

Inside the HandleTextChanged:

if (OnTextChanged.HasDelegate) await OnTextChanged.InvokeAsync(text);

That would make it optional if You would want to handle that.
Or use the available callback, preferable with a bool param.

Guys, I completely forgot that I already implemented this feature in one of previews for v0,9. The event is called SearchChanged and is raised whenever the text is changed.

I think this event should cover it all. It should go live in a day or two.

Was this page helpful?
0 / 5 - 0 ratings

Related issues

danlbb picture danlbb  路  4Comments

robalexclark picture robalexclark  路  4Comments

smilyte picture smilyte  路  3Comments

njannink picture njannink  路  4Comments

brettwinters picture brettwinters  路  5Comments