Cascading kendoDropDownList, get selected text in first dropdown - kendo-ui

I'm fairly new to Kendo UI and got the basics for my code here : http://demos.telerik.com/kendo-ui/dropdownlist/cascadingdropdownlist
I got 2 api calls, where the first take no parameters and return a list if items (Id, Name)
The second api call take in an Id, and return a seconds list of items (also just an object with Id and Name)
From this I want to have 2 cascading kendo dropdowns.
However my problem is the second one's url always have the id being null or empty, and I cannot figure out what is the right syntax:
// First dropdown, all good
var controllers = $("#Controller").kendoDropDownList({
optionLabel: "Select controller...",
dataTextField: "Name",
dataValueField: "Id",
dataSource: {
serverFiltering: true,
transport: {
read: "/SharedData/GetControllers/"
}
}
}).data("kendoDropDownList");
// second dropdown, always hit the api method with the id being null or empty (depending on syntax for url)
var actions = $("#Action").kendoDropDownList({
autoBind: true,
cascadeFrom: "controllers",
cascadeFromField: "Id",
optionLabel: "Select Action...",
dataTextField: "Id",
dataValueField: "Name",
dataSource: {
serverFiltering: true,
transport: {
// HELP: need pass id to this route (which is id of selected controller)
read: "/SharedData/GetControllerActions/id=" + $("#Controller").data("kendoDropDownList").text()
}
}
}).data("kendoDropDownList");

I believe the problem is that your datasource only gets set one time - at the time of initialization - and at this time the value of the dropdown is null. What i would do is add a change event on the first dropdown like this:
var controllers = $("#Controller").kendoDropDownList({
optionLabel: "Select controller...",
dataTextField: "Name",
dataValueField: "Id",
dataSource: {
serverFiltering: true,
transport: {
read: "/SharedData/GetControllers/"
}
},
change: function(e) {
setSecondDS();
}
}).data("kendoDropDownList");
var setSecondDS = function() {
//initialize your new kendo datasource here
var dataSource = new kendo.data.DataSource({
//your stuff here
transport:
serverFiltering:
});
$("#Action").data("kendoDropDownList").setDataSource(dataSource);
}

Related

Kendo datasource: add method wipes out existing data

The code below gets my list of categories and displays them. However, when I uncomment the middle line of code to add an "All Categories" entry then all the other categories go away and it only displays the inserted "All Categories" entry.
var categoryDataSource = new kendo.data.DataSource({
transport: { read: resolveUrl('~/Catalog/Categories') },
});
//categoryDataSource.insert({ "Title": "All Categories", "OID": "0" }, 0);
$("#categoriesDropDown").kendoDropDownList({
dataTextField: "Title",
dataValueField: "OID",
dataSource: categoryDataSource
});
What am I doing wrong here?
I believe the problem is because the dataSource hasn't done a fetch of the data, it doesn't have a set of records to insert into. So when you insert one, it trounces all over what is going to be used as the data set.
I can reproduce the behavior using a local array (http://jsbin.com/xaruka/1/edit?html,js,output).
I think you do a read once the dataSource is setup, it will have its internal list of items to insert into.
var categoryDataSource = new kendo.data.DataSource({
transport: { read: resolveUrl('~/Catalog/Categories') },
});
categoryDataSource.read();
categoryDataSource.insert(0, { "Title": "All Categories", "OID": "0" });
$("#categoriesDropDown").kendoDropDownList({
dataTextField: "Title",
dataValueField: "OID",
dataSource: categoryDataSource
});
Working sample http://jsbin.com/xaruka/2/edit?html,js,output

Setting dataTextField value in Kendo UI kendoComboBox object

I have a Kendo UI combobox object something like this :
widget: "kendoComboBox",
options: {
dataTextField: "#:userFirstName#&nbsp#:userLastName#",
dataValueField: "userId",
template: "#:userFirstName#&nbsp#:userLastName#",
change: function (e) {
that.model.fn.bringUserData();
}
}
I can arrange the template, but i cannot dataTextField value depends on that template. It is possible to make it "userId" etc. But seems not possible to set selected value as #:userFirstName#&nbsp#:userLastName#. (dataTextFieldTemplate doesn't work.)
Could you help me to solve this?
Correct, you cannot make it a composition of two fields. It needs to be a field per se. What you can do is when reading data from the DataSource create an additional field that is the concatenation of those two fields. You can add to you DataSource definition something like this:
var dataSource = new kendo.data.DataSource({
transport: {
read: {
url: "..."
}
},
schema: {
parse: function(response) {
$.each(response, function(idx, elem) {
elem.fullName = elem.firstName + " " + elem.lastName;
});
return response;
}
}
});
Then the options for the combobox are simply:
options: {
dataTextField: "fullName",
dataValueField: "userId",
...
}
See it in action here : http://jsfiddle.net/OnaBai/12hpLeux/1/

kendo grid delete command not working

i have developed a web application using kendo ui tools and theres a kendo grid with batch edit mode..
but when i press the delete button for any record in kendo grid it will erase from the list in grid but actually not in the data source.when i reload the page or grid the deleted item will still exist..
here is the code of my grid
<div id="grid">
</div>
<script type="text/javascript">
$("#submitMarketUser").click(function () {
var grid = $("#grid").data("kendoGrid");
var dataSource = new kendo.data.DataSource({
transport: {
read: {
url: "WholeSaleTrade/GetTradeProductDetail",
dataType: "json",
data: {
test: $("#Names").val()
}
},
destroy: {
url: "WholeSaleTrade/DeletePro",
type: "POST",
dataType: "jsonp",
data: {
DAKy: $("#Names").val(),
DIKy: $("#btntxt").val()
}
},
create: {
url: "WholeSaleTrade/CreateProduct",
type: "POST",
dataType: "jsonp",
data: {
AKy: $("#Names").val(),
IKy: $("#btntxt").val()
}
}
},
pageSize: 5,
schema: {
model: {
id: "ProductKey",
fields: {
ProductKey: { editable: false, nullable: true },
ProductName: { validation: { required: true} }
}
}
}
});
$("#grid").kendoGrid({
dataSource: dataSource,
editable: true,
toolbar: ["create", "save"],
autobind: true,
pageable: true,
columns: [
{ field: "ProductName", title: "Product Name",
editor: function (container, options) {
var model = options.model;
$('<input id="btntxt" name="' + options.field + '"/>').appendTo(container).kendoComboBox({
dataSource: {
type: "POST",
transport: {
read: {
url: "MarketInformation/PopulateProducts",
success: function (data) {
var prod = data[0];
model.set("ProductName", prod.ItmNm);
model.set("ItmKy", prod.ItmKy);
model.set("UserKey", $("#Names").val());
}
}
}
},
dataValueField: "ItmKy",
dataTextField: "ItmNm"
});
}
},
{ command: ["destroy"], title: " " }
]
});
});
</script>
can not identify that where is the fault going and can somebody please help me to solve this matter.
There are three common reasons delete won't work:
1. Not setting editable of grid to inline or popup. The deleted items will be automatically processed through transport destroy only for "inline"/"popup" edit modes. Ex:
editable: {
mode: "inline",
}
//or
editable: "inline"
2. If on your datasource, you have the batch flag set to true, this means the datasource will make the call only after you tell it to, e.g calling sync(). Ex:
var dataSource = new kendo.data.DataSource({
batch: true,
//.....
});
//... in some where e.g in a save button click event call the following line:
dataSource.sync();
3. You should define id to your primary key of database field name inside model of datasource. Ex:
model: {
id: "ProductID",
fields: {
ProductID: { editable: false, nullable: true },
}
}
So the problem with your code is first one, i.e you did not set editable to inline or popup
If you choose not to include editable.mode in order to utilize the in-cell editing, you can set the toolbar of the grid to include the option save:
$("#grid").kendoGrid({
dataSource: {
transport: {
....
},
schema: {
....
}
},
toolbar: ["create", "save", "cancel"],
columns: [
....
],
editable: true
});
This will create a save button at the toolbar of the grid. After deleting any records by clicking the destroy command button, click on the save button to have the grid to make an Ajax call to the server to delete the record.
If you would rather delete the record automatically without including the save button, you could add a change event handler to the datasource of the grid:
$("#grid").kendoGrid({
dataSource: {
transport: {
....
},
schema: {
....
},
change: function(e) {
if (e.action === "remove") {
this.sync();
}
}
},
columns: [
....
],
editable: true
});
This will automatically sync the changes you made to the grid with the server when there's a data change.
Hmm try not including type: "POST", and see if it now works since as far as I can see that bit isn't included on the demo's and I don't think I included it when I last did inline edits/deletes.
I had put an arbitray name for an int on the server Delete Method.
[HttpPost]
public ActionResult DeleteRandomTest(Int32 randomTestId)
{
...
}
The default modelbinder was probably looking for a property called Id (same as the primary key of my type according to the configuration of the model).
.Model(config => config.Id(p => p.Id))
In fact, I proved this by changing the signature to the following:
[HttpPost]
public ActionResult DeleteRandomTest(Int32 Id)
{
...
}
My break point was hit after that.
Ultimately, I used the full type as the parameter as shown in the Kendo examples because I didn't want to have poorly named parameter names (not camel case) in the action. Shown as follows:
[HttpPost]
public ActionResult DeleteRandomTest([DataSourceRequest]
DataSourceRequest request, RandomDrugTest randomDrugTest)
{
...
}
This seems to the be the reason it wasn't working.
I had the same issue. My issue was caused by having a data property in the kendo model. Example:
{id: 1, data: ""}

KendoUI grid databinding

Can someone tell me how to bind kendo grid based on previous control selection?
Ex: I've placed one dropdown list and grid in a page. Now I wanted to populate data in grid based on dropdown selected value.
Can someone help me to do this. I'm working with MVC.
try this :
$("#dept").kendoComboBox({
filter: "contains",
index: 0,
dataTextField: "Name",
dataValueField: "ID",
dataSource: data,
select: onSelect
});
//Dropdown change event
function onSelect(e) {
var dataItem = this.dataItem(e.item.index());
UpdateUPGridSource(dataItem.value);
}
//Refresh Datasource by Role wise
function UpdateGridSource(DropdownValue) {
var grd = $("#users").data("kendoGrid");
//Set url property of the grid data source
grd.dataSource.transport.options.read.url = '/Controller/JSONMethodName?ParameterName='+ RoleID;
//Read data source to update
grd.dataSource.read();
}
Maybe you can do this as follow:
$("#dept").kendoComboBox({
filter: "contains",
suggest: true,
index: 0,
dataTextField: "Name",
dataValueField: "ID",
dataSource: data,
change: function(e){
grid.data("kendoGrid").dataSource.filter({
field: "someField",
operator: "eq|etc.",
value: this.value()
});
}
});
grid is the object you defined by kendoGrid() method.
hope it will help you.

Kendo AutoComplete does not re-query the datasource when retyping search string

I have a problem with the Kendo AutoComplete widget.
I am trying it to query the datasource after the user has entered the first two characters of their search.
On the server (web api) I restrict the search using those two chars and all is well, i.e. a subset is returned and correctly shown and further filtered if I carry on typing in the search.
However, I then retype a new search entry which is no longer firing back to the datasource so I am stuck with the data that was retrieved from the first query.
How do I go about this properly?
Thanks
Here is my test code:
public class AlbumsController : ApiController
{
HttpRequest _request = HttpContext.Current.Request;
// GET api/albums
public IEnumerable<Album> GetForAutoComplete()
{
string sw = _request["sw"] == null ? "" : _request["sw"].ToString();
var query = (from a in Albums.MyAlbums
where a.Title.ToLower().StartsWith(sw)
orderby a.Title
select a).ToArray();
return query;
}
and my javascript on the client is like this:
var dataSource = new kendo.data.DataSource({
transport: {
read: {
url: "/api/Albums/GetForAutoComplete",
data: {
sw: function () {
return $("#albumSearch").data("kendoAutoComplete").value();
}
}
}
}
});
$("#albumSearch").kendoAutoComplete({
dataSource: dataSource,
dataTextField: "Title",
minLength: 2,
placeholder: "type in here.."
});
Set serverFiltering to true. The default is false, so it will only grab data once and assume that it now has all the data, and subsequent filtering is done on the client.
To have it re-send to the server every time, add this:
var dataSource = new kendo.data.DataSource({
serverFiltering: true, // <-- add this line.
transport: {
...
}
});
The code for selecting an European country while typing using kendo autocomplete from database as below:
$("#countries").kendoAutoComplete({
dataTextField: "yourfield",
filter: "startswith", // or you can use filter: "contains",
minLength: 3, //what ever you want. In my case its 0.
placeholder: "Select country...",
dataSource: {
type: "get",
serverFiltering: true, //or can also make it false
transport: {
read: {
url: "/yourController/yourAction",
datatype: "json"
}
}
}
});
It works fine for me.

Resources