Temporarily collapse every comment out of the editor, leaving a compact view of
just the code. Built for reading unfamiliar code and for debugging, where
comment blocks push the lines you care about off the screen.
The feature is purely visual. No file is ever edited, no buffer is ever
marked dirty, and Git sees nothing.
Usage
Click Comments: Shown in the status bar to hide comments in the active
editor. Click it again to bring them back.
For a pristine copy with no fold markers at all, run Hide Comments: Open Clean
View from the command palette.
| Command |
What it does |
Hide Comments: Toggle Hidden Comments |
Collapses / restores comments in the active editor |
Hide Comments: Open Clean View |
Replaces the tab with a read-only, comment-free rendering |
Hide Comments: Close Clean View |
Returns to the real file at the matching line |
VS Code offers no API to give a line zero height. Decorations can hide comment
text, but the line keeps its vertical space - which would leave exactly the
blank gaps this extension exists to avoid.
So full-line comments are hidden with folding, anchored to the line above.
A normal fold leaves its first line on screen; by starting the fold range at the
last line of preceding code (or the blank line above it), the whole comment
block collapses into a line that was already there and disappears completely.
SOURCE (unchanged on disk) HIDDEN
──────────────────────────── ────────────────────────────
1 import { sum } from './m' 1⌄ import { sum } from './m' ⋯
2 2
3 // Adds two numbers 5 function calc(a) {
4 // and returns the result 6 return sum(a, 2)
5 function calc(a) { 7 }
6 return sum(a, 2) // note
7 }
These are VS Code manual folding ranges, not a FoldingRangeProvider. A
provider's ranges get merged with the language's own, and any range that
overlaps another without nesting is silently discarded - which is the exact
shape of a fold anchored to the line above. Manual ranges are merged with
priority instead, so they survive.
Comments that share a line with code cannot be handled that way, because the
line holds working code. Those are collapsed to zero width with a display: none
decoration, so the line ends flush against the code.
Comment tokens come from each language's own language-configuration.json,
which every language extension contributes. Any language you have installed is
therefore supported, including ones this extension has never heard of.
Those files describe comment delimiters but not string literals, so the scanner
adds the syntax needed to avoid false positives:
- template literals and
${...} interpolation, and regex literals with the
standard preceding-token heuristic, so /https?:\/\// is not a comment;
- Python triple-quoted strings, Go raw backtick strings, Rust raw strings and
nested block comments, C# verbatim strings with doubled quotes;
- prose languages such as HTML, Markdown and LaTeX have string detection
disabled, so the apostrophe in "don't" cannot swallow the rest of the file;
- GraphQL descriptions, covered below;
<script> and <style> sections inside HTML are scanned with JavaScript and
CSS rules.
Two rules keep a scanner mistake from ever hiding real code:
- an unterminated block comment is discarded rather than run to end of file;
- an unterminated single-line string is abandoned at the newline and
scanning resumes as code.
Beyond that, only spans that occupy every line they touch are ever folded away.
GraphQL descriptions
GraphQL has no comment syntax for documentation. It uses string literals:
"""A registered user."""
type User {
"""The unique identifier."""
id: ID!
}
These are hidden along with # comments. The catch is that the identical
literal is real data in another position - an argument, a default, a list
element - and hiding that would remove working content:
mutation {
create(body: """
A multi-line argument value.
""") # stays visible
}
input F {
limit: Int = 10
labels: [String!] = ["active"] # stays visible
}
type T {
old: String @deprecated(reason: "use new") # stays visible
}
A literal counts as a description only when the preceding significant
character is not one of : ( , [ =. Anything in value position
falls through to ordinary string handling and is left alone.
"Preceding significant character" is tracked as the scan moves forward, so
comments are skipped rather than read through. A backward search would break on
a banner like # ====== sitting above a description: its trailing = would
misfile the description as a default value. A description
sharing a line with code (type User { """id""" id: ID! }) is also left
alone, since the line holds working schema.
# comments work even without a GraphQL extension installed; VS Code ships no
GraphQL support, so the extension supplies that token itself.
Some comments instruct a tool rather than a human, and hiding them makes nearby
code look inexplicably broken or mis-linted. These stay visible by default:
- Tooling directives -
eslint-disable, prettier-ignore, @ts-ignore,
@ts-expect-error, # noqa, # type:, pylint:, mypy:, //go:build,
//go:generate, nolint, NOLINT, clang-format off, shellcheck disable,
istanbul ignore, swiftlint:, ktlint-disable and others.
- Shebang lines -
#!/usr/bin/env ..., which is functionally required.
#region / #endregion markers, read from the language's own folding
marker patterns, because VS Code's folding depends on them.
Each group can be turned off, and hideComments.additionalDirectivePatterns
takes your own regular expressions.
Settings
| Setting |
Default |
Meaning |
hideComments.hideTrailingComments |
true |
Collapse comments that share a line with code |
hideComments.exemptDirectives |
true |
Keep tooling directives visible |
hideComments.exemptShebang |
true |
Keep a leading #! line visible |
hideComments.exemptRegionMarkers |
true |
Keep #region / #endregion visible |
hideComments.additionalDirectivePatterns |
[] |
Extra regexes that mark a comment as a directive |
hideComments.absorbBlankLine |
true |
Hide one blank line when a comment block is fenced by blanks on both sides |
hideComments.reapplyOnEdit |
true |
Recompute hiding after edits |
hideComments.showStatusBarItem |
true |
Show the status bar toggle |
Known limits
- A comment block starting on line 1 cannot fully disappear. A fold needs a
line above to collapse into, and there is none. Its text is collapsed, so it
renders as a single blank line. Clean View has no such limit.
- Restoring unfolds everything. VS Code provides no API to read which ranges
are currently folded, so an exact snapshot-and-restore of your own folds is
not possible. Showing comments again runs a plain unfold-all.
- A fold arrow and a faint
⋯ appear on the anchor line. That is VS Code's
own folding chrome and cannot be suppressed.
- Clean View is read-only and its line numbers do not match the real file.
Breakpoints and the debugger's current-line highlight belong to the real file,
which is why the fold-based toggle is the primary action.
- Requires
editor.folding to be enabled; the extension warns if it is off.
Scope
A toggle affects the active editor only. Other tabs keep their own state,
matching how VS Code's built-in fold commands behave.
Development
npm install
npm run compile
npm test # scanner and block-grouping suites, run headless against a vscode stub
Press F5 in VS Code to launch an Extension Development Host.