001    // License: GPL. For details, see LICENSE file.
002    package org.openstreetmap.josm.gui.layer;
003    
004    import static org.openstreetmap.josm.tools.I18n.tr;
005    
006    import java.awt.event.ActionEvent;
007    import java.awt.event.KeyEvent;
008    import java.lang.ref.WeakReference;
009    import java.util.List;
010    
011    import javax.swing.AbstractAction;
012    
013    import org.openstreetmap.josm.gui.dialogs.LayerListDialog;
014    import org.openstreetmap.josm.tools.MultikeyActionsHandler;
015    import org.openstreetmap.josm.tools.MultikeyShortcutAction;
016    import org.openstreetmap.josm.tools.Shortcut;
017    
018    public class JumpToMarkerActions {
019    
020        public interface JumpToMarkerLayer {
021            void jumpToNextMarker();
022            void jumpToPreviousMarker();
023        }
024    
025        private static JumpToNextMarker jumpToNextMarkerAction;
026        private static JumpToPreviousMarker jumpToPreviousMarkerAction;
027    
028        public static void initialize() {
029            jumpToNextMarkerAction = new JumpToNextMarker(null);
030            jumpToPreviousMarkerAction = new JumpToPreviousMarker(null);
031            MultikeyActionsHandler.getInstance().addAction(jumpToNextMarkerAction);
032            MultikeyActionsHandler.getInstance().addAction(jumpToPreviousMarkerAction);
033        }
034    
035        public static void unregisterActions() {
036            MultikeyActionsHandler.getInstance().removeAction(jumpToNextMarkerAction);
037            MultikeyActionsHandler.getInstance().removeAction(jumpToPreviousMarkerAction);
038        }
039    
040        public static final class JumpToNextMarker extends AbstractAction implements MultikeyShortcutAction {
041    
042            private final Layer layer;
043            private WeakReference<Layer> lastLayer;
044            private Shortcut multikeyShortcut;
045    
046            public JumpToNextMarker(JumpToMarkerLayer layer) {
047                multikeyShortcut = Shortcut.registerShortcut("core_multikey:nextMarker", tr("Multikey: {0}", tr("Next marker")),
048                        KeyEvent.VK_J, Shortcut.ALT_CTRL);
049                multikeyShortcut.setAccelerator(this);
050                putValue(SHORT_DESCRIPTION, tr("Jump to next marker"));
051                putValue(NAME, tr("Jump to next marker"));
052    
053                this.layer = (Layer)layer;
054            }
055    
056            @Override
057            public Shortcut getMultikeyShortcut() {
058                return multikeyShortcut;
059            }
060    
061            @Override
062            public void actionPerformed(ActionEvent e) {
063                execute(layer);
064            }
065    
066            @Override
067            public void executeMultikeyAction(int index, boolean repeat) {
068                Layer l = LayerListDialog.getLayerForIndex(index);
069                if (l != null) {
070                    if (l instanceof JumpToMarkerLayer) {
071                        execute(l);
072                    }
073                } else if (repeat && lastLayer != null) {
074                    l = lastLayer.get();
075                    if (LayerListDialog.isLayerValid(l)) {
076                        execute(l);
077                    }
078                }
079            }
080    
081            private void execute(Layer l) {
082                ((JumpToMarkerLayer)l).jumpToNextMarker();
083                lastLayer = new WeakReference<Layer>(l);
084            }
085    
086            @Override
087            public List<MultikeyInfo> getMultikeyCombinations() {
088                return LayerListDialog.getLayerInfoByClass(JumpToMarkerLayer.class);
089            }
090    
091            @Override
092            public MultikeyInfo getLastMultikeyAction() {
093                if (lastLayer != null)
094                    return LayerListDialog.getLayerInfo(lastLayer.get());
095                else
096                    return null;
097            }
098    
099        }
100    
101        public static final class JumpToPreviousMarker extends AbstractAction implements MultikeyShortcutAction {
102    
103            private WeakReference<Layer> lastLayer;
104            private final Layer layer;
105            private Shortcut multikeyShortcut;
106    
107            public JumpToPreviousMarker(JumpToMarkerLayer layer) {
108                this.layer = (Layer)layer;
109    
110                multikeyShortcut = Shortcut.registerShortcut("core_multikey:previousMarker", tr("Multikey: {0}", tr("Previos marker")),
111                        KeyEvent.VK_P, Shortcut.ALT_CTRL);
112                multikeyShortcut.setAccelerator(this);
113                putValue(SHORT_DESCRIPTION, tr("Jump to previous marker"));
114                putValue(NAME, tr("Jump to previous marker"));
115            }
116    
117            @Override
118            public Shortcut getMultikeyShortcut() {
119                return multikeyShortcut;
120            }
121    
122            @Override
123            public void actionPerformed(ActionEvent e) {
124                execute(layer);
125            }
126    
127            @Override
128            public void executeMultikeyAction(int index, boolean repeat) {
129                Layer l = LayerListDialog.getLayerForIndex(index);
130                if (l != null) {
131                    if (l instanceof JumpToMarkerLayer) {
132                        execute(l);
133                    }
134                } else if (repeat && lastLayer != null) {
135                    l = lastLayer.get();
136                    if (LayerListDialog.isLayerValid(l)) {
137                        execute(l);
138                    }
139                }
140            }
141    
142            private void execute(Layer l) {
143                ((JumpToMarkerLayer) l).jumpToPreviousMarker();
144                lastLayer = new WeakReference<Layer>(l);
145            }
146    
147            @Override
148            public List<MultikeyInfo> getMultikeyCombinations() {
149                return LayerListDialog.getLayerInfoByClass(JumpToMarkerLayer.class);
150            }
151    
152            @Override
153            public MultikeyInfo getLastMultikeyAction() {
154                if (lastLayer != null)
155                    return LayerListDialog.getLayerInfo(lastLayer.get());
156                else
157                    return null;
158            }
159        }
160    }