;;; acdw-modeline.el -*- lexical-binding: t; coding: utf-8-unix -*- ;; Author: Case Duckworth ;; Created: Sometime during Covid-19, 2020 ;; Keywords: configuration ;; URL: https://tildegit.org/acdw/emacs ;; This file is NOT part of GNU Emacs. ;;; License: ;; Everyone is permitted to do whatever with this software, without ;; limitation. This software comes without any warranty whatsoever, ;; but with two pieces of advice: ;; - Don't hurt yourself. ;; - Make good choices. ;;; Commentary: ;; `acdw-modeline' is a dumping ground for extra modeline functions, so they ;; don't clutter up `init.el'. ;;; Code: (require 'simple-modeline) (require 'minions) (defcustom acdw-modeline/word-count-modes (mapcar (lambda (m) (cons m nil)) simple-modeline-word-count-modes) "Alist of modes to functions that `acdw-modeline/word-count' should dispatch. If the cdr of the cons cell is nil, use the default function (`count-words'). Otherwise, cdr should be a function that takes two points (see `count-words')." :type '(alist :key-type (symbol :tag "Major-Mode") :value-type function) :group 'simple-modeline) (defun acdw-modeline/buffer-name () ; gonsie "Display the buffer name in a face reflecting its modified status." (propertize " %b " 'face (if (buffer-modified-p) 'font-lock-warning-face 'font-lock-type-face) 'help-echo (buffer-file-name))) (defun acdw-modeline/erc () "ERC indicator for the modeline." (when (and (bound-and-true-p erc-track-mode) (boundp 'erc-modified-channels-object)) (format-mode-line erc-modified-channels-object))) (defun acdw-modeline/god-mode-indicator () "Display an indicator if `god-local-mode' is active." (when (bound-and-true-p god-local-mode) " Ω")) (defun acdw-modeline/major-mode () "Displays the current major mode in the mode-line." (propertize (concat " " (or (and (boundp 'delighted-modes) (cadr (assq major-mode delighted-modes))) (format-mode-line mode-name))) 'face 'bold 'keymap mode-line-major-mode-keymap 'mouse-face 'mode-line-highlight)) (defun acdw-modeline/minions () ; by me "Display a button for `minions-minor-modes-menu'." (concat " " (propertize "&" 'help-echo (format "Minor modes menu\nmouse-1: show menu.") 'local-map (purecopy (simple-modeline-make-mouse-map 'mouse-1 (lambda (event) (interactive "e") (with-selected-window (posn-window (event-start event)) (minions-minor-modes-menu))))) 'mouse-face 'mode-line-highlight))) (defun acdw-modeline/modified () ; modified from `simple-modeline' "Displays a color-coded buffer modification/read-only indicator in the mode-line." (if (not (string-match-p "\\*.*\\*" (buffer-name))) (let* ((read-only (and buffer-read-only (buffer-file-name))) (modified (buffer-modified-p))) (propertize (concat " " (cond ((derived-mode-p 'special-mode 'lui-mode) "~") (read-only "=") (modified "+") (t "-"))) 'help-echo (format (concat "Buffer is %s and %smodified\n" "mouse-1: Toggle read-only status.") (if read-only "read-only" "writable") (if modified "" "not ")) 'local-map (purecopy (simple-modeline-make-mouse-map 'mouse-1 (lambda (event) (interactive "e") (with-selected-window (posn-window (event-start event)) (read-only-mode 'toggle))))) 'mouse-face 'mode-line-highlight)))) (defun acdw-modeline/narrowed () "Display an indication if the buffer is narrowed." (when (buffer-narrowed-p) (concat "" (propertize "N" 'help-echo (format "%s\n%s" "Buffer is narrowed" "mouse-2: widen buffer.") 'local-map (purecopy (simple-modeline-make-mouse-map 'mouse-2 #'mode-line-widen)) 'mouse-face 'mode-line-highlight)))) (defun acdw-modeline/position () "Displays the current cursor position in the mode-line. Unlike `simple-modeline-segment-position', this changes the first character from '+' to '-' if the region goes 'backward' -- that is, if point < mark." `((line-number-mode ((column-number-mode (column-number-indicator-zero-based (8 " %l:%c") (8 " %l:%C")) (5 " L%l"))) ((column-number-mode (column-number-indicator-zero-based (5 " C%c") (5 " C%C"))))) ,(if (region-active-p) (propertize (format "%s%s" (if (and (mark) (< (point) (mark))) "-" "+") (apply #'+ (mapcar (lambda (pos) (- (cdr pos) (car pos))) (region-bounds)))) 'font-lock-face 'font-lock-variable-name-face)))) (defun acdw-modeline/text-scale () "Display the text scaling from the modeline, if scaled." ;; adapted from https://github.com/seagle0128/doom-modeline (when (and (boundp 'text-scale-mode-amount) (/= text-scale-mode-amount 0)) (format (if (> text-scale-mode-amount 0) " (%+d)" " (%-d)") text-scale-mode-amount))) (defun acdw-modeline/track () "Display `tracking-mode' information." (when tracking-mode tracking-mode-line-buffers)) (defun acdw-modeline/vc-branch () "Display the version control branch of the current buffer in the modeline." ;; from https://www.gonsie.com/blorg/modeline.html, from Doom (if-let ((backend (vc-backend buffer-file-name))) (substring vc-mode (+ (if (eq backend 'Hg) 2 3) 2)))) (defun acdw-modeline/wc () "Display current `wc-buffer-stats'." (when (bound-and-true-p wc-mode) (or wc-buffer-stats "[w]"))) (defun acdw-modeline/winum () "Show the `winum' number of the current window in the modeline. Only shows if there is more than one window." (when (and (bound-and-true-p winum-mode) (> winum--window-count 1)) (format winum-format (winum-get-number-string)))) (defun acdw-modeline/word-count () "Display a buffer word count, depending on the major mode. Uses `acdw-modeline/word-count-modes' to determine which function to use." (when-let ((modefun (assoc major-mode acdw-modeline/word-count-modes #'equal))) (let* ((fn (or (cdr modefun) #'count-words)) (r (region-active-p)) (min (if r (region-beginning) (point-min))) (max (if r (region-end) (point-max)))) (format " %s%dW" (if r "+" "") (funcall fn min max))))) (provide 'acdw-modeline)