PDA

View Full Version : GXT3.0 - Reuse of UI widgets



raivis
15 Dec 2011, 6:16 AM
Hello, all!

There are some methods in widgets that can be used only pre-render. If you remove widget from one container and attach it to another, there is a possibility to get assertion error about calling pre-render method, because widget has been rendered when attached for the first time.
So, my question is - how is it supposed to use the same widget in another container?

WesleyMoy
15 Dec 2011, 7:41 AM
In Ext GWT 2, certain methods could only be called on a component pre-render. In Ext GWT 3, we no longer lazily construct components. In effect, a component "renders" as soon as you create it. You should have no problem removing a component from one container and adding it to another. As always, because of the GWT's widget system, you will not be able to add a widget to multiple containers at the same time.

Which methods on which components are you noticing this issue on?

raivis
15 Dec 2011, 10:10 PM
e.g. - Moving Accordeon's one of the content panels to another Accordeon. Here is an example:



import com.google.gwt.core.client.EntryPoint;
import com.google.gwt.event.dom.client.ClickEvent;
import com.google.gwt.event.dom.client.ClickHandler;
import com.google.gwt.user.client.ui.RootLayoutPanel;
import com.sencha.gxt.widget.core.client.ContentPanel;
import com.sencha.gxt.widget.core.client.button.TextButton;
import com.sencha.gxt.widget.core.client.container.AccordionLayoutContainer;
import com.sencha.gxt.widget.core.client.container.VerticalLayoutContainer;
import com.sencha.gxt.widget.core.client.container.VerticalLayoutContainer.VerticalLayoutData;
import com.sencha.gxt.widget.core.client.container.Viewport;


public class GxtModule implements EntryPoint {


boolean isAtFirst = true;


public void onModuleLoad() {
final Viewport vp = new Viewport();
final VerticalLayoutContainer vlc = new VerticalLayoutContainer();


final AccordionLayoutContainer acc1 = new AccordionLayoutContainer();
final ContentPanel cp1 = new ContentPanel();
cp1.setHeadingText("First");
acc1.add(cp1);


final ContentPanel cpMovable = new ContentPanel();
cpMovable.setHeadingText("Movable");
acc1.add(cpMovable);


final AccordionLayoutContainer acc2 = new AccordionLayoutContainer();
final ContentPanel cp2 = new ContentPanel();
cp2.setHeadingText("Second");
acc2.add(cp2);


final TextButton b = new TextButton("Swap");
b.addDomHandler(new ClickHandler() {


public void onClick(ClickEvent p_event) {
if (isAtFirst) {
acc1.remove(cpMovable);
acc2.add(cpMovable);
isAtFirst = false;
} else {
acc2.remove(cpMovable);
acc1.add(cpMovable);
isAtFirst = true;
}


}
}, ClickEvent.getType());


vlc.add(acc1, new VerticalLayoutData(1, 0.4));
vlc.add(acc2, new VerticalLayoutData(1, 0.4));
vlc.add(b, new VerticalLayoutData(1, 0.2));


vp.add(vlc);


RootLayoutPanel.get().add(vp);


}
}

Try to run it in hosted debug mode, and click swap button. It tries to remove content panel named "Movable" from first accordeon and attach it to second accordeon. You will notice an exception leading to AccordeonLayoutContainer's method "protected void onInsert(int index, Widget child)". Problem raises because this method calls setCollapsible(true) for content panel, but that method has pre-render assertion check.