ExtJS に関する Sencha のドキュメントに非常に困惑しています。ドキュメントは、アプリケーションのクラスとソース コードに適した構造の重要性を強調し、説明する入門ガイドから始まります。ただし、提供されている例は、入門ガイドで定められたすべての規則を破っています。コードを適切なモデル、ストア、ビューなどのクラス ファイルに分割する代わりに、サンプル ソース コードを含む 1 つのファイルとしてサンプルが提供されます。
ポータルの例 ( http://docs.sencha.com/ext-js/4-1/#!/example/portal/portal.html ) に従うことから始めました。これは私が作成したいアプリケーションの一種だからです。ポータルの例を拡張し、グリッドを表示して RESTful Web サービスをデータ バックエンドとして使用する画面を追加したいと考えました。フロントエンドを作成したいだけのバックエンドを作成しました。そこで、RESTful の例 ( http://docs.sencha.com/ext-js/4-1/#!/example/restful/restful.html )を見ました。
モデル、ストア、ビューなどの個別のクラスの推奨パターンに RESTful な例をコピーしようとしました。
モデル:
Ext.define('MyLodge.model.Member', {
extend: 'Ext.data.Model',
fields: [
{name: 'name', type: 'string'},
{name: 'email', type: 'string'},
{name: 'href', type: 'string'}
]
});
店:
Ext.require('MyLodge.model.Member');
Ext.define('MyLodge.store.Members', {
autoLoad: true,
autoSync: true,
model: 'MyLodge.model.Member',
proxy: {
type: 'rest',
url: 'http://localhost:8888/rest/memberapi/members' ,
reader: {
type: 'json',
root: 'data'
},
writer: {
type: 'json'
}
},
listeners: {
write: function(store, operation){
var record = operation.getRecords()[0],
name = Ext.String.capitalize(operation.action),
verb;
if (name == 'Destroy' ) {
record = operation.records[0];
verb = 'Destroyed';
} else {
verb = name + 'd';
}
Ext.example.msg(name, Ext.String.format( "{0} member: {1}", verb, record.getId()));
}
}
});
意見:
Ext.define('MyLodge.view.content.MemberGrid', {
extend: 'Ext.grid.Panel',
alias: 'widget.membergrid',
initComponent: function(){
var store = Ext.create('MyLodge.store.Members' );
Ext.apply( this, {
height: this.height,
store: store,
stripeRows: true,
columnLines: true,
columns: [{
id : 'name',
text : 'Name',
flex: 1,
sortable : true,
dataIndex: 'name'
},{
text : 'E-Mail',
width : 150,
sortable : true,
dataIndex: 'email'
},{
text : 'Href',
width : 200,
sortable : true,
dataIndex: 'href'
}],
dockedItems: [{
xtype: 'toolbar',
items: [{
text: 'Add',
iconCls: 'icon-add',
handler: function(){
// empty record
store.insert(0, new MyLodge.model.Member());
rowEditing.startEdit(0, 0);
}
}, '-', {
itemId: 'delete',
text: 'Delete',
iconCls: 'icon-delete',
disabled: true,
handler: function(){
var selection = grid.getView().getSelectionModel().getSelection()[0];
if (selection) {
store.remove(selection);
}
}
}]
}]
});
this.callParent(arguments);
}
});
しかし、グリッド行の選択を制御し、[削除] ボタンを有効にするコードをどこに配置すればよいかわかりません。
grid.getSelectionModel().on('selectionchange', function(selModel, selections){
grid.down('#delete').setDisabled(selections.length === 0);
});
また、[追加] ボタンを押すと、次のエラーが表示されます。
Uncaught TypeError: Object [object Object] has no method 'insert'.
どんな助けでも大歓迎です。