Table of Contents

Loading Fonts and Collections

The quickest way to get comfortable with Fonts is to separate three ideas: where fonts come from, how a family becomes a concrete font instance, and how that font is later used for measurement or rendering. This page walks through that path before the more advanced layout guides.

The main types you will meet first are:

  • FontCollection stores the families you load.
  • FontFamily represents a family and the styles available for it.
  • Font represents a concrete instance of a family at a given point size, style, and optional variation settings.
  • SystemFonts gives you access to the fonts installed on the current machine.

Load a single font

Use FontCollection.Add(...) when you want to register an individual font file such as a .ttf, .otf, .woff, or .woff2.

using SixLabors.Fonts;

FontCollection collection = new();
FontFamily family = collection.Add("fonts/SourceSans3-Regular.ttf");
Font font = family.CreateFont(16, FontStyle.Regular);

Font.Size is expressed in points. Measurement and rendering are then converted to pixels using TextOptions.Dpi.

Load from a stream and inspect metadata

The Add(...) overloads can also return a FontDescription, which is useful when you want to inspect what was loaded.

using System.IO;
using SixLabors.Fonts;

FontCollection collection = new();

using FileStream stream = File.OpenRead("fonts/SourceSans3-Regular.ttf");
FontFamily family = collection.Add(stream, out FontDescription description);

string familyName = description.FontFamilyInvariantCulture;
Font font = family.CreateFont(16);

If you only need metadata, use FontDescription.LoadDescription(...) or FontDescription.LoadFontCollectionDescriptions(...) instead of adding the font to a collection. See Font Metadata and Inspection for more detail.

Load a font collection

Use AddCollection(...) for files that contain multiple faces, such as .ttc collections.

using SixLabors.Fonts;

FontCollection collection = new();
var families = collection.AddCollection("fonts/NotoSansCJK-Regular.ttc");

Resolve families by name

Once fonts are loaded, resolve a family with Get(...) or TryGet(...).

using SixLabors.Fonts;

FontCollection collection = new();
collection.Add("fonts/SourceSans3-Regular.ttf");
collection.Add("fonts/NotoColorEmoji-Regular.ttf");

if (collection.TryGet("Source Sans 3", out FontFamily textFamily) &&
    collection.TryGet("Noto Color Emoji", out FontFamily emojiFamily))
{
    TextOptions options = new(textFamily.CreateFont(16))
    {
        FallbackFontFamilies = [emojiFamily]
    };
}

FallbackFontFamilies is a list of FontFamily instances, not Font instances. Fonts are created after the fallback family is selected for a run.

Use system fonts

If you want to work with fonts installed on the current machine, use SystemFonts.

using SixLabors.Fonts;

Font caption = SystemFonts.CreateFont("Segoe UI", 12);
Font heading = SystemFonts.CreateFont("Segoe UI", 24, FontStyle.Bold);

Replace "Segoe UI" with any installed family that exists on your machine.

You can also merge the system font set into your own FontCollection.

using SixLabors.Fonts;

FontCollection collection = new();
collection.AddSystemFonts();
collection.Add("fonts/BrandSans-Regular.ttf");

When you need localized family-name lookup, use AddWithCulture(...), GetByCulture(...), or TryGetByCulture(...).

See System Fonts for the fuller system-font API surface, including enumeration, culture-aware lookup, and SearchDirectories.

Create variable-font instances

Variable fonts are exposed through FontVariation and KnownVariationAxes.

using SixLabors.Fonts;

FontCollection collection = new();
FontFamily family = collection.Add("fonts/RobotoFlex.ttf");

Font font = family.CreateFont(
    16,
    new FontVariation(KnownVariationAxes.Weight, 700),
    new FontVariation(KnownVariationAxes.OpticalSize, 16));

The active variation values become part of the Font instance, so the same family can be reused to create multiple design-space instances.

Practical guidance

  • Use a private FontCollection when output must be stable across machines.
  • Use SystemFonts for host-dependent behavior such as diagnostics, user font pickers, or "use what is installed here" workflows.
  • Create Font instances for the size, style, culture, and variation values you actually intend to measure or render.
  • Keep font loading separate from per-request or per-frame layout work when the same files are reused.

Next steps

  • Use Measuring Text when you need layout metrics before rendering.
  • Use System Fonts when you want to inspect or consume the fonts installed on the current machine.
  • Use Font Metadata and Inspection when you need names, styles, or version information without loading a font for shaping.
  • Use Text Layout and Options to control wrapping, alignment, direction, shaping, fallback fonts, and text runs.
  • Use OpenType Features when you want to request fractions, tabular figures, stylistic sets, or other font features explicitly.
  • Use Fallback Fonts and Multilingual Text when one family is not enough for your content.
  • Use Variable Fonts when you want to work with weight, width, optical size, or custom axes from a single font file.
  • Use Custom Rendering if you need to render glyph geometry to your own output surface.