Skip to end of metadata
Go to start of metadata

You are viewing an old version of this page. View the current version.

Compare with Current View Page History

« Previous Version 4 Next »

Command Framework

The command framework in the ReportDesigner is used to create menubars, toolbars and popup menus. The design of the framework simplifies the separation of model, view and control.

The main advantage lies in the updating of the presentations (actual menubar, toolbar) depending on the context. The command framework is responsible to detect whenever the underlying model, selection or focused element changes and makes the commands update its presentations. Commands don't have to register listeners in the model nor must commands know the exact structure of the application their working on. Only the data is important to a command. A command which moves the selected ReportElement 10 pixels up can simply ask for the selected element and call setPosition on this element. The element  can be selected in the structure tree or the main report panel or somewhere else, it does not matter to the command. The command does not even have to know that a structure tree is existing in the application.

Main classes involved when using the framework

org.pentaho.reportdesigner.lib.client.commands.Command

Interface implemented by all commands used to create a toolbarbutton or menu item. Implementations should be stateless. The command class implements the controller part of an action. One command can appear multiple times on the user interface and should therefore be stateless.
Samples of commands: OpenReportCommand, SaveReportCommand, ExitCommand

org.pentaho.reportdesigner.lib.client.commands.Presentation 

The presentation is the view of a command. It holds localized text, descriptions, icons, accelerator. Multiple presentations of a command can exist at the same time. e.g one presentation in the menubar, one in the toolbar and one temporarily in a popup menu. The command is responsible to update the presentation whenever the update method is called. A command usually disables the presentation when the required data is not available. The command can also change the text/icon/visibility of the presentation. e.g The undo command might change the text to contain a description of the operation to undo ("Undo change background").

org.pentaho.reportdesigner.lib.client.commands.CommandGroup

A CommandGroup can contain a set of commands belonging together.
Sample of a command group: Align Left/Center/Right etc. form a group. The group itself can be specified to be of type popup or normal to change the appearance type in the menubar or toolbar.

org.pentaho.reportdesigner.lib.client.commands.DataContext

Interface used by commands to request data of the current context. The context is usually focus dependent and changes whenever the user selects another component/element or the reporting model changes by an automated action from a background thread.
The datacontext is determined by the command framework by hierarchically walking the component tree from the deepest focused component upwards to the frame. The first encountered DataProvider is used to return the datacontext.

org.pentaho.reportdesigner.lib.client.commands.CommandManager

Central class to register command groups using a key. This class is used to create a menubar, toolbar or popup menu from the previously defined key.
e.g a command group containing all commands destined for the toolbar can be registerd using the key "Toolbar" (the key is completely user defined and has no special meaning).

Howto create a command from scratch 

Step 1: Create the command class (controller)

public class MoveUpCommand extends AbstractCommand
{
    public SampleMoveUpCommand()
    {
        super("MoveUpCommand");
        getTemplatePresentation().setText("Move 10 pixels up");
    }


    public void update(@NotNull CommandEvent event)
    {
        ReportElement[] selectedElements = (ReportElement[]) event.getDataContext().getData(CommandKeys.KEY_SELECTED_ELEMENTS_ARRAY);
        event.getPresentation().setEnabled(selectedElements != null && selectedElements.length > 0);//only enable when something is selected
    }


    public void execute(@NotNull CommandEvent event)
    {
        ReportDialog reportDialog = (ReportDialog) event.getPresentation().getCommandApplicationRoot();
        reportDialog.getUndo().startTransaction(UndoConstants.MOVE_UP);
        ReportElement[] reportElements = (ReportElement[]) event.getDataContext().getData(CommandKeys.KEY_SELECTED_ELEMENTS_ARRAY);
        if (reportElements != null)
        {
            for (ReportElement reportElement : reportElements)
            {
                double x = reportElement.getPosition().x;
                double y = reportElement.getPosition().y - 10;
                reportElement.setPosition(new Point2D.Double(x, y));
            }
        }
        reportDialog.getUndo().endTransaction();
    }
}

The update method is automatically invoked whenever the command framework likes to (don't assume anything). The CommandEvent contains the presentation that should be updated. The update method is usually invoked for every presentation (e.g toolbar and menubar) of a command.

The execute method is invoked when a user selects the menuitem or presses the toolbar button. The datacontext accessible in the execute method returns the same data as the datacontext returned in the last update call. But it's usually a good idea to prevent

NPEs by checking for null.

Step 2: Register the command in a group. 

CommandManager.addCommandToGroup(reportDialog, "Toolbar", new MoveUpCommand(), CommandConstraint.LAST);

Additional commands could be added the the "Toolbar" group.

Step 3: Creating a toolbar and adding the JToolbar to the UI.

commandToolBar = CommandManager.createCommandToolBar(this, "Toolbar");
getContentPane().add(commandToolBar.getToolBar(), BorderLayout.NORTH);




  • No labels