Ext JS 5 の ViewModel / ViewController の使い方を検証してみました。
参考にしてください。
仕様
- ユーザー一覧を Grid 表示する
- Grid の行をダブルクリックしたらそのデータをフォームに表示する
- フォームを編集するとグリッドに反映される
これを、ViewModel で備わった双方向データバインディングで実現させます。
まずは、model を作ります。
app/model/User.js
[js]
Ext.define(‘Ext5.model.User’, {
extend: ‘Ext.data.Model’,
fields: [
‘id’, ‘name’, ‘email’
]
});
[/js]
Sencha Cmd で generate したプロジェクトの view/main/Main.js を変更します。
app/view/main/Main.js
[js]
Ext.define(‘Ext5.view.main.Main’, {
extend: ‘Ext.container.Container’,
requires: [
‘Ext5.view.edit.Edit’,
‘Ext5.view.list.List’
],
xtype: ‘app-main’,
layout: {
type: ‘border’
},
items: [{
xtype: ‘component’,
padding: 8,
html: ‘My Ext JS 5 App’,
region: ‘north’
},{
xtype: ‘mylist’,
region: ‘center’
},{
xtype: ‘myedit’,
width: 300,
region: ‘east’
}]
});
[/js]
同じディレクトリにある、MainModel.js と MainController.js はいらないので削除します。
items
の 2つめと3つめのビューを作っていきます。
app/view/list/List.js
[js]
Ext.define("Ext5.view.list.List",{
extend: "Ext.grid.Panel",
xtype: ‘mylist’,
controller: "list-list", // ViewControllerの指定
viewModel: { // ViewModelの指定
type: "list-list"
},
bind: ‘{users}’, // データバインド
columns: [{
dataIndex: ‘id’,
text: ‘ID’
},{
dataIndex: ‘name’,
text: ‘名前’,
width: 300
},{
dataIndex: ‘email’,
text: ‘メール’,
width: 300
}],
listeners: { // イベントリスナー
itemdblclick: {
fn: ‘onSelectItem’,
scope: ‘controller’
}
}
});
[/js]
ごく普通の GridPanel です。
最初の方で、ViewController と ViewModel を指定しています。
bind: '{users}'
という記述が見慣れないですね。
これが、データバインドです。この Grid に ViewModel の持っているデータをバインドします。
Grid の場合は、その対象はストアです。
このビューが持つ ViewModel に users
という名前のストアがなくてはいけません。
listeners
では、fn
に 'onSelectItem'
と文字列で指定しています。
scope: 'controller'
の指定があるので、実際のリスナー関数は、ViewController が持っている onSelectItem
メソッドになります。
次にこのビューの ViewModel を見てみます。
app/view/list/ListModel.js
[js]
Ext.define(‘Ext5.view.list.ListModel’, {
extend: ‘Ext.app.ViewModel’,
alias: ‘viewmodel.list-list’,
requires: [
‘Ext5.model.User’
],
stores: {
users: {
model: ‘Ext5.model.User’,
data: [{
id:1, name: ‘中村’, email: ‘nakamura@examplecom’
},{
id:2, name: ‘山田’, email: ‘yamada@examplecom’
},{
id:3, name: ‘田中’, email: ‘tanaka@examplecom’
},{
id:4, name: ‘佐藤’, email: ‘sato@examplecom’
},{
id:5, name: ‘齋藤’, email: ‘saito@examplecom’
}]
}
}
});
[/js]
stores
の中に users
というキーの値としてオブジェクトリテラルをセットしています。
これで、Grid にバインドするストアを定義しています。
Ext JS 5 では、app/store 下にストアの定義を書くよりも、このように ViewModel の中でインスタンスを作る方法がメインになるようです。
ここでは、data
コンフィグを使ってインラインでデータを指定しています。
次に ViewController です。
app/view/list/ListController.js
[js]
Ext.define(‘Ext5.view.list.ListController’, {
extend: ‘Ext.app.ViewController’,
alias: ‘controller.list-list’,
onSelectItem: function(grid, rec) {
var me = this,
form = me.getEditForm();
form.getViewModel().setData({rec: rec});
},
getEditForm: function() {
return Ext.ComponentQuery.query(‘myedit’)[0];
}
});
[/js]
ここで、onSelectItem
メソッドを定義しています。
以前のコントローラーのように、control メソッドにどうこうという記述は不要です。
リスナーの中で、Edit ビューを取得して、その ViewModel にレコードをセットしています。
(ここのやり方はなんかイマイチだと思っています。もうちょっとスマートなやり方がありそう)
では、データをセットされる Edit ビューを見てみます。
app/view/edit/Edit.js
[js]
Ext.define("Ext5.view.edit.Edit",{
extend: "Ext.form.Panel",
xtype: ‘myedit’,
viewModel: {
type: "edit-edit"
},
bodyPadding: 10,
items: [{
xtype: ‘textfield’,
fieldLabel: ‘ID’,
bind: ‘{rec.id}’
}, {
xtype: ‘textfield’,
fieldLabel: ‘名前’,
bind: ‘{rec.name}’
}, {
xtype: ‘textfield’,
fieldLabel: ‘メール’,
bind: ‘{rec.email}’
}]
});
[/js]
なんの変哲も無い FormPanel です。
ただ、ここも items
の中に bind
コンフィグがあります。
ViewModel を見てみましょう。
app/view/edit/EditModel.js
[js]
Ext.define(‘Ext5.view.edit.EditModel’, {
extend: ‘Ext.app.ViewModel’,
alias: ‘viewmodel.edit-edit’,
data: {
rec: null
}
});
[/js]
これだけです。
この data
コンフィグの中のものとビューがバインドします。
data
コンフィグの中には rec
があります。
この rec にレコード (モデルのインスタンス) をセットしてやると、フォームの方では、{rec.id}
などとバインドさせているので、そのデータが表示されます。
これで、Grid の行をダブルクリックすると Form に内容が表示されます。
そこで、フォームの内容を書き換えると、リアルタイムで Grid の表示も変化するのがわかります。
これが双方向データバインディングです。
次の URL から Sencha Fiddle で実際の動きを見ることができます。
https://fiddle.sencha.com/#fiddle/6lp
Reviews On cheap Chargers jersey cheap Panthers jerseys http://simplexsystem.com/wp-content/themes/souffle/images/search.html
ピンバック: Ext JS 5 資料リスト | Sunvisor Lab. Ext JS 別館