97 KiB
Flinner's Config
- README:
- Performance
- Packaging
- Basic Configuration
- Auth!
- Help
- Keybinds
- Completions
- Org-Mode
- Development
- Misc
- Elfeed org
- IRC
- Email (mu4e)
- Telega
- COMMENT Matrix Ement
- Buffers and Windows
- Startpage
README:
After the first run that installs things, run the following
; code-block not tangled
(all-the-icons-install-fonts)
(fira-code-mode-set-font)
Performance
;;lsp performance improvement
(setq gc-cons-threshold-original gc-cons-threshold)
(setq gc-cons-threshold (* 1024 1024 100))
(setq read-process-output-max (* 1024 4024))
Packaging
Initialize Package sources
(require 'package)
(setq package-archives '(("melpa" . "https://melpa.org/packages/")
("org" . "https://orgmode.org/elpa/")
("elpa" . "https://elpa.gnu.org/packages/")))
(package-initialize)
(unless package-archive-contents
(package-refresh-contents))
;; Initialize use-package on non-Linux platforms
(unless (package-installed-p 'use-package)
(package-install 'use-package))
Make sure to download packages if not present
(require 'use-package)
(setq package-native-compile t)
(setq use-package-always-ensure t)
straight
(defvar bootstrap-version)
(let ((bootstrap-file
(expand-file-name "straight/repos/straight.el/bootstrap.el" user-emacs-directory))
(bootstrap-version 5))
(unless (file-exists-p bootstrap-file)
(with-current-buffer
(url-retrieve-synchronously
"https://raw.githubusercontent.com/raxod502/straight.el/develop/install.el"
'silent 'inhibit-cookies)
(goto-char (point-max))
(eval-print-last-sexp)))
(load bootstrap-file nil 'nomessage))
(straight-use-package 'use-package)
(setq straight-use-package-by-default t)
remove warning by use-package
(custom-set-variables '(warning-suppress-types '((use-package))))
Basic Configuration
Better Defaults
(setq inhibit-startup-message t)
(scroll-bar-mode -1) ; Disable visible scrollbar
(tool-bar-mode -1) ; Disable the toolbar
(tooltip-mode -1) ; Disable tooltips
(set-fringe-mode 10) ; Give some breathing room
(menu-bar-mode -1) ; Disable the menu bar
(winner-mode 1) ; Disable the menu bar
(setq visible-bell nil) ; Set up the visible bell
(column-number-mode) ; Display Column Number in the modline
(setq use-dialog-box nil) ; I don't like to confirm anything with a mouse!
(defalias 'yes-or-no-p 'y-or-n-p) ; I don't want to type 'yes' everytime!, 'y' is enough
;(setq native-comp-deferred-compilation t); emacs 30+ i guess
(setq comp-deferred-compilation-deny-list '()) ;; turn off bytecompiler warnings
(setq native-comp-async-report-warnings-errors nil)
Emacs Backups trashing local dir!
(use-package no-littering)
(setq auto-save-file-name-transforms
`((".*" ,(no-littering-expand-var-file-name "auto-save/") t)))
(setq backup-directory-alist `((".*" . "~/.local/share/emacs-backups")))
(setq make-backup-files t ; backup of a file the first time it is saved.
backup-by-copying t ; don't clobber symlinks
version-control t ; version numbers for backup files
vc-make-backup-files t ; version control for git/vcs dirs
delete-old-versions t ; delete excess backup files silently
delete-by-moving-to-trash t
kept-old-versions 6 ; oldest versions to keep when a new numbered backup is made
kept-new-versions 9 ; newest versions to keep when a new numbered backup is made
auto-save-default t ; auto-save every buffer that visits a file
auto-save-timeout 20 ; number of seconds idle time before auto-save (default: 30)
auto-save-interval 200 ; number of keystrokes between auto-saves (default: 300)
create-lockfiles nil ; don't use lockfiles (default: t)
)
Better Scrolling
(setq scroll-conservatively 10)
(setq scroll-margin 3)
;; (use-package smooth-scrolling
;; :custom (smooth-scrolling-mode 1))
Fonts
Setting fonts here as vars to stay sane
(setq my/ui/monofont "FiraCode Nerd Font")
(setq my/ui/varfont "Noto Serif")
(setq my/ui/arabicfont "Noto Sans Arabic")
(set-face-attribute 'default nil :font my/ui/monofont :height 90)
(set-face-attribute 'fixed-pitch nil :font my/ui/monofont :height 90)
(set-face-attribute 'variable-pitch nil :font my/ui/varfont :height 90)
;; Info has a horrible mono font
(set-face-attribute 'Info-quoted nil :font my/ui/monofont :height 90)
emacs-client frames don't adhire to the font for some reason, need to run this hook:
(defun my/ui/font-check ()
"Do font check, then remove self from `focus-in-hook'; need to run this just once."
(set-face-attribute 'default nil :font my/ui/monofont :height 90)
(set-face-attribute 'fixed-pitch nil :font my/ui/monofont :height 90)
(set-face-attribute 'variable-pitch nil :font my/ui/varfont :height 90)
;; Info has a horrible mono font
(set-face-attribute 'Info-quoted nil :font my/ui/monofont :height 90)
;; Arabic
(when window-system (set-fontset-font "fontset-default" '(#x600 . #x6ff) my/ui/arabicfont))
(remove-hook 'focus-in-hook #'my/ui/font-check))
(add-hook 'focus-in-hook #'my/ui/font-check)
Arabic fonts :)
(when window-system (set-fontset-font "fontset-default" '(#x600 . #x6ff) my/ui/arabicfont))
Theme
Run M-x
all-the-icons-install-fonts for the first time!
(use-package all-the-icons)
The status line
(use-package doom-modeline
:ensure t
:init (doom-modeline-mode 1)
:config
(display-battery-mode 1)
:custom
((doom-modeline-height 15) (doom-modeline-icon t)))
buffers with dimmed colors
(use-package solaire-mode
:init (solaire-global-mode +1))
Actuall Theme:
(use-package doom-themes
:config
;; Global settings (defaults)
(setq doom-themes-enable-bold t ; if nil, bold is universally disabled
doom-themes-enable-italic t) ; if nil, italics is universally disabled
(load-theme 'doom-gruvbox t)
;; (load-theme 'doom-one-light t)
(custom-set-faces
;; custom-set-faces was added by Custom.
;; If you edit it by hand, you could mess it up, so be careful.
;; Your init file should contain only one such instance.
;; If there is more than one, they won't work right.
;; '(flycheck-warning ((t (:background "#282828" :underline "#fabd2f"))))
'(org-date ((t (:inherit fixed-pitch))))
;; '(ivy-posframe-border ((t (:background "#ffffff")))))
)
;; Enable custom neotree theme (all-the-icons must be installed!)
(doom-themes-neotree-config)
;; or for treemacs users
(setq doom-themes-treemacs-theme "doom-atom") ; use "doom-colors" for less minimal icon theme
(doom-themes-treemacs-config)
;; Corrects (and improves) org-mode's native fontification.
(doom-themes-org-config))
Transparency!
;; for the first frame
(set-frame-parameter nil 'alpha-background 0.9)
;; for other frames
(add-hook 'server-after-make-frame-hook
(lambda nil (set-frame-parameter nil 'alpha-background 0.9)))
Center text in the frame, looks nice ;)
(use-package olivetti
:diminish
:hook (text-mode . olivetti-mode)
:hook (prog-mode . olivetti-mode)
:hook (Info-mode . olivetti-mode)
:config
(setq-default olivetti-body-width 120))
Line Numbers
I don't use line numbers anymore, chad.png
DEPRECATED Enable Globally
; this block has ":tangle no"
(global-display-line-numbers-mode 0)
DEPRECATED Disable for the following modes
(defun disable-line-numbers () "Disables line number" (interactive) (display-line-numbers-mode 0))
(dolist (mode '(org-mode-hook
term-mode-hook
treemacs-mode-hook
cargo-test-mode-hook
shell-mode-hook
eshell-mode-hook))
(add-hook mode #'disable-line-numbers))
ONLY IN PROG!
;; (add-hook 'prog-mode-hook 'display-line-numbers-mode)
Undo
Self explanatory
(use-package undo-fu)
Org roam warning
(setq org-roam-v2-ack t) ; anonying startup message
Tab Width
8 Spaces for a single tab is too much
(setq-default tab-width 4)
Spaces > Tabs
(setq-default indent-tabs-mode nil)
Auth!
should i really be commiting this? :>
auth sources
(setq auth-sources '("~/.authinfo.gpg"
"secrets:local"; keepassxc db
"~/.authinfo"
"~/.netrc"))
(require 'epa-file)
(epa-file-enable)
Help
helpful-key
and describe-function
(use-package helpful
:commands (helpful-callable helpful-variable helpful-command helpful-key)
:custom
(counsel-describe-function-function #'helpful-callable)
(counsel-describe-variable-function #'helpful-variable)
:bind
([remap describe-function] . counsel-describe-function)
([remap describe-command] . helpful-command)
([remap describe-variable] . counsel-describe-variable)
([remap describe-key] . helpful-key))
Keybinds
Single Esc to Quit, instead of three
(global-set-key (kbd "<escape>") 'keyboard-escape-quit)
Function keys
(global-set-key (kbd "M-<f8>") '(lambda () (interactive) (org-agenda nil "n")))
(global-set-key (kbd "<f8>" ) '(lambda () (interactive) (org-ql-view "Overview: Agenda-like")))
(global-set-key (kbd "M-<f6>") 'elfeed-dashboard)
General.el
Eval First and Last at least block! Edit: honestly I have no clue wtf that meant, or why I wrote it, but I will keep it
use-package
(use-package general
:after evil
:defer t
:preface
Helper Functions
(defun my/keybind/config ()
(interactive)
(counsel-find-file "emacs" "~/.config/"))
(defun my/keybind/capture-inbox ()
(interactive)
(org-capture nil "gi"))
(defun my/counsel-insert-file-path ()
"Insert relative file path using counsel minibuffer"
(interactive)
(unless (featurep 'counsel) (require 'counsel))
(ivy-read "Insert filename: " 'read-file-name-internal
:matcher #'counsel--find-file-matcher
:action
(lambda (x)
(insert (file-relative-name x)))))
leader-keys
config head declartion
:config
(general-create-definer my/leader-keys
:keymaps 'override
:states '(normal insert visual emacs)
:prefix "SPC"
:global-prefix "C-SPC")
Symbols, Spaces, Numbers, u, tabs
(my/leader-keys
"." '(counsel-find-file :which-key "find file")
"SPC" '(counsel-projectile-find-file :which-key "projectile find file")
"/" '(counsel-projectile-rg :which-key "projects")
"," '(counsel-rg :which-key "rg")
"u" '(universal-argument :which-key "universal arg")
";" '(counsel-M-x :which-key "M-x")
":" '(eval-expression :which-key "eval expression")
Toggles (t)
"t" '(:ignore t :which-key "toggles")
Help (h)
"h" '(:ignore t :which-key "Help")
"ht" '(counsel-load-theme :which-key "Choose Theme")
"hk" '(helpful-key :which-key "Describe Key")
"hf" '(counsel-describe-function :which-key "Describe Function")
"hv" '(counsel-describe-variable :which-key "Describe Variable")
"hF" '(counsel-describe-face :which-key "Describe Face")
"hi" '(info :which-key "info")
"hm" '(woman :which-key "woman")
search (s)
"s" '(:ignore t :which-key "Search")
"sb" '(swiper :which-key "swiper")
Files (f)
"f" '(:ignore t :which-key "Files")
"fr" '(counsel-recentf :which-key "Recent Files")
"fp" '(my/keybind/config :which-key "Config")
"fd" '(dired :which-key "dired prompt")
"fD" '(dired-jump :which-key "dired current")
Roam and Org, Capture, Inbox(r/C/I)
"r" '(:ignore t :which-key "Roam+Org")
"ra" '(org-agenda :which-key "Agenda")
"rA" '(cfw:open-org-calendar :which-key "Calendar")
"rh" '(helm-org-ql-views :which-key "org-ql views")
"rD" '(deft :which-key "Deft")
"rf" '(org-roam-node-find :which-key "Find Note")
"rl" '(org-roam-buffer-toggle :which-key "Toggle Sidebar")
"rr" '(org-roam-db-sync :which-key "Roam Sync")
"ri" '(org-roam-node-insert :which-key "Node Insert")
"rI" '(org-id-get-create :which-key "Org Id get/create")
"rT" '(counsel-org-tag :which-key "Org Id get/create")
;; Dailies
"rd" '(:ignore t :which-key "Dailies")
"rdD" '(org-roam-dailies-goto-date :which-key "Go To Date")
"rdT" '(org-roam-dailies-goto-today :which-key "Go To Today")
"rdt" '(org-roam-dailies-capture-today :which-key "Capture Today")
"rdY" '(org-roam-dailies-goto-yesterday :which-key "Go To yesterday")
"rdy" '(org-roam-dailies-capture-yesterday :which-key "Capture yesterday")
"rdM" '(org-roam-dailies-goto-tomorrow :which-key "Go To tomorrow")
"rdm" '(org-roam-dailies-capture-tomorrow :which-key "Capture tomorrow")
;; Clocks
"rc" '(:ignore t :which-key "Clocks")
"rci" '(org-clock-in :which-key "Clock In")
"rcI" '(org-clock-in-last :which-key "Clock In Last")
"rco" '(org-clock-out :which-key "Clock Out")
"rcp" '(org-pomodoro :which-key "Pomodoro")
"rcR" '(org-clock-report :which-key "Clock Report")
"rcg" '(org-clock-goto :which-key "Goto Clock")
;; Anki
"rn" '(:ignore t :which-key "AnKi")
"rnp" '(anki-editor-push-notes :which-key "Clock In")
"rni" '(anki-editor-insert-notes :which-key "Clock In")
;; Schedules and Deadlines
;; TODO!
Capture
"C" '(org-capture :which-key "Org-Capture")
"I" '(my/keybind/capture-inbox :which-key "Capture Inbox")
Open (o)
"o" '(:ignore t :which-key "Open")
"oT" '(vterm :which-key "Vterm in current window")
; use C-t
;"ot" '(vterm-toggle :which-key "Vterm in other window")
"ob" '(bookmark-jump :which-key "Bookmark Jump")
"oB" '(bookmark-set :which-key "Bookmark set")
"op" '(list-processes :which-key "List Proccess")
"om" '(mu4e :which-key "mu4e")
"ot" '(telega :which-key "Telega")
"oc" '(circe :which-key "Circe")
"os" '(easy-hugo :which-key "site")
"oe" '(elfeed-dashboard :which-key "Elfeed Dashboard")
Insert (i)
"i" '(:ignore t :which-key "Insert")
"ie" '(emoji-insert :which-key "Emoji")
"if" '(my/counsel-insert-file-path :which-key "Insert Relative path")
"ik" '(helm-show-kill-ring :which-key "Insert from Kill ring")
Buffers (b)
"b" '(:ignore t :which-key "buffers")
"bs" '(save-buffer :which-key "Save Buffer")
"bk" '(kill-current-buffer :which-key "Kill Buffer")
"bl" '(evil-switch-to-windows-last-buffer :which-key "Last Buffer")
"bi" '(ibuffer :which-key "Ibuffer")
"br" '(revert-buffer :which-key "Revert Buffer")
"bb" '(helm-buffers-list :which-key "Switch to buffer")
"bc" '(my/circe/helm-buffers :which-key "Circe Helm")
"bt" '(telega-switch-buffer :which-key "Telega buffers")
Windows (w)
"w" '(:ignore t :which-key "Windows")
"wj" '(evil-window-down :which-key "Window Down")
"wk" '(evil-window-up :which-key "Window Up")
"wl" '(evil-window-right :which-key "Window Left")
"wh" '(evil-window-left :which-key "Window Down")
"wJ" '(evil-window-move-very-bottom :which-key "Move Window Down")
"wK" '(evil-window-move-very-top :which-key "Move Window Up")
"wL" '(evil-window-move-far-right :which-key "Move Window Left")
"wH" '(evil-window-move-far-left :which-key "Move Window Down")
"ws" '(evil-window-split :which-key "Window Split")
"wv" '(evil-window-vsplit :which-key "Window Vsplit")
"wd" '(evil-window-delete :which-key "Window delete")
"wu" '(winner-undo :which-key "Window Undo")
"wo" '(other-window :which-key "Window Other")
"wr" '(winner-redo :which-key "Window Redo")
"wt" '(treemacs :which-key "Treemacs")
Code (c)
"c" '(:ignore t :which-key "code")
"cE" '(eval-defun :which-key "Eval Function at Point")
"ce" '(eval-last-sexp :which-key "Eval Function")
"cb" '(eval-buffer :which-key "Eval Buffer")
"ca" '(lsp-execute-code-action :which-key "Code Action")
"cl" '(lsp-avy-lens :which-key "Code Action")
"ci" '(lsp-ui-imenu :which-key "lsp imenu")
"cr" '(lsp-rename :which-key "rename")
;"cs" '(lsp-find-refernces :which-key "find refernces")
"cd" '(lsp-find-definition :which-key "goto defintion")
"cD" '(lsp-ui-peek-find-definitions :which-key "goto defintion")
"cs" '(lsp-ui-peek-find-refernces :which-key "find refernces")
"cc" '(recompile :which-key "find refernces")
"cC" '(compile :which-key "find refernces")
Git (g)
"g" '(:ignore t :which-key "Git")
"gg" '(magit-status :which-key "Magit")
Projectile (p)
"p" '(projectile-command-map t :which-key "Projectile")
Quit (q)
"q" '(:ignore t :which-key "Quit and Stuff")
"qf" '(delete-frame :which-key "Close Frame")
Closing Brackets
))
Evil
Basic Evil
(use-package evil
:init
(setq evil-want-integration t
evil-want-keybinding nil
evil-want-C-u-scroll t
evil-want-C-w-delete t
evil-want-C-i-jump t
evil-want-Y-yank-to-eol t
evil-normal-state-cursor 'box
evil-emacs-state-cursor '(box +evil-emacs-cursor-fn); TODO: fix
evil-insert-state-cursor 'bar
evil-visual-state-cursor 'hollow
evil-undo-system 'undo-redo)
:config
(evil-mode 1)
(define-key evil-insert-state-map (kbd "C-g") 'evil-normal-state)
(define-key evil-insert-state-map (kbd "C-h") 'evil-delete-backward-char-and-join)
(define-key evil-normal-state-map "u" 'undo-fu-only-undo)
(define-key evil-normal-state-map "\C-r" 'undo-fu-only-redo)
(define-key evil-normal-state-map "\C-e" 'evil-end-of-line)
(define-key evil-insert-state-map "\C-a" 'evil-beginning-of-line)
(define-key evil-insert-state-map "\C-e" 'end-of-line)
(define-key evil-visual-state-map "\C-e" 'evil-end-of-line)
(define-key evil-motion-state-map "\C-e" 'evil-end-of-line)
(define-key evil-normal-state-map "\C-f" 'evil-forward-char)
(define-key evil-insert-state-map "\C-f" 'evil-forward-char)
(define-key evil-insert-state-map "\C-f" 'evil-forward-char)
(define-key evil-normal-state-map "\C-b" 'evil-backward-char)
(define-key evil-insert-state-map "\C-b" 'evil-backward-char)
(define-key evil-visual-state-map "\C-b" 'evil-backward-char)
(define-key evil-insert-state-map "\C-d" 'evil-delete-char)
(define-key evil-normal-state-map "\C-i" 'evil-jump-forward)
(define-key evil-normal-state-map "\C-n" 'evil-next-line)
(define-key evil-insert-state-map "\C-n" 'evil-next-line)
(define-key evil-visual-state-map "\C-n" 'evil-next-line)
(define-key evil-normal-state-map "\C-p" 'evil-previous-line)
(define-key evil-insert-state-map "\C-p" 'evil-previous-line)
(define-key evil-visual-state-map "\C-p" 'evil-previous-line)
;; (define-key evil-normal-state-map "\C-w" 'evil-delete);; in custom
(define-key evil-insert-state-map "\C-w" 'evil-delete-backward-word)
(define-key evil-visual-state-map "\C-w" 'evil-delete-backward-word)
(define-key evil-normal-state-map "\C-y" 'yank)
(define-key evil-insert-state-map "\C-y" 'yank)
(define-key evil-visual-state-map "\C-y" 'yank)
;(define-key evil-normal-state-map "K" 'lsp-ui-doc-glance); moved to lsp-ui
(define-key evil-visual-state-map "\C-y" 'yank)
(define-key evil-insert-state-map "\C-k" 'kill-line)
(define-key evil-normal-state-map "Q" 'call-last-kbd-macro)
(define-key evil-visual-state-map "Q" 'call-last-kbd-macro)
;; (define-key evil-normal-state-map (kbd "TAB") 'evil-undefine)
;; Use visual line motions even outside of visual-line-mode buffers
(evil-global-set-key 'motion "j" 'evil-next-visual-line)
(evil-global-set-key 'motion "k" 'evil-previous-visual-line)
(evil-set-initial-state 'messages-buffer-mode 'normal)
(evil-set-initial-state 'dashboard-mode 'normal))
(Not Working) Emacs State Cursor Color
(defun +evil-default-cursor-fn (interactive)
(evil-set-cursor-color (get 'cursor 'evil-normal-color)))
(defun +evil-emacs-cursor-fn () (interactive)
(evil-set-cursor-color (get 'cursor 'evil-emacs-color)))
Evil Collection
(use-package evil-collection
:after evil
; :custom
; (evil-collection-outline-bind-tab-p t)
:config
(evil-collection-init))
Evil Escape
;; ; https://emacs.stackexchange.com/questions/19961/using-jk-to-exit-insert-mode-with-key-chord-or-anything-else
;; (defun my-jk ()
;; (interactive)
;; (let* ((initial-key ?j)
;; (final-key ?k)
;; (timeout 0.5)
;; (event (read-event nil nil timeout)))
;; (if event
;; ;; timeout met
;; (if (and (characterp event) (= event final-key))
;; (evil-normal-state)
;; (insert initial-key)
;; (push event unread-command-events))
;; ;; timeout exceeded
;; (insert initial-key))))
;; (define-key evil-insert-state-map (kbd "j") 'my-jk)
(use-package key-chord
:after evil
:custom
(key-chord-two-keys-delay 0.05)
(key-chord-safety-interval-forward 0.1)
:config
(key-chord-mode 1)
(key-chord-define evil-insert-state-map "jk" 'evil-normal-state)
(key-chord-define evil-replace-state-map "jk" 'evil-normal-state))
;; (use-package evil-escape
;; :after evil
;; :init
;; (setq 'evil-escape-excluded-major-modes '(magit-status-mode))
;; (evil-escape-mode)
;; :config
;; (setq evil-escape-key-sequence "jk")
;; (setq evil-escape-delay 0.2)
;; (setq evil-escape-unordered-key-sequence t))
Evil args
wcsmith/evil-args: Motions and text objects for delimited arguments in Evil.
(use-package evil-args
:config
;; bind evil-args text objects
(define-key evil-inner-text-objects-map "a" 'evil-inner-arg)
(define-key evil-outer-text-objects-map "a" 'evil-outer-arg)
;; bind evil-forward/backward-args
(define-key evil-normal-state-map "L" 'evil-forward-arg)
(define-key evil-normal-state-map "H" 'evil-backward-arg)
(define-key evil-motion-state-map "L" 'evil-forward-arg)
(define-key evil-motion-state-map "H" 'evil-backward-arg)
;; bind evil-jump-out-args
;; (define-key evil-normal-state-map "K" 'evil-jump-out-args))
)
Evil Easy Motion
PythonNut/evil-easymotion: A port of vim easymotion to Emacs' evil-mode
(use-package evil-easymotion
:config
(evilem-default-keybindings "SPC"))
evil-org
(use-package evil-org
:hook (org-mode . evil-org-mode))
Evil snipe
hlissner/evil-snipe: 2-char searching ala vim-sneak & vim-seek, for evil-mode
(use-package evil-snipe
:config
(setq evil-snipe-repeat-scope 'whole-visible)
(evil-snipe-mode +1))
Evil numbers
(use-package evil-numbers
:config
(evil-define-key '(normal visual) 'global (kbd "C-c +") 'evil-numbers/inc-at-pt)
(evil-define-key '(normal visual) 'global (kbd "C-c -") 'evil-numbers/dec-at-pt)
(evil-define-key '(normal visual) 'global (kbd "C-c C-+") 'evil-numbers/inc-at-pt-incremental)
(evil-define-key '(normal visual) 'global (kbd "C-c C--") 'evil-numbers/dec-at-pt-incremental)
)
Completions
ivy
Better Completions
(use-package ivy
:defer t
:diminish
:bind (("C-s" . swiper); TODO: move to Keybinds
:map ivy-minibuffer-map
("TAB" . ivy-alt-done)
("C-l" . ivy-alt-done)
("C-j" . ivy-next-line)
("C-k" . ivy-previous-line)
:map ivy-switch-buffer-map
("C-k" . ivy-previous-line)
("C-l" . ivy-done)
("C-d" . ivy-switch-buffer-kill)
:map ivy-reverse-i-search-map
("C-k" . ivy-previous-line)
("C-d" . ivy-reverse-i-search-kill))
:config
(ivy-mode 1))
Ivy Rich for having M-x
description and keybinds
(use-package ivy-rich
:after counsel
:init (ivy-rich-mode 1))
Ivy floating
(use-package ivy-posframe
:after ivy
:diminish
:custom-face
(ivy-posframe-border ((t (:background "#ffffff"))))
:config
(setq ivy-posframe-display-functions-alist '((t . ivy-posframe-display-at-frame-top-center))
ivy-posframe-height-alist '((t . 20))
ivy-posframe-parameters '((internal-border-width . 10)))
(setq ivy-posframe-width 120)
(setq ivy-posframe-parameters
'((left-fringe . 8)
(right-fringe . 8)))
(ivy-posframe-mode +1))
Counsel
(use-package counsel
:defer t
:bind (("M-x" . counsel-M-x)
;("C-x b" . counsel-ibuffer)
("C-x C-f" . counsel-find-file)
:map minibuffer-local-map
("C-r" . 'counsel-minibuffer-history)
("C-w" . 'evil-delete-backward-word))
:config (setq ivy-initial-inputs-alist nil)) ;; Don't start searches with '^'
Which Key (Shows Next keys)
slow loading! defer it
(use-package which-key
:defer 10
:diminish which-key-mode
:config
(which-key-mode)
(setq which-key-idle-delay 1
which-key-max-display-columns 5))
Company Mode
(use-package company
:ensure
:defer 5
:diminish company-mode
:custom
(company-tooltip-minimum-width 40) ;reduce flicker due to changing width
(global-company-mode t)
(company-idle-delay 0.3) ;; how long to wait until popup
(company-minimum-prefix-length 1) ;; The minimum prefix length for idle completion.
(company-selection-wrap-around t)
;; (company-begin-commands nil) ;; uncomment to disable popup
:bind
(:map company-active-map
;; ("C-n". company-select-next)
("C-w". evil-delete-backward-word)
("<tab>" . company-complete-common-or-cycle)
("RET" . company-complete-selection)
;; ("C-p". company-select-previous)
("M-<". company-select-first)
("M->". company-select-last)))
(use-package company-box
:after company
:hook (company-mode . company-box-mode))
lsp + yasnippet
(defun my-backends ()
(set (make-local-variable 'company-backends)
'((company-capf ;; I think this must come first?
:with
company-yasnippet
company-files
company-dabbrev-code))))
Prescient
better sorting for ivy, company..
(use-package prescient
:defer t
:diminish
:config (prescient-persist-mode 1))
(use-package ivy-prescient
:after counsel
:init (ivy-prescient-mode 1))
(use-package company-prescient
:after company
:config
(company-prescient-mode 1)
(prescient-persist-mode)
)
;; (use-package selectrum-prescient)
Yasnippet
(use-package yasnippet
:defer 9
:config
(yas-global-mode))
(use-package yasnippet-snippets
:after yasnippet)
Helm
(use-package helm
:defer t
:config (helm-autoresize-mode 1))
Org-Mode
Set directories
(setq org-directory "~/Documents/Emacs/gtd/"
org-roam-directory "~/Documents/Emacs/roam/"
;; org-s-file (car (org-roam-id-find "34f6b040-ea49-421c-ade6-3834a9c86e0f"))
;; org-books-file (concat org-roam-directory "book_list.org")
org-agenda-files (list org-directory ); org-s-file)
rmh-elfeed-org-files (list "~/Documents/private.el/elfeed.org")
elfeed-dashboard-file "~/Documents/private.el/elfeed-dashboard.org"
org-preview-latex-image-directory "~/.cache/ltx/ltximg"
org-my-anki-file (concat org-roam-directory "anki.org")
org-refile-targets '((org-agenda-files . (:level . 1))))
use-package
Modes To Start
(defun my/org-mode/org-mode-setup ()
(interactive)
(flyspell-mode 1)
(org-indent-mode)
(variable-pitch-mode 0)
(visual-line-mode 1))
use-package
(use-package org
:defer t
:hook (org-mode . my/org-mode/org-mode-setup)
(org-mode . my/org-mode/load-prettify-symbols); symbols
(org-mode . auto-fill-mode)
:config
(require 'org-tempo)
(require 'org-habit)
(add-to-list 'org-file-apps '("\\.xlsx\\'" . default))
(setq geiser-default-implementation 'guile)
(setq org-ellipsis " ⤵")
(setq org-agenda-start-with-log-mode t)
(setq org-highlight-latex-and-related '(latex))
(setq org-log-done 'time)
(setq org-log-into-drawer t)
(dolist (face '((org-document-title . 2.0)
(org-level-1 . 1.5)
(org-level-2 . 1.0)
(org-level-3 . 1.0)
(org-level-4 . 1.0)
(org-level-5 . 1.0)
(org-level-6 . 1.0)
(org-level-7 . 1.0)
(org-level-8 . 1.0)))
;; (set-face-attribute (car face) nil :font my/ui/varfont :weight 'regular :height (cdr face)))
(set-face-attribute (car face) nil :font my/ui/monofont :weight 'regular :height (cdr face)))
;)
(setq org-todo-keyword-faces `(("NOW" (:foreground "white" :background "#444527"))
("NEXT" (:foreground "bright-white" :background "#444527"))))
(setq org-format-latex-options (plist-put org-format-latex-options :scale 1.5))
;; Ensure that anything that should be fixed-pitch in Org files appears that way
(set-face-attribute 'org-block nil :foreground nil :inherit 'fixed-pitch)
(set-face-attribute 'org-code nil :inherit '(shadow fixed-pitch))
(set-face-attribute 'org-table nil :inherit '(shadow fixed-pitch))
(set-face-attribute 'org-verbatim nil :inherit '(shadow fixed-pitch))
(set-face-attribute 'org-special-keyword nil :inherit '(font-lock-comment-face fixed-pitch))
(set-face-attribute 'org-meta-line nil :inherit '(font-lock-comment-face fixed-pitch))
(set-face-attribute 'org-todo nil :background "#444527" )
(set-face-attribute 'org-done nil :strike-through t)
(set-face-attribute 'org-headline-done nil :strike-through t)
(set-face-attribute 'org-checkbox nil :inherit 'fixed-pitch))
Capture Templates
(use-package doct
:ensure t
;;recommended: defer until calling doct
:commands (doct))
Open with external app
;; Excel with xdg-open
;;(add-to-list 'org-file-apps '("\\.xlsx\\'" . default))
;; moved to org use package
Appearance
Symbols
(defun my/org-mode/load-prettify-symbols ()
(interactive)
(setq prettify-symbols-alist
(mapcan (lambda (x) (list x (cons (upcase (car x)) (cdr x))))
'(("#+begin_src" . ?)
("#+end_src" . ?)
("#+begin_example" . ?)
("#+end_example" . ?)
("#+header:" . ?)
("#+name:" . ?﮸)
("#+title:" . "")
("#+results:" . ?)
("#+call:" . ?)
(":properties:" . ?)
(":logbook:" . ?))))
(prettify-symbols-mode 1))
COMMENT Visual Fill (center)
I now use olivetti mode, this code block is ignored!
(defun my/org-mode/org-mode-visual-fill ()
(interactive)
(setq visual-fill-column-width 110
visual-fill-column-center-text t
fill-column 90)
(visual-fill-column-mode 1))
(use-package visual-fill-column; center text
:hook (org-mode . my/org-mode/org-mode-visual-fill))
org-bullets
(use-package org-bullets
:after org
:hook (org-mode . org-bullets-mode)
:custom
(org-bullets-bullet-list '("◉" "○" "●" "○" "●" "○" "●")))
Latex
scale inline
; moved to use -package
; (setq org-format-latex-options (plist-put org-format-latex-options :scale 1.5))
Babel
Don't confirm, I know what I am doing!
(setq org-confirm-babel-evaluate nil)
Language List
(org-babel-do-load-languages
'org-babel-load-languages
'((emacs-lisp . t)
(python . t)
;(restclient . t)
(sql . t)
;(mermaid . t)
(octave . t)
(scheme . t)
(shell . t)))
Structure Templates
Allow fast code insertion
;; This is needed as of Org 9.2
(add-to-list 'org-structure-template-alist '("sh" . "src shell"))
(add-to-list 'org-structure-template-alist '("el" . "src emacs-lisp"))
(add-to-list 'org-structure-template-alist '("re" . "src restclient"))
(add-to-list 'org-structure-template-alist '("sq" . "src sql"))
(add-to-list 'org-structure-template-alist '("sql" . "src sql"))
(add-to-list 'org-structure-template-alist '("oc" . "src octave"))
(add-to-list 'org-structure-template-alist '("py" . "src python"))
(add-to-list 'org-structure-template-alist '("scm" . "src scheme"))
Mermaid graphs
; :tangle no
(use-package ob-mermaid
:after org)
Capture
Templates
(setq org-capture-templates
(doct `(("Consume: Read/watch" :keys "c"
:file ,(concat org-directory "inbox.org")
:prepend t
:template ("* %{todo-state} %^{Description}"
":PROPERTIES:"
":Created: %U"
":END:"
"%?")
:children (("Read" :keys "r"
:headline "Read"
:todo-state "TODO")
("Watch" :keys "w"
:headline "Watch"
:todo-state "TODO")))
("Ideas" :keys "i"
:file ,(concat org-directory "inbox.org")
:prepend t
:template ("* %{todo-state} %^{Description}"
":PROPERTIES:"
":Created: %U"
":END:"
"%?")
:children (("Project" :keys "p"
:olp ("Ideas" "Project")
:todo-state "")
("Blogs" :keys "b"
:olp ("Blog")
:todo-state "")
("placeholder" :keys "w"
:headline "Watch"
:todo-state "TODO")))
("GTD" :keys "g"
:file ,(concat org-directory "inbox.org")
:prepend t
:template ("* %{todo-state} %^{Description}"
":PROPERTIES:"
":Created: %U"
":END:"
"%?")
:children (("Inbox" :keys "i"
:headline "Inbox"
:todo-state "")
("placeholder" :keys "w"
:headline "Watch"
:todo-state "TODO"))))))
Utils
launch with emacsclient -e '(make-orgcapture-frame)'
From: https://yiufung.net/post/anki-org/
(defun make-orgcapture-frame ()
"Create a new frame and run org-capture."
(interactive)
;(make-frame '((name . "org-capture") (window-system . x))); window-system breaks for some reason :(
(make-frame '((name . "org-capture")))
(select-frame-by-name "org-capture")
(counsel-org-capture)
(delete-other-windows))
Agenda
Customizations
;;laggy :(
(setq org-agenda-show-outline-path nil
org-deadline-warning-days 30)
T/ODOs
(setq org-todo-keywords '((sequence "TODO(t!)" "NOW(o)" "NEXT(n)" "|" "DONE(d!)")
(sequence "|" "CANCELED(c!)")))
start on sunday!
(setq org-agenda-start-on-weekday 0 ;0 is sunday
org-agenda-weekend-days '(5 6))
Weeks per semester
(defun org-week-to-class-week (week)
(- week 34))
(advice-add 'org-days-to-iso-week :filter-return
#'org-week-to-class-week)
Go EVIL!
(eval-after-load 'org-agenda
'(progn
(evil-set-initial-state 'org-agenda-mode 'normal)
(evil-define-key 'normal org-agenda-mode-map
(kbd "<RET>") 'org-agenda-goto
;;;; (kbd "\t") 'org-agenda-goto
"q" 'org-agenda-quit
"S" 'org-save-all-org-buffers
;;;; Clocking
"c" nil
"ci" 'org-agenda-clock-in
"co" 'org-agenda-clock-out
"cx" 'org-agenda-clock-cancel
"cR" 'org-agenda-clockreport-mode
;;;; Properties
"s" 'org-agenda-schedule
"d" 'org-agenda-deadline
"p" 'org-agenda-priority
"+" 'org-agenda-priority-up
"-" 'org-agenda-priority-down
"t" 'org-agenda-todo
"T" 'counsel-org-tag
":" 'org-agenda-set-tags
"e" 'org-agenda-set-effort
;;;; Movement
"j" 'org-agenda-next-line
"k" 'org-agenda-previous-line
"f" 'org-agenda-later
"b" 'org-agenda-earlier
"J" 'org-agenda-next-date-line
"K" 'org-agenda-previous-date-line
"." 'org-agenda-goto-today
;;;; View toggles
"vt" 'org-agenda-toggle-time-grid
"vw" 'org-agenda-week-view
"vd" 'org-agenda-day-view
"vl" 'org-agenda-log-mode
"vr" 'org-agenda-redo
"r" 'org-agenda-redo;; often used
"F" 'org-agenda-follow-mode
;;;; Other
"C" 'org-capture
"R" 'my/org-agenda/process-inbox-item
"A" 'org-agenda-archive
"g/" 'org-agenda-filter-by-tag
"gr" 'org-ql-view-refresh
"gh" 'helm-org-ql-views
;;;; cool but inactive
;; "gj" 'org-agenda-goto-date
;; "gJ" 'org-agenda-clock-goto
"gm" 'org-agenda-bulk-mark
"go" 'org-agenda-open-link
;; "y" 'org-agenda-todo-yesterday
;; "n" 'org-agenda-add-note
;; ";" 'org-timer-set-timer
;; "I" 'helm-org-task-file-headings
;; "i" 'org-agenda-clock-in-avy
;; "O" 'org-agenda-clock-out-avy
;; "u" 'org-agenda-bulk-unmark
;; "x" 'org-agenda-exit
;; "va" 'org-agenda-archives-mode
;;"vc" 'org-agenda-show-clocking-issues
;; "o" 'delete-other-windows
;; "gh" 'org-agenda-holiday
;; "gv" 'org-agenda-view-mode-dispatch
"n" nil ; evil-search-next
;; "{" 'org-agenda-manipulate-query-add-re
;; "}" 'org-agenda-manipulate-query-subtract-re
;; "0" 'evil-digit-argument-or-evil-beginning-of-line
;; "<" 'org-agenda-filter-by-category
;; ">" 'org-agenda-date-prompt
;; "H" 'org-agenda-holidays
;; "L" 'org-agenda-recenter
;; "Z" 'org-agenda-sunrise-sunset
;; "T" 'org-agenda-show-tags
;; "X" 'org-agenda-clock-cancel
;; "[" 'org-agenda-manipulate-query-add
;; "g\\" 'org-agenda-filter-by-tag-refine
;; "]" 'org-agenda-manipulate-query-subtract
)))
;; TODO check this
habits
(setq org-habit-graph-column 80 ; prevent overwriting title
org-habit-show-habits-only-for-today 't
org-habit-show-all-today nil) ; show even if DONE
;; (with-eval-after-load 'org-habit
;; (defun org-habit-streak-count ()
;; (goto-char (point-min))
;; (while (not (eobp))
;; ;;on habit line?
;; (when (get-text-property (point) 'org-habit-p)
;; (let ((streak 0)
;; (counter (+ org-habit-graph-column (- org-habit-preceding-days org-habit-following-days)))
;; )
;; (move-to-column counter)
;; ;;until end of line
;; (while (= (char-after (point)) org-habit-completed-glyph)
;; (setq streak (+ streak 1))
;; (setq counter (- counter 1))
;; (backward-char 1))
;; (end-of-line)
;; (insert (number-to-string streak))))
;; (forward-line 1)))
;; (add-hook 'org-agenda-finalize-hook 'org-habit-streak-count))
org SUPER agenda
(use-package org-super-agenda
:after org-agenda
:config
(setq org-agenda-span 'day); a week is too much
(setq org-super-agenda-groups
'((:log t :order 99); logs at bottom
(:name "S"
:order 97
:tag ("S"))
(:name "Life"
:order 97
:tag ("L"))
(:name "Habits"
:order 98
:habit t)
(:name "Overdue"
:deadline past
:scheduled past)
(:name "Today" ; today is what
:time-grid t ; Items that appear on the time grid
:scheduled today)
(:name "Now" ; today is what
:todo "NOW")
(:name "Deadlines"
:deadline t)
(:name "To Refile"
:tag ("INBOX"))))
(org-super-agenda-mode 1)
:hook (org-agenda-mode . origami-mode)
(org-agenda-mode . org-super-agenda-mode); need this sadly
(org-agenda-mode . olivetti-mode)
;(org-agenda-mode . olivetti-mode)
;(evil-define-key '(normal visual) 'org-super-agenda-header-map "j" 'org-agenda-next-line)
:bind (:map org-super-agenda-header-map
([tab] . origami-toggle-node)
;; evil doesn't work on headers, bruh
("j" . org-agenda-next-line)
("k" . org-agenda-previous-line)
("h" . evil-backward-char)
("l" . evil-forward-char)))
COMMENT org-ql
(use-package helm-org-ql :after org-ql)
; TODO: tasks not in inbox, and have no schedule/effort/etc
(use-package org-ql
:config
(setq org-ql-views (list
(cons "Agenda:Today"
(list :buffers-files #'org-agenda-files
:query '(and (not (done))
(or (deadline auto)
(scheduled :to today)
(todo "NOW")
(ts-active :on today)))
:sort '(priority date todo)
:super-groups 'org-super-agenda-groups
:title "Overview: Today"))
(cons "To Refile"
(list :buffers-files #'org-agenda-files
:query '(or
(parent (tags "INBOX"))
(done))
:super-groups '((:name "Done" :todo "DONE")
(:name "Canceled" :todo "CANCELED")
(:name "Inbox" :anything))
:title "Inbox"))
(cons "Plans"
(list :buffers-files #'org-agenda-files
:query '(and
(parent (tags "PLAN"))
(not (done)))
:super-groups '((:auto-outline-path))
:sort '(priority date todo)
:title "Plans"))
(cons "Consoom and Create"
(list :buffers-files #'org-agenda-files
:query '(parent (tags "READ" "WATCH" "TO_BLOG"))
:super-groups '((:tag "READ")
(:tag "WATCH")
(:tag "TO_BLOG"))
:sort '(todo)
:title "Goals"))
(cons "Orphans"
(list :buffers-files #'org-agenda-files
:query '(and ;(not (todo))
(not (done))
(not (effort))
(not (tags "NOT_ORPHAN" "INBOX"))
(not (scheduled))
(not (deadline))
(parent))))
(cons "Quick Picks"
(list :buffers-files #'org-agenda-files
:query '(and (not (done))
(effort <= 10))
:sort '(todo)
:super-groups 'org-super-agenda-groups
:title "Quick Picks")))))
COMMENT org-timeblock
(use-package org-timeblock
:straight (org-timeblock :type git
:host github
:repo "ichernyshovvv/org-timeblock"))
COMMENT org-hyperscheduler
(use-package org-hyperscheduler
:straight
( :repo "dmitrym0/org-hyperscheduler"
:host github
:type git
:files ("*"))
:custom
(org-hyperscheduler-readonly-mode nil))
Helper functions
Stolen from: Org-mode Workflow Part 2: Processing the Inbox · Jethro Kuan
(defun my/org-agenda/process-inbox-item ()
"Process a single item in the org-agenda."
(interactive)
(org-with-wide-buffer
(org-agenda-set-tags)
;(org-agenda-priority)
(org-agenda-set-effort)
(org-agenda-refile nil nil t)))
Calfw calendar
(use-package calfw :after org)
(use-package calfw-org
:after calfw
:config
; looks nice
(setq cfw:fchar-junction ?╬
cfw:fchar-vertical-line ?║
cfw:fchar-horizontal-line ?═
cfw:fchar-left-junction ?╠
cfw:fchar-right-junction ?╣
cfw:fchar-top-junction ?╦
cfw:fchar-top-left-corner ?╔
cfw:fchar-top-right-corner ?╗)
(evil-set-initial-state 'cfw:details-mode 'emacs))
org-pomodoro
(use-package org-pomodoro
:defer t
:custom
(org-pomodoro-length 25)
(org-pomodoro-keep-killed-pomodoro-time t)
(org-pomodoro-manual-break t))
Org analyzer
(use-package org-analyzer)
org-roam
use-package
(use-package org-roam
:defer t
:custom
(org-roam-completion-everywhere t)
(org-roam-db-gc-threshold most-positive-fixnum) ;; preformance
(org-roam-capture-ref-templates
'(("r" "ref" plain "%?" :if-new
(file+head "%<%Y%m%d%H%M%S>-${slug}.org" "#+title: ${title}")
:unnarrowed t)))
:config
;; side window
;(require 'org-roam-protocol)
(org-roam-db-autosync-mode)
(add-to-list 'display-buffer-alist
'("\\*org-roam\\*"
(display-buffer-in-side-window)
(side . right)
(slot . 0)
(window-width . 0.33)
(window-parameters . ((no-other-window . t)
(no-delete-other-windows . t))))))
org roam server
(use-package websocket
:after org-roam)
(use-package simple-httpd
:after org-roam)
(use-package org-roam-ui
:straight (org-roam-ui
:type git
:host github
:repo "org-roam/org-roam-ui"
:files ("*.el" "out"))
:after org-roam ;; or :after org
:hook (org-roam . org-roam-ui-mode)
:config)
Deft
(use-package deft
:after org
:bind
:custom
(deft-strip-summary-regexp "\\`\\(.+\n\\)+\n")
(deft-recursive t)
(deft-use-filter-string-for-filename t)
(deft-default-extension "org")
(deft-directory org-roam-directory))
(setq deft-recursive t)
(setq deft-strip-summary-regexp ":PROPERTIES:\n\\(.+\n\\)+:END:\n")
(setq deft-use-filename-as-title 't)
org-download and clip-link
(use-package org-download
:after org)
(use-package org-cliplink
:after org)
COMMENT org-book
(use-package org-books
:after org )
COMMENT Anki
Stopped using this, I just use Anki like a normal person
(use-package anki-editor
:after org
:bind (:map org-mode-map
("<f12>" . anki-editor-cloze-region-auto-incr))
:init
(setq-default anki-editor-use-math-jax t)
:config
(setq anki-editor-create-decks nil ;; Allow anki-editor to create a new deck if it doesn't exist
anki-editor-org-tags-as-anki-tags t)
)
Development
General
Brackets setup
(use-package rainbow-delimiters
:hook (prog-mode . rainbow-delimiters-mode)
(prog-mode . show-paren-mode)
;(prog-mode . electric-pair-local-mode)
)
;; (use-package paredit :defer t)
(use-package parinfer-rust-mode ;
:hook
(emacs-lisp-mode . parinfer-rust-mode)
(scheme-mode . parinfer-rust-mode)
(clojure-mode . parinfer-rust-mode)
;tabs break parinfer rust mode
(parinfer-rust-mode . (lambda () (setq indent-tabs-mode nil)));
:init
(setq parinfer-rust-auto-download t
; this variable is only available on my fork
parinfer-rust-disable-troublesome-modes t))
Compilation output
When running M-x compile
the output is colored!
(add-hook 'compilation-filter-hook 'ansi-color-compilation-filter)
Projectile
(use-package projectile
:defer t
:diminish projectile-mode
:config (projectile-mode)
:custom ((projectile-completion-system 'ivy))
:init
;; NOTE: Set this to the folder where you keep your Git repos!
(when (file-directory-p "~/code")
(setq projectile-project-search-path '("~/code")))
(setq projectile-switch-project-action #'projectile-dired))
Counsel Projectile
(use-package counsel-projectile
:defer 9
:config (counsel-projectile-mode))
Recentf
(use-package recentf
:defer 10
:config (recentf-mode 1)
; https://github.com/emacscollective/no-littering#suggested-settings
(with-eval-after-load 'no-littering
(add-to-list 'recentf-exclude no-littering-var-directory)
(add-to-list 'recentf-exclude no-littering-etc-directory)))
lsp performance
This is done in Performance section
(setq gc-cons-threshold 100000000) ;; 100 mb
(setq read-process-output-max (* 1024 4024)) ;; 4mb
lsp-mode
(use-package lsp-mode
:commands (lsp lsp-deferred)
;; :hook
;; (lsp-mode . my/lsp/lsp-mode-setup)
:custom
(lsp-headerline-breadcrumb-segments '(path-up-to-project file))
(lsp-rust-analyzer-cargo-watch-command "clippy")
(lsp-eldoc-render-all t)
(lsp-eldoc-enable-hover nil)
(lsp-ui-doc-show-with-mouse nil)
(lsp-keep-workspace-alive nil)
(lsp-idle-delay 0.6)
(lsp-completion-provider :capf)
(lsp-prefer-flymake nil)
(lsp-idle-delay 0.6)
(lsp-rust-analyzer-server-display-inlay-hints t)
(lsp-rust-analyzer-display-parameter-hints t)
;(setq lsp-keymap-prefix "C-c l") ;; Or 'C-l', 's-l'
:config
(lsp-enable-which-key-integration t)
(setq lsp-headerline-breadcrumb-enable nil); anonying tabs
(setq lsp-log-io nil) ; if set to true can cause a performance hit
(add-hook 'lsp-mode-hook 'lsp-ui-mode)
(lsp-headerline-breadcrumb-mode -1)
(flycheck-mode 1)
:bind
(:map lsp-mode-map
;; ("<tab>" . company-indent-or-complete-common); commented cuz tabs for yasnippet!
)
)
Lsp UI
(use-package lsp-ui
:commands lsp-ui-mode
:custom
(lsp-ui-peek-always-show t)
(lsp-ui-doc-mode t)
(lsp-ui-sideline-show-hover nil)
;; (lsp-ui-doc-enable nil)
:bind
(:map lsp-ui-mode-map
([remap evil-lookup] . lsp-ui-doc-glance)
([remap xref-find-references] . lsp-ui-peek-find-references)
("C-c z" . lsp-ui-doc-focus-frame)
:map lsp-ui-doc-frame-mode-map
("C-g" . lsp-ui-doc-unfocus-frame)
("C-c z" . lsp-ui-doc-unfocus-frame)
))
lsp treemacs
;; (use-package lsp-treemacs
;; :after lsp)
Flycheck
(use-package flycheck
:custom-face (flycheck-warning ((t (:underline (:color "#fabd2f" :style line :position line)))))
(flycheck-error ((t (:underline (:color "#fb4934" :style line :position line)))))
(flycheck-info ((t (:underline (:color "#83a598" :style line :position line))))))
Hide Show
(use-package origami
:hook (prog-mode . origami-mode))
COMMENT Formatting
(use-package format-all
;; :commands (format-all-mode)
:defer
:config
(setq my/format-all-formatters '(("Verilog" verible)))
:hook (prog-mode . format-all-mode)
(format-all-mode . (lambda () (setq format-all-formatters my/format-all-formatters)))
(format-all-mode . format-all-ensure-formatter))
Debug
Use the Debug Adapter Protocol for running tests and debugging
(use-package dap-mode
:hook
(lsp-mode . dap-mode)
(lsp-mode . dap-ui-mode))
Highlihght Indenation Mode
(use-package highlight-indent-guides
:hook (prog-mode . highlight-indent-guides-mode)
:custom (highlight-indent-guides-method 'character)
(highlight-indent-guides-responsive 'top))
Git
(setq vc-handled-backends '(Git))
Magit
(use-package magit
:commands (magit)
:custom
(magit-display-buffer-function #'magit-display-buffer-same-window-except-diff-v1))
Magit TODOs!
(use-package magit-todos
:after magit
:config (magit-todos-mode 1))
TODO Forge
;(use-package forge)
Git gutter
(use-package git-gutter
:hook (prog-mode . git-gutter-mode)
:config
(setq git-gutter:update-interval 0.02))
(use-package git-gutter-fringe
:config
(define-fringe-bitmap 'git-gutter-fr:added [224] nil nil '(center repeated))
(define-fringe-bitmap 'git-gutter-fr:modified [224] nil nil '(center repeated))
(define-fringe-bitmap 'git-gutter-fr:deleted [128 192 224 240] nil nil 'bottom)
:ensure t)
Treemacs
use-package
(use-package treemacs
:commands (treemacs)
:init
(setq treemacs-follow-after-init t
treemacs-is-never-other-window t
treemacs-sorting 'alphabetic-case-insensitive-asc))
fix evil keybinds
(use-package treemacs-evil
;:when (package-installed-p 'evil-collection)
;:defer t
:after treemacs
:init
:config
(general-def evil-treemacs-state-map
[return] #'treemacs-RET-action
[tab] #'treemacs-TAB-action
"TAB" #'treemacs-TAB-action
"o v" #'treemacs-visit-node-horizontal-split
"o s" #'treemacs-visit-node-vertical-split))
Get treemacs-lsp
(use-package lsp-treemacs
:after (treemacs lsp))
(use-package treemacs-magit
:after treemacs magit)
(use-package treemacs-persp
:after treemacs
:config (treemacs-set-scope-type 'Perspectives))
Language
COMMENT Arduino
(use-package arduino-mode
:config
(lsp-register-client
(make-lsp-client
:new-connection (lsp-stdio-connection '("arduino-language-server" "-clangd" "clangd" "-cli" "arduino-cli" "-cli-config" "/home/lambda/.arduino15/arduino-cli.yaml" "-fqbn" "arduino:avr:uno"))
:activation-fn (lsp-activate-on "arduino")
:server-id 'arduino-language-server))
:defer t)
Clojure
(use-package cider
:defer t
:config (require 'flycheck-clj-kondo)
:hook (clojure-mode . zprint-format-on-save-mode)
(clojure-mode . flycheck-mode)
; (clojure-mode . electric-pair-local-mode)
:bind (:map cider-mode-map
([remap lsp-find-definition] . cider-find-var)
([remap eval-defun] . cider-eval-list-at-point)
([remap eval-last-sexp] . cider-eval-last-sexp)))
Auto format
(use-package zprint-format
:after cider)
(use-package flycheck-clj-kondo
:after cider)
COMMENT Rust
(use-package rustic
:defer t
:ensure
:bind (:map rustic-mode-map
("C-c C-c l" . lsp-ui-flycheck-list)
("C-c C-c s" . lsp-rust-analyzer-status)
("<f5>" . rustic-cargo-test)
("C-<f5>" . rustic-cargo-run))
:config
;; uncomment for less flashiness
;; (setq lsp-eldoc-hook nil)
;; (setq lsp-enable-symbol-highlighting nil)
;; (setq lsp-signature-auto-activate nil)
;; comment to disable rustfmt on save
(setq rustic-format-on-save t)
(add-hook 'rustic-mode-hook 'my/dev/rustic-mode-hook)
(add-hook 'rustic-mode-hook 'lsp)
:custom
(rustic-rustfmt-config-alist '((edition . "2021"))))
(defun my/dev/rustic-mode-hook ()
;; so that run C-c C-c C-r works without having to confirm, but don't try to
;; save rust buffers that are not file visiting. Once
;; https://github.com/brotzeit/rustic/issues/253 has been resolved this should
;; no longer be necessary.
(when buffer-file-name
(setq-local buffer-save-without-query t)))
emacs-lisp
;; (add-hook 'emacs-lisp-mode-hook 'company-mode)
(add-hook 'emacs-lisp-mode-hook 'flycheck-mode)
COMMENT V
(use-package v-mode
:defer t
:preface
(defun my/lsp/v ()
(interactive)
(lsp)
(flycheck-mode 1)
(company-mode 1))
:init
(delete '("\\.[ds]?va?h?\\'" . verilog-mode) auto-mode-alist)
;; :straight (v-mode
;; :type git
;; :host github
;; :repo "damon-kwok/v-mode"
;; :files ("tokens" "v-mode.el"))
(setq auto-mode-alist
(cons '("\\(\\.v\\|\\.vv\\|\\.vsh\\)$" . v-mode) auto-mode-alist))
:hook (v-mode . my/lsp/v)
:config
(flycheck-define-checker v-checker
"A v syntax checker using the v fmt."
:command ("v" "fmt" "-verify" (eval (buffer-file-name)))
:error-patterns
((error line-start (file-name) ":" line ":" column ": error: " (message) line-end))
:modes v-mode)
(add-to-list 'flycheck-checkers 'v-checker)
:bind-keymap
("M-z" . v-menu)
("<f6>" . v-menu)
("C-c C-f" . v-format-buffer)
:mode ("\\.v\\.vsh\\'" . 'v-mode))
Haskell
(use-package haskell-mode
:defer t
:config (require 'lsp-haskell))
(use-package lsp-haskell
:preface
;; lambda symbol
(defun my/font/pretty-lambdas-haskell ()
(font-lock-add-keywords
nil `((,(concat "\\(" (regexp-quote "\\") "\\)")
(0 (progn (compose-region (match-beginning 1) (match-end 1)
,(make-char 'greek-iso8859-7 107))
nil))))))
:hook (haskell-mode . lsp)
;(haskell-literate-mode-hook lsp)
(prog-mode . electric-pair-local-mode)
(haskell-mode . my/font/pretty-lambdas-haskell)
(haskell-mode . flymake-mode)
:config
(haskell-indentation-mode -1)
(add-hook 'before-save-hook 'lsp-format-buffer)
:custom (haskell-stylish-on-save t))
COMMENT yaml
(use-package yaml-mode
:hook (yaml-mode . lsp))
Web
(use-package typescript-mode
:defer t
:hook (typescript-mode . electric-pair-mode)
:hook (typescript-mode . setup-tide-mode)
:hook (typescript-mode . prettier-mode)
:hook (typescript-mode . lsp)
:config (add-to-list 'auto-mode-alist '("\\.tsx\\'" . typescript-mode)))
(use-package tide
:defer t
:preface
(defun setup-tide-mode ()
(interactive)
(tide-setup)
(flycheck-mode +1)
(setq flycheck-check-syntax-automatically '(save mode-enabled))
(eldoc-mode +1)
(tide-hl-identifier-mode +1)
;; company is an optional dependency. You have to
;; install it separately via package-install
;; `M-x package-install [ret] company`
(company-mode +1))
:config
;; aligns annotation to the right hand side
(setq company-tooltip-align-annotations t)
;; formats the buffer before saving
;; (add-hook 'before-save-hook 'tide-format-before-save)
(add-hook 'before-save-hook 'prettier-js))
svelte
(use-package svelte-mode
:hook (svelte-mode . lsp)
(svelte-mode . (lambda ()
(add-hook 'before-save-hook 'lsp-format-buffer nil t))))
prettier
(use-package prettier
:defer t
)
lsp hooks setups
(add-hook 'html-mode-hook 'lsp)
(add-hook 'js-mode-hook 'lsp)
(add-hook 'js-jsx-mode-hook 'lsp)
COMMENT Lua
(use-package lua-mode
:hook (lua-mode . lsp))
Markdown
Better Diff in header sizes
(eval-after-load 'markdown-mode
'(custom-set-faces
'(markdown-header-face-1 ((t (:inherit markdown-header-face :height 1.7))))
'(markdown-header-face-2 ((t (:inherit markdown-header-face :height 1.4))))
'(markdown-header-face-3 ((t (:inherit markdown-header-face :height 1.3))))
'(markdown-header-face-4 ((t (:inherit markdown-header-face :height 1.2))))
'(markdown-header-face-5 ((t (:inherit markdown-header-face :height 1.1))))
'(markdown-header-face-6 ((t (:inherit markdown-header-face :height 1.0))))
))
;; (add-hook 'markdown-mode-hook 'my/org-mode/org-mode-visual-fill)
;; (add-hook 'markdown-mode-hook 'outline-minor-mode)
COMMENT Vue
(use-package vue-mode
:hook (vue-mode . lsp)
:hook (vue-mode . prettier-js-mode))
COMMENT Scheme (guile)
(use-package geiser
:defer
;; :bind ([remap eval-last-sexp] . geiser-eval-last-sexp))
)
(use-package geiser-guile)
Scala
Scala mode for highlighting, indents and motion commands
(use-package scala-mode
:hook
(scala-mode . flycheck-mode)
(scala-mode . lsp)
(scala-mode . electric-pair-local-mode)
(scala-mode . (lambda ()
(add-hook 'before-save-hook 'lsp-format-buffer nil t)))
:interpreter
("scala" . scala-mode))
Sbt for sbt commands…
(use-package sbt-mode
:commands sbt-start sbt-command
:config
;; WORKAROUND: https://github.com/ensime/emacs-sbt-mode/issues/31
;; allows using SPACE when in the minibuffer
(substitute-key-definition
'minibuffer-complete-word
'self-insert-command
minibuffer-local-completion-map)
;; sbt-supershell kills sbt-mode: https://github.com/hvesalai/emacs-sbt-mode/issues/152
(setq sbt:program-options '("-Dsbt.supershell=false")))
; for scala
(use-package lsp-metals)
C and cpp
;; (use-package ccls
;; :hook ((c-mode c++-mode) . (lambda () (require 'ccls) (lsp)))
;; ((c-mode c++-mode) . (lambda () (add-hook 'before-save-hook 'lsp-format-buffer nil t)))
;; ((c-mode c++-mode) . electric-pair-local-mode)
;; ((c-mode c++-mode) . yas-minor-mode))
(use-package cc-mode
:defer t
:hook ((c++-mode cc-mode c-mode) . lsp)
((c++-mode cc-mode c-mode) . lsp)
((c++-mode cc-mode c-mode) . electric-pair-local-mode)
((c++-mode cc-mode c-mode) . yas-minor-mode)
((c++-mode cc-mode c-mode) . (lambda ()
(add-hook 'before-save-hook 'lsp-format-buffer nil t))))
COMMENT Ruby
(use-package ruby-mode
:hook
(ruby-mode . lsp)
(ruby-mode . electric-pair-mode)
(ruby-mode . (lambda ()
(add-hook 'before-save-hook 'lsp-format-buffer nil t))))
python
(use-package elpy
:ensure t
:defer t
:bind ([remap lsp-find-definition] . elpy-goto-definition)
:config
(setq elpy-modules (remove 'elpy-module-highlight-indentation elpy-modules))
:init
;(advice-add 'python-mode :before 'elpy-enable)
(elpy-enable))
(setq python-interpreter "~/.python/venv/bin/python")
(setq python-shell-interpreter "~/.python/venv/bin/python")
LaTeX
AucTex
;; latexmk
(use-package magic-latex-buffer
:custom (magic-latex-buffer 1)
:defer t)
(use-package auctex-latexmk
:defer t)
;; company
(use-package company-math
:after company)
(use-package company-auctex
:after company)
(use-package company-reftex
:after company)
;; use cdlatex
(use-package cdlatex
:defer t)
;; https://gist.github.com/saevarb/367d3266b3f302ecc896
;; https://piotr.is/2010/emacs-as-the-ultimate-latex-editor/
(use-package latex
:straight auctex
:defer t
:custom
(cdlatex-simplify-sub-super-scripts nil)
(reftex-default-bibliography
'("~/Documents/refs.bib"))
(bibtex-dialect 'biblatex)
:mode
("\\.tex\\'" . latex-mode)
;; also see evil-define-key in :config
:bind (:map LaTeX-mode-map
("TAB" . cdlatex-tab)
("'" . cdlatex-math-modify)
("C-c C-e" . cdlatex-environment))
:hook
(LaTeX-mode . flyspell-mode)
(LaTeX-mode . flycheck-mode)
(LaTeX-mode . turn-on-reftex)
(LaTeX-mode . auto-fill-mode)
(LaTeX-mode . format-all-mode)
(LaTeX-mode . TeX-source-correlate-mode)
(LaTeX-mode . try/latex-mode-setup)
(LaTeX-mode . turn-on-cdlatex)
(LaTeX-mode . origami-mode)
;; (LaTeX-mode . TeX-fold-mode)
(LaTeX-mode . lsp)
;; (LaTeX-mode . olivetti-mode);; already set as a text-mode-hook
;; (LaTeX-mode . TeX-PDF-mode) ;; what does it do?
;; (LaTeX-mode . company-mode) ;; already enabled globaly
;; (LaTeX-mode . xenops-mode) ;; svgs too lagy :(
;; (LaTeX-mode . flycheck-mode);; already enabled with lsp
;; (LaTeX-mode . LaTeX-math-mode)
:config
;; pressing "$" while selecting text will cycle between \(\) and \[\] environment
;; where does \[\] come from? I have no clue!
;; I only defined \(\) lol
(setq TeX-electric-math (quote ("\\(" . "\\)")))
(evil-define-key 'visual 'LaTeX-mode-map
"$" 'TeX-insert-dollar
"'" 'cdlatex-math-modify)
;; (setq TeX-auto-save t)
(setq TeX-parse-self t)
(setq-default TeX-master nil)
(setq-default TeX-command-default "LatexMK")
(setq TeX-save-query nil)
;; this is becuase i set $out_dir = '/tmp/tex' in `.latexmkrc`
;; and I want to enable forward synctex. don't use it if you don't do like me...
(setq-default TeX-output-dir "/tmp/tex")
(setq reftex-plug-into-AUCTeX t)
;; ;; pdftools
;; ;; https://emacs.stackexchange.com/questions/21755/use-pdfview-as-default-auctex-pdf-viewer#21764
(setq TeX-view-program-selection '((output-pdf "Zathura"))
;; TeX-view-program-list '(("PDF Tools" TeX-pdf-tools-sync-view))
TeX-source-correlate-start-server t) ;; not sure if last line is neccessary
;; (add-to-list 'TeX-view-program-selection '(output-pdf "Zathura"))
;; clean intermdiate tex crap
(add-to-list 'LaTeX-clean-intermediate-suffixes '"-figure[0-9]*\\.\\(pdf\\|md5\\|log\\|dpth\\|dep\\|run\\.xml\\)")
(add-to-list 'LaTeX-clean-intermediate-suffixes '".auxlock")
; (eval-after-load 'latex
; `(dolist (face '((font-latex-sectioning-0-face . 3.0) ; \part
; (font-latex-sectioning-1-face . 2.5) ; \chapter
; (font-latex-sectioning-2-face . 2.0) ; \section
; (font-latex-sectioning-3-face . 1.5) ; \subsection
; (font-latex-sectioning-4-face . 1.5))) ; \subsubsection
; (set-face-attribute (car face) nil :font my/ui/varfont :weight 'bold :height (cdr face))))
;; to have the buffer refresh after compilation,
;; very important so that PDFView refesh itself after comilation
;; (add-hook 'TeX-after-compilation-finished-functions
;; #'TeX-revert-document-buffer)
;; latexmk
(require 'auctex-latexmk)
(auctex-latexmk-setup)
(setq auctex-latexmk-inherit-TeX-PDF-mode t)
)
Custom functions
(defun try/latex-mode-setup ()
(require 'company-reftex)
(turn-on-reftex)
(require 'company-auctex)
(require 'company-math)
(setq-local company-backends
(append '((company-reftex-labels company-reftex-citations)
(company-math-symbols-unicode company-math-symbols-latex company-latex-commands)
(company-auctex-macros company-auctex-symbols company-auctex-environments)
company-ispell)
company-backends)))
Insert from clip Quickly insert hand-drawn figures in a LaTeX document in Emacs
(defvar latex/insert-image-format "\\begin{center}\\includegraphics[width=\\linewidth]{%s}\\end{center}")
(defvar latex/insert-figure-format
" \\begin{figure}[h]
\\centering
\\includegraphics[width=\\linewidth]{%s}
\\caption{\\label{fig:TODO} TODO}
\\end{figure}
\\FloatBarrier")
(defun latex/insert-image-from-clipboard ()
(interactive)
(let*
;; Ask for a filename
((image-name (read-string "image-name: "))
;; This is getting uply...
(image-file-location (concat "\"" (expand-file-name (concat (TeX-master-directory) "img/" image-name ".png" )) "\"")))
;; Make the "img" directory if it does not exist
(make-directory (concat (TeX-master-directory) "img") t)
;; Copy the image in clipboard to "img/" directory
(shell-command (concat "xclip -selection clipboard -t image/png -o > " image-file-location))
;; Insert the latex snippet to include the figure
(insert (format latex/insert-image-format (concat "img/" (file-name-nondirectory image-file-location) )))))
(defun latex/insert-figure-from-clipboard ()
(interactive)
(let*
;; Ask for a filename
((image-name (read-string "image-name: "))
;; This is getting uply...
(image-file-location (concat "\"" (expand-file-name (concat (TeX-master-directory) "img/" image-name ".png" )) "\"")))
;; Make the "img" directory if it does not exist
(make-directory (concat (TeX-master-directory) "img") t)
;; Copy the image in clipboard to "img/" directory
(message (concat "xclip -selection clipboard -t image/png -o > " image-file-location))
(shell-command (concat "xclip -selection clipboard -t image/png -o > " image-file-location))
;; Insert the latex snippet to include the figure
(insert (format latex/insert-figure-format (concat "img/" (file-name-nondirectory (concat image-name ".png")))))))
Folding
(use-package outshine ;
:defer t
:config
(setq LaTeX-section-list '(
("part" 0)
("chapter" 1)
("section" 2)
("subsection" 3)
("subsubsection" 4)
("paragraph" 5)
("subparagraph" 6)
("begin" 7)))
(add-hook 'LaTeX-mode-hook #'(lambda ()
(outshine-mode 1)
(setq outline-level #'LaTeX-outline-level)
(setq outline-regexp (LaTeX-outline-regexp t))
(setq outline-heading-alist
(mapcar (lambda (x)
(cons (concat "\\" (nth 0 x)) (nth 1 x)))
LaTeX-section-list)))))
(general-define-key
:states '(normal visual)
:keymaps 'LaTeX-mode-map
"TAB" '(outshine-cycle :which-key "outshine-cycle"))
ivy bibtex
(use-package ivy-bibtex
:defer t
:custom
(bibtex-completion-bibliography
'("~/Documents/refs.bib"))
(bibtex-completion-library-path '("~/papers"))
(bibtex-completion-cite-prompt-for-optional-arguments nil)
(bibtex-completion-cite-default-as-initial-input t)
)
(use-package lsp-latex
:hook ((tex-mode . lsp)
(latex-mode . lsp)))
COMMENT Ledger
Unused, switched to hledger
(use-package ledger-mode
;; :mode ("\\.dat\\'" "\\.ledger\\'")
:mode ("\\.ledger\\'")
:bind (:map ledger-mode-map
("C-x C-s" . my/ledger-save))
:custom (ledger-clear-whole-transactions t)
:hook ((ledger-mode . flycheck-mode)
(ledger-mode . flyspell-mode))
:config
;(add-hook 'ledger-mode-hook (lambda () (add-hook 'before-save-hook 'ledger-mode-clean-buffer)))
)
(use-package flycheck-ledger :after ledger-mode)
hledger
(use-package hledger-mode
:mode ("\\.journal\\'" "\\.hledger\\'")
;:commands hledger-enable-reporting
:preface
(defun hledger/next-entry ()
"Move to next entry and pulse."
(interactive)
(hledger-next-or-new-entry)
(hledger-pulse-momentary-current-entry))
(defface hledger-warning-face
'((((background dark))
:background "Red" :foreground "White")
(((background light))
:background "Red" :foreground "White")
(t :inverse-video t))
"Face for warning"
:group 'hledger)
(defun hledger/prev-entry ()
"Move to last entry and pulse."
(interactive)
(hledger-backward-entry)
(hledger-pulse-momentary-current-entry))
:bind (("C-c j" . hledger-run-command)
:map hledger-mode-map
("C-c e" . hledger-jentry)
("M-p" . hledger/prev-entry)
("M-n" . hledger/next-entry))
:init
(setq hledger-jfile (expand-file-name "~/Documents/ledger/data_2024.hledger")
hledger-currency-string "SAR"
;hledger-email-secrets-file (expand-file-name "secrets.el" emacs-assets-directory)
)
;; Expanded account balances in the overall monthly report are
;; mostly noise for me and do not convey any meaningful information.
(setq hledger-show-expanded-report nil)
(when (boundp 'my-hledger-service-fetch-url)
(setq hledger-service-fetch-url
my-hledger-service-fetch-url))
:config
(require 'hledger-input)
(add-hook 'hledger-view-mode-hook #'hl-line-mode)
;(add-hook 'hledger-view-mode-hook #'center-text-for-reading)
(add-hook 'hledger-view-mode-hook
(lambda ()
(run-with-timer 1
nil
(lambda ()
(when (equal hledger-last-run-command
"balancesheet")
;; highlight frequently changing accounts
(highlight-regexp "^.*\\(savings\\|cash\\).*$")
(highlight-regexp "^.*credit-card.*$"
'hledger-warning-face))))))
(add-hook 'hledger-mode-hook
(lambda ()
(make-local-variable 'company-backends)
(add-to-list 'company-backends 'hledger-company))))
(use-package flycheck-hledger
:after (flycheck hledger-mode)
:demand t)
COMMENT Verilog
(setq verilog-linter "verilator --lint-only")
(setq verilog-auto-newline nil
verilog-auto-arg-sort t
verilog-case-fold nil)
; (setq verilog-indent-level 1)
(add-hook 'verilog-mode-hook 'electric-pair-mode)
(add-hook 'verilog-mode-hook 'lsp)
(add-hook 'verilog-mode-hook 'flycheck-mode)
(add-hook 'verilog-mode-hook (lambda ()
(add-hook 'before-save-hook 'verilog-indent-buffer nil t)))
(with-eval-after-load 'lsp-mode
(add-to-list 'lsp-language-id-configuration '(verilog-mode . "verilog"))
(lsp-register-client
(make-lsp-client :new-connection (lsp-stdio-connection "verible-verilog-ls")
:major-modes '(verilog-mode)
:server-id 'verible-ls)))
SystemVerilog
(use-package verilog-ext
:hook ((verilog-mode . verilog-ext-mode)
(verilog-ext-mode . electric-pair-local-mode)
(verilog-ext-mode . lsp-mode))
:init
;; Can also be set through `M-x RET customize-group RET verilog-ext':
;; Comment out/remove the ones you do not need
(setq verilog-ext-feature-list
'(font-lock
xref
capf
hierarchy
eglot
lsp
;lsp-bridge
;lspce
flycheck
beautify
navigation
template
formatter
compilation
imenu
which-func
hideshow
typedefs
time-stamp
block-end-comments
ports))
:config
(verilog-ext-mode-setup))
VHDL
(setq lsp-vhdl-server 'vhdl-ls)
(add-hook 'vhdl-mode-hook 'vhdl-electric-mode)
(add-hook 'vhdl-mode-hook 'flycheck-mode)
(add-hook 'vhdl-mode-hook (lambda ()
(add-hook 'before-save-hook 'vhdl-beautify-buffer nil t)))
Bash
(use-package flymake-shellcheck
:commands flymake-shellcheck-load
:init
(add-hook 'sh-mode-hook 'flymake-shellcheck-load))
Nix(OS)
(use-package nix-mode
:hook (nix-mode . (lambda ()
;(add-hook 'before-save-hook 'nix-mode-format nil t)))); doesn't require nixfmt
(add-hook 'before-save-hook 'nix-format-buffer nil t))))
Tramp
; moved to Git
; https://emacs.stackexchange.com/questions/16489/tramp-is-unbearably-slow-osx-ssh
; (setq vc-handled-backends '(Git))
(setq tramp-backup-directory-alist backup-directory-alist)
(setq vc-ignore-dir-regexp
(format "\\(%s\\)\\|\\(%s\\)"
vc-ignore-dir-regexp
tramp-file-name-regexp))
(setq vc-handled-backends '(Git))
;https://libredd.it/r/emacs/comments/320cvb/projectile_slows_tramp_mode_to_a_crawl_is_there_a/
(add-hook 'find-file-hook
(lambda ()
(when (file-remote-p default-directory)
(setq-local projectile-mode-line "Projectile"
vc-handled-backends '()))))
Misc
Restart Emacs
(use-package restart-emacs)
Vterm
(use-package vterm
:commands vterm
:bind (:map vterm-mode-map
("C-t" . vterm-toggle))
:config
;;Toggle vterm
(evil-define-key '(normal visual insert) 'vterm-mode-map (kbd "C-t") 'vterm-toggle)
:custom
; claimed to be faster: https://teddit.net/r/emacs/comments/tpey9g/making_vterm_snappy_by_setting_vtermtimerdelay_to/
(vterm-timer-delay nil)
:ensure t)
(use-package vterm-toggle)
Server
(unless (server-running-p) (server-start))
(add-hook 'server-after-make-frame-hook '(lambda () (set-cursor-color "#FFFFFF")))
COMMENT ranger
(use-package ranger
:defer t
:config (ranger-override-dired-mode t))
Ligatures
(let ((ligatures `((?- . ,(regexp-opt '("-|" "-~" "---" "-<<" "-<" "--" "->" "->>" "-->")))
(?/ . ,(regexp-opt '("/**" "/*" "///" "/=" "/==" "/>" "//")))
;; (?* . ,(regexp-opt '("*>" "***" "*/")))
(?* . ,(regexp-opt '("*>" "*/")))
(?< . ,(regexp-opt '("<-" "<<-" "<=>" "<=" "<|" "<||" "<|||::=" "<|>" "<:" "<>" "<-<"
"<<<" "<==" "<<=" "<=<" "<==>" "<-|" "<<" "<~>" "<=|" "<~~" "<~"
"<$>" "<$" "<+>" "<+" "</>" "</" "<*" "<*>" "<->" "<!--")))
(?: . ,(regexp-opt '(":>" ":<" ":::" "::" ":?" ":?>" ":=")))
(?= . ,(regexp-opt '("=>>" "==>" "=/=" "=!=" "=>" "===" "=:=" "==")))
(?! . ,(regexp-opt '("!==" "!!" "!=")))
(?> . ,(regexp-opt '(">]" ">:" ">>-" ">>=" ">=>" ">>>" ">-" ">=")))
(?& . ,(regexp-opt '("&&&" "&&")))
(?| . ,(regexp-opt '("|||>" "||>" "|>" "|]" "|}" "|=>" "|->" "|=" "||-" "|-" "||=" "||")))
(?. . ,(regexp-opt '(".." ".?" ".=" ".-" "..<" "...")))
(?+ . ,(regexp-opt '("+++" "+>" "++")))
(?\[ . ,(regexp-opt '("[||]" "[<" "[|")))
(?\{ . ,(regexp-opt '("{|")))
(?\? . ,(regexp-opt '("??" "?." "?=" "?:")))
(?# . ,(regexp-opt '("####" "###" "#[" "#{" "#=" "#!" "#:" "#_(" "#_" "#?" "#(" "##")))
(?\; . ,(regexp-opt '(";;")))
(?_ . ,(regexp-opt '("_|_" "__")))
(?\\ . ,(regexp-opt '("\\" "\\/")))
(?~ . ,(regexp-opt '("~~" "~~>" "~>" "~=" "~-" "~@")))
(?$ . ,(regexp-opt '("$>")))
(?^ . ,(regexp-opt '("^=")))
(?\] . ,(regexp-opt '("]#"))))))
(dolist (char-regexp ligatures)
(set-char-table-range composition-function-table (car char-regexp)
`([,(cdr char-regexp) 0 font-shape-gstring]))))
Key freq
(use-package keyfreq
:defer 10
:custom
(keyfreq-mode 1)
(keyfreq-autosave-mode 1))
Polybar
org clock
(defun my/polybar/org-clock ()
"Gets polybar formatted message"
(let ((message nil)
(icon nil)
(icon-color nil))
(if (org-clock-is-active)
(setq message (substring-no-properties (org-clock-get-clock-string))
icon ""; there is an icon here, in case it isn't rendered...
icon-color "#BA68C8")
(setq message ""
icon ""; "";; I want it to be empty
icon-color "#FDD835"))
(concat "%{F" icon-color "}" icon "%{F-}" message)))
Gemini
(use-package elpher
:defer t
:hook (elpher-mode . olivetti-mode) )
Easy hugo
(use-package easy-hugo
:init
(easy-hugo-enable-menu)
(setq easy-hugo-basedir "~/code/sites/ammar.engineer/")
(setq easy-hugo-postdir "content/posts")
(setq easy-hugo-url "https://ammar.engineer")
;; (setq easy-hugo-sshdomain "blogdomain")
;; (setq easy-hugo-root "")
(setq easy-hugo-previewtime "300"))
;:bind
;("C-c C-e" . easy-hugo))
Elfeed org
;; (setq rmh-elfeed-org-files (list "~/Documents/private.el/elfeed.org"))
Elfeed-org
(use-package elfeed-org
:after elfeed
:config (elfeed-org))
Elfeed Dashboard
(use-package elfeed-dashboard
:commands elfeed-dashboard
:config
;; (setq elfeed-dashboard-file "~/Documents/private.el/elfeed-dashboard.org")
;; update feed counts on elfeed-quit
(advice-add 'elfeed-search-quit-window :after #'elfeed-dashboard-update-links)
(evil-set-initial-state 'elfeed-dashboard-mode 'emacs)
:hook (elfeed-dashboard-mode . (lambda () (variable-pitch-mode -1))))
Helper Functions
From: https://old.reddit.com/r/emacs/comments/hbdlv8/elfeed_mpv_youtube/fv9yhb2/
(defun my/elfeed/visit-entry-dwim (&optional arg)
(interactive "P")
(if arg
(elfeed-search-browse-url)
(-let [entry (if (eq major-mode 'elfeed-show-mode) elfeed-show-entry (elfeed-search-selected :single))]
(if (s-matches? (rx "https://www.youtube.com/watch" (1+ any))
(elfeed-entry-link entry))
(let* ((quality (completing-read "Max height resolution (0 for unlimited): " '("0" "480" "720" "1080")))
(format (if (= 0 (string-to-number quality)) "" (format "--ytdl-format=[height<=?%s]" quality))))
(message "Opening %s with height ≤ %s with mpv..."
(elfeed-entry-link entry) quality)
(elfeed-untag entry 'unread)
(start-process "elfeed-mpv" nil "mpv" format (elfeed-entry-link entry))
(elfeed-search-update :force))
(if (eq major-mode 'elfeed-search-mode)
(elfeed-search-browse-url)
(elfeed-show-visit))))))
I wrote that, neat isn't it? :P
(defun my/elfeed/toggle-search-tag (tag)
(interactive)
;example: tag = "unread"
(elfeed-search-set-filter
;s-contains matches agains "+unread"; i.e (concat "+" tag) => "+unread"
(if (s-contains? (concat "+" tag) elfeed-search-filter)
;regex will be " ?\\+unread"
(s-replace-regexp (concat " ?\\+" tag) "" elfeed-search-filter)
;concat will be " +unread"
(concat elfeed-search-filter (concat " +" tag)))))
(defun my/elfeed/toggle-search-unread () (interactive) (my/elfeed/toggle-search-tag "unread" ))
(defun my/elfeed/toggle-search-to_read () (interactive) (my/elfeed/toggle-search-tag "to_read"))
Visual, binds, directory
(use-package elfeed
:defer t
:config
;; (defun my/elfeed/visual ()
;; (interactive)
;; (set-face-attribute 'variable-pitch (selected-frame) :font (font-spec :family my/ui/varfont :size 13))
;; (setq visual-fill-column-width 110
;; visual-fill-column-center-text t
;; fill-column 90)
;; (visual-fill-column-mode 1)
;; (visual-line-mode 1))
(elfeed-org)
(evil-define-key 'normal elfeed-search-mode-map
"O" 'my/elfeed/visit-entry-dwim
;"tr" 'my/elfeed/toggle-read
"tr" 'my/elfeed/toggle-search-unread
"tt" 'my/elfeed/toggle-search-to_read)
:custom
(elfeed-db-directory "~/.local/share/elfeed")
:hook ;(elfeed-show-mode . my/elfeed/visual)
(elfeed-show-mode . olivetti-mode))
IRC
COMMENT unsused 'erc'
(use-package erc
:defer t
:custom
(erc-autojoin-timing 'ident)
(erc-fill-function 'erc-fill-static)
(erc-fill-static-center 25)
(erc-hide-list '("JOIN" "PART" "QUIT"))
(erc-lurker-hide-list '("JOIN" "PART" "QUIT"))
(erc-lurker-threshold-time 43200)
(erc-prompt-for-nickserv-password nil)
(erc-server-reconnect-attempts 5)
(erc-server-reconnect-timeout 3)
(erc-track-exclude-types '("JOIN" "MODE" "NICK" "PART" "QUIT"
"324" "329" "332" "333" "353" "477"))
:config
;; (add-to-list 'erc-modules 'notifications)
(add-to-list 'erc-modules 'spelling)
(erc-services-mode 1)
(erc-update-modules))
(use-package erc-hl-nicks
:after erc)
(use-package erc-image
:after erc)
(use-package znc
:defer t
:config
(setq znc-servers
`(("flinner.my.to" 6697 t ((main ,my/secret/znc/flinner.my.to/username
,my/secret/znc/flinner.my.to/secret))))))
(defun my/znc-all ()
"Connect to all ZNC networks. Accept incoming self signed certificates."
(interactive)
(let ((tls-checktrust nil)
(gnutls-verify-error nil))
(znc-all)))
circe
Secrets :^)
;; Doesn't tangle!
;; loaded in use-package (block below)
(load "~/Nextcloud/Documents/Passwords/circe-networks.el")
; example content
(add-to-list 'circe-networks `("chat.name/username" :host "irc.example.com" :port 69
:tls t
:nick "nicky"
:pass ,(secrets-get-secret "local" "hehe :^)")
:user "username"))
Helper Functions!
(defun my/circe/clear ()
"Clear the buffer"
(interactive)
(circe-command-CLEAR))
(defun my/circe/build-helm-sources (server-buf)
"Builds helm candidates for a single server"
(helm-build-sync-source (buffer-name server-buf)
:candidates
(cons (cons (buffer-name server-buf) server-buf)
(cl-loop for buf in (with-current-buffer server-buf (circe-server-chat-buffers))
collect (cons
(let ((buf-name (buffer-name buf)))
(concat buf-name
; add " ***" if buffer has new messagse
(if (member buf-name tracking-buffers) " ***" "")))
buf)))
:action (list (cons "Switch to circe" #'switch-to-buffer)
(cons "Kill buffer" #'kill-buffer))))
(defun my/circe/helm-buffers ()
"Switch between circe buffers using helm"
(interactive)
(helm :sources
(cl-loop for server-buf in (circe-server-buffers)
collect (my/circe/build-helm-sources server-buf))
:buffer "*helm circe*"))
Setup
(use-package circe
:defer t
:preface
:config
(enable-lui-track)
;(add-to-list 'circe-networks `())
;; adding to list happens here!
(load "~/Documents/Passwords/circe-networks.el")
(setq circe-color-nicks-min-constrast-ratio 4.5
circe-color-nicks-everywhere t)
:hook (circe-channel-mode . enable-circe-color-nicks)
(circe-channel-mode . (lambda () (smooth-scrolling-mode -1)))
:custom
(circe-format-say "{nick:-16s} {body}")
;; :bind(("C-l" . my/circe/clear))
:bind (:map circe-mode-map
([remap counsel-projectile-find-file] . my/circe/helm-buffers))
)
(setq
lui-time-stamp-position 'right-margin
lui-flyspell-p t
lui-fill-type nil
;Display your own nickname instead of >>> in the channel buffers when you're talking.
circe-format-self-say "{nick:-15s} {body}"
)
(add-hook 'lui-mode-hook 'my-lui-setup)
(defun my-lui-setup ()
(setf (cdr (assoc 'continuation fringe-indicator-alist)) nil)
(olivetti-mode 1)
(setq
fringes-outside-margins t
right-margin-width 0
word-wrap t
wrap-prefix " "))
znc stuff
(defun circe-command-ZNC (what)
"Send a message to ZNC incorporated by user '*status'."
(circe-command-MSG "*status" what))
Email (mu4e)
Package
(use-package mu4e ;
;; this line is for nixos
;; until here
;;:ensure-system-package mu
:init
(defun mu4e--main-action-str (str &optional func-or-shortcut))
(defun evil-collection-mu4e-update-main-view@override())
(advice-add 'evil-collection-mu4e-update-main-view :override #'evil-collection-mu4e-update-main-view@override)
:commands (mu4e)
:bind (:map mu4e-main-mode-map
([remap revert-buffer] . mu4e-update-index))
:custom
(mu4e-change-filenames-when-moving t)
(mu4e-html2text-command "iconv -c -t utf-8 | pandoc -f html -t plain")
(mu4e-attachment-dir "~/Downloads")
(mu4e-compose-signature-auto-include t)
(mu4e-get-mail-command "mbsync -a")
(mu4e-update-interval 300)
(mu4e-use-fancy-chars t)
(mu4e-view-show-addresses t)
(mu4e-view-show-images t)
:hook
(mu4e-view-mode . visual-line-mode)
(mu4e-view-mode . olivetti-mode)
(mu4e-main-mode . olivetti-mode)
(mu4e-compose-mode . flyspell-mode)
(mu4e-context-changed . mu4e-update-index))
Contexts
;; assumed Maildir layout
;; ~/Maildir/Account0/{Inbox,Sent,Trash}
;; ~/Maildir/Account1/{Inbox,Sent,Trash}
;; where Account0 is context name
(with-eval-after-load 'mu4e
(defun my-make-mu4e-context (context-name full-name mail-address signature)
"Return a mu4e context named CONTEXT-NAME with :match-func matching
folder name CONTEXT-NAME in Maildir. The context's `user-mail-address',
`user-full-name' and `mu4e-compose-signature' is set to MAIL-ADDRESS
FULL-NAME and SIGNATURE respectively.
Special folders are set to context specific folders."
(let ((dir-name (concat "/" context-name))
(context-filter (concat " maildir:/" context-name "/")))
(make-mu4e-context
:name context-name
;; we match based on the maildir of the message
;; this matches maildir /Arkham and its sub-directories
:match-func
`(lambda (msg)
(when msg
(string-match-p
,(concat "^" dir-name)
(mu4e-message-field msg :maildir))))
:vars
`(
(mu4e-bookmarks .
,`(
;(:name "All Unread messages" :query ,"flag:unread AND NOT flag:trashed AND NOT flag:list" :key ?a)
(:name "All Unread messages" :query ,"flag:unread AND NOT flag:trashed" :key ?a)
(:name "Unread messages" :query ,(concat "flag:unread AND NOT flag:trashed" context-filter) :key ?u)
(:name "Inbox" :query ,(concat "maildir:/Inbox/" context-filter) :key ?i)
(:name "Today's messages" :query ,(concat "date:today..now" context-filter) :key ?t)
(:name "Last 7 days" :query ,(concat "date:7d..now" context-filter) :hide-unread t :key ?w)
(:name "Messages with attachments" :query ,(concat "mime:application/*" context-filter) :key ?p)
(:name "Lists" :query ,(concat "flag:list" context-filter) :key ?b)
)
)
(mu4e-maildir-shortcuts . ,`(
(:maildir ,(concat dir-name "/Inbox") :key ?i)
(:maildir ,(concat dir-name "/Sent") :key ?s)
(:maildir ,(concat dir-name "/Archive") :key ?a)
(:maildir ,(concat dir-name "/Drafts") :key ?d)
(:maildir ,(concat dir-name "/Junk") :key ?j)
(:maildir ,(concat dir-name "/Trash") :key ?t)
))
(mu4e-sent-messages-behavior . 'delete)
(user-mail-address . ,mail-address)
;; (mu4e-maildir . ,(concat "~/.mail" dir-name))
(user-full-name . ,full-name)
(mu4e-sent-folder . ,(concat dir-name "/Sent"))
(mu4e-drafts-folder . ,(concat dir-name "/Drafts"))
(mu4e-trash-folder . ,(concat dir-name "/Trash"))
(mu4e-refile-folder . ,(concat dir-name "/Archive"))
(mu4e-compose-signature . ,signature))))))
;;Fixing duplicate UID errors when using mbsync and mu4e
Email List here!
;; This is a sample, it doesn't get included in init.el
;; I put mine at location specified in the next code block
;; any number of email can be used ofc
(with-eval-after-load 'mu4e
(setq mu4e-contexts `(
,(my-make-mu4e-context
"maildir-context" "Full Name"
"Email Address" "Signature")
,(my-make-mu4e-context
"maildir-context2" "Full Name2"
"Email Address2" "Signature2")
)))
or don't include in git source :)
(with-eval-after-load 'mu4e
(load "~/Documents/Passwords/mu4e-context.el"))
Other fixes
see: djcb/mu#1136 Shouldn't set flag T after moving to trash. Deleting should only move to trash, not delete entirely from the server
(with-eval-after-load 'mu4e
(setf (alist-get 'trash mu4e-marks)
(list :char '("d" . "▼")
:prompt "dtrash"
:dyn-target (lambda (target msg)
(mu4e-get-trash-folder msg))
:action (lambda (docid msg target)
;; Here's the main difference to the regular trash mark,
;; no +T before -N so the message is not marked as
;; IMAP-deleted:
(mu4e--server-move docid (mu4e--mark-check-target target) "-N")))))
(setq mu4e-completing-read-function 'completing-read);; Use Helm
(setq message-kill-buffer-on-exit t) ;; Why would I want to leave my message open after I've sent it?
Breaking change betweeen mu4e-alert
and mu
:(
(I don't use mu4e-alert
anymore, but will keep this cuz y not?)
(defvaralias 'mu4e~context-current 'mu4e--context-current)
I prefer text/plain, over everything >:)
(with-eval-after-load "mm-decode"
(add-to-list 'mm-discouraged-alternatives "text/richtext")
(add-to-list 'mm-discouraged-alternatives "text/html"))
djcb/mu#2665 {mu4e rfe} Switch between "Reply" and "Wide Reply"
Supersede rather than reply to my own emails. Only ask whether to reply to all if there are more than one recipients
(with-eval-after-load 'mu4e
(defun mu4e-supersede-or-compose-reply-ask-wide ()
"Supersede own messages or ask whether to reply-to-all."
(interactive)
(if (mu4e-message-contact-field-matches-me (mu4e-message-at-point) :from)
(mu4e-compose-supersede)
(let ((tos (length (mu4e-message-field-at-point :to)))
(ccs (length (mu4e-message-field-at-point :cc))))
(mu4e-compose-reply
(and (> (+ tos ccs) 1)
(yes-or-no-p "Reply to all?")))))
(evil-define-key 'normal mu4e-headers-mode-map "R" 'mu4e-supersede-or-compose-reply-ask-wide)
(evil-define-key 'normal mu4e-view-mode-map "R" 'mu4e-supersede-or-compose-reply-ask-wide)))
Send email (msmtp)
(setq sendmail-program (executable-find "msmtp") ;"/usr/bin/msmtp"
message-sendmail-f-is-evil t
message-sendmail-extra-arguments '("--read-envelope-from")
send-mail-function 'smtpmail-send-it
message-send-mail-function 'message-send-mail-with-sendmail)
Telega
(use-package telega
:init
(defun my/telega/olivetti () (setq-local olivetti-body-width 80))
(defun my/telega/company-backends ()
(setq-local company-backends
(append '(telega-company-username telega-company-botcmd telega-company-emoji)
company-backends)))
:hook (telega-chat-mode . olivetti-mode)
(telega-chat-mode . my/telega/olivetti)
(telega-chat-mode . my/telega/company-backends)
;; installed telegram-tdlib from AUR
:config
(telega-mode-line-mode)
;(telega-appindicator-mode)
;(telega-notifications-mode)
:custom (telega-server-libs-prefix "/usr")
(telega-chat-bidi-display-reordering 'right-to-left)
(telega-sticker-size '(10 . 24))
(telega-emoji-use-images nil)
(telega-symbol-checkmark "🄌")
(telega-symbol-heavy-checkmark "⬤")
)
COMMENT Matrix Ement
(use-package ement
:straight (ement
:type git
:host github
:repo "alphapapa/ement.el"))
;; :after org-roam ;; or :after org
;; :hook (org-roam . org-roam-ui-mode)
;; :config)
Buffers and Windows
COMMENT Workspaces (Persepective
(use-package persp-mode
:defer t
:config
(setq persp-keymap-prefix (kbd "SPC <tab>"))
Startpage
(use-package dashboard
:after solaire-mode
:init
(dashboard-setup-startup-hook)
:config
(setq dashboard-startup-banner "~/Downloads/haskell-rec.png")
;; Value can be
;; 'official which displays the official emacs logo
;; 'logo which displays an alternative emacs logo
;; 1, 2 or 3 which displays one of the text banners
;; "path/to/your/image.png" or "path/to/your/text.txt" which
;; displays whatever image/text you would prefer
;; Content is not centered by default. To center, set
(setq dashboard-center-content t)
(setq dashboard-set-heading-icons t)
(setq dashboard-set-file-icons t)
(setq dashboard-items '((recents . 5)
(bookmarks . 5)
(projects . 5)
(agenda . 5)))
(setq dashboard-set-init-info t)
(setq dashboard-projects-switch-function 'counsel-projectile-switch-project-by-name))