@@ -746,33 +746,61 @@ The possible values for this variable are
746
746
((parent-is " list_lit" ) parent 1 )
747
747
((parent-is " set_lit" ) parent 2 ))))
748
748
749
- (defvar clojure-ts--symbols-with-body-expressions -regexp
749
+ (defvar clojure-ts--symbols-block-0 -regexp
750
750
(eval-and-compile
751
- (rx (or
752
- ; ; Match def* symbols,
753
- ; ; we also explicitly do not match symbols beginning with
754
- ; ; "default" "deflate" and "defer", like cljfmt
755
- (and line-start " def" )
756
- ; ; Match with-* symbols
757
- (and line-start " with-" )
758
- ; ; Exact matches
759
- (and line-start
760
- (or " alt!" " alt!!" " are" " as->"
761
- " binding" " bound-fn"
762
- " case" " catch" " comment" " cond" " condp" " cond->" " cond->>"
763
- " delay" " do" " doseq" " dotimes" " doto"
764
- " extend" " extend-protocol" " extend-type"
765
- " fdef" " finally" " fn" " for" " future"
766
- " go" " go-loop"
767
- " if" " if-let" " if-not" " if-some"
768
- " let" " letfn" " locking" " loop"
769
- " match" " ns" " proxy" " reify" " struct-map"
770
- " testing" " thread" " try"
771
- " use-fixtures"
772
- " when" " when-first" " when-let" " when-not" " when-some" " while" )
773
- line-end))))
751
+ (rx (and line-start
752
+ (or " alt!" " alt!!"
753
+ " comment"
754
+ " cond"
755
+ " delay"
756
+ " do"
757
+ " finally"
758
+ " future"
759
+ " go"
760
+ " thread"
761
+ " try"
762
+ " with-out-str" )
763
+ line-end)))
774
764
" A regex to match symbols that are functions/macros with a body argument.
775
- Taken from cljfmt:
765
+ Taken from cljfmt (all symbols with [[:block 0]] rule):
766
+ https://github.com/weavejester/cljfmt/blob/fb26b22f569724b05c93eb2502592dfc2de898c3/cljfmt/resources/cljfmt/indents/clojure.clj" )
767
+
768
+ (defun clojure-ts--match-block-0-body (node parent bol )
769
+ " Match NODE if it is an argument to a PARENT expression.
770
+
771
+ Check if the first expression in the body is not at the same line as
772
+ NODE. If there is no body, check that BOL is not at the same line."
773
+ (and (clojure-ts--list-node-p parent)
774
+ (let* ((first-child (clojure-ts--node-child-skip-metadata parent 0 ))
775
+ (body-pos (if-let* ((body (treesit-node-next-sibling first-child)))
776
+ (treesit-node-start body)
777
+ bol)))
778
+ (and (not (clojure-ts--match-with-metadata node))
779
+ (clojure-ts--symbol-matches-p
780
+ clojure-ts--symbols-block-0-regexp
781
+ first-child)
782
+ (< (line-number-at-pos (treesit-node-start first-child))
783
+ (line-number-at-pos body-pos))))))
784
+
785
+ (defvar clojure-ts--symbols-block-1-regexp
786
+ (eval-and-compile
787
+ (rx (and line-start
788
+ (or " defprotocol"
789
+ " binding"
790
+ " case" " cond->" " cond->>"
791
+ " doseq" " dotimes" " doto"
792
+ " extend" " extend-protocol" " extend-type"
793
+ " for"
794
+ " go-loop"
795
+ " if" " if-let" " if-not" " if-some"
796
+ " let" " letfn" " locking" " loop"
797
+ " match" " ns" " struct-map"
798
+ " testing"
799
+ " when" " when-first" " when-let" " when-not" " when-some" " while"
800
+ " with-local-vars" " with-open" " with-precision" " with-redefs" )
801
+ line-end)))
802
+ " A regex to match symbols that are functions/macros with a body argument.
803
+ Taken from cljfmt (all symbols with [[:block 1]] rule):
776
804
https://github.com/weavejester/cljfmt/blob/fb26b22f569724b05c93eb2502592dfc2de898c3/cljfmt/resources/cljfmt/indents/clojure.clj" )
777
805
778
806
(defun clojure-ts--match-function-call-arg (node parent _bol )
@@ -787,23 +815,93 @@ https://github.com/weavejester/cljfmt/blob/fb26b22f569724b05c93eb2502592dfc2de89
787
815
(clojure-ts--keyword-node-p first-child)
788
816
(clojure-ts--var-node-p first-child)))))
789
817
790
- (defun clojure-ts--match-expression-in-body (node parent _bol )
818
+ (defun clojure-ts--node-pos-match-block (node parent bol block )
819
+ " Return TRUE if NODE index in the PARENT matches requested BLOCK.
820
+
821
+ NODE might be nil (when we insert an empty line for example), in this
822
+ case we look for next available child node in the PARENT after BOL
823
+ position.
824
+
825
+ The first node in the expression is usually an opening paren, the last
826
+ node is usually a closing paren (unless some automatic parens mode is
827
+ not enabled). If requested BLOCK is 1, the NODE index should be at
828
+ least 3 (first node is opening paren, second node is matched symbol,
829
+ third node is first argument, and the rest is body which should be
830
+ indented.)"
831
+ (if node
832
+ (> (treesit-node-index node) (1+ block))
833
+ (when-let* ((node-after-bol (treesit-node-first-child-for-pos parent bol)))
834
+ (> (treesit-node-index node-after-bol) (1+ block)))))
835
+
836
+ (defun clojure-ts--match-block-1-body (node parent bol )
791
837
" Match NODE if it is an expression used in a body argument.
792
- PARENT is expected to be a list literal.
793
- See `treesit-simple-indent-rules' ."
838
+
839
+ The NODE has to be at least second argument of the expression. This
840
+ rule matches [[:block 1]] rule of cljfmt. If NODE is nil check the next
841
+ found node after BOL. PARENT is expected to be a list literal. See
842
+ `treesit-simple-indent-rules' ."
794
843
(and
795
844
(clojure-ts--list-node-p parent)
796
845
(let ((first-child (clojure-ts--node-child-skip-metadata parent 0 )))
797
- (and
798
- (not
799
- (clojure-ts--symbol-matches-p
800
- ; ; Symbols starting with this are false positives
801
- (rx line-start (or " default" " deflate" " defer" ))
802
- first-child))
803
- (not (clojure-ts--match-with-metadata node))
804
- (clojure-ts--symbol-matches-p
805
- clojure-ts--symbols-with-body-expressions-regexp
806
- first-child)))))
846
+ (and (not (clojure-ts--match-with-metadata node))
847
+ (clojure-ts--symbol-matches-p
848
+ clojure-ts--symbols-block-1-regexp
849
+ first-child)
850
+ (clojure-ts--node-pos-match-block node parent bol 1 )))))
851
+
852
+ (defvar clojure-ts--symbols-block-2-regexp
853
+ (eval-and-compile
854
+ (rx (and line-start
855
+ (or " defrecord" " deftype" " are" " as->" " catch" " condp" )
856
+ line-end)))
857
+ " A regex to match symbols that are functions/macros with a body argument.
858
+ Taken from cljfmt (all symbols with [[:block 2]] rule):
859
+ https://github.com/weavejester/cljfmt/blob/fb26b22f569724b05c93eb2502592dfc2de898c3/cljfmt/resources/cljfmt/indents/clojure.clj" )
860
+
861
+ (defun clojure-ts--match-block-2-body (node parent bol )
862
+ " Match NODE if it is an argument to a PARENT expression.
863
+
864
+ The NODE has to be at least third argument of the expression. This rule
865
+ matches [[:block 2]] rule of cljfmt. If NODE is nil check the next
866
+ found node after BOL."
867
+ (and (clojure-ts--list-node-p parent)
868
+ (let ((first-child (clojure-ts--node-child-skip-metadata parent 0 )))
869
+ (and (not (clojure-ts--match-with-metadata node))
870
+ (clojure-ts--symbol-matches-p
871
+ clojure-ts--symbols-block-2-regexp
872
+ first-child)
873
+ (clojure-ts--node-pos-match-block node parent bol 2 )))))
874
+
875
+ (defvar clojure-ts--symbols-inner-0-regexp
876
+ (eval-and-compile
877
+ (rx (and line-start
878
+ (or " bound-fn"
879
+ " def"
880
+ " defmacro"
881
+ " defmethod"
882
+ " defmulti"
883
+ " defn"
884
+ " defn-"
885
+ " defonce"
886
+ " deftest"
887
+ " fdef"
888
+ " fn"
889
+ " reify"
890
+ " use-fixtures" )
891
+ line-end)))
892
+ " A regex to match symbols that match [[:inner 0]] cljfmt rule." )
893
+
894
+ (defun clojure-ts--match-inner-0-body (node parent _bol )
895
+ " Match NODE if it is an argument to a PARENT expression.
896
+
897
+ The NODE has to be a child of an epression that matches rule [[:inner
898
+ 0]] of cljfmt."
899
+ (and (clojure-ts--list-node-p parent)
900
+ (let ((first-child (clojure-ts--node-child-skip-metadata parent 0 )))
901
+ (and (not (clojure-ts--match-with-metadata node))
902
+ (clojure-ts--symbol-matches-p
903
+ clojure-ts--symbols-inner-0-regexp
904
+ first-child)))))
807
905
808
906
(defun clojure-ts--match-method-body (_node parent _bol )
809
907
" Matches a `NODE' in the body of a `PARENT' method implementation.
@@ -885,7 +983,10 @@ forms like deftype, defrecord, reify, proxy, etc."
885
983
(clojure-ts--match-docstring parent 0 )
886
984
; ; https://guide.clojure.style/#body-indentation
887
985
(clojure-ts--match-method-body parent 2 )
888
- (clojure-ts--match-expression-in-body parent 2 )
986
+ (clojure-ts--match-block-0-body parent 2 )
987
+ (clojure-ts--match-block-1-body parent 2 )
988
+ (clojure-ts--match-block-2-body parent 2 )
989
+ (clojure-ts--match-inner-0-body parent 2 )
889
990
; ; https://guide.clojure.style/#threading-macros-alignment
890
991
(clojure-ts--match-threading-macro-arg prev-sibling 0 )
891
992
; ; https://guide.clojure.style/#vertically-align-fn-args
0 commit comments