1 ;;; hydra-test.el --- Tests for Hydra
3 ;; Copyright (C) 2015 Free Software Foundation, Inc.
7 ;; This file is part of GNU Emacs.
9 ;; GNU Emacs is free software: you can redistribute it and/or modify
10 ;; it under the terms of the GNU General Public License as published by
11 ;; the Free Software Foundation, either version 3 of the License, or
12 ;; (at your option) any later version.
14 ;; GNU Emacs is distributed in the hope that it will be useful,
15 ;; but WITHOUT ANY WARRANTY; without even the implied warranty of
16 ;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 ;; GNU General Public License for more details.
19 ;; You should have received a copy of the GNU General Public License
20 ;; along with GNU Emacs. If not, see <http://www.gnu.org/licenses/>.
29 (ert-deftest hydra-red-error ()
33 '(defhydra hydra-error (global-map "M-g")
35 ("h" first-error "first")
36 ("j" next-error "next")
37 ("k" previous-error "prev")
38 ("SPC" hydra-repeat "rep" :bind nil)))
40 (defun hydra-error/first-error nil "Create a hydra with a \"M-g\" body and the heads:
44 \"k\": `previous-error',
45 \"SPC\": `hydra-repeat'
47 The body can be accessed via `hydra-error/body'.
49 Call the head: `first-error'."
52 (catch (quote hydra-disable)
53 (condition-case err (prog1 t (call-interactively (function first-error)))
56 (unless hydra-lv (sit-for 0.8))
58 (when hydra-is-helpful (hydra-error/hint))
60 (hydra-set-transient-map
62 (quote (keymap (7 . hydra-keyboard-quit)
64 (107 . hydra-error/previous-error)
65 (106 . hydra-error/next-error)
66 (104 . hydra-error/first-error)
67 (kp-subtract . hydra--negative-argument)
68 (kp-9 . hydra--digit-argument)
69 (kp-8 . hydra--digit-argument)
70 (kp-7 . hydra--digit-argument)
71 (kp-6 . hydra--digit-argument)
72 (kp-5 . hydra--digit-argument)
73 (kp-4 . hydra--digit-argument)
74 (kp-3 . hydra--digit-argument)
75 (kp-2 . hydra--digit-argument)
76 (kp-1 . hydra--digit-argument)
77 (kp-0 . hydra--digit-argument)
78 (57 . hydra--digit-argument)
79 (56 . hydra--digit-argument)
80 (55 . hydra--digit-argument)
81 (54 . hydra--digit-argument)
82 (53 . hydra--digit-argument)
83 (52 . hydra--digit-argument)
84 (51 . hydra--digit-argument)
85 (50 . hydra--digit-argument)
86 (49 . hydra--digit-argument)
87 (48 . hydra--digit-argument)
88 (45 . hydra--negative-argument)
89 (21 . hydra--universal-argument))))
90 t (lambda nil (hydra-cleanup))))))
91 (defun hydra-error/next-error nil "Create a hydra with a \"M-g\" body and the heads:
95 \"k\": `previous-error',
96 \"SPC\": `hydra-repeat'
98 The body can be accessed via `hydra-error/body'.
100 Call the head: `next-error'."
103 (catch (quote hydra-disable)
104 (condition-case err (prog1 t (call-interactively (function next-error)))
107 (unless hydra-lv (sit-for 0.8))
109 (when hydra-is-helpful (hydra-error/hint))
111 (hydra-set-transient-map
113 (quote (keymap (7 . hydra-keyboard-quit)
115 (107 . hydra-error/previous-error)
116 (106 . hydra-error/next-error)
117 (104 . hydra-error/first-error)
118 (kp-subtract . hydra--negative-argument)
119 (kp-9 . hydra--digit-argument)
120 (kp-8 . hydra--digit-argument)
121 (kp-7 . hydra--digit-argument)
122 (kp-6 . hydra--digit-argument)
123 (kp-5 . hydra--digit-argument)
124 (kp-4 . hydra--digit-argument)
125 (kp-3 . hydra--digit-argument)
126 (kp-2 . hydra--digit-argument)
127 (kp-1 . hydra--digit-argument)
128 (kp-0 . hydra--digit-argument)
129 (57 . hydra--digit-argument)
130 (56 . hydra--digit-argument)
131 (55 . hydra--digit-argument)
132 (54 . hydra--digit-argument)
133 (53 . hydra--digit-argument)
134 (52 . hydra--digit-argument)
135 (51 . hydra--digit-argument)
136 (50 . hydra--digit-argument)
137 (49 . hydra--digit-argument)
138 (48 . hydra--digit-argument)
139 (45 . hydra--negative-argument)
140 (21 . hydra--universal-argument))))
141 t (lambda nil (hydra-cleanup))))))
142 (defun hydra-error/previous-error nil "Create a hydra with a \"M-g\" body and the heads:
144 \"h\": `first-error',
146 \"k\": `previous-error',
147 \"SPC\": `hydra-repeat'
149 The body can be accessed via `hydra-error/body'.
151 Call the head: `previous-error'."
154 (catch (quote hydra-disable)
155 (condition-case err (prog1 t (call-interactively (function previous-error)))
158 (unless hydra-lv (sit-for 0.8))
160 (when hydra-is-helpful (hydra-error/hint))
162 (hydra-set-transient-map
164 (quote (keymap (7 . hydra-keyboard-quit)
166 (107 . hydra-error/previous-error)
167 (106 . hydra-error/next-error)
168 (104 . hydra-error/first-error)
169 (kp-subtract . hydra--negative-argument)
170 (kp-9 . hydra--digit-argument)
171 (kp-8 . hydra--digit-argument)
172 (kp-7 . hydra--digit-argument)
173 (kp-6 . hydra--digit-argument)
174 (kp-5 . hydra--digit-argument)
175 (kp-4 . hydra--digit-argument)
176 (kp-3 . hydra--digit-argument)
177 (kp-2 . hydra--digit-argument)
178 (kp-1 . hydra--digit-argument)
179 (kp-0 . hydra--digit-argument)
180 (57 . hydra--digit-argument)
181 (56 . hydra--digit-argument)
182 (55 . hydra--digit-argument)
183 (54 . hydra--digit-argument)
184 (53 . hydra--digit-argument)
185 (52 . hydra--digit-argument)
186 (51 . hydra--digit-argument)
187 (50 . hydra--digit-argument)
188 (49 . hydra--digit-argument)
189 (48 . hydra--digit-argument)
190 (45 . hydra--negative-argument)
191 (21 . hydra--universal-argument))))
192 t (lambda nil (hydra-cleanup))))))
193 (unless (keymapp (lookup-key global-map (kbd "M-g")))
194 (define-key global-map (kbd "M-g")
196 (define-key global-map [134217831 104]
197 (function hydra-error/first-error))
198 (define-key global-map [134217831 106]
199 (function hydra-error/next-error))
200 (define-key global-map [134217831 107]
201 (function hydra-error/previous-error))
202 (defun hydra-error/hint nil
203 (if hydra-lv (lv-message (format #("error: [h]: first, [j]: next, [k]: prev, [SPC]: rep." 8 9 (face hydra-face-red)
204 20 21 (face hydra-face-red)
205 31 32 (face hydra-face-red)
206 42 45 (face hydra-face-red))))
207 (message (format #("error: [h]: first, [j]: next, [k]: prev, [SPC]: rep." 8 9 (face hydra-face-red)
208 20 21 (face hydra-face-red)
209 31 32 (face hydra-face-red)
210 42 45 (face hydra-face-red))))))
211 (defun hydra-error/body nil "Create a hydra with a \"M-g\" body and the heads:
213 \"h\": `first-error',
215 \"k\": `previous-error',
216 \"SPC\": `hydra-repeat'
218 The body can be accessed via `hydra-error/body'."
221 (catch (quote hydra-disable)
222 (when hydra-is-helpful (hydra-error/hint))
224 (hydra-set-transient-map
227 (keymap (7 . hydra-keyboard-quit)
229 (107 . hydra-error/previous-error)
230 (106 . hydra-error/next-error)
231 (104 . hydra-error/first-error)
232 (kp-subtract . hydra--negative-argument)
233 (kp-9 . hydra--digit-argument)
234 (kp-8 . hydra--digit-argument)
235 (kp-7 . hydra--digit-argument)
236 (kp-6 . hydra--digit-argument)
237 (kp-5 . hydra--digit-argument)
238 (kp-4 . hydra--digit-argument)
239 (kp-3 . hydra--digit-argument)
240 (kp-2 . hydra--digit-argument)
241 (kp-1 . hydra--digit-argument)
242 (kp-0 . hydra--digit-argument)
243 (57 . hydra--digit-argument)
244 (56 . hydra--digit-argument)
245 (55 . hydra--digit-argument)
246 (54 . hydra--digit-argument)
247 (53 . hydra--digit-argument)
248 (52 . hydra--digit-argument)
249 (51 . hydra--digit-argument)
250 (50 . hydra--digit-argument)
251 (49 . hydra--digit-argument)
252 (48 . hydra--digit-argument)
253 (45 . hydra--negative-argument)
254 (21 . hydra--universal-argument))))
255 t (lambda nil (hydra-cleanup))))
256 (setq prefix-arg current-prefix-arg)))))))
258 (ert-deftest hydra-blue-toggle ()
262 '(defhydra hydra-toggle (:color blue)
264 ("t" toggle-truncate-lines "truncate")
265 ("f" auto-fill-mode "fill")
266 ("a" abbrev-mode "abbrev")
269 (defun hydra-toggle/toggle-truncate-lines nil "Create a hydra with no body and the heads:
271 \"t\": `toggle-truncate-lines',
272 \"f\": `auto-fill-mode',
273 \"a\": `abbrev-mode',
276 The body can be accessed via `hydra-toggle/body'.
278 Call the head: `toggle-truncate-lines'."
282 (catch (quote hydra-disable)
283 (call-interactively (function toggle-truncate-lines))))
284 (defun hydra-toggle/auto-fill-mode nil "Create a hydra with no body and the heads:
286 \"t\": `toggle-truncate-lines',
287 \"f\": `auto-fill-mode',
288 \"a\": `abbrev-mode',
291 The body can be accessed via `hydra-toggle/body'.
293 Call the head: `auto-fill-mode'."
297 (catch (quote hydra-disable)
298 (call-interactively (function auto-fill-mode))))
299 (defun hydra-toggle/abbrev-mode nil "Create a hydra with no body and the heads:
301 \"t\": `toggle-truncate-lines',
302 \"f\": `auto-fill-mode',
303 \"a\": `abbrev-mode',
306 The body can be accessed via `hydra-toggle/body'.
308 Call the head: `abbrev-mode'."
312 (catch (quote hydra-disable)
313 (call-interactively (function abbrev-mode))))
314 (defun hydra-toggle/nil nil "Create a hydra with no body and the heads:
316 \"t\": `toggle-truncate-lines',
317 \"f\": `auto-fill-mode',
318 \"a\": `abbrev-mode',
321 The body can be accessed via `hydra-toggle/body'.
323 Call the head: `nil'."
327 (catch (quote hydra-disable)))
328 (defun hydra-toggle/hint nil
329 (if hydra-lv (lv-message (format #("toggle: [t]: truncate, [f]: fill, [a]: abbrev, [q]: cancel." 9 10 (face hydra-face-blue)
330 24 25 (face hydra-face-blue)
331 35 36 (face hydra-face-blue)
332 48 49 (face hydra-face-blue))))
333 (message (format #("toggle: [t]: truncate, [f]: fill, [a]: abbrev, [q]: cancel." 9 10 (face hydra-face-blue)
334 24 25 (face hydra-face-blue)
335 35 36 (face hydra-face-blue)
336 48 49 (face hydra-face-blue))))))
337 (defun hydra-toggle/body nil "Create a hydra with no body and the heads:
339 \"t\": `toggle-truncate-lines',
340 \"f\": `auto-fill-mode',
341 \"a\": `abbrev-mode',
344 The body can be accessed via `hydra-toggle/body'."
347 (catch (quote hydra-disable)
348 (when hydra-is-helpful (hydra-toggle/hint))
350 (hydra-set-transient-map
353 (keymap (7 . hydra-keyboard-quit)
354 (113 . hydra-toggle/nil)
355 (97 . hydra-toggle/abbrev-mode)
356 (102 . hydra-toggle/auto-fill-mode)
357 (116 . hydra-toggle/toggle-truncate-lines)
358 (kp-subtract . hydra--negative-argument)
359 (kp-9 . hydra--digit-argument)
360 (kp-8 . hydra--digit-argument)
361 (kp-7 . hydra--digit-argument)
362 (kp-6 . hydra--digit-argument)
363 (kp-5 . hydra--digit-argument)
364 (kp-4 . hydra--digit-argument)
365 (kp-3 . hydra--digit-argument)
366 (kp-2 . hydra--digit-argument)
367 (kp-1 . hydra--digit-argument)
368 (kp-0 . hydra--digit-argument)
369 (57 . hydra--digit-argument)
370 (56 . hydra--digit-argument)
371 (55 . hydra--digit-argument)
372 (54 . hydra--digit-argument)
373 (53 . hydra--digit-argument)
374 (52 . hydra--digit-argument)
375 (51 . hydra--digit-argument)
376 (50 . hydra--digit-argument)
377 (49 . hydra--digit-argument)
378 (48 . hydra--digit-argument)
379 (45 . hydra--negative-argument)
380 (21 . hydra--universal-argument))))
381 t (lambda nil (hydra-cleanup))))
382 (setq prefix-arg current-prefix-arg)))))))
384 (ert-deftest hydra-amaranth-vi ()
390 (set-cursor-color "#e52b50")
392 (set-cursor-color "#ffffff")
399 (defun hydra-vi/next-line nil "Create a hydra with no body and the heads:
402 \"k\": `previous-line',
405 The body can be accessed via `hydra-vi/body'.
407 Call the head: `next-line'."
409 (set-cursor-color "#e52b50")
411 (catch (quote hydra-disable)
412 (condition-case err (prog1 t (call-interactively (function next-line)))
413 ((quit error) (message "%S" err)
414 (unless hydra-lv (sit-for 0.8))
416 (when hydra-is-helpful (hydra-vi/hint))
418 (hydra-set-transient-map
421 (keymap (t lambda nil (interactive)
422 (message "An amaranth Hydra can only exit through a blue head")
423 (hydra-set-transient-map hydra-curr-map t)
424 (when hydra-is-helpful (unless hydra-lv (sit-for 0.8))
426 (7 . hydra-keyboard-quit)
428 (107 . hydra-vi/previous-line)
429 (106 . hydra-vi/next-line)
430 (kp-subtract . hydra--negative-argument)
431 (kp-9 . hydra--digit-argument)
432 (kp-8 . hydra--digit-argument)
433 (kp-7 . hydra--digit-argument)
434 (kp-6 . hydra--digit-argument)
435 (kp-5 . hydra--digit-argument)
436 (kp-4 . hydra--digit-argument)
437 (kp-3 . hydra--digit-argument)
438 (kp-2 . hydra--digit-argument)
439 (kp-1 . hydra--digit-argument)
440 (kp-0 . hydra--digit-argument)
441 (57 . hydra--digit-argument)
442 (56 . hydra--digit-argument)
443 (55 . hydra--digit-argument)
444 (54 . hydra--digit-argument)
445 (53 . hydra--digit-argument)
446 (52 . hydra--digit-argument)
447 (51 . hydra--digit-argument)
448 (50 . hydra--digit-argument)
449 (49 . hydra--digit-argument)
450 (48 . hydra--digit-argument)
451 (45 . hydra--negative-argument)
452 (21 . hydra--universal-argument))))
453 t (lambda nil (hydra-cleanup))))))
454 (defun hydra-vi/previous-line nil "Create a hydra with no body and the heads:
457 \"k\": `previous-line',
460 The body can be accessed via `hydra-vi/body'.
462 Call the head: `previous-line'."
464 (set-cursor-color "#e52b50")
466 (catch (quote hydra-disable)
467 (condition-case err (prog1 t (call-interactively (function previous-line)))
468 ((quit error) (message "%S" err)
469 (unless hydra-lv (sit-for 0.8))
471 (when hydra-is-helpful (hydra-vi/hint))
473 (hydra-set-transient-map
476 (keymap (t lambda nil (interactive)
477 (message "An amaranth Hydra can only exit through a blue head")
478 (hydra-set-transient-map hydra-curr-map t)
479 (when hydra-is-helpful (unless hydra-lv (sit-for 0.8))
481 (7 . hydra-keyboard-quit)
483 (107 . hydra-vi/previous-line)
484 (106 . hydra-vi/next-line)
485 (kp-subtract . hydra--negative-argument)
486 (kp-9 . hydra--digit-argument)
487 (kp-8 . hydra--digit-argument)
488 (kp-7 . hydra--digit-argument)
489 (kp-6 . hydra--digit-argument)
490 (kp-5 . hydra--digit-argument)
491 (kp-4 . hydra--digit-argument)
492 (kp-3 . hydra--digit-argument)
493 (kp-2 . hydra--digit-argument)
494 (kp-1 . hydra--digit-argument)
495 (kp-0 . hydra--digit-argument)
496 (57 . hydra--digit-argument)
497 (56 . hydra--digit-argument)
498 (55 . hydra--digit-argument)
499 (54 . hydra--digit-argument)
500 (53 . hydra--digit-argument)
501 (52 . hydra--digit-argument)
502 (51 . hydra--digit-argument)
503 (50 . hydra--digit-argument)
504 (49 . hydra--digit-argument)
505 (48 . hydra--digit-argument)
506 (45 . hydra--negative-argument)
507 (21 . hydra--universal-argument))))
508 t (lambda nil (hydra-cleanup))))))
509 (defun hydra-vi/nil nil "Create a hydra with no body and the heads:
512 \"k\": `previous-line',
515 The body can be accessed via `hydra-vi/body'.
517 Call the head: `nil'."
519 (set-cursor-color "#e52b50")
522 (catch (quote hydra-disable)
523 (set-cursor-color "#ffffff")))
524 (defun hydra-vi/hint nil
525 (if hydra-lv (lv-message (format #("vi: j, k, [q]: quit." 4 5 (face hydra-face-amaranth)
526 7 8 (face hydra-face-amaranth)
527 11 12 (face hydra-face-blue))))
528 (message (format #("vi: j, k, [q]: quit." 4 5 (face hydra-face-amaranth)
529 7 8 (face hydra-face-amaranth)
530 11 12 (face hydra-face-blue))))))
531 (defun hydra-vi/body nil "Create a hydra with no body and the heads:
534 \"k\": `previous-line',
537 The body can be accessed via `hydra-vi/body'."
539 (set-cursor-color "#e52b50")
541 (catch (quote hydra-disable)
542 (when hydra-is-helpful (hydra-vi/hint))
544 (hydra-set-transient-map
547 (keymap (t lambda nil (interactive)
548 (message "An amaranth Hydra can only exit through a blue head")
549 (hydra-set-transient-map hydra-curr-map t)
550 (when hydra-is-helpful (unless hydra-lv (sit-for 0.8))
552 (7 . hydra-keyboard-quit)
554 (107 . hydra-vi/previous-line)
555 (106 . hydra-vi/next-line)
556 (kp-subtract . hydra--negative-argument)
557 (kp-9 . hydra--digit-argument)
558 (kp-8 . hydra--digit-argument)
559 (kp-7 . hydra--digit-argument)
560 (kp-6 . hydra--digit-argument)
561 (kp-5 . hydra--digit-argument)
562 (kp-4 . hydra--digit-argument)
563 (kp-3 . hydra--digit-argument)
564 (kp-2 . hydra--digit-argument)
565 (kp-1 . hydra--digit-argument)
566 (kp-0 . hydra--digit-argument)
567 (57 . hydra--digit-argument)
568 (56 . hydra--digit-argument)
569 (55 . hydra--digit-argument)
570 (54 . hydra--digit-argument)
571 (53 . hydra--digit-argument)
572 (52 . hydra--digit-argument)
573 (51 . hydra--digit-argument)
574 (50 . hydra--digit-argument)
575 (49 . hydra--digit-argument)
576 (48 . hydra--digit-argument)
577 (45 . hydra--negative-argument)
578 (21 . hydra--universal-argument))))
579 t (lambda nil (hydra-cleanup))))
580 (setq prefix-arg current-prefix-arg)))))))
582 (ert-deftest defhydradio ()
585 '(defhydradio hydra-test ()
586 (num "Num" [0 1 2 3 4 5 6 7 8 9 10])
587 (str "Str" ["foo" "bar" "baz"])))
589 (defvar hydra-test/num 0
591 (put 'hydra-test/num 'range [0 1 2 3 4 5 6 7 8 9 10])
592 (defun hydra-test/num ()
593 (hydra--cycle-radio 'hydra-test/num))
594 (defvar hydra-test/str "foo"
596 (put 'hydra-test/str 'range ["foo" "bar" "baz"])
597 (defun hydra-test/str ()
598 (hydra--cycle-radio 'hydra-test/str))
599 (defvar hydra-test/names '(hydra-test/num hydra-test/str))))))
601 (ert-deftest hydra-blue-compat ()
605 '(defhydra hydra-toggle (:color blue)
607 ("t" toggle-truncate-lines "truncate")
608 ("f" auto-fill-mode "fill")
609 ("a" abbrev-mode "abbrev")
612 '(defhydra hydra-toggle (:exit t)
614 ("t" toggle-truncate-lines "truncate")
615 ("f" auto-fill-mode "fill")
616 ("a" abbrev-mode "abbrev")
617 ("q" nil "cancel"))))))
619 (ert-deftest hydra-amaranth-compat ()
625 (set-cursor-color "#e52b50")
627 (set-cursor-color "#ffffff")
636 (set-cursor-color "#e52b50")
638 (set-cursor-color "#ffffff")
643 ("q" nil "quit"))))))
645 (ert-deftest hydra-pink-compat ()
649 '(defhydra hydra-zoom (global-map "<f2>"
652 ("g" text-scale-increase "in")
653 ("l" text-scale-decrease "out")
656 '(defhydra hydra-zoom (global-map "<f2>"
659 ("g" text-scale-increase "in")
660 ("l" text-scale-decrease "out")
661 ("q" nil "quit"))))))
663 (ert-deftest hydra-teal-compat ()
667 '(defhydra hydra-zoom (global-map "<f2>"
670 ("g" text-scale-increase "in")
671 ("l" text-scale-decrease "out")
674 '(defhydra hydra-zoom (global-map "<f2>"
678 ("g" text-scale-increase "in")
679 ("l" text-scale-decrease "out")
680 ("q" nil "quit"))))))
682 (ert-deftest hydra-format ()
684 (let ((hydra-fontify-head-function
685 'hydra-fontify-head-greyscale))
690 _a_ abbrev-mode: %`abbrev-mode
691 _d_ debug-on-error: %`debug-on-error
692 _f_ auto-fill-mode: %`auto-fill-function
693 " '(("a" abbrev-mode nil)
694 ("d" toggle-debug-on-error nil)
695 ("f" auto-fill-mode nil)
696 ("g" golden-ratio-mode nil)
697 ("t" toggle-truncate-lines nil)
698 ("w" whitespace-mode nil)
700 '(concat (format "%s abbrev-mode: %S
701 %s debug-on-error: %S
702 %s auto-fill-mode: %S
703 " "{a}" abbrev-mode "{d}" debug-on-error "{f}" auto-fill-function) "[[q]]: quit"))))
705 (ert-deftest hydra-format-with-sexp ()
707 (let ((hydra-fontify-head-function
708 'hydra-fontify-head-greyscale))
711 "\n_n_ narrow-or-widen-dwim %(progn (message \"checking\")(buffer-narrowed-p))asdf\n"
712 '(("n" narrow-to-region nil) ("q" nil "cancel"))))
713 '(concat (format "%s narrow-or-widen-dwim %Sasdf\n"
717 (buffer-narrowed-p)))
720 (ert-deftest hydra-compat-colors-1 ()
721 (should (equal (hydra--head-color
722 '("e" (message "Exiting now") "blue")
723 '(nil nil :color blue))
725 (should (equal (hydra--head-color
726 '("c" (message "Continuing") "red" :color red)
727 '(nil nil :color blue))
729 (should (equal (hydra--head-color
730 '("e" (message "Exiting now") "blue")
733 (should (equal (hydra--head-color
734 '("c" (message "Continuing") "red" :exit nil)
737 (equal (hydra--head-color
738 '("a" abbrev-mode nil)
739 '(nil nil :color teal))
741 (equal (hydra--head-color
742 '("a" abbrev-mode :exit nil)
743 '(nil nil :color teal))
746 (ert-deftest hydra-compat-colors-2 ()
750 '(defhydra hydra-test (:color amaranth)
752 ("b" fun-b :color blue)
753 ("c" fun-c :color blue)
754 ("d" fun-d :color blue)
755 ("e" fun-e :color blue)
756 ("f" fun-f :color blue)))
758 '(defhydra hydra-test (:color teal)
759 ("a" fun-a :color red)
766 (ert-deftest hydra-compat-colors-3 ()
770 '(defhydra hydra-test ()
772 ("b" fun-b :color blue)
773 ("c" fun-c :color blue)
774 ("d" fun-d :color blue)
775 ("e" fun-e :color blue)
776 ("f" fun-f :color blue)))
778 '(defhydra hydra-test (:color blue)
779 ("a" fun-a :color red)
786 (ert-deftest hydra-compat-colors-4 ()
790 '(defhydra hydra-test ()
796 ("f" fun-f :exit t)))
798 '(defhydra hydra-test (:exit t)
799 ("a" fun-a :exit nil)
806 (ert-deftest hydra-zoom-duplicate-1 ()
810 '(defhydra hydra-zoom ()
812 ("r" (text-scale-set 0) "reset")
813 ("0" (text-scale-set 0) :bind nil :exit t)
814 ("1" (text-scale-set 0) nil :bind nil :exit t)))
816 (defun hydra-zoom/lambda-r nil "Create a hydra with no body and the heads:
818 \"r\": `(text-scale-set 0)',
819 \"0\": `(text-scale-set 0)',
820 \"1\": `(text-scale-set 0)'
822 The body can be accessed via `hydra-zoom/body'.
824 Call the head: `(text-scale-set 0)'."
827 (catch (quote hydra-disable)
828 (condition-case err (prog1 t (call-interactively (function (lambda nil (interactive)
829 (text-scale-set 0)))))
832 (unless hydra-lv (sit-for 0.8))
834 (when hydra-is-helpful (hydra-zoom/hint))
836 (hydra-set-transient-map
838 (quote (keymap (7 . hydra-keyboard-quit)
839 (114 . hydra-zoom/lambda-r)
840 (kp-subtract . hydra--negative-argument)
841 (kp-9 . hydra--digit-argument)
842 (kp-8 . hydra--digit-argument)
843 (kp-7 . hydra--digit-argument)
844 (kp-6 . hydra--digit-argument)
845 (kp-5 . hydra--digit-argument)
846 (kp-4 . hydra--digit-argument)
847 (kp-3 . hydra--digit-argument)
848 (kp-2 . hydra--digit-argument)
849 (kp-1 . hydra--digit-argument)
850 (kp-0 . hydra--digit-argument)
851 (57 . hydra--digit-argument)
852 (56 . hydra--digit-argument)
853 (55 . hydra--digit-argument)
854 (54 . hydra--digit-argument)
855 (53 . hydra--digit-argument)
856 (52 . hydra--digit-argument)
857 (51 . hydra--digit-argument)
858 (50 . hydra--digit-argument)
859 (49 . hydra-zoom/lambda-0)
860 (48 . hydra-zoom/lambda-0)
861 (45 . hydra--negative-argument)
862 (21 . hydra--universal-argument))))
863 t (lambda nil (hydra-cleanup))))))
864 (defun hydra-zoom/lambda-0 nil "Create a hydra with no body and the heads:
866 \"r\": `(text-scale-set 0)',
867 \"0\": `(text-scale-set 0)',
868 \"1\": `(text-scale-set 0)'
870 The body can be accessed via `hydra-zoom/body'.
872 Call the head: `(text-scale-set 0)'."
876 (catch (quote hydra-disable)
877 (call-interactively (function (lambda nil (interactive)
878 (text-scale-set 0))))))
879 (defun hydra-zoom/hint nil
880 (if hydra-lv (lv-message (format #("zoom: [r 0]: reset." 7 8 (face hydra-face-red)
881 9 10 (face hydra-face-blue))))
882 (message (format #("zoom: [r 0]: reset." 7 8 (face hydra-face-red)
883 9 10 (face hydra-face-blue))))))
884 (defun hydra-zoom/body nil "Create a hydra with no body and the heads:
886 \"r\": `(text-scale-set 0)',
887 \"0\": `(text-scale-set 0)',
888 \"1\": `(text-scale-set 0)'
890 The body can be accessed via `hydra-zoom/body'."
893 (catch (quote hydra-disable)
894 (when hydra-is-helpful (hydra-zoom/hint))
896 (hydra-set-transient-map
898 (quote (keymap (7 . hydra-keyboard-quit)
899 (114 . hydra-zoom/lambda-r)
900 (kp-subtract . hydra--negative-argument)
901 (kp-9 . hydra--digit-argument)
902 (kp-8 . hydra--digit-argument)
903 (kp-7 . hydra--digit-argument)
904 (kp-6 . hydra--digit-argument)
905 (kp-5 . hydra--digit-argument)
906 (kp-4 . hydra--digit-argument)
907 (kp-3 . hydra--digit-argument)
908 (kp-2 . hydra--digit-argument)
909 (kp-1 . hydra--digit-argument)
910 (kp-0 . hydra--digit-argument)
911 (57 . hydra--digit-argument)
912 (56 . hydra--digit-argument)
913 (55 . hydra--digit-argument)
914 (54 . hydra--digit-argument)
915 (53 . hydra--digit-argument)
916 (52 . hydra--digit-argument)
917 (51 . hydra--digit-argument)
918 (50 . hydra--digit-argument)
919 (49 . hydra-zoom/lambda-0)
920 (48 . hydra-zoom/lambda-0)
921 (45 . hydra--negative-argument)
922 (21 . hydra--universal-argument))))
923 t (lambda nil (hydra-cleanup))))
924 (setq prefix-arg current-prefix-arg)))))))
926 (ert-deftest hydra-zoom-duplicate-2 ()
930 '(defhydra hydra-zoom ()
932 ("r" (text-scale-set 0) "reset")
933 ("0" (text-scale-set 0) :bind nil :exit t)
934 ("1" (text-scale-set 0) nil :bind nil)))
936 (defun hydra-zoom/lambda-r nil "Create a hydra with no body and the heads:
938 \"r\": `(text-scale-set 0)',
939 \"0\": `(text-scale-set 0)',
940 \"1\": `(text-scale-set 0)'
942 The body can be accessed via `hydra-zoom/body'.
944 Call the head: `(text-scale-set 0)'."
947 (catch (quote hydra-disable)
948 (condition-case err (prog1 t (call-interactively (function (lambda nil (interactive)
949 (text-scale-set 0)))))
952 (unless hydra-lv (sit-for 0.8))
954 (when hydra-is-helpful (hydra-zoom/hint))
956 (hydra-set-transient-map
958 (quote (keymap (7 . hydra-keyboard-quit)
959 (114 . hydra-zoom/lambda-r)
960 (kp-subtract . hydra--negative-argument)
961 (kp-9 . hydra--digit-argument)
962 (kp-8 . hydra--digit-argument)
963 (kp-7 . hydra--digit-argument)
964 (kp-6 . hydra--digit-argument)
965 (kp-5 . hydra--digit-argument)
966 (kp-4 . hydra--digit-argument)
967 (kp-3 . hydra--digit-argument)
968 (kp-2 . hydra--digit-argument)
969 (kp-1 . hydra--digit-argument)
970 (kp-0 . hydra--digit-argument)
971 (57 . hydra--digit-argument)
972 (56 . hydra--digit-argument)
973 (55 . hydra--digit-argument)
974 (54 . hydra--digit-argument)
975 (53 . hydra--digit-argument)
976 (52 . hydra--digit-argument)
977 (51 . hydra--digit-argument)
978 (50 . hydra--digit-argument)
979 (49 . hydra-zoom/lambda-r)
980 (48 . hydra-zoom/lambda-0)
981 (45 . hydra--negative-argument)
982 (21 . hydra--universal-argument))))
983 t (lambda nil (hydra-cleanup))))))
984 (defun hydra-zoom/lambda-0 nil "Create a hydra with no body and the heads:
986 \"r\": `(text-scale-set 0)',
987 \"0\": `(text-scale-set 0)',
988 \"1\": `(text-scale-set 0)'
990 The body can be accessed via `hydra-zoom/body'.
992 Call the head: `(text-scale-set 0)'."
996 (catch (quote hydra-disable)
997 (call-interactively (function (lambda nil (interactive)
998 (text-scale-set 0))))))
999 (defun hydra-zoom/hint nil
1000 (if hydra-lv (lv-message (format #("zoom: [r 0]: reset." 7 8 (face hydra-face-red)
1001 9 10 (face hydra-face-blue))))
1002 (message (format #("zoom: [r 0]: reset." 7 8 (face hydra-face-red)
1003 9 10 (face hydra-face-blue))))))
1004 (defun hydra-zoom/body nil "Create a hydra with no body and the heads:
1006 \"r\": `(text-scale-set 0)',
1007 \"0\": `(text-scale-set 0)',
1008 \"1\": `(text-scale-set 0)'
1010 The body can be accessed via `hydra-zoom/body'."
1013 (catch (quote hydra-disable)
1014 (when hydra-is-helpful (hydra-zoom/hint))
1016 (hydra-set-transient-map
1017 (setq hydra-curr-map
1018 (quote (keymap (7 . hydra-keyboard-quit)
1019 (114 . hydra-zoom/lambda-r)
1020 (kp-subtract . hydra--negative-argument)
1021 (kp-9 . hydra--digit-argument)
1022 (kp-8 . hydra--digit-argument)
1023 (kp-7 . hydra--digit-argument)
1024 (kp-6 . hydra--digit-argument)
1025 (kp-5 . hydra--digit-argument)
1026 (kp-4 . hydra--digit-argument)
1027 (kp-3 . hydra--digit-argument)
1028 (kp-2 . hydra--digit-argument)
1029 (kp-1 . hydra--digit-argument)
1030 (kp-0 . hydra--digit-argument)
1031 (57 . hydra--digit-argument)
1032 (56 . hydra--digit-argument)
1033 (55 . hydra--digit-argument)
1034 (54 . hydra--digit-argument)
1035 (53 . hydra--digit-argument)
1036 (52 . hydra--digit-argument)
1037 (51 . hydra--digit-argument)
1038 (50 . hydra--digit-argument)
1039 (49 . hydra-zoom/lambda-r)
1040 (48 . hydra-zoom/lambda-0)
1041 (45 . hydra--negative-argument)
1042 (21 . hydra--universal-argument))))
1043 t (lambda nil (hydra-cleanup))))
1044 (setq prefix-arg current-prefix-arg)))))))
1046 (ert-deftest hydra--pad ()
1047 (should (equal (hydra--pad '(a b c) 3)
1049 (should (equal (hydra--pad '(a) 3)
1052 (ert-deftest hydra--matrix ()
1053 (should (equal (hydra--matrix '(a b c) 2 2)
1055 (should (equal (hydra--matrix '(a b c d e f g h i) 4 3)
1056 '((a b c d) (e f g h) (i nil nil nil)))))
1058 (ert-deftest hydra--cell ()
1059 (should (equal (hydra--cell "% -75s %%`%s" '(hydra-lv hydra-verbose))
1060 "When non-nil, `lv-message' (not `message') will be used to display hints. %`hydra-lv^^^^^
1061 When non-nil, hydra will issue some non essential style warnings. %`hydra-verbose")))
1063 (ert-deftest hydra--vconcat ()
1064 (should (equal (hydra--vconcat '("abc\ndef" "012\n34" "def\nabc"))
1065 "abc012def\ndef34abc")))
1067 (defhydradio hydra-tng ()
1068 (picard "_p_ Captain Jean Luc Picard:")
1069 (riker "_r_ Commander William Riker:")
1070 (data "_d_ Lieutenant Commander Data:")
1072 (la-forge "_f_ Geordi La Forge:")
1073 (troi "_t_ Deanna Troi:")
1074 (dr-crusher "_c_ Doctor Beverly Crusher:")
1075 (phaser "_h_ Set phasers to " [stun kill]))
1077 (ert-deftest hydra--table ()
1078 (let ((hydra-cell-format "% -30s %% -8`%s"))
1079 (should (equal (hydra--table hydra-tng/names 5 2)
1081 _p_ Captain Jean Luc Picard: % -8`hydra-tng/picard^^ _t_ Deanna Troi: % -8`hydra-tng/troi^^^^^^
1082 _r_ Commander William Riker: % -8`hydra-tng/riker^^^ _c_ Doctor Beverly Crusher: % -8`hydra-tng/dr-crusher
1083 _d_ Lieutenant Commander Data: % -8`hydra-tng/data^^^^ _h_ Set phasers to % -8`hydra-tng/phaser^^^^
1084 _w_ Worf: % -8`hydra-tng/worf^^^^
1085 _f_ Geordi La Forge: % -8`hydra-tng/la-forge" 1)))
1086 (should (equal (hydra--table hydra-tng/names 4 3)
1088 _p_ Captain Jean Luc Picard: % -8`hydra-tng/picard _f_ Geordi La Forge: % -8`hydra-tng/la-forge^^
1089 _r_ Commander William Riker: % -8`hydra-tng/riker^ _t_ Deanna Troi: % -8`hydra-tng/troi^^^^^^
1090 _d_ Lieutenant Commander Data: % -8`hydra-tng/data^^ _c_ Doctor Beverly Crusher: % -8`hydra-tng/dr-crusher
1091 _w_ Worf: % -8`hydra-tng/worf^^ _h_ Set phasers to % -8`hydra-tng/phaser^^^^" 1)))))
1093 (provide 'hydra-test)
1095 ;;; hydra-test.el ends here