Personal emacs config
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.

346 lines
11 KiB

  1. * Global
  2. ** Add features/modes
  3. *** ibuffer-mode
  4. #+BEGIN_SRC emacs-lisp
  5. (require 'ibuffer-vc)
  6. (add-hook 'ibuffer-mode-hook (lambda ()
  7. (ibuffer-vc-set-filter-groups-by-vc-root)))
  8. (global-set-key (kbd "C-x C-b") 'ibuffer)
  9. ;; Use human readable Size column instead of original one
  10. (define-ibuffer-column size-h
  11. (:name "Size" ;; :inline t
  12. )
  13. (cond
  14. ((> (buffer-size) 1000000) (format "%7.1fM" (/ (buffer-size) 1000000.0)))
  15. ((> (buffer-size) 100000) (format "%7.0fk" (/ (buffer-size) 1000.0)))
  16. ((> (buffer-size) 1000) (format "%7.1fk" (/ (buffer-size) 1000.0)))
  17. (t (format "%8d" (buffer-size)))))
  18. ;; Modify the default ibuffer-formats
  19. (setq ibuffer-formats
  20. '((mark modified read-only " "
  21. (name 18 18 :left :elide)
  22. " "
  23. (size-h 9 -1 :right)
  24. " "
  25. (mode 16 16 :left :elide)
  26. " "
  27. filename-and-process)))
  28. #+END_SRC
  29. *** string-inflection
  30. #+BEGIN_SRC emacs-lisp
  31. (require 'string-inflection)
  32. ;; C-q C-u is the key bindings similar to Vz Editor.
  33. (global-set-key (kbd "C-M-,") 'my-string-inflection-cycle-auto)
  34. (defun my-string-inflection-cycle-auto ()
  35. "switching by major-mode"
  36. (interactive)
  37. (cond
  38. ;; for emacs-lisp-mode
  39. ((eq major-mode 'emacs-lisp-mode)
  40. (string-inflection-all-cycle))
  41. ;; for python
  42. ((eq major-mode 'python-mode)
  43. (string-inflection-python-style-cycle))
  44. ;; for java
  45. ((eq major-mode 'java-mode)
  46. (string-inflection-java-style-cycle))
  47. (t
  48. ;; default
  49. (string-inflection-ruby-style-cycle))))
  50. #+END_SRC
  51. *** undo-tree
  52. #+begin_src emacs-lisp
  53. (require 'undo-tree)
  54. (global-undo-tree-mode)
  55. #+end_src
  56. *** ssh-config-mode
  57. #+begin_src emacs-lisp
  58. (require 'ssh-config-mode)
  59. (add-to-list 'auto-mode-alist '("~/.ssh/config\\'" . ssh-config-mode))
  60. #+end_src
  61. *** yaml-mode
  62. #+begin_src emacs-lisp
  63. (require 'yaml-mode)
  64. (add-to-list 'auto-mode-alist '("\\.yml\\'" . yaml-mode))
  65. #+end_src
  66. *** elpy move line up and down globally
  67. #+begin_src emacs-lisp
  68. (require 'elpy)
  69. (global-set-key (kbd "M-<up>") 'elpy-nav-move-line-or-region-up)
  70. (global-set-key (kbd "M-<down>") 'elpy-nav-move-line-or-region-down)
  71. (global-set-key (kbd "C-c <left>") 'windmove-left)
  72. (global-set-key (kbd "C-c <right>") 'windmove-right)
  73. (global-set-key (kbd "C-c <up>") 'windmove-up)
  74. (global-set-key (kbd "C-c <down>") 'windmove-down)
  75. #+end_src
  76. *** iedit-mode
  77. #+begin_src emacs-lisp
  78. (global-set-key (kbd "C-;") 'iedit-mode)
  79. #+end_src
  80. *** spellcheck entire buffer
  81. #+begin_src emacs-lisp
  82. (global-set-key (kbd "C-!") 'ispell-buffer)
  83. #+end_src
  84. *** find/replace
  85. #+begin_src emacs-lisp
  86. (require 'visual-regexp-steroids)
  87. (define-key global-map (kbd "C-c r") 'vr/replace)
  88. (define-key global-map (kbd "C-c q") 'vr/query-replace)
  89. #+end_src
  90. *** duplicate line function
  91. #+begin_src emacs-lisp
  92. (defun duplicate-line()
  93. (interactive)
  94. (move-beginning-of-line 1)
  95. (kill-line)
  96. (yank)
  97. (open-line 1)
  98. (next-line 1)
  99. (yank))
  100. (global-set-key (kbd "C-c d") 'duplicate-line)
  101. #+end_src
  102. *** magit
  103. #+begin_src emacs-lisp
  104. (global-set-key (kbd "C-x g") 'magit-status)
  105. #+end_src
  106. #+begin_src emacs-lisp
  107. (add-hook 'git-commit-setup-hook 'git-commit-turn-on-flyspell)
  108. #+end_src
  109. *** filename completion
  110. #+BEGIN_SRC emacs-lisp
  111. (global-set-key (kbd "C->") 'comint-dynamic-complete-filename)
  112. #+END_SRC
  113. *** hippie expand
  114. #+BEGIN_SRC emacs-lisp
  115. (global-set-key (kbd "M-/") 'hippie-expand)
  116. (setq hippie-expand-try-functions-list '(try-expand-dabbrev try-expand-dabbrev-all-buffers try-expand-dabbrev-from-kill
  117. try-complete-file-name-partially try-complete-file-name
  118. try-expand-all-abbrevs try-expand-list try-expand-line
  119. try-complete-lisp-symbol-partially try-complete-lisp-symbol))
  120. #+END_SRC
  121. *** window numbering mode
  122. #+BEGIN_SRC emacs-lisp
  123. (window-numbering-mode)
  124. #+END_SRC
  125. ** options
  126. *** global
  127. **** recent files
  128. #+begin_src emacs-lisp
  129. (require 'recentf)
  130. (recentf-mode 1)
  131. #+end_src
  132. **** backup
  133. #+begin_src emacs-lisp
  134. (let ((backup-dir (concat user-emacs-directory "backup"))
  135. (auto-save-dir (concat user-emacs-directory "autosave"))
  136. )
  137. (if (not (file-directory-p backup-dir))
  138. (make-directory backup-dir))
  139. (if (not(file-directory-p auto-save-dir))
  140. (make-directory auto-save-dir)
  141. )
  142. (setq backup-directory-alist
  143. `((".*" . , backup-dir)))
  144. (setq auto-save-file-name-transforms
  145. `((".*" , (concat auto-save-dir "/") t))))
  146. #+end_src
  147. **** kill buffer option
  148. #+begin_src emacs-lisp
  149. (global-set-key (kbd "C-x k") 'kill-this-buffer)
  150. #+end_src
  151. **** inhibit start screen
  152. #+begin_src emacs-lisp
  153. (setq inhibit-startup-screen t)
  154. #+end_src
  155. **** save options
  156. #+begin_src emacs-lisp
  157. (add-hook 'before-save-hook 'delete-trailing-whitespace)
  158. #+end_src
  159. **** theming
  160. #+begin_src emacs-lisp
  161. (load-theme 'dracula t)
  162. #+end_src
  163. **** bell
  164. #+BEGIN_SRC emacs-lisp
  165. (mode-line-bell-mode)
  166. #+END_SRC
  167. **** ivy
  168. #+BEGIN_SRC emacs-lisp
  169. (ivy-mode)
  170. (global-set-key (kbd "C-s") 'swiper)
  171. #+END_SRC
  172. **** kill-emacs key
  173. #+BEGIN_SRC emacs-lisp
  174. (global-set-key (kbd "C-x C-k C-x C-k") 'kill-emacs)
  175. #+END_SRC
  176. **** linum
  177. #+BEGIN_SRC emacs-lisp
  178. (global-display-line-numbers-mode)
  179. #+END_SRC
  180. **** enable commands
  181. #+BEGIN_SRC emacs-lisp
  182. (put 'downcase-region 'disabled nil)
  183. #+END_SRC
  184. *** dired
  185. #+begin_src emacs-lisp
  186. (setq ls-lisp-use-insert-directory-program t)
  187. #+end_src
  188. #+begin_src emacs-lisp
  189. (setq dired-listing-switches "-alh")
  190. #+end_src
  191. * Tramp configuration
  192. ** Android
  193. #+begin_src emacs-lisp
  194. (let
  195. (
  196. (default-directory "/data/data/com.termux/files/")
  197. )
  198. (add-to-list 'tramp-connection-properties
  199. (list
  200. "/ssh:termux.*"
  201. "tmpdir" (expand-file-name "temp/")
  202. "remote-shell" (expand-file-name "usr/bin/sh")
  203. "remote path" (append (mapcar 'expand-file-name '(
  204. "home/.local/bin"
  205. "usr/bin"
  206. "usr/bin/applets"
  207. ))
  208. '("/sbin"
  209. "/vendor/bin"
  210. "/system/sbin"
  211. "/system/bin"
  212. "/system/xbin")))))
  213. #+end_src
  214. * Web things
  215. ** javascript stuff
  216. #+begin_src emacs-lisp
  217. (require 'js2-mode)
  218. (add-to-list 'auto-mode-alist '("\\.js\\'" . js2-mode))
  219. (add-hook 'js2-mode-hook #'js2-imenu-extras-mode)
  220. (require 'js2-refactor)
  221. (require 'xref-js2)
  222. (add-hook 'js2-mode-hook #'js2-refactor-mode)
  223. (js2r-add-keybindings-with-prefix "C-c C-r")
  224. (define-key js2-mode-map (kbd "C-k") #'js2r-kill)
  225. (define-key js-mode-map (kbd "M-.") nil)
  226. (add-hook 'js2-mode-hook (lambda ()
  227. (add-hook 'xref-backend-functions #'xref-js2-xref-backend nil t)))
  228. (define-key js2-mode-map (kbd "C-k") #'js2r-kill)
  229. #+end_src
  230. ** web mode
  231. #+begin_src emacs-lisp
  232. (require 'web-mode)
  233. (add-to-list 'auto-mode-alist '("\\.phtml\\'" . web-mode))
  234. (add-to-list 'auto-mode-alist '("\\.tpl\\.php\\'" . web-mode))
  235. (add-to-list 'auto-mode-alist '("\\.[agj]sp\\'" . web-mode))
  236. (add-to-list 'auto-mode-alist '("\\.as[cp]x\\'" . web-mode))
  237. (add-to-list 'auto-mode-alist '("\\.erb\\'" . web-mode))
  238. (add-to-list 'auto-mode-alist '("\\.mustache\\'" . web-mode))
  239. (add-to-list 'auto-mode-alist '("\\.djhtml\\'" . web-mode))
  240. (add-to-list 'auto-mode-alist '("\\.html?\\'" . web-mode))
  241. #+end_src
  242. * Platform Specific
  243. #+begin_src emacs-lisp
  244. (cond
  245. #+end_src
  246. ** Windows
  247. #+begin_src emacs-lisp
  248. ((string-equal system-type "windows-nt")
  249. (progn
  250. (defun rlbr/quote-exe (path)
  251. (w32-short-file-name path))
  252. (defun rlbr/start-external-shell ()
  253. (interactive)
  254. (start-process-shell-command (format "cmd(%s)" default-directory) nil "start default.bat"))
  255. (global-set-key (kbd "C-S-C") 'rlbr/start-external-shell)
  256. (defun rlbr/start-windows-explorer-here ()
  257. (interactive)
  258. (start-process-shell-command "explorer" nil
  259. (format "explorer %s"
  260. (replace-regexp-in-string "/" (regexp-quote "\\") (expand-file-name default-directory))))
  261. )
  262. (global-set-key (kbd "C-S-E") 'rlbr/start-windows-explorer-here)
  263. (defun rlbr/case-insensitive-match (string1 string2)
  264. (apply 'string-equal (mapcar 'downcase (list string1 string2))))
  265. (defun rlbr/output-matches (output-matches-p exe args)
  266. "locate the executable whose output satifies output-matches-p when fed args and return the fullpath"
  267. (let
  268. (
  269. (exec-path exec-path)
  270. (output)
  271. (bad)
  272. (command-output)
  273. (current-exe)
  274. (failed)
  275. )
  276. (while (not (or output failed))
  277. (setq current-exe (executable-find exe))
  278. (if current-exe
  279. (progn
  280. (setq command-output (shell-command-to-string (format "%s %s" (rlbr/quote-exe current-exe) args)))
  281. (if (funcall output-matches-p command-output)
  282. (setq output current-exe)
  283. (progn
  284. (setq bad (replace-regexp-in-string "/$" "" (file-name-directory current-exe)))
  285. (setq exec-path (seq-filter (lambda (item) (not (rlbr/case-insensitive-match item bad))) exec-path)))))
  286. (setq failed t)))
  287. output))
  288. (let
  289. ((find)
  290. (grep)
  291. (ls))
  292. (progn
  293. (setq find (rlbr/output-matches (lambda (output) (string-equal ".\n" output)) "find" "-maxdepth 0"))
  294. (if find
  295. (setq find-program (rlbr/quote-exe find)))
  296. (setq grep (rlbr/output-matches (lambda (output) (string-match "grep (\\w+ grep)" output)) "grep" "-V"))
  297. (if grep
  298. (setq grep-program (rlbr/quote-exe grep)))
  299. (setq ls (rlbr/output-matches (lambda (output) (string-match "ls: .*'\\?/': No such file or directory" output)) "ls" "?/"))
  300. (if ls
  301. (setq insert-directory-program (rlbr/quote-exe ls)))))
  302. (setq python-shell-interpreter (rlbr/quote-exe (executable-find "python")))
  303. (setq python-check-command (rlbr/quote-exe (executable-find "flake8")))
  304. (setq delete-by-moving-to-trash t)
  305. (defun python-shell-interpreter-refresh ()
  306. (interactive)
  307. (setq python-shell-interpreter (rlbr/quote-exe (executable-find "python"))))
  308. (add-hook 'python-django-project-root-hook 'python-shell-interpreter-refresh)
  309. ))
  310. #+end_src
  311. ** Linux
  312. #+begin_src emacs-lisp
  313. ((string-equal system-type "gnu/linux")
  314. (progn
  315. (setq python-shell-interpreter "python3")
  316. (setq elpy-rpc-python-command python-shell-interpreter)
  317. (defun get-elpa-package-install-directory (pkg)
  318. "Return the install directory of elpa PKG. Return nil if it is not found."
  319. (let ((elpa-dir package-user-dir))
  320. (when (file-exists-p elpa-dir)
  321. (let* ((pkg-match (concat "\\`" (symbol-name pkg) "-[0-9]+"))
  322. (dir (car (directory-files elpa-dir 'full pkg-match))))
  323. (when dir (file-name-as-directory dir))))))
  324. (setq vr/command-python
  325. (format "python3 %s" (expand-file-name "regexp.py" (get-elpa-package-install-directory 'visual-regexp-steroids))))
  326. )))
  327. #+end_src
  328. * Python
  329. #+begin_src emacs-lisp
  330. (elpy-enable)
  331. (when (require 'flycheck nil t)
  332. (setq elpy-modules (delq 'elpy-module-flymake elpy-modules))
  333. (add-hook 'elpy-mode-hook 'flycheck-mode))
  334. (require 'blacken)
  335. (defun python-mode-keys ()
  336. "Modify python-mode local key map"
  337. (local-set-key (kbd "C-=") 'elpy-goto-assignment))
  338. (add-hook 'python-mode-hook 'python-mode-keys)
  339. (add-hook 'elpy-mode-hook 'blacken-mode)
  340. (setq elpy-syntax-check-command python-check-command)
  341. #+end_src