flow
flow copied to clipboard
When using the Element API I want to be able to create SVG elements
When creating components with the Element API I want to be able to create simple SVG elements, so I do not have to include other files and I can keep my source tree clean.
The Element API enforces attribute names to be lower case, but with SVG elements this may cause trouble since browsers are picky on SVG attribute case, e.g. Chrome won't render an <svg>
with attribute viewBox
written all lowercase.
This prevents creating SVG elements with the Element API, while a developer would expect to be able to do so in HTML5 documents e.g. as shown in MDN SVG element reference.
Previously discussed in #1097. Not sure if the namespace is still an issue also
This SO answer about HTML5 is very enlightening: https://stackoverflow.com/a/23322429/1006669
HTML is also namespace aware, but namespaces are assigned implicitly. HTML is converted to a DOM using an HTML parser, which knows which elements go in which namespace. That is, it knows that
<div>
goes in the http://www.w3.org/1999/xhtml namespace and that<svg>
goes in the http://www.w3.org/2000/svg namespace.
Plus:
The HTML parser knows about HTML elements, SVG elements, and MathML elements and no others. There is no option to use elements from other namespaces, neither implicitly nor explicitly. That is, xmlns attributes have no effect.
So it seems like the Element API does not need any special handling of namespaces, it should just respect the right case for some SVG attributes and tags (MathML already has all lower-case attributes/tags).
This is a comprehensive index of all SVG attributes and elements where they may appear:
https://www.w3.org/TR/SVG/attindex.html
As a workaround, you could try creating a regular element as a wrapper, and then do element.setProperty("innerHTML", svgString);
Any update on this?
As far as i understand the problem its caused by the way nodes and attributes are created on the client side (JavaScript):
document.createElement("svg"); is being called when we add a new Element to the UI. This creates an
If the element would be created by calling document.createElementNS("http://www.w3.org/2000/svg", "svg"); the Tag would look the same in DevTools but its correctly listed as a "SVGElement" and it gets rendered.
Same thing about adding attributes: setAttribute(...); puts an attribute in lowercase, as HTML is not case-sensitive while setAtributeNS(...); is case-sensitive.
I got the same problem. I thought it would be easy to just create a svg with elements. Someone found any hack/solution/workaround for this problem?
Thank you.
Someone found any hack/solution/workaround for this problem?
https://github.com/vaadin/flow/issues/2842#issuecomment-341652190
Still looking for a solution :)
Any news on this? I need to render inline SVGs too.
For me it seems that this is related to: #4644
Setting the outerHTML-Attribute "as it is actually" via javascript renders the svg correctly.
svg.getElement().executeJs("this.outerHTML= $0", svg.getElement().getOuterHTML());
Any news? I would be interested as well.
There has been quite many requests for SVG support, but this is not currently very high on our TODO list. I'd love to learn more about the needs so I could prioritise this properly.
- What kind of use cases do you have for SVG. Static drawings or something dynamic with e.g. click listeners?
- What kind of workarounds have you used? Custom client side componts? Plain JS from server-side? Assigning inner/outerHTML?
A quite straight forward way is to create the SVG using LitElement
, create a Java class for it and pass dynamic data through properties, as done e.g. in here
- https://github.com/Artur-/dynamic-svg/blob/master/frontend/fill-indicator.js
- https://github.com/Artur-/dynamic-svg/blob/master/src/main/java/com/example/app/FillIndicator.java
OK I just lost almost a day over this bug. I was using the Html
class to create a few simple <svg>
elements and I thought there was something wrong with the CSS. If this is not going to be resolved anytime soon, please at least indicate in the Html
class constructor javadoc that it can't be used to generate <svg>
elements.
We could even go one step further. We're already parsing the HTML on the server so we could explicitly look for usage of <svg>
and throw an exception saying that it won't work.
@Legioth I really have not the insight and knowledge about this, but could we not even find someone to actually make it work :)
We could even go one step further. We're already parsing the HTML on the server so we could explicitly look for usage of
<svg>
and throw an exception saying that it won't work.
Well maybe it's better just to support it (2022 already), rather than throw an exception
I created a draft PR to add trivial SVG support to Html, but only read-only: https://github.com/vaadin/flow/pull/15539. For that use case it might be though better to create a separate Svg component.
A proper support via Element API (as I think @heruan originally ment in this issue) would be great as well, would help to create some more advanced components.
Also drafted the Svg component idea: https://github.com/vaadin/flow/pull/15540
Status update: The master branch now contains Svg component to display images (and to allow styling them with css), but Element API still don't support SVG.
There is a start by @Legioth to fix this actual issue, but we'd still need to get rid of attribute name lowercasing (or some other workaround if we want to make the framework more complicated than would be required ;-) ): https://github.com/vaadin/flow/commit/9472e95710ed3741834198e15732113d1408c825