issue on kendodropdownlist showing undefine word - asp.net-mvc-3

im having a issue on my kendodropdownlist... whenever i add a optionlabel on it, it always shows undefine fields.. how can i get rid of the undefined on my dropdown list... functionalities of the dropdown is good just the word "undefine" really bugging me out.
here's my code:
<input id="ddlWorker" name="ddlWorker" class:"validate[required] inputLong" style="width: 400px;" value="#workerPosId" />
$("#ddlWorker").kendoDropDownList({
dataTextField: "workerName",
dataValueField: "workerID",
autoBind: false,
optionLabel: {
workerName: "-- Select An Option --",
workerID: ""
},
// define custom template
template:
'<h5>${ data.workerName }</h5>' +
// '<p>${ data.workerID }</p>' +
'<p>${ data.AvailableDay_LookID }</p>' +
'<p>${ data.StartTime } - ${ data.EndTime }</p>',
dataSource: {
transport: {
read: {
url: '/Client/LoadWorkerDropdownList?clientCusPosShiftId=' + clientCusPosShiftId,
dataType: "json",
type: "POST"
}
}
}
});
var dropdownlist = $("#ddlWorker").data("kendoDropDownList");
thanks

That is because it feeds your optionLabel object:
{
workerName: "-- Select An Option --",
workerID: ""
}
into your template:
'<h5>${ data.workerName }</h5>' +
'<p>${ data.AvailableDay_LookID }</p>' +
'<p>${ data.StartTime } - ${ data.EndTime }</p>'
so it is trying to print the AvailableDay_LookID, StartTime, and EndTime data which are undefined on your object.
You would want to skip those fields if they do not exist. Try the template:
'<h5>${ data.workerName }</h5>' +
'#if(data.AvailableDay_LookID) {#<p>${ data.AvailableDay_LookID }</p>#}#' +
'#if(data.StartTime && data.EndTime) {#<p>${ data.StartTime } - ${ data.EndTime }</p>#}#'

Related

kendo grid is taking more time to load when using kendo editor inside a template

I am trying to load the documents on click of a button which is inside a grid but it is creating a new pages for every row and it is taking more time how to resolve it using kendo editor template or another specific methods.
// open window
function openWin(id) {
var myWindow = $("#" + id);
var did = id.replace("win", "doc");
console.log("Value from DID", did);
var rid = Number(id.replace("win", ""));
kendo.ui.progress($(".k-window"), true);
myWindow.data("kendoWindow").center().open();
$.ajax({
type: "POST",
url: "",
data: JSON.stringify(rid),
dataType: "json",
contentType: 'application/json; charset=utf-8',
success: function(data) {
kendo.ui.progress($(".k-window"), false);
$("#" + did).data("kendoEditor").value(data);
},
error: function() {
alert("Error occured!!");
}
});
}
// column definition
{
field: "Document",
template: docTemplateFunction,
title: "Document Intake",
width: "250px",
editable: "inline"
}
// template definition
function docTemplateFunction(dataItem) {
var input = '<div id="win' + dataItem.id + '"><textarea id="doc' + dataItem.id + '" style="width:100%;" aria-label="editor"></textarea></div><button class="k-button" onclick="openWin(' + "'win" + dataItem.id + "'" + ')">Open Doc</button><span class="k-button k-state-disabled doc-btn"><i class="red k-icon k-i-close k-state-disabled"></i></span>';
return input;
}

Using fetch method inside Kendo UI grid.template

How to return value from .fetch() method inside grid.template ?
$("#grid-single-user-groups").kendoGrid({
dataSource: assignedUsersDataSource,
toolbar: ["create"],
columns: [
{
field: "UserID", width: "100%",
editor: userDropDownEditor,
template: function(userID) {
//here I can return everything, and its visible in grid cell
//return "BAR"
allUsersDataSource.fetch(function() {
//Here everything is UNDEFINED
return "FOO";
var data = this.data();
console.log(data.length);
for (var idx = 0, length = data.length; idx < length; idx++) {
console.log(data.length); //show right length
console.log(data[idx].UserName);// //show right UserName
if (data[idx].UserNameID === userID.UserID) {
return userID.Login; //UNDEFINED
//return "foo"; //UNDEFINED
}
})
edit:
allUsersDataSource is Kendo DataSource:
var allUsersDataSource = new kendo.data.DataSource({
transport: {
read: {
url: API_URL + "frank/getusers",
dataType: "json"
}
},
});
results JSON:
[{"UserNameID":"2","UserName":"foo","Surname":"foo2","Login":"foo3","GroupName":"admin"},]
edit2:
trying with read() function instead od fetch, with below code:
template: function(userID) {
allUsersDataSource.read().then(function() {
var view = allUsersDataSource.view();
console.log(view[0].Login)// displays right Login
return view[0].Login; // displays "undefined" in grid cell
});
}
edit3:
My entire code where I whant to use DropDown inside Grid cell:
var allUsersDataSource = new kendo.data.DataSource({
transport: {
read: {
url: API_URL + "frank/getusers",
dataType: "json"
}
},
});
allUsersDataSource.fetch(function() {
allUsers = allUsersDataSource.data();
})
var assignedUsersDataSource = new kendo.data.DataSource({
transport: {
read:{
url: API_URL+"frank/getassignedusers/"+documentId,
dataType: "json"
},
create: {
type: "POST",
url: API_URL+"frank/addusertodocument",
dataType: "json"
},
destroy:{
type: "POST",
url: API_URL+"frank/removeuserdocument",
dataType: "json"
},
},
pageSize: 4,
schema: {
model: {
fields: {
UserName: { editable: false, nullable: true },
Surname: { editable: false, nullable: true },
UserID: { field: "UserID", defaultValue: 1 },
GroupName: { editable: false, nullable: true },
}
}
}
});
$("\#grid-single-user-groups").kendoGrid({
dataSource: assignedUsersDataSource,
filterable: true,
scrollable: false,
toolbar: ["create"],
pageable: true,
columns: [
{
field: "UserID", width: "100%",
editor: userDropDownEditor,
title: "Agent",
template: function(userID) {
for (var idx = 0, length = allUsers.length; idx < length; idx++) {
if (allUsers[idx].UserNameID === userID.UserID) {
return userID.Login;
}
}
}
},
{ command: "destroy" }
],
editable: true,
remove: function(e) {
console.log("Removing", e.model.name);
}
});
function userDropDownEditor(container, options) {
$('<input data-bind="value:' + options.field + '"/>')
.appendTo(container)
.kendoDropDownList({
dataTextField: "Login",
dataValueField: "UserNameID",
filter: "contains",
dataSource: allUsersDataSource
})
}
JSON DataSources - assignedUsersDataSource:
[{"UserID":"198","UserName":"Paw","Surname":"yui","Login":"ddz","GroupName":"ddd"},...]
JSON DataSources - allUsersDataSource:
[{"UserNameID":"198","UserName":"Paw","Surname":"yui","Login":"ddz","GroupName":"ddd"},...]
edit4:
corrected sample datasource:
var assignedUsersDataSource = new kendo.data.DataSource({
data: [{"UserID":"198","UserName":"Paw","Surname":"Mu","Login":"pc","GroupName":"ad"}]
});
var allUsers = new kendo.data.DataSource({
data: [{"UserNameID":"198","UserName":"Paw","Surname":"Mu","Login":"pc","GroupName":"ad"},{"UserNameID":"199","UserName":"Jakub","Surname":"Ch","Login":"jc","GroupName":"ki"}]
});
So to avoid cluttering up the comments here is a possible answer to your problem:
http://dojo.telerik.com/INukUVoT/4
If you now select the item from the dropdown it is changing the id as it retains the last selected item in the selection when you go in and out of it. The reason the name stays the same is a simple one. It's looking in the wrong place for the value to display.
You are simply doing the following:
Look at all the values in the allusers store and then if i get a match of id's just show the value in the model's Login value rather than the value that was found in the data item in the Login.
So you are currently going through a needs loop. you literally could change your template to:
template: "#=data.Login#" rather than having to loop around.
what you seemingly want to do is have one column which is a user object or defined as an id either way will work as you can see in my new examples.
the first grid is binding the UserID property to the grid and then presenting back the value from the dropdown's datasource (you need to ensure that you set the valuePrimitive property to true so it binds only the value and not the object.
the second grid binds the full object and just so you see what is being bound i am stingify'ing the object and putting that into the grid.

Kendo ui grid inline date edit, passing date from Kendo UI to ASP.NET causes invalid ModelState

I have a nullable DateTime property in my DataSource - ExpectedReceiptDate, and i'm implementing inline editing in the grid:
$(document).ready(function() {
$("#grid").kendoGrid({
dataSource: {
transport: {
//setup transport
},
schema:
{
data: 'Data', total: 'Total', errors: 'Errors',
model:
{
id: 'Id',
fields: {
Id : { editable: false, type: 'number' },
Name : { editable: false, type: 'string' },
ExpectedReceiptDate : {
editable: true,
format: "{0: dd/MMM/yyyy}",
nullable: true,
type: 'date'
}
}
}
},
requestEnd: function(e) {
if (e.type == 'update') {this.read();}
},
serverFiltering: true,
serverSorting: true
},
editable: {
mode: "inline"
},
columns: [
{
field: "Id",
title: "ID"
},{
field: "Name",
title: "Name"
},{
field: "ExpectedReceiptDate",
title: "Date",
editor: DateEditor,
},
{
title: " ",
command: ["edit"],
width: 200
}
]
});
});
the editor is simple:
function DateEditor(container, options) {
$('<input required name="' + options.field + '"/>')
.appendTo(container)
.kendoDatePicker({format: "dd/MMM/yyyy"});
}
when editing the row picking up the date for example 24/Feb/2017 i got an error:
Invalid model state ExpectedReceiptDate, the value '(date) FLE Standard Time' is not valid for ExpectedReceiptDate
I have tried to add custom validation for that field:
function ExpectedReceiptDateValidator(input){
if (input.is("[name='ExpectedReceiptDate']") && input.val() != "") {
try {
var date = kendo.parseDate(input.val(), "dd/MMM/yyyy");
if(!date)
return false;
} catch (err) { return false;}
console.log('res', true);
}
return true;
}
The validation passes, the entered date value is parsed well into Date obj, but model state error is still there.
What causes the model state error?
Try moving the format specifier from the schema.model definition to the column definition as format isn't a configuration option of datasource.schema.model but is of grid.columns(http://docs.telerik.com/kendo-ui/api/javascript/ui/grid#configuration-columns.format), which kind of makes sense as date format is a presentation concern.
With the format specifier on the column, you will not need the custom editor as the built-in date editor will use the format from the column configuration automatically. You would only need the custom editor if you want to do some additional customization that is not standard.
Also, I'm not sure the "this.read()" call in the requestEnd is required.
Demo: http://dojo.telerik.com/#Stephen/oNOja
it turns out that the error with invalid model state was a Server's response, i didn't notice that and thought it was a client side issue.
But anyway the issue with inline date edit was still there, finally i found an answer here:
Passing dates from Kendo UI to ASP.NET MVC
MVC uses the “/Date(…)/” format when mapping JSON parameters, but not when mapping form data. By default, Kendo passes the parameters as a form.
One way to handle this date parsing issue is to have the Kendo UI
DataSource send JSON data to the server instead of form data. Then MVC
will properly convert “/Date(…)/” to a DateTime automatically.
The alternative to sending JSON formatted data is to leave our data as
form data, which is the default, and instead just change the
formatting of our dates.
So i did the following:
transport:{
update: ..,
parameterMap: function(data, operation) {
if (operation === "update") {
data.ExpectedReceiptDate = formatDate(data.ExpectedReceiptDate);
}
return data;
}
}
None of the below worked for me as the Link is broken and couldn't find any working solutions out there.
So... in my case(well the only way I could get it to work), I have a change function on one of my grid fields (moving away from a physical save button #AutoSaveIsTheFuture)
schema: {
data: "Data",
total: "Total",
errors: "Errors",
model: {
fields: {
...
ItemDate: { editable: true, type: "date", validation: { required: true }},
...
Amount: { editable: true, type: "decimal", validation: { required: true }}
}
}
},
...
columns: [{
...
{
field: "ItemDate",
title: "Item Date",
format: "{0:yyyy/MM/dd}",
},
field: "Amount",
title: "Amount",
format: "{0:n2}",
editor: customAmountEditor
}],
...
function customAmountEditor(container, options)
{
$('<input data-text-field="' + options.field + '" data-value-field="' + options.field + '" data-bind="value:' + options.field + '" data-format="' + options.format + '"/>')
.appendTo(container)
.kendoNumericTextBox({
change: SaveLineItem
});
}
that sends the fields to my Controller via AJAX POST method, in which I do the following :
function SaveLineItem(e)
{
var element = e.sender.element;
var row = element.closest("tr");
var grid = $("#GridName").data("kendoGrid");
var dataItem = grid.dataItem(row);
var dateField = row.find("input[name='ItemDate']");
var dateValue = dateField.val();
$.ajax({
cache: false,
type: "POST",
url: "#Html.Raw(Url.Action("MethodName", "ControllerName"))",
data: {
"Id": dataItem.Id,
"ItemDateString": dateValue,
...
"Amount": dataItem.Amount,
},
success: function (data)
{
AddRow();
},
error: function (XMLHttpRequest, textStatus, errorThrown) {
if (XMLHttpRequest.status === 410) {
alert(errorThrown);
}
}
});
}
It is received as a String on the Controller side , but at least its in the correct format ("yyyy/mm/dd") and easy to Convert using Convert.ToDateTime(ItemDateString);
Hope this helps. (Apologies if it's Messy)

Scroll to selected row when the row is selected programatic

grid.kendoGrid({
dataTextField: "Description",
dataValueField: "ID",
dataSource: {
data: gridData
},
filterable: {
extra: false,
operators: {
string: {
startswith: $("#" + getId(controlPrefix, "hiddenFilterStartsWith")).val(),
endswith: $("#" + getId(controlPrefix, "hiddenFilterEndsWith")).val(),
eq: $("#" + getId(controlPrefix, "hiddenFilterEq")).val(),
neq: $("#" + getId(controlPrefix, "hiddenFilterNeq")).val(),
contains: $("#" + getId(controlPrefix, "hiddenFilterContains")).val()
}
},
messages: {
clear: $("#" + getId(controlPrefix, "hiddenFilterClear")).val(),
filter: $("#" + getId(controlPrefix, "hiddenFilterFilter")).val(),
info: $("#" + getId(controlPrefix, "hiddenFilterInfo")).val()
}
},
columns: [
{ field: "ID", title: gridTitles[0], width: 200 },
{ field: "Description", title: gridTitles[1], width: 200 }
],
height: 450,
selectable: "row",
change: function (e) {
this.element.find(".k-grid-content").animate({
scrollTop: this.select().offset().top - this.element.find('.k-grid-content').offset().top
});
}
});
I have this kendo grid and I wanto to select a item and automatic scroll to it, the change event is triggered but when I select from code the offset().top has the same values for both elements and when I select it with the mouse it works
Here I make the selection in the code
var employeeFilter = $("#" + getId(controlPrefix, inputControlId)).val();
if (employeeFilter != "") {
grid.data("kendoGrid").select(grid.data("kendoGrid").tbody.find(">tr:has(td:contains('" + employeeFilter + "'))"));
}
If somebody can help me to select the item using code and automatic scroll to it ?
Your selector for the row is correct, but I shortened it like this:
grid.data("kendoGrid").select(grid.find("tr:has(td:contains('" + employeeFilter + "'))"));
The problem is how you compute the value for scrollTop. Since you use animate() on the grid and not on the whole page you need the relative offset of the row to the grid and not to the page. You get the relative offset to the parent with position() (offset() gives you the offset relative to the document). And you don't need to substract the offset of the grid, actually you need to add the scrollTop() value to get the proper value for scrollTop even if the grid was already scrolled.
This is how you it works:
var kendoGrid = grid.data("kendoGrid");
kendoGrid.element.find(".k-grid-content").animate({
scrollTop: kendoGrid.select().position().top
- kendoGrid.element.find('.k-grid-content').position().top
+ kendoGrid.element.find('.k-grid-content').scrollTop()
});
You can try it here: http://dojo.telerik.com/OvIMa

Kendo Ui add on change action drop down list on grid column

I want to add onchange action for the drop down lists on this example:
http://demos.kendoui.com/web/grid/foreignkeycolumn.html
I need to send row id to this function.
If you see this example you can specify a custom editor for a column and do what ever you need in that method like this,
function categoryDropDownEditor(container, options) {
$('<input required data-text-field="CategoryName" data-value-field="CategoryID" data-bind="value:' + options.field + '"/>')
.appendTo(container)
.kendoDropDownList({
autoBind: false,
select: function(e) {
var item = e.item;
var text = item.text();
// Use the selected item or its text
},
dataSource: {
type: "odata",
transport: {
read: "http://demos.kendoui.com/service/Northwind.svc/Categories"
}
}
});
}

Resources