-
7 Jun 2012 1:15 AM #1
Answered: setActiveItem only works once
Answered: setActiveItem only works once
Hi,
For the last two days i´ve trying to get this to work.
Have tried with both NavigationView and plain Panels but without any luck!
First of all, i´ve not made up my mind if im going for a NavigationView or not so im all open for suggestions.
However, this is my problem.
When the application starts a menu is first shown, icons displayed side by side, when a icon is selected a new "flow" is started containing two or more views.
When the new flow is started it first checks if a order is already in store, if not a list of possible orders is shown.
This works the first time but not the second time the icon is selected.
Cant seem to find the solution to this and really need your help!
The code below is one of all the tests i´ve been trying...
Some code.
Menu view:
Order main view:Code:Ext.define('App.view.Main', { extend : 'Ext.tab.Panel', alias : 'widget.main', requires: [ 'Ext.TitleBar', 'Ext.data.Store', 'Ext.dataview.DataView' ], config: { tabBarPosition: 'bottom', items: [ { xtype : 'dataview', title : 'Menu', iconCls : 'home', items: [ { xtype : 'titlebar', title : 'Order Test', docked : 'top' } ], store : { fields : [ 'title', 'xtype', ], data : [ { title: 'Order', xtype: 'orderview' } ] }, itemTpl: '<div style="float:left;height:100px;width:100px;border:1px solid black;background:#fff;">{title}</div>' } ] } });
Order view:Code:Ext.define('App.view.order.View', { extend : 'Ext.Panel', alias : 'widget.orderview', requires: [ 'App.view.order.Main', 'App.view.order.List' ], config: { fullscreen: true, layout: { type: 'card', animation: { type: 'slide', direction: 'left', duration: 250 } }, items: [ { xtype: 'ordermain' }, { xtype: 'orderlist' } ] } });
Order list view:Code:Ext.define('App.view.order.Main', { extend : 'Ext.Panel', alias : 'widget.ordermain', config: { html: 'Main', items: [ { xtype : 'titlebar', title : 'Order', docked : 'top', items : [ { xtype : 'button', text : 'Back', ui : 'back', action : 'back' } ] } ] } });
App controller:Code:Ext.define('App.view.order.List', { extend : 'Ext.Panel', alias : 'widget.orderlist', config: { html: 'List', items: [ { xtype : 'titlebar', title : 'Orderlist', docked : 'top', items : [ { xtype : 'button', text : 'Back', ui : 'back', action : 'back' } ] } ] } });
Order controller:Code:Ext.define('App.controller.Application', { extend : 'Ext.app.Controller', requires: [ 'App.view.order.View' ], config: { refs: { tab : 'main', menu: 'main dataview' }, control: { menu: { itemtap: 'onMenuItemTap' } } }, onMenuItemTap: function (dataView, index, target, record) { var tab = this.getTab(), id = record.get('xtype'), view = Ext.ClassManager.isCreated(id) ? Ext.ClassManager.getByAlias(id) : Ext.widget(id); Ext.Viewport.animateActiveItem(view, { type: 'slide', direction: 'left' }); } });
Best regardsCode:Ext.define('App.controller.Order', { extend: 'Ext.app.Controller', requires: [ 'App.view.order.View', 'App.view.order.Main', 'App.view.order.List' ], config: { refs: { view : 'orderview', main : 'ordermain', list : 'orderlist' }, control: { view: { show : 'onShow' }, 'ordermain button[action=back]': { tap: 'onReturnToMenu' }, 'orderlist button[action=back]': { tap: 'onBack' } } }, onShow: function () { this.getView().setActiveItem(Ext.widget('orderlist')); }, onReturnToMenu: function (field) { Ext.Viewport.animateActiveItem(0, { type: 'slide', direction: 'right' }); }, onBack: function (field) { this.getView().setActiveItem(Ext.widget('ordermain')); } });
Robert
-
Best Answer Posted by rob.n
After some fiddling this is what i've come up with.
First of all i've decided to go with the Navigation View.
In the navigation view i added a listener to the push event, fired one event before and one after the standard event.
The controller registered the after event and loaded the order list view.Code:Ext.define('App.view.Main', { extend: 'Ext.navigation.View', alias: 'widget.main', requires: [ 'App.view.Menu' ], config: { autoDestroy: false, items: [ { xtype: 'menu' } ] }, push: function () { this.fireEvent('beforepush', this); this.callParent(arguments); this.fireEvent('afterpush', arguments, this); } });
Thanks for your help.Code:onAfterPush: function (item, view) { if (view.getActiveItem() == this.getOrdermain()) { if (!this.orderlist) this.orderlist = Ext.create('App.view.order.List'); if (this.isFirst) this.getMain().push(this.orderlist); } this.isFirst = false; }
-
7 Jun 2012 4:21 AM #2
It seems to me that you're trying to create a new component every time you want to show it. Why not use autoCreate in the ref and letting your view automatically be created when needed?
Code:Ext.define('App.controller.Order', { extend: 'Ext.app.Controller', requires: [ 'App.view.order.View', 'App.view.order.Main', 'App.view.order.List' ], config: { refs: { view : 'orderview', main : { xtype: 'ordermain', selector: 'ordermain', autoCreate: true }, list : { xtype: 'orderlist', selector: 'orderlist', autoCreate: true } }, control: { view: { show : 'onShow' }, 'ordermain button[action=back]': { tap: 'onReturnToMenu' }, 'orderlist button[action=back]': { tap: 'onBack' } } }, onShow: function () { this.getView().setActiveItem(this.getList()); }, onReturnToMenu: function (field) { Ext.Viewport.animateActiveItem(0, { type: 'slide', direction: 'right' }); }, onBack: function (field) { this.getView().setActiveItem(this.getMain()); }
-
7 Jun 2012 11:45 AM #3
Thanks for your reply aatiis but i can´t get it to work, same result.
The show event in order main does not load my order list.
Could there be another way to accomplish what I’m after?Code:this.getView().setActiveItem(this.getList());
-
7 Jun 2012 1:49 PM #4
Is your onShow callback even called the next time you show that view? Because if you're just swapping active items in the viewport, it may be that the show event is not even fired the next time.
Try putting a breakpoint in onShow or adding some log statements.
Try listening to the "activate" event instead of "show".
-
8 Jun 2012 1:38 AM #5
After some fiddling this is what i've come up with.
First of all i've decided to go with the Navigation View.
In the navigation view i added a listener to the push event, fired one event before and one after the standard event.
The controller registered the after event and loaded the order list view.Code:Ext.define('App.view.Main', { extend: 'Ext.navigation.View', alias: 'widget.main', requires: [ 'App.view.Menu' ], config: { autoDestroy: false, items: [ { xtype: 'menu' } ] }, push: function () { this.fireEvent('beforepush', this); this.callParent(arguments); this.fireEvent('afterpush', arguments, this); } });
Thanks for your help.Code:onAfterPush: function (item, view) { if (view.getActiveItem() == this.getOrdermain()) { if (!this.orderlist) this.orderlist = Ext.create('App.view.order.List'); if (this.isFirst) this.getMain().push(this.orderlist); } this.isFirst = false; }


Reply With Quote
