サーバーからデータをフェッチし、それをストアに入れ、テンプレートにレンダリングするデータビュー リストがあります。標準的なもの。
UI のデータビュー リストの上には、いくつかの Ext.Button を含むボタン バーがあります。ボタンをタップして、ボタンの名前に基づいてリストをフィルタリングできるようにしたい。例: 「English 9A」ボタンをクリックして、「English 9A」の「title」を持つアイテムをリストに表示します。
今のところ、ボタンをクリックすると、リストが消えて、「Uncaught TypeError: Cannot read property 'position' of undefined」というコンソール エラーが表示され、リストがあった場所に読み込みスピナーが表示されます。
同様の質問があることは知っていますが、すべての解決策を試しましたが、まったくうまくいきませんでした。
サンプル json データ:
{
"ftype":"Announcement",
"value":{
"created":"7/18/2013 05:40:06 PM",
"content":"Hello class, it is July 29th. This is quiz",
"announcementtypename":"HW",
"announcementtypeid":2,
"expiresdate":"2013-07-19",
"isowner":false,
"gradable":false,
"starred":false,
"id":172459,
"order":1,
"state":1,
"statetyped":1,
"qnacount":0,
"attachmentscount":0,
"ownerattachmentscount":0,
"title":"Spanish 9A",
}
},
{
"ftype":"Announcement",
"value":{
"created":"7/18/2013 12:04:45 PM",
"content":"Hello class, it is July 18th. Here is an essay",
"announcementtypename":"HW",
"announcementtypeid":2,
"expiresdate":"2013-07-19",
"isowner":false,
"gradable":false,
"starred":false,
"id":172009,
"order":61,
"state":1,
"statetyped":1,
"qnacount":0,
"attachmentscount":0,
"ownerattachmentscount":0,
"title":"English 9A",
}
}
モデル:
Ext.define('app.model.FeedModel', {
extend: 'Ext.data.Model',
config: {
sorters: 'title',
fields: [
{name: 'content', type: "string"},
{name: 'created', type: "string"},
{name: 'announcementtypename', type: "string"},
{name: 'announcementtypeid', type: "integer"},
{name: 'attachmentscount', type: "integer"},
{name: 'applicationscount', type: "integer"},
{name: 'ftype', type: "string"},
{name: 'title', type: "string"},
{name: 'expiresdate', type: "string"},
{name: 'starred', type: "boolean"}
]
}
});
店:
Ext.define('app.store.FeedStore',{
extend: 'Ext.data.Store',
config:{
storeId:'FeedStore',
model:'app.model.FeedModel',
filterRoot: 'title', // * --does nothing
filters: [
{
property: 'title' // * --does nothing
}
],
}
});
コントローラー: (助けが必要)
//the button name matches the "title" node in the json
filterFeedFunc: function(button){
var name = button.config.name;
var sto = Ext.getStore('FeedStore');
var all = "allname";
if (name == all){
sto.clearFilter(); // when they click "all" it should show all items - doesn't work
}
//sto.clearFilter(); // * --doesn't work
//sto.filter('title', name); // * --doesn't work
sto.filter({
property: 'title', // * --doesn't work, need something new here
value: name,
exactMatch: true
});
sto.load(); // no
},
更新・編集
景色:
Ext.define('app.view.feed.Feed', {
extend: 'Ext.dataview.List',
xtype: 'Feed',
alias: 'widget.feedlist',
config: {
cls: 'feedlist',
store : 'FeedStore',
model: 'FeedModel',
title:'',
emptyText:'no items',
style: 'background-color:#ffffff',
itemTpl: new Ext.XTemplate(
'<tpl for=".">'+
'<div class="feed-item-box">'+
'<tpl if="values.starred == true"> <img src="img/Important.png"> </tpl>'+
'<tpl if="!values.starred"> <img src="img/not-starred.png"> </tpl>'+
'<div class="anntype"><h1>{announcementtypename} </h1></div>' +
'<div class="classname"><h2>{title:ellipsis(30)} </h2></div>' +
'<div class="content"><h4>{content:ellipsis(50)} {summary}</h4></div>' +
'<tpl if="values.attachmentscount || values.applicationscount"><div class="attachment-clip"></div> </tpl>' +
'<div class="due"> ' +
'<h4>{[this.dueInfo(values.expiresdate)]} </h4>' +
'</div>' +
'</div>'+
'</tpl>',{
getUrl: function(){
var store = Ext.getStore('UrlStore');
var url = store.last();
return url.data.url;
},
dueInfo: function(date){
var origDate = moment(date).format("MMMM Do");
var today = moment().format("MMMM Do");
if (today.match(origDate)){
return "Today"
} else{
return origDate
}
}
}),
listeners:{
refresh: function(records) {
var me = this;
var classes = Ext.getStore('ClassListStore')._data.items;
me.setItems([{
cls : 'classbar',
docked : 'top',
xtype : 'dataview',
inline: {
wrap: false
},
scrollable: {
direction: 'horizontal',
directionLock: true
},
height : 101,
html : '<div class="select-all" style= "float: left"></div>',
itemTpl: ''.concat (
'<tpl for=".">',
'<div class="select-{id}"></div>',
'</tpl>'
),
store : Ext.getStore('ClassListStore'),
model : 'app.model.ClassListModel',
listeners:{
refresh: function(){
var bar = jQuery('.classbar');
function getUserRole(){
var store = Ext.getStore('UserStore');
store.load();
var userRole = store.last();
return userRole.data.roledescription;
}
if (getUserRole() != app.UserRoles.ADMIN){
for(var i = 0; i < classes.length; i++){
var data = classes[i].data;
var render = Ext.DomQuery.select('.classbar .select-' + data.id)[0];
var allbutren = Ext.DomQuery.select('.classbar .select-all')[0];
var button = new Ext.Button({
ui: 'chalk-light',
text: data.name,
renderTo: render,
name: data.name,
clazzId: data.id,
cls: 'class-button',
action: 'filterFeed',
html: '<img width="45" style="margin-top: -45px;" src="https://www.app.com/Course/GetIcon?courseInfoId=' + data.courseinfoid + '"/>' +
'<div class="classnamer">' + data.name + '</div>'
});
var allbutton = new Ext.Button({
ui: 'chalk-light',
text: 'All',
renderTo: allbutren,
name: 'allname',
clazzId: 'someId',
cls: 'class-button x-button-pressing',
action: 'filterFeed',
html: '<img width="45" style="margin-top: -45px;" src="https://www.app.com/Content/images/common/course-icons/all.png"/>' +
'<div class="classnamer">All</div>'
});
}
} else{
bar.hide();
}
}
}
}
,
{
cls : 'feedbar',
itemId : 'something',
docked : 'top',
xtype : 'panel',
items:[
{
xtype: 'panel',
html:'Feed',
cls: 'feedTitle'
},
{
xtype: 'button',
action: 'feedAll',
text: 'All',
cls: 'allBtn',
ui: 'chalk-light'
//see feedController.all()
},
{
xtype: 'button',
action: 'starred',
cls: 'impBtn',
ui: 'chalk-light',
html: '<img src="img/not-starred.png"> Important'
}
]
}]
);
}
}
}
});