Multi-part question, so I'm going to try to hit this in several parts:
What is the cost of GWT.create()
?
Most of the GWT
class is 'magic', things that you cannot wrote for yourself in other ways, as they call on the compiler to fill in specific details for you. These are often different when running in dev mode vs compiled to JS.
In the case of GWT.create
, it turns out that this is compiled out to new
- it is used just to create new instances. So what is the cost of a new instance versus a singleton? This depends entirely on the object being created. If there are no fields in the object, then the cost is essentially free - in fact, the compiler may choose to actually remove the constructor call, and rewrite all later methods as static
anyway!
This is what happens in most cases - GWT.create
should be considered to be very cheap, unless you are doing something silly like calling it within a loop that is run many times.
What happens when I list a ClientBundle
method inside another ClientBundle
?
Well, what happens when you list anything inside a ClientBundle
?
Anything that can be listed in a ClientBundle must be annotated with @ResourceGeneratorType
, indicating how to generate that type. For example, here is ImageResource
:
/**
* Provides access to image resources at runtime.
*/
@DefaultExtensions(value = {".png", ".jpg", ".gif", ".bmp"})
@ResourceGeneratorType(ImageResourceGenerator.class)
public interface ImageResource extends ResourcePrototype {
//...
It calls on ImageResourceGenerator
to create images as needed. Any class described in that annotation must implement com.google.gwt.resources.ext.ResourceGenerator
, which describes how to get ready to work, how to create necessary fields, how to initialize them, and how to finish up.
So what does this look like for ClientBundle itself? Check out com.google.gwt.resources.rg.BundleResourceGenerator
- it is a very simple class that just calls GWT.create()
on the type of the method given. So, predictable, this means that those 'child' ClientBundles are created via GWT.create, more or less the same as you might otherwise do.
Okay, what does that mean in this specific case?
It turns out that ClientBundles instances don't have fields where they track newly created objects from, but instead have static members that they use instead - effectively singletons. This means that once you have called a method once, the instance it returns will be the same instance created as the next time you call it. Two different ClientBundles with the same contents will of course then keep two different copies of the objects, but it doesn't matter how many times you create a ClientBundle - its internals will always be the same.
Anything else?
Yep! Remember that you are dealing with interfaces here, not classes, so you can actually extend more than once at once!
public interface MyAppResources extends
ClientBundle,
CellTable.Resources,
CellTree.Resources {//etc
//...
Now, if two interfaces describe the same methods you may have problems, but if not, this can provide an advantage when generated sprited images. Each individual ClientBundle
will draw on its own pool of images when preparing them for use - if you have a ClientBundle
within a ClientBundle
, they won't work together to sprite images into bigger pieces. To get that, you need to make just one ClientBundle
type. This may not matter in your particular case, but I figured it was also worth mentioning.