Overview

# NetBeans Architecture Answers for Actions module

- Author: pzavadsky@netbeans.org
- Answers as of: Dec 7, 2006
- Answers for questions version: 1.12
- Latest available version of questions: 1.26

WARNING: answering questions version 1.12 rather than the current 1.26.

## Interfaces table

##### Group of java interfaces

Interface Name | In/Out | Stability | Specified in What Document?
NodesAPI | Imported | Official | .../overview-summary.html
WindowSystemAPI | Imported | Official | .../overview-summary.html
ExplorerAPI | Imported | Official | .../overview-summary.html
FilesystemsAPI | Imported | Official | .../overview-summary.html
LoadersAPI | Imported | Official | .../overview-summary.html
UtilitiesAPI | Imported | Official | ../org-openide-util/overview-summary.html ../org-openide-util/overview-summary.html The module is needed for compilation. The module is used during runtime. Specification version 6.4 is required.
org.openide.nodes | Imported | Private | .../overview-summary.html The module is needed for compilation. The module is used during runtime. Specification version 6.2 is required.
org.openide.awt | Imported | Private | ../org-openide-awt/overview-summary.html The module is needed for compilation. The module is used during runtime. Specification version 6.5 is required.
org.openide.options | Imported | Private | .../overview-summary.html The module is needed for compilation. The module is used during runtime. Specification version 6.2 is required.
org.openide.text | Imported | Private | ../org-openide-text/overview-summary.html The module is needed for compilation. The module is used during runtime. Specification version 6.2 is required.
org.openide.explorer | Imported | Private | .../overview-summary.html The module is needed for compilation. The module is used during runtime. Specification version 6.2 is required.
org.openide.dialogs | Imported | Private | .../overview-summary.html The module is needed for compilation. The module is used during runtime. Specification version 6.2 is required.
org.openide.windows | Imported | Private | .../overview-summary.html The module is needed for compilation. The module is used during runtime. Specification version 6.2 is required.
ActionsAPI | Exported | Official | overview-summary.html

##### Group of property interfaces

Interface Name | In/Out | Stability | Specified in What Document?
OpenIDE-Transmodal-Action | Exported | Under Development | Inidicates action can be performed (typicaly via shortcut) even when dialog is popped out (modal or modeless).
delegates | Exported | Under Development | Used internaly in `PasteAction` delegate action which serves to pass an array of `PasteType` or `Action` to global instance (it is the only one which actually performs paste operation).
iconBase | Exported | Under Development | Used in companion to Actions.SMALL_ICON. Because there is no way to specify values for other types of icons the value of "iconBase" is used to construct the resource names of disabled, pressed and rollover icons. The value is expected to contain a resource path of the normal icon. Strings "_pressed", "_disabled" and "_rollover" are inserted before the suffix when searching for the other types of icons.
noIconInMenu | Exported | Under Development | Allowed value `Boolean.TRUE`. Influences the display of the action in the main menu, the item will have no icon there. Works for Actions that don't define custom MenuPresenter.
PreferredIconSize | Exported | Under Development | Used to support 24x24 icons in toolbars. If toolbar button has client property "PreferredIconSize" set to Integer(24) button tries to load icon with name "iconBase" + "24" eg. "cut24.gif". Strings "_pressed","_disabled" and "_rollover" are inserted before the suffix when searching for the other types of icons eg.:"cut24_pressed.gif".
waitFinished | Exported | Friend | There is a new contract established between the caller of an action that allows mutual communication and possible synchronous execution even for actions that by default perform their operations asynchronously. If the action's `actionPeformed` method is passed `ActionEvent` with command waitFinished the action shall be executed synchronously. The code:
                 action.actionPerformed (new ActionEvent (this, 0, "waitFinished"))
shall be executed synchronously, even if the action by default runs asynchronously. All asynchronous actions are asked to obey this contract, `CallableSystemAction` does it by default. However this contract is defined as friend one and may be abandoned in future.
ActionMapKeys | Exported | Stable | `CallableSystemAction` uses its `getActionMapKey()` method (usually overriden by subclasses) to get a key which is then searched in the `ActionMap` obtained from the action's context. Other modules can register their own action then:
    topComponent.getActionMap ().put (theKey, new YourOwnSwingAction ());
Here is the list of special keys: `"cloneWindow"` - an action to be executed when a top component is to be cloned `"closeWindow"` - an action when a view is about to be closed `DefaultEditorKit.copyAction` - copy action handler `DefaultEditorKit.cutAction` - cut action handler `"delete"` - delete action handler `DefaultEditorKit.pasteAction` - paste action handler `"jumpNext"` - when a next element shall be selected `"jumpPrev"` - when a previous element shall be selected
org.openide.util.actions.CallableSystemAction.synchronousByDefault | Exported | Friend | If set to `true`, changes default value of the `asynchronous()` method. Useful for unit tests which would prefer to run all tested actions synchronously.

## General Information

Question (arch-what): What is this project good for?

Answer: Actions provides system of support and utility classes for 'actions' usage in NetBeans.

Question (arch-overall): Describe the overall architecture.

Answer:

XXX no answer for arch-overall

Question (arch-usecases): Describe the main use cases of the new API. Who will use it under what circumstances? What kind of code would typically need to be written to use the module?

Answer: First see the API description. Here is just a list of frequently asked or interesting questions slowly expanding as people ask them:

### Actions faq:

#### How to define configurable Shortcut for Component based shortcut?

Q: The usual Swing way of defining Actions for your component is to create an Action instance and put it into the Input and Action maps of your component. However how to make this Action's shortcut configurable from the Tools/Keyboard Shortcuts dialog?

In order for the action to show up in Keyboards Shortcut dialog you need the action defined in the layer file under "Actions" folder and have the shortcut defined there under "Keymaps/<Profile Name>" linking to your action.

        <folder name="Actions" >
            <folder name="Window">
                <file name="org-netbeans-core-actions-PreviousViewCallbackAction.instance"/>
            </folder>
        </folder>

        <folder name="Keymaps">
            <folder name="NetBeans">
                <file name="S-A-Left.shadow">
                    <attr name="originalFile" stringvalue="Actions/Window/org-netbeans-core-actions-PreviousViewCallbackAction.instance"/>
                </file>
            </folder>
        </folder>

The mentioned Action has to be a subclass of `org.openide.util.actions.CallbackSystemAction`. It does not necessarily has to perform the action, it's just a placeholder for linking the shortcut. You might want to override it's `getActionMapKey()` and give it a reasonable key.

The actual action that does the work in your component (preferably a simple Swing `javax.swing.Action`) is to be put into your `TopComponent`'s `ActionMap`. The key for the `ActionMap` has to match the key defined in the global action's `getActionMapKey()` method.

            getActionMap().put("PreviousViewAction", new MyPreviousTabAction());

This way even actions from multiple `TopComponent`s with the same gesture (eg. "switch to next tab") can share the same configurable shortcut.

Note: Don't define your action's shortcut and don't put it into any of the `TopComponent`'s `javax.swing.InputMap`. Otherwise the component would not pick up the changed shortcut from the global context.

Question (arch-time): What are the time estimates of the work?

Answer:

XXX no answer for arch-time

Question (arch-quality): How will the quality of your code be tested and how are future regressions going to be prevented?

Answer:

XXX no answer for arch-quality

Question (arch-where): Where one can find sources for your module?

Answer:

The sources for the module are in NetBeans CVS in openide/actions directory.

## Project and platform dependencies

Question (dep-nb): What other NetBeans projects and modules does this one depend on?

Answer: It uses various kinds of API's:

- NodesAPI The support class `NodeAction`.
- WindowSystemAPI `NodeAction` uses `TopComponent.Registry`.
- ExplorerAPI `PasteAction` uses `ExplorerManager`.
- FilesystemsAPI E.g. `FileSystemAction` uses `FileSystem`.
- LoadersAPI E.g. `FileSystemAction` uses `DataObject`.
- UtilitiesAPI

Default answer to this question is:

These modules are required in project.xml file:

- UtilitiesAPI - The module is needed for compilation. The module is used during runtime. Specification version 6.4 is required.
- org.openide.nodes - The module is needed for compilation. The module is used during runtime. Specification version 6.2 is required.
- org.openide.awt - The module is needed for compilation. The module is used during runtime. Specification version 6.5 is required.
- org.openide.options - The module is needed for compilation. The module is used during runtime. Specification version 6.2 is required.
- org.openide.text - The module is needed for compilation. The module is used during runtime. Specification version 6.2 is required.
- org.openide.explorer - The module is needed for compilation. The module is used during runtime. Specification version 6.2 is required.
- org.openide.dialogs - The module is needed for compilation. The module is used during runtime. Specification version 6.2 is required.
- org.openide.windows - The module is needed for compilation. The module is used during runtime. Specification version 6.2 is required.

Question (dep-non-nb): What other projects outside NetBeans does this one depend on?

Answer: No.

Question (dep-platform): On which platforms does your module run? Does it run in the same way on each?

Answer: 100% pure Java. It should run anywhere.

Question (dep-jre): Which version of JRE do you need (1.2, 1.3, 1.4, etc.)?

Answer: It uses JRE 1.3.

Question (dep-jrejdk): Do you require the JDK or is the JRE enough?

Answer: JRE is enough.

## Deployment

Question (deploy-jar): Do you deploy just module JAR file(s) or other files as well?

Answer: Classes belonging to this module do not reside in standalone library. They are bundled together with other parts of the openide in `openide.jar`.

Question (deploy-nbm): Can you deploy an NBM via the Update Center?

Answer: Whole openide can be deployed via AU center.

Question (deploy-shared): Do you need to be installed in the shared location only, or in the user directory only, or can your module be installed anywhere?

Answer: `openide.jar` needs to be in the system directory.

Question (deploy-packages): Are packages of your module made inaccessible by not declaring them public?

Answer: No, ther are ActionsAPI.

Question (deploy-dependencies): What do other modules need to do to declare a dependency on this one?

Answer:

XXX no answer for deploy-dependencies

## Compatibility with environment

Question (compat-i18n): Is your module correctly internationalized?

Answer: Yes.

Question (compat-standards): Does the module implement or define any standards? Is the implementation exact or does it deviate somehow?

Answer: Before the Actions was build on `org.openide.util.actions.SystemAction`, this was recently changed that Actions supports `javax.swing.Action` which is java API standard, and Actions will be improving towards this more and more.

Question (compat-version): Can your module coexist with earlier and future versions of itself? Can you correctly read all old settings? Will future versions be able to read your current settings? Can you read or politely ignore settings stored by a future version?

Answer: Yes up to now it is supposed to be compatible with older versions.

## Access to resources

Question (resources-file): Does your module use `java.io.File` directly?

Answer: No.

Question (resources-layer): Does your module provide own layer? Does it create any files or folders in it? What it is trying to communicate by that and with which components?

Answer: No in fact. Just concrete action implementation provided by this module are typically used in xml layers.

Question (resources-read): Does your module read any resources from layers? For what purpose?

Answer: There are special folders containing actions in xml layers.

- Menu contains actions which are present in menu.
- Toolbars contains actions which will be present in toolbars.
- Shortcuts contains actions which will have assigned shortcuts.
- Actions contains actions which are possible to manipulate with (via Options).

Note: Those layers are not necessarily read by Actions module. Probably it belongs to Window system module.

Question (resources-mask): Does your module mask/hide/override any resources provided by other modules in their layers?

Answer: No.

## Lookup of components

Question (lookup-lookup): Does your module use `org.openide.util.Lookup` or any similar technology to find any components to communicate with? Which ones?

Answer: It uses `Lookup` as a representation of context in which are certain action types `ContextAwareAction`s used. Current implementations lookup in the context for `javax.swing.ActionMap` or `org.openide.nodes.Node` or `org.openide.Node.Cookie` instances.

Question (lookup-register): Do you register anything into lookup for other code to find?

Answer: No. Actions are just clients of some lookups.

Question (lookup-remove): Do you remove entries of other modules from lookup?

Answer: No.

## Execution Environment

Question (exec-property): Is execution of your code influenced by any environment or Java system (`System.getProperty`) property?

Answer:

- org.openide.util.actions.CallableSystemAction.synchronousByDefault - If set to `true`, changes default value of the `asynchronous()` method. Useful for unit tests which would prefer to run all tested actions synchronously.

Question (exec-component): Is execution of your code influenced by any (string) property of any of your components?

Answer: There are used three values (via `Action.getValue()`).

- OpenIDE-Transmodal-Action - Inidicates action can be performed (typicaly via shortcut) even when dialog is popped out (modal or modeless).
- delegates - Used internaly in `PasteAction` delegate action which serves to pass an array of `PasteType` or `Action` to global instance (it is the only one which actually performs paste operation).
- iconBase - Used in companion to Actions.SMALL_ICON. Because there is no way to specify values for other types of icons the value of "iconBase" is used to construct the resource names of disabled, pressed and rollover icons. The value is expected to contain a resource path of the normal icon. Strings "_pressed", "_disabled" and "_rollover" are inserted before the suffix when searching for the other types of icons.
- noIconInMenu - Allowed value `Boolean.TRUE`. Influences the display of the action in the main menu, the item will have no icon there. Works for Actions that don't define custom MenuPresenter.
- PreferredIconSize - Used to support 24x24 icons in toolbars. If toolbar button has client property "PreferredIconSize" set to Integer(24) button tries to load icon with name "iconBase" + "24" eg. "cut24.gif". Strings "_pressed","_disabled" and "_rollover" are inserted before the suffix when searching for the other types of icons eg.:"cut24_pressed.gif".
- waitFinished - There is a new contract established between the caller of an action that allows mutual communication and possible synchronous execution even for actions that by default perform their operations asynchronously. If the action's `actionPeformed` method is passed `ActionEvent` with command waitFinished the action shall be executed synchronously. The code:

                   action.actionPerformed (new ActionEvent (this, 0, "waitFinished"))

  shall be executed synchronously, even if the action by default runs asynchronously. All asynchronous actions are asked to obey this contract, `CallableSystemAction` does it by default. However this contract is defined as friend one and may be abandoned in future.

ActionMapKeys - `CallableSystemAction` uses its `getActionMapKey()` method (usually overriden by subclasses) to get a key which is then searched in the `ActionMap` obtained from the action's context. Other modules can register their own action then:

    topComponent.getActionMap ().put (theKey, new YourOwnSwingAction ());

Here is the list of special keys:

- `"cloneWindow"` - an action to be executed when a top component is to be cloned
- `"closeWindow"` - an action when a view is about to be closed
- `DefaultEditorKit.copyAction` - copy action handler
- `DefaultEditorKit.cutAction` - cut action handler
- `"delete"` - delete action handler
- `DefaultEditorKit.pasteAction` - paste action handler
- `"jumpNext"` - when a next element shall be selected
- `"jumpPrev"` - when a previous element shall be selected

Question (exec-ant-tasks): Do you define or register any ant tasks that other can use?

Answer:

XXX no answer for exec-ant-tasks

Question (exec-classloader): Does your code create its own class loader(s)?

Answer: No.

Question (exec-reflection): Does your code use Java Reflection to execute other code?

Answer: A bit indirectly. `SystemAction.get (...)` calls to `SharedClassObject.findObject` which calls constructor by reflection.

Question (exec-privateaccess): Are you aware of any other parts of the system calling some of your methods by reflection?

Answer: No.

Question (exec-process): Do you execute an external process from your module? How do you ensure that the result is the same on different platforms? Do you parse output? Do you depend on result code?

Answer:

XXX no answer for exec-process

Question (exec-introspection): Does your module use any kind of runtime type information (`instanceof`, work with `java.lang.Class`, etc.)?

Answer:

XXX no answer for exec-introspection

Question (exec-threading): What threading models, if any, does your module adhere to?

Answer:

XXX no answer for exec-threading

Question (security-policy): Does your functionality require modifications to the standard policy file?

Answer:

XXX no answer for security-policy

Question (security-grant): Does your code grant additional rights to some other code?

Answer:

XXX no answer for security-grant

## Format of files and protocols

Question (format-types): Which protocols and file formats (if any) does your module read or write on disk, or transmit or receive over the network? Do you generate an ant build script? Can it be edited and modified?

Answer: None.

Question (format-dnd): Which protocols (if any) does your code understand during Drag & Drop?

Answer: See format-clibpoard.

Question (format-clipboard): Which data flavors (if any) does your code read from or insert to the clipboard (by access to clipboard on means calling methods on `java.awt.datatransfer.Transferable`?

Answer: Implementations of cut, copy and paste (`CutAction`, `CopyAction` and `PasteAction`) reads/writes from/into clipboard. It uses standard java datatransfer mechanism and Netbeans extension to the mechanism.

## Performance and Scalability

Question (perf-startup): Does your module run any code on startup?

Answer: No.

Question (perf-exit): Does your module run any code on exit?

Answer: No.

Question (perf-scale): Which external criteria influence the performance of your program (size of file in editor, number of files in menu, in source directory, etc.) and how well your code scales?

Answer: This should be irrelevant, as far as I know, Actions shouldn't use any collections of data or something like that. One exception I know is global keymap implementation which scales linear.

Question (perf-limit): Are there any hard-coded or practical limits in the number or size of elements your code can handle?

Answer: None is defined.

Question (perf-mem): How much memory does your component consume? Estimate with a relation to the number of windows, etc.

Answer: There is one class in VM per action. Because currently all actions are subclasses of `SystemAction`. Those kind of actions are singletons. That older approach is getting away. There are already newer implementation which creates short living action instances (context sensitive actions) when invoking popup menu.
It should be measured how much of memory they take. I guess the amount shouldn't be signicant.

Question (perf-wakeup): Does any piece of your code wake up periodically and do something even when the system is otherwise idle (no user interaction)?

Answer: No. At least I do not know about that.

Question (perf-progress): Does your module execute any long-running tasks?

Answer: No.

Question (perf-huge_dialogs): Does your module contain any dialogs or wizards with a large number of GUI controls such as combo boxes, lists, trees, or text areas?

Answer: Core implementation provides component for customizing shorcuts. `org.netbeans.core.ShortcutsEditor`.

Question (perf-menus): Does your module use dynamically updated context menus, or context-sensitive actions with complicated and slow enablement logic?

Answer: Actions doesn't use menus, it is vice versa.

Question (perf-spi): How the performance of the plugged in code will be enforced?

Answer:

XXX no answer for perf-spi

Built on December 7 2006. | Portions Copyright 1997-2005 Sun Microsystems, Inc. All rights reserved.