Sone

Text & Typography

Master rich text formatting and multilingual support in Sone

Text & Typography

Sone provides powerful text rendering capabilities with advanced typography features, rich formatting options, and excellent multilingual support.

Text Component

The Text component is the primary way to display text content:

import { Text } from "sone";

Text("Hello, World!")
  .size(24)
  .color("blue")
  .weight("bold")

Rich Text with Spans

Use Span components within Text to apply different styling to portions of text:

Text(
  "Welcome to ",
  Span("Sone").color("blue").weight("bold"),
  " - the declarative layout engine!"
)
.size(16)
.align("center")

Font Management

Loading Custom Fonts

import { Font } from "sone";

// Load a custom font
await Font.load("CustomFont", "/path/to/font.ttf");

// Check if font is loaded
if (Font.has("CustomFont")) {
  console.log("Font is ready to use");
}

// Use the font
Text("Custom Typography")
  .font("CustomFont", "sans-serif") // Font stack with fallback
  .size(20)

Font Families

Sone supports font stacks similar to CSS:

Text("Professional Text")
  .font("Helvetica", "Arial", "sans-serif")
  .size(16)

Built-in font families:

  • "sans-serif" - System sans-serif font
  • "serif" - System serif font
  • "monospace" - System monospace font

Typography Properties

Font Styling

Text("Styled Text")
  .size(18)                    // Font size in pixels
  .weight("bold")              // Font weight: "normal", "bold", or number (100-900)
  .style("italic")             // Font style: "normal", "italic", "oblique"
  .letterSpacing(2)            // Spacing between characters
  .wordSpacing(4)              // Spacing between words

Text Layout

Text("Lorem ipsum dolor sit amet...")
  .align("justify")            // "left", "center", "right", "justify"
  .lineHeight(1.5)            // Line height multiplier
  .nowrap()                   // Prevent text wrapping
  .indent(20)                 // First line indent
  .hangingIndent(10)          // Subsequent lines indent

Auto-fit Text

Make text automatically adjust its size to fit available space:

Text("This text will scale to fit")
  .autofit(true)
  .maxWidth(300)
  .maxHeight(100)

Text Decorations

Underlines, Strikethrough, and Overlines

Text("Decorated Text")
  .underline(2)                    // Underline thickness
  .underlineColor("red")           // Custom underline color
  .lineThrough(1)                  // Strikethrough thickness
  .lineThroughColor("blue")        // Custom strikethrough color  
  .overline(1)                     // Overline thickness
  .overlineColor("green")          // Custom overline color

Text Highlighting

Span("Highlighted text")
  .highlight("yellow")          // Background highlight
  .color("black")

Text Shadows

Text("Shadow Text")
  .size(32)
  .dropShadow("2px 2px 4px rgba(0,0,0,0.5)")
  .color("white")

Text Stroke (Outline)

Text("Outlined Text")
  .size(48)
  .color("white")
  .strokeColor("black")
  .strokeWidth(2)

Advanced Text Features

Vertical Offset

Fine-tune text positioning:

Text(
  "Normal text ",
  Span("superscript").offsetY(-8).size(12),
  " and ",
  Span("subscript").offsetY(4).size(12)
)
.size(16)

Gradient Text

Apply gradients to text:

Text("Gradient Text")
  .size(48)
  .color(["linear-gradient(45deg, red, blue)"])

Multilingual Support

Sone excels at rendering complex scripts and multilingual content:

Khmer Script

import { Font } from "sone";

// Load Khmer font
await Font.load("KhmerFont", "/path/to/NotoSansKhmer.ttf");

Text(
  "English text mixed with ",
  Span("ខ្មែរ").font("KhmerFont"),
  " script"
)
.font("Arial", "sans-serif")
.size(16)

Mixed Scripts

Text(
  "English ",
  Span("العربية").font("NotoSansArabic"),
  " ",
  Span("中文").font("NotoSansCJK"),
  " ",
  Span("हिंदी").font("NotoSansDevanagari")
)
.size(18)
.align("center")

Text Direction

Text("نص عربي")
  .font("NotoSansArabic")
  .direction("rtl")            // Right-to-left text direction
  .align("right")

Text Defaults

Use TextDefault to apply styling to multiple text components:

import { TextDefault, Text, Column } from "sone";

TextDefault(
  Column(
    Text("This inherits default styling"),
    Text("So does this text"),
    Text("And this one too")
  )
)
.font("Helvetica", "sans-serif")
.size(16)
.color("black")
.lineHeight(1.4)

Practical Examples

Article Header

function ArticleHeader(title, subtitle, author) {
  return Column(
    Text(title)
      .size(32)
      .weight("bold")
      .color("black")
      .align("center")
      .marginBottom(10),
      
    Text(subtitle)
      .size(18)
      .color("gray")
      .align("center")
      .marginBottom(20),
      
    Text(`By ${author}`)
      .size(14)
      .weight("500")
      .color("blue")
      .align("center")
  );
}

Formatted Quote

function Quote(text, author) {
  return Column(
    Text(`"${text}"`)
      .size(20)
      .style("italic")
      .color("black")
      .align("center")
      .lineHeight(1.6)
      .padding(20),
      
    Text(`— ${author}`)
      .size(14)
      .weight("bold")
      .color("gray")
      .align("right")
  )
  .bg("#f9f9f9")
  .padding(30)
  .rounded(8);
}

Multilingual Business Card

async function BusinessCard() {
  await Font.load("KhmerFont", "NotoSansKhmer.ttf");
  
  return Column(
    Text("John Doe").size(24).weight("bold"),
    Text("Software Developer").size(16).color("gray"),
    Text(
      "Email: john@example.com\n",
      Span("ផ្ទះលេខ 123 ផ្លូវ ABC").font("KhmerFont").size(14)
    )
    .size(14)
    .lineHeight(1.4)
  )
  .padding(30)
  .bg("white")
  .rounded(8)
  .shadow("0 4px 8px rgba(0,0,0,0.1)");
}

Dynamic Font Size

function ResponsiveTitle(title, maxWidth) {
  return Text(title)
    .size(32)
    .weight("bold")
    .color("black")
    .autofit(true)
    .maxWidth(maxWidth)
    .align("center");
}

Best Practices

Performance

  • Load fonts once at application startup
  • Use font stacks with system fallbacks
  • Cache font loading status

Typography

  • Use consistent line heights (1.4-1.6 for body text)
  • Limit font variations (2-3 font families maximum)
  • Ensure sufficient color contrast

Internationalization

  • Always provide font fallbacks for international scripts
  • Test text rendering with actual content in target languages
  • Consider text direction (RTL) for Arabic, Hebrew, etc.

Accessibility

  • Use semantic font sizes (relative to base size)
  • Ensure text has sufficient contrast ratios
  • Avoid using color alone to convey information