Skip to content

Commit

Permalink
Add keydown handler for rendered markdown strings (#166999)
Browse files Browse the repository at this point in the history
  • Loading branch information
rzhao271 authored Nov 28, 2022
1 parent 14cd314 commit 90e3aea
Show file tree
Hide file tree
Showing 3 changed files with 26 additions and 14 deletions.
3 changes: 2 additions & 1 deletion src/vs/base/browser/formattedTextRenderer.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,11 +4,12 @@
*--------------------------------------------------------------------------------------------*/

import * as DOM from 'vs/base/browser/dom';
import { IKeyboardEvent } from 'vs/base/browser/keyboardEvent';
import { IMouseEvent } from 'vs/base/browser/mouseEvent';
import { DisposableStore } from 'vs/base/common/lifecycle';

export interface IContentActionHandler {
callback: (content: string, event: IMouseEvent) => void;
callback: (content: string, event: IMouseEvent | IKeyboardEvent) => void;
readonly disposables: DisposableStore;
}

Expand Down
33 changes: 22 additions & 11 deletions src/vs/base/browser/markdownRenderer.ts
Original file line number Diff line number Diff line change
Expand Up @@ -7,13 +7,15 @@ import * as DOM from 'vs/base/browser/dom';
import * as dompurify from 'vs/base/browser/dompurify/dompurify';
import { DomEmitter } from 'vs/base/browser/event';
import { createElement, FormattedTextRenderOptions } from 'vs/base/browser/formattedTextRenderer';
import { StandardKeyboardEvent } from 'vs/base/browser/keyboardEvent';
import { StandardMouseEvent } from 'vs/base/browser/mouseEvent';
import { renderLabelWithIcons } from 'vs/base/browser/ui/iconLabel/iconLabels';
import { onUnexpectedError } from 'vs/base/common/errors';
import { Event } from 'vs/base/common/event';
import { IMarkdownString, escapeDoubleQuotes, parseHrefAndDimensions, removeMarkdownEscapes, MarkdownStringTrustedOptions } from 'vs/base/common/htmlContent';
import { markdownEscapeEscapedIcons } from 'vs/base/common/iconLabels';
import { defaultGenerator } from 'vs/base/common/idGenerator';
import { KeyCode } from 'vs/base/common/keyCodes';
import { Lazy } from 'vs/base/common/lazy';
import { DisposableStore } from 'vs/base/common/lifecycle';
import { marked } from 'vs/base/common/marked/marked';
Expand Down Expand Up @@ -158,15 +160,8 @@ export function renderMarkdown(markdown: IMarkdownString, options: MarkdownRende
}

if (options.actionHandler) {
const onClick = options.actionHandler.disposables.add(new DomEmitter(element, 'click'));
const onAuxClick = options.actionHandler.disposables.add(new DomEmitter(element, 'auxclick'));
options.actionHandler.disposables.add(Event.any(onClick.event, onAuxClick.event)(e => {
const mouseEvent = new StandardMouseEvent(e);
if (!mouseEvent.leftButton && !mouseEvent.middleButton) {
return;
}

let target: HTMLElement | null = mouseEvent.target;
const _activateLink = function (event: StandardMouseEvent | StandardKeyboardEvent): void {
let target: HTMLElement | null = event.target;
if (target.tagName !== 'A') {
target = target.parentElement;
if (!target || target.tagName !== 'A') {
Expand All @@ -179,13 +174,29 @@ export function renderMarkdown(markdown: IMarkdownString, options: MarkdownRende
if (markdown.baseUri) {
href = resolveWithBaseUri(URI.from(markdown.baseUri), href);
}
options.actionHandler!.callback(href, mouseEvent);
options.actionHandler!.callback(href, event);
}
} catch (err) {
onUnexpectedError(err);
} finally {
mouseEvent.preventDefault();
event.preventDefault();
}
};
const onClick = options.actionHandler.disposables.add(new DomEmitter(element, 'click'));
const onAuxClick = options.actionHandler.disposables.add(new DomEmitter(element, 'auxclick'));
options.actionHandler.disposables.add(Event.any(onClick.event, onAuxClick.event)(e => {
const mouseEvent = new StandardMouseEvent(e);
if (!mouseEvent.leftButton && !mouseEvent.middleButton) {
return;
}
_activateLink(mouseEvent);
}));
options.actionHandler.disposables.add(DOM.addDisposableListener(element, 'keydown', (e) => {
const keyboardEvent = new StandardKeyboardEvent(e);
if (!keyboardEvent.equals(KeyCode.Space) && !keyboardEvent.equals(KeyCode.Enter)) {
return;
}
_activateLink(keyboardEvent);
}));
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -141,15 +141,15 @@ class UntitledTextEditorHintContentWidget implements IContentWidget {
}

// the actual command handlers...
const languageOnClickOrTap = async (e: MouseEvent) => {
const languageOnClickOrTap = async (e: UIEvent) => {
e.stopPropagation();
// Need to focus editor before so current editor becomes active and the command is properly executed
this.editor.focus();
await this.commandService.executeCommand(ChangeLanguageAction.ID, { from: 'hint' });
this.editor.focus();
};

const chooseEditorOnClickOrTap = async (e: MouseEvent) => {
const chooseEditorOnClickOrTap = async (e: UIEvent) => {
e.stopPropagation();

const activeEditorInput = this.editorGroupsService.activeGroup.activeEditor;
Expand Down

0 comments on commit 90e3aea

Please sign in to comment.