diff options
-rw-r--r-- | LICENSE | 2 | ||||
-rw-r--r-- | README.md | 145 | ||||
-rw-r--r-- | config.org | 2176 |
3 files changed, 1201 insertions, 1122 deletions
diff --git a/LICENSE b/LICENSE index 9c31dda..de537e6 100644 --- a/LICENSE +++ b/LICENSE | |||
@@ -11,4 +11,4 @@ DO WHAT THE FUCK YOU WANT TO PUBLIC LICENSE | |||
11 | 11 | ||
12 | TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION | 12 | TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION |
13 | 13 | ||
14 | 0. You just DO WHAT THE FUCK YOU WANT TO. | 14 | 0. You just DO WHAT THE FUCK YOU WANT TO. |
diff --git a/README.md b/README.md index 9450ea5..bde17e1 100644 --- a/README.md +++ b/README.md | |||
@@ -393,17 +393,27 @@ helper function, though, to add things to the whitelist. | |||
393 | (cuss calendar-latitude 30.4515) | 393 | (cuss calendar-latitude 30.4515) |
394 | (cuss calendar-longitude -91.1871) | 394 | (cuss calendar-longitude -91.1871) |
395 | 395 | ||
396 | ;; sunrise | 396 | (defun acdw/run-with-sun (sunrise-command sunset-command) |
397 | (run-at-time (nth 1 (split-string (sunrise-sunset))) | 397 | "Run commands at sunrise and sunset." |
398 | (* 60 60 24) | 398 | (let* ((times-regex (rx (* nonl) |
399 | (lambda () | 399 | (: (any ?s ?S) "unrise") " " |
400 | (modus-themes-load-operandi))) | 400 | (group (repeat 1 2 digit) ":" |
401 | 401 | (repeat 1 2 digit) | |
402 | ;; sunset | 402 | (: (any ?a ?A ?p ?P) (any ?m ?M))) |
403 | (run-at-time (nth 4 (split-string (sunrise-sunset))) | 403 | (* nonl) |
404 | (* 60 60 24) | 404 | (: (any ?s ?S) "unset") " " |
405 | (lambda () | 405 | (group (repeat 1 2 digit) ":" |
406 | (modus-themes-load-vivendi))) | 406 | (repeat 1 2 digit) |
407 | (: (any ?a ?A ?p ?P) (any ?m ?M))) | ||
408 | (* nonl))) | ||
409 | (ss (sunrise-sunset)) | ||
410 | (m_ (string-match times-regex ss)) | ||
411 | (sunrise-time (match-string 1 ss)) | ||
412 | (sunset-time (match-string 2 ss))) | ||
413 | (run-at-time sunrise-time (* 60 60 24) sunrise-command) | ||
414 | (run-at-time sunset-time (* 60 60 24) sunset-command))) | ||
415 | |||
416 | (acdw/run-with-sun #'modus-themes-load-operandi #'modus-themes-load-vivendi) | ||
407 | 417 | ||
408 | 418 | ||
409 | ### Fonts | 419 | ### Fonts |
@@ -430,19 +440,24 @@ helper function, though, to add things to the whitelist. | |||
430 | ;; fixed-pitch /is/ the default | 440 | ;; fixed-pitch /is/ the default |
431 | (set-face-from-alternatives face nil | 441 | (set-face-from-alternatives face nil |
432 | '(:family "Input Mono" | 442 | '(:family "Input Mono" |
443 | :slant normal | ||
433 | :weight normal | 444 | :weight normal |
434 | :height 110) | 445 | :height 110) |
435 | '(:family "Go Mono" | 446 | '(:family "Go Mono" |
447 | :slant normal | ||
436 | :weight normal | 448 | :weight normal |
437 | :height 100) | 449 | :height 100) |
438 | '(:family "Consolas" | 450 | '(:family "Consolas" |
451 | :slant normal | ||
439 | :weight normal | 452 | :weight normal |
440 | :height 100))) | 453 | :height 100))) |
441 | ;; variable-pitch is different | 454 | ;; variable-pitch is different |
442 | (set-face-from-alternatives 'variable-pitch nil | 455 | (set-face-from-alternatives 'variable-pitch nil |
443 | '(:family "Input Sans" | 456 | '(:family "Input Sans" |
457 | :slant normal | ||
444 | :weight normal) | 458 | :weight normal) |
445 | '(:family "Georgia" | 459 | '(:family "Georgia" |
460 | :slant normal | ||
446 | :weight normal))) | 461 | :weight normal))) |
447 | 462 | ||
448 | ;; remove myself from the hook | 463 | ;; remove myself from the hook |
@@ -524,15 +539,11 @@ helper function, though, to add things to the whitelist. | |||
524 | 539 | ||
525 | (straight-use-package '(consult | 540 | (straight-use-package '(consult |
526 | :host github | 541 | :host github |
527 | :repo "minad/consult")) | 542 | :repo "minad/consult" |
543 | :files (:defaults "consult-pkg.el"))) | ||
528 | (require 'consult) | 544 | (require 'consult) |
529 | 545 | ||
530 | (straight-use-package '(consult-selectrum | 546 | (with-eval-after-load 'consult |
531 | :host github | ||
532 | :repo "minad/consult")) | ||
533 | (require 'consult-selectrum) | ||
534 | |||
535 | (with-eval-after-load 'consult | ||
536 | (define-key ctl-x-map "b" #'consult-buffer) | 547 | (define-key ctl-x-map "b" #'consult-buffer) |
537 | (define-key ctl-x-map (kbd "C-r") #'consult-buffer) | 548 | (define-key ctl-x-map (kbd "C-r") #'consult-buffer) |
538 | (define-key ctl-x-map "4b" #'consult-buffer-other-window) | 549 | (define-key ctl-x-map "4b" #'consult-buffer-other-window) |
@@ -724,12 +735,20 @@ from [u/TheFrenchPoulp](https://www.reddit.com/r/emacs/comments/km9by4/weekly_ti | |||
724 | 735 | ||
725 | #### UTF-8 | 736 | #### UTF-8 |
726 | 737 | ||
727 | (set-language-environment "UTF-8") | 738 | from [Mastering Emacs](https://www.masteringemacs.org/article/working-coding-systems-unicode-emacs). |
728 | (set-terminal-coding-system 'utf-8) | 739 | |
729 | (cuss locale-coding-system 'utf-8) | ||
730 | (set-default-coding-systems 'utf-8) | ||
731 | (set-selection-coding-system 'utf-8) | ||
732 | (prefer-coding-system 'utf-8) | 740 | (prefer-coding-system 'utf-8) |
741 | (set-default-coding-systems 'utf-8) | ||
742 | (set-terminal-coding-system 'utf-8) | ||
743 | (set-keyboard-coding-system 'utf-8) | ||
744 | ;; backwards compatibility: | ||
745 | ;; `default-buffer-file-coding-system' is deprecated in 23.2. | ||
746 | (if (boundp 'buffer-file-coding-system) | ||
747 | (setq-default buffer-file-coding-system 'utf-8) | ||
748 | (setq default-buffer-file-coding-system 'utf-8)) | ||
749 | |||
750 | ;; Treat clipboard as UTF-8 string first; compound text next, etc. | ||
751 | (setq x-select-request-type '(UTF8_STRING COMPOUND_TEXT TEXT STRING)) | ||
733 | 752 | ||
734 | 753 | ||
735 | #### Convert all files to UNIX-style line endings | 754 | #### Convert all files to UNIX-style line endings |
@@ -885,14 +904,14 @@ I’ve pretty much cribbed this from [recentf-remove-sudo-tramp-prefix](https:// | |||
885 | 904 | ||
886 | #### Replace with Anzu | 905 | #### Replace with Anzu |
887 | 906 | ||
888 | (straight-use-package 'anzu) | 907 | (straight-use-package 'anzu) |
889 | (require 'anzu) | 908 | (require 'anzu) |
890 | 909 | ||
891 | ;; show search count in the modeline | 910 | ;; show search count in the modeline |
892 | (global-anzu-mode +1) | 911 | (global-anzu-mode +1) |
893 | 912 | ||
894 | (cuss anzu-replace-to-string-separator " → " | 913 | (cuss anzu-replace-to-string-separator " → " |
895 | "What to separate the search from the replacement.") | 914 | "What to separate the search from the replacement.") |
896 | 915 | ||
897 | (global-set-key [remap query-replace] #'anzu-query-replace) | 916 | (global-set-key [remap query-replace] #'anzu-query-replace) |
898 | (global-set-key [remap query-replace-regexp] #'anzu-query-replace-regexp) | 917 | (global-set-key [remap query-replace-regexp] #'anzu-query-replace-regexp) |
@@ -1028,7 +1047,9 @@ I’ve pretty much cribbed this from [recentf-remove-sudo-tramp-prefix](https:// | |||
1028 | (straight-use-package 'janet-mode) | 1047 | (straight-use-package 'janet-mode) |
1029 | (require 'janet-mode) | 1048 | (require 'janet-mode) |
1030 | 1049 | ||
1031 | (straight-use-package 'inf-janet-mode) | 1050 | (straight-use-package '(inf-janet |
1051 | :host github | ||
1052 | :repo "velkyel/inf-janet")) | ||
1032 | 1053 | ||
1033 | (add-hook 'janet-mode-hook #'inf-janet-minor-mode) | 1054 | (add-hook 'janet-mode-hook #'inf-janet-minor-mode) |
1034 | 1055 | ||
@@ -1180,8 +1201,7 @@ I’ve put org mode under Applications, as opposed to Writing, because it’s m | |||
1180 | 1201 | ||
1181 | ### Basics | 1202 | ### Basics |
1182 | 1203 | ||
1183 | (straight-use-package '(org | 1204 | (straight-use-package 'org) |
1184 | :repo "https://code.orgmode.org/bzg/org-mode.git")) | ||
1185 | 1205 | ||
1186 | (with-eval-after-load 'org | 1206 | (with-eval-after-load 'org |
1187 | (require 'org-tempo) | 1207 | (require 'org-tempo) |
@@ -1226,8 +1246,8 @@ I’ve put org mode under Applications, as opposed to Writing, because it’s m | |||
1226 | (defun acdw/org-mode-prettify () | 1246 | (defun acdw/org-mode-prettify () |
1227 | "Prettify `org-mode'." | 1247 | "Prettify `org-mode'." |
1228 | (dolist (cell '(("[ ]" . ?□) ("[X]" . ?☑) ("[-]" . ?◐) | 1248 | (dolist (cell '(("[ ]" . ?□) ("[X]" . ?☑) ("[-]" . ?◐) |
1229 | ("#+begin_src" . ?✎) ("#+BEGIN_SRC" . ?✎) | 1249 | ("#+begin_src" . ?✎) ("#+begin_src" . ?✎) |
1230 | ("#+end_src" . ?■) ("#+END_SRC" . ?■))) | 1250 | ("#+end_src" . ?■) ("#+end_src" . ?■))) |
1231 | (add-to-list 'prettify-symbols-alist cell :append)) | 1251 | (add-to-list 'prettify-symbols-alist cell :append)) |
1232 | (prettify-symbols-mode +1)) | 1252 | (prettify-symbols-mode +1)) |
1233 | 1253 | ||
@@ -1391,6 +1411,12 @@ from [unpackaged.el](https://github.com/alphapapa/unpackaged.el#ensure-blank-lin | |||
1391 | (add-hook 'before-save-hook #'cribbed/org-mode-fix-blank-lines) | 1411 | (add-hook 'before-save-hook #'cribbed/org-mode-fix-blank-lines) |
1392 | 1412 | ||
1393 | 1413 | ||
1414 | ### Org Templates (`org-tempo`) | ||
1415 | |||
1416 | (add-to-list 'org-structure-template-alist | ||
1417 | '("el" . "src emacs-lisp")) | ||
1418 | |||
1419 | |||
1394 | ### Org Agenda | 1420 | ### Org Agenda |
1395 | 1421 | ||
1396 | (cuss org-agenda-files | 1422 | (cuss org-agenda-files |
@@ -1405,12 +1431,13 @@ from [unpackaged.el](https://github.com/alphapapa/unpackaged.el#ensure-blank-lin | |||
1405 | 1431 | ||
1406 | (cuss org-todo-keywords | 1432 | (cuss org-todo-keywords |
1407 | '((sequence "RECUR(r)" "TODO(t)" "|" "DONE(d)") | 1433 | '((sequence "RECUR(r)" "TODO(t)" "|" "DONE(d)") |
1434 | (sequence "APPT(a)") | ||
1408 | (sequence "|" "CANCELLED(c)"))) | 1435 | (sequence "|" "CANCELLED(c)"))) |
1409 | 1436 | ||
1410 | (cuss org-agenda-skip-scheduled-if-done t) | 1437 | (cuss org-agenda-skip-scheduled-if-done t) |
1411 | (cuss org-agenda-skip-deadline-if-done t) | 1438 | (cuss org-agenda-skip-deadline-if-done t) |
1412 | (cuss org-deadline-warning-days 4 | 1439 | (cuss org-deadline-warning-days 0 |
1413 | "Warn of a deadline beginning four days before.") | 1440 | "Don't warn of an impending deadline.") |
1414 | 1441 | ||
1415 | 1442 | ||
1416 | ### TODO Capture | 1443 | ### TODO Capture |
@@ -1479,10 +1506,10 @@ I’m only enabling this at home for now, since it requires building stuff. | |||
1479 | (visual-fill-column-mode -1)) | 1506 | (visual-fill-column-mode -1)) |
1480 | 1507 | ||
1481 | (at-home | 1508 | (at-home |
1482 | (straight-use-package 'pdf-tools) | 1509 | (straight-use-package 'pdf-tools) |
1483 | (pdf-loader-install) | 1510 | (pdf-loader-install) |
1484 | 1511 | ||
1485 | (add-hook 'pdf-view-mode-hook #'acdw/disable-visual-fill-column-mode)) | 1512 | (add-hook 'pdf-view-mode-hook #'acdw/disable-visual-fill-column-mode)) |
1486 | 1513 | ||
1487 | 1514 | ||
1488 | ## E-book tools | 1515 | ## E-book tools |
@@ -1729,12 +1756,12 @@ I’m only enabling this at home for now, since it requires building stuff. | |||
1729 | ### Exec path from shell | 1756 | ### Exec path from shell |
1730 | 1757 | ||
1731 | (at-home | 1758 | (at-home |
1732 | (straight-use-package 'exec-path-from-shell) | 1759 | (straight-use-package 'exec-path-from-shell) |
1733 | (defvar acdw/exec-path-from-shell-initialized nil | 1760 | (defvar acdw/exec-path-from-shell-initialized nil |
1734 | "Stores whether we've initialized or not.") | 1761 | "Stores whether we've initialized or not.") |
1735 | (unless acdw/exec-path-from-shell-initialized | 1762 | (unless acdw/exec-path-from-shell-initialized |
1736 | (exec-path-from-shell-initialize) | 1763 | (exec-path-from-shell-initialize) |
1737 | (setq acdw/exec-path-from-shell-initialized (current-time)))) | 1764 | (setq acdw/exec-path-from-shell-initialized (current-time)))) |
1738 | 1765 | ||
1739 | 1766 | ||
1740 | # Appendices | 1767 | # Appendices |
@@ -1820,8 +1847,6 @@ I’m only enabling this at home for now, since it requires building stuff. | |||
1820 | 1847 | ||
1821 | ### emacsdc | 1848 | ### emacsdc |
1822 | 1849 | ||
1823 | :header-args: :tangle bin/emacsdc :tangle-mode (identity #o755) | ||
1824 | |||
1825 | Here's a wrapper script that'll start `emacs --daemon` if there isn't | 1850 | Here's a wrapper script that'll start `emacs --daemon` if there isn't |
1826 | one, and then launch `emacsclient` with the arguments. I'd recommend | 1851 | one, and then launch `emacsclient` with the arguments. I'd recommend |
1827 | installing with either `ln -s bin/emacsdc $HOME/.local/bin/`, or | 1852 | installing with either `ln -s bin/emacsdc $HOME/.local/bin/`, or |
@@ -1835,14 +1860,24 @@ adding `$HOME/.local/bin` to your `$PATH`. | |||
1835 | 1860 | ||
1836 | ### Emacs.cmd | 1861 | ### Emacs.cmd |
1837 | 1862 | ||
1838 | Here's a wrapper script that'll run Emacs on Windows, with a custom `$HOME`. I have | 1863 | Here's a wrapper script that'll run Emacs on Windows, with a |
1839 | mine setup like this: Emacs is downloaded from [the GNU mirror](https://mirrors.tripadvisor.com/gnu/emacs/windows/emacs-27/emacs-27.1-x86_64.zip) and unzipped to | 1864 | custom `$HOME`. I have mine setup like this: Emacs is downloaded |
1840 | `~/Downloads/emacs/`. For some reason, Emacs by default sets `$HOME` to `%APPDATA%`, | 1865 | from [the GNU mirror](https://mirrors.tripadvisor.com/gnu/emacs/windows/emacs-27/emacs-27.1-x86_64.zip) and unzipped to `~/Downloads/emacs/`. For |
1841 | which doesn’t make a lot of sense to me. I change it to `%USERPROFILE%`, and then run | 1866 | some reason, Emacs by default sets `$HOME` to `%APPDATA%`, which |
1842 | Emacs with the supplied arguments. | 1867 | doesn’t make a lot of sense to me. I change it to |
1868 | `%USERPROFILE%\Downloads\home`, and then run Emacs with the | ||
1869 | supplied arguments. | ||
1843 | 1870 | ||
1844 | set HOME=%USERPROFILE% | 1871 | As far as creating a shortcut to the Desktop, you’ll have to do |
1845 | set EMACS="%USERPROFILE%\Downloads\emacs\bin\runemacs.exe" | 1872 | that yourself – *apparently* Windows doesn’t have a built-in |
1873 | shortcut-creating software >:(. | ||
1874 | |||
1875 | REM Set variables | ||
1876 | set HOME=%USERPROFILE%\Downloads\home | ||
1877 | set EMACS=%USERPROFILE%\Downloads\emacs\bin\runemacs.exe | ||
1878 | |||
1879 | REM Change the directory | ||
1880 | chdir %HOME% | ||
1846 | 1881 | ||
1847 | REM Run "Quick Mode" | 1882 | REM Run "Quick Mode" |
1848 | REM "%EMACS%" -Q %* | 1883 | REM "%EMACS%" -Q %* |
@@ -1873,7 +1908,7 @@ following source block, for details. | |||
1873 | 1908 | ||
1874 | TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION | 1909 | TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION |
1875 | 1910 | ||
1876 | 0. You just DO WHAT THE FUCK YOU WANT TO. | 1911 | 0. You just DO WHAT THE FUCK YOU WANT TO. |
1877 | 1912 | ||
1878 | 1913 | ||
1879 | ### Note on the license | 1914 | ### Note on the license |
diff --git a/config.org b/config.org index d926c32..fb78c55 100644 --- a/config.org +++ b/config.org | |||
@@ -5,7 +5,7 @@ | |||
5 | #+EXPORT_FILE_NAME: README.md | 5 | #+EXPORT_FILE_NAME: README.md |
6 | #+OPTIONS: toc:nil | 6 | #+OPTIONS: toc:nil |
7 | #+BANKRUPTCY_COUNT: 3.2 | 7 | #+BANKRUPTCY_COUNT: 3.2 |
8 | #+Time-stamp: <2021-01-10 21:37:08 acdw> | 8 | #+Time-stamp: <2021-01-12 17:49:44 aduckworth> |
9 | 9 | ||
10 | * Basics | 10 | * Basics |
11 | 11 | ||
@@ -19,117 +19,117 @@ | |||
19 | 19 | ||
20 | ** About me | 20 | ** About me |
21 | 21 | ||
22 | #+BEGIN_SRC emacs-lisp | 22 | #+begin_src emacs-lisp |
23 | (setq user-full-name "Case Duckworth" | 23 | (setq user-full-name "Case Duckworth" |
24 | user-mail-address "acdw@acdw.net") | 24 | user-mail-address "acdw@acdw.net") |
25 | #+END_SRC | 25 | #+end_src |
26 | 26 | ||
27 | ** Correct =exec-path= | 27 | ** Correct =exec-path= |
28 | 28 | ||
29 | Straight depends on Git, so I need to tell Emacs where different paths are. | 29 | Straight depends on Git, so I need to tell Emacs where different paths are. |
30 | 30 | ||
31 | #+BEGIN_SRC emacs-lisp | 31 | #+begin_src emacs-lisp |
32 | (let ((win-downloads "c:/Users/aduckworth/Downloads")) | 32 | (let ((win-downloads "c:/Users/aduckworth/Downloads")) |
33 | (dolist (path (list | 33 | (dolist (path (list |
34 | ;; Linux | 34 | ;; Linux |
35 | (expand-file-name "bin" | 35 | (expand-file-name "bin" |
36 | user-emacs-directory) | 36 | user-emacs-directory) |
37 | (expand-file-name "~/bin") | 37 | (expand-file-name "~/bin") |
38 | (expand-file-name "~/.local/bin") | 38 | (expand-file-name "~/.local/bin") |
39 | (expand-file-name "~/Scripts") | 39 | (expand-file-name "~/Scripts") |
40 | ;; Windows | 40 | ;; Windows |
41 | (expand-file-name "emacs/bin" | 41 | (expand-file-name "emacs/bin" |
42 | win-downloads) | 42 | win-downloads) |
43 | (expand-file-name "m/usr/bin" | 43 | (expand-file-name "m/usr/bin" |
44 | win-downloads) | 44 | win-downloads) |
45 | (expand-file-name "m/mingw64/bin" | 45 | (expand-file-name "m/mingw64/bin" |
46 | win-downloads) | 46 | win-downloads) |
47 | (expand-file-name "PortableGit/bin" | 47 | (expand-file-name "PortableGit/bin" |
48 | win-downloads) | 48 | win-downloads) |
49 | (expand-file-name "PortableGit/usr/bin" | 49 | (expand-file-name "PortableGit/usr/bin" |
50 | win-downloads))) | 50 | win-downloads))) |
51 | (when (file-exists-p path) | 51 | (when (file-exists-p path) |
52 | (add-to-list 'exec-path path)))) | 52 | (add-to-list 'exec-path path)))) |
53 | #+END_SRC | 53 | #+end_src |
54 | 54 | ||
55 | ** Package management | 55 | ** Package management |
56 | 56 | ||
57 | *** Straight.el | 57 | *** Straight.el |
58 | 58 | ||
59 | Straight can't bootstrap itself on Windows, so I've wrapped the | 59 | Straight can't bootstrap itself on Windows, so I've wrapped the |
60 | bootstrap code from straight's repo in a function. | 60 | bootstrap code from straight's repo in a function. |
61 | 61 | ||
62 | #+BEGIN_SRC emacs-lisp | 62 | #+begin_src emacs-lisp |
63 | (defun acdw/bootstrap-straight () | 63 | (defun acdw/bootstrap-straight () |
64 | "Bootstrap straight.el." | 64 | "Bootstrap straight.el." |
65 | (defvar bootstrap-version) | 65 | (defvar bootstrap-version) |
66 | (let ((bootstrap-file | 66 | (let ((bootstrap-file |
67 | (expand-file-name | 67 | (expand-file-name |
68 | "straight/repos/straight.el/bootstrap.el" | 68 | "straight/repos/straight.el/bootstrap.el" |
69 | user-emacs-directory)) | 69 | user-emacs-directory)) |
70 | (bootstrap-version 5)) | 70 | (bootstrap-version 5)) |
71 | (unless (file-exists-p bootstrap-file) | 71 | (unless (file-exists-p bootstrap-file) |
72 | (with-current-buffer | 72 | (with-current-buffer |
73 | (url-retrieve-synchronously | 73 | (url-retrieve-synchronously |
74 | (concat | 74 | (concat |
75 | "https://raw.githubusercontent.com/" | 75 | "https://raw.githubusercontent.com/" |
76 | "raxod502/straight.el/" | 76 | "raxod502/straight.el/" |
77 | "develop/install.el") | 77 | "develop/install.el") |
78 | 'silent 'inhibit-cookies) | 78 | 'silent 'inhibit-cookies) |
79 | (goto-char (point-max)) | 79 | (goto-char (point-max)) |
80 | (eval-print-last-sexp))) | 80 | (eval-print-last-sexp))) |
81 | (load bootstrap-file nil 'nomessage))) | 81 | (load bootstrap-file nil 'nomessage))) |
82 | #+END_SRC | 82 | #+end_src |
83 | 83 | ||
84 | Now, I'll /try/ running it regular-style, ignoring the errors. If it | 84 | Now, I'll /try/ running it regular-style, ignoring the errors. If it |
85 | doesn't work, I'll call git directly and clone the repo myself. | 85 | doesn't work, I'll call git directly and clone the repo myself. |
86 | 86 | ||
87 | #+BEGIN_SRC emacs-lisp | 87 | #+begin_src emacs-lisp |
88 | (unless (ignore-errors (acdw/bootstrap-straight)) | 88 | (unless (ignore-errors (acdw/bootstrap-straight)) |
89 | (message "%s" "Straight.el didn't bootstrap correctly. Cloning directly...") | 89 | (message "%s" "Straight.el didn't bootstrap correctly. Cloning directly...") |
90 | (call-process "git" nil | 90 | (call-process "git" nil |
91 | (get-buffer-create "*bootstrap-straight-messages*") nil | 91 | (get-buffer-create "*bootstrap-straight-messages*") nil |
92 | "clone" | 92 | "clone" |
93 | "https://github.com/raxod502/straight.el" | 93 | "https://github.com/raxod502/straight.el" |
94 | (expand-file-name "straight/repos/straight.el" | 94 | (expand-file-name "straight/repos/straight.el" |
95 | user-emacs-directory)) | 95 | user-emacs-directory)) |
96 | (acdw/bootstrap-straight)) | 96 | (acdw/bootstrap-straight)) |
97 | #+END_SRC | 97 | #+end_src |
98 | 98 | ||
99 | ** Ease-of-configuring functions | 99 | ** Ease-of-configuring functions |
100 | 100 | ||
101 | *** Emulate use-package’s =:custom= | 101 | *** Emulate use-package’s =:custom= |
102 | 102 | ||
103 | #+BEGIN_SRC emacs-lisp | 103 | #+begin_src emacs-lisp |
104 | (defmacro cuss (var val &optional docstring) | 104 | (defmacro cuss (var val &optional docstring) |
105 | "Basically, `:custom' from `use-package', but without `use-package'." | 105 | "Basically, `:custom' from `use-package', but without `use-package'." |
106 | (declare (doc-string 3) | 106 | (declare (doc-string 3) |
107 | (indent 2)) | 107 | (indent 2)) |
108 | `(funcall (or (get ',var 'custom-set) #'set-default) | 108 | `(funcall (or (get ',var 'custom-set) #'set-default) |
109 | ',var ,val)) | 109 | ',var ,val)) |
110 | #+END_SRC | 110 | #+end_src |
111 | 111 | ||
112 | *** Emulate use-package’s =:custom-face=, but better | 112 | *** Emulate use-package’s =:custom-face=, but better |
113 | 113 | ||
114 | #+begin_src emacs-lisp | 114 | #+begin_src emacs-lisp |
115 | (defvar acdw--custom-faces () | 115 | (defvar acdw--custom-faces () |
116 | "List of custom faces to run through acdw/set-custom-faces.") | 116 | "List of custom faces to run through acdw/set-custom-faces.") |
117 | 117 | ||
118 | (defun acdw/set-custom-faces () | 118 | (defun acdw/set-custom-faces () |
119 | "Run `customize-set-faces' on `acdw--custom-faces'." | 119 | "Run `customize-set-faces' on `acdw--custom-faces'." |
120 | (message "%s" "Customizing faces...") | 120 | (message "%s" "Customizing faces...") |
121 | (apply #'custom-set-faces acdw--custom-faces)) | 121 | (apply #'custom-set-faces acdw--custom-faces)) |
122 | 122 | ||
123 | (defun cussface (spec) | 123 | (defun cussface (spec) |
124 | "Add SPEC to `acdw--custom-faces', and add a hook to run | 124 | "Add SPEC to `acdw--custom-faces', and add a hook to run |
125 | `acdw/set-custom-faces' after init." | 125 | `acdw/set-custom-faces' after init." |
126 | (add-to-list 'acdw--custom-faces spec) | 126 | (add-to-list 'acdw--custom-faces spec) |
127 | (add-hook 'after-init-hook #'acdw/set-custom-faces)) | 127 | (add-hook 'after-init-hook #'acdw/set-custom-faces)) |
128 | #+end_src | 128 | #+end_src |
129 | 129 | ||
130 | *** Determine whether any Emacs frame is focused or not | 130 | *** Determine whether any Emacs frame is focused or not |
131 | 131 | ||
132 | This comes in handy when I want to garbage collect, say, or save recent files. | 132 | This comes in handy when I want to garbage collect, say, or save recent files. |
133 | 133 | ||
134 | #+begin_src emacs-lisp | 134 | #+begin_src emacs-lisp |
135 | (defun acdw/when-unfocused (func &rest args) | 135 | (defun acdw/when-unfocused (func &rest args) |
@@ -140,144 +140,144 @@ This comes in handy when I want to garbage collect, say, or save recent files. | |||
140 | 140 | ||
141 | *** Determine where I am | 141 | *** Determine where I am |
142 | 142 | ||
143 | I use Emacs at home, with Linux, and at work, with Windows. | 143 | I use Emacs at home, with Linux, and at work, with Windows. |
144 | |||
145 | #+begin_src emacs-lisp | ||
146 | (defmacro at-work (&rest commands) | ||
147 | "Only do COMMANDS when at work." | ||
148 | (declare (indent defun)) | ||
149 | `(when (memq system-type '(ms-dos windows-nt)) | ||
150 | ,@commands)) | ||
151 | 144 | ||
152 | (defmacro at-home (&rest commands) | 145 | #+begin_src emacs-lisp |
153 | "Only do COMMANDS when at home." | 146 | (defmacro at-work (&rest commands) |
154 | (declare (indent defun)) | 147 | "Only do COMMANDS when at work." |
155 | `(when (memq system-type '(gnu gnu/linux gnu/kfreebsd)) | 148 | (declare (indent defun)) |
156 | ,@commands)) | 149 | `(when (memq system-type '(ms-dos windows-nt)) |
157 | #+end_src | 150 | ,@commands)) |
151 | |||
152 | (defmacro at-home (&rest commands) | ||
153 | "Only do COMMANDS when at home." | ||
154 | (declare (indent defun)) | ||
155 | `(when (memq system-type '(gnu gnu/linux gnu/kfreebsd)) | ||
156 | ,@commands)) | ||
157 | #+end_src | ||
158 | 158 | ||
159 | ** Clean =.emacs.d= | 159 | ** Clean =.emacs.d= |
160 | 160 | ||
161 | #+BEGIN_SRC emacs-lisp | 161 | #+begin_src emacs-lisp |
162 | (straight-use-package 'no-littering) | 162 | (straight-use-package 'no-littering) |
163 | (require 'no-littering) | 163 | (require 'no-littering) |
164 | #+END_SRC | 164 | #+end_src |
165 | 165 | ||
166 | *** Don’t clutter =init.el= with customizations | 166 | *** Don’t clutter =init.el= with customizations |
167 | 167 | ||
168 | #+begin_src emacs-lisp | 168 | #+begin_src emacs-lisp |
169 | (with-eval-after-load 'no-littering | 169 | (with-eval-after-load 'no-littering |
170 | (cuss custom-file (no-littering-expand-etc-file-name "custom.el"))) | 170 | (cuss custom-file (no-littering-expand-etc-file-name "custom.el"))) |
171 | #+end_src | 171 | #+end_src |
172 | 172 | ||
173 | ** Look and feel | 173 | ** Look and feel |
174 | 174 | ||
175 | *** Cursor | 175 | *** Cursor |
176 | 176 | ||
177 | #+BEGIN_SRC emacs-lisp | 177 | #+begin_src emacs-lisp |
178 | (cuss cursor-type 'bar | 178 | (cuss cursor-type 'bar |
179 | "Show a vertical bar for the cursor.") | 179 | "Show a vertical bar for the cursor.") |
180 | 180 | ||
181 | (cuss cursor-in-non-selected-windows 'hbar | 181 | (cuss cursor-in-non-selected-windows 'hbar |
182 | "Show an empty box in inactive windows.") | 182 | "Show an empty box in inactive windows.") |
183 | 183 | ||
184 | ;; Don't blink the cursor | 184 | ;; Don't blink the cursor |
185 | (blink-cursor-mode -1) | 185 | (blink-cursor-mode -1) |
186 | #+END_SRC | 186 | #+end_src |
187 | 187 | ||
188 | *** Tool Bars | 188 | *** Tool Bars |
189 | 189 | ||
190 | **** Tool bars and menu bars | 190 | **** Tool bars and menu bars |
191 | 191 | ||
192 | #+BEGIN_SRC emacs-lisp | 192 | #+begin_src emacs-lisp |
193 | (menu-bar-mode -1) | 193 | (menu-bar-mode -1) |
194 | (tool-bar-mode -1) | 194 | (tool-bar-mode -1) |
195 | #+END_SRC | 195 | #+end_src |
196 | 196 | ||
197 | **** Scroll bars | 197 | **** Scroll bars |
198 | 198 | ||
199 | #+BEGIN_SRC emacs-lisp | 199 | #+begin_src emacs-lisp |
200 | (scroll-bar-mode -1) | 200 | (scroll-bar-mode -1) |
201 | (horizontal-scroll-bar-mode -1) | 201 | (horizontal-scroll-bar-mode -1) |
202 | #+END_SRC | 202 | #+end_src |
203 | 203 | ||
204 | *** Dialogs | 204 | *** Dialogs |
205 | 205 | ||
206 | #+BEGIN_SRC emacs-lisp | 206 | #+begin_src emacs-lisp |
207 | (cuss use-dialog-box nil | 207 | (cuss use-dialog-box nil |
208 | "Don't use dialog boxes to ask questions.") | 208 | "Don't use dialog boxes to ask questions.") |
209 | #+END_SRC | 209 | #+end_src |
210 | 210 | ||
211 | **** Yes or no questions | 211 | **** Yes or no questions |
212 | 212 | ||
213 | #+BEGIN_SRC emacs-lisp | 213 | #+begin_src emacs-lisp |
214 | (fset 'yes-or-no-p #'y-or-n-p) | 214 | (fset 'yes-or-no-p #'y-or-n-p) |
215 | #+END_SRC | 215 | #+end_src |
216 | 216 | ||
217 | **** The Bell | 217 | **** The Bell |
218 | 218 | ||
219 | from [[https://www.emacswiki.org/emacs/AlarmBell#h5o-3][EmacsWiki]]. | 219 | from [[https://www.emacswiki.org/emacs/AlarmBell#h5o-3][EmacsWiki]]. |
220 | 220 | ||
221 | #+BEGIN_SRC emacs-lisp | 221 | #+begin_src emacs-lisp |
222 | (setq visible-bell nil | 222 | (setq visible-bell nil |
223 | ring-bell-function 'flash-mode-line) | 223 | ring-bell-function 'flash-mode-line) |
224 | 224 | ||
225 | (defun flash-mode-line () | 225 | (defun flash-mode-line () |
226 | (invert-face 'mode-line) | 226 | (invert-face 'mode-line) |
227 | (run-with-timer 0.1 nil #'invert-face 'mode-line)) | 227 | (run-with-timer 0.1 nil #'invert-face 'mode-line)) |
228 | #+END_SRC | 228 | #+end_src |
229 | 229 | ||
230 | *** Frames | 230 | *** Frames |
231 | 231 | ||
232 | **** Fringes | 232 | **** Fringes |
233 | 233 | ||
234 | #+BEGIN_SRC emacs-lisp | 234 | #+begin_src emacs-lisp |
235 | (cuss indicate-empty-lines t | 235 | (cuss indicate-empty-lines t |
236 | "Show an indicator on the left fringe of empty lines past the | 236 | "Show an indicator on the left fringe of empty lines past the |
237 | end of the buffer.") | 237 | end of the buffer.") |
238 | (cuss indicate-buffer-boundaries 'right | 238 | (cuss indicate-buffer-boundaries 'right |
239 | "Indicate the beginning and end of the buffer and whether it | 239 | "Indicate the beginning and end of the buffer and whether it |
240 | scrolls off-window in the right fringe.") | 240 | scrolls off-window in the right fringe.") |
241 | #+END_SRC | 241 | #+end_src |
242 | 242 | ||
243 | **** Minibuffer | 243 | **** Minibuffer |
244 | 244 | ||
245 | #+BEGIN_SRC emacs-lisp | 245 | #+begin_src emacs-lisp |
246 | (cuss minibuffer-prompt-properties | 246 | (cuss minibuffer-prompt-properties |
247 | '(read-only t cursor-intangible t face minibuffer-prompt) | 247 | '(read-only t cursor-intangible t face minibuffer-prompt) |
248 | "Keep the cursor away from the minibuffer prompt.") | 248 | "Keep the cursor away from the minibuffer prompt.") |
249 | #+END_SRC | 249 | #+end_src |
250 | 250 | ||
251 | **** Tabs | 251 | **** Tabs |
252 | 252 | ||
253 | #+BEGIN_SRC emacs-lisp | 253 | #+begin_src emacs-lisp |
254 | (cuss tab-bar-tab-name-function | 254 | (cuss tab-bar-tab-name-function |
255 | #'tab-bar-tab-name-current-with-count | 255 | #'tab-bar-tab-name-current-with-count |
256 | "Show the tab name as the name of the current buffer, plus a | 256 | "Show the tab name as the name of the current buffer, plus a |
257 | count of the windows in the tab.") | 257 | count of the windows in the tab.") |
258 | 258 | ||
259 | (cuss tab-bar-show 1 | 259 | (cuss tab-bar-show 1 |
260 | "Show the tab bar, when there's more than one tab.") | 260 | "Show the tab bar, when there's more than one tab.") |
261 | #+END_SRC | 261 | #+end_src |
262 | 262 | ||
263 | *** Windows | 263 | *** Windows |
264 | 264 | ||
265 | **** Winner mode | 265 | **** Winner mode |
266 | 266 | ||
267 | #+BEGIN_SRC emacs-lisp | 267 | #+begin_src emacs-lisp |
268 | (when (fboundp 'winner-mode) | 268 | (when (fboundp 'winner-mode) |
269 | (winner-mode +1)) | 269 | (winner-mode +1)) |
270 | #+END_SRC | 270 | #+end_src |
271 | 271 | ||
272 | **** Switch windows | 272 | **** Switch windows |
273 | 273 | ||
274 | #+BEGIN_SRC emacs-lisp | 274 | #+begin_src emacs-lisp |
275 | (global-set-key (kbd "M-o") #'other-window) | 275 | (global-set-key (kbd "M-o") #'other-window) |
276 | #+END_SRC | 276 | #+end_src |
277 | 277 | ||
278 | **** Pop-up windows | 278 | **** Pop-up windows |
279 | 279 | ||
280 | #+BEGIN_SRC emacs-lisp | 280 | #+begin_src emacs-lisp |
281 | (straight-use-package 'popwin) | 281 | (straight-use-package 'popwin) |
282 | (popwin-mode +1) | 282 | (popwin-mode +1) |
283 | #+end_src | 283 | #+end_src |
@@ -286,56 +286,56 @@ end of the buffer.") | |||
286 | 286 | ||
287 | **** Uniquify buffers | 287 | **** Uniquify buffers |
288 | 288 | ||
289 | #+BEGIN_SRC emacs-lisp | 289 | #+begin_src emacs-lisp |
290 | (require 'uniquify) | 290 | (require 'uniquify) |
291 | (cuss uniquify-buffer-name-style 'forward | 291 | (cuss uniquify-buffer-name-style 'forward |
292 | "Uniquify buffers' names by going up the path trees until they | 292 | "Uniquify buffers' names by going up the path trees until they |
293 | become unique.") | 293 | become unique.") |
294 | #+END_SRC | 294 | #+end_src |
295 | 295 | ||
296 | **** Startup buffers | 296 | **** Startup buffers |
297 | 297 | ||
298 | #+BEGIN_SRC emacs-lisp | 298 | #+begin_src emacs-lisp |
299 | (cuss inhibit-startup-screen t | 299 | (cuss inhibit-startup-screen t |
300 | "Don't show Emacs' startup buffer.") | 300 | "Don't show Emacs' startup buffer.") |
301 | 301 | ||
302 | (cuss initial-buffer-choice t | 302 | (cuss initial-buffer-choice t |
303 | "Start with *scratch*.") | 303 | "Start with *scratch*.") |
304 | 304 | ||
305 | (cuss initial-scratch-message "" | 305 | (cuss initial-scratch-message "" |
306 | "Empty *scratch* buffer.") | 306 | "Empty *scratch* buffer.") |
307 | #+END_SRC | 307 | #+end_src |
308 | 308 | ||
309 | **** COMMENT Focus and move buffers directionally | 309 | **** COMMENT Focus and move buffers directionally |
310 | 310 | ||
311 | Commented for now because I really need to figure out the keybindings I want to use for this. The real issue is the collisions between Org-mode, Windows, and Emacs’ normal bindings. | 311 | Commented for now because I really need to figure out the keybindings I want to use for this. The real issue is the collisions between Org-mode, Windows, and Emacs’ normal bindings. |
312 | |||
313 | #+begin_src emacs-lisp | ||
314 | ;; change focus | ||
315 | ;; for more on `ignore-error-wrapper', see | ||
316 | ;; https://www.emacswiki.org/emacs/WindMove#h5o-3 | ||
317 | (defun ignore-error-wrapper (fn) | ||
318 | "Funtion return new function that ignore errors. | ||
319 | The function wraps a function with `ignore-errors' macro." | ||
320 | (lexical-let ((fn fn)) | ||
321 | (lambda () | ||
322 | (interactive) | ||
323 | (ignore-errors | ||
324 | (funcall fn))))) | ||
325 | 312 | ||
326 | (global-set-key [S-left] (ignore-error-wrapper 'windmove-left)) | 313 | #+begin_src emacs-lisp |
327 | (global-set-key [S-right] (ignore-error-wrapper 'windmove-right)) | 314 | ;; change focus |
328 | (global-set-key [S-up] (ignore-error-wrapper 'windmove-up)) | 315 | ;; for more on `ignore-error-wrapper', see |
329 | (global-set-key [S-down] (ignore-error-wrapper 'windmove-down)) | 316 | ;; https://www.emacswiki.org/emacs/WindMove#h5o-3 |
330 | 317 | (defun ignore-error-wrapper (fn) | |
331 | ;; shift buffers | 318 | "Funtion return new function that ignore errors. |
332 | (straight-use-package 'buffer-move) | 319 | The function wraps a function with `ignore-errors' macro." |
333 | 320 | (lexical-let ((fn fn)) | |
334 | (global-set-key (kbd "<C-S-up>") 'buf-move-up) | 321 | (lambda () |
335 | (global-set-key (kbd "<C-S-down>") 'buf-move-down) | 322 | (interactive) |
336 | (global-set-key (kbd "<C-S-left>") 'buf-move-left) | 323 | (ignore-errors |
337 | (global-set-key (kbd "<C-S-right>") 'buf-move-right) | 324 | (funcall fn))))) |
338 | #+end_src | 325 | |
326 | (global-set-key [S-left] (ignore-error-wrapper 'windmove-left)) | ||
327 | (global-set-key [S-right] (ignore-error-wrapper 'windmove-right)) | ||
328 | (global-set-key [S-up] (ignore-error-wrapper 'windmove-up)) | ||
329 | (global-set-key [S-down] (ignore-error-wrapper 'windmove-down)) | ||
330 | |||
331 | ;; shift buffers | ||
332 | (straight-use-package 'buffer-move) | ||
333 | |||
334 | (global-set-key (kbd "<C-S-up>") 'buf-move-up) | ||
335 | (global-set-key (kbd "<C-S-down>") 'buf-move-down) | ||
336 | (global-set-key (kbd "<C-S-left>") 'buf-move-left) | ||
337 | (global-set-key (kbd "<C-S-right>") 'buf-move-right) | ||
338 | #+end_src | ||
339 | 339 | ||
340 | **** Kill the current buffer | 340 | **** Kill the current buffer |
341 | 341 | ||
@@ -386,160 +386,175 @@ Commented for now because I really need to figure out the keybindings I want to | |||
386 | 386 | ||
387 | **** Smart mode line | 387 | **** Smart mode line |
388 | 388 | ||
389 | #+BEGIN_SRC emacs-lisp | 389 | #+begin_src emacs-lisp |
390 | (straight-use-package 'smart-mode-line) | 390 | (straight-use-package 'smart-mode-line) |
391 | 391 | ||
392 | (cuss sml/no-confirm-load-theme t | 392 | (cuss sml/no-confirm-load-theme t |
393 | "Pass the NO-CONFIRM flag to `load-theme'.") | 393 | "Pass the NO-CONFIRM flag to `load-theme'.") |
394 | 394 | ||
395 | (sml/setup) | 395 | (sml/setup) |
396 | #+END_SRC | 396 | #+end_src |
397 | 397 | ||
398 | **** Rich minority | 398 | **** Rich minority |
399 | 399 | ||
400 | Since this /comes/ with smart mode line, I’m just going to use it, | 400 | Since this /comes/ with smart mode line, I’m just going to use it, |
401 | instead of =diminish= or another package. I do have to write this | 401 | instead of =diminish= or another package. I do have to write this |
402 | helper function, though, to add things to the whitelist. | 402 | helper function, though, to add things to the whitelist. |
403 | 403 | ||
404 | #+BEGIN_SRC emacs-lisp | 404 | #+begin_src emacs-lisp |
405 | (defun rm/whitelist-add (regexp) | 405 | (defun rm/whitelist-add (regexp) |
406 | "Add a REGEXP to the whitelist for `rich-minority'." | 406 | "Add a REGEXP to the whitelist for `rich-minority'." |
407 | (if (listp 'rm--whitelist-regexps) | 407 | (if (listp 'rm--whitelist-regexps) |
408 | (add-to-list 'rm--whitelist-regexps regexp) | 408 | (add-to-list 'rm--whitelist-regexps regexp) |
409 | (setq rm--whitelist-regexps `(,regexp))) | 409 | (setq rm--whitelist-regexps `(,regexp))) |
410 | (setq rm-whitelist | 410 | (setq rm-whitelist |
411 | (mapconcat 'identity rm--whitelist-regexps "\\|"))) | 411 | (mapconcat 'identity rm--whitelist-regexps "\\|"))) |
412 | 412 | ||
413 | (straight-use-package 'rich-minority) | 413 | (straight-use-package 'rich-minority) |
414 | 414 | ||
415 | (rm/whitelist-add "^$") | 415 | (rm/whitelist-add "^$") |
416 | #+END_SRC | 416 | #+end_src |
417 | 417 | ||
418 | *** Theme | 418 | *** Theme |
419 | 419 | ||
420 | **** Modus Themes | 420 | **** Modus Themes |
421 | 421 | ||
422 | #+BEGIN_SRC emacs-lisp | 422 | #+begin_src emacs-lisp |
423 | (straight-use-package 'modus-themes) | 423 | (straight-use-package 'modus-themes) |
424 | 424 | ||
425 | (cuss modus-themes-slanted-constructs t | 425 | (cuss modus-themes-slanted-constructs t |
426 | "Use more slanted constructs.") | 426 | "Use more slanted constructs.") |
427 | (cuss modus-themes-bold-constructs t | 427 | (cuss modus-themes-bold-constructs t |
428 | "Use more bold constructs.") | 428 | "Use more bold constructs.") |
429 | 429 | ||
430 | (cuss modus-themes-region 'bg-only | 430 | (cuss modus-themes-region 'bg-only |
431 | "Only highlight the background of the selected region.") | 431 | "Only highlight the background of the selected region.") |
432 | 432 | ||
433 | (cuss modus-themes-org-blocks 'grayscale | 433 | (cuss modus-themes-org-blocks 'grayscale |
434 | "Show org-blocks with a grayscale background.") | 434 | "Show org-blocks with a grayscale background.") |
435 | (cuss modus-themes-headings | 435 | (cuss modus-themes-headings |
436 | '((1 . line) | 436 | '((1 . line) |
437 | (t . t)) | 437 | (t . t)) |
438 | "Highlight top headings with `line' style, and others by default.") | 438 | "Highlight top headings with `line' style, and others by default.") |
439 | 439 | ||
440 | (cuss modus-themes-scale-headings t | 440 | (cuss modus-themes-scale-headings t |
441 | "Scale headings by the ratios below.") | 441 | "Scale headings by the ratios below.") |
442 | (cuss modus-themes-scale-1 1.1) | 442 | (cuss modus-themes-scale-1 1.1) |
443 | (cuss modus-themes-scale-2 1.15) | 443 | (cuss modus-themes-scale-2 1.15) |
444 | (cuss modus-themes-scale-3 1.21) | 444 | (cuss modus-themes-scale-3 1.21) |
445 | (cuss modus-themes-scale-4 1.27) | 445 | (cuss modus-themes-scale-4 1.27) |
446 | (cuss modus-themes-scale-5 1.33) | 446 | (cuss modus-themes-scale-5 1.33) |
447 | 447 | ||
448 | (load-theme 'modus-operandi t) | 448 | (load-theme 'modus-operandi t) |
449 | #+END_SRC | 449 | #+end_src |
450 | 450 | ||
451 | **** Change themes based on time of day | 451 | **** Change themes based on time of day |
452 | 452 | ||
453 | #+BEGIN_SRC emacs-lisp | 453 | #+begin_src emacs-lisp |
454 | (cuss calendar-latitude 30.4515) | 454 | (cuss calendar-latitude 30.4515) |
455 | (cuss calendar-longitude -91.1871) | 455 | (cuss calendar-longitude -91.1871) |
456 | 456 | ||
457 | ;; sunrise | 457 | (defun acdw/run-with-sun (sunrise-command sunset-command) |
458 | (run-at-time (nth 1 (split-string (sunrise-sunset))) | 458 | "Run commands at sunrise and sunset." |
459 | (* 60 60 24) | 459 | (let* ((times-regex (rx (* nonl) |
460 | (lambda () | 460 | (: (any ?s ?S) "unrise") " " |
461 | (modus-themes-load-operandi))) | 461 | (group (repeat 1 2 digit) ":" |
462 | 462 | (repeat 1 2 digit) | |
463 | ;; sunset | 463 | (: (any ?a ?A ?p ?P) (any ?m ?M))) |
464 | (run-at-time (nth 4 (split-string (sunrise-sunset))) | 464 | (* nonl) |
465 | (* 60 60 24) | 465 | (: (any ?s ?S) "unset") " " |
466 | (lambda () | 466 | (group (repeat 1 2 digit) ":" |
467 | (modus-themes-load-vivendi))) | 467 | (repeat 1 2 digit) |
468 | #+END_SRC | 468 | (: (any ?a ?A ?p ?P) (any ?m ?M))) |
469 | (* nonl))) | ||
470 | (ss (sunrise-sunset)) | ||
471 | (m_ (string-match times-regex ss)) | ||
472 | (sunrise-time (match-string 1 ss)) | ||
473 | (sunset-time (match-string 2 ss))) | ||
474 | (run-at-time sunrise-time (* 60 60 24) sunrise-command) | ||
475 | (run-at-time sunset-time (* 60 60 24) sunset-command))) | ||
476 | |||
477 | (acdw/run-with-sun #'modus-themes-load-operandi #'modus-themes-load-vivendi) | ||
478 | #+end_src | ||
469 | 479 | ||
470 | *** Fonts | 480 | *** Fonts |
471 | 481 | ||
472 | **** Define fonts | 482 | **** Define fonts |
473 | 483 | ||
474 | #+BEGIN_SRC emacs-lisp | 484 | #+begin_src emacs-lisp |
475 | (defun set-face-from-alternatives (face frame &rest fontspecs) | 485 | (defun set-face-from-alternatives (face frame &rest fontspecs) |
476 | "Set FACE on FRAME from first available spec from FONTSPECS. | 486 | "Set FACE on FRAME from first available spec from FONTSPECS. |
477 | FACE and FRAME work the same as with `set-face-attribute.'" | 487 | FACE and FRAME work the same as with `set-face-attribute.'" |
478 | (catch :return | 488 | (catch :return |
479 | (dolist (spec fontspecs) | 489 | (dolist (spec fontspecs) |
480 | (when-let ((found (find-font (apply #'font-spec spec)))) | 490 | (when-let ((found (find-font (apply #'font-spec spec)))) |
481 | (set-face-attribute face frame :font found) | 491 | (set-face-attribute face frame :font found) |
482 | (throw :return found))))) | 492 | (throw :return found))))) |
483 | 493 | ||
484 | (defun acdw/setup-fonts () | 494 | (defun acdw/setup-fonts () |
485 | "Setup fonts. This has to happen after the frame is setup for | 495 | "Setup fonts. This has to happen after the frame is setup for |
486 | the first time, so it should be added to `window-setup-hook'. It | 496 | the first time, so it should be added to `window-setup-hook'. It |
487 | removes itself from that hook." | 497 | removes itself from that hook." |
488 | (interactive) | 498 | (interactive) |
489 | (when (display-graphic-p) | 499 | (when (display-graphic-p) |
490 | (dolist (face '(default fixed-pitch)) | 500 | (dolist (face '(default fixed-pitch)) |
491 | ;; fixed-pitch /is/ the default | 501 | ;; fixed-pitch /is/ the default |
492 | (set-face-from-alternatives face nil | 502 | (set-face-from-alternatives face nil |
493 | '(:family "Input Mono" | 503 | '(:family "Input Mono" |
494 | :weight normal | 504 | :slant normal |
495 | :height 110) | 505 | :weight normal |
496 | '(:family "Go Mono" | 506 | :height 110) |
497 | :weight normal | 507 | '(:family "Go Mono" |
498 | :height 100) | 508 | :slant normal |
499 | '(:family "Consolas" | 509 | :weight normal |
500 | :weight normal | 510 | :height 100) |
501 | :height 100))) | 511 | '(:family "Consolas" |
502 | ;; variable-pitch is different | 512 | :slant normal |
503 | (set-face-from-alternatives 'variable-pitch nil | 513 | :weight normal |
504 | '(:family "Input Sans" | 514 | :height 100))) |
505 | :weight normal) | 515 | ;; variable-pitch is different |
506 | '(:family "Georgia" | 516 | (set-face-from-alternatives 'variable-pitch nil |
507 | :weight normal))) | 517 | '(:family "Input Sans" |
508 | 518 | :slant normal | |
509 | ;; remove myself from the hook | 519 | :weight normal) |
510 | (remove-function after-focus-change-function #'acdw/setup-fonts)) | 520 | '(:family "Georgia" |
511 | 521 | :slant normal | |
512 | (add-function :before after-focus-change-function #'acdw/setup-fonts) | 522 | :weight normal))) |
513 | #+END_SRC | 523 | |
524 | ;; remove myself from the hook | ||
525 | (remove-function after-focus-change-function #'acdw/setup-fonts)) | ||
526 | |||
527 | (add-function :before after-focus-change-function #'acdw/setup-fonts) | ||
528 | #+end_src | ||
514 | 529 | ||
515 | **** Custom faces | 530 | **** Custom faces |
516 | 531 | ||
517 | #+begin_src emacs-lisp | 532 | #+begin_src emacs-lisp |
518 | (cussface '(font-lock-comment-face | 533 | (cussface '(font-lock-comment-face |
519 | ((t (:inherit (custom-comment italic variable-pitch)))))) | 534 | ((t (:inherit (custom-comment italic variable-pitch)))))) |
520 | #+end_src | 535 | #+end_src |
521 | 536 | ||
522 | **** Line spacing | 537 | **** Line spacing |
523 | 538 | ||
524 | #+BEGIN_SRC emacs-lisp | 539 | #+begin_src emacs-lisp |
525 | (cuss line-spacing 0.1 | 540 | (cuss line-spacing 0.1 |
526 | "Add 10% extra space below each line.") | 541 | "Add 10% extra space below each line.") |
527 | #+END_SRC | 542 | #+end_src |
528 | 543 | ||
529 | **** Underlines | 544 | **** Underlines |
530 | 545 | ||
531 | #+begin_src emacs-lisp | 546 | #+begin_src emacs-lisp |
532 | (cuss x-underline-at-descent-line t | 547 | (cuss x-underline-at-descent-line t |
533 | "Draw the underline at the same place as the descent line.") | 548 | "Draw the underline at the same place as the descent line.") |
534 | #+end_src | 549 | #+end_src |
535 | 550 | ||
536 | **** Unicode Fonts | 551 | **** Unicode Fonts |
537 | 552 | ||
538 | #+BEGIN_SRC emacs-lisp | 553 | #+begin_src emacs-lisp |
539 | (straight-use-package 'unicode-fonts) | 554 | (straight-use-package 'unicode-fonts) |
540 | (require 'unicode-fonts) | 555 | (require 'unicode-fonts) |
541 | (unicode-fonts-setup) | 556 | (unicode-fonts-setup) |
542 | #+END_SRC | 557 | #+end_src |
543 | 558 | ||
544 | ** Interactivity | 559 | ** Interactivity |
545 | 560 | ||
@@ -547,173 +562,169 @@ Commented for now because I really need to figure out the keybindings I want to | |||
547 | 562 | ||
548 | **** Shadow file names in =completing-read=. | 563 | **** Shadow file names in =completing-read=. |
549 | 564 | ||
550 | #+BEGIN_SRC emacs-lisp | 565 | #+begin_src emacs-lisp |
551 | (cuss file-name-shadow-properties '(invisible t)) | 566 | (cuss file-name-shadow-properties '(invisible t)) |
552 | 567 | ||
553 | (file-name-shadow-mode +1) | 568 | (file-name-shadow-mode +1) |
554 | #+END_SRC | 569 | #+end_src |
555 | 570 | ||
556 | **** Ignore case in =completing-read= | 571 | **** Ignore case in =completing-read= |
557 | 572 | ||
558 | #+BEGIN_SRC emacs-lisp | 573 | #+begin_src emacs-lisp |
559 | (cuss completion-ignore-case t) | 574 | (cuss completion-ignore-case t) |
560 | (cuss read-buffer-completion-ignore-case t) | 575 | (cuss read-buffer-completion-ignore-case t) |
561 | (cuss read-file-name-completion-ignore-case t) | 576 | (cuss read-file-name-completion-ignore-case t) |
562 | #+END_SRC | 577 | #+end_src |
563 | 578 | ||
564 | **** Minibuffer recursivity | 579 | **** Minibuffer recursivity |
565 | 580 | ||
566 | #+begin_src emacs-lisp | 581 | #+begin_src emacs-lisp |
567 | (cuss enable-recursive-minibuffers t) | 582 | (cuss enable-recursive-minibuffers t) |
568 | (minibuffer-depth-indicate-mode +1) | 583 | (minibuffer-depth-indicate-mode +1) |
569 | #+end_src | 584 | #+end_src |
570 | 585 | ||
571 | **** Selectrum | 586 | **** Selectrum |
572 | 587 | ||
573 | #+BEGIN_SRC emacs-lisp | 588 | #+begin_src emacs-lisp |
574 | (straight-use-package 'selectrum) | 589 | (straight-use-package 'selectrum) |
575 | (require 'selectrum) | 590 | (require 'selectrum) |
576 | (selectrum-mode +1) | 591 | (selectrum-mode +1) |
577 | #+END_SRC | 592 | #+end_src |
578 | 593 | ||
579 | **** Prescient | 594 | **** Prescient |
580 | 595 | ||
581 | #+BEGIN_SRC emacs-lisp | 596 | #+begin_src emacs-lisp |
582 | (straight-use-package 'prescient) | 597 | (straight-use-package 'prescient) |
583 | (require 'prescient) | 598 | (require 'prescient) |
584 | (prescient-persist-mode +1) | 599 | (prescient-persist-mode +1) |
585 | 600 | ||
586 | (straight-use-package 'selectrum-prescient) | 601 | (straight-use-package 'selectrum-prescient) |
587 | (require 'selectrum-prescient) | 602 | (require 'selectrum-prescient) |
588 | (selectrum-prescient-mode +1) | 603 | (selectrum-prescient-mode +1) |
589 | #+END_SRC | 604 | #+end_src |
590 | 605 | ||
591 | **** Consult | 606 | **** Consult |
592 | 607 | ||
593 | #+BEGIN_SRC emacs-lisp | 608 | #+begin_src emacs-lisp |
594 | (straight-use-package '(consult | 609 | (straight-use-package '(consult |
595 | :host github | 610 | :host github |
596 | :repo "minad/consult")) | 611 | :repo "minad/consult" |
597 | (require 'consult) | 612 | :files (:defaults "consult-pkg.el"))) |
598 | 613 | (require 'consult) | |
599 | (straight-use-package '(consult-selectrum | 614 | |
600 | :host github | 615 | (with-eval-after-load 'consult |
601 | :repo "minad/consult")) | 616 | (define-key ctl-x-map "b" #'consult-buffer) |
602 | (require 'consult-selectrum) | 617 | (define-key ctl-x-map (kbd "C-r") #'consult-buffer) |
603 | 618 | (define-key ctl-x-map "4b" #'consult-buffer-other-window) | |
604 | (with-eval-after-load 'consult | 619 | (define-key ctl-x-map "5b" #'consult-buffer-other-frame) |
605 | (define-key ctl-x-map "b" #'consult-buffer) | 620 | |
606 | (define-key ctl-x-map (kbd "C-r") #'consult-buffer) | 621 | (define-key goto-map "o" #'consult-outline) |
607 | (define-key ctl-x-map "4b" #'consult-buffer-other-window) | 622 | (define-key goto-map "g" #'consult-line) |
608 | (define-key ctl-x-map "5b" #'consult-buffer-other-frame) | 623 | (define-key goto-map (kbd "M-g") #'consult-line) |
609 | 624 | (define-key goto-map "l" #'consult-line) | |
610 | (define-key goto-map "o" #'consult-outline) | 625 | (define-key goto-map "m" #'consult-mark) |
611 | (define-key goto-map "g" #'consult-line) | 626 | (define-key goto-map "i" #'consult-imenu) |
612 | (define-key goto-map (kbd "M-g") #'consult-line) | 627 | (define-key goto-map "e" #'consult-error) |
613 | (define-key goto-map "l" #'consult-line) | 628 | |
614 | (define-key goto-map "m" #'consult-mark) | 629 | (global-set-key (kbd "M-y") #'consult-yank-pop) |
615 | (define-key goto-map "i" #'consult-imenu) | 630 | |
616 | (define-key goto-map "e" #'consult-error) | 631 | (define-key help-map "a" #'consult-apropos) |
617 | 632 | ||
618 | (global-set-key (kbd "M-y") #'consult-yank-pop) | 633 | (fset 'multi-occur #'consult-multi-occur)) |
619 | 634 | #+end_src | |
620 | (define-key help-map "a" #'consult-apropos) | ||
621 | |||
622 | (fset 'multi-occur #'consult-multi-occur)) | ||
623 | #+END_SRC | ||
624 | 635 | ||
625 | **** Marginalia | 636 | **** Marginalia |
626 | 637 | ||
627 | #+BEGIN_SRC emacs-lisp | 638 | #+begin_src emacs-lisp |
628 | (straight-use-package '(marginalia | 639 | (straight-use-package '(marginalia |
629 | :host github | 640 | :host github |
630 | :repo "minad/marginalia" | 641 | :repo "minad/marginalia" |
631 | :branch "main")) | 642 | :branch "main")) |
632 | 643 | ||
633 | (cuss marginalia-annotators | 644 | (cuss marginalia-annotators |
634 | '(marginalia-annotators-heavy | 645 | '(marginalia-annotators-heavy |
635 | marginalia-annotators-light)) | 646 | marginalia-annotators-light)) |
636 | 647 | ||
637 | (marginalia-mode +1) | 648 | (marginalia-mode +1) |
638 | #+END_SRC | 649 | #+end_src |
639 | 650 | ||
640 | **** COMMENT Ido | 651 | **** COMMENT Ido |
641 | 652 | ||
642 | [[https://wandersoncferreira.github.io/blog/ido/][Let’s try this out]]. | 653 | [[https://wandersoncferreira.github.io/blog/ido/][Let’s try this out]]. |
643 | 654 | ||
644 | #+begin_src emacs-lisp | 655 | #+begin_src emacs-lisp |
645 | (defun ido-choose-from-recentf () | 656 | (defun ido-choose-from-recentf () |
646 | "Use ido to select recently visited files." | 657 | "Use ido to select recently visited files." |
647 | (interactive) | 658 | (interactive) |
648 | (find-file (ido-completing-read "Open file: " recentf-list nil t))) | 659 | (find-file (ido-completing-read "Open file: " recentf-list nil t))) |
649 | 660 | ||
650 | (defun bk/go-straight-home () | 661 | (defun bk/go-straight-home () |
651 | (interactive) | 662 | (interactive) |
652 | (cond | 663 | (cond |
653 | ((looking-back "~/") (insert "projects/")) | 664 | ((looking-back "~/") (insert "projects/")) |
654 | ((looking-back "/") (insert "~/")) | 665 | ((looking-back "/") (insert "~/")) |
655 | (:else (call-interactively 'self-insert-command)))) | 666 | (:else (call-interactively 'self-insert-command)))) |
656 | 667 | ||
657 | (defun ido-disable-line-truncation () | 668 | (defun ido-disable-line-truncation () |
658 | (set (make-local-variable 'truncate-lines) nil)) | 669 | (set (make-local-variable 'truncate-lines) nil)) |
659 | 670 | ||
660 | (defun ido-define-keys () | 671 | (defun ido-define-keys () |
661 | (define-key ido-completion-map (kbd "C-n") 'ido-next-match) | 672 | (define-key ido-completion-map (kbd "C-n") 'ido-next-match) |
662 | (define-key ido-completion-map (kbd "C-p") 'ido-prev-match)) | 673 | (define-key ido-completion-map (kbd "C-p") 'ido-prev-match)) |
663 | 674 | ||
664 | (setq ido-enable-flex-matching t | 675 | (setq ido-enable-flex-matching t |
665 | ido-use-filename-at-point nil | 676 | ido-use-filename-at-point nil |
666 | ido-create-new-buffer 'always | 677 | ido-create-new-buffer 'always |
667 | confirm-nonexistent-file-or-buffer nil | 678 | confirm-nonexistent-file-or-buffer nil |
668 | completion-ignored-extensions (cons "*.aux" completion-ignored-extensions) | 679 | completion-ignored-extensions (cons "*.aux" completion-ignored-extensions) |
669 | max-mini-window-height 0.5 | 680 | max-mini-window-height 0.5 |
670 | ido-enable-tramp-completion t | 681 | ido-enable-tramp-completion t |
671 | ido-auto-merge-work-directories-length -1 | 682 | ido-auto-merge-work-directories-length -1 |
672 | ido-confirm-unique-completion t | 683 | ido-confirm-unique-completion t |
673 | ido-default-file-method 'selected-window | 684 | ido-default-file-method 'selected-window |
674 | ido-case-fold t | 685 | ido-case-fold t |
675 | ido-show-dot-for-dired t | 686 | ido-show-dot-for-dired t |
676 | ido-everywhere t | 687 | ido-everywhere t |
677 | ido-ignore-buffers (list (rx (or (and bos " ") | 688 | ido-ignore-buffers (list (rx (or (and bos " ") |
678 | (and bos | 689 | (and bos |
679 | (or "*Completions*" | 690 | (or "*Completions*" |
680 | "*Compile-Log*" | 691 | "*Compile-Log*" |
681 | "*Ido Completions*" | 692 | "*Ido Completions*" |
682 | "*Shell Command Output*" | 693 | "*Shell Command Output*" |
683 | "*vc-diff*") | 694 | "*vc-diff*") |
684 | eos)))) | 695 | eos)))) |
685 | ido-decorations (quote ("\n-> " "" "\n " "\n ..." "[" "]" " | 696 | ido-decorations (quote ("\n-> " "" "\n " "\n ..." "[" "]" " |
686 | [No match]" " [Matched]" " [Not readable]" " [Too big]" " | 697 | [No match]" " [Matched]" " [Not readable]" " [Too big]" " |
687 | [Confirm]"))) | 698 | [Confirm]"))) |
688 | 699 | ||
689 | (with-eval-after-load 'ido | 700 | (with-eval-after-load 'ido |
690 | (define-key ido-common-completion-map (kbd "M-SPC") 'just-one-space) | 701 | (define-key ido-common-completion-map (kbd "M-SPC") 'just-one-space) |
691 | (define-key ido-common-completion-map (kbd "SPC") 'self-insert-command) | 702 | (define-key ido-common-completion-map (kbd "SPC") 'self-insert-command) |
692 | (define-key ido-file-completion-map (kbd "~") 'bk/go-straight-home) | 703 | (define-key ido-file-completion-map (kbd "~") 'bk/go-straight-home) |
693 | 704 | ||
694 | (add-hook 'ido-setup-hook 'ido-define-keys) | 705 | (add-hook 'ido-setup-hook 'ido-define-keys) |
695 | 706 | ||
696 | (add-hook 'ido-minibuffer-setup-hook 'ido-disable-line-truncation) | 707 | (add-hook 'ido-minibuffer-setup-hook 'ido-disable-line-truncation) |
697 | 708 | ||
698 | (set-default 'imenu-auto-rescan t) | 709 | (set-default 'imenu-auto-rescan t) |
699 | 710 | ||
700 | (add-to-list 'ido-ignore-directories "target") | 711 | (add-to-list 'ido-ignore-directories "target") |
701 | (add-to-list 'ido-ignore-directories "node_modules") | 712 | (add-to-list 'ido-ignore-directories "node_modules") |
702 | ) | 713 | ) |
703 | 714 | ||
704 | (defun setup-ido-mode () | 715 | (defun setup-ido-mode () |
705 | (require 'ido) | 716 | (require 'ido) |
706 | (ido-mode +1) | 717 | (ido-mode +1) |
707 | (ido-everywhere +1)) | 718 | (ido-everywhere +1)) |
708 | 719 | ||
709 | (add-hook 'after-init-hook #'setup-ido-mode) | 720 | (add-hook 'after-init-hook #'setup-ido-mode) |
710 | #+end_src | 721 | #+end_src |
711 | 722 | ||
712 | *** Completion | 723 | *** Completion |
713 | 724 | ||
714 | #+begin_src emacs-lisp | 725 | #+begin_src emacs-lisp |
715 | (global-set-key (kbd "M-/") #'hippie-expand) | 726 | (global-set-key (kbd "M-/") #'hippie-expand) |
716 | #+end_src | 727 | #+end_src |
717 | 728 | ||
718 | *** Garbage collection | 729 | *** Garbage collection |
719 | 730 | ||
@@ -734,23 +745,23 @@ Commented for now because I really need to figure out the keybindings I want to | |||
734 | 745 | ||
735 | *** =ESC= cancels all | 746 | *** =ESC= cancels all |
736 | 747 | ||
737 | #+BEGIN_SRC emacs-lisp | 748 | #+begin_src emacs-lisp |
738 | (global-set-key (kbd "<escape>") #'keyboard-escape-quit) | 749 | (global-set-key (kbd "<escape>") #'keyboard-escape-quit) |
739 | #+END_SRC | 750 | #+end_src |
740 | 751 | ||
741 | *** Personal prefix key: =C-z= | 752 | *** Personal prefix key: =C-z= |
742 | 753 | ||
743 | #+BEGIN_SRC emacs-lisp | 754 | #+begin_src emacs-lisp |
744 | (defvar acdw/map | 755 | (defvar acdw/map |
745 | (let ((map (make-sparse-keymap)) | 756 | (let ((map (make-sparse-keymap)) |
746 | (c-z (global-key-binding "\C-z"))) | 757 | (c-z (global-key-binding "\C-z"))) |
747 | (global-unset-key "\C-z") | 758 | (global-unset-key "\C-z") |
748 | (define-key global-map "\C-z" map) | 759 | (define-key global-map "\C-z" map) |
749 | (define-key map "\C-z" c-z) | 760 | (define-key map "\C-z" c-z) |
750 | map)) | 761 | map)) |
751 | 762 | ||
752 | (run-hooks 'acdw/map-defined-hook) | 763 | (run-hooks 'acdw/map-defined-hook) |
753 | #+END_SRC | 764 | #+end_src |
754 | 765 | ||
755 | *** Show keybindings | 766 | *** Show keybindings |
756 | 767 | ||
@@ -763,107 +774,107 @@ Commented for now because I really need to figure out the keybindings I want to | |||
763 | 774 | ||
764 | *** Preserve screen position when scrolling with the mouse wheel | 775 | *** Preserve screen position when scrolling with the mouse wheel |
765 | 776 | ||
766 | from [[https://www.reddit.com/r/emacs/comments/km9by4/weekly_tipstricketc_thread/ghg2c9d/][u/TheFrenchPoulp]]. | 777 | from [[https://www.reddit.com/r/emacs/comments/km9by4/weekly_tipstricketc_thread/ghg2c9d/][u/TheFrenchPoulp]]. |
767 | 778 | ||
768 | #+BEGIN_SRC emacs-lisp | 779 | #+begin_src emacs-lisp |
769 | (advice-add 'mwheel-scroll :around #'me/mwheel-scroll) | 780 | (advice-add 'mwheel-scroll :around #'me/mwheel-scroll) |
770 | 781 | ||
771 | (defun me/mwheel-scroll (original &rest arguments) | 782 | (defun me/mwheel-scroll (original &rest arguments) |
772 | "Like `mwheel-scroll' but preserve screen position. | 783 | "Like `mwheel-scroll' but preserve screen position. |
773 | See `scroll-preserve-screen-position'." | 784 | See `scroll-preserve-screen-position'." |
774 | (let ((scroll-preserve-screen-position :always)) | 785 | (let ((scroll-preserve-screen-position :always)) |
775 | (apply original arguments))) | 786 | (apply original arguments))) |
776 | #+end_src | 787 | #+end_src |
777 | 788 | ||
778 | ** Persistence | 789 | ** Persistence |
779 | 790 | ||
780 | *** Minibuffer history | 791 | *** Minibuffer history |
781 | 792 | ||
782 | #+BEGIN_SRC emacs-lisp | 793 | #+begin_src emacs-lisp |
783 | (require 'savehist) | 794 | (require 'savehist) |
784 | 795 | ||
785 | (cuss savehist-additional-variables | 796 | (cuss savehist-additional-variables |
786 | '(kill-ring | 797 | '(kill-ring |
787 | search-ring | 798 | search-ring |
788 | regexp-search-ring) | 799 | regexp-search-ring) |
789 | "Other variables to save alongside the minibuffer history.") | 800 | "Other variables to save alongside the minibuffer history.") |
790 | 801 | ||
791 | (cuss history-length t | 802 | (cuss history-length t |
792 | "Don't truncate history.") | 803 | "Don't truncate history.") |
793 | 804 | ||
794 | (cuss history-delete-duplicates t | 805 | (cuss history-delete-duplicates t |
795 | "Delete history duplicates.") | 806 | "Delete history duplicates.") |
796 | 807 | ||
797 | (savehist-mode +1) | 808 | (savehist-mode +1) |
798 | #+END_SRC | 809 | #+end_src |
799 | 810 | ||
800 | *** File places | 811 | *** File places |
801 | 812 | ||
802 | #+BEGIN_SRC emacs-lisp | 813 | #+begin_src emacs-lisp |
803 | (require 'saveplace) ; this isn't required, but ... I like having it here | 814 | (require 'saveplace) ; this isn't required, but ... I like having it here |
804 | 815 | ||
805 | (cuss save-place-forget-unreadable-files t | 816 | (cuss save-place-forget-unreadable-files t |
806 | "Don't check if files are readable or not.") | 817 | "Don't check if files are readable or not.") |
807 | 818 | ||
808 | (save-place-mode +1) | 819 | (save-place-mode +1) |
809 | #+END_SRC | 820 | #+end_src |
810 | 821 | ||
811 | *** Recent files | 822 | *** Recent files |
812 | 823 | ||
813 | #+BEGIN_SRC emacs-lisp | 824 | #+begin_src emacs-lisp |
814 | (require 'recentf) | 825 | (require 'recentf) |
815 | 826 | ||
816 | (cuss recentf-max-menu-items 100 | 827 | (cuss recentf-max-menu-items 100 |
817 | "The maximum number of items in the recentf menu.") | 828 | "The maximum number of items in the recentf menu.") |
818 | (cuss recentf-max-saved-items nil | 829 | (cuss recentf-max-saved-items nil |
819 | "Don't limit the number of recent files.") | 830 | "Don't limit the number of recent files.") |
820 | 831 | ||
821 | (with-eval-after-load 'no-littering | 832 | (with-eval-after-load 'no-littering |
822 | (add-to-list 'recentf-exclude no-littering-var-directory) | 833 | (add-to-list 'recentf-exclude no-littering-var-directory) |
823 | (add-to-list 'recentf-exclude no-littering-etc-directory)) | 834 | (add-to-list 'recentf-exclude no-littering-etc-directory)) |
824 | 835 | ||
825 | (recentf-mode +1) | 836 | (recentf-mode +1) |
826 | 837 | ||
827 | ;; save recentf list when focusing away | 838 | ;; save recentf list when focusing away |
828 | (defun acdw/maybe-save-recentf () | 839 | (defun acdw/maybe-save-recentf () |
829 | "Save `recentf-file' when out of focus, but only if we haven't | 840 | "Save `recentf-file' when out of focus, but only if we haven't |
830 | in five minutes." | 841 | in five minutes." |
831 | (defvar recentf-last-save (time-convert nil 'integer) | 842 | (defvar recentf-last-save (time-convert nil 'integer) |
832 | "How long it's been since we last saved the recentf list.") | 843 | "How long it's been since we last saved the recentf list.") |
833 | 844 | ||
834 | (when (> (time-convert (time-since recentf-last-save) 'integer) | 845 | (when (> (time-convert (time-since recentf-last-save) 'integer) |
835 | (* 60 5)) | 846 | (* 60 5)) |
836 | (setq recentf-last-save (time-convert nil 'integer)) | 847 | (setq recentf-last-save (time-convert nil 'integer)) |
837 | (acdw/when-unfocused #'recentf-save-list))) | 848 | (acdw/when-unfocused #'recentf-save-list))) |
838 | 849 | ||
839 | (add-function :after after-focus-change-function | 850 | (add-function :after after-focus-change-function |
840 | #'acdw/maybe-save-recentf) | 851 | #'acdw/maybe-save-recentf) |
841 | #+END_SRC | 852 | #+end_src |
842 | 853 | ||
843 | ** Undo | 854 | ** Undo |
844 | 855 | ||
845 | #+BEGIN_SRC emacs-lisp | 856 | #+begin_src emacs-lisp |
846 | (straight-use-package 'undo-fu) | 857 | (straight-use-package 'undo-fu) |
847 | (require 'undo-fu) | 858 | (require 'undo-fu) |
848 | 859 | ||
849 | (global-set-key (kbd "C-/") #'undo-fu-only-undo) | 860 | (global-set-key (kbd "C-/") #'undo-fu-only-undo) |
850 | (global-set-key (kbd "C-?") #'undo-fu-only-redo) | 861 | (global-set-key (kbd "C-?") #'undo-fu-only-redo) |
851 | 862 | ||
852 | (straight-use-package 'undo-fu-session) | 863 | (straight-use-package 'undo-fu-session) |
853 | (require 'undo-fu-session) | 864 | (require 'undo-fu-session) |
854 | 865 | ||
855 | (cuss undo-fu-session-incompatible-files | 866 | (cuss undo-fu-session-incompatible-files |
856 | '("/COMMIT_EDITMSG\\'" | 867 | '("/COMMIT_EDITMSG\\'" |
857 | "/git-rebase-todo\\'") | 868 | "/git-rebase-todo\\'") |
858 | "A list of files that are incompatible with the concept of undo sessions.") | 869 | "A list of files that are incompatible with the concept of undo sessions.") |
859 | 870 | ||
860 | (with-eval-after-load 'no-littering | 871 | (with-eval-after-load 'no-littering |
861 | (let ((dir (no-littering-expand-var-file-name "undos"))) | 872 | (let ((dir (no-littering-expand-var-file-name "undos"))) |
862 | (make-directory dir 'parents) | 873 | (make-directory dir 'parents) |
863 | (cuss undo-fu-session-directory dir))) | 874 | (cuss undo-fu-session-directory dir))) |
864 | 875 | ||
865 | (global-undo-fu-session-mode +1) | 876 | (global-undo-fu-session-mode +1) |
866 | #+END_SRC | 877 | #+end_src |
867 | 878 | ||
868 | ** Files | 879 | ** Files |
869 | 880 | ||
@@ -871,101 +882,109 @@ from [[https://www.reddit.com/r/emacs/comments/km9by4/weekly_tipstricketc_thread | |||
871 | 882 | ||
872 | **** UTF-8 | 883 | **** UTF-8 |
873 | 884 | ||
874 | #+BEGIN_SRC emacs-lisp | 885 | from [[https://www.masteringemacs.org/article/working-coding-systems-unicode-emacs][Mastering Emacs]]. |
875 | (set-language-environment "UTF-8") | 886 | |
876 | (set-terminal-coding-system 'utf-8) | 887 | #+begin_src emacs-lisp |
877 | (cuss locale-coding-system 'utf-8) | 888 | (prefer-coding-system 'utf-8) |
878 | (set-default-coding-systems 'utf-8) | 889 | (set-default-coding-systems 'utf-8) |
879 | (set-selection-coding-system 'utf-8) | 890 | (set-terminal-coding-system 'utf-8) |
880 | (prefer-coding-system 'utf-8) | 891 | (set-keyboard-coding-system 'utf-8) |
881 | #+END_SRC | 892 | ;; backwards compatibility: |
893 | ;; `default-buffer-file-coding-system' is deprecated in 23.2. | ||
894 | (if (boundp 'buffer-file-coding-system) | ||
895 | (setq-default buffer-file-coding-system 'utf-8) | ||
896 | (setq default-buffer-file-coding-system 'utf-8)) | ||
897 | |||
898 | ;; Treat clipboard as UTF-8 string first; compound text next, etc. | ||
899 | (setq x-select-request-type '(UTF8_STRING COMPOUND_TEXT TEXT STRING)) | ||
900 | #+end_src | ||
882 | 901 | ||
883 | **** Convert all files to UNIX-style line endings | 902 | **** Convert all files to UNIX-style line endings |
884 | 903 | ||
885 | from [[https://www.emacswiki.org/emacs/EndOfLineTips][Emacs Wiki]]. | 904 | from [[https://www.emacswiki.org/emacs/EndOfLineTips][Emacs Wiki]]. |
886 | 905 | ||
887 | #+BEGIN_SRC emacs-lisp | 906 | #+begin_src emacs-lisp |
888 | (defun ewiki/no-junk-please-were-unixish () | 907 | (defun ewiki/no-junk-please-were-unixish () |
889 | "Convert line endings to UNIX, dammit." | 908 | "Convert line endings to UNIX, dammit." |
890 | (let ((coding-str (symbol-name buffer-file-coding-system))) | 909 | (let ((coding-str (symbol-name buffer-file-coding-system))) |
891 | (when (string-match "-\\(?:dos\\|mac\\)$" coding-str) | 910 | (when (string-match "-\\(?:dos\\|mac\\)$" coding-str) |
892 | (set-buffer-file-coding-system 'unix)))) | 911 | (set-buffer-file-coding-system 'unix)))) |
893 | #+END_SRC | 912 | #+end_src |
894 | 913 | ||
895 | I add it to the ~find-file-hook~ /and/ ~before-save-hook~ because I | 914 | I add it to the ~find-file-hook~ /and/ ~before-save-hook~ because I |
896 | don't want to ever work with anything other than UNIX line endings | 915 | don't want to ever work with anything other than UNIX line endings |
897 | ever again. I just don't care. Even Microsoft Notepad can handle | 916 | ever again. I just don't care. Even Microsoft Notepad can handle |
898 | UNIX line endings, so I don't want to hear it. | 917 | UNIX line endings, so I don't want to hear it. |
899 | 918 | ||
900 | #+BEGIN_SRC emacs-lisp | 919 | #+begin_src emacs-lisp |
901 | (add-hook 'find-file-hook #'ewiki/no-junk-please-were-unixish) | 920 | (add-hook 'find-file-hook #'ewiki/no-junk-please-were-unixish) |
902 | (add-hook 'before-save-hook #'ewiki/no-junk-please-were-unixish) | 921 | (add-hook 'before-save-hook #'ewiki/no-junk-please-were-unixish) |
903 | #+END_SRC | 922 | #+end_src |
904 | 923 | ||
905 | *** Backups | 924 | *** Backups |
906 | 925 | ||
907 | #+BEGIN_SRC emacs-lisp | 926 | #+begin_src emacs-lisp |
908 | (cuss backup-by-copying 1) | 927 | (cuss backup-by-copying 1) |
909 | (cuss delete-old-versions -1) | 928 | (cuss delete-old-versions -1) |
910 | (cuss version-control t) | 929 | (cuss version-control t) |
911 | (cuss vc-make-backup-files t) | 930 | (cuss vc-make-backup-files t) |
912 | 931 | ||
913 | (with-eval-after-load 'no-littering | 932 | (with-eval-after-load 'no-littering |
914 | (let ((dir (no-littering-expand-var-file-name "backup"))) | 933 | (let ((dir (no-littering-expand-var-file-name "backup"))) |
915 | (make-directory dir 'parents) | 934 | (make-directory dir 'parents) |
916 | (cuss backup-directory-alist | 935 | (cuss backup-directory-alist |
917 | `((".*" . ,dir))))) | 936 | `((".*" . ,dir))))) |
918 | #+END_SRC | 937 | #+end_src |
919 | 938 | ||
920 | *** Auto-saves | 939 | *** Auto-saves |
921 | 940 | ||
922 | #+BEGIN_SRC emacs-lisp | 941 | #+begin_src emacs-lisp |
923 | (with-eval-after-load 'no-littering | 942 | (with-eval-after-load 'no-littering |
924 | (let ((dir (no-littering-expand-var-file-name "autosaves"))) | 943 | (let ((dir (no-littering-expand-var-file-name "autosaves"))) |
925 | (make-directory dir 'parents) | 944 | (make-directory dir 'parents) |
926 | (cuss auto-save-file-name-transforms | 945 | (cuss auto-save-file-name-transforms |
927 | `((".*" ,dir t)))) | 946 | `((".*" ,dir t)))) |
928 | 947 | ||
929 | (auto-save-mode +1)) | 948 | (auto-save-mode +1)) |
930 | #+END_SRC | 949 | #+end_src |
931 | 950 | ||
932 | *** Super-save | 951 | *** Super-save |
933 | 952 | ||
934 | Because I like /overkill/, or at least … over-/saving/. | 953 | Because I like /overkill/, or at least … over-/saving/. |
935 | 954 | ||
936 | #+BEGIN_SRC emacs-lisp | 955 | #+begin_src emacs-lisp |
937 | (straight-use-package 'super-save) | 956 | (straight-use-package 'super-save) |
938 | 957 | ||
939 | (cuss super-save-remote-files nil | 958 | (cuss super-save-remote-files nil |
940 | "Don't super-save remote files.") | 959 | "Don't super-save remote files.") |
941 | 960 | ||
942 | (cuss super-save-exclude '(".gpg") | 961 | (cuss super-save-exclude '(".gpg") |
943 | "Ignore these files when saving.") | 962 | "Ignore these files when saving.") |
944 | 963 | ||
945 | (super-save-mode +1) | 964 | (super-save-mode +1) |
946 | #+end_src | 965 | #+end_src |
947 | 966 | ||
948 | *** Auto-revert buffers to files on disk | 967 | *** Auto-revert buffers to files on disk |
949 | 968 | ||
950 | #+BEGIN_SRC emacs-lisp | 969 | #+begin_src emacs-lisp |
951 | (global-auto-revert-mode +1) | 970 | (global-auto-revert-mode +1) |
952 | #+END_SRC | 971 | #+end_src |
953 | 972 | ||
954 | *** Add a timestamp to files | 973 | *** Add a timestamp to files |
955 | 974 | ||
956 | #+BEGIN_SRC emacs-lisp | 975 | #+begin_src emacs-lisp |
957 | (add-hook 'before-save-hook #'time-stamp) | 976 | (add-hook 'before-save-hook #'time-stamp) |
958 | #+END_SRC | 977 | #+end_src |
959 | 978 | ||
960 | *** Require a final new line | 979 | *** Require a final new line |
961 | 980 | ||
962 | #+BEGIN_SRC emacs-lisp | 981 | #+begin_src emacs-lisp |
963 | (cuss require-final-newline t) | 982 | (cuss require-final-newline t) |
964 | #+END_SRC | 983 | #+end_src |
965 | 984 | ||
966 | *** Edit files with =sudo= | 985 | *** Edit files with =sudo= |
967 | 986 | ||
968 | #+BEGIN_SRC emacs-lisp | 987 | #+begin_src emacs-lisp |
969 | (straight-use-package 'sudo-edit) | 988 | (straight-use-package 'sudo-edit) |
970 | 989 | ||
971 | (with-eval-after-load 'sudo-edit | 990 | (with-eval-after-load 'sudo-edit |
@@ -974,72 +993,72 @@ Because I like /overkill/, or at least … over-/saving/. | |||
974 | 993 | ||
975 | **** Don’t add =/sudo:= files to =recentf=, though | 994 | **** Don’t add =/sudo:= files to =recentf=, though |
976 | 995 | ||
977 | I’ve pretty much cribbed this from [[https://github.com/ncaq/recentf-remove-sudo-tramp-prefix/][recentf-remove-sudo-tramp-prefix]] – it’s a small enough package that I can just include it completely here. | 996 | I’ve pretty much cribbed this from [[https://github.com/ncaq/recentf-remove-sudo-tramp-prefix/][recentf-remove-sudo-tramp-prefix]] – it’s a small enough package that I can just include it completely here. |
978 | |||
979 | #+BEGIN_SRC emacs-lisp | ||
980 | (defun recentf-remove-sudo-tramp-prefix (path) | ||
981 | "Remove sudo from PATH." | ||
982 | (require 'tramp) | ||
983 | (if (tramp-tramp-file-p path) | ||
984 | (let ((tx (tramp-dissect-file-name path))) | ||
985 | (if (string-equal "sudo" (tramp-file-name-method tx)) | ||
986 | (tramp-file-name-localname tx) | ||
987 | path)) | ||
988 | path)) | ||
989 | |||
990 | (defun recentf-remove-sudo-tramp-prefix-from-recentf-list () | ||
991 | (require 'recentf) | ||
992 | (setq recentf-list | ||
993 | (mapcar #'recentf-remove-sudo-tramp-prefix recentf-list))) | ||
994 | 997 | ||
995 | (advice-add 'recentf-cleanup | 998 | #+begin_src emacs-lisp |
996 | :before #'recentf-remove-sudo-tramp-prefix-from-recentf-list) | 999 | (defun recentf-remove-sudo-tramp-prefix (path) |
997 | #+end_src | 1000 | "Remove sudo from PATH." |
1001 | (require 'tramp) | ||
1002 | (if (tramp-tramp-file-p path) | ||
1003 | (let ((tx (tramp-dissect-file-name path))) | ||
1004 | (if (string-equal "sudo" (tramp-file-name-method tx)) | ||
1005 | (tramp-file-name-localname tx) | ||
1006 | path)) | ||
1007 | path)) | ||
1008 | |||
1009 | (defun recentf-remove-sudo-tramp-prefix-from-recentf-list () | ||
1010 | (require 'recentf) | ||
1011 | (setq recentf-list | ||
1012 | (mapcar #'recentf-remove-sudo-tramp-prefix recentf-list))) | ||
1013 | |||
1014 | (advice-add 'recentf-cleanup | ||
1015 | :before #'recentf-remove-sudo-tramp-prefix-from-recentf-list) | ||
1016 | #+end_src | ||
998 | 1017 | ||
999 | ** Text editing | 1018 | ** Text editing |
1000 | 1019 | ||
1001 | *** Operate visually on lines | 1020 | *** Operate visually on lines |
1002 | 1021 | ||
1003 | #+BEGIN_SRC emacs-lisp | 1022 | #+begin_src emacs-lisp |
1004 | (global-visual-line-mode +1) | 1023 | (global-visual-line-mode +1) |
1005 | #+END_SRC | 1024 | #+end_src |
1006 | 1025 | ||
1007 | *** View long lines like filled lines in the beginning | 1026 | *** View long lines like filled lines in the beginning |
1008 | 1027 | ||
1009 | #+BEGIN_SRC emacs-lisp | 1028 | #+begin_src emacs-lisp |
1010 | (straight-use-package 'adaptive-wrap) | 1029 | (straight-use-package 'adaptive-wrap) |
1011 | (adaptive-wrap-prefix-mode +1) | 1030 | (adaptive-wrap-prefix-mode +1) |
1012 | #+end_src | 1031 | #+end_src |
1013 | 1032 | ||
1014 | *** Stay snappy with long-lined files | 1033 | *** Stay snappy with long-lined files |
1015 | 1034 | ||
1016 | #+BEGIN_SRC emacs-lisp | 1035 | #+begin_src emacs-lisp |
1017 | (when (fboundp 'global-so-long-mode) | 1036 | (when (fboundp 'global-so-long-mode) |
1018 | (global-so-long-mode +1)) | 1037 | (global-so-long-mode +1)) |
1019 | #+END_SRC | 1038 | #+end_src |
1020 | 1039 | ||
1021 | *** Killing & Yanking | 1040 | *** Killing & Yanking |
1022 | 1041 | ||
1023 | **** Replace selection when typing | 1042 | **** Replace selection when typing |
1024 | 1043 | ||
1025 | #+BEGIN_SRC emacs-lisp | 1044 | #+begin_src emacs-lisp |
1026 | (delete-selection-mode +1) | 1045 | (delete-selection-mode +1) |
1027 | #+END_SRC | 1046 | #+end_src |
1028 | 1047 | ||
1029 | **** Work better with the system clipboard | 1048 | **** Work better with the system clipboard |
1030 | 1049 | ||
1031 | #+BEGIN_SRC emacs-lisp | 1050 | #+begin_src emacs-lisp |
1032 | (cuss save-interprogram-paste-before-kill t | 1051 | (cuss save-interprogram-paste-before-kill t |
1033 | "Save existing clipboard text into the kill ring before | 1052 | "Save existing clipboard text into the kill ring before |
1034 | replacing it.") | 1053 | replacing it.") |
1035 | 1054 | ||
1036 | (cuss yank-pop-change-selection t | 1055 | (cuss yank-pop-change-selection t |
1037 | "Update the X selection when rotating the kill ring.") | 1056 | "Update the X selection when rotating the kill ring.") |
1038 | #+END_SRC | 1057 | #+end_src |
1039 | 1058 | ||
1040 | **** Don’t append the same thing twice to the kill-ring | 1059 | **** Don’t append the same thing twice to the kill-ring |
1041 | 1060 | ||
1042 | #+BEGIN_SRC emacs-lisp | 1061 | #+begin_src emacs-lisp |
1043 | (cuss kill-do-not-save-duplicates t) | 1062 | (cuss kill-do-not-save-duplicates t) |
1044 | #+end_src | 1063 | #+end_src |
1045 | 1064 | ||
@@ -1047,33 +1066,33 @@ I’ve pretty much cribbed this from [[https://github.com/ncaq/recentf-remove-su | |||
1047 | 1066 | ||
1048 | **** COMMENT Search with CtrlF | 1067 | **** COMMENT Search with CtrlF |
1049 | 1068 | ||
1050 | For right now, I’m /just/ using Anzu – I don’t like parts of =isearch= but … CtrlF doesn’t match with that sweet replace flow. | 1069 | For right now, I’m /just/ using Anzu – I don’t like parts of =isearch= but … CtrlF doesn’t match with that sweet replace flow. |
1051 | 1070 | ||
1052 | #+begin_src emacs-lisp | 1071 | #+begin_src emacs-lisp |
1053 | (straight-use-package 'ctrlf) | 1072 | (straight-use-package 'ctrlf) |
1054 | (ctrlf-mode +1) | 1073 | (ctrlf-mode +1) |
1055 | #+end_src | 1074 | #+end_src |
1056 | 1075 | ||
1057 | **** Replace with Anzu | 1076 | **** Replace with Anzu |
1058 | 1077 | ||
1059 | #+begin_src emacs-lisp | 1078 | #+begin_src emacs-lisp |
1060 | (straight-use-package 'anzu) | 1079 | (straight-use-package 'anzu) |
1061 | (require 'anzu) | 1080 | (require 'anzu) |
1062 | 1081 | ||
1063 | ;; show search count in the modeline | 1082 | ;; show search count in the modeline |
1064 | (global-anzu-mode +1) | 1083 | (global-anzu-mode +1) |
1065 | 1084 | ||
1066 | (cuss anzu-replace-to-string-separator " → " | 1085 | (cuss anzu-replace-to-string-separator " → " |
1067 | "What to separate the search from the replacement.") | 1086 | "What to separate the search from the replacement.") |
1068 | 1087 | ||
1069 | (global-set-key [remap query-replace] #'anzu-query-replace) | 1088 | (global-set-key [remap query-replace] #'anzu-query-replace) |
1070 | (global-set-key [remap query-replace-regexp] #'anzu-query-replace-regexp) | 1089 | (global-set-key [remap query-replace-regexp] #'anzu-query-replace-regexp) |
1071 | 1090 | ||
1072 | (define-key isearch-mode-map [remap isearch-query-replace] #'anzu-isearch-query-replace) | 1091 | (define-key isearch-mode-map [remap isearch-query-replace] #'anzu-isearch-query-replace) |
1073 | (define-key isearch-mode-map [remap isearch-query-replace-regexp] #'anzu-isearch-query-replace-regexp) | 1092 | (define-key isearch-mode-map [remap isearch-query-replace-regexp] #'anzu-isearch-query-replace-regexp) |
1074 | 1093 | ||
1075 | 1094 | ||
1076 | #+end_src | 1095 | #+end_src |
1077 | 1096 | ||
1078 | *** Overwrite mode | 1097 | *** Overwrite mode |
1079 | 1098 | ||
@@ -1122,41 +1141,41 @@ For right now, I’m /just/ using Anzu – I don’t like parts of =isearch= but | |||
1122 | 1141 | ||
1123 | ** Prettify symbols | 1142 | ** Prettify symbols |
1124 | 1143 | ||
1125 | #+begin_src emacs-lisp | 1144 | #+begin_src emacs-lisp |
1126 | (cuss prettify-symbols-unprettify-at-point 'right-edge | 1145 | (cuss prettify-symbols-unprettify-at-point 'right-edge |
1127 | "Unprettify a symbol when inside it or next to it.") | 1146 | "Unprettify a symbol when inside it or next to it.") |
1128 | 1147 | ||
1129 | (add-hook 'prog-mode-hook #'prettify-symbols-mode) | 1148 | (add-hook 'prog-mode-hook #'prettify-symbols-mode) |
1130 | #+end_src | 1149 | #+end_src |
1131 | 1150 | ||
1132 | ** Parentheses | 1151 | ** Parentheses |
1133 | 1152 | ||
1134 | *** Smart parentheses | 1153 | *** Smart parentheses |
1135 | 1154 | ||
1136 | #+BEGIN_SRC emacs-lisp | 1155 | #+begin_src emacs-lisp |
1137 | (straight-use-package 'smartparens) | 1156 | (straight-use-package 'smartparens) |
1138 | (require 'smartparens-config) | 1157 | (require 'smartparens-config) |
1139 | 1158 | ||
1140 | ;; replace show-paren | 1159 | ;; replace show-paren |
1141 | 1160 | ||
1142 | (cuss sp-show-pair-delay 0 | 1161 | (cuss sp-show-pair-delay 0 |
1143 | "Don't delay before showing the pairs.") | 1162 | "Don't delay before showing the pairs.") |
1144 | (cuss sp-show-pair-from-inside t | 1163 | (cuss sp-show-pair-from-inside t |
1145 | "Highlight the enclosing pair when immediately inside.") | 1164 | "Highlight the enclosing pair when immediately inside.") |
1146 | 1165 | ||
1147 | (add-hook 'prog-mode-hook #'show-smartparens-mode +1) | 1166 | (add-hook 'prog-mode-hook #'show-smartparens-mode +1) |
1148 | 1167 | ||
1149 | ;; enable strict smartparens in prog mode | 1168 | ;; enable strict smartparens in prog mode |
1150 | (add-hook 'prog-mode-hook #'smartparens-strict-mode) | 1169 | (add-hook 'prog-mode-hook #'smartparens-strict-mode) |
1151 | #+END_SRC | 1170 | #+end_src |
1152 | 1171 | ||
1153 | ** Indent aggressively | 1172 | ** Indent aggressively |
1154 | 1173 | ||
1155 | #+BEGIN_SRC emacs-lisp | 1174 | #+begin_src emacs-lisp |
1156 | (straight-use-package 'aggressive-indent) | 1175 | (straight-use-package 'aggressive-indent) |
1157 | 1176 | ||
1158 | (global-aggressive-indent-mode +1) | 1177 | (global-aggressive-indent-mode +1) |
1159 | #+END_SRC | 1178 | #+end_src |
1160 | 1179 | ||
1161 | ** Completion | 1180 | ** Completion |
1162 | 1181 | ||
@@ -1198,27 +1217,29 @@ For right now, I’m /just/ using Anzu – I don’t like parts of =isearch= but | |||
1198 | 1217 | ||
1199 | *** Emacs lisp | 1218 | *** Emacs lisp |
1200 | 1219 | ||
1201 | #+BEGIN_SRC emacs-lisp | 1220 | #+begin_src emacs-lisp |
1202 | (cuss eval-expression-print-length nil | 1221 | (cuss eval-expression-print-length nil |
1203 | "Don't truncate printed expressions by length.") | 1222 | "Don't truncate printed expressions by length.") |
1204 | (cuss eval-expression-print-level nil | 1223 | (cuss eval-expression-print-level nil |
1205 | "Don't truncate printed expressions by level.") | 1224 | "Don't truncate printed expressions by level.") |
1206 | #+END_SRC | 1225 | #+end_src |
1207 | 1226 | ||
1208 | *** Janet | 1227 | *** Janet |
1209 | 1228 | ||
1210 | #+BEGIN_SRC emacs-lisp | 1229 | #+begin_src emacs-lisp |
1211 | (straight-use-package 'janet-mode) | 1230 | (straight-use-package 'janet-mode) |
1212 | (require 'janet-mode) | 1231 | (require 'janet-mode) |
1213 | 1232 | ||
1214 | (straight-use-package 'inf-janet-mode) | 1233 | (straight-use-package '(inf-janet |
1234 | :host github | ||
1235 | :repo "velkyel/inf-janet")) | ||
1215 | 1236 | ||
1216 | (add-hook 'janet-mode-hook #'inf-janet-minor-mode) | 1237 | (add-hook 'janet-mode-hook #'inf-janet-minor-mode) |
1217 | #+end_src | 1238 | #+end_src |
1218 | 1239 | ||
1219 | *** INI | 1240 | *** INI |
1220 | 1241 | ||
1221 | #+BEGIN_SRC emacs-lisp | 1242 | #+begin_src emacs-lisp |
1222 | (straight-use-package 'ini-mode) | 1243 | (straight-use-package 'ini-mode) |
1223 | 1244 | ||
1224 | (add-to-list 'auto-mode-alist | 1245 | (add-to-list 'auto-mode-alist |
@@ -1227,11 +1248,11 @@ For right now, I’m /just/ using Anzu – I don’t like parts of =isearch= but | |||
1227 | 1248 | ||
1228 | *** PHP | 1249 | *** PHP |
1229 | 1250 | ||
1230 | see also [[https://sasanidas.gitlab.io/f-site/php-development/][this post by Fermin M]], it looks really useful. | 1251 | see also [[https://sasanidas.gitlab.io/f-site/php-development/][this post by Fermin M]], it looks really useful. |
1231 | 1252 | ||
1232 | #+BEGIN_SRC emacs-lisp | 1253 | #+begin_src emacs-lisp |
1233 | (straight-use-package 'php-mode) | 1254 | (straight-use-package 'php-mode) |
1234 | #+end_src | 1255 | #+end_src |
1235 | 1256 | ||
1236 | * Writing | 1257 | * Writing |
1237 | 1258 | ||
@@ -1239,64 +1260,64 @@ see also [[https://sasanidas.gitlab.io/f-site/php-development/][this post by Fer | |||
1239 | 1260 | ||
1240 | *** Fix scrolling in margins | 1261 | *** Fix scrolling in margins |
1241 | 1262 | ||
1242 | This has to be done /before/ loading the package. It's included in =visual-fill-column=, too, but for some reason isn't loaded there. | 1263 | This has to be done /before/ loading the package. It's included in =visual-fill-column=, too, but for some reason isn't loaded there. |
1243 | |||
1244 | #+BEGIN_SRC emacs-lisp | ||
1245 | (dolist (margin '(right-margin left-margin)) | ||
1246 | (dolist (button '(mouse-1 mouse-2 mouse-3)) | ||
1247 | (global-set-key (vector margin button) | ||
1248 | (global-key-binding (vector button))))) | ||
1249 | 1264 | ||
1250 | (mouse-wheel-mode +1) | 1265 | #+begin_src emacs-lisp |
1251 | 1266 | (dolist (margin '(right-margin left-margin)) | |
1252 | (when (bound-and-true-p mouse-wheel-mode) | 1267 | (dolist (button '(mouse-1 mouse-2 mouse-3)) |
1253 | (dolist (margin '(right-margin left-margin)) | 1268 | (global-set-key (vector margin button) |
1254 | (dolist (event '(mouse-wheel-down-event | 1269 | (global-key-binding (vector button))))) |
1255 | mouse-wheel-up-event | 1270 | |
1256 | wheel-down | 1271 | (mouse-wheel-mode +1) |
1257 | wheel-up | 1272 | |
1258 | mouse-4 | 1273 | (when (bound-and-true-p mouse-wheel-mode) |
1259 | mouse-5)) | 1274 | (dolist (margin '(right-margin left-margin)) |
1260 | (global-set-key (vector margin event) #'mwheel-scroll)))) | 1275 | (dolist (event '(mouse-wheel-down-event |
1261 | #+END_SRC | 1276 | mouse-wheel-up-event |
1277 | wheel-down | ||
1278 | wheel-up | ||
1279 | mouse-4 | ||
1280 | mouse-5)) | ||
1281 | (global-set-key (vector margin event) #'mwheel-scroll)))) | ||
1282 | #+end_src | ||
1262 | 1283 | ||
1263 | *** Load the package | 1284 | *** Load the package |
1264 | 1285 | ||
1265 | #+BEGIN_SRC emacs-lisp | 1286 | #+begin_src emacs-lisp |
1266 | (straight-use-package 'visual-fill-column) | 1287 | (straight-use-package 'visual-fill-column) |
1267 | 1288 | ||
1268 | (cuss visual-fill-column-center-text nil | 1289 | (cuss visual-fill-column-center-text nil |
1269 | "Whether to center the text in the frame.") | 1290 | "Whether to center the text in the frame.") |
1270 | 1291 | ||
1271 | (cuss fill-column 84 | 1292 | (cuss fill-column 84 |
1272 | "Width of fill-column, and thus, visual-fill-column.") | 1293 | "Width of fill-column, and thus, visual-fill-column.") |
1273 | 1294 | ||
1274 | (advice-add 'text-scale-adjust | 1295 | (advice-add 'text-scale-adjust |
1275 | :after #'visual-fill-column-adjust) | 1296 | :after #'visual-fill-column-adjust) |
1276 | 1297 | ||
1277 | (global-visual-fill-column-mode +1) | 1298 | (global-visual-fill-column-mode +1) |
1278 | #+END_SRC | 1299 | #+end_src |
1279 | 1300 | ||
1280 | ** Typographical niceties | 1301 | ** Typographical niceties |
1281 | 1302 | ||
1282 | *** Variable pitch in text-modes | 1303 | *** Variable pitch in text-modes |
1283 | 1304 | ||
1284 | #+begin_src emacs-lisp | 1305 | #+begin_src emacs-lisp |
1285 | (add-hook 'text-mode-hook #'variable-pitch-mode) | 1306 | (add-hook 'text-mode-hook #'variable-pitch-mode) |
1286 | #+end_src | 1307 | #+end_src |
1287 | 1308 | ||
1288 | *** Typo mode | 1309 | *** Typo mode |
1289 | 1310 | ||
1290 | #+BEGIN_SRC emacs-lisp | 1311 | #+begin_src emacs-lisp |
1291 | (straight-use-package 'typo) | 1312 | (straight-use-package 'typo) |
1292 | 1313 | ||
1293 | (add-hook 'text-mode-hook #'typo-mode) | 1314 | (add-hook 'text-mode-hook #'typo-mode) |
1294 | 1315 | ||
1295 | ;; Disable `typo-mode' when inside an Org source block | 1316 | ;; Disable `typo-mode' when inside an Org source block |
1296 | (with-eval-after-load 'typo | 1317 | (with-eval-after-load 'typo |
1297 | (add-to-list 'typo-disable-electricity-functions | 1318 | (add-to-list 'typo-disable-electricity-functions |
1298 | #'org-in-src-block-p)) | 1319 | #'org-in-src-block-p)) |
1299 | #+END_SRC | 1320 | #+end_src |
1300 | 1321 | ||
1301 | *** Show =^L= as a horizontal line | 1322 | *** Show =^L= as a horizontal line |
1302 | 1323 | ||
@@ -1307,13 +1328,13 @@ This has to be done /before/ loading the package. It's included in =visual-fill | |||
1307 | 1328 | ||
1308 | ** Word count | 1329 | ** Word count |
1309 | 1330 | ||
1310 | #+BEGIN_SRC emacs-lisp | 1331 | #+begin_src emacs-lisp |
1311 | (straight-use-package 'wc-mode) | 1332 | (straight-use-package 'wc-mode) |
1312 | 1333 | ||
1313 | (add-hook 'text-mode-hook #'wc-mode) | 1334 | (add-hook 'text-mode-hook #'wc-mode) |
1314 | 1335 | ||
1315 | (rm/whitelist-add "WC") | 1336 | (rm/whitelist-add "WC") |
1316 | #+end_src | 1337 | #+end_src |
1317 | 1338 | ||
1318 | * Applications | 1339 | * Applications |
1319 | 1340 | ||
@@ -1321,7 +1342,7 @@ This has to be done /before/ loading the package. It's included in =visual-fill | |||
1321 | 1342 | ||
1322 | *** Basic customization | 1343 | *** Basic customization |
1323 | 1344 | ||
1324 | #+BEGIN_SRC emacs-lisp | 1345 | #+begin_src emacs-lisp |
1325 | ;; highlight the current line in dired. | 1346 | ;; highlight the current line in dired. |
1326 | (add-hook 'dired-mode-hook #'hl-line-mode) | 1347 | (add-hook 'dired-mode-hook #'hl-line-mode) |
1327 | 1348 | ||
@@ -1335,16 +1356,16 @@ This has to be done /before/ loading the package. It's included in =visual-fill | |||
1335 | *** Expand subtrees | 1356 | *** Expand subtrees |
1336 | 1357 | ||
1337 | 1358 | ||
1338 | #+BEGIN_SRC emacs-lisp | 1359 | #+begin_src emacs-lisp |
1339 | (straight-use-package 'dired-subtree) | 1360 | (straight-use-package 'dired-subtree) |
1340 | 1361 | ||
1341 | (with-eval-after-load 'dired | 1362 | (with-eval-after-load 'dired |
1342 | (define-key dired-mode-map "i" #'dired-subtree-toggle)) | 1363 | (define-key dired-mode-map "i" #'dired-subtree-toggle)) |
1343 | #+end_src | 1364 | #+end_src |
1344 | 1365 | ||
1345 | *** Collapse singleton directories | 1366 | *** Collapse singleton directories |
1346 | 1367 | ||
1347 | #+BEGIN_SRC emacs-lisp | 1368 | #+begin_src emacs-lisp |
1348 | (straight-use-package 'dired-collapse) | 1369 | (straight-use-package 'dired-collapse) |
1349 | 1370 | ||
1350 | (add-hook 'dired-mode-hook #'dired-collapse-mode) | 1371 | (add-hook 'dired-mode-hook #'dired-collapse-mode) |
@@ -1352,66 +1373,65 @@ This has to be done /before/ loading the package. It's included in =visual-fill | |||
1352 | 1373 | ||
1353 | *** Kill dired buffers | 1374 | *** Kill dired buffers |
1354 | 1375 | ||
1355 | from [[https://github.com/munen/emacs.d/][munen]]. | 1376 | from [[https://github.com/munen/emacs.d/][munen]]. |
1356 | 1377 | ||
1357 | #+BEGIN_SRC emacs-lisp | 1378 | #+begin_src emacs-lisp |
1358 | (defun kill-dired-buffers () | 1379 | (defun kill-dired-buffers () |
1359 | "Kill all open dired buffers." | 1380 | "Kill all open dired buffers." |
1360 | (interactive) | 1381 | (interactive) |
1361 | (mapc (lambda (buffer) | 1382 | (mapc (lambda (buffer) |
1362 | (when (eq 'dired-mode (buffer-local-value 'major-mode buffer)) | 1383 | (when (eq 'dired-mode (buffer-local-value 'major-mode buffer)) |
1363 | (kill-buffer buffer))) | 1384 | (kill-buffer buffer))) |
1364 | (buffer-list))) | 1385 | (buffer-list))) |
1365 | #+end_src | 1386 | #+end_src |
1366 | 1387 | ||
1367 | ** Org mode | 1388 | ** Org mode |
1368 | 1389 | ||
1369 | I’ve put org mode under Applications, as opposed to Writing, because it’s more generally-applicable than that. | 1390 | I’ve put org mode under Applications, as opposed to Writing, because it’s more generally-applicable than that. |
1370 | 1391 | ||
1371 | *** Basics | 1392 | *** Basics |
1372 | 1393 | ||
1373 | #+BEGIN_SRC emacs-lisp | 1394 | #+begin_src emacs-lisp |
1374 | (straight-use-package '(org | 1395 | (straight-use-package 'org) |
1375 | :repo "https://code.orgmode.org/bzg/org-mode.git")) | 1396 | |
1376 | 1397 | (with-eval-after-load 'org | |
1377 | (with-eval-after-load 'org | 1398 | (require 'org-tempo) |
1378 | (require 'org-tempo) | 1399 | (require 'ox-md) |
1379 | (require 'ox-md) | 1400 | (define-key org-mode-map (kbd "M-n") #'outline-next-visible-heading) |
1380 | (define-key org-mode-map (kbd "M-n") #'outline-next-visible-heading) | 1401 | (define-key org-mode-map (kbd "M-p") #'outline-previous-visible-heading)) |
1381 | (define-key org-mode-map (kbd "M-p") #'outline-previous-visible-heading)) | 1402 | |
1382 | 1403 | (cuss org-hide-emphasis-markers t) | |
1383 | (cuss org-hide-emphasis-markers t) | 1404 | (cuss org-fontify-done-headline t) |
1384 | (cuss org-fontify-done-headline t) | 1405 | (cuss org-fontify-whole-heading-line t) |
1385 | (cuss org-fontify-whole-heading-line t) | 1406 | (cuss org-fontify-quote-and-verse-blocks t) |
1386 | (cuss org-fontify-quote-and-verse-blocks t) | 1407 | (cuss org-pretty-entities t) |
1387 | (cuss org-pretty-entities t) | 1408 | (cuss org-src-tab-acts-natively t) |
1388 | (cuss org-src-tab-acts-natively t) | 1409 | (cuss org-src-fontify-natively t) |
1389 | (cuss org-src-fontify-natively t) | 1410 | (cuss org-src-window-setup 'current-window) |
1390 | (cuss org-src-window-setup 'current-window) | 1411 | (cuss org-confirm-babel-evaluate nil) |
1391 | (cuss org-confirm-babel-evaluate nil) | 1412 | (cuss org-directory "~/Org") |
1392 | (cuss org-directory "~/Org") | 1413 | (cuss org-ellipsis "…") |
1393 | (cuss org-ellipsis "…") | 1414 | (cuss org-catch-invisible-edits 'show) |
1394 | (cuss org-catch-invisible-edits 'show) | 1415 | (cuss org-special-ctrl-a/e t) |
1395 | (cuss org-special-ctrl-a/e t) | 1416 | (cuss org-special-ctrl-k t) |
1396 | (cuss org-special-ctrl-k t) | 1417 | |
1397 | 1418 | (cuss org-export-headline-levels 8 | |
1398 | (cuss org-export-headline-levels 8 | 1419 | "Maximum level of headlines to export /as/ a headline.") |
1399 | "Maximum level of headlines to export /as/ a headline.") | 1420 | #+end_src |
1400 | #+END_SRC | ||
1401 | 1421 | ||
1402 | **** Tags | 1422 | **** Tags |
1403 | 1423 | ||
1404 | #+begin_src emacs-lisp | 1424 | #+begin_src emacs-lisp |
1405 | (cuss org-tags-column 0 | 1425 | (cuss org-tags-column 0 |
1406 | "Show tags directly after the headline. | 1426 | "Show tags directly after the headline. |
1407 | This is the best-looking option with variable-pitch fonts.") | 1427 | This is the best-looking option with variable-pitch fonts.") |
1408 | 1428 | ||
1409 | (cussface | 1429 | (cussface |
1410 | '(org-tag | 1430 | '(org-tag |
1411 | ((t | 1431 | ((t |
1412 | (:height 0.8 :weight normal :slant italic :foreground "grey40" :inherit | 1432 | (:height 0.8 :weight normal :slant italic :foreground "grey40" :inherit |
1413 | (variable-pitch)))))) | 1433 | (variable-pitch)))))) |
1414 | #+end_src | 1434 | #+end_src |
1415 | 1435 | ||
1416 | **** Prettify | 1436 | **** Prettify |
1417 | 1437 | ||
@@ -1419,8 +1439,8 @@ I’ve put org mode under Applications, as opposed to Writing, because it’s m | |||
1419 | (defun acdw/org-mode-prettify () | 1439 | (defun acdw/org-mode-prettify () |
1420 | "Prettify `org-mode'." | 1440 | "Prettify `org-mode'." |
1421 | (dolist (cell '(("[ ]" . ?□) ("[X]" . ?☑) ("[-]" . ?◐) | 1441 | (dolist (cell '(("[ ]" . ?□) ("[X]" . ?☑) ("[-]" . ?◐) |
1422 | ("#+begin_src" . ?✎) ("#+BEGIN_SRC" . ?✎) | 1442 | ("#+begin_src" . ?✎) ("#+begin_src" . ?✎) |
1423 | ("#+end_src" . ?■) ("#+END_SRC" . ?■))) | 1443 | ("#+end_src" . ?■) ("#+end_src" . ?■))) |
1424 | (add-to-list 'prettify-symbols-alist cell :append)) | 1444 | (add-to-list 'prettify-symbols-alist cell :append)) |
1425 | (prettify-symbols-mode +1)) | 1445 | (prettify-symbols-mode +1)) |
1426 | 1446 | ||
@@ -1431,7 +1451,7 @@ I’ve put org mode under Applications, as opposed to Writing, because it’s m | |||
1431 | 1451 | ||
1432 | **** [[https://github.com/alphapapa/unpackaged.el#org-return-dwim][Org Return: DWIM]] | 1452 | **** [[https://github.com/alphapapa/unpackaged.el#org-return-dwim][Org Return: DWIM]] |
1433 | 1453 | ||
1434 | #+BEGIN_SRC emacs-lisp | 1454 | #+begin_src emacs-lisp |
1435 | (defun unpackaged/org-element-descendant-of (type element) | 1455 | (defun unpackaged/org-element-descendant-of (type element) |
1436 | "Return non-nil if ELEMENT is a descendant of TYPE. | 1456 | "Return non-nil if ELEMENT is a descendant of TYPE. |
1437 | TYPE should be an element type, like `item' or `paragraph'. | 1457 | TYPE should be an element type, like `item' or `paragraph'. |
@@ -1531,89 +1551,97 @@ I’ve put org mode under Applications, as opposed to Writing, because it’s m | |||
1531 | 1551 | ||
1532 | (with-eval-after-load 'org | 1552 | (with-eval-after-load 'org |
1533 | (define-key org-mode-map (kbd "RET") #'unpackaged/org-return-dwim)) | 1553 | (define-key org-mode-map (kbd "RET") #'unpackaged/org-return-dwim)) |
1534 | #+END_SRC | 1554 | #+end_src |
1535 | 1555 | ||
1536 | **** Insert blank lines around headers | 1556 | **** Insert blank lines around headers |
1537 | 1557 | ||
1538 | from [[https://github.com/alphapapa/unpackaged.el#ensure-blank-lines-between-headings-and-before-contents][unpackaged.el]]. | 1558 | from [[https://github.com/alphapapa/unpackaged.el#ensure-blank-lines-between-headings-and-before-contents][unpackaged.el]]. |
1539 | |||
1540 | #+BEGIN_SRC emacs-lisp | ||
1541 | ;;;###autoload | ||
1542 | (defun unpackaged/org-fix-blank-lines (&optional prefix) | ||
1543 | "Ensure that blank lines exist between headings and between headings and their contents. | ||
1544 | With prefix, operate on whole buffer. Ensures that blank lines | ||
1545 | exist after each headings's drawers." | ||
1546 | (interactive "P") | ||
1547 | (org-map-entries (lambda () | ||
1548 | (org-with-wide-buffer | ||
1549 | ;; `org-map-entries' narrows the buffer, which prevents us | ||
1550 | ;; from seeing newlines before the current heading, so we | ||
1551 | ;; do this part widened. | ||
1552 | (while (not (looking-back "\n\n" nil)) | ||
1553 | ;; Insert blank lines before heading. | ||
1554 | (insert "\n"))) | ||
1555 | (let ((end (org-entry-end-position))) | ||
1556 | ;; Insert blank lines before entry content | ||
1557 | (forward-line) | ||
1558 | (while (and (org-at-planning-p) | ||
1559 | (< (point) (point-max))) | ||
1560 | ;; Skip planning lines | ||
1561 | (forward-line)) | ||
1562 | (while (re-search-forward org-drawer-regexp end t) | ||
1563 | ;; Skip drawers. You might think that `org-at-drawer-p' | ||
1564 | ;; would suffice, but for some reason it doesn't work | ||
1565 | ;; correctly when operating on hidden text. This | ||
1566 | ;; works, taken from `org-agenda-get-some-entry-text'. | ||
1567 | (re-search-forward "^[ \t]*:END:.*\n?" end t) | ||
1568 | (goto-char (match-end 0))) | ||
1569 | (unless (or (= (point) (point-max)) | ||
1570 | (org-at-heading-p) | ||
1571 | (looking-at-p "\n")) | ||
1572 | (insert "\n")))) | ||
1573 | t (if prefix | ||
1574 | nil | ||
1575 | 'tree))) | ||
1576 | #+END_SRC | ||
1577 | 1559 | ||
1578 | ***** Add a before-save-hook | 1560 | #+begin_src emacs-lisp |
1561 | ;;;###autoload | ||
1562 | (defun unpackaged/org-fix-blank-lines (&optional prefix) | ||
1563 | "Ensure that blank lines exist between headings and between headings and their contents. | ||
1564 | With prefix, operate on whole buffer. Ensures that blank lines | ||
1565 | exist after each headings's drawers." | ||
1566 | (interactive "P") | ||
1567 | (org-map-entries (lambda () | ||
1568 | (org-with-wide-buffer | ||
1569 | ;; `org-map-entries' narrows the buffer, which prevents us | ||
1570 | ;; from seeing newlines before the current heading, so we | ||
1571 | ;; do this part widened. | ||
1572 | (while (not (looking-back "\n\n" nil)) | ||
1573 | ;; Insert blank lines before heading. | ||
1574 | (insert "\n"))) | ||
1575 | (let ((end (org-entry-end-position))) | ||
1576 | ;; Insert blank lines before entry content | ||
1577 | (forward-line) | ||
1578 | (while (and (org-at-planning-p) | ||
1579 | (< (point) (point-max))) | ||
1580 | ;; Skip planning lines | ||
1581 | (forward-line)) | ||
1582 | (while (re-search-forward org-drawer-regexp end t) | ||
1583 | ;; Skip drawers. You might think that `org-at-drawer-p' | ||
1584 | ;; would suffice, but for some reason it doesn't work | ||
1585 | ;; correctly when operating on hidden text. This | ||
1586 | ;; works, taken from `org-agenda-get-some-entry-text'. | ||
1587 | (re-search-forward "^[ \t]*:END:.*\n?" end t) | ||
1588 | (goto-char (match-end 0))) | ||
1589 | (unless (or (= (point) (point-max)) | ||
1590 | (org-at-heading-p) | ||
1591 | (looking-at-p "\n")) | ||
1592 | (insert "\n")))) | ||
1593 | t (if prefix | ||
1594 | nil | ||
1595 | 'tree))) | ||
1596 | #+end_src | ||
1579 | 1597 | ||
1580 | #+BEGIN_SRC emacs-lisp | 1598 | ***** Add a before-save-hook |
1581 | (defun cribbed/org-mode-fix-blank-lines () | ||
1582 | (when (eq major-mode 'org-mode) | ||
1583 | (let ((current-prefix-arg 4)) ; Emulate C-u | ||
1584 | (call-interactively 'unpackaged/org-fix-blank-lines)))) | ||
1585 | 1599 | ||
1586 | (add-hook 'before-save-hook #'cribbed/org-mode-fix-blank-lines) | 1600 | #+begin_src emacs-lisp |
1587 | #+END_SRC | 1601 | (defun cribbed/org-mode-fix-blank-lines () |
1602 | (when (eq major-mode 'org-mode) | ||
1603 | (let ((current-prefix-arg 4)) ; Emulate C-u | ||
1604 | (call-interactively 'unpackaged/org-fix-blank-lines)))) | ||
1588 | 1605 | ||
1589 | *** Org Agenda | 1606 | (add-hook 'before-save-hook #'cribbed/org-mode-fix-blank-lines) |
1607 | #+end_src | ||
1590 | 1608 | ||
1591 | #+BEGIN_SRC emacs-lisp | 1609 | *** Org Templates (=org-tempo=) |
1592 | (cuss org-agenda-files | ||
1593 | (let ((list)) | ||
1594 | (dolist (file '(;; add more files to this list | ||
1595 | "home.org" | ||
1596 | "work.org") | ||
1597 | list) | ||
1598 | (push (expand-file-name file org-directory) list)))) | ||
1599 | 1610 | ||
1600 | (define-key acdw/map (kbd "C-a") #'org-agenda) | 1611 | #+begin_src emacs-lisp |
1612 | (add-to-list 'org-structure-template-alist | ||
1613 | '("el" . "src emacs-lisp")) | ||
1614 | #+end_src | ||
1601 | 1615 | ||
1602 | (cuss org-todo-keywords | 1616 | *** Org Agenda |
1603 | '((sequence "RECUR(r)" "TODO(t)" "|" "DONE(d)") | ||
1604 | (sequence "|" "CANCELLED(c)"))) | ||
1605 | 1617 | ||
1606 | (cuss org-agenda-skip-scheduled-if-done t) | 1618 | #+begin_src emacs-lisp |
1607 | (cuss org-agenda-skip-deadline-if-done t) | 1619 | (cuss org-agenda-files |
1608 | (cuss org-deadline-warning-days 4 | 1620 | (let ((list)) |
1609 | "Warn of a deadline beginning four days before.") | 1621 | (dolist (file '(;; add more files to this list |
1610 | #+END_SRC | 1622 | "home.org" |
1623 | "work.org") | ||
1624 | list) | ||
1625 | (push (expand-file-name file org-directory) list)))) | ||
1626 | |||
1627 | (define-key acdw/map (kbd "C-a") #'org-agenda) | ||
1628 | |||
1629 | (cuss org-todo-keywords | ||
1630 | '((sequence "RECUR(r)" "TODO(t)" "|" "DONE(d)") | ||
1631 | (sequence "APPT(a)") | ||
1632 | (sequence "|" "CANCELLED(c)"))) | ||
1633 | |||
1634 | (cuss org-agenda-skip-scheduled-if-done t) | ||
1635 | (cuss org-agenda-skip-deadline-if-done t) | ||
1636 | (cuss org-deadline-warning-days 0 | ||
1637 | "Don't warn of an impending deadline.") | ||
1638 | #+end_src | ||
1611 | 1639 | ||
1612 | *** TODO Capture | 1640 | *** TODO Capture |
1613 | 1641 | ||
1614 | *** Include Org links in source code | 1642 | *** Include Org links in source code |
1615 | 1643 | ||
1616 | #+BEGIN_SRC emacs-lisp | 1644 | #+begin_src emacs-lisp |
1617 | (straight-use-package '(org-link-minor-mode | 1645 | (straight-use-package '(org-link-minor-mode |
1618 | :host github | 1646 | :host github |
1619 | :repo "seanohalpin/org-link-minor-mode")) | 1647 | :repo "seanohalpin/org-link-minor-mode")) |
@@ -1624,11 +1652,11 @@ I’ve put org mode under Applications, as opposed to Writing, because it’s m | |||
1624 | 1652 | ||
1625 | ** Git | 1653 | ** Git |
1626 | 1654 | ||
1627 | #+begin_src emacs-lisp | 1655 | #+begin_src emacs-lisp |
1628 | (straight-use-package 'magit) | 1656 | (straight-use-package 'magit) |
1629 | 1657 | ||
1630 | (define-key acdw/map "g" #'magit-status) | 1658 | (define-key acdw/map "g" #'magit-status) |
1631 | #+end_src | 1659 | #+end_src |
1632 | 1660 | ||
1633 | *** Git file modes | 1661 | *** Git file modes |
1634 | 1662 | ||
@@ -1642,24 +1670,24 @@ I’ve put org mode under Applications, as opposed to Writing, because it’s m | |||
1642 | 1670 | ||
1643 | ** Beancount mode | 1671 | ** Beancount mode |
1644 | 1672 | ||
1645 | #+begin_src emacs-lisp | 1673 | #+begin_src emacs-lisp |
1646 | (straight-use-package '(beancount-mode | 1674 | (straight-use-package '(beancount-mode |
1647 | :host github | 1675 | :host github |
1648 | :repo "beancount/beancount-mode")) | 1676 | :repo "beancount/beancount-mode")) |
1649 | (require 'beancount) | 1677 | (require 'beancount) |
1650 | 1678 | ||
1651 | (add-to-list 'auto-mode-alist '("\\.beancount\\'" . beancount-mode)) | 1679 | (add-to-list 'auto-mode-alist '("\\.beancount\\'" . beancount-mode)) |
1652 | 1680 | ||
1653 | (defun acdw/disable-aggressive-indent () | 1681 | (defun acdw/disable-aggressive-indent () |
1654 | "Turn `aggressive-indent-mode' off for a buffer." | 1682 | "Turn `aggressive-indent-mode' off for a buffer." |
1655 | (aggressive-indent-mode -1)) | 1683 | (aggressive-indent-mode -1)) |
1656 | 1684 | ||
1657 | (add-hook 'beancount-mode-hook #'outline-minor-mode) | 1685 | (add-hook 'beancount-mode-hook #'outline-minor-mode) |
1658 | (add-hook 'beancount-mode-hook #'acdw/disable-aggressive-indent) | 1686 | (add-hook 'beancount-mode-hook #'acdw/disable-aggressive-indent) |
1659 | 1687 | ||
1660 | (define-key beancount-mode-map (kbd "M-n") #'outline-next-visible-heading) | 1688 | (define-key beancount-mode-map (kbd "M-n") #'outline-next-visible-heading) |
1661 | (define-key beancount-mode-map (kbd "M-p") #'outline-previous-visible-heading) | 1689 | (define-key beancount-mode-map (kbd "M-p") #'outline-previous-visible-heading) |
1662 | #+end_src | 1690 | #+end_src |
1663 | 1691 | ||
1664 | *** Company integration with company-ledger | 1692 | *** Company integration with company-ledger |
1665 | 1693 | ||
@@ -1672,19 +1700,19 @@ I’ve put org mode under Applications, as opposed to Writing, because it’s m | |||
1672 | 1700 | ||
1673 | ** PDF Tools | 1701 | ** PDF Tools |
1674 | 1702 | ||
1675 | I’m only enabling this at home for now, since it requires building stuff. | 1703 | I’m only enabling this at home for now, since it requires building stuff. |
1676 | 1704 | ||
1677 | #+begin_src emacs-lisp | 1705 | #+begin_src emacs-lisp |
1678 | (defun acdw/disable-visual-fill-column-mode () | 1706 | (defun acdw/disable-visual-fill-column-mode () |
1679 | "Disable `visual-fill-column-mode'." | 1707 | "Disable `visual-fill-column-mode'." |
1680 | (visual-fill-column-mode -1)) | 1708 | (visual-fill-column-mode -1)) |
1681 | 1709 | ||
1682 | (at-home | 1710 | (at-home |
1683 | (straight-use-package 'pdf-tools) | 1711 | (straight-use-package 'pdf-tools) |
1684 | (pdf-loader-install) | 1712 | (pdf-loader-install) |
1685 | 1713 | ||
1686 | (add-hook 'pdf-view-mode-hook #'acdw/disable-visual-fill-column-mode)) | 1714 | (add-hook 'pdf-view-mode-hook #'acdw/disable-visual-fill-column-mode)) |
1687 | #+end_src | 1715 | #+end_src |
1688 | 1716 | ||
1689 | ** E-book tools | 1717 | ** E-book tools |
1690 | 1718 | ||
@@ -1824,42 +1852,42 @@ I’m only enabling this at home for now, since it requires building stuff. | |||
1824 | 1852 | ||
1825 | *** Elpher | 1853 | *** Elpher |
1826 | 1854 | ||
1827 | #+begin_src emacs-lisp | 1855 | #+begin_src emacs-lisp |
1828 | (straight-use-package '(elpher | 1856 | (straight-use-package '(elpher |
1829 | :repo "git://thelambdalab.xyz/elpher.git")) | 1857 | :repo "git://thelambdalab.xyz/elpher.git")) |
1830 | 1858 | ||
1831 | (with-eval-after-load 'no-littering | 1859 | (with-eval-after-load 'no-littering |
1832 | (cuss elpher-certificate-directory | 1860 | (cuss elpher-certificate-directory |
1833 | (no-littering-expand-var-file-name "elpher-certificates/"))) | 1861 | (no-littering-expand-var-file-name "elpher-certificates/"))) |
1834 | 1862 | ||
1835 | (cuss elpher-ipv4-always t) | 1863 | (cuss elpher-ipv4-always t) |
1836 | 1864 | ||
1837 | (cussface '(elpher-gemini-heading1 | 1865 | (cussface '(elpher-gemini-heading1 |
1838 | ((t (:inherit (modus-theme-heading-1 variable-pitch)))))) | 1866 | ((t (:inherit (modus-theme-heading-1 variable-pitch)))))) |
1839 | (cussface '(elpher-gemini-heading2 | 1867 | (cussface '(elpher-gemini-heading2 |
1840 | ((t (:inherit (modus-theme-heading-2 variable-pitch)))))) | 1868 | ((t (:inherit (modus-theme-heading-2 variable-pitch)))))) |
1841 | (cussface '(elpher-gemini-heading3 | 1869 | (cussface '(elpher-gemini-heading3 |
1842 | ((t (:inherit (modus-theme-heading-3 variable-pitch)))))) | 1870 | ((t (:inherit (modus-theme-heading-3 variable-pitch)))))) |
1843 | 1871 | ||
1844 | (defun elpher:eww-browse-url (original url &optional new-window) | 1872 | (defun elpher:eww-browse-url (original url &optional new-window) |
1845 | "Handle gemini/gopher links with eww." | 1873 | "Handle gemini/gopher links with eww." |
1846 | (cond ((string-match-p "\\`\\(gemini\\|gopher\\)://" url) | 1874 | (cond ((string-match-p "\\`\\(gemini\\|gopher\\)://" url) |
1847 | (require 'elpher) | 1875 | (require 'elpher) |
1848 | (elpher-go url)) | 1876 | (elpher-go url)) |
1849 | (t (funcall original url new-window)))) | 1877 | (t (funcall original url new-window)))) |
1850 | (advice-add 'eww-browse-url :around 'elpher:eww-browse-url) | 1878 | (advice-add 'eww-browse-url :around 'elpher:eww-browse-url) |
1851 | 1879 | ||
1852 | (with-eval-after-load 'elpher | 1880 | (with-eval-after-load 'elpher |
1853 | (define-key elpher-mode-map "n" #'elpher-next-link) | 1881 | (define-key elpher-mode-map "n" #'elpher-next-link) |
1854 | (define-key elpher-mode-map "p" #'elpher-prev-link) | 1882 | (define-key elpher-mode-map "p" #'elpher-prev-link) |
1855 | (define-key elpher-mode-map "o" #'elpher-follow-current-link) | 1883 | (define-key elpher-mode-map "o" #'elpher-follow-current-link) |
1856 | (define-key elpher-mode-map "G" #'elpher-go-current)) | 1884 | (define-key elpher-mode-map "G" #'elpher-go-current)) |
1857 | 1885 | ||
1858 | (add-hook 'elpher-mode-hook #'acdw/setup-smolweb) | 1886 | (add-hook 'elpher-mode-hook #'acdw/setup-smolweb) |
1859 | 1887 | ||
1860 | (autoload 'elpher-bookmarks "elpher") | 1888 | (autoload 'elpher-bookmarks "elpher") |
1861 | (define-key acdw/map "e" #'elpher-bookmarks) | 1889 | (define-key acdw/map "e" #'elpher-bookmarks) |
1862 | #+end_src | 1890 | #+end_src |
1863 | 1891 | ||
1864 | *** Gemini-mode | 1892 | *** Gemini-mode |
1865 | 1893 | ||
@@ -1936,163 +1964,179 @@ I’m only enabling this at home for now, since it requires building stuff. | |||
1936 | 1964 | ||
1937 | #+begin_src emacs-lisp | 1965 | #+begin_src emacs-lisp |
1938 | (at-home | 1966 | (at-home |
1939 | (straight-use-package 'exec-path-from-shell) | 1967 | (straight-use-package 'exec-path-from-shell) |
1940 | (defvar acdw/exec-path-from-shell-initialized nil | 1968 | (defvar acdw/exec-path-from-shell-initialized nil |
1941 | "Stores whether we've initialized or not.") | 1969 | "Stores whether we've initialized or not.") |
1942 | (unless acdw/exec-path-from-shell-initialized | 1970 | (unless acdw/exec-path-from-shell-initialized |
1943 | (exec-path-from-shell-initialize) | 1971 | (exec-path-from-shell-initialize) |
1944 | (setq acdw/exec-path-from-shell-initialized (current-time)))) | 1972 | (setq acdw/exec-path-from-shell-initialized (current-time)))) |
1945 | #+end_src | 1973 | #+end_src |
1946 | 1974 | ||
1947 | * Appendices | 1975 | * Appendices |
1976 | :PROPERTIES: | ||
1977 | :header-args: :tangle LICENSE :comments no | ||
1978 | :END: | ||
1948 | 1979 | ||
1949 | ** Emacs' files | 1980 | ** Emacs' files |
1950 | 1981 | ||
1951 | *** init.el | 1982 | *** init.el |
1952 | 1983 | ||
1953 | #+BEGIN_SRC emacs-lisp :tangle init.el :comments no | 1984 | #+begin_src emacs-lisp :tangle init.el |
1954 | ;; init.el -*- lexical-binding: t -*- | 1985 | ;; init.el -*- lexical-binding: t -*- |
1955 | 1986 | ||
1956 | (setq load-prefer-newer t) | 1987 | (setq load-prefer-newer t) |
1957 | 1988 | ||
1958 | (let* (;; Speed up init | 1989 | (let* (;; Speed up init |
1959 | (gc-cons-threshold most-positive-fixnum) | 1990 | (gc-cons-threshold most-positive-fixnum) |
1960 | (file-name-handler-alist nil) | 1991 | (file-name-handler-alist nil) |
1961 | ;; Config file names | 1992 | ;; Config file names |
1962 | (conf (expand-file-name "config" | 1993 | (conf (expand-file-name "config" |
1963 | user-emacs-directory)) | 1994 | user-emacs-directory)) |
1964 | (conf-el (concat conf ".el")) | 1995 | (conf-el (concat conf ".el")) |
1965 | (conf-org (concat conf ".org"))) | 1996 | (conf-org (concat conf ".org"))) |
1966 | (unless (and (file-newer-than-file-p conf-el conf-org) | 1997 | (unless (and (file-newer-than-file-p conf-el conf-org) |
1967 | (load conf 'no-error)) | 1998 | (load conf 'no-error)) |
1968 | ;; A plain require here just loads the older `org' | 1999 | ;; A plain require here just loads the older `org' |
1969 | ;; in Emacs' install dir. We need to add the newer | 2000 | ;; in Emacs' install dir. We need to add the newer |
1970 | ;; one to the `load-path', hopefully that's all. | 2001 | ;; one to the `load-path', hopefully that's all. |
1971 | (add-to-list 'load-path (expand-file-name "straight/build/org" | 2002 | (add-to-list 'load-path (expand-file-name "straight/build/org" |
1972 | user-emacs-directory)) | 2003 | user-emacs-directory)) |
1973 | (require 'org) | 2004 | (require 'org) |
1974 | (org-babel-load-file conf-org))) | 2005 | (org-babel-load-file conf-org))) |
1975 | #+END_SRC | 2006 | #+end_src |
1976 | 2007 | ||
1977 | *** early-init.el | 2008 | *** early-init.el |
1978 | 2009 | ||
1979 | #+BEGIN_SRC emacs-lisp :tangle early-init.el :comments no | 2010 | #+begin_src emacs-lisp :tangle early-init.el |
1980 | ;; early-init.el -*- no-byte-compile: t; -*- | 2011 | ;; early-init.el -*- no-byte-compile: t; -*- |
1981 | 2012 | ||
1982 | ;; I use `straight.el' instead of `package.el'. | 2013 | ;; I use `straight.el' instead of `package.el'. |
1983 | (setq package-enable-at-startup nil) | 2014 | (setq package-enable-at-startup nil) |
1984 | 2015 | ||
1985 | ;; Don't resize the frame when loading fonts | 2016 | ;; Don't resize the frame when loading fonts |
1986 | (setq frame-inhibit-implied-resize t) | 2017 | (setq frame-inhibit-implied-resize t) |
1987 | ;; Resize frame by pixels | 2018 | ;; Resize frame by pixels |
1988 | (setq frame-resize-pixelwise t) | 2019 | (setq frame-resize-pixelwise t) |
1989 | #+end_src | 2020 | #+end_src |
1990 | 2021 | ||
1991 | ** Ease tangling and loading of Emacs' init | 2022 | ** Ease tangling and loading of Emacs' init |
1992 | 2023 | ||
1993 | #+BEGIN_SRC emacs-lisp | 2024 | #+begin_src emacs-lisp :tangle config.el |
1994 | (defun refresh-emacs (&optional disable-load) | 2025 | (defun refresh-emacs (&optional disable-load) |
1995 | "Tangle `config.org', then byte-compile the resulting files. | 2026 | "Tangle `config.org', then byte-compile the resulting files. |
1996 | Then, load the byte-compilations unless passed with a prefix argument." | 2027 | Then, load the byte-compilations unless passed with a prefix argument." |
1997 | (interactive "P") | 2028 | (interactive "P") |
1998 | (let ((config (expand-file-name "config.org" user-emacs-directory))) | 2029 | (let ((config (expand-file-name "config.org" user-emacs-directory))) |
1999 | (save-mark-and-excursion | 2030 | (save-mark-and-excursion |
2000 | (with-current-buffer (find-file config) | 2031 | (with-current-buffer (find-file config) |
2001 | (let ((prog-mode-hook nil)) | 2032 | (let ((prog-mode-hook nil)) |
2002 | ;; generate the readme | 2033 | ;; generate the readme |
2003 | (when (file-newer-than-file-p config (expand-file-name | 2034 | (when (file-newer-than-file-p config (expand-file-name |
2004 | "README.md" | 2035 | "README.md" |
2005 | user-emacs-directory)) | 2036 | user-emacs-directory)) |
2006 | (message "%s" "Exporting README.md...") | 2037 | (message "%s" "Exporting README.md...") |
2007 | (require 'ox-md) | 2038 | (require 'ox-md) |
2008 | (with-demoted-errors "Problem exporting README.md: %S" | 2039 | (with-demoted-errors "Problem exporting README.md: %S" |
2009 | (org-md-export-to-markdown))) | 2040 | (org-md-export-to-markdown))) |
2010 | ;; tangle config.org | 2041 | ;; tangle config.org |
2011 | (when (file-newer-than-file-p config (expand-file-name | 2042 | (when (file-newer-than-file-p config (expand-file-name |
2012 | "config.el" | 2043 | "config.el" |
2013 | user-emacs-directory)) | 2044 | user-emacs-directory)) |
2014 | (message "%s" "Tangling config.org...") | 2045 | (message "%s" "Tangling config.org...") |
2015 | (add-to-list 'load-path (expand-file-name "straight/build/org/" | 2046 | (add-to-list 'load-path (expand-file-name "straight/build/org/" |
2016 | user-emacs-directory)) | 2047 | user-emacs-directory)) |
2017 | (require 'org) | 2048 | (require 'org) |
2018 | (let ((inits (org-babel-tangle))) | 2049 | (let ((inits (org-babel-tangle))) |
2019 | ;; byte-compile resulting files | 2050 | ;; byte-compile resulting files |
2020 | (message "%s" "Byte-compiling...") | 2051 | (message "%s" "Byte-compiling...") |
2021 | (dolist (f inits) | 2052 | (dolist (f inits) |
2022 | (when (string-match "\\.el\\'" f) | 2053 | (when (string-match "\\.el\\'" f) |
2023 | (byte-compile-file f (not disable-load))))))))))) | 2054 | (byte-compile-file f (not disable-load))))))))))) |
2024 | #+END_SRC | 2055 | #+end_src |
2025 | 2056 | ||
2026 | ** Ancillary scripts | 2057 | ** Ancillary scripts |
2027 | 2058 | ||
2028 | *** emacsdc | 2059 | *** emacsdc |
2029 | :PROPERTY: | 2060 | :PROPERTIES: |
2030 | :header-args: :tangle bin/emacsdc :tangle-mode (identity #o755) | 2061 | :header-args: :mkdirp yes :tangle-mode (identity #o755) |
2031 | :END: | 2062 | :END: |
2032 | 2063 | ||
2033 | Here's a wrapper script that'll start =emacs --daemon= if there isn't | 2064 | Here's a wrapper script that'll start =emacs --daemon= if there isn't |
2034 | one, and then launch =emacsclient= with the arguments. I'd recommend | 2065 | one, and then launch =emacsclient= with the arguments. I'd recommend |
2035 | installing with either ~ln -s bin/emacsdc $HOME/.local/bin/~, or | 2066 | installing with either ~ln -s bin/emacsdc $HOME/.local/bin/~, or |
2036 | adding =$HOME/.local/bin= to your =$PATH=. | 2067 | adding =$HOME/.local/bin= to your =$PATH=. |
2037 | 2068 | ||
2038 | #+BEGIN_SRC sh :shebang "#!/bin/sh" | 2069 | #+begin_src sh :tangle bin/emacsdc :shebang "#!/bin/sh" |
2039 | if ! emacsclient -nc "$@" 2>/dev/null; then | 2070 | if ! emacsclient -nc "$@" 2>/dev/null; then |
2040 | emacs --daemon | 2071 | emacs --daemon |
2041 | emacsclient -nc "$@" | 2072 | emacsclient -nc "$@" |
2042 | fi | 2073 | fi |
2043 | #+END_SRC | 2074 | #+end_src |
2044 | 2075 | ||
2045 | *** Emacs.cmd | 2076 | *** Emacs.cmd |
2046 | 2077 | :PROPERTIES: | |
2047 | Here's a wrapper script that'll run Emacs on Windows, with a custom =$HOME=. I have | 2078 | :header-args: :mkdirp yes |
2048 | mine setup like this: Emacs is downloaded from [[https://mirrors.tripadvisor.com/gnu/emacs/windows/emacs-27/emacs-27.1-x86_64.zip][the GNU mirror]] and unzipped to | 2079 | :END: |
2049 | =~/Downloads/emacs/=. For some reason, Emacs by default sets =$HOME= to =%APPDATA%=, | 2080 | |
2050 | which doesn’t make a lot of sense to me. I change it to =%USERPROFILE%=, and then run | 2081 | Here's a wrapper script that'll run Emacs on Windows, with a |
2051 | Emacs with the supplied arguments. | 2082 | custom =$HOME=. I have mine setup like this: Emacs is downloaded |
2052 | 2083 | from [[https://mirrors.tripadvisor.com/gnu/emacs/windows/emacs-27/emacs-27.1-x86_64.zip][the GNU mirror]] and unzipped to =~/Downloads/emacs/=. For | |
2053 | #+begin_src bat :tangle bin/Emacs.cmd | 2084 | some reason, Emacs by default sets =$HOME= to =%APPDATA%=, which |
2054 | set HOME=%USERPROFILE% | 2085 | doesn’t make a lot of sense to me. I change it to |
2055 | set EMACS="%USERPROFILE%\Downloads\emacs\bin\runemacs.exe" | 2086 | =%USERPROFILE%\Downloads\home=, and then run Emacs with the |
2056 | 2087 | supplied arguments. | |
2057 | REM Run "Quick Mode" | 2088 | |
2058 | REM "%EMACS%" -Q %* | 2089 | As far as creating a shortcut to the Desktop, you’ll have to do |
2059 | 2090 | that yourself – /apparently/ Windows doesn’t have a built-in | |
2060 | REM Regular | 2091 | shortcut-creating software >:(. |
2061 | "%EMACS%" %* | 2092 | |
2062 | #+end_src | 2093 | #+begin_src bat :tangle bin/Emacs.cmd |
2094 | REM Set variables | ||
2095 | set HOME=%USERPROFILE%\Downloads\home | ||
2096 | set EMACS=%USERPROFILE%\Downloads\emacs\bin\runemacs.exe | ||
2097 | |||
2098 | REM Change the directory | ||
2099 | chdir %HOME% | ||
2100 | |||
2101 | REM Run "Quick Mode" | ||
2102 | REM "%EMACS%" -Q %* | ||
2103 | |||
2104 | REM Regular | ||
2105 | "%EMACS%" %* | ||
2106 | #+end_src | ||
2063 | 2107 | ||
2064 | ** License | 2108 | ** License |
2065 | :PROPERTIES: | 2109 | :PROPERTIES: |
2066 | :header-args: :tangle LICENSE :comments no | 2110 | :header-args: :tangle LICENSE :comments no |
2067 | :END: | 2111 | :END: |
2068 | 2112 | ||
2069 | Copyright © 2020 Case Duckworth <acdw@acdw.net> | 2113 | Copyright © 2020 Case Duckworth <acdw@acdw.net> |
2070 | 2114 | ||
2071 | This work is free. You can redistribute it and/or modify it under the | 2115 | This work is free. You can redistribute it and/or modify it under the |
2072 | terms of the Do What the Fuck You Want To Public License, Version 2, | 2116 | terms of the Do What the Fuck You Want To Public License, Version 2, |
2073 | as published by Sam Hocevar. See the =LICENSE= file, tangled from the | 2117 | as published by Sam Hocevar. See the =LICENSE= file, tangled from the |
2074 | following source block, for details. | 2118 | following source block, for details. |
2075 | 2119 | ||
2076 | #+BEGIN_SRC text | 2120 | #+begin_src text |
2077 | DO WHAT THE FUCK YOU WANT TO PUBLIC LICENSE | 2121 | DO WHAT THE FUCK YOU WANT TO PUBLIC LICENSE |
2078 | 2122 | ||
2079 | Version 2, December 2004 | 2123 | Version 2, December 2004 |
2080 | 2124 | ||
2081 | Copyright (C) 2004 Sam Hocevar <sam@hocevar.net> | 2125 | Copyright (C) 2004 Sam Hocevar <sam@hocevar.net> |
2082 | 2126 | ||
2083 | Everyone is permitted to copy and distribute verbatim or modified copies of | 2127 | Everyone is permitted to copy and distribute verbatim or modified copies of |
2084 | this license document, and changing it is allowed as long as the name is changed. | 2128 | this license document, and changing it is allowed as long as the name is changed. |
2085 | 2129 | ||
2086 | DO WHAT THE FUCK YOU WANT TO PUBLIC LICENSE | 2130 | DO WHAT THE FUCK YOU WANT TO PUBLIC LICENSE |
2087 | 2131 | ||
2088 | TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION | 2132 | TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION |
2089 | 2133 | ||
2090 | 0. You just DO WHAT THE FUCK YOU WANT TO. | 2134 | 0. You just DO WHAT THE FUCK YOU WANT TO. |
2091 | #+END_SRC | 2135 | #+end_src |
2092 | 2136 | ||
2093 | *** Note on the license | 2137 | *** Note on the license |
2094 | 2138 | ||
2095 | It's highly likely that the WTFPL is completely incompatible with the | 2139 | It's highly likely that the WTFPL is completely incompatible with the |
2096 | GPL, for what should be fairly obvious reasons. To that, I say: | 2140 | GPL, for what should be fairly obvious reasons. To that, I say: |
2097 | 2141 | ||
2098 | *SUE ME, RMS!* | 2142 | *SUE ME, RMS!* |