una tablas tabla modificar hacer for dinamicas datos crear con javascript kendo-ui kendo-grid kendo-asp.net-mvc

tablas - modificar tabla con javascript



Hacer que la celda sea de solo lectura en la rejilla Kendo si se cumple la condiciĆ³n (5)

La forma más simple es usar el evento dataBound para aplicar condicionalmente una de las clases CSS especiales a las celdas que la cuadrícula ignora para editarlas:

  • http://dojo.telerik.com/izOka

    dataBound: function(e) { var colIndex = 1; var rows = this.table.find("tr:not(.k-grouping-row)"); for (var i = 0; i < rows.length; i++) { var row = rows[i]; var model = this.dataItem(row); if (!model.Discontinued) { var cell = $($(row).find("td")[colIndex]); cell.addClass("k-group-cell"); } } },

Digamos que tengo una información como esta:

[ {ID: 1, SomeForeignKeyID: 4, IsFkEnabled: true}, {ID: 2, SomeForeignKeyID: 9, IsFkEnabled: false} ]

Kendo Grid está usando esta información:

columns.Bound(m => m.ID); columns.ForeignKey(p => p.SomeForeignKeyID, ViewBag.ForeignKeys as IEnumerable<object>, "Value", "Name");

Aquí está el problema: cómo hacer que la columna ForeignKey sea editable, pero solo en filas, donde IsFkEnabled == true? El modo de edición es InCell.


Ninguno de estos enfoques funcionó para mí. Una implementación muy simple se parece a esto

edit: function (e) { e.container.find("input[name=''Name'']").each(function () { $(this).attr("disabled", "disabled") }); }

Donde la edición es parte de la declaración de la red kendo y Name es el nombre real del campo.


Otro enfoque es usar su propia función de "editor" para la definición de columna que proporciona un elemento de entrada o un div simple dependiendo de su condición.


Por favor intente con el siguiente fragmento de código.

VER

<script type="text/javascript"> function errorHandler(e) { if (e.errors) { var message = "Errors:/n"; $.each(e.errors, function (key, value) { if (''errors'' in value) { $.each(value.errors, function () { message += this + "/n"; }); } }); alert(message); } } function onGridEdit(arg) { if (arg.container.find("input[name=IsFkEnabled]").length > 0) { arg.container.find("input[name=IsFkEnabled]").click(function () { if ($(this).is(":checked") == false) { } else { arg.model.IsFkEnabled = true; $("#Grid").data("kendoGrid").closeCell(arg.container); $("#Grid").data("kendoGrid").editCell(arg.container.next()); } }); } if (arg.container.find("input[name=FID]").length > 0) { if (arg.model.IsFkEnabled == false) { $("#Grid").data("kendoGrid").closeCell(arg.container) } } } </script> <div> @(Html.Kendo().Grid<MvcApplication1.Models.TestModels>() .Name("Grid") .Columns(columns => { columns.Bound(p => p.ID); columns.Bound(p => p.Name); columns.Bound(p => p.IsFkEnabled); columns.ForeignKey(p => p.FID, (System.Collections.IEnumerable)ViewData["TestList"], "Value", "Text"); }) .ToolBar(toolBar => toolBar.Save()) .Editable(editable => editable.Mode(GridEditMode.InCell)) .Pageable() .Sortable() .Scrollable() .Filterable() .Events(e => e.Edit("onGridEdit")) .DataSource(dataSource => dataSource .Ajax() .Batch(true) .ServerOperation(false) .Events(events => events.Error("errorHandler")) .Model(model => { model.Id(p => p.ID); model.Field(p => p.ID).Editable(false); }) .Read(read => read.Action("ForeignKeyColumn_Read", "Home")) .Update(update => update.Action("ForeignKeyColumn_Update", "Home")) ) ) </div>

MODELO

namespace MvcApplication1.Models { public class TestModels { public int ID { get; set; } public string Name { get; set; } public bool IsFkEnabled { get; set; } public int FID { get; set; } } }

CONTROLADOR

public class HomeController : Controller { public ActionResult Index() { List<SelectListItem> items = new List<SelectListItem>(); for (int i = 1; i < 6; i++) { SelectListItem item = new SelectListItem(); item.Text = "text" + i.ToString(); item.Value = i.ToString(); items.Add(item); } ViewData["TestList"] = items; return View(); } public ActionResult ForeignKeyColumn_Read([DataSourceRequest] DataSourceRequest request) { List<TestModels> models = new List<TestModels>(); for (int i = 1; i < 6; i++) { TestModels model = new TestModels(); model.ID = i; model.Name = "Name" + i; if (i % 2 == 0) { model.IsFkEnabled = true; } model.FID = i; models.Add(model); } return Json(models.ToDataSourceResult(request)); } [AcceptVerbs(HttpVerbs.Post)] public ActionResult ForeignKeyColumn_Update([DataSourceRequest] DataSourceRequest request, [Bind(Prefix = "models")]IEnumerable<TestModels> tests) { if (tests != null && ModelState.IsValid) { // Save/Update logic comes here } return Json(ModelState.ToDataSourceResult()); } }

Si quieres descargar una demo, haz clic here .


Notas:

  • esta solución funciona solo para la edición interna (la edición en línea o emergente requiere un enfoque diferente)
  • el primer enfoque puede provocar efectos visuales no deseados (salto de cuadrícula) bajo ciertas circunstancias; si experimentas eso, recomiendo el enfoque n. ° 2
  • el enfoque n.º 2 puede no funcionar si desea utilizar los contenedores MVC (aunque es posible ampliar Kendo.Mvc.UI.Fluent.GridEventBuilder); en ese caso, deberá vincular el controlador de edición en JS

Enfoque # 1

Use el evento de edit la grilla y luego haga algo como esto:

$("#grid").kendoGrid({ dataSource: dataSource, height: "300px", columns: columns, editable: true, edit: function (e) { var fieldName = e.container.find("input").attr("name"); // alternative (if you don''t have the name attribute in your editable): // var columnIndex = this.cellIndex(e.container); // var fieldName = this.thead.find("th").eq(columnIndex).data("field"); if (!isEditable(fieldName, e.model)) { this.closeCell(); // prevent editing } } }); /** * @returns {boolean} True if the column with the given field name is editable */ function isEditable(fieldName, model) { if (fieldName === "SomeForeignKeyID") { // condition for the field "SomeForeignKeyID" // (default to true if defining property doesn''t exist) return model.hasOwnProperty("IsFkEnabled") && model.IsFkEnabled; } // additional checks, e.g. to only allow editing unsaved rows: // if (!model.isNew()) { return false; } return true; // default to editable }

Demostración aquí ( actualizado para Q1 2014 )

Para usar esto a través de la sintaxis fluida de MVC, simplemente dé la función de edit anónima sobre un nombre (por ejemplo, en onEdit ):

function onEdit(e) { var fieldName = e.container.find("input").attr("name"); // alternative (if you don''t have the name attribute in your editable): // var columnIndex = this.cellIndex(e.container); // var fieldName = this.thead.find("th").eq(columnIndex).data("field"); if (!isEditable(fieldName, e.model)) { this.closeCell(); // prevent editing } }

y hacer referencia de esta manera:

@(Html.Kendo().Grid() .Name("Grid") .Events(events => events.Edit("onEdit")) )

La desventaja de esto es que el editor se crea primero antes de que se desencadene el evento de edición, que a veces puede tener efectos visuales no deseados.

Enfoque # 2

Extienda la grilla anulando su método editCell con una variación que desencadena un evento beforeEdit ; para que eso funcione con las opciones de cuadrícula, también tendrás que anular el método init:

var oEditCell = kendo.ui.Grid.fn.editCell; var oInit = kendo.ui.Grid.fn.init; kendo.ui.Grid = kendo.ui.Grid.extend({ init: function () { oInit.apply(this, arguments); if (typeof this.options.beforeEdit === "function") { this.bind("beforeEdit", this.options.beforeEdit.bind(this)); } }, editCell: function (cell) { var that = this, cell = $(cell), column = that.columns[that.cellIndex(cell)], model = that._modelForContainer(cell), event = { container: cell, model: model, field: column.field }; if (model && this.trigger("beforeEdit", event)) { // don''t edit if prevented in beforeEdit if (event.isDefaultPrevented()) return; } oEditCell.call(this, cell); } }); kendo.ui.plugin(kendo.ui.Grid);

luego utilícelo de manera similar a # 1:

$("#grid").kendoGrid({ dataSource: dataSource, height: "300px", columns: columns, editable: true, beforeEdit: function(e) { var columnIndex = this.cellIndex(e.container); var fieldName = this.thead.find("th").eq(columnIndex).data("field"); if (!isEditable(fieldName, e.model)) { e.preventDefault(); } } });

La diferencia de este enfoque es que el editor no se creará (y enfocará) primero. El método beforeEdit está utilizando el mismo método isEditable desde # 1. Vea una demostración de este enfoque aquí .

Si desea utilizar este enfoque con envoltorios MVC pero no desea / no puede extender GridEventBuilder, puede enlazar su controlador de eventos en JavaScript (coloque debajo del inicializador MVC de la grilla):

$(function() { var grid = $("#grid").data("kendoGrid"); grid.bind("beforeEdit", onEdit.bind(grid)); });