Red Hot Chilli Peppers Logo Red Hot Chilli Peppers

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 , 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:

  1. A <path>, which must be have an id and be in the <defs> section of the SVG document.
  2. A <text> element.
  3. Some characters within a <textPath> element, inside of the <text> element. This <textPath> must reference the id 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:

  1. 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.
  2. 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:

  1. 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.
  2. The text will always start at a particular point on the circular path, although this can be adjusted (see below).
  3. 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.
  4. The text is styled with the typographic CSS you’re probably already familiar with; the only difference is the <text> selector, the fill color, the dy attribute and the textLength attribute (discussed below).
  5. textLength - essentially the circumference of the circle in this case - is used as an alternative to letter-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 (or x) 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 that dx 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 or dx 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:

    1. 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”
    2. 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 use Reverse Path Direction in the Attributes panel (again, you may have to use Show Options in the top right corner to see these controls).

    SVG2 adds the side attribute, which will make text directionality on paths significantly easier: a side value of left or right 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.

    Starbucks Coffee Logo Starbucks Coffee

    There are two ways to achieve this result in SVG:

    1. 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 the dy attribute)
    2. 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 a stroke and stroke-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