From: Eshel Yaron Date: Sat, 19 Aug 2023 19:41:51 +0000 (+0200) Subject: Update Emacs configuration X-Git-Url: http://git.eshelyaron.com/gitweb/?a=commitdiff_plain;h=9beb885881b597048db47e3c971c500f78ea1fb6;p=dotfiles.git Update Emacs configuration --- diff --git a/.emacs.d/init.el b/.emacs.d/init.el index 0170532..5cb7ddb 100644 --- a/.emacs.d/init.el +++ b/.emacs.d/init.el @@ -10,6 +10,7 @@ ;;; Code: ;;; Temporarily increase GC threshold to expedite Emacs startup + (let ((normal-gc-cons-threshold (* 20 1024 1024)) (init-gc-cons-threshold (* 1024 1024 1024))) (setq gc-cons-threshold init-gc-cons-threshold) @@ -18,10 +19,12 @@ (setq gc-cons-threshold normal-gc-cons-threshold)))) ;;; OS-specific settings + (pcase system-type ('darwin (setq default-frame-alist '((fullscreen . fullboth))))) ;;; Set some variables + (setq ;; my name user-full-name "Eshel Yaron" @@ -67,8 +70,7 @@ package-archive-column-width 12 package-version-column-width 28 ;; configure package archives - package-archives '(("melpa" . "http://melpa.org/packages/") - ("gnu" . "https://elpa.gnu.org/devel/") + package-archives '(("gnu" . "https://elpa.gnu.org/devel/") ("nongnu" . "https://elpa.nongnu.org/nongnu-devel/")) ;; select some packages to install package-selected-packages '( @@ -85,18 +87,18 @@ embark-consult emms gnu-elpa-keyring-update - gnuplot graphql-mode - graphviz-dot-mode htmlize ialign keycast kubernetes + ledger-mode lin magit markdown-mode mastodon ob-prolog + openai orderless org org-transclusion @@ -114,6 +116,45 @@ vterm whitespace-cleanup-mode ) + package-vc-selected-packages + '( + (avy :url "https://github.com/abo-abo/avy.git") + (devdocs :url "https://github.com/astoff/devdocs.el.git" + :doc "README.org") + (diff-hl :url "https://github.com/dgutov/diff-hl.git") + (elfeed :url "https://github.com/skeeto/elfeed.git") + (embark-consult :url "https://github.com/oantolin/embark.git" + :doc "README.org") + (esy-publish :url "git://git.eshelyaron.com/esy-publish.git") + (graphql-mode :url "https://github.com/davazp/graphql-mode.git") + (htmlize :url "https://github.com/hniksic/emacs-htmlize.git") + (ialign :url "https://github.com/mkcms/interactive-align.git" + :doc "README.org") + (keycast :url "https://github.com/tarsius/keycast.git" + :doc "README.org") + (kubernetes :url "https://github.com/kubernetes-el/kubernetes-el.git") + (ledger-mode :url "https://github.com/ledger/ledger-mode.git" + :doc "doc/ledger-mode.texi") + (magit :url "https://github.com/magit/magit.git" + :lisp-dir "lisp" :doc "docs/magit.texi") + (ob-prolog :url "https://github.com/ljos/ob-prolog.git" + :doc "README.org") + (openai :url "https://git.sr.ht/~eshel/openai.el") + (orderless :url "https://github.com/oantolin/orderless.git" + :doc "orderless.texi") + (osm :url "https://github.com/minad/osm.git" + :doc "README.org") + (package-lint :url "https://github.com/purcell/package-lint.git") + (rainbow-delimiters :url "https://github.com/Fanael/rainbow-delimiters.git") + (rg :url "https://github.com/dajva/rg.el.git") + (smtpmail-multi :url "https://github.com/vapniks/smtpmail-multi.git" + :doc "README.org") + (sqlformat :url "https://github.com/purcell/sqlformat.git") + (terraform-mode :url "https://github.com/syohex/emacs-terraform-mode.git") + (vterm :url "https://github.com/akermu/emacs-libvterm.git") + (whitespace-cleanup-mode :url "https://github.com/purcell/whitespace-cleanup-mode.git") + ) + ;; configure Org capture templates org-capture-templates '(("t" "Todo [inbox]" entry (file+headline "~/org/inbox.org" "Tasks") @@ -402,12 +443,13 @@ "Global Bindings:" "Function key map translations" "pixel-scroll-precision-mode" - "context-menu-mode"))))) + "context-menu-mode")))) + report-emacs-bug-no-explanations t + submit-emacs-patch-display-help nil) (setq-default indent-tabs-mode nil) ;;; Load and enable a custom theme -;; (require-theme 'modus-themes) -;; (load-theme 'modus-vivendi) + (require 'ef-themes) (defvar esy/ef-themes-ring (make-ring 16)) @@ -459,6 +501,7 @@ (esy/ef-themes-load-random) ;;; Set up the Iosevka font family + (when (eq system-type 'darwin) (set-face-attribute 'default nil :height 130)) (set-face-attribute 'default nil :family "Iosevka") @@ -466,12 +509,14 @@ (set-face-attribute 'variable-pitch nil :family "Iosevka Etoile") ;;; Add custom code directory to `load-path' + (add-to-list 'load-path (expand-file-name "lisp/" user-emacs-directory)) (autoload 'some-button "some-button" nil t) (autoload 'esy-capture "esy-capture" nil t) (autoload 'pdf-view-mode "pdf-view" nil t) ;;; Define custom commands + (defvar-keymap transpose-lines-repeat-map :doc "Repeat map for \\[transpose-lines]" "C-t" #'transpose-lines) @@ -763,6 +808,7 @@ Interactively, POINT is point and KILL is the prefix argument." (error "Git tag failed"))))) ;;; Ensure scripts ran with `executable-interpret' are executable + (with-eval-after-load 'executable (define-advice executable-interpret (:before (&rest _) ensure-executable) (unless (file-exists-p buffer-file-name) @@ -778,15 +824,21 @@ Interactively, POINT is point and KILL is the prefix argument." #'esy/pulse-on-window-selection-change) ;;; Override the default startup message + (define-advice startup-echo-area-message (:override () report-init-time) (format "%s started in %s. Hack away." (propertize "Emacs" 'face 'success) (propertize (emacs-init-time) 'face 'error ))) ;;; Ensure external packages are installed + +(package-vc-install-selected-packages) + (package-install-selected-packages) + ;;; Extend standard programming mode hooks + (dolist (mode '(bug-reference-prog-mode display-fill-column-indicator-mode display-line-numbers-mode @@ -797,9 +849,11 @@ Interactively, POINT is point and KILL is the prefix argument." (add-hook 'lisp-data-mode-hook #'paredit-mode) ;;; Extend other standard hooks + (add-hook 'text-mode-hook #'flyspell-mode) ;;; Bind some keys + (keymap-global-set "C-c c" #'org-capture) (keymap-global-set "C-c l" #'org-store-link) (keymap-global-set "C-c a" #'org-agenda) @@ -886,6 +940,7 @@ Interactively, POINT is point and KILL is the prefix argument." (put 'suspend-frame 'disabled t) ;;; Configure project management commands + (with-eval-after-load 'project (define-advice project--find-in-directory (:override (dir) no-remote-projects) (unless (file-remote-p dir) @@ -931,6 +986,7 @@ as the initial input for completion, and return that directory." dir))))) ;;; Configure SQL connections + (with-eval-after-load 'sql (defun esy/update-sql-connection-alist () (interactive) @@ -960,6 +1016,7 @@ as the initial input for completion, and return that directory." (apply fun args)))) ;;; Configure Org mode + (with-eval-after-load 'org (keymap-unset org-mode-map "C-," t) (esy-publish-setup)) @@ -971,6 +1028,7 @@ as the initial input for completion, and return that directory." '("h" "Holland TODOs" tags-todo "+holland"))) ;;; Configure email via `gnus' + (with-eval-after-load 'gnus (require 'gnus-icalendar) (add-hook 'gnus-group-mode-hook #'gnus-topic-mode) @@ -979,10 +1037,12 @@ as the initial input for completion, and return that directory." (bbdb-initialize 'gnus 'mail 'message)) ;;; Configure `dired' + (with-eval-after-load 'dired (put 'dired-find-alternate-file 'disabled nil)) ;;; Configure remote access via `tramp' + (with-eval-after-load 'tramp (tramp-set-completion-function "ssh" '((tramp-parse-netrc "~/.authinfo.gpg"))) (add-to-list 'backup-directory-alist (cons tramp-file-name-regexp nil)) @@ -995,15 +1055,18 @@ as the initial input for completion, and return that directory." (list string pred action))))) ;;; Configure `proced' + (with-eval-after-load 'proced (add-hook 'proced-mode-hook (lambda () (setq proced-auto-update-flag t)))) ;;; Configure `world-clock' + (with-eval-after-load 'time (add-to-list 'zoneinfo-style-world-list '("Europe/Amsterdam" "Amsterdam"))) ;;; Configure spelling errors correction via `flyspell' + (with-eval-after-load 'flyspell (keymap-unset flyspell-mode-map "C-," t) (keymap-unset flyspell-mode-map "C-." t) @@ -1041,6 +1104,7 @@ as the initial input for completion, and return that directory." (require 'embark-consult))) ;;; Set up some global `completion-at-point-functions' + (defun esy/dabbrev-capf () "Workaround for issue with `dabbrev-capf'." (require 'dabbrev) @@ -1064,12 +1128,14 @@ as the initial input for completion, and return that directory." (add-to-list 'completion-at-point-functions #'esy/file-capf) ;;; Configure highlighting of the current line via `lin' + (with-eval-after-load 'lin (add-to-list 'lin-mode-hooks 'gnus-summary-mode-hook) (add-to-list 'lin-mode-hooks 'gnus-group-mode-hook) (add-to-list 'lin-mode-hooks 'gnus-server-mode-hook)) ;;; Configure `completion-in-region' UI with `corfu' + (let ((original-completion-in-region-function completion-in-region-function)) (defun esy/setup-corfu (&rest args) (setq completion-in-region-function original-completion-in-region-function) @@ -1085,6 +1151,7 @@ as the initial input for completion, and return that directory." (corfu-indexed-mode)) ;;; Enable some global minor modes + (dolist (mode '( column-number-mode context-menu-mode @@ -1107,6 +1174,7 @@ as the initial input for completion, and return that directory." (funcall mode)) ;;; Set up EMMS + (dolist (command '(emms-start emms-stop emms-next @@ -1122,6 +1190,7 @@ as the initial input for completion, and return that directory." (defvar-keymap esy/emms-map :doc "My keymap for EMMS commands." :prefix 'esy/emms-map + :repeat t "N" #'emms-next "P" #'emms-previous "S" #'emms-stop @@ -1133,22 +1202,11 @@ as the initial input for completion, and return that directory." "s" #'emms-start "t" #'emms-seek-to) -(dolist (command '(emms-start - emms-stop - emms-next - emms-previous - emms-pause - emms-seek - emms-seek-to - emms-seek-forward - emms-seek-backward - emms-show)) - (put command 'repeat-map 'esy/emms-map)) - (with-eval-after-load 'emms (emms-minimalistic)) ;;; Configure PDF handling + (with-eval-after-load 'pdf-view (require 'pdf-tools)) (with-eval-after-load 'pdf-tools @@ -1157,17 +1215,20 @@ as the initial input for completion, and return that directory." (add-to-list 'revert-without-query "\\.pdf\\'") ;;; Configure terminal emulation via `vterm' + (with-eval-after-load 'vterm (when (eq system-type 'darwin) (setq vterm-shell "/bin/zsh")) (add-to-list 'vterm-tramp-shells '("kubernetes" "/bin/bash"))) ;;; Remove some over-intrusive keybindings in `paredit' + (with-eval-after-load 'paredit (keymap-unset paredit-mode-map "M-s" t) (keymap-unset paredit-mode-map "M-?" t)) ;;; Configure Prolog integration via `sweeprolog' + (setq-default prolog-system 'swi) (add-to-list 'major-mode-remap-alist '(prolog-mode . sweeprolog-mode)) (with-eval-after-load 'sweeprolog @@ -1177,15 +1238,18 @@ as the initial input for completion, and return that directory." (add-hook 'sweeprolog-top-level-mode-hook #'compilation-shell-minor-mode)) ;;; Configure recursive grepping via `rg' + (with-eval-after-load 'rg (add-to-list 'rg-custom-type-aliases '("Prolog" . "*.pl *.plt *.pro *.prolog"))) ;;; Configure custom faces in `terraform-mode' + (with-eval-after-load 'terraform-mode (setq terraform--resource-name-face font-lock-function-name-face terraform--resource-type-face font-lock-type-face)) ;;; Associate major modes with files based on their extensions + (dolist (cell '(("Dockerfile" . dockerfile-ts-mode) ("\\.ya?ml\\'" . yaml-ts-mode) ("\\.toml\\'" . toml-ts-mode) @@ -1200,12 +1264,14 @@ as the initial input for completion, and return that directory." (push cell auto-mode-alist)) ;;; Configure Help + (with-eval-after-load 'help-fns (with-eval-after-load 'shortdoc (add-hook 'help-fns-describe-function-functions #'shortdoc-help-fns-examples-function))) ;;; Configure dictionary + (with-eval-after-load 'dictionary (setopt dictionary-search-interface 'help dictionary-default-dictionary "gcide" @@ -1213,6 +1279,7 @@ as the initial input for completion, and return that directory." dictionary-server "dict.org")) ;;; Configure news feeds + (with-eval-after-load 'elfeed (keymap-set elfeed-show-mode-map "S-SPC" #'scroll-down-command) @@ -1282,6 +1349,7 @@ as the initial input for completion, and return that directory." ;;; Track currency exchange rates (defvar esy/eur-to-ils-rates nil) +(defvar esy/eur-to-ils-average-rate 0) (add-to-list 'savehist-additional-variables 'esy/eur-to-ils-rates) @@ -1308,7 +1376,14 @@ as the initial input for completion, and return that directory." (push (cons time (string-to-number (caddar (dom-by-class (libxml-parse-html-region (point)) "ccOutputRslt")))) - esy/eur-to-ils-rates)) + esy/eur-to-ils-rates) + (setq esy/eur-to-ils-average-rate + (/ (round (* (apply #'+ + (mapcar #'cdr + (take 100 + esy/eur-to-ils-rates))) + 10)) + 1000.0))) nil t))) (run-at-time t 300 #'esy/update-eur-to-ils-rate) @@ -1356,20 +1431,27 @@ as the initial input for completion, and return that directory." (defvar esy/mode-line-format '(" %+ " mode-line-buffer-identification - " (%[" mode-name mode-line-process minor-mode-alist "%n%])" + " (%[" + mode-name mode-line-process minor-mode-alist + (:eval (when (window-dedicated-p) + " Dedicated")) + "%n%])" (vc-mode vc-mode) mode-line-format-right-align (:eval (when (mode-line-window-selected-p) (list (let* ((last-rate (cdar esy/eur-to-ils-rates)) - (prev-rate (cdadr esy/eur-to-ils-rates)) (face-arrw (cond - ((< prev-rate last-rate) '("↑" . error)) - ((< last-rate prev-rate) '("↓" . success)) - (t '("→" . warning)))) + ((< esy/eur-to-ils-average-rate last-rate) + '("↑" . error)) + ((< last-rate esy/eur-to-ils-average-rate) + '("↓" . success)) + (t + '("→" . warning)))) (arrw (car face-arrw)) (face (cdr face-arrw))) - (propertize (concat "€" arrw (number-to-string last-rate) "₪") + (propertize (concat "€" arrw + (number-to-string last-rate) "₪") 'face face)) " " 'display-time-string