Skip to content

Commit

Permalink
Merge pull request #2661 from BetterThanTomorrow/2660-toplevel-ignore…
Browse files Browse the repository at this point in the history
…-style

* Fixes #2660
  • Loading branch information
PEZ authored Oct 29, 2024
2 parents a8910fe + eef974a commit b2b4819
Show file tree
Hide file tree
Showing 6 changed files with 58 additions and 27 deletions.
1 change: 1 addition & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ Changes to Calva.
- [Add extension when contexts for Calva states such as project root, session type, ns](https://github.com/BetterThanTomorrow/calva/issues/2652)
- Fix: [Calva internals: The `backwardSexp` function can't handle skipping ignored forms, even though it says it can](https://github.com/BetterThanTomorrow/calva/issues/2657)
- Fix: [Keep support for evaluating top level form in ignored forms when at top level](https://github.com/BetterThanTomorrow/calva/issues/2655)
- [Enable separate styling for top level ignored forms](https://github.com/BetterThanTomorrow/calva/issues/2660)

## [2.0.480] - 2024-10-21

Expand Down
3 changes: 2 additions & 1 deletion docs/site/syntax-highlighting.md
Original file line number Diff line number Diff line change
Expand Up @@ -43,7 +43,8 @@ You are in charge of how brackets and comments are highlighted via the `calva.hi
| `cycleBracketColors` | Whether same colors should be <br> reused for deeply nested brackets | `true` |
| `misplacedBracketStyle` | Style of misplaced bracket | `{ "border": "2px solid #c33" }` |
| `matchedBracketStyle` | Style of bracket pair highlight | `{"backgroundColor": "#E0E0E0"}` |
| `ignoredFormStyle` | Style of `#_...` form | `{"textDecoration": "none; opacity: 0.5"}` |
| `ignoredFormStyle` | Style of `#_...` forms | `{"textDecoration": "none; opacity: 0.5"}` |
| `ignoredTopLevelFormStyle` | Style of `#_...` forms at the top level. (If not set, uses `ignoredFormStyle`) | `{ "textDecoration": "none; text-shadow: 2px 2px 5px rgba(255, 215, 0, 0.75)" }` |
| `commentFormStyle` | Style of `(comment ...)` form | `{"fontStyle": "italic"}` |

!!! Note "Calva disables the VS Code built-in indent guides"
Expand Down
6 changes: 6 additions & 0 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -1142,6 +1142,12 @@
"default": null,
"description": "Style of `#_` ignored forms",
"scope": "resource"
},
"calva.highlight.ignoredTopLevelFormStyle": {
"type": "object",
"default": null,
"markdownDescription": "Style of top level `#_` ignored forms. If not specified, it will be the same as what's set for `calva.highlight.ignoredFormStyle`",
"scope": "resource"
}
}
}
Expand Down
62 changes: 41 additions & 21 deletions src/highlight/src/extension.ts
Original file line number Diff line number Diff line change
Expand Up @@ -39,6 +39,8 @@ let lastHighlightedEditor,
commentFormType: vscode.TextEditorDecorationType,
ignoredFormStyle,
ignoredFormType: vscode.TextEditorDecorationType,
ignoredTopLevelFormStyle,
ignoredTopLevelFormType: vscode.TextEditorDecorationType,
enableBracketColors,
useRainbowIndentGuides,
highlightActiveIndent,
Expand Down Expand Up @@ -152,6 +154,13 @@ function reset_styles() {
}
ignoredFormType = decorationType(ignoredFormStyle || { textDecoration: 'none; opacity: 0.5' });

if (ignoredTopLevelFormType) {
activeEditor.setDecorations(ignoredTopLevelFormType, []);
}
ignoredTopLevelFormType = decorationType(
ignoredTopLevelFormStyle || ignoredFormStyle || { textDecoration: 'none; opacity: 0.5' }
);

dirty = false;
}

Expand Down Expand Up @@ -206,6 +215,11 @@ function reloadConfig() {
dirty = true;
}

if (!isEqual(ignoredTopLevelFormStyle, configuration.get('ignoredTopLevelFormStyle'))) {
ignoredTopLevelFormStyle = configuration.get('ignoredTopLevelFormStyle');
dirty = true;
}

if (dirty) {
scheduleRainbowBrackets();
}
Expand All @@ -231,18 +245,19 @@ function updateRainbowBrackets() {
reset_styles();
}

const doc = activeEditor.document,
mirrorDoc = docMirror.getDocument(doc),
rainbow = rainbowTypes.map(() => []),
rainbowGuides = rainbowTypes.map(() => []),
misplaced = [],
comment_forms = [],
ignores = [],
len = rainbowTypes.length,
colorsEnabled = enableBracketColors && len > 0,
guideColorsEnabled = useRainbowIndentGuides && len > 0,
activeGuideEnabled = highlightActiveIndent && len > 0,
colorIndex = cycleBracketColors ? (i) => i % len : (i) => Math.min(i, len - 1);
const doc = activeEditor.document;
const mirrorDoc = docMirror.getDocument(doc);
const rainbow = rainbowTypes.map(() => []);
const rainbowGuides = rainbowTypes.map(() => []);
const misplaced = [];
const comment_forms = [];
const ignores = [];
const topLevelIgnores = [];
const len = rainbowTypes.length;
const colorsEnabled = enableBracketColors && len > 0;
const guideColorsEnabled = useRainbowIndentGuides && len > 0;
const activeGuideEnabled = highlightActiveIndent && len > 0;
const colorIndex = cycleBracketColors ? (i) => i % len : (i) => Math.min(i, len - 1);

let in_comment_form = false;
let stack_depth = 0;
Expand All @@ -252,14 +267,14 @@ function updateRainbowBrackets() {
placedGuidesColor = new Map();
activeEditor.visibleRanges.forEach((range) => {
// Find the visible forms
const startOffset = doc.offsetAt(range.start),
endOffset = doc.offsetAt(range.end),
startCursor: LispTokenCursor = mirrorDoc.getTokenCursor(0),
startRange = startCursor.rangeForDefun(startOffset, false),
endCursor: LispTokenCursor = mirrorDoc.getTokenCursor(endOffset),
endRange = endCursor.rangeForDefun(endOffset, false),
rangeStart = startRange ? startRange[0] : startOffset,
rangeEnd = endRange ? endRange[1] : endOffset;
const startOffset = doc.offsetAt(range.start);
const endOffset = doc.offsetAt(range.end);
const startCursor: LispTokenCursor = mirrorDoc.getTokenCursor(0);
const startRange = startCursor.rangeForDefun(startOffset, false);
const endCursor: LispTokenCursor = mirrorDoc.getTokenCursor(endOffset);
const endRange = endCursor.rangeForDefun(endOffset, false);
const rangeStart = startRange ? startRange[0] : startOffset;
const rangeEnd = endRange ? endRange[1] : endOffset;
// Look for top level ignores, and adjust starting point if found
const topLevelSentinelCursor = mirrorDoc.getTokenCursor(rangeStart);
let startPaintingFrom = rangeStart;
Expand Down Expand Up @@ -299,7 +314,11 @@ function updateRainbowBrackets() {
ignoreCursor.forwardSexp(true, true, true);
}
const ignore_end = activeEditor.document.positionAt(ignoreCursor.offsetStart);
ignores.push(new Range(ignore_start, ignore_end));
if (cursor.atTopLevel()) {
topLevelIgnores.push(new Range(ignore_start, ignore_end));
} else {
ignores.push(new Range(ignore_start, ignore_end));
}
}
}
const token = cursor.getToken(),
Expand Down Expand Up @@ -399,6 +418,7 @@ function updateRainbowBrackets() {
activeEditor.setDecorations(misplacedType, misplaced);
activeEditor.setDecorations(commentFormType, comment_forms);
activeEditor.setDecorations(ignoredFormType, ignores);
activeEditor.setDecorations(ignoredTopLevelFormType, topLevelIgnores);
matchPairs();
if (activeGuideEnabled) {
decorateActiveGuides();
Expand Down
5 changes: 4 additions & 1 deletion test-data/.vscode/settings.json
Original file line number Diff line number Diff line change
Expand Up @@ -139,5 +139,8 @@
"afterCL]ReplJackInCode": ["(println :hello)", "(println :world!)"],
"cljsType": "none"
}
]
],
"calva.highlight.ignoredTopLevelFormStyle": {
"textDecoration": "none; text-shadow: 2px 2px 5px rgba(255, 215, 0, 0.75)"
}
}
8 changes: 4 additions & 4 deletions test-data/test-files/highlight_test.clj
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@
;; \
"()"
;; \
;;
;;
(((#((())))))
([ #{ }()[]])
Expand Down Expand Up @@ -54,10 +54,10 @@
(println "I ❤️Clojure")
([{} () []]))
(comment
(+ (* 2 2)
2)
2)
(Math/abs -1)
(defn hello [s]
(str "Hello " s))
Expand Down Expand Up @@ -143,7 +143,7 @@ bar
[:c {:d :e}]]
[:b
[:c {:d :e}]]]
(comment
(comment
(foo #_"bar" baz))
#_{:foo "foo"
:bar (comment [["bar"]])}
Expand Down

0 comments on commit b2b4819

Please sign in to comment.