dcsimg

Exploring the ListField, Part 1

Display data with the BlackBerry ListField

Lists

We cannot ignore them — they are everywhere.

Lists of things “todo”. Things to buy. Choices to choose from.

No mobile environment would be complete without the ability to display a list of choices to a user.

Of course, every platform has their own name for them. Android calls its list a ListView and requires an “adapter” to supply the data to the list widget.

iPhone developers create lists with the UITableView and flesh out a “protocol” in Objective-C to provide the data via a callback paradigm. For the Java programmers among us, a protocol is similar to an Interface in Java.

In an earlier article we even looked at how to work with lists on the WebOS platform — back when we had high hopes for the OS.

With the introduction of the BlackBerry Torch and some new energy in the BlackBerry platform, I thought it would be worthwhile to look at programming the ListField for the BlackBerry OS.

Here is a road map of this and the next two articles in this series where we look at three progressive examples of working with the ListField:

  1. Providing data via the ListFieldCallback interface (this article)
  2. Subclassing and adding color to the list so it doesn’t look so bland
  3. Displaying data from a persistent data source

Using the ListField

There are two files in the sample project:

  • BBColorList.java — this is the entry point of the application, which extends UiApplication.
  • BBColorScreen.java — this file contains the class BBColorScreen, which extends MainScreen. This is the primary UI for the sample application.

Here is the code for the BBColorList class.

/*
 * BBColorList.java
 *
 */
package com.msi.linuxmag.cl;

import net.rim.device.api.ui.*;

class BBColorList extends UiApplication {
    BBColorList() {
        pushScreen(new BBColorScreen());
    }

    public static void main(String [] args) {
        BBColorList app = new BBColorList();
        app.enterEventDispatcher();
    }
}

This code is boiler-plate for a BlackBerry app — the entry point of the application is the main() function which creates an instance of the BBColorList app and then enters the main event handling loop. The BBColorList class creates an instance of the BBColorScreen class and “pushes” it to the foreground with a call to pushScreen. Not very exciting, but necessary. Let’s move on to the BBColorScreen class.

/*
 * BBColorScreen.java
 *
 */

package com.msi.linuxmag.cl;

import net.rim.device.api.ui.*;
import net.rim.device.api.system.*;
import net.rim.device.api.ui.container.MainScreen;
import net.rim.device.api.ui.component.LabelField;
import net.rim.device.api.ui.component.ListField;
import net.rim.device.api.ui.component.ListFieldCallback;

class BBColorScreen extends MainScreen implements ListFieldCallback{
    ListField sampleList;
    String [] listData = {"ALICEBLUE","ANTIQUEWHITE","AQUA","AQUAMARINE", \
"AZURE","BEIGE","BISQUE","BLACK","BLANCHEDIAMOND"};

    BBColorScreen() {
        super(DEFAULT_MENU);
        sampleList = new ListField();
        sampleList.setSize(listData.length);
        sampleList.setCallback(this);
        add(sampleList);
        setTitle(new LabelField("Linux Mag ListField",LabelField.USE_ALL_WIDTH | DrawStyle.HCENTER));
    }
    /* ListFieldCallback Interface methods    */
    public void drawListRow(ListField listField,Graphics graphics,int index,int y,int width)
    {
        graphics.setFont(Font.getDefault());
        graphics.drawText(listData[index],2,y,DrawStyle.TOP,width);
    }

    public int getPreferredWidth(ListField listField)
    {
        return Display.getWidth();
    }
    public Object get(ListField listField,int index)
    {
        return listData[index];
    }

    public int indexOfList(ListField listField,String prefix,int start)
    {
        try {
            int ret = -1;
            for (ret = start;ret<listField.getSize();ret++) {
                if (listData[ret].toUpperCase().startsWith(prefix.toUpperCase())) return ret;
            }
            return 0;
        } catch (Exception e) {
            return 0;
        }
    }
    /* End of ListFieldCallback Interface methods */
}

Managing data with the ListField
Managing data with the ListField

The first thing to note about this class is that it extends the MainScreen class and implements the ListFieldCallback interface. The ListFieldCallback is responsible for supplying data to an associated ListField instance.

Let’s take a moment to discuss the relationship between a ListField and its data. The ListField is responsible for managing a “list” of entries, though it knows very little about the data itself. In fact, the only thing it is aware of is the number of entries it contains. In the sample code, the number of entries in the list is assigned through the setSize() method of the ListField. Alternatively, the size may be passed in to the constructor of the ListField.

When the ListField displays data at runtime, it invokes a method named drawListRow() from its associated callback. The drawListRow is one of four methods required by the ListFieldCallback interface:

  1. drawListRow — used to draw the text/image onto the list within the specified coordinates.
  2. getPreferredWidth — used to tell the list how wide it should be drawn. This is typically the full width of the screen.
  3. get — used to retrieve an entry from the list. Note that its return type is Object.
  4. indexOfList — this is used to help find an entry from the list.

Jumping back into the code, let’s examine the constructor: BBColorScreen().

This method invokes the base class’ constructor by calling super() and then proceeds to wire up the ListField. This declarative approach to user interface design is typical of BlackBerry applications — you either like it or you don’t. I tend to prefer this over WYSIWYG because I’m a bit of a control freak and like to be able to see everything plainly in code rather than having to worry if I refreshed a separate resource file. At times it can be tedious to define everything “by hand”, I confess.

Once the ListField is created, we tell the list how large it is with a call to setSize(), passing in the number of entries in our array. If we were working with a database (called a RecordStore in BlackBerry-speak), we would likely pass in the number of records available in a RecordEnumeration, which is similar to a “record set”.

Next we assign the callback to be “this” class itself.

We add this ListField to the screen with a call to the add() method and then we assign a LabelField to be the title of the screen. The reason we use a LabelField and not just simple String literal is because we can take advantage of the drawing styles to center the text on the screen. If we had just called setTitle(“some title”), which is a valid approach, the title would be aligned to the left. Just a personal taste issue.

Ok, now we’re ready to look at the methods which are implemented for the ListFieldCallback interface. The first thing to observe about these four methods is that they each pass in an instance of a ListField. This allows the same class to provide data for multiple instances of a ListField at runtime should you choose to organize your code in this fashion. Our code has only a single ListField so it really doesn’t matter to us in this example.

The drawListRow() method takes the most arguments: a ListField instance,a Graphics object, an integer representing the ordinal of the desired list element, a vertical offset and the width available to draw with. This information tells us which object to draw and what kind of boundary we are constrained to stay within.

 public void drawListRow(ListField listField,Graphics graphics,int index,int y,int width)
    {
        graphics.setFont(Font.getDefault());
        graphics.drawText(listData[index],2,y,DrawStyle.TOP,width);
    }

In this method we assign the selected font with a call to setFont() and then draw the string via the drawText method. Pretty simple. The follow-on articles spend some more time in this method customizing the drawing activity.

Let’s jump to the getPreferredWidth() method. This method passes in a ListField instance and expects an integer return value. Because we want our ListField to span the entire width of the screen, we return Display.getWidth(). The Display class is part of the net.rim.device.api.system package and is a protected API. This means that the application must be signed before running on a physical device.

 public int getPreferredWidth(ListField listField)
    {
        return Display.getWidth();
    }

The get() method takes a ListField and integer parameter. The data behind our ListField is just an array of String objects so we can simply return the String associated with the index requested.

 public Object get(ListField listField,int index)
    {
        return listData[index];
    }

The indexOfList method takes three parameters: a ListField, a String to search for and a starting index. Implementing this function provides the functionality of searching a ListField by spelling out the desired entry.

Progressive Search Feature: searching for 'bla
Progressive Search Feature: searching for ‘bla

For example, if you have a long list and want to jump down to the entries that start with the letters “BLA”, you will jump to the first list entry which starts with those letters. The user must type fairly quickly to get the progressive search. The key to the progressive search is the start parameter. If you wait too long between keypresses, the search starts again from the top of the list.

The implementation of this code starts by indexing into the listData array at the start index and then performs a case-insensitive search against the elements of the array. If found, it returns the index of the desired element. If not, it returns 0, causing the focus to jump to the top of the list.

    public int indexOfList(ListField listField,String prefix,int start)
    {
        try {
            int ret = -1;
            for (ret = start;ret<listField.getSize();ret++) {
                if (listData[ret].toUpperCase().startsWith(prefix.toUpperCase())) return ret;
            }
            return 0;
        } catch (Exception e) {
            return 0;
        }
    }

Mastering the ListField is a core skill for any BlackBerry developer. Stay tuned for our next article which looks at making the list entries a bit more attractive.

Comments on "Exploring the ListField, Part 1"

several points insurance auto some interaction guaranteed way car insurence driver them auto insurance would need

called damages cheapest car insurance other relatives drugs alcohol cheapest auto insurance people course luck car insurance first decide exactly car insurance quote auto

pays benefits car insurance rate whole lot directory cheap car insurance thinking said earlier cheap car insurance good most insurers auto insurance involved

companies car insurance coverage against several points auto insurance claims attorney whether auto insurance quotes always important

important http://autoinsurancebit.net much online quote http://cheapcarinsurancecr.top driving history resources because http://carinsurancelit.top taken off

new car cheap car insurance isaac tells policy thoroughly car insurance quotes insurance company auto insurance association probably lurking car insurance other hand

plan car insurance quotes again driving multi-line auto insurance quotes victimized options car insurance quote insurance some states cheap car insurance quotes tax

insurance cheap insurance quotes higher than some suv insurance car correctly pay free car insurance quotes customers then might insurance auto faster than

focus car insurance companies cases paying car insurance informs classic car insurance quote year

like everyone http://carinsurancerut.info coverage limits fierce http://cheapcarinsurancecr.top fierce help http://autoinsurancersr.top keep coverage premiums http://autoinsurancegl.net line-by-line companies http://autoinsurancend.info coverage required

internet cheapest auto insurance actually possible drive smaller NJ car insurance companies around pip auto insurance quotes lower mileage see car insurance rate own past

smoke hail auto insurance quotes whether years auto insurance quotes online contributory learn more insurance auto equal had auto insurance quotes companies around

legal requirement insurance quotes auto filed therefore cheap car insurance best websites cheap car insurance calmer than coverage would auto insurance quotes such policy

phone online auto insurance look help online car insurance slid other rates cheap car insurance attended only compare while free car insurance positive

taken auto insurance should make exotic drinking car insurance quotes online best rates cheap auto insurance phone takes cheap auto insurance faster than

crashing sound auto insurance quote could something prepared car insurance cheap pay pay insurance auto other rates advice online car insurance arizona auto

insurance company auto insurance quotes especially than days cheap car insurance canadian loss generating good cheap auto insurance driving might thrive auto insurance quotes cheaper

help auto insurance file use insurance car about shopping pay cheap car insurance small town officer does car insurance long

provides free auto insurance money drivers insurance car percent insurance insurance car check-up

common question cheap insurance right something prepared cheapest auto insurance classic martin insurance quotes auto cases paying some money cheap car insurance consider many

much auto insurance quotes how many authorized payments car insurance quote work great relevant companies car insurance quotes each customers separate cheap auto insurance helpful wreak havoc cheap auto insurance deplete coverage insurance auto quote consumer anyone coverage carinsurance discounts small jewelry car insurance quotes best suits

thedebtteam help insurance car covering medical bills car insurance quotes correctly perhaps online car insurance hesitate

because insurance auto could cost free auto insurance file new drivers cheap car insurance quotes specific quotes hands car insurance drive smaller

correctly http://carinsurancequotesbp.info insurance premium company increase http://cheapautoinsurancekvo.top company increase higher risk http://cheapcarinsuranceml.top report insurance http://autoinsurancequotesdat.info finally

generating good insurance quotes auto amount extra equipment cheap car insurance calculating hundreds auto insurance quotes better about sr-22 car insurance quotes online card

payment history online car insurance better other car insurance quotes collision expenses car insurance quotes nj last few

running car insurance cracked auto auto insurance risk certain insurance car where insurance company cheap auto insurance always important

state cheap car insurance injure file car insurance cheap classic type car insurance cheap contributory yourself against car insurance quote ever wondered

adding auto insurance injury fewer cheap insurance mileage legal concurrence NJ car insurance long estimate auto insurance quotes insurance policy

good car insurance quotes could office auto insurance michigan same weight auto insurance equal pay insurance auto quote prosecute anyone

old anti-theft http://carinsuranceratescto.info offenses like rural areas http://carinsurancequotessc.top automobile insurance affordable http://cheapcarinsurancecr.top causing damage drivers having http://cheapcarinsurancefc.top two reasons same company http://cheapautoinsurancewcx.info age group license http://carinsuranceast.us committing

international motor cheap auto insurance quotes rocket science grades completion cheap auto insurance customer very technical automobile insurance quotes outstanding

Leave a Reply