# HG changeset patch # User Frank Benoit # Date 1207176015 -7200 # Node ID 7e823642932bdfbe4570ad892cb502833465cc5e # Parent cb935a3f6e90822cd7278719e1d6921b190162b5 MessageDialogWithToggle diff -r cb935a3f6e90 -r 7e823642932b dwtx/jface/dialogs/MessageDialogWithToggle.d --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/dwtx/jface/dialogs/MessageDialogWithToggle.d Thu Apr 03 00:40:15 2008 +0200 @@ -0,0 +1,713 @@ +/******************************************************************************* + * Copyright (c) 2000, 2006 IBM Corporation and others. + * All rights reserved. This program and the accompanying materials + * are made available under the terms of the Eclipse Public License v1.0 + * which accompanies this distribution, and is available at + * http://www.eclipse.org/legal/epl-v10.html + * + * Contributors: + * IBM Corporation - initial API and implementation + * Port to the D programming language: + * Frank Benoit + *******************************************************************************/ + +module dwtx.jface.dialogs.MessageDialogWithToggle; + +import dwtx.jface.dialogs.MessageDialog; +import dwtx.jface.dialogs.IDialogConstants; + +import dwt.DWT; +import dwt.events.SelectionAdapter; +import dwt.events.SelectionEvent; +import dwt.graphics.Image; +import dwt.layout.GridData; +import dwt.widgets.Button; +import dwt.widgets.Composite; +import dwt.widgets.Control; +import dwt.widgets.Shell; +import dwtx.jface.preference.IPreferenceStore; +import dwtx.jface.resource.JFaceResources; + +import dwt.dwthelper.utils; + +/** + *

+ * A message dialog which also allows the user to adjust a toggle setting. If a + * preference store is provided and the user selects the toggle, then the user's + * answer (yes/ok or no) will be persisted in the store. If no store is + * provided, then this information can be queried after the dialog closes. + *

+ *

+ * This type of dialog should be used whenever you want to user to be able to + * avoid being prompted in the future. It is strongly + * recommended that a cancel option be provided, so that the user has the option + * of making the decision at a later point in time. The semantic for a cancel + * button should be to cancel the operation (if it has not yet started), or stop + * the operation (if it has already started). + *

+ *

+ * It is the responsibility of the developer to provide a mechanism for the user + * to change this preference at some later point in time (e.g., through a + * preference page). + *

+ * + * @since 3.0 + */ +public class MessageDialogWithToggle : MessageDialog { + + /** + * The value of the preference when the user has asked that the answer to + * the question always be "okay" or "yes". + */ + public static const String ALWAYS = "always"; //$NON-NLS-1$ + + /** + * The value of the preference when the user has asked that the answer to + * the question always be "no". + */ + public static const String NEVER = "never"; //$NON-NLS-1$ + + /** + * The value of the preference when the user wishes to prompted for an + * answer every time the question is to be asked. + */ + public static const String PROMPT = "prompt"; //$NON-NLS-1$ + + /** + * Convenience method to open a standard error dialog. + * + * @param parent + * the parent shell of the dialog, or null if none + * @param title + * the dialog's title, or null if none + * @param message + * the message + * @param toggleMessage + * the message for the toggle control, or null for + * the default message + * @param toggleState + * the initial state for the toggle + * @param store + * the IPreference store in which the user's preference should be + * persisted; null if you don't want it persisted + * automatically. + * @param key + * the key to use when persisting the user's preference; + * null if you don't want it persisted. + * @return the dialog, after being closed by the user, which the client can + * only call getReturnCode() or + * getToggleState() + */ + public static MessageDialogWithToggle openError(Shell parent, String title, + String message, String toggleMessage, bool toggleState, + IPreferenceStore store, String key) { + MessageDialogWithToggle dialog = new MessageDialogWithToggle(parent, + title, null, // accept the default window icon + message, ERROR, [ IDialogConstants.OK_LABEL ], 0, // ok + // is + // the + // default + toggleMessage, toggleState); + dialog.prefStore = store; + dialog.prefKey = key; + dialog.open(); + return dialog; + } + + /** + * Convenience method to open a standard information dialog. + * + * @param parent + * the parent shell of the dialog, or null if none + * @param title + * the dialog's title, or null if none + * @param message + * the message + * @param toggleMessage + * the message for the toggle control, or null for + * the default message + * @param toggleState + * the initial state for the toggle + * @param store + * the IPreference store in which the user's preference should be + * persisted; null if you don't want it persisted + * automatically. + * @param key + * the key to use when persisting the user's preference; + * null if you don't want it persisted. + * + * @return the dialog, after being closed by the user, which the client can + * only call getReturnCode() or + * getToggleState() + */ + public static MessageDialogWithToggle openInformation(Shell parent, + String title, String message, String toggleMessage, + bool toggleState, IPreferenceStore store, String key) { + MessageDialogWithToggle dialog = new MessageDialogWithToggle(parent, + title, null, // accept the default window icon + message, INFORMATION, + [ IDialogConstants.OK_LABEL ], 0, // ok is the + // default + toggleMessage, toggleState); + dialog.prefStore = store; + dialog.prefKey = key; + dialog.open(); + return dialog; + } + + /** + * Convenience method to open a simple confirm (OK/Cancel) dialog. + * + * @param parent + * the parent shell of the dialog, or null if none + * @param title + * the dialog's title, or null if none + * @param message + * the message + * @param toggleMessage + * the message for the toggle control, or null for + * the default message + * @param toggleState + * the initial state for the toggle + * @param store + * the IPreference store in which the user's preference should be + * persisted; null if you don't want it persisted + * automatically. + * @param key + * the key to use when persisting the user's preference; + * null if you don't want it persisted. + * @return the dialog, after being closed by the user, which the client can + * only call getReturnCode() or + * getToggleState() + */ + public static MessageDialogWithToggle openOkCancelConfirm(Shell parent, + String title, String message, String toggleMessage, + bool toggleState, IPreferenceStore store, String key) { + MessageDialogWithToggle dialog = new MessageDialogWithToggle(parent, + title, null, // accept the default window icon + message, QUESTION, [ IDialogConstants.OK_LABEL, + IDialogConstants.CANCEL_LABEL ], 0, // OK is the default + toggleMessage, toggleState); + dialog.prefStore = store; + dialog.prefKey = key; + dialog.open(); + return dialog; + } + + /** + * Convenience method to open a standard warning dialog. + * + * @param parent + * the parent shell of the dialog, or null if none + * @param title + * the dialog's title, or null if none + * @param message + * the message + * @param toggleMessage + * the message for the toggle control, or null for + * the default message + * @param toggleState + * the initial state for the toggle + * @param store + * the IPreference store in which the user's preference should be + * persisted; null if you don't want it persisted + * automatically. + * @param key + * the key to use when persisting the user's preference; + * null if you don't want it persisted. + * @return the dialog, after being closed by the user, which the client can + * only call getReturnCode() or + * getToggleState() + */ + public static MessageDialogWithToggle openWarning(Shell parent, + String title, String message, String toggleMessage, + bool toggleState, IPreferenceStore store, String key) { + MessageDialogWithToggle dialog = new MessageDialogWithToggle(parent, + title, null, // accept the default window icon + message, WARNING, [ IDialogConstants.OK_LABEL ], + 0, // ok is the default + toggleMessage, toggleState); + dialog.prefStore = store; + dialog.prefKey = key; + dialog.open(); + return dialog; + } + + /** + * Convenience method to open a simple question Yes/No/Cancel dialog. + * + * @param parent + * the parent shell of the dialog, or null if none + * @param title + * the dialog's title, or null if none + * @param message + * the message + * @param toggleMessage + * the message for the toggle control, or null for + * the default message + * @param toggleState + * the initial state for the toggle + * @param store + * the IPreference store in which the user's preference should be + * persisted; null if you don't want it persisted + * automatically. + * @param key + * the key to use when persisting the user's preference; + * null if you don't want it persisted. + * @return the dialog, after being closed by the user, which the client can + * only call getReturnCode() or + * getToggleState() + */ + public static MessageDialogWithToggle openYesNoCancelQuestion(Shell parent, + String title, String message, String toggleMessage, + bool toggleState, IPreferenceStore store, String key) { + MessageDialogWithToggle dialog = new MessageDialogWithToggle(parent, + title, null, // accept the default window icon + message, QUESTION, [ IDialogConstants.YES_LABEL, + IDialogConstants.NO_LABEL, + IDialogConstants.CANCEL_LABEL ], 0, // YES is the + // default + toggleMessage, toggleState); + dialog.prefStore = store; + dialog.prefKey = key; + dialog.open(); + return dialog; + } + + /** + * Convenience method to open a simple Yes/No question dialog. + * + * @param parent + * the parent shell of the dialog, or null if none + * @param title + * the dialog's title, or null if none + * @param message + * the message + * @param toggleMessage + * the message for the toggle control, or null for + * the default message + * @param toggleState + * the initial state for the toggle + * @param store + * the IPreference store in which the user's preference should be + * persisted; null if you don't want it persisted + * automatically. + * @param key + * the key to use when persisting the user's preference; + * null if you don't want it persisted. + * + * @return the dialog, after being closed by the user, which the client can + * only call getReturnCode() or + * getToggleState() + */ + public static MessageDialogWithToggle openYesNoQuestion(Shell parent, + String title, String message, String toggleMessage, + bool toggleState, IPreferenceStore store, String key) { + MessageDialogWithToggle dialog = new MessageDialogWithToggle(parent, + title, null, // accept the default window icon + message, QUESTION, [ IDialogConstants.YES_LABEL, + IDialogConstants.NO_LABEL ], 0, // yes is the default + toggleMessage, toggleState); + dialog.prefStore = store; + dialog.prefKey = key; + dialog.open(); + return dialog; + } + + /** + * The key at which the toggle state should be stored within the + * preferences. This value may be null, which indicates that + * no preference should be updated automatically. It is then the + * responsibility of the user of this API to use the information from the + * toggle. Note: a prefStore is also needed. + */ + private String prefKey = null; + + /** + * The preference store which will be affected by the toggle button. This + * value may be null, which indicates that no preference + * should be updated automatically. It is then the responsibility of the + * user of this API to use the information from the toggle. Note: a + * prefKey is also needed. + */ + private IPreferenceStore prefStore = null; + + /** + * The toggle button (widget). This value is null until the + * dialog is created. + */ + private Button toggleButton = null; + + /** + * The message displayed to the user, with the toggle button. This is the + * text besides the toggle. If it is null, this means that + * the default text for the toggle should be used. + */ + private String toggleMessage; + + /** + * The initial selected state of the toggle. + */ + private bool toggleState; + + /** + * Creates a message dialog with a toggle. See the superclass constructor + * for info on the other parameters. + * + * @param parentShell + * the parent shell + * @param dialogTitle + * the dialog title, or null if none + * @param image + * the dialog title image, or null if none + * @param message + * the dialog message + * @param dialogImageType + * one of the following values: + * + * @param dialogButtonLabels + * an array of labels for the buttons in the button bar + * @param defaultIndex + * the index in the button label array of the default button + * @param toggleMessage + * the message for the toggle control, or null for + * the default message + * @param toggleState + * the initial state for the toggle + * + */ + public this(Shell parentShell, String dialogTitle, + Image image, String message, int dialogImageType, + String[] dialogButtonLabels, int defaultIndex, + String toggleMessage, bool toggleState) { + super(parentShell, dialogTitle, image, message, dialogImageType, + dialogButtonLabels, defaultIndex); + this.toggleMessage = toggleMessage; + this.toggleState = toggleState; + setButtonLabels(dialogButtonLabels); + } + + /** + * @see dwtx.jface.dialogs.Dialog#buttonPressed(int) + */ + protected void buttonPressed(int buttonId) { + super.buttonPressed(buttonId); + + if (buttonId !is IDialogConstants.CANCEL_ID && toggleState + && prefStore !is null && prefKey !is null) { + switch (buttonId) { + case IDialogConstants.YES_ID: + case IDialogConstants.YES_TO_ALL_ID: + case IDialogConstants.PROCEED_ID: + case IDialogConstants.OK_ID: + prefStore.setValue(prefKey, ALWAYS); + break; + case IDialogConstants.NO_ID: + case IDialogConstants.NO_TO_ALL_ID: + prefStore.setValue(prefKey, NEVER); + break; + } + } + } + + /** + * @see Dialog#createButtonBar(Composite) + */ + protected void createButtonsForButtonBar(Composite parent) { + String[] buttonLabels = getButtonLabels(); + Button[] buttons = new Button[buttonLabels.length]; + int defaultButtonIndex = getDefaultButtonIndex(); + + int suggestedId = IDialogConstants.INTERNAL_ID; + for (int i = 0; i < buttonLabels.length; i++) { + String label = buttonLabels[i]; + // get the JFace button ID that matches the label, or use the specified + // id if there is no match. + int id = mapButtonLabelToButtonID(label, suggestedId); + + // if the suggested id was used, increment the default for next use + if (id is suggestedId) { + suggestedId++; + } + + Button button = createButton(parent, id, label, + defaultButtonIndex is i); + buttons[i] = button; + + } + setButtons(buttons); + } + + /** + * @see Dialog#createDialogArea(Composite) + */ + protected Control createDialogArea(Composite parent) { + Composite dialogAreaComposite = cast(Composite) super + .createDialogArea(parent); + setToggleButton(createToggleButton(dialogAreaComposite)); + return dialogAreaComposite; + } + + /** + * Creates a toggle button without any text or state. The text and state + * will be created by createDialogArea. + * + * @param parent + * The composite in which the toggle button should be placed; + * must not be null. + * @return The added toggle button; never null. + */ + protected Button createToggleButton(Composite parent) { + Button button = new Button(parent, DWT.CHECK | DWT.LEFT); + + GridData data = new GridData(DWT.NONE); + data.horizontalSpan = 2; + button.setLayoutData(data); + button.setFont(parent.getFont()); + + button.addSelectionListener(new class SelectionAdapter { + Button button_; + this(){ button_=button; } + public void widgetSelected(SelectionEvent e) { + toggleState = button_.getSelection(); + } + + }); + + return button; + } + + /** + * Returns the toggle button. + * + * @return the toggle button + */ + protected Button getToggleButton() { + return toggleButton; + } + + /** + * An accessor for the current preference store for this dialog. + * + * @return The preference store; this value may be null if no + * preference is being used. + */ + public IPreferenceStore getPrefStore() { + return prefStore; + } + + /** + * An accessor for the current key of the toggle preference. + * + * @return The preference key; this value may be null if no + * preference is being used. + */ + public String getPrefKey() { + return prefKey; + } + + /** + * Returns the toggle state. This can be called even after the dialog is + * closed. + * + * @return true if the toggle button is checked, + * false if not + */ + public bool getToggleState() { + return toggleState; + } + + /** + * A mutator for the key of the preference to be modified by the toggle + * button. + * + * @param prefKey + * The prefKey to set. If this value is null, + * then no preference will be modified. + */ + public void setPrefKey(String prefKey) { + this.prefKey = prefKey; + } + + /** + * A mutator for the preference store to be modified by the toggle button. + * + * @param prefStore + * The prefStore to set. If this value is null, + * then no preference will be modified. + */ + public void setPrefStore(IPreferenceStore prefStore) { + this.prefStore = prefStore; + } + + /** + * A mutator for the button providing the toggle option. If the button + * exists, then it will automatically get the text set to the current toggle + * message, and its selection state set to the current selection state. + * + * @param button + * The button to use; must not be null. + */ + protected void setToggleButton(Button button) { + if (button is null) { + throw new NullPointerException( + "A message dialog with toggle may not have a null toggle button.");} //$NON-NLS-1$ + + if (!button.isDisposed()) { + String text; + if (toggleMessage is null) { + text = JFaceResources + .getString("MessageDialogWithToggle.defaultToggleMessage"); //$NON-NLS-1$ + } else { + text = toggleMessage; + } + button.setText(text); + button.setSelection(toggleState); + } + + this.toggleButton = button; + } + + /** + * A mutator for the text on the toggle button. The button will + * automatically get updated with the new text, if it exists. + * + * @param message + * The new text of the toggle button; if it is null, + * then used the default toggle message. + */ + protected void setToggleMessage(String message) { + this.toggleMessage = message; + + if ((toggleButton !is null) && (!toggleButton.isDisposed())) { + String text; + if (toggleMessage is null) { + text = JFaceResources + .getString("MessageDialogWithToggle.defaultToggleMessage"); //$NON-NLS-1$ + } else { + text = toggleMessage; + } + toggleButton.setText(text); + } + } + + /** + * A mutator for the state of the toggle button. This method will update the + * button, if it exists. + * + * @param toggleState + * The desired state of the toggle button (true + * means the toggle should be selected). + */ + public void setToggleState(bool toggleState) { + this.toggleState = toggleState; + + // Update the button, if it exists. + if ((toggleButton !is null) && (!toggleButton.isDisposed())) { + toggleButton.setSelection(toggleState); + } + } + + /** + * Attempt to find a standard JFace button id that matches the specified button + * label. If no match can be found, use the default id provided. + * + * @param buttonLabel the button label whose id is sought + * @param defaultId the id to use for the button if there is no standard id + * @return the id for the specified button label + */ + private int mapButtonLabelToButtonID(String buttonLabel, int defaultId) { + // Not pretty but does the job... + if (IDialogConstants.OK_LABEL.equals(buttonLabel)) { + return IDialogConstants.OK_ID; + } + + if (IDialogConstants.YES_LABEL.equals(buttonLabel)) { + return IDialogConstants.YES_ID; + } + + if (IDialogConstants.NO_LABEL.equals(buttonLabel)) { + return IDialogConstants.NO_ID; + } + + if (IDialogConstants.CANCEL_LABEL.equals(buttonLabel)) { + return IDialogConstants.CANCEL_ID; + } + + if (IDialogConstants.YES_TO_ALL_LABEL.equals(buttonLabel)) { + return IDialogConstants.YES_TO_ALL_ID; + } + + if (IDialogConstants.SKIP_LABEL.equals(buttonLabel)) { + return IDialogConstants.SKIP_ID; + } + + if (IDialogConstants.STOP_LABEL.equals(buttonLabel)) { + return IDialogConstants.STOP_ID; + } + + if (IDialogConstants.ABORT_LABEL.equals(buttonLabel)) { + return IDialogConstants.ABORT_ID; + } + + if (IDialogConstants.RETRY_LABEL.equals(buttonLabel)) { + return IDialogConstants.RETRY_ID; + } + + if (IDialogConstants.IGNORE_LABEL.equals(buttonLabel)) { + return IDialogConstants.IGNORE_ID; + } + + if (IDialogConstants.PROCEED_LABEL.equals(buttonLabel)) { + return IDialogConstants.PROCEED_ID; + } + + if (IDialogConstants.OPEN_LABEL.equals(buttonLabel)) { + return IDialogConstants.OPEN_ID; + } + + if (IDialogConstants.CLOSE_LABEL.equals(buttonLabel)) { + return IDialogConstants.CLOSE_ID; + } + + if (IDialogConstants.BACK_LABEL.equals(buttonLabel)) { + return IDialogConstants.BACK_ID; + } + + if (IDialogConstants.NEXT_LABEL.equals(buttonLabel)) { + return IDialogConstants.NEXT_ID; + } + + if (IDialogConstants.FINISH_LABEL.equals(buttonLabel)) { + return IDialogConstants.FINISH_ID; + } + + if (IDialogConstants.HELP_LABEL.equals(buttonLabel)) { + return IDialogConstants.HELP_ID; + } + + if (IDialogConstants.NO_TO_ALL_LABEL.equals(buttonLabel)) { + return IDialogConstants.NO_TO_ALL_ID; + } + + // No XXX_LABEL in IDialogConstants for these. Unlikely + // they would be used in a message dialog though. + // public int DETAILS_ID = 13; + // public int SELECT_ALL_ID = 18; + // public int DESELECT_ALL_ID = 19; + // public int SELECT_TYPES_ID = 20; + + return defaultId; + } +}