config.phundrak.com/docs/stumpwm/mode-line.org
Lucien Cartier-Tilet c02d6690ed
All checks were successful
deploy / build (push) Successful in 5m30s
fix: restore broken links
2024-09-21 15:27:37 +02:00

7.3 KiB
Raw Blame History

Mode-Line

Mode-Line

Mode-Line

The timeout of the modeline indicates how often it refreshes in seconds. I think two seconds is good.

(setf *mode-line-timeout* 2)

Formatting Options

Next we get to the content of the modeline. This format follows the format indicated in the manpage of date.

(setf *time-modeline-string* "%F %H:%M")

Lets also indicate how the groupname is displayed.

(setf *group-format* "%t")

The window format should display first its window number, then its titled, limited to 30 characters.

(setf *window-format* "%n: %30t")

Mode-Line Theme

The modeline is pretty easy. First, lets load the colors.lisp file we just created:

(load "~/.stumpwm.d/colors.lisp")

Next, we can set some colours for the modeline. Lets set the background of the modeline to Nord1 and the foreground to Nord5, I think this is a pretty good combination.

(setf *mode-line-background-color* phundrak-nord1
      ,*mode-line-foreground-color* phundrak-nord5)

We could also use some borders in the modeline. But we wont. Lets still set its colour to Nord1, just in case.

(setf *mode-line-border-color* phundrak-nord1
      ,*mode-line-border-width* 0)

Mode-Line Modules

Here are some modules that we will load for the modeline:

Module Name Why Do I Need It?
battery-portable Get information on the battery level of a laptop
cpu Get the CPU usage
mpd Display MPDs status
mem Get the memory usage
Modules used by the modeline
(mapconcat (lambda (module)
             (format "(load-module \"%s\")" (car module)))
           modules
           "\n")
(load-module "battery-portable")
(load-module "cpu")
(load-module "mpd")
(load-module "mem")

We need to set some variables, so modules can be displayed correctly. Note that the character between the font switchers in the second CPU formatter is U+E082, which symbolizes the CPU.

(setf cpu::*cpu-modeline-fmt*        "%c"
      cpu::*cpu-usage-modeline-fmt*  "^f2^f0^[~A~2D%^]"
      mem::*mem-modeline-fmt*        "%a%p"
      mpd:*mpd-modeline-fmt*         "%a - %t"
      mpd:*mpd-status-fmt*           "%a - %t"
      ,*hidden-window-color*          "^**"
      ,*mode-line-highlight-template* "«~A»")

Generating the Mode-Line

We can indicate what to display in our modeline. Each formatter will be separated by a Powerline separator with the code point 0xE0B0 in the font I am using (see Theme » Fonts).

Formatter What it does Command?
%g Display list of groups
%W Display list of windows in the current group and head
^> Rest of the modeline align to the right
docker-running Display number of docker containers currently running yes
mu-unread Display number of unread emails yes
%m Display current MPD song
%C Display CPU usage
%M Display RAM usage
%B Display battery status
%d Display date
Formatters for the modeline
(("%g") ("%W") ("^>") ("docker-running" . t) ("mu-unread" . t) ("%m") ("%C") ("%M") ("%B") ("%d"))
(defvar *mode-line-formatter-list*
  '<<modeline-format-gen()>>
  "List of formatters for the modeline.")

As you can see, generate-modeline generates the string defining *screen-mode-line-format* from the list of formatters we gave it with the table /phundrak/config.phundrak.com/src/commit/5631935f8f0292086b08321f7dbe5c0cfa83f3fe/docs/stumpwm/modeline-format.

(defun generate-modeline (elements &optional not-invertedp rightp)
  "Generate a modeline for StumpWM.
ELEMENTS should be a list of `cons'es which `car' is the modeline
formatter or the shell command to run, and their `cdr' is either nil
when the `car' is a formatter and t when it is a shell command."
  (when elements
    (cons (format nil
                  " ^[~A^]^(:bg \"~A\") "
                  (format nil "^(:fg \"~A\")^(:bg \"~A\")^f1~A^f0"
                          (if (xor not-invertedp rightp) phundrak-nord1 phundrak-nord3)
                          (if (xor not-invertedp rightp) phundrak-nord3 phundrak-nord1)
                          (if rightp "" ""))
                  (if not-invertedp phundrak-nord3 phundrak-nord1))
          (let* ((current-element (car elements))
                 (formatter       (car current-element))
                 (commandp        (cdr current-element)))
            (cons (if commandp
                      `(:eval (run-shell-command ,formatter t))
                    (format nil "~A" formatter))
                  (generate-modeline (cdr elements)
                                     (not not-invertedp)
                                     (if (string= "^>" (caar elements)) t rightp)))))))

It is then easy to define a command that can call this function and set this variable, so we can sort of reload the mode-line.

(defcommand reload-modeline () ()
  "Reload modeline."
  (sb-thread:make-thread
   (lambda ()
     (setf *screen-mode-line-format*
           (cdr (generate-modeline *mode-line-formatter-list*))))))

And actually, lets reload the modeline immediately.

(reload-modeline)