This is my personal Doxygen cheatsheet: Its initial (and primary) purpose is to be a compact help on this topic for myself.
It’s not meant as a general introduction or comprehensive reference for this tool, but it is meant to be a small knowledge base or collection of basics & “gotchas”, often-used commands, snippets, tips, and instructions on how to do certain tasks.
First steps
-
Download and install Doxygen.
-
Create a configuration file:
doxygen -g [<ConfigFilename>]
The filename is optional; if omitted, the default name Doxyfile will be used.
The configuration file can be customized, see below. -
Generate the documentation:
doxygen [<ConfigFilename>]
The filename is optional; if omitted, the default name Doxyfile will be used.
Assumes that the source code has been prepared, see below.
Configuration
I use a customized input file (Doxyfile.in), that file relies on a CMake build process to replace some variables/placeholders (which is automatically done in my standard setup).
Build quiet/silent
If you don’t want all the “noise” on the command line output:
QUIET = YES
Input
Doxygen needs to know, which files and directories it should investigate:
INPUT = <repo>/ReadMe.md <repo>/src/ ...
RECURSIVE = YES
GENERATE_TREEVIEW = YES
- One can specify particular files or whole directories (path items must be seperated by spaces).
- Enable recursion, so that all files beneath e.g. the CMAKE_SOURCE_DIR should be checked.
- A treeview might also be helpful, if more files are added.
Related:
The
EXCLUDE
tag can be used to specify files and/or directories that should be excluded from the INPUT source files.
Or better:
If the value of the
INPUT
tag contains directories, you can use theEXCLUDE_PATTERNS
tag to specify one or more wildcard patterns to exclude certain files from those directories.
Documenting the Source Code
First off, I actually use this mainly as a broad guideline/orientation on how to write and structure comments in the source code itself, for myself; the fact that Doxygen can “additionally” generate nice looking documentation in multiple other output formats is currently just a nice bonus 😄
By the way: My comment style has been heavily inspired by Powershell’s comment-based help over the last couple of years. It doesn’t fit C++ or Doxygen 100%, but it’s a good orientation mark for me.
Tip: Since Doxygen 1.8.0 Markdown can be used as a plain text formatting syntax in the source code comments as well as in custom pages (see below); its by default enabled in the Doxyfile.
Tip: Use \n
to force a new line in the generated HTML output.
Special comment block (before)
A special comment block marks the comment therein for Doxygen.
There are multiple ways to denote blocks and commands; I prefer the “Qt style”, using the exclamation mark (!
) and at sign (@
):
/*!
Text for doxygen...
*/
//!
//! At least two lines are required for this version to work!
//!
Important: If you have very simple source code file (where Doxygen can’t detect things automatically),
there needs to be at least one special comment block (see below) with a @file
command in it.
Otherwise, Doxygen won’t pick up this file at all and global stuff in it (like functions, variables, etc.) won’t show up in the generated pages!
/*!
@file
@authors Name 1, Name 2
@copyright © 2025 Name (address@example.net)
@license SPDX-License-Identifier: ...-... (see LICENSE.txt).
*/
Within a special comment block, a Doxygen section is marked (tagged) with either @sectionname
or \sectionname
commands
(I prefer the @
symbol).
A few things also work automatically, without these tags (e.g. a brief line or details), if the configuration fits; see the Doxygen docu for more – but I usually prefer to make it distinctively clear (with a command/tag), what the section/paragraph is about.
Normally a section is valid until a blank line or the start of another section is encountered;
but there are also exceptions to the first rule (blank line); the @details
section for example can consist
of multiple paragraphs (that are separated by a blank line, see below).
Same-line comments (after members)
Same-line Doxygen comments (also known as “documentation after members”)
can also be used.
As usual, multiple ways/styles are possible; applying the Qt-Style (!<
) is just one way.
int a; //!< This comment is for this line item.
int b; /*!< Another documentation after a member. */
These “same-line” blocks can only be used to document members and parameters; they cannot be used to document files, classes, unions, structs, groups, namespaces, macros or enums!
Commands
The essentials
This is a small excerpt that includes a lot of the standard keywords and structure that I would use to comment a function (template), for example:
/*!
@brief (or @short)
A short abstract/summary (one line) of the content/functionality of this item (file, function or class, etc.)
@details
A more extensive description.
Can consist of multiple paragraphs.
@authors Names of the authors (on a single line!)
@author Name 1 (Multiple entries will be combined
@author Name 2 as separate lines under one heading)
@param P Describes the parameter named "P".
@tparam T Describes a template parameter named "T".
@param [in] PI
Describes an input parameter with the name "PI".
@param [out] PO
Describes an output parameter with the name "PO".
@param[in,out] PIO
Describes an input/output parameter with the name "PIO".
A note on lengthy parameter description:
Tested and failed; found https://developer.lsst.io/cpp/api-docs.html#cpp-doxygen-parameters>:
> Doxygen will not properly parse parameter descriptions that have multiple paragraphs.
> If your function's input requires a lengthy explanation, put the explanation in the Notes
> and refer to it from the parameter descriptions.
@return (or @returns or @result)
The description of what will be returned (by a function)/what will be the result (of a function).
@retval <return value>
The description of the returned value.
@throws (or @throw or @exception) <exception-object>
A text that desecribes the thrown exception more...
*/
Other, often used commands and tags
Special parapgraphs
Command | Description |
---|---|
@attention |
manual |
@warning |
manual |
@bug |
manual |
@fixme |
A custom alias in my Doxyfile |
@deprecated |
manual |
@important |
manual |
@note |
manual |
@remark |
manual |
@todo |
manual |
Authorship, dates, versions
Command | Description |
---|---|
@version |
|
@date |
|
@copyright |
|
@license |
Custom aliases in my Doxyfile, based on this GitHub Gist |
- Examples for the license command/alias:
/*! @license Licensed under the Xyz License (see LICENSE.txt). @license{The Xyz License} Permission to use, copy, modify, and/or distribute this software for any purpose with or without fee is hereby granted. @licenseblock Licensed under the Xyz License. ... block with multiple paragraphs... @endlicenseblock @licenseblock{The Xyz License} Permission is hereby granted, free of charge, to any person obtaining a copy ... block with multiple paragraphs... @endlicenseblock */
Other
Command | Description |
---|---|
@test |
Text describing a test case. |
@see |
A “see also” note; cross-references to classes, functions, methods, variables, files or URL… |
More:
Command | Description |
---|---|
@struct |
to document a structure. |
@union |
to document an union. |
@enum |
to document an enumeration type. |
@fn |
to document a function. |
@var |
to document a variable or typedef or enum value. |
@def |
to document a pre-processor definition. |
@typedef |
to document a type definition. |
@file |
to document a file. |
@namespace |
to document a namespace (e.g. @namespace NiftyOddity::Toolkit::CLI::Utilities ) |
- Note on
@namespace
: - Doxygen 1.9.3 makes a difference between C++17 nested namespaces “with spaces/without spaces”
and build two different hierarchies (with the same display name) – weird stuff:
/*! @namespace NiftyOddity::Toolkit::CastConvert ... @namespace NiftyOddity :: Toolkit :: CastConvert ... */ namespace NiftyOddity::Toolkit::CastConvert { /*...*/ } namespace NiftyOddity :: Toolkit :: CastConvert { /*...*/ }
Common features of all the above:
- The text of the paragraph has no special internal structure.
- All visual enhancement commands may be used inside the paragraph.
- Multiple adjacent commands (of the same kind) will be joined into a single paragraph.
- The command/section ends when a blank line or some other sectioning command is encountered.
Mark a (small) code snippet:
/*!
@code
// Some short code excerpt:
int a = func(3,0,5);
@endcode
*/
For internal use only
/*!
@internal
Some internal comment that should not appear in the generated (public) documentation
... unless INTERNAL_DOCS is set to YES in the Doxyfile! (The default is NO)
@endinternal
*/
Including an example
/*!
@example <filename>
*/
But this works a bit different then what I first assumed:
- This indicates that a comment block contains documentation for a source code example from
<filename>
- The contents of this file (as a whole!) will be included in the documentation (after the text in this block)!
- The filename will be searched according to the value of EXAMPLE_PATH in the Doxyfile.
Lists
Tip: Better not use asterisks (*
) for lists, they may get removed (see the entry in the manual)
/*!
Unordered & nested:
- item 1
- item 1.a
- item 2
Ordered (& multiline):
1. item 1\n
Continued...
2. item 2
Checklist:
- [ ] Unchecked
- [x] Checked
*/
Tables
Tables can be included in either in HTML format (verbose/distracting) or in the simpler Markdown syntax:
/*!
Column 1 Header | Column 2 Header
---------------- | -------------
Cell Content | Cell Content
Cell Content | Cell Content
*/
Don’t repeat yourself, use @copy*
@copydoc <WHAT_TO_COPY>
@copybrief <WHAT_TO_COPY>
@copydetails <WHAT_TO_COPY>
If in doubt that Doxygen will use the correct item, be specific:
Full namespace, no return value, no parameters, parantheses without space!
Example: @copydoc NamespaceOrClass1::NamespaceOrClass2::function_name()
- Example
- If in the Doxyfile, two input directories have been set up, then Doxygen knows where to look stuff up:
- C:\devel\git\TheNiftyOddityToolkit\
- C:\devel\git\TheNiftyOddityToolkit\src\
@copybrief KeyboardLED.h --> A file with that name only exists once (for Doxygen). @copybrief KeyboardLED/KeyboardLED.h --> Specifycing a (relative/partial) path also works. | +--> Means file C:\devel\git\TheNiftyOddityToolkit\src\KeyboardLED\KeyboardLED.h
Pages
Additional Documentation (that is not directly related to one specific class, file or member) can also be included as custom pages.
Supported file extensions for these are .dox
, .txt
or .md
.
Weirdly though, Doxygen will treat *.dox
or *.txt
files as C/C++ source code, but *.md
files as Markdown.
By default Doxygen won’t know about these files; use INPUT
(see above) to point it.
If you specify the src directory there and enable recursion, then other *.md
files in its subdirectories
(e.g. a directory-specific ReadMe.me) will also be picked up by Doxygen (but the name in the filelist/filetree will not be
like the Markdown heading!).
Main page (index page)
This command in a special comment block marks it as custom content for the main/index page:
/*!
@mainpage The Title
...
*/
But instead of this, I usually specify in my Doxyfile the repository’s top-level ReadMe markdown file
as its main page (note that *_REPO_ROOT_DIR
is a custom variable in my CMakeLists.txt):
USE_MDFILE_AS_MAINPAGE = ${${CMAKE_PROJECT_NAME}_REPO_ROOT_DIR}/ReadMe.md
Custom Pages
- The command
@page
can be used in the source code to define custom pages (incl. sections, sub[-sub-]sections and a TOC). - Pages can also be grouped by subpaging (
@subpage
). - The command
@ref
can be used to links to named symbols, files, sections/subsections, pages or anchors.
/*!
@page page1 A documentation page
Leading text.
@tableofcontents
@section sec An example section
This page contains the subsections @ref subsection1 and @ref subsection2.
For more info see page @ref page2.
@subsection subsection1 The first subsection
Text.
@subsection subsection2 The second subsection
More text.
@subsubsection subsection2 A subsection to a subsection
Text for the sub-subsection.
*/
/*!
@page page2 Another page
Even more info.
*/
Customization (output format, layout & style)
Disclaimer: Doxygen can output, directly or indirectly, several formats; at the moment, I’m only interested in the generated HTML output!
The default layout and colors of generated Doxygen documentation looks a bit, hmmm, “functional” or “expedient”: It’s not bad, but the look and feel can seem a bit dull and dated…
But fear not, there are ways the change (customize) the layout and style: https://www.doxygen.nl/manual/customize.html
–> TODO
Further reading
Film & Television (54)
How To (63)
Journal (17)
Miscellaneous (4)
News & Announcements (21)
On Software (12)
Projects (26)