While it is possible to rotate and position HTML text into new orientations on a page using a combination of CSS transforms, anything more than a few rotated characters or words on an angle is usually best left to SVG, which has it’s own specialized element for achieving the effect: textpath
.
Walking The Path
Placing text on a path in SVG requires three components:
- A
<path>
, which must be have anid
and be in the<defs>
section of the SVG document. - A
<text>
element. - Some characters within a
<textPath>
element, inside of the<text>
element. This<textPath>
must reference theid
of the<path>
In SVG 1.2, the path must be a <path>
element: you can’t yet make text cling to a <circle>
or <rect>
. Since I assume that most designers will be primarily interested in putting text on a circle or an ellipse, I’ll start by addressing that issue.
Converting a circle to a path
There are two methods I’m aware of to convert an SVG circle to a path:
- In Adobe Illustrator or other vector editing tools, there are several possibilities: moving any individual point on the shape, even slightly, will turn a circle into a path, as will deleting a point from a shape; alternatively use Object / Compound Path / Make on the circle.
- If you’re more comfortable with SVG itself, you can use this neat little JavaScript conversion tool that takes the attributes for a SVG circle and turns it into the equivalent path data.
Attaching the Text
The full SVG for the logo above (excluding the central “star” and animation; to see that and more, visit the CodePen demo):
<svg xmlns="http://www.w3.org/2000/svg"
xmlns:xlink="http://www.w3.org/1999/xlink" viewBox="0 0 500 500">
<title>Red Hot Chilli Peppers Logo</title>
<defs>
<path d="M243.2, 382.4c-74.8,
0-135.5-60.7-135.5-135.5s60.7-135.5,135.5-135.5s135.5, 60.7, 135.5,
135.5 S318, 382.4, 243.2, 382.4z" id="textcircle" />
<style>
text {
font-size: 60px;
font-family: Franklin Gothic, sans-serif;
font-weight: 900;
text-transform: uppercase;
letter-spacing: 22px;
}
</style>
</defs>
<text dy="70" textLength="1200">
<textPath xlink:href="#textcircle">
Red Hot Chilli Peppers
</textPath>
</text>
</svg>
There are just a few things to note:
- Obviously the text must be large enough to read, which will depend, in turn, on how large it is relative to the size of the path.
- The text will always start at a particular point on the circular path, although this can be adjusted (see below).
- If the text wraps past its starting point, it will effectively “eat its own tail”, and any excess characters at the end will be invisible.
- The text is styled with the typographic CSS you’re probably already familiar with; the only difference is the
<text>
selector, thefill
color, thedy
attribute and thetextLength
attribute (discussed below). textLength
- essentially the circumference of the circle in this case - is used as an alternative toletter-spacing
for Firefox, which has a bug in regards to the latter when it comes to SVG.
Setting A Starting Point
The text will begin at what SVG perceives to be the “starting point” of the path. This starting point can be altered in a number of ways:
It’s usually easiest to rotate the path to your preferred orientation, which will carry the text along with it:
<path d="…" id="textcircle" transform="rotate(90 250 250)" />
Alternatively, you could rotate the circle in your vector editing application before exporting it.
If the text starts too “early” on the circle but has room to move on the end, use
startOffset
. The value of this attribute determines the “starting point” for the text, and is measured in percentages, with 0% being the default and 100% (i.e. “starting” at the very end of the path) as the maximum possible value. As before, text that goes past the end point of the path will effectively disappear.Add an
dx
(orx
) attribute value to the<text>
element, which will move the text along the path by the value of the attribute (this value is interpreted as pixels, by default). Note thatdx
currently works best with Firefox, so it’s the option I recommend.<text dx="50"> <textPath xlink:href="#textcircle"> Red Hot Chilli Peppers </textPath> </text>
Negative values for
x
ordx
will suck the leading letters for the text into invisibility.SVG text placement on the same circular path with different path directions: clockwise (left) and counter-clockwise (right) Reversing Course
The text will proceed in the direction implied by the way the path is drawn. There are two possible interpretations in SVG:
- A circle that proceeds clockwise will have the bases of the letters set on the outside of the path: that is, the letters will be “facing outwards”
- A circle that is interpreted as being “anticlockwise” will have the bases of the letters set on the inside of the path: that is, the letters will be “facing inwards”.
Reverse-path option for a compound path in Adobe Illustrator The easiest way to reverse the course of a path in Adobe Illustrator is to make sure it is a Compound Path (
Object / Compound Path / Make
) and then useReverse Path Direction
in theAttributes
panel (again, you may have to useShow Options
in the top right corner to see these controls).SVG2 adds the
side
attribute, which will make text directionality on paths significantly easier: aside
value ofleft
orright
will effectively reverse the directionality of a path.side
will also allow the application of text around, and within, basic shapes like rectangles and circles, rather than exclusively paths. Sadly, as of this writing, no browser yet supports it.Reversing the path doesn’t remove the potential problem of having clockwise text appear on the outside while anticlockwise text appears on the inside of a path. The easiest way to fix this is to use the
dy
attribute to move the text “up” or “down” relative to the path. For example:<text dy="50"> <textPath xlink:href="#textcircle"> Red Hot Chilli Peppers </textPath> </text>
The result, on a clockwise path, is to move the text inward. You can also use a negative value to move the text outwards.
Alternate Curves
Text read in opposite directions on the same curve are fairly frequent in logo design. The most familiar identity that uses this technique is probably the ubiquitous Starbucks Coffee logo.
There are two ways to achieve this result in SVG:
- Use a copy of the same path, but reversed in direction, with a new
id
, as a reference for the other text element. (You’ll need to move the characters using thedy
attribute) - Assuming both text fragments are the same size: use another path that touches the top of the lower characters. This will become the baseline for the upper text. (You may still have to reverse the direction of one path).
In the example above, I used the second technique. The code, without the central mermaid design or stars:
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" viewBox="0 0 200 200"> <title>Starbucks Coffee Logo</title> <defs> <path d="M15,100a85,85 0 1,0 170,0a85,85 0 1,0 -170,0" id="coffeecircle" /> <path d="M100,37c34.8,0,63,28.2,63,63s-28.2,63-63,63s-63-28.2-63-63S65.2,37,100,37z" id="starbuckscircle" transform="rotate(-85 100 100)" /> </defs> <circle cx="100" cy="100" r="100" fill="#067655" id="background" /> <circle fill="none" stroke="#FFF" cx="100" cy="100" r="93.8" stroke-width="3" id="rim" /> <text> <textPath xlink:href="#starbuckscircle">Starbucks</textPath> </text> <text dx="55" textLength="160" class="coffee"> <textPath xlink:href="#coffeecircle">Coffee</textPath> </text> </svg>
The associated styles:
text { font-family: Santana-Black, sans-serif; fill: #fff; text-transform: uppercase; font-size: 32px; } .coffee { letter-spacing: 6px; }
You can see the actual paths used for the text by dragging them out of the
<defs>
section and applying astroke
andstroke-width
attribute in the CodePen version.Conclusion
There are several reasons why you might want to place text on a path:
- You want the text to remain readable, accessible, and SEO-friendly
- You plan to animate the text.
- You want the text to be easily editable and/or selectable.
If you don’t want these qualities - or can built alternatives to them - then it may be easier to break the text into paths and export the result as a “frozen” SVG.
Of course, circles and ellipses are not the only way text can be applied to a path: I’ll look at other possibilities in the next article.
Enjoy this piece? I invite you to follow me at twitter.com/dudleystorey to learn more.
Check out the CodePen demo for this article at https://codepen.io/dudleystorey/pen/grOgLp