在我的应用中,我有MyAppResources
,主要包含应用的自定义样式。我正在考虑将自定义样式应用于标准窗口小部件(例如CellTable)以及布局和自定义窗口小部件上的自定义样式的好方法是什么?
我的问题:
由于MyAppResources是一个单例(它不必如其他帖子中所述),但CellTableResources
不是,CellTableResources
是此实例的成员,该实例也是一个扩展的接口{ {1}},是否会在每个ClientBundle
上创建代理'CellTableResources'?
如果是这样,我可以创建一个MyAppResources.INSTANCE.cellTableResources().foo()
来解决这个问题吗?或者代理的创建是否可以忽略不计,即使有大量的MyAppResources.CELLTABLE_RESOURCE_INSTANCE
来电?
其次,更多讨论问题:在这种情况下,使用多个MyAppResources.INSTANCE.cellTableResources().#
的最佳做法是什么?我应该单独使用ClientBundle
(从CellTableResources
中删除它),在需要它的小部件中使用MyAppResources
(或使用像我GWT.create(CellTableResources.class);
那样的单例)?< / p>
MyAppResources
:
MyAppResources
public interface MyAppResources extends ClientBundle {
public static final MyAppResources INSTANCE = GWT.create(MyAppResources.class);
@Source("MyAppStyles.css")
public MyAppCssResource css();
public CellTableResources cellTableResources();
}
:
CellTableResources
感谢您的阅读。
答案 0 :(得分:2)
多部分问题,所以我将尝试分几个部分:
GWT.create()
的费用是多少?大多数GWT
类都是'魔术',你不能用其他方式为自己写的东西,因为他们要求编译器为你填写具体的细节。在开发模式下运行与编译为JS时,这些通常是不同的。
在GWT.create
的情况下,事实证明这是编译到new
- 它仅用于创建新实例。那么新实例与单身实体的成本是多少?这完全取决于正在创建的对象。如果对象中没有字段,那么成本基本上是免费的 - 事实上,编译器可能会选择实际删除构造函数调用,并且无论如何都要将所有后续方法重写为static
!
在大多数情况下会发生这种情况 - GWT.create
应该被认为是非常便宜的,除非你做了一些愚蠢的事情,比如在一个多次运行的循环中调用它。
ClientBundle
内列出ClientBundle
方法时会发生什么?那么,当您在ClientBundle
中列出任何时会发生什么?
ClientBundle中列出的任何内容都必须使用@ResourceGeneratorType
进行注释,以指示如何生成该类型。例如,这里是ImageResource
:
/**
* Provides access to image resources at runtime.
*/
@DefaultExtensions(value = {".png", ".jpg", ".gif", ".bmp"})
@ResourceGeneratorType(ImageResourceGenerator.class)
public interface ImageResource extends ResourcePrototype {
//...
它会根据需要调用ImageResourceGenerator
来创建图像。该注释中描述的任何类都必须实现com.google.gwt.resources.ext.ResourceGenerator
,其中描述了如何准备工作,如何创建必要的字段,如何初始化它们以及如何完成。
那么ClientBundle本身的情况如何呢?查看com.google.gwt.resources.rg.BundleResourceGenerator
- 这是一个非常简单的类,只需对给定方法的类型调用GWT.create()
。所以,可预测的,这意味着那些'子'ClientBundle是通过GWT.create创建的,或多或少与你可能做的一样。
事实证明,ClientBundles实例没有跟踪新创建对象的字段,而是使用他们使用的静态成员 - 实际上是单例。这意味着一旦您调用了一次方法,它返回的实例将与您下次调用它时创建的实例相同。具有相同内容的两个不同的ClientBundle当然会保留两个不同的对象副本,但是创建ClientBundle的次数并不重要 - 它的内部结构将始终相同。
是的!请记住,您在这里处理的是接口,而不是类,因此您实际上可以多次扩展一次!
public interface MyAppResources extends
ClientBundle,
CellTable.Resources,
CellTree.Resources {//etc
//...
现在,如果两个接口描述相同的方法,您可能会遇到问题,但如果没有,这可以在生成sprited图像时提供优势。每个人ClientBundle
在准备使用时都会使用自己的图像池 - 如果ClientBundle
中有ClientBundle
,他们将无法合作将图像拼凑成更大的图像。为此,您只需制作一个ClientBundle
类型。这在你的特定情况下可能无关紧要,但我认为这也值得一提。