-
-
Notifications
You must be signed in to change notification settings - Fork 122
/
promptUser.ts
80 lines (67 loc) · 3.28 KB
/
promptUser.ts
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
import type { QuickPickOptions } from 'vscode';
import { Uri, window } from 'vscode';
import { extractMatchingDiagTexts, getCSpellDiags } from './diags';
import { normalizeWords } from './settings/CSpellSettings';
import { findEditor } from './util/findEditor';
import { toUri } from './util/uriHelper';
const compareStrings = new Intl.Collator().compare;
export function onCommandUseDiagsSelectionOrPrompt(
prompt: string,
fnAction: (text: string, uri: Uri | undefined) => Promise<void>,
): (text?: string, uri?: Uri | string) => Promise<void> {
return async function (text?: string, uri?: Uri | string) {
// console.log('onCommandUseDiagsSelectionOrPrompt %o', { prompt, text, uri });
const selected = await determineTextSelection(prompt, text, uri);
if (!selected) return;
const editor = window.activeTextEditor;
await fnAction(selected.text, selected.uri);
await (editor?.document && window.showTextDocument(editor.document));
};
}
async function determineTextSelection(
prompt: string,
textOrUri?: string | Uri,
uri?: Uri | string,
): Promise<{ text: string; uri?: Uri } | undefined> {
uri = uri ? toUri(uri) : textOrUri instanceof Uri ? textOrUri : undefined;
if (typeof textOrUri === 'string' && textOrUri) {
return { text: textOrUri, uri: uri || window.activeTextEditor?.document.uri };
}
const editor = findEditor(uri);
const document = editor?.document;
const selection = editor?.selection;
const range = selection && document?.getWordRangeAtPosition(selection.active);
const diags = document ? getCSpellDiags(document.uri) : undefined;
const matchingDiagWords = normalizeWords(extractMatchingDiagTexts(document, selection, diags) || []);
if (matchingDiagWords.length) {
const picked =
selection?.anchor.isEqual(selection.active) && matchingDiagWords.length === 1
? matchingDiagWords
: await chooseWords(matchingDiagWords.sort(compareStrings), { title: prompt, placeHolder: 'Choose words' });
if (!picked) return;
return { text: picked.join(' '), uri: document?.uri };
}
if (!range || !selection || !document || !document.getText(range)) {
const word = await window.showInputBox({ title: prompt, prompt });
if (!word) return;
return { text: word, uri: document?.uri };
}
const text = selection.contains(range) ? document.getText(selection) : document.getText(range);
const words = normalizeWords(text);
const picked =
words.length > 1
? await chooseWords(words.sort(compareStrings), { title: prompt, placeHolder: 'Choose words' })
: [await window.showInputBox({ title: prompt, prompt, value: words[0] })];
if (!picked) return;
return { text: picked.join(' '), uri: document.uri };
}
async function chooseWords(words: string[], options: QuickPickOptions): Promise<string[] | undefined> {
if (words.length <= 1) {
const picked = await window.showInputBox({ ...options, value: words[0] });
if (!picked) return;
return [picked];
}
const items = words.map((label) => ({ label, picked: true }));
const picked = await window.showQuickPick(items, { ...options, canPickMany: true });
return picked?.map((p) => p.label);
}