[](https://github.com/tecolicom/App-mdee/actions?workflow=test) [](https://metacpan.org/release/App-mdee)
# NAME
mdee - em·dee, Markdown Easy on the Eyes
# SYNOPSIS
mdee [ options ] file ...
-h --help show help
--version show version
-d --debug debug level (repeatable)
-x --[no-]trace trace mode (set -x)
-n --dryrun dry-run mode
-s --style=# output style (nup/pager/cat/filter/raw)
-f --filter shortcut for --style=filter
-p --plain shortcut for --style=pager
--[no-]fold line folding (default: on)
--[no-]table table formatting (default: on)
--[no-]nup nup paged output (default: on)
--[no-]rule use Unicode rules for tables (default: on)
-w --width=# fold width (default: 80)
-t --theme=#[,#,...] color theme(s)
-m --mode=# light or dark (default: light)
-B --base-color=# override theme's base color
(e.g., Ivory, #780043, (120,0,67))
--list-themes list available themes
--show=# set field visibility (e.g., italic=1)
-C --pane=# number of columns
-R --row=# number of rows
-G --grid=# grid layout (e.g., 2x3)
-P --page=# page height in lines
-S --pane-width=# pane width (default: 85)
--bs --border-style=# border style
--[no-]pager[=#] pager command
# VERSION
Version 0.13
# DESCRIPTION
**em·dee** (command: `mdee`) is a terminal-based multi-column
Markdown text viewer with syntax highlighting, particularly
useful for reading documents generated by LLMs.
It displays Markdown text as-is with minimal formatting: syntax
highlighting, line folding for long list items, and table column
alignment. Markup characters (`**`, `` ` ``, `#`, etc.) are
preserved in the output. Link URLs are removed from the display,
showing only the link text (e.g., `[text](url)` becomes
`[text]`). On terminals supporting OSC 8 hyperlinks, the link
text remains clickable.
It does not render Markdown into formatted output or reflow
paragraphs. For full Markdown rendering, many other viewers are
available. Combine them with [nup(1)](https://metacpan.org/pod/App%3A%3Anup) for similar paged output
(e.g., `nup glow README.md`).
The pipeline combines [greple(1)](https://metacpan.org/pod/App%3A%3AGreple) for colorization and
[nup(1)](https://metacpan.org/pod/App%3A%3Anup) for multi-column paged output.
Supported elements: headers (h1-h6), bold, italic, strikethrough,
inline code, code blocks, HTML comments, tables, and list items.
# OPTIONS
## General Options
- **-h**, **--help**
Show help message.
- **--version**
Show version.
- **-d**, **--debug**
Set debug level. Can be repeated for increasing verbosity.
- `-d`
Show color values and pipeline stage names.
- `-dd`
Above, plus full command lines for each pipeline stage.
- **-x**, **--trace**, **--no-trace**
Enable or disable shell trace mode (`set -x`). Useful for
debugging script execution. Can be toggled: `-x --no-x` enables
then disables tracing.
- **-n**, **--dryrun**
Dry-run mode. Show the pipeline without executing.
With `-dd`, shows expanded command lines for each stage instead
of function names.
## Processing Options
- **-s** _STYLE_, **--style**=_STYLE_
Set the output style. Default is `nup`. Available styles:
- `nup` - Full pipeline: fold + table + nup paged output (default)
- `pager` - Fold + table, output to pager (`$PAGER` or `less`)
- `cat` - Fold + table, output to stdout
- `filter` - Table only (no fold, no nup), suitable for piping
- `raw` - Highlight only (no fold, no table, no nup)
The style sets the initial state of `--fold`, `--table`, and
`--nup` options. Subsequent options can override individual
settings:
mdee -s filter --fold file.md # filter + fold
mdee -p --no-fold file.md # pager without fold
- **-f**, **--filter**
Shortcut for `--style=filter`. Reads from stdin (or files) and
outputs highlighted Markdown to stdout. Disables line folding and
nup paged output, but keeps table formatting enabled. Useful for
piping Markdown content through mdee for syntax highlighting.
- **-p**, **--plain**
Shortcut for `--style=pager`. Enables fold and table formatting,
outputs through a pager (`$PAGER` or `less`) instead of nup.
- **--\[no-\]fold**
Enable or disable line folding for list items. When enabled, long
lines in list items are wrapped with proper indentation using
[ansifold(1)](https://metacpan.org/pod/App%3A%3Aansifold). Default is enabled.
Supported list markers: `*`, `-`, `1.`, `1)`, `#.`, `#)`.
The `#.` and `#)` forms are Pandoc's auto-numbered list syntax.
- **--\[no-\]table**
Enable or disable table formatting. When enabled, Markdown tables
are formatted using [ansicolumn(1)](https://metacpan.org/pod/App%3A%3Aansicolumn) for aligned column display.
Default is enabled.
- **--\[no-\]nup**
Enable or disable [nup(1)](https://metacpan.org/pod/App%3A%3Anup) for multi-column paged output. When
disabled, output goes directly to stdout without formatting.
Default is enabled.
- **--\[no-\]rule**
Enable or disable Unicode rule characters for table borders.
When enabled, ASCII pipe characters (`|`) are replaced with
Unicode box-drawing characters (`│`, `├`, `┤`, `┼`) and
dashes (`-`) in separator lines are replaced with horizontal
rules (`─`). Default is enabled.
- **-w** _N_, **--width**=_N_
Set the fold width for text wrapping. Default is 80.
Only effective when `--fold` is enabled.
## Theme Options
**em·dee** supports color themes for customizing syntax highlighting.
Themes define colors for various Markdown elements (headers, code blocks,
bold text, etc.).
- **-t** _NAME_, **--theme**=_NAME_\[,_NAME_,...\]
Select color themes. Multiple themes can be specified as
comma-separated names or by repeating the option. Each theme is
applied in order as a transformation to the default theme:
mdee --theme=warm file.md # warm base color
mdee --theme=warm,closing file.md # warm + closing hashes
mdee --theme=warm --theme=closing # same effect
Theme files are searched in the following order:
- 1. User theme directory: `${XDG_CONFIG_HOME:-~/.config}/mdee/theme/NAME.sh`
- 2. Share theme directory: installed with the distribution under `auto/share/dist/App-mdee/theme/`
Theme files are Bash scripts that modify `theme_light`
and/or `theme_dark` arrays directly:
# theme/warm.sh — change base color
theme_light[base]='=y25'
theme_dark[base]='=y80'
# theme/closing.sh — append closing hashes to h3-h6
for _mode in light dark; do
declare -n _theme="theme_${_mode}"
_theme[h3]+=';sub{s/(?` brackets or
other syntax), the default luminance adjustment is applied based on
the current mode:
-B RoyalBlue # becomes =y25 in light mode
# becomes =y80 in dark mode
This makes it easy to try different colors without worrying about
luminance values. The default adjustments (`=y25` for light, `=y80`
for dark) are designed to provide good contrast against typical terminal
backgrounds.
**Full color specification** - used exactly as specified:
If you include `<>` brackets, luminance modifiers, or use RGB
notation, the value is used as-is without any automatic adjustment:
-B '' # original color, no adjustment
-B '=y50' # explicit luminance 50
-B '#780043' # burgundy in hex
-B '(120,0,67)' # same color in RGB decimal
**Customizing the default adjustment**:
The automatic luminance adjustment values can be customized with the
`--adjust` option:
--adjust light='=y30' # use =y30 instead of =y25 for light mode
--adjust dark='=y70' # use =y70 instead of =y80 for dark mode
**Note**: Basic ANSI color codes (`R`, `G`, `B`, etc.) cannot be used
because heading variations require luminance adjustment, which only works
with full color specifications (X11 names, RGB hex, or RGB decimal).
- **--list-themes**
List available themes with color samples and exit.
## Highlight Options
- **--show**=_FIELD_\[=_VALUE_\],...
Control field visibility for highlighting. Empty value or `0` disables
the field; any other value (including `1`) enables it.
--show italic # enable italic
--show bold=0 # disable bold
--show all # enable all fields
--show all= --show bold # disable all, then enable only bold
Multiple fields can be specified with commas or by repeating the option.
The special field `all` affects all fields and is processed first.
Available fields: `comment`, `bold`, `italic`, `strike`, `h1`,
`h2`, `h3`, `h4`, `h5`, `h6`, `inline_code`, `code_block`,
`link`, `image`, `image_link`.
All fields are enabled by default.
## Layout Options (passed to nup)
- **-C** _N_, **--pane**=_N_
Set the number of columns (panes).
- **-R** _N_, **--row**=_N_
Set the number of rows.
- **-G** _CxR_, **--grid**=_CxR_
Set grid layout. For example, `-G2x3` creates 2 columns and 3 rows.
- **-P** _N_, **--page**=_N_
Set the page height in lines.
- **-S** _N_, **--pane-width**=_N_
Set the pane width in characters. Default is 85.
- **--bs**=_STYLE_, **--border-style**=_STYLE_
Set the border style.
## Pager Options
- **--\[no-\]pager**\[=_COMMAND_\]
Set the pager command. Use `--pager=less` to specify a pager,
or `--no-pager` to disable paging.
# CONFIGURATION
User configuration is loaded from:
${XDG_CONFIG_HOME:-~/.config}/mdee/config.sh
This is a shell script that can set defaults and override colors:
# ~/.config/mdee/config.sh
default[mode]='dark' # set default mode
default[theme]='warm,closing' # set default theme(s)
default[style]='pager' # set default style
default[width]=100 # set default fold width
default[base_color]='DarkCyan' # set default base color
The `default` associative array supports the following keys:
- `default[mode]` - Corresponds to `--mode` (e.g., `dark`, `light`)
- `default[theme]` - Corresponds to `--theme` (e.g., `warm`, `warm,closing`)
- `default[style]` - Corresponds to `--style` (e.g., `pager`, `cat`)
- `default[width]` - Corresponds to `--width` (e.g., `100`)
- `default[base_color]` - Corresponds to `--base-color` (e.g., `DarkCyan`)
**Overriding theme colors**
Config.sh can modify theme arrays directly, using the same mechanism
as theme files:
# Change base color for both modes
theme_light[base]='=y25'
theme_dark[base]='=y80'
# Append to both light and dark using declare -n
for _array in theme_light theme_dark; do
declare -n _theme=$_array
_theme[h3]+=';sub{s/(?`)
Code block detection follows the CommonMark specification:
- Opening fence: 0-3 spaces indentation, then 3+ backticks or tildes
- Closing fence: 0-3 spaces indentation, same character, same or more count
- Backticks and tildes cannot be mixed (```` ``` ```` must close with ```` ``` ````)
#### Text Folding
The second stage wraps long lines in list items using [ansifold(1)](https://metacpan.org/pod/App%3A%3Aansifold)
via [Greple::tee](https://metacpan.org/pod/Greple%3A%3Atee). It preserves ANSI escape sequences and maintains
proper indentation for nested lists.
Recognized list markers include `*`, `-`, `1.`, `1)`, `#.`,
and `#)`. The `#` marker is Pandoc's auto-numbered list syntax.
The folding width is controlled by `--width` option (default: 80).
#### Table Formatting
The third stage formats Markdown tables using [ansicolumn(1)](https://metacpan.org/pod/App%3A%3Aansicolumn).
Tables are detected by the pattern `^(\|.+\|\n){3,}` and formatted
with aligned columns while preserving ANSI colors.
### Output Stage
The final stage uses [nup(1)](https://metacpan.org/pod/App%3A%3Anup) to provide multi-column paged output.
Layout options (`--pane`, `--row`, `--grid`, `--page`) are passed
directly to nup.
## Theme System
**em·dee** implements a theme system where themes are transformations
applied to the built-in default theme. Multiple themes can be
chained via `--theme=NAME1,NAME2,...`.
### Theme Structure
The built-in default theme is defined as `theme_light` and
`theme_dark` associative arrays. Dark inherits undefined
keys from light immediately after declaration. Theme files modify
these arrays directly:
# theme/warm.sh
theme_light[base]='=y25'
theme_dark[base]='=y80'
#### Base Color Expansion
The `${base}` placeholder is expanded to the effective base color
after theme loading. The base color is determined by the
`--base-color` option (default: RoyalBlue) with automatic luminance
adjustment based on mode (`=y25` for light, `=y80` for dark).
### Color Specifications
Colors are specified using [Term::ANSIColor::Concise](https://metacpan.org/pod/Term%3A%3AANSIColor%3A%3AConcise) format.
The `--cm` option maps colors to captured groups. For example,
`L00DE/${base}` specifies gray foreground on base-colored background.
The color specification supports modifiers:
- `+y10` / `-y10`: Adjust luminance by percentage
- `=y50`: Set absolute luminance
- `D`: Bold, `U`: Underline, `E`: Erase line
### Terminal Mode Detection
**em·dee** uses [Getopt::EX::termcolor](https://metacpan.org/pod/Getopt%3A%3AEX%3A%3Atermcolor) to detect terminal background
luminance. If luminance is below 50%, dark mode is automatically
selected.
# LIMITATIONS
## HTML Comments
Only HTML comments starting at the beginning of a line are highlighted.
Inline comments are not matched to avoid conflicts with inline code
containing comment-like text (e.g., `` `` ``).
## Emphasis
Emphasis patterns (bold and italic) do not span multiple lines.
Multi-line emphasis text is not supported.
## Links
Link patterns do not span multiple lines. The link text and URL must
be on the same line.
Reference-style links (`[text][ref]` with `[ref]: url` elsewhere)
are not supported.
## OSC 8 Hyperlinks
Links are converted to OSC 8 terminal hyperlinks for clickable URLs:
- `[text](url)` - `[text]` links to url
- `` - `![alt]` links to url (image)
- `[](url)` - `!` links to img, `[alt]` links to url
This requires terminal support. Compatible terminals include iTerm2,
Kitty, WezTerm, Ghostty, and recent versions of GNOME Terminal.
Apple's default Terminal.app does not support OSC 8.
When using `less` as pager, version 566 or later is required with
`-R` option.
For OSC 8 specification, see:
[https://gist.github.com/egmontkob/eb114294efbcd5adb1944c9f3cb5feda](https://gist.github.com/egmontkob/eb114294efbcd5adb1944c9f3cb5feda)
## Less Environment Variables
When `less` is used as pager (either directly via `--style=pager` or
through `nup`), the following environment variables affect behavior.
**mdee** sets defaults for these when they are not already defined:
- `LESS`
Default: `-R`. The `-R` option is required for ANSI color
sequences to be displayed correctly.
- `LESSANSIENDCHARS`
Default: `mK`. This tells `less` to recognize ANSI sequences
ending with `m` (SGR color) and `K` (erase line). The erase line
sequence is used for background color rendering.
If you already have these variables set in your environment, **mdee**
does not override them.
# SEE ALSO
[nup(1)](https://metacpan.org/pod/App%3A%3Anup), [greple(1)](https://metacpan.org/pod/App%3A%3AGreple), [ansifold(1)](https://metacpan.org/pod/App%3A%3Aansifold), [ansicolumn(1)](https://metacpan.org/pod/App%3A%3Aansicolumn)
# AUTHOR
Kazumasa Utashiro
# LICENSE
Copyright 2026 Kazumasa Utashiro.
This software is released under the MIT License.
[https://opensource.org/licenses/MIT](https://opensource.org/licenses/MIT)