blob: a5c66c357dd0c83ea22a5560412be045eb01010c [file] [log] [blame]
/*******************************************************************************
* Copyright (c) 2000, 2010 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.gef.ui.actions;
import org.eclipse.jface.action.Action;
import org.eclipse.ui.IWorkbenchPart;
import org.eclipse.gef.Disposable;
import org.eclipse.gef.commands.Command;
import org.eclipse.gef.commands.CommandStack;
/**
* Base class for actions involving a WorkbenchPart. The workbench part is
* useful for obtaining data needed by the action. For example, selection can be
* obtained using the part's site. Anything can potentially be obtained using
* {@link org.eclipse.core.runtime.IAdaptable#getAdapter(java.lang.Class)}.
*/
public abstract class WorkbenchPartAction extends Action implements Disposable,
UpdateAction {
private IWorkbenchPart workbenchPart;
private boolean lazyEnablement = true;
/**
* Constructs a WorkbenchPartAction for the given part.
*
* @param part
* the workbench part
*/
public WorkbenchPartAction(IWorkbenchPart part) {
setWorkbenchPart(part);
init();
}
/**
* Constructs a WorkbenchPartAction for the given part and style.
*
* @param part
* the workbench part
* @param style
* one of <code>AS_PUSH_BUTTON</code>, <code>AS_CHECK_BOX</code>,
* <code>AS_DROP_DOWN_MENU</code>, <code>AS_RADIO_BUTTON</code>,
* and <code>AS_UNSPECIFIED</code>.
*/
public WorkbenchPartAction(IWorkbenchPart part, int style) {
super(null, style);
setWorkbenchPart(part);
init();
}
/**
* Calculates and returns the enabled state of this action.
*
* @return <code>true</code> if the action is enabled
*/
protected abstract boolean calculateEnabled();
/**
* Disposes the action when it is no longer needed.
*/
public void dispose() {
}
/**
* Executes the given {@link Command} using the command stack. The stack is
* obtained by calling {@link #getCommandStack()}, which uses
* <code>IAdapatable</code> to retrieve the stack from the workbench part.
*
* @param command
* the command to execute
*/
protected void execute(Command command) {
if (command == null || !command.canExecute())
return;
getCommandStack().execute(command);
}
/**
* Returns the editor's command stack. This is done by asking the workbench
* part for its CommandStack via
* {@link org.eclipse.core.runtime.IAdaptable#getAdapter(java.lang.Class)}.
*
* @return the command stack
*/
protected CommandStack getCommandStack() {
return (CommandStack) getWorkbenchPart().getAdapter(CommandStack.class);
}
/**
* Returns the workbench part given in the constructor
*
* @return the workbench part
*/
protected IWorkbenchPart getWorkbenchPart() {
return workbenchPart;
}
/**
* Initializes this action.
*/
protected void init() {
}
/**
* Returns <code>true</code> if the action is enabled. If the action
* determines enablemenu lazily, then {@link #calculateEnabled()} is always
* called. Otherwise, the enablement state set using
* {@link Action#setEnabled(boolean)} is returned.
*
* @see #setLazyEnablementCalculation(boolean)
* @return <code>true</code> if the action is enabled
*/
public boolean isEnabled() {
if (lazyEnablement)
setEnabled(calculateEnabled());
return super.isEnabled();
}
/**
* Refreshes the properties of this action.
*/
protected void refresh() {
setEnabled(calculateEnabled());
}
/**
* Sets lazy calculation of the isEnabled property. If this value is set to
* <code>true</code>, then the action will always use
* {@link #calculateEnabled()} whenever {@link #isEnabled()} is called.
* <P>
* Sometimes a value of <code>false</code> can be used to improve
* performance and reduce the number of times {@link #calculateEnabled()} is
* called. However, the client must then call the {@link #update()} method
* at the proper times to force the update of enablement.
* <P>
* Sometimes a value of <code>true</code> can be used to improve
* performance. If an <code>Action</code> only appears in a dynamic context
* menu, then there is no reason to agressively update its enablement status
* because the user cannot see the Action. Instead, its enablement only
* needs to be determined when asked for, or <i>lazily</i>.
* <P>
* The default value for this setting is <code>true</code>.
*
* @param value
* <code>true</code> if the enablement should be lazy
*/
public void setLazyEnablementCalculation(boolean value) {
lazyEnablement = value;
}
/**
* Sets the workbench part.
*
* @param part
* the workbench part
*/
protected void setWorkbenchPart(IWorkbenchPart part) {
workbenchPart = part;
}
/**
* @see UpdateAction#update()
*/
public void update() {
refresh();
}
}