You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

1309 lines
44 KiB

2 months ago
2 months ago
2 months ago
  1. ;;; init.el --- -*- lexical-binding: t -*-
  2. (defun my/tangle-config ()
  3. "Export code blocks from the literate config file."
  4. (interactive)
  5. ;; prevent emacs from killing until tangle-process has finished
  6. (add-to-list 'kill-emacs-query-functions
  7. (lambda ()
  8. (or (not (process-live-p (get-process "tangle-process")))
  9. (y-or-n-p "\"my/tangle-config\" is running; kill it? "))))
  10. (org-babel-tangle-file config-org init-el)
  11. (message "reloading user-init-file")
  12. (load-file init-el))
  13. (add-hook 'org-mode-hook
  14. (lambda ()
  15. (if (equal (buffer-file-name) config-org)
  16. (my--add-local-hook 'after-save-hook 'my/tangle-config))))
  17. (defun my--add-local-hook (hook function)
  18. "Add buffer-local hook."
  19. (add-hook hook function :local t))
  20. (add-hook 'emacs-startup-hook
  21. (lambda ()
  22. (message "Emacs ready in %s with %d garbage collections."
  23. (format "%.2f seconds"
  24. (float-time
  25. (time-subtract after-init-time before-init-time)))
  26. gcs-done)))
  27. ;(setq gc-cons-threshold (* 50 1000 1000))
  28. (defconst *sys/gui*
  29. (display-graphic-p)
  30. "Is emacs running in a gui?")
  31. (defconst *sys/linux*
  32. (string-equal system-type 'gnu/linux)
  33. "Is the system running Linux?")
  34. (defconst *sys/windows*
  35. (string-equal system-type 'windows-nt)
  36. "Is the system running Windows?")
  37. (defconst *home_desktop*
  38. (string-equal (system-name) "marc")
  39. "Is emacs running on my desktop?")
  40. (defconst *home_laptop*
  41. (string-equal (system-name) "laptop")
  42. "Is emacs running on my laptop?")
  43. (defconst *work_local*
  44. (string-equal (system-name) "PMPCNEU08")
  45. "Is emacs running at work on the local system?")
  46. (defconst *work_remote*
  47. (or (string-equal (system-name) "PMTS01")
  48. (string-equal (system-name) "PMTSNEU01"))
  49. "Is emacs running at work on the remote system?")
  50. (defvar MY--PATH_USER_LOCAL (concat user-emacs-directory "user-local/"))
  51. (defvar MY--PATH_USER_GLOBAL (concat user-emacs-directory "user-global/"))
  52. (add-to-list 'custom-theme-load-path (concat MY--PATH_USER_GLOBAL "themes"))
  53. (when *sys/linux*
  54. (defconst MY--PATH_ORG_FILES (expand-file-name "~/Archiv/Organisieren/"))
  55. (defconst MY--PATH_ORG_FILES_MOBILE (expand-file-name "~/Archiv/Organisieren/mobile/"))
  56. (defconst MY--PATH_ORG_JOURNAl (expand-file-name "~/Archiv/Organisieren/Journal/"))
  57. (defconst MY--PATH_ORG_ROAM (file-truename "~/Archiv/Organisieren/")))
  58. (when *work_remote*
  59. (defconst MY--PATH_ORG_FILES "p:/Eigene Dateien/Notizen/")
  60. (defconst MY--PATH_ORG_FILES_MOBILE nil) ;; hacky way to prevent "free variable" compiler error
  61. (defconst MY--PATH_ORG_JOURNAL nil) ;; hacky way to prevent "free variable" compiler error
  62. (defconst MY--PATH_START "p:/Eigene Dateien/Notizen/")
  63. (defconst MY--PATH_ORG_ROAM (expand-file-name "p:/Eigene Dateien/Notizen/")))
  64. (setq custom-file (concat MY--PATH_USER_LOCAL "custom.el")) ;; don't spam init.e with saved customization settings
  65. (setq backup-directory-alist `((".*" . ,temporary-file-directory)))
  66. (setq auto-save-file-name-transforms `((".*" ,temporary-file-directory)))
  67. (customize-set-variable 'auth-sources (list (concat MY--PATH_USER_LOCAL "authinfo")
  68. (concat MY--PATH_USER_LOCAL "authinfo.gpg")
  69. (concat MY--PATH_USER_LOCAL "netrc")))
  70. (defvar elpaca-installer-version 0.7)
  71. (defvar elpaca-directory (expand-file-name "elpaca/" user-emacs-directory))
  72. (defvar elpaca-builds-directory (expand-file-name "builds/" elpaca-directory))
  73. (defvar elpaca-repos-directory (expand-file-name "repos/" elpaca-directory))
  74. (defvar elpaca-order '(elpaca :repo "https://github.com/progfolio/elpaca.git"
  75. :ref nil :depth 1
  76. :files (:defaults "elpaca-test.el" (:exclude "extensions"))
  77. :build (:not elpaca--activate-package)))
  78. (let* ((repo (expand-file-name "elpaca/" elpaca-repos-directory))
  79. (build (expand-file-name "elpaca/" elpaca-builds-directory))
  80. (order (cdr elpaca-order))
  81. (default-directory repo))
  82. (add-to-list 'load-path (if (file-exists-p build) build repo))
  83. (unless (file-exists-p repo)
  84. (make-directory repo t)
  85. (when (< emacs-major-version 28) (require 'subr-x))
  86. (condition-case-unless-debug err
  87. (if-let ((buffer (pop-to-buffer-same-window "*elpaca-bootstrap*"))
  88. ((zerop (apply #'call-process `("git" nil ,buffer t "clone"
  89. ,@(when-let ((depth (plist-get order :depth)))
  90. (list (format "--depth=%d" depth) "--no-single-branch"))
  91. ,(plist-get order :repo) ,repo))))
  92. ((zerop (call-process "git" nil buffer t "checkout"
  93. (or (plist-get order :ref) "--"))))
  94. (emacs (concat invocation-directory invocation-name))
  95. ((zerop (call-process emacs nil buffer nil "-Q" "-L" "." "--batch"
  96. "--eval" "(byte-recompile-directory \".\" 0 'force)")))
  97. ((require 'elpaca))
  98. ((elpaca-generate-autoloads "elpaca" repo)))
  99. (progn (message "%s" (buffer-string)) (kill-buffer buffer))
  100. (error "%s" (with-current-buffer buffer (buffer-string))))
  101. ((error) (warn "%s" err) (delete-directory repo 'recursive))))
  102. (unless (require 'elpaca-autoloads nil t)
  103. (require 'elpaca)
  104. (elpaca-generate-autoloads "elpaca" repo)
  105. (load "./elpaca-autoloads")))
  106. (add-hook 'after-init-hook #'elpaca-process-queues)
  107. (elpaca `(,@elpaca-order))
  108. ;;at work symlinks wont work, and open file limit can be an issue
  109. (when *work_remote*
  110. (setq elpaca-queue-limit 12)
  111. (elpaca-no-symlink-mode))
  112. ;(setq use-package-always-ensure t)
  113. (elpaca elpaca-use-package
  114. ;; enable use-package :ensure support for elpaca
  115. (elpaca-use-package-mode))
  116. (elpaca-wait)
  117. (defmacro use-feature (name &rest args)
  118. "Like `use-package' but accounting for asynchronous installation.
  119. NAME and ARGS are in `use-package'."
  120. (declare (indent defun))
  121. `(use-package ,name
  122. :ensure nil
  123. ,@args))
  124. (use-package general
  125. :ensure t
  126. :demand t)
  127. (use-package diminish
  128. :ensure t
  129. :demand t)
  130. ;;wait for elpaca any time a use-package keyword is added
  131. (elpaca-wait)
  132. (setq-default create-lockfiles nil) ;; disable lock files, can cause trouble in e.g. lsp-mode
  133. (defalias 'yes-or-no-p 'y-or-n-p) ;; answer with y and n
  134. (setq custom-safe-themes t) ;; don't ask me if I want to load a theme
  135. (setq sentence-end-double-space nil) ;; don't coun two spaces after a period as the end of a sentence.
  136. (delete-selection-mode t) ;; delete selected region when typing
  137. (use-package saveplace
  138. :ensure nil
  139. :config
  140. (save-place-mode 1) ;; saves position in file when it's closed
  141. :custom
  142. (save-place-file (concat MY--PATH_USER_LOCAL "places")))
  143. (setq save-place-forget-unreadable-files nil) ;; checks if file is readable before saving position
  144. (global-set-key (kbd "RET") 'newline-and-indent) ;; indent after newline
  145. (setq save-interprogram-paste-before-kill t) ;; put replaced text into killring
  146. ;; https://emacs.stackexchange.com/questions/3673/how-to-make-vc-and-magit-treat-a-symbolic-link-to-a-real-file-in-git-repo-just
  147. (setq find-file-visit-truename t) ;; some programs like lsp have trouble following symlinks, maybe vc-follow-symlinks would be enough
  148. (defconst 1mb 1048576)
  149. (defconst 20mb 20971520)
  150. (defconst 30mb 31457280)
  151. (defconst 50mb 52428800)
  152. (defun my--defer-garbage-collection ()
  153. (setq gc-cons-threshold most-positive-fixnum))
  154. (defun my--restore-garbage-collection ()
  155. (run-at-time 1 nil (lambda () (setq gc-cons-threshold 30mb))))
  156. (add-hook 'emacs-startup-hook 'my--restore-garbage-collection 100)
  157. (add-hook 'minibuffer-setup-hook 'my--defer-garbage-collection)
  158. (add-hook 'minibuffer-exit-hook 'my--restore-garbage-collection)
  159. (setq read-process-output-max 1mb) ;; lsp-mode's performance suggest
  160. (set-charset-priority 'unicode)
  161. (setq-default locale-coding-system 'utf-8
  162. default-process-coding-system '(utf-8-unix . utf-8-unix))
  163. (set-terminal-coding-system 'utf-8)
  164. (set-keyboard-coding-system 'utf-8)
  165. (set-selection-coding-system 'utf-8)
  166. (if *sys/windows*
  167. (progn
  168. (prefer-coding-system 'utf-8-dos)
  169. (set-clipboard-coding-system 'utf-16-le)
  170. (set-selection-coding-system 'utf-16-le))
  171. (prefer-coding-system 'utf-8))
  172. (setq-default bidi-paragraph-direction 'left-to-right
  173. bidi-inhibit-bpa t ;; both settings reduce line rescans
  174. uniquify-buffer-name-style 'forward
  175. indent-tabs-mode nil ;; avoid tabs in place of multiple spaces (they look bad in tex)
  176. indicate-empty-lines t ;; show empty lines
  177. scroll-margin 5 ;; smooth scrolling
  178. scroll-conservatively 10000
  179. scroll-preserve-screen-position 1
  180. scroll-step 1
  181. ring-bell-function 'ignore ;; disable pc speaker bell
  182. visible-bell t)
  183. (global-hl-line-mode t) ;; highlight current line
  184. (blink-cursor-mode -1) ;; turn off blinking cursor
  185. (column-number-mode t)
  186. (when *sys/linux*
  187. (set-face-font 'default "Hack-10"))
  188. (when *work_remote*
  189. (set-face-font 'default "Lucida Sans Typewriter-11"))
  190. (defun my/toggle-theme ()
  191. (interactive)
  192. (when (or *sys/windows* *sys/linux*)
  193. (if (eq (car custom-enabled-themes) 'plastic)
  194. (progn (disable-theme 'plastic)
  195. (load-theme 'leuven))
  196. (progn
  197. (disable-theme 'leuven)
  198. (load-theme 'plastic)))))
  199. (bind-key "C-c t" 'my/toggle-theme)
  200. (when *sys/windows*
  201. (mapcar #'disable-theme custom-enabled-themes)
  202. (load-theme 'tango))
  203. (when *sys/linux*
  204. (mapcar #'disable-theme custom-enabled-themes)
  205. (load-theme 'plastic))
  206. (global-visual-line-mode)
  207. ;(diminish 'visual-line-mode)
  208. (use-package adaptive-wrap
  209. :ensure t
  210. :hook
  211. (visual-line-mode . adaptive-wrap-prefix-mode))
  212. ; :init
  213. ; (when (fboundp 'adaptive-wrap-prefix-mode)
  214. ; (defun me/activate-adaptive-wrap-prefix-mode ()
  215. ; "Toggle `visual-line-mode' and `adaptive-wrap-prefix-mode' simultaneously."
  216. ; (adaptive-wrap-prefix-mode (if visual-line-mode 1 -1)))
  217. ; (add-hook 'visual-line-mode-hook 'me/activate-adaptive-wrap-prefix-mode)))
  218. (use-package display-line-numbers
  219. :ensure nil
  220. :init
  221. :hook
  222. ((prog-mode
  223. org-src-mode) . display-line-numbers-mode)
  224. :config
  225. (setq-default display-line-numbers-type 'visual
  226. display-line-numbers-current-absolute t
  227. display-line-numbers-with 4
  228. display-line-numbers-widen t))
  229. (use-package rainbow-mode
  230. :ensure t
  231. :diminish
  232. :hook
  233. ((org-mode
  234. emacs-lisp-mode) . rainbow-mode))
  235. (use-package delight
  236. :if *sys/linux*
  237. :ensure t)
  238. (show-paren-mode t) ;; show other part of brackets
  239. (setq blink-matching-paren nil) ;; not necessary with show-paren-mode, bugs out on C-s counsel-line
  240. (use-package rainbow-delimiters
  241. :ensure t
  242. :hook
  243. (prog-mode . rainbow-delimiters-mode))
  244. (use-package dired
  245. :ensure nil
  246. :custom
  247. (dired-kill-when-opening-new-dired-buffer t))
  248. (use-package bookmark
  249. :ensure nil
  250. :custom
  251. (bookmark-default-file (concat MY--PATH_USER_LOCAL "bookmarks")))
  252. ;;do I really want this?
  253. (use-package bookmark+
  254. :ensure (:host github :repo "emacsmirror/bookmark-plus"))
  255. (when *sys/windows*
  256. (remove-hook 'find-file-hook 'vc-refresh-state)
  257. ; (progn
  258. ; (setq gc-cons-threshold (* 511 1024 1024)
  259. ; gc-cons-percentage 0.5
  260. ; garbage-collection-messages t
  261. ; (run-with-idle-timer 5 t #'garbage-collect))
  262. (when (boundp 'w32-pipe-read-delay)
  263. (setq w32-pipe-read-delay 0))
  264. (when (boundp 'w32-get-true-file-attributes)
  265. (setq w32-get-true-file-attributes nil)))
  266. (use-package burly
  267. :ensure t
  268. :config
  269. (burly-tabs-mode) ;;open a burly window bookbark in a new tab
  270. )
  271. (use-package recentf
  272. :ensure nil
  273. ; :defer 1
  274. :config
  275. (recentf-mode)
  276. :custom
  277. (recentf-exclude '(".*-autoloads\\.el\\'"
  278. "[/\\]\\elpa/"
  279. "COMMIT_EDITMSG\\'"))
  280. (recentf-save-file (concat MY--PATH_USER_LOCAL "recentf"))
  281. (recentf-max-menu-items 600)
  282. (recentf-max-saved-items 600))
  283. (use-package savehist
  284. :ensure nil
  285. :config
  286. (savehist-mode)
  287. :custom
  288. (savehist-file (concat MY--PATH_USER_LOCAL "history")))
  289. (use-package undo-tree
  290. :ensure t
  291. :diminish undo-tree-mode
  292. :init
  293. (global-undo-tree-mode 1)
  294. :custom
  295. (undo-tree-auto-save-history nil))
  296. (use-package which-key
  297. :ensure t
  298. :diminish which-key-mode
  299. :custom
  300. (which-key-idle-delay 0.5)
  301. (which-key-sort-order 'which-key-description-order)
  302. :config
  303. (which-key-mode)
  304. (which-key-setup-side-window-bottom))
  305. (use-package abbrev
  306. :ensure nil
  307. :diminish abbrev-mode
  308. :hook
  309. ((text-mode org-mode) . abbrev-mode)
  310. :init
  311. (setq abbrev-file-name (concat MY--PATH_USER_GLOBAL "abbrev_tables.el"))
  312. :config
  313. (if (file-exists-p abbrev-file-name)
  314. (quietly-read-abbrev-file))
  315. (setq save-abbrevs 'silently)) ;; don't bother me with asking for abbrev saving
  316. (use-package imenu-list
  317. :ensure t
  318. :demand t ; otherwise mode loads too late and won't work on first file it's being activated on
  319. :config
  320. (setq imenu-list-focus-after-activation t
  321. imenu-list-auto-resize t
  322. imenu-list-position 'right)
  323. :general
  324. ([f9] 'imenu-list-smart-toggle)
  325. (:states '(normal insert)
  326. :keymaps 'imenu-list-major-mode-map
  327. "RET" '(imenu-list-goto-entry :which-key "goto")
  328. "TAB" '(hs-toggle-hiding :which-key "collapse")
  329. "v" '(imenu-list-display-entry :which-key "show") ; also prevents visual mode
  330. "q" '(imenu-list-quit-window :which-key "quit"))
  331. :custom
  332. (org-imenu-depth 4))
  333. (use-package eldoc
  334. :ensure nil
  335. :diminish eldoc-mode
  336. :defer t)
  337. (use-package meow
  338. :ensure t
  339. :config
  340. (setq meow-cheatsheet-layout meow-cheatsheet-layout-qwerty)
  341. (meow-motion-overwrite-define-key
  342. '("j" . meow-next)
  343. '("k" . meow-prev)
  344. '("<escape>" . ignore))
  345. (meow-leader-define-key
  346. ;; SPC j/k will run the original command in MOTION state.
  347. '("j" . "H-j")
  348. '("k" . "H-k")
  349. ;; Use SPC (0-9) for digit arguments.
  350. '("1" . meow-digit-argument)
  351. '("2" . meow-digit-argument)
  352. '("3" . meow-digit-argument)
  353. '("4" . meow-digit-argument)
  354. '("5" . meow-digit-argument)
  355. '("6" . meow-digit-argument)
  356. '("7" . meow-digit-argument)
  357. '("8" . meow-digit-argument)
  358. '("9" . meow-digit-argument)
  359. '("0" . meow-digit-argument)
  360. '("/" . meow-keypad-describe-key)
  361. '("?" . meow-cheatsheet))
  362. (meow-normal-define-key
  363. '("0" . meow-expand-0)
  364. '("9" . meow-expand-9)
  365. '("8" . meow-expand-8)
  366. '("7" . meow-expand-7)
  367. '("6" . meow-expand-6)
  368. '("5" . meow-expand-5)
  369. '("4" . meow-expand-4)
  370. '("3" . meow-expand-3)
  371. '("2" . meow-expand-2)
  372. '("1" . meow-expand-1)
  373. '("-" . negative-argument)
  374. '(";" . meow-reverse)
  375. '("," . meow-inner-of-thing)
  376. '("." . meow-bounds-of-thing)
  377. '("[" . meow-beginning-of-thing)
  378. '("]" . meow-end-of-thing)
  379. '("a" . meow-append)
  380. '("A" . meow-open-below)
  381. '("b" . meow-back-word)
  382. '("B" . meow-back-symbol)
  383. '("c" . meow-change)
  384. '("d" . meow-delete)
  385. '("D" . meow-backward-delete)
  386. '("e" . meow-next-word)
  387. '("E" . meow-next-symbol)
  388. '("f" . meow-find)
  389. '("g" . meow-cancel-selection)
  390. '("G" . meow-grab)
  391. '("h" . meow-left)
  392. '("H" . meow-left-expand)
  393. '("i" . meow-insert)
  394. '("I" . meow-open-above)
  395. '("j" . meow-next)
  396. '("J" . meow-next-expand)
  397. '("k" . meow-prev)
  398. '("K" . meow-prev-expand)
  399. '("l" . meow-right)
  400. '("L" . meow-right-expand)
  401. '("m" . meow-join)
  402. '("n" . meow-search)
  403. '("o" . meow-block)
  404. '("O" . meow-to-block)
  405. '("p" . meow-yank)
  406. '("q" . meow-quit)
  407. '("Q" . meow-goto-line)
  408. '("r" . meow-replace)
  409. '("R" . meow-swap-grab)
  410. '("s" . meow-kill)
  411. '("t" . meow-till)
  412. '("u" . meow-undo)
  413. '("U" . meow-undo-in-selection)
  414. '("v" . meow-visit)
  415. '("w" . meow-mark-word)
  416. '("W" . meow-mark-symbol)
  417. '("x" . meow-line)
  418. '("X" . meow-goto-line)
  419. '("y" . meow-save)
  420. '("Y" . meow-sync-grab)
  421. '("z" . meow-pop-selection)
  422. '("'" . repeat)
  423. '("<escape>" . ignore))
  424. ; :config
  425. (meow-global-mode t))
  426. (use-package avy
  427. :ensure t
  428. :general
  429. (:prefix "M-s"
  430. "" '(:ignore t :which-key "avy")
  431. "w" '(avy-goto-char-2 :which-key "avy-jump")
  432. "s" '(avy-goto-char-timer :which-key "avy-timer")
  433. "c" '(:ignore t :which-key "avy copy")
  434. "c l" '(avy-copy-line :which-key "avy copy line")
  435. "c r" '(avy-copy-region :which-key "avy copy region")
  436. "m" '(:ignore t :which-key "avy move")
  437. "m l" '(avy-move-line :which-key "avy move line")
  438. "m r" '(avy-move-region :which-key "avy move region")))
  439. ;; completion ui
  440. (use-package vertico
  441. :ensure t
  442. :init
  443. (vertico-mode))
  444. (use-package corfu
  445. :ensure t
  446. :after savehist
  447. :custom
  448. (corfu-popupinfo-delay t)
  449. (corfu-auto t)
  450. (corfu-cycle t)
  451. (corfu-auto-delay 0.3)
  452. (corfu-preselect-first nil)
  453. (corfu-popupinfo-delay '(1.0 . 0.0)) ;1s for first popup, instant for subsequent popups
  454. (corfu-popupinfo-max-width 70)
  455. (corfu-popupinfo-max-height 20)
  456. :init
  457. (global-corfu-mode)
  458. ; (corfu-popupinfo-mode) ; causes corfu window to stay
  459. (corfu-history-mode)
  460. ;; belongs to emacs
  461. (add-to-list 'savehist-additional-variables 'corfu-history)
  462. :hook
  463. (corfu-mode . corfu-popupinfo-mode))
  464. ; :bind
  465. ; (:map corfu-map
  466. ; ("TAB" . corfu-next)
  467. ; ("<C-return>" . corfu-insert)
  468. ; ("C-TAB" . corfu-popupinfo-toggle)))
  469. ;; (general-define-key
  470. ;; :states 'insert
  471. ;; :definer 'minor-mode
  472. ;; :keymaps 'completion-in-region-mode
  473. ;; :predicate 'corfu-mode
  474. ;; "C-d" 'corfu-info-documentation)
  475. (use-package emacs
  476. :ensure nil
  477. :init
  478. ;; hide commands in M-x which do not apply to current mode
  479. (setq read-extended-command-predicate #'command-completion-default-include-p)
  480. ;; enable indentation + completion using TAB
  481. (setq tab-always-indent 'complete))
  482. (use-package cape
  483. :ensure t
  484. :bind
  485. (("C-c p p" . completion-at-point) ;; capf
  486. ("C-c p t" . complete-tag) ;; etags
  487. ("C-c p d" . cape-dabbrev)
  488. ("C-c p h" . cape-history)
  489. ("C-c p f" . cape-file))
  490. :init
  491. (advice-add #'lsp-completion-at-point :around #'cape-wrap-noninterruptible) ;; for performance issues with lsp
  492. (add-to-list 'completion-at-point-functions #'cape-dabbrev)
  493. (add-to-list 'completion-at-point-functions #'cape-file)
  494. (add-to-list 'completion-at-point-functions #'cape-history))
  495. (use-package kind-icon
  496. :ensure t
  497. :after corfu
  498. :custom
  499. (kind-icon-default-face 'corfu-default) ;; to compute blended backgrounds correctly
  500. :config
  501. (add-to-list 'corfu-margin-formatters #'kind-icon-margin-formatter))
  502. (use-package orderless
  503. :ensure t
  504. :init
  505. (setq completion-styles '(orderless partial-completion basic)
  506. completion-category-defaults nil
  507. completion-category-overrides nil))
  508. ; completion-category-overrides '((file (styles partial-completion)))))
  509. (use-package consult
  510. :ensure t
  511. :bind
  512. (("C-x C-r" . consult-recent-file)
  513. ("C-x b" . consult-buffer)
  514. ("C-s" . consult-line)
  515. ("C-x r b" . consult-bookmark)) ;replace bookmark-jump
  516. :config
  517. ;; disable preview for some commands and buffers
  518. ;; and enable it by M-.
  519. ;; see https://github.com/minad/consult#use-package-example
  520. (consult-customize
  521. consult-theme :preview-key '(debounce 0.2 any)
  522. consult-ripgrep consult-git-grep consult-grep
  523. consult-bookmark consult-recent-file consult-xref
  524. consult--source-bookmark consult--source-file-register
  525. consult--source-recent-file consult--source-project-recent-file
  526. :preview-key '(:debounce 0.2 any)))
  527. (use-package marginalia
  528. :ensure t
  529. :init
  530. (marginalia-mode)
  531. :bind
  532. (:map minibuffer-local-map
  533. ("M-A" . marginalia-cycle))
  534. :custom
  535. ;; switch by 'marginalia-cycle
  536. (marginalia-annotators '(marginalia-annotators-heavy
  537. marginalia-annotators-light
  538. nil)))
  539. (use-package embark
  540. :ensure t
  541. :bind
  542. (("C-S-a" . embark-act)
  543. ("C-h B" . embark-bindings))
  544. :init
  545. (setq prefix-help-command #'embark-prefix-help-command)
  546. :config
  547. ;; hide modeline of the embark live/completions buffers
  548. (add-to-list 'display-buffer-alist
  549. '("\\`\\*Embark Collect \\(Live\\|Completions\\)\\*"
  550. nil
  551. (window-parameters (mode-line-format . none)))))
  552. (use-package embark-consult
  553. :ensure t
  554. :after (embark consult)
  555. :demand t
  556. :hook
  557. (embark-collect-mode . embark-consult-preview-minor-mode))
  558. (when *sys/linux*
  559. (use-package tree-sitter
  560. :ensure t
  561. :init
  562. (global-tree-sitter-mode t)
  563. :hook
  564. (tree-sitter-after-on . tree-sitter-hl-mode))
  565. (use-package tree-sitter-langs
  566. :ensure t
  567. :after tree-sitter)
  568. )
  569. (use-package org-ql
  570. :ensure t
  571. )
  572. ;(use-package notmuch
  573. ; :ensure t)
  574. (use-feature mu4e
  575. :if *sys/linux*
  576. ; :ensure nil
  577. :after (org)
  578. :init
  579. (require 'mu4e)
  580. :config
  581. ;; this is set to 't' to avoid mail syncing issues when using mbsync
  582. (setq mu4e-change-filenames-when-moving t)
  583. (setq smtpmail-servers-requiring-authorization ".*")
  584. (setq mu4e-update-interval (* 10 60))
  585. (setq mu4e-get-mail-command "mbsync -a")
  586. (setq mu4e-maildir "/mnt/archiv/Dokumente/email")
  587. (setq mu4e-headers-fields
  588. '((:human-date . 12)
  589. (:flags . 6)
  590. (:from . 22)
  591. (:to . 25)
  592. (:subject)))
  593. (setq mu4e-contexts
  594. `( ,(make-mu4e-context
  595. :name "mail.de"
  596. :enter-func (lambda () (mu4e-message "switch to mail.de context"))
  597. :match-func (lambda (msg)
  598. (when msg
  599. (string-match-p "^/mailde" (mu4e-message-field msg :maildir))))
  600. :vars '((user-mail-address . "marc.pohling@mail.de")
  601. (user-full-name . "Marc Pohling")
  602. (message-send-mail-function . smtpmail-send-it)
  603. (smtpmail-smtp-user . "marc.pohling@mail.de")
  604. (smtpmail-smtp-server . "smtp.mail.de")
  605. (smtpmail-smtp-service . 587)
  606. (smtpmail-stream-type . starttls)
  607. (mu4e-drafts-folder . "/mailde/drafts")
  608. (mu4e-sent-folder . "/mailde/sent")
  609. (mu4e-refile-folder . "/mailde/archive")
  610. (mu4e-trash-folder . "/mailde/trash")))
  611. ,(make-mu4e-context
  612. :name "web.de"
  613. :enter-func (lambda () (mu4e-message "switch to web.de context"))
  614. :match-func (lambda (msg)
  615. (when msg
  616. (string-match-p "^/mailde" (mu4e-message-field msg :maildir))))
  617. :vars '((user-mail-address . "marc.pohling@web.de")
  618. (user-full-name . "Marc Pohling")
  619. (mu4e-drafts-folder . "/webde/drafts")
  620. (mu4e-sent-folder . "/webde/sent")
  621. (mu4e-refile-folder . "/webde/archive")
  622. (mu4e-trash-folder . "/webde/trash")))
  623. ,(make-mu4e-context
  624. :name "gmail loui"
  625. :enter-func (lambda () (mu4e-message "switch to gmail loui context"))
  626. :match-func (lambda (msg)
  627. (when msg
  628. (string-match-p "^/gmailloui" (mu4e-message-field msg :maildir))))
  629. :vars '((user-mail-address . "louithelou1@gmail.com")
  630. (user-full-name . "Loui")
  631. (message-send-mail-function . smtpmail-send-it)
  632. (smtpmail-smtp-user . "louithelou1@gmail.com")
  633. (smtpmail-smtp-server . "smtp.gmail.com")
  634. (smtpmail-smtp-service . 587)
  635. (smtpmail-stream-type . starttls)
  636. (mu4e-drafts-folder . "/gmailloui/drafts")
  637. (mu4e-sent-folder . "/gmailloui/sent")
  638. (mu4e-refile-folder . "/gmailloui/archive")
  639. (mu4e-trash-folder . "/gmailloui/trash")))))
  640. )
  641. (push 'mu4e elpaca-ignored-dependencies)
  642. (use-package mu4e-dashboard
  643. :if *sys/linux*
  644. :ensure (:host github :repo "rougier/mu4e-dashboard")
  645. :after mu4e
  646. :hook
  647. (mu4e-dashboard-mode . (lambda () (display-line-numbers-mode -1)))
  648. :custom
  649. (mu4e-dashboard-file (concat MY--PATH_USER_GLOBAL "mu4e-dashboard.org"))
  650. :config
  651. ; (require 'mu4e)
  652. (defun mu4e-dashboard-edit ()
  653. (interactive)
  654. (let ((edit-buffer "*edit-mu4e-dashboard*"))
  655. (when (get-buffer edit-buffer)
  656. (kill-buffer (get-buffer edit-buffer)))
  657. (make-indirect-buffer (current-buffer) edit-buffer)
  658. (switch-to-buffer-other-window (get-buffer edit-buffer))
  659. (org-mode 1)))
  660. (display-line-numbers-mode -1)
  661. (flyspell-mode -1))
  662. ;(org-add-link-type "outlook" 'my--org-outlook-open)
  663. ;(org-add-link-type "outlooknewmail" 'my--org-outlook-new-mail)
  664. (defun my--org-outlook-open (id)
  665. (w32-shell-execute "open" "outlook" (concat " /select outlook:" id)))
  666. (defun my--org-outlook-new-mail (receipients)
  667. ; separate RECEIPIENTS for main, cc and bcc by |
  668. (setq recp (split-string receipients "|"))
  669. (setq mailstring (concat " /c ipm.note /m " (nth 0 recp)))
  670. (if (nth 1 recp)
  671. ; this check has tp be separated because (and..) would stumble over a nil
  672. (if (not (equal "" (nth 1 recp)))
  673. (setq mailstring (concat mailstring "&cc=" (nth 1 recp)))))
  674. (if (nth 2 recp)
  675. (setq mailstring (concat mailstring "&bcc=" (nth 2 recp))))
  676. (w32-shell-execute "open" "outlook" mailstring))
  677. (defun my/org-outlook-open-test ()
  678. (interactive)
  679. (w32-shell-execute "open" "outlook" " /select outlook:000000008A209C397CEF2C4FBA9E54AEB5B1F97F0700846D043B407C5B43A0C05AFC46DC5C630587BE5E020900006E48FF8F6027694BA6593777F542C19E0002A6434D000000"))'
  680. (use-package autorevert
  681. :diminish auto-revert-mode)
  682. ;(assq-delete-all 'org package--builtins)'
  683. ;(assq-delete-all 'org package--builtin-versions)
  684. (defun my--buffer-prop-set (name value)
  685. "Set a file property called NAME to VALUE in buffer file.
  686. If the property is already set, replace its value."
  687. (setq name (downcase name))
  688. (org-with-point-at 1
  689. (let ((case-fold-search t))
  690. (if (re-search-forward (concat "^#\\+" name ":\\(.*\\)")
  691. (point-max) t)
  692. (replace-match (concat "#+" name ": " value) 'fixedcase)
  693. (while (and (not (eobp))
  694. (looking-at "^[#:]"))
  695. (if (save-excursion (end-of-line) (eobp))
  696. (progn
  697. (end-of-line)
  698. (insert "\n"))
  699. (forward-line)
  700. (beginning-of-line)))
  701. (insert "#+" name ": " value "\n")))))
  702. (defun my--buffer-prop-remove (name)
  703. "Remove a buffer property called NAME."
  704. (org-with-point-at 1
  705. (when (re-search-forward (concat "\\(^#\\+" name ":.*\n?\\)")
  706. (point-max) t)
  707. (replace-match ""))))
  708. (use-package org
  709. :ensure t
  710. ; :pin gnu
  711. :mode (("\.org$" . org-mode))
  712. :diminish org-indent-mode
  713. :defer 1
  714. :hook
  715. (org-mode . org-indent-mode)
  716. (org-source-mode . smartparens-mode)
  717. :bind (("C-c l" . org-store-link)
  718. ("C-c c" . org-capture)
  719. ("C-c a" . org-agenda)
  720. :map org-mode-map ("S-<right>" . org-shiftright)
  721. ("S-<left>" . org-shiftleft))
  722. :init
  723. (defun my--org-agenda-files-set ()
  724. "Sets default agenda files.
  725. Necessary when updating roam agenda todos."
  726. (setq org-agenda-files (list (concat MY--PATH_ORG_FILES "notes.org")
  727. (concat MY--PATH_ORG_FILES "projects.org")
  728. (concat MY--PATH_ORG_FILES "tasks.org")))
  729. (when *sys/linux*
  730. (nconc org-agenda-files
  731. (directory-files-recursively MY--PATH_ORG_FILES_MOBILE "\\.org$"))))
  732. (my--org-agenda-files-set)
  733. (defun my--org-skip-subtree-if-priority (priority)
  734. "Skip an agenda subtree if it has a priority of PRIORITY.
  735. PRIORITY may be one of the characters ?A, ?B, or ?C."
  736. (let ((subtree-end (save-excursion (org-end-of-subtree t)))
  737. (pri-value (* 1000 (- org-lowest-priority priority)))
  738. (pri-current (org-get-priority (thing-at-point 'line t))))
  739. (if (= pri-value pri-current)
  740. subtree-end
  741. nil)))
  742. :config
  743. (when *work_remote*
  744. (org-add-link-type "outlook" 'my--org-outlook-open)
  745. (org-add-link-type "outlooknewmail" 'my--org-outlook-new-mail)
  746. (setq org-todo-keywords
  747. '((sequence "OPEN" "TODO" "UNCLEAR" "|" "DONE" "IMPOSSIBLE" "CANCELLED")))
  748. (setq org-capture-templates
  749. '(("t" "telephone call" entry
  750. ; (file+olp+datetree (concat MY--PATH_ORG_FILES "phone_calls.org"))
  751. (file+datetree "p:/Eigene Dateien/Notizen/phone_calls.org")
  752. "* [%<%Y-%m-%d %H:%M>] %?"
  753. :empty-lines 0 :jump-to-captured t))))
  754. (when *sys/linux*
  755. (setq org-pretty-entities t))
  756. :custom
  757. (org-startup-truncated t)
  758. (org-startup-align-all-tables t)
  759. (org-src-fontify-natively t) ;; use syntax highlighting in code blocks
  760. (org-src-preserve-indentation t) ;; no extra indentation
  761. (org-src-window-setup 'current-window) ;; C-c ' opens in current window
  762. (org-modules (quote (org-id
  763. org-habit
  764. org-tempo))) ;; easy templates
  765. (org-default-notes-file (concat MY--PATH_ORG_FILES "notes.org"))
  766. (org-id-locations-file (concat MY--PATH_USER_LOCAL ".org-id-locations"))
  767. (org-log-into-drawer "LOGBOOK")
  768. (org-log-done 'time) ;; create timestamp when task is done
  769. (org-blank-before-new-entry '((heading) (plain-list-item))) ;; prevent new line before new item
  770. (org-src-tab-acts-natively t)
  771. ;;Sort agenda by deadline and priority
  772. (org-agenda-sorting-strategy
  773. (quote
  774. ((agenda deadline-up priority-down)
  775. (todo priority-down category-keep)
  776. (tags priority-down category-keep)
  777. (search category-keep))))
  778. (org-agenda-custom-commands
  779. '(("c" "Simple agenda view"
  780. ((tags "PRIORITY=\"A\""
  781. ((org-agenda-skip-function '(org-agenda-skip-entry-if 'todo 'done))
  782. (org-agenda-overriding-header "Hohe Priorität:")))
  783. (agenda ""
  784. ((org-agenda-skip-function '(org-agenda-skip-entry-if 'todo 'done))
  785. (org-agenda-span 7)
  786. (org-agenda-start-on-weekday nil)
  787. (org-agenda-overriding-header "Nächste 7 Tage:")))
  788. (alltodo ""
  789. ((org-agenda-skip-function '(or (my--org-skip-subtree-if-priority ?A)
  790. (org-agenda-skip-if nil '(scheduled deadline))))
  791. (org-agenda-overriding-header "Sonstige Aufgaben:"))))))))
  792. (use-package org-contacts
  793. :ensure (:host nil :repo "https://repo.or.cz/org-contacts.git")
  794. :after org
  795. :custom
  796. (org-contacts-files (list (concat MY--PATH_ORG_ROAM "contacts.org"))))
  797. (use-package emacsql-sqlite-builtin
  798. :ensure t)
  799. (use-package org-roam
  800. :requires emacsql-sqlite-builtin
  801. :ensure t
  802. :defer 2
  803. :after org
  804. :init
  805. (setq org-roam-v2-ack t)
  806. (defun my--roamtodo-p ()
  807. "Return non-nil if current buffer has any todo entry.
  808. TODO entries marked as done are ignored, meaning this function
  809. returns nil if current buffer contains only completed tasks."
  810. (seq-find
  811. (lambda (type)
  812. (eq type 'todo))
  813. (org-element-map
  814. (org-element-parse-buffer 'headline)
  815. 'headline
  816. (lambda (h)
  817. (org-element-property :todo-type h)))))
  818. (defun my--roamtodo-update-tag ()
  819. "Update ROAMTODO tag in the current buffer."
  820. (when (and (not (active-minibuffer-window))
  821. (my--buffer-roam-note-p))
  822. (save-excursion
  823. (goto-char (point-min))
  824. (let* ((tags (my--buffer-tags-get))
  825. (original-tags tags))
  826. (if (my--roamtodo-p)
  827. (setq tags (cons "roamtodo" tags))
  828. (setq tags (remove "roamtodo" tags)))
  829. ;;cleanup duplicates
  830. (when (or (seq-difference tags original-tags)
  831. (seq-difference original-tags tags))
  832. (apply #'my--buffer-tags-set tags))))))
  833. (defun my--buffer-tags-get ()
  834. "Return filetags value in current buffer."
  835. (my--buffer-prop-get-list "filetags" "[ :]"))
  836. (defun my--buffer-tags-set (&rest tags)
  837. "Set TAGS in current buffer.
  838. If filetags value is already set, replace it."
  839. (if tags
  840. (my--buffer-prop-set
  841. "filetags" (concat ":" (string-join tags ":") ":"))
  842. (my--buffer-prop-remove "filetags")))
  843. (defun my--buffer-tags-add (tag)
  844. "Add a TAG to filetags in current buffer."
  845. (let* ((tags (my--buffer-tags-get))
  846. (tags (append tags (list tag))))
  847. (apply #'my--buffer-tags-set tags)))
  848. (defun my--buffer-tags-remove (tag)
  849. "Remove a TAG from filetags in current buffer."
  850. (let* ((tags (my--buffer-tags-get))
  851. (tags (delete tag tags)))
  852. (apply #'my--buffer-tags-set tags)))
  853. (defun my--buffer-prop-set (name value)
  854. "Set a file property called NAME to VALUE in buffer file.
  855. If the property is already set, replace its value."
  856. (setq name (downcase name))
  857. (org-with-point-at 1
  858. (let ((case-fold-search t))
  859. (if (re-search-forward (concat "^#\\+" name ":\\(.*\\)")
  860. (point-max) t)
  861. (replace-match (concat "#+" name ": " value) 'fixedcase)
  862. (while (and (not (eobp))
  863. (looking-at "^[#:]"))
  864. (if (save-excursion (end-of-line) (eobp))
  865. (progn
  866. (end-of-line)
  867. (insert "\n"))
  868. (forward-line)
  869. (beginning-of-line)))
  870. (insert "#+" name ": " value "\n")))))
  871. (defun my--buffer-prop-set-list (name values &optional separators)
  872. "Set a file property called NAME to VALUES in current buffer.
  873. VALUES are quoted and combined into single string using
  874. `combine-and-quote-strings'.
  875. If SEPARATORS is non-nil, it should be a regular expression
  876. matching text that separates, but is not part of, the substrings.
  877. If nil it defaults to `split-string-and-unquote', normally
  878. \"[ \f\t\n\r\v]+\", and OMIT-NULLS is forced to t.
  879. If the property is already set, replace its value."
  880. (my--buffer-prop-set
  881. name (combine-and-quote-strings values separators)))
  882. (defun my--buffer-prop-get (name)
  883. "Get a buffer property called NAME as a string."
  884. (org-with-point-at 1
  885. (when (re-search-forward (concat "^#\\+" name ": \\(.*\\)")
  886. (point-max) t)
  887. (buffer-substring-no-properties
  888. (match-beginning 1)
  889. (match-end 1)))))
  890. (defun my--buffer-prop-get-list (name &optional separators)
  891. "Get a buffer property NAME as a list using SEPARATORS.
  892. If SEPARATORS is non-nil, it should be a regular expression
  893. matching text that separates, but is not part of, the substrings.
  894. If nil it defaults to `split-string-default-separators', normally
  895. \"[ \f\t\n\r\v]+\", and OMIT-NULLS is forced to t."
  896. (let ((value (my--buffer-prop-get name)))
  897. (when (and value (not (string-empty-p value)))
  898. (split-string-and-unquote value separators))))
  899. (defun my--buffer-prop-remove (name)
  900. "Remove a buffer property called NAME."
  901. (org-with-point-at 1
  902. (when (re-search-forward (concat "\\(^#\\+" name ":.*\n?\\)")
  903. (point-max) t)
  904. (replace-match ""))))
  905. (defun my--buffer-roam-note-p ()
  906. "Return non-nil if the currently visited buffer is a note."
  907. (and buffer-file-name
  908. (string-prefix-p
  909. (expand-file-name (file-name-as-directory MY--PATH_ORG_ROAM))
  910. (file-name-directory buffer-file-name))))
  911. (defun my--org-roam-filter-by-tag (tag-name)
  912. (lambda (node)
  913. (member tag-name (org-roam-node-tags node))))
  914. (defun my--org-roam-list-notes-by-tag (tag-name)
  915. (mapcar #'org-roam-node-file
  916. (seq-filter
  917. (my--org-roam-filter-by-tag tag-name)
  918. (org-roam-node-list))))
  919. (defun my/org-roam-refresh-agenda-list ()
  920. "Add all org roam files with #+filetags: roamtodo"
  921. (interactive)
  922. (my--org-agenda-files-set)
  923. (nconc org-agenda-files
  924. (my--org-roam-list-notes-by-tag "roamtodo"))
  925. (setq org-agenda-files (delete-dups org-agenda-files)))
  926. (add-hook 'find-file-hook #'my--roamtodo-update-tag)
  927. (add-hook 'before-save-hook #'my--roamtodo-update-tag)
  928. (advice-add 'org-agenda :before #'my/org-roam-refresh-agenda-list)
  929. (advice-add 'org-todo-list :before #'my/org-roam-refresh-agenda-list)
  930. (add-to-list 'org-tags-exclude-from-inheritance "roamtodo")
  931. :config
  932. (require 'org-roam-dailies) ;; ensure the keymap is available
  933. (org-roam-db-autosync-mode)
  934. ;; build the agenda list the first ime for the session
  935. (my/org-roam-refresh-agenda-list)
  936. (when *work_remote*
  937. (setq org-roam-capture-templates
  938. '(("n" "note" plain
  939. "%?"
  940. :if-new (file+head "notes/%<%Y%m%d%H%M%S>-${slug}.org" "#+title: ${title}\n")
  941. :unnarrowed t)
  942. ("i" "idea" plain
  943. "%?"
  944. :if-new (file+head "ideas/%<%Y%m%d%H%M%S>-${slug}.org" "#+title: ${title}\n")
  945. :unnarrowed t)
  946. ("p" "project" plain
  947. "%?"
  948. :target (file+head "projects/${slug}.org" "#+title: ${title}\n#+filetags: :project:\n")
  949. :unnarrowed t)
  950. ("s" "Sicherheitenmeldung" plain
  951. "*** TODO [#A] Sicherheitenmeldung ${title}\n :PROPERTIES:\n :ID: %(org-id-uuid)\n:END:\n%u\n"
  952. :target (file+olp "tasks.org" ("Todos" "Sicherheitenmeldungen")))
  953. ("m" "Monatsbericht" plain
  954. "*** TODO [#A] Monatsbericht ${title}\n :PROPERTIES:\n :ID: %(org-id-uuid)\n:END:\n%u\n"
  955. :target (file+olp "tasks.org" ("Todos" "Monatsberichte"))))))
  956. :custom
  957. (org-roam-database-connector 'sqlite-builtin)
  958. (org-roam-directory MY--PATH_ORG_ROAM)
  959. (org-roam-completion-everywhere t)
  960. (org-roam-capture-templates
  961. '(("n" "note" plain
  962. "%?"
  963. :if-new (file+head "notes/%<%Y%m%d%H%M%S>-${slug}.org" "#+title: ${title}\n")
  964. :unnarrowed t)
  965. ("i" "idea" plain
  966. "%?"
  967. :if-new (file+head "ideas/%<%Y%m%d%H%M%S>-${slug}.org" "#+title: ${title}\n")
  968. :unnarrowed t)
  969. ))
  970. :bind (("C-c n l" . org-roam-buffer-toggle)
  971. ("C-c n f" . org-roam-node-find)
  972. ("C-c n i" . org-roam-node-insert)
  973. :map org-mode-map
  974. ("C-M-i" . completion-at-point)
  975. :map org-roam-dailies-map
  976. ("Y" . org-roam-dailies-capture-yesterday)
  977. ("T" . org-roam-dailies-capture-tomorrow))
  978. :bind-keymap
  979. ("C-c n d" . org-roam-dailies-map))
  980. ;; updated version needed for magit, at least on windows
  981. (use-package transient
  982. :ensure t)
  983. (use-package magit
  984. :ensure t
  985. ; :pin melpa-stable
  986. :defer t
  987. :init
  988. ; set git-path in work environment
  989. (if (string-equal user-login-name "POH")
  990. (setq magit-git-executable "P:/Tools/Git/bin/git.exe")
  991. )
  992. :bind (("C-x g" . magit-status)))
  993. (defun corfu-lsp-setup ()
  994. (setf (alist-get 'styles (alist-get 'lsp-capf completion-category-defaults))
  995. '(orderless)))
  996. (use-package lsp-mode
  997. :ensure t
  998. ; :hook
  999. ; ((python-mode . lsp))
  1000. :custom
  1001. (lsp-completion-provider :none)
  1002. (lsp-enable-suggest-server-download nil)
  1003. :hook
  1004. (lsp-completion-mode #'corfu-lsp-setup))
  1005. ;(use-package lsp-ui
  1006. ; :ensure t
  1007. ; :commands lsp-ui-mode)
  1008. (use-package lsp-pyright
  1009. :ensure t
  1010. :after (python lsp-mode)
  1011. :custom
  1012. (lsp-pyright-multi-root nil)
  1013. :hook
  1014. (python-mode-hook . (lambda ()
  1015. (require 'lsp-pyright) (lsp))))
  1016. (setq python-flymake-command '("ruff" "--quiet" "--stdin-filename=stdin" "-"))
  1017. (use-package sideline
  1018. :ensure t)
  1019. (use-package sideline-flymake
  1020. :ensure t
  1021. :requires sideline
  1022. :hook
  1023. (flymake-mode . sideline-mode)
  1024. :init
  1025. (setq sideline-flymake-display-mode 'line ; 'point or 'line
  1026. ; sideline-backends-left '(sideline-lsp)
  1027. sideline-backends-right '(sideline-flymake)))
  1028. (use-package yasnippet
  1029. :ensure t
  1030. :defer t
  1031. :diminish yas-minor-mode
  1032. :config
  1033. (setq yas-snippet-dirs (list (concat MY--PATH_USER_GLOBAL "snippets")))
  1034. (yas-global-mode t)
  1035. (yas-reload-all)
  1036. (unbind-key "TAB" yas-minor-mode-map)
  1037. (unbind-key "<tab>" yas-minor-mode-map))
  1038. (use-package hippie-exp
  1039. :ensure nil
  1040. :defer t
  1041. :bind
  1042. ("C-<return>" . hippie-expand)
  1043. :config
  1044. (setq hippie-expand-try-functions-list
  1045. '(yas-hippie-try-expand emmet-expand-line)))
  1046. (use-package smartparens
  1047. :ensure t
  1048. :diminish smartparens-mode
  1049. :bind
  1050. (:map smartparens-mode-map
  1051. ("C-M-f" . sp-forward-sexp)
  1052. ("C-M-b" . sp-backward-sexp)
  1053. ("C-M-a" . sp-backward-down-sexp)
  1054. ("C-M-e" . sp-up-sexp)
  1055. ("C-M-w" . sp-copy-sexp)
  1056. ("M-k" . sp-kill-sexp)
  1057. ("C-M-<backspace>" . sp-slice-sexp-killing-backward)
  1058. ("C-S-<backspace>" . sp-slice-sexp-killing-around)
  1059. ("C-]" . sp-select-next-thing-exchange))
  1060. :config
  1061. (setq sp-show-pair-from-inside nil
  1062. sp-escape-quotes-after-insert nil)
  1063. (require 'smartparens-config))
  1064. (use-package elisp-mode
  1065. :ensure nil
  1066. :defer t)
  1067. (use-package web-mode
  1068. :ensure t
  1069. :defer t
  1070. :mode
  1071. ("\\.phtml\\'"
  1072. "\\.tpl\\.php\\'"
  1073. "\\.djhtml\\'"
  1074. "\\.[t]?html?\\'")
  1075. :hook
  1076. (web-mode . smartparens-mode)
  1077. :init
  1078. (if *work_remote*
  1079. (setq exec-path (append exec-path '("P:/Tools/node"))))
  1080. :config
  1081. (setq web-mode-enable-auto-closing t
  1082. web-mode-enable-auto-pairing t))
  1083. (use-package emmet-mode
  1084. :ensure t
  1085. :defer t
  1086. :hook
  1087. ((web-mode . emmet-mode)
  1088. (css-mode . emmet-mode))
  1089. :config
  1090. (unbind-key "C-<return>" emmet-mode-keymap))
  1091. (use-package rjsx-mode
  1092. :ensure t
  1093. :mode ("\\.js\\'"
  1094. "\\.jsx'"))
  1095. ; :config
  1096. ; (setq js2-mode-show-parse-errors nil
  1097. ; js2-mode-show-strict-warnings nil
  1098. ; js2-basic-offset 2
  1099. ; js-indent-level 2)
  1100. ; (setq-local flycheck-disabled-checkers (cl-union flycheck-disable-checkers
  1101. ; '(javascript-jshint)))) ; jshint doesn"t work for JSX
  1102. (use-package tide
  1103. :ensure t
  1104. :after (rjsx-mode company flycheck)
  1105. ; :hook (rjsx-mode . setup-tide-mode)
  1106. :config
  1107. (defun setup-tide-mode ()
  1108. "Setup function for tide."
  1109. (interactive)
  1110. (tide-setup)
  1111. (flycheck-mode t)
  1112. (setq flycheck-check-synta-automatically '(save mode-enabled))
  1113. (tide-hl-identifier-mode t)))
  1114. ;; needs npm install -g prettier
  1115. (use-package prettier-js
  1116. :ensure t
  1117. :after (rjsx-mode)
  1118. :defer t
  1119. :diminish prettier-js-mode
  1120. :hook ((js2-mode rsjx-mode) . prettier-js-mode))
  1121. (use-package yaml-mode
  1122. :if *sys/linux*
  1123. :ensure t
  1124. :defer t
  1125. :mode ("\\.yml$" . yaml-mode))
  1126. (use-package ess
  1127. :ensure t
  1128. :defer t
  1129. :init
  1130. (if *work_remote*
  1131. (setq exec-path (append exec-path '("P:/Tools/R/bin/x64"))
  1132. org-babel-R-command "P:/Tools/R/bin/x64/R --slave --no-save")))
  1133. (use-package project
  1134. :custom
  1135. (project-vc-extra-root-markers '(".project.el" ".project" )))
  1136. (use-package python
  1137. :if *sys/linux*
  1138. :delight "π "
  1139. :defer t
  1140. :bind (("M-[" . python-nav-backward-block)
  1141. ("M-]" . python-nav-forward-block))
  1142. :mode
  1143. (("\\.py\\'" . python-mode)))
  1144. (use-package pyvenv
  1145. ; :if *sys/linux*
  1146. :ensure t
  1147. :defer t
  1148. :after python
  1149. :hook
  1150. (python-mode . pyvenv-mode)
  1151. :custom
  1152. (pyvenv-default-virtual-env-name ".env")
  1153. (pyvenv-mode-line-indicator '(pyvenv-virtual-env-name ("[venv:" pyvenv-virtual-env-name "]"))))
  1154. ;; formatting to pep8
  1155. ;; requires pip install black
  1156. ;(use-package blacken
  1157. ; :ensure t)
  1158. (use-package beancount
  1159. :ensure nil
  1160. :if *sys/linux*
  1161. :load-path "user-global/elisp/"
  1162. ; :ensure t
  1163. :defer t
  1164. :mode
  1165. ("\\.beancount$" . beancount-mode)
  1166. :hook
  1167. (beancount-mode . my/beancount-company)
  1168. :config
  1169. (defun my/beancount-company ()
  1170. (setq-local completion-at-point-functions #'beancount-completion-at-point))
  1171. (setq beancount-filename-main "/home/marc/Archiv/Finanzen/Transaktionen/transactions.beancount"))
  1172. ;(setq gc-cons-threshold (* 2 1000 1000))