001// License: GPL. For details, see LICENSE file.
002package org.openstreetmap.josm.gui.util;
003
004import javax.swing.ComponentInputMap;
005import javax.swing.InputMap;
006import javax.swing.JComponent;
007import javax.swing.KeyStroke;
008
009/**
010 * Make shortcuts from main window work in dialog windows.
011 *
012 * It's not possible to simply set component input map parent to be Main.contentPane.getInputMap
013 * because there is check in setParent that InputMap is for the same component.
014 * Yes, this is a hack.
015 * Another possibility would be simply copy InputMap, but that would require to
016 * keep copies synchronized when some shortcuts are changed later.
017 */
018public class RedirectInputMap extends ComponentInputMap {
019
020    private final InputMap target;
021
022    public RedirectInputMap(JComponent component, InputMap target) {
023        super(component);
024        this.target = target;
025    }
026
027    @Override
028    public Object get(KeyStroke keyStroke) {
029        return target.get(keyStroke);
030    }
031
032    @Override
033    public KeyStroke[] keys() {
034        return target.keys();
035    }
036
037    @Override
038    public int size() {
039        return target.size();
040    }
041
042    @Override
043    public KeyStroke[] allKeys() {
044        return target.allKeys();
045    }
046
047    @Override
048    public void put(KeyStroke keyStroke, Object actionMapKey) {
049        throw new UnsupportedOperationException();
050    }
051
052    @Override
053    public void remove(KeyStroke key) {
054        throw new UnsupportedOperationException();
055    }
056
057    @Override
058    public void clear() {
059        throw new UnsupportedOperationException();
060    }
061
062    public static void redirect(JComponent source, JComponent target) {
063        InputMap lastParent = source.getInputMap(JComponent.WHEN_IN_FOCUSED_WINDOW);
064        while (lastParent.getParent() != null) {
065            lastParent = lastParent.getParent();
066        }
067        lastParent.setParent(new RedirectInputMap(source, target.getInputMap(JComponent.WHEN_IN_FOCUSED_WINDOW)));
068        source.getActionMap().setParent(target.getActionMap());
069    }
070}