4 <meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
5 <title>The source code</title>
6 <link href="../prettify/prettify.css" type="text/css" rel="stylesheet" />
7 <script type="text/javascript" src="../prettify/prettify.js"></script>
8 <style type="text/css">
9 .highlight { display: block; background-color: #ddd; }
11 <script type="text/javascript">
12 function highlight() {
13 document.getElementById(location.hash.replace(/#/, "")).className = "highlight";
17 <body onload="prettyPrint(); highlight();">
18 <pre class="prettyprint lang-js"><span id='Ext-grid-plugin-CellEditing'>/**
19 </span> * @class Ext.grid.plugin.CellEditing
20 * @extends Ext.grid.plugin.Editing
22 * The Ext.grid.plugin.CellEditing plugin injects editing at a cell level for a Grid. Only a single
23 * cell will be editable at a time. The field that will be used for the editor is defined at the
24 * {@link Ext.grid.column.Column#field field}. The editor can be a field instance or a field configuration.
26 * If an editor is not specified for a particular column then that cell will not be editable and it will
27 * be skipped when activated via the mouse or the keyboard.
29 * The editor may be shared for each column in the grid, or a different one may be specified for each column.
30 * An appropriate field type should be chosen to match the data structure that it will be editing. For example,
31 * to edit a date, it would be useful to specify {@link Ext.form.field.Date} as the editor.
33 * {@img Ext.grid.plugin.CellEditing/Ext.grid.plugin.CellEditing.png Ext.grid.plugin.CellEditing plugin}
37 * Ext.create('Ext.data.Store', {
38 * storeId:'simpsonsStore',
39 * fields:['name', 'email', 'phone'],
41 * {"name":"Lisa", "email":"lisa@simpsons.com", "phone":"555-111-1224"},
42 * {"name":"Bart", "email":"bart@simpsons.com", "phone":"555--222-1234"},
43 * {"name":"Homer", "email":"home@simpsons.com", "phone":"555-222-1244"},
44 * {"name":"Marge", "email":"marge@simpsons.com", "phone":"555-222-1254"}
55 * Ext.create('Ext.grid.Panel', {
57 * store: Ext.data.StoreManager.lookup('simpsonsStore'),
59 * {header: 'Name', dataIndex: 'name', field: 'textfield'},
60 * {header: 'Email', dataIndex: 'email', flex:1,
66 * {header: 'Phone', dataIndex: 'phone'}
68 * selType: 'cellmodel',
70 * Ext.create('Ext.grid.plugin.CellEditing', {
76 * renderTo: Ext.getBody()
79 Ext.define('Ext.grid.plugin.CellEditing', {
80 alias: 'plugin.cellediting',
81 extend: 'Ext.grid.plugin.Editing',
82 requires: ['Ext.grid.CellEditor'],
84 constructor: function() {
85 <span id='Ext-grid-plugin-CellEditing-event-beforeedit'> /**
86 </span> * @event beforeedit
87 * Fires before cell editing is triggered. The edit event object has the following properties <br />
88 * <ul style="padding:5px;padding-left:16px;">
89 * <li>grid - The grid</li>
90 * <li>record - The record being edited</li>
91 * <li>field - The field name being edited</li>
92 * <li>value - The value for the field being edited.</li>
93 * <li>row - The grid table row</li>
94 * <li>column - The grid {@link Ext.grid.column.Column Column} defining the column that is being edited.</li>
95 * <li>rowIdx - The row index that is being edited</li>
96 * <li>colIdx - The column index that is being edited</li>
97 * <li>cancel - Set this to true to cancel the edit or return false from your handler.</li>
99 * @param {Ext.grid.plugin.Editing} editor
100 * @param {Object} e An edit event (see above for description)
102 <span id='Ext-grid-plugin-CellEditing-event-edit'> /**
103 </span> * @event edit
104 * Fires after a cell is edited. The edit event object has the following properties <br />
105 * <ul style="padding:5px;padding-left:16px;">
106 * <li>grid - The grid</li>
107 * <li>record - The record that was edited</li>
108 * <li>field - The field name that was edited</li>
109 * <li>value - The value being set</li>
110 * <li>originalValue - The original value for the field, before the edit.</li>
111 * <li>row - The grid table row</li>
112 * <li>column - The grid {@link Ext.grid.column.Column Column} defining the column that was edited.</li>
113 * <li>rowIdx - The row index that was edited</li>
114 * <li>colIdx - The column index that was edited</li>
117 * <pre><code>
118 grid.on('edit', onEdit, this);
121 // execute an XHR to send/commit data to the server, in callback do (if successful):
124 * </code></pre>
125 * @param {Ext.grid.plugin.Editing} editor
126 * @param {Object} e An edit event (see above for description)
128 <span id='Ext-grid-plugin-CellEditing-event-validateedit'> /**
129 </span> * @event validateedit
130 * Fires after a cell is edited, but before the value is set in the record. Return false
131 * to cancel the change. The edit event object has the following properties <br />
132 * <ul style="padding:5px;padding-left:16px;">
133 * <li>grid - The grid</li>
134 * <li>record - The record being edited</li>
135 * <li>field - The field name being edited</li>
136 * <li>value - The value being set</li>
137 * <li>originalValue - The original value for the field, before the edit.</li>
138 * <li>row - The grid table row</li>
139 * <li>column - The grid {@link Ext.grid.column.Column Column} defining the column that is being edited.</li>
140 * <li>rowIdx - The row index that is being edited</li>
141 * <li>colIdx - The column index that is being edited</li>
142 * <li>cancel - Set this to true to cancel the edit or return false from your handler.</li>
144 * Usage example showing how to remove the red triangle (dirty record indicator) from some
145 * records (not all). By observing the grid's validateedit event, it can be cancelled if
146 * the edit occurs on a targeted row (for example) and then setting the field's new value
147 * in the Record directly:
148 * <pre><code>
149 grid.on('validateedit', function(e) {
152 if (e.row == myTargetRow) {
154 e.record.data[e.field] = e.value;
157 * </code></pre>
158 * @param {Ext.grid.plugin.Editing} editor
159 * @param {Object} e An edit event (see above for description)
161 this.callParent(arguments);
162 this.editors = Ext.create('Ext.util.MixedCollection', false, function(editor) {
163 return editor.editorId;
167 <span id='Ext-grid-plugin-CellEditing-method-destroy'> /**
169 * AbstractComponent calls destroy on all its plugins at destroy time.
171 destroy: function() {
173 me.editors.each(Ext.destroy, Ext);
175 me.callParent(arguments);
178 onBodyScroll: function() {
179 var ed = this.getActiveEditor();
180 if (ed && ed.field) {
181 if (ed.field.triggerBlur) {
182 ed.field.triggerBlur();
190 // Template method called from base class's initEvents
191 initCancelTriggers: function() {
196 view.addElListener('mousewheel', me.cancelEdit, me);
197 me.mon(view, 'bodyscroll', me.onBodyScroll, me);
199 columnresize: me.cancelEdit,
200 columnmove: me.cancelEdit,
205 <span id='Ext-grid-plugin-CellEditing-method-startEdit'> /**
206 </span> * Start editing the specified record, using the specified Column definition to define which field is being edited.
207 * @param {Model} record The Store data record which backs the row to be edited.
208 * @param {Model} columnHeader The Column object defining the column to be edited.
211 startEdit: function(record, columnHeader) {
213 ed = me.getEditor(record, columnHeader),
214 value = record.get(columnHeader.dataIndex),
215 context = me.getEditingContext(record, columnHeader);
217 record = context.record;
218 columnHeader = context.column;
220 // Complete the edit now, before getting the editor's target
221 // cell DOM element. Completing the edit causes a view refresh.
224 // See if the field is editable for the requested record
225 if (columnHeader && !columnHeader.getEditor(record)) {
230 context.originalValue = context.value = value;
231 if (me.beforeEdit(context) === false || me.fireEvent('beforeedit', context) === false || context.cancel) {
235 me.context = context;
236 me.setActiveEditor(ed);
237 me.setActiveRecord(record);
238 me.setActiveColumn(columnHeader);
240 // Defer, so we have some time between view scroll to sync up the editor
241 Ext.defer(ed.startEdit, 15, ed, [me.getCell(record, columnHeader), value]);
243 // BrowserBug: WebKit & IE refuse to focus the element, rather
244 // it will focus it and then immediately focus the body. This
245 // temporary hack works for Webkit and IE6. IE7 and 8 are still
247 me.grid.getView().el.focus((Ext.isWebKit || Ext.isIE) ? 10 : false);
251 completeEdit: function() {
252 var activeEd = this.getActiveEditor();
254 activeEd.completeEdit();
258 // internal getters/setters
259 setActiveEditor: function(ed) {
260 this.activeEditor = ed;
263 getActiveEditor: function() {
264 return this.activeEditor;
267 setActiveColumn: function(column) {
268 this.activeColumn = column;
271 getActiveColumn: function() {
272 return this.activeColumn;
275 setActiveRecord: function(record) {
276 this.activeRecord = record;
279 getActiveRecord: function() {
280 return this.activeRecord;
283 getEditor: function(record, column) {
285 editors = me.editors,
286 editorId = column.itemId || column.id,
287 editor = editors.getByKey(editorId);
292 editor = column.getEditor(record);
297 // Allow them to specify a CellEditor in the Column
298 if (!(editor instanceof Ext.grid.CellEditor)) {
299 editor = Ext.create('Ext.grid.CellEditor', {
304 editor.parentEl = me.grid.getEditorParent();
305 // editor.parentEl should be set here.
308 specialkey: me.onSpecialKey,
309 complete: me.onEditComplete,
310 canceledit: me.cancelEdit
317 <span id='Ext-grid-plugin-CellEditing-method-getCell'> /**
318 </span> * Get the cell (td) for a particular record and column.
319 * @param {Ext.data.Model} record
320 * @param {Ext.grid.column.Colunm} column
323 getCell: function(record, column) {
324 return this.grid.getView().getCell(record, column);
327 onSpecialKey: function(ed, field, e) {
328 var grid = this.grid,
330 if (e.getKey() === e.TAB) {
332 sm = grid.getSelectionModel();
333 if (sm.onEditorTab) {
334 sm.onEditorTab(this, e);
339 onEditComplete : function(ed, value, startValue) {
342 sm = grid.getSelectionModel(),
343 activeColumn = me.getActiveColumn(),
347 dataIndex = activeColumn.dataIndex;
349 me.setActiveEditor(null);
350 me.setActiveColumn(null);
351 me.setActiveRecord(null);
352 delete sm.wasEditing;
354 if (!me.validateEdit()) {
357 // Only update the record if the new value is different than the
358 // startValue, when the view refreshes its el will gain focus
359 if (value !== startValue) {
360 me.context.record.set(dataIndex, value);
361 // Restore focus back to the view's element.
363 grid.getView().el.focus();
365 me.context.value = value;
366 me.fireEvent('edit', me, me.context);
372 <span id='Ext-grid-plugin-CellEditing-method-cancelEdit'> /**
373 </span> * Cancel any active editing.
375 cancelEdit: function() {
377 activeEd = me.getActiveEditor(),
378 viewEl = me.grid.getView().el;
380 me.setActiveEditor(null);
381 me.setActiveColumn(null);
382 me.setActiveRecord(null);
384 activeEd.cancelEdit();
389 <span id='Ext-grid-plugin-CellEditing-method-startEditByPosition'> /**
390 </span> * Starts editing by position (row/column)
391 * @param {Object} position A position with keys of row and column.
393 startEditByPosition: function(position) {
396 sm = grid.getSelectionModel(),
397 editRecord = grid.store.getAt(position.row),
398 editColumnHeader = grid.headerCt.getHeaderAtIndex(position.column);
400 if (sm.selectByPosition) {
401 sm.selectByPosition(position);
403 me.startEdit(editRecord, editColumnHeader);