Comments (7)
As URL can have the protocol, selectors should as well.
They already do, as I discuss in the first post. 🙃 The syntax discussion here was about what subset of relative selectors to support, not to define relative selectors.
from html.
I can share some pains, design decisions and experiences we had with relative references over the years. This is from my work with Unpoly, an HTML extension where links update fragments instead of full pages. For this we needed a way to reliably target elements.
- We use CSS selectors to target fragments. We haven't had a need for something more powerful since
:has()
. - We also use a pseudo
:origin
to refer to the current element (:scope
wasn't a thing when we named this). - When you show content in overlays ("dialog", "modal"), the risk of references matching the wrong element increases. In Unpoly CSS selectors never match an element in another layer unless the other explicitly allows this with an
[up-layer=any]
attribute. I feel this is already an issue in HTML since<dialog>
was introduced. - A sharp edge with
<label for="some-id">
is that clicking will blindly focus the first element with thatid
. Unintuitvely this may match elements in another form, or in another layer. We patch thelabel
/input
matching so elements within the same form are preferred. - A very common use case is to match within an ancestor of the current element. E.g. the form of an input, or another input within the same form. You can do this explicitly
:has()
and:origin
, e.g.form:has(:origin) .other-input
. - For convenience we also match ancestor elements preferrably. E.g.
form
would first look for the closest ancestorform
and only then look through the rest of the page. Alsoform .other-input
would first try to find.other-input
within the same form, before looking at other forms.
We have not needed introduce new syntax aside from :origin
and :has()
(before browser support was there). However, a similiar library htmx uses custom selector synxtax like closest .foo
.
from html.
The scope perhaps can be less demanded when the root element for web components become a thing beyond CSS styling. But even with that, the relative selector is highly needed.
The selectors language perhaps need to be addressed in another proposal. As URL can have the protocol, selectors should as well.
CSS and XPath are natively supported by most of browser. Others or extensions of base ones would be polifilled.
from html.
This is another area where it makes it hard to reason about server side template partials like I discussed re hN
tags in #5033 (comment)
Another problem with id
other than uniqueness is that it does way too much.
I would like something like this sketch:
A refscope
tag (or maybe it's an attribute) defines a new scope. :root
implicitly defines a root scope.
Elements have a ref
attr to use instead of id
. Unlike id
it only defines a name and that name is local to the current scope. (If there are multiple identically named refs, then which one wins should be defined in the standard and browsers should print a warning in the debug console.)
If something is referred to by name, the refs in the current scope are searched first. If there's no match, check the parent scope; repeating as necessary until reaching the root scope. If there's no match after all that, check for a matching id
.
A tag could have both a ref
and id
and that may be confusing and certainly not recommended but everything works out.
from html.
The MathML 4 effort has some overlapping interest in improved DX for referencing. Exactly due to the difficulties of managing global ids, we have tentatively introduced a new arg
attribute to anchor referencing in MathML Intent, targeting the feature of accessible navigation of math expressions:
https://w3c.github.io/mathml/spec.html#intent_reference
Simple example:
<msup intent="power($base,$exp)">
<mi arg="base">x</mi>
<mi arg="exp">n</mi>
</msup>
We have had the constraint of keeping the traversal algorithm as simple as possible, which has so far kept us from introducing relative selectors (sibling, ancestor). Nevertheless, MathML has viable use cases where relative selectors are quite natural, such as accessible walks through tabular diagrams (realized via <mtable>
).
The traversal algorithm for intent
/arg
referencing is scoped to the current subtree (references can only point to descendant nodes). It also has an additional stopping condition at nodes carrying the intent
or arg
attributes, to allow stacking of multiple math notations.
As we have multi-format content (such as scientific diagrams via SVG+MathML, as well as block equations mixed with text), it would be a significant boost to DX if we could share a uniform referencing scheme.
from html.
Feedback
Many HTML attributes need to reference one or more HTML elements in the document
It may be worth distinguishing the problems describing 1-to-1 relationships with those describing 1-to-N. For example, ids are not used for <input type="radio">
but are, unfortunately, required for things like aria-controls
.
Potential to solve more than ergonomics
I suggest this be promoted to a core goal of the proposal. This is a bit spicy but arguably the current lack of a way to associate elements across scopes violates platform design principles.
Being able to link to elements in a way that is relative to the element the attribute is specified on would solve all of these issues, and make writing ARIA much more pleasant.
I think the problem isn't clearly enough defined to determine if this is true. In particular, the id based system is independent of document structure, and most of the ideas here for a relative system depend on it. That just seems like a trade off that may be better or worse for the various different use cases.
Proposed solutions
The various options here are a little hard to understand. It'd be great to add some illustrating examples.
Another problem with id other than uniqueness is that it does way too much.
Totally agree, and this may even be the core problem to solve.
Thinking Aloud...
- Naming things is hard, but uniquely naming things can be really problematic since it requires global knowledge. Where this isn't necessary, it shouldn't be required. This is already the case for
<input type="radio" name="a">
since these are form scoped. - If the tree is used for scoping, explicitly using a scoping element may be worth it for clarity.
- There are currently often special attributes for one side of the equation only, e.g.
for
,popovertarget
,invokertarget
. Perhaps the other side should have them as well: e.g.popoverid
, etc. - Shadow DOM is an existing DOM scoping mechanism, can it be used as part of the solution here? If not, what abilities might it need to gain to be useful for this?
- At least for loose relationships that aren't exclusive, not claiming a general attribute value like
id
orname
is valuable since it makes the naming easier, e.g.refs="popoverA invokerB"
from html.
I just added another proposed idea to the first post:
3. What if we could fix this without any new syntax?
This is a stretch, but might be worth exploring.
name
is an existing attribute that identifies an element similarly to an id, but does not have the restriction of uniqueness.The algorithm for resolving references could be redefined as:
- First, look for an element with that
id
. If found, return that.- Let scopingRoot = referencing element
- While scopingRoot != document
- Look for an element with a
name
equal to the identifier provided inside scopingRoot.- If found, return it.
- Otherwise, let scopingRoot = parent of scopingRoot
I wonder how web-compatible something like that would be. Since it would only make a difference if the reference is broken to begin with, maybe it's not too unrealistic?
Thanks for the thoughtful response @sorvell. Some replies:
Many HTML attributes need to reference one or more HTML elements in the document
It may be worth distinguishing the problems describing 1-to-1 relationships with those describing 1-to-N. For example, ids are not used for
<input type="radio">
but are, unfortunately, required for things likearia-controls
.
Interesting. What do you think are the differences?
Potential to solve more than ergonomics
I suggest this be promoted to a core goal of the proposal. This is a bit spicy but arguably the current lack of a way to associate elements across scopes violates platform design principles.
As an editor of the document you are referencing, I have no idea how that principle relates to this problem. 😁
That said, I'd be fine with making that a core goal of the proposal, though I'm not sure how that will materially affect the odds of it moving forwards.
Being able to link to elements in a way that is relative to the element the attribute is specified on would solve all of these issues, and make writing ARIA much more pleasant.
I think the problem isn't clearly enough defined to determine if this is true. In particular, the id based system is independent of document structure, and most of the ideas here for a relative system depend on it. That just seems like a trade off that may be better or worse for the various different use cases.
Why is it a goal to have a referencing system that is independent of document structure? Document structure is not created in a vacuum, it typically reflects hierarchical relationships (and when it doesn't, that's a failing of some web platform technology — e.g. when authors have to put elements directly inside <body>
to make sure they're on top).
Also, the id-based system is not going away. That wouldn't be web compatible. Any relative referencing system is in addition to it.
Proposed solutions
The various options here are a little hard to understand. It'd be great to add some illustrating examples.
Agreed. I added a few examples, does this help? I could add more if you point me to specific sections that are still unclear.
- Naming things is hard, but uniquely naming things can be really problematic since it requires global knowledge.
+1000
Where this isn't necessary, it shouldn't be required. This is already the case for
<input type="radio" name="a">
since these are form scoped.
- There are currently often special attributes for one side of the equation only, e.g.
for
,popovertarget
,invokertarget
. Perhaps the other side should have them as well: e.g.popoverid
, etc.
Naming things is hard so let's add more naming tasks? 😁
What are some use cases where you may want to have a different name for e.g. popover use cases and a different one for e.g. forms?
- If the tree is used for scoping, explicitly using a scoping element may be worth it for clarity.
Unless any ancestor container could potentially be the scope, and proximity determines where to look, see new option 3.
- Shadow DOM is an existing DOM scoping mechanism, can it be used as part of the solution here? If not, what abilities might it need to gain to be useful for this?
Shadow DOM is a very heavyweight scoping mechanism that does too much. Nobody would switch to Shadow DOM simply to use relative references, as the friction involved in that far, far outweighs the friction of assigning unique ids.
from html.
Related Issues (20)
- Structured serialization does not allow [[PrivateElements]] or any other ES-internal internal slots HOT 2
- Improving Enumerated Attributes in the HTML Standard HOT 1
- Add AbortSignal for popover.showPopover() for initialize internal CloseWatcher HOT 7
- DOMString and USVString are not linked in IDL
- Should clicking a label contained in a button with popovertarget toggle the popover?
- TC39 AsyncContext Integration HOT 1
- fragment parsing algorithm steps take DocumentFragment but it's never used HOT 1
- Should popovertarget work on a reset button / input in a form? HOT 4
- should default reset/submit button text and default summary text use node's language rather than being locale-specific? HOT 1
- move style changes for opening/closing details into UA sheet rather than being style attribute manipulation
- Upcoming WHATNOT meeting on 7/4/2024 HOT 1
- Add an imperative way to set popover invoker relationships HOT 3
- A way to declare ties in ordered lists
- offsetParent, offsetLeft & offsetTop should be on Element or Node instead of HTMLElement HOT 1
- When should use of `currentcolor` inside a drop-shadow filter be resolved when used with canvas. HOT 2
- structuredClone should not throw for Arguments exotic objects HOT 5
- Show popover 11.5 ignores throwExceptions
- Should dialog removal steps unset is modal flag? HOT 2
- Focusability of `<dialog>` itself HOT 3
- Elements with invalid filters HOT 2
Recommend Projects
-
React
A declarative, efficient, and flexible JavaScript library for building user interfaces.
-
Vue.js
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
-
Typescript
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
-
TensorFlow
An Open Source Machine Learning Framework for Everyone
-
Django
The Web framework for perfectionists with deadlines.
-
Laravel
A PHP framework for web artisans
-
D3
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
-
Recommend Topics
-
javascript
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
-
web
Some thing interesting about web. New door for the world.
-
server
A server is a program made to process requests and deliver data to clients.
-
Machine learning
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
-
Visualization
Some thing interesting about visualization, use data art
-
Game
Some thing interesting about game, make everyone happy.
Recommend Org
-
Facebook
We are working to build community through open source technology. NB: members must have two-factor auth.
-
Microsoft
Open source projects and samples from Microsoft.
-
Google
Google ❤️ Open Source for everyone.
-
Alibaba
Alibaba Open Source for everyone
-
D3
Data-Driven Documents codes.
-
Tencent
China tencent open source team.
from html.