Simple hierarchical popupmenu for Node

I recently got a question how you can organize your Node’s popup menus hierarchically, while keeping registration declarative. Organizing your actions hierachically in the Layer and then using Lookups.forPath().lookupAll(Action.class) doesn’t work, the result is a flat list. So here’s the simplest version I know:

AbstractNode example = new AbstractNode(Children.LEAF) {
            @Override
            public Action[] getActions(boolean context) {
                return findActionsForFolder(FileUtil.getConfigFile("MYPATH"));
            }

            protected Action[] findActionsForFolder(FileObject folder) {
                ArrayList actions = new ArrayList();
                if (folder != null && folder.isFolder()) {

                FileObject[] children = folder.getChildren();
                for (FileObject fileObject : children) {
                    if (fileObject.isFolder()) {
                        Action[] findActionsForFolder = findActionsForFolder(fileObject);
                        Action menu = new MenuAction(fileObject.getName(), findActionsForFolder);
                        actions.add(menu);
                    } else {
                        try {
                            Action action = (Action) DataObject.find(fileObject).getLookup().lookup(InstanceCookie.class).instanceCreate();
                            actions.add(action);
                        } catch (IOException ex) {
                            Exceptions.printStackTrace(ex);
                        } catch (ClassNotFoundException ex) {
                            Exceptions.printStackTrace(ex);
                        }
                    }
                }
}
                return actions.toArray(new Action[actions.size()]);
            }
        };

I’ll leave it as an exercise for you to change the code to use InstanceCookie.Of…
And here’s the MenuNode:

class MenuAction extends AbstractAction implements Presenter.Popup, Presenter.Menu {

Action[] actions;
String name;
public JMenu menu;

public MenuAction(String name, Action[] findActionsForFolder) {
super(name);
this.name = name;
this.actions = findActionsForFolder;
this.menu = new JMenu(name);
for (Action action : actions) {
if (action instanceof Presenter.Popup) {
menu.add(((Presenter.Popup)action).getPopupPresenter());
} else {
menu.add(action);
}

}
}

@Override
public void actionPerformed(ActionEvent e) {
}

@Override
public JMenuItem getPopupPresenter() {

return menu;
}

@Override
public JMenuItem getMenuPresenter() {
return menu;
}
}


That’s it. Now register your actions under MYPATH in hierarchies, e.g.:

@ActionID(
category = "Build",
id = "asd.SomeAction")
@ActionRegistration(
displayName = "#CTL_SomeAction")
@ActionReference(path = "MYPATH/mysubcategory/usd", position = 0)
@Messages("CTL_SomeAction=asd")
public final class SomeAction implements ActionListener {

@Override
public void actionPerformed(ActionEvent e) {
// TODO implement action body
}
}

Dieser Eintrag wurde in netbeans geschrieben. Link merken.

Hinterlasse eine Antwort

Deine E-Mail-Adresse wird nicht veröffentlicht. Erforderliche Felder sind markiert *

Du kannst folgende HTML-Tags benutzen: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <strike> <strong>