M
Design System

MitoWare Design System

Living style guide for mitoware.com. Every specimen below uses the production stylesheet. When blog.css changes, this page changes with it.

Brand Identity

MitoWare

Thoughts on UX, AI, and Design

Clean & Modern Editorial Serif Prose Light Theme Content-First

MitoWare is the Mitoware company blog. Articles are sourced from Directus CMS, rendered through Flask/Jinja, and served via Docker on Gogli. The design is intentionally restrained; typography and whitespace do the heavy lifting. Two fonts carry the brand: Inter (UI, headings) and Merriweather (long-form prose).

Color

8 tokens in :root

Core Palette

Primary --color-primary: #4361ee
Primary Dark --color-primary-dark: #3a56d4
Accent --color-accent: #0891b2

Backgrounds & Borders

Background --color-bg: #ffffff
Background Alt --color-bg-alt: #f8f9fa
Border --color-border: #e9ecef

Text

Text --color-text: #1a1a2e
Text Muted --color-text-muted: #6c757d

Gradient

Used on image placeholders when no featured image exists.

Placeholder Gradient 135deg, primary → accent

Typography

2 font families

Font Families

--font-sans: Inter UI, headings, metadata

The quick brown fox jumps over the lazy dog. 0123456789

--font-serif: Merriweather Prose / article body

The quick brown fox jumps over the lazy dog. 0123456789

--font-serif (italic) Blockquotes

The quick brown fox jumps over the lazy dog. 0123456789

Type Scale (Sans / UI)

2.5rem / 700 .article-title

Article Title

2rem / 700 .featured-title, .page-title

Featured Title

1.5rem / 700 .section-title

Section Title

1.25rem / 600 .site-logo, .list-item-title

Logo / List Title

1.1rem / 600 .card-title

Card Title

0.9rem / 500 .nav-link

Navigation Link

0.875rem / 400 .card-date, .featured-meta

February 10, 2026

Type Scale (Serif / Prose)

1.125rem / 400 / 1.8 .prose

Long-form article body text uses Merriweather for comfortable reading at sustained lengths. Line height is generous at 1.8 to give each line room to breathe.

Spacing

7 tokens
--space-xs
0.25rem (4px)
--space-sm
0.5rem (8px)
--space-md
1rem (16px)
--space-lg
1.5rem (24px)
--space-xl
2rem (32px)
--space-2xl
3rem (48px)
--space-3xl
4rem (64px)

Shadows

3 tokens
--shadow-sm
--shadow-md
--shadow-lg
CSS Variables
/* Shadows */
--shadow-sm: 0 1px 2px rgba(0, 0, 0, 0.05);
--shadow-md: 0 4px 6px rgba(0, 0, 0, 0.07);
--shadow-lg: 0 10px 15px rgba(0, 0, 0, 0.1);

Buttons & Controls

view-btn, read-more, back-link, view-all

View Toggle Buttons

Used in the articles toolbar to switch between list and card views.

Default / Active / Hover
View toggle markup
<div class="view-toggle">
  <button type="button" class="view-btn">
    <!-- SVG list icon -->
  </button>
  <button type="button" class="view-btn active">
    <!-- SVG grid icon -->
  </button>
</div>

Text Links (Interactive)

Link markup
<a href="..." class="read-more">Read Article &rarr;</a>
<a href="..." class="view-all">View All Articles &rarr;</a>
<a href="..." class="back-link">&larr; Back to Articles</a>

Cards

article-card, article-card-small, article-list-item

Article Card (Grid View)

3-column grid on desktop, 2 on tablet, 1 on mobile. Cards lift on hover with shadow-lg and translateY(-2px).

Article card markup
<article class="article-card">
  <a href="..." class="card-image">
    <img src="..." alt="...">
  </a>
  <div class="card-content">
    <span class="article-hub article-hub-small">HUB</span>
    <h3 class="card-title">
      <a href="...">Title</a>
    </h3>
    <p class="card-excerpt">Excerpt...</p>
    <time class="card-date">Date</time>
  </div>
</article>

Article Card (Placeholder Image)

When no featured image exists, a gradient placeholder (primary → accent) fills the image area.

Article Card Small (Related Articles)

Used in the "More Articles" section on article pages. No image, tighter padding.

Small card markup
<article class="article-card article-card-small">
  <div class="card-content">
    <span class="article-hub article-hub-small">HUB</span>
    <h3 class="card-title">
      <a href="...">Title</a>
    </h3>
    <time class="card-date">Date</time>
  </div>
</article>

Article List Item (List View)

Horizontal layout with 200px image on the left. Used in the articles archive when list view is active.

List item markup
<article class="article-list-item">
  <a href="..." class="list-item-image">
    <img src="..." alt="...">
  </a>
  <div class="list-item-content">
    <span class="article-hub article-hub-small">HUB</span>
    <h2 class="list-item-title">
      <a href="...">Title</a>
    </h2>
    <p class="list-item-excerpt">Excerpt...</p>
    <div class="list-item-meta">
      <time>Date</time>
      <div class="article-tags">
        <span class="tag">Tag</span>
      </div>
    </div>
  </div>
</article>

Forms & Toolbar

toolbar-select, toolbar-control, articles-toolbar

Toolbar Select

Used for sort and per-page controls in the articles archive.

Default / Focus States
Toolbar control markup
<div class="toolbar-control">
  <label for="sort-select">Sort:</label>
  <select id="sort-select" class="toolbar-select">
    <option value="newest">Newest First</option>
    <option value="oldest">Oldest First</option>
  </select>
</div>

Full Toolbar

Complete toolbar as it appears on the articles archive page.

Layout

container, grids, breakpoints

Container Widths

--container-max: 1200px
--container-narrow: 720px

Article Grid (3-column)

Used on home page (recent articles) and archive page (card view).

grid-template-columns: repeat(3, 1fr) · gap: var(--space-xl)

Featured Article Grid (2-column)

Image left, content right. Collapses to single column at 1024px.

grid-template-columns: 1fr 1fr · gap: var(--space-2xl)

Breakpoints

1024px Featured grid stacks. Article grid → 2 columns.
768px Article grid → 1 column. List items stack. Toolbar wraps.
480px Tighter padding. Toolbar stacks vertically. Prose → 1rem.

Prose

.prose (article body content)

The .prose class wraps all article body content. It switches to Merriweather serif, increases font size to 1.125rem, and sets generous line-height (1.8). Headings inside prose revert to Inter sans-serif.

Heading Two (1.5rem / Inter)

This is how body text looks inside a prose block. Merriweather at 1.125rem with 1.8 line-height provides comfortable sustained reading. The generous spacing between lines prevents the text from feeling cramped, even in longer articles.

Heading Three (1.25rem / Inter)

Links inside prose are underlined and blue, distinguishing them from the non-underlined links used elsewhere in the UI. This follows the convention that prose links should be clearly identifiable within running text.

Blockquotes use a 4px left border in primary blue, italic Merriweather, and muted text color. They provide visual distinction for quoted material.

Heading Four (1.1rem / Inter)

  • Unordered list items have bottom margin for readability
  • Lists are indented with padding-left at --space-xl
  • Each item gets 0.5rem bottom spacing

Inline code spans use a light background and smaller font size. Code blocks use the same background with more padding:

// Pre-formatted code blocks
const title = article.title;
const slug = article.slug;

Bold text uses font-weight 700 for emphasis within the serif body copy.

Prose markup
<div class="article-content prose">
  <h2>Heading Two</h2>
  <p>Body text...</p>
  <blockquote>Quoted text...</blockquote>
  <ul>
    <li>List item</li>
  </ul>
  <pre><code>Code block</code></pre>
</div>

Decorative Elements

article-hub, tag, section-title, placeholders

Hub Badge

Labels articles by source hub (UX, AI, DESIGN). Two sizes: standard and small.

Standard / Small
UX AI DESIGN UX AI DESIGN
Hub badge markup
<span class="article-hub">UX</span>
<span class="article-hub article-hub-small">UX</span>

Tags

Light gray pills used for article categorization.

Tag markup
<div class="article-tags">
  <span class="tag">UX</span>
  <span class="tag">AI</span>
</div>

Section Title

Used for "Recent Articles", "More Articles" headings. Has a 2px border-bottom.

Recent Articles

Page Header

Centered header with title and subtitle. Used on the articles archive page.

States & Feedback

empty, error, placeholder, hover

Empty State

Shown when no articles exist.

No articles yet

Check back soon for new content.

Empty state markup
<section class="empty-state">
  <h2>No articles yet</h2>
  <p>Check back soon for new content.</p>
</section>

Error Page

Oops!

Something went wrong

← Back to Home
Error page markup
<section class="error-page">
  <h1 class="error-title">Oops!</h1>
  <p class="error-message">Something went wrong</p>
  <a href="/" class="error-link">&larr; Back to Home</a>
</section>

Image Placeholders

Two sizes: featured (16:10 aspect ratio) and card (16:9 aspect ratio).

Featured (16:10)
Card (16:9)

Hover States

.article-card shadow-lg + translateY(-2px)
a color → primary-dark (#3a56d4)
.site-logo color → primary (#4361ee)
.toolbar-select border-color → primary
.pagination-page border-color + text → primary

Transitions

--transition-fast 150ms ease (links, buttons, borders)
--transition-normal 250ms ease (card hover, shadows)

Future Components

Predicted needs

Search

As the article count grows, a search input in the toolbar or header becomes essential. Should follow the existing .toolbar-select styling pattern with matching border radius, padding, and hover/focus states.

Proposed markup
<div class="toolbar-control">
  <input type="search"
         class="toolbar-search"
         placeholder="Search articles...">
</div>

Tag Filtering

Clickable tags that filter the article list. Reuse the existing .tag class with an active state that swaps to primary blue background and white text.

Proposed CSS
/* Active tag filter */
.tag-filter {
  cursor: pointer;
  transition: all var(--transition-fast);
}
.tag-filter:hover {
  background: var(--color-primary);
  color: white;
}
.tag-filter.active {
  background: var(--color-primary);
  color: white;
}

Reading Time

Estimated reading time in the article meta. Would appear alongside the date in .article-meta and .featured-meta with a dot separator.

Proposed markup
<div class="article-meta">
  <time>February 10, 2026</time>
  <span class="reading-time">5 min read</span>
</div>

Newsletter CTA

An email capture section at the end of articles or in the footer. Should use the primary blue for the submit button, matching the hub badge treatment, and the toolbar-select styling for the email input.

Proposed markup
<section class="newsletter-cta">
  <h3>Stay in the loop</h3>
  <p>New articles on UX, AI, and design.</p>
  <form class="newsletter-form">
    <input type="email" class="toolbar-select"
           placeholder="[email protected]">
    <button class="newsletter-submit">Subscribe</button>
  </form>
</section>

Dark Mode

The CSS variable architecture supports a dark mode toggle by swapping :root values. All components use variables exclusively; no hard-coded colors in component CSS. A @media (prefers-color-scheme: dark) block or class-based toggle would work without changing any component styles.

Proposed CSS
/* Dark mode token overrides */
@media (prefers-color-scheme: dark) {
  :root {
    --color-bg: #1a1a2e;
    --color-bg-alt: #252542;
    --color-text: #f0f0f0;
    --color-text-muted: #94a3b8;
    --color-border: #3a3a5c;
  }
}