SVG

Editable SVG text

HTML5 has introduced contenteditable attribute. This attribute specifies whether the content of an element is editable or not. How to make svg text editable? To put html elements in an svg element, we need to use <foreignObject>. Within that object we can add any html element, for example div that has attribute contenteditable. The problem is that we want svg text to be editable, and not div. Solution is to add svg elements inside contenteditable div. When the contenteditable attribute is not set on an element, the element will inherit it from its parent. svg will be converted into html in render-time and inherit the contenteditable attribute from parent div. The last trick to make this work is to set the same width and height to foreignObject and to svg object that need to be editable. Except these steps, it is also necessary to check if the solution is working fine in all targeted browsers , because browser’s support for contenteditable is different in different browsers which can cause strange behaviour of svg.

SVG text align browser support

I had a task to build an online editor for creating graphic content, like visit cards. I chose to work with svg. All svg elements (e.g. line, rectangle, circle etc.) are positioned in a parent component with x and y attributes (like in a coordinate system). I wanted to have a text element with a rectangle around it which indicates that the text is in edit mode. In order to position the text inside the rectangle, I had to calculate x and y values. The problem was that the point that is taken to position the text is at the beginning of a text (before first letter) and at the baseline of the text. What I wanted to have is that this point is exactly in the middle of text (vertically and horizontally). I adjusted the point horizontally, but the problem was adjusting it vertically. I used svg attribute alignment-baseline=“middle” and it worked in Chrome, but when I opened the svg in some other browser, it acted different. The reason for that was that some svg attributes are not supported in all browsers. I searched for another solution and I found another attribute, dominant-baseline=“central”. There is a lot more examples of poorly support for svg attributes in different browsers. My recommendation is to test the svg code as soon as it is done in all targeted browsers, because later it can be hard to find a solution for a lot of bugs that are mutually dependent.

Use icon system with svg sprites

It is possible to use inline SVG elements with special "\use\" tag. First of all, we assume that a collection of items is represented as a .svg collection (it is possible to extract and convert files from a font file to svg using online converters). There are utilities that can help combine all svg files into a single file, e.g. https://github.com/FWeinb/grunt-svgstore.

Elements inside svg can be referenced as normal DOM elements, e.g. by using their id. There are then two ways to add a single element (icon) into web page:
1) Reference in the same document:
\svg\
\use xlink:href="#icon-1"\\/use\
\/svg\

2) Reference from external document
\svg\
\use xlink:href="sprite.svg#icon-1"\\/use\
\/svg\

In this example #icon-1 - is a unique identifier inside svg document.
Further reading: https://css-tricks.com/svg-sprites-use-better-icon-fonts/

Cross-window messaging

Web pages often consist of multiple frames that coexist on a single visual page. A good example are advertisements, which are semantically not part of the content of the actual page and technically separated into an own frame. The consequence of this separation is that such ads have their own context and cannot access the context of the main web page. This is a necessary security measure, since otherwise ads would be able to spy on the user as he interacts with the web application. Sometimes however, it is necessary to split a single web application into multiple frames for technical reasons even if they belong together from a semantic point of view. Such an example would be a SVG graphic nested in its own <em>iframe</em> within a web application. Let's take an application as an example, that has a SVG graphic with selectable areas which the user can click on, that then displays data for the selected area in the main application. The browser forbids direct JavaScript interaction like function calls or changes of variables between the main frame and the frame that contains the SVG graphic, making it impossible to notify the web application about the users action in the graphic.
Subscribe to SVG