Should Ext.Container methods add and remove actually add and remove?
Should Ext.Container methods add and remove actually add and remove?
Hi All,
I've come across an issue where adding a panel to a window and removing it doesn't actually update the DOM. IMHO the "add" and "remove" methods should do exactly what they suggest which is adding and removing a component from its container and also make the necessary changes to the DOM. The add method only adds a component to a container requiring a call to doLayout to actually update the DOM. The remove successfully removes a component from its container but doesn't update the DOM, leaving the components html markup behind. Even a call to doLayout doesn't remove the components markup.
I understand that doLayout is there so you can add multiple components and only calculate the layout once. However, the add method allows you to add an array of components providing a way of keeping the performance up. Surely the add method could automatically call doLayout when components are added?
Removing components is the biggest problem. Once a component has been rendered its markup is not removed until the component is destroyed. You can only show or hide the components markup. So, if you add a panel to a window, call doLayout, then remove the panel, the window still shows the panels markup. More code would have to be written to also hide a panel after removing it. This seems like redundant code to me and something I should not have to worry about. Coming from Objective-C / C++ / VB / .Net etc, the last thing I expected is to manually have to hide a panel after its been removed which took quite a while to figure out, especially as there is no mention on the "remove" method about also hiding a component in the docs.
Rendering a component means doing layout on the container it appears in. If you were to render a component inside the add() call, it would mean a fresh layout per added component. Adding ten components would mean ten layout actions. Since layout is the heaviest action you can do in the ext framework, this would be very slow.
The way to solve this is to buffer requests for layout until the current javascript thread completes (which involves setting a timeout). As I understand it (but I may be wrong), this is what extjs 4 does.
Thats great that Ext4 may fix the adding components issue. But the Removing components problem still exists. After removing a component from its container, the component still exists within the containers DOM, even after a doLayout.
to remove a child from the parent Container's items collection without removing the child's corresponding markup (default behaviour) -- this allows the child to be moved to a different parent.
pass true as the 2nd argument to Container#remove() if you want to destroy the child + remove its associated markup.
But what if I wanted to remove the child from its container without destroying it so I can add it to another container at some point?
The docs aren't particularly clear on this. They say that the remove method removes a child from its container and allows you to destroy it to clean up resources etc. This would suggest to me that once a child is removed, no trace of it exists in the container object regardless of weather or not you destroy the child.
It seems counter intuitive to remove something and then have to hide it because it has not actually been removed.
At the very least, the docs should be updated to say that removing a child doesn't update the DOM and child.hide() should be called to remove it from view.
2 ideas I've had that would make more sense to me.
1. Store the markup in the components js object
Could the markup be removed from the DOM and stored in a property of the removed component and then added back into the DOM when the component is added to a container? I'm not sure if there are performance implications with this method.
2. Move the markup to a hidden container
Could Ext not create a hidden container on startup that would serve as a scratch area for all removed components? When a component is removed it's markup would be moved to the scratch container and then moved back to the right place in the DOM when its added to a new container.