[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[nongnu] elpa/rust-mode 55e7483 113/486: Add a hook so that we briefly h
From: |
ELPA Syncer |
Subject: |
[nongnu] elpa/rust-mode 55e7483 113/486: Add a hook so that we briefly highlight the matching `<` when `>` is typed. |
Date: |
Sat, 7 Aug 2021 09:25:00 -0400 (EDT) |
branch: elpa/rust-mode
commit 55e7483d507b8ff88e7f84685ab83a10ac754856
Author: Niko Matsakis <niko@alum.mit.edu>
Commit: Niko Matsakis <niko@alum.mit.edu>
Add a hook so that we briefly highlight the matching `<` when `>` is typed.
Also add an interactive command for finding the matching `<`. I'd like to
bind
this to `C-c >` (reserved for major modes), but I can't figure out what the
local
keymap is for rust-mode (help!).
---
rust-mode.el | 76 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++-
1 file changed, 75 insertions(+), 1 deletion(-)
diff --git a/rust-mode.el b/rust-mode.el
index 8da04bd..b2e0d5d 100644
--- a/rust-mode.el
+++ b/rust-mode.el
@@ -481,11 +481,84 @@ This is written mainly to be used as
`end-of-defun-function' for Rust."
;; There is no opening brace, so consider the whole buffer to be one
"defun"
(goto-char (point-max))))
+;; Angle-bracket matching. This is kind of a hack designed to deal
+;; with the fact that we can't add angle-brackets to the list of
+;; matching characters unconditionally. Basically we just have some
+;; special-case code such that whenever `>` is typed, we look
+;; backwards to find a matching `<` and highlight it, whether or not
+;; this is *actually* appropriate. This could be annoying so it is
+;; configurable (but on by default because it's awesome).
+
+(defcustom rust-blink-matching-angle-brackets t
+ "Blink matching `<` (if any) when `>` is typed"
+ :type 'boolean
+ :group 'rust-mode)
+
+(defvar rust-point-before-matching-angle-bracket 0)
+
+(defvar rust-matching-angle-bracker-timer nil)
+
+(defun rust-find-matching-angle-bracket ()
+ (save-excursion
+ (let ((angle-brackets 1)
+ (start-point (point))
+ (invalid nil))
+ (while (and
+ ;; didn't find a match
+ (> angle-brackets 0)
+ ;; we have no guarantee of a match, so give up eventually
+ (< (- start-point (point)) blink-matching-paren-distance)
+ ;; didn't hit the top of the buffer
+ (> (point) (point-min))
+ ;; didn't hit something else weird like a `;`
+ (not invalid))
+ (backward-char 1)
+ (cond
+ ((looking-at ">")
+ (setq angle-brackets (+ angle-brackets 1)))
+ ((looking-at "<")
+ (setq angle-brackets (- angle-brackets 1)))
+ ((looking-at "[;{]")
+ (setq invalid t))))
+ (cond
+ ((= angle-brackets 0) (point))
+ (t nil)))))
+
+(defun rust-restore-point-after-angle-bracket ()
+ (goto-char rust-point-before-matching-angle-bracket)
+ (when rust-matching-angle-bracker-timer
+ (cancel-timer rust-matching-angle-bracker-timer))
+ (setq rust-matching-angle-bracker-timer nil)
+ (remove-hook 'pre-command-hook 'rust-restore-point-after-angle-bracket))
+
+(defun rust-match-angle-bracket-hook ()
+ "If the most recently inserted character is a `>`, briefly moves point to
matching `<` (if any)."
+ (interactive)
+ (when (and rust-blink-matching-angle-brackets
+ (looking-back ">"))
+ (let ((matching-angle-bracket-point (save-excursion
+ (backward-char 1)
+ (rust-find-matching-angle-bracket))))
+ (when matching-angle-bracket-point
+ (progn
+ (setq rust-point-before-matching-angle-bracket (point))
+ (goto-char matching-angle-bracket-point)
+ (add-hook 'pre-command-hook 'rust-restore-point-after-angle-bracket)
+ (setq rust-matching-angle-bracker-timer
+ (run-at-time blink-matching-delay nil
'rust-restore-point-after-angle-bracket)))))))
+
+(defun rust-match-angle-bracket ()
+ "The point should be placed on a `>`. Finds the matching `<` and moves point
there."
+ (interactive)
+ (let ((matching-angle-bracket-point (rust-find-matching-angle-bracket)))
+ (if matching-angle-bracket-point
+ (goto-char matching-angle-bracket-point)
+ (message "no matching angle bracket found"))))
+
;; For compatibility with Emacs < 24, derive conditionally
(defalias 'rust-parent-mode
(if (fboundp 'prog-mode) 'prog-mode 'fundamental-mode))
-
;;;###autoload
(define-derived-mode rust-mode rust-parent-mode "Rust"
"Major mode for Rust code."
@@ -519,6 +592,7 @@ This is written mainly to be used as
`end-of-defun-function' for Rust."
(setq-local end-of-defun-function 'rust-end-of-defun)
(setq-local parse-sexp-lookup-properties t)
(add-hook 'syntax-propertize-extend-region-functions
'rust-syntax-propertize-extend-region)
+ (add-hook 'post-self-insert-hook 'rust-match-angle-bracket-hook)
(setq-local syntax-propertize-function 'rust-syntax-propertize))
(defun rust-syntax-propertize-extend-region (start end)
- [nongnu] elpa/rust-mode fa51087 057/486: Minor cleanup and formatting tweaks to the rust-mode README, (continued)
- [nongnu] elpa/rust-mode fa51087 057/486: Minor cleanup and formatting tweaks to the rust-mode README, ELPA Syncer, 2021/08/07
- [nongnu] elpa/rust-mode 4e0a334 081/486: emacs: do not highlight `#foo]` as an attribute, ELPA Syncer, 2021/08/07
- [nongnu] elpa/rust-mode 2d12c3e 072/486: Emacs: always jump the cursor if needed on indent, ELPA Syncer, 2021/08/07
- [nongnu] elpa/rust-mode 5ebe4c7 080/486: emacs: highlight `macro_name!` in macro invocations using [] delimiters, ELPA Syncer, 2021/08/07
- [nongnu] elpa/rust-mode 76bcb8d 074/486: etc: attempts at fixing editor highlighting for new attribute syntax, ELPA Syncer, 2021/08/07
- [nongnu] elpa/rust-mode a59ef8e 090/486: Fix spelling mistakes in comments., ELPA Syncer, 2021/08/07
- [nongnu] elpa/rust-mode 9c0846a 101/486: Add test for '\'' single quote char literal, ELPA Syncer, 2021/08/07
- [nongnu] elpa/rust-mode 55080f6 100/486: Fix syntax and highlighting for char literals, ELPA Syncer, 2021/08/07
- [nongnu] elpa/rust-mode 8a69f69 104/486: Use old code style for emacs 23 compat, ELPA Syncer, 2021/08/07
- [nongnu] elpa/rust-mode 9e83b30 110/486: Merge pull request #21 from pnkfelix/tests-allow-override-of-which-emacs, ELPA Syncer, 2021/08/07
- [nongnu] elpa/rust-mode 55e7483 113/486: Add a hook so that we briefly highlight the matching `<` when `>` is typed.,
ELPA Syncer <=
- [nongnu] elpa/rust-mode 439da40 115/486: disable emacs23 testing on travis., ELPA Syncer, 2021/08/07
- [nongnu] elpa/rust-mode d2c6d6c 116/486: Merge pull request #26 from pnkfelix/disable-emacs23-testing, ELPA Syncer, 2021/08/07
- [nongnu] elpa/rust-mode 8c9ea88 127/486: Fix raw string bugs, ELPA Syncer, 2021/08/07
- [nongnu] elpa/rust-mode a653c6b 123/486: Highlight raw strings correctly, ELPA Syncer, 2021/08/07
- [nongnu] elpa/rust-mode f3e8f20 119/486: Re-enable emacs23 in Travis, ELPA Syncer, 2021/08/07
- [nongnu] elpa/rust-mode 5b73df1 133/486: Fix typo/missing lines in comment in test, ELPA Syncer, 2021/08/07
- [nongnu] elpa/rust-mode 3a0a727 129/486: Merge pull request #35 from MicahChalmer/fix-raw-string-bugs, ELPA Syncer, 2021/08/07
- [nongnu] elpa/rust-mode c7413e6 130/486: Don't set syntax-begin-function, ELPA Syncer, 2021/08/07
- [nongnu] elpa/rust-mode b15b0eb 140/486: Merge pull request #45 from MicahChalmer/backslash-and-double-quote-char-literals, ELPA Syncer, 2021/08/07
- [nongnu] elpa/rust-mode 52febe9 137/486: Add a few more tests for indents inside strings, ELPA Syncer, 2021/08/07