Getting Started

Writing Doxygen

Doxygen comments and settings that render cleanly with Moxygen

Moxygen works best when Doxygen is used as the parser, not as the final renderer. Write normal Doxygen comments, generate XML, then let Moxygen turn that XML into Markdown your docs site can own.

This page describes the Doxygen input patterns that produce good Moxygen output.

Doxyfile settings

Start with XML output enabled:

GENERATE_XML = YES
XML_OUTPUT = xml
XML_PROGRAMLISTING = YES
MARKDOWN_SUPPORT = YES

XML_PROGRAMLISTING lets Doxygen include source listings in the XML. Moxygen renders those as fenced code blocks and uses the filename extension as the fence language when Doxygen provides one.

If you want private members in the generated Markdown, Doxygen must emit them first:

EXTRACT_PRIVATE = YES

For grouped output, keep the XML directory and source tree relationship clear. If Doxygen emits sparse group XML for file-level @addtogroup blocks or @file comments with @ingroup, pass --source-root so Moxygen can inspect the source comments that Doxygen left out of the group compound XML.

moxygen --groups \
  --source-root /path/to/project/src \
  --output api-%s.md \
  /path/to/doxygen/xml

Classes and members

Use @brief for the summary row, then write normal paragraphs for the member body. @param entries become a parameter table when they include descriptions.

/// HTTP client used by the runtime.
///
/// Client owns the connection pool and retries transient network errors.
class Client {
public:
  /// Opens a session.
  ///
  /// The session stays valid until it is closed or the client is destroyed.
  ///
  /// @param url Remote endpoint URL.
  /// @param timeoutMs Connect timeout in milliseconds.
  /// @return true when the session was opened.
  /// @warning This call may block while DNS resolves.
  bool open(std::string_view url, int timeoutMs);
};

Moxygen uses this data in two places:

  • Summary tables use @brief or the first useful sentence.
  • Member pages include the signature, body text, parameter table, return section, and warning or note blocks.

Pages

Doxygen pages are useful for guides, build instructions, and conceptual docs that should live beside API reference.

/**
 * @page build Build
 *
 * # Build
 *
 * ## Linux
 *
 * ```bash
 * cmake -S . -B build
 * cmake --build build
 * ```
 *
 * @anchor build-options
 *
 * Options:
 *
 * - `BUILD_TESTING`
 * - `CMAKE_BUILD_TYPE`
 */

Run with --pages to write page output:

moxygen --pages --output api.md /path/to/doxygen/xml

Headings, anchors, lists, tables, links, and code blocks are all rendered from the XML Doxygen emits for these pages.

Groups

Use Doxygen groups when you want module-style output instead of one large API file.

/// @defgroup transport Transport
/// Types and functions for transport devices.
/// @{

/// @brief Bicycle transport.
class Bicycle {};

/// @}

For explicit group XML, this is enough:

moxygen --groups --output api-%s.md /path/to/doxygen/xml

For file-level grouping where Doxygen keeps the real class and namespace ownership outside the group XML, add --source-root. See Grouping Modes for the full behavior.

What renders well

This table starts from the comments users write. The XML column is included for debugging and issue reports.

Doxygen inputXML Doxygen emitsMoxygen output
@briefbriefdescriptionSummary text for tables and page metadata
Paragraphs and Markdowndetaileddescription, paraNormal Markdown prose
@paramparameterlist kind="param"Member parameter table when descriptions are present
@return / @returnssimplesect kind="return"Returns section
@warning, @attentionsimplesect kind="warning" / attentionWarning block
@note, @remarksimplesect kind="note" / remarkNote block
@deprecatedsimplesect kind="deprecated"Warning block marked deprecated
@seesimplesect kind="see"See also line
@sincesimplesect kind="since"Since line
@ref, \refrefInternal Markdown link, resolved to the right file and anchor
Markdown linksulinkExternal or relative Markdown link
Markdown headings / Doxygen sectionssect1 through sect6, titleMarkdown headings with optional anchors
@anchoranchorPandoc or HTML anchor when anchor output is enabled
Markdown listsorderedlist, itemizedlist, listitemOrdered and unordered Markdown lists
Variable listsvariablelist, varlistentry, termBold term with description text
Markdown tablestable, row, entryMarkdown table
Fenced code / @code / source listingsprogramlisting, verbatimFenced code block
Inline emphasis, bold, codeemphasis, bold, computeroutputMarkdown emphasis, bold, and inline code
FormulasformulaInline math or fenced display math
En dash, em dash, line breaksndash, mdash, linebreakMarkdown-safe HTML entity or line break
Classes, structs, unions, interfacescompounddef kind="class" / struct / union / interfaceType page with member sections
Enums and enum valuesmemberdef kind="enum", enumvalueEnum signature and value table
Groupscompounddef kind="group"Group/module page when --groups is enabled

Known gaps

Moxygen does not try to mirror every Doxygen HTML feature. The goal is clean Markdown API docs.

The main gaps are:

  • Diagrams and media-oriented tags such as image, dot, msc, and plantuml are not converted into generated assets.
  • Doxygen bookkeeping tags such as indexentry, toclist, language, and copydoc are not first-class output features.
  • Full named-entity coverage is not exhaustive, though common page punctuation such as mdash, ndash, and linebreak is handled.
  • Template parameter docs may appear in the rendered detail text, but they are not promoted into a separate structured table like function parameters.

If output looks wrong, run without --quiet. Unsupported XML tags are reported as warnings so you can see exactly what Doxygen emitted.