Planned
Last Updated: 22 Dec 2021 09:18 by ADMIN
layton
Created on: 04 May 2021 05:02
Category: DropDownList
Type: Bug Report
10
Selected text does not update when changing the data collection
the dropdown options display correctly until some come from a second service call.

The problem is that if the selected option is in the options added later then it does not show it as the selected value.

Example below shows correct function for "6" but incorrect for "7".

---

ADMIN EDIT

Here is a reproducible with the workaround highlighted in green:

 

@using System.Collections.ObjectModel

<h4>Option Selected: 6 @selectedSix</h4>
<br />

<TelerikDropDownList Data="@myDdlData"
                     TextField="MyTextField"
                     ValueField="MyValueField"
                     @bind-Value="@selectedSix" />

<h4>Option Selected: 7 @selectedSeven</h4>
<br />

<TelerikDropDownList Data="@myDdlData"
                     TextField="MyTextField"
                     ValueField="MyValueField"
                     @bind-Value="@selectedSeven">
</TelerikDropDownList>

<TelerikButton OnClick="@AddOption">Add Item</TelerikButton>

<ul>
    @foreach (var item in myDdlData)
    {
        <li>@item.MyValueField</li>
    }
</ul>

@code {
    int selectedSix { get; set; } = 6;
    int selectedSeven { get; set; } = 7;

    ObservableCollection<MyDdlModel> myDdlData = new ObservableCollection<MyDdlModel>(Enumerable.Range(1, 5).Select(x => new MyDdlModel { MyTextField = "item " + x, MyValueField = x }));

    protected override async Task OnInitializedAsync()
    {
        AddOption();

        await Task.Delay(TimeSpan.FromSeconds(1));

        AddOption();
    }

    void AddOption()
    {
        myDdlData.Add(new MyDdlModel { MyTextField = "item " + (myDdlData.Count + 1), MyValueField = myDdlData.Count + 1 });

        int origSelection = selectedSeven;
        selectedSeven = 0;
        StateHasChanged();
        //add this if it does not work
        //await Task.Delay(30);//wait a rendering frame
        selectedSeven = origSelection;
        //add this if it does not work
        //StateHasChanged();
    }

    public class MyDdlModel
    {
        public int MyValueField { get; set; }
        public string MyTextField { get; set; }
    }
}

 

Note: This behavior also occurs if the initial data is received after the component is initialized. The workaround in this case will be similar - set the selected value after the data is received.

---

3 comments
ADMIN
Nadezhda Tacheva
Posted on: 22 Dec 2021 09:18

Hi Michal,

Thank you for the provided details and video!

Generally speaking, the current bug report covers a scenario in which the selected text is not updated when the data collection is changed and the selection is included in the options added later. However, in this case, the selected text is not updated if you focus the input as per your report.

The behavior you are experiencing might be caused by a different reason, so I'd like to further investigate it to validate that. That said, could you please send us a runnable reproduction, so we can perform some tests on our side using your exact configuration. Thus, we can debug and see if something is missing or there is a bug associated with the ComboBox component.

I would recommend to open a separate thread and attach the runnable sample there - thus we can cover your scenario separately and not mix the discussions in case the problem is a different one. If when testing we validate that both reports are connected, I can update the current thread.

Thank you in advance! I will be looking forward to receiving your response!

Regards,
Nadezhda Tacheva
Progress Telerik

Learn about the important changes coming in UI for Blazor 3.0 in January 2022!
Michal
Posted on: 15 Dec 2021 16:51

- Attached video

Doing same thing repetitively in video:

1 - load new page(pencil-edit)
2 - comboboxes are loaded and value bound at OnParametersSetAsync
3 * sometimes it shows OK
3 * sometimes it looks empty, but value is still the same (@CurrentEdit.CisloOrg etc)
4 - click inside combobox, TAB out - and value is here as it shoud be at pageload(1)
5 - GO BACK from page
6 -  goto 1
hope it helped

components version: 2.30.0

Attached Files:
Michal
Posted on: 15 Dec 2021 13:29

Hello,

 iam found similar, but not the same problem:

- combobox doesnt showing binded value(Visualy it seems empty), UNTIL you jump to the combobox input area and out(by the mouse cursor or run over by tab tab tab tab key).
- it is not happening all the time, but "randomly" according, how fast the page decide to render the components. Mostly when using NavigateTo and have lot(6 and more) combobxes on page.
- My fix was to put "waitfor delay '00:00:00.5'" (like await Task.Delay(...))to one of the many SQL calls.
- Because we dont know the "exact order" how blazor decid to call/load data in the ui, so workaround where to place "reasign value" is not 100% fix(but helped a little)
- doesnt matter if OnRead or Direct assign of datasource is used
- adding statehaschanged() to the OnParametersSetAsync didnt helped OR where is the only 1 correct place to be called ONCE)?

- two differently configuret comboboxes with same behavior(which is good for testing :) )
<TelerikComboBox Width="" @bind-Value="@CurrentEdit.CisloOrg"
ScrollMode="@DropDownScrollMode.Virtual"
Data="@CisOrg"
OnRead="@(args=>ReadComboData(args,6))"
ValueMapper="@GetSelValueComboboxOrg"
ItemHeight="30"
TotalCount="@CNT6"
PageSize="14"
PopupHeight="400px"
TextField="Nazev1"
ValueField="KeyValint"
Filterable="true"
FilterOperator="StringFilterOperator.Contains">
</TelerikComboBox>

<TelerikComboBox Width="" @bind-Value="@CurrentEdit.CisloStred"
Data="@CisStred"
ValueField="KeyVal"
TextField="Nazev1"
Filterable="true"
FilterOperator="StringFilterOperator.Contains">
</TelerikComboBox>


Code:
public IEnumerable<BaseKeyModel> CisStred { get; set; } = Enumerable.Empty<BaseKeyModel>();
public IEnumerable<BaseKeyModel> CisOrg { get; set; } = Enumerable.Empty<BaseKeyModel>();
....and much more sources....
protected override async Task OnParametersSetAsync()
{
//await base.OnParametersSetAsync();

if (lastp != did)
{
lastp = did;
IsBusy = true;

CisStred = await glob.SQL.QueryAsync<BaseKeyModel>(sql: "dbo.sqlprocedureXYZ");
..... and so on X TIMES once per every combobox on page....
...
.the last one to load - bind selected values:
CurrentEdit
= await glob.SQL.QueryFirstOrDefaultAsync<EditRowModel>(sql: "dbo.sqlprocedureXYZ");

IsBusy = false;
}
}



async Task ReadComboData(ComboBoxReadEventArgs e, int xtyp)
{
try
{
var p = new DynamicParameters();
var f = SqlClass.GetSQLFiterString(e.Request);
p.AddDynamicParams(new

xWhere = f.xWhere,
xOrd = f.xOrd,
PageSize = e.Request.PageSize,
PageIndex = e.Request.Skip,
});

var r = await glob.SQL.QueryAsync<BaseKeyModel>(sql: "dbo.sqlprocedureXYZ", param: p, commandType: System.Data.CommandType.StoredProcedure);
if (xtyp == 3) {CisZak = r;  CNT3 = p.Get<int>("CNT"); }
if (xtyp == 6) { CisOrg = r; CNT6 = p.Get<int>("CNT");}
.....

}
}
catch (Exception ex)
{
Notification.ShowSQLErr(ex.Message);
}
}

Task<BaseKeyModel> GetSelValueComboboxOrg(int? selectedValue)
{
return Task.FromResult<BaseKeyModel>(new BaseKeyModel() { KeyValint = selectedValue, Nazev1 = selectedValue.ToString()});
}