Re: [HTML Imports]: Sync, async, -ish?

On Tue, Dec 3, 2013 at 2:22 PM, Bryan McQuade <bmcquade@google.com> wrote:

> Second question: should *rendering* of page content block on the load of
> <link rel=import>
>
> Steve Souders wrote another nice post about this topic:
> http://www.stevesouders.com/blog/2013/11/26/performance-and-custom-elements/which I recommend reading (read the comments too).
>
> We should start by looking to how the web platform behaves today. All
> browsers I am aware of block rendering on the load of pending stylesheets.
> Note that blocking rendering (blocking of render tree construction and
> painting content to the screen) is different from blocking parsing.
> Browsers do not block HTML parsing (DOM construction) on stylesheets. Nor
> should they block DOM construction on loading of <link rel=import>s.
>
>
Correct. Imports are even better than the main document though.
document.write doesn't work, and we allow the parser to "run ahead" and not
block on <script> inside an import. That means putting <script
src="slow-resource.js"></script> in your import will not slow down the
parser as it processes the import tree. It'll continue building the
documents of imports while the resource loads.


> The reason to block rendering while a custom element's load is pending is
> to prevent a flash of unstyled content/reflow of content on the page. At a
> high level:
>

We are not blocking rendering on custom elements. We're waiting for a
critical resource to load because it may contain <style> or <script>.


> 1. if there are no custom elements in the DOM, [...]
> 2. if there are custom elements in the DOM [...]
>

We should not be focusing on custom elements here. Imports and custom
elements are separate but related features and neither depends on the
other. Lots of things could be inside the import. Custom elements don't
block anything.


> However, if the positioning of the custom element changes as a result of
> its being upgraded, i.e. its x/y/width/height changes, [...]
>

> So how do we strike a balance between fast rendering and avoiding
> reflow/content moving around on the screen? In the case of custom elements
> there are a few things that browsers can do:
>
>  1. if there are no custom elements in the DOM, then even if a load of a
> custom element import is pending, then there is no reason to block
> rendering of the rest of the page, since the custom element's load can't
> impact the styling of content in the DOM.
>

This is not correct. Imports are not just for custom elements, they're a
generic system for importing "stuff". You can put a <style> in the import
and it will apply to the main page.


> 2. if there are custom elements in the DOM and a custom element import's
> load is pending, *and* it can be determined by the rendering engine that
> the load/upgrade of that element will not cause its *position* to change
> (e.g. that element has a "style="width:x;height:y;" attribute, or a
> style="display:none", etc - we'll have to overlook !important styles for
> this...) then we should not block rendering of the rest of the page, since
> the content other than the custom element will not change position as a
> result of the custom element loading.
>

This is a heuristic that browsers could apply, yes. I don't believe there
is a spec for browsers waiting to paint on remote stylesheets though, in
fact they probably should paint if the sheet is taking forever to load.


>
> However, if there are custom elements in the DOM whose position isn't
> specified in an inline style, and a custom element import load is pending,
> then rendering (not parsing!) should block until that custom element has
> finished loading, to prevent a FOUC/reflow.
>

The parser does not block on rel="import" and document.write() is disabled
down there for this reason. There's no predictability for where it's going
to write since the parser could be anywhere when your import finally loads.


>
> If we take this approach, then developers have two ways to prevent the
> load of custom elements from blocking rendering:
> ...
>


> So, I propose that, similar to pending stylesheets, the load of custom
> elements should block rendering
>

We can't block anything on custom elements, but we certainly can on
imports. I think we should as well and then add an async attribute to allow
an author to declare the import as non-critical.


> . With custom elements, however, we can be a bit smarter than with
> stylesheets: rendering should block only in cases where the upgrade of a
> custom element in the DOM might cause a reflow, moving other page content
> on the screen.
>

There is no way to do this. A document might contain custom elements that
are not upgraded until hours later when the author decides to call
document.register. In general imports are separate from custom elements as
well, we block on them because they're effectively a set of packaged
<style> and <script> blocks which would have blocked painting had they been
inside the main document.

- E

Received on Wednesday, 4 December 2013 09:18:43 UTC