leekscript_tooling/formatter/options.rs
1//! Formatter configuration options.
2//!
3//! Supports round-trip (preserve layout) and canonical formatting (normalize indentation, braces, semicolons).
4
5use sipha::red::SyntaxNode;
6
7/// Indentation style for canonical formatting.
8#[derive(Clone, Copy, Debug, PartialEq, Eq, Default)]
9pub enum IndentStyle {
10 /// Use tab characters.
11 #[default]
12 Tabs,
13 /// Use the given number of spaces per indent level.
14 Spaces(u32),
15}
16
17/// Brace placement for blocks.
18#[derive(Clone, Copy, Debug, PartialEq, Eq, Default)]
19pub enum BraceStyle {
20 /// Opening brace on same line as keyword/expression: `if (x) {`.
21 #[default]
22 SameLine,
23 /// Opening brace on next line.
24 NextLine,
25}
26
27/// Semicolon style for statement ends.
28#[derive(Clone, Copy, Debug, PartialEq, Eq, Default)]
29pub enum SemicolonStyle {
30 /// Ensure semicolon after every statement (add if missing).
31 #[default]
32 Always,
33 /// Omit optional semicolons (emit only when required by grammar).
34 Omit,
35}
36
37/// Options for printing the syntax tree.
38#[derive(Clone, Debug)]
39pub struct FormatterOptions {
40 /// Include trivia (whitespace, comments) in the output. If false, only semantic tokens are emitted.
41 pub preserve_comments: bool,
42 /// Wrap expressions in parentheses to make precedence explicit (e.g. `a + b + c * d` → `((a + b) + (c * d))`).
43 pub parenthesize_expressions: bool,
44 /// Add block comments `/* type */` with the inferred type after expressions and variables.
45 pub annotate_types: bool,
46 /// When `annotate_types` is true, use these signature roots (e.g. stdlib) so built-in function/global types are inferred.
47 pub signature_roots: Option<Vec<SyntaxNode>>,
48 /// When true, normalize layout: indentation, brace style, semicolons. Ignores source whitespace/comment layout.
49 pub canonical_format: bool,
50 /// Indentation for canonical format (tabs or N spaces).
51 pub indent_style: IndentStyle,
52 /// Brace placement for canonical format.
53 pub brace_style: BraceStyle,
54 /// Semicolon placement for canonical format.
55 pub semicolon_style: SemicolonStyle,
56}
57
58impl Default for FormatterOptions {
59 fn default() -> Self {
60 Self {
61 preserve_comments: true,
62 parenthesize_expressions: false,
63 annotate_types: false,
64 signature_roots: None,
65 canonical_format: false,
66 indent_style: IndentStyle::default(),
67 brace_style: BraceStyle::default(),
68 semicolon_style: SemicolonStyle::default(),
69 }
70 }
71}