To support UiBinder in GWT Designer we need to have several changes
in UiBinder generators, writer and parsers.
  I will describe below these changes as they are done now.
  In real patch I will group as much implementation details as
possible into single class like DesignTimeUtils or GWTDesignerSupport.
It will check for GWT Designer presence and do something only in this
case.

  So, main question is following. Will GWT team accept patch with such
changes?
  This would allow us avoid creating internal patches for 2.0 and each
future version of GWT.


1. Declare in binder implementation interface and field with it.
Something like this:
       public static interface WBPObjectHandler {void handle(String
path, Object object);}
       public WBPObjectHandler wbpObjectHandler;
    In method createAndBindUi() directly after creating each Widget
instance (but before applying setX() methods) "wbpObjectHandler" is
used to notify GWT Designer about new widget and its path in XML. GWT
Designer bind Widget instance to model (using path) and also asks
default values for all properties using getX() methods.

  Path in XML is "/" separated string of indexes.
  For example in
<ui:UiBinder>
        <ui:style/>
        <g:FlowPanel styleName="{style.panel}">
                <g:Button text="New Button"/>
        </g:FlowPanel>
</ui:UiBinder>

  "0/1" is FlowPanel
  "0/1/0" is Button

2. Declare in binder implementation Map with values of attributes.
       public final java.util.Map wbpAttributes = new
java.util.HashMap();
  and fill it, here is example if code generated for ui.xml above

    if (wbpObjectHandler != null) wbpObjectHandler.handle("0/1/0",
f_Button2);
    f_Button2.setText("New Button");
    wbpAttributes.put("0/1/0 text", "New Button");
    f_FlowPanel1.add(f_Button2);
    if (wbpObjectHandler != null) wbpObjectHandler.handle("0/1",
f_FlowPanel1);
    f_FlowPanel1.setStyleName("" + style.panel() + "");

  GWT Designer needs to know attribute values to show them to user in
properties table. Not all properties have getter, so we can not get
these values for existing Widget object.


3. In special parsers for panels, remember also values of attributes
for artificial elements. For example "Cell" in CellPanelParser (and
"Dock" in DockPanel).

    // Parse horizontal and vertical alignment attributes.
    if (cellElem.hasAttribute(HALIGN_ATTR)) {
      String value = cellElem.consumeAttribute(HALIGN_ATTR,
hAlignConstantType);
      writer.addStatement("%1$s.setCellHorizontalAlignment(%2$s,
%3$s);",
          fieldName, childFieldName, value);
      //XXX <Instantiations
      writer.addStatement("wbpAttributes.put(\"%s\", %s);",
widgetElem.getPath() + " Cell." + HALIGN_ATTR, value);
      //XXX >Instantiations
    }



4. To allow quick updates of design canvas as user changes properties,
without reloading GWT context each time, we should:
4.1. Generate Binder implementation class with new name each time, so
be able to define each time new class in same ClassLoader. Right now
we just add current time to the name of class.
    //XXX <Instantiations
    // generate class with new name each time, to allow refresh in
same ClassLoader
    implName += "_wbp" + System.currentTimeMillis();
    //XXX >Instantiations
4.2. To parse/render UI.XML file content without saving, i.e. from
memory/editor, generate should try to read document from memory.
Something like this:
  private Document getW3cDoc(MortalLogger logger, String templatePath)
      throws UnableToCompleteException {
    //XXX <Instantiations
    {
      String content = System.getProperty("wbp.gwt.UiBinder " +
templatePath);
      if (content != null) {
        Document doc = null;
        try {
          doc = new
W3cDomHelper(logger.getTreeLogger()).documentFor(content);
        } catch (SAXParseException e) {
          logger.die("Error parsing XML (line " + e.getLineNumber() +
"): "
              + e.getMessage() + " " + content, e);
        } catch (Throwable e) {
          logger.die("Error parsing XML  " + content, e);
        }
        return doc;
      }
    }
    //XXX >Instantiations

    URL url =
UiBinderGenerator.class.getClassLoader().getResource(templatePath); //
this is default implementation

-- 
http://groups.google.com/group/Google-Web-Toolkit-Contributors

Reply via email to