This is a migrated thread and some comments may be shown as answers.

Dropdown Cascade with Adding a New row

8 Answers 531 Views
Grid
This is a migrated thread and some comments may be shown as answers.
Paul
Top achievements
Rank 1
Paul asked on 20 Mar 2018, 06:52 PM

The grids I'm working on have quite a bit going on so I have tried to cut the details down to just what seems to pertain to this query.

 

For these grids, which are in InLine mode, there is a dropdown cascade setup so when a location is chosen the state gets set as well though can still be changed.

This is working well for all of the rows which are already in the grid to be updated.

However it is not triggering for a new row before it is submitted into the datasource.

The cascade works off of the onchange event; found this way through the forums here.

 

Here is one of the grid definitions:

@(Html.Kendo().Grid<NexusPWI.ViewModels.Wizard.OfficerPayrollReportingViewModel>()
    .Name("OfficerGrid")
    .Columns(c =>
    {
    c.Command(command => { command.Edit(); }).Width(120).Title("Update");
    c.Bound(vm => vm.FirstName).Width(120);
    c.Bound(vm => vm.LastName).Width(120);
    c.Bound(vm => vm.Title).Width(120);
 
    c.ForeignKey(vm => vm.LocationNumber, (System.Collections.IEnumerable)ViewData["LocationsList"], "LocationNumber", "Drop_Text").HtmlAttributes(new { onchange = "triggerDropChange(this);" }).Width(200).Hidden(Model.Locations_ColumnInitHidden); //Display UIHint in Dropdown through LocationsList ClientTemplate with just the LocationNumber value behind
 
    c.Bound(vm => vm.State).HtmlAttributes(new { @class = "locationLinkedState" }).Width(180).ClientFooterTemplate("Total");
 
    c.Command(command => { command.Edit(); }).Width(120);
    c.Command(command => { command.Destroy(); }).Width(40);
    c.Template(@<text></text>);//Blank Column to handle Scrollable variable width so headers do not skew
    })
    .Scrollable(s => s.Enabled(true).Height("auto"))//Scrollable to control column widths
    .ToolBar(toolbar =>
    {
        toolbar.Template("<div class='col-lg-8'>" +
            @Html.Raw(@Model.OfficerPayrollHeader) +
            "</div>" +
            "<div class='col-lg-3'>" +
            "<a class='pull-right k-button k-button-icontext k-grid-add' href='/Wizard/OfficerPayrollRead?OfficerGrid-mode=insert'><span class='k-icon k-add'></span>Add Row</a>" +
            "</div>");
    })
    .Editable(editable => editable.Mode(GridEditMode.InLine)
        .CreateAt(GridInsertRowPosition.Bottom)
        )
 
    .Navigatable()
    .Pageable()
    .Events(events => events.Edit("gEdit('OfficerGrid')")
        .Remove("gRemove('OfficerGrid')")
        .DataBound("gDataBoundOfficer")
        .Cancel("gCancel('OfficerGrid')")
        )
    .DataSource(dataSource => dataSource
        .Ajax()
        .Batch(true)
        .ServerOperation(false)
        .Events(events => events.Error("officerGrid_error") // Handle the "error" event
            .RequestEnd("Grid_RequestEnd")
            .RequestStart("dRequestStart")//Hooked up for event sequencing and debugging
            .Change("Grid_Delete")
            .Sync("dSync('OfficerGrid')")
            )
        .Model(model => {
            model.Id(vm => vm.PolicyHolderPayroll_OfficerGridId);
        })
        )
        .PageSize(1000)
        .Create("OfficerPayrollCreate", "Wizard")
        .Read("OfficerPayrollRead", "Wizard")
        .Update("OfficerPayrollUpdate", "Wizard")
        .Destroy("OfficerPayrollDestroy", "Wizard")
))

The Javascript Event:

function triggerDropChange(e) {
        var dropKey = e.innerText.replace("select", "");
        var locationCode = dropKey.split(":")
        var currentRowIndex = $(e).closest("tr").index();
        var digOutToGrid = e.parentElement;
        var digOutToGrid2 = digOutToGrid.parentElement;
        var digOutToGrid3 = digOutToGrid2.parentElement;
        var digOutToGrid4 = digOutToGrid3.parentElement;
        var GridLevel = digOutToGrid4.parentElement;
        var grid = $("#" + GridLevel.id.toString()).data().kendoGrid;
 
        var dataItem = grid.dataItem("tr:eq(" + (currentRowIndex + 1) + ")"); //Row
         
        var locationValueList = {};
 
        @foreach(EntityLocationsViewModel entry in (System.Collections.IEnumerable)ViewData["LocationsList"])
        {//Make Value LookUp Listing
            <text>locationValueList["@entry.LocationNumber"] = "@entry.State";</text>
        }
 
        @if (Model.DisplayEntities)
        {
        <text>
        var inVal = dataItem.LocationNumber.trim();
        var changeTo = locationValueList[inVal];
        </text>
        }
        else
        {
            <text>var changeTo = locationValueList[locationCode[0].trim()];</text>
        }
 
        dataItem.set("State", changeTo);
 
        var nod = 2;
    }

 

Is there any way to have this cascade applied to the dropdown in the new row before it is submitted?

 

Also is there is a way to have this new row have some default values (such as dropdown values pre-selected) before "entered" and sent to the controller to be inserted?

8 Answers, 1 is accepted

Sort by
0
Stefan
Telerik team
answered on 22 Mar 2018, 08:18 AM
Hello, Paul,

Thank you for the details.

I can suggest checking the following runnable example of the Grid with cascading DropDownLists in InLine mode:

https://docs.telerik.com/aspnet-mvc/helpers/grid/how-to/editing/grid-editing-cascading-dropdownlist

I hope this example to help to achieve the desired functionality.

Please advise if there are any issues after using this approach.

Regards,
Stefan
Progress Telerik
Try our brand new, jQuery-free Angular components built from ground-up which deliver the business app essential building blocks - a grid component, data visualization (charts) and form elements.
0
Paul
Top achievements
Rank 1
answered on 23 Mar 2018, 06:31 PM

Working through the example project it does indeed use a cascade; and the dropdowns work for new rows.

The type of cascade is a bit different from what aiming at.

1) The example filters the options for the next drop down based on the one further up. What I'm looking for is to have the location dropdown pre-select an option from the state dropdown without limiting the set of options. Do you know if there is another setup or some options that will work this way?

 

2) While the dropdown definition's DataTextField shows when the field is in dropdown format; in the grid when committed it shows the DataValueField. Is there a way to display in grid like the DataTextField with the underlying DataValueField value? Or would that be up to using 2 columns and shuffling the data in the Create and Update calls?

0
Stefan
Telerik team
answered on 26 Mar 2018, 06:48 AM
Hello, Paul,

Regarding the questions:

1) The second DropDownList should automatically receive a selected value which is the first value in the collection. When a value in the first DropDownList is selected the second one should appear as its first value selected. Please advise if the first value is not selected on your end?

2) This is expected because the column field is an int field and does not contain any information of the corresponding data text field. This could be resolved using two approaches:

 2.a) Using the ClientTemplate with a function and a value description table, this will require based on the selected value to return a string containing the value and the description:

 https://docs.telerik.com/aspnet-mvc/helpers/grid/configuration#clienttemplate

2.b) Using complex objects as values which will contain the text and the value. A similar approach is used in our DropDownList editor in the Grid demo:

https://demos.telerik.com/aspnet-mvc/grid/editing-custom

Regards,
Stefan
Progress Telerik
Try our brand new, jQuery-free Angular components built from ground-up which deliver the business app essential building blocks - a grid component, data visualization (charts) and form elements.
0
Paul
Top achievements
Rank 1
answered on 26 Mar 2018, 08:34 PM

Continuing 1)

The value from dropdown 1 (location) is reaching the JsonResult for getting the values for dropdown 2 (state).

Assuming "first value in the collection" is first entry in the IEnumerable that is the Json return to fill dropdown 2 (state):

Pre-pended a duplicate state entry at the beginning of the list:

 

Using this; only on a completely fresh new entry when dropdown 1 (location) is chosen does will the 1st entry become selected in dropdown 2 (state).

The 1st entry is NOT selected when dropdown 1 (location) is changed again or there are already values in the row. Then which entry in dropdown 2 (state) is selected becomes jumbled and an entry part way down the list gets selected which is not the one that matches the new 1st value in the list.

 

Do you know of a way to force the 1st to be selected or another way to set which entry is selected without limiting the list of entries?

0
Paul
Top achievements
Rank 1
answered on 26 Mar 2018, 08:35 PM

The JsonResult function:

public JsonResult GetStates2(string sr91)
        {//Fills DropDown2 (State) like GetVendors does for Vendors in the example project
            var LS = Session["LocationsList"] as IEnumerable<EntityLocationsViewModel>;
            string State = Session["DefaultState"] + "";
            StatesModel ReturnState = new StatesModel();
            if (LS != null)
            {
                State = LS.First(c => c.LocationNumber == sr91).State;
            }
 
            ReturnState = States2.First(c => c.Drop_Value == State);
            List<StatesModel> ReturnList = new List<StatesModel>();
            ReturnList.Add(ReturnState);//1st Selected
            ReturnList.AddRange(States2);//Everything
 
            IEnumerable<StatesModel> sList = ReturnList;//IEnumerable Convert
            return Json(sList, JsonRequestBehavior.AllowGet);
        }
0
Stefan
Telerik team
answered on 28 Mar 2018, 06:55 AM
Hello, Paul,

Thank you for the code.

I noticed that the "ReturnState" is added and then the entire collection. In order to not duplicate the records, after finding the desired "ReturnState" loop through the records of "States2" and remove the record that contains the "ReturnState".

Also, please share with us a short video of the result and more details on this part of the questions:

"another way to set which entry is selected without limiting the list of entries".

Regards,
Stefan
Progress Telerik
Try our brand new, jQuery-free Angular components built from ground-up which deliver the business app essential building blocks - a grid component, data visualization (charts) and form elements.
0
riz
Top achievements
Rank 1
answered on 15 Feb 2020, 06:57 AM
the link you provided has no documentation whatsoever. Are we just supposed to guess how the inline cascades work? Why not provide a working playground example with ample documentation?
0
Viktor Tachev
Telerik team
answered on 18 Feb 2020, 12:51 PM

Hello Riz,

 

Using cascading dropdown editors in the Grid is illustrated in the following sample project. The approach is applicable for InLine and PopUp edit modes:

https://github.com/telerik/ui-for-aspnet-mvc-examples/tree/master/grid/grid-editing-cascading-dropdownlist

 

In case you are using the Kendo UI for jQuery widget check out the knowledge base article below that shows how the functionality can be implemented for different edit modes in the Grid:

https://docs.telerik.com/kendo-ui/knowledge-base/cascading-dropdown-editors

 

Regards,
Viktor Tachev
Progress Telerik

Get quickly onboarded and successful with your Telerik UI for ASP.NET MVC with the dedicated Virtual Classroom technical training, available to all active customers.
Tags
Grid
Asked by
Paul
Top achievements
Rank 1
Answers by
Stefan
Telerik team
Paul
Top achievements
Rank 1
riz
Top achievements
Rank 1
Viktor Tachev
Telerik team
Share this question
or