Re: Custom tags over wire, was Re: HTMLElement.register--giving components tag names
On Sat, Sep 3, 2011 at 4:31 AM, Anne van Kesteren ann...@opera.com wrote: On Fri, 02 Sep 2011 20:47:27 +0200, Dimitri Glazkov dglaz...@chromium.org wrote: BTW, I really ought to put this fears list on the Wiki. Yeah that would probably be a good idea. Done: http://wiki.whatwg.org/wiki/Custom_Tags_Analysis it still needs work, but the main stuff is there. :DG
Re: HTMLElement.register--giving components tag names
On Sat, Sep 3, 2011 at 8:20 PM, Ian Hickson i...@hixie.ch wrote: On Sat, 3 Sep 2011, Dominic Cooney wrote: I think the XBL approach is far superior here -- have authors use existing elements, and use XBL to augment them. For example, if you want the user to select a country from a map, you can use a select with a list of countries in option elements in the markup, but then use CSS/XBL to bind that select to a component that instead makes the select look like a map, with all the interactivity that implies. That sounds appealing, but it looks really hard to implement from where we right now. I don't think it's hard is a good reason to adopt an inferior solution, Likewise, intimating that something is better because it's hard is a distraction. especially given that this is something that will dramatically impact the Web for decades to come. The more complex the thing, the more we're saddled with. XBL(2) is more complex than the proposed model. It likewise needs to be justified all the more. XBL already has multiple implementations in various forms. I certainly agree that we should adjust XBL2 to take into account lessons we have learnt over the past five years, such as dropping namespaces and merging it into HTML instead of forcing an XML language on authors, but taking a significantly less capable solution simply because XBL is difficult seems like a very poor trade-off. It *may* be capable of handling the use-cases in question, but that case hasn't been made, and from where I sit, it's not easy or trivial to do by inspection. Regards
Re: HTMLElement.register--giving components tag names
On 7/09/11 7:20 AM, Alex Russell wrote: On Sat, Sep 3, 2011 at 8:20 PM, Ian Hicksoni...@hixie.ch wrote: On Sat, 3 Sep 2011, Dominic Cooney wrote: I think the XBL approach is far superior here -- have authors use existing elements, and use XBL to augment them. For example, if you want the user to select a country from a map, you can use aselect with a list of countries inoption elements in the markup, but then use CSS/XBL to bind thatselect to a component that instead makes theselect look like a map, with all the interactivity that implies. That sounds appealing, but it looks really hard to implement from where we right now. I don't think it's hard is a good reason to adopt an inferior solution, Likewise, intimating that something is better because it's hard is a distraction. especially given that this is something that will dramatically impact the Web for decades to come. The more complex the thing, the more we're saddled with. XBL(2) is more complex than the proposed model. It likewise needs to be justified all the more. I agree that XBL2 may have been too ambitious for it's time. I would say that the simplest thing that would be useful would be: a) provide a bare-bones shadow DOM b) implement something like the NodeWatcher proposal - http://www.w3.org/2008/webapps/wiki/MutationReplacement#NodeWatch_.28A_Microsoft_Proposal.29 These features are independently useful and would facilitate Javascript library solutions similar to both HTMLElement.register and XBL2. Then step back and see what the Javascript guys do with it. The next step might write itself. Sean
Re: Custom tags over wire, was Re: HTMLElement.register--giving components tag names
On Sun, Sep 4, 2011 at 1:56 PM, Dimitri Glazkov dglaz...@chromium.orgwrote: The offsetWidth query could've triggered an event handler execution I don't think offsetWidth should be able to trigger synchronous execution of an event listener in the content. How would that happen? Rob -- If we claim to be without sin, we deceive ourselves and the truth is not in us. If we confess our sins, he is faithful and just and will forgive us our sins and purify us from all unrighteousness. If we claim we have not sinned, we make him out to be a liar and his word is not in us. [1 John 1:8-10]
Re: Custom tags over wire, was Re: HTMLElement.register--giving components tag names
On 3/09/11 4:47 AM, Dimitri Glazkov wrote: On Fri, Sep 2, 2011 at 2:30 AM, Anne van Kesterenann...@opera.com wrote: Examples of elements that should not be replaced but could be changed by a binding: Having a sortable binding fortable; Exposing cite= on blockquote; Turning aselect listing countries into a map. Great! Let's go through them: * Sortable binding for a table is really just a table subclass with some event listeners registered. * Exposing cite on blockquote sounds like something CSS should do. There's no extra behavior, and you're not really creating a new type of element. It's just extra boxes. * Turning select listing countries into a map -- composition to the rescue!: x-country-map select optionLilliput optionBlefuscu /select /x-country-map From the author's perspective, you don't actually need the select element. If you intend to show a map on cool browsers and select on the less cool ones, you are completely uninterested in having your select semantics dutifully reproduced. All you need is something that does what you need. Besides, the behavior of a map and a select are so different than you probably would scrap the former to build the latter anyway. The author wants the select element so that form submission works. The semantics of select are also quite useful as you might want the country-map widget to allow multiple selections, have a default selected country, and have a non-comprehensive list of countries to choose from. As you have indicated, the user needs the select element as the fallback presentation. It would also be useful if user stylesheets could override the behavior chosen by the author - either reverting to a browser select widget, or something provided by a browser add-on. This capability depends on there being a defacto standard for applying the country-map behavior. Which do you think would take on more quickly: a) custom tag-names, or b) aria or data attributes I'm almost certain it's b. My personal opinion is that most of the perceived need for custom tag-names is to put presentation into HTML. Kind of like font and center but without the benefit of being standards (de facto or de jure). Sean
Re: Custom tags over wire, was Re: HTMLElement.register--giving components tag names
On Fri, 02 Sep 2011 20:47:27 +0200, Dimitri Glazkov dglaz...@chromium.org wrote: Fear 6: Accessibility. Accessibility! Accessibility!? I contend that the Component Model does not make accessibility any worse. And likely the opposite. By allowing ATs to traverse into shadow subtrees, and ensuring that the shadow subtrees are well-behaving accessibility citizens, you allow authors of components to encapsulate good practices and aid in killing the re-created poorly anti-pattern. That's what Sencha, SproutCore, Dijit all try to do -- and the Component Model will enable them do this right. In fact, things like access keys or even z-index are quite hard (impossible) to get right, unless you have something like a well-functioning shadow DOM. The problem is not so much that you cannot make it accessible. It is that making it accessible is complicated for the average authors. This leaves us with the argument of replacing semantics. Since we're in business of sub-typing HTML elements, we don't necessarily need to forego their semantics: // ... var AwesomeButton = HTMLButtonElement.extend(awesomeButtonInitializerBag); Element.register('x-awesome-button', AwesomeButton); // ... should give you a thing that behaves like a button, with the awesome behavior added. In the situations where existing semantics are representative, but deficient, you are much better off replacing them anyway: button becomes=x-plus-one-button+1/button Depending on the specifics, I suppose this might work. What we need is not a becomes= attribute (that renames an element and therefore forgoes its semantics) but rather a way to get complete control over a semantic element and tweak aspects of it. Otherwise creating such controls is prohibitively expensive and only useful if you have vast resources. I would argue that replacing is exactly the right thing to do. You are changing an element from having some basic meaning to a more specific meaning. Replacement seems natural and matches what authors do today. It depends on what is exposed to assistive technolgoy and how much authors have to implement themselves regarding e.g. keyboard accessibility. If you get them somehow magically by using extend() you might not even need becomes=. Examples of elements that should not be replaced but could be changed by a binding: Having a sortable binding for table; Exposing cite= on blockquote; Turning a select listing countries into a map. Great! Let's go through them: * Sortable binding for a table is really just a table subclass with some event listeners registered. But how do make this work as a new element? Especially for table parsing is somewhat hairy. * Exposing cite on blockquote sounds like something CSS should do. There's no extra behavior, and you're not really creating a new type of element. It's just extra boxes. There might be extra behavior, such as clicking on the blockquote exposing it, or some such. * Turning select listing countries into a map -- composition to the rescue!: x-country-map select optionLilliput optionBlefuscu /select /x-country-map From the author's perspective, you don't actually need the select element. If you intend to show a map on cool browsers and select on the less cool ones, you are completely uninterested in having your select semantics dutifully reproduced. All you need is something that does what you need. Besides, the behavior of a map and a select are so different than you probably would scrap the former to build the latter anyway. The idea is that the outcome is the same, but that the presentation is completely different. Both controls have the same goal and semantics, just their presentation is different. So wrapping it in a x-country-map does not seem like the proper approach. Having some way to mint custom elements as a last resort may very well make sense too, but I think the emphasis should be on enhancing existing elements as that is less complex (for authors anyway) and more accessible. Minting new elements only seems crazy and unreasonable if you can't do it. That's not what I said. The thing is, today's Web apps have already retreated into the mostly imperative world. Despite the angry rumors, the battle for markup has been lost. Look the source and weep: http://dev.sencha.com/deploy/touch/docs/, http://www.npr.org/webapp, and lots, and lots of others. However, harnessing the HTML parser to construct an object tree gives us a new round. You don't have to think divs and spans anymore. Once you can start viewing any functional block of your page as a custom element, you can return to using markup as composition medium. Hell, in this case fetching markup lazily becomes more attractive than JSON! I don't think there is any disagreement about current practice. Heck, maybe we do not even disagree and I just not understand it fully. And FWIW, I do not think that has to be seen as Decorator
Re: Custom tags over wire, was Re: HTMLElement.register--giving components tag names
On 9/2/2011 6:39 PM, Alex Russell wrote: Similarly, WCAG is a series of principles for designing usable, high quality applications. ARIA presents a set of semantic roles that don't exist in HTML, and for those, alignment with custom element implementations is outstanding. Components that express those semantics can use ARIA to help communicate what they mean, taking the burden off of the users of the components to understand and manage the role/state groups. When working with accessibility, it's super-set of HTML: img { role: 'img'; }; img[alt=] { role: 'presentation'; } Yes, I'd like to see Components express aligned semantics, such as button:aria-pressed, in the shadow DOM. It's the same method we use with the Canvas subtree. Pseudo-classes as a state mechanism need a lot more examination, AFAICT. It's a non-extensible vocabulary, it doesn't appear to be scriptable, and as a result, we haven't been able to use them to handle things like states for animations (which should be transitions between states in a node-graph). +shans I meant to short-hand the specs in the HTML element to Accessibility API Role Mapping Matrix: http://dev.w3.org/html5/html-api-map/#api-role As evolved from: 2010: http://www.paciellogroup.com/blog/misc/HTML5/aria-html5-proposal.html 2009: http://dev.w3.org/html5/markup/aria/ I didn't mean to introduce a new state mechanism. CSS selectors already work with ARIA. With transitions, and generated content, CSS is quite flexible. This would work fine with transitions: div[aria-checked=true] { content: 'Checked'; color: red;} div[aria-checked=false] { content: 'Not Checked'; color: black; } I suspect we're talking about different things. How should ATs be notified/detect that there is a shadow DOM? Focus works as it always has. It can move inside the shadow. Does the following statement make sense?: ATs that walk the DOM should check for element.shadow [currently webkitShadow], prior to looking for element.childNodes. I'd imagine the accessibility tree simply contains the appropriate data, but for ATs using simple DOM, and getAttribute, should they now check for a .shadow attribute on elements in addition to their usual heuristics? That'll work for components with a public shadow, which I think will be most of them. Components can also note state by setting role/state directly on the outer component. What of components that contain multiple roles? Would those components, necessarily, require a public shadow? There was some discussion about allowing multiple children on the shadow. Perhaps this would be a good use case for it. data-* works for arbitrary metadata, and aria-* for UI semantics. Yes! And for low-complexity tasks, they're perfect. For larger, reusable components that need bundled behavior (Closure, JQuery UI, Dijit), the task of setting up and managing all of this can be made easier for users and developers of components by giving them a place to hang behavior, shadow DOM, and data model concerns from. We're certainly experimenting, with the Canvas tag and subtree. The component approach turns this around, by letting you construct a logical tree that might havecanvas elements in the shadow, meaning you don't need a hidden tree per sae. I like to think that it encapsulates current practice. I'm all for it. We still need a canvas subtree, to operate with the canvas 2d spec on drawFocusRing. 4. Let's look at the button example: button becomes=x-awesome-buttonWeee!!/button Becomes: x-awesome-buttonWeee!!/x-awesome-button For the sake of ATs, that should include ARIA semantics: x-awesome-button role=button tabindex=0/x-awesome-botton Now the OS and ATs think of that as a button, in every way thatbutton would be. The UA, though, does not; it leaves it up to the scripting environment. There's a lack of terseness here that's sort of concerning. One possible way forward might be to use role as a shorthand for becomes and allow components to register for roles which they implement. Hmmm. These extended attributes are something to be managed via script. You would not expect someone to author ARIA states into their static markup, though you would include roles. I do think shorthand is valuable. As I understand it, ARIA tries to stay out of the way. There is no current CSS+ARIA profile, it could be helpful if there were. I think this gets back to the idea of how does a component advertise it's state?, and as far as I know, there's no unified approach in the web platform. ARIA exists outside of the existing HTML pseudo-class system. Anyone who wants to target states with CSS needs an extensible vocabulary, and so a lot of stuff gets stuffed into CSS class names too. Sort of mess today, and I'd love for us to find a way to unify these theories of state. CSS selectors make this easy enough. ARIA has an extensible vocabulary, and CSS has an easy query language. ARIA is intended to advertise the state of a component. ATs need
Re: HTMLElement.register--giving components tag names
On Tue, 30 Aug 2011, Dominic Cooney wrote: I'm proposing we add something that lets script extend the set of tag names, so there is less of a bright line between elements defined in the HTML spec and elements defined in script. Something like: HTMLElement.register('x-contacts', ContactPicker); What's the fallback behaviour for when script is disabled? I think the XBL approach is far superior here -- have authors use existing elements, and use XBL to augment them. For example, if you want the user to select a country from a map, you can use a select with a list of countries in option elements in the markup, but then use CSS/XBL to bind that select to a component that instead makes the select look like a map, with all the interactivity that implies. -- Ian Hickson U+1047E)\._.,--,'``.fL http://ln.hixie.ch/ U+263A/, _.. \ _\ ;`._ ,. Things that are impossible just take longer. `._.-(,_..'--(,_..'`-.;.'
Re: Custom tags over wire, was Re: HTMLElement.register--giving components tag names
On Fri, 2 Sep 2011, Anne van Kesteren wrote: What we need is not a becomes= attribute (that renames an element and therefore forgoes its semantics) but rather a way to get complete control over a semantic element and tweak aspects of it. Otherwise creating such controls is prohibitively expensive and only useful if you have vast resources. Exactly. This is in fact how XBL works. This is why the widgets in the HTML spec are defined in terms of bindings -- the idea is that authors can then provide their own alternative bindings or inherit from them. We would provide basic bindings that they can reuse in their inheritance chain, e.g. so that they can override just the look of the button but get all the interactive behaviour (accessibility roles, keyboard navigation, mouse click reactions, etc) for free. -- Ian Hickson U+1047E)\._.,--,'``.fL http://ln.hixie.ch/ U+263A/, _.. \ _\ ;`._ ,. Things that are impossible just take longer. `._.-(,_..'--(,_..'`-.;.'
Re: HTMLElement.register--giving components tag names
On Sat, Sep 3, 2011 at 12:04 PM, Ian Hickson i...@hixie.ch wrote: On Tue, 30 Aug 2011, Dominic Cooney wrote: I'm proposing we add something that lets script extend the set of tag names, so there is less of a bright line between elements defined in the HTML spec and elements defined in script. Something like: HTMLElement.register('x-contacts', ContactPicker); What's the fallback behaviour for when script is disabled? The fallback behavior is basically that you’ll author your markup either progressively enhance. If you want to support script being disabled, I guess you’re going to use postbacks. Progressive enhancement: div becomes=x-contacts-picker form action=contacts.cgi method=post label for=nameName:/name input type=text name=name input type=submit value=Search /form /div Fallback: x-contacts-picker … form same as before … /x-contacts-picker In this case when the x-contacts-picker is available, it suppresses the fallback form with shadow DOM, or even by yanking it out of the DOM. Since registration is imperative, components imply running script. There’s no story yet for when you have components but no script. Looking at the use cases, they mostly (ie except for panel layout manager) want to wire up event listeners for interactivity. I think has components, but doesn’t have script will not be something people design for. Declarative would be nice for initializing the shadow DOM in a more succinct way, though. One thing that isn’t worked out is that sometimes you want to write components that present their children, but if those children don’t coincide with your fallback content you’re SOL. I expect one pattern that might emerge is nested subcomponents, and have CSS handle switching: x-spectacle x-rockin !-- 11 stonehenge, dwarves -- … /x-rockin img src=puppetshow.gif /x-spectacle x-rockin { display: none; } x-rockin:bound { display: block; } Shadow DOM would select and output the subcomponent to flip the switch on the fallback content. I think the XBL approach is far superior here -- have authors use existing elements, and use XBL to augment them. For example, if you want the user to select a country from a map, you can use a select with a list of countries in option elements in the markup, but then use CSS/XBL to bind that select to a component that instead makes the select look like a map, with all the interactivity that implies. That sounds appealing, but it looks really hard to implement from where we right now. Wearing my WebKit hat, one nice property of the above is that we either have an element we’re going to rip out of the DOM and replace: div becomes=x-contact-picker (gets replaced somewhat like renameNode) Or one that isn’t particularly rich to begin with: x-contact-picker (is HTMLUnknownElement until registered; perfect tabula rasa for a component) Whereas in the general case we’d be fighting with suppressing parts of the nature of the element being bound. Similarly, one thing that simplifies shadow DOM is that it affects the rendering of the child content of an element, but the element (as a block or whatever) is still there. This is relatively simple to implement because we can just switch from one list of child content to another when shadow DOM is present. But making the replacement happen outside the box is more complicated, because there are many more places that would need to be aware of this switch—many things that are data would need to be behavior/logic. It is hard to be confident that they interact well. There are a few other things that I like about this compared to XBL. However I don’t want to reject every idea in XBL out of hand—parts of it are appealing, some parts look hard, but in total it is staggering. Some ways in which this proposal is much simpler than XBL: inheritance—there is none. You might layer behavioral changes in a kind of inheritance of prototype chains in JavaScript, but one bespoke prototype is just as onerous as many from the browser’s point of view. multiple bindings—no, only a single binding. unbinding—there is no unregister. (Not stated but I am guessing re-registering the same element name does something simple—throws, or the last one wins.) There’s no way to remove a shadow root, either. complexity of selectors—you just get to match on the element name. So it is very simple and static. Dominic -- Ian Hickson U+1047E )\._.,--,'``. fL http://ln.hixie.ch/ U+263A /, _.. \ _\ ;`._ ,. Things that are impossible just take longer. `._.-(,_..'--(,_..'`-.;.'
Re: Custom tags over wire, was Re: HTMLElement.register--giving components tag names
On Sat, Sep 3, 2011 at 12:08 PM, Ian Hickson i...@hixie.ch wrote: On Fri, 2 Sep 2011, Anne van Kesteren wrote: What we need is not a becomes= attribute (that renames an element and therefore forgoes its semantics) but rather a way to get complete control over a semantic element and tweak aspects of it. Otherwise creating such controls is prohibitively expensive and only useful if you have vast resources. Exactly. This is in fact how XBL works. This is why the widgets in the HTML spec are defined in terms of bindings -- the idea is that authors can then provide their own alternative bindings or inherit from them. We would provide basic bindings that they can reuse in their inheritance chain, e.g. so that they can override just the look of the button but get all the interactive behaviour (accessibility roles, keyboard navigation, mouse click reactions, etc) for free. You get all of those for free with the ability to sub-type the elements, as explained elsewhere in this thread. What you also get with the Component Model vs. XBL-like bindings is the consistency of the API surface. Note: I am explicitly calling this XBL-like, because XBL2 intentionally avoids the ability to extend a DOM element API surface with a binding -- so we're not operating in real of a currently existing spec here. But in a general XBL-like model, the problem you have is that at any given moment of time, it is unclear whether your element has a certain API or not. Consider this: in your JS application, you hold a reference to DOM element, and know for a fact it has methods/properties of some Widget binding, that's currently applied to the element. You then access an offsetWidth property on that DOM element... Pop quiz: what's the API surface of your widget now? The answer is: you can never know. The offsetWidth query could've triggered an event handler execution, which could've modified some CSS that binds that particular Widget binding to this element, unbinding it or worse yet, turning it into some other type. BOOM goes the landmine, and there you are, watching your leg fly off. That's the trouble with decorators -- they are ephemeral things that should never, _ever_ expose an API on DOM elements. Otherwise, _anytime_ you are about to access a property or call a method on a DOM element, you'd have to first do a hasBinding check on it. Show of hands -- who wants to write their code that way? If I see any, it's not for long -- those landmines will expeditiously take care of those extra limbs for you. XBL2 provides a set of machinery to make decorators, but in doing so it fails miserably at addressing the use cases that Web application and Web framework developers actually need. And that's why XBL-like approach is a pie-in-the-sky key phrase that should never be applied to element behavior attachment. :DG -- Ian Hickson U+1047E )\._.,--,'``. fL http://ln.hixie.ch/ U+263A /, _.. \ _\ ;`._ ,. Things that are impossible just take longer. `._.-(,_..'--(,_..'`-.;.'
Re: HTMLElement.register--giving components tag names
On Sat, 3 Sep 2011, Dominic Cooney wrote: I think the XBL approach is far superior here -- have authors use existing elements, and use XBL to augment them. For example, if you want the user to select a country from a map, you can use a select with a list of countries in option elements in the markup, but then use CSS/XBL to bind that select to a component that instead makes the select look like a map, with all the interactivity that implies. That sounds appealing, but it looks really hard to implement from where we right now. I don't think it's hard is a good reason to adopt an inferior solution, especially given that this is something that will dramatically impact the Web for decades to come. XBL already has multiple implementations in various forms. I certainly agree that we should adjust XBL2 to take into account lessons we have learnt over the past five years, such as dropping namespaces and merging it into HTML instead of forcing an XML language on authors, but taking a significantly less capable solution simply because XBL is difficult seems like a very poor trade-off. -- Ian Hickson U+1047E)\._.,--,'``.fL http://ln.hixie.ch/ U+263A/, _.. \ _\ ;`._ ,. Things that are impossible just take longer. `._.-(,_..'--(,_..'`-.;.'
Re: HTMLElement.register--giving components tag names
Be careful with the big words. It can't be that inferior if it satisfies use cases that XBL2 can't. :DG On Sat, Sep 3, 2011 at 8:20 PM, Ian Hickson i...@hixie.ch wrote: On Sat, 3 Sep 2011, Dominic Cooney wrote: I think the XBL approach is far superior here -- have authors use existing elements, and use XBL to augment them. For example, if you want the user to select a country from a map, you can use a select with a list of countries in option elements in the markup, but then use CSS/XBL to bind that select to a component that instead makes the select look like a map, with all the interactivity that implies. That sounds appealing, but it looks really hard to implement from where we right now. I don't think it's hard is a good reason to adopt an inferior solution, especially given that this is something that will dramatically impact the Web for decades to come. XBL already has multiple implementations in various forms. I certainly agree that we should adjust XBL2 to take into account lessons we have learnt over the past five years, such as dropping namespaces and merging it into HTML instead of forcing an XML language on authors, but taking a significantly less capable solution simply because XBL is difficult seems like a very poor trade-off. -- Ian Hickson U+1047E )\._.,--,'``. fL http://ln.hixie.ch/ U+263A /, _.. \ _\ ;`._ ,. Things that are impossible just take longer. `._.-(,_..'--(,_..'`-.;.'
Re: HTMLElement.register--giving components tag names
On Sat, Sep 3, 2011 at 8:20 PM, Ian Hickson i...@hixie.ch wrote: On Sat, 3 Sep 2011, Dominic Cooney wrote: I think the XBL approach is far superior here -- have authors use existing elements, and use XBL to augment them. For example, if you want the user to select a country from a map, you can use a select with a list of countries in option elements in the markup, but then use CSS/XBL to bind that select to a component that instead makes the select look like a map, with all the interactivity that implies. That sounds appealing, but it looks really hard to implement from where we right now. I don't think it's hard is a good reason to adopt an inferior solution, especially given that this is something that will dramatically impact the Web for decades to come. XBL already has multiple implementations in various forms. I certainly agree that we should adjust XBL2 to take into account lessons we have learnt over the past five years, such as dropping namespaces and merging it into HTML instead of forcing an XML language on authors, but taking a significantly less capable solution simply because XBL is difficult seems like a very poor trade-off. Be careful with the big words. It can't be that inferior if it satisfies use cases that XBL2 can't. While trying to adjust XBL2 to the set of actual use cases (http://wiki.whatwg.org/wiki/Component_Model_Use_Cases), you'll quickly realize that by its nature, the decorator behavior attachment simply isn't what's needed. You need element attachment. And once you need element attachment, it's fairly easy to arrive at the design that we propose with the Component Model. :DG -- Ian Hickson U+1047E )\._.,--,'``. fL http://ln.hixie.ch/ U+263A /, _.. \ _\ ;`._ ,. Things that are impossible just take longer. `._.-(,_..'--(,_..'`-.;.'
Re: Custom tags over wire, was Re: HTMLElement.register--giving components tag names
On Wed, 31 Aug 2011 19:29:28 +0200, Dimitri Glazkov dglaz...@chromium.org wrote: To put it differently, you want to start with a well-known element in markup, and, through the magic of computing, this element _becomes_ your component in the DOM tree. In other words, the markup: button becomes=x-awesome-buttonWeee!!/button Becomes: x-awesome-buttonWeee!!/x-awesome-button This does not work for assistive technology. That is, you would still have to completely implement the button element from scratch, including all its semantics such as keyboard accessibility, etc. What we need is not a becomes= attribute (that renames an element and therefore forgoes its semantics) but rather a way to get complete control over a semantic element and tweak aspects of it. Otherwise creating such controls is prohibitively expensive and only useful if you have vast resources. Examples of elements that should not be replaced but could be changed by a binding: Having a sortable binding for table; Exposing cite= on blockquote; Turning a select listing countries into a map. Having some way to mint custom elements as a last resort may very well make sense too, but I think the emphasis should be on enhancing existing elements as that is less complex (for authors anyway) and more accessible. And FWIW, I do not think that has to be seen as Decorator http://wiki.whatwg.org/wiki/Behavior_Attachment as for the examples I listed above I would expect the binding to be permanent. (I would also expect you could expose additional DOM members, etc.) -- Anne van Kesteren http://annevankesteren.nl/
Re: Custom tags over wire, was Re: HTMLElement.register--giving components tag names
On Fri, Sep 2, 2011 at 2:30 AM, Anne van Kesteren ann...@opera.com wrote: On Wed, 31 Aug 2011 19:29:28 +0200, Dimitri Glazkov dglaz...@chromium.org wrote: To put it differently, you want to start with a well-known element in markup, and, through the magic of computing, this element _becomes_ your component in the DOM tree. In other words, the markup: button becomes=x-awesome-buttonWeee!!/button Becomes: x-awesome-buttonWeee!!/x-awesome-button This does not work for assistive technology. That is, you would still have to completely implement the button element from scratch, including all its semantics such as keyboard accessibility, etc. Ah, thanks Anne! I do indeed need to enumerate... Fear 6: Accessibility. Accessibility! Accessibility!? I contend that the Component Model does not make accessibility any worse. And likely the opposite. By allowing ATs to traverse into shadow subtrees, and ensuring that the shadow subtrees are well-behaving accessibility citizens, you allow authors of components to encapsulate good practices and aid in killing the re-created poorly anti-pattern. That's what Sencha, SproutCore, Dijit all try to do -- and the Component Model will enable them do this right. In fact, things like access keys or even z-index are quite hard (impossible) to get right, unless you have something like a well-functioning shadow DOM. This leaves us with the argument of replacing semantics. Since we're in business of sub-typing HTML elements, we don't necessarily need to forego their semantics: // ... var AwesomeButton = HTMLButtonElement.extend(awesomeButtonInitializerBag); Element.register('x-awesome-button', AwesomeButton); // ... should give you a thing that behaves like a button, with the awesome behavior added. In the situations where existing semantics are representative, but deficient, you are much better off replacing them anyway: button becomes=x-plus-one-button+1/button What we need is not a becomes= attribute (that renames an element and therefore forgoes its semantics) but rather a way to get complete control over a semantic element and tweak aspects of it. Otherwise creating such controls is prohibitively expensive and only useful if you have vast resources. I would argue that replacing is exactly the right thing to do. You are changing an element from having some basic meaning to a more specific meaning. Replacement seems natural and matches what authors do today. Examples of elements that should not be replaced but could be changed by a binding: Having a sortable binding for table; Exposing cite= on blockquote; Turning a select listing countries into a map. Great! Let's go through them: * Sortable binding for a table is really just a table subclass with some event listeners registered. * Exposing cite on blockquote sounds like something CSS should do. There's no extra behavior, and you're not really creating a new type of element. It's just extra boxes. * Turning select listing countries into a map -- composition to the rescue!: x-country-map select optionLilliput optionBlefuscu /select /x-country-map From the author's perspective, you don't actually need the select element. If you intend to show a map on cool browsers and select on the less cool ones, you are completely uninterested in having your select semantics dutifully reproduced. All you need is something that does what you need. Besides, the behavior of a map and a select are so different than you probably would scrap the former to build the latter anyway. Having some way to mint custom elements as a last resort may very well make sense too, but I think the emphasis should be on enhancing existing elements as that is less complex (for authors anyway) and more accessible. Minting new elements only seems crazy and unreasonable if you can't do it. The thing is, today's Web apps have already retreated into the mostly imperative world. Despite the angry rumors, the battle for markup has been lost. Look the source and weep: http://dev.sencha.com/deploy/touch/docs/, http://www.npr.org/webapp, and lots, and lots of others. However, harnessing the HTML parser to construct an object tree gives us a new round. You don't have to think divs and spans anymore. Once you can start viewing any functional block of your page as a custom element, you can return to using markup as composition medium. Hell, in this case fetching markup lazily becomes more attractive than JSON! And FWIW, I do not think that has to be seen as Decorator http://wiki.whatwg.org/wiki/Behavior_Attachment as for the examples I listed above I would expect the binding to be permanent. (I would also expect you could expose additional DOM members, etc.) Right. The problem with aspects/decorators is that they are essentially the October Revolution (http://en.wikipedia.org/wiki/October_Revolution): we attempt to make things better by abandoning the old ways (sub-typing, that is) that quite obviously have
Re: Custom tags over wire, was Re: HTMLElement.register--giving components tag names
Since Dimitri has already said everything I would, and better, I just want to very quickly second his point about where we are today vs. where we fear we might be: non-trivial apps have *already* given up on HTML. Suggesting that there's an un-semantic future that will be *caused* by the component model is to fight a battle that's already lost. The only question we need to answer now is: how do we repair the situation? In spending the last 9 months thinking and working through the issues Dimitri presents below, our strongest theory now is that there *is* a market for semantics, that it *does* organize around winners (e.g., Microformats), and that we're missing a mechanism for more directly allowing authors to express their intent at app construction time in ways that don't either pull them fully out of markup/html (see: Closure, GWT, etc.). Instead of imagining total anarchy, imagine a world where something like jquery-for-WebComponents comes along: a winner toolkit that a statistically significant fraction of the web uses. Once that intent is in markup and not code, it helps us set the agenda for the next round of HTML's evolution. Think of Web Components and custom elements not as (marginally) a way to defeat HTML's semantics, but as a way for developers to get back in touch with markup and a path for HTML's evolution that paves a sustainable path. The toolkits and frameworks of today are the TODO list for the current round of HTML's evolution, and Web Components give us a better, *more* semantic, lower-friction way to evolve in the future. On Fri, Sep 2, 2011 at 11:47 AM, Dimitri Glazkov dglaz...@chromium.org wrote: On Fri, Sep 2, 2011 at 2:30 AM, Anne van Kesteren ann...@opera.com wrote: On Wed, 31 Aug 2011 19:29:28 +0200, Dimitri Glazkov dglaz...@chromium.org wrote: To put it differently, you want to start with a well-known element in markup, and, through the magic of computing, this element _becomes_ your component in the DOM tree. In other words, the markup: button becomes=x-awesome-buttonWeee!!/button Becomes: x-awesome-buttonWeee!!/x-awesome-button This does not work for assistive technology. That is, you would still have to completely implement the button element from scratch, including all its semantics such as keyboard accessibility, etc. Ah, thanks Anne! I do indeed need to enumerate... Fear 6: Accessibility. Accessibility! Accessibility!? I contend that the Component Model does not make accessibility any worse. And likely the opposite. By allowing ATs to traverse into shadow subtrees, and ensuring that the shadow subtrees are well-behaving accessibility citizens, you allow authors of components to encapsulate good practices and aid in killing the re-created poorly anti-pattern. That's what Sencha, SproutCore, Dijit all try to do -- and the Component Model will enable them do this right. In fact, things like access keys or even z-index are quite hard (impossible) to get right, unless you have something like a well-functioning shadow DOM. This leaves us with the argument of replacing semantics. Since we're in business of sub-typing HTML elements, we don't necessarily need to forego their semantics: // ... var AwesomeButton = HTMLButtonElement.extend(awesomeButtonInitializerBag); Element.register('x-awesome-button', AwesomeButton); // ... should give you a thing that behaves like a button, with the awesome behavior added. In the situations where existing semantics are representative, but deficient, you are much better off replacing them anyway: button becomes=x-plus-one-button+1/button What we need is not a becomes= attribute (that renames an element and therefore forgoes its semantics) but rather a way to get complete control over a semantic element and tweak aspects of it. Otherwise creating such controls is prohibitively expensive and only useful if you have vast resources. I would argue that replacing is exactly the right thing to do. You are changing an element from having some basic meaning to a more specific meaning. Replacement seems natural and matches what authors do today. Examples of elements that should not be replaced but could be changed by a binding: Having a sortable binding for table; Exposing cite= on blockquote; Turning a select listing countries into a map. Great! Let's go through them: * Sortable binding for a table is really just a table subclass with some event listeners registered. * Exposing cite on blockquote sounds like something CSS should do. There's no extra behavior, and you're not really creating a new type of element. It's just extra boxes. * Turning select listing countries into a map -- composition to the rescue!: x-country-map select optionLilliput optionBlefuscu /select /x-country-map From the author's perspective, you don't actually need the select element. If you intend to show a map on cool browsers and select on the less cool ones, you are
Re: Custom tags over wire, was Re: HTMLElement.register--giving components tag names
On 9/2/11 12:10 PM, Alex Russell wrote: Since Dimitri has already said everything I would, and better, I just want to very quickly second his point about where we are today vs. where we fear we might be: non-trivial apps have *already* given up on HTML. Suggesting that there's an un-semantic future that will be *caused* by the component model is to fight a battle that's already lost. The only question we need to answer now is: how do we repair the situation? In spending the last 9 months thinking and working through the issues Dimitri presents below, our strongest theory now is that there *is* a market for semantics, that it *does* organize around winners (e.g., Microformats), and that we're missing a mechanism for more directly allowing authors to express their intent at app construction time in ways that don't either pull them fully out of markup/html (see: Closure, GWT, etc.). Instead of imagining total anarchy, imagine a world where something like jquery-for-WebComponents comes along: a winner toolkit that a statistically significant fraction of the web uses. Once that intent is in markup and not code, it helps us set the agenda for the next round of HTML's evolution. Alex, Dimitri: 1. I've found ARIA to be an appropriate microformat for new components. That is what it was designed for, after all. data-* works for arbitrary metadata, and aria-* for UI semantics. 2. ARIA 1.0 may not be sufficient, but I do think it's been designed to be forward compatible, and meta compatible with HTML5. I can, for instance, use: role=spreadsheet grid even though spreadsheet is not an ARIA 1.0 role; thus forward compatibility, and semantic lenience. 3. Let's look at how jquery fails to support ARIA, though it's an easy fix. Many jquery widgets have ARIA hooks in place. But what about jquery itself? $('#div').attr('role', 'button') vs $('#div').role('button'); $('#div').attr('aria-pressed','true') vs $('div').pressed(); Those later examples are what first class ARIA support would look like, in a JS framework. 4. Let's look at the button example: button becomes=x-awesome-buttonWeee!!/button Becomes: x-awesome-buttonWeee!!/x-awesome-button For the sake of ATs, that should include ARIA semantics: x-awesome-button role=button tabindex=0/x-awesome-botton Now the OS and ATs think of that as a button, in every way that button would be. The UA, though, does not; it leaves it up to the scripting environment. It'd be darn-handy if the UA would enable additional markup, such that: x-awesome-button role=button style=appearance: button would inherit default events for buttons, For instance, when a user presses down, on the button, the UA would actually set the aria-pressed property if onmousedown does not run event.preventDefault(). There's precedent for this with textarea css resize. 5. Mozilla has gone ahead and allowed input type=file to be completely embedded, receiving .click() delegates. x-awesome-button role=button onclick=this.getElementsByTagName('file')[0].click()input type=file //x-awesome-button ... This e-mail was heavy with examples, and my examples lately have been a little loose. Let me know if there is any confusion on these. -Charles
Re: Custom tags over wire, was Re: HTMLElement.register--giving components tag names
On 9/2/11 3:00 PM, Alex Russell wrote: On Fri, Sep 2, 2011 at 1:40 PM, Charles Pritchardch...@jumis.com wrote: On 9/2/11 12:10 PM, Alex Russell wrote: Since Dimitri has already said everything I would, and better, I just want to very quickly second his point about where we are today vs. where we fear we might be: non-trivial apps have *already* given up on HTML. Suggesting that there's an un-semantic future that will be *caused* by the component model is to fight a battle that's already lost. The only question we need to answer now is: how do we repair the situation? In spending the last 9 months thinking and working through the issues Dimitri presents below, our strongest theory now is that there *is* a market for semantics, that it *does* organize around winners (e.g., Microformats), and that we're missing a mechanism for more directly allowing authors to express their intent at app construction time in ways that don't either pull them fully out of markup/html (see: Closure, GWT, etc.). Instead of imagining total anarchy, imagine a world where something like jquery-for-WebComponents comes along: a winner toolkit that a statistically significant fraction of the web uses. Once that intent is in markup and not code, it helps us set the agenda for the next round of HTML's evolution. Alex, Dimitri: 1. I've found ARIA to be an appropriate microformat for new components. That is what it was designed for, after all. ARIA is how we envision components developed in this world will communicate with assistive technology. Nothing in Web Components is designed to supplant or replace it. I suggest looking at ARIA as more than a method for communicating with assistive technology. It's a means for communicating UI component states. Similarly, WCAG is a series of principles for designing usable, high quality applications. ARIA presents a set of semantic roles that don't exist in HTML, and for those, alignment with custom element implementations is outstanding. Components that express those semantics can use ARIA to help communicate what they mean, taking the burden off of the users of the components to understand and manage the role/state groups. When working with accessibility, it's super-set of HTML: img { role: 'img'; }; img[alt=] { role: 'presentation'; } Yes, I'd like to see Components express aligned semantics, such as button:aria-pressed, in the shadow DOM. It's the same method we use with the Canvas subtree. How should ATs be notified/detect that there is a shadow DOM? I'd imagine the accessibility tree simply contains the appropriate data, but for ATs using simple DOM, and getAttribute, should they now check for a .shadow attribute on elements in addition to their usual heuristics? data-* works for arbitrary metadata, and aria-* for UI semantics. Yes! And for low-complexity tasks, they're perfect. For larger, reusable components that need bundled behavior (Closure, JQuery UI, Dijit), the task of setting up and managing all of this can be made easier for users and developers of components by giving them a place to hang behavior, shadow DOM, and data model concerns from. We're certainly experimenting, with the Canvas tag and subtree. It seems like event.preventDefault() is an important hook to keep in mind. Is Web Components, in some manner, calling for a registerDefault method? 2. ARIA 1.0 may not be sufficient, but I do think it's been designed to be forward compatible, and meta compatible with HTML5. I can, for instance, use: role=spreadsheet grid even though spreadsheet is not an ARIA 1.0 role; thus forward compatibility, and semantic lenience. Nothing we're doing reduces the utility or need for ARIA. It works *great* with these component types, and to the extent that we can align them, I'm excited by how much easier it's going to be for component authors to be, allowing them to focus on concerns like a11y instead of how do I get this thing to fly in the first place? I agree, I think it'll work great, and be easier. I'm hopeful there will be lessons to apply to an ARIA 1.1 spec. ARIA 1.0 has gone through a lot of work, but it hasn't gone through the rugged real-world testing of hundreds of thousands of programmers developing custom components. Authoring a spreadsheet component in ARIA is a mixed-bag. There are great items, lots of expressiveness, but also some areas that feel lacking. The spreadsheet widget metaphor has been around a long time, but it's open-ended in ways, much like rich text editing, and so, only by authoring, do we get an idea of the vocabulary. contentEditable could be wrapped as a web component. Rich text styles have long been in accessibility interfaces. 3. Let's look at how jquery fails to support ARIA, though it's an easy fix. Many jquery widgets have ARIA hooks in place. But what about jquery itself? $('#div').attr('role', 'button') vs $('#div').role('button');
Re: Custom tags over wire, was Re: HTMLElement.register--giving components tag names
On Fri, Sep 2, 2011 at 3:58 PM, Charles Pritchard ch...@jumis.com wrote: On 9/2/11 3:00 PM, Alex Russell wrote: On Fri, Sep 2, 2011 at 1:40 PM, Charles Pritchardch...@jumis.com wrote: On 9/2/11 12:10 PM, Alex Russell wrote: Since Dimitri has already said everything I would, and better, I just want to very quickly second his point about where we are today vs. where we fear we might be: non-trivial apps have *already* given up on HTML. Suggesting that there's an un-semantic future that will be *caused* by the component model is to fight a battle that's already lost. The only question we need to answer now is: how do we repair the situation? In spending the last 9 months thinking and working through the issues Dimitri presents below, our strongest theory now is that there *is* a market for semantics, that it *does* organize around winners (e.g., Microformats), and that we're missing a mechanism for more directly allowing authors to express their intent at app construction time in ways that don't either pull them fully out of markup/html (see: Closure, GWT, etc.). Instead of imagining total anarchy, imagine a world where something like jquery-for-WebComponents comes along: a winner toolkit that a statistically significant fraction of the web uses. Once that intent is in markup and not code, it helps us set the agenda for the next round of HTML's evolution. Alex, Dimitri: 1. I've found ARIA to be an appropriate microformat for new components. That is what it was designed for, after all. ARIA is how we envision components developed in this world will communicate with assistive technology. Nothing in Web Components is designed to supplant or replace it. I suggest looking at ARIA as more than a method for communicating with assistive technology. It's a means for communicating UI component states. And Web Components is designed explicitly to work with it. Similarly, WCAG is a series of principles for designing usable, high quality applications. ARIA presents a set of semantic roles that don't exist in HTML, and for those, alignment with custom element implementations is outstanding. Components that express those semantics can use ARIA to help communicate what they mean, taking the burden off of the users of the components to understand and manage the role/state groups. When working with accessibility, it's super-set of HTML: img { role: 'img'; }; img[alt=] { role: 'presentation'; } Yes, I'd like to see Components express aligned semantics, such as button:aria-pressed, in the shadow DOM. It's the same method we use with the Canvas subtree. Pseudo-classes as a state mechanism need a lot more examination, AFAICT. It's a non-extensible vocabulary, it doesn't appear to be scriptable, and as a result, we haven't been able to use them to handle things like states for animations (which should be transitions between states in a node-graph). +shans How should ATs be notified/detect that there is a shadow DOM? Focus works as it always has. It can move inside the shadow. I'd imagine the accessibility tree simply contains the appropriate data, but for ATs using simple DOM, and getAttribute, should they now check for a .shadow attribute on elements in addition to their usual heuristics? That'll work for components with a public shadow, which I think will be most of them. Components can also note state by setting role/state directly on the outer component. data-* works for arbitrary metadata, and aria-* for UI semantics. Yes! And for low-complexity tasks, they're perfect. For larger, reusable components that need bundled behavior (Closure, JQuery UI, Dijit), the task of setting up and managing all of this can be made easier for users and developers of components by giving them a place to hang behavior, shadow DOM, and data model concerns from. We're certainly experimenting, with the Canvas tag and subtree. The component approach turns this around, by letting you construct a logical tree that might have canvas elements in the shadow, meaning you don't need a hidden tree per sae. It seems like event.preventDefault() is an important hook to keep in mind. Is Web Components, in some manner, calling for a registerDefault method? 2. ARIA 1.0 may not be sufficient, but I do think it's been designed to be forward compatible, and meta compatible with HTML5. I can, for instance, use: role=spreadsheet grid even though spreadsheet is not an ARIA 1.0 role; thus forward compatibility, and semantic lenience. Nothing we're doing reduces the utility or need for ARIA. It works *great* with these component types, and to the extent that we can align them, I'm excited by how much easier it's going to be for component authors to be, allowing them to focus on concerns like a11y instead of how do I get this thing to fly in the first place? I agree, I think it'll work great, and be easier. I'm hopeful there will be lessons to apply to
Custom tags over wire, was Re: HTMLElement.register--giving components tag names
Splitting off to its own thread, because this deserves a good discussion. On Wed, Aug 31, 2011 at 12:00 AM, Anne van Kesteren ann...@opera.com wrote: On Wed, 31 Aug 2011 07:33:16 +0200, Dominic Cooney domin...@chromium.org wrote: Thanks for reading this far! These proposals aren't formal or detailed. I would love to get feedback as I try to nail down some specifics. The basic problem with this is that you get proprietary markup going over the wire: http://ln.hixie.ch/?start=1064828134count=1 FWIW, I am in total agreement with this post. If the author requires a UA to have a proprietary parser that has its own, separate means of producing a valid DOM tree, you are so screwed. Having said that, I am not sure what the correct alternative would be. XBL (as Ian envisioned it anyway) was meant to enhance non-proprietary markup, not to let authors create novel constructs. Now you cannot stop authors from exploring novel constructs of course, but whether we should explicitly endorse it is another matter. Yes, indeed. We are at the crossroads. The Web needs element behavior attachment (http://wiki.whatwg.org/wiki/Behavior_Attachment) and the ability to define new types elements, yet we are really afraid of following through with that. But... are these fears rational? Let's examine the them in detail. Fear 1: Fallback bogeyman cometh. x-accordion/x-accordion is no worse than div class=accordion/div in every mechanical sense. In the absence of definition for x-accordion (or Component Model plumbing), both mean the same thing, both can be styled in the same way. One is HTMLUnknownElement, the other is HTMLDivElement, and their API surface is identical. So... no fallback problems. Fear 2: Custom tags are confusing. The x-accordion clearly identifies the type of the behavior expected from the element, and conveys element behavior attachment nicely. On the other hand, div class=accordion implies decorator behavior attachement, e.g. that removing the class value (and thus turning it back into a vanilla div) is perfectly ok, which by the way, is probably _not_ what the author of the Accordion component expects in real life. I mean, you can _make_ the author expect that, but that seems like cruel and unusual punishment. In other words -- it's quite the opposite. Custom tags are more _clear_. In fact, they are as close as _saying_what_you_mean_ as it gets. Fear 3: Custom tags have no meaning. Well, friends -- this train had left the station a long time ago. Alex Russell joked once that you already totally can add custom tags in HTML -- as long as you're Hixie. As HTML spec grows new tags, their meaning is only captured in a written document that's meaningless to the UAs that were built a priori. If anything, the Component Model provides an explicit path _learn_ about the need for new elements in the spec. Just grep the Web for x- and look at the common names. In all seriousness, I expect HTML to grow new tags, and I think it will add a great many new things that will make authors' life easier. I don't expect HTML to grow every element ever needed -- the long tail is far too massive. Addressing this long tail in a local (meaningful in your document), organized fashion is what the Component Model does. Fear 4: Custom tags will clash with newly invented HTML tags. Well, here, FTFY -- the Component Model explicitly requires prefixing all elements with x-. Fear 5: The Author will forego well-known semantics in lieu of their awesome custom tags. Indeed they will. I yell regularly at authors (like that old man from his front porch) for using divs to build buttons and links. Those anti-patterns suck. We should not make it worse. If anything, we have an opportunity to provide a progressive enhancement vehicle, whereby authors can use components as a way for hiding implementation specifics and leaving out only the commonly established semantics in markup. Soo.. how would something like this work? We need a way to let the authors specify a well-known element to describe underlying semantics of their component, coincidentally providing a proper fallback element for non-Component Model-aware UAs. It's similar to ARIA, but the machinery is about populating the DOM tree with the most-specific thing, while keeping markup most-generic. To put it differently, you want to start with a well-known element in markup, and, through the magic of computing, this element _becomes_ your component in the DOM tree. In other words, the markup: button becomes=x-awesome-buttonWeee!!/button Becomes: x-awesome-buttonWeee!!/x-awesome-button As soon as: 1) the definition of x-awesome-button is registered and; 2) the element is in the DOM tree. I will write up the exact algorithm in a wiki shortly. I hope this addressed our worst fears and some. I thereby declare that we should stop being afraid and liberate ourselves from the burden of custom tag anxiety. Long live custom tags! :DG
Re: Custom tags over wire, was Re: HTMLElement.register--giving components tag names
On Wed, Aug 31, 2011 at 10:29 AM, Dimitri Glazkov dglaz...@chromium.org wrote: I will write up the exact algorithm in a wiki shortly. Here it is: http://wiki.whatwg.org/wiki/Component_Model_Progressive_Enhancement :DG
Re: HTMLElement.register--giving components tag names
On Tue, Aug 30, 2011 at 10:33 PM, Dominic Cooney domin...@chromium.org wrote: Components (see http://wiki.whatwg.org/wiki/Component_Model_Use_Cases for examples of what I mean) need to present an API to script. For example, a contacts component might want to expose a refresh() method that pulls new contacts from the server. Components also need to hook up internal behavior implemented in script; a split pane might need to hook up a mouse listener on its splitter before it can really behave like a split pane. In script widget libraries today (YUI, Closure, etc.) this is easy when the widget has been created from script: when the author calls the constructor/factory method/whatever the widget can create DOM, hook up event listeners, set up the prototype chain however it wants, etc. However things get really murky when authors start to use markup, because then the parser is creating elements that are at best only minimally functional until they're enhanced. So today widget implementations need to handle enhancing an existing element; frameworks need to detect these unenhanced elements and invoke something to enhance them; and authors needs to debug this unholy mess when an unenhanced element escapes and their page breaks. Wouldn't it be nice if the browser made this problem go away? I think HTML itself shows us how life could be better: Consider the HTML video element. It looks like a subtype of HTML element, with all of the methods and attributes a HTML element has (via the prototype chain), and adds methods and attributes specific for doing video. When you do document.createElement('video') you get back an object that is ready to use. There's no step to enhance it. When you do p.innerHTML = video src=… controls=true, you get a video player. There's no flash of unstyled content. If you clone it and insert the copy into the DOM again, all of the playback controls are still wired up and responsive. I'm proposing we add something that lets script extend the set of tag names, so there is less of a bright line between elements defined in the HTML spec and elements defined in script. Something like: HTMLElement.register('x-contacts', ContactPicker); The first argument is an element name. The second is a constructor function, whose prototype property points to an object which introduces the API for contacts (eg a refresh method) and is wired up to HTMLElement.prototype. When the parser encounters x-contacts/, it creates an object by calling the ContactPicker function as a constructor. The constructor can wire up any internal state it wants, like creating DOM and attaching event listeners. When a script later retrieves the element, say with document.querySelector('x-contacts'), the object created earlier with ContactPicker is what it gets back. Since the constructor is run as the parser is creating the element, there's no time when the unenhanced element is available to script. My proposal pretty much ends here: The component itself is just implemented with script, DOM and CSS. There are no special hooks for participating in layout (just use DOM and CSS) or form submission (just create form controls using DOM) or security (same origin policy still applies) or networking (just use WebSockets or XHR) or anything else. There is no magic, other than teaching the browser about the new tag name. I'm suggesting that all registered tag names have to start with x-. This is to give component authors a place to build without worrying about conflicting with future HTML specs; the HTML spec won't define elements with names starting with x-. (Component authors may chose x- names that conflict with each other, though.) People working on the HTML spec can study what kinds of components are popular in the wild and consolidate the best ideas into new HTML elements. Page authors can decide if and when to move their pages from their bespoke x- components to the HTML alternatives, which should be better. Pages that have to work in older browsers can use fallback content. (This is exactly what the HTML spec advises authors to do with the video element, incidentally.) In newer browsers the component script can remove or hide the fallback content. There's the question of what to do when there is a call to HTMLElement.register('x-contacts', …) at some point after an x-contact element has been parsed. We have to do something that makes sense for async scripts. I think the solution is to replace the element, and the recent discussion on this list about renameNode is interesting and relevant. One practical issue with this proposal is that creating a subtype of HTMLElement in script (ie defining the ContactPicker function in the above example) is hard/impossible. A couple of the problems are: - Defining a subtypes in JavaScript is hard to begin with: You need to create a function, and maybe set its object prototype up; you need to create a prototype
Re: HTMLElement.register--giving components tag names
On Tue, Aug 30, 2011 at 10:33 PM, Dominic Cooney domin...@chromium.org wrote: Components (see http://wiki.whatwg.org/wiki/Component_Model_Use_Cases for examples of what I mean) need to present an API to script. For example, a contacts component might want to expose a refresh() method that pulls new contacts from the server. Components also need to hook up internal behavior implemented in script; a split pane might need to hook up a mouse listener on its splitter before it can really behave like a split pane. In script widget libraries today (YUI, Closure, etc.) this is easy when the widget has been created from script: when the author calls the constructor/factory method/whatever the widget can create DOM, hook up event listeners, set up the prototype chain however it wants, etc. However things get really murky when authors start to use markup, because then the parser is creating elements that are at best only minimally functional until they're enhanced. So today widget implementations need to handle enhancing an existing element; frameworks need to detect these unenhanced elements and invoke something to enhance them; and authors needs to debug this unholy mess when an unenhanced element escapes and their page breaks. Wouldn't it be nice if the browser made this problem go away? I think HTML itself shows us how life could be better: Consider the HTML video element. It looks like a subtype of HTML element, with all of the methods and attributes a HTML element has (via the prototype chain), and adds methods and attributes specific for doing video. When you do document.createElement('video') you get back an object that is ready to use. There's no step to enhance it. When you do p.innerHTML = video src=… controls=true, you get a video player. There's no flash of unstyled content. If you clone it and insert the copy into the DOM again, all of the playback controls are still wired up and responsive. I'm proposing we add something that lets script extend the set of tag names, so there is less of a bright line between elements defined in the HTML spec and elements defined in script. Something like: HTMLElement.register('x-contacts', ContactPicker); The first argument is an element name. The second is a constructor function, whose prototype property points to an object which introduces the API for contacts (eg a refresh method) and is wired up to HTMLElement.prototype. When the parser encounters x-contacts/, it creates an object by calling the ContactPicker function as a constructor. The constructor can wire up any internal state it wants, like creating DOM and attaching event listeners. When a script later retrieves the element, say with document.querySelector('x-contacts'), the object created earlier with ContactPicker is what it gets back. Since the constructor is run as the parser is creating the element, there's no time when the unenhanced element is available to script. My proposal pretty much ends here: The component itself is just implemented with script, DOM and CSS. There are no special hooks for participating in layout (just use DOM and CSS) or form submission (just create form controls using DOM) or security (same origin policy still applies) or networking (just use WebSockets or XHR) or anything else. There is no magic, other than teaching the browser about the new tag name. I'm suggesting that all registered tag names have to start with x-. This is to give component authors a place to build without worrying about conflicting with future HTML specs; the HTML spec won't define elements with names starting with x-. (Component authors may chose x- names that conflict with each other, though.) People working on the HTML spec can study what kinds of components are popular in the wild and consolidate the best ideas into new HTML elements. Page authors can decide if and when to move their pages from their bespoke x- components to the HTML alternatives, which should be better. Pages that have to work in older browsers can use fallback content. (This is exactly what the HTML spec advises authors to do with the video element, incidentally.) In newer browsers the component script can remove or hide the fallback content. There's the question of what to do when there is a call to HTMLElement.register('x-contacts', …) at some point after an x-contact element has been parsed. We have to do something that makes sense for async scripts. I think the solution is to replace the element, and the recent discussion on this list about renameNode is interesting and relevant. One practical issue with this proposal is that creating a subtype of HTMLElement in script (ie defining the ContactPicker function in the above example) is hard/impossible. A couple of the problems are: - Defining a subtypes in JavaScript is hard to begin with: You need to create a function, and maybe set its object prototype up; you need to create a prototype
Re: HTMLElement.register--giving components tag names
On Wed, Aug 31, 2011 at 1:38 PM, Erik Arvidsson a...@chromium.org wrote: On Tue, Aug 30, 2011 at 22:33, Dominic Cooney domin...@chromium.org wrote: You will notice that this says nothing about how prototypes are wired up. It should. Maybe the argument to extend should have an optional second field, proto, that specifies the new methods/getters/setters that ContactPicker's prototype should introduce. This is not a general subtyping mechanism! It is only designed for setting up subtypes of HTMLElement for use with register. When ECMAScript and the DOM bindings are sufficiently aligned, HTMLElement.register can be opened up to accept constructors defined using ordinary ECMAScript mechanisms for subtyping DOM interfaces. Scripts can continue to use extend (it is pretty succinct) or constructors set up their own way. Providing a prototype is important. So here’s a refinement. I will add this to the wiki: interface ExtensibleElement { object extend(ElementRegisterOptions options) raises (DOMException); } HTMLElement implements ExtensibleElement; … [Callback] interface ExtensionElementInitializer { void init(HTMLElement element); // should this have a return value, to allow replacement? } dictionary ElementRegisterOptions { ExtensionElementInitializer init; object? proto; // ECMAScript-ism? } Author: If options.proto is specified, HTMLElement.prototype.isPrototypeOf(options.proto) should be true, and options.proto should not be a platform object, nor have a platform object on the prototype chain. UA: If options.proto is specified, and HTMLElement.prototype.isPrototypeOf(options.proto) is false, or options.proto is a platform object, or options.proto has a platform object on the prototype chain, register may throw a TYPE_ERROR. If options.proto is not specified, the resulting constructor’s prototype property will be HTMLElement.prototype or HTMLElement.prototype.isPrototypeOf(resulting prototype) will be true. This object might have been synthesized by the UA. UA: When the constructor is invoked, (same conditions on the proto as before) the constructor may throw a TYPE_ERROR. For example I can imagine UI toolkits providing their own base class that all the custom elements extend. That is most straightforward when you have FancyWidgetBase : HTMLElement FancyButton : FancyWidgetBase It does not work so well when you want FancyButton to be a HTMLButtonElement. Then you need a factory of FancyWidgetBases that hook one up to HTMLButtonElement, HTMLDivElement, etc. Also, it seems essential to allow extending other things than just HTMLElement. Wearing my author hat, that sounds appealing. Browser internals may do things like switch on an element’s tag name. It would need to start consulting the table of extensions when it did that in order to realize that x-fancy-button is a button element.
Re: HTMLElement.register--giving components tag names
Referencing a note dated 2003 may not sound strong any more - web-based applications (or to be more specific - their UI) have evolved significantly since the date. Today limiting developers to an extremely low level markup API, such as SVG or HTML only leads to huge, hardly manageable JavaScript UI code in any more or less complex solution. The need in custom markup that facilitates higher level UI technologies abstractions is here. (Meaning - has been here. Since, say 2003) As for searching engines not capable of indexing applications - this is in no way a concern, I bet neither GMail, nor AdSense apps etc. have been successfully indexed so far. Exposing data or electronic documents is something else. Sergey/ On 31 August 2011 09:00, Anne van Kesteren ann...@opera.com wrote: On Wed, 31 Aug 2011 07:33:16 +0200, Dominic Cooney domin...@chromium.org wrote: Thanks for reading this far! These proposals aren't formal or detailed. I would love to get feedback as I try to nail down some specifics. The basic problem with this is that you get proprietary markup going over the wire: http://ln.hixie.ch/?start=**1064828134count=1http://ln.hixie.ch/?start=1064828134count=1 Having said that, I am not sure what the correct alternative would be. XBL (as Ian envisioned it anyway) was meant to enhance non-proprietary markup, not to let authors create novel constructs. Now you cannot stop authors from exploring novel constructs of course, but whether we should explicitly endorse it is another matter. -- Anne van Kesteren http://annevankesteren.nl/