Path: blob/main/extensions/markdown-language-features/src/languageFeatures/updateLinksOnPaste.ts
3292 views
/*---------------------------------------------------------------------------------------------1* Copyright (c) Microsoft Corporation. All rights reserved.2* Licensed under the MIT License. See License.txt in the project root for license information.3*--------------------------------------------------------------------------------------------*/45import * as vscode from 'vscode';6import { MdLanguageClient } from '../client/client';7import { Mime } from '../util/mimes';89class UpdatePastedLinksEditProvider implements vscode.DocumentPasteEditProvider {1011public static readonly kind = vscode.DocumentDropOrPasteEditKind.Text.append('updateLinks', 'markdown');1213public static readonly metadataMime = 'application/vnd.vscode.markdown.updatelinks.metadata';1415constructor(16private readonly _client: MdLanguageClient,17) { }1819async prepareDocumentPaste(document: vscode.TextDocument, ranges: readonly vscode.Range[], dataTransfer: vscode.DataTransfer, token: vscode.CancellationToken): Promise<void> {20if (!this._isEnabled(document)) {21return;22}2324const metadata = await this._client.prepareUpdatePastedLinks(document.uri, ranges, token);25if (token.isCancellationRequested) {26return;27}2829dataTransfer.set(UpdatePastedLinksEditProvider.metadataMime, new vscode.DataTransferItem(metadata));30}3132async provideDocumentPasteEdits(33document: vscode.TextDocument,34ranges: readonly vscode.Range[],35dataTransfer: vscode.DataTransfer,36context: vscode.DocumentPasteEditContext,37token: vscode.CancellationToken,38): Promise<vscode.DocumentPasteEdit[] | undefined> {39if (!this._isEnabled(document)) {40return;41}4243const metadata = dataTransfer.get(UpdatePastedLinksEditProvider.metadataMime)?.value;44if (!metadata) {45return;46}4748const textItem = dataTransfer.get(Mime.textPlain);49const text = await textItem?.asString();50if (!text || token.isCancellationRequested) {51return;52}5354// TODO: Handle cases such as:55// - copy empty line56// - Copy with multiple cursors and paste into multiple locations57// - ...58const edits = await this._client.getUpdatePastedLinksEdit(document.uri, ranges.map(x => new vscode.TextEdit(x, text)), metadata, token);59if (!edits?.length || token.isCancellationRequested) {60return;61}6263const pasteEdit = new vscode.DocumentPasteEdit('', vscode.l10n.t("Paste and update pasted links"), UpdatePastedLinksEditProvider.kind);64const workspaceEdit = new vscode.WorkspaceEdit();65workspaceEdit.set(document.uri, edits.map(x => new vscode.TextEdit(new vscode.Range(x.range.start.line, x.range.start.character, x.range.end.line, x.range.end.character,), x.newText)));66pasteEdit.additionalEdit = workspaceEdit;6768if (!context.only || !UpdatePastedLinksEditProvider.kind.contains(context.only)) {69pasteEdit.yieldTo = [vscode.DocumentDropOrPasteEditKind.Text];70}7172return [pasteEdit];73}7475private _isEnabled(document: vscode.TextDocument): boolean {76return vscode.workspace.getConfiguration('markdown', document.uri).get<boolean>('editor.updateLinksOnPaste.enabled', true);77}78}7980export function registerUpdatePastedLinks(selector: vscode.DocumentSelector, client: MdLanguageClient) {81return vscode.languages.registerDocumentPasteEditProvider(selector, new UpdatePastedLinksEditProvider(client), {82copyMimeTypes: [UpdatePastedLinksEditProvider.metadataMime],83providedPasteEditKinds: [UpdatePastedLinksEditProvider.kind],84pasteMimeTypes: [UpdatePastedLinksEditProvider.metadataMime],85});86}878889