How-to use the AutoCompleteField

How-to

Version 5.0 of the BlackBerry® Development Platform introduces a number of improvements that make it even easier for you to develop compelling user interfaces. One of these improvements is the introduction of a new AutoCompleteField.

In this article, we will get our feet wet by looking at how the field makes it easier for users to quickly enter information. As a user types characters in the field the characters are compared to a data source, and matches are displayed in a list box below the field. The user can select one of the presented options or continue to type to further narrow the list.

The above screenshot shows an AutoCompleteField bound to a dataset comprised of an array of strings – the days of the week.

Here’s the source code for an application that displays the above field.

import net.rim.device.api.ui.UiApplication;
import net.rim.device.api.ui.container.MainScreen;
import net.rim.device.api.ui.component.AutoCompleteField;
import net.rim.device.api.collection.util.*;

public class AutoCompleteFieldApp extends UiApplication
{
  public static void main(String[] args)
  {
    AutoCompleteFieldApp app = new AutoCompleteFieldApp();
    app.enterEventDispatcher();
  }

  AutoCompleteFieldApp()
  {
    HomeScreen scr = new HomeScreen();
    this.pushScreen(scr);
  }
}

class HomeScreen extends MainScreen
{
  public HomeScreen()
  {
    BasicFilteredList filterList = new BasicFilteredList();
    String[] days = {"Monday","Tuesday","Wednesday",
                     "Thursday","Friday","Saturday","Sunday"};
    filterList.addDataSet(1,days,"days",BasicFilteredList.COMPARISON_IGNORE_CASE);
    AutoCompleteField autoCompleteField = new AutoCompleteField(filterList);
    add(autoCompleteField);
  }
}

Although you create an AutoCompleteField by constructing an AutoCompleteField object and adding it to a screen, the real work involved is in constructing the associated dataset to compare against – represented by a BasicFilteredList object. When you construct an AutoCompleteField, you pass in an instance of a BasicFilteredList that is bound to the data to be searched against.

There are a few different types of data you can bind to a BasicFilteredList. In the example above, we used the addDataSet() method to bind an array of strings. But the more interesting option is to use the addDataSource() method to bind data sources like contacts, pictures and tasks. The following code snippet demonstrates how to do that. Specifically, it demonstrates how to use Contacts as a data source and searches against and returns results from the email and name fields of the Contacts database.

BasicFilteredList filterList = new BasicFilteredList();
filterList.addDataSource(
1,                                                 //1st
BasicFilteredList.DATA_SOURCE_CONTACTS,            //2nd
BasicFilteredList.DATA_FIELD_CONTACTS_EMAIL,       //3rd
BasicFilteredList.DATA_FIELD_CONTACTS_EMAIL|       //4th
 BasicFilteredList.DATA_FIELD_CONTACTS_NAME_FULL,  //4th continued
BasicFilteredList.DATA_FIELD_CONTACTS_NAME_FULL,   //5th
BasicFilteredList.DATA_FIELD_CONTACTS_EMAIL,       //6th
"Contact email");

AutoCompleteField autoCompleteField = new AutoCompleteField(filterList);
add(autoCompleteField);

The addDataSource() method takes more parameters than you might expect. So, let’s walk through each of them and explain their purpose.

Parameter Purpose
1st This is a unique ID that you define for the data source.
2nd This is the type of data source. See the API reference for BasicFilteredList for a complete list of available data sources.
3rd These are the fields within the data source to search. When you specify a field, make sure it corresponds to the data source you are using. In this case, we’re using the CONTACTS data source, so we have to use fields like CONTACTS_EMAIL or CONTACTS_NAME_FULL. To search more than one field, include both fields with a bitwise OR operator (|) between them.
4th This is the field you want returned. In this case, we searched on email address and want to return the email address that matched. But this parameter lets you return fields other than the one you searched on. And, because we want to use the full name of the contact as the primary field (see the description of the next parameter), we need to specify it here to have it returned. Basically, any field that you are going to use following the search, must be specified in this parameter.
5th This parameter designates one of the returned fields (must be one passed in the 4th parameter) as the primary field. The primary field is used by AutoCompleteField in displaying results to the user. You can control how results are displayed by specifying style flags when you construct AutoCompleteField.
6th This parameter designates one of the returned fields (must be one passed in the 4th parameter) as the secondary field. The secondary field is used by AutoCompleteField in displaying results to the user. By default, the value of the secondary field is displayed in parentheses after the value of the primary field. You can control how results are displayed by specifying style flags when you construct AutoCompleteField. If you do not want to specify a secondary field, use the value -1.
7th This is a name that you define for the data source. The data source name can be used by AutoCompleteField in displaying results to the user. Again, you can control how results are displayed by specifying style flags when you construct AutoCompleteField.

Replacing the body of the HomeScreen constructor in the original sample with the snippet above gives us a program that displays the following:

Notice that what we type is compared to the email addresses of our contacts – even though the full name of the contact is also returned. We specified the field to match against in the 3rd parameter of addDataSource() – namely BasicFilteredList.DATA_FIELD_CONTACTS_EMAIL.

As we’ve mentioned, you can control how the field displays results to the user. You do this by specifying style flags in the second parameter of the AutoCompleteField constructor. The screenshot above shows what the display looks like by default – the value of the primary field is displayed, followed by the value of the secondary field in parenthesis.

Here’s a snippet of code that demonstrates how to use an AutoCompleteField style flag.

AutoCompleteField autoCompleteField =
new AutoCompleteField(filterList,AutoCompleteField.LIST_SHOW_DATA_SET_NAME);

This style flag indicates that the displayed results should be prefixed by the name of the bound data set – “Contact email” in this case. Here’s what the result looks like:

You can find a list of the available style flags in the API reference for AutoCompleteField.

The AutoCompleteField and BasicFilteredList team provide a lot more functionality than we’ve explored here. For instance, two other types of data sources are supported. You can bind to any array of objects – in which case the string that is compared against is that returned by toString(). Or, you can bind to an array of strings and an associated array of objects. The arrays are associated one-to-one with each other by index. Searches take place against the string array and you specify the fields from the corresponding object to return as results. Oh, and you can create your own custom versions of the field or make creative use of the BasicFilteredList functionality on its own.

But that’s enough for this post. Please leave comments to let us know if you’d like to see more information about this functionality or other BlackBerry JDE 5.0 features.

About Dean T.

Dean is a Technical Writer at Research In Motion (RIM). He writes documentation for developers, so writing for the BlackBerry Developer's Blog is a natural extension of what he does every day. He has been in the software industry for about 15 years and is either completely delusional or still enjoys it. Either way, he loves being the first to try out a new API and thinks the only way to really understand something is to try to explain it to others. He hopes his posts will be easy to read and useful.

Join the conversation

Show comments Hide comments
+ -
blog comments powered by Disqus