From ebd3186b3028e43f08bcd77e69f98b454dce65aa Mon Sep 17 00:00:00 2001 From: Sergey Simonchik Date: Mon, 25 Mar 2019 19:36:26 +0300 Subject: [PATCH] terminal: move focus back to the editor on Escape (IDEA-116221) --- .../intellij/terminal/JBTerminalPanel.java | 7 +++ .../intellij/terminal/JBTerminalWidget.java | 18 -------- .../terminal/TerminalEscapeKeyListener.java | 46 +++++++++++++++++++ 3 files changed, 53 insertions(+), 18 deletions(-) create mode 100644 platform/platform-impl/src/com/intellij/terminal/TerminalEscapeKeyListener.java diff --git a/platform/platform-impl/src/com/intellij/terminal/JBTerminalPanel.java b/platform/platform-impl/src/com/intellij/terminal/JBTerminalPanel.java index 71a283d94cf6..62426915e9d2 100644 --- a/platform/platform-impl/src/com/intellij/terminal/JBTerminalPanel.java +++ b/platform/platform-impl/src/com/intellij/terminal/JBTerminalPanel.java @@ -76,6 +76,7 @@ public class JBTerminalPanel extends TerminalPanel implements FocusListener, Ter }; private final JBTerminalSystemSettingsProviderBase mySettingsProvider; + private final TerminalEscapeKeyListener myEscapeKeyListener; private List myActionsToSkip; @@ -91,6 +92,7 @@ public class JBTerminalPanel extends TerminalPanel implements FocusListener, Ter addFocusListener(this); mySettingsProvider.addListener(this); + myEscapeKeyListener = new TerminalEscapeKeyListener(this); } private static void registerKeymapActions(final TerminalPanel terminalPanel) { @@ -157,6 +159,11 @@ public class JBTerminalPanel extends TerminalPanel implements FocusListener, Ter return false; } + @Override + public void handleKeyEvent(@NotNull KeyEvent e) { + myEscapeKeyListener.handleKeyEvent(e); + super.handleKeyEvent(e); + } @Override protected void setupAntialiasing(Graphics graphics) { diff --git a/platform/platform-impl/src/com/intellij/terminal/JBTerminalWidget.java b/platform/platform-impl/src/com/intellij/terminal/JBTerminalWidget.java index ead733ee5c59..2818f8d29c3d 100644 --- a/platform/platform-impl/src/com/intellij/terminal/JBTerminalWidget.java +++ b/platform/platform-impl/src/com/intellij/terminal/JBTerminalWidget.java @@ -23,7 +23,6 @@ import com.intellij.openapi.fileEditor.impl.FileEditorManagerImpl; import com.intellij.openapi.project.Project; import com.intellij.openapi.util.Disposer; import com.intellij.openapi.vfs.VirtualFile; -import com.intellij.openapi.wm.ToolWindowManager; import com.intellij.ui.SearchTextField; import com.intellij.ui.components.JBScrollBar; import com.intellij.ui.components.JBScrollPane; @@ -55,7 +54,6 @@ import java.awt.event.KeyListener; import java.util.List; public class JBTerminalWidget extends JediTermWidget implements Disposable { - private Project myProject; private final JBTerminalSystemSettingsProviderBase mySettingsProvider; private JBTerminalWidgetListener myListener; @@ -75,7 +73,6 @@ public class JBTerminalWidget extends JediTermWidget implements Disposable { JBTerminalSystemSettingsProviderBase settingsProvider, Disposable parent) { super(columns, lines, settingsProvider); - myProject = project; mySettingsProvider = settingsProvider; setName("terminal"); @@ -161,20 +158,6 @@ public class JBTerminalWidget extends JediTermWidget implements Disposable { myListener.showTabs(); return true; }).withMnemonicKey(KeyEvent.VK_T).withEnabledSupplier(() -> myListener != null)); - if (!mySettingsProvider.overrideIdeShortcuts()) { - actions - .add(new TerminalAction("EditorEscape", new KeyStroke[]{KeyStroke.getKeyStroke(KeyEvent.VK_ESCAPE, 0)}, input -> { - if (!myTerminalPanel.getTerminalTextBuffer().isUsingAlternateBuffer()) { - if (myProject != null) { - ToolWindowManager.getInstance(myProject).activateEditorComponent(); - } - return true; - } - else { - return false; - } - }).withHidden(true)); - } actions.add(new TerminalAction("Close Session", mySettingsProvider.getCloseSessionKeyStrokes(), input -> { myListener.onSessionClosed(); return true; @@ -184,7 +167,6 @@ public class JBTerminalWidget extends JediTermWidget implements Disposable { @Override public void dispose() { - myProject = null; close(); } diff --git a/platform/platform-impl/src/com/intellij/terminal/TerminalEscapeKeyListener.java b/platform/platform-impl/src/com/intellij/terminal/TerminalEscapeKeyListener.java new file mode 100644 index 000000000000..e8a79fdd7565 --- /dev/null +++ b/platform/platform-impl/src/com/intellij/terminal/TerminalEscapeKeyListener.java @@ -0,0 +1,46 @@ +// Copyright 2000-2019 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license that can be found in the LICENSE file. +package com.intellij.terminal; + +import com.intellij.ide.DataManager; +import com.intellij.openapi.actionSystem.CommonDataKeys; +import com.intellij.openapi.project.Project; +import com.intellij.openapi.wm.ToolWindowManager; +import com.jediterm.terminal.ui.TerminalPanel; +import org.jetbrains.annotations.NotNull; + +import java.awt.event.KeyEvent; + +/** + * Moves focus to editor on Escape key pressed, similarly to {@link com.intellij.openapi.wm.impl.InternalDecorator#init}. + * Respects ESC+F/ESC+B and other combinations with ESC. + */ +public class TerminalEscapeKeyListener { + private final TerminalPanel myTerminalPanel; + private boolean myEscapePressed = false; + + public TerminalEscapeKeyListener(@NotNull TerminalPanel terminalPanel) { + myTerminalPanel = terminalPanel; + } + + public void handleKeyEvent(@NotNull KeyEvent e) { + if (e.getID() == KeyEvent.KEY_PRESSED) { + myEscapePressed = e.getKeyCode() == KeyEvent.VK_ESCAPE && e.getModifiers() == 0; + } + else if (e.getID() == KeyEvent.KEY_RELEASED) { + if (myEscapePressed && e.getKeyCode() == KeyEvent.VK_ESCAPE && e.getModifiers() == 0) { + performIdeEscapeAction(); + } + myEscapePressed = false; + } + } + + private void performIdeEscapeAction() { + if (!myTerminalPanel.getTerminalTextBuffer().isUsingAlternateBuffer()) { + Project project = DataManager.getInstance().getDataContext(myTerminalPanel).getData(CommonDataKeys.PROJECT); + if (project != null && !project.isDisposed()) { + // Repeat logic of InternalDecorator#init from 8cf12b35fe3e44a32622f52a151ed2bf8880faba + ToolWindowManager.getInstance(project).activateEditorComponent(); + } + } + } +}