[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[nongnu] elpa/go-mode 4acf733 468/495: Fully fontify type and const decl
From: |
ELPA Syncer |
Subject: |
[nongnu] elpa/go-mode 4acf733 468/495: Fully fontify type and const decls. |
Date: |
Sat, 7 Aug 2021 09:06:10 -0400 (EDT) |
branch: elpa/go-mode
commit 4acf7333e131607831a975b0d22773729886736b
Author: Muir Manders <muir@mnd.rs>
Commit: Peter Sanford <psanford@sanford.io>
Fully fontify type and const decls.
- fontify declared types within block "type" decls, including type
aliases
- fontify declared constants within "const" decls
Closes: #317 [via git-merge-pr]
---
go-mode.el | 144 ++++++++++++++++++++++++++++++++--------------
test/go-font-lock-test.el | 39 ++++++-------
2 files changed, 121 insertions(+), 62 deletions(-)
diff --git a/go-mode.el b/go-mode.el
index 0722769..44b53cd 100644
--- a/go-mode.el
+++ b/go-mode.el
@@ -433,8 +433,12 @@ For mode=set, all covered lines will have this weight."
;; An anchored matcher for type switch case clauses.
(go--match-type-switch-case (go--fontify-type-switch-case nil nil (1
font-lock-type-face)))
- ;; Match variable names in var decls.
- (go--match-var-decl 1 font-lock-variable-name-face)
+ ;; Match variable names in var decls, constant names in const
+ ;; decls, and type names in type decls.
+ (go--match-decl
+ (1 font-lock-variable-name-face nil t)
+ (2 font-lock-constant-face nil t)
+ (3 font-lock-type-face nil t))
(,(concat "\\_<" (regexp-opt go-mode-keywords t) "\\_>") .
font-lock-keyword-face)
(,(concat "\\(\\_<" (regexp-opt go-builtins t) "\\_>\\)[[:space:]]*(") 1
font-lock-builtin-face)
@@ -455,8 +459,8 @@ For mode=set, all covered lines will have this weight."
;; Raw string literal, needed for font-lock-syntactic-keywords
("\\(`[^`]*`\\)" 1 font-lock-multiline)
- ;; Type decl
- (,(concat "\\_<type\\_>[[:space:]]+\\(" go-identifier-regexp
"\\)[[:space:]]*\\(?:=[[:space:]]*\\)?\\(?:" go-type-name-regexp "\\)?" ) (1
font-lock-type-face) (2 font-lock-type-face nil t))
+ ;; RHS of type alias.
+ (go--match-type-alias 2 font-lock-type-face)
;; Arrays/slices: []<type> | [123]<type> | [some.Const]<type> |
[someConst]<type> | [...]<type>
(,(concat "\\[\\(?:[[:digit:]]+\\|" go-qualified-identifier-regexp "\\|"
go-identifier-regexp "\\|\\.\\.\\.\\)?\\]" go-type-name-regexp) 1
font-lock-type-face)
@@ -1401,58 +1405,97 @@ comma, it stops at it. Return non-nil if comma was
found."
(setq done (not (go--search-next-comma end))))
found-match))
-(defun go--in-var-decl-p ()
- "Return non-nil if insde a \"var\" decl."
- (or
- (go--in-paren-with-prefix-p ?\( "var")
- (save-excursion
- (let ((depth (go-paren-level)))
- (beginning-of-line)
+(defun go--containing-decl ()
+ "Return containing decl kind var|const|type, if any."
+ (save-match-data
+ (or
+ (save-excursion
(and
- (= (go-paren-level) depth)
- (looking-at-p "[[:space:]]*var[[:space:]]"))))))
-
-(defconst go--match-var-re (concat "\\(?:^\\|[[:space:]]\\)\\("
go-identifier-regexp "\\)\\_>"))
-
-(defun go--match-var-decl (end)
- "Match variable declarations inside \"var\" decls and \":=\"
- assignments."
- (let (found-match)
+ (go-goto-opening-parenthesis)
+ (eq (char-after) ?\()
+ (skip-syntax-backward " ")
+ (skip-syntax-backward "w")
+ (looking-at "\\(var\\|const\\|type\\)[[:space:]]")
+ (match-string-no-properties 1)))
+
+ (save-excursion
+ (let ((depth (go-paren-level)))
+ (beginning-of-line)
+ (and
+ (= (go-paren-level) depth)
+ (looking-at "[[:space:]]*\\(var\\|const\\|type\\)[[:space:]]")
+ (match-string-no-properties 1)))))))
+
+(defconst go--decl-ident-re (concat "\\(?:^\\|[[:space:]]\\)\\(\\(\\("
go-identifier-regexp "\\)\\)\\)\\_>"))
+
+(defun go--match-decl (end)
+ "Match identifers in \"var\", \"type\" and \"const\" decls, as
+well as \":=\" assignments.
+
+In order to only scan once, the regex has three subexpressions
+that match the same identifier. Depending on the kind of
+containing decl we zero out the subexpressions so the right one
+gets highlighted by the font lock keyword."
+ (let (found-match decl)
(while (and
(not found-match)
- (re-search-forward go--match-var-re end t))
+ (re-search-forward go--decl-ident-re end t))
- (save-match-data
- (save-excursion
- (cond
+ (save-excursion
+ ;; Skip keywords.
+ (cond
((member (match-string 1) go-mode-keywords))
((and
- ;; We are inside a "var" decl.
- (go--in-var-decl-p)
+ ;; We are in a decl of some kind.
+ (setq decl (go--containing-decl))
+
+ ;; We aren't on right side of equals sign.
+ (not (go--looking-back-p "=")))
(or
- ;; We are followed directly by comma and aren't on right
- ;; side of equals sign.
- (and
- (looking-at "[[:space:]]*,")
- (not (looking-back "=.*" (line-beginning-position))))
+ ;; We are followed directly by comma.
+ (looking-at-p "[[:space:]]*,")
;; Or we are followed by a space and non-space (non-space
;; might be a type name or "=").
- (looking-at "[[:space:]]+[^[:space:]]")))
- (setq found-match t))
-
- ;; Left side of ":=" assignmnet.
- ((looking-at ".*:=")
- (let ((depth (go-paren-level)))
- (goto-char (match-end 0))
- ;; Make sure the ":=" isn't in a comment or a sub-block.
- (setq found-match (and
- (not (go-in-string-or-comment-p))
- (= depth (go-paren-level))))))))))
+ (looking-at-p "[[:space:]]+[^[:space:]]"))
+
+ (setq found-match t)
+
+ ;; Unset match data subexpressions that don't apply based on
+ ;; the decl kind.
+ (let ((md (match-data)))
+ (cond
+ ((string= decl "var")
+ (setf (nth 4 md) nil (nth 5 md) nil (nth 6 md) nil (nth 7 md)
nil))
+ ((string= decl "const")
+ (setf (nth 2 md) nil (nth 3 md) nil (nth 6 md) nil (nth 7 md)
nil))
+ ((string= decl "type")
+ (setf (nth 2 md) nil (nth 3 md) nil (nth 4 md) nil (nth 5 md)
nil)))
+ (set-match-data md)))
+
+ (t
+ (save-match-data
+ ;; Left side of ":=" assignmnet.
+ (when (looking-at ".*:=")
+ (let ((depth (go-paren-level)))
+ (goto-char (match-end 0))
+ ;; Make sure the ":=" isn't in a comment or a sub-block.
+ (setq found-match (and
+ (not (go-in-string-or-comment-p))
+ (= depth (go-paren-level)))))))))))
found-match))
+(defun go--looking-back-p (re)
+ "Return non-nil if RE matches beginning of line to point.
+
+RE is not anchored automatically."
+ (string-match-p
+ re
+ (buffer-substring-no-properties (point) (line-beginning-position))))
+
+
(defconst go--ident-type-pair-re (concat "\\_<\\(" go-identifier-regexp
"\\)[[:space:]]+" go-type-name-regexp))
(defun go--match-ident-type-pair (end)
@@ -1477,6 +1520,23 @@ succeeds."
found-match))
+(defconst go--type-alias-re
+ (concat "^[[:space:]]*\\(type\\)?[[:space:]]*" go-identifier-regexp
"[[:space:]]*=[[:space:]]*" go-type-name-regexp))
+
+(defun go--match-type-alias (end)
+ "Search for type aliases.
+
+We are looking for the right-hand-side of the type alias"
+ (let (found-match)
+ (while (and
+ (not found-match)
+ (re-search-forward go--type-alias-re end t))
+ ;; Either line started with "type", or we are in a "type" block.
+ (setq found-match (or
+ (match-string 1)
+ (go--in-paren-with-prefix-p ?\( "type"))))
+ found-match))
+
(defun go--parameter-list-type (end)
"Return `present' if the parameter list has names, or `absent' if not.
diff --git a/test/go-font-lock-test.el b/test/go-font-lock-test.el
index bbe62cf..9fb5ae3 100644
--- a/test/go-font-lock-test.el
+++ b/test/go-font-lock-test.el
@@ -36,25 +36,6 @@ KfuncK FfooF(
VjustV TstopT,
) { }"))
-(ert-deftest go--fontify-decls ()
- (should-fontify "KvarK VfooV TintT")
- (should-fontify "KvarK VfooV *[3]TintT")
- (should-fontify "KvarK VfooV Tfoo.ZebraT")
- (should-fontify "KvarK VfooV, VbarV Tfoo.ZebraT")
-
- (should-fontify "
-KvarK (
- VaV TbT
- VaV, VbV TbT
- VaV KfuncK(VbV TcT)
-)")
-
- (should-fontify "
-KconstK (
- a = 1
- a TintT = 1
-)"))
-
(ert-deftest go--fontify-struct ()
(should-fontify "KstructK { i TintT }")
(should-fontify "KstructK { a, b TintT }")
@@ -128,12 +109,20 @@ KcaseK string:
;; Don't fontify "!=" operator.
(should-fontify "foo != bar"))
+
(ert-deftest go--fontify-type-decl ()
(should-fontify "KtypeK TfooT TbarT")
(should-fontify "KtypeK TfooT Tbar.ZarT")
(should-fontify "KtypeK TfooT KstructK { }")
(should-fontify "KtypeK TfooT = Tbar.ZarT")
- (should-fontify "KtypeK TfooT = KmapK[TstringT]TstringT"))
+ (should-fontify "KtypeK TfooT = KmapK[TstringT]TstringT")
+
+ (should-fontify "
+KtypeK (
+ TfooT TbarT
+ TfooT KstructK {}
+ TfooT = *Tbar.ZarT
+)"))
(ert-deftest go--fontify-var-decl ()
(should-fontify "KvarK VfooV = bar")
@@ -153,6 +142,16 @@ KvarK (
VfooV, VbarV TbazT = qux, zorb
)"))
+(ert-deftest go--fontify-const-decl ()
+ (should-fontify "KconstK CfooC, CbarC = 123, 456 D// D")
+ (should-fontify "KconstK CfooC, CbarC TbazT = 123, 456")
+ (should-fontify "
+KconstK (
+ CaC = 1
+ CaC TintT = 1
+ CaC, CbC TintT = 1, 2
+)"))
+
(ert-deftest go--fontify-assign ()
(should-fontify "VfooV := bar")
(should-fontify "foo = bar D// DQ:=Q")
- [nongnu] elpa/go-mode 88ffc9e 452/495: Add github action yaml file to run ert tests, (continued)
- [nongnu] elpa/go-mode 88ffc9e 452/495: Add github action yaml file to run ert tests, ELPA Syncer, 2021/08/07
- [nongnu] elpa/go-mode 4f15abf 449/495: Fix fill-paragraph for certain block comments., ELPA Syncer, 2021/08/07
- [nongnu] elpa/go-mode a13b814 448/495: Add option to reuse a single buffer for godoc, ELPA Syncer, 2021/08/07
- [nongnu] elpa/go-mode a82369b 453/495: Readme: add basic information about gopls., ELPA Syncer, 2021/08/07
- [nongnu] elpa/go-mode 839190b 455/495: Run all tests in GH CI, ELPA Syncer, 2021/08/07
- [nongnu] elpa/go-mode 7248358 462/495: Fontify type names in type switch statements, ELPA Syncer, 2021/08/07
- [nongnu] elpa/go-mode 4fabba6 464/495: Small fix for fontification of array types, ELPA Syncer, 2021/08/07
- [nongnu] elpa/go-mode 656590a 463/495: Fontify qualified composite literal types., ELPA Syncer, 2021/08/07
- [nongnu] elpa/go-mode d304565 474/495: Fix signature fontification after comments., ELPA Syncer, 2021/08/07
- [nongnu] elpa/go-mode e9b9c0e 473/495: Add some fontification faces for go-dot-mod-mode., ELPA Syncer, 2021/08/07
- [nongnu] elpa/go-mode 4acf733 468/495: Fully fontify type and const decls.,
ELPA Syncer <=
- [nongnu] elpa/go-mode dac200f 469/495: Fix font locking in nested signatures., ELPA Syncer, 2021/08/07
- [nongnu] elpa/go-mode fa2162b 475/495: Fix "nil" fontification in type switch clause., ELPA Syncer, 2021/08/07
- [nongnu] elpa/go-mode 7ce031c 481/495: Allow disabling variable font locking., ELPA Syncer, 2021/08/07
- [nongnu] elpa/go-mode e10d677 478/495: indent: fix func literals in dangling lines, ELPA Syncer, 2021/08/07
- [nongnu] elpa/go-mode c9f5e92 483/495: Fix indentation of chained dangling selectors., ELPA Syncer, 2021/08/07
- [nongnu] elpa/go-mode fdf46fe 492/495: Fix go.mod fontification., ELPA Syncer, 2021/08/07
- [nongnu] elpa/go-mode e8eea7f 487/495: Fix fontification of multiline type switch clauses., ELPA Syncer, 2021/08/07
- [nongnu] elpa/go-mode 2f2910c 223/495: fix end-of-defun for function with inline struct/interface arguments, ELPA Syncer, 2021/08/07
- [nongnu] elpa/go-mode f1adac0 230/495: switch versioning to semver, ELPA Syncer, 2021/08/07
- [nongnu] elpa/go-mode d9f0bee 232/495: add variable to customize godef command, ELPA Syncer, 2021/08/07