Skip to content

Commit b52f653

Browse files
release: v2.2.2
1 parent b98d29f commit b52f653

5 files changed

Lines changed: 92 additions & 24 deletions

File tree

CHANGELOG.md

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,15 @@ All notable changes to Tree Mapper are documented here.
44

55
---
66

7+
## v2.2.2 — 2026-06-21
8+
9+
### Added
10+
11+
- **"Deselect filtered" toolbar button** — Appears next to **Select filtered** whenever a search filter is active, letting you uncheck only the files currently visible in the filtered tree without affecting the rest of your selection.
12+
- **Clear (×) button in the search box** — A small clear button now appears inside the filter input as soon as you start typing, letting you reset the search and restore the full tree view in one click.
13+
14+
---
15+
716
## v2.2.1 — 2026-05-06
817

918
### Fixed

README.md

Lines changed: 20 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -17,25 +17,6 @@ Snapshots are saved to `.tree/yyyy-mm-dd-hh-mm-ss.md` inside the `.tree` folder.
1717

1818
---
1919

20-
## Installation
21-
22-
**From the Marketplace** *(recommended)*
23-
24-
Open Extensions (`Ctrl+Shift+X`), search **Tree Mapper**, and click Install — or visit the [VS Code Marketplace](https://marketplace.visualstudio.com/items?itemName=MrDeveloperJIS.tree-mapper) directly.
25-
26-
```
27-
ext install MrDeveloperJIS.tree-mapper
28-
```
29-
30-
**From a VSIX file**
31-
32-
Download from the [Releases page](https://github.com/MrDeveloperJIS/tree-mapper/releases), then:
33-
34-
- Extensions panel → `` menu → **Install from VSIX…**
35-
- Or via terminal: `code --install-extension path/to/tree-mapper-x.x.x.vsix`
36-
37-
---
38-
3920
## Usage
4021

4122
**Snapshot a folder**
@@ -64,11 +45,11 @@ Before generating, Tree Mapper opens a full-screen webview panel with every file
6445
| **Reset defaults** | Restore the default checked/unchecked state |
6546
| **Restore last** | Re-apply the selection from your previous run *(appears when a saved selection exists)* |
6647
| **Select filtered** | Check only the files currently visible in the search filter |
48+
| **Deselect filtered** | Uncheck only the files currently visible in the search filter |
6749
| **Filter** | Type to narrow the tree by filename or path |
6850

6951
**Other picker features:**
7052

71-
- **File-type colour icons** — each file shows a colour-coded icon based on its extension (JS, TS, CSS, JSON, Markdown, Python, Rust, Go, and more)
7253
- **Indentation connector lines** — vertical guide lines between nesting levels for clear hierarchy
7354
- **Auto-collapsed excluded dirs** — folders whose entire contents are excluded by default patterns start collapsed, reducing noise in large repos
7455
- **Live file count** — the footer updates in real time as you check and uncheck files
@@ -133,6 +114,25 @@ When a `.git` folder is detected, Tree Mapper automatically adds `.tree/` to you
133114

134115
---
135116

117+
## Installation
118+
119+
**From the Marketplace** *(recommended)*
120+
121+
Open Extensions (`Ctrl+Shift+X`), search **Tree Mapper**, and click Install — or visit the [VS Code Marketplace](https://marketplace.visualstudio.com/items?itemName=MrDeveloperJIS.tree-mapper) directly.
122+
123+
```
124+
ext install MrDeveloperJIS.tree-mapper
125+
```
126+
127+
**From a VSIX file**
128+
129+
Download from the [Releases page](https://github.com/MrDeveloperJIS/tree-mapper/releases), then:
130+
131+
- Extensions panel → `` menu → **Install from VSIX…**
132+
- Or via terminal: `code --install-extension path/to/tree-mapper-x.x.x.vsix`
133+
134+
---
135+
136136
## Requirements
137137

138138
VS Code **1.85.0** or higher.

package-lock.json

Lines changed: 2 additions & 2 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

package.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@
22
"name": "tree-mapper",
33
"displayName": "Tree Mapper",
44
"description": "Generate a complete Markdown snapshot of any folder in your VS Code workspace — including a full directory tree and every file's source code.",
5-
"version": "2.2.1",
5+
"version": "2.2.2",
66
"publisher": "MrDeveloperJIS",
77
"engines": {
88
"vscode": "^1.85.0"

src/extension.js

Lines changed: 60 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -505,7 +505,7 @@ function buildPickerHtml(treeNodes, projectName, lastSelection) {
505505
color: var(--fg);
506506
font-family: var(--mono);
507507
font-size: 11.5px;
508-
padding: 5px 12px 5px 30px;
508+
padding: 5px 26px 5px 30px;
509509
outline: none;
510510
transition: border-color var(--t), box-shadow var(--t);
511511
letter-spacing: -0.01em;
@@ -515,6 +515,33 @@ function buildPickerHtml(treeNodes, projectName, lastSelection) {
515515
border-color: rgba(124,92,252,0.5);
516516
box-shadow: 0 0 0 3px rgba(124,92,252,0.12);
517517
}
518+
.search-clear {
519+
position: absolute;
520+
right: 6px;
521+
top: 50%;
522+
transform: translateY(-50%);
523+
width: 16px;
524+
height: 16px;
525+
display: none;
526+
align-items: center;
527+
justify-content: center;
528+
border: none;
529+
background: transparent;
530+
padding: 0;
531+
border-radius: 50%;
532+
color: var(--fg-muted);
533+
cursor: pointer;
534+
transition: background var(--t), color var(--t);
535+
}
536+
.search-clear svg {
537+
width: 9px;
538+
height: 9px;
539+
stroke: currentColor;
540+
}
541+
.search-clear:hover {
542+
background: rgba(255,255,255,0.08);
543+
color: var(--fg);
544+
}
518545
519546
.stats-pill {
520547
margin-left: auto;
@@ -843,8 +870,14 @@ function buildPickerHtml(treeNodes, projectName, lastSelection) {
843870
<path d="M11 11l3 3" stroke-linecap="round"/>
844871
</svg>
845872
<input class="search-input" id="searchInput" type="text" placeholder="Filter files…" oninput="filterTree(this.value)">
873+
<button class="search-clear" id="searchClearBtn" style="display:none" onclick="clearSearch()" aria-label="Clear search" type="button">
874+
<svg viewBox="0 0 16 16" fill="none" xmlns="http://www.w3.org/2000/svg" stroke-width="1.8">
875+
<path d="M4 4l8 8M12 4l-8 8" stroke-linecap="round"/>
876+
</svg>
877+
</button>
846878
</div>
847879
<button class="btn-ghost select-filtered" id="selectFilteredBtn" style="display:none" onclick="selectFiltered()">Select filtered</button>
880+
<button class="btn-ghost deselect-filtered" id="deselectFilteredBtn" style="display:none" onclick="deselectFiltered()">Deselect filtered</button>
848881
<div class="stats-pill" id="statsLabel"><span class="count selected">—</span> / <span class="count">—</span></div>
849882
</div>
850883
@@ -1075,6 +1108,10 @@ function restoreLastSelection() {
10751108
function filterTree(q) {
10761109
q = q.toLowerCase().trim();
10771110
const filterBtn = document.getElementById('selectFilteredBtn');
1111+
const deselectBtn = document.getElementById('deselectFilteredBtn');
1112+
const clearBtn = document.getElementById('searchClearBtn');
1113+
1114+
clearBtn.style.display = q ? 'flex' : 'none';
10781115
10791116
if (!q) {
10801117
document.querySelectorAll('.tree-row').forEach(r => r.classList.remove('hidden'));
@@ -1093,6 +1130,7 @@ function filterTree(q) {
10931130
}
10941131
});
10951132
filterBtn.style.display = 'none';
1133+
deselectBtn.style.display = 'none';
10961134
return;
10971135
}
10981136
@@ -1102,6 +1140,14 @@ function filterTree(q) {
11021140
row.classList.toggle('hidden', !rel.toLowerCase().includes(q));
11031141
});
11041142
filterBtn.style.display = '';
1143+
deselectBtn.style.display = '';
1144+
}
1145+
1146+
function clearSearch() {
1147+
const input = document.getElementById('searchInput');
1148+
input.value = '';
1149+
filterTree('');
1150+
input.focus();
11051151
}
11061152
11071153
function selectFiltered() {
@@ -1115,6 +1161,19 @@ function selectFiltered() {
11151161
updateStats();
11161162
}
11171163
1164+
function deselectFiltered() {
1165+
document.querySelectorAll('.tree-row:not(.hidden)').forEach(row => {
1166+
if (row.dataset.isDir === '1') return;
1167+
const rel = row.dataset.rel;
1168+
const cb = getCb(rel);
1169+
if (cb) { cb.checked = false; cb.indeterminate = false; }
1170+
});
1171+
allFileNodes.forEach(n => updateAncestors(n.rel));
1172+
updateStats();
1173+
}
1174+
1175+
1176+
11181177
// ── Stats ───────────────────────────────────────────────────────────────────
11191178
function updateStats() {
11201179
let total = 0, selected = 0;

0 commit comments

Comments
 (0)