提交 9aa90a52 编写于 作者: C Christof Marti

Fix events firing multiple times (fixes #52894)

上级 748d3125
......@@ -13,7 +13,10 @@ interface QuickPickExpected {
events: string[];
activeItems: string[][];
selectionItems: string[][];
acceptedItems: string[][];
acceptedItems: {
active: string[][];
selection: string[][];
};
}
suite('window namespace tests', function () {
......@@ -31,8 +34,11 @@ suite('window namespace tests', function () {
events: ['active', 'active', 'selection', 'accept', 'hide'],
activeItems: [['eins'], ['zwei']],
selectionItems: [['zwei']],
acceptedItems: [['zwei']],
}, done);
acceptedItems: {
active: [['zwei']],
selection: [['zwei']]
},
}, (err?: any) => done(err));
quickPick.items = ['eins', 'zwei', 'drei'].map(label => ({ label }));
quickPick.show();
......@@ -53,8 +59,11 @@ suite('window namespace tests', function () {
events: ['active', 'selection', 'accept', 'hide'],
activeItems: [['zwei']],
selectionItems: [['zwei']],
acceptedItems: [['zwei']],
}, done);
acceptedItems: {
active: [['zwei']],
selection: [['zwei']]
},
}, (err?: any) => done(err));
quickPick.items = ['eins', 'zwei', 'drei'].map(label => ({ label }));
quickPick.activeItems = [quickPick.items[1]];
quickPick.show();
......@@ -64,6 +73,35 @@ suite('window namespace tests', function () {
})()
.catch(err => done(err));
});
test('createQuickPick, select first and second', function (_done) {
let done = (err?: any) => {
done = () => {};
_done(err);
};
const quickPick = createQuickPick({
events: ['active', 'selection', 'active', 'selection', 'accept', 'hide'],
activeItems: [['eins'], ['zwei']],
selectionItems: [['eins'], ['eins', 'zwei']],
acceptedItems: {
active: [['zwei']],
selection: [['eins', 'zwei']]
},
}, (err?: any) => done(err));
quickPick.canSelectMany = true;
quickPick.items = ['eins', 'zwei', 'drei'].map(label => ({ label }));
quickPick.show();
(async () => {
await commands.executeCommand('workbench.action.quickOpenSelectNext');
await commands.executeCommand('workbench.action.quickPickManyToggle');
await commands.executeCommand('workbench.action.quickOpenSelectNext');
await commands.executeCommand('workbench.action.quickPickManyToggle');
await commands.executeCommand('workbench.action.acceptSelectedQuickOpenItem');
})()
.catch(err => done(err));
});
});
});
......@@ -92,9 +130,10 @@ function createQuickPick(expected: QuickPickExpected, done: (err?: any) => void)
quickPick.onDidAccept(() => {
try {
assert.equal('accept', expected.events.shift());
const expectedItems = expected.acceptedItems.shift();
assert.deepEqual(quickPick.activeItems.map(item => item.label), expectedItems);
assert.deepEqual(quickPick.selectedItems.map(item => item.label), expectedItems);
const expectedActive = expected.acceptedItems.active.shift();
assert.deepEqual(quickPick.activeItems.map(item => item.label), expectedActive);
const expectedSelection = expected.acceptedItems.selection.shift();
assert.deepEqual(quickPick.selectedItems.map(item => item.label), expectedSelection);
quickPick.dispose();
} catch (err) {
done(err);
......
......@@ -410,9 +410,14 @@ suite('window namespace tests', () => {
test('showQuickPick, accept second', async function () {
const resolves: ((value: string) => void)[] = [];
let done: () => void;
const unexpected = new Promise((resolve, reject) => {
done = () => resolve();
resolves.push(reject);
});
const first = new Promise(resolve => resolves.push(resolve));
const pick = window.showQuickPick(['eins', 'zwei', 'drei'], {
onDidSelectItem: item => resolves.shift()!(item as string)
onDidSelectItem: item => resolves.pop()!(item as string)
});
assert.equal(await first, 'eins');
const second = new Promise(resolve => resolves.push(resolve));
......@@ -420,12 +425,19 @@ suite('window namespace tests', () => {
assert.equal(await second, 'zwei');
await commands.executeCommand('workbench.action.acceptSelectedQuickOpenItem');
assert.equal(await pick, 'zwei');
done!();
return unexpected;
});
test('showQuickPick, select first two', async function () {
const resolves: ((value: string) => void)[] = [];
let done: () => void;
const unexpected = new Promise((resolve, reject) => {
done = () => resolve();
resolves.push(reject);
});
const picks = window.showQuickPick(['eins', 'zwei', 'drei'], {
onDidSelectItem: item => resolves.shift()!(item as string),
onDidSelectItem: item => resolves.pop()!(item as string),
canPickMany: true
});
const first = new Promise(resolve => resolves.push(resolve));
......@@ -438,6 +450,8 @@ suite('window namespace tests', () => {
await commands.executeCommand('workbench.action.quickPickManyToggle');
await commands.executeCommand('workbench.action.acceptSelectedQuickOpenItem');
assert.deepStrictEqual(await picks, ['eins', 'zwei']);
done!();
return unexpected;
});
test('showQuickPick, keep selection (Microsoft/vscode-azure-account#67)', async function () {
......
......@@ -41,6 +41,7 @@ import { Action } from 'vs/base/common/actions';
import URI from 'vs/base/common/uri';
import { IdGenerator } from 'vs/base/common/idGenerator';
import { IKeybindingService } from 'vs/platform/keybinding/common/keybinding';
import { equals } from 'vs/base/common/arrays';
const $ = dom.$;
......@@ -289,9 +290,11 @@ class QuickPick<T extends IQuickPickItem> extends QuickInput implements IQuickPi
private _matchOnDetail = false;
private _activeItems: T[] = [];
private activeItemsUpdated = false;
private activeItemsToConfirm: T[] = [];
private onDidChangeActiveEmitter = new Emitter<T[]>();
private _selectedItems: T[] = [];
private selectedItemsUpdated = false;
private selectedItemsToConfirm: T[] = [];
private onDidChangeSelectionEmitter = new Emitter<T[]>();
private quickNavigate = false;
......@@ -429,8 +432,7 @@ class QuickPick<T extends IQuickPickItem> extends QuickInput implements IQuickPi
if (this.activeItemsUpdated) {
return; // Expect another event.
}
// Drop initial event.
if (!focusedItems.length && !this._activeItems.length) {
if (this.activeItemsToConfirm !== this._activeItems && equals(focusedItems, this._activeItems, (a, b) => a === b)) {
return;
}
this._activeItems = focusedItems as T[];
......@@ -440,8 +442,7 @@ class QuickPick<T extends IQuickPickItem> extends QuickInput implements IQuickPi
if (this.canSelectMany) {
return;
}
// Drop initial event.
if (!selectedItems.length && !this._selectedItems.length) {
if (this.selectedItemsToConfirm !== this._selectedItems && equals(selectedItems, this._selectedItems, (a, b) => a === b)) {
return;
}
this._selectedItems = selectedItems as T[];
......@@ -452,6 +453,9 @@ class QuickPick<T extends IQuickPickItem> extends QuickInput implements IQuickPi
if (!this.canSelectMany) {
return;
}
if (this.selectedItemsToConfirm !== this._selectedItems && equals(checkedItems, this._selectedItems, (a, b) => a === b)) {
return;
}
this._selectedItems = checkedItems as T[];
this.onDidChangeSelectionEmitter.fire(checkedItems as T[]);
}),
......@@ -490,15 +494,23 @@ class QuickPick<T extends IQuickPickItem> extends QuickInput implements IQuickPi
}
if (this.activeItemsUpdated) {
this.activeItemsUpdated = false;
this.activeItemsToConfirm = this._activeItems;
this.ui.list.setFocusedElements(this.activeItems);
if (this.activeItemsToConfirm === this._activeItems) {
this.activeItemsToConfirm = null;
}
}
if (this.selectedItemsUpdated) {
this.selectedItemsUpdated = false;
this.selectedItemsToConfirm = this._selectedItems;
if (this.canSelectMany) {
this.ui.list.setCheckedElements(this.selectedItems);
} else {
this.ui.list.setSelectedElements(this.selectedItems);
}
if (this.selectedItemsToConfirm === this._selectedItems) {
this.selectedItemsToConfirm = null;
}
}
this.ui.list.matchOnDescription = this.matchOnDescription;
this.ui.list.matchOnDetail = this.matchOnDetail;
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册