60693f7f6eacc54e2cd58b1725b02caed3215f87
[dotfiles.git] / emacs.d / config / init-hydra.el
1
2 (require 'hydra)
3
4 ;; misc operation for toggle some style
5 ;; such as toggle line number
6 ;; windows layout restore / maximum
7 ;; 
8
9
10 (defhydra hydra-helm (global-map "M-c")
11   "Helm"
12   ("j" helm-mini "helm-mini")
13   ("q" nil "quit"))
14 ;;* Examples
15 ;;** Example 1: text scale
16
17   (defhydra hydra-zoom (global-map "<f2>")
18     "zoom"
19     ("g" text-scale-increase "in")
20     ("l" text-scale-decrease "out"))
21
22
23
24 ;;** Example 2: move window splitter
25
26   (defhydra hydra-splitter (global-map "C-M-s")
27     "splitter"
28     ("h" hydra-move-splitter-left)
29     ("j" hydra-move-splitter-down)
30     ("k" hydra-move-splitter-up)
31     ("l" hydra-move-splitter-right))
32
33 ;;** Example 3: jump to error
34
35   (defhydra hydra-error (global-map "M-g")
36     "goto-error"
37     ("h" first-error "first")
38     ("j" next-error "next")
39     ("k" previous-error "prev")
40     ("v" recenter-top-bottom "recenter")
41     ("q" nil "quit"))
42
43
44
45 ;;** Example 4: toggle rarely used modes
46
47   (defvar whitespace-mode nil)
48   (global-set-key
49    (kbd "C-c C-v")
50    (defhydra hydra-toggle-simple (:color blue)
51      "toggle"
52      ("a" abbrev-mode "abbrev")
53      ("d" toggle-debug-on-error "debug")
54      ("f" auto-fill-mode "fill")
55      ("t" toggle-truncate-lines "truncate")
56      ("w" whitespace-mode "whitespace")
57      ("q" nil "cancel")))
58
59
60
61 ;;** Example 5: mini-vi
62 (defun hydra-vi/pre ()
63   (set-cursor-color "#e52b50"))
64
65 (defun hydra-vi/post ()
66   (set-cursor-color "#ffffff"))
67
68
69   (global-set-key
70    (kbd "C-z")
71    (defhydra hydra-vi (:pre hydra-vi/pre :post hydra-vi/post :color amaranth)
72      "vi"
73      ("l" forward-char)
74      ("h" backward-char)
75      ("j" next-line)
76      ("k" previous-line)
77      ("m" set-mark-command "mark")
78      ("a" move-beginning-of-line "beg")
79      ("e" move-end-of-line "end")
80      ("d" delete-region "del" :color blue)
81      ("y" kill-ring-save "yank" :color blue)
82      ("q" nil "quit")))
83
84
85
86 ;;** Example 6: selective global bind
87
88   (defhydra hydra-next-error (global-map "C-x")
89     "next-error"
90     ("`" next-error "next")
91     ("j" next-error "next" :bind nil)
92     ("k" previous-error "previous" :bind nil))
93
94 ;; This example will bind "C-x `" in `global-map', but it will not
95 ;; bind "C-x j" and "C-x k".
96 ;; You can still "C-x `jjk" though.
97
98 ;;** Example 7: toggle with Ruby-style docstring
99 (defvar whitespace-mode nil)
100 (defhydra hydra-toggle (:color pink)
101   "
102 _a_ abbrev-mode:       %`abbrev-mode
103 _d_ debug-on-error:    %`debug-on-error
104 _f_ auto-fill-mode:    %`auto-fill-function
105 _t_ truncate-lines:    %`truncate-lines
106 _w_ whitespace-mode:   %`whitespace-mode
107
108 "
109   ("a" abbrev-mode nil)
110   ("d" toggle-debug-on-error nil)
111   ("f" auto-fill-mode nil)
112   ("t" toggle-truncate-lines nil)
113   ("w" whitespace-mode nil)
114   ("q" nil "quit"))
115 ;; Recommended binding:
116 ;; (global-set-key (kbd "C-c C-v") 'hydra-toggle/body)
117
118 ;; Here, using e.g. "_a_" translates to "a" with proper face.
119 ;; More interestingly:
120 ;;
121 ;;     "foobar %`abbrev-mode" means roughly (format "foobar %S" abbrev-mode)
122 ;;
123 ;; This means that you actually see the state of the mode that you're changing.
124
125 ;;** Example 8: the whole menu for `Buffer-menu-mode'
126 (defhydra hydra-buffer-menu (:color pink
127                              :hint nil)
128   "
129 ^Mark^             ^Unmark^           ^Actions^          ^Search
130 ^^^^^^^^-----------------------------------------------------------------                        (__)
131 _m_: mark          _u_: unmark        _x_: execute       _R_: re-isearch                         (oo)
132 _s_: save          _U_: unmark up     _b_: bury          _I_: isearch                      /------\\/
133 _d_: delete        ^ ^                _g_: refresh       _O_: multi-occur                 / |    ||
134 _D_: delete up     ^ ^                _T_: files only: % -28`Buffer-menu-files-only^^    *  /\\---/\\
135 _~_: modified      ^ ^                ^ ^                ^^                                 ~~   ~~
136 "
137   ("m" Buffer-menu-mark)
138   ("u" Buffer-menu-unmark)
139   ("U" Buffer-menu-backup-unmark)
140   ("d" Buffer-menu-delete)
141   ("D" Buffer-menu-delete-backwards)
142   ("s" Buffer-menu-save)
143   ("~" Buffer-menu-not-modified)
144   ("x" Buffer-menu-execute)
145   ("b" Buffer-menu-bury)
146   ("g" revert-buffer)
147   ("T" Buffer-menu-toggle-files-only)
148   ("O" Buffer-menu-multi-occur :color blue)
149   ("I" Buffer-menu-isearch-buffers :color blue)
150   ("R" Buffer-menu-isearch-buffers-regexp :color blue)
151   ("c" nil "cancel")
152   ("v" Buffer-menu-select "select" :color blue)
153   ("o" Buffer-menu-other-window "other-window" :color blue)
154   ("q" quit-window "quit" :color blue))
155 ;; Recommended binding:
156 ;; (define-key Buffer-menu-mode-map "." 'hydra-buffer-menu/body)
157
158 ;;** Example 9: s-expressions in the docstring
159 ;; You can inline s-expresssions into the docstring like this:
160 (defvar dired-mode-map)
161 (when (bound-and-true-p hydra-examples-verbatim)
162   (require 'dired)
163   (defhydra hydra-marked-items (dired-mode-map "")
164     "
165 Number of marked items: %(length (dired-get-marked-files))
166 "
167     ("m" dired-mark "mark")))
168
169 ;; This results in the following dynamic docstring:
170 ;;
171 ;;     (format "Number of marked items: %S\n"
172 ;;             (length (dired-get-marked-files)))
173 ;;
174 ;; You can use `format'-style width specs, e.g. % 10(length nil).
175
176 ;;** Example 10: apropos family
177 (defhydra hydra-apropos (:color blue
178                          :hint nil)
179   "
180 _a_propos        _c_ommand
181 _d_ocumentation  _l_ibrary
182 _v_ariable       _u_ser-option
183 ^ ^          valu_e_"
184   ("a" apropos)
185   ("d" apropos-documentation)
186   ("v" apropos-variable)
187   ("c" apropos-command)
188   ("l" apropos-library)
189   ("u" apropos-user-option)
190   ("e" apropos-value))
191 ;; Recommended binding:
192 ;; (global-set-key (kbd "C-c h") 'hydra-apropos/body)
193
194 ;;** Example 11: rectangle-mark-mode
195 (defhydra hydra-rectangle (:body-pre (rectangle-mark-mode 1)
196                            :color pink
197                            :post (deactivate-mark))
198   "
199   ^_k_^     _d_elete    _s_tring
200 _h_   _l_   _o_k        _y_ank
201   ^_j_^     _n_ew-copy  _r_eset
202 ^^^^        _e_xchange  _u_ndo
203 ^^^^        ^ ^         _p_aste
204 "
205   ("h" backward-char nil)
206   ("l" forward-char nil)
207   ("k" previous-line nil)
208   ("j" next-line nil)
209   ("e" hydra-ex-point-mark nil)
210   ("n" copy-rectangle-as-kill nil)
211   ("d" delete-rectangle nil)
212   ("r" (if (region-active-p)
213            (deactivate-mark)
214          (rectangle-mark-mode 1)) nil)
215   ("y" yank-rectangle nil)
216   ("u" undo nil)
217   ("s" string-rectangle nil)
218   ("p" kill-rectangle nil)
219   ("o" nil nil))
220
221 ;; Recommended binding:
222 ;; (global-set-key (kbd "C-x SPC") 'hydra-rectangle/body)
223
224 ;;* Helpers
225 (require 'windmove)
226
227 (defun hydra-move-splitter-left (arg)
228   "Move window splitter left."
229   (interactive "p")
230   (if (let ((windmove-wrap-around))
231         (windmove-find-other-window 'right))
232       (shrink-window-horizontally arg)
233     (enlarge-window-horizontally arg)))
234
235 (defun hydra-move-splitter-right (arg)
236   "Move window splitter right."
237   (interactive "p")
238   (if (let ((windmove-wrap-around))
239         (windmove-find-other-window 'right))
240       (enlarge-window-horizontally arg)
241     (shrink-window-horizontally arg)))
242
243 (defun hydra-move-splitter-up (arg)
244   "Move window splitter up."
245   (interactive "p")
246   (if (let ((windmove-wrap-around))
247         (windmove-find-other-window 'up))
248       (enlarge-window arg)
249     (shrink-window arg)))
250
251 (defun hydra-move-splitter-down (arg)
252   "Move window splitter down."
253   (interactive "p")
254   (if (let ((windmove-wrap-around))
255         (windmove-find-other-window 'up))
256       (shrink-window arg)
257     (enlarge-window arg)))
258
259 (defvar rectangle-mark-mode)
260 (defun hydra-ex-point-mark ()
261   "Exchange point and mark."
262   (interactive)
263   (if rectangle-mark-mode
264       (exchange-point-and-mark)
265     (let ((mk (mark)))
266       (rectangle-mark-mode 1)
267       (goto-char mk))))
268
269 (provide 'init-hydra)