Key Bindings for text components are all fixed.

2005-12-20  Lillian Angel  <[EMAIL PROTECTED]>

        * javax/swing/plaf/basic/BasicLookAndFeel.java
        (initClassDefaults): Fixed typo.
        (initComponentDefaults): Removed keyBindings defaults for
        Text*. Added focusInputMap for Text*.
        * javax/swing/plaf/basic/BasicTextUI.java
        (installKeyBoardActions): Added code to load the focusInputMap
        and install all the actions for each key.
        (ActionListenerProxy): New class implemented.
        (converModifiers): New method to convert the modifiers.
        (getActionMap): Removed function. Not needed.
        (createActionMap): Likewise.
        * javax/swing/text/JTextComponent.java
        (JTextComponent): Removed code to load the keymap.




On Wed, 2005-12-21 at 13:50 +0100, Roman Kennke wrote:
> Hi Lillian,
> 
> I would prefer the more efficient (and more correct?) solution and fix
> the viewToModel() methods. I don't really care if it doesn't work yet
> because of the viewToModel() methods not working properly, this way we
> have some more reasons to fix those.
> 
> Also, in JTextComponent you directly create KeyBindings for the new
> Actions. This doesn't sound right, IMO this should be done by the UI
> (BasicTextUI). The UIDefaults should have an array of InputMap-like
> bindings (e.g. in TextField.focusInputMap) that should then be loaded
> into an InputMap (using LookAndFeel.loadKeyBindings()) and installed in
> the text component (using SwingUtilities.replaceUIInputMap()). Direct
> key bindings are not what we want.
> 
> Could you please fix that? (At least the keybinding thing?) Also note
> that there is a getActionMap() method in BasicTextUI that really
> shouldn't be there. We should figure out how to properly install an
> ActionMap on the text component, I would think that we fetch
> getActions() from JTextComponent and create an ActionMap out of it by
> fetching the NAME from the Action instances and put them into an
> ActionMap using the NAME as key.
> 
> Cheers, Roman
> 
Index: javax/swing/plaf/basic/BasicLookAndFeel.java
===================================================================
RCS file: /cvsroot/classpath/classpath/javax/swing/plaf/basic/BasicLookAndFeel.java,v
retrieving revision 1.69
diff -u -r1.69 BasicLookAndFeel.java
--- javax/swing/plaf/basic/BasicLookAndFeel.java	17 Dec 2005 01:35:38 -0000	1.69
+++ javax/swing/plaf/basic/BasicLookAndFeel.java	21 Dec 2005 16:45:50 -0000
@@ -220,7 +220,7 @@
       "TextPaneUI", "javax.swing.plaf.basic.BasicTextPaneUI",
       "TextAreaUI", "javax.swing.plaf.basic.BasicTextAreaUI",
       "TextFieldUI", "javax.swing.plaf.basic.BasicTextFieldUI",
-      "TextPaneUI", "javax.swing.plaf.basic.BasicTextPaneUI",
+      "TextUI", "javax.swing.plaf.basic.BasicTextUI",
       "ToggleButtonUI", "javax.swing.plaf.basic.BasicToggleButtonUI",
       "ToolBarSeparatorUI", "javax.swing.plaf.basic.BasicToolBarSeparatorUI",
       "ToolBarUI", "javax.swing.plaf.basic.BasicToolBarUI",
@@ -1052,28 +1052,32 @@
       "TableHeader.font", new FontUIResource("Dialog", Font.PLAIN, 12),
       "TableHeader.foreground", new ColorUIResource(new ColorUIResource(0, 0, 0)),
 
-            "TextArea.background", new ColorUIResource(light),
-      "TextArea.border",
-      new BorderUIResource(BasicBorders.getMarginBorder()),
+      "TextArea.background", new ColorUIResource(light),
+      "TextArea.border", new BorderUIResource(BasicBorders.getMarginBorder()),
       "TextArea.caretBlinkRate", new Integer(500),
       "TextArea.caretForeground", new ColorUIResource(Color.black),
       "TextArea.font", new FontUIResource("MonoSpaced", Font.PLAIN, 12),
       "TextArea.foreground", new ColorUIResource(Color.black),
       "TextArea.inactiveForeground", new ColorUIResource(Color.gray),
-      "TextArea.keyBindings", new JTextComponent.KeyBinding[] {
-        new JTextComponent.KeyBinding(KeyStroke.getKeyStroke(KeyEvent.VK_UP,
-                                                             0), "caret-up"),
-        new JTextComponent.KeyBinding(KeyStroke.getKeyStroke(KeyEvent.VK_DOWN,
-                                                             0), "caret-down"),
-        new JTextComponent.KeyBinding(KeyStroke.getKeyStroke(KeyEvent.VK_PAGE_UP,
-                                                             0), "page-up"),
-        new JTextComponent.KeyBinding(KeyStroke.getKeyStroke(KeyEvent.VK_PAGE_DOWN,
-                                                             0), "page-down"),
-        new JTextComponent.KeyBinding(KeyStroke.getKeyStroke(KeyEvent.VK_ENTER,
-                                                             0), "insert-break"),
-        new JTextComponent.KeyBinding(KeyStroke.getKeyStroke(KeyEvent.VK_TAB,
-                                                             0), "insert-tab")
-          },
+      "TextArea.focusInputMap", new UIDefaults.LazyInputMap(new Object[] {
+         "UP", "caret-up",
+         "DOWN", "caret-down",
+         "PAGE_UP", "page-up",
+         "PAGE_DOWN", "page-down",
+         "ENTER", "insert-break",
+         "TAB", "insert-tab",
+         "LEFT", "caret-backward",
+         "RIGHT", "caret-forward",
+         "BACK_SPACE", "delete-previous",
+         "ctrl X", "cut-to-clipboard",
+         "ctrl C", "copy-to-clipboard",
+         "ctrl V", "paste-from-clipboard",
+         "shift LEFT", "selection-backward",
+         "shift RIGHT", "selection-forward",
+         "HOME", "caret-begin-line",
+         "END", "caret-end-line",
+         "DELETE", "delete-next"
+      }),
       "TextArea.margin", new InsetsUIResource(0, 0, 0, 0),
       "TextArea.selectionBackground", new ColorUIResource(Color.black),
       "TextArea.selectionForeground", new ColorUIResource(Color.white),
@@ -1089,17 +1093,20 @@
       "TextField.inactiveForeground", new ColorUIResource(Color.GRAY),
       "TextField.light", new ColorUIResource(highLight),
       "TextField.highlight", new ColorUIResource(light),
-      "TextField.keyBindings", new JTextComponent.KeyBinding[] {
-        new JTextComponent.KeyBinding(KeyStroke.getKeyStroke(KeyEvent.VK_ENTER,
-                                                             0),
-                                      "notify-field-accept"),
-        new JTextComponent.KeyBinding(KeyStroke.getKeyStroke(KeyEvent.VK_LEFT,
-                                 InputEvent.SHIFT_DOWN_MASK),
-                                 "selection-backward"),
-        new JTextComponent.KeyBinding(KeyStroke.getKeyStroke(KeyEvent.VK_RIGHT,
-                                 InputEvent.SHIFT_DOWN_MASK),
-                                 "selection-forward"),
-          },
+      "TextField.focusInputMap", new UIDefaults.LazyInputMap(new Object[] {
+         "ENTER", "notify-field-accept",
+         "LEFT", "caret-backward",
+         "RIGHT", "caret-forward",
+         "BACK_SPACE", "delete-previous",
+         "ctrl X", "cut-to-clipboard",
+         "ctrl C", "copy-to-clipboard",
+         "ctrl V", "paste-from-clipboard",
+         "shift LEFT", "selection-backward",
+         "shift RIGHT", "selection-forward",
+         "HOME", "caret-begin-line",
+         "END", "caret-end-line",
+         "DELETE", "delete-next"
+      }),
       "TextField.margin", new InsetsUIResource(0, 0, 0, 0),
       "TextField.selectionBackground", new ColorUIResource(Color.black),
       "TextField.selectionForeground", new ColorUIResource(Color.white),
@@ -1110,20 +1117,25 @@
       "TextPane.font", new FontUIResource("Serif", Font.PLAIN, 12),
       "TextPane.foreground", new ColorUIResource(Color.black),
       "TextPane.inactiveForeground", new ColorUIResource(Color.gray),
-      "TextPane.keyBindings", new JTextComponent.KeyBinding[] {
-        new JTextComponent.KeyBinding(KeyStroke.getKeyStroke(KeyEvent.VK_UP,
-                                                             0), "caret-up"),
-        new JTextComponent.KeyBinding(KeyStroke.getKeyStroke(KeyEvent.VK_DOWN,
-                                                             0), "caret-down"),
-        new JTextComponent.KeyBinding(KeyStroke.getKeyStroke(KeyEvent.VK_PAGE_UP,
-                                                             0), "page-up"),
-        new JTextComponent.KeyBinding(KeyStroke.getKeyStroke(KeyEvent.VK_PAGE_DOWN,
-                                                             0), "page-down"),
-        new JTextComponent.KeyBinding(KeyStroke.getKeyStroke(KeyEvent.VK_ENTER,
-                                                             0), "insert-break"),
-        new JTextComponent.KeyBinding(KeyStroke.getKeyStroke(KeyEvent.VK_TAB,
-                                                             0), "insert-tab")
-          },
+      "TextPane.focusInputMap", new UIDefaults.LazyInputMap(new Object[] {
+          "UP", "caret-up",
+          "DOWN", "caret-down",
+          "PAGE_DOWN", "page-down",
+          "PAGE_UP", "page-up",
+          "ENTER", "insert-break",
+          "TAB", "insert-tab",
+          "LEFT", "caret-backward",
+          "RIGHT", "caret-forward",
+          "BACK_SPACE", "delete-previous",
+          "ctrl X", "cut-to-clipboard",
+          "ctrl C", "copy-to-clipboard",
+          "ctrl V", "paste-from-clipboard",
+          "shift LEFT", "selection-backward",
+          "shift RIGHT", "selection-forward",
+          "HOME", "caret-begin-line",
+          "END", "caret-end-line",
+          "DELETE", "delete-next"
+      }),
       "TextPane.margin", new InsetsUIResource(3, 3, 3, 3),
       "TextPane.selectionBackground", new ColorUIResource(Color.black),
       "TextPane.selectionForeground", new ColorUIResource(Color.white),
@@ -1178,8 +1190,6 @@
       }),
       "Tree.background", new ColorUIResource(new Color(255, 255, 255)),
       "Tree.changeSelectionWithFocus", Boolean.TRUE,
-//      "Tree.closedIcon", new IconUIResource(new ImageIcon("icons/TreeClosed.png")),
-//      "Tree.collapsedIcon", new IconUIResource(new ImageIcon("icons/TreeCollapsed.png")),
       "Tree.drawsFocusBorderAroundIcon", Boolean.FALSE,
       "Tree.editorBorder", new BorderUIResource.LineBorderUIResource(Color.lightGray),
       "Tree.focusInputMap", new UIDefaults.LazyInputMap(new Object[] {
Index: javax/swing/plaf/basic/BasicTextUI.java
===================================================================
RCS file: /cvsroot/classpath/classpath/javax/swing/plaf/basic/BasicTextUI.java,v
retrieving revision 1.57
diff -u -r1.57 BasicTextUI.java
--- javax/swing/plaf/basic/BasicTextUI.java	23 Nov 2005 11:59:30 -0000	1.57
+++ javax/swing/plaf/basic/BasicTextUI.java	21 Dec 2005 16:45:51 -0000
@@ -46,15 +46,20 @@
 import java.awt.Point;
 import java.awt.Rectangle;
 import java.awt.Shape;
+import java.awt.event.ActionEvent;
+import java.awt.event.ActionListener;
 import java.awt.event.FocusEvent;
 import java.awt.event.FocusListener;
+import java.awt.event.KeyEvent;
 import java.beans.PropertyChangeEvent;
 import java.beans.PropertyChangeListener;
 
+import javax.swing.AbstractAction;
 import javax.swing.Action;
 import javax.swing.ActionMap;
 import javax.swing.InputMap;
 import javax.swing.JComponent;
+import javax.swing.KeyStroke;
 import javax.swing.LookAndFeel;
 import javax.swing.SwingConstants;
 import javax.swing.SwingUtilities;
@@ -62,6 +67,7 @@
 import javax.swing.event.DocumentEvent;
 import javax.swing.event.DocumentListener;
 import javax.swing.plaf.ActionMapUIResource;
+import javax.swing.plaf.InputMapUIResource;
 import javax.swing.plaf.TextUI;
 import javax.swing.plaf.UIResource;
 import javax.swing.text.BadLocationException;
@@ -636,7 +642,7 @@
    * Installs the keyboard actions on the text components.
    */
   protected void installKeyboardActions()
-  {    
+  {
     // load any bindings for the older Keymap interface
     Keymap km = JTextComponent.getKeymap(getKeymapName());
     if (km == null)
@@ -644,10 +650,104 @@
     textComponent.setKeymap(km);
 
     // load any bindings for the newer InputMap / ActionMap interface
-    SwingUtilities.replaceUIInputMap(textComponent, 
-                                     JComponent.WHEN_FOCUSED,
+    SwingUtilities.replaceUIInputMap(textComponent, JComponent.WHEN_FOCUSED,
                                      getInputMap(JComponent.WHEN_FOCUSED));
-    SwingUtilities.replaceUIActionMap(textComponent, getActionMap());
+    SwingUtilities.replaceUIActionMap(textComponent, textComponent.getActionMap());
+
+    InputMap focusInputMap = textComponent.getInputMap(JComponent.WHEN_FOCUSED);
+    InputMapUIResource parentInputMap = new InputMapUIResource();
+    ActionMap parentActionMap = new ActionMapUIResource();
+    Object keys[] = focusInputMap.allKeys();
+
+    for (int i = 0; i < keys.length; i++)
+      {
+        String act = (String) focusInputMap.get((KeyStroke) keys[i]);
+        Action[] actions = textComponent.getActions();
+        for (int j = 0; j < actions.length; j++)
+          {
+            Action currAction = actions[j];
+            if (currAction != null
+                && (currAction.getValue(Action.NAME).equals(act)))
+              parentActionMap.put(act, new ActionListenerProxy(currAction, act));
+          }
+        
+        parentInputMap.put(KeyStroke.getKeyStroke(((KeyStroke) keys[i]).getKeyCode(),
+                                                  convertModifiers(((KeyStroke) keys[i]).getModifiers())),
+                           act);
+        parentInputMap.put(KeyStroke.getKeyStroke(((KeyStroke) keys[i]).getKeyCode(),
+                                                  ((KeyStroke) keys[i]).getModifiers()),
+                           act);
+      }
+
+    parentInputMap.setParent(textComponent.getInputMap(JComponent.WHEN_FOCUSED).getParent());
+    parentActionMap.setParent(textComponent.getActionMap().getParent());
+    textComponent.getInputMap(JComponent.WHEN_FOCUSED).setParent(parentInputMap);
+    textComponent.getActionMap().setParent(parentActionMap);
+  }
+  
+  /**
+   * This class is used to mimic the behaviour of the JDK when registering
+   * keyboard actions. It is the same as the private class used in JComponent
+   * for the same reason. This class receives an action event and dispatches it
+   * to the true receiver after altering the actionCommand property of the
+   * event.
+   */
+  private static class ActionListenerProxy extends AbstractAction
+  {
+    ActionListener target;
+
+    String bindingCommandName;
+
+    public ActionListenerProxy(ActionListener li, String cmd)
+    {
+      target = li;
+      bindingCommandName = cmd;
+    }
+
+    public void actionPerformed(ActionEvent e)
+    {
+      ActionEvent derivedEvent = new ActionEvent(e.getSource(), e.getID(),
+                                                 bindingCommandName,
+                                                 e.getModifiers());
+      target.actionPerformed(derivedEvent);
+    }
+  }
+  
+  /**
+   * Converts the modifiers.
+   * 
+   * @param mod -
+   *          modifier to convert
+   * @returns the new modifier
+   */
+  private int convertModifiers(int mod)
+  {
+    if ((mod & KeyEvent.SHIFT_DOWN_MASK) != 0)
+      {
+        mod |= KeyEvent.SHIFT_MASK;
+        mod &= ~KeyEvent.SHIFT_DOWN_MASK;
+      }
+    if ((mod & KeyEvent.CTRL_DOWN_MASK) != 0)
+      {
+        mod |= KeyEvent.CTRL_MASK;
+        mod &= ~KeyEvent.CTRL_DOWN_MASK;
+      }
+    if ((mod & KeyEvent.META_DOWN_MASK) != 0)
+      {
+        mod |= KeyEvent.META_MASK;
+        mod &= ~KeyEvent.META_DOWN_MASK;
+      }
+    if ((mod & KeyEvent.ALT_DOWN_MASK) != 0)
+      {
+        mod |= KeyEvent.ALT_MASK;
+        mod &= ~KeyEvent.ALT_DOWN_MASK;
+      }
+    if ((mod & KeyEvent.ALT_GRAPH_DOWN_MASK) != 0)
+      {
+        mod |= KeyEvent.ALT_GRAPH_MASK;
+        mod &= ~KeyEvent.ALT_GRAPH_DOWN_MASK;
+      }
+    return mod;
   }
 
   /**
@@ -674,46 +774,6 @@
   }
 
   /**
-   * Returns the ActionMap to be installed on the text component.
-   *
-   * @return the ActionMap to be installed on the text component
-   */
-  // FIXME: The UIDefaults have no entries for .actionMap, so this should
-  // be handled somehow different.
-  ActionMap getActionMap()
-  {
-    String prefix = getPropertyPrefix();
-    ActionMap am = (ActionMap) UIManager.get(prefix + ".actionMap");
-    if (am == null)
-      {
-        am = createActionMap();
-        // FIXME: Putting something in the UIDefaults map is certainly wrong.
-        // However, the whole method seems wrong and must be replaced by
-        // something that is less wrong.
-        UIManager.put(prefix + ".actionMap", am);
-      }
-    return am;
-  }
-
-  /**
-   * Creates an ActionMap to be installed on the text component.
-   *
-   * @return an ActionMap to be installed on the text component
-   */
-  ActionMap createActionMap()
-  {
-    Action[] actions = textComponent.getActions();
-    ActionMap am = new ActionMapUIResource();
-    for (int i = 0; i < actions.length; ++i)
-      {
-        String name = (String) actions[i].getValue(Action.NAME);
-        if (name != null)
-          am.put(name, actions[i]);
-      }
-    return am;
-  }
-
-  /**
    * Uninstalls this TextUI from the text component.
    *
    * @param component the text component to uninstall the UI from
Index: javax/swing/text/JTextComponent.java
===================================================================
RCS file: /cvsroot/classpath/classpath/javax/swing/text/JTextComponent.java,v
retrieving revision 1.47
diff -u -r1.47 JTextComponent.java
--- javax/swing/text/JTextComponent.java	20 Dec 2005 22:42:04 -0000	1.47
+++ javax/swing/text/JTextComponent.java	21 Dec 2005 16:45:51 -0000
@@ -906,53 +906,16 @@
   public JTextComponent()
   {
     Keymap defkeymap = getKeymap(DEFAULT_KEYMAP);
-    boolean creatingKeymap = false;
     if (defkeymap == null)
       {
         defkeymap = addKeymap(DEFAULT_KEYMAP, null);
         defkeymap.setDefaultAction(new DefaultEditorKit.DefaultKeyTypedAction());
-        creatingKeymap = true;
       }
 
     setFocusable(true);
     setEditable(true);
     enableEvents(AWTEvent.KEY_EVENT_MASK);
     updateUI();
-    
-    // need to do this after updateUI()
-    if (creatingKeymap)
-      loadKeymap(
-                 defkeymap,
-                 new KeyBinding[] {
-                     new KeyBinding(KeyStroke.getKeyStroke(KeyEvent.VK_LEFT, 0),
-                                    DefaultEditorKit.backwardAction),
-                     new KeyBinding(KeyStroke.getKeyStroke(KeyEvent.VK_RIGHT, 0),
-                                    DefaultEditorKit.forwardAction),
-                     new KeyBinding(KeyStroke.getKeyStroke("typed \b"),
-                                    DefaultEditorKit.deletePrevCharAction),
-                     new KeyBinding(KeyStroke.getKeyStroke(KeyEvent.VK_X, 
-                                                           KeyEvent.CTRL_DOWN_MASK),
-                                    DefaultEditorKit.cutAction),
-                     new KeyBinding(KeyStroke.getKeyStroke(KeyEvent.VK_C, 
-                                                           KeyEvent.CTRL_DOWN_MASK),
-                                    DefaultEditorKit.copyAction),
-                     new KeyBinding(KeyStroke.getKeyStroke(KeyEvent.VK_V, 
-                                                           KeyEvent.CTRL_DOWN_MASK),
-                                    DefaultEditorKit.pasteAction),
-                     new KeyBinding(KeyStroke.getKeyStroke(KeyEvent.VK_LEFT, 
-                                                            KeyEvent.SHIFT_DOWN_MASK),
-                                     DefaultEditorKit.selectionBackwardAction),
-                     new KeyBinding(KeyStroke.getKeyStroke(KeyEvent.VK_RIGHT, 
-                                                           KeyEvent.SHIFT_DOWN_MASK),
-                                    DefaultEditorKit.selectionForwardAction),
-                     new KeyBinding(KeyStroke.getKeyStroke(KeyEvent.VK_HOME, 0),
-                                   DefaultEditorKit.beginLineAction),
-                     new KeyBinding(KeyStroke.getKeyStroke(KeyEvent.VK_END, 0),
-                                   DefaultEditorKit.endLineAction),
-                     new KeyBinding(KeyStroke.getKeyStroke("typed \u007f"),
-                                    DefaultEditorKit.deleteNextCharAction)
-                                    },
-                 getActions());
   }
 
   public void setDocument(Document newDoc)
_______________________________________________
Classpath-patches mailing list
[email protected]
http://lists.gnu.org/mailman/listinfo/classpath-patches

Reply via email to