PDA

View Full Version : [CLOSED-472] One Time Buttons



NeoVanGoth
28 Oct 2010, 6:13 AM
Sencha Touch version tested:

0.98

only default ext-all.css
custom css (apple.css)




Platform tested against:

iOS 3.x
iOS 4
Chrome 8 (Windows 7)
Chrome 7 (OSX 10.6)


Description:

Listeners do not work after removing and readding a component with reusing it's id.


Steps to reproduce the problem:

Add a button with a handler (doing an alert or something) to a panel. Give the button a manual id.
Remove the button from the panel.
Add another button with the same id as the first to the panel.


The result that was expected:

Second button works ;)


The result that occurs instead:

The second buttons handler will not be executed on click / tip.



It seems, that this bug occurs with every listener on every component with reused id. Even when attaching listeners to elements (like a swipe listener via Ext.getCmp(...).getEl ()), they work only for the first element with this id.


Workaround:

Call .purgeListeners() before removing / destroying the component. (This is NOT nice when removing a panel containing lots of dynamically created components with listeners)



[Edit: Tested in Chrome 7 / OSX)

NeoVanGoth
28 Oct 2010, 7:16 AM
Better Workaround:

Use Ext.override to call purgeListeners() on the beforedestroy event.




Ext.override(Ext.Component, {
listeners: {
beforedestroy: function(cmp) {
cmp.purgeListeners();
}
}
});

BrendanC
28 Oct 2010, 1:23 PM
Thanks for the bug report.

NeoVanGoth
29 Oct 2010, 3:06 AM
Workaround doesn't work for listeners on Ext.Element. :(

In my case:

Add a panel to a card layout, change to new panel
Add a swipe listener to the panels element
On swipe, go back to previous card and remove/destroy panel
[Tried workaround: beforedestroy do cmp.getEl().removeAllListeners() - doesn't change anything)
Add another panel with the same id to the card layout, change to new panel
Add swipe listener to the new panels element
Swipe event will not be fired

Steffen Hiller
29 Oct 2010, 11:53 AM
In general I find it problematic using manual ids for components that are destroyed and recreated. I think the Sencha team is also recommending caution regarding using manual ids.

If you need to access a cmp from somewhere else, try to assign it as a property to the owner container or to some global name within your apps namespace, such as App.saveButton and remove the id.

evant
8 Nov 2010, 12:18 PM
I believe the bug has been resolved due to another ticket, I was unable to reproduce the issue using the following test case, which uses the method describe above:



Ext.setup({
onReady: function(){
var p = new Ext.Panel({
fullscreen: true,
items: [{
xtype: 'button',
text: 'foo',
id: 'btn',
handler: function(){
console.log('fyah1');
}
}]
});
setTimeout(function(){
p.removeAll();
p.add({
xtype: 'button',
text: 'bar',
id: 'btn',
handler: function(){
console.log('fyah2');
}
});
p.doLayout();
}, 1000);
}
});

evant
8 Nov 2010, 12:25 PM
Similarly, with Element:



Ext.setup({
onReady: function(){
var el = Ext.getBody().createChild({
id: 'foo',
tag: 'button',
html: 'b1'
});
el.on('click', function(){
console.log('fire1');
setTimeout(function(){
Ext.destroy(el);
el = Ext.getBody().createChild({
id: 'foo',
tag: 'button',
html: 'b2'
});
el.on('click', function(){
console.log('fire2');
});
}, 1000);
});

}
});