Skip to content

Commit d3e6780

Browse files
committed
There must always be at least one visible line (microsoft#44805)
1 parent 47497b7 commit d3e6780

2 files changed

Lines changed: 44 additions & 0 deletions

File tree

src/vs/editor/common/viewModel/splitLinesCollection.ts

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -288,6 +288,7 @@ export class SplitLinesCollection implements IViewModelLinesCollection {
288288
let hiddenAreaIdx = -1;
289289
let nextLineNumberToUpdateHiddenArea = (hiddenAreaIdx + 1 < hiddenAreas.length) ? hiddenAreaEnd + 1 : this.lines.length + 2;
290290

291+
let hasVisibleLine = false;
291292
for (let i = 0; i < this.lines.length; i++) {
292293
let lineNumber = i + 1;
293294

@@ -306,6 +307,7 @@ export class SplitLinesCollection implements IViewModelLinesCollection {
306307
lineChanged = true;
307308
}
308309
} else {
310+
hasVisibleLine = true;
309311
// Line should be visible
310312
if (!this.lines[i].isVisible()) {
311313
this.lines[i] = this.lines[i].setVisible(true);
@@ -318,6 +320,11 @@ export class SplitLinesCollection implements IViewModelLinesCollection {
318320
}
319321
}
320322

323+
if (!hasVisibleLine) {
324+
// Cannot have everything be hidden => reveal everything!
325+
this.setHiddenAreas([]);
326+
}
327+
321328
return true;
322329
}
323330

@@ -465,6 +472,10 @@ export class SplitLinesCollection implements IViewModelLinesCollection {
465472

466473
public acceptVersionId(versionId: number): void {
467474
this._validModelVersionId = versionId;
475+
if (this.lines.length === 1 && !this.lines[0].isVisible()) {
476+
// At least one line must be visible => reset hidden areas
477+
this.setHiddenAreas([]);
478+
}
468479
}
469480

470481
public getViewLineCount(): number {

src/vs/editor/test/common/viewModel/viewModelImpl.test.ts

Lines changed: 33 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -74,6 +74,39 @@ suite('ViewModel', () => {
7474
});
7575
});
7676

77+
test('issue #44805: No visible lines via API call', () => {
78+
const text = [
79+
'line1',
80+
'line2',
81+
'line3'
82+
];
83+
testViewModel(text, {}, (viewModel, model) => {
84+
assert.equal(viewModel.getLineCount(), 3);
85+
viewModel.setHiddenAreas([new Range(1, 1, 3, 1)]);
86+
assert.ok(viewModel.getVisibleRanges() !== null);
87+
});
88+
});
89+
90+
test('issue #44805: No visible lines via undoing', () => {
91+
const text = [
92+
''
93+
];
94+
testViewModel(text, {}, (viewModel, model) => {
95+
assert.equal(viewModel.getLineCount(), 1);
96+
97+
model.pushEditOperations([], [{
98+
range: new Range(1, 1, 1, 1),
99+
text: 'line1\nline2\nline3'
100+
}], () => ([]));
101+
102+
viewModel.setHiddenAreas([new Range(1, 1, 1, 1)]);
103+
assert.equal(viewModel.getLineCount(), 2);
104+
105+
model.undo();
106+
assert.ok(viewModel.getVisibleRanges() !== null);
107+
});
108+
});
109+
77110
function assertGetPlainTextToCopy(text: string[], ranges: Range[], emptySelectionClipboard: boolean, expected: string | string[]): void {
78111
testViewModel(text, {}, (viewModel, model) => {
79112
let actual = viewModel.getPlainTextToCopy(ranges, emptySelectionClipboard);

0 commit comments

Comments
 (0)