← Back to DevBytes

Mastering CSS Writing Modes: Tips and Best Practices

What Are CSS Writing Modes?

CSS Writing Modes define the primary directions in which text flows and blocks stack on a page. They are a fundamental but often overlooked part of modern CSS layout that control the inline progression (the direction a line of text flows) and the block progression (the direction in which lines stack one after another). The core property is writing-mode, supported by direction and text-orientation.

The writing-mode property accepts the following key values:

Understanding writing modes unlocks the ability to create layouts that adapt to different language directions and to build vertical content without heavy JavaScript or CSS transforms.

Why Writing Modes Matter

🚀 Deploy your AI agent in 10 minutes

Managed Hermes hosting. Zero DevOps. 100M tokens/mo included.

Try it free →

CSS Writing Modes are not just for multilingual websites—they are a design superpower. Here’s why you should master them:

Getting Started with the writing-mode Property

The writing-mode property is the starting point. It sets both the inline direction (where letters go next) and the block direction (where the next line appears). Below are practical code examples that demonstrate each main value.

Default Horizontal Top-to-Bottom

<div class="horizontal-box">
  <p>The quick brown fox jumps over the lazy dog.</p>
</div>

<style>
.horizontal-box {
  writing-mode: horizontal-tb;
  width: 200px;
  border: 1px solid #ccc;
  padding: 0.5em;
}
</style>

This is the standard flow. The text runs left-to-right (or right-to-left if direction: rtl is applied), and lines stack downward.

Vertical Right-to-Left (Classical East Asian)

<div class="vertical-rl-box">
  <p>TEXT TEXT</p>
</div>

<style>
.vertical-rl-box {
  writing-mode: vertical-rl;
  height: 200px;          /* block dimension is now vertical */
  width: auto;            /* inline dimension becomes horizontal */
  border: 1px solid #ccc;
  padding: 0.5em;
  font-family: 'Noto Serif JP', serif;
}
</style>

Here text flows top‑to‑bottom within each line, and the lines stack from right to left. Notice we use height to constrain the block axis (now vertical) rather than width.

Vertical Left-to-Right

<div class="vertical-lr-box">
  <p>Vertical text, lines stack left to right.</p>
</div>

<style>
.vertical-lr-box {
  writing-mode: vertical-lr;
  height: 150px;
  border: 1px solid #ccc;
  padding: 0.5em;
}
</style>

This mode is less common for natural languages but useful for UI elements like vertical tabs or progress indicators where you want the first column on the left.

Controlling Text Orientation with text-orientation

In vertical writing modes, the text-orientation property determines how individual characters are rotated. It applies only when writing-mode is a vertical value.

Example: Mixed vs Upright

<div class="vert-mixed">
  <p>CSS Writing Modes waTEXT</p>
</div>
<div class="vert-upright">
  <p>CSS Writing Modes waTEXT</p>
</div>

<style>
.vert-mixed {
  writing-mode: vertical-rl;
  text-orientation: mixed;
  height: 150px;
}
.vert-upright {
  writing-mode: vertical-rl;
  text-orientation: upright;
  height: 150px;
}
</style>

With mixed, the Latin letters "CSS Writing Modes" rotate sideways while the Japanese characters stay upright. With upright, everything stands upright—Latin letters appear one below the other, which is often used for narrow UI elements.

Embracing Logical Properties for Robust Layouts

Physical properties like margin-left, width, or border-right are tied to the physical screen. When writing-mode changes, their meaning can become counterintuitive. Logical properties describe dimensions relative to the flow: inline (along the text flow) and block (perpendicular to the flow).

Key logical properties include:

Example: A Card That Works in Any Writing Mode

<div class="card">
  <h3>Article Title</h3>
  <p>This is a short description that should flow correctly regardless of writing mode.</p>
</div>

<style>
.card {
  /* Logical dimensions */
  inline-size: 250px;
  block-size: auto;

  /* Logical margins */
  margin-block-end: 1rem;

  /* Logical padding */
  padding-inline: 1rem;
  padding-block: 1rem;

  border-inline-start: 4px solid tomato;
  background: #fafafa;
}
</style>

If you later add writing-mode: vertical-rl to the .card or to a parent, the inline-size automatically constrains the horizontal dimension (now the inline axis), and the thick border moves to the top (since inline‑start becomes top in vertical‑rl). No manual adjustments needed.

Practical Layout Examples

Vertical Navigation Sidebar

A common pattern is a sidebar where each menu item is rotated vertically. Instead of CSS transforms, writing modes keep text selection natural and allow flexible sizing.

<nav class="vert-nav">
  <a href="#">Home</a>
  <a href="#">About</a>
  <a href="#">Services</a>
  <a href="#">Contact</a>
</nav>

<style>
.vert-nav {
  writing-mode: vertical-rl;
  text-orientation: mixed;   /* keeps Latin letters rotated */
  block-size: 100vh;         /* full height */
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: 1rem;
  padding-block: 1rem;
  background: #2c3e50;
}
.vert-nav a {
  color: white;
  text-decoration: none;
  padding-inline: 0.5em;
  border-block-end: 2px solid transparent;
}
.vert-nav a:hover {
  border-block-end-color: #e67e22;
}
</style>

The navigation links stack vertically, the text inside them flows top‑to‑bottom, and the hover underline appears on the block‑end side (which in this mode is the bottom of the line). Screen readers and search engines still read the text as "Home" etc.

Vertical Headings in a Horizontal Article

<article>
  <h2 class="vert-heading">Introduction</h2>
  <p>This paragraph flows horizontally as normal.</p>
</article>

<style>
.vert-heading {
  writing-mode: vertical-lr;
  text-orientation: upright;
  float: left;              /* classic float to wrap text around */
  margin-inline-end: 1rem;
  border-inline-end: 2px solid #333;
  padding-inline-end: 0.5rem;
  font-size: 2rem;
}
</style>

The heading sits to the left, its letters upright one below the other, while the paragraph text wraps around it. Logical margins ensure spacing adjusts if you ever flip the whole document.

Full Vertical Page (Like a Traditional Book)

<div class="vertical-page">
  <header>TEXT1chapter: TEXTnoTEXT</header>
  <section>
    <p>Once upon a time、TEXT…</p>
    <p>TEXTnoTEXTwaTEXT。</p>
  </section>
</div>

<style>
.vertical-page {
  writing-mode: vertical-rl;
  text-orientation: mixed;
  inline-size: 100%;       /* horizontal becomes inline axis */
  block-size: 100vh;       /* vertical becomes block axis */
  overflow-y: auto;        /* scroll horizontally? Actually overflow becomes overflow-inline */
  column-width: 15em;      /* columns now stack horizontally */
  column-gap: 2em;
  padding-inline: 1em;
}
.vertical-page header {
  font-weight: bold;
  border-block-end: 1px solid #aaa;
  margin-block-end: 1em;
}
</style>

This creates a paginated vertical layout with columns that flow right‑to‑left, resembling a Japanese novel. The column-width property works in the inline direction, so it automatically creates horizontal columns.

Best Practices and Tips

Common Pitfalls and How to Avoid Them

Conclusion

Mastering CSS Writing Modes opens a world of expressive, culturally aware, and maintainable layouts. By shifting from physical dimensions to logical properties and embracing the writing-mode property, you can create components that gracefully adapt to horizontal and vertical flows, right‑to‑left or left‑to‑right languages. Start small—add vertical headings or a sidebar—and gradually adopt logical sizing everywhere. The result is a codebase that respects the diversity of language and design without fragile workarounds. Experiment with the examples above, test with real multilingual content, and let your layouts flow naturally in every direction.

🚀 Need a reliable AI agent for your project?

Deploy Hermes Agent in 10 minutes. Managed hosting, zero DevOps.

Get Started — $23.99/mo
← Back to all articles