Edit online

Disable Context-Sensitive Menu Items for Custom Author Actions

Use Case

You want to disable menu items for custom Author mode actions depending on the cursor context.

Solution

By default, Oxygen XML Editor does not toggle the enabled/disabled states for actions based on whether or not the activation XPath expressions for that certain Author mode action are fulfilled. This is done because the actions can be many and evaluating XPath expression on each cursor move can lead to performance problems. However, if you have your own ro.sync.ecss.extensions.api.ExtensionsBundle implementation you can overwrite the method:

ro.sync.ecss.extensions.api.ExtensionsBundle.createAuthorExtensionStateListener()

and when the extension state listener gets activated, you can use the API like this:

    /**
     * @see ro.sync.ecss.extensions.api.AuthorExtensionStateListener#activated
(ro.sync.ecss.extensions.api.AuthorAccess)
     */
    public void activated(final AuthorAccess authorAccess) {

      //Add a caret listener to enable/disable extension actions:
authorAccess.getEditorAccess().addAuthorCaretListener(new AuthorCaretListener() 
{
    @Override
    public void caretMoved(AuthorCaretEvent caretEvent) {
      try {
        Map<String, Object> authorExtensionActions = 
authorAccess.getEditorAccess().getActionsProvider().getAuthorExtensionActions();
        //Get the action used to insert a paragraph. It's ID is "paragraph"
        AbstractAction insertParagraph = (
AbstractAction) authorExtensionActions.get("paragraph");
        //Evaluate an XPath expression in context of the current node
     Object[] evaluateXPath = authorAccess.getDocumentController().evaluateXPath
(".[ancestor-or-self::p]", false, false, false, false);
        if(evaluateXPath != null && evaluateXPath.length > 0 && 
evaluateXPath[0] != null) {
          //We are inside a paragraph, disable the action.
          insertParagraph.setEnabled(false);
        } else {
          //Enable the action
          insertParagraph.setEnabled(true);
        }
      } catch (AuthorOperationException e) {
        e.printStackTrace();
      }
    }
  });
When the extension is deactivated, you should remove the CaretListener to avoid adding multiple listeners that perform the same functionality.