My favorite emacs theme.
Go to file
Protesilaos Stavrou 3406e29e82
Upgrade to version 0.9.0
This entry records the changes since version 0.8.0 (2020-04-28).  The
present release contains about 50 commits, covering a month of active
development.

All changes are aligned with the primary objective of this project,
which is conformance with the WCAG AAA accessibility standard for colour
contrast.  This translates to a minimum contrast ratio of 7:1 between a
given combination of foreground and background colours.  The highest
standard of its kind.

All customisation options that are booleans are off ('nil') by default.
The project's policy is to offer such features on an "opt-in" basis,
while always respecting the principle of least surprise.

Refer to the README for further information on the exact names of
symbols and the like.

New customisation options
-------------------------

+ It is now possible to make the faces of Icomplete, Ido, and a few
  other related tools such as 'orderless', use coloured backgrounds to
  style their feedback.  This is the aesthetic already in effect for
  Ivy, Helm, and Selectrum.  The default is more subtle, in that it uses
  just an accented foreground value without any added background.

+ Advanced users can now override both the exact values of colour
  variables, as well as the mapping of properties/variables to faces.
  In practice this means that it is possible to completely change parts
  of the theme (or the entirety of it for that matter).  It also means
  that users can simply access the theme's palette for the sake of
  correctly passing the appropriate value to some bespoke face of
  theirs.

+ An extra increment for scaled headings is now available.  This should
  hold the highest value on the scale.  Such variables only take effect
  when the user opts for the "scaled headings" option.

Overview of changes
-------------------

+ A set of internal reforms were carried through in order to allow the
  colour palette to be accessed from user configuration files.  This
  required a lot of debugging work to make sure the themes compile
  properly and performance is not affected.

  - The original idea for this redesign was suggested by Len Trigg in
    issue 39: https://gitlab.com/protesilaos/modus-themes/-/issues/39.
    Len also provided a real-world implementation of this new option,
    which is included in the project's README.

  - André Alexandre Gomes helped figure out the problems caused by the
    initial design of this feature.  In particular, André identified a
    performance penalty as well as errors pertaining to byte
    compilation.  Everything was eventually resolved.  For more see
    issue 44: https://gitlab.com/protesilaos/modus-themes/-/issues/44.

+ Several org-mode faces were reviewed in order to cope well with mixed
  font settings.  This is about use-cases where the main typeface is
  proportionately-spaced, either by default or by some minor mode like
  the built-in 'variable-pitch-mode'.  The intent of configuring those
  faces is to make them always inherit a fixed-pitch (monospace) font
  family, in the interest of preserving the alignment of elements.  The
  idea, suggested code, as well as user feedback were offered by Ben in
  issue 40: https://gitlab.com/protesilaos/modus-themes/-/issues/40.

+ Mixed font settings may have some side-effects depending on user
  configurations.  This is unavoidable as we cannot control how users
  define their fonts.  Mark Barton reported one such case, while he was
  able to fix it by making use of the suggested typeface definitions.
  See issue 42: https://gitlab.com/protesilaos/modus-themes/-/issues/42.

+ The faces for the 'tab-bar-mode' and 'tab-line-mode' that ship with
  Emacs 27 were written anew.  Same for those of 'centaur-tabs'.  The
  ideas for the redesign as well as the overall aesthetic are Ben's, per
  issue 41: https://gitlab.com/protesilaos/modus-themes/-/issues/41.

+ An edge case with Helm's interpretation of colour values for its
  ripgrep interface was reported by Manuel Uberti in issue 49:
  https://gitlab.com/protesilaos/modus-themes/-/issues/49.  It
  essentially had to do with the syntax for the regexp engine as read by
  the underlying 'rg' executable.  Collaboration on that front
  eventually led to fixes in Helm itself, committed by its maintainer.
  Note that the README for the Modus themes already contains information
  on how Helm applies a face to the matches of grep or grep-like
  commands.  Issue 49 confirmed what was already known in that regard
  (i.e. that the "--color=never" command-line option is required to use
  the Helm face, else a colour value from the ANSI colour vector is
  used---both are supported by the themes).

+ The faces for Flycheck, Flymake, and Flyspell that would apply an
  underline effect were completely rewritten to account for relevant
  differences between GUI and TUI Emacs.

  - For GUI Emacs, all affected faces will now just use a colour-coded
    wavy underline.  Empowered by the introduction of dedicated
    linter-related colours in prior commits (for version 0.8.0), we no
    longer have to change the foreground value of the offending text in
    addition to applying the underline effect.  Whereas before the text
    would also get repainted, which was too intrusive in most
    circumstances.

  - If support for wavy underlines is not available, we assume the
    presence of a TUI, which generally is relatively more limited in its
    ability to reproduce colours with precision (meaning that the
    dedicated linter colour could be distorted, potentially producing
    inaccessible combinations).  So for those cases we apply a straight
    underline combined with a colour-coded foreground for the affected
    text.  This makes it more intense compared to the GUI equivalent,
    but is the necessary course of action to overcome the constraints
    imposed by the underlying terminal.

+ The palette of Modus Operandi underwent lots of subtle changes to make
  the background value of hl-line-mode more visible while retaining the
  overall style and character of the theme.  In principle, you should
  not be able to tell the difference, unless presented with a careful
  side-by-side comparison.  This is the comprehensive report, including
  a reproducible org-mode document with all the relevant contrast ratios:
  https://protesilaos.com/codelog/2020-05-10-modus-operandi-palette-review/.

+ Fixed `org-hide' to actually "hide" by using the appropriate colour
  value.

+ Several other face groups received minor tweaks.

+ The README was improved to better present the available customisation
  options and to cover other topics of interest.

+ Updated the screen shots and their description in the relevant Wiki
  page: https://gitlab.com/protesilaos/modus-themes/-/wikis/Screenshots.

Added support for
-----------------

+ circe
+ el-search
+ eros
+ golden-ratio-scroll-screen
+ highlight-indentation
+ hyperlist
+ indium
+ journalctl-mode
+ minimap
+ nxml-mode
+ vdiff
+ yasnippet
2020-06-04 14:26:56 +03:00
.gitignore Add missing newline char in end of file 2020-04-09 11:35:50 +03:00
CHANGELOG.org Upgrade to version 0.9.0 2020-06-04 14:26:56 +03:00
COPYING Rename LICENSE to the more appropriate COPYING 2019-09-28 08:55:54 +03:00
modus-operandi-theme.el Upgrade to version 0.9.0 2020-06-04 14:26:56 +03:00
modus-vivendi-theme.el Upgrade to version 0.9.0 2020-06-04 14:26:56 +03:00
README.org Add support for NXML-MODE 2020-06-03 13:09:11 +03:00

Modus Themes for GNU Emacs

Overview

This is a set of accessible themes for GNU Emacs. The contrast ratio between foreground and background values should always be >= 7:1, which conforms with the WCAG AAA accessibility standard. This is the highest standard of its kind.

The Modus themes project consists of two standalone items, one where dark text is cast on a light backdrop (Modus Operandi) and another where light text is displayed against a dark background (Modus Vivendi).

The themes are highly customisable and can be made to look much different than their default austere aesthetic. Make sure to read the section on the customisation options.

Links with demo content

Check the Wiki page with the screen shots. There are lots of scenaria on display that draw attention to details and important aspects in the design of the themes. They also showcase the numerous customisation options.

Also note that I use these themes in my Emacs-related screen casts (although older videos contain earlier, "alpha" versions).

Install and auto-load

Install the packages

I maintain Modus Operandi (light theme) and Modus Vivendi (dark) as standalone packages in ELPA, MELPA, and MELPA Stable.

Just run:

M-x package-install RET modus-operandi-theme RET

And/or:

M-x package-install RET modus-vivendi-theme RET

To be clear, that sequence means:

  • press `Meta-X'
  • type `package-install'
  • hit the Return key
  • type the name of the package
  • hit Return to confirm your choice

Remember to refresh your package lists (M-x package-refresh-contents or M-x list-packages), in case Emacs complains that a package is no longer available.

With `use-package'

For a declarative approach with use-package, you can write something like this (also see the customisation options for how to expand this):

(use-package modus-operandi-theme
  :ensure t)

(use-package modus-vivendi-theme
  :ensure t)

Manual installation method

Download the files in this repository ending in *-theme.el and place them in an appropriate directory, such as ~/.emacs.d/themes/. To make sure the filesystem path of your choice is read by Emacs, insert the following in your initialisation file:

(add-to-list 'custom-theme-load-path "~/.emacs.d/themes/")

Load automatically

To load the theme from your Emacs initialisation file use the relevant snippet:

(load-theme 'modus-operandi t)          ; Light theme
(load-theme 'modus-vivendi t)           ; Dark theme

Make sure to remove any other theme that is being loaded, otherwise you might run into unexpected issues (you can also M-x disable-theme).

Load depending on the time of the day

This is a neat trick contributed by b3n on r/emacs. It will select the appropriate theme based on the time of the day and it will also switch themes when the time comes.

;; Light for the day
(load-theme 'modus-operandi t t)
(run-at-time "05:00" (* 60 60 24) (lambda () (enable-theme 'modus-operandi)))

;; Dark for the night
(load-theme 'modus-vivendi t t)
(run-at-time "21:00" (* 60 60 24) (lambda () (enable-theme 'modus-vivendi)))

Note that the load-theme here is slightly different than the one in the section right above, because it does not enable the theme directly (the subsequent enable-theme does that when needed).

Customisation options

Both of the Modus themes expose variables that allow users to tweak how certain styles are configured. Check the Wiki with the screen shots to see how these will change things.

By default, all variables are deactivated (nil), meaning that you need to explicitly opt in like this:

(setq CUSTOMISATION-OPTION-NAME t)

;; example with "rainbow" headings for Modus Operandi:
(setq modus-operandi-theme-rainbow-headings t)

Put the point (cursor) exactly to the right of the closing parenthesis and use C-x C-e to evaluate each setq form individually, or the entire expression that holds it (e.g. a function or use-package declaration).

All customisation options must be declared before loading the theme, else they will not be parsed and have no immediate effect. To [re-]load a theme, you can evaluate either of these:

(load-theme 'modus-operandi t)
(load-theme 'modus-vivendi t)

Consult the section below with the complete example configuration for a fully fledged use-package declaration.

Option for distinct Org source blocks

  • modus-operandi-theme-distinct-org-blocks
  • modus-vivendi-theme-distinct-org-blocks

Use a distinct background for Org's source blocks and extend the background of their beginning and end lines to the edge of the window (the "extend" part is for Emacs versions >= 27, whereas before they would extend regardless).

The default is to use the same background as the rest of the buffer for the contents of the block, while beginning and end lines do not extend to the end of the window (again, the "extend" is for Emacs 27 or higher).

Option for colourful "rainbow" headings

  • modus-operandi-theme-rainbow-headings
  • modus-vivendi-theme-rainbow-headings

Apply more saturated colours to headings in org-mode and outline-mode while retaining all other heading properties (such as a bold weight and the optional scaled height —see relevant customisation toggle). The colours follow the rainbow's spectrum. In Org headings, some additional tweaks are made to adapt keywords (like "TODO") to the more vivid presentation.

The default uses a more frugal aesthetic for headings, letting their bold typography and the nuances between the various heading levels provide the elements of differentiation.

Option for sectioned headings

  • modus-operandi-theme-section-headings
  • modus-vivendi-theme-section-headings

Uses a background colour and an overline to mark section headings in org-mode and outline-mode. These attributes are applied in addition to the existing foreground colour and the bold weight and can, therefore, be combined with the "rainbow" headings option (as well as all the other options pertaining to headings). For Org several additional faces are configured accordingly, such as TODO keywords which gain a box style.

The default is to use only a subtle foreground and a bold weight for headings, while no boxes or {under,over}-line effects are present.

Note that the background for sectioned headings will extend to the edge of the window. To make it cover just the area occupied by the heading's text, use this:

(setq org-fontify-whole-heading-line nil)

Option for scaled headings

  • modus-operandi-theme-scale-headings
  • modus-vivendi-theme-scale-headings

Make headings larger in size relative to the main text. This is noticeable in modes like Org. The default is to use the same size for headers and body copy.

In addition to toggles for enabling scaled headings, users can also specify a number of their own.

  • If it is a floating point, say, 1.5, it is interpreted as a multiple of the base font size (there are many ways to set the main font in Emacs, such as those I documented in issue 43, though the most robust method is covered below in Font configurations for Org (and others)).
  • If it is an integer, it is read as an absolute font height. The number is basically the point size multiplied by a hundred. So if you want it to be 18pt you must pass 180.

Below are the variables in their default values, using the floating point paradigm. The numbers are very conservative, but you are free to change them to your liking, such as 1.2, 1.4, 1.6, 1.8, 2.0—or use a resource for finding a consistent scale, like modularscale.com:

(setq modus-operandi-theme-scale-1 1.05
      modus-operandi-theme-scale-2 1.1
      modus-operandi-theme-scale-3 1.15
      modus-operandi-theme-scale-4 1.2
      modus-operandi-theme-scale-5 1.3)

(setq modus-vivendi-theme-scale-1 1.05
      modus-vivendi-theme-scale-2 1.1
      modus-vivendi-theme-scale-3 1.15
      modus-vivendi-theme-scale-4 1.2
      modus-vivendi-theme-scale-5 1.3)

Note that in Org, scaling only increases the size of the heading, but not of keywords that are added to it, like "TODO". This is outside the control of the themes and I am not aware of any way to make such keywords scale accordingly (see issue 37).

Also note that in the latest tagged release (0.8.1) an Org file's #+TITLE will not scale at all. This has been fixed in master and will be available in version 0.9.0, which is expected in early June 2020 (the fix pertains to the introduction of *-scale-5).

Option for visible fringes

  • modus-operandi-theme-visible-fringe
  • modus-vivendi-theme-visible-fringe

When enabled, this will render the fringes in a subtle background colour.

The default is to use the same colour as that of the main background, meaning that the fringes are not obvious though they still occupy the space given to them by fringe-mode (8px on either side by default).

Option for more slanted constructs

  • modus-operandi-theme-slanted-constructs
  • modus-vivendi-theme-slanted-constructs

Choose to render more faces in slanted text (italics). This typically affects documentation strings and code comments.

The default is to not use italics unless it is absolutely necessary.

Option for more bold constructs

  • modus-operandi-theme-bold-constructs
  • modus-vivendi-theme-bold-constructs

Display several constructs in bold weight. This concerns keywords and other important aspects of code syntax. It also affects certain mode line indicators.

The default is to only use a bold weight when it is necessary.

Option for three-dimensional focused mode line

  • modus-operandi-theme-3d-modeline
  • modus-vivendi-theme-3d-modeline

Use a three-dimensional, "released button" effect for the focused window's mode line. When enabled, this option will also affect the styles of any inactive mode lines, making them slightly less intense in order to accommodate the added element of depth.

The default is to present the mode lines as rectangles with a border around them and with the active one having more intense colours than any inactive ones.

Option for subtle diffs

  • modus-operandi-theme-subtle-diff
  • modus-vivendi-theme-subtle-diff

Display diff-mode, ediff, smerge-mode, magit diff buffers with fewer and/or less intense background colours or, where possible, with no background colours applied to the presentation of the added and removed lines. Concerning magit, an extra set of tweaks are introduced for the effect of highlighting the current diff hunk, so as to remain consistent with the overall experience of that mode.

The default is to use colour-coded backgrounds for line-wise highlights. "Refined" changes (word-wise highlights) always use a background value which is, nonetheless, more subtle with this option than with its default equivalent.

Option for intense standard completions

  • modus-operandi-theme-intense-standard-completions
  • modus-vivendi-theme-intense-standard-completions

Display faces for built-in completion frameworks, such as icomplete, with a combination of background and foreground colours. This covers every completion interface that either is part of the upstream Emacs distribution or extends some built-in library. For example, orderless is a powerful completion style that can be used with core Emacs. So it also is covered by this customisation option.

With this enabled, Icomplete and others will use similar UI metaphors to those of ivy, helm, selectrum (among others).

The default is to only use foreground colour values for the various matching characters or items of standard completion tools.

Option for proportional fonts in headings

  • modus-operandi-theme-proportional-fonts
  • modus-vivendi-theme-proportional-fonts

Choose to apply a proportionately-spaced typeface to headings (such as in Org mode). The default is to use whatever the main typeface is, typically a monospaced family.

Though also read Font configurations for Org (and others) as the themes are designed to cope well with more prose-friendly typeface configurations (e.g. using a proportionately-spaced sans-serif font for the main text, while letting inline code and some other space-sensitive constructs use a monospaced font).

Complete example configuration for the above

This is a complete use-package declaration with Modus Operandi as an example. You can modify it to your preferences. Here we enable all variables before loading the theme. You can also see a different form of setq that sets the value of multiple variables at once: use one setq expression for each variable, if in doubt.

Do not forget to M-x package-refresh-contents to get your package list up-to-date, else the initial download may fail due to a newer version being available.

(use-package modus-operandi-theme
  :ensure t
  :init
  (setq modus-operandi-theme-slanted-constructs t
        modus-operandi-theme-bold-constructs t
        modus-operandi-theme-visible-fringes t
        modus-operandi-theme-3d-modeline t
        modus-operandi-theme-subtle-diffs t
        modus-operandi-theme-intense-standard-completions t
        modus-operandi-theme-distinct-org-blocks t
        modus-operandi-theme-proportional-fonts t
        modus-operandi-theme-rainbow-headings t
        modus-operandi-theme-section-headings t
        modus-operandi-theme-scale-headings t
        modus-operandi-theme-scale-1 1.05
        modus-operandi-theme-scale-2 1.1
        modus-operandi-theme-scale-3 1.15
        modus-operandi-theme-scale-4 1.2
        modus-operandi-theme-scale-5 1.3)
  :config
  (load-theme 'modus-operandi t))

Need more ideas? Check the Modus themes section of my dotemacs (though do not try to interpret the values of the variables, as I always test different combinations and scenaria).

Full access to the palette for further tweaks (advanced)

Unlike the previous options which follow a straightforward pattern of allowing the user to quickly select their preference, the themes also provide a more powerful, albeit difficult, mechanism of controlling things with precision.

Option 1 to redefine colour values

The variables are:

  • modus-operandi-theme-override-colors-alist
  • modus-vivendi-theme-override-colors-alist

Users can specify an association list that maps the names of colour variables to hexadecimal RGB values (in the form of #RRGGBB). This means that it is possible to override the entire palette or subsets thereof (see the source code for the actual names and values).

Example:

;; Redefine the values of those three variables for the given theme
(setq modus-vivendi-theme-override-colors-alist
      '(("magenta" . "#ffaabb")
        ("magenta-alt" . "#ee88ff")
        ("magenta-alt-other" . "#bbaaff")))

Option 2 to apply colour variables to faces

The macro symbols are:

  • modus-operandi-theme-with-color-variables
  • modus-vivendi-theme-with-color-variables

Users can wrap face customisation snippets inside this macro in order to pass the variables that the themes use and map them to face attributes. This means that one can essentially override or extend the original design (also in tandem with option 1).

Len Trigg who proposed the whole idea in issue 39 uses this method to tweak how a couple of Magit faces will look in GUI and terminal Emacs respectively (follow the link for screen shots and details). This is Len's sample package declaration (with comments by me):

(use-package modus-vivendi-theme
  :init                                 ; enable some of the customisation options before loading the theme
  (setq modus-vivendi-theme-visible-fringe t
        modus-vivendi-theme-3d-modeline t)
  :config
  (defun customize-modus-vivendi ()     ; function that passes further customisations to the theme
    "Customize modus-vivendi theme"
    (if (member 'modus-vivendi custom-enabled-themes)
        (modus-vivendi-theme-with-color-variables ; this macro allows us to access the colour palette
         (custom-theme-set-faces
          'modus-vivendi
          `(magit-branch-current ((((supports :box t)) (:foreground ,blue-alt-other :background ,bg-alt :box t)) ; use a box property if possible and also apply a background
                                  (t (:foreground ,blue-alt-other :background ,bg-alt :underline t)))) ; use an underline if the box is not available
          `(magit-branch-remote-head ((((supports :box t)) (:foreground ,magenta-alt-other :background ,bg-alt :box t))
                                      (t (:foreground ,magenta-alt-other :background ,bg-alt :underline t))))

          ))))
  (add-hook 'after-load-theme-hook 'customize-modus-vivendi) ; invoke the above function when appropriate in order to override the styles of the desired faces
  (load-theme 'modus-vivendi t))                             ; load the theme

Perhaps you want something simpler, such as a nice style for the cursor:

(modus-operandi-theme-with-color-variables
  (custom-theme-set-faces
   'modus-operandi
   `(cursor ((t (:background ,blue-alt))))))

(modus-vivendi-theme-with-color-variables
  (custom-theme-set-faces
   'modus-vivendi
   `(cursor ((t (:background ,red-alt))))))

The code for the bespoke after-load-theme-hook could be something like the following (courtesy of the Centaur Emacs project):

(defvar after-load-theme-hook nil
  "Hook run after a color theme is loaded using `load-theme'.")

(defun run-after-load-theme-hook (&rest _)
  "Run `after-load-theme-hook'."
  (run-hooks 'after-load-theme-hook))

(advice-add #'load-theme :after #'run-after-load-theme-hook)

If you need more ideas check how I configure the themes in my dotemacs. If something is not clear or not working as intended, please let me know.

Further considerations

Please understand that these customisation methods are meant for advanced users or those who are prepared to do their own research. If you think that the themes do not work well in some context you can inform me about it: maybe you do not need to carry your own customisations. We can just fix the issue in its source.

To harness the potential of this method you will need to study the source code of the themes. You can always open an issue in case you need some help. To support you in this task, try the rainbow-mode package which offers live colour previews. This is how I configure it:

(use-package rainbow-mode
  :ensure
  :diminish                             ; optional if you use `diminish'
  :commands rainbow-mode                ; optional
  :config
  (setq rainbow-ansi-colors nil)
  (setq rainbow-x-colors nil))

As for the means to check the contrast in perceived luminance between a foreground colour and its expected background combination, refer to the methods documented in my Modus Operandi theme subtle palette review (2020-05-10).

Font configurations for Org (and others)

The themes are designed to cope well with mixed font settings. Currently this applies to Org mode (courtesy of Ben in issue 40), though it may be extended to other major modes as well (e.g. markdown).

In practice it means that some parts of a buffer will use a monospaced font even when the user opts for a proportionately-spaced typeface as their default (such as by enabling variable-pitch-mode). This is to ensure that code blocks, tables, and other relevant elements use the appropriate type settings and are positioned correctly.

To make everything use your desired font families, you need to configure the variable-pitch (proportional spacing) and fixed-pitch (monospaced) faces respectively. Otherwise you may get unintended combinations (such as those experienced by Mark in issue 42).

Put something like this in your initialisation file:

(set-face-attribute 'variable-pitch nil :family "DejaVu Sans" :height 110)
(set-face-attribute 'fixed-pitch nil :family "Source Code Pro" :height 110)

You can also set your standard font the same way. For example:

(set-face-attribute 'default nil :family "Fira Code" :height 120)

The value of the :height attribute essentially is the point size × 100. So if you want to use Fira Code at point size 12, you set the height to 120. Values do not need to be rounded to multiples of ten, so the likes of 125 are perfectly valid.

If any Org power user is reading this section, I encourage you to recommend some other minimal tweaks and customisations that could improve the user experience.

Face coverage

This list will always be updated to reflect the current state of the project. The idea is to offer an overview of the known status of all affected face groups.

Full support

The items with an appended asterisk * tend to have lots of extensions, so the "full support" may not be 100% true…

  • ace-window
  • ag
  • alert
  • all-the-icons
  • annotate
  • anzu
  • apropos
  • apt-sources-list
  • artbollocks-mode
  • auctex and TeX
  • auto-dim-other-buffers
  • avy
  • bm
  • breakpoint (provided by built-in gdb-mi.el)
  • buffer-expose
  • calendar and diary
  • calfw
  • centaur-tabs
  • change-log and log-view (vc-print-log and vc-print-root-log)
  • cider
  • circe
  • color-rg
  • column-enforce-mode
  • company-mode*
  • company-posframe
  • compilation-mode
  • completions
  • counsel*
  • counsel-css
  • counsel-notmuch
  • counsel-org-capture-string
  • cov
  • csv-mode
  • ctrlf
  • custom (M-x customize)
  • dap-mode
  • dashboard (emacs-dashboard)
  • deadgrep
  • debbugs
  • define-word
  • deft
  • diff-hl
  • diff-mode
  • dim-autoload
  • dired
  • dired-async
  • dired-git
  • dired-git-info
  • dired-narrow
  • dired-subtree
  • diredfl
  • disk-usage
  • doom-modeline
  • dynamic-ruler
  • easy-jekyll
  • easy-kill
  • ebdb
  • ediff
  • eglot
  • el-search
  • eldoc-box
  • elfeed
  • elfeed-score
  • emms
  • enhanced-ruby-mode
  • epa
  • equake
  • erc
  • eros
  • ert
  • eshell
  • evil* (evil-mode)
  • evil-goggles
  • evil-visual-mark-mode
  • eww
  • eyebrowse
  • fancy-dabbrev
  • flycheck
  • flycheck-indicator
  • flycheck-posframe
  • flymake
  • flyspell
  • flyspell-correct
  • flx
  • freeze-it
  • frog-menu
  • focus
  • fold-this
  • font-lock (generic syntax highlighting)
  • forge
  • fountain (fountain-mode)
  • geiser
  • git
  • git-gutter (and variants)
  • git-lens
  • git-timemachine
  • git-walktree
  • gnus
  • golden-ratio-scroll-screen
  • helm* (also see section below on Helm's grep-related functions)
  • helm-ls-git
  • helm-switch-shell
  • helm-xref
  • helpful
  • highlight-blocks
  • highlight-defined
  • highlight-escape-sequences (hes-mode)
  • highlight-indentation
  • highlight-numbers
  • highlight-symbol
  • highlight-thing
  • hl-fill-column
  • hl-line-mode
  • hl-todo
  • hydra
  • hyperlist
  • ibuffer
  • icomplete
  • icomplete-vertical
  • ido-mode
  • iedit
  • iflipb
  • imenu-list
  • indium
  • info
  • info-colors
  • interaction-log
  • ioccur
  • isearch, occur, etc.
  • ivy*
  • ivy-posframe
  • jira (org-jira)
  • journalctl-mode
  • js2-mode
  • julia
  • jupyter
  • kaocha-runner
  • keycast
  • line numbers (display-line-numbers-mode and global variant)
  • lsp-mode
  • lsp-ui
  • magit
  • magit-imerge
  • man
  • markdown-mode
  • markup-faces (adoc-mode)
  • mentor
  • messages
  • minimap
  • modeline
  • mood-line
  • mu4e
  • mu4e-conversation
  • multiple-cursors
  • neotree
  • no-emoji
  • num3-mode
  • nxml-mode
  • orderless
  • org*
  • org-journal
  • org-noter
  • org-pomodoro
  • org-recur
  • org-roam
  • org-superstar
  • org-treescope
  • origami
  • outline-mode
  • outline-minor-faces
  • package (M-x list-packages)
  • page-break-lines
  • paradox
  • paren-face
  • parrot
  • pass
  • persp-mode
  • perspective
  • phi-grep
  • phi-search
  • pomidor
  • powerline
  • powerline-evil
  • proced
  • prodigy
  • rainbow-blocks
  • rainbow-identifiers
  • rainbow-delimiters
  • rcirc
  • regexp-builder (also known as re-builder)
  • rg (rg.el)
  • ripgrep
  • rmail
  • ruler-mode
  • sallet
  • selectrum
  • sesman
  • shell-script-mode
  • show-paren-mode
  • side-notes
  • skewer-mode
  • smart-mode-line
  • smartparens
  • smerge
  • speedbar
  • spell-fu
  • stripes
  • suggest
  • switch-window
  • swiper
  • swoop
  • sx
  • symbol-overlay
  • syslog-mode
  • telephone-line
  • term
  • tomatinho
  • transient (pop-up windows like Magit's)
  • trashed
  • treemacs
  • tuareg
  • undo-tree
  • vc (built-in mode line status for version control)
  • vc-annotate (C-x v g)
  • vdiff
  • vimish-fold
  • visible-mark
  • visual-regexp
  • volatile-highlights
  • vterm
  • wcheck-mode
  • web-mode
  • wgrep
  • which-function-mode
  • which-key
  • whitespace-mode
  • window-divider-mode
  • winum
  • writegood-mode
  • woman
  • xah-elisp-mode
  • xref
  • xterm-color (and ansi-colors)
  • yaml-mode
  • yasnippet
  • ztree

Plus many other miscellaneous faces that are provided by the out-of-the-box Emacs distribution.

Covered but not styled explicitly

These do not require any extra styles because they are configured to inherit from some basic faces. Please confirm.

  • comint
  • bongo
  • edit-indirect
  • swift-mode

Help needed

These are face groups that I am aware of but do not know how to access or do not actively use. I generally need to see how a face looks in its context before assessing its aesthetics or specific requirements.

Use M-x list-faces-display to get these.

  • tty-menu

Will NOT be supported

I have thus far identified a single package that does fit into the overarching objective of this project: solaire. It basically tries to cast a less intense background on the main file-visiting buffers, so that secondary elements like sidebars can have the default (pure white/black) background.

I will only support this package if it ever supports the inverse effect: less intense colours (but still accessible) for supportive interfaces and the intended styles for the content you are actually working on.

Note about colour-coded ORG source blocks

It is possible to apply unique coloured backgrounds to Org's source blocks on a per-language basis. The customisation option is org-src-block-faces.

Because this is an inherently subjective choice, it is impossible to reach a consensus of what colour should be assigned to each language. Furthermore, there are so many languages to choose from, making it impractical to apply a unique background to each of them without adding disproportionate complexity to the themes.

The least we could do is provide a set of background values that have been tested with all colours that highlight code syntax.

These approved colour variants are as follows:

Background Modus Operandi Modus Vivendi
red #fef2f2 #180505
yellow #fcf6f1 #18140a
magenta #fff4fc #160616
green #f4faf4 #061206
blue #f4f4ff #070722
cyan #f0f6fa #091620

The differences between those colour values are subtle, but quite noticeable when applied to large, contiguous areas (such as code blocks).

Pick the one you wish to use for your language of choice. Here is an example:

;; Modus Operandi
(setq org-src-block-faces '(("emacs-lisp" (:background "#fef2f2"))
                            ("python" (:background "#f4f4ff"))))

;; Modus Vivendi
(setq org-src-block-faces '(("emacs-lisp" (:background "#180505"))
                            ("python" (:background "#070722"))))

For versions of Emacs >= 27, also add the :extend t property, like this:

;; Modus Operandi
(setq org-src-block-faces '(("emacs-lisp" (:background "#fef2f2" :extend t))
                            ("python" (:background "#f4f4ff" :extend t))))

;; Modus Vivendi
(setq org-src-block-faces '(("emacs-lisp" (:background "#180505" :extend t))
                            ("python" (:background "#070722" :extend t))))

Feel free to contribute any concrete proposals on how to improve support for this at the theme level (see the "Contributing" section).

Note for HELM users of grep or grep-like functions

There is one face from the Helm package that is meant to highlight the matches of a grep or grep-like command (ag or ripgrep). It is helm-grep-match. However, this face can only apply when the user does not pass --color=always as a command-line option for their command.

Here is the docstring for that face, which is defined in the helm-grep.el library (view a library with M-x find-library).

Face used to highlight grep matches. Have no effect when grep backend use "color="

The user must either remove --color from the flags passed to the grep function, or explicitly use --color=never (or equivalent). Helm provides user-facing customisation options for controlling the grep function's parameters, such as helm-grep-default-command and helm-grep-git-grep-command.

When --color=always is in effect, the grep output will use red text in bold letter forms to present the matching part in the list of candidates. That style still meets the contrast ratio target of >= 7:1 (accessibility standard WCAG AAA), because it draws the reference to ANSI colour number 1 (red) from the already-supported array of ansi-color-names-vector.

I presented some screen shots of this in issue 21.

A similar scenario was also encountered in issue 49 which was promptly fixed by the Helm maintainer.

Note on VC-ANNOTATE-BACKGROUND-MODE

Due to the unique way vc-annotate (C-x v g) applies colours, support for its background mode (vc-annotate-background-mode) is disabled at the theme level.

Normally, such a drastic measure should not belong in a theme: assuming the user's preferences is bad practice. However, it has been deemed necessary in the interest of preserving colour contrast accessibility while still supporting a useful built-in tool.

If there actually is a way to avoid such a course of action, without prejudice to the accessibility standard of this project, then please report as much (or contribute as per the information in the Contributing section).

Contributing

A few tasks you can help me with:

  • Suggest refinements to packages that are covered.
  • Report packages not covered thus far.
  • Report bugs, inconsistencies, shortcomings.
  • Help expand the documentation of covered-but-not-styled packages.
  • Suggest refinements to the colour palette.
  • Help expand this document or any other piece of documentation.

It would be great if your feedback also includes some screenshots, GIFs, or short videos. Though this is not a requirement.

Whatever you do, please bear in mind the overarching objective of the Modus themes: to keep a contrast ratio that is greater or equal to 7:1 between background and foreground colours. If a compromise is ever necessary between aesthetics and accessibility, it shall always be made in the interest of the latter.

Code contributions require copyright assignment to the FSF

I accept code contributions as well (send merge requests!). But for any major contribution (more than 15 lines, or so, in aggregate), you need to make a copyright assignment to the Free Software Foundation. This is necessary because the themes are distributed through the official GNU ELPA repository and the FSF must be in a position to enforce the GNU General Public License.

Copyright assignment is a simple process that I had to follow as well. Check the request form. You must send an email to the address mentioned in the form and then wait for the FSF to send you a legal agreement. Sign the document and file it back to them. This should all happen via email and take about a week.

I encourage you to go through this process. You only need to do it once. It will allow you to make contributions to Emacs in general.

Meta

If you interested in the principles that govern the development of this project, read my article On the design of the Modus themes (2020-03-17).

COPYING

The Modus Themes are distributed under the terms of the GNU General Public License version 3 or, at your choice, any later version. See the COPYING file distributed in the project's Git repository.