# HG changeset patch # Parent 2dd92128839ef60275afe6c3da86a5a9e0892c53 # User Jesse Glick #206093: allow an @ActionRegistration to be explicitly marked lazy or eager. diff --git a/ant.debugger/src/org/netbeans/modules/ant/debugger/RunTargetsAction.java b/ant.debugger/src/org/netbeans/modules/ant/debugger/RunTargetsAction.java --- a/ant.debugger/src/org/netbeans/modules/ant/debugger/RunTargetsAction.java +++ b/ant.debugger/src/org/netbeans/modules/ant/debugger/RunTargetsAction.java @@ -86,7 +86,7 @@ * undocumented targets. */ @ActionID(id = "org.netbeans.modules.ant.debugger.RunTargetsAction", category = "Build") -@ActionRegistration(displayName = "#LBL_run_targets_action") +@ActionRegistration(displayName = "#LBL_run_targets_action", lazy=false) @ActionReference(path = "Loaders/text/x-ant+xml/Actions", position = 300) public final class RunTargetsAction extends SystemAction implements ContextAwareAction { diff --git a/ant.freeform/src/org/netbeans/modules/ant/freeform/Actions.java b/ant.freeform/src/org/netbeans/modules/ant/freeform/Actions.java --- a/ant.freeform/src/org/netbeans/modules/ant/freeform/Actions.java +++ b/ant.freeform/src/org/netbeans/modules/ant/freeform/Actions.java @@ -493,7 +493,7 @@ } @ActionID(id = "org.netbeans.modules.ant.freeform.Actions$Custom", category = "Project") - @ActionRegistration(displayName = "Custom Freeform Actions") // should not be displayed in UI anyway + @ActionRegistration(displayName = "Custom Freeform Actions", lazy=false) // should not be displayed in UI anyway @ActionReference(position = 300, path = "Projects/org-netbeans-modules-ant-freeform/Actions") public static final class Custom extends AbstractAction implements ContextAwareAction { public Custom() { diff --git a/apisupport.installer.maven/src/org/netbeans/modules/apisupport/installer/maven/actions/BuildInstallersAction.java b/apisupport.installer.maven/src/org/netbeans/modules/apisupport/installer/maven/actions/BuildInstallersAction.java --- a/apisupport.installer.maven/src/org/netbeans/modules/apisupport/installer/maven/actions/BuildInstallersAction.java +++ b/apisupport.installer.maven/src/org/netbeans/modules/apisupport/installer/maven/actions/BuildInstallersAction.java @@ -88,7 +88,7 @@ * @author Dmitry Lipin */ @ActionID(id = "org.netbeans.modules.apisupport.installer.maven.actions.BuildInstallersAction", category = "Project") -@ActionRegistration(displayName = "#CTL_BuildInstallers") +@ActionRegistration(displayName = "#CTL_BuildInstallers", lazy=false) @ActionReference(position = 1290, path = "Projects/org-netbeans-modules-maven/Actions") public final class BuildInstallersAction extends AbstractAction implements ContextAwareAction { diff --git a/apisupport.installer/src/org/netbeans/modules/apisupport/installer/actions/BuildInstallersAction.java b/apisupport.installer/src/org/netbeans/modules/apisupport/installer/actions/BuildInstallersAction.java --- a/apisupport.installer/src/org/netbeans/modules/apisupport/installer/actions/BuildInstallersAction.java +++ b/apisupport.installer/src/org/netbeans/modules/apisupport/installer/actions/BuildInstallersAction.java @@ -86,7 +86,7 @@ import org.openide.util.Utilities; @ActionID(id = "org.netbeans.modules.apisupport.installer.actions.BuildInstallersAction", category = "Project") -@ActionRegistration(displayName = "#CTL_BuildInstallers") +@ActionRegistration(displayName = "#CTL_BuildInstallers", /* XXX might work to be context action on List */ lazy=false) @ActionReference(position = 1, path = "Projects/org-netbeans-modules-apisupport-project-suite/Actions") public final class BuildInstallersAction extends AbstractAction implements ContextAwareAction { diff --git a/apisupport.refactoring/src/org/netbeans/modules/apisupport/hints/ActionRegistrationHinter.java b/apisupport.refactoring/src/org/netbeans/modules/apisupport/hints/ActionRegistrationHinter.java --- a/apisupport.refactoring/src/org/netbeans/modules/apisupport/hints/ActionRegistrationHinter.java +++ b/apisupport.refactoring/src/org/netbeans/modules/apisupport/hints/ActionRegistrationHinter.java @@ -52,10 +52,7 @@ import java.util.Map; import java.util.concurrent.Callable; import javax.lang.model.element.Element; -import javax.lang.model.element.ElementKind; -import javax.lang.model.element.ExecutableElement; import javax.lang.model.element.TypeElement; -import javax.lang.model.type.TypeMirror; import org.netbeans.api.java.source.GeneratorUtilities; import org.netbeans.api.java.source.TreeMaker; import org.netbeans.api.java.source.WorkingCopy; @@ -75,15 +72,6 @@ @ServiceProvider(service=Hinter.class) public class ActionRegistrationHinter implements Hinter { - private static final String[] EAGER_INTERFACES = { - "org.openide.util.actions.Presenter.Menu", - "org.openide.util.actions.Presenter.Toolbar", - "org.openide.util.actions.Presenter.Popup", - "org.openide.util.ContextAwareAction", - "org.openide.awt.DynamicMenuContent" - }; - - @Messages({"# {0} - class or method return type", "ActionRegistrationHinter.not_presenter=You cannot use @ActionRegistration on the eager action {0} unless it is assignable to ContextAwareAction, DynamicMenuContent, or some Presenter.* interface."}) public @Override void process(final Context ctx) throws Exception { final FileObject file = ctx.file(); if (!file.isData() || !file.hasExt("instance")) { @@ -96,7 +84,7 @@ if (!annotationsAvailable(ctx)) { return null; } - ctx.findAndModifyDeclaration(file.getAttribute("literal:delegate"), new RegisterAction(ctx)); + ctx.findAndModifyDeclaration(file.getAttribute("literal:delegate"), new RegisterAction(ctx, false)); return null; } }); @@ -126,29 +114,7 @@ action = "new:" + file.getName().replace('-', '.'); } } - ctx.findAndModifyDeclaration(action, new RegisterAction(ctx) { - public @Override void run(WorkingCopy wc, Element declaration, ModifiersTree modifiers) throws Exception { - TypeMirror type; - if (declaration.getKind() == ElementKind.CLASS) { - type = ((TypeElement) declaration).asType(); - } else { - type = ((ExecutableElement) declaration).getReturnType(); - } - boolean ok = false; - for (String xface : EAGER_INTERFACES) { - TypeElement xfaceEl = wc.getElements().getTypeElement(xface); - if (xfaceEl != null && wc.getTypes().isAssignable(type, xfaceEl.asType())) { - ok = true; - break; - } - } - if (!ok) { - DialogDisplayer.getDefault().notify(new Message(ActionRegistrationHinter_not_presenter(type), NotifyDescriptor.WARNING_MESSAGE)); - return; - } - super.run(wc, declaration, modifiers); - } - }); + ctx.findAndModifyDeclaration(action, new RegisterAction(ctx, true)); return null; } }); @@ -168,9 +134,11 @@ private static class RegisterAction implements Context.ModifyDeclarationTask { private final Context ctx; + private final boolean eager; - RegisterAction(Context ctx) { + RegisterAction(Context ctx, boolean eager) { this.ctx = ctx; + this.eager = eager; } public @Override void run(WorkingCopy wc, Element declaration, ModifiersTree modifiers) throws Exception { @@ -192,6 +160,11 @@ params.put("iconInMenu", !((Boolean) noIconInMenu)); } params.put("asynchronous", file.getAttribute("asynchronous")); + if (eager) { + params.put("lazy", false); + } else { + // XXX specify lazy=true if implements one of the 5 specials even though using Actions.* factory (but probably rare) + } nue = ctx.addAnnotation(wc, nue, "org.openide.awt.ActionRegistration", null, params); ctx.delete(file); TreeMaker make = wc.getTreeMaker(); diff --git a/core.ui/src/org/netbeans/core/ui/options/filetypes/OpenAsAction.java b/core.ui/src/org/netbeans/core/ui/options/filetypes/OpenAsAction.java --- a/core.ui/src/org/netbeans/core/ui/options/filetypes/OpenAsAction.java +++ b/core.ui/src/org/netbeans/core/ui/options/filetypes/OpenAsAction.java @@ -67,7 +67,7 @@ * @author Jiri Skrivanek */ @ActionID(id = "org.netbeans.core.ui.options.filetypes.OpenAsAction", category = "Edit") -@ActionRegistration(displayName = "#OpenAsAction.name") +@ActionRegistration(displayName = "#OpenAsAction.name", /* XXX might work to be context action on DataObject */ lazy=false) @ActionReference(path = "Loaders/content/unknown/Actions", position = 150) public final class OpenAsAction extends NodeAction { diff --git a/core.ui/src/org/netbeans/core/ui/sysopen/SystemOpenAction.java b/core.ui/src/org/netbeans/core/ui/sysopen/SystemOpenAction.java --- a/core.ui/src/org/netbeans/core/ui/sysopen/SystemOpenAction.java +++ b/core.ui/src/org/netbeans/core/ui/sysopen/SystemOpenAction.java @@ -71,7 +71,7 @@ * @author Jesse Glick */ @ActionID(id = "org.netbeans.core.ui.sysopen.SystemOpenAction", category = "Edit") -@ActionRegistration(displayName = "#CTL_SystemOpenAction") +@ActionRegistration(displayName = "#CTL_SystemOpenAction", lazy=false) @ActionReference(path = "Loaders/content/unknown/Actions", position = 200) public final class SystemOpenAction extends AbstractAction implements ContextAwareAction { diff --git a/favorites/src/org/netbeans/modules/favorites/Actions.java b/favorites/src/org/netbeans/modules/favorites/Actions.java --- a/favorites/src/org/netbeans/modules/favorites/Actions.java +++ b/favorites/src/org/netbeans/modules/favorites/Actions.java @@ -93,7 +93,7 @@ } @ActionID(id = "org.netbeans.modules.favorites.Add", category = "Window") - @ActionRegistration(displayName = "#ACT_Add") + @ActionRegistration(displayName = "#ACT_Add", lazy=false) @ActionReference(position = 300, path = "UI/ToolActions/Files") public static ContextAwareAction add() { return Add.getDefault(); } @@ -104,7 +104,7 @@ public static Action remove () { return Remove.getDefault(); } @ActionID(id = "org.netbeans.modules.favorites.Select", category = "Window/SelectDocumentNode") - @ActionRegistration(displayName = "#ACT_Select_Main_Menu") + @ActionRegistration(displayName = "#ACT_Select_Main_Menu", lazy=false) @ActionReference(position = 2800, name = "org-netbeans-modules-favorites-SelectInFavorites", path = "Menu/GoTo") public static ContextAwareAction select () { return Select.getDefault(); } diff --git a/hudson/src/org/netbeans/modules/hudson/ui/actions/PersistInstanceAction.java b/hudson/src/org/netbeans/modules/hudson/ui/actions/PersistInstanceAction.java --- a/hudson/src/org/netbeans/modules/hudson/ui/actions/PersistInstanceAction.java +++ b/hudson/src/org/netbeans/modules/hudson/ui/actions/PersistInstanceAction.java @@ -60,7 +60,7 @@ import static org.netbeans.modules.hudson.ui.actions.Bundle.*; @ActionID(category="Team", id="org.netbeans.modules.hudson.ui.actions.PersistInstanceAction") -@ActionRegistration(displayName="#LBL_Persist_Instance", iconInMenu=false) +@ActionRegistration(displayName="#LBL_Persist_Instance", iconInMenu=false, lazy=false) @ActionReference(path=HudsonInstance.ACTION_PATH, position=700) @Messages("LBL_Persist_Instance=&Persist") // XXX cannot just use List ctor: must be disabled when context menu created, so must be eager diff --git a/hudson/src/org/netbeans/modules/hudson/ui/actions/SynchronizeAction.java b/hudson/src/org/netbeans/modules/hudson/ui/actions/SynchronizeAction.java --- a/hudson/src/org/netbeans/modules/hudson/ui/actions/SynchronizeAction.java +++ b/hudson/src/org/netbeans/modules/hudson/ui/actions/SynchronizeAction.java @@ -61,7 +61,7 @@ import org.openide.util.NbBundle.Messages; @ActionID(category="Team", id="org.netbeans.modules.hudson.ui.actions.SynchronizeAction") -@ActionRegistration(displayName="#LBL_SynchronizeAction", iconInMenu=false) +@ActionRegistration(displayName="#LBL_SynchronizeAction", iconInMenu=false, lazy=false) @ActionReference(path=HudsonInstance.ACTION_PATH, position=500) @Messages("LBL_SynchronizeAction=&Synchronize") public class SynchronizeAction extends AbstractAction implements ContextAwareAction { diff --git a/hudson/src/org/netbeans/modules/hudson/ui/actions/ViewSwitcher.java b/hudson/src/org/netbeans/modules/hudson/ui/actions/ViewSwitcher.java --- a/hudson/src/org/netbeans/modules/hudson/ui/actions/ViewSwitcher.java +++ b/hudson/src/org/netbeans/modules/hudson/ui/actions/ViewSwitcher.java @@ -65,7 +65,7 @@ import org.openide.util.actions.Presenter; @ActionID(category="Team", id="org.netbeans.modules.hudson.ui.actions.ViewSwitcher") -@ActionRegistration(displayName="#ViewSwitcher.label") +@ActionRegistration(displayName="#ViewSwitcher.label", lazy=false) @ActionReference(path=HudsonInstance.ACTION_PATH, position=100) @Messages("ViewSwitcher.label=View") public class ViewSwitcher extends AbstractAction implements ContextAwareAction, Presenter.Popup { diff --git a/java.j2seproject/src/org/netbeans/modules/java/j2seproject/ui/J2SELogicalViewProvider.java b/java.j2seproject/src/org/netbeans/modules/java/j2seproject/ui/J2SELogicalViewProvider.java --- a/java.j2seproject/src/org/netbeans/modules/java/j2seproject/ui/J2SELogicalViewProvider.java +++ b/java.j2seproject/src/org/netbeans/modules/java/j2seproject/ui/J2SELogicalViewProvider.java @@ -466,7 +466,7 @@ } @ActionID(id = "org.netbeans.modules.java.j2seproject.ui.J2SELogicalViewProvider$BrokenLinksActionFactory", category = "Project") - @ActionRegistration(displayName = "#LBL_Fix_Broken_Links_Action") + @ActionRegistration(displayName = "#LBL_Fix_Broken_Links_Action", lazy=false) @ActionReference(position = 2600, path = "Projects/org-netbeans-modules-java-j2seproject/Actions") public static final class BrokenLinksActionFactory extends AbstractAction implements ContextAwareAction { diff --git a/javahelp/src/org/netbeans/modules/javahelp/HelpAction.java b/javahelp/src/org/netbeans/modules/javahelp/HelpAction.java --- a/javahelp/src/org/netbeans/modules/javahelp/HelpAction.java +++ b/javahelp/src/org/netbeans/modules/javahelp/HelpAction.java @@ -55,7 +55,6 @@ import java.awt.event.WindowEvent; import java.util.logging.Level; import javax.swing.AbstractAction; -import javax.swing.Action; import javax.swing.MenuElement; import javax.swing.MenuSelectionManager; import javax.swing.SwingUtilities; @@ -64,7 +63,6 @@ import org.openide.awt.ActionReference; import org.openide.awt.ActionRegistration; import org.openide.awt.StatusDisplayer; -import org.openide.util.ContextAwareAction; import org.openide.util.HelpCtx; import org.openide.util.Lookup; import org.openide.util.NbBundle; @@ -75,9 +73,10 @@ * @author Jesse Glick */ @ActionID(category="Help", id="org.netbeans.modules.javahelp.HelpAction") -@ActionRegistration(displayName="#LBL_HelpAction", iconBase="org/netbeans/modules/javahelp/resources/show-help.gif") +@ActionRegistration(displayName="#LBL_HelpAction", iconBase="org/netbeans/modules/javahelp/resources/show-help.gif", + /* OpenIDE-Transmodal-Action must be present from the start (#206089) */ lazy=false) @ActionReference(path="Shortcuts", name="F1") -public class HelpAction extends AbstractAction implements ContextAwareAction { +public class HelpAction extends AbstractAction { public HelpAction() { Installer.log.fine("HelpAction.initialize"); @@ -85,13 +84,6 @@ putValue("OpenIDE-Transmodal-Action", true); // NOI18N } - /** - * #206093 workaround. OpenIDE-Transmodal-Action must be present from the start (#206089). - */ - @Override public Action createContextAwareInstance(Lookup actionContext) { - return this; - } - static class WindowActivatedDetector implements AWTEventListener { private static java.lang.ref.WeakReference currentWindowRef; private static WindowActivatedDetector detector = null; diff --git a/maven.apisupport/src/org/netbeans/modules/maven/apisupport/NbmActionGoalProvider.java b/maven.apisupport/src/org/netbeans/modules/maven/apisupport/NbmActionGoalProvider.java --- a/maven.apisupport/src/org/netbeans/modules/maven/apisupport/NbmActionGoalProvider.java +++ b/maven.apisupport/src/org/netbeans/modules/maven/apisupport/NbmActionGoalProvider.java @@ -107,7 +107,7 @@ @ActionID(id = "org.netbeans.modules.maven.apisupport.NBMReload", category = "Project") - @ActionRegistration(displayName = "#ACT_NBM_Reload") + @ActionRegistration(displayName = "#ACT_NBM_Reload", lazy=false) @ActionReference(position = 1250, path = "Projects/org-netbeans-modules-maven/Actions") @Messages("ACT_NBM_Reload=Install/Reload in Development IDE") public static ContextAwareAction createReloadAction() { @@ -117,7 +117,7 @@ } @ActionID(id = "org.netbeans.modules.maven.apisupport.NBMReloadTarget", category = "Project") - @ActionRegistration(displayName = "#ACT_NBM_Reload_Target") + @ActionRegistration(displayName = "#ACT_NBM_Reload_Target", lazy=false) @ActionReference(position = 1225, path = "Projects/org-netbeans-modules-maven/Actions") @Messages("ACT_NBM_Reload_Target=Reload in Target Platform") public static ContextAwareAction createReloadTargetAction() { diff --git a/maven.apisupport/src/org/netbeans/modules/maven/apisupport/OpenBrandingEditorAction.java b/maven.apisupport/src/org/netbeans/modules/maven/apisupport/OpenBrandingEditorAction.java --- a/maven.apisupport/src/org/netbeans/modules/maven/apisupport/OpenBrandingEditorAction.java +++ b/maven.apisupport/src/org/netbeans/modules/maven/apisupport/OpenBrandingEditorAction.java @@ -83,7 +83,7 @@ * @author S. Aubrecht */ @ActionID(id = "org.netbeans.modules.maven.apisupport.OpenBrandingEditorAction", category = "Project") -@ActionRegistration(displayName = "#LBL_OpenBrandingEditor") +@ActionRegistration(displayName = "#LBL_OpenBrandingEditor", lazy=false) @ActionReference(position = 3150, path = "Projects/org-netbeans-modules-maven/Actions") @Messages("LBL_OpenBrandingEditor=Branding...") public class OpenBrandingEditorAction extends AbstractAction implements ContextAwareAction { diff --git a/maven.coverage/src/org/netbeans/modules/maven/coverage/CoveragePopup.java b/maven.coverage/src/org/netbeans/modules/maven/coverage/CoveragePopup.java --- a/maven.coverage/src/org/netbeans/modules/maven/coverage/CoveragePopup.java +++ b/maven.coverage/src/org/netbeans/modules/maven/coverage/CoveragePopup.java @@ -56,7 +56,7 @@ import org.openide.util.Lookup; @ActionID(category="Project", id="org.netbeans.modules.maven.coverage.CoveragePopup") -@ActionRegistration(displayName="Maven Coverage") // NOI18N +@ActionRegistration(displayName="Maven Coverage", lazy=false) // NOI18N @ActionReference(path="Projects/org-netbeans-modules-maven/Actions", position=1205) public class CoveragePopup extends AbstractAction implements ContextAwareAction { diff --git a/maven.graph/src/org/netbeans/modules/maven/graph/ShowGraphAction.java b/maven.graph/src/org/netbeans/modules/maven/graph/ShowGraphAction.java --- a/maven.graph/src/org/netbeans/modules/maven/graph/ShowGraphAction.java +++ b/maven.graph/src/org/netbeans/modules/maven/graph/ShowGraphAction.java @@ -62,7 +62,7 @@ * @author mkleint */ @ActionID(id = "org.netbeans.modules.maven.graph.ShowGraphAction", category = "Project") -@ActionRegistration(displayName = "#ACT_Show_Graph") +@ActionRegistration(displayName = "#ACT_Show_Graph", lazy=false) @ActionReferences({ @ActionReference(position = 1650, path = "Projects/org-netbeans-modules-maven/Actions", separatorAfter=1655), @ActionReference(position = 113, path = "Editors/text/x-maven-pom+xml/Popup", separatorAfter=213) diff --git a/maven.j2ee/src/org/netbeans/modules/maven/j2ee/J2eeActions.java b/maven.j2ee/src/org/netbeans/modules/maven/j2ee/J2eeActions.java --- a/maven.j2ee/src/org/netbeans/modules/maven/j2ee/J2eeActions.java +++ b/maven.j2ee/src/org/netbeans/modules/maven/j2ee/J2eeActions.java @@ -74,7 +74,7 @@ public class J2eeActions { @ActionID(id = "org.netbeans.modules.maven.j2ee.verify", category = "Project") - @ActionRegistration(displayName = "#ACT_Verify") + @ActionRegistration(displayName = "#ACT_Verify", lazy=false) @ActionReference(position = 651, path = "Projects/org-netbeans-modules-maven/Actions") @Messages("ACT_Verify=Verify") public static ContextAwareAction verifyAction() { diff --git a/maven/src/org/netbeans/modules/maven/ActionProviderImpl.java b/maven/src/org/netbeans/modules/maven/ActionProviderImpl.java --- a/maven/src/org/netbeans/modules/maven/ActionProviderImpl.java +++ b/maven/src/org/netbeans/modules/maven/ActionProviderImpl.java @@ -407,7 +407,7 @@ } @ActionID(id = "org.netbeans.modules.maven.customPopup", category = "Project") - @ActionRegistration(displayName = "#LBL_Custom_Run") + @ActionRegistration(displayName = "#LBL_Custom_Run", lazy=false) @ActionReference(position = 1400, path = "Projects/org-netbeans-modules-maven/Actions") @Messages("LBL_Custom_Run=Custom") public static ContextAwareAction customPopupActions() { @@ -472,7 +472,7 @@ } @ActionID(id = "org.netbeans.modules.maven.closeSubprojects", category = "Project") - @ActionRegistration(displayName = "#ACT_CloseRequired") + @ActionRegistration(displayName = "#ACT_CloseRequired", lazy=false) @ActionReference(position = 2000, path = "Projects/org-netbeans-modules-maven/Actions") @Messages("ACT_CloseRequired=Close Required Projects") public static ContextAwareAction closeSubprojectsAction() { @@ -502,7 +502,7 @@ } @ActionID(id = "org.netbeans.modules.maven.showProblems", category = "Project") - @ActionRegistration(displayName = "#ACT_ShowProblems") + @ActionRegistration(displayName = "#ACT_ShowProblems", lazy=false) @ActionReference(position = 3100, path = "Projects/org-netbeans-modules-maven/Actions") @Messages("ACT_ShowProblems=Show and Resolve Problems...") public static ContextAwareAction showProblemsAction() { @@ -539,7 +539,7 @@ } @ActionID(id = "org.netbeans.modules.maven.buildWithDependencies", category = "Project") - @ActionRegistration(displayName = "#ACT_Build_Deps") + @ActionRegistration(displayName = "#ACT_Build_Deps", lazy=false) @ActionReference(position = 500, path = "Projects/org-netbeans-modules-maven/Actions") @Messages("ACT_Build_Deps=Build with Dependencies") public static ContextAwareAction buildWithDependenciesAction() { diff --git a/maven/src/org/netbeans/modules/maven/actions/RefreshAction.java b/maven/src/org/netbeans/modules/maven/actions/RefreshAction.java --- a/maven/src/org/netbeans/modules/maven/actions/RefreshAction.java +++ b/maven/src/org/netbeans/modules/maven/actions/RefreshAction.java @@ -59,7 +59,7 @@ @SuppressWarnings(value = "serial") @ActionID(id = "org.netbeans.modules.maven.refresh", category = "Project") -@ActionRegistration(displayName = "#ACT_Reload_Project") +@ActionRegistration(displayName = "#ACT_Reload_Project", lazy=false) @ActionReference(position = 1700, path = "Projects/org-netbeans-modules-maven/Actions") @Messages("ACT_Reload_Project=Reload POM") public class RefreshAction extends AbstractAction implements ContextAwareAction { diff --git a/o.apache.tools.ant.module/src/org/apache/tools/ant/module/run/RunTargetsAction.java b/o.apache.tools.ant.module/src/org/apache/tools/ant/module/run/RunTargetsAction.java --- a/o.apache.tools.ant.module/src/org/apache/tools/ant/module/run/RunTargetsAction.java +++ b/o.apache.tools.ant.module/src/org/apache/tools/ant/module/run/RunTargetsAction.java @@ -81,7 +81,7 @@ * undocumented targets. */ @ActionID(id = "org.apache.tools.ant.module.nodes.RunTargetsAction", category = "Build") -@ActionRegistration(displayName = "#LBL_run_targets_action") +@ActionRegistration(displayName = "#LBL_run_targets_action", lazy=false) @ActionReferences(value = { @ActionReference(position = 900, path = "Editors/text/x-ant+xml/Popup"), @ActionReference(position = 200, path = "Loaders/text/x-ant+xml/Actions")}) diff --git a/openide.awt/manifest.mf b/openide.awt/manifest.mf --- a/openide.awt/manifest.mf +++ b/openide.awt/manifest.mf @@ -2,5 +2,5 @@ OpenIDE-Module: org.openide.awt OpenIDE-Module-Localizing-Bundle: org/openide/awt/Bundle.properties AutoUpdate-Essential-Module: true -OpenIDE-Module-Specification-Version: 7.40 +OpenIDE-Module-Specification-Version: 7.41 diff --git a/openide.awt/src/org/netbeans/modules/openide/awt/ActionProcessor.java b/openide.awt/src/org/netbeans/modules/openide/awt/ActionProcessor.java --- a/openide.awt/src/org/netbeans/modules/openide/awt/ActionProcessor.java +++ b/openide.awt/src/org/netbeans/modules/openide/awt/ActionProcessor.java @@ -42,6 +42,7 @@ import java.awt.event.ActionListener; import java.util.Collections; import java.util.HashSet; +import java.util.Map; import java.util.Set; import java.util.regex.Pattern; import javax.annotation.processing.Completion; @@ -51,6 +52,7 @@ import javax.annotation.processing.SupportedSourceVersion; import javax.lang.model.SourceVersion; import javax.lang.model.element.AnnotationMirror; +import javax.lang.model.element.AnnotationValue; import javax.lang.model.element.Element; import javax.lang.model.element.ElementKind; import javax.lang.model.element.ExecutableElement; @@ -63,6 +65,7 @@ import javax.swing.Action; import javax.swing.JSeparator; import javax.swing.KeyStroke; +import javax.tools.Diagnostic; import org.openide.awt.ActionID; import org.openide.awt.ActionReference; import org.openide.awt.ActionReferences; @@ -238,17 +241,33 @@ key = ar.key(); } - boolean direct; - if (e.getKind() == ElementKind.FIELD) { - direct = false; - } else { - TypeMirror type = e.getKind() == ElementKind.CLASS ? e.asType() : ((ExecutableElement) e).getReturnType(); - direct = isAssignable(type, p1) || isAssignable(type, p2) || isAssignable(type, p3) || isAssignable(type, caa) || isAssignable(type, dmc); + Boolean direct = null; + for (AnnotationMirror m : e.getAnnotationMirrors()) { + if (m.getAnnotationType().toString().equals(ActionRegistration.class.getCanonicalName())) { + for (Map.Entry entry : m.getElementValues().entrySet()) { + if (entry.getKey().getSimpleName().contentEquals("lazy")) { + direct = ! (Boolean) entry.getValue().getValue(); + assert direct == !ar.lazy(); + break; + } + } + } + } + if (direct == null) { + if (e.getKind() == ElementKind.FIELD) { + direct = false; + } else { + TypeMirror type = e.getKind() == ElementKind.CLASS ? e.asType() : ((ExecutableElement) e).getReturnType(); + direct = isAssignable(type, p1) || isAssignable(type, p2) || isAssignable(type, p3) || isAssignable(type, caa) || isAssignable(type, dmc); + if (direct) { + processingEnv.getMessager().printMessage(Diagnostic.Kind.WARNING, "Should explicitly specify lazy attribute", e); + } + } } if (direct) { if (key.length() != 0) { - throw new LayerGenerationException("Cannot specify key and implement Presenter interface", e, processingEnv, ar, "key"); + throw new LayerGenerationException("Cannot specify key and use eager registration", e, processingEnv, ar, "key"); } f.instanceAttribute("instanceCreate", Action.class); } else { diff --git a/openide.awt/src/org/openide/awt/ActionRegistration.java b/openide.awt/src/org/openide/awt/ActionRegistration.java --- a/openide.awt/src/org/openide/awt/ActionRegistration.java +++ b/openide.awt/src/org/openide/awt/ActionRegistration.java @@ -39,11 +39,14 @@ package org.openide.awt; +import java.awt.event.ActionListener; import java.lang.annotation.ElementType; import java.lang.annotation.Retention; import java.lang.annotation.RetentionPolicy; import java.lang.annotation.Target; +import javax.swing.Action; import javax.swing.ActionMap; +import org.openide.util.ContextAwareAction; /** Registers an action under associated identifier specified by separate * {@link ActionID} annotation on the same element. Here is few usage examples: @@ -108,4 +111,40 @@ /** Shall the action work on last selection when it was enabled? */ boolean surviveFocusChange() default false; + + /** + * Whether a lazy factory registration from {@link Actions} should be used. + *

Most actions can be registered using a lazy factory (see class Javadoc for list), + * which permits the application to avoid loading the action class unless and until it + * is actually run. Before then, queries on the name, icon, etc. are serviced using + * static metadata, which minimizes startup overhead. + *

In limited cases, using this sort of lazy delegate is impossible or undesirable: + * the action needs to export some special key from {@link Action#getValue}; + * it presents multiple menu items according to dynamic conditions; or for UI reasons + * it is preferred to visually disable the action under certain conditions (rather than + * leaving it enabled and showing a message if selected under those conditions). + *

For these special cases, + * you may specify {@code lazy=false} to force the action registration to use the + * traditional direct registration of an instance of the action, without any lazy factory. + * That allows the action to supply arbitrary customized behavior even before it is ever run, + * at the expense of overhead when the registration is first encountered (such as when the + * main menu bar is populated, or a context menu of a certain kind is first shown). + *

It is an error to specify {@code lazy=false} on an element which is not assignable + * to {@link Action} (e.g. an {@link ActionListener}, or a {@code String} field); + * or which requires a context parameter in its constructor (or factory method). + *

For compatibility, registrations which do not explicitly specify this + * attribute but which are on elements assignable to any of the following types + * will be registered as if {@code lazy=false}, despite the default value of the attribute + * (but a warning will be issued and the attribute should be made explicit): + *

    + *
  • {@link org.openide.util.actions.Presenter.Menu} + *
  • {@link org.openide.util.actions.Presenter.Toolbar} + *
  • {@link org.openide.util.actions.Presenter.Popup} + *
  • {@link ContextAwareAction} + *
  • {@link DynamicMenuContent} + *
+ * @since 7.41 + */ + boolean lazy() default true; + } diff --git a/openide.awt/test/unit/src/org/netbeans/modules/openide/awt/ActionProcessorTest.java b/openide.awt/test/unit/src/org/netbeans/modules/openide/awt/ActionProcessorTest.java --- a/openide.awt/test/unit/src/org/netbeans/modules/openide/awt/ActionProcessorTest.java +++ b/openide.awt/test/unit/src/org/netbeans/modules/openide/awt/ActionProcessorTest.java @@ -625,6 +625,19 @@ return null; } } + @ActionID(category="eager", id="direct.seven") + @ActionRegistration(displayName="Direct Action", lazy=false) + public static class Direct7 extends AbstractAction { + @Override public void actionPerformed(ActionEvent e) {} + } + @ActionID(category="eager", id="direct.eight") + @ActionRegistration(displayName="Direct Action", lazy=true) + public static class Direct8 extends AbstractAction implements ContextAwareAction { + @Override public void actionPerformed(ActionEvent e) {} + @Override public Action createContextAwareInstance(Lookup actionContext) { + return this; + } + } @ActionID(category="menutext", id="namedaction") @ActionRegistration(displayName="This is an Action", menuText="This is a Menu Action", popupText="This is a Popup Action") @@ -692,6 +705,20 @@ assertNotNull("Action created", obj); assertEquals("Direct class is created", Direct6.class, obj.getClass()); } + public void testDirectInstanceIfRequested() throws Exception { + FileObject fo = FileUtil.getConfigFile("Actions/eager/direct-seven.instance"); + assertNotNull("Instance found", fo); + Object obj = fo.getAttribute("instanceCreate"); + assertNotNull("Action created", obj); + assertEquals("Direct class is created", Direct7.class, obj.getClass()); + } + public void testIndirectInstanceIfRequested() throws Exception { + FileObject fo = FileUtil.getConfigFile("Actions/eager/direct-eight.instance"); + assertNotNull("Instance found", fo); + Object obj = fo.getAttribute("instanceCreate"); + assertNotNull("Action created", obj); + assertNotSame("Direct class is not created", Direct8.class, obj.getClass()); + } public void testNoKeyForDirects() throws IOException { clearWorkDir(); diff --git a/progress.ui/src/org/netbeans/modules/progress/ui/ProgressListAction.java b/progress.ui/src/org/netbeans/modules/progress/ui/ProgressListAction.java --- a/progress.ui/src/org/netbeans/modules/progress/ui/ProgressListAction.java +++ b/progress.ui/src/org/netbeans/modules/progress/ui/ProgressListAction.java @@ -44,7 +44,6 @@ package org.netbeans.modules.progress.ui; -import javax.swing.JMenuItem; import org.netbeans.modules.progress.spi.Controller; import javax.swing.AbstractAction; import javax.swing.SwingUtilities; @@ -53,18 +52,16 @@ import org.openide.awt.ActionID; import org.openide.awt.ActionReference; import org.openide.awt.ActionRegistration; -import org.openide.awt.Actions; import org.openide.util.NbBundle; -import org.openide.util.actions.Presenter; /** * * @author mkleint */ @ActionID(id = "org.netbeans.modules.progress.ui.ProgressListAction", category = "Window") -@ActionRegistration(displayName = "#CTL_ProcessListAction") +@ActionRegistration(displayName = "#CTL_ProcessListAction", lazy=false) @ActionReference(position = 1900, name = "ProgressListAction", path = "Menu/Window") -public class ProgressListAction extends AbstractAction implements ListDataListener, Runnable, Presenter.Menu { +public class ProgressListAction extends AbstractAction implements ListDataListener, Runnable { /** Creates a new instance of ProcessListAction */ public ProgressListAction() { @@ -104,12 +101,4 @@ updateEnabled(); } - // XXX could remove impl of this interface; then it would be "always enabled" (until first selected, then enablement would update) - public @Override JMenuItem getMenuPresenter() { - JMenuItem presenter = new JMenuItem(); - Actions.connect(presenter, this, false); - return presenter; - } - - } diff --git a/projectimport.eclipse.core/src/org/netbeans/modules/projectimport/eclipse/core/UpdateProjectAction.java b/projectimport.eclipse.core/src/org/netbeans/modules/projectimport/eclipse/core/UpdateProjectAction.java --- a/projectimport.eclipse.core/src/org/netbeans/modules/projectimport/eclipse/core/UpdateProjectAction.java +++ b/projectimport.eclipse.core/src/org/netbeans/modules/projectimport/eclipse/core/UpdateProjectAction.java @@ -57,7 +57,7 @@ import org.openide.util.NbBundle; @ActionID(id = "org.netbeans.modules.projectimport.eclipse.core.UpdateProjectAction", category = "Project") -@ActionRegistration(displayName = "#UpdateProjectAction.Name") +@ActionRegistration(displayName = "#UpdateProjectAction.Name", lazy=false) @ActionReference(position = 234, path = "Projects/Actions") public final class UpdateProjectAction extends AbstractAction implements ContextAwareAction { diff --git a/projectui/src/org/netbeans/modules/project/ui/SyncEditorWithViewsAction.java b/projectui/src/org/netbeans/modules/project/ui/SyncEditorWithViewsAction.java --- a/projectui/src/org/netbeans/modules/project/ui/SyncEditorWithViewsAction.java +++ b/projectui/src/org/netbeans/modules/project/ui/SyncEditorWithViewsAction.java @@ -63,7 +63,7 @@ * @author Milan Kubec */ @ActionID(id = "org.netbeans.modules.project.ui.SyncEditorWithViewsAction", category = "Project") -@ActionRegistration(displayName = "#CTL_SYNC_EDITOR_WITH_VIEWS") +@ActionRegistration(displayName = "#CTL_SYNC_EDITOR_WITH_VIEWS", lazy=false) @ActionReference(path = "Menu/View", position = 1050) public class SyncEditorWithViewsAction extends SystemAction implements DynamicMenuContent { diff --git a/projectui/src/org/netbeans/modules/project/ui/actions/ActiveConfigAction.java b/projectui/src/org/netbeans/modules/project/ui/actions/ActiveConfigAction.java --- a/projectui/src/org/netbeans/modules/project/ui/actions/ActiveConfigAction.java +++ b/projectui/src/org/netbeans/modules/project/ui/actions/ActiveConfigAction.java @@ -110,7 +110,7 @@ * @author Greg Crawley, Adam Sotona, Jesse Glick */ @ActionID(id="org.netbeans.modules.project.ui.actions.ActiveConfigAction", category="Project") -@ActionRegistration(displayName="#ActiveConfigAction.label") +@ActionRegistration(displayName="#ActiveConfigAction.label", lazy=false) @ActionReferences({ @ActionReference(path="Menu/BuildProject", position=300), @ActionReference(path="Toolbars/Build", position=80) diff --git a/projectui/src/org/netbeans/modules/project/ui/actions/OpenProjectFolderAction.java b/projectui/src/org/netbeans/modules/project/ui/actions/OpenProjectFolderAction.java --- a/projectui/src/org/netbeans/modules/project/ui/actions/OpenProjectFolderAction.java +++ b/projectui/src/org/netbeans/modules/project/ui/actions/OpenProjectFolderAction.java @@ -74,7 +74,7 @@ * @author Jesse Glick */ @ActionID(id = "org.netbeans.modules.project.ui.actions.OpenProjectFolderAction", category = "Project") -@ActionRegistration(displayName = "#OpenProjectFolderAction.LBL_action") +@ActionRegistration(displayName = "#OpenProjectFolderAction.LBL_action", lazy=false) @ActionReference(path = "Loaders/folder/any/Actions", position = 100) @Messages("OpenProjectFolderAction.LBL_action=Open Project of Folder") public final class OpenProjectFolderAction extends AbstractAction implements ContextAwareAction { diff --git a/projectui/src/org/netbeans/modules/project/ui/actions/RunLastBuildAction.java b/projectui/src/org/netbeans/modules/project/ui/actions/RunLastBuildAction.java --- a/projectui/src/org/netbeans/modules/project/ui/actions/RunLastBuildAction.java +++ b/projectui/src/org/netbeans/modules/project/ui/actions/RunLastBuildAction.java @@ -70,7 +70,7 @@ * @see "#47925" */ @ActionID(id = "org.netbeans.modules.project.ui.Rerun", category = "Project") -@ActionRegistration(displayName = "#LBL_RunLastBuildAction_general") +@ActionRegistration(displayName = "#LBL_RunLastBuildAction_general", lazy=false) @ActionReference(path = "Menu/BuildProject", position = 1000) public final class RunLastBuildAction extends AbstractAction implements ChangeListener, Presenter.Menu, Presenter.Toolbar { diff --git a/projectui/src/org/netbeans/modules/project/ui/actions/SelectNodeAction.java b/projectui/src/org/netbeans/modules/project/ui/actions/SelectNodeAction.java --- a/projectui/src/org/netbeans/modules/project/ui/actions/SelectNodeAction.java +++ b/projectui/src/org/netbeans/modules/project/ui/actions/SelectNodeAction.java @@ -69,7 +69,7 @@ private final String findIn; @ActionID(id = "org.netbeans.modules.project.ui.SelectInProjects", category = "Window/SelectDocumentNode") - @ActionRegistration(displayName = "#LBL_SelectInProjectsAction_MainMenuName") + @ActionRegistration(displayName = "#LBL_SelectInProjectsAction_MainMenuName", lazy=false) @ActionReferences({ @ActionReference(path = "Shortcuts", name = "DS-1"), @ActionReference(path = "Menu/GoTo", position = 2600, separatorBefore = 2500), @@ -80,7 +80,7 @@ } @ActionID(id = "org.netbeans.modules.project.ui.SelectInFiles", category = "Window/SelectDocumentNode") - @ActionRegistration(displayName = "#LBL_SelectInFilesAction_MainMenuName") + @ActionRegistration(displayName = "#LBL_SelectInFilesAction_MainMenuName", lazy=false) @ActionReferences({ @ActionReference(path = "Shortcuts", name = "DS-2"), @ActionReference(path = "Menu/GoTo", position = 2700) diff --git a/projectui/src/org/netbeans/modules/project/ui/actions/StopBuildingAction.java b/projectui/src/org/netbeans/modules/project/ui/actions/StopBuildingAction.java --- a/projectui/src/org/netbeans/modules/project/ui/actions/StopBuildingAction.java +++ b/projectui/src/org/netbeans/modules/project/ui/actions/StopBuildingAction.java @@ -69,7 +69,7 @@ * @see "issue #43143" */ @ActionID(id = "org.netbeans.modules.project.ui.actions.StopBuildingAction", category = "Project") -@ActionRegistration(displayName = "#LBL_stop_building") +@ActionRegistration(displayName = "#LBL_stop_building", lazy=false) @ActionReference(path = "Menu/BuildProject", position = 1100) public final class StopBuildingAction extends CallableSystemAction implements ChangeListener { diff --git a/projectui/src/org/netbeans/modules/project/ui/groups/GroupsMenu.java b/projectui/src/org/netbeans/modules/project/ui/groups/GroupsMenu.java --- a/projectui/src/org/netbeans/modules/project/ui/groups/GroupsMenu.java +++ b/projectui/src/org/netbeans/modules/project/ui/groups/GroupsMenu.java @@ -75,7 +75,7 @@ * @author Jesse Glick */ @ActionID(id = "org.netbeans.modules.project.ui.groups.GroupsMenu", category = "Project") -@ActionRegistration(displayName = "#GroupsMenu.label") +@ActionRegistration(displayName = "#GroupsMenu.label", lazy=false) @ActionReferences({ @ActionReference(path = "Menu/File", position = 1100), @ActionReference(path = ProjectsRootNode.ACTIONS_FOLDER, position = 600, separatorAfter = 700) diff --git a/spi.quicksearch/src/org/netbeans/modules/quicksearch/QuickSearchAction.java b/spi.quicksearch/src/org/netbeans/modules/quicksearch/QuickSearchAction.java --- a/spi.quicksearch/src/org/netbeans/modules/quicksearch/QuickSearchAction.java +++ b/spi.quicksearch/src/org/netbeans/modules/quicksearch/QuickSearchAction.java @@ -56,7 +56,7 @@ * @author Jan Becicka */ @ActionID(id = "org.netbeans.modules.quicksearch.QuickSearchAction", category = "Edit") -@ActionRegistration(displayName = "#CTL_QuickSearchAction") +@ActionRegistration(displayName = "#CTL_QuickSearchAction", lazy=false) @ActionReference(name = "D-I", path = "Shortcuts") public final class QuickSearchAction extends CallableSystemAction { diff --git a/utilities/src/org/netbeans/modules/openfile/RecentFileAction.java b/utilities/src/org/netbeans/modules/openfile/RecentFileAction.java --- a/utilities/src/org/netbeans/modules/openfile/RecentFileAction.java +++ b/utilities/src/org/netbeans/modules/openfile/RecentFileAction.java @@ -85,7 +85,7 @@ * * @author Dafe Simonek */ -@ActionRegistration( +@ActionRegistration(lazy=false, displayName="#LBL_RecentFileAction_Name" ) @ActionID(category="System", id="org.netbeans.modules.openfile.RecentFileAction")