Eric Clayberg: Welcome to
the second day of Google IO.
I hope everybody is
enjoying their new toys
and future new toys.
That was quite
an announcement at the keynote.
This is "GWT and UI Designer
Enterprise Web UIs Made Easy".
I'm Eric Clayberg.
The hashtags for
this session: #io2011 #DevTools,
and there's
the link for feedback.
If you'd like
to leave some of it,
we'd love to have feedback.
The agenda for this session:
I'm going to go through
a quick introduction,
go through some of the
basics of the UI Designer tool,
do a quick, basic demonstration
of some of those features,
then go on to some of
the more advanced features.
Do a second demo at the end
of the session,
then we'll wrap up,
open it up for Q&A,
and let you go about
your business.
So who am I, and what
is the UI Designer?
A little background.
Again, I'm Eric Clayberg.
I'm a software
engineering manager
with the Developer Tools Group
at Google.
Formerly I was with
Instantiations,
a Java Eclipse toolmaker
acquired by Google in 2010.
How many of you
were familiar with
Instantiations
in the past?
Oh, great. Thanks.
I'm also a co-author with
Dan Rubel of the book
Eclipse Plug-Ins.
Anybody read my book?
Well, thank you for that.
You can reach me at
clayberg@google.com.
GWT Designer was a tool
originally created
by Instantiations in 2006.
It was acquired by
Google in 2010,
and September of last year,
we made it free to everybody
who wanted to use it,
which was pretty cool.
It was also
fully integrated
with the Google plug-in
for Eclipse,
or the GPE version 2.2,
as the built-in UI designer.
It comes in two versions.
There's the embedded
version in the GPE.
There's also still a full
version that provides
access to various third
party components like GXT,
SmartGWT, and a few other
things that I'll mention.
And the whole thing is
built on the new
WindowBuilder open-source
project at eclipse.org
that Google contributed
back in December
and is going to go out as part
of Eclipse 3.7 in June.
So the basics of the UI
design--before I go on--
How many people have
actually played with the tool?
It's called GWT Designer
in the past.
Now it's just the UI Designer
and the GPE.
All right, great.
Well, hopefully I'll be
able to teach you a few tricks
that you might
not have run across yet.
For those of you
who aren't familiar with it,
we'll talk about
some of the basics.
So the user interface of
the tool
is composed of the following
major components.
There's the Source View, where
you see all your Java source,
or if you were using UI Binder,
you'd see the XML source.
Switch to Design tab.
You see the design surface,
which has a bunch of
subcomponents to it.
In the upper left hand corner
you have the Component Tree,
where you see a hierarchical
view of all the components.
You have a Property Pane where
you can edit the properties.
There's a Palette.
There are a large number
of Wizards you can access
to create different
UI components,
and then there are
various Toolbar
and Context Menu options.
And I'll touch on each of these
in a little bit more detail.
Source View--again, there
are separate tabs
for the source
and the design view.
You can switch back and forth
between those very easily.
If you are someone who
likes to see the design view
and the source view
simultaneously,
you can also put it into a mode
where you can see both of them
in a top/bottom or left/right
configuration like this.
The design view--
basically,
each different type of layout
or GWT panel type
has its own unique UI model
and basic and different
visual feedback.
You can move and resize
components visually.
If you hit the space bar,
you can put it
into direct edit mode
to change text labels,
check boxes,
buttons, things
of that nature.
Depending on the layout manager,
things like layout panels.
You can also right click
to set attachments
using pop-up context menus.
Component tree, again,
is a hierarchal view
of all the components.
It shows the variable name
of the component,
the text of the component.
You can right click to
cut, copy, and paste.
Use drag/drop to reorder
and nest components.
And that component tree
can be docked on any side
of the editor or
even pulled off
as a stand-alone view
if you prefer.
The Properties View shows
all of the standard common
properties by default.
If you want, you can also reveal
various advanced properties
by clicking the little icon
in the corner.
Those are properties you
typically don't need to access,
but you might,
and if you need to,
you can get to them.
All of the most
important properties
are highlighted in bold
so you can
see them quickly.
There are commands to
automatically convert a widget
from a local variable
to a field.
By default, the tool will create
components as local variables,
which is nice
for things like labels or things
that you don't need
to communicate with,
but for things like checkboxes
or text fields
where you might want
to programmatically
interact with them,
you can convert them with
a single click into fields
in the application.
You can also directly access
and jump right to
the source code
for a particular widget
you're dealing with.
You can also switch over
to the configured events
for any component
very easily.
You can also,
if you right click,
you can tell the system what you
consider to be the preferred
or advance properties yourself,
so you could actually fine-tune
the tool then.
The Palette has some
commands for doing system
or marquee level select.
You can choose any
components,
whether they're on
the palette or not,
using the choose
component command,
so that's nice if you've created
your own custom components,
or if you have some
third party components
that aren't on the palette yet,
you can easily access them.
In the full version,
there are special palettes
for GXT and SmartGWT,
and you can add your
own palettes and categories
very easily.
Just like the Property
Pane and Component Tree,
you can dock the Palette
to any side of the editor
or pull it off to
a separate stand-alone view.
And the palette is also
fully customizable by the user,
so if you right
click on it,
you can get this
customization dialogue,
where you can rearrange the
categories, add/remove widgets,
export the palette
to a XML file
to share with
other developer members.
If you actually store
the palette in the project,
then that project will
automatically adapt
to that palette.
So if you've got a project,
you're working with a team
and you want to configure
the palette for the entire team,
you can do that very easily.
Just store the palette
file in the project.
Everybody on the team will
then use that same palette.
The full version has a very
large number of UI wizards
which you can
access using the File,
New, Other, WindowBuilder,
GWT Designer Link.
There's also a drop-down
toolbar menu
on the main Eclipse toolbar
that you can access
that shows those various
categories.
And there are dozens of
templates for creating
GWT Java, UI Binder, MVP, GXT,
and SmartGWT components.
And finally, a large
number of context menu commands,
toolbar options, things like
cut, copy, paste,
alignment and distribution,
deleting components,
ordering and
selecting components,
renaming components--
if you want to rename multiple
instance variables
at the same time,
you can do that--
Add event handlers,
and access morphing
of factory tools.
This is just a quick
comparison of
the sort of the two main flavors
of the UI Designer,
the embedded version versus
the fuller version.
Again, both versions support
all the standard GWT widgets
and panel types.
Both support both Java
and UI Binder-based UIs.
The full version adds
support for additional
third party widgets
like GXT and SmartGWT.
There are also a much
larger number of
built-in wizards accessible.
The full version also has a lot
more customization options,
but the basic
version has sort of
the primary ones
that you need.
And the most important
thing is both versions
are completely free,
thanks to Google.
So now I'm going to jump
into a quick demo
of some of the basic
features.
So here I have a standard
entry point--
very simple Java class.
It shows up as an empty box
in this case.
The root panel by default is
in a sort of absolute layout,
so if I were to
drop various widgets,
notice you get
various drop feedback.
There are margin
alignments you can select.
If I drop it in the corner,
that widget will go there.
Automatically goes
into direct edit mode.
Give it a name, and notice
it automatically selected
the variable name based
on the text I entered.
If I add a second widget, notice
you get automatic alignment,
drop zones if you want.
I can also drop and resize
a widget at the same time.
And there are handy
commands in the toolbar
for doing things like
left-right-center alignment,
making the widgets
all the same size,
distributing them
horizontally,
vertically, centering them,
all kinds of things like that
for absolute layouts.
Some of the, uh--
I mentioned that the palette
and this structure view
composed of component
and property view are--
you can move them around,
so if I want to,
I can just drag the palette
to the other side of the screen,
if you like
that particular layout.
And again if I right click,
I can bring up
the palette manager
and rearrange the categories,
remove categories
that I'm not using,
remove widgets
that I'm not using,
add widgets that I might have
that I've created custom,
and then easily export that
and share that
with other team members.
Other types of layouts,
since I mentioned
they all have
different feedbacks.
A standard flow panel.
I'll just drop one of
these in here.
And if I drop some widgets
on that,
you see that they just
basically drop in
in a left-right manner.
And I can drop widgets
in between other widgets
and they flow perfectly
according to
that particular layout.
I'll show you a, uh,
I'll show you a grid
and a flex table.
The grid is basically
rows and columns,
so the first widget I drop in
goes into
the only available cell.
And I can basically add
new rows and columns
by dropping on any of the sides
of the existing layout here.
So I automatically add
a new column and add a new row,
and you can do things
like tell it to--a widget
to fill a particular cell
if you want to--oops.
Very simple.
Now the grid widget,
the grid panel,
is quite simple.
Contrast that with
the flex table,
which, as its name suggests,
is a bit more flexible.
Once I drop a few widgets
in here,
I can do a couple additional
things.
Let me get a couple in here.
Tell this to fill.
But then I can do things
like have it span multiple
rows and columns.
So by dragging this little
green handle over,
I can have that widget expand to
fill an entire row
or an entire column
very easily.
Again, if I want
to direct edit,
I can just hit the space bar
and put the widget into direct
edit to change its labels.
Over here on the property view,
you can see all the various
properties
for the component in context.
Some of these properties
are expandable
to show you various
sub-properties,
such as various
alignment options,
things like that.
You also set things like
CSS dials and so on.
I'll show that actually
in the more advanced demo.
All right, I'm going to
switch back to the slides here.
So let's talk about some
of the more advanced
features of the tool,
where it starts to get
really interesting.
So the tool has quite a
few pretty interesting features.
Many of them are actually
quite unique
for a Java-based UI designer.
First, obviously, almost
any GUI builder
needs to have
a WYSIWYG layout.
But one of the nice things
we have
is a truly bi-directional
code generation.
So as we start editing
in the design view,
if I show you
the source view,
as I add widgets,
you'll see those automatically
added to the source view,
and that second widget,
and a third widget.
And then if I go
into the source view,
and make a change
in the source view,
that change is immediately
reflected in the design view.
So you could actually work
comfortably in either place,
and the two will
automatically parse
back and forth in
either direction.
One of the nice features
of this is something
we call micro-editing.
So if you were to go into
the design view,
change the label on a component,
it makes the smallest possible
change to the source code
that it can.
So in this case it will update
just that one string.
Now the nice thing
about that is,
if you've actually
formatted your code,
or re-factored your code,
or moved things around,
it doesn't rewrite
the entire class.
It literally, it actually
has an AST model of
the entire UI class.
It knows exactly
where that string is.
It changes
just that string for you.
I think it's one of the only
UI tools in the world
that actually
works that way.
I mentioned the parser.
It has a very powerful
and flexible code parser.
Not only can it parse
its own code,
it can generally parse most
handwritten code quite well,
typically in the 80-90% range.
We're quite
successful with that.
There are no protected
code blocks,
so there's nothing that says,
"Your code must go here."
You can basically put your own
modifications anywhere you like.
Since it creates a structure
of the entire UI class,
it knows exactly
where the UI code is.
It can differentiate
that from model code
or any other code that you might
have written by hand.
It has a very nice
understanding of data flow.
So if you were to re-factor
an existing layout,
maybe rather than having all
these widgets defined
in one method,
you could actually use
extract method,
pull a few of them
out into a second method,
and it'll be
perfectly happy.
It'll continue to update
the widgets,
whatever method they're in,
and so on.
It ignores and
preserves non-UI codes.
So again, if you've added
your own code,
in line or anywhere
in the class,
it'll ignore it, preserve it.
The formatting
remains unchanged.
Again, since it's making
micro-edits.
There's never a point where
it regenerates the entire class
and messes up
the formatting
or does anything like that.
Again,
very re-factoring friendly,
resilient
to hand-made changes.
And one key aspect
is that there
is a true one-to-one
relationship
between what
you see in the UI design
and what's in the Java
or XML code for UI Binder.
There's no secondary
metadata file
that are often used
in other UI tools
that can get out of sync.
So, the tool basically
parses the Java code,
and everything about
the design is derived from that.
There's nothing else
that you need to worry about.
The tool can read or write
almost any style,
so if you have a particular
style of Java coding
that you like, you can
actually adapt the output
to almost anything you like.
So for example, when
generating new widgets,
you can have them
generated
as local variables
or as fields.
If you want them all as fields,
you can do that.
You can have them all
generated as local variables
and then selectively
decide which ones you want
to make fields later on.
It also supports sort of
a flat layout versus
sort of a nested block layout.
So if you have
a hierarchal components,
you could actually see those
in nested blocks,
which some people like.
Also, you can do
pre-initialized fields.
Rather than having
the widgets initialized in line,
they're actually initialized
where they were created.
And finally, for anybody coming
from the far distant
VA Java world,
you might remember
the lazy declaration style
from VA Java,
where you have each widget
defining its own method.
We support that kind
of generation as well.
Tool supports very nice
internationalization.
So initially if you're
just dropping widgets
on the canvas,
you're going to have
a bunch of hard-coded strings
for each of those widgets--
not something you want to have
if you have an internationalized
app obviously.
You want to pull those strings
out into resource bundles.
So we start by clicking on
the little world icon up here
in the toolbar,
and that opens up the
externalized strings dialog,
and identifies
all of the strings
in that parallel application
here.
There are basically
two widgets with strings.
And we need a place to
actually extract that to,
so we need to actually
create a string source.
In this case we want to
generate an app constance class
that's going to
hold those definitions
for those extracted strings.
So let's give an example
of the code
it's going to generate.
So, I'll go ahead
and do that.
Select all of the widgets
and tell it to externalize them,
and then what it
does is automatically
creates keys
and values for you.
Now at this point, we just
have a single default locale.
If we want to deal
with multiple locales,
different languages, we just
click on the new locale button.
That brings up a list of
known locales,
or you can create your own
combination of
language and country code.
I'll pick French here,
and it generates a new locale.
I've already provided
the translations,
or at least what Google told me
the translations were.
I apologize to anybody
who actually speaks French.
And then the tool
goes and generates
the appropriate resource
property files.
So we have a default locale
with English translations,
and our French locale
with the French translations.
And now you notice
that up in the toolbar,
that the drop-down list now
actually shows us the locales
that we have in play here.
So if I select the first locale,
you see that the strings all
update to show the French text.
If I switch back to
the default locale,
it switches back to
the default text.
The nice thing is, I could
actually continue to work.
If I were to make changes
to these widgets
and change their text,
rather than updating the text
in the actual source
of the class,
it'll actually update
the appropriate property file.
So if I'm in the default locale,
it'll update the default
properties file.
If I'm in the French mode,
it'll update
the French property file.
And I can also go down here,
change the property files,
and then see
the results reflected back
in the UI if I want.
Tool also has very nice
support for visual inheritance,
both through hierarchies--
so visual hierarchies,
like a base class with
a couple of ace widgets,
and various
derived subclasses,
or containment hierarchies.
So if you want to create
a custom composite,
expose some components,
and then show that.
I'll actually do
a demonstration of this
a little bit later.
So visual inheritance,
let's start with a real
simple example here
with a couple of widgets.
One of the things I can do is
I can expose various properties.
So if I wanted to actually
make this reusable,
you know, and invent
a subclass,
or maybe if it was
a composite,
I'd want to expose things
like the text on this label
so I could actually change it
somewhere else.
So I could right click.
If I right click on
that text property,
and select the expose
property command,
it offers to create
a new property,
new public property
with accessors,
and it goes ahead and generates
the appropriate--
I don't know if you can see
that at this resolution--
but it generated basically
an accessor pair
for that particular
label property,
or the text property of
that particular label.
And then I can also,
if I want to,
expose an entire widget--
for example,
maybe this button here,
if I want to change
its label--
maybe I want to be able to add
an event handler to it.
I want to be able to
basically access it
publicly from
somewhere else,
so I can right click
on the widget,
select expose widget.
It offers to create
an accessor,
and then generates
an accessor for it.
Now once you've done that,
now I've got a subclass.
Now the subclass
automatically shows
the widgets inherited
from the parent,
although I can't actually
click on any of them
except for the button.
And now I can basically
add additional widgets
to the subclass,
and also change the public
properties
of the inherited components.
So for example, I added
this last name field.
Well, maybe I want to change
that label up here
to first name,
so I can just change
that label text,
and it basically
reflects that properly.
So this label text
property was basically
the one we created
in the earlier step,
and it was automatically picked
up by reflection.
And you can see the source
code was generated using
that new property.
Likewise, I can change
properties of
the inherited fields.
If I want to, I could
direct edit the button,
change its label,
and it goes ahead
and uses the accessor
for the button and then changes
the appropriate property.
But I could add an event handler
or pretty much do anything
to the widget that I wanted
to at this point.
Now, UI Factories.
Another useful way to be
able to reuse components--
you can create your own.
Obviously you can create
custom widgets,
create composites of widgets.
But if you just have cases where
you want to have, you know,
a variety of say,
customized buttons,
maybe a search button,
or almost any kind of widget
where you're going to be using
the same widget
definition,
the same properties over
and over again,
you can basically right click
on the widget,
select the factory,
Create Factory command,
and that pops up a wizard
where you can tell it
the factory class
you want to create,
the name of the method
you want to create,
and it shows the various
properties of the widget.
In this case for our
little search button,
we want to create a new static
method on this factory class
that creates the button
and returns it.
But you can imagine, this could
be arbitrarily complex
with other properties,
and then this actual
factory element
can actually be added
to the palette
as a first class element.
So if I wanted to add a whole
bunch of search buttons
to a layout, or use them
over and over again,
I could do
that very easily.
And here's another example
where they take this label here.
Maybe I'd made it
right justified
and done a whole bunch of
other things to it.
I can extract various
properties,
maybe have it
pass in the string
while hard-coding
other properties.
So you could make these
fully parameterized,
and then hard code various
properties inside the factory.
Tool also has a morphing
capability,
which basically lets you change
any widget type
into another widget type.
So for example, if I had
started out with a button,
I could right click morph.
It shows a bunch of
similar types,
as well as I could
access subclasses
or any arbitrary widget I want,
and it actually will,
in the UI,
change that widget from
one type to another,
maps over all the properties
and updates
all the source code for you.
So for example,
I can change button types,
or a real common case here
would be if you started out
with a list box
and you discovered later on
in your UI
that you didn't have enough room
for a full list box
and you wanted to convert it
into a drop down list,
you could basically do that
and it preserves
all the widget properties
that you set up at that point--
event handlers,
anything like that
that makes sense.
And again of course,
it wouldn't be useful if it
didn't provide full support
for all the various built in
widget types
and all the various
panel types in GWT.
And it does that, so, there's
like absolute panel,
flow panel, doc panel, grid,
flex table, layout panel,
and pretty much everything
in between.
And the last slide
before I go into the more
advanced demo
also supports
graphical menu editing.
So if you want to put
menus in your application,
you can start by dropping
in a menu bar,
and then you can drop a cascade
submenu in there,
start adding items to it.
I could add cascading
submenus out to other levels,
add submenus to that.
Add separators.
I can use drag/drop to
rearrange those menu items.
And again, I can also use
direct edit to edit
any of those menu items.
So, very easy to create
menu bars and menus.
So the next few minutes
I'm going to switch back into
the live demo here
and show some of the more
advance features.
So just to start off with some
of the bi-directional editing
I showed you earlier.
If I drop a button on
the screen, give it some text,
switch back over to
the source,
change the label,
instantaneously reflect it
back in the design view.
So again, you can work
in either direction.
If I were to put this
into the mode
where you actually saw the
source and design view
simultaneously, you could
actually be typing
in the source view
and then you can set it
to how fast,
how often it synchronizes,
and then watch it update
the design view.
So a very nice way to--even if
you prefer to work in source,
it's a really nice way to see
a live preview
of what the UI's going to
look like
without having to go through
actually launching
the application,
going through dev mode,
all of that.
It's basically sort of
instantaneous feedback for you.
Let's--Let me add a couple
more widgets here.
Go into the source.
And you see that it is
basically generating
a nicely formatted source.
Let's take this
button here.
I mentioned, I can do
re-factoring,
so I'll right click and say
re-factor, extract method.
Call it
"create my button".
And now it's extracted that
component into its own method,
and the design view is
still working just fine.
In fact, if I were to change
the label on this button,
it's reflected properly
in the design view.
If I move it around,
change it here,
it updates
at the appropriate place.
So again, it basically has
an ST model of the entire class.
It knows where every
widget is defined,
where every property is defined,
so it really doesn't matter
how you re-factor
the generating codes.
That's a very unique
feature of this tool,
and it actually makes it
really easy
if you're doing things
like visual inheritance.
If you break out certain
widgets into methods,
you can then just override
just certain methods,
to add or change various
widgets,
and do some very, very powerful
visual inheritance.
Let me show you what you
can do with custom composites.
This is really fun
when you want to
start doing, um, custom--
you know, creating your own
custom widgets.
So let's start with
an empty composite.
I've got a basically empty
horizontal panel here.
I'm going to
drop in a label.
I'm going to drop in
a text box.
And I'm going to drop in
a button.
I don't like the variable
name of this,
so I can change the variable
name if I want to,
likewise with the button.
You just basically derive
it based on the text.
One thing I noticed is,
I don't really like this layout.
So this is a horizontal panel,
if I look at the generated
source code.
Let's morph that into
a flow panel.
So right click Morph,
and changes it
into a flow panel.
Updates the source formatting.
Now I've got these
three widgets.
Let's save that, go back over to
our empty entry point here,
drop that custom component
on the screen.
Come on.
So there are our widgets.
Now let's go back to
the custom component here.
And if I were to say,
add another button
or anything like that,
I switch back
over to the entry point.
It automatically detects
that class change,
so it basically has to
reload the class loader,
pull in that new widget
definition, and show it to me.
Now this new component
isn't very useful
if I don't actually expose
any of these properties,
so if I come back over to
the label, right click on it,
select expose property.
Again you can see the accessors
it wants to generate,
and it went ahead and generated
those accessors for me.
Save it, come back to
my entry point,
reload that class.
And now you notice
that this composite now
has a new property,
automatically picked up
by reflection,
and it actually uses that
new property appropriately.
Likewise, if I go over
and take one of these buttons,
I can right click on it,
expose widget.
Come back over to
my design view here.
And now you'll notice
that that widget
actually shows up as a child,
since it's actually now
a publicly visible component,
and I can do anything
I want to it.
I can change its label.
I could right click on it
and add event handlers,
and so on.
Let me show you what we can
do with built-in CSS support.
So let's drop
a couple more.
So the CSS style names,
any CSS styles that
are defined in the CSS
for this project will show up,
and I can just select them
if I want to and apply them.
Or if I want, I can go
ahead and create a new CSS style
for that button.
Edit it.
There's a built-in CSS editor,
so I can do things like pick the
size of the widgets,
the style of the widget,
maybe the color.
I'll make it a big
blue button here.
I can set the background,
set margins if I want to,
put borders, pretty much
any of the CSS styles.
And now let's actually set
this widget to use that style,
and then any time I go and
actually change CSS styles--
so if I actually
go back into my project,
find the CSS--
oh, wrong project.
Hold on.
If I actually come in and
change the CSS by hand,
maybe I'll change
this to red.
See, it automatically gets
picked up by the design surface.
Now maybe if I wanted to
create a factory.
Maybe I like
this style of button
and I want to use it
over and over again.
If I look at the widget
definition for the button,
let's say I want to make
it a search button,
so let's change
the text to search.
Let's change the style--
well, let's make it
a send button, actually,
because I've got
a style for that already.
And then right click on it,
select Factory,
Create Factory.
Create a new factory
called My Factory.
And I don't want to
hard code the size,
so let's go ahead
and take that out.
Tell it create
send button method,
and actually in the process,
it's actually going to
rewrite that code
to now call my factory
creation method,
and I went ahead and created
a factory class,
with that new static method
in there.
I go back to
my entry point now.
I could actually at this point
add this right to my palette.
So add--let's find
my factory class,
my factory,
find that one method.
And it's added
that to the palette.
I could drag/drop this element
and put it anywhere I want.
Let's put it back up with
the rest of the buttons.
And now if I click this
palette command,
it'll basically create a new
send button for me,
using that factory command.
So if you think about that,
by creating factories
of common UI components,
you could basically have
a whole palette
of really highly customized
reusable components,
and make them available
to everybody
on your team quite easily.
Let me show some
internationalization,
notice that it picked up the CSS
style change there, too.
If we click on
the internationalization tool,
tell it to extract those--
Well, first, let's look at
the source code here,
because we have a bunch of
hard-coded strings.
Don't want to get rid of
one of these buttons,
just make it
a little simpler.
So we have hard-coded
strings right now.
Let's internationalize
this class.
We'll create
an app constance class,
tell it to externalize
all the components.
It's generated the keys
and values for me,
and updated the source code
appropriately.
So no longer do we have any
hard-coded strings,
and it's also at
this point created
that app constance
properties file,
which, we'll open that up,
pull it down here
so you can see it.
And now if I go back into
the design view,
and if I change anything,
notice it updates
the property file for me
rather than--and leaves
the source code,
which has already been
internationalized,
completely untouched.
And again if I had
a second language,
it would work that way
as well.
Now I'm going to do a slightly
more complex example,
so I'm going to close some
of these classes
that I don't need anymore.
And I'm going to do
a real simple example
showing how to attach a custom
composite to a cell table.
So first I have a little
domain class here,
very simple person class,
first name, last name,
male, true or false, and age.
And I've already built
a person composite,
which basically has fields
for editing each of
those properties.
It's basically just a very
simple little flex table,
and you can see the source
for this class.
And what it does is
it has fields
for each of the components.
Any time any of those
text fields changes,
it automatically updates
the embedded person object
that was passed in,
and it has accessors
for setting the person
for this composite,
getting the person,
resetting it to a new person,
things like that.
So it's a very, very
simple custom composite design
to edit this very simple
person class.
So let's take this--
let's start out with
an empty entry point class.
The first thing
I'm going to do
is I'm going to drop this
person composite on the screen.
I'd like it to fill
the entire width,
so I'm going to
start dragging it out.
Hold the control key down,
and let go--
pulls it to 100%.
Then I'm going to
add a button,
call it "Add".
And finally, let's come
down and add a cell table.
And a cell table is
basically parameterized
by type of object,
so I'm going to tell it
to make this cell table
work with my person object.
Okay, an empty cell table--
not very useful unless
we add some--
well first of all,
let's make it
fill the entire
available width as well.
And then start adding
some columns to it.
So I'll add a text column,
call this "First Name",
Add another one.
"Last Name."
Number column for age,
and a checkbox column
for whether the person
is male or not.
And so far, it's gone
and generated code
for all of these columns,
but this is
where we have to start
actually adding some
intelligence to this.
So it's basically just
generated some default text
for the column,
so I'm going to go in
and tell it to do something
more interesting.
So for the first name column,
I want to get basically the--
Get, uh--
There should be an accessor
for that.
There we go.
Okay, last name,
and object Get Age.
And for the button,
I want it to basically add
the person object here,
so I'm going to
right click on it,
tell it to, um,
add a click handler,
and I've actually got
some methods--
or I had some methods here.
Hold on.
Oops.
I've just got to
pull out my--whoops.
All right.
Pull out some code I'd written
before to do some of this work.
I also want to take
this person composite
and make it into a field--
do the same thing
with the table.
And on that click handler,
I want to do my comma do
add method.
And I've also got a method
that sets up
the data priority for me,
so I'm just going to call
that as well.
And hopefully--
Save that, and let's try
launching it.
And if I start adding some
names--
It works,
the first time.
Thank you. Phew!
[applause]
I was sweating bullets
there for a second.
So a real simple example
of hooking up a custom composite
to a cell table,
and that is pretty much
the end of the demo
that I wanted to show.
So let's go back to the slides,
and then we can wrap it up.
So what did we talk about?
First of all,
Google Web Toolkit,
a great way to build web apps,
as hopefully many of you know.
Google plug-in for Eclipse,
a great way to build GWT apps.
And the UI Designer, a great
way to build GWT web UIs.
So at this point, happy to, if
anybody wants to ask questions,
just use the microphone
there at the back of the room.
And I'll put up
a thank you
with basically
links you can go to,
to get the documentation,
the wiki, the GWT blog,
et cetera.
So if anybody has any questions,
feel free to ask.
man: What do you see
as the future direction
for the UI Binder?
Clayberg:
For the UI Binder?
In terms of
the UI Designer, or?
man: Yes,
like are you looking at
higher speed, more features?
What's--?
Clayberg: Oh, yeah.
Well, first of all,
the goal of the UI Binder
is to stay completely
current with GWT itself.
So as new features get
added to GWT,
as more capability gets
added to UI Binder,
they'll be immediately surfaced
in the UI Design Tool
at the same time.
So we try to keep them--
Back when we were at
Instantiations,
we were usually lagging
five or six weeks behind.
Now our goal is to actually be
current with any new--
since we're part
of the team--
be current with
any new releases.
man: As a Python guy
and not a Java guy,
I'm very interested in GWT,
but I've been trying to
figure out,
how do I put that on the front
end of a Python
back end like Jango?
Can you give me
any guidance?
Clayberg: Unfortunately,
I'm not a Python guy,
and I really can't help
you with that.
But if you can give me
your card, I'd be happy to
find out some
information for you.
man: Okay, well I've actually
got two questions.
One, I didn't see you demo
any of the Designer
with the UI Binder itself.
Does it support that?
Clayberg:
Oh, yeah, yeah.
I mean, in fact
I could just--
man: And the second question
is actually,
how well does
the Designer work
with a pattern such as MVP?
Clayberg:
With a what?
man:
MVP--Model View Presenter,
where all your logic is
elsewhere and your UI Design
is in a single place.
Clayberg: Actually, with more
recent releases,
we've added support for MVP,
and the fact is,
even in MVP Wizard,
that'll create an entire
structure for you.
man:
Oh, nice.
Clayberg:
But as far as UI Binder,
I can, say, create
a new UI Binder composite here,
let me just do that real quick.
And so there's your
standard XML for the UI.
And notice it shows XML source
rather than just plain source.
Switch over to the design
view here in a second.
The very first time I have
to access this,
it takes a few seconds.
And I can just go about
doing what I was doing before,
start adding widgets, switch
back over to the XML source.
See, it's basically added XML
source rather than Java source,
so it works quite well
with UI Binder as well.
man one:
Oh, thank you.
man two:
Earlier in the presentation
you had a split view
between the GWT Designer
and the code view.
How do you access that?
I'm still trying
to figure it out.
Clayberg: Well, one thing
I didn't show is
basically the extensive
properties or preferences
the tool has.
So if you go into Google
Web Toolkit designer,
you can basically--
one of the first properties is
the editor layout.
So you can say, do you want
the notebook,
which order do you want
the notebook tabs?
Do you want them above each
other, split pane, side by side?
There's a bunch of edit
things for like,
setting coding style,
changing how event handlers
are generated.
And by the way, if you
have the full version,
which actually shows up
in your WindowBuilder option,
you get actually a whole bunch
of additional preferences
for really
fine-tuning stuff,
like setting things like
the auto-rename pattern
for variable names.
When you type in text
for a widget,
how does it
automatically decide
what the variable name
should be for that?
So you can have control over
the patterns involved there,
so there are a bunch of
additional preferences there.
man two:
Great. Thanks.
man: How does the bi-directional
updates deal with components
that are dynamically
generated at one time.
So say like I have a grid
of components
where the cells of the grid are
commanded at one time?
Clayberg:
So the question is,
how does it work with
dynamically created components
as opposed to statically
created components?
The basic answer is,
it doesn't, really.
Really, the tool deals
with static UIs.
So anything that's sort of
dynamically created,
it really doesn't know about it,
so it can't really render it.
So if you had
a flex table or a grid
that you were adding components
to dynamically,
you would see the empty flex
table in the design,
but you wouldn't see any
of the widgets
you're going to add
at run time.
That's unfortunately
one of the limitations.
man:
All right.
Basically it deals
with gracefully.
Thanks.
Clayberg: Okay.
man: I'm going to ask if you
could put up the last slide.
Clayberg:
Sure. That's a good idea.
man: If you could get
to my question.
Clayberg: All right.
There you go.
man: I was wondering how
well it plays with
other development patterns,
like using GIN,
if there's any issues.
Clayberg:
I honestly don't know.
man:
All right. Thank you.
Clayberg: But if you want to
give me your card,
I can find out about that.
man: What about dealing with
existing components,
existing designs you have?
Clayberg: Well,
as I mentioned earlier,
the tool actually works
remarkably well
with hand-written code or code
that you already have existing.
So I would say
just give it a try.
And I mean, one of our
goals is to keep improving that,
so if you come
across cases
where it does not do a good job
rendering your handwritten code,
either whether it's
Java code or UI Binder code,
I would encourage you to
actually send us an example,
or maybe strip it down
to just the minimum
that you're willing
to part with,
take out anything
that's proprietary,
but send us examples
that don't work.
And we are very interested in
working with those examples
and making them work
with the tool,
and improving it over time.
man:
Thank you.
Clayberg: Yeah.
man: Do you have any facilities
for test generation?
Clayberg: Actually in
the full version of the tool,
there actually is a Janit
test generation wizard
that just creates a GWT Janit
stub for you, but it doesn't--
we don't have any UI automated
record/playback testing,
anything like
that for this tool, no.
man:
Any plans for that?
Clayberg: It's something
that's been talked about,
but at this point, we don't have
any plans to do that.
man:
Thanks.
man two: When it comes to
databases, do you have it
so that it'll automatically link
when you create--
you know, how you create
the first and last name,
like you want
it to link to a database,
like you can create
the database
and then automatically pull it
in like you did before?
Is there an option
in there for that?
Clayberg: Well, we don't
have anything like that.
We do have, actually,
for GXT, if you're using GXT,
we actually have support
for the GXT data-binding model,
which basically is,
if you have a database,
if you have a pojo,
plain old java object,
any kind of data source,
you can hook those data sources
to UI elements.
Whenever GWT gets
to the point of having its own
data-binding API,
we would obviously build
a support for that as well.
But at this point,
in the basic UI designer tool,
there isn't really support
for that with basic GWT.
man:
Right. Thank you.
Clayberg:
But it's definitely something
we would be very interested in.
man: Could you show how you
add a widget to the palette?
Clayberg: Sure.
man: I saw how you were doing it
with the composite.
I'm more interested in a class
that extends from another--
Clayberg: Right. Basically,
it's quite simple.
So if we pull up any one
of these classes here,
you basically just right click
on the palette,
say if you're going to
add a category,
I can add a component to
an existing category.
And you basically
just choose the class.
So if it's a sub-class
of button, my button,
you just find it
and it'll automatically--
then you can give it
a description
and it'll just show up
if you hover over the component
in the palette,
and you can pick which category
you want it to go into.
And that's it.
Hit okay, and there
it is on your palette.
man:
Thank you.
Clayberg: All right,
any other questions?
Well, I guess I can give
you all back
a minute and thirty seconds.
Thank you for attending.
[applause]
