;;; Indent
+(defun c-ts-mode--preproc-offset (_n _p &rest _)
+ "This anchor is used for preprocessor directives.
+
+Because node is nil at the moment of indentation, we use
+`treesit-node-on' to capture the anonymous node covering the
+newline. If the grand-parent of that node is the
+translation_unit itself, we don't indent. Otherwise, just indent
+one step according to the great-grand-parent indent level. The
+reason there is a difference between grand-parent and
+great-grand-parent here is that the node containing the newline
+is actually the parent of point at the moment of indentation."
+ (when-let ((node (treesit-node-on (point) (point))))
+ (if (string-equal "translation_unit"
+ (treesit-node-type
+ (treesit-node-parent
+ (treesit-node-parent node))))
+ 0
+ c-ts-mode-indent-offset)))
+
(defun c-ts-mode--indent-styles (mode)
"Indent rules supported by `c-ts-mode'.
MODE is either `c' or `cpp'."
((match nil "do_statement" "body") parent-bol c-ts-mode-indent-offset)
((match nil "for_statement" "body") parent-bol c-ts-mode-indent-offset)
- ((match "preproc_ifdef" "compound_statement") point-min 0)
- ((match "#endif" "preproc_ifdef") point-min 0)
- ((match "preproc_if" "compound_statement") point-min 0)
- ((match "#endif" "preproc_if") point-min 0)
- ((match "preproc_function_def" "compound_statement") point-min 0)
+ ((node-is "preproc") point-min 0)
+ ((node-is "#endif") point-min 0)
((match "preproc_call" "compound_statement") point-min 0)
+ ((n-p-gp nil "preproc" "translation_unit") point-min 0)
+ ((n-p-gp nil "\n" "preproc") great-grand-parent c-ts-mode--preproc-offset)
+ ((parent-is "preproc") grand-parent c-ts-mode-indent-offset)
+
((parent-is "function_definition") parent-bol 0)
((parent-is "conditional_expression") first-sibling 0)
((parent-is "assignment_expression") parent-bol c-ts-mode-indent-offset)
(skip-unless (treesit-ready-p 'c))
(ert-test-erts-file (ert-resource-file "indent.erts")))
+(ert-deftest c-ts-mode-test-indentation-preproc ()
+ (skip-unless (treesit-ready-p 'c))
+ (ert-test-erts-file (ert-resource-file "indent-preproc.erts")))
+
(ert-deftest c-ts-mode-test-indentation-bsd ()
(skip-unless (treesit-ready-p 'c))
(ert-test-erts-file (ert-resource-file "indent-bsd.erts")))