blob: fa669a33ecf313a664115b6d34e8928c8d779887 [file] [log] [blame]
/*******************************************************************************
* 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
*******************************************************************************/
package org.eclipse.ui.part;
import java.util.HashMap;
import java.util.Iterator;
import org.eclipse.core.runtime.Assert;
import org.eclipse.jface.action.Action;
import org.eclipse.jface.action.IAction;
import org.eclipse.jface.util.IPropertyChangeListener;
import org.eclipse.jface.util.PropertyChangeEvent;
import org.eclipse.jface.viewers.CellEditor;
import org.eclipse.swt.SWT;
import org.eclipse.swt.widgets.Control;
import org.eclipse.swt.widgets.Event;
import org.eclipse.swt.widgets.Listener;
import org.eclipse.ui.IActionBars;
import org.eclipse.ui.PlatformUI;
import org.eclipse.ui.actions.ActionFactory;
import org.eclipse.ui.internal.IWorkbenchHelpContextIds;
import org.eclipse.ui.internal.WorkbenchMessages;
/**
* Handles the redirection of the global actions Cut, Copy, Paste,
* Delete, Select All, Find, Undo and Redo to either the current
* inline cell editor or the part's supplied action handler.
* <p>
* This class may be instantiated; it is not intended to be subclassed.
* </p><p>
* Example usage:
* <pre>
* actionHandler = new CellEditorActionHandler(this.getViewSite().getActionBars());
* actionHandler.addCellEditor(textCellEditor1);
* actionHandler.addCellEditor(textCellEditor2);
* actionHandler.setSelectAllAction(selectAllAction);
* </pre>
* </p>
*/
public class CellEditorActionHandler {
private CutActionHandler cellCutAction = new CutActionHandler();
private CopyActionHandler cellCopyAction = new CopyActionHandler();
private PasteActionHandler cellPasteAction = new PasteActionHandler();
private DeleteActionHandler cellDeleteAction = new DeleteActionHandler();
private SelectAllActionHandler cellSelectAllAction = new SelectAllActionHandler();
private FindActionHandler cellFindAction = new FindActionHandler();
private UndoActionHandler cellUndoAction = new UndoActionHandler();
private RedoActionHandler cellRedoAction = new RedoActionHandler();
private IAction cutAction;
private IAction copyAction;
private IAction pasteAction;
private IAction deleteAction;
private IAction selectAllAction;
private IAction findAction;
private IAction undoAction;
private IAction redoAction;
private IPropertyChangeListener cutActionListener = new ActionEnabledChangeListener(
cellCutAction);
private IPropertyChangeListener copyActionListener = new ActionEnabledChangeListener(
cellCopyAction);
private IPropertyChangeListener pasteActionListener = new ActionEnabledChangeListener(
cellPasteAction);
private IPropertyChangeListener deleteActionListener = new ActionEnabledChangeListener(
cellDeleteAction);
private IPropertyChangeListener selectAllActionListener = new ActionEnabledChangeListener(
cellSelectAllAction);
private IPropertyChangeListener findActionListener = new ActionEnabledChangeListener(
cellFindAction);
private IPropertyChangeListener undoActionListener = new ActionEnabledChangeListener(
cellUndoAction);
private IPropertyChangeListener redoActionListener = new ActionEnabledChangeListener(
cellRedoAction);
private CellEditor activeEditor;
private IPropertyChangeListener cellListener = new CellChangeListener();
private Listener controlListener = new ControlListener();
private HashMap controlToEditor = new HashMap();
private class ControlListener implements Listener {
public void handleEvent(Event event) {
switch (event.type) {
case SWT.Activate:
activeEditor = (CellEditor) controlToEditor.get(event.widget);
if (activeEditor != null) {
activeEditor.addPropertyChangeListener(cellListener);
}
updateActionsEnableState();
break;
case SWT.Deactivate:
if (activeEditor != null) {
activeEditor.removePropertyChangeListener(cellListener);
}
activeEditor = null;
updateActionsEnableState();
break;
default:
break;
}
}
}
private class ActionEnabledChangeListener implements
IPropertyChangeListener {
private IAction actionHandler;
protected ActionEnabledChangeListener(IAction actionHandler) {
super();
this.actionHandler = actionHandler;
}
public void propertyChange(PropertyChangeEvent event) {
if (activeEditor != null) {
return;
}
if (event.getProperty().equals(IAction.ENABLED)) {
Boolean bool = (Boolean) event.getNewValue();
actionHandler.setEnabled(bool.booleanValue());
return;
}
// If the underlying action's text has changed, we need to
// change the text. See
// https://bugs.eclipse.org/bugs/show_bug.cgi?id=154410
if (event.getProperty().equals(IAction.TEXT)) {
String text = (String) event.getNewValue();
actionHandler.setText(text);
return;
}
if (event.getProperty().equals(IAction.TOOL_TIP_TEXT)) {
String text = (String) event.getNewValue();
actionHandler.setToolTipText(text);
return;
}
}
}
private class CellChangeListener implements IPropertyChangeListener {
public void propertyChange(PropertyChangeEvent event) {
if (activeEditor == null) {
return;
}
if (event.getProperty().equals(CellEditor.CUT)) {
cellCutAction.setEnabled(activeEditor.isCutEnabled());
return;
}
if (event.getProperty().equals(CellEditor.COPY)) {
cellCopyAction.setEnabled(activeEditor.isCopyEnabled());
return;
}
if (event.getProperty().equals(CellEditor.PASTE)) {
cellPasteAction.setEnabled(activeEditor.isPasteEnabled());
return;
}
if (event.getProperty().equals(CellEditor.DELETE)) {
cellDeleteAction.setEnabled(activeEditor.isDeleteEnabled());
return;
}
if (event.getProperty().equals(CellEditor.SELECT_ALL)) {
cellSelectAllAction.setEnabled(activeEditor
.isSelectAllEnabled());
return;
}
if (event.getProperty().equals(CellEditor.FIND)) {
cellFindAction.setEnabled(activeEditor.isFindEnabled());
return;
}
if (event.getProperty().equals(CellEditor.UNDO)) {
cellUndoAction.setEnabled(activeEditor.isUndoEnabled());
return;
}
if (event.getProperty().equals(CellEditor.REDO)) {
cellRedoAction.setEnabled(activeEditor.isRedoEnabled());
return;
}
}
}
private class CutActionHandler extends Action {
protected CutActionHandler() {
setId("CellEditorCutActionHandler");//$NON-NLS-1$
setEnabled(false);
PlatformUI.getWorkbench().getHelpSystem().setHelp(this, IWorkbenchHelpContextIds.CELL_CUT_ACTION);
}
public void runWithEvent(Event event) {
if (activeEditor != null) {
activeEditor.performCut();
return;
}
if (cutAction != null) {
cutAction.runWithEvent(event);
return;
}
}
public void updateEnabledState() {
if (activeEditor != null) {
setEnabled(activeEditor.isCutEnabled());
return;
}
if (cutAction != null) {
setEnabled(cutAction.isEnabled());
return;
}
setEnabled(false);
}
}
private class CopyActionHandler extends Action {
protected CopyActionHandler() {
setId("CellEditorCopyActionHandler");//$NON-NLS-1$
setEnabled(false);
PlatformUI.getWorkbench().getHelpSystem().setHelp(this, IWorkbenchHelpContextIds.CELL_COPY_ACTION);
}
public void runWithEvent(Event event) {
if (activeEditor != null) {
activeEditor.performCopy();
return;
}
if (copyAction != null) {
copyAction.runWithEvent(event);
return;
}
}
public void updateEnabledState() {
if (activeEditor != null) {
setEnabled(activeEditor.isCopyEnabled());
return;
}
if (copyAction != null) {
setEnabled(copyAction.isEnabled());
return;
}
setEnabled(false);
}
}
private class PasteActionHandler extends Action {
protected PasteActionHandler() {
setId("CellEditorPasteActionHandler");//$NON-NLS-1$
setEnabled(false);
PlatformUI.getWorkbench().getHelpSystem().setHelp(this, IWorkbenchHelpContextIds.CELL_PASTE_ACTION);
}
public void runWithEvent(Event event) {
if (activeEditor != null) {
activeEditor.performPaste();
return;
}
if (pasteAction != null) {
pasteAction.runWithEvent(event);
return;
}
}
public void updateEnabledState() {
if (activeEditor != null) {
setEnabled(activeEditor.isPasteEnabled());
return;
}
if (pasteAction != null) {
setEnabled(pasteAction.isEnabled());
return;
}
setEnabled(false);
}
}
private class DeleteActionHandler extends Action {
protected DeleteActionHandler() {
setId("CellEditorDeleteActionHandler");//$NON-NLS-1$
setEnabled(false);
PlatformUI.getWorkbench().getHelpSystem().setHelp(this, IWorkbenchHelpContextIds.CELL_DELETE_ACTION);
}
public void runWithEvent(Event event) {
if (activeEditor != null) {
activeEditor.performDelete();
return;
}
if (deleteAction != null) {
deleteAction.runWithEvent(event);
return;
}
}
public void updateEnabledState() {
if (activeEditor != null) {
setEnabled(activeEditor.isDeleteEnabled());
return;
}
if (deleteAction != null) {
setEnabled(deleteAction.isEnabled());
return;
}
setEnabled(false);
}
}
private class SelectAllActionHandler extends Action {
protected SelectAllActionHandler() {
setId("CellEditorSelectAllActionHandler");//$NON-NLS-1$
setEnabled(false);
PlatformUI.getWorkbench().getHelpSystem().setHelp(this, IWorkbenchHelpContextIds.CELL_SELECT_ALL_ACTION);
}
public void runWithEvent(Event event) {
if (activeEditor != null) {
activeEditor.performSelectAll();
return;
}
if (selectAllAction != null) {
selectAllAction.runWithEvent(event);
return;
}
}
public void updateEnabledState() {
if (activeEditor != null) {
setEnabled(activeEditor.isSelectAllEnabled());
return;
}
if (selectAllAction != null) {
setEnabled(selectAllAction.isEnabled());
return;
}
setEnabled(false);
}
}
private class FindActionHandler extends Action {
protected FindActionHandler() {
setId("CellEditorFindActionHandler");//$NON-NLS-1$
setEnabled(false);
PlatformUI.getWorkbench().getHelpSystem().setHelp(this, IWorkbenchHelpContextIds.CELL_FIND_ACTION);
}
public void runWithEvent(Event event) {
if (activeEditor != null) {
activeEditor.performFind();
return;
}
if (findAction != null) {
findAction.runWithEvent(event);
return;
}
}
public void updateEnabledState() {
if (activeEditor != null) {
setEnabled(activeEditor.isFindEnabled());
return;
}
if (findAction != null) {
setEnabled(findAction.isEnabled());
return;
}
setEnabled(false);
}
}
private class UndoActionHandler extends Action {
protected UndoActionHandler() {
setId("CellEditorUndoActionHandler");//$NON-NLS-1$
setEnabled(false);
PlatformUI.getWorkbench().getHelpSystem().setHelp(this, IWorkbenchHelpContextIds.CELL_UNDO_ACTION);
}
public void runWithEvent(Event event) {
if (activeEditor != null) {
activeEditor.performUndo();
return;
}
if (undoAction != null) {
undoAction.runWithEvent(event);
return;
}
}
public void updateEnabledState() {
if (activeEditor != null) {
setEnabled(activeEditor.isUndoEnabled());
setText(WorkbenchMessages.Workbench_undo);
setToolTipText(WorkbenchMessages.Workbench_undoToolTip);
return;
}
if (undoAction != null) {
setEnabled(undoAction.isEnabled());
setText(undoAction.getText());
setToolTipText(undoAction.getToolTipText());
return;
}
setEnabled(false);
}
}
private class RedoActionHandler extends Action {
protected RedoActionHandler() {
setId("CellEditorRedoActionHandler");//$NON-NLS-1$
setEnabled(false);
PlatformUI.getWorkbench().getHelpSystem().setHelp(this, IWorkbenchHelpContextIds.CELL_REDO_ACTION);
}
public void runWithEvent(Event event) {
if (activeEditor != null) {
activeEditor.performRedo();
return;
}
if (redoAction != null) {
redoAction.runWithEvent(event);
return;
}
}
public void updateEnabledState() {
if (activeEditor != null) {
setEnabled(activeEditor.isRedoEnabled());
setText(WorkbenchMessages.Workbench_redo);
setToolTipText(WorkbenchMessages.Workbench_redoToolTip);
return;
}
if (redoAction != null) {
setEnabled(redoAction.isEnabled());
setText(redoAction.getText());
setToolTipText(redoAction.getToolTipText());
return;
}
setEnabled(false);
}
}
/**
* Creates a <code>CellEditor</code> action handler
* for the global Cut, Copy, Paste, Delete, Select All,
* Find, Undo, and Redo of the action bar.
*
* @param actionBar the action bar to register global
* action handlers.
*/
public CellEditorActionHandler(IActionBars actionBar) {
super();
actionBar.setGlobalActionHandler(ActionFactory.CUT.getId(),
cellCutAction);
actionBar.setGlobalActionHandler(ActionFactory.COPY.getId(),
cellCopyAction);
actionBar.setGlobalActionHandler(ActionFactory.PASTE.getId(),
cellPasteAction);
actionBar.setGlobalActionHandler(ActionFactory.DELETE.getId(),
cellDeleteAction);
actionBar.setGlobalActionHandler(ActionFactory.SELECT_ALL.getId(),
cellSelectAllAction);
actionBar.setGlobalActionHandler(ActionFactory.FIND.getId(),
cellFindAction);
actionBar.setGlobalActionHandler(ActionFactory.UNDO.getId(),
cellUndoAction);
actionBar.setGlobalActionHandler(ActionFactory.REDO.getId(),
cellRedoAction);
}
/**
* Adds a <code>CellEditor</code> to the handler so that the
* Cut, Copy, Paste, Delete, Select All, Find, Undo, and Redo
* actions are redirected to it when active.
*
* @param editor the <code>CellEditor</code>
*/
public void addCellEditor(CellEditor editor) {
if (editor == null) {
return;
}
Control control = editor.getControl();
Assert.isNotNull(control);
controlToEditor.put(control, editor);
control.addListener(SWT.Activate, controlListener);
control.addListener(SWT.Deactivate, controlListener);
if (control.isFocusControl()) {
activeEditor = editor;
editor.addPropertyChangeListener(cellListener);
updateActionsEnableState();
}
}
/**
* Disposes of this action handler
*/
public void dispose() {
setCutAction(null);
setCopyAction(null);
setPasteAction(null);
setDeleteAction(null);
setSelectAllAction(null);
setFindAction(null);
setUndoAction(null);
setRedoAction(null);
Iterator itr = controlToEditor.keySet().iterator();
while (itr.hasNext()) {
Control control = (Control) itr.next();
if (!control.isDisposed()) {
control.removeListener(SWT.Activate, controlListener);
control.removeListener(SWT.Deactivate, controlListener);
}
}
controlToEditor.clear();
if (activeEditor != null) {
activeEditor.removePropertyChangeListener(cellListener);
}
activeEditor = null;
}
/**
* Removes a <code>CellEditor</code> from the handler
* so that the Cut, Copy, Paste, Delete, Select All, Find
* Undo, and Redo actions are no longer redirected to it.
*
* @param editor the <code>CellEditor</code>
*/
public void removeCellEditor(CellEditor editor) {
if (editor == null) {
return;
}
if (activeEditor == editor) {
activeEditor.removePropertyChangeListener(cellListener);
activeEditor = null;
}
Control control = editor.getControl();
if (control != null) {
controlToEditor.remove(control);
if (!control.isDisposed()) {
control.removeListener(SWT.Activate, controlListener);
control.removeListener(SWT.Deactivate, controlListener);
}
}
}
/**
* Sets the default <code>IAction</code> handler for the Copy
* action. This <code>IAction</code> is run only if no active
* cell editor control.
*
* @param action the <code>IAction</code> to run for the
* Copy action, or <code>null</code> if not interested.
*/
public void setCopyAction(IAction action) {
if (copyAction == action) {
return;
}
if (copyAction != null) {
copyAction.removePropertyChangeListener(copyActionListener);
}
copyAction = action;
if (copyAction != null) {
copyAction.addPropertyChangeListener(copyActionListener);
}
cellCopyAction.updateEnabledState();
}
/**
* Sets the default <code>IAction</code> handler for the Cut
* action. This <code>IAction</code> is run only if no active
* cell editor control.
*
* @param action the <code>IAction</code> to run for the
* Cut action, or <code>null</code> if not interested.
*/
public void setCutAction(IAction action) {
if (cutAction == action) {
return;
}
if (cutAction != null) {
cutAction.removePropertyChangeListener(cutActionListener);
}
cutAction = action;
if (cutAction != null) {
cutAction.addPropertyChangeListener(cutActionListener);
}
cellCutAction.updateEnabledState();
}
/**
* Sets the default <code>IAction</code> handler for the Delete
* action. This <code>IAction</code> is run only if no active
* cell editor control.
*
* @param action the <code>IAction</code> to run for the
* Delete action, or <code>null</code> if not interested.
*/
public void setDeleteAction(IAction action) {
if (deleteAction == action) {
return;
}
if (deleteAction != null) {
deleteAction.removePropertyChangeListener(deleteActionListener);
}
deleteAction = action;
if (deleteAction != null) {
deleteAction.addPropertyChangeListener(deleteActionListener);
}
cellDeleteAction.updateEnabledState();
}
/**
* Sets the default <code>IAction</code> handler for the Find
* action. This <code>IAction</code> is run only if no active
* cell editor control.
*
* @param action the <code>IAction</code> to run for the
* Find action, or <code>null</code> if not interested.
*/
public void setFindAction(IAction action) {
if (findAction == action) {
return;
}
if (findAction != null) {
findAction.removePropertyChangeListener(findActionListener);
}
findAction = action;
if (findAction != null) {
findAction.addPropertyChangeListener(findActionListener);
}
cellFindAction.updateEnabledState();
}
/**
* Sets the default <code>IAction</code> handler for the Paste
* action. This <code>IAction</code> is run only if no active
* cell editor control.
*
* @param action the <code>IAction</code> to run for the
* Paste action, or <code>null</code> if not interested.
*/
public void setPasteAction(IAction action) {
if (pasteAction == action) {
return;
}
if (pasteAction != null) {
pasteAction.removePropertyChangeListener(pasteActionListener);
}
pasteAction = action;
if (pasteAction != null) {
pasteAction.addPropertyChangeListener(pasteActionListener);
}
cellPasteAction.updateEnabledState();
}
/**
* Sets the default <code>IAction</code> handler for the Redo
* action. This <code>IAction</code> is run only if no active
* cell editor control.
*
* @param action the <code>IAction</code> to run for the
* Redo action, or <code>null</code> if not interested.
*/
public void setRedoAction(IAction action) {
if (redoAction == action) {
return;
}
if (redoAction != null) {
redoAction.removePropertyChangeListener(redoActionListener);
}
redoAction = action;
if (redoAction != null) {
redoAction.addPropertyChangeListener(redoActionListener);
}
cellRedoAction.updateEnabledState();
}
/**
* Sets the default <code>IAction</code> handler for the Select All
* action. This <code>IAction</code> is run only if no active
* cell editor control.
*
* @param action the <code>IAction</code> to run for the
* Select All action, or <code>null</code> if not interested.
*/
public void setSelectAllAction(IAction action) {
if (selectAllAction == action) {
return;
}
if (selectAllAction != null) {
selectAllAction
.removePropertyChangeListener(selectAllActionListener);
}
selectAllAction = action;
if (selectAllAction != null) {
selectAllAction.addPropertyChangeListener(selectAllActionListener);
}
cellSelectAllAction.updateEnabledState();
}
/**
* Sets the default <code>IAction</code> handler for the Undo
* action. This <code>IAction</code> is run only if no active
* cell editor control.
*
* @param action the <code>IAction</code> to run for the
* Undo action, or <code>null</code> if not interested.
*/
public void setUndoAction(IAction action) {
if (undoAction == action) {
return;
}
if (undoAction != null) {
undoAction.removePropertyChangeListener(undoActionListener);
}
undoAction = action;
if (undoAction != null) {
undoAction.addPropertyChangeListener(undoActionListener);
}
cellUndoAction.updateEnabledState();
}
/**
* Updates the enable state of the Cut, Copy,
* Paste, Delete, Select All, Find, Undo, and
* Redo action handlers
*/
private void updateActionsEnableState() {
cellCutAction.updateEnabledState();
cellCopyAction.updateEnabledState();
cellPasteAction.updateEnabledState();
cellDeleteAction.updateEnabledState();
cellSelectAllAction.updateEnabledState();
cellFindAction.updateEnabledState();
cellUndoAction.updateEnabledState();
cellRedoAction.updateEnabledState();
}
}