注释
ExtJS版本:6.2.1.167
Fiddle: fiddle.sencha.com/#view/editor&fiddle/1tlt
这个功能在ExtJS 2.x中可用,没有任何问题。
目标
创建一个带有分组功能和单元格编辑插件的网格,可以在单个列中使用多个不同的编辑器(textfield
和combo
)。
该网格已经颠倒了传统的表格系统,使字段名称和记录值垂直显示。下面是表头的示例:
+-------------+-----------------+-----------------+-----------------
- Field Names - Record 1 Values - Record 2 Values - Editable Column
+-------------+-----------------+-----------------+-----------------
因为有数百个字段,但只有几条记录可供比较,因此我们无法使用传统系统。
代码
以下是主要的代码,它允许我使用多个编辑器:
Ext.define('MemberCellEditing', {
extend: 'Ext.grid.plugin.CellEditing',
xtype: 'membercellediting',
alias: 'plugin.membercellediting',
getCachedEditor: function(editorId, record, column) {
var me = this,
editors = me.editors,
dropDownName = record.get('dropDown');
// If dropdown field, use dropdown name as editor id
if (dropDownName && dropDownName != 'N') editorId = dropDownName;
// Attempt to get editor
var editor = editors.getByKey(editorId);
if (!editor) {
if (dropDownName && dropDownName != 'N') {
// Retrieve combo
var combo = DropDownManager.getCombo(editorId);
// Create editor with combo
editor = Ext.create('Ext.grid.CellEditor', {
editorId: editorId, // Each dropdown field will have its own combo
field: combo,
floating: true
});
} else {
// Use default editor configured for column
editor = column.getEditor(record);
}
if (!editor) {
return false;
}
// Allow them to specify a CellEditor in the Column
if (!(editor instanceof Ext.grid.CellEditor)) {
// Apply the field's editorCfg to the CellEditor config.
// See Editor#createColumnField. A Column's editor config may
// be used to specify the CellEditor config if it contains a field property.
editor = new Ext.grid.CellEditor(Ext.apply({
floating: true,
editorId: editorId,
field: editor
}, editor.editorCfg));
}
// Add the Editor as a floating child of the grid
// Prevent this field from being included in an Ext.form.Basic
// collection, if the grid happens to be used inside a form
editor.field.excludeForm = true;
// If the editor is new to this grid, then add it to the grid, and ensure it tells us about its life cycle.
if (editor.column !== column) {
editor.column = column;
column.on('removed', me.onColumnRemoved, me);
}
editors.add(editor);
}
// Inject an upward link to its owning grid even though it is not an added child.
editor.ownerCmp = me.grid.ownerGrid;
if (column.isTreeColumn) {
editor.isForTree = column.isTreeColumn;
editor.addCls(Ext.baseCSSPrefix + 'tree-cell-editor');
}
// Set the owning grid.
// This needs to be kept up to date because in a Lockable assembly, an editor
// needs to swap sides if the column is moved across.
editor.setGrid(me.grid);
// Keep upward pointer correct for each use - editors are shared between locking sides
editor.editingPlugin = me;
return editor;
}
});
问题
我的代码可以让你在单个列中使用多个编辑器,但它会“随机”抛出错误。我说“随机”,是因为我无法找到错误的实际原因。
错误#1
无法获取未定义或空引用的style
属性
错误#2
无法获取未定义或空引用的parentNode
属性
这两个错误的原因是当前引用的编辑器上的el
属性已被销毁,意味着没有dom
属性。
如何重现
这是我无法解决此问题的部分原因。我无法找到一个具体的方法来复制该问题。不幸的是,我可以获得错误的方式是点击/切换到单元格,输入数据,切换到其他单元格,切换组等的随机组合... 我目前通常使用的方法涉及输入一些随机数据,然后疯狂地点击以在两个相邻单元格之间交替聚焦。大多数时候,少于30秒就会出现错误。
我目前的理论是有一个事件被触发,调用某个函数,由于某种原因销毁了编辑器的el
属性。我尝试查看错误调用堆栈顶部的值,似乎在该点上el
属性已经被销毁。
底线
我正在寻找如何跟踪问题实际原因的建议。
更新
事实证明,目前存在一个与在单元格编辑器中使用组合框有关的错误。这里有另一个人遇到的非常类似的问题:
这里是错误ID:EXTJS-23330
据Sencha Support表示,目前没有可用的解决方法,该bug仍然存在。更新 #2
该缺陷存在于 6.0.2 和 6.5 版本。
幸运的是,我找到了一种更加一致地重现该缺陷的方法:
- 将光标悬停在 Group A 上 5 秒钟。 展开 Group A。
- 将光标悬停在 (Field 1, Value Column) 上 5 秒钟。
- 单击 (Field 1, Value Column)。
- 等待 5 秒钟,然后折叠 Group A。
- 等待 3 秒钟,然后将光标悬停在 Group B 标题上。
- 等待 10 秒钟,然后将光标悬停在 Group A 标题上。
- 等待 3 秒钟,然后展开 Group A。
- 将光标悬停在 (Field 1, Value Column) 字段上 3 秒钟。
- 将光标悬停在 (Field 1, Value 2 Column) 上 3 秒钟。
- 单击 (Field 1, Value 2 Column)。
如果错误没有发生(似乎还未在6.5中发生):
- 等待 3 秒钟,然后单击 (Field 1, Value Column)。
- 等待 1 秒钟,然后再次单击 (Field 1, Value Column)。
它并不是100%可靠的,但比随机点击要可靠得多。