The Formatting Values page introduced the basics of fmt_number(), fmt_currency(), fmt_date(), and fmt_time(). But Great Tables has a much larger formatting toolkit. This page covers additional formatters that handle percentages, byte sizes, durations, scientific units, icons, flags, images, boolean values, Markdown, and more. Each formatter transforms raw cell data into presentation-ready content.
When choosing a formatter, start with the semantic meaning of your data. If a column represents a file size, reach for fmt_bytes() rather than fmt_number() with manual suffix logic. If a column holds time durations, use fmt_duration() instead of formatting seconds by hand. Semantic formatters produce more consistent output and handle edge cases (like unit boundaries and scaling) automatically, so you get correct results without writing extra logic.
Percentage Formatting
The fmt_percent() method formats numeric values as percentages. By default, it assumes the input values are proportions (e.g., 0.25 becomes "25.00%"). If your values are already in percent form, set scale_values=False.
Both columns display correctly as percentages, but the proportion column needed scaling (the default behavior) while already_pct did not.
Byte Size Formatting
The fmt_bytes() method converts raw byte counts into human-readable sizes. It automatically selects the appropriate unit (kB, MB, GB, etc.) based on the magnitude of the value.
With the binary standard, the same byte values display in KiB, MiB, and GiB units. Choose whichever standard matches the conventions of your domain.
As a rule of thumb, use decimal units (kB, MB, GB) for storage marketed to consumers (disk drives, cloud storage quotas, and network transfer speeds all use powers of 1000). Use binary units (KiB, MiB, GiB) for memory and technical contexts where powers of 1024 are precise, such as RAM capacity, cache sizes, and buffer allocations. Picking the right standard avoids confusing your readers with numbers that don’t match what they see elsewhere.
Duration Formatting
The fmt_duration() method formats numeric values (or timedelta objects) as styled time duration strings. You specify the input unit and the method handles the conversion and display.
Limiting the output to two units (e.g., "2d 3h" instead of "2d 3h 15m") keeps the display compact when exact precision is not required.
Engineering Notation
The fmt_engineering() method formats values in engineering notation, where the exponent is always a multiple of 3. This aligns with SI prefixes (kilo, mega, milli, micro, etc.) and is common in technical and scientific contexts.
Each value is expressed with a mantissa between 1 and 999 and an exponent that is a multiple of 3. This makes it straightforward to mentally convert to SI prefixes (e.g., 4.7 x 10^3 = 4.7 kilo).
Engineering notation is preferred over scientific notation when your audience thinks in terms of SI prefixes. Because the exponent is always a multiple of 3, values map directly to familiar units: kilohms, microfarads, gigahertz, milliwatts, and so on. Readers can interpret the numbers without mental conversion. If your data spans a wide range of magnitudes in a technical domain, engineering notation is almost always the better choice.
Parts-Per Formatting
The fmt_partsper() method formats values as parts-per quantities: per mille, ppm, ppb, and more. By default, it assumes input values are proportions and scales them accordingly.
The case= argument accepts "upper" (the default, producing "I", "II", "III") or "lower" (producing "i", "ii", "iii").
Scientific Units
The fmt_units() method renders measurement units with proper subscripts, superscripts, and special symbols. It uses a concise notation syntax where ^ indicates superscripts, _ indicates subscripts, and special names are referenced with colons.
The units notation supports Greek letters (:alpha:, :beta:, :sigma:), chemical formulas in percent delimiters (%H2O%), and combined subscripts and superscripts (t_i^2).
True/False Formatting
The fmt_tf() method transforms boolean values into visual indicators. It offers a variety of preset styles including text labels, check marks, shapes, and arrows.
When you provide two colors, the first applies to True values and the second to False values.
Markdown in Cells
The fmt_markdown() method renders Markdown-formatted text that appears in cells. This is useful when your data contains text with emphasis, links, or other inline formatting.
md_df = pl.DataFrame({"package": ["polars", "pandas", "numpy"],"description": ["**Fast** DataFrame library for *Rust* and Python","Flexible data analysis with **labeled** axes","Fundamental package for *scientific computing*", ],})( GT(md_df, rowname_col="package") .fmt_markdown(columns="description"))
description
polars
Fast DataFrame library for Rust and Python
pandas
Flexible data analysis with labeled axes
numpy
Fundamental package for scientific computing
The Markdown is converted to HTML during rendering, so standard inline Markdown syntax (bold, italic, links, code) is supported.
Icons in Cells
The fmt_icon() method renders Font Awesome icons based on icon names stored in cells. This is a visually engaging way to represent categories, statuses, or types.
The flags render as small inline images with a hover tooltip showing the country name (controlled by use_title=).
Images in Cells
The fmt_image() method renders image paths or URLs as inline images within cells. This is useful for product catalogs, team rosters, or any dataset where visual identification matters.
The path= argument provides a common prefix for all file references, and height=/width= control the rendered dimensions. When encode=True (the default), local image files are base64-encoded directly into the HTML output, making the table self-contained.
When none of the built-in formatters fit your needs, the generic fmt() method lets you supply any function as a formatter. The function receives a raw cell value and should return a formatted string.
def format_score(value):"""Convert a 0-100 score to a letter grade."""if value >=90:return"A"elif value >=80:return"B"elif value >=70:return"C"elif value >=60:return"D"else:return"F"grades_df = pl.DataFrame({"student": ["Alice", "Bob", "Charlie", "Diana"],"score": [95, 82, 67, 91],})( GT(grades_df, rowname_col="student") .fmt(fns=format_score, columns="score"))
score
Alice
A
Bob
B
Charlie
D
Diana
A
The fmt() method is the escape hatch for any formatting logic that the specialized fmt_*() methods do not cover. Your function can return plain text or HTML strings for rich formatting.
fmt() is what makes Great Tables’ formatting system fully extensible. Any transformation you can express in Python (lookups, conditional logic, external API calls) can become a cell formatter. If you find yourself writing the same custom formatter repeatedly, consider wrapping it in a reusable function and sharing it across tables. This is exactly the pattern described in the Extending Great Tables page.
The formatting methods in Great Tables cover a wide spectrum of data types and presentation needs. From scientific notation to country flags, from boolean indicators to custom functions, you have the tools to make every column in your table look exactly right for its audience and context.