mirror of
https://github.com/Foltik/dotfiles
synced 2024-11-22 03:54:16 -05:00
28 May 2022 19:10:46
This commit is contained in:
parent
95f20d227d
commit
7f3c027a8d
580
.doom.d/config.el
Normal file
580
.doom.d/config.el
Normal file
@ -0,0 +1,580 @@
|
||||
(doom-load-envvars-file (concat doom-private-dir "env.el"))
|
||||
|
||||
(setq doom-theme 'doom-catppuccin)
|
||||
|
||||
(setq doom-font (font-spec :family "monospace" :size 13)
|
||||
doom-big-font (font-spec :family "monospace" :size 13)
|
||||
doom-variable-pitch-font (font-spec :family "sans-serif" :size 13))
|
||||
|
||||
(set-frame-parameter (selected-frame) 'alpha-background 85)
|
||||
(add-to-list 'default-frame-alist '(alpha-background . 85))
|
||||
|
||||
(setq evil-want-fine-undo t)
|
||||
|
||||
(defun my/line-numbers-relative ()
|
||||
(setq display-line-numbers 'relative))
|
||||
(defun my/line-numbers-absolute ()
|
||||
(setq display-line-numbers 'absolute))
|
||||
(add-hook 'evil-insert-state-entry-hook #'my/line-numbers-absolute)
|
||||
(add-hook 'evil-insert-state-exit-hook #'my/line-numbers-relative)
|
||||
|
||||
(use-package copilot
|
||||
:commands (copilot-complete))
|
||||
|
||||
(defun my/copilot-complete ()
|
||||
(interactive)
|
||||
(copilot-complete)
|
||||
(my/hydra-copilot/body)
|
||||
(copilot-clear-overlay))
|
||||
|
||||
(defhydra my/hydra-copilot ()
|
||||
"Copilot"
|
||||
("<return>" copilot-accept-completion "Accept" :color blue )
|
||||
("<tab>" copilot-next-completion "Next" )
|
||||
("<backtab>" copilot-previous-completion "Prev")
|
||||
("<escape>" copilot-clear-overlay "Cancel" :color blue))
|
||||
|
||||
(setq doom-scratch-initial-major-mode 'lisp-interaction-mode)
|
||||
|
||||
(map! :leader
|
||||
"b" nil
|
||||
"f" nil
|
||||
"h" nil
|
||||
"p" nil
|
||||
"t" nil)
|
||||
|
||||
(map! :map evil-org-mode-map
|
||||
:n "zc" nil)
|
||||
|
||||
(map!
|
||||
:desc "Increase font size" :ni "C-=" #'text-scale-increase
|
||||
:desc "Decrease font size" :ni "C--" #'text-scale-decrease)
|
||||
|
||||
(map!
|
||||
:desc "Copilot" :i "C-," #'my/copilot-complete)
|
||||
|
||||
|
||||
|
||||
(map! :map minibuffer-mode-map
|
||||
:desc "Next history" "C-j" #'next-history-element
|
||||
:desc "Prev history" "C-k" #'previous-history-element)
|
||||
|
||||
(map! :leader
|
||||
:desc "M-x" "x" #'counsel-M-x
|
||||
:desc "M-:" ";" #'pp-eval-expression)
|
||||
|
||||
(map! :leader
|
||||
:desc "Find file" "." #'counsel-find-file
|
||||
:desc "Find dir" ">" #'+default/dired
|
||||
|
||||
:desc "Find in project" "SPC" #'+ivy/projectile-find-file
|
||||
:desc "Find in project uncached" "C-SPC" #'my/projectile-find-file-nocache)
|
||||
|
||||
(defun my/projectile-find-file-nocache ()
|
||||
(interactive)
|
||||
(projectile-invalidate-cache nil)
|
||||
(+ivy/projectile-find-file))
|
||||
|
||||
(map! :leader
|
||||
:desc "Switch buffer" "," #'+vertico/switch-workspace-buffer
|
||||
:desc "Switch all buffers" ">" #'consult-buffer)
|
||||
|
||||
(map! :leader
|
||||
:desc "Search online" "/" #'counsel-search)
|
||||
|
||||
(map! :leader
|
||||
:prefix ("b" . "buffers")
|
||||
|
||||
:desc "Switch buffer" "b" #'consult-buffer
|
||||
:desc "ibuffer" "i" #'ibuffer
|
||||
|
||||
:desc "Kill buffer" "d" #'kill-current-buffer
|
||||
:desc "Kill all buffers" "D" #'doom/kill-all-buffers)
|
||||
|
||||
(map! :leader
|
||||
:prefix ("f" . "files")
|
||||
|
||||
:desc "Recent files" "r" #'consult-recent-file
|
||||
|
||||
:desc "Find file" "f" #'counsel-find-file
|
||||
:desc "Find file as root" "u" #'doom/sudo-find-file
|
||||
:desc "Find package" "p" #'counsel-find-library
|
||||
|
||||
:desc "Copy this file" "c" #'doom/copy-this-file
|
||||
:desc "Delete this file" "d" #'doom/delete-this-file
|
||||
:desc "Move this file" "m" #'doom/move-this-file
|
||||
:desc "Revert this file" "l" #'revert-buffer
|
||||
|
||||
:desc "Copy file path" "y" #'+default/yank-buffer-path
|
||||
:desc "Copy project file path" "Y" #'+default/yank-buffer-path-relative-to-project
|
||||
|
||||
:desc "Open scratch" "x" #'doom/open-scratch-buffer)
|
||||
|
||||
(map! :leader
|
||||
:prefix ("f s" . "snippets")
|
||||
:desc "New snippet" "n" #'yas-new-snippet
|
||||
:desc "Edit snippet" "e" #'yas-visit-snippet-file
|
||||
:desc "Browse docs" "?" #'my/yas-browse-docs)
|
||||
|
||||
(defun my/yas-browse-docs ()
|
||||
(interactive)
|
||||
(browse-url "https://joaotavora.github.io/yasnippet"))
|
||||
|
||||
(map! :leader
|
||||
:prefix ("f e" . "emacs")
|
||||
:desc "Find in config" "f" #'doom/find-file-in-private-config
|
||||
:desc "Reload config" "r" #'doom/reload
|
||||
|
||||
:desc "Edit config" "c" #'my/edit-config
|
||||
:desc "Edit packages" "p" #'my/edit-packages
|
||||
:desc "Edit env" "e" #'my/edit-env
|
||||
:desc "Edit init" "i" #'my/edit-init)
|
||||
|
||||
(defun my/edit-config ()
|
||||
(interactive)
|
||||
(find-file (concat doom-private-dir "config.org")))
|
||||
(defun my/edit-packages ()
|
||||
(interactive)
|
||||
(find-file (concat doom-private-dir "packages.el")))
|
||||
(defun my/edit-init ()
|
||||
(interactive)
|
||||
(find-file (concat doom-private-dir "init.el")))
|
||||
(defun my/edit-env ()
|
||||
(interactive)
|
||||
(find-file (concat doom-private-dir "env.el")))
|
||||
|
||||
(define-derived-mode org-config-mode org-mode "Org config mode")
|
||||
(add-to-list 'auto-mode-alist '("config\\.org" . org-config-mode))
|
||||
|
||||
(map! :leader
|
||||
:prefix ("h" . "help")
|
||||
|
||||
:desc "Apropos" "/" #'consult-apropos
|
||||
:desc "Apropos docs" "?" #'apropos-documentation
|
||||
|
||||
:desc "Help at point" "p" #'helpful-at-point
|
||||
:desc "Help info" "h" #'info
|
||||
:desc "Help for help" "H" #'help-for-help
|
||||
|
||||
:desc "Describe function" "f" #'counsel-describe-function
|
||||
:desc "Describe function key" "F" #'where-is
|
||||
:desc "Describe variable" "v" #'counsel-describe-variable
|
||||
:desc "Describe custom variable" "V" #'doom/help-custom-variable
|
||||
:desc "Describe command" "x" #'helpful-command
|
||||
:desc "Describe key" "k" #'describe-key-briefly
|
||||
:desc "Describe key fully" "K" #'describe-key
|
||||
:desc "Describe char" "'" #'describe-char
|
||||
:desc "Describe coding system" "\"" #'describe-coding-system
|
||||
:desc "Describe input method" "i" #'describe-input-method
|
||||
|
||||
:desc "Emacs manual" "e" #'info-emacs-manual
|
||||
:desc "ASCII table" "a" #'my/ascii-table
|
||||
|
||||
:desc "View messages" "e" #'view-echo-area-messages
|
||||
:desc "View keystrokes" "l" #'view-lossage)
|
||||
|
||||
(defface my/ascii-table-highlight-face
|
||||
'((t (:foreground "pink")))
|
||||
"Face for highlighting ASCII chars.")
|
||||
|
||||
(defun my/ascii-table ()
|
||||
"Display basic ASCII table (0 thru 128)."
|
||||
(interactive)
|
||||
(pop-to-buffer "*ASCII*")
|
||||
(erase-buffer)
|
||||
(setq buffer-read-only nil)
|
||||
(my/buffer-local-set-key "q" #'+popup/quit-window)
|
||||
(setq lower32 '("nul" "soh" "stx" "etx" "eot" "enq" "ack" "bel"
|
||||
"bs" "ht" "nl" "vt" "np" "cr" "so" "si"
|
||||
"dle" "dc1" "dc2" "dc3" "dc4" "nak" "syn" "etb"
|
||||
"can" "em" "sub" "esc" "fs" "gs" "rs" "us"))
|
||||
(save-excursion (let ((i -1))
|
||||
(insert " Hex Dec Char | Hex Dec Char | Hex Dec Char | Hex Dec Char\n")
|
||||
(insert " ---------------+-----------------+-----------------+----------------\n")
|
||||
(while (< i 31)
|
||||
(insert (format "%4x %4d %4s | %4x %4d %4s | %4x %4d %4s | %4x %4d %4s\n"
|
||||
(setq i (+ 1 i)) i (elt lower32 i)
|
||||
(setq i (+ 32 i)) i (single-key-description i)
|
||||
(setq i (+ 32 i)) i (single-key-description i)
|
||||
(setq i (+ 32 i)) i (single-key-description i)))
|
||||
(overlay-put (make-overlay (- (point) 4) (- (point) 1)) 'face 'my/ascii-table-highlight-face)
|
||||
(overlay-put (make-overlay (- (point) 22) (- (point) 19)) 'face 'my/ascii-table-highlight-face)
|
||||
(overlay-put (make-overlay (- (point) 40) (- (point) 37)) 'face 'my/ascii-table-highlight-face)
|
||||
(overlay-put (make-overlay (- (point) 58) (- (point) 55)) 'face 'my/ascii-table-highlight-face)
|
||||
(setq i (- i 96))
|
||||
))))
|
||||
|
||||
(set-popup-rule! "^\\*ASCII"
|
||||
:side 'right
|
||||
:select t
|
||||
:width 70)
|
||||
|
||||
(map! :leader
|
||||
:prefix ("h d" . "doom")
|
||||
|
||||
:desc "Doom manual" "d" #'doom/help
|
||||
:desc "Doom FAQ" "f" #'doom/help-faq
|
||||
:desc "Doom modules" "m" #'doom/help-modules
|
||||
:desc "Doom news" "n" #'doom/help-news
|
||||
:desc "Doom help search" "/" #'doom/help-search-headings
|
||||
|
||||
:desc "Doom version" #'doom/version
|
||||
|
||||
:desc "Doom package configuration" "p" #'doom/help-package-config
|
||||
:desc "Doom sandbox" "x" #'doom/sandbox)
|
||||
|
||||
(map! :leader
|
||||
:prefix ("p" . "projects")
|
||||
:desc "Switch project" "p" #'counsel-projectile-switch-project
|
||||
:desc "Add new project" "a" #'projectile-add-known-project
|
||||
:desc "Remove project" "d" #'projectile-remove-known-project
|
||||
|
||||
:desc "Find in project root" "." #'counsel-projectile-find-file
|
||||
:desc "Search in project" "/" #'+default/search-project
|
||||
|
||||
:desc "Invalidate project cache" "i" #'projectile-invalidate-cache
|
||||
|
||||
:desc "Run cmd in project root" "!" #'projectile-run-shell-command-in-root
|
||||
:desc "Run async cmd in project root" "&" #'projectile-run-async-shell-command-in-root)
|
||||
|
||||
(defun my/projectile-find-in-root ()
|
||||
(interactive)
|
||||
(counsel-find-file nil projectile-project-root))
|
||||
|
||||
(map! :leader
|
||||
:prefix ("t" . "toggle")
|
||||
;; Wrap
|
||||
:desc "Auto Wrap" "a" #'auto-fill-mode
|
||||
:desc "Wrap Indicator" "c" #'global-display-fill-column-indicator-mode
|
||||
:desc "Wrap Column" "C" #'set-fill-column
|
||||
:desc "Line Wrap" "w" #'visual-line-mode
|
||||
;; Modes
|
||||
:desc "Flycheck" "f" #'flycheck-mode
|
||||
;; Files
|
||||
:desc "Read-only" "r" #'read-only-mode)
|
||||
|
||||
(defun my/auto-fill-mode (cols)
|
||||
(interactive))
|
||||
|
||||
(map! :leader
|
||||
:prefix-map ("w" . "window")
|
||||
;; Navigation
|
||||
:desc "Go..." "w" #'ace-window
|
||||
:desc "Go left" "h" #'evil-window-left
|
||||
:desc "Go down" "j" #'evil-window-down
|
||||
:desc "Go up" "k" #'evil-window-up
|
||||
:desc "Go right" "l" #'evil-window-right
|
||||
:desc "Go other" "o" #'other-window
|
||||
;; Layout
|
||||
:desc "Rotate up" "K" #'evil-window-rotate-upwards
|
||||
:desc "Rotate down" "J" #'evil-window-rotate-downwards
|
||||
;; Splits
|
||||
:desc "VSplit" "=" #'+evil/window-vsplit-and-follow
|
||||
:desc "HSplit" "-" #'+evil/window-split-and-follow
|
||||
:desc "Tear off" "t" #'tear-off-window
|
||||
;; History
|
||||
:desc "Undo" "u" #'winner-undo
|
||||
:desc "Redo" "U" #'winner-redo
|
||||
;; Misc
|
||||
:desc "Resize" "r" #'my/hydra-window-resize/body
|
||||
:desc "Balance" "b" #'balance-windows
|
||||
;; Management
|
||||
:desc "Kill window" "d" #'+workspace/close-window-or-workspace)
|
||||
;; TODO: Maybe check out:
|
||||
;; evil-window-mru
|
||||
|
||||
(setq my/window-resize-step 3)
|
||||
|
||||
(defun my/window-increase-height ()
|
||||
(interactive)
|
||||
(evil-window-increase-height my/window-resize-step))
|
||||
(defun my/window-decrease-height ()
|
||||
(interactive)
|
||||
(evil-window-decrease-height my/window-resize-step))
|
||||
(defun my/window-increase-width ()
|
||||
(interactive)
|
||||
(evil-window-increase-width my/window-resize-step))
|
||||
(defun my/window-decrease-width ()
|
||||
(interactive)
|
||||
(evil-window-decrease-width my/window-resize-step))
|
||||
|
||||
(defhydra my/hydra-window-resize ()
|
||||
"Resize window"
|
||||
("=" my/window-increase-height "++Height")
|
||||
("-" my/window-decrease-height "--Height")
|
||||
("<" my/window-decrease-width "--Width")
|
||||
(">" my/window-increase-width "++Width"))
|
||||
|
||||
(map! :map org-config-mode-map
|
||||
:localleader
|
||||
:v :desc "Eval Region" "e" #'eval-region
|
||||
:n :desc "Eval Source" "e" #'my/org-config-eval-source)
|
||||
|
||||
(defun my/org-config-eval-source ()
|
||||
(interactive)
|
||||
(org-ctrl-c-ctrl-c)
|
||||
(org-babel-remove-result))
|
||||
|
||||
(map! :map rustic-mode-map
|
||||
:localleader
|
||||
:desc "Debug..." "d" #'my/rust/dap-hydra/body)
|
||||
|
||||
(map! :map rustic-mode-map
|
||||
:desc "Pluralize import" "," #'my/rust/import-pluralize
|
||||
:desc "Singularize import" "<backspace>" #'my/rust/import-singularize
|
||||
:desc "Singularize import" "C-<backspace>" #'my/rust/import-c-singularize)
|
||||
|
||||
(defhydra my/rust/dap-hydra (:color pink :hint nil :foreign-keys run)
|
||||
"
|
||||
^Stepping^ ^Switch^ ^Breakpoints^ ^Debug^ ^Eval
|
||||
^^^^^^^^----------------------------------------------------------------------------------------------------------------
|
||||
_n_: Next _ss_: Session _bb_: Toggle _dd_: Debug binary _ee_: Eval
|
||||
_i_: Step in _st_: Thread _bd_: Delete _dr_: Restart debugging _es_: Eval thing at point
|
||||
_o_: Step out _sf_: Stack frame _ba_: Add _ea_: Add expression
|
||||
_c_: Continue _su_: Up stack frame _bc_: Set condition
|
||||
_Q_: Disconnect _sd_: Down stack frame _bh_: Set hit count
|
||||
_sl_: List locals _bl_: Set log message
|
||||
_sb_: List breakpoints
|
||||
_sS_: List sessions
|
||||
"
|
||||
("n" dap-next)
|
||||
("i" dap-step-in)
|
||||
("o" dap-step-out)
|
||||
("c" dap-continue)
|
||||
("r" dap-restart-frame)
|
||||
("ss" dap-switch-session)
|
||||
("st" dap-switch-thread)
|
||||
("sf" dap-switch-stack-frame)
|
||||
("su" dap-up-stack-frame)
|
||||
("sd" dap-down-stack-frame)
|
||||
("sl" dap-ui-locals)
|
||||
("sb" dap-ui-breakpoints)
|
||||
("sS" dap-ui-sessions)
|
||||
("bb" dap-breakpoint-toggle)
|
||||
("ba" dap-breakpoint-add)
|
||||
("bd" dap-breakpoint-delete)
|
||||
("bc" dap-breakpoint-condition)
|
||||
("bh" dap-breakpoint-hit-condition)
|
||||
("bl" dap-breakpoint-log-message)
|
||||
("dd" my/rust/debug-binary)
|
||||
("dr" dap-debug-restart)
|
||||
("ee" dap-eval)
|
||||
("ea" dap-ui-expressions-add)
|
||||
("es" dap-eval-thing-at-point)
|
||||
("q" nil "quit" :color blue)
|
||||
("Q" dap-disconnect :color red))
|
||||
|
||||
(map! :prefix "z"
|
||||
:desc "Kill buffer" :n "x" #'kill-current-buffer
|
||||
:desc "Kill window" :n "c" #'+workspace/close-window-or-workspace)
|
||||
|
||||
(map! :prefix "["
|
||||
:desc "Start of fn" :n "f" #'beginning-of-defun)
|
||||
|
||||
(map! :prefix "]"
|
||||
:desc "End of fn" :n "f" #'end-of-defun)
|
||||
|
||||
|
||||
|
||||
(add-to-list 'projectile-globally-ignored-files "Cargo.lock")
|
||||
|
||||
(defun my/rust/import-pluralize ()
|
||||
"Convert a singular import into a brace-wrapped plural import."
|
||||
(interactive)
|
||||
(if (and
|
||||
(not (my/kbd!-p))
|
||||
(my/insert-mode-p)
|
||||
(my/line-match-p
|
||||
;; use foo::bar::baz;
|
||||
(rx line-start "use "
|
||||
(+ (+ word) "::")
|
||||
(+ word)
|
||||
(? ";") line-end)))
|
||||
(kbd! "ESC vb S} f} i,")
|
||||
(insert ",")))
|
||||
|
||||
(defun my/rust/import-singularize ()
|
||||
"Convert a brace-wrapped plural import into a singular import."
|
||||
(interactive)
|
||||
(if (and
|
||||
(not (my/kbd!-p))
|
||||
(my/insert-mode-p)
|
||||
(my/line-match-p
|
||||
;; use foo::bar::baz::{qux::quo,};
|
||||
(rx line-start "use "
|
||||
(+ (+ word) "::")
|
||||
"{" (* (+ word) "::") (+ word) ",}"
|
||||
(? ";") line-end)))
|
||||
(kbd! "ESC l dF, ds} $i")
|
||||
(evil-delete-backward-char-and-join 1)))
|
||||
|
||||
(defun my/rust/import-c-singularize ()
|
||||
"Convert a brace-wrapped plural import into a singular import."
|
||||
(interactive)
|
||||
(if (and
|
||||
(not (my/kbd!-p))
|
||||
(my/insert-mode-p)
|
||||
(my/line-match-p
|
||||
;; use foo::bar::baz::{qux::quo, };
|
||||
(rx line-start
|
||||
"use "
|
||||
(+ (+ word) "::")
|
||||
"{" (* (+ word) "::") (+ word) "," (* whitespace) "}"
|
||||
(? ";") line-end)))
|
||||
(kbd! "ESC l dF, ds} $i")
|
||||
(backward-kill-word 1)))
|
||||
|
||||
(defun my/rust/debug-config (args)
|
||||
(append
|
||||
`(:type "lldb-vscode"
|
||||
;; `(:type "lldb"
|
||||
:request "launch"
|
||||
:dap-server-path ,(list (executable-find "lldb-vscode"))
|
||||
;; :dap-server-path ,(list (executable-find "rust-lldb"))
|
||||
,@args)))
|
||||
|
||||
;; use a::TestThin
|
||||
;; (:MIMode "gdb"
|
||||
;; :miDebuggerPath "gdb"
|
||||
;; :stopAtEntry t
|
||||
;; :externalConsole
|
||||
;; :json-false
|
||||
;; :type "cppdbg"
|
||||
;; :request "launch"
|
||||
;; :name "test test2"
|
||||
;; :args ["test2" "--exact" "--nocapture"]
|
||||
;; :cwd "/home/lain/Code/test/rust/debug"
|
||||
;; :sourceLanguages ["rust"]
|
||||
;; :program "/home/lain/Code/test/rust/debug/target/debug/deps/...")
|
||||
|
||||
;; (require 'dap-cpptools)
|
||||
(defun my/rust/debug-binary (args)
|
||||
(interactive "sArgs: ")
|
||||
(let* ((root (projectile-project-root))
|
||||
(name (projectile-project-name))
|
||||
(target (concat root "target/debug/" name)))
|
||||
;; (rustic-cargo-build)
|
||||
(dap-debug
|
||||
(my/rust/debug-config
|
||||
`(:program ,target
|
||||
:cwd ,root
|
||||
:args ,(apply #'vector (split-string-and-unquote args)))))))
|
||||
|
||||
(defun my/rust/debug-lsp-runnable (runnable)
|
||||
"Select and debug a RUNNABLE action."
|
||||
(interactive (list (lsp-rust-analyzer--select-runnable)))
|
||||
(-let (((&rust-analyzer:Runnable
|
||||
:args (&rust-analyzer:RunnableArgs :cargo-args :workspace-root? :executable-args)
|
||||
:label) runnable))
|
||||
(pcase (aref cargo-args 0)
|
||||
("run" (aset cargo-args 0 "build"))
|
||||
("test" (when (-contains? (append cargo-args ()) "--no-run")
|
||||
(cl-callf append cargo-args (list "--no-run")))))
|
||||
(->> (append (list (executable-find "cargo"))
|
||||
cargo-args
|
||||
(list "--message-format=json"))
|
||||
(s-join " ")
|
||||
(shell-command-to-string)
|
||||
(s-lines)
|
||||
(-keep (lambda (s)
|
||||
(condition-case nil
|
||||
(-let* ((json-object-type 'plist)
|
||||
((msg &as &plist :reason :executable) (json-read-from-string s)))
|
||||
(when (and executable (string= "compiler-artifact" reason))
|
||||
executable))
|
||||
(error))))
|
||||
(funcall
|
||||
(lambda (artifact-spec)
|
||||
(pcase artifact-spec
|
||||
(`() (user-error "No compilation artifacts or obtaining the runnable artifacts failed"))
|
||||
(`(,spec) spec)
|
||||
(_ (user-error "Multiple compilation artifacts are not supported")))))
|
||||
(list :name label
|
||||
:args executable-args
|
||||
:cwd workspace-root?
|
||||
;; :sourceLanguages ["rust"]
|
||||
:stopAtEntry t
|
||||
:stopAtEntry :json-true
|
||||
:externalConsole :json-false
|
||||
:program)
|
||||
(my/rust/debug-config)
|
||||
(dap-debug))))
|
||||
(advice-add #'lsp-rust-analyzer-debug :override #'my/rust/debug-lsp-runnable)
|
||||
|
||||
;; (setq projectile-project-search-path
|
||||
;; '("~/Code"))
|
||||
|
||||
(let ((found (nth 0 (auth-source-search :host "kagi.com"))))
|
||||
(when found
|
||||
(let ((token (plist-get found :secret)))
|
||||
(when (functionp token)
|
||||
(setq token (funcall token)))
|
||||
(add-to-list
|
||||
'counsel-search-engines-alist
|
||||
`(kagi
|
||||
"https://duckduckgo.com/ac/"
|
||||
,(format "https://kagi.com/search?token=%s&q=" token)
|
||||
counsel--search-request-data-ddg))
|
||||
(setq counsel-search-engine 'kagi))))
|
||||
|
||||
(load! "lisp/emacs-everywhere.el")
|
||||
(setq emacs-everywhere-paste-command '("xdotool" "key" "--clearmodifiers" "ctrl+v"))
|
||||
(setq emacs-everywhere-frame-parameters
|
||||
'((title . "Emacs Everywhere")
|
||||
(width . 120)
|
||||
(height . 36)))
|
||||
|
||||
(defun my/line ()
|
||||
(buffer-substring-no-properties
|
||||
(line-beginning-position)
|
||||
(line-end-position)))
|
||||
|
||||
(defun my/line-match-p (regexp)
|
||||
(string-match-p regexp (my/line)))
|
||||
|
||||
(defun my/insert-mode-p ()
|
||||
(eq evil-state 'insert))
|
||||
(defun my/normal-mode-p ()
|
||||
(eq evil-state 'normal))
|
||||
|
||||
(defun my/kbd-replace (str)
|
||||
"Convert STR into a keyboard macro string by replacing terminal key sequences with GUI keycodes."
|
||||
(let ((kbd-regex '(("ESC" . "<escape>")
|
||||
("DEL" . "<delete>" )
|
||||
("BS" . "<backspace>")
|
||||
("RET" . "<return>")
|
||||
("SPC" . "<SPC>")
|
||||
("TAB" . "<tab>"))))
|
||||
(my/replace-regexps-in-string str kbd-regex)))
|
||||
|
||||
(setq my//kbd-p nil)
|
||||
(defun my/kbd!-p () (eq my//kbd-p t))
|
||||
|
||||
(defun kbd! (str)
|
||||
"Execute the key sequence defined by STR like a VIM macro."
|
||||
(let ((minibuffer-message-timeout 0))
|
||||
(setq my//kbd-p t)
|
||||
(execute-kbd-macro (read-kbd-macro (my/kbd-replace str)))
|
||||
(setq my//kbd-p nil)))
|
||||
|
||||
(defun my/buffer-local-set-key (key fn)
|
||||
(let ((mode (intern (format "%s-local-mode" (buffer-name))))
|
||||
(map (intern (format "%s-local-mode-map" (buffer-name)))))
|
||||
(unless (boundp map)
|
||||
(set map (make-sparse-keymap))
|
||||
(evil-make-overriding-map map 'normal))
|
||||
(eval
|
||||
`(define-minor-mode ,mode
|
||||
"A minor mode for buffer-local keybinds."
|
||||
:keymap ,map))
|
||||
(eval
|
||||
`(define-key ,map ,key #',fn))
|
||||
(funcall mode t)))
|
||||
|
||||
(defun my/replace-regexps-in-string (str regexps)
|
||||
"Replace all pairs of (regex . replacement) defined by REGEXPS in STR."
|
||||
(if (null regexps)
|
||||
str
|
||||
(my/replace-regexps-in-string
|
||||
(replace-regexp-in-string (caar regexps) (cdar regexps) str t)
|
||||
(cdr regexps))))
|
733
.doom.d/config.org
Normal file
733
.doom.d/config.org
Normal file
@ -0,0 +1,733 @@
|
||||
#+title: Config
|
||||
|
||||
* Setup
|
||||
** Environment Variables
|
||||
#+BEGIN_SRC elisp
|
||||
(doom-load-envvars-file (concat doom-private-dir "env.el"))
|
||||
#+END_SRC
|
||||
* Appearance
|
||||
Set a nice theme and font.
|
||||
#+BEGIN_SRC elisp
|
||||
(setq doom-theme 'doom-catppuccin)
|
||||
|
||||
(setq doom-font (font-spec :family "monospace" :size 13)
|
||||
doom-big-font (font-spec :family "monospace" :size 13)
|
||||
doom-variable-pitch-font (font-spec :family "sans-serif" :size 13))
|
||||
#+END_SRC
|
||||
|
||||
Sprinkle in a little background transparency. Instead of making the entire frame
|
||||
transparent (including the text) with =alpha=, we use the =alpha-background=
|
||||
frame parameter which just landed in the Emacs 29 development branch.
|
||||
#+BEGIN_SRC elisp
|
||||
(set-frame-parameter (selected-frame) 'alpha-background 85)
|
||||
(add-to-list 'default-frame-alist '(alpha-background . 85))
|
||||
#+END_SRC
|
||||
* Editing
|
||||
** Evil
|
||||
#+BEGIN_SRC elisp
|
||||
(setq evil-want-fine-undo t)
|
||||
#+END_SRC
|
||||
|
||||
*** Line Numbers
|
||||
Use relative line numbers in normal mode, and absolute line numbers in insert
|
||||
mode.
|
||||
#+BEGIN_SRC emacs-lisp
|
||||
(defun my/line-numbers-relative ()
|
||||
(setq display-line-numbers 'relative))
|
||||
(defun my/line-numbers-absolute ()
|
||||
(setq display-line-numbers 'absolute))
|
||||
(add-hook 'evil-insert-state-entry-hook #'my/line-numbers-absolute)
|
||||
(add-hook 'evil-insert-state-exit-hook #'my/line-numbers-relative)
|
||||
#+END_SRC
|
||||
** Copilot
|
||||
Add support for GitHub Copilot ([[*Copilot][keybinds]]).
|
||||
|
||||
#+BEGIN_SRC elisp
|
||||
(use-package copilot
|
||||
:commands (copilot-complete))
|
||||
|
||||
(defun my/copilot-complete ()
|
||||
(interactive)
|
||||
(copilot-complete)
|
||||
(my/hydra-copilot/body)
|
||||
(copilot-clear-overlay))
|
||||
|
||||
(defhydra my/hydra-copilot ()
|
||||
"Copilot"
|
||||
("<return>" copilot-accept-completion "Accept" :color blue )
|
||||
("<tab>" copilot-next-completion "Next" )
|
||||
("<backtab>" copilot-previous-completion "Prev")
|
||||
("<escape>" copilot-clear-overlay "Cancel" :color blue))
|
||||
#+END_SRC
|
||||
** Scratch
|
||||
Use =lisp-interaction-mode= by default for the scratch buffer.
|
||||
#+BEGIN_SRC elisp
|
||||
(setq doom-scratch-initial-major-mode 'lisp-interaction-mode)
|
||||
#+END_SRC
|
||||
* Keybinds
|
||||
** Unmaps
|
||||
Unmap a bunch of the default keybindings.
|
||||
#+BEGIN_SRC elisp
|
||||
(map! :leader
|
||||
"b" nil
|
||||
"f" nil
|
||||
"h" nil
|
||||
"p" nil
|
||||
"t" nil)
|
||||
|
||||
(map! :map evil-org-mode-map
|
||||
:n "zc" nil)
|
||||
#+END_SRC
|
||||
|
||||
** Global
|
||||
*** Font Size
|
||||
#+BEGIN_SRC elisp
|
||||
(map!
|
||||
:desc "Increase font size" :ni "C-=" #'text-scale-increase
|
||||
:desc "Decrease font size" :ni "C--" #'text-scale-decrease)
|
||||
#+END_SRC
|
||||
|
||||
*** Copilot
|
||||
#+BEGIN_SRC elisp
|
||||
(map!
|
||||
:desc "Copilot" :i "C-," #'my/copilot-complete)
|
||||
#+END_SRC
|
||||
*** LSP
|
||||
#+BEGIN_SRC elisp
|
||||
#+END_SRC
|
||||
*** Minibuffer
|
||||
#+BEGIN_SRC elisp
|
||||
(map! :map minibuffer-mode-map
|
||||
:desc "Next history" "C-j" #'next-history-element
|
||||
:desc "Prev history" "C-k" #'previous-history-element)
|
||||
#+END_SRC
|
||||
|
||||
** Leader
|
||||
*** Root
|
||||
**** Eval
|
||||
#+BEGIN_SRC elisp
|
||||
(map! :leader
|
||||
:desc "M-x" "x" #'counsel-M-x
|
||||
:desc "M-:" ";" #'pp-eval-expression)
|
||||
#+END_SRC
|
||||
|
||||
**** Files
|
||||
#+BEGIN_SRC elisp
|
||||
(map! :leader
|
||||
:desc "Find file" "." #'counsel-find-file
|
||||
:desc "Find dir" ">" #'+default/dired
|
||||
|
||||
:desc "Find in project" "SPC" #'+ivy/projectile-find-file
|
||||
:desc "Find in project uncached" "C-SPC" #'my/projectile-find-file-nocache)
|
||||
|
||||
(defun my/projectile-find-file-nocache ()
|
||||
(interactive)
|
||||
(projectile-invalidate-cache nil)
|
||||
(+ivy/projectile-find-file))
|
||||
#+END_SRC
|
||||
**** Buffers
|
||||
#+BEGIN_SRC elisp
|
||||
(map! :leader
|
||||
:desc "Switch buffer" "," #'+vertico/switch-workspace-buffer
|
||||
:desc "Switch all buffers" ">" #'consult-buffer)
|
||||
#+END_SRC
|
||||
|
||||
**** Search
|
||||
#+BEGIN_SRC elisp
|
||||
(map! :leader
|
||||
:desc "Search online" "/" #'counsel-search)
|
||||
#+END_SRC
|
||||
|
||||
*** b: Buffers
|
||||
#+BEGIN_SRC elisp
|
||||
(map! :leader
|
||||
:prefix ("b" . "buffers")
|
||||
|
||||
:desc "Switch buffer" "b" #'consult-buffer
|
||||
:desc "ibuffer" "i" #'ibuffer
|
||||
|
||||
:desc "Kill buffer" "d" #'kill-current-buffer
|
||||
:desc "Kill all buffers" "D" #'doom/kill-all-buffers)
|
||||
#+END_SRC
|
||||
|
||||
*** f: Files
|
||||
#+BEGIN_SRC elisp
|
||||
(map! :leader
|
||||
:prefix ("f" . "files")
|
||||
|
||||
:desc "Recent files" "r" #'consult-recent-file
|
||||
|
||||
:desc "Find file" "f" #'counsel-find-file
|
||||
:desc "Find file as root" "u" #'doom/sudo-find-file
|
||||
:desc "Find package" "p" #'counsel-find-library
|
||||
|
||||
:desc "Copy this file" "c" #'doom/copy-this-file
|
||||
:desc "Delete this file" "d" #'doom/delete-this-file
|
||||
:desc "Move this file" "m" #'doom/move-this-file
|
||||
:desc "Revert this file" "l" #'revert-buffer
|
||||
|
||||
:desc "Copy file path" "y" #'+default/yank-buffer-path
|
||||
:desc "Copy project file path" "Y" #'+default/yank-buffer-path-relative-to-project
|
||||
|
||||
:desc "Open scratch" "x" #'doom/open-scratch-buffer)
|
||||
#+END_SRC
|
||||
|
||||
**** s: Snippets
|
||||
#+BEGIN_SRC emacs-lisp
|
||||
(map! :leader
|
||||
:prefix ("f s" . "snippets")
|
||||
:desc "New snippet" "n" #'yas-new-snippet
|
||||
:desc "Edit snippet" "e" #'yas-visit-snippet-file
|
||||
:desc "Browse docs" "?" #'my/yas-browse-docs)
|
||||
#+END_SRC
|
||||
|
||||
Add a command to open the YASnippet docs.
|
||||
#+BEGIN_SRC elisp
|
||||
(defun my/yas-browse-docs ()
|
||||
(interactive)
|
||||
(browse-url "https://joaotavora.github.io/yasnippet"))
|
||||
#+END_SRC
|
||||
|
||||
**** e: Emacs Files
|
||||
#+BEGIN_SRC elisp
|
||||
(map! :leader
|
||||
:prefix ("f e" . "emacs")
|
||||
:desc "Find in config" "f" #'doom/find-file-in-private-config
|
||||
:desc "Reload config" "r" #'doom/reload
|
||||
|
||||
:desc "Edit config" "c" #'my/edit-config
|
||||
:desc "Edit packages" "p" #'my/edit-packages
|
||||
:desc "Edit env" "e" #'my/edit-env
|
||||
:desc "Edit init" "i" #'my/edit-init)
|
||||
#+END_SRC
|
||||
|
||||
#+BEGIN_SRC elisp
|
||||
(defun my/edit-config ()
|
||||
(interactive)
|
||||
(find-file (concat doom-private-dir "config.org")))
|
||||
(defun my/edit-packages ()
|
||||
(interactive)
|
||||
(find-file (concat doom-private-dir "packages.el")))
|
||||
(defun my/edit-init ()
|
||||
(interactive)
|
||||
(find-file (concat doom-private-dir "init.el")))
|
||||
(defun my/edit-env ()
|
||||
(interactive)
|
||||
(find-file (concat doom-private-dir "env.el")))
|
||||
#+END_SRC
|
||||
|
||||
Define a derived mode for editing the literate config so we can specify some
|
||||
keybindings specific to =config.org=.
|
||||
#+BEGIN_SRC elisp
|
||||
(define-derived-mode org-config-mode org-mode "Org config mode")
|
||||
(add-to-list 'auto-mode-alist '("config\\.org" . org-config-mode))
|
||||
#+END_SRC
|
||||
|
||||
*** h: Help
|
||||
#+BEGIN_SRC elisp
|
||||
(map! :leader
|
||||
:prefix ("h" . "help")
|
||||
|
||||
:desc "Apropos" "/" #'consult-apropos
|
||||
:desc "Apropos docs" "?" #'apropos-documentation
|
||||
|
||||
:desc "Help at point" "p" #'helpful-at-point
|
||||
:desc "Help info" "h" #'info
|
||||
:desc "Help for help" "H" #'help-for-help
|
||||
|
||||
:desc "Describe function" "f" #'counsel-describe-function
|
||||
:desc "Describe function key" "F" #'where-is
|
||||
:desc "Describe variable" "v" #'counsel-describe-variable
|
||||
:desc "Describe custom variable" "V" #'doom/help-custom-variable
|
||||
:desc "Describe command" "x" #'helpful-command
|
||||
:desc "Describe key" "k" #'describe-key-briefly
|
||||
:desc "Describe key fully" "K" #'describe-key
|
||||
:desc "Describe char" "'" #'describe-char
|
||||
:desc "Describe coding system" "\"" #'describe-coding-system
|
||||
:desc "Describe input method" "i" #'describe-input-method
|
||||
|
||||
:desc "Emacs manual" "e" #'info-emacs-manual
|
||||
:desc "ASCII table" "a" #'my/ascii-table
|
||||
|
||||
:desc "View messages" "e" #'view-echo-area-messages
|
||||
:desc "View keystrokes" "l" #'view-lossage)
|
||||
#+END_SRC
|
||||
|
||||
**** a: Ascii Table
|
||||
#+BEGIN_SRC elisp
|
||||
(defface my/ascii-table-highlight-face
|
||||
'((t (:foreground "pink")))
|
||||
"Face for highlighting ASCII chars.")
|
||||
|
||||
(defun my/ascii-table ()
|
||||
"Display basic ASCII table (0 thru 128)."
|
||||
(interactive)
|
||||
(pop-to-buffer "*ASCII*")
|
||||
(erase-buffer)
|
||||
(setq buffer-read-only nil)
|
||||
(my/buffer-local-set-key "q" #'+popup/quit-window)
|
||||
(setq lower32 '("nul" "soh" "stx" "etx" "eot" "enq" "ack" "bel"
|
||||
"bs" "ht" "nl" "vt" "np" "cr" "so" "si"
|
||||
"dle" "dc1" "dc2" "dc3" "dc4" "nak" "syn" "etb"
|
||||
"can" "em" "sub" "esc" "fs" "gs" "rs" "us"))
|
||||
(save-excursion (let ((i -1))
|
||||
(insert " Hex Dec Char | Hex Dec Char | Hex Dec Char | Hex Dec Char\n")
|
||||
(insert " ---------------+-----------------+-----------------+----------------\n")
|
||||
(while (< i 31)
|
||||
(insert (format "%4x %4d %4s | %4x %4d %4s | %4x %4d %4s | %4x %4d %4s\n"
|
||||
(setq i (+ 1 i)) i (elt lower32 i)
|
||||
(setq i (+ 32 i)) i (single-key-description i)
|
||||
(setq i (+ 32 i)) i (single-key-description i)
|
||||
(setq i (+ 32 i)) i (single-key-description i)))
|
||||
(overlay-put (make-overlay (- (point) 4) (- (point) 1)) 'face 'my/ascii-table-highlight-face)
|
||||
(overlay-put (make-overlay (- (point) 22) (- (point) 19)) 'face 'my/ascii-table-highlight-face)
|
||||
(overlay-put (make-overlay (- (point) 40) (- (point) 37)) 'face 'my/ascii-table-highlight-face)
|
||||
(overlay-put (make-overlay (- (point) 58) (- (point) 55)) 'face 'my/ascii-table-highlight-face)
|
||||
(setq i (- i 96))
|
||||
))))
|
||||
|
||||
(set-popup-rule! "^\\*ASCII"
|
||||
:side 'right
|
||||
:select t
|
||||
:width 70)
|
||||
#+END_SRC
|
||||
|
||||
**** d: Doom
|
||||
#+BEGIN_SRC elisp
|
||||
(map! :leader
|
||||
:prefix ("h d" . "doom")
|
||||
|
||||
:desc "Doom manual" "d" #'doom/help
|
||||
:desc "Doom FAQ" "f" #'doom/help-faq
|
||||
:desc "Doom modules" "m" #'doom/help-modules
|
||||
:desc "Doom news" "n" #'doom/help-news
|
||||
:desc "Doom help search" "/" #'doom/help-search-headings
|
||||
|
||||
:desc "Doom version" #'doom/version
|
||||
|
||||
:desc "Doom package configuration" "p" #'doom/help-package-config
|
||||
:desc "Doom sandbox" "x" #'doom/sandbox)
|
||||
#+END_SRC
|
||||
|
||||
*** p: Projects
|
||||
#+BEGIN_SRC elisp
|
||||
(map! :leader
|
||||
:prefix ("p" . "projects")
|
||||
:desc "Switch project" "p" #'counsel-projectile-switch-project
|
||||
:desc "Add new project" "a" #'projectile-add-known-project
|
||||
:desc "Remove project" "d" #'projectile-remove-known-project
|
||||
|
||||
:desc "Find in project root" "." #'counsel-projectile-find-file
|
||||
:desc "Search in project" "/" #'+default/search-project
|
||||
|
||||
:desc "Invalidate project cache" "i" #'projectile-invalidate-cache
|
||||
|
||||
:desc "Run cmd in project root" "!" #'projectile-run-shell-command-in-root
|
||||
:desc "Run async cmd in project root" "&" #'projectile-run-async-shell-command-in-root)
|
||||
|
||||
(defun my/projectile-find-in-root ()
|
||||
(interactive)
|
||||
(counsel-find-file nil projectile-project-root))
|
||||
#+END_SRC
|
||||
|
||||
*** t: Toggle
|
||||
#+BEGIN_SRC elisp
|
||||
(map! :leader
|
||||
:prefix ("t" . "toggle")
|
||||
;; Wrap
|
||||
:desc "Auto Wrap" "a" #'auto-fill-mode
|
||||
:desc "Wrap Indicator" "c" #'global-display-fill-column-indicator-mode
|
||||
:desc "Wrap Column" "C" #'set-fill-column
|
||||
:desc "Line Wrap" "w" #'visual-line-mode
|
||||
;; Modes
|
||||
:desc "Flycheck" "f" #'flycheck-mode
|
||||
;; Files
|
||||
:desc "Read-only" "r" #'read-only-mode)
|
||||
#+END_SRC
|
||||
|
||||
#+BEGIN_SRC elisp
|
||||
(defun my/auto-fill-mode (cols)
|
||||
(interactive))
|
||||
#+END_SRC
|
||||
*** w: Window
|
||||
#+BEGIN_SRC elisp
|
||||
(map! :leader
|
||||
:prefix-map ("w" . "window")
|
||||
;; Navigation
|
||||
:desc "Go..." "w" #'ace-window
|
||||
:desc "Go left" "h" #'evil-window-left
|
||||
:desc "Go down" "j" #'evil-window-down
|
||||
:desc "Go up" "k" #'evil-window-up
|
||||
:desc "Go right" "l" #'evil-window-right
|
||||
:desc "Go other" "o" #'other-window
|
||||
;; Layout
|
||||
:desc "Rotate up" "K" #'evil-window-rotate-upwards
|
||||
:desc "Rotate down" "J" #'evil-window-rotate-downwards
|
||||
;; Splits
|
||||
:desc "VSplit" "=" #'+evil/window-vsplit-and-follow
|
||||
:desc "HSplit" "-" #'+evil/window-split-and-follow
|
||||
:desc "Tear off" "t" #'tear-off-window
|
||||
;; History
|
||||
:desc "Undo" "u" #'winner-undo
|
||||
:desc "Redo" "U" #'winner-redo
|
||||
;; Misc
|
||||
:desc "Resize" "r" #'my/hydra-window-resize/body
|
||||
:desc "Balance" "b" #'balance-windows
|
||||
;; Management
|
||||
:desc "Kill window" "d" #'+workspace/close-window-or-workspace)
|
||||
;; TODO: Maybe check out:
|
||||
;; evil-window-mru
|
||||
#+END_SRC
|
||||
|
||||
#+BEGIN_SRC elisp
|
||||
(setq my/window-resize-step 3)
|
||||
|
||||
(defun my/window-increase-height ()
|
||||
(interactive)
|
||||
(evil-window-increase-height my/window-resize-step))
|
||||
(defun my/window-decrease-height ()
|
||||
(interactive)
|
||||
(evil-window-decrease-height my/window-resize-step))
|
||||
(defun my/window-increase-width ()
|
||||
(interactive)
|
||||
(evil-window-increase-width my/window-resize-step))
|
||||
(defun my/window-decrease-width ()
|
||||
(interactive)
|
||||
(evil-window-decrease-width my/window-resize-step))
|
||||
|
||||
(defhydra my/hydra-window-resize ()
|
||||
"Resize window"
|
||||
("=" my/window-increase-height "++Height")
|
||||
("-" my/window-decrease-height "--Height")
|
||||
("<" my/window-decrease-width "--Width")
|
||||
(">" my/window-increase-width "++Width"))
|
||||
#+END_SRC
|
||||
|
||||
** Local Leader
|
||||
*** Org Config
|
||||
#+BEGIN_SRC elisp
|
||||
(map! :map org-config-mode-map
|
||||
:localleader
|
||||
:v :desc "Eval Region" "e" #'eval-region
|
||||
:n :desc "Eval Source" "e" #'my/org-config-eval-source)
|
||||
|
||||
(defun my/org-config-eval-source ()
|
||||
(interactive)
|
||||
(org-ctrl-c-ctrl-c)
|
||||
(org-babel-remove-result))
|
||||
#+END_SRC
|
||||
*** Rust
|
||||
#+BEGIN_SRC elisp
|
||||
(map! :map rustic-mode-map
|
||||
:localleader
|
||||
:desc "Debug..." "d" #'my/rust/dap-hydra/body)
|
||||
|
||||
(map! :map rustic-mode-map
|
||||
:desc "Pluralize import" "," #'my/rust/import-pluralize
|
||||
:desc "Singularize import" "<backspace>" #'my/rust/import-singularize
|
||||
:desc "Singularize import" "C-<backspace>" #'my/rust/import-c-singularize)
|
||||
#+END_SRC
|
||||
|
||||
#+BEGIN_SRC elisp
|
||||
(defhydra my/rust/dap-hydra (:color pink :hint nil :foreign-keys run)
|
||||
"
|
||||
^Stepping^ ^Switch^ ^Breakpoints^ ^Debug^ ^Eval
|
||||
^^^^^^^^----------------------------------------------------------------------------------------------------------------
|
||||
_n_: Next _ss_: Session _bb_: Toggle _dd_: Debug binary _ee_: Eval
|
||||
_i_: Step in _st_: Thread _bd_: Delete _dr_: Restart debugging _es_: Eval thing at point
|
||||
_o_: Step out _sf_: Stack frame _ba_: Add _ea_: Add expression
|
||||
_c_: Continue _su_: Up stack frame _bc_: Set condition
|
||||
_Q_: Disconnect _sd_: Down stack frame _bh_: Set hit count
|
||||
_sl_: List locals _bl_: Set log message
|
||||
_sb_: List breakpoints
|
||||
_sS_: List sessions
|
||||
"
|
||||
("n" dap-next)
|
||||
("i" dap-step-in)
|
||||
("o" dap-step-out)
|
||||
("c" dap-continue)
|
||||
("r" dap-restart-frame)
|
||||
("ss" dap-switch-session)
|
||||
("st" dap-switch-thread)
|
||||
("sf" dap-switch-stack-frame)
|
||||
("su" dap-up-stack-frame)
|
||||
("sd" dap-down-stack-frame)
|
||||
("sl" dap-ui-locals)
|
||||
("sb" dap-ui-breakpoints)
|
||||
("sS" dap-ui-sessions)
|
||||
("bb" dap-breakpoint-toggle)
|
||||
("ba" dap-breakpoint-add)
|
||||
("bd" dap-breakpoint-delete)
|
||||
("bc" dap-breakpoint-condition)
|
||||
("bh" dap-breakpoint-hit-condition)
|
||||
("bl" dap-breakpoint-log-message)
|
||||
("dd" my/rust/debug-binary)
|
||||
("dr" dap-debug-restart)
|
||||
("ee" dap-eval)
|
||||
("ea" dap-ui-expressions-add)
|
||||
("es" dap-eval-thing-at-point)
|
||||
("q" nil "quit" :color blue)
|
||||
("Q" dap-disconnect :color red))
|
||||
#+END_SRC
|
||||
|
||||
** Modes
|
||||
*** Evil
|
||||
**** z
|
||||
#+BEGIN_SRC elisp
|
||||
(map! :prefix "z"
|
||||
:desc "Kill buffer" :n "x" #'kill-current-buffer
|
||||
:desc "Kill window" :n "c" #'+workspace/close-window-or-workspace)
|
||||
#+END_SRC
|
||||
|
||||
**** g
|
||||
**** [
|
||||
#+BEGIN_SRC elisp
|
||||
(map! :prefix "["
|
||||
:desc "Start of fn" :n "f" #'beginning-of-defun)
|
||||
|
||||
(map! :prefix "]"
|
||||
:desc "End of fn" :n "f" #'end-of-defun)
|
||||
#+END_SRC
|
||||
*** Dap
|
||||
#+BEGIN_SRC elisp
|
||||
#+END_SRC
|
||||
|
||||
* Languages
|
||||
** Rust
|
||||
*** General
|
||||
#+BEGIN_SRC elisp
|
||||
(add-to-list 'projectile-globally-ignored-files "Cargo.lock")
|
||||
#+END_SRC
|
||||
|
||||
*** Editing
|
||||
#+BEGIN_SRC elisp
|
||||
(defun my/rust/import-pluralize ()
|
||||
"Convert a singular import into a brace-wrapped plural import."
|
||||
(interactive)
|
||||
(if (and
|
||||
(not (my/kbd!-p))
|
||||
(my/insert-mode-p)
|
||||
(my/line-match-p
|
||||
;; use foo::bar::baz;
|
||||
(rx line-start "use "
|
||||
(+ (+ word) "::")
|
||||
(+ word)
|
||||
(? ";") line-end)))
|
||||
(kbd! "ESC vb S} f} i,")
|
||||
(insert ",")))
|
||||
|
||||
(defun my/rust/import-singularize ()
|
||||
"Convert a brace-wrapped plural import into a singular import."
|
||||
(interactive)
|
||||
(if (and
|
||||
(not (my/kbd!-p))
|
||||
(my/insert-mode-p)
|
||||
(my/line-match-p
|
||||
;; use foo::bar::baz::{qux::quo,};
|
||||
(rx line-start "use "
|
||||
(+ (+ word) "::")
|
||||
"{" (* (+ word) "::") (+ word) ",}"
|
||||
(? ";") line-end)))
|
||||
(kbd! "ESC l dF, ds} $i")
|
||||
(evil-delete-backward-char-and-join 1)))
|
||||
|
||||
(defun my/rust/import-c-singularize ()
|
||||
"Convert a brace-wrapped plural import into a singular import."
|
||||
(interactive)
|
||||
(if (and
|
||||
(not (my/kbd!-p))
|
||||
(my/insert-mode-p)
|
||||
(my/line-match-p
|
||||
;; use foo::bar::baz::{qux::quo, };
|
||||
(rx line-start
|
||||
"use "
|
||||
(+ (+ word) "::")
|
||||
"{" (* (+ word) "::") (+ word) "," (* whitespace) "}"
|
||||
(? ";") line-end)))
|
||||
(kbd! "ESC l dF, ds} $i")
|
||||
(backward-kill-word 1)))
|
||||
#+END_SRC
|
||||
|
||||
*** Debugging
|
||||
#+BEGIN_SRC elisp
|
||||
(defun my/rust/debug-config (args)
|
||||
(append
|
||||
`(:type "lldb-vscode"
|
||||
;; `(:type "lldb"
|
||||
:request "launch"
|
||||
:dap-server-path ,(list (executable-find "lldb-vscode"))
|
||||
;; :dap-server-path ,(list (executable-find "rust-lldb"))
|
||||
,@args)))
|
||||
|
||||
;; use a::TestThin
|
||||
;; (:MIMode "gdb"
|
||||
;; :miDebuggerPath "gdb"
|
||||
;; :stopAtEntry t
|
||||
;; :externalConsole
|
||||
;; :json-false
|
||||
;; :type "cppdbg"
|
||||
;; :request "launch"
|
||||
;; :name "test test2"
|
||||
;; :args ["test2" "--exact" "--nocapture"]
|
||||
;; :cwd "/home/lain/Code/test/rust/debug"
|
||||
;; :sourceLanguages ["rust"]
|
||||
;; :program "/home/lain/Code/test/rust/debug/target/debug/deps/...")
|
||||
|
||||
;; (require 'dap-cpptools)
|
||||
(defun my/rust/debug-binary (args)
|
||||
(interactive "sArgs: ")
|
||||
(let* ((root (projectile-project-root))
|
||||
(name (projectile-project-name))
|
||||
(target (concat root "target/debug/" name)))
|
||||
;; (rustic-cargo-build)
|
||||
(dap-debug
|
||||
(my/rust/debug-config
|
||||
`(:program ,target
|
||||
:cwd ,root
|
||||
:args ,(apply #'vector (split-string-and-unquote args)))))))
|
||||
|
||||
(defun my/rust/debug-lsp-runnable (runnable)
|
||||
"Select and debug a RUNNABLE action."
|
||||
(interactive (list (lsp-rust-analyzer--select-runnable)))
|
||||
(-let (((&rust-analyzer:Runnable
|
||||
:args (&rust-analyzer:RunnableArgs :cargo-args :workspace-root? :executable-args)
|
||||
:label) runnable))
|
||||
(pcase (aref cargo-args 0)
|
||||
("run" (aset cargo-args 0 "build"))
|
||||
("test" (when (-contains? (append cargo-args ()) "--no-run")
|
||||
(cl-callf append cargo-args (list "--no-run")))))
|
||||
(->> (append (list (executable-find "cargo"))
|
||||
cargo-args
|
||||
(list "--message-format=json"))
|
||||
(s-join " ")
|
||||
(shell-command-to-string)
|
||||
(s-lines)
|
||||
(-keep (lambda (s)
|
||||
(condition-case nil
|
||||
(-let* ((json-object-type 'plist)
|
||||
((msg &as &plist :reason :executable) (json-read-from-string s)))
|
||||
(when (and executable (string= "compiler-artifact" reason))
|
||||
executable))
|
||||
(error))))
|
||||
(funcall
|
||||
(lambda (artifact-spec)
|
||||
(pcase artifact-spec
|
||||
(`() (user-error "No compilation artifacts or obtaining the runnable artifacts failed"))
|
||||
(`(,spec) spec)
|
||||
(_ (user-error "Multiple compilation artifacts are not supported")))))
|
||||
(list :name label
|
||||
:args executable-args
|
||||
:cwd workspace-root?
|
||||
;; :sourceLanguages ["rust"]
|
||||
:stopAtEntry t
|
||||
:stopAtEntry :json-true
|
||||
:externalConsole :json-false
|
||||
:program)
|
||||
(my/rust/debug-config)
|
||||
(dap-debug))))
|
||||
(advice-add #'lsp-rust-analyzer-debug :override #'my/rust/debug-lsp-runnable)
|
||||
#+END_SRC
|
||||
** Go
|
||||
*** Debugging
|
||||
Setup: run =M-x dap-go-setup=
|
||||
* Tools
|
||||
** Projectile
|
||||
#+BEGIN_SRC elisp
|
||||
;; (setq projectile-project-search-path
|
||||
;; '("~/Code"))
|
||||
#+END_SRC
|
||||
** Counsel Search
|
||||
#+BEGIN_SRC elisp
|
||||
(let ((found (nth 0 (auth-source-search :host "kagi.com"))))
|
||||
(when found
|
||||
(let ((token (plist-get found :secret)))
|
||||
(when (functionp token)
|
||||
(setq token (funcall token)))
|
||||
(add-to-list
|
||||
'counsel-search-engines-alist
|
||||
`(kagi
|
||||
"https://duckduckgo.com/ac/"
|
||||
,(format "https://kagi.com/search?token=%s&q=" token)
|
||||
counsel--search-request-data-ddg))
|
||||
(setq counsel-search-engine 'kagi))))
|
||||
#+END_SRC
|
||||
|
||||
* Apps
|
||||
** Emacs Everywhere
|
||||
#+BEGIN_SRC elisp
|
||||
(load! "lisp/emacs-everywhere.el")
|
||||
(setq emacs-everywhere-paste-command '("xdotool" "key" "--clearmodifiers" "ctrl+v"))
|
||||
(setq emacs-everywhere-frame-parameters
|
||||
'((title . "Emacs Everywhere")
|
||||
(width . 120)
|
||||
(height . 36)))
|
||||
#+END_SRC
|
||||
* Lisp
|
||||
** Editing
|
||||
#+BEGIN_SRC elisp
|
||||
(defun my/line ()
|
||||
(buffer-substring-no-properties
|
||||
(line-beginning-position)
|
||||
(line-end-position)))
|
||||
|
||||
(defun my/line-match-p (regexp)
|
||||
(string-match-p regexp (my/line)))
|
||||
#+END_SRC
|
||||
|
||||
#+BEGIN_SRC elisp
|
||||
(defun my/insert-mode-p ()
|
||||
(eq evil-state 'insert))
|
||||
(defun my/normal-mode-p ()
|
||||
(eq evil-state 'normal))
|
||||
#+END_SRC
|
||||
|
||||
** Keybindings
|
||||
#+BEGIN_SRC elisp
|
||||
(defun my/kbd-replace (str)
|
||||
"Convert STR into a keyboard macro string by replacing terminal key sequences with GUI keycodes."
|
||||
(let ((kbd-regex '(("ESC" . "<escape>")
|
||||
("DEL" . "<delete>" )
|
||||
("BS" . "<backspace>")
|
||||
("RET" . "<return>")
|
||||
("SPC" . "<SPC>")
|
||||
("TAB" . "<tab>"))))
|
||||
(my/replace-regexps-in-string str kbd-regex)))
|
||||
|
||||
(setq my//kbd-p nil)
|
||||
(defun my/kbd!-p () (eq my//kbd-p t))
|
||||
|
||||
(defun kbd! (str)
|
||||
"Execute the key sequence defined by STR like a VIM macro."
|
||||
(let ((minibuffer-message-timeout 0))
|
||||
(setq my//kbd-p t)
|
||||
(execute-kbd-macro (read-kbd-macro (my/kbd-replace str)))
|
||||
(setq my//kbd-p nil)))
|
||||
#+END_SRC
|
||||
|
||||
|
||||
#+BEGIN_SRC elisp
|
||||
(defun my/buffer-local-set-key (key fn)
|
||||
(let ((mode (intern (format "%s-local-mode" (buffer-name))))
|
||||
(map (intern (format "%s-local-mode-map" (buffer-name)))))
|
||||
(unless (boundp map)
|
||||
(set map (make-sparse-keymap))
|
||||
(evil-make-overriding-map map 'normal))
|
||||
(eval
|
||||
`(define-minor-mode ,mode
|
||||
"A minor mode for buffer-local keybinds."
|
||||
:keymap ,map))
|
||||
(eval
|
||||
`(define-key ,map ,key #',fn))
|
||||
(funcall mode t)))
|
||||
#+END_SRC
|
||||
|
||||
** Regex
|
||||
#+BEGIN_SRC elisp
|
||||
(defun my/replace-regexps-in-string (str regexps)
|
||||
"Replace all pairs of (regex . replacement) defined by REGEXPS in STR."
|
||||
(if (null regexps)
|
||||
str
|
||||
(my/replace-regexps-in-string
|
||||
(replace-regexp-in-string (caar regexps) (cdar regexps) str t)
|
||||
(cdr regexps))))
|
||||
#+END_SRC
|
2
.doom.d/env.el
Normal file
2
.doom.d/env.el
Normal file
@ -0,0 +1,2 @@
|
||||
("DISPLAY=:0"
|
||||
"SSH_AUTH_SOCK=/run/user/1000/gnupg/S.gpg-agent.ssh")
|
189
.doom.d/init.el
Normal file
189
.doom.d/init.el
Normal file
@ -0,0 +1,189 @@
|
||||
;;; init.el -*- lexical-binding: t; -*-
|
||||
|
||||
;; This file controls what Doom modules are enabled and what order they load
|
||||
;; in. Remember to run 'doom sync' after modifying it!
|
||||
|
||||
;; NOTE Press 'SPC h d h' (or 'C-h d h' for non-vim users) to access Doom's
|
||||
;; documentation. There you'll find a "Module Index" link where you'll find
|
||||
;; a comprehensive list of Doom's modules and what flags they support.
|
||||
|
||||
;; NOTE Move your cursor over a module's name (or its flags) and press 'K' (or
|
||||
;; 'C-c c k' for non-vim users) to view its documentation. This works on
|
||||
;; flags as well (those symbols that start with a plus).
|
||||
;;
|
||||
;; Alternatively, press 'gd' (or 'C-c c d') on a module to browse its
|
||||
;; directory (for easy access to its source code).
|
||||
|
||||
(doom! :input
|
||||
;;chinese
|
||||
;;japanese
|
||||
;;layout ; auie,ctsrnm is the superior home row
|
||||
|
||||
:completion
|
||||
company ; the ultimate code completion backend
|
||||
;;helm ; the *other* search engine for love and life
|
||||
;;ido ; the other *other* search engine...
|
||||
(ivy +prescient +icons) ; a search engine for love and life
|
||||
vertico ; the search engine of the future
|
||||
|
||||
:ui
|
||||
;;deft ; notational velocity for Emacs
|
||||
doom ; what makes DOOM look the way it does
|
||||
doom-dashboard ; a nifty splash screen for Emacs
|
||||
doom-quit ; DOOM quit-message prompts when you quit Emacs
|
||||
(emoji +unicode) ; 🙂
|
||||
hl-todo ; highlight TODO/FIXME/NOTE/DEPRECATED/HACK/REVIEW
|
||||
hydra
|
||||
;;indent-guides ; highlighted indent columns
|
||||
;;ligatures ; ligatures and symbols to make your code pretty again
|
||||
;;minimap ; show a map of the code on the side
|
||||
modeline ; snazzy, Atom-inspired modeline, plus API
|
||||
;;nav-flash ; blink cursor line after big motions
|
||||
;;neotree ; a project drawer, like NERDTree for vim
|
||||
ophints ; highlight the region an operation acts on
|
||||
(popup +defaults) ; tame sudden yet inevitable temporary windows
|
||||
;;tabs ; a tab bar for Emacs
|
||||
(treemacs +lsp) ; a project drawer, like neotree but cooler
|
||||
;;unicode ; extended unicode support for various languages
|
||||
vc-gutter ; vcs diff in the fringe
|
||||
vi-tilde-fringe ; fringe tildes to mark beyond EOB
|
||||
;;window-select ; visually switch windows
|
||||
workspaces ; tab emulation, persistence & separate workspaces
|
||||
;;zen ; distraction-free coding or writing
|
||||
|
||||
:editor
|
||||
(evil +everywhere); come to the dark side, we have cookies
|
||||
;;file-templates ; auto-snippets for empty files
|
||||
fold ; (nigh) universal code folding
|
||||
format ; (+onsave) automated prettiness
|
||||
;;god ; run Emacs commands without modifier keys
|
||||
lispy ; vim for lisp, for people who don't like vim
|
||||
multiple-cursors ; editing in many places at once
|
||||
;;objed ; text object editing for the innocent
|
||||
;;parinfer ; turn lisp into python, sort of
|
||||
;;rotate-text ; cycle region at point between text candidates
|
||||
snippets ; my elves. They type so I don't have to
|
||||
;;word-wrap ; soft wrapping with language-aware indent
|
||||
|
||||
:emacs
|
||||
dired ; making dired pretty [functional]
|
||||
electric ; smarter, keyword-based electric-indent
|
||||
;;ibuffer ; interactive buffer management
|
||||
undo ; persistent, smarter undo for your inevitable mistakes
|
||||
vc ; version-control and Emacs, sitting in a tree
|
||||
|
||||
:term
|
||||
eshell ; the elisp shell that works everywhere
|
||||
;;shell ; simple shell REPL for Emacs
|
||||
;;term ; basic terminal emulator for Emacs
|
||||
;;vterm ; the best terminal emulation in Emacs
|
||||
|
||||
:checkers
|
||||
syntax ; tasing you for every semicolon you forget
|
||||
;;(spell +flyspell) ; tasing you for misspelling mispelling
|
||||
;;grammar ; tasing grammar mistake every you make
|
||||
|
||||
:tools
|
||||
;;ansible
|
||||
(debugger +lsp) ; FIXME stepping through code, to help you add bugs
|
||||
;;direnv
|
||||
docker
|
||||
editorconfig ; let someone else argue about tabs vs spaces
|
||||
;;ein ; tame Jupyter notebooks with emacs
|
||||
(eval +overlay) ; run code, run (also, repls)
|
||||
;;gist ; interacting with github gists
|
||||
lookup ; navigate your code and its documentation
|
||||
lsp ; M-x vscode
|
||||
(magit +forge) ; a git porcelain for Emacs
|
||||
make ; run make tasks from Emacs
|
||||
;;pass ; password manager for nerds
|
||||
pdf ; pdf enhancements
|
||||
;;prodigy ; FIXME managing external services & code builders
|
||||
;;rgb ; creating color strings
|
||||
taskrunner ; taskrunner for all your projects
|
||||
terraform ; infrastructure as code
|
||||
tmux ; an API for interacting with tmux
|
||||
;;upload ; map local to remote projects via ssh/ftp
|
||||
|
||||
:os
|
||||
(:if IS-MAC macos) ; improve compatibility with macOS
|
||||
;;tty ; improve the terminal Emacs experience
|
||||
|
||||
:lang
|
||||
;;agda ; types of types of types of types...
|
||||
;;beancount ; mind the GAAP
|
||||
(cc +lsp) ; C > C++ == 1
|
||||
;;clojure ; java with a lisp
|
||||
;;common-lisp ; if you've seen one lisp, you've seen them all
|
||||
;;coq ; proofs-as-programs
|
||||
;;crystal ; ruby at the speed of c
|
||||
;;csharp ; unity, .NET, and mono shenanigans
|
||||
;;data ; config/data formats
|
||||
;;(dart +flutter) ; paint ui and not much else
|
||||
;;dhall
|
||||
elixir ; erlang done right
|
||||
;;elm ; care for a cup of TEA?
|
||||
emacs-lisp ; drown in parentheses
|
||||
;;erlang ; an elegant language for a more civilized age
|
||||
;;ess ; emacs speaks statistics
|
||||
;;factor
|
||||
;;faust ; dsp, but you get to keep your soul
|
||||
;;fsharp ; ML stands for Microsoft's Language
|
||||
;;fstar ; (dependent) types and (monadic) effects and Z3
|
||||
;;gdscript ; the language you waited for
|
||||
(go +lsp) ; the hipster dialect
|
||||
(haskell +lsp) ; a language that's lazier than I am
|
||||
;;hy ; readability of scheme w/ speed of python
|
||||
;;idris ; a language you can depend on
|
||||
json ; At least it ain't XML
|
||||
(java +meghanada) ; the poster child for carpal tunnel syndrome
|
||||
javascript ; all(hope(abandon(ye(who(enter(here))))))
|
||||
julia ; a better, faster MATLAB
|
||||
;;kotlin ; a better, slicker Java(Script)
|
||||
latex ; writing papers in Emacs has never been so fun
|
||||
;;lean ; for folks with too much to prove
|
||||
;;ledger ; be audit you can be
|
||||
lua ; one-based indices? one-based indices
|
||||
markdown ; writing docs for people to ignore
|
||||
;;nim ; python + lisp at the speed of c
|
||||
;;nix ; I hereby declare "nix geht mehr!"
|
||||
;;ocaml ; an objective camel
|
||||
org ; organize your plain life in plain text
|
||||
php ; perl's insecure younger brother
|
||||
;;plantuml ; diagrams for confusing people more
|
||||
;;purescript ; javascript, but functional
|
||||
(python +lsp +pyright) ; beautiful is better than ugly
|
||||
;;qt ; the 'cutest' gui framework ever
|
||||
;;racket ; a DSL for DSLs
|
||||
;;raku ; the artist formerly known as perl6
|
||||
;;rest ; Emacs as a REST client
|
||||
;;rst ; ReST in peace
|
||||
;;(ruby +rails) ; 1.step {|i| p "Ruby is #{i.even? ? 'love' : 'life'}"}
|
||||
(rust +lsp) ; Fe2O3.unwrap().unwrap().unwrap().unwrap()
|
||||
;;scala ; java, but good
|
||||
(scheme +guile) ; a fully conniving family of lisps
|
||||
(sh +fish) ; she sells {ba,z,fi}sh shells on the C xor
|
||||
;;sml
|
||||
;;solidity ; do you need a blockchain? No.
|
||||
;;swift ; who asked for emoji variables?
|
||||
;;terra ; Earth and Moon in alignment for performance.
|
||||
web ; the tubes
|
||||
yaml ; JSON, but readable
|
||||
;;zig ; C, but simpler
|
||||
|
||||
:email
|
||||
;;(mu4e +org +gmail)
|
||||
;;notmuch
|
||||
;;(wanderlust +gmail)
|
||||
|
||||
:app
|
||||
calendar
|
||||
;;emms
|
||||
everywhere ; *leave* Emacs!? You must be joking
|
||||
irc ; how neckbeards socialize
|
||||
;;(rss +org) ; emacs as an RSS reader
|
||||
;;twitter ; twitter client https://twitter.com/vnought
|
||||
|
||||
:config
|
||||
literate
|
||||
(default +bindings +smartparens))
|
546
.doom.d/lisp/emacs-everywhere.el
Normal file
546
.doom.d/lisp/emacs-everywhere.el
Normal file
@ -0,0 +1,546 @@
|
||||
;;; emacs-everywhere.el --- System-wide popup windows for quick edits -*- lexical-binding: t; -*-
|
||||
|
||||
;; Copyright (C) 2021 TEC
|
||||
|
||||
;; Author: TEC <https://github.com/tecosaur>
|
||||
;; Maintainer: TEC <tec@tecosaur.com>
|
||||
;; Created: February 06, 2021
|
||||
;; Modified: February 06, 2021
|
||||
;; Version: 0.1.0
|
||||
;; Keywords: conenience, frames
|
||||
;; Homepage: https://github.com/tecosaur/emacs-everywhere
|
||||
;; Package-Requires: ((emacs "26.3"))
|
||||
|
||||
;;; License:
|
||||
|
||||
;; This file is part of org-pandoc-import, which is not part of GNU Emacs.
|
||||
;; SPDX-License-Identifier: GPL-3.0-or-later
|
||||
|
||||
;;; Commentary:
|
||||
|
||||
;; System-wide popup Emacs windows for quick edits
|
||||
|
||||
;;; Code:
|
||||
|
||||
(require 'cl-lib)
|
||||
(require 'server)
|
||||
|
||||
(defgroup emacs-everywhere ()
|
||||
"Customise group for Emacs-everywhere."
|
||||
:group 'convenience)
|
||||
|
||||
(define-obsolete-variable-alias
|
||||
'emacs-everywhere-paste-p 'emacs-everywhere-paste-command "0.1.0")
|
||||
|
||||
(defvar emacs-everywhere--display-server
|
||||
(cond
|
||||
((eq system-type 'darwin) 'quartz)
|
||||
((memq system-type '(ms-dos windows-nt cygwin)) 'windows)
|
||||
((executable-find "loginctl")
|
||||
(pcase (string-trim
|
||||
(shell-command-to-string "loginctl show-session $(loginctl | grep $(whoami) | awk '{print $1}') -p Type")
|
||||
"Type=" "\n")
|
||||
("x11" 'x11)
|
||||
("wayland" 'wayland)
|
||||
(_ 'unknown)))
|
||||
(t 'unknown))
|
||||
"The detected display server.")
|
||||
|
||||
(defcustom emacs-everywhere-paste-command
|
||||
(pcase emacs-everywhere--display-server
|
||||
('quartz (list "osascript" "-e" "tell application \"System Events\" to keystroke \"v\" using command down"))
|
||||
('x11 (list "xdotool" "key" "--clearmodifiers" "Shift+Insert"))
|
||||
((or 'wayland 'unknown)
|
||||
(list "notify-send"
|
||||
"No paste command defined for emacs-everywhere"
|
||||
"-a" "Emacs" "-i" "emacs")))
|
||||
"Command to trigger a system paste from the clipboard.
|
||||
This is given as a list in the form (CMD ARGS...).
|
||||
To not run any command, set to nil."
|
||||
:type '(set (repeat string) (const nil))
|
||||
:group 'emacs-everywhere)
|
||||
|
||||
(defcustom emacs-everywhere-copy-command
|
||||
(pcase emacs-everywhere--display-server
|
||||
('x11 (list "xclip" "-selection" "clipboard" "%f"))
|
||||
((and 'wayland (guard (executable-find "wl-copy")))
|
||||
(list "sh" "-c" "wl-copy < %f")))
|
||||
"Command to write to the system clipboard from a file (%f).
|
||||
This is given as a list in the form (CMD ARGS...).
|
||||
In the arguments, \"%f\" is treated as a placeholder for the path
|
||||
to the file.
|
||||
When nil, nothing is executed.
|
||||
`gui-select-text' is always called on the buffer content, however experience
|
||||
suggests that this can be somewhat flakey, and so an extra step to make sure
|
||||
it worked can be a good idea."
|
||||
:type '(set (repeat string) (const nil))
|
||||
:group 'emacs-everywhere)
|
||||
|
||||
(defcustom emacs-everywhere-window-focus-command
|
||||
(pcase emacs-everywhere--display-server
|
||||
('quartz (list "osascript" "-e" "tell application \"%w\" to activate"))
|
||||
('x11 (list "xdotool" "windowactivate" "--sync" "%w")))
|
||||
"Command to refocus the active window when emacs-everywhere was triggered.
|
||||
This is given as a list in the form (CMD ARGS...).
|
||||
In the arguments, \"%w\" is treated as a placeholder for the window ID,
|
||||
as returned by `emacs-everywhere-app-id'.
|
||||
When nil, nothing is executed, and pasting is not attempted."
|
||||
:type '(set (repeat string) (const nil))
|
||||
:group 'emacs-everywhere)
|
||||
|
||||
(defcustom emacs-everywhere-markdown-windows
|
||||
'("Reddit" "Stack Exchange" "Stack Overflow" ; Sites
|
||||
"Discord" "Element" "Slack" "HedgeDoc" "HackMD" "Zulip" ; Web Apps
|
||||
"Pull Request" "Issue" "Comparing .*\\.\\.\\.") ; Github
|
||||
"For use with `emacs-everywhere-markdown-p'.
|
||||
Patterns which are matched against the window title."
|
||||
:type '(rep string)
|
||||
:group 'emacs-everywhere)
|
||||
|
||||
(defcustom emacs-everywhere-markdown-apps
|
||||
'("Discord" "Element" "Fractal" "NeoChat" "Slack")
|
||||
"For use with `emacs-everywhere-markdown-p'.
|
||||
Patterns which are matched against the app name."
|
||||
:type '(rep string)
|
||||
:group 'emacs-everywhere)
|
||||
|
||||
(defcustom emacs-everywhere-frame-name-format "Emacs Everywhere :: %s — %s"
|
||||
"Format string used to produce the frame name.
|
||||
Formatted with the app name, and truncated window name."
|
||||
:type 'string
|
||||
:group 'emacs-everywhere)
|
||||
|
||||
(defcustom emacs-everywhere-init-hooks
|
||||
`(emacs-everywhere-set-frame-name
|
||||
emacs-everywhere-set-frame-position
|
||||
,(cond
|
||||
((executable-find "pandoc") #'org-mode)
|
||||
((fboundp 'markdown-mode) #'emacs-everywhere-major-mode-org-or-markdown)
|
||||
(t #'text-mode))
|
||||
emacs-everywhere-insert-selection
|
||||
emacs-everywhere-remove-trailing-whitespace
|
||||
emacs-everywhere-init-spell-check)
|
||||
"Hooks to be run before function `emacs-everywhere-mode'."
|
||||
:type 'hook
|
||||
:group 'emacs-everywhere)
|
||||
|
||||
(defcustom emacs-everywhere-final-hooks
|
||||
'(emacs-everywhere-remove-trailing-whitespace
|
||||
emacs-everywhere-return-converted-org-to-gfm)
|
||||
"Hooks to be run just before content is copied."
|
||||
:type 'hook
|
||||
:group 'emacs-everywhere)
|
||||
|
||||
(defcustom emacs-everywhere-frame-parameters
|
||||
`((name . "emacs-everywhere")
|
||||
(width . 80)
|
||||
(height . 12))
|
||||
"Parameters `make-frame' recognises to apply to the emacs-everywhere frame."
|
||||
:type 'list
|
||||
:group 'emacs-everywhere)
|
||||
|
||||
(defcustom emacs-everywhere-file-dir
|
||||
temporary-file-directory
|
||||
"The default directory for temp files generated by `emacs-everywhere-filename-function'."
|
||||
:type 'string
|
||||
:group 'emacs-everywhere)
|
||||
|
||||
(defcustom emacs-everywhere-file-patterns
|
||||
(let ((default-directory emacs-everywhere-file-dir))
|
||||
(list (concat "^" (regexp-quote (file-truename "emacs-everywhere-")))
|
||||
;; For qutebrowser 'editor.command' support
|
||||
(concat "^" (regexp-quote (file-truename "qutebrowser-editor-")))))
|
||||
"A list of file regexps to activate `emacs-everywhere-mode' for."
|
||||
:type '(repeat regexp)
|
||||
:group 'emacs-everywhere)
|
||||
|
||||
(defun emacs-everywhere-temp-filename (app-info)
|
||||
"Generate a temp file."
|
||||
(concat "emacs-everywhere-"
|
||||
(format-time-string "%Y%m%d-%H%M%S-" (current-time))
|
||||
(emacs-everywhere-app-class app-info)))
|
||||
|
||||
(defcustom emacs-everywhere-filename-function
|
||||
#'emacs-everywhere-temp-filename
|
||||
"A function which generates a file name for the buffer.
|
||||
The function is passed the result of `emacs-everywhere-app-info'.
|
||||
Make sure that it will be matched by `emacs-everywhere-file-patterns'."
|
||||
:type 'function
|
||||
:group 'emacs-everywhere)
|
||||
|
||||
;; Semi-internal variables
|
||||
|
||||
(defconst emacs-everywhere-osascript-accessibility-error-message
|
||||
"osascript is not allowed assistive access"
|
||||
"String to search for to determine if Emacs does not have accessibility rights.")
|
||||
|
||||
(defvar-local emacs-everywhere-current-app nil
|
||||
"The current `emacs-everywhere-app'")
|
||||
;; Prevents buffer-local variable from being unset by major mode changes
|
||||
(put 'emacs-everywhere-current-app 'permanent-local t)
|
||||
|
||||
(defvar-local emacs-everywhere--contents nil)
|
||||
|
||||
;; Make the byte-compiler happier
|
||||
|
||||
(declare-function org-in-src-block-p "org")
|
||||
(declare-function org-ctrl-c-ctrl-c "org")
|
||||
(declare-function org-export-to-buffer "ox")
|
||||
(declare-function evil-insert-state "evil-states")
|
||||
(declare-function spell-fu-buffer "spell-fu")
|
||||
(declare-function markdown-mode "markdown-mode")
|
||||
|
||||
;;; Primary functionality
|
||||
|
||||
;;;###autoload
|
||||
(defun emacs-everywhere (&optional file line column)
|
||||
"Lanuch the emacs-everywhere frame from emacsclient."
|
||||
(let ((app-info (emacs-everywhere-app-info)))
|
||||
(apply #'call-process "emacsclient" nil 0 nil
|
||||
(delq
|
||||
nil (list
|
||||
(when (server-running-p)
|
||||
(if server-use-tcp
|
||||
(concat "--server-file="
|
||||
(shell-quote-argument
|
||||
(expand-file-name server-name server-auth-dir)))
|
||||
(concat "--socket-name="
|
||||
(shell-quote-argument
|
||||
(expand-file-name server-name server-socket-dir)))))
|
||||
"-c" "-F"
|
||||
(prin1-to-string
|
||||
(cons (cons 'emacs-everywhere-app app-info)
|
||||
emacs-everywhere-frame-parameters))
|
||||
(cond ((and line column) (format "+%d:%d" line column))
|
||||
(line (format "+%d" line)))
|
||||
(or file
|
||||
(expand-file-name
|
||||
(funcall emacs-everywhere-filename-function app-info)
|
||||
emacs-everywhere-file-dir)))))))
|
||||
|
||||
(defun emacs-everywhere-file-p (file)
|
||||
"Return non-nil if FILE should be handled by emacs-everywhere.
|
||||
This matches FILE against `emacs-everywhere-file-patterns'."
|
||||
(let ((file (file-truename file)))
|
||||
(cl-some (lambda (pattern) (string-match-p pattern file))
|
||||
emacs-everywhere-file-patterns)))
|
||||
|
||||
;;;###autoload
|
||||
(defun emacs-everywhere-initialise ()
|
||||
"Entry point for the executable.
|
||||
APP is an `emacs-everywhere-app' struct."
|
||||
(let ((file (buffer-file-name (buffer-base-buffer))))
|
||||
(when (and file (emacs-everywhere-file-p file))
|
||||
(let ((app (or (frame-parameter nil 'emacs-everywhere-app)
|
||||
(emacs-everywhere-app-info))))
|
||||
(setq-local emacs-everywhere-current-app app)
|
||||
(with-demoted-errors "Emacs Everywhere: error running init hooks, %s"
|
||||
(run-hooks 'emacs-everywhere-init-hooks))
|
||||
(emacs-everywhere-mode 1)
|
||||
(setq emacs-everywhere--contents (buffer-string))))))
|
||||
|
||||
;;;###autoload
|
||||
(add-hook 'server-visit-hook #'emacs-everywhere-initialise)
|
||||
(add-hook 'server-done-hook #'emacs-everywhere-finish)
|
||||
|
||||
(defvar emacs-everywhere-mode-initial-map
|
||||
(let ((keymap (make-sparse-keymap)))
|
||||
(define-key keymap (kbd "DEL") #'emacs-everywhere-erase-buffer)
|
||||
(define-key keymap (kbd "C-SPC") #'emacs-everywhere-erase-buffer)
|
||||
keymap)
|
||||
"Transient keymap invoked when an emacs-everywhere buffer is first created.
|
||||
Set to `nil' to prevent this transient map from activating in emacs-everywhere
|
||||
buffers.")
|
||||
|
||||
(define-minor-mode emacs-everywhere-mode
|
||||
"Tweak the current buffer to add some emacs-everywhere considerations."
|
||||
:init-value nil
|
||||
:keymap `((,(kbd "C-c C-c") . emacs-everywhere-finish-or-ctrl-c-ctrl-c)
|
||||
(,(kbd "C-x 5 0") . emacs-everywhere-finish)
|
||||
(,(kbd "C-c C-k") . emacs-everywhere-abort))
|
||||
;; line breaking
|
||||
(turn-off-auto-fill)
|
||||
(visual-line-mode t)
|
||||
;; DEL/C-SPC to clear (first keystroke only)
|
||||
(when (keymapp emacs-everywhere-mode-initial-map)
|
||||
(set-transient-map emacs-everywhere-mode-initial-map)))
|
||||
|
||||
(defun emacs-everywhere-erase-buffer ()
|
||||
"Delete the contents of the current buffer."
|
||||
(interactive)
|
||||
(delete-region (point-min) (point-max)))
|
||||
|
||||
(defun emacs-everywhere-finish-or-ctrl-c-ctrl-c ()
|
||||
"Finish emacs-everywhere session or invoke `org-ctrl-c-ctrl-c' in org-mode."
|
||||
(interactive)
|
||||
(if (and (eq major-mode 'org-mode)
|
||||
(org-in-src-block-p))
|
||||
(org-ctrl-c-ctrl-c)
|
||||
(emacs-everywhere-finish)))
|
||||
|
||||
(defun emacs-everywhere-finish (&optional abort)
|
||||
"Copy buffer content, close emacs-everywhere window, and maybe paste.
|
||||
Must only be called within a emacs-everywhere buffer.
|
||||
Never paste content when ABORT is non-nil."
|
||||
(interactive)
|
||||
(when emacs-everywhere-mode
|
||||
(when (equal emacs-everywhere--contents (buffer-string))
|
||||
(setq abort t))
|
||||
(unless abort
|
||||
(run-hooks 'emacs-everywhere-final-hooks)
|
||||
(gui-select-text (buffer-string))
|
||||
(when emacs-everywhere-copy-command ; handle clipboard finicklyness
|
||||
(let ((inhibit-message t)
|
||||
(require-final-newline nil)
|
||||
write-file-functions)
|
||||
(write-file buffer-file-name)
|
||||
(apply #'call-process (car emacs-everywhere-copy-command)
|
||||
nil nil nil
|
||||
(mapcar (lambda (arg)
|
||||
(replace-regexp-in-string "%f" buffer-file-name arg))
|
||||
(cdr emacs-everywhere-copy-command))))))
|
||||
(sleep-for 0.01) ; prevents weird multi-second pause, lets clipboard info propagate
|
||||
(when emacs-everywhere-window-focus-command
|
||||
(let* ((window-id (emacs-everywhere-app-id emacs-everywhere-current-app))
|
||||
(window-id-str (if (numberp window-id) (number-to-string window-id) window-id)))
|
||||
(apply #'call-process (car emacs-everywhere-window-focus-command)
|
||||
nil nil nil
|
||||
(mapcar (lambda (arg)
|
||||
(replace-regexp-in-string "%w" window-id-str arg))
|
||||
(cdr emacs-everywhere-window-focus-command)))
|
||||
;; The frame only has this parameter if this package initialized the temp
|
||||
;; file its displaying. Otherwise, it was created by another program, likely
|
||||
;; a browser with direct EDITOR support, like qutebrowser.
|
||||
(when (and (frame-parameter nil 'emacs-everywhere-app)
|
||||
emacs-everywhere-paste-command
|
||||
(not abort))
|
||||
(apply #'call-process (car emacs-everywhere-paste-command)
|
||||
nil nil nil (cdr emacs-everywhere-paste-command)))))
|
||||
;; Clean up after ourselves in case the buffer survives `server-buffer-done'
|
||||
;; (b/c `server-existing-buffer' is non-nil).
|
||||
(emacs-everywhere-mode -1)
|
||||
(server-buffer-done (current-buffer))))
|
||||
|
||||
(defun emacs-everywhere-abort ()
|
||||
"Abort current emacs-everywhere session."
|
||||
(interactive)
|
||||
(set-buffer-modified-p nil)
|
||||
(emacs-everywhere-finish t))
|
||||
|
||||
;;; Window info
|
||||
|
||||
(cl-defstruct emacs-everywhere-app
|
||||
"Metadata about the last focused window before emacs-everywhere was invoked."
|
||||
id class title geometry)
|
||||
|
||||
(defun emacs-everywhere-app-info ()
|
||||
"Return information on the active window."
|
||||
(let ((w (pcase system-type
|
||||
(`darwin (emacs-everywhere-app-info-osx))
|
||||
(_ (emacs-everywhere-app-info-linux)))))
|
||||
(setf (emacs-everywhere-app-title w)
|
||||
(replace-regexp-in-string
|
||||
(format " ?-[A-Za-z0-9 ]*%s"
|
||||
(regexp-quote (emacs-everywhere-app-class w)))
|
||||
""
|
||||
(replace-regexp-in-string
|
||||
"[^[:ascii:]]+" "-" (emacs-everywhere-app-title w))))
|
||||
w))
|
||||
|
||||
(defun emacs-everywhere-call (command &rest args)
|
||||
"Execute COMMAND with ARGS synchronously."
|
||||
(with-temp-buffer
|
||||
(apply #'call-process command nil t nil (remq nil args))
|
||||
(when (and (eq system-type 'darwin)
|
||||
(string-match-p emacs-everywhere-osascript-accessibility-error-message (buffer-string)))
|
||||
(call-process "osascript" nil nil nil
|
||||
"-e" (format "display alert \"emacs-everywhere\" message \"Emacs has not been granted accessibility permissions, cannot run emacs-everywhere!
|
||||
Please go to 'System Preferences > Security & Privacy > Privacy > Accessibility' and allow Emacs.\"" ))
|
||||
(error "MacOS accessibility error, aborting."))
|
||||
(string-trim (buffer-string))))
|
||||
|
||||
(defun emacs-everywhere-app-info-linux ()
|
||||
"Return information on the active window, on linux."
|
||||
(let ((window-id (emacs-everywhere-call "xdotool" "getactivewindow")))
|
||||
(let ((app-name
|
||||
(car (split-string-and-unquote
|
||||
(string-trim-left
|
||||
(emacs-everywhere-call "xprop" "-id" window-id "WM_CLASS")
|
||||
"[^ ]+ = \"[^\"]+\", "))))
|
||||
(window-title
|
||||
(car (split-string-and-unquote
|
||||
(string-trim-left
|
||||
(emacs-everywhere-call "xprop" "-id" window-id "_NET_WM_NAME")
|
||||
"[^ ]+ = "))))
|
||||
(window-geometry
|
||||
(let ((info (mapcar (lambda (line)
|
||||
(split-string line ":" nil "[ \t]+"))
|
||||
(split-string
|
||||
(emacs-everywhere-call "xwininfo" "-id" window-id) "\n"))))
|
||||
(mapcar #'string-to-number
|
||||
(list (cadr (assoc "Absolute upper-left X" info))
|
||||
(cadr (assoc "Absolute upper-left Y" info))
|
||||
(cadr (assoc "Relative upper-left X" info))
|
||||
(cadr (assoc "Relative upper-left Y" info))
|
||||
(cadr (assoc "Width" info))
|
||||
(cadr (assoc "Height" info)))))))
|
||||
(make-emacs-everywhere-app
|
||||
:id (string-to-number window-id)
|
||||
:class app-name
|
||||
:title window-title
|
||||
:geometry (list
|
||||
(if (= (nth 0 window-geometry) (nth 2 window-geometry))
|
||||
(nth 0 window-geometry)
|
||||
(- (nth 0 window-geometry) (nth 2 window-geometry)))
|
||||
(if (= (nth 1 window-geometry) (nth 3 window-geometry))
|
||||
(nth 1 window-geometry)
|
||||
(- (nth 1 window-geometry) (nth 3 window-geometry)))
|
||||
(nth 4 window-geometry)
|
||||
(nth 5 window-geometry))))))
|
||||
|
||||
(defvar emacs-everywhere--dir (file-name-directory load-file-name))
|
||||
|
||||
(defun emacs-everywhere-app-info-osx ()
|
||||
"Return information on the active window, on osx."
|
||||
(emacs-everywhere-ensure-oscascript-compiled)
|
||||
(let ((default-directory emacs-everywhere--dir))
|
||||
(let ((app-name (emacs-everywhere-call
|
||||
"osascript" "app-name"))
|
||||
(window-title (emacs-everywhere-call
|
||||
"osascript" "window-title"))
|
||||
(window-geometry (mapcar #'string-to-number
|
||||
(split-string
|
||||
(emacs-everywhere-call
|
||||
"osascript" "window-geometry") ", "))))
|
||||
(make-emacs-everywhere-app
|
||||
:id app-name
|
||||
:class app-name
|
||||
:title window-title
|
||||
:geometry window-geometry))))
|
||||
|
||||
(defun emacs-everywhere-ensure-oscascript-compiled (&optional force)
|
||||
"Ensure that compiled oscascript files are present.
|
||||
Will always compile when FORCE is non-nil."
|
||||
(unless (and (file-exists-p "app-name")
|
||||
(file-exists-p "window-geometry")
|
||||
(file-exists-p "window-title")
|
||||
(not force))
|
||||
(let ((default-directory emacs-everywhere--dir)
|
||||
(app-name
|
||||
"tell application \"System Events\"
|
||||
set frontAppName to name of first application process whose frontmost is true
|
||||
end tell
|
||||
return frontAppName")
|
||||
(window-geometry
|
||||
"tell application \"System Events\"
|
||||
set frontWindow to front window of (first application process whose frontmost is true)
|
||||
set windowPosition to (get position of frontWindow)
|
||||
set windowSize to (get size of frontWindow)
|
||||
end tell
|
||||
return windowPosition & windowSize")
|
||||
(window-title
|
||||
"set windowTitle to \"\"
|
||||
tell application \"System Events\"
|
||||
set frontAppProcess to first application process whose frontmost is true
|
||||
end tell
|
||||
tell frontAppProcess
|
||||
if count of windows > 0 then
|
||||
set windowTitle to name of front window
|
||||
end if
|
||||
end tell
|
||||
return windowTitle"))
|
||||
(dolist (script `(("app-name" . ,app-name)
|
||||
("window-geometry" . ,window-geometry)
|
||||
("window-title" . ,window-title)))
|
||||
(write-region (cdr script) nil (concat (car script) ".applescript"))
|
||||
(shell-command (format "osacompile -r scpt:128 -t osas -o %s %s"
|
||||
(car script) (concat (car script) ".applescript")))))))
|
||||
|
||||
;;; Secondary functionality
|
||||
|
||||
(defun emacs-everywhere-set-frame-name ()
|
||||
"Set the frame name based on `emacs-everywhere-frame-name-format'."
|
||||
(set-frame-name
|
||||
(format emacs-everywhere-frame-name-format
|
||||
(emacs-everywhere-app-class emacs-everywhere-current-app)
|
||||
(truncate-string-to-width
|
||||
(emacs-everywhere-app-title emacs-everywhere-current-app)
|
||||
45 nil nil "…"))))
|
||||
|
||||
(defun emacs-everywhere-remove-trailing-whitespace ()
|
||||
"Move point to the end of the buffer, and remove all trailing whitespace."
|
||||
(goto-char (max-char))
|
||||
(delete-trailing-whitespace)
|
||||
(delete-char (- (skip-chars-backward "\n"))))
|
||||
|
||||
(defun emacs-everywhere-set-frame-position ()
|
||||
"Set the size and position of the emacs-everywhere frame."
|
||||
(cl-destructuring-bind (x . y) (mouse-absolute-pixel-position)
|
||||
(set-frame-position (selected-frame)
|
||||
(- x 100)
|
||||
(- y 50))))
|
||||
|
||||
(defun emacs-everywhere-insert-selection ()
|
||||
"Insert the last text selection into the buffer."
|
||||
(if (eq system-type 'darwin)
|
||||
(progn
|
||||
(call-process "osascript" nil nil nil
|
||||
"-e" "tell application \"System Events\" to keystroke \"c\" using command down")
|
||||
(sleep-for 0.01) ; lets clipboard info propagate
|
||||
(yank))
|
||||
(when-let ((selection (gui-get-selection 'PRIMARY 'UTF8_STRING)))
|
||||
(gui-backend-set-selection 'PRIMARY "")
|
||||
(insert selection)))
|
||||
(when (and (eq major-mode 'org-mode)
|
||||
(emacs-everywhere-markdown-p)
|
||||
(executable-find "pandoc"))
|
||||
(shell-command-on-region (point-min) (point-max)
|
||||
"pandoc -f markdown-auto_identifiers -t org" nil t)
|
||||
(deactivate-mark) (goto-char (point-max)))
|
||||
(cond ((bound-and-true-p evil-local-mode) (evil-insert-state))))
|
||||
|
||||
(defun emacs-everywhere-init-spell-check ()
|
||||
"Run a spell check function on the buffer, using a relevant enabled mode."
|
||||
(cond ((bound-and-true-p spell-fu-mode) (spell-fu-buffer))
|
||||
((bound-and-true-p flyspell-mode) (flyspell-buffer))))
|
||||
|
||||
(defun emacs-everywhere-markdown-p ()
|
||||
"Return t if the original window is recognised as markdown-flavoured."
|
||||
(let ((title (emacs-everywhere-app-title emacs-everywhere-current-app))
|
||||
(class (emacs-everywhere-app-class emacs-everywhere-current-app)))
|
||||
(or (cl-some (lambda (pattern)
|
||||
(string-match-p pattern title))
|
||||
emacs-everywhere-markdown-windows)
|
||||
(cl-some (lambda (pattern)
|
||||
(string-match-p pattern class))
|
||||
emacs-everywhere-markdown-apps))))
|
||||
|
||||
(defun emacs-everywhere-major-mode-org-or-markdown ()
|
||||
"Use markdow-mode, when window is recognised as markdown-flavoured.
|
||||
Otherwise use `org-mode'."
|
||||
(if (emacs-everywhere-markdown-p)
|
||||
(markdown-mode)
|
||||
(org-mode)))
|
||||
|
||||
(defcustom emacs-everywhere-org-export-options
|
||||
"#+property: header-args :exports both
|
||||
#+options: toc:nil\n"
|
||||
"A string inserted at the top of the Org buffer prior to export.
|
||||
This is with the purpose of setting #+property and #+options parameters.
|
||||
Should end in a newline to avoid interfering with the buffer content."
|
||||
:type 'string
|
||||
:group 'emacs-everywhere)
|
||||
|
||||
(defvar org-export-show-temporary-export-buffer)
|
||||
(defun emacs-everywhere-return-converted-org-to-gfm ()
|
||||
"When appropriate, convert org buffer to markdown."
|
||||
(when (and (eq major-mode 'org-mode)
|
||||
(emacs-everywhere-markdown-p))
|
||||
(goto-char (point-min))
|
||||
(insert emacs-everywhere-org-export-options)
|
||||
(let (org-export-show-temporary-export-buffer)
|
||||
(require 'ox-md)
|
||||
(org-export-to-buffer (if (featurep 'ox-gfm) 'gfm 'md) (current-buffer)))))
|
||||
|
||||
(provide 'emacs-everywhere)
|
||||
;;; emacs-everywhere.el ends here
|
57
.doom.d/packages.el
Normal file
57
.doom.d/packages.el
Normal file
@ -0,0 +1,57 @@
|
||||
;; -*- no-byte-compile: t; -*-
|
||||
;;; $DOOMDIR/packages.el
|
||||
|
||||
;; To install a package with Doom you must declare them here and run 'doom sync'
|
||||
;; on the command line, then restart Emacs for the changes to take effect -- or
|
||||
;; use 'M-x doom/reload'.
|
||||
|
||||
|
||||
;; To install SOME-PACKAGE from MELPA, ELPA or emacsmirror:
|
||||
;(package! some-package)
|
||||
|
||||
;; To install a package directly from a remote git repo, you must specify a
|
||||
;; `:recipe'. You'll find documentation on what `:recipe' accepts here:
|
||||
;; https://github.com/raxod502/straight.el#the-recipe-format
|
||||
;(package! another-package
|
||||
; :recipe (:host github :repo "username/repo"))
|
||||
|
||||
;; If the package you are trying to install does not contain a PACKAGENAME.el
|
||||
;; file, or is located in a subdirectory of the repo, you'll need to specify
|
||||
;; `:files' in the `:recipe':
|
||||
;(package! this-package
|
||||
; :recipe (:host github :repo "username/repo"
|
||||
; :files ("some-file.el" "src/lisp/*.el")))
|
||||
|
||||
;; If you'd like to disable a package included with Doom, you can do so here
|
||||
;; with the `:disable' property:
|
||||
;(package! builtin-package :disable t)
|
||||
|
||||
;; You can override the recipe of a built in package without having to specify
|
||||
;; all the properties for `:recipe'. These will inherit the rest of its recipe
|
||||
;; from Doom or MELPA/ELPA/Emacsmirror:
|
||||
;(package! builtin-package :recipe (:nonrecursive t))
|
||||
;(package! builtin-package-2 :recipe (:repo "myfork/package"))
|
||||
|
||||
;; Specify a `:branch' to install a package from a particular branch or tag.
|
||||
;; This is required for some packages whose default branch isn't 'master' (which
|
||||
;; our package manager can't deal with; see raxod502/straight.el#279)
|
||||
;(package! builtin-package :recipe (:branch "develop"))
|
||||
|
||||
;; Use `:pin' to specify a particular commit to install.
|
||||
;(package! builtin-package :pin "1a2b3c4d5e")
|
||||
|
||||
|
||||
;; Doom's packages are pinned to a specific commit and updated from release to
|
||||
;; release. The `unpin!' macro allows you to unpin single packages...
|
||||
;(unpin! pinned-package)
|
||||
;; ...or multiple packages
|
||||
;(unpin! pinned-package another-pinned-package)
|
||||
;; ...Or *all* packages (NOT RECOMMENDED; will likely break things)
|
||||
;(unpin! t)
|
||||
|
||||
(package! emacs-everywhere :ignore t)
|
||||
(package! doom-snippets :ignore t)
|
||||
|
||||
(package! copilot
|
||||
:recipe (:host github :repo "zerolfx/copilot.el"
|
||||
:files ("dist" "copilot.el")))
|
0
.doom.d/snippets/org-config-mode/.yas-parents
Normal file
0
.doom.d/snippets/org-config-mode/.yas-parents
Normal file
8
.doom.d/snippets/org-mode/src_elisp
Normal file
8
.doom.d/snippets/org-mode/src_elisp
Normal file
@ -0,0 +1,8 @@
|
||||
# -*- mode: snippet -*-
|
||||
# name: src_elisp
|
||||
# key: <el
|
||||
# expand-env: ((yas-after-exit-snippet-hook #'org-edit-special))
|
||||
# --
|
||||
#+BEGIN_SRC elisp
|
||||
$0
|
||||
#+END_SRC
|
154
.doom.d/themes/doom-catppuccin-theme.el
Normal file
154
.doom.d/themes/doom-catppuccin-theme.el
Normal file
@ -0,0 +1,154 @@
|
||||
;;; doom-catppuccin-theme.el --- inspired by Catppuccin -*- lexical-binding: t; no-byte-compile: t; -*-
|
||||
|
||||
(require 'doom-themes)
|
||||
|
||||
|
||||
;;
|
||||
;;; Variables
|
||||
|
||||
(defgroup doom-catppuccin-theme nil
|
||||
"Options for the `doom-catppuccin' theme."
|
||||
:group 'doom-themes)
|
||||
|
||||
(defcustom doom-catppuccin-brighter-modeline nil
|
||||
"If non-nil, more vivid colors will be used to style the mode-line."
|
||||
:group 'doom-catppuccin-theme
|
||||
:type 'boolean)
|
||||
|
||||
(defcustom doom-catppuccin-brighter-comments nil
|
||||
"If non-nil, comments will be highlighted in more vivid colors."
|
||||
:group 'doom-catppuccin-theme
|
||||
:type 'boolean)
|
||||
|
||||
(defcustom doom-catppuccin-padded-modeline doom-themes-padded-modeline
|
||||
"If non-nil, adds a 4px padding to the mode-line.
|
||||
Can be an integer to determine the exact padding."
|
||||
:group 'doom-catppuccin-theme
|
||||
:type '(choice integer boolean))
|
||||
|
||||
|
||||
;;
|
||||
;;; Theme definition
|
||||
|
||||
(def-doom-theme doom-catppuccin
|
||||
"A dark theme inspired by Catppuccin."
|
||||
|
||||
;; name default 256 16
|
||||
((bg '("#1e1e2e" "black" "black" ))
|
||||
(fg '("#d9e0ee" "#bfbfbf" "brightwhite" ))
|
||||
|
||||
;; These are off-color variants of bg/fg, used primarily for `solaire-mode',
|
||||
;; but can also be useful as a basis for subtle highlights (e.g. for hl-line
|
||||
;; or region), especially when paired with the `doom-darken', `doom-lighten',
|
||||
;; and `doom-blend' helper functions.
|
||||
(bg-alt '("#1a1826" "black" "black" ))
|
||||
(fg-alt '("#d9e0ee" "#2d2d2d" "white" ))
|
||||
|
||||
;; These should represent a spectrum from bg to fg, where base0 is a starker
|
||||
;; bg and base8 is a starker fg. For example, if bg is light grey and fg is
|
||||
;; dark grey, base0 should be white and base8 should be black.
|
||||
(base0 '("#161320" "black" "black" ))
|
||||
(base1 '("#1a1826" "#1e1e1e" "brightblack" ))
|
||||
(base2 '("#1e1e1e" "#2e2e2e" "brightblack" ))
|
||||
(base3 '("#302d41" "#262626" "brightblack" ))
|
||||
(base4 '("#575268" "#3f3f3f" "brightblack" ))
|
||||
(base5 '("#6e6c7e" "#525252" "brightblack" ))
|
||||
(base6 '("#988ba2" "#6b6b6b" "brightblack" ))
|
||||
(base7 '("#c3bac6" "#979797" "brightblack" ))
|
||||
(base8 '("#d9e0ee" "#dfdfdf" "white" ))
|
||||
|
||||
(grey base4)
|
||||
(red '("#f28fad" "#ff6655" "red" ))
|
||||
(orange '("#f8bd96" "#dd8844" "brightred" ))
|
||||
(green '("#abe9b3" "#99bb66" "green" ))
|
||||
(teal '("#b5e8e0" "#44b9b1" "brightgreen" ))
|
||||
(yellow '("#fae3b0" "#ECBE7B" "yellow" ))
|
||||
(blue '("#96cdfb" "#51afef" "brightblue" ))
|
||||
(dark-blue '("#96cdfb" "#2257A0" "blue" ))
|
||||
(magenta '("#f5c2e7" "#c678dd" "brightmagenta"))
|
||||
(violet '("#ddb6f2" "#a9a1e1" "magenta" ))
|
||||
(cyan '("#89dceb" "#46D9FF" "brightcyan" ))
|
||||
(dark-cyan '("#89dceb" "#5699AF" "cyan" ))
|
||||
|
||||
;; These are the "universal syntax classes" that doom-themes establishes.
|
||||
;; These *must* be included in every doom themes, or your theme will throw an
|
||||
;; error, as they are used in the base theme defined in doom-themes-base.
|
||||
(highlight magenta)
|
||||
(vertical-bar (doom-darken base1 0.1))
|
||||
(selection dark-blue)
|
||||
(builtin teal)
|
||||
(comments (if doom-catppuccin-brighter-comments green base5))
|
||||
(doc-comments (doom-lighten (if doom-catppuccin-brighter-comments green base5) 0.25))
|
||||
(constants orange)
|
||||
(functions blue)
|
||||
(keywords magenta)
|
||||
(methods blue)
|
||||
(operators blue)
|
||||
(type yellow)
|
||||
(strings green)
|
||||
(variables cyan)
|
||||
;; (variables (doom-lighten magenta 0.4))
|
||||
(numbers orange)
|
||||
(region `(,(doom-lighten (car bg-alt) 0.15) ,@(doom-lighten (cdr base1) 0.35)))
|
||||
(error red)
|
||||
(warning yellow)
|
||||
(success green)
|
||||
(vc-modified orange)
|
||||
(vc-added green)
|
||||
(vc-deleted red)
|
||||
|
||||
;; These are extra color variables used only in this theme; i.e. they aren't
|
||||
;; mandatory for derived themes.
|
||||
(modeline-fg fg)
|
||||
(modeline-fg-alt base5)
|
||||
(modeline-bg (if doom-catppuccin-brighter-modeline
|
||||
(doom-darken blue 0.45)
|
||||
(doom-darken bg-alt 0.1)))
|
||||
(modeline-bg-alt (if doom-catppuccin-brighter-modeline
|
||||
(doom-darken blue 0.475)
|
||||
`(,(doom-darken (car bg-alt) 0.15) ,@(cdr bg))))
|
||||
(modeline-bg-inactive `(,(car bg-alt) ,@(cdr base1)))
|
||||
(modeline-bg-inactive-alt `(,(doom-darken (car bg-alt) 0.1) ,@(cdr bg)))
|
||||
|
||||
(-modeline-pad
|
||||
(when doom-catppuccin-padded-modeline
|
||||
(if (integerp doom-catppuccin-padded-modeline) doom-catppuccin-padded-modeline 4))))
|
||||
|
||||
|
||||
;;;; Base theme face overrides
|
||||
(((line-number &override) :foreground base4)
|
||||
((line-number-current-line &override) :foreground fg)
|
||||
((font-lock-comment-face &override)
|
||||
:background (if doom-catppuccin-brighter-comments (doom-lighten bg 0.05)))
|
||||
(mode-line
|
||||
:background modeline-bg :foreground modeline-fg
|
||||
:box (if -modeline-pad `(:line-width ,-modeline-pad :color ,modeline-bg)))
|
||||
(mode-line-inactive
|
||||
:background modeline-bg-inactive :foreground modeline-fg-alt
|
||||
:box (if -modeline-pad `(:line-width ,-modeline-pad :color ,modeline-bg-inactive)))
|
||||
(mode-line-emphasis :foreground (if doom-catppuccin-brighter-modeline base8 highlight))
|
||||
|
||||
;;;; css-mode <built-in> / scss-mode
|
||||
(css-proprietary-property :foreground orange)
|
||||
(css-property :foreground magenta)
|
||||
(css-selector :foreground blue)
|
||||
;;;; doom-modeline
|
||||
(doom-modeline-bar :background (if doom-catppuccin-brighter-modeline modeline-bg highlight))
|
||||
(doom-modeline-buffer-file :inherit 'mode-line-buffer-id :weight 'bold)
|
||||
(doom-modeline-buffer-path :inherit 'mode-line-emphasis :weight 'bold)
|
||||
(doom-modeline-buffer-project-root :foreground magenta :weight 'bold)
|
||||
;;;; ivy
|
||||
(ivy-current-match :background dark-blue :distant-foreground base0 :weight 'normal)
|
||||
;;;; LaTeX-mode
|
||||
(font-latex-math-face :foreground magenta)
|
||||
;;;; markdown-mode
|
||||
(markdown-markup-face :foreground base5)
|
||||
(markdown-header-face :inherit 'bold :foreground red)
|
||||
((markdown-code-face &override) :background (doom-lighten base3 0.05))
|
||||
;;;; rjsx-mode
|
||||
)
|
||||
|
||||
;;;; Base theme variable overrides-
|
||||
())
|
||||
|
||||
;;; doom-catppuccin-theme.el ends here
|
Loading…
Reference in New Issue
Block a user