How do I add an action (incl. shortcut) at runtime?
Create system file system entries in the Actions
/Menu
/Shortcuts
folders! See the following example
Usage:
private void initActions() {
ActionRegistrationService ars = Lookup.getDefault().lookup(ActionRegistrationService.class);
try {
String menuPath = "Menu/Machine/Jog";
ars.registerAction(getMessage(this.getClass(), "JogService.xPlus") , "Machine", "M-RIGHT" , menuPath, new JogAction(this, 1, 0, 0));
ars.registerAction(getMessage(this.getClass(), "JogService.xMinus"), "Machine", "M-LEFT" , menuPath, new JogAction(this,-1, 0, 0));
ars.registerAction(getMessage(this.getClass(), "JogService.yPlus") , "Machine", "M-UP" , menuPath, new JogAction(this, 0, 1, 0));
} catch (IOException ex) {
Exceptions.printStackTrace(ex);
}
}
Helper-Service
import com.google.common.base.Joiner;
import java.io.IOException;
import java.util.Arrays;
import javax.swing.Action;
import org.openide.filesystems.FileObject;
import org.openide.filesystems.FileUtil;
import org.openide.util.lookup.ServiceProvider;
/**
*
* @author wwinder
*/
@ServiceProvider(service=ActionRegistrationService.class)
public class ActionRegistrationService {
/**
* Registers an action with the platform along with optional shortcuts and
* menu items.
* @param name Display name of the action.
* @param category Category in the Keymap tool.
* @param shortcut Default shortcut, use an empty string or null for none.
* @param menuPath Menu location starting with "Menu", like "Menu/File"
* @param action an action object to attach to the action entry.
* @throws IOException
*/
public void registerAction(String name, String category, String shortcut, String menuPath, Action action) throws IOException {
///////////////////////
// Add/Update Action //
///////////////////////
String originalFile = "Actions/" + category + "/" + name + ".instance";
FileObject in = getFolderAt("Actions/" + category);
FileObject obj = in.getFileObject(name, "instance");
if (obj == null) {
obj = in.createData(name, "instance");
}
action.putValue(Action.NAME, name);
obj.setAttribute("instanceCreate", action);
obj.setAttribute("instanceClass", action.getClass().getName());
/////////////////////
// Add/Update Menu //
/////////////////////
in = getFolderAt(menuPath);
obj = in.getFileObject(name, "shadow");
// Create if missing.
if (obj == null) {
obj = in.createData(name, "shadow");
obj.setAttribute("originalFile", originalFile);
}
/////////////////////////
// Add/Update Shortcut //
/////////////////////////
in = getFolderAt("Shortcuts");
obj = in.getFileObject(shortcut, "shadow");
if (obj == null) {
obj = in.createData(shortcut, "shadow");
obj.setAttribute("originalFile", originalFile);
}
}
private FileObject getFolderAt(String inputPath) throws IOException {
String parts[] = inputPath.split("/");
FileObject existing = FileUtil.getConfigFile(inputPath);
if (existing != null)
return existing;
FileObject base = FileUtil.getConfigFile(parts[0]);
if (base == null) return null;
for (int i = 1; i < parts.length; i++) {
String path = Joiner.on('/').join(Arrays.copyOfRange(parts,0,i+1));
FileObject next = FileUtil.getConfigFile(path);
if (next == null) {
next = base.createFolder(parts[i]);
}
base = next;
}
return FileUtil.getConfigFile(inputPath);
}
}
Taken from mailing list http://forums.netbeans.org/topic65421.html Based on [front::blogs/geertjan/dynamically_creating_menu_items_part]