×
Namespaces

Variants
Actions

How to build a Canvas based list in Java ME

From Nokia Developer Wiki
Jump to: navigation, search
Article Metadata
Article
Created: jappit (11 Sep 2008)
Last edited: hamishwillee (09 Aug 2013)

This article explains how it is possible to build a Canvas based List in Java ME.

Java me canvas based list.png

It is possible to see this code in action on this page: Java ME Canvas based list in action

Source code: CanvasList

To start, you should define the CanvasList class, that will extend Canvas:

public class CanvasList extends Canvas
{
}

First thing to do now is to define some style-related properties, that will be used to paint the List items. Name of single properties is self-explaining.

int linePadding = 2;
int margin = 2;
int padding = 2;
Font font = Font.getDefaultFont();
 
int bgColor = 0xffffff;
 
int foreColor = 0x000000;
int foreSelectedColor = 0xffffff;
int backColor = 0xffffff;
int backSelectedColor = 0x0000ff;
 
int borderWidth = 3;
int borderColor = 0x000000;
int borderSelectedColor = 0xff0000;

Now, here are some internal properties, that will be used to handle list items content and positioning.

// will contain item splitted lines
String[][] itemLines = null;
// will hold items image parts
Image[] images = null;
// will hold selected item index
public int selectedItem = 0;
 
// these will hold item graphical properties
int[] itemsTop = null;
int[] itemsHeight = null;
 
// this will hold the whole list height
int listHeight = 0;
 
// these will hold List vertical scrolling
int scrollTop = 0;
final int SCROLL_STEP = 40;

Now, here is the CanvasList constructor. Its arguments are (similarly to javax.microedition.lcdui.List constructor):

  • the screen's title
  • set of strings specifying the string parts of the List elements
  • set of images specifying the image parts of the List elements

This article will not cover the handling of different types of Lists (e.g.: exclusive, multiple, ..).

public CanvasList(String title, String[] items, Image[] imageElements)
{
setTitle(title);
 
this.images = imageElements;
 
itemLines = new String[items.length][];
 
itemsTop = new int[itemLines.length];
itemsHeight = new int[itemLines.length];
 
for(int i = 0; i < itemLines.length; i++)
{
// get image part of this item, if available
Image imagePart = getImage(i);
 
// get avaiable width for text
int w = getItemWidth() - (imagePart != null ? imagePart.getWidth() + padding : 0);
 
// and split item text into text rows, to fit available width
itemLines[i] = getTextRows((String) items[i], font, w);
}
}

Here are the 2 utility methods found in the CanvasList constructor:

public int getItemWidth()
{
return getWidth() - 2 * borderWidth - 2 * padding - 2 * margin;
}
Image getImage(int index)
{
return images != null && images.length > index ? images[index] : null;
}

Now, here is the paint() method:

protected void paint(Graphics g)
{
// paint List background
g.setColor(bgColor);
g.fillRect(0, 0, getWidth(), getHeight());
 
// translate accordingly to current List vertical scroll
g.translate(0, - scrollTop);
 
int top = 0;
 
g.setFont(font);
 
// loop List items
for(int i = 0; i < itemLines.length; i++)
{
int itemRows = itemLines[i].length;
 
Image imagePart = getImage(i);
 
int itemHeight = itemRows * font.getHeight() + linePadding * (itemRows - 1);
 
itemsTop[i] = top;
itemsHeight[i] = itemHeight;
 
// is image part higher than the text part?
if(imagePart != null && imagePart.getHeight() > itemHeight)
{
itemHeight = imagePart.getHeight();
}
itemHeight += 2 * padding + 2 * borderWidth;
 
g.translate(0, top);
 
if(borderWidth > 0)
{
// paint item border
g.setColor(i == selectedItem ? borderSelectedColor : borderColor);
g.fillRect(margin, margin, getWidth() - 2 * margin, itemHeight);
}
 
// paint item background
g.setColor(i == selectedItem ? backSelectedColor : backColor);
g.fillRect(margin + borderWidth, margin + borderWidth, getWidth() - 2 * margin - 2 * borderWidth, itemHeight - 2 * borderWidth);
 
// has this item an image part?
if(imagePart != null)
{
g.drawImage(imagePart, margin + borderWidth + padding, margin + borderWidth + padding, Graphics.TOP | Graphics.LEFT);
}
 
// paint item text rows
g.setColor(i == selectedItem ? foreSelectedColor : foreColor);
 
int textLeft = margin + borderWidth + padding + (imagePart != null ? imagePart.getWidth() + padding : 0);
 
for(int j = 0; j < itemRows; j++)
{
g.drawString(itemLines[i][j], textLeft, margin + borderWidth + padding + j * (linePadding + font.getHeight()), Graphics.TOP | Graphics.LEFT);
}
 
g.translate(0, - top);
 
top += itemHeight + 2 * margin;
}
 
// set current list height
listHeight = top;
 
// finally, translate back
g.translate(0, scrollTop);
}

And finally, to handle user key events, here is the keyPressed() event:

protected void keyPressed(int key)
{
int keyCode = getGameAction(key);
 
// is there 1 item at least?
if(itemLines.length > 0)
{
// going up
if(keyCode == Canvas.UP)
{
// current item is clipped on top, so can scroll up
if(itemsTop[selectedItem] < scrollTop)
{
scrollList(- SCROLL_STEP);
}
// is there a previous item?
else if(selectedItem > 0)
{
selectedItem--;
 
repaint();
}
}
//going down
else if(keyCode == Canvas.DOWN)
{
// current item is clipped on bottom, so can scroll down
if(itemsTop[selectedItem] + itemsHeight[selectedItem] >= scrollTop + getHeight())
{
scrollList(SCROLL_STEP);
}
// is there a following item?
else if(selectedItem < itemLines.length - 1)
{
selectedItem++;
 
repaint();
}
}
}
}
protected void scrollList(int deltaY)
{
scrollTop += deltaY;
 
if(scrollTop < 0)
scrollTop = 0;
else if(scrollTop + getHeight() > listHeight)
scrollTop = listHeight - getHeight();
 
repaint();
}

About the getTextRows() method, you can grab its implementation on this other Wiki article: Scrollable Text in Java ME


Source code: sample usage

Here is a sample usage of CanvasList class, that will display a list (without image parts):

String[] items = new String[]{"Item 1", "Item 2", "Item 3"};
 
CanvasList myCanvas = new CanvasList("Test canvas", items, null);

Download code

You can download CanvasList source code here: CanvasList.java

This page was last modified on 9 August 2013, at 09:18.
100 page views in the last 30 days.
×