I want to make it possible for Firefox 3 to apply some site- and page-specific user settings to pages during layout. Some settings will get applied by rules in a user stylesheet (f.e. text and background colors), while others will get applied via other mechanisms (f.e. text size, which prescontext apparently handles).
I'm trying to figure out how best to integrate the application of these various settings into layout.
I chatted with dbaron about it, and he suggested this might best be accomplished with a new settings object that gets queried by the various other objects for relevant settings at appropriate stages in the loading process.
For example, stylecontext (?) might query the object when it's ready to style the page, while prescontext might query it before setting the page's text size.
Does that seem like the right approach, and are there any potential pitfalls to be aware of? Is there any reason not to implement such an object as a JavaScript component?
Myk Melez wrote: > Some settings will get applied by rules in a user stylesheet
We already have a mechanism for this, right?
> I chatted with dbaron about it, and he suggested this might best be > accomplished with a new settings object that gets queried by the various > other objects for relevant settings at appropriate stages in the loading > process.
That might work, yeah. It's certainly a flexible enough idea to do pretty much anything with it depending on how much core code you're willing to change to be aware of this settings object.
> Is there any reason not to implement such an object as a JavaScript component?
Depends on how you use it. If it's queried once per pageload to get some data that core layout then uses, it can probably be a JS component. If it's going to be hooked into something that happens often, then performance could be a problem with the JS component approach.
Boris Zbarsky wrote: > Myk Melez wrote: >> Some settings will get applied by rules in a user stylesheet
> We already have a mechanism for this, right?
We have nsIStylesheetService for adding a user stylesheet, and we also have a CSS extension providing URL-based selectors, so we could just load a single user stylesheet with rules for every site and page being styled.
But then the stylesheet will get applied to every page the user loads, even though most pages won't be styled by it.
Another option is for the style context to query the settings object for a page-specific stylesheet on page load.
In that case we would need to modify the style context to do the query and apply the result (if any). And, if we wanted to implement this as a JS component, we'd also have to expose a way to instantiate a stylesheet from script (unless there's such a way already; I haven't found one).
> Depends on how you use it. If it's queried once per pageload to get > some data that core layout then uses, it can probably be a JS > component. If it's going to be hooked into something that happens > often, then performance could be a problem with the JS component approach.
In general, the settings object will get queried once per page load (or perhaps a handful of times per page load, if different parts of layout do their own queries). We'll also need to apply the changes users make to their settings, but those will happen much less frequently than once per page load.
Myk Melez wrote: > We have nsIStylesheetService for adding a user stylesheet, and we also > have a CSS extension providing URL-based selectors, so we could just > load a single user stylesheet with rules for every site and page being > styled.
Right.
> But then the stylesheet will get applied to every page the user loads, > even though most pages won't be styled by it.
Also right. Although this will be more or less a one-time cost per pageload (since this sheet will be immutable and we only filter by moz-document rule when we construct the rule cascade, which only happens when there isn't one already or when the sheet changes).
> Another option is for the style context to query the settings object for > a page-specific stylesheet on page load.
(I assume you mean style set here, not style context, btw... Or possibly even the document viewer, which is where we put in UA/user sheets right now).
Right. So this would also be a one-time cost. Which one is more expensive probably depends on how long it takes to query the settings object and how many rules you expect to have.
There's one more thing to think about, I guess, and that's whether it would be easier to create/edit one sheet per page or a single sheet. I'm not sure where the sheets are coming from, so....
> In that case we would need to modify the style context to do the query > and apply the result (if any). And, if we wanted to implement this as a > JS component, we'd also have to expose a way to instantiate a stylesheet > from script (unless there's such a way already; I haven't found one).
So how complicated do you expect the answers to the "what sheets should I apply to this site" question be? If we're talking just a hostname match, we could just extend nsIStylesheetService to allow registering sheets for a particular hostname. If we'll take various information and then compute what sheets should apply, the way to go is probably to return a list of URIs and then have layout use the stylesheet cache to actually get sheets for the URIs or something...
Not sure any of this answers your question, of course.... sorry this became so stream-of-consciousness...
On 11/9/06, Boris Zbarsky <bzbar...@mit.edu> wrote:
> So how complicated do you expect the answers to the "what sheets should I apply > to this site" question be? If we're talking just a hostname match, we could > just extend nsIStylesheetService to allow registering sheets for a particular > hostname. If we'll take various information and then compute what sheets should > apply, the way to go is probably to return a list of URIs and then have layout > use the stylesheet cache to actually get sheets for the URIs or something...
Could we not just use a single sheet, and the per-site selectors that dbaron implemented a while back?
If it gets to be a performance issue for people who have bazillions of such rules, we could revisit it, but this would seem to be a pretty quick path to a proof of concept against which we could measure performance characteristics and get user feedback.
Mike Shaver wrote: > Could we not just use a single sheet, and the per-site selectors that > dbaron implemented a while back?
That was my main suggestion, yes. The rest was describing the pros and cons of doing that and trying to figure out what the design criteria are. In particular, we can't use this approach if we're doing something more complicated than host matches (e.g. if we want different style rules depending on the hour mod 3 or whatever). ;)
On 11/10/06, Boris Zbarsky <bzbar...@mit.edu> wrote:
> Mike Shaver wrote: > > Could we not just use a single sheet, and the per-site selectors that > > dbaron implemented a while back?
> That was my main suggestion, yes. The rest was describing the pros and cons of > doing that and trying to figure out what the design criteria are. In > particular, we can't use this approach if we're doing something more complicated > than host matches (e.g. if we want different style rules depending on the hour > mod 3 or whatever). ;)
Ahem, quite! *blush*
I thought from the subject that it was settled on per-site and per-page settings, and the @-moz-document selector seems to handle page/URL-prefix/site all.
Boris Zbarsky wrote: > There's one more thing to think about, I guess, and that's whether it > would be easier to create/edit one sheet per page or a single sheet. > I'm not sure where the sheets are coming from, so....
Creating is probably the same either way, but it'll be easier to edit one sheet per page, I reckon, since we'll be editing a much smaller and simpler document.
> So how complicated do you expect the answers to the "what sheets should > I apply to this site" question be? If we're talking just a hostname > match, we could just extend nsIStylesheetService to allow registering > sheets for a particular hostname.
For the application I'm considering, the answers will be simple. For a given page, the answer will comprise one sheet for the site on which the page is located and one sheet for the page itself.
Of course, we'll need to define what we mean by "site" and "page" and, if we choose the single sheet approach, make sure dbaron's per-site selector syntax supports those definitions (which it seems like it does, based on some early working commonsense definitions of those terms).
Mike Shaver wrote: > Could we not just use a single sheet, and the per-site selectors that > dbaron implemented a while back?
Yes, we could, and we probably should start with this, for the prototype anyway, since doing this appears to require no changes to layout code (as long as the settings service can access the stylesheet for editing once the stylesheet service has loaded it), and thus could conceivably be done by an extension.
But note that this doesn't get us all the functionality I'm looking for, even if it turns out to be the right approach for settings which affect style, because not all settings are style-based. Text size, for one, is (surprisingly) set by prescontext.
Boris Zbarsky wrote: > Myk Melez wrote: >> (as long as the settings service can access the stylesheet for editing >> once the stylesheet service has loaded it)
> This is probably best handled by unloading the sheet, editing it, then > reloading it.
>> because not all settings are style-based. Text size, for one, is >> (surprisingly) set by prescontext.
> Yeah, indeed. Do we have a list of the "settings" we want to affect?
Not a complete or final one, but candidates include:
* text size * text and background colors * ability to run JavaScript (+ advanced JavaScript settings?) * ability to open popup windows (already applied per-site)
In general, the stuff in the Preferences > Content panel (or that would go there if implemented) are the kinds of settings I'm targeting for improvement, although issues vary (some are already applied per-site, others may not be common enough to warrant additional exposure, etc.).
Myk Melez wrote: > * text size > * text and background colors > * ability to run JavaScript (+ advanced JavaScript settings?) > * ability to open popup windows (already applied per-site)
Hmm... So we already have mechanisms for per-site customization for some of these. In fact, for some of them we effectively have multiple such mechanisms (ability to run JavaScript comes to mind; I believe we have at least 3 different ways of affecting it, and none use nsIPermissionManager, which is the general API for per-site permissions for various stuff that we have)...
It feels to me like we might want different solutions to the different parts of this. Things that can be expressed as permissions ought to use the existing nsIPermissionManager (or pseudo-CAPS stuff like JS execution does) if they can. Things that correspond to layout behavior can be gotten by prescontext from some service instead of getting them from prefs, and the service could either use prefs or whatever it wants. For backwards compat, we should probably have a version of this service that just looks at the existing prefs.
But I have to admit that I haven't thought about this much, so please take everything I say with some caution!