emacs-elpa-diffs
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[nongnu] elpa/go-mode fdc1545 436/495: Fix indent for case statement com


From: ELPA Syncer
Subject: [nongnu] elpa/go-mode fdc1545 436/495: Fix indent for case statement comments
Date: Sat, 7 Aug 2021 09:06:04 -0400 (EDT)

branch: elpa/go-mode
commit fdc1545d0ca494eb533d006b42c4bb4a6fb73d6e
Author: Muir Manders <muir@retailnext.net>
Commit: Peter Sanford <psanford@sanford.io>

    Fix indent for case statement comments
    
    Try to replicate gofmt behavior. In particular (assuming there are no
    non-comment lines between comment in question and proceeding "case"):
    - comments above first "case" always align with case
    - comments between a case-aligned comment and the proceeding "case"
      always align with the "case"
    - all other cases are ambiguous, so if comment is aligned with "case"
      or with the case block, maintain the indent, otherwise default
      indent to the case block
    
    Closes: #287 [via git-merge-pr]
---
 go-mode.el                                | 70 ++++++++++++++++++++++++++++---
 test/testdata/indentation_tests/switch.go | 34 +++++++++++++++
 2 files changed, 98 insertions(+), 6 deletions(-)

diff --git a/go-mode.el b/go-mode.el
index e0f95e2..11646cc 100644
--- a/go-mode.el
+++ b/go-mode.el
@@ -755,6 +755,60 @@ The return value is the position of the opening paren."
        (t
         (current-indentation))))))
 
+(defconst go--comment-start-regexp "[[:space:]]*\\(/\\*\\|//\\)")
+
+(defun go--case-comment-p (indent)
+  "Return non-nil if looking at a comment attached to a case statement.
+
+INDENT is the normal indent of this line, i.e. that of the case body."
+  (when (looking-at go--comment-start-regexp)
+    (let (switch-before
+          case-after
+          has-case-aligned-preceding-comment)
+
+      (save-excursion
+        ;; Search for previous case-aligned comment.
+        (while (and
+                (zerop (forward-line -1))
+                (cond
+                 ((go-in-comment-p))
+
+                 ((looking-at "^[[:space:]]*$"))
+
+                 ((looking-at go--comment-start-regexp)
+                  (when (= (current-indentation) (- indent tab-width))
+                    (setq has-case-aligned-preceding-comment t))
+                  t))))
+
+        ;; Record if a switch (or select) precedes us.
+        (setq switch-before (looking-at 
"^[[:space:]]*\\(switch\\|select\\)[[:space:]]")))
+
+      ;; Record if first proceeding non-comment line is a case statement.
+      (save-excursion
+        (while (and
+                (zerop (forward-line 1))
+                (or
+                 (go-in-comment-p)
+                 (looking-at go--comment-start-regexp)
+                 (looking-at "^[[:space:]]*$"))))
+
+        (setq case-after (looking-at go--case-or-default-regexp)))
+
+      (and
+       ;; a "case" statement comes after our comment
+       case-after
+
+       (or
+        ;; "switch" statement precedes us, always align with "case"
+        switch-before
+
+        ;; a preceding comment is aligned with "case", we should too
+        has-case-aligned-preceding-comment
+
+        ;; other cases are ambiguous, so if comment is currently
+        ;; aligned with "case", leave it that way
+        (= (current-indentation) (- indent tab-width)))))))
+
 (defun go--non-dangling-indent ()
   (save-excursion
     (while (go-previous-line-has-dangling-op-p)
@@ -777,12 +831,16 @@ The return value is the position of the opening paren."
     (if (go-in-string-or-comment-p)
         (goto-char point)
       (setq indent (go-indentation-at-point))
-      (if (and
-           (looking-at (concat go-label-regexp ":\\([[:space:]]*/.+\\)?$\\|" 
go--case-or-default-regexp))
-           ;; don't think last part of multiline case statement is a label
-           (not (go-previous-line-has-dangling-op-p))
-           (not (go--in-case-clause-list-p)))
-          (cl-decf indent tab-width))
+      (when (or
+             (and
+              (looking-at (concat go-label-regexp 
":\\([[:space:]]*/.+\\)?$\\|" go--case-or-default-regexp))
+              ;; don't think last part of multiline case statement is a label
+              (not (go-previous-line-has-dangling-op-p))
+              (not (go--in-case-clause-list-p)))
+
+             ;; comment attached above a "case" statement
+             (go--case-comment-p indent))
+        (cl-decf indent tab-width))
       (setq shift-amt (- indent (current-column)))
       (if (zerop shift-amt)
           nil
diff --git a/test/testdata/indentation_tests/switch.go 
b/test/testdata/indentation_tests/switch.go
index 7d0f972..07fd34a 100644
--- a/test/testdata/indentation_tests/switch.go
+++ b/test/testdata/indentation_tests/switch.go
@@ -29,4 +29,38 @@ func main() {
                "hi",
                "there":
        }
+
+       switch {
+       // attached
+       case true:
+               // body
+               code()
+               // could go either way
+       case true:
+       // could go either way
+       case true:
+               // could go both ways
+       // could go both ways
+       case true:
+
+       /* this works too */
+       case true:
+
+       /* hi */
+       /* this works too */
+       case true:
+
+       /* hi
+          this works too */
+       case true:
+
+       // could go either way
+       case true:
+
+               // could go either way
+       case true:
+
+       // also works
+       default:
+       }
 }



reply via email to

[Prev in Thread] Current Thread [Next in Thread]