package com.limegroup.gnutella.gui.options; import java.awt.Component; import java.awt.Dimension; import java.awt.Toolkit; import java.awt.event.WindowAdapter; import java.awt.event.WindowEvent; import java.io.IOException; import javax.swing.Box; import javax.swing.BoxLayout; import javax.swing.JComponent; import javax.swing.JDialog; import javax.swing.WindowConstants; import com.limegroup.gnutella.gui.GUIMediator; import com.limegroup.gnutella.gui.GUIUtils; import com.limegroup.gnutella.gui.PaddedPanel; import com.limegroup.gnutella.settings.SettingsHandler; import com.limegroup.gnutella.util.CommonUtils; /** * This class constructs the options tree on the left side of the options dialog. * <p> * The panes that show up when a leaf in the tree is selected are created * lazily in {@link OptionsPaneFactory}. * <p> * If you want to add a new {@link OptionsPane}, * add a call to {@link #addOption(String, String)} in the constructor here * and add the construction of the pane to * {@link OptionsPaneFactory#createOptionsPane(String)}. */ //2345678|012345678|012345678|012345678|012345678|012345678|012345678|012345678| public final class OptionsConstructor { /** * Handle to the top-level <tt>JDialog</tt window that contains all * of the other GUI components. */ private final JDialog DIALOG; /** * Constant for the default width of the options window. */ private final int OPTIONS_WIDTH = 600; /** * Constant for the default height of the options window. */ private final int OPTIONS_HEIGHT = 460; /** * Stored for convenience to allow using this in helper methods * during construction. */ private final OptionsTreeManager TREE_MANAGER; /** * Stored for convenience to allow using this in helper methods * during construction. */ private final OptionsPaneManager PANE_MANAGER; static final String SAVE_KEY = "OPTIONS_SAVE_MAIN_TITLE"; static final String SHARED_KEY = "OPTIONS_SHARED_MAIN_TITLE"; static final String SPEED_KEY = "OPTIONS_SPEED_MAIN_TITLE"; static final String DOWNLOAD_KEY = "OPTIONS_DOWNLOAD_MAIN_TITLE"; static final String UPLOAD_KEY = "OPTIONS_UPLOAD_MAIN_TITLE"; static final String UPLOAD_BASIC_KEY = "OPTIONS_UPLOAD_BASIC_MAIN_TITLE"; static final String UPLOAD_SLOTS_KEY = "OPTIONS_UPLOAD_SLOTS_MAIN_TITLE"; static final String CONNECTIONS_KEY = "OPTIONS_CONNECTIONS_MAIN_TITLE"; static final String SHUTDOWN_KEY = "OPTIONS_SHUTDOWN_MAIN_TITLE"; static final String UPDATE_KEY = "OPTIONS_UPDATE_MAIN_TITLE"; static final String CHAT_KEY = "OPTIONS_CHAT_MAIN_TITLE"; static final String PLAYER_KEY = "OPTIONS_PLAYER_MAIN_TITLE"; static final String STATUS_BAR_KEY = "OPTIONS_STATUS_BAR_MAIN_TITLE"; static final String ITUNES_KEY = "OPTIONS_ITUNES_MAIN_TITLE"; static final String ITUNES_IMPORT_KEY = "OPTIONS_ITUNES_PREFERENCE_MAIN_TITLE"; static final String ITUNES_DAAP_KEY = "OPTIONS_ITUNES_DAAP_MAIN_TITLE"; static final String POPUPS_KEY = "OPTIONS_POPUPS_MAIN_TITLE"; static final String BUGS_KEY = "OPTIONS_BUGS_MAIN_TITLE"; static final String APPS_KEY = "OPTIONS_APPS_MAIN_TITLE"; static final String SEARCH_KEY = "OPTIONS_SEARCH_MAIN_TITLE"; static final String SEARCH_LIMIT_KEY = "OPTIONS_SEARCH_LIMIT_MAIN_TITLE"; static final String SEARCH_QUALITY_KEY = "OPTIONS_SEARCH_QUALITY_MAIN_TITLE"; static final String SEARCH_SPEED_KEY = "OPTIONS_SEARCH_SPEED_MAIN_TITLE"; static final String CONTENT_FILTER_KEY = "OPTIONS_CONTENT_FILTER_MAIN_TITLE"; static final String SEARCH_JUNK_KEY = "OPTIONS_SEARCH_JUNK_MAIN_TITLE"; static final String FILTERS_KEY = "OPTIONS_FILTERS_MAIN_TITLE"; static final String RESULTS_KEY = "OPTIONS_RESULTS_MAIN_TITLE"; static final String MESSAGES_KEY = "OPTIONS_MESSAGES_MAIN_TITLE"; static final String ADVANCED_KEY = "OPTIONS_ADVANCED_MAIN_TITLE"; static final String PREFERENCING_KEY = "OPTIONS_PREFERENCING_MAIN_TITLE"; static final String FIREWALL_KEY = "OPTIONS_FIREWALL_MAIN_TITLE"; static final String GUI_KEY = "OPTIONS_GUI_MAIN_TITLE"; static final String AUTOCOMPLETE_KEY = "OPTIONS_AUTOCOMPLETE_MAIN_TITLE"; static final String STARTUP_KEY = "OPTIONS_STARTUP_MAIN_TITLE"; static final String PROXY_KEY = "OPTIONS_PROXY_MAIN_TITLE"; /** * The constructor create all of the options windows and their * components. * * @param treeManager the <tt>OptionsTreeManager</tt> instance to * use for constructing the main panels and * adding elements * @param paneManager the <tt>OptionsPaneManager</tt> instance to * use for constructing the main panels and * adding elements */ public OptionsConstructor(final OptionsTreeManager treeManager, final OptionsPaneManager paneManager) { TREE_MANAGER = treeManager; PANE_MANAGER = paneManager; final String title = GUIMediator.getStringResource("OPTIONS_TITLE"); final boolean shouldBeModal = !CommonUtils.isMacOSX(); DIALOG = new JDialog(GUIMediator.getAppFrame(), title, shouldBeModal); DIALOG.setDefaultCloseOperation(WindowConstants.DO_NOTHING_ON_CLOSE); GUIUtils.addHideAction((JComponent)DIALOG.getContentPane()); // make the window non-resizable only for operating systems // where we know this will not cause a problem if(CommonUtils.isWindows() || CommonUtils.isMacOSX()) { DIALOG.setResizable(false); } DIALOG.setSize(OPTIONS_WIDTH, OPTIONS_HEIGHT); // most Mac users expect changes to be saved when the window // is closed, so save them DIALOG.addWindowListener(new WindowAdapter() { public void windowClosing(WindowEvent e) { try { int answer = -1; if(OptionsMediator.instance().isDirty()) { answer = GUIMediator.showYesNoCancelMessage("OPTIONS_SAVE_ON_CLOSE"); if(answer == GUIMediator.YES_OPTION) { OptionsMediator.instance().applyOptions(); SettingsHandler.save(); } } if(answer != GUIMediator.CANCEL_OPTION) { DIALOG.dispose(); OptionsMediator.instance().disposeOptions(); } } catch(IOException ioe) { // nothing we should do here. a message should // have been displayed to the user with more // information } } }); PaddedPanel mainPanel = new PaddedPanel(); Box splitBox = new Box(BoxLayout.X_AXIS); Component treeComponent = TREE_MANAGER.getComponent(); Component paneComponent = PANE_MANAGER.getComponent(); splitBox.add(treeComponent); splitBox.add(paneComponent); mainPanel.add(splitBox); mainPanel.add(Box.createVerticalStrut(17)); mainPanel.add(new OptionsButtonPanel().getComponent()); DIALOG.getContentPane().add(mainPanel); addOption(OptionsMediator.ROOT_NODE_KEY, SAVE_KEY); addOption(OptionsMediator.ROOT_NODE_KEY, SHARED_KEY); addOption(OptionsMediator.ROOT_NODE_KEY, SPEED_KEY); addOption(OptionsMediator.ROOT_NODE_KEY, DOWNLOAD_KEY); // add the upload options group addGroupTreeNode(OptionsMediator.ROOT_NODE_KEY, UPLOAD_KEY); addOption(UPLOAD_KEY, UPLOAD_BASIC_KEY); addOption(UPLOAD_KEY, UPLOAD_SLOTS_KEY); addOption(OptionsMediator.ROOT_NODE_KEY, CONNECTIONS_KEY); addOption(OptionsMediator.ROOT_NODE_KEY, SHUTDOWN_KEY); addOption(OptionsMediator.ROOT_NODE_KEY, UPDATE_KEY); addOption(OptionsMediator.ROOT_NODE_KEY, CHAT_KEY); addOption(OptionsMediator.ROOT_NODE_KEY, PLAYER_KEY); addOption(OptionsMediator.ROOT_NODE_KEY, STATUS_BAR_KEY); addGroupTreeNode(OptionsMediator.ROOT_NODE_KEY, ITUNES_KEY); if (CommonUtils.isMacOSX()) { addOption(ITUNES_KEY, ITUNES_IMPORT_KEY); } addOption(ITUNES_KEY, ITUNES_DAAP_KEY); if (!CommonUtils.isWindows() && !CommonUtils.isAnyMac()) { addOption(OptionsMediator.ROOT_NODE_KEY, APPS_KEY); } addOption(OptionsMediator.ROOT_NODE_KEY, BUGS_KEY); addGroupTreeNode(OptionsMediator.ROOT_NODE_KEY, GUI_KEY); addOption(GUI_KEY, POPUPS_KEY); addOption(GUI_KEY, AUTOCOMPLETE_KEY); // add the search options group addGroupTreeNode(OptionsMediator.ROOT_NODE_KEY, SEARCH_KEY); addOption(SEARCH_KEY, SEARCH_LIMIT_KEY); addOption(SEARCH_KEY, SEARCH_QUALITY_KEY); addOption(SEARCH_KEY, SEARCH_SPEED_KEY); // add the filters options group addGroupTreeNode(OptionsMediator.ROOT_NODE_KEY, FILTERS_KEY); addOption(FILTERS_KEY, CONTENT_FILTER_KEY); addOption(FILTERS_KEY, SEARCH_JUNK_KEY); addOption(FILTERS_KEY, RESULTS_KEY); addOption(FILTERS_KEY, MESSAGES_KEY); // add the advanced options group addGroupTreeNode(OptionsMediator.ROOT_NODE_KEY, ADVANCED_KEY); addOption(ADVANCED_KEY, PREFERENCING_KEY); addOption(ADVANCED_KEY, FIREWALL_KEY); addOption(ADVANCED_KEY, PROXY_KEY); if (GUIUtils.shouldShowStartOnStartupWindow()) { addOption(ADVANCED_KEY, STARTUP_KEY); } PANE_MANAGER.show(SAVE_KEY); } /** * Adds a parent node to the tree. This node serves navigational * purposes only, and so has no corresponding <tt>OptionsPane</tt>. * This method allows for multiple tiers of parent nodes, not only * top-level parents. * * @param parentKey the key of the parent node to add this parent * node to * @param childKey the key of the new parent node that is a child of * the <tt>parentKey</tt> argument */ private final void addGroupTreeNode(final String parentKey, final String childKey) { TREE_MANAGER.addNode(parentKey, childKey, GUIMediator.getStringResource(childKey)); } /** * Adds the specified key and <tt>OptionsPane</tt> to current * set of options. This adds this <tt>OptionsPane</tt> to the set of * <tt>OptionsPane</tt>s the user can select. * * @param parentKey the key of the parent node to add the new node to * @param pane the new pane that also supplies the name of the node * in the tree */ private final void addOption(final String parentKey, final String childKey) { TREE_MANAGER.addNode(parentKey, childKey, GUIMediator.getStringResource(childKey)); } /** * Makes the options window either visible or not visible depending on the * boolean argument. * * @param visible <tt>boolean</tt> value specifying whether the options * window should be made visible or not visible * @param key the unique identifying key of the panel to show */ final void setOptionsVisible(boolean visible, final String key) { if(!visible) { DIALOG.dispose(); OptionsMediator.instance().disposeOptions(); } else { if(GUIMediator.isAppVisible()) DIALOG.setLocationRelativeTo(GUIMediator.getAppFrame()); else { Dimension screenSize = Toolkit.getDefaultToolkit().getScreenSize(); Dimension dialogSize = DIALOG.getSize(); DIALOG.setLocation((screenSize.width - dialogSize.width)/2, (screenSize.height - dialogSize.height)/2); } // initial tree selection if (key == null) TREE_MANAGER.setDefaultSelection(); else TREE_MANAGER.setSelection(key); DIALOG.setVisible(true); } } /** Returns if the Options Box is visible. * @return true if the Options Box is visible. */ public final boolean isOptionsVisible() { return DIALOG.isVisible(); } /** * Returns the main <tt>JDialog</tt> instance for the options window, * allowing other components to position themselves accordingly. * * @return the main options <tt>JDialog</tt> window */ JDialog getMainOptionsComponent() { return DIALOG; } }