On Wednesday, February 19, 2014 10:59:51 AM UTC+1, Thomas Broyer wrote:
>
>
>
> On Tuesday, February 18, 2014 6:38:36 PM UTC+1, GWTter wrote:
>>
>> Hi all,
>>
>> Let me just go with an example right off the bat.
>>
>> Let's say I have the following:
>>
>> === Pseudocode ===
>>
>> SuperCssResource: This is injected onModuleLoad before anything else
>> .genButton{
>> color: black;
>> }
>>
>> Widget1 consists of:
>> --- css ---
>> MyCssResource:
>> .myButton{
>> color: red;
>> }
>>
>> --- html ---
>> <button class="genButton myButton" />
>>
>> Widget2 consists of:
>> --- css ---
>> XCssResource extends SuperCssResource:
>> ... rules that use classes from SuperCssResource
>>
>> --- html ---
>> ...elements
>>
>> My problem is that if I display Widget1 first and then display Widget2 
>> then the button in Widget1 will have a color of black instead of red.
>>
>> I know that this is expected behavior (GWT will merge the stylesheets 
>> together) since inheritance is basically the cssresource equivalent of CSS 
>> @import <http://www.w3.org/TR/css3-cascade/#at-import>
>>
>
> Er, no.
>
> Inheritance of CssResource interfaces only deals with that: inheriting 
> methods. The actual CSS backing the resource is given by the @Source 
> annotation on your ClientBundle method, and if you use the same CSS file 
> for 2 different CssResource interfaces, the CSS will be duplicated, because 
> obfuscation of the class names is based on the interface fully-qualified 
> name: http://www.gwtproject.org/doc/latest/DevGuideClientBundle.html#Scope 
> (the 
> order of the files in @Source will impact merging, just as they'd impact 
> precedence in CSS).
>

Hi Thomas,

I guess I should have specified that it is inheritance along with 
specifying the source css that for all intents and purposes acts like CSS 
@import. I know that GWT will error if you extend the super resource and 
don't include it's source to match the classes, unless you're 
reimplementing them in the extending css resource which is not what I'm 
after and not the best idea IMHO. 

>  
>
>> but I thought since this was GWT maybe there was a way to use inheritance 
>> in the sense that the inherited stylesheet would only be injected if
>> not injected already. Is this currently possible? or could it be done 
>> with like a @Require annotation on the extending interface which would 
>> indicate
>> that merging of the super stylesheet should not be done but rather a 
>> check would be made to see if it already exists and if not to inject it.
>> This would easily resolve the specificity overriding issue in the example 
>> when it's not the desired behavior.
>>
>> I know I could also get around this by importing with a prefix, however I 
>> still don't like the idea of essentially reinjecting the same styles.
>>
>
> If you don't want duplication, then you need a "shared scope" or "imported 
> scope". In any case, that means you should only use the shared/imported 
> class names in more complex selectors, you shouldn't change the styles 
> attached to the selector by itself.
>
> None of this applies if you use "@external" though, then it just works 
> like standard CSS.
>

I know, like you mentioned, that I could avoid the precedence override by 
importing with prefix for example. And my use case is only to increase 
specificity on the extending css resource, definitely not to change the 
super's rule def by redefining the super selector in the extending 
resource. But I'm not thrilled with essentially reinjecting all the same 
rules with just different prefixes and @external does really fit my need as 
I don't want to forgo the obfuscation. 

>
> …and no, there's no way to say "please make sure that other stylesheet is 
> injected when injecting that one", because, to begin with, it'd be hard to 
> define what "that other stylesheet" is (the interface is not enough, given 
> that the @Source is set on the ClientBundle method, so you'd have to say 
> "this method from this ClientBundle interface", but it wouldn't even be 
> enough: what if you composed that interface with another one and 
> GWT.create()d the composed interface? should that @Require mean that GWT 
> would do a GWT.create() of the lone interface, therefore duplicating 
> efforts? –in all honesty, I haven't looked closely at the impact in terms 
> of generated code and how it could be optimized, but it could limit future 
> evolutions of ClientBundle in which code it generates, just to make sure 
> that feature would still be correctly optimized–)
>

Originally I did think that the interface would be enough but as you 
pointed out you can technically use another source css to attach to the 
interface when defining it in the Clientbundle, wouldn't necessarily always 
be the same one. I only thought of what I think you alluded to which would 
have been to specify the clientbundle such as in the 
@Required(MyClientbundle). In that composed case you mention isn't that 
what's currently happening? From what I can see in the generated css, the 
extended resources are basically inlined before the extending resource css 
and the whole thing becomes the final css which GWT injects on 
ensureInjected. Taking what you said into consideration and some more 
thought it might have to be something a little more like this:

@Source(leafCss={css files}, requiredSupers={
    @required(resource=superResource.class, bundle=MyClientBundle.class),
    @required(resource=super2Resource.class, bundle=My2ClientBundle.class)
})
MyCssResource css();

where leafCss would be the css that GWT uses for initial creation. The 
requiredSupers would tell GWT both where to find the appropriate interface 
and associated css and also the resources which it could would need to keep 
track of to check if injected when
ensureInjected is performed for the leaf resource. I tried to show a less 
common use case where MyCssResource extends 2 different resources to better 
illustrate that it could be handled instead of the trivial 1 resource being 
extended. Or am I way off and this is pretty half-baked?

I just think such a feature would be extremely useful especially with large 
apps where you have many localized resources as well as global ones and you 
don't want to worry about displaying something who's dragged in css causes 
a precedence override when all you wanted that extended css for was to 
qualify your selectors.
 

> No really, given that ensureInjected() is a no-op if already injected, 
> just make sure you call ensureInjected() on your "required" CssResource 
> before calling ensureInjected() on the one that requires it, and document 
> it thoroughly in the javadoc of the requiring ClientBundle method.
>

Thanks again for the reply, much appreciated.

-- 
You received this message because you are subscribed to the Google Groups 
"Google Web Toolkit" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to google-web-toolkit+unsubscr...@googlegroups.com.
To post to this group, send email to google-web-toolkit@googlegroups.com.
Visit this group at http://groups.google.com/group/google-web-toolkit.
For more options, visit https://groups.google.com/groups/opt_out.

Reply via email to