branch: elpa/go-mode
commit dac200f7a8de7bf22793d39b5dd46756cbadb295
Author: Muir Manders <[email protected]>
Commit: Peter Sanford <[email protected]>
Fix font locking in nested signatures.
We weren't font locking nested signatures such as:
func foo(i int, f func(b bool) string) float32
I fixed the param list fontification to jump back to the opening "("
after fontifying the list. This allows it to match param lists
contained within the outer list.
I also fixed the "single result" rule to properly match the "string"
in the above example. I had to break it out into a function to avoid
consuming the ")" after "string", which prevented it from matching the
following float32 result type.
Closes: #318 [via git-merge-pr]
---
go-mode.el | 47 +++++++++++++++++++++++++++++++++++++++++++----
test/go-font-lock-test.el | 3 +++
2 files changed, 46 insertions(+), 4 deletions(-)
diff --git a/go-mode.el b/go-mode.el
index 44b53cd..f1a207e 100644
--- a/go-mode.el
+++ b/go-mode.el
@@ -416,7 +416,8 @@ For mode=set, all covered lines will have this weight."
(go--fontify-param
;; Pre-match form that runs before the first sub-match.
(go--fontify-param-pre)
- nil ;; We don't use the post-match form.
+ ;; Post-match form that runs after last sub-match.
+ (go--fontify-param-post)
;; Subexp 1 is the param variable name, if any.
(1 font-lock-variable-name-face)
;; Subexp 2 is the param type name, if any. We set the LAXMATCH
@@ -425,7 +426,7 @@ For mode=set, all covered lines will have this weight."
;; Special case to match non-parenthesized function results. For
;; example, "func(i int) string".
- (,(concat ")[[:space:]]+" go-type-name-regexp "\\([[:space:]]\\|$\\)") 1
font-lock-type-face)
+ (go--match-single-func-result 1 font-lock-type-face)
;; Match name+type pairs, such as "foo bar" in "var foo bar".
(go--match-ident-type-pair 2 font-lock-type-face)
@@ -1266,8 +1267,13 @@ INDENT is the normal indent of this line, i.e. that of
the case body."
This is used during fontification of function signatures.")
+(defvar go--fontify-param-beg nil
+ "Position of \"(\" starting param list.
+
+This is used during fontification of function signatures.")
+
(defun go--fontify-param-pre ()
- "Set `go--fontify-param-has-name' appropriately.
+ "Set `go--fontify-param-has-name' and `go--fontify-param-beg' appropriately.
This is used as an anchored font lock keyword PRE-MATCH-FORM. We
must set `go--fontify-param-has-name' ahead of time because you
@@ -1283,15 +1289,29 @@ func foo(i, j int) {}
(setq go--fontify-param-has-name (eq
(go--parameter-list-type (point-max))
'present))
+
+ ;; Remember where our match started so we can continue our serach
+ ;; from here.
+ (setq go--fontify-param-beg (point))
+
;; Return position of closing paren so we process the entire
;; multiline param list.
(save-excursion
(let ((depth (go-paren-level)))
(while (and
(re-search-forward ")" nil t)
- (> (go-paren-level) depth))))
+ (>= (go-paren-level) depth))))
(point)))
+(defun go--fontify-param-post ()
+ "Move point back to opening paren.
+
+This is used as an anchored font lock keyword POST-MATCH-FORM. We
+move point back to the opening \"(\" so we find nested param
+lists.
+"
+ (goto-char go--fontify-param-beg))
+
(defun go--match-param-start (end)
"Search for the starting of param lists.
@@ -1520,6 +1540,25 @@ succeeds."
found-match))
+(defconst go--single-func-result-re (concat ")[[:space:]]+"
go-type-name-regexp "\\(?:$\\|[[:space:]),]\\)"))
+
+(defun go--match-single-func-result (end)
+ "Match single result types.
+
+Parenthetical result lists are handled by the param list keyword,
+so we need a separate keyword to handle singular reuslt types
+such as \"string\" in:
+
+func foo(i int) string"
+ (let (found-match)
+ (while (and
+ (not found-match)
+ (re-search-forward go--single-func-result-re end t))
+ (when (not (member (match-string 1) go-mode-keywords))
+ (setq found-match t)
+ (goto-char (match-end 1))))
+ found-match))
+
(defconst go--type-alias-re
(concat "^[[:space:]]*\\(type\\)?[[:space:]]*" go-identifier-regexp
"[[:space:]]*=[[:space:]]*" go-type-name-regexp))
diff --git a/test/go-font-lock-test.el b/test/go-font-lock-test.el
index 9fb5ae3..417fdf6 100644
--- a/test/go-font-lock-test.el
+++ b/test/go-font-lock-test.el
@@ -27,6 +27,9 @@
(should-fontify "KfuncK(KinterfaceK { FfooF() }, TstringT) KinterfaceK{}")
+ (should-fontify "KfuncK(VaV TbT, VcV KfuncK(VdV *TeT) TdT) TfT")
+ (should-fontify "KfuncK(VaV KfuncK() TbT, VcV TdT)")
+
(should-fontify "
KfuncK FfooF(
VaV TcatT, VbV KinterfaceK { FbarkF() },