In order to make relative links work, the documentās base URL is set to the notebook URL, such as:
https://beta.observablehq.com/@mbostock/19-circle
Unfortunately, in some browsers this affects the interpretation of SVG IRIs, the identifiers that are used within SVGs to refer to things like gradients, patterns, and reusable content. In these browsers, relative IRIs (such as #foo) donāt work on a page with a different document base URL because the SVG itself is interpreted as being on the original URL, while the IRI is interpreted as relative to the base URL.
Even if this browser inconsistency did not exist, the other problem (fundamental to the design of SVG) is that ids are global to the page, and thus when you import SVG content from another notebook, you can easily get namespace collisions.
This is why DOM.uid is in Observableās standard library.
See this notebook for an example:
You can also use window.location to convert a relative IRI to an absolute IRI, but DOM.uid is still preferred because it will avoid namespace collisions when importing.
Hi @mbostock, thanks for your elaborative reply. Iāve run into this problem earlier (svg defs of gradients, to be used later on) using DOM.uid to create a universal and unique ID.
Now the next challenge is to elegantly and automatically tweak the embedded (and imported, foreign) SVG to inject and use these IDs. Any tip for that, too?
NEVER MIND! I fixed it: A bit of a hack, but I replaced all relevant id="_string_" in id="${_string_.id}", created corresponding const _string_ = DOM.uid("_string_"), and referred to it as ${_string_.toString()}.