import java.awt.event.ActionListener;
import java.awt.event.InputEvent;
import java.awt.event.KeyEvent;
+
import javax.swing.JButton;
-import javax.swing.JFrame;
+import javax.swing.JCheckBoxMenuItem;
import javax.swing.JMenu;
import javax.swing.JMenuBar;
import javax.swing.JMenuItem;
import javax.swing.KeyStroke;
import tim.prune.App;
+import tim.prune.Config;
import tim.prune.DataSubscriber;
+import tim.prune.FunctionLibrary;
+import tim.prune.GenericFunction;
import tim.prune.I18nManager;
-import tim.prune.browser.UrlGenerator;
+import tim.prune.UpdateMessageBroker;
import tim.prune.data.PhotoList;
import tim.prune.data.Selection;
import tim.prune.data.Track;
import tim.prune.data.TrackInfo;
+import tim.prune.function.RearrangeWaypointsFunction.Rearrange;
+import tim.prune.function.browser.UrlGenerator;
/**
* Class to manage the menu bar and tool bar,
*/
public class MenuManager implements DataSubscriber
{
- private JFrame _parent = null;
private App _app = null;
private Track _track = null;
private Selection _selection = null;
private PhotoList _photos = null;
// Menu items which need enabling/disabling
+ private JMenuItem _sendGpsItem = null;
private JMenuItem _saveItem = null;
private JMenuItem _exportKmlItem = null;
private JMenuItem _exportGpxItem = null;
private JMenuItem _editWaypointNameItem = null;
private JMenuItem _deletePointItem = null;
private JMenuItem _deleteRangeItem = null;
- private JMenuItem _deleteDuplicatesItem = null;
private JMenuItem _compressItem = null;
+ private JMenuItem _deleteMarkedPointsItem = null;
private JMenuItem _interpolateItem = null;
+ private JMenuItem _averageItem = null;
private JMenuItem _selectAllItem = null;
private JMenuItem _selectNoneItem = null;
private JMenuItem _selectStartItem = null;
private JMenuItem _selectEndItem = null;
+ private JMenuItem _findWaypointItem = null;
private JMenuItem _reverseItem = null;
private JMenuItem _addTimeOffsetItem = null;
+ private JMenuItem _addAltitudeOffsetItem = null;
private JMenuItem _mergeSegmentsItem = null;
private JMenu _rearrangeMenu = null;
private JMenuItem _cutAndMoveItem = null;
private JMenuItem _show3dItem = null;
private JMenu _browserMapMenu = null;
+ private JMenuItem _chartItem = null;
+ private JCheckBoxMenuItem _paceCheckbox = null;
+ private JMenuItem _getGpsiesItem = null;
+ private JMenuItem _distanceItem = null;
private JMenuItem _saveExifItem = null;
private JMenuItem _connectPhotoItem = null;
private JMenuItem _deletePhotoItem = null;
private JButton _selectEndButton = null;
private JButton _connectPhotoButton = null;
+ /** Array of key events */
+ private static final int[] KEY_EVENTS = {
+ KeyEvent.VK_A, KeyEvent.VK_B, KeyEvent.VK_C, KeyEvent.VK_D, KeyEvent.VK_E,
+ KeyEvent.VK_F, KeyEvent.VK_G, KeyEvent.VK_H, KeyEvent.VK_I, KeyEvent.VK_J,
+ KeyEvent.VK_K, KeyEvent.VK_L, KeyEvent.VK_M, KeyEvent.VK_N, KeyEvent.VK_O,
+ KeyEvent.VK_P, KeyEvent.VK_Q, KeyEvent.VK_R, KeyEvent.VK_S, KeyEvent.VK_T,
+ KeyEvent.VK_U, KeyEvent.VK_V, KeyEvent.VK_W, KeyEvent.VK_X, KeyEvent.VK_Y, KeyEvent.VK_Z};
+
/**
* Constructor
- * @param inParent parent object for dialogs
* @param inApp application to call on menu actions
* @param inTrackInfo track info object
*/
- public MenuManager(JFrame inParent, App inApp, TrackInfo inTrackInfo)
+ public MenuManager(App inApp, TrackInfo inTrackInfo)
{
- _parent = inParent;
_app = inApp;
_track = inTrackInfo.getTrack();
_selection = inTrackInfo.getSelection();
{
JMenuBar menubar = new JMenuBar();
JMenu fileMenu = new JMenu(I18nManager.getText("menu.file"));
+ setAltKey(fileMenu, "altkey.menu.file");
// Open file
JMenuItem openMenuItem = new JMenuItem(I18nManager.getText("menu.file.open"));
- openMenuItem.setAccelerator(KeyStroke.getKeyStroke(KeyEvent.VK_O, InputEvent.CTRL_DOWN_MASK));
+ setShortcut(openMenuItem, "shortcut.menu.file.open");
_openFileAction = new ActionListener() {
public void actionPerformed(ActionEvent e)
{
};
addPhotosMenuItem.addActionListener(_addPhotoAction);
fileMenu.add(addPhotosMenuItem);
- // Add photos
- JMenuItem loadFromGpsMenuItem = new JMenuItem(I18nManager.getText("menu.file.loadfromgps"));
- loadFromGpsMenuItem.addActionListener(new ActionListener() {
- public void actionPerformed(ActionEvent e)
- {
- _app.beginLoadFromGps();
- }
- });
+ fileMenu.addSeparator();
+ // Load from GPS
+ JMenuItem loadFromGpsMenuItem = makeMenuItem(FunctionLibrary.FUNCTION_GPSLOAD);
+ setShortcut(loadFromGpsMenuItem, "shortcut.menu.file.load");
fileMenu.add(loadFromGpsMenuItem);
+ // Send to GPS
+ _sendGpsItem = makeMenuItem(FunctionLibrary.FUNCTION_GPSSAVE);
+ _sendGpsItem.setEnabled(false);
+ fileMenu.add(_sendGpsItem);
fileMenu.addSeparator();
// Save
_saveItem = new JMenuItem(I18nManager.getText("menu.file.save"), KeyEvent.VK_S);
+ setShortcut(_saveItem, "shortcut.menu.file.save");
_saveAction = new ActionListener() {
public void actionPerformed(ActionEvent e)
{
_saveItem.setEnabled(false);
fileMenu.add(_saveItem);
// Export - Kml
- _exportKmlItem = new JMenuItem(I18nManager.getText("menu.file.exportkml"));
- _exportKmlItem.addActionListener(new ActionListener() {
- public void actionPerformed(ActionEvent e)
- {
- _app.exportKml();
- }
- });
+ _exportKmlItem = makeMenuItem(FunctionLibrary.FUNCTION_KMLEXPORT);
_exportKmlItem.setEnabled(false);
fileMenu.add(_exportKmlItem);
// Gpx
- _exportGpxItem = new JMenuItem(I18nManager.getText("menu.file.exportgpx"));
- _exportGpxItem.addActionListener(new ActionListener() {
- public void actionPerformed(ActionEvent e)
- {
- _app.exportGpx();
- }
- });
+ _exportGpxItem = makeMenuItem(FunctionLibrary.FUNCTION_GPXEXPORT);
_exportGpxItem.setEnabled(false);
fileMenu.add(_exportGpxItem);
// Pov
- _exportPovItem = new JMenuItem(I18nManager.getText("menu.file.exportpov"));
- _exportPovItem.addActionListener(new ActionListener() {
- public void actionPerformed(ActionEvent e)
- {
- _app.exportPov();
- }
- });
+ _exportPovItem = makeMenuItem(FunctionLibrary.FUNCTION_POVEXPORT);
_exportPovItem.setEnabled(false);
fileMenu.add(_exportPovItem);
fileMenu.addSeparator();
menubar.add(fileMenu);
// Edit menu
JMenu editMenu = new JMenu(I18nManager.getText("menu.edit"));
- editMenu.setMnemonic(KeyEvent.VK_E);
+ setAltKey(editMenu, "altkey.menu.edit");
_undoItem = new JMenuItem(I18nManager.getText("menu.edit.undo"));
+ setShortcut(_undoItem, "shortcut.menu.edit.undo");
_undoAction = new ActionListener() {
public void actionPerformed(ActionEvent e)
{
_editPointItem.addActionListener(_editPointAction);
_editPointItem.setEnabled(false);
editMenu.add(_editPointItem);
- _editWaypointNameItem = new JMenuItem(I18nManager.getText("menu.edit.editwaypointname"));
- _editWaypointNameItem.addActionListener(new ActionListener() {
- public void actionPerformed(ActionEvent e)
- {
- _app.editCurrentPointName();
- }
- });
+ _editWaypointNameItem = makeMenuItem(FunctionLibrary.FUNCTION_EDIT_WAYPOINT_NAME);
_editWaypointNameItem.setEnabled(false);
editMenu.add(_editWaypointNameItem);
_deletePointItem = new JMenuItem(I18nManager.getText("menu.edit.deletepoint"));
_deleteRangeItem.addActionListener(_deleteRangeAction);
_deleteRangeItem.setEnabled(false);
editMenu.add(_deleteRangeItem);
- _deleteDuplicatesItem = new JMenuItem(I18nManager.getText("menu.edit.deleteduplicates"));
- _deleteDuplicatesItem.addActionListener(new ActionListener() {
- public void actionPerformed(ActionEvent e)
- {
- _app.deleteDuplicates();
- }
- });
- _deleteDuplicatesItem.setEnabled(false);
- editMenu.add(_deleteDuplicatesItem);
- _compressItem = new JMenuItem(I18nManager.getText("menu.edit.compress"));
- _compressItem.addActionListener(new ActionListener() {
+ editMenu.addSeparator();
+ _compressItem = makeMenuItem(FunctionLibrary.FUNCTION_COMPRESS);
+ setShortcut(_compressItem, "shortcut.menu.edit.compress");
+ _compressItem.setEnabled(false);
+ editMenu.add(_compressItem);
+ _deleteMarkedPointsItem = new JMenuItem(I18nManager.getText("menu.edit.deletemarked"));
+ _deleteMarkedPointsItem.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e)
{
- _app.compressTrack();
+ _app.finishCompressTrack();
}
});
- _compressItem.setEnabled(false);
- editMenu.add(_compressItem);
+ _deleteMarkedPointsItem.setEnabled(false);
+ editMenu.add(_deleteMarkedPointsItem);
editMenu.addSeparator();
_interpolateItem = new JMenuItem(I18nManager.getText("menu.edit.interpolate"));
_interpolateItem.addActionListener(new ActionListener() {
});
_interpolateItem.setEnabled(false);
editMenu.add(_interpolateItem);
+ _averageItem = new JMenuItem(I18nManager.getText("menu.edit.average"));
+ _averageItem.addActionListener(new ActionListener() {
+ public void actionPerformed(ActionEvent e)
+ {
+ _app.averageSelection();
+ }
+ });
+ _averageItem.setEnabled(false);
+ editMenu.add(_averageItem);
_reverseItem = new JMenuItem(I18nManager.getText("menu.edit.reverse"));
_reverseItem.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e)
});
_reverseItem.setEnabled(false);
editMenu.add(_reverseItem);
- _addTimeOffsetItem = new JMenuItem(I18nManager.getText("menu.edit.addtimeoffset"));
- _addTimeOffsetItem.addActionListener(new ActionListener() {
- public void actionPerformed(ActionEvent e)
- {
- _app.beginAddTimeOffset();
- }
- });
+ _addTimeOffsetItem = makeMenuItem(FunctionLibrary.FUNCTION_ADD_TIME_OFFSET);
_addTimeOffsetItem.setEnabled(false);
editMenu.add(_addTimeOffsetItem);
+ _addAltitudeOffsetItem = makeMenuItem(FunctionLibrary.FUNCTION_ADD_ALTITUDE_OFFSET);
+ _addAltitudeOffsetItem.setEnabled(false);
+ editMenu.add(_addAltitudeOffsetItem);
_mergeSegmentsItem = new JMenuItem(I18nManager.getText("menu.edit.mergetracksegments"));
_mergeSegmentsItem.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e)
rearrangeStartItem.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e)
{
- _app.rearrangeWaypoints(App.REARRANGE_TO_START);
+ FunctionLibrary.FUNCTION_REARRANGE_WAYPOINTS.rearrangeWaypoints(Rearrange.TO_START);
}
});
rearrangeStartItem.setEnabled(true);
rearrangeEndItem.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e)
{
- _app.rearrangeWaypoints(App.REARRANGE_TO_END);
+ FunctionLibrary.FUNCTION_REARRANGE_WAYPOINTS.rearrangeWaypoints(Rearrange.TO_END);
}
});
rearrangeEndItem.setEnabled(true);
rearrangeNearestItem.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e)
{
- _app.rearrangeWaypoints(App.REARRANGE_TO_NEAREST);
+ FunctionLibrary.FUNCTION_REARRANGE_WAYPOINTS.rearrangeWaypoints(Rearrange.TO_NEAREST);
}
});
rearrangeNearestItem.setEnabled(true);
// Select menu
JMenu selectMenu = new JMenu(I18nManager.getText("menu.select"));
+ setAltKey(selectMenu, "altkey.menu.select");
_selectAllItem = new JMenuItem(I18nManager.getText("menu.select.all"));
+ setShortcut(_selectAllItem, "shortcut.menu.select.all");
_selectAllItem.setEnabled(false);
_selectAllItem.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e)
{
- _app.selectAll();
+ _selection.selectRange(0, _track.getNumPoints()-1);
}
});
selectMenu.add(_selectAllItem);
};
_selectEndItem.addActionListener(_selectEndAction);
selectMenu.add(_selectEndItem);
+ selectMenu.addSeparator();
+ _findWaypointItem = makeMenuItem(FunctionLibrary.FUNCTION_FIND_WAYPOINT);
+ _findWaypointItem.setEnabled(false);
+ selectMenu.add(_findWaypointItem);
menubar.add(selectMenu);
// Add view menu
JMenu viewMenu = new JMenu(I18nManager.getText("menu.view"));
- _show3dItem = new JMenuItem(I18nManager.getText("menu.view.show3d"));
- _show3dItem.addActionListener(new ActionListener() {
- public void actionPerformed(ActionEvent e)
- {
- _app.show3dWindow();
- }
- });
+ setAltKey(viewMenu, "altkey.menu.view");
+ _show3dItem = makeMenuItem(FunctionLibrary.FUNCTION_3D);
_show3dItem.setEnabled(false);
viewMenu.add(_show3dItem);
// browser submenu
}
});
_browserMapMenu.add(openMapsItem);
+ JMenuItem mapquestMapsItem = new JMenuItem(I18nManager.getText("menu.view.browser.mapquest"));
+ mapquestMapsItem.addActionListener(new ActionListener() {
+ public void actionPerformed(ActionEvent e)
+ {
+ _app.showExternalMap(UrlGenerator.MAP_SOURCE_MAPQUEST);
+ }
+ });
+ _browserMapMenu.add(mapquestMapsItem);
+ JMenuItem yahooMapsItem = new JMenuItem(I18nManager.getText("menu.view.browser.yahoo"));
+ yahooMapsItem.addActionListener(new ActionListener() {
+ public void actionPerformed(ActionEvent e)
+ {
+ _app.showExternalMap(UrlGenerator.MAP_SOURCE_YAHOO);
+ }
+ });
+ _browserMapMenu.add(yahooMapsItem);
viewMenu.add(_browserMapMenu);
+ // Charts
+ _chartItem = makeMenuItem(FunctionLibrary.FUNCTION_CHARTS);
+ _chartItem.setEnabled(false);
+ viewMenu.add(_chartItem);
+ // Distances
+ _distanceItem = makeMenuItem(FunctionLibrary.FUNCTION_DISTANCES);
+ _distanceItem.setEnabled(false);
+ viewMenu.add(_distanceItem);
+ // Get gpsies tracks
+ _getGpsiesItem = makeMenuItem(FunctionLibrary.FUNCTION_GET_GPSIES);
+ _getGpsiesItem.setEnabled(false);
+ viewMenu.add(_getGpsiesItem);
menubar.add(viewMenu);
// Add photo menu
JMenu photoMenu = new JMenu(I18nManager.getText("menu.photo"));
+ setAltKey(photoMenu, "altkey.menu.photo");
addPhotosMenuItem = new JMenuItem(I18nManager.getText("menu.file.addphotos"));
addPhotosMenuItem.addActionListener(_addPhotoAction);
photoMenu.add(addPhotosMenuItem);
photoMenu.add(_deletePhotoItem);
photoMenu.addSeparator();
// correlate all photos
- _correlatePhotosItem = new JMenuItem(I18nManager.getText("menu.photo.correlate"));
- _correlatePhotosItem.addActionListener(new ActionListener() {
- public void actionPerformed(ActionEvent e)
- {
- _app.beginCorrelatePhotos();
- }
- });
+ _correlatePhotosItem = makeMenuItem(FunctionLibrary.FUNCTION_CORRELATE_PHOTOS);
_correlatePhotosItem.setEnabled(false);
photoMenu.add(_correlatePhotosItem);
menubar.add(photoMenu);
- // Help menu
- JMenu helpMenu = new JMenu(I18nManager.getText("menu.help"));
- JMenuItem helpItem = new JMenuItem(I18nManager.getText("menu.help"));
- helpItem.addActionListener(new ActionListener() {
- public void actionPerformed(ActionEvent e)
- {
- _app.showHelp();
+ // Settings menu
+ JMenu settingsMenu = new JMenu(I18nManager.getText("menu.settings"));
+ setAltKey(settingsMenu, "altkey.menu.settings");
+ // Set the map background
+ JMenuItem mapBgItem = makeMenuItem(FunctionLibrary.FUNCTION_SET_MAP_BG);
+ settingsMenu.add(mapBgItem);
+ // Turn pace display on/off
+ _paceCheckbox = new JCheckBoxMenuItem(
+ I18nManager.getText("menu.settings.showpace"), false);
+ _paceCheckbox.addActionListener(new ActionListener() {
+ public void actionPerformed(ActionEvent e) {
+ Config.setConfigBoolean(Config.KEY_SHOW_PACE, _paceCheckbox.isSelected());
+ UpdateMessageBroker.informSubscribers();
}
});
+ settingsMenu.add(_paceCheckbox);
+ // Set kmz image size
+ JMenuItem setKmzImageSizeItem = makeMenuItem(FunctionLibrary.FUNCTION_SET_KMZ_IMAGE_SIZE);
+ settingsMenu.add(setKmzImageSizeItem);
+ // Set program paths
+ JMenuItem setPathsItem = makeMenuItem(FunctionLibrary.FUNCTION_SET_PATHS);
+ settingsMenu.add(setPathsItem);
+ settingsMenu.addSeparator();
+ // Save configuration
+ JMenuItem saveConfigMenuItem = makeMenuItem(FunctionLibrary.FUNCTION_SAVECONFIG);
+ settingsMenu.add(saveConfigMenuItem);
+ menubar.add(settingsMenu);
+
+ // Help menu
+ JMenu helpMenu = new JMenu(I18nManager.getText("menu.help"));
+ setAltKey(helpMenu, "altkey.menu.help");
+ JMenuItem helpItem = makeMenuItem(FunctionLibrary.FUNCTION_HELP);
+ setShortcut(helpItem, "shortcut.menu.help.help");
helpMenu.add(helpItem);
- JMenuItem aboutItem = new JMenuItem(I18nManager.getText("menu.help.about"));
- aboutItem.addActionListener(new ActionListener() {
- public void actionPerformed(ActionEvent e)
- {
- new AboutScreen(_parent).show();
- }
- });
+ JMenuItem showKeysItem = makeMenuItem(FunctionLibrary.FUNCTION_SHOW_KEYS);
+ helpMenu.add(showKeysItem);
+ JMenuItem aboutItem = makeMenuItem(FunctionLibrary.FUNCTION_ABOUT);
helpMenu.add(aboutItem);
- JMenuItem checkVersionItem = new JMenuItem(I18nManager.getText("menu.help.checkversion"));
- checkVersionItem.addActionListener(new ActionListener() {
- public void actionPerformed(ActionEvent e)
- {
- CheckVersionScreen.show(_parent);
- }
- });
+ JMenuItem checkVersionItem = makeMenuItem(FunctionLibrary.FUNCTION_CHECK_VERSION);
helpMenu.add(checkVersionItem);
menubar.add(helpMenu);
return menubar;
}
+ /**
+ * Convenience method for making a menu item using a function
+ * @param inFunction function
+ * @return menu item using localized name of function
+ */
+ private static JMenuItem makeMenuItem(GenericFunction inFunction)
+ {
+ JMenuItem item = new JMenuItem(I18nManager.getText(inFunction.getNameKey()));
+ item.addActionListener(new FunctionLauncher(inFunction));
+ return item;
+ }
+
+ /**
+ * Set the alt key for the given menu
+ * @param inMenu menu to set
+ * @param inKey key to lookup to get language-sensitive altkey
+ */
+ private static void setAltKey(JMenu inMenu, String inKey)
+ {
+ // Lookup the key in the properties
+ String altKey = I18nManager.getText(inKey);
+ if (altKey != null && altKey.length() == 1)
+ {
+ int code = altKey.charAt(0) - 'A';
+ if (code >= 0 && code < 26)
+ {
+ // Found a valid code between A and Z
+ inMenu.setMnemonic(KEY_EVENTS[code]);
+ }
+ }
+ }
+
+ /**
+ * Set the shortcut key for the given menu item
+ * @param inMenuItem menu item to set
+ * @param inKey key to lookup to get language-sensitive shortcut
+ */
+ private static void setShortcut(JMenuItem inMenuItem, String inKey)
+ {
+ // Lookup the key in the properties
+ String altKey = I18nManager.getText(inKey);
+ if (altKey != null && altKey.length() == 1)
+ {
+ int code = altKey.charAt(0) - 'A';
+ if (code >= 0 && code < 26)
+ {
+ // Found a valid code between A and Z
+ inMenuItem.setAccelerator(KeyStroke.getKeyStroke(KEY_EVENTS[code], InputEvent.CTRL_DOWN_MASK));
+ }
+ }
+ }
/**
* Create a JToolBar containing all toolbar buttons
public void informFileLoaded()
{
// save, undo, delete enabled
+ _sendGpsItem.setEnabled(true);
_saveItem.setEnabled(true);
_undoItem.setEnabled(true);
- _deleteDuplicatesItem.setEnabled(true);
_compressItem.setEnabled(true);
+ _deleteMarkedPointsItem.setEnabled(false);
}
{
boolean hasData = (_track != null && _track.getNumPoints() > 0);
// set functions which require data
+ _sendGpsItem.setEnabled(hasData);
_saveItem.setEnabled(hasData);
_saveButton.setEnabled(hasData);
_exportKmlItem.setEnabled(hasData);
_exportGpxItem.setEnabled(hasData);
_exportPovItem.setEnabled(hasData);
- _deleteDuplicatesItem.setEnabled(hasData);
_compressItem.setEnabled(hasData);
- _rearrangeMenu.setEnabled(hasData && _track.hasMixedData());
+ _deleteMarkedPointsItem.setEnabled(hasData && _track.hasMarkedPoints());
+ _rearrangeMenu.setEnabled(hasData && _track.hasTrackPoints() && _track.hasWaypoints());
_selectAllItem.setEnabled(hasData);
_selectNoneItem.setEnabled(hasData);
- if (_show3dItem != null)
- _show3dItem.setEnabled(hasData);
+ _show3dItem.setEnabled(hasData);
+ _chartItem.setEnabled(hasData);
_browserMapMenu.setEnabled(hasData);
+ _distanceItem.setEnabled(hasData);
+ _getGpsiesItem.setEnabled(hasData);
+ _findWaypointItem.setEnabled(hasData && _track.hasWaypoints());
// is undo available?
boolean hasUndo = !_app.getUndoStack().isEmpty();
_undoItem.setEnabled(hasUndo);
_deleteRangeButton.setEnabled(hasRange);
_interpolateItem.setEnabled(hasRange
&& (_selection.getEnd() - _selection.getStart()) == 1);
+ _averageItem.setEnabled(hasRange);
_mergeSegmentsItem.setEnabled(hasRange);
_reverseItem.setEnabled(hasRange);
_addTimeOffsetItem.setEnabled(hasRange);
+ _addAltitudeOffsetItem.setEnabled(hasRange);
// Is the currently selected point outside the current range?
_cutAndMoveItem.setEnabled(hasRange && hasPoint &&
(_selection.getCurrentPointIndex() < _selection.getStart()