Dynamically Change Form Item Properties in the Editing State
The following instructions explain how to dynamically change a form item's properties based on another form editor's value:
Specify the form.customizeItem callback function
This function allows you to change form item properties dynamically. Within this function, get the index of the row that a user edits and use this index to get the cell value that should affect form item properties.NOTEIf you enable the repaintChangesOnly property, the form.customizeItem is not executed.In the following code, the
"AddressRequired"
value affects the"Home Address"
item's visibility:jQuery
JavaScript$(function() { var dataGrid = $("#dataGridСontainer").dxDataGrid({ // ... columns: [ "State", { dataField: "Address", visible: false }, { dataField: "AddressRequired", visible: false } ], editing: { mode: "form", allowUpdating: true, allowAdding: true, form: { items: [ // ... "AddressRequired", { itemType: "group", caption: "Home Address", items: ["State", "Address"] } ], customizeItem: function(item) { if (item && item.itemType === "group" && item.caption === "Home Address") { const editRowKey = gridInstance.option('editing.editRowKey'); const rowIndex = gridInstance.getRowIndexByKey(editRowKey); item.visible = gridInstance.cellValue(rowIndex, "AddressRequired"); } }, } } }).dxDataGrid("instance"); });
Angular
app.component.htmlapp.component.tsapp.module.ts<dx-data-grid ... > <!-- ... --> <dxi-column dataField="State"></dxi-column> <dxi-column dataField="Address" [visible]="false"></dxi-column> <dxi-column dataField="AddressRequired" [visible]="false"></dxi-column> <dxo-editing mode="form" [allowUpdating]="true" [allowAdding]="true"> <dxo-form [customizeItem]="customizeItem"> <!-- ... --> <dxi-item dataField="AddressRequired"></dxi-item> <dxi-item itemType="group" caption="Home Address"> <dxi-item dataField="State"></dxi-item> <dxi-item dataField="Address"></dxi-item> </dxi-item> </dxo-form> </dxo-editing> </dx-data-grid>
import { Component, ViewChild } from '@angular/core'; import { DxDataGridComponent } from 'devextreme-angular'; @Component({ selector: 'app-root', templateUrl: './app.component.html', styleUrls: ['./app.component.css'] }) export class AppComponent { @ViewChild(DxDataGridComponent, { static: false }) dataGrid: DxDataGridComponent; // Prior to Angular 8 // @ViewChild(DxDataGridComponent) dataGrid: DxDataGridComponent; // ... customizeItem = (item) => { if (item && item.itemType === 'group' && item.caption === 'Home Address') { const gridInstance = this.dataGrid.instance; const editRowKey = gridInstance.option('editing.editRowKey'); const rowIndex = gridInstance.getRowIndexByKey(editRowKey); item.visible = gridInstance.cellValue(rowIndex, "AddressRequired"); } } }
import { BrowserModule } from '@angular/platform-browser'; import { NgModule } from '@angular/core'; import { AppComponent } from './app.component'; import { DxDataGridModule } from 'devextreme-angular'; @NgModule({ declarations: [ AppComponent ], imports: [ BrowserModule, DxDataGridModule ], providers: [ ], bootstrap: [AppComponent] }) export class AppModule { }
Vue
App.vue<template> <DxDataGrid :ref="gridRefName" ... > <!-- ... --> <DxColumn data-field="State" /> <DxColumn data-field="AddressRequired" :visible="false" /> <DxColumn data-field="Address" :visible="false" /> <DxEditing :allow-updating="true" :allow-adding="true" mode="form"> <DxForm :customize-item="customizeItem"> <!-- ... --> <DxSimpleItem data-field="AddressRequired" /> <DxGroupItem caption="Home Address"> <DxSimpleItem data-field="State" /> <DxSimpleItem data-field="Address" /> <DxGroupItem> </DxForm> </DxEditing> </DxDataGrid> </template> <script> import 'devextreme/dist/css/dx.light.css'; import DxDataGrid, { DxColumn, DxEditing, DxForm, DxSimpleItem, DxGroupItem } from "devextreme-vue/data-grid"; export default { components: { DxDataGrid, DxColumn, DxEditing, DxForm, DxSimpleItem, DxGroupItem }, data() { return { // ... rowKey: -1 } }, methods: { customizeItem(item) { if (item && item.itemType === "group" && item.caption === "Home Address") { const gridInstance = this.dataGrid; const editRowKey = gridInstance.option('editing.editRowKey'); const rowIndex = gridInstance.getRowIndexByKey(editRowKey); item.visible = gridInstance.cellValue(rowIndex, "AddressRequired"); } } }, computed: { dataGrid: function() { return this.$refs[this.gridRefName].instance; } } } </script>
React
App.jsimport React from 'react'; import 'devextreme/dist/css/dx.light.css'; import DataGrid, { Column, Editing, Form, SimpleItem, GroupItem } from 'devextreme-react/data-grid'; class App extends React.Component { constructor(props) { super(props); this.dataGridRef = React.createRef(); } get dataGrid() { return this.dataGridRef.current.instance; } render() { return ( <DataGrid ref={this.dataGridRef} ... > {/* ... */} <Column dataField="State" /> <Column dataField="Address" visible={false} /> <Column dataField="AddressRequired" visible={false} /> <Editing allowUpdating={true} allowAdding={true} mode="form"> <Form customizeItem={this.customizeItem}> {/* ... */} <SimpleItem dataField="AddressRequired" /> <GroupItem caption="Home Address"> <SimpleItem dataField="StateID" /> <SimpleItem dataField="Address" /> </GroupItem> </Form> </Editing> </DataGrid> ); } customizeItem = (item) => { if (item && item.itemType === "group" && item.caption === "Home Address") { let gridInstance = this.dataGrid.current.instance; const editRowKey = gridInstance.option('editing.editRowKey'); const rowIndex = gridInstance.getRowIndexByKey(editRowKey); item.visible = gridInstance.cellValue(rowIndex, "AddressRequired"); } } } export default App;
ASP.NET Core Controls
Razor C#@(Html.DevExtreme().DataGrid() // ... .ID("dataGridContainer") .Columns(columns => { // ... columns.Add().DataField("State"); columns.Add().DataField("AddressRequired").Visible(false); columns.Add().DataField("Address").Visible(false); }) .Editing(e => e.Mode(GridEditMode.Form) .AllowUpdating(true) .AllowAdding(true) .Form(f => f.Items(items => { // ... items.AddSimple().DataField("AddressRequired"); items.AddGroup() .Caption("Home Address") .Items(groupItems => { groupItems.AddSimple().DataField("State"); groupItems.AddSimple().DataField("Address"); }); .CustomizeItem("customizeItem") })) ) ) <script type="text/javascript"> // ... function customizeItem(item) { if (item && item.itemType === "group" && item.caption === "Home Address") { const gridInstance = $("#gridContainer").dxDataGrid("instance"); const editRowKey = gridInstance.option('editing.editRowKey'); const rowIndex = gridInstance.getRowIndexByKey(editRowKey); item.visible = gridInstance.cellValue(rowIndex, "AddressRequired"); } } </script>
Specify the setCellValue callback function
Specify setCellValue for those columns whose editors affect other form items. In the function, call its default implementation as shown below. This call forces all form items to re-render themselves with the new properties.In the following code, we declare the setCellValue function for the
"AddressRequired"
column:jQuery
JavaScript$(function() { $("#dataGridСontainer").dxDataGrid({ // ... columns: [ // ... { dataField: "AddressRequired", setCellValue: function(newData, value) { this.defaultSetCellValue(newData, value); } } ] }); });
Angular
app.component.htmlapp.component.ts<dx-data-grid ... > <!-- ... --> <dxi-column dataField="AddressRequired" [setCellValue]="setCellValue"></dxi-column> </dx-data-grid>
import { Component } from '@angular/core'; @Component({ selector: 'app-root', templateUrl: './app.component.html', styleUrls: ['./app.component.css'] }) export class AppComponent { // ... setCellValue(newData, value) { let column = (<any>this); column.defaultSetCellValue(newData, value); } }
Vue
App.vue<template> <DxDataGrid ... > <!-- ... --> <DxColumn data-field="AddressRequired" :set-cell-value="setCellValue" /> </DxDataGrid> </template> <script> // ... export default { // ... methods: { setCellValue(newData,value) { let column = this; column.defaultSetCellValue(newData, value); } } } </script>
React
App.js// ... class App extends React.Component { // ... render() { return ( <DataGrid ... > {/* ... */} <Column dataField="AddressRequired" setCellValue={this.setCellValue} /> </DataGrid> ); } setCellValue(newData, value) { let column = this; column.defaultSetCellValue(newData, value); } } export default App;
ASP.NET Core Controls
Razor C#@(Html.DevExtreme().DataGrid() // ... .Columns(cols => { // ... cols.Add().DataField("AddressRequired") .SetCellValue("setCellValue"); }) ) <script type="text/javascript"> // ... function setCellValue(newData, value) { this.defaultSetCellValue(newData, value); } </script>
The full project is available on GitHub: DataGrid - How to hide/disable Edit Form items based on another item's value