Just An Application

June 27, 2009

What’s New In MIDP 3.0 ? Part 20: LCDUI – Menus

Filed under: Java, JME, LCDUI, MIDP, MIDP3, MIDP3Issues, MIDP3LCDUI — Tags: , , , , , , — Simon Lewis @ 7:09 pm

1. The Menu Model

  • a Menu is a container for a group of items, where an item is either a Command or a Menu

    • a Command cannot be present in a Menu more than once

  • a Menu has a label which will be displayed to the user

  • a Menu’s label is mutable

  • a Menu may have a long label

  • a Menu may have an associated Image which may be displayed to the user

  • a Menu may have an associated Font which may be used to render the label of the Menu itself, but it will not be used to render the labels of its items

  • a Menu may be disabled or enabled

    • if a Menu is disabled then its items are not available for selection by the user

  • a Menu may be a sub-menu of another Menu

    • a Menu may only be the sub-menu of one other Menu

    • a Menu may not be a sub-menu of itself either directly or indirectly

  • there is a device specific limit on the maximum depth of a Menu tree

    • this will always be at least five

  • a Menu can be added to more than one Displayable

  • a Menu is visible if the labels of its items are visible to the user, or if if the labels of its items are visible to the user and one of its sub-Menus is also visible.

  • a Menu can only be visible on a single Display at a time

2. Attributes

A Menu has the same attributes as a Command, namely

  • a label
  • a long label (optional)
  • a font (optional)
  • an image (optional)

They have the same semantics and accessors as those in a Command.

3. Items

A Menu item can be either a Command or a Menu.

Neither a Command or a Menu can be present in a given Menu more than once. A Command can, however, be present in more than one Menu.

A Menu’s items can be considered to be a list, indexed from 0.

An item, subject to the constraints above, can be

  • appended to the list
  • inserted into the list at a specific index
  • removed from the list

When a Command in a Menu is selected the Menu is associated directly or indirectly with a Displayable, and the commandAction(Command, Displayable) method of the CommandListener, if any, associated with that Displayable will be invoked.

The implementation is responsible for handling the user selection of a sub-Menu.

Note

  • There are two things to consider when deciding whether to add an instance of Command to more than one Menu

    1. Commands are now mutable. Changes to a Command will be visible in each Menu
      in which it appears.

    2. When a Command is selected the only information available is the Displayable and the Command.
      There is no other context.

4. Functionality

4.1 Creating A Menu

An empty Menu can be created using the

    public Menu(String label, String longLabel, Image image)

constructor.

It is an error if the label argument is null and a NullPointerException will be thrown.

4.2 Disabling/Enabling A Menu

A Menu can be disabled/enabled by calling it’s

    public void setEnabled(boolean isEnabled)

passing false/true respectively.

4.3 Is A Menu Enabled ?

Whether a Menu is currently enabled can be determined by calling its

    public boolean isEnabled()

method.

4.4 Is A Menu Visible ?

Whether a Menu is currently visible can be determined by calling its

    public boolean isVisible()

method.

4.5 Item Access

4.5.1 Getting The Number Of Items In A Menu

The number of items in a Menu can be obtained calling the Menu’s

    public int size()

method.

4.5.2 Getting The Item At A Specific Index

The Command or Menu at a specific index in a Menu’s item list can be obtained by calling the Menu’s

    public Command getCommand(int index)

or

    public Menu getMenu(int index)

method respectively.

It is an error if index is less than 0, or greater than or equal to the number of items in the Menu and an IndexOutOfBoundsException will be thrown.

It is an error if the item at the specified index is not a Command or Menu respectively, and an IllegalArgumentException will be thrown.

4.5.3 Is The Item At A Specific Index A Command ?

Whether the item at a specific index in a Menu is a Command can be determined by calling the Menu’s

    public boolean isCommand(int index)

It is an error if index is less than 0, or greater than or equal to the number of items in the Menu and an IndexOutOfBoundsException will be thrown.

4.5.4 Appending An Item To A Menu

A Command or sub-Menu can be appended to a Menu by calling it’s

    public int append(Command cmd)

or

    public int append(Menu menu)

method respectively.

It is an error if the Command being appended is already present in the Menu and an IllegalArgumentException will be thrown.

It is an error if the Menu being appended is already a sub-Menu of a Menu, or if it is the root Menu of the tree containing this Menu.

It is an error if appending a Menu would result in the depth of the Menu tree exceeding the supported maximum depth, and an IllegalStateException will be thrown.

The item is added to the end of the list of items and its index is returned.

4.5.5 Inserting An Item Into A Menu At A Specific Index

A Command or Menu can be inserted into a Menu at a specific index by calling the Menu’s

    public void insert(int index, Command cmd)

or

    public void insert(int index, Menu menu)

method.

It is an error if index is negative or greater than the number of items in the Menu.

It is an error if the Command being inserted is already present in the Menu and an IllegalArgumentException will be thrown.

It is an error if Menu being inserted is already a sub-Menu of a Menu, or if it is the root Menu of the tree containing this Menu.

It is an error if inserting a Menu would result in the depth of the Menu tree exceeding the supported maximum depth, and an IllegalStateException will be thrown.

If index is less than the number of items in the Menu then the item will be inserted at that index, otherwise it will be appended to the Menu.

4.5.6 Removing An Item From A Menu

A Command or Menu can be removed from a Menu by calling its

    public void remove(Command cmd)

or

    public public void remove(Menu menu)

method repectively.

It is an error if the item is not present in the Menu and an IllegalArgumentException will be thrown.

4.5.7 Iterating Over The Items In A Menu

The Menu class does not provide a method for obtaining an Enumeration of a Menu’s items, but iterating over a Menu’s items is simple nonetheless.

Code Fragment


	...

    int nItems = menu.size();
	
    for (int i = 0; i < nItems; i++)
    {
        if (menu.isCommand(i))
        {
           Command c = menu.getCommand(i);
		   
           ...
        }
        else
        {
            Menu m = menu.getMenu(i);
         
            ...
        }
   }
   
   ...

4.6 Getting The Maximum Menu Tree Depth

The maximum supported Menu tree depth can be obtained by calling the Menu method

    public static int getMaxMenuDepth()

5. Issues

5.1 Menu Depth

At the moment the specification of Menu depth is inconsistent and either ambiguous or incomplete.

In the ‘Menu Creation and Population’ section of the Menu class documentation it says

The present depth of a menu, with the menu closest to the Displayable having depth 1, may be retrieved by the getMenuDepth() method.

In the Menu.getMenuDepth() method documentation it says

Returns this menu’s depth within its menu tree. The top menu is of depth 0, the menus attached to it are of depth 1, 2, etc. The top menu is the menu in the menu tree that has [been ?] attached to a Displayable. The depth of a non-anchored menu will be -1.

Assuming it is the latter that is correct, and putting aside the somewhat mangled wording, I think what this says is

  1. the depth of a Menu directly attached to one or more Displayables is 0 (zero), and the depth of a sub-menu in this Menu tree is the parent’s depth plus one ?

  2. the depth of a Menu that is not directly attached (non-anchored ?) to any Displayable, and is not a sub-Menu of another Menu, is -1 (minus one) ?

It is not clear from the documentation what the depth of a sub-Menu in the second Menu tree is.

For this to work, assuming that you wanted it to, a Menu cannot be attached to a Displayable and be a sub-Menu of another Menu, otherwise it would theoretically have two depths. There are two ways that this could happen.

  1. if a sub-Menu is added directly to a Displayable, or

  2. if a Menu that has been added directly to a Displayable, is then added as a sub-Menu of a completely unrelated Menu

The documentation for the Displayable.setMenu(Menu,int) does not place any restrictions on the Menu to be added at all, so the first should be posssible.

The methods Menu.append(Menu) and Menu.insert(int, Menu) will both throw an IllegalArgumentException, if

if the menu already has a parent menu or if it is the top menu in this menu’s tree.

but that would not apply to a root Menu that has been added to a Displayable, so the second should be possible as well.

Things would arguably be a lot simpler if the depth of a Menu was simply its distance from the root as is more usual.

If there really is a need to be able to determine whether a Menu has been attached to one or more Displayables it would be better if there was a separate method. The information will have to be available to the implementation for it to make the proposed depth scheme work, so why not make it directly available ?

5.2 The onParentEnabled Method

The Menu class defines the method

    public void onParentEnabled(boolean enabled)

The method documentation states

Informs the menu of a change in its parent’s enabled value. The application must itself decide how the Menu should handle this information. The default is to do nothing.

To make use of this method it would be necessary to define a sub-class of the Menu class and then over-ride the implementation in Menu, but it is not clear why this would actually be useful.

Unlike a Command, a Menu can only have one parent since a Menu may only be a sub-Menu of one other Menu, so we can assume that this method would be called when the Menu containing the sub-Menu was disabled/enabled, and that is about all.

It would be useful if the specification supplied a use-case of some sorts for this method. Either that or it should be removed. At the moment an implementation is responsible for calling this method as appropriate which is fairly pointless unless there is some particularly good reason for it to exist.


Copyright (c) 2009 By Simon Lewis. All Rights Reserved.

Advertisements

2 Comments »

  1. […] a MIDlet may choose to present a Displayable’s Commands individually or grouped into Menus. […]

    Pingback by What’s New In MIDP 3.0 ? Part 21: LCDUI – Command Layout « Just An Application — June 29, 2009 @ 11:31 am

  2. […] What’s New In MIDP 3.0: Redux – Menus Filed under: JME, Java, MIDP, MIDP3, MIDP3Issues, MIDP3LCDUI, Mobile Java — Tags: Java, JME, JSR271, MIDP, MIDP3, MIDP3SpecIssues — Simon Lewis @ 9:30 pm Original Post […]

    Pingback by What’s New In MIDP 3.0: Redux – Menus « Just An Application — December 15, 2009 @ 9:30 pm


RSS feed for comments on this post. TrackBack URI

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s

Blog at WordPress.com.

%d bloggers like this: