IDEA-165950 National keyboard layouts support

This commit is contained in:
Denis Fokin
2017-04-17 13:02:48 +03:00
parent fb2f4214e5
commit 5a8f656e5c
8 changed files with 44 additions and 40 deletions
@@ -39,8 +39,6 @@ public class KeyboardSettingsExternalizable implements PersistentStateComponent<
private static final String [] supportedNonEnglishLanguages = {"de", "fr", "it", "uk"};
public static boolean isSupportedKeyboardLayout(@NotNull Component component) {
if (Registry.is("ide.keyboard.dvorak")) return true;
if (SystemInfo.isMac) return false;
String keyboardLayoutLanguage = getLanguageForComponent(component);
for (String language : supportedNonEnglishLanguages) {
if (language.equals(keyboardLayoutLanguage)) {
@@ -97,6 +97,16 @@ public class VMOptions {
}
public static void writeOption(@NotNull MemoryKind option, int value) {
String optionValue = option.option + value + "m";
writeGeneralOption(option.pattern, optionValue);
}
public static void writeOption(@NotNull String option, @NotNull String separator, @NotNull String value) {
writeGeneralOption(Pattern.compile("-D" + option + separator + "(true|false)*([a-zA-Z]*)"), "-D" + option + separator + value);
}
private static void writeGeneralOption(@NotNull Pattern pattern, @NotNull String value) {
File file = getWriteFile();
if (file == null) {
LOG.warn("VM options file not configured");
@@ -106,22 +116,20 @@ public class VMOptions {
try {
String content = file.exists() ? FileUtil.loadFile(file) : read();
String optionValue = option.option + value + "m";
if (!StringUtil.isEmptyOrSpaces(content)) {
Matcher m = option.pattern.matcher(content);
Matcher m = pattern.matcher(content);
if (m.find()) {
StringBuffer b = new StringBuffer();
m.appendReplacement(b, Matcher.quoteReplacement(optionValue));
m.appendReplacement(b, Matcher.quoteReplacement(value));
m.appendTail(b);
content = b.toString();
}
else {
content = StringUtil.trimTrailing(content) + SystemProperties.getLineSeparator() + optionValue;
content = StringUtil.trimTrailing(content) + SystemProperties.getLineSeparator() + value;
}
}
else {
content = optionValue;
content = value;
}
if (file.exists()) {
@@ -348,8 +348,6 @@ public class IdeEventQueue extends EventQueue {
return;
}
e = fixNonEnglishKeyboardLayouts(e);
e = mapEvent(e);
if (Registry.is("keymap.windows.as.meta")) {
e = mapMetaState(e);
@@ -427,9 +425,6 @@ public class IdeEventQueue extends EventQueue {
private static AWTEvent fixNonEnglishKeyboardLayouts(@NotNull AWTEvent e) {
if (!(e instanceof KeyEvent)) return e;
KeyboardSettingsExternalizable externalizable = KeyboardSettingsExternalizable.getInstance();
if (!Registry.is("ide.non.english.keyboard.layout.fix") || externalizable == null || !externalizable.isNonEnglishKeyboardSupportEnabled()) return e;
KeyEvent ke = (KeyEvent)e;
switch (ke.getID()) {
@@ -928,7 +928,6 @@ public final class EditorImpl extends UserDataHolderBase implements EditorEx, Hi
if (e.getKeyCode() >= KeyEvent.VK_A && e.getKeyCode() <= KeyEvent.VK_Z) {
myCharKeyPressed = true;
}
KeyboardInternationalizationNotificationManager.showNotification();
}
@Override
@@ -38,7 +38,7 @@ public class KeyboardInternationalizationNotificationManager {
private KeyboardInternationalizationNotificationManager() {
}
public static void showNotification() {
/* public static void showNotification() {
Window mostRecentFocusedWindow = WindowManagerEx.getInstanceEx().getMostRecentFocusedWindow();
if (notificationHasBeenShown || (mostRecentFocusedWindow != null && !KeyboardSettingsExternalizable.isSupportedKeyboardLayout(mostRecentFocusedWindow))) return;
@@ -48,9 +48,9 @@ public class KeyboardInternationalizationNotificationManager {
Notifications.Bus.notify(createNotification(LOCALIZATION_GROUP_DISPLAY_ID, listener));
notificationHasBeenShown = true;
}
}*/
public static Notification createNotification(@NotNull final String groupDisplayId, @Nullable NotificationListener listener) {
/* public static Notification createNotification(@NotNull final String groupDisplayId, @Nullable NotificationListener listener) {
Window recentFocusedWindow = WindowManagerEx.getInstanceEx().getMostRecentFocusedWindow();
@@ -71,7 +71,7 @@ public class KeyboardInternationalizationNotificationManager {
text,
NotificationType.INFORMATION,
listener);
}
}*/
private static class MyNotificationListener implements NotificationListener {
@@ -16,6 +16,7 @@
package com.intellij.openapi.keymap.impl.ui;
import com.intellij.CommonBundle;
import com.intellij.diagnostic.VMOptions;
import com.intellij.icons.AllIcons;
import com.intellij.ide.CommonActionsManager;
import com.intellij.ide.DataManager;
@@ -26,6 +27,7 @@ import com.intellij.openapi.actionSystem.ex.QuickList;
import com.intellij.openapi.actionSystem.ex.QuickListsManager;
import com.intellij.openapi.actionSystem.impl.ActionToolbarImpl;
import com.intellij.openapi.application.ApplicationManager;
import com.intellij.openapi.application.ModalityState;
import com.intellij.openapi.keymap.*;
import com.intellij.openapi.keymap.ex.KeymapManagerEx;
import com.intellij.openapi.keymap.impl.ActionShortcutRestrictions;
@@ -63,6 +65,7 @@ import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import javax.swing.*;
import javax.swing.border.EmptyBorder;
import java.awt.*;
import java.awt.event.*;
import java.beans.PropertyChangeEvent;
@@ -115,7 +118,7 @@ public class KeymapPanel extends JPanel implements SearchableConfigurable, Confi
private JButton myCopyButton;
private JButton myDeleteButton;
private JButton myResetToDefault;
private JCheckBox myNonEnglishKeyboardSupportOption;
private JCheckBox preferKeyPositionOverCharOption;
private JLabel myBaseKeymapLabel;
@@ -132,6 +135,25 @@ public class KeymapPanel extends JPanel implements SearchableConfigurable, Confi
JPanel keymapPanel = new JPanel(new BorderLayout());
keymapPanel.add(createKeymapListPanel(), BorderLayout.NORTH);
keymapPanel.add(createKeymapSettingsPanel(), BorderLayout.CENTER);
IdeFrame ideFrame = IdeFocusManager.getGlobalInstance().getLastFocusedFrame();
if (ideFrame != null && KeyboardSettingsExternalizable.isSupportedKeyboardLayout(ideFrame.getComponent())) {
preferKeyPositionOverCharOption = new JCheckBox(new AbstractAction(" " + KeyMapBundle.message("prefer.key.position")) {
@Override
public void actionPerformed(ActionEvent e) {
VMOptions.writeOption("com.jetbrains.use.old.keyevent.processing", "=",
Boolean.toString(preferKeyPositionOverCharOption.isSelected()));
ApplicationManager.getApplication().invokeLater(
() -> ApplicationManager.getApplication().restart(),
ModalityState.NON_MODAL
);
}
});
//preferKeyPositionOverCharOption.setSelected();
preferKeyPositionOverCharOption.setBorder(new EmptyBorder(0, 0, 0, 0));
keymapPanel.add(preferKeyPositionOverCharOption, BorderLayout.SOUTH);
}
add(keymapPanel, BorderLayout.CENTER);
addPropertyChangeListener(new PropertyChangeListener() {
@Override
@@ -269,18 +291,6 @@ public class KeymapPanel extends JPanel implements SearchableConfigurable, Confi
gc.weightx = 1;
panel.add(myDeleteButton, gc);
IdeFrame ideFrame = IdeFocusManager.getGlobalInstance().getLastFocusedFrame();
if (ideFrame != null && KeyboardSettingsExternalizable.isSupportedKeyboardLayout(ideFrame.getComponent()))
{
String displayLanguage = ideFrame.getComponent().getInputContext().getLocale().getDisplayLanguage();
myNonEnglishKeyboardSupportOption = new JCheckBox(new AbstractAction(displayLanguage + " " + KeyMapBundle.message("use.non.english.keyboard.layout.support")) {
@Override
public void actionPerformed(ActionEvent e) {
KeyboardSettingsExternalizable.getInstance().setNonEnglishKeyboardSupportEnabled(myNonEnglishKeyboardSupportOption.isSelected());
}
});
myNonEnglishKeyboardSupportOption.setSelected(KeyboardSettingsExternalizable.getInstance().isNonEnglishKeyboardSupportEnabled());
panel.add(myNonEnglishKeyboardSupportOption, gc);
}
myResetToDefault.addActionListener(new ActionListener() {
@Override
@@ -663,8 +673,8 @@ public class KeymapPanel extends JPanel implements SearchableConfigurable, Confi
@Override
public void reset() {
if (myNonEnglishKeyboardSupportOption != null) {
myNonEnglishKeyboardSupportOption.setSelected(KeyboardSettingsExternalizable.getInstance().isNonEnglishKeyboardSupportEnabled());
if (preferKeyPositionOverCharOption != null) {
preferKeyPositionOverCharOption.setSelected(KeyboardSettingsExternalizable.getInstance().isNonEnglishKeyboardSupportEnabled());
}
Keymap activeKeymap = KeymapManagerEx.getInstanceEx().getActiveKeymap();
@@ -46,7 +46,7 @@ remove.keymap.label=Remo&ve
unnamed.list.display.name=unnamed
copy.keymap.button=&Copy
delete.keymap.button=De&lete
use.non.english.keyboard.layout.support=la&yout support
prefer.key.position=Prefer key position over key char with national layout
parent.keymap.label=Parent keymap:
disable.mnemonic.in.menu.check.box=Disable mnemonics in &menu
@@ -450,12 +450,6 @@ ide.goto.rebuild.delay.description=How many milliseconds to wait before updating
ide.structural.navigation.visit.fields=false
ide.structural.navigation.visit.fields.description=Whether fields should be stopped at when navigating to the nex/previous structural member by Alt+Down/Up.
ide.non.english.keyboard.layout.fix=false
ide.non.english.keyboard.layout.fix.description=Enables a fix for key codes with non-English keyboard layouts
ide.keyboard.dvorak=false
ide.keyboard.dvorak.description=Enables Dvorak layout support if ide.non.english.keyboard.layout.fix is enabled
ide.dfa.getters.with.side.effects=
ide.dfa.getters.with.side.effects.description=A regex on qualified names of methods that look like getters but are not. For Constant Conditions & Exception inspection