This chapter provides some principles that you should follow when designing your ACCESS Linux Platform application. It begins by describing how an ACCESS Linux Platform device differs from other types of computers and how these differences affect your user interface design. Then it outlines a design process that helps you to create a successful user interface.
This chapter supplies only very general design principles. Read it to give yourself a grounding in ACCESS Linux Platform design. Specific guidelines are given in ACCESS Linux Platform Widget Reference.
Basic Design Principles
An ACCESS Linux Platform application should provide information that users will want to access when they are away from their desks. Its user interface should allow the user to get to the most relevant information as quickly as possible.
It's common for beginning ACCESS Linux Platform programmers and designers to believe that an ACCESS Linux Platform device is simply a very small laptop. These designers try to port their existing desktop application's look and feel directly over to the device, resulting in a very complex and often unusable interface.
Instead of duplicating a desktop application's look and feel, it is better to provide only the features that your users will want on the device. Handheld devices are designed and used for different purposes than laptop and desktop computers. Good user interface design for any platform begins by considering what the user needs to accomplish, and the ACCESS Linux Platform is no different in this regard. If you simply try to duplicate your desktop user interface on the device, your users may become frustrated and give up on your application.
This section describes some of the device's key characteristics and how they should influence the design of your user interface.
- Pocket Size
- Fast and Simple
- Low Cost, Long Battery Life, and High Value
- Seamless Connection with Desktops
Pocket Size
An ACCESS Linux Platform device has a small screen and a small keyboard—it is designed to fit in a shirt pocket. The small device size has the following effects on application design.
Applications Should Limit Data Entry
Try not to require users to enter a lot of data on the device itself. Because of the small size of the keyboard, users cannot enter data at nearly the same rate as they would with a full-sized keyboard and mouse.
Menus Are Hidden
To allow more room for data, the menu bar is not displayed by default. Instead, the menu bar is displayed by tapping the application's title bar. Because menus are hidden, users do not always realize that they are available. Limit your use of menus to power commands not necessary for the basic use of the application.
No Button Toolbars
It's common to see a long strip of buttons at the top of a desktop application. These button toolbars are not ideal for the ACCESS Linux Platform because the buttons can be hard to tell apart. Instead, provide buttons only for the most essential commands.
Less Is More
To save space, sacrifice features that don't belong on a small device. On a desktop system, users use 20% of an application's features 80% of the time. Your application should provide only that top 20% of features. Save any other functionality for the desktop application.
On a desktop system, it's easy to just add another button to the button toolbar or add another menu. For an ACCESS Linux Platform application, you'll have to resist that temptation. Otherwise, your screen becomes too cluttered, and your application becomes too complicated to use.
Fast and Simple
The ACCESS Linux Platform device is fast to use and easy to learn. Because the device's main purposes are to make it easy to communicate and to manage your life, it requires a minimal learning curve. Users should be able to pick up an ACCESS Linux Platform device and, with no training or instruction, figure out how to navigate between applications (without getting stuck) and execute basic commands.
This contrasts with desktop systems. Although desktop systems are also designed to be easy to use, there is a desktop paradigm that new users must spend a day or two learning.
Because the ACCESS Linux Platform device must be fast and easy to use, it has the following effects on application design.
Perceived Speed Is Important
On a desktop, users don't mind waiting a few seconds while an application loads because they plan to use the application for an extended amount of time. On a device, users often want to quickly look something up and then go on about their lives, and they do this several times a day (see Figure 4.1).
Figure 4.1 Opposite usage patterns
Optimize your application to these short bursts of user activity. Remember that requiring a user to spend an extra 30 seconds to find necessary information is excusable when they are sitting down for 3 hours at a desktop computer but cumbersome on a device when that is the only thing they are going to do before they turn it off.
As a rule of thumb, the user should be able to keep up with someone on the telephone when setting up appointments, looking up phone numbers, and so on. Priorities include the ability to:
- Execute key commands quickly
- Navigate to key screens quickly
- Find key data quickly (for example, phone numbers)
Minimize Required Steps
Minimize the number of steps a user must perform to see vital information. Display the most essential information on the first screen of the application. For example, Calendar always displays today's calendar or agenda when it starts up. It does so because most users access Calendar to see their current schedule or agenda 80% of the time.
Reduce clutter so that users will find the information they need quickly. Strive for a balance between providing enough information and overcrowding the screen.
Place command buttons on the first screen that perform the tasks the user will want to perform most often. Accomplishing common tasks should be fast and easy.
Choose the number of buttons on the screen carefully:
- The fewer buttons on the screen, the less time it takes to learn how to use the product. If there are too many buttons, users are forced to hunt and peck to find what they need until they eventually learn the placement of each button.
- On the other hand, keeping a few frequently used buttons on screen helps reduce the time spent learning basic functionality.
Minimize "Taps"
A given ACCESS Linux Platform device may or may not have a touchscreen. Whether the device has a touchscreen—and thus the user needs to remove a stylus and tap the screen in order to interact with on-screen widgets—or whether it does not have a touchscreen—in which case the user needs to navigate and "tap" the on-screen widgets using a one-handed navigation device such as a 5-way pad—you should ensure that most information about that data is accessible in a minimal number of taps (one or two).
Desktop user interfaces are typically designed to display commands as if they were used equally. In reality, some commands are used very frequently while most are used only rarely. Similarly, some settings are more likely to be used than others. On ACCESS Linux Platform devices, more frequently used commands and settings should be easier to find and faster to execute.
- Frequently executed software commands should be accessible by one tap.
- Infrequently used or dangerous commands may require more user action.
Table 4.1 shows how the frequency of an action maps to its accessibility in a calendaring application.
Table 4.1 Frequency of actions
This goal of minimizing taps can be taken too far. It must be balanced with other guidelines. For example, using a command button generally minimizes the taps to perform a command, but if you have too many buttons, you overcrowd the screen and introduce confusion into the interface.
Some designers break the behavior guidelines for a particular element for the sole purpose of minimizing taps. User interface elements should behave the way users expect them to behave unless there is good reason for them not to. Minimizing taps is not always a good enough reason to break guidelines.
Be Consistent
Consistency reduces the time needed to learn an application by limiting the number of things that people need to keep in their heads at once. The user should not have to memorize an entire set of rules to use the device easily. For example, the up arrow key should not do different things on different screens.
If possible, make your application consistent with the device's built-in applications; users know how to interact with them and will quickly learn your application if the user interface is similar to applications they already know.
Optimize Frequent Tasks
Most users launch Calendar to see today's schedule most of the time. Calendar helps with this task. Not only does it open to today's schedule, it also always tries to show you all of today's appointments, even if it means some of the hour blocks disappear. For example, if you have appointments at 8:00Â AM, 3:00Â PM, and 8:00Â PM, Calendar shows you all three appointments without forcing you to scroll to see that last appointment. To do so, it hides the unused hour blocks between 4:00Â PM and 8:00Â PM. (See Figure 4.2.)
Figure 4.2 Datebook calendar optimization
Similarly, Contacts is optimized to display a large number of contacts because most users will have long lists of contacts. It allows the user to divide contacts into different categories and display only the contacts in the selected category. It also has a look-up field on the main screen that allows the user to easily navigate to the contact he or she wants by pressing a key on the keyboard.
Consider providing power user features for people who use your application often. These advanced features should be easily accessible but not get in the way.
Low Cost, Long Battery Life, and High Value
Two key design goals of ACCESS Linux Platform devices have been to have the device fall into a specific price range and operate for a long time on a single charge.
Keeping costs down and battery life high are key factors in determining which hardware components are selected. Those component choices, in turn, affect the decisions you make when designing your applications.
Keep User Costs Down
Your application should help keep user costs down by maximizing battery life. To maximize battery life, consider your actions carefully before performing tasks that consume a lot of power. Wireless communications, playing video or even sounds, disabling the auto-off feature, and extended animation are among the tasks that consume a lot of power. When your application must perform these tasks, it should do so in a way that consumes as little power as possible.
You affect battery life more with your programming choices than you do with your user interface design choices. See Chapter 10, "Improving Usability," for programming tips on reducing the amount of power consumption.
Seamless Connection with Desktops
Desktop connectivity is an integral component of the ACCESS Linux Platform platform. The device comes with software for the desktop that provides "one-button" backup and synchronization of all data on the device with the user's desktop.
Many ACCESS Linux Platform applications have a corresponding application on the desktop.
The Design Process
In the previous section, you learned the key characteristics of the ACCESS Linux Platform device and how these characteristics should affect your application's user interface. The device's characteristics were determined by a design process that focused on the user: the user wanted a fast, easy-to-use, relatively inexpensive, yet powerful device with a long battery life. All design decisions were made to give users just that.
This section introduces a user-centered design process used by successful designers both inside of and outside of ACCESS Systems Americas, Inc. You can ensure that your application is successful if you follow this process. A design process that focuses on the user is nothing particularly new or unique; successful interface designers for any platform follow a similar process.
Even though there's nothing earth-shattering here, all too often the user-centered design process is not followed. The results are poor user interfaces. For this reason, this section begins by describing the wrong approach to interface design, an approach all too commonly followed. Then it describes the recommended approach.
The Usual Approach
As soon as you know what application you're working on, it is very tempting to jump right in and start coding features, thinking you'll fix any design problems later in the development cycle. However, this is almost always the wrong way to design an application, particularly an ACCESS Linux Platform application.
To an extent, you can get away with a poor user interface when you have a large, colorful screen on a computer with almost unlimited processing power and storage. Design flaws on an ACCESS Linux Platform device are more visible.
Because application developers are comfortable with technology, their first instinct often is to focus on technological solutions. The actual user problem that they are trying to solve gets lost in the rush to add cool features.
Suppose you have been assigned to design an application for book collectors. These users want to keep track of the books they own, to whom they have lent the books out, and when they are due back. A typical technology-focused approach to this problem goes something like this:
"This application needs at least two screens. The main screen lists the books, and the second screen is a detail screen showing if the book is lent and to whom. We need a New button to create a book, so we might as well add an Edit button and a Delete button just in case. We can sort the books by title and author. For data entry, we'll allow users to scan in the ISBN number for newly acquired books in case they have a bar code scanner. That's much faster than entering ISBN numbers by hand. We can allow the users to send book titles back and forth to each other. We'll also link the application to the web in case they want to buy a book online with it..." and so on.
Shortly after this initial thought process, the initial sketches are drawn (see Figure 4.3).
Figure 4.3 Initial design sketches
As you can see, this method of application design more closely resembles a brainstorming session than a reliable process.
Such a process may or may not lead you to an acceptable application. Some problems with this initial design:
- Scanning the ISBN number might be nice, but that only gives you the ISBN number. The user must then translate that into a book title by looking up the number on the web. What if the user does not have a bar code scanner on the device or owns a lot of old books that do not have an ISBN number?
- Sending the book title to another user has little utility and requires a lot of power. What would it mean to send a book title to someone else?
- Forcing the user to navigate to a detail screen to show who has borrowed the book might become tedious if what the user really wants is to scan through his or her list of books and know at a glance which books have been loaned out.
The Recommended Approach
Now that we've learned a little bit about the usual approach to interface design, let's discuss a better approach. The better approach is a multi-step process that is more likely to give you the desired results: lots of happy users willing to part with their money. The steps to the right approach are:
- Decide on Design Goals
- Know Your Users
- Develop User Scenarios
- Propose an Implementation
- Develop the Initial Design Concept
- Complete the Design
You might not follow all of this design process exactly as it is described here, particularly if you work in a small company or by yourself. Creating software is a complicated task affected by a lot of variables. Every project is unique. Still, it's useful to know about this recommended user interface design process and to try to follow it as closely as possible.
Decide on Design Goals
The ACCESS Linux Platform designers made decisions to achieve these design goals: a device that fits in a shirt pocket, is fast and simple to use, requires no learning curve, and has a worry-free battery life. Just as the ACCESS Linux Platform designers started with their design goals, you should start with a design goal for your application. A generic set of design goals for all ACCESS Linux Platform applications is the following:
- Easy to learn and use
- Convenient
- Provides access to what most people want and need most of the time
- Helps users quickly achieve their goals
Your application may have additional goals, but to be successful on the ACCESS Linux Platform, it should achieve the design goals listed above.
In a small company, you'll no doubt come up with the application idea and its design goals on your own. In a large company, the design goals should come from the Marketing department. Consider the Books application example from the previous section. The statement of what the application should do may have come from the Marketing department of a large company or it may have been an independent idea. "Create an application that allows book collectors to keep track of their books, to whom they have loaned them out, and when." To this, the traditional ACCESS Linux Platform design goals simply adds adverbs: "Create an application that allows book lovers to quickly and easily keep track of their books and to whom they have loaned them."
Know Your Users
Users come in all shapes and sizes. If you are like most computer professionals, then you are not the typical user of an ACCESS Linux Platform device or of your future product.
Handheld devices attract many people outside the computer industry due to their ease of use. Because you work in the computer industry, you are comfortable with the differences between "hardware," "software," and "applications." Typical users outside of the industry see the ACCESS Linux Platform device as one integrated device. They have no notion of what indicates a hardware problem, a software problem, or an application bug. They only know that they have a task to perform, and they want their ACCESS Linux Platform devices to help them with that task.
Examine the user base your application is likely to attract. If possible, set up a focus group to learn more about your target users and why they want to use your application. A wine database application is likely to attract a wide non-technical audience. A utility to examine internal memory is going to have a mostly technical audience. A computer game might attract both the technical and non-technical members of the ACCESS Linux Platform community.
For broad audiences, you'll want to follow the built-in applications as much as possible. Users already know how to use those, so they will implicitly know how to use your application as well. Don't "improve" the features.
If you have a narrow, highly technical audience, you can probably get away with a lot more in your user interface design; however, it never hurts to have an excellent interface. Your users will appreciate your application more if you do.
Like the design goals from the previous section, a description of the typical user is another piece of information that often comes from a Marketing department. A small company may not have the luxury of a large Marketing department with expertise in market research; however, you can still identify target users among your friends and family and talk to them about their needs.
For our Books application, we have discovered that people who are likely to buy our application have the following characteristics:
- They love to read.
- They typically own hundreds of books.
- They spend much free time browsing book stores.
- They often can't remember which books they own, which they don't, and which they own but still haven't read.
- Many freely loan books to friends, which becomes a problem when trying to determine which books they own.
- Many are not very comfortable with technology.
Because a large part of our target audience is uncomfortable with technology, we'll need to make our application as easy to use as possible, and we'll need to focus on making it work like the built-in ACCESS Linux Platform applications with which our user base is already familiar.
Develop User Scenarios
After gathering a picture of your typical user, begin your design by considering that user. What problem is the user trying to solve by using your application? Under what circumstances will they be using the application? Will they be at the office, the airport, at home, or in the car?
Develop some user scenarios. User scenarios are statements of what the user will do with the application and when. "The user needs to access email five times a day while riding on the subway" is a good scenario statement. It describes what the user is doing, where he or she is doing it, and how often. The best way to develop user scenarios is, of course, to talk to potential users, whether in focus groups or through other means.
To determine user scenarios, you must know these things:
- The likelihood that the user will perform a task
- The frequency with which the user will perform the task
For example, starting up the calendar application to access today's schedule is both likely and frequent—it is often done several times throughout the day. Tasks that are likely and frequent should be the easiest to perform.
Scheduling an appointment is another task that is both likely and frequent; however, scheduling a appointment that begins at other than a half hour or hour (for example, at 3:05) is unlikely and infrequent. We might allow people to schedule such appointments, but we can require more taps to do so because we know it is infrequently done.
A task may be likely but infrequent. For example, users are likely to run the Welcome application because it is always the first application run when they start up a new ACCESS Linux Platform device. However, it usually is only run that one time, so its use is infrequent.
Develop as many scenarios as possible, including those you imagine to be unlikely and infrequent. This is a tricky stage in the design process. It's easy to come up with only scenarios that support preconceived notions of the application development team. If you focus only on those scenarios, you'll end up with an application that meets the needs of your team but not necessarily the needs of your users. An exhaustive user scenario effort keeps you focused on the needs of the users.
Remember our discussion of the wrong approach to designing the Books application? We came up with a design that involved bar code scanning, beaming, and buying books using a wireless Internet connection. These were not bad ideas, but we've since learned that our user base is likely to include many people uncomfortable with technology. Such people most certainly don't have bar code scanners. So we'll have to abandon our ideas of scanning ISBN numbers.
Since the technology-focused design has led us down the wrong path, let's consider doing some user scenarios for the application:
- Users want to see a list of all of the books they own, which may number in the hundreds. (likely, frequent)
- Users are at a bookstore and want to see if they own a particular book. (likely, frequent)
- Users are at a bookstore and want to add a newly purchased book to the list. (likely, frequent)
- Users are away from their desktop computers and want to buy a book on the Internet (unlikely, infrequent)
- Users want to lend a book to a friend (likely, infrequent).
- Users are at home, looking for a particular book, and want to see if it is loaned out. (likely, frequent)
- Users want to see all books they have loaned out. (likely, infrequent)
- Users want to see all books they own by a particular author or about a particular subject. (likely, infrequent)
- Users want to see all books they have loaned to a given person and when they are due back. (unlikely, infrequent)
- Users have a bar code scanner and want to scan in the ISBN number of a new book. (unlikely, infrequent)
Notice that we have not yet focused on how to solve the users problems in these first three design steps (decide on design goals, know the user, and develop user scenarios). Instead, we have focused on understanding our users so that we can solve their problems.
Propose an Implementation
Now that we have an idea of who the user is and how the user will use our application, the next step is to describe the proposed implementation of the application. This description should focus on the feel of the application rather than its look. In this way, the proposed implementation flows naturally from the user scenarios.
The idea behind this step is twofold. First, once everybody involved in designing and developing the application agree upon the proposed implementation, engineers can begin to architect the features at the same time that human interface designers are designing the look. Second, by focusing on the feel of the application, you postpone the traditional arguments about the application look, which may unnecessarily delay software development at this point.
If you are working alone, of course, these two reasons for proposing an implementation before developing the look are not relevant. You may find it helpful to write the software without focusing much on the look until a little later, or you may not. Either way, you still should develop an implementation that flows from the user scenarios and the description of the typical users you created in the previous steps.
The proposed implementation for our Books application is:
- The initial screen will look very similar to the Contacts application. It will be a list of all owned books, sorted alphabetically by title. We've decided to mimic the Contacts application's main screen so that users will instantly feel familiar with our application.
- Because users may own hundreds of books, we will allow them to type on the keyboard to quickly navigate through this list of books in the same way they navigate through Contacts.
- To allow the user to quickly determine whether he or she owns a particular book, we will provide filters that allow special displays: All books by a particular author, all books on a particular subject, all books currently on loan.
- The initial screen will provide ways to enter a new book or to see more details about a book.
- The Details screen will have fields for title, author, and category and will have a way to loan a book to a friend.
- The main screen will have a way to indicate which books are out on loan so that the user can quickly scroll through the list and see which books are out on loan.
- To ease data entry, we'll provide enable integration with a desktop application so users can enter most of their books on the desktop and synchronize them down to the device. People often buy several books by the same author, so we'll provide name completion for the author name based on existing authors in the database.
- We'll also integrate with other built-in applications. Loaning a book to a friend is linked to Contacts as the friend's name and contact information is likely to be included there. We might integrate with Calendar by entering an event on the date that a friend is to return a book; however, because many people do not assign due dates when they lend to friends, we would make this an optional feature enabled by a user preference rather than a feature that is always available.
Recall that in our technology-focused design approach, we immediately came up with an Edit and Delete button in addition to the New button (plus scanning and sending—ideas we all but eliminated in the previous steps). In focusing on what tasks the user will perform most often, the Edit and Delete buttons did not come up in the conversation. Information about a book does not change, so the Edit button isn't as important as it is in, say, Contacts. Book lovers rarely throw away books either. However, we should provide some way for users to correct mistakes in data entry, so we might provide Edit and Delete menu items or command buttons on a sub-screen.
Develop the Initial Design Concept
After you have described the feel of the application, it is time to develop the look. Begin by focusing on the initial design concept. The initial design focuses on the main screens. At this point, selection of user interface elements comes into play. However, the exact details of the user interface may not be pinned down and sub-screens, such as alerts, may be ignored until later on.
It's important to consider the usage frequency and likelihood of your user scenarios. More frequently used commands and settings should be easier to find and faster to execute.
To make your application's important features easily accessible, choose the appropriate user interface element. Element selection is covered in detail later in this book and in the ACCESS Linux Platform Widget Reference.
Figure 4.4 shows the initial design concept for the Books application. Notice how it differs from the initial design shown for the wrong approach (Figure 4.3).
Figure 4.4 Initial design concept
Because we took the time to study our users' wants and needs, we know that the major problem they are having is managing the hundreds of books in their collections. The likely and frequent tasks from our user scenarios involve the user wanting to see what books they own and where those books are. Because the list of books can grow to be lengthy, we've decided that the most important tasks are the presentation of the list of books and the ability to enter new books. The main screen helps the user navigate the list of books by allowing them to filter the display according to categories of the user's own choosing and by entering text in the Look Up field to navigate to a particular book. It uses an icon so that the user can easily scroll through the list of books and see which ones are out on loan. Tapping the icon shows more information about the loan. The loan information shows to whom the book is loaned, when it was loaned, when it is due back, and provides a Lookup button so that the user can quickly go to the contact information for this person in Contacts if the person needs reminding that the book is due.
We will also provide other screens: a Preferences dialog that allows the user to sort by author name instead of title and a Search screen that allows them to search for all books loaned to a particular person. Because these tasks were described as likely but infrequent in our user scenarios, they are accessed through menu items instead of through command buttons.
You may only have sketches at this point, but it is appropriate to begin usability testing your interface at this stage to ensure that what you've designed meets the user's needs. You can mock up a user interface using technology as simple as note cards and have the user walk through common tasks. After you've performed a set of usability tests, refine your design concept and retest as you complete the next stage.
Complete the Design
After the main concepts have been agreed upon by everyone involved in the project (which might include human interface designers, marketing, and engineering), the design can be solidified. At this point, you should design every screen for the application, know how to get to every screen, have all user interface elements properly aligned and spaced on the screen, and design the menus. All error states are also defined.
This phase should coincide with the alpha build of your software. Thus, after the alpha release, you can have more user testing and feedback, which will refine your design for the beta build and then for the final build.
Notice that we complete the design during alpha development. Many developers are tempted to leave user interface design until much later in the product development cycle, but doing so is a mistake. If you wait until the end, you have solidified your initial design in the code you have written. The longer you wait to change the design, the harder it becomes to do so, and the easier it becomes to rationalize leaving the interface as-is.
ACCESS Linux Platform User Interface Elements
UI Widgets
ACCESS Linux Platform uses a version of GTK+ optimized for handheld displays. ACCESS Linux Platform adds a number of widgets to the set of GTK+ widgets that are most useful when writing applications targeted to a small screen. In addition, the platform supports Palm OS-style categories and preferences.
GTK+
GTK+ is a portable and "free" (LGPL) toolkit for creating graphical user interfaces that runs on UNIX systems (X Window or frame-buffer based) as well as on Windows platforms. ACCESS Linux Platform uses GTK+ version 2.6, which is based on X11.
GTK+ is a popular open source framework and set of libraries for the creation of graphical user interfaces by both system and application developers. GTK+ contains a full-featured widget set that is designed for high performance and has good support for internationalization.
To simplify the creation of ACCESS Linux Platform application user interfaces, developers can use Glade (version 3). Glade is a free user interface builder for GTK+ and GNOME, released under the GNU GPL license. The user interfaces designed in Glade are saved as XML and can be loaded by applications dynamically as needed.
Widget Properties
GTK+ supports two types of attributes for widgets, properties and style properties. Properties generally control widget containership and layout, while style properties generally control color and appearance—although there are many counterexamples for both. Properties can be set in the XML files produced by Glade and cannot be controlled by the theming mechanisms. Style properties can be set in the gtkrc resource file and can be controlled by theming.
Preferred GTK+ Widgets
GTK+ has an extensive list of widgets, not all of which are suitable for the small screens that will be found on ACCESS Linux Platform devices. Table 4.2 lists those GTK+ widgets that are appropriate for use in ACCESS Linux Platform applications (the set of GTK+ widgets contained in the platform is based on the subset proposed by the LiPS consortium). ACCESS Linux Platform application developers should limit themselves to the widgets in this list, plus those listed under "ACCESS Linux Platform User Interface Toolkit".
Table 4.2 Preferred GTK+ widgets
ACCESS Linux Platform adds additional widgets to GTK+ for internal use as well as for use by application developers. See "ACCESS Linux Platform User Interface Toolkit" for a list of the new ACCESS Linux Platform widgets.
GTK+ Widget Limitations
ACCESS imposes some minor limitations on a small number of GTK+ widgets.
- When using
GTKFixed, do not use the Fixed container widget. It keeps the UI from scaling on different resolution screens. UseGtkHBox,GtkVBox,GtkLayoutorGtkTableinstead. - Dialogs must use a
GtkDialogwidget as their topmost widget, not aGtkWindow. This is to allow the theme engine to properly identify the widgets in the dialog. In dialogs that do not use aGtkDialog, the widgets will not have the proper theming and look. -
GtkDialogwidgets must have thehas_separatorproperty set toFALSE. - Forms that have a title bar at the top must use the
AlpTitleBarwidget. This widget must be included as a child of the topmostGtkVBoxof the form and be packed into theGtkVBoxwith "expand" set toFALSEand "padding" set to 0. TheGtkVBoxshould have "homogeneous" set toFALSE. -
AlpTitleBaris derived fromGtkHBox; and any other widgets that appear on the title bar (combo box dropdowns, etc.) must be packed into theAlpTitleBar.
Themes
The ACCESS Linux Platform Theme Engine provides the ability to extensively customize the graphical appearance of all GTK+ applications running on the platform. A theme consists of a package that allows customization of most graphical attributes of applications, including colors, widget shapes and spacing, font and text properties, icons, and window decorations.
- One or more
gtkrcfiles used to specify widget properties. - A GTK theme engine that overrides a number of GTK
gtk_paint_*drawing functions. Each overridden function is called by one or more of the widget drawing functions. - A set of SVG files that provide vector art for drawing widgets and icons.
- An XML file that specifies properties used by the Matchbox window manager to decorate windows.
- A theme manifest file that specifies where the files in the package are to be installed and provides information needed by the theme selection dialogs.
The theme engine does not provide a general mechanism for customizing the layout of applications.
ACCESS Linux Platform includes a default theme; licensees can create additional themes as needed.
ACCESS Linux Platform User Interface Toolkit
In addition to the GTK+ widgets listed earlier, ACCESS Linux Platform adds the following widgets to simplify the process of creating applications with user interfaces optimized for small screens:
- AlpDateSelector
- AlpMediaSelector
- AlpMediaSelectorDialog
- AlpMenuBar
- AlpProgressDialog
- AlpRepeatButton
- AlpSpinButton
- AlpTimeSelector
- AlpTitleBar
It also adds the AlpSmartText engine, which enhances the GtkTextView widget to add some interactive behaviors.
AlpDateSelector
The AlpDateSelector is a widget which lets the user easily select a calendar day. It emits a day_clicked signal when the user selects a day, and emits a month_clicked signal when the user changes the month. It can be displayed with a specific day highlighted.
The AlpDateSelector widget is optimized for one-handed navigation, and supports year values ranging from 1 to 65535.
NOTE: Unlike the date selector in Palm OS, which supports the selection of a particular week or month,
AlpDateSelector only allows the selection of a single day.
AlpMediaSelector
The AlpMediaSelector widget simplifies the process of selecting media (music, photos, videos, etc.).
AlpMediaSelectorDialog
The AlpMediaSelectorDialog widget allows application developers to easily create a complete dialog that allows the user to select media (music, photos, videos, etc.).
AlpMenuBar
AlpMenuBar inherits from GtkMenuBar. In conjunction with AlpTitleBar, it allows the display of the application's menu when the user clicks the title bar. The GtkMenuBar widget doesn't have the ability to "pop-up" and disappear automatically. AlpMenuBar adds this functionality.
When the user clicks the title bar, the AlpMenuBar pops up. The menu bar then disappears when the user selects a menu item or taps outside of the menu.
AlpMenuBar creates the top-level GtkWindow as its parent window. When the menu bar pops up, it shows the top-level window and grabs mouse and keyboard events.
AlpMenuBar positions itself at the same location as the base window and makes its width the same as the base window.
AlpProgressDialog
Occasionally, operations—often, communications-related—take a noticeable amount of time to complete. For operations such as this developers can use the AlpProgressDialog widget to provide feedback to the user, indicating the progress or state of the operation.
The purpose of a progress dialog is to placate the impatient or unknowing user who may believe that the device has stopped working or crashed. The progress dialog informs the user of what the system or application is doing. If the task does not have multiple steps and if takes less than three seconds, then this dialog is not a good choice. In general, use progress dialogs sparingly.
An AlpProgressDialog widget can have a progress bar, an image, a couple of text fields, and one or more buttons. Applications can make programmatic updates to the progress bar, image, text, and other fields of the dialog as the associated operation progresses. For example, when a contact is beamed to another user, the Beam progress dialog might toggle the image between two beaming bitmaps and update the messages in the following order: "Initializing," "Starting," "Searching," "Connected," and "Sending."
The presence or absence of various elements, as well as their placement and format, can be programmatically controlled. As well, the widget has properties that control its configuration such that it can be used with a UI builder such as Glade. Finally, the AlpProgressDialog widget has a number of properties that allow it to be themed.
The AlpProgressDialog widget by default is packaged within a modal dialog window. This window can be optionally linked to a parent window; it is then transient to that parent window1 and remains on top of the parent window. The dialog window is anchored to the bottom of the parent window and its width is automatically extended to match the width of the parent window.
When the underlying operation completes, the progress dialog widget is dismissed. Because of this, the widget doesn't include an OK or Done button. The widget does provide a Cancel button to allow the user to signal their desire to abort the operation: a programmer-specified function is called when the user clicks Cancel. An attempt by the user to close the containing dialog window (window decoration permitting) is treated as if the Cancel button has been pressed.
Although the programmer can add additional buttons, doing so is discouraged.
AlpRepeatButton
Unlike GtkButton, from which it inherits, AlpRepeatButton produces a stream of "clicked" signals while the pen is held down on the button or while the center key of the 5-way navigation set is held down. Both the period after which repeating begins and the interval between "clicked" signals are customizable.
AlpSpinButton
An AlpSpinButton is a widget equipped with two small buttons, each displaying an arrow, that allows the user to alter a numeric (integer) value within a predefined range. The two small buttons increase and decrease the value. AlpSpinButton is similar in purpose to a slider, but it takes up much less screen real estate.
AlpTimeSelector
The AlpTimeSelector is a standard widget that allows the user to quickly and easily specify a time value. It supports one-handed navigation, and depending upon a preference value, presents time values in a 12 or 24 hour format.
NOTE: The
AlpTimeSelector widget only allows the user to specify a single time value. Time zones and dates are handled by other widgets.
AlpTitleBar
Traditionally in X the window title is part of the window decoration. It is controlled by the window manager, and can be moved, resized, and have its depth-order altered.
In ACCESS Linux Platform, the window title is a widget within the form that opens the form's menu when tapped. This saves screen space while the menu is not in use. AlpTitleBar implements this behavior: it displays the window's title, and pops up a specified AlpMenuBar when tapped.
AlpTitleBar inherits from GtkHBox. It uses a GtkLabel widget to present the window title. Normally, the window title is left-justified within the AlpTitleBar, but because it is made up of standard GTK widgets, the layout and contents of the title bar can be customized. For instance, you can insert another widget—a small icon, say—to the left of the label. The appearance of an AlpTitleBar can be altered programmatically, or it can be specified with .gtkrc.
AlpSmartText
The Smart Text Engine is a high-level component that works in conjunction with the GtkTextView widget and enhances the widget's behavior to:
- Recognize phone numbers, email addresses, and URLs in the text and display them as hyperlinks.
- Allow the user to activate the hyperlink. Depending upon the format of the hyperlink and (if necessary) input from the user, the Smart Text Engine dial the phone number, open a compose window in the email application, launch the web browser with the specified URL,.
The Smart Text Engine consists of two parts:
- API and an event handler for the
GtkTextView. - A library providing callbacks that parse text to identify phone numbers, email addresses, and URLs and callbacks that perform link actions.
The library can be modified and built by licensees. A sample library will be provided that parses using the regular expression functions provided by libc. When the link is clicked, the sample library uses the Exchange Manager to go to the link. By organizing the code this way, the licensee has full control over parsing and link activation.
When a user taps on one of the links, the Smart Text Engine receives an event and uses the tap location (as a position in the text buffer) to determine the tag and the range of the tagged text. The Smart Text Engine "scrapes" the tagged text from the buffer and forwards it to the Exchange Manager using a scheme based on the type of the tag, i.e., whether it's a phone number tag, an email tag, or a URL tag.
The Smart Text Engine also watches for the 5-way center press event to activate the link.
The text engine destroys itself by creating a weak reference (using g_object_weak_ref) to the text view. When the text view is destroyed, the text engine destroys itself by freeing its arrays and calling the finalize function in the parent class.
Attention Manager
The Attention Manager provides a standard mechanism by which applications can tell the user that something of significance has occurred. It is designed to support communications devices which can receive data without explicit user interaction. The Attention Manager is responsible only for interacting with the user; it is not responsible for generating those events. In particular, the Alarm Manager can be used in conjunction with the Attention Manager to inform the user that a particular point in time has been reached.
The Attention Manager provides both a single alert dialog and a list of alert-like events. Together these improve the user's experience by getting the user's attention when needed, and allowing the user to quickly deal with the attention or dismiss it for later review. This eliminates the need to click through a series of old alert dialogs. Often the user doesn't care about most of the missed appointments or phone calls—although they might care about a few of them. Without the Attention Manager, the user cannot selectively dismiss or follow up on the alert events but would instead have to deal with each alert dialog in turn.
Attentions, Alarms and Notifications
The Attention, Alarm, and Notification Managers are distinct subsystems that are often used in combination.
- The Attention Manager is designed solely to interact with the user when an event must be brought to the user's attention.
- The Alarm Manager simply sends an event to an application when a particular point in time is reached. The application can then use the Attention Manager or some other mechanism to bring the alarm to the user's attention, if appropriate.
- The Notification Manager informs those applications that have registered their interest whenever certain system-level or application-level events occur. If the user is to be informed of the event, the executable can use the Attention Manager. The Attention Manager itself uses the Notification Manager to broadcast notifications when getting the user's attention or nagging him about an existing attention item.
When the Attention Manager Isn't Appropriate
The Attention Manager is designed solely to interact with the user when an event must be brought to the user's attention. It is primarily designed for attention-getting attempts that can be effectively handled or suspended, and not necessarily for those requiring an immediate response. In particular, the Attention Manager is not intended to display error messages. Applications should use modal dialogs and other existing facilities to handle these cases.
The Attention Manager is also not intended to replace the Tasks application, or to act as a universal inbox. Applications must make it clear that an item appearing in the Attention Manager is simply a reminder, and that dismissing it does not delete or cancel the item itself. That is, saying "OK" to an attention message does not delete the appointment, and dismissing an SMS reminder does not delete the SMS message from the SMS inbox. Dismissing the event simply clears the event message from the list maintained by the Attention Manager.
Finally, note that the Attention Manager is not an event logger or event history mechanism. It only contains active attention events.
Attention Manager Design
The Attention Manager consists of the following major components:
- Attention events
- An API library for posting, updating, deleting and querying events
- A server through which events are posted, retrieved and managed.
- An application that displays the alert dialogs
- An event database and associated API
- A status bar gadget that allows quick access to the Attention Manager client application
The following is the typical flow of an attention event:
- An application (the Calendar, for example) asks the Alarm Manager to wake it up at some time in the future.
- When that future point in time is reached, the Alarm Manager sends a launch code to the application. The application then posts an attention event.
- The Attention Manager presents the appropriate alert dialog based on the event type and priority.
The Attention Manager maintains a database that stores each posted event until that event is dismissed or no longer active. The database is made up of two tables, one for the events and another to hold the properties associated with the events.
Events (and associated properties) are removed when:
- The user dismisses the event
- The source application requests that it be removed
- The event duration has expired
- The source application is removed
The Attention Manager Dialogs
The Attention Manager interacts with the user using a pair of alert dialogs. The alert item dialog is a modal window that displays a single event. The alert list dialog displays the list of active events, with the more recent events being listed first.
The Alert Item Dialog
Figure 4.5 shows an example of the Attention Manager dialog that is usually displayed when an event is first posted (whether or not this dialog is displayed depends upon the priority of the posted event). It is divided into four basic sections, all of which can be controlled by the posting event (note that the dashed lines delineating the parts of the dialog do not actually appear on screen):
- Title Area
- The event can contain a text string that specifies the text displayed in this area.
- Image or Icon
- An optional image (static or animated) or icon can be displayed here. If the event has neither an image nor an icon, a default icon is displayed.
- Text Area
- Up to eight lines of text can be displayed. Each line of text can be plain text, text with HTML markup, "smart text" (shown in the second and third lines), or a checkbox.
- Button Bar
- By default the dialog contains the three buttons shown in the figure: "OK", "Snooze", and "Go To". An optional fourth button can be added, and each button's label and function can individually specified.
Figure 4.5 Attention Manager alert item dialog
Some of the properties of the alert item dialog are:
- The dialog is modal.
- The dialog is always on top.
- If a sound resource is specified, that sound will be played. If not, a default sound will be played.
- If vibrate mode is enabled, it will be activated when the dialog is presented.
- If a Snooze button is clicked, the dialog is dismissed for the snooze period (5 minutes, by default). It reappears upon expiration of the snooze period.
The alert item dialog is meant to be intrusive and is displayed when the user's attention is required.
The Alert List Dialog
The alert list dialog has a somewhat different set of properties:
- The dialog is modal.
- The dialog is always on top.
- Clicking on an event in the list will go to that event.
- Checking an event's checkbox dismisses the event.
- Clicking on Clear All dismisses all events.
- Clicking on the alert indicator in the status bar displays and dismisses the alert list dialog.
If there are more events than will fit in the dialog, a vertical scroll bar allows the user to view the additional events.
Figure 4.6 shows the alert list dialog presenting a single event (the same event as in Figure 4.5). Each active event is listed, with the most recent at the top. In this dialog, each event is represented by three lines of text (essentially, the first three lines from the alert item dialog) along with the event's icon. If the event has no associated icon, the default icon shown in Figure 4.6 is displayed.
Figure 4.6 Attention Manager list of active events
Categories
Many ACCESS Linux Platform applications will use categories to allow the user to group records logically into manageable lists. In the user interface, categories typically appear:
- In a pop-up list in a form's title bar if the form displays multiple database records.
- In a pop-up list in dialogs (such as the Details dialog) that allow you to edit a single database record.
- In a combo box in a form's title bar if the form allows you to edit a single database record.
The Category Manager allows you to apply category information to SQLite database records, but it doesn't interact with the user in any way. That task is left up to the Category User Interface module. The APIs provided by the Category User Interface module provide a simple set of functions that:
- Display a dialog that allows the user to choose the category for the specified record in a specified database.
- Display a dialog that allows the user to edit the categories of a specified database. The user can create, delete, or rename categories.
- Create a
GtkListStoreand attach it to a specified combo box.
In ACCESS Linux Platform, categories work a lot like they do in Palm OS; although in ACCESS Linux Platform, unlike in Palm OS, a given record can be assigned to multiple categories (this feature is optional; programs have control over whether or not the displayed category list allows multiple selection).
Launching and Launch Codes
On the ACCESS Linux Platform, application execution is controlled by the Application Manager. The Application Manager is an open-source component—one of the key components of the Hiker Application Framework—that is responsible for starting and stopping applications (and moving them to the background or foreground, if appropriate). By centralizing control over application lifetimes, the Application Manager enforces the ACCESS Linux Platform application execution model whereby only one application is designated to be the "main UI" application at a given time. It also ensures that only one instance of a given application is running at one time.
The Launch Sequence
Requests to launch a given application as the main UI application are sent to the Application Manager. The Application Manager checks to see if the requested application is already running. If not, the Application Manager first shuts down (or moves to the background, as appropriate) the currently running main UI application. Then, it sets up the application execution environment, loads the application's executable, and calls its main entry point.
If the application is already running, it is relaunched. How a relaunch is performed depends upon whether or not the application has registered a relaunch handler. If so, the specified callback function is called and passed the launch codes and any parameters. If the application has not registered a specific relaunch handler, the application is first sent an exit request, which causes its gtk_main() function to exit. Then, its alp_main() function is re-invoked along with the launch codes and any parameters.
Applications aren't always launched as the main UI application, of course. For instance, an application could be launched to run in the background. Or, it can be launched to see if a particular search string is among the data that it controls, as part of a system-wide find operation. How does an application know why and how it is being launched? That is what launch codes are for.
Launch Codes
Irrespective of why an ACCESS Linux Platform application is being launched—or relaunched—it is passed one or more launch codes that allow the application to know why it is being launched or relaunched. Table 4.3 lists a number of common launch code constants. Launch codes are passed, like all parameters to alp_main(), as strings. Most launch code strings are defined as part of the Hiker Application Framework: see the reference documentation for the Application Manager for a list of system-defined launch codes.
Table 4.3 Common launch codesÂ
The application is the new "primary" application, and should display its full UI. |
||
The application is no longer the primary UI application. It should hide its UI. |
||
The application should display a particular piece of data. This launch code is often received in response to a find request (where the user has tapped on the find result) or from the Attention Manager, when the user wants to "Go To" the data associated with the alert. |
The key that uniquely identifies the data to be displayed. Your application supplied this key in response to a Find request, or passed it to the Attention Manager; see Chapter 10, "Improving Usability," for more on supporting Find and the Attention Manager. |
|
The string being searched for. See "Responding to a Find Request" for more information. |
||
Indicates that the application should be prepared for debugging. |
||
The application is being launched or relaunched to handle a notification. |
The first parameter contains the notification details. The second contains the notification type. See "Receiving Notifications" for specifics. |
|
The application is being launched or relaunched to run an exchange handler. |
||
The application is being launched because one of its alarms went off. |
An "alarm identifier" that uniquely identifies the alarm. This value was supplied when the alarm was set. See "Alerts and Alarms" for more information. |
|
The application is being launched in order to receive an attention event. |
An "event handle" that uniquely identifies the event that caused the alert to be posted. This handle is typically the key for a data record, tying the alert to a specific piece of data. See "Posting the Alert" for more information. |
|
The application is being launched as transient, and should go away when the primary application changes. |
The ALP_APP_PRIMARY launch code is the most common; nearly all applications will handle it. Many, in fact, will handle only this one launch code. It signals to the application that it is being launched as the primary UI application. Among the other launch codes, most are sent if only if your application has taken some specific action. For instance:
- Unless your application specifically sends itself to the background, or unless it has specified that it should not exit but instead be switched to the background, it won't see
ALP_APP_BACKGROUNDED. - You have to specifically tell the Application Manager (using your application's manifest) that you want to receive Find requests. Unless you do so, you won't receive
ALP_APP_FIND(and, consequently,ALP_APP_FIND_CANCEL). - You won't receive the
ALP_APP_NOTIFYlaunch code unless you specifically register for notifications. - Most applications don't handle Exchange Manager requests and thus don't encounter the
ALP_APP_EXCHANGElaunch code. - Unless you set alarms or post alerts (or unless someone else does it for you) you won't receive
ALP_APP_ALARMorALP_APP_ALERTlaunch codes.
How Launch Codes are Passed
By default, an ACCESS Linux Platform application's main entry point is its alp_main() function. Launch codes are passed through the main entry point's argc and argv parameters.
Following typical C program conventions, argc contains the number of arguments in the argv[] array of C strings. Further following C programming conventions, argv[0] contains the name by which the program was invoked. In this case, it is the full name of the bundle (for example, "bar:com.access.apps.hello").
The remaining arguments in argv are launch codes and any needed launch code parameters. Some, such as ALP_APP_PRIMARY, have no parameters. Others, such as ALP_APP_FIND, are followed by one or more parameters—in this case, the term to be searched for. Table 4.3 lists the most common system launch codes and identifies any accompanying parameters.
IMPORTANT: Launch codes can be passed in any order. Do not assume that a particular launch code—such as
ALP_APP_PRIMARY—will be the first in the list (that is, will be at argv[1]).
In our sample Hello World application, we do not support background operation, we do not respond to search requests, and we do not deal with alerts and alarms. In fact, the only launch code that our application can sensibly respond to is ALP_APP_PRIMARY; any other launch codes should be ignored. This is the reason for the regularLaunch variable, the loop in lines 53-57, and the if statement on line 59; only if ALP_APP_PRIMARY is among the launch codes sent by the Application Manager should our application actually launch. All other launch codes and any relaunch requests are ignored.
Note that many applications will respond to additional launch codes. As well, note that running applications should be prepared to have their alp_main() function called again. "Application Launch" goes into further detail on writing code to handle launch codes in general, and discusses relaunch handlers. For a detailed examination of system features such as Find, Alarms, and Alerts that operate by sending launch codes to your application, see Chapter 10, "Improving Usability."
Notifications
Notifications are general system-level or application-level events such as (but not limited to):
- application installed or uninstalled
- expansion card inserted or removed
- VFS filesystem mounted or unmounted
- incoming call
- clamshell opened or closed
- time changed
- locale changed
- low power
- device is going to sleep or is waking up
A key term in the basic definition of a notification is "general." Notifications should not be used for application-specific or directed purposes, such as alarms or find.
Notification Manager
The Notification Manager provides a mechanism for sending and receiving notifications. It consists of a server and a client library.
The Notification Manager server is a persistent thread in a separate system process which keep track of all registered notifications and broadcasts notifications to registered clients. The Notification Manager server also communicates with other Platform components such as the Bundle Manager and the Application Manager.
The Notification Manager facilitates the sending and receiving of notifications but it does not itself broadcast them. Individual components are responsible for broadcasting their own notifications.
The Notification Manager does not enforce any security policies in regard to registering and broadcasting notifications.
The Notification Manager is part of the open source Hiker Application Framework. Reference documentation for the Notification Manager is included with the Framework.
How Notifications Work
Client processes call functions in the Notification Manager client library to:
- register to receive notifications
- unregister previously registered notifications
- signal the completion of a notification
- broadcast notifications
Multiple receivers may register for the same notification. Broadcasts occur sequentially. That is, the notification is sent and handled and completed by one receiver before the notification is sent to the next receiver.
Concurrent notifications to the same process are not supported because of the additional complexity this would add to an application. When this condition occurs, the second notification must wait for the first to complete.
Broadcast Queues
Notifications are placed into broadcast queues, allowing them to be serialized. The notification at the front of the queue must have been sent to all registered clients before the next notification in the queue is broadcast. The Notification Manager actually supports up to 32 queues, allowing you to group related notifications.
While the notifications in a single queue are broadcast serially, the notifications at the head of the different broadcast queues are broadcast concurrently. When directing the Notification Manager to broadcast a particular notification, you tell it into which queues the notification should be placed. Any combination of the 32 queues can be specified—the queue argument is an unsigned 32-bit value, where each bit represents a different queue.
If you specify that a given notification be placed in multiple queues, a linkage is established such that the notification isn't sent until it reaches the head of all of the specified queues. Note that even though the notification has been assigned to multiple queues, it is only broadcast once; the linkage between the queues simply allows you to synchronize the queues.
Figure 4.7 illustrates two queues with three distinct notifications followed by a notification ("Notification 4") that has been assigned to both Queue 1 and Queue 2.
In this example, Notification 4 is not broadcast until the Notification 1, Notification 2, and Notification 3 have been broadcast. Also note that Notification 1 and Notification 2 will be broadcast in parallel. Notification 3 will not be broadcast until after Notification 2 has been broadcast.
Synchronizing across multiple queues is useful for sleep and wake notifications to ensure they are the first (sleep) and last (wake) notifications received by clients.
Broadcast Priorities
By default, notifications are added to the end of the specified broadcast queue. If you specify the ALP_NOTIFY_BROADCAST_IMMEDIATE flag when calling alp_notify_broadcast(), however, the notification is instead added to the beginning of the queue. Note that this flag is rarely used: it should only be used for extremely important notifications that would take priority over all other notifications. A "Low Battery" notification might fall into this category.
Notification Names
Notifications are identified using a string formatted like a file path. Those notifications that are generated by ACCESS Linux Platform begin with "/alp", followed by the name of the component that defines the notification, followed by (optionally) any additional grouping levels, and ending with the specific name of the notification. For instance, when the device is about to go to into sleep mode, the Power Manager sends out the following notification:
"/alp/power/wake_state/sleep"
The notification strings are all defined as constant strings, generally with a name that begins with ALP_NOTIFY_EVENT_. The name of the above sleep notification, for instance, is ALP_NOTIFY_EVENT_POWER_SLEEP.
Key Notifications
There are a great many notifications defined by the Platform; as of this writing there were 114, as listed in Table 6.1.
Of all of the notifications broadcast by various parts of the operating system, a couple stand out as particularly interesting to ACCESS Linux Platform applications:
- ALP_NOTIFY_EVENT_NOTIFY_BOOT
- The device just rebooted. Register for this only if your application needs to gain control at system boot, for instance if it needs to do some hardware configuration. Do not register for this unless you absolutely need to, since the time it takes to start up your application and process the notification simply slows the boot process. Note that if your application isn't present at boot, you'll never receive this.
- ALP_NOTIFY_EVENT_NOTIFY_INSTALL
- This notification is deprecated, and should not be used.
- ALP_NOTIFY_EVENT_NOTIFY_REGISTER
- This notification is sent when your application is first installed. This is a key notification for most applications, since this is where your application will generally register for other notifications it is interested in. (Registrations with the Notification Manager persist across system resets, so you needn't reregister for your notifications when the device reboots.) Note that you will only receive this notification is you have registered for it in your application's
Manifest.xmlfile. - ALP_NOTIFY_EVENT_POWER_SLEEP
- The device is about to switch into sleep mode.
- ALP_NOTIFY_EVENT_VOLUME_ADDED
- A removable storage device (such as an SD card) has been mounted and is available for use.
- ALP_NOTIFY_EVENT_VOLUME_REMOVED
- A removable storage device (such as an SD card) has been unmounted and is no longer available for use.
User-Created Notifications
It is possible for your application to create and broadcast its own notifications. However, doing so is rare. it is more likely that you'll want to register to receive the predefined notifications. But you can supply an application-specific notification name and accompanying data when broadcasting a notification, and if some other executable has registered for it, it will be broadcast and received just like one of the system notifications listed above.
Playing System Sounds
The audio subsystem provides two convenience functions for playing system sounds. One function plays based upon the name of the sound, and the other plays the sound from a specified file. Both of these functions are exposed in alp/media_session.h.
Playing a System Sound by Name
If you want to play the system sound designated for a particular function—the sound that is normally played when the user performs an illegal operation, say—use alp_media_session_syssnd_play(). This function takes one of the ALP_SYS_SOUND_... values defined in alp/media_defs.h indicating the type of sound to be played. Because you are specifying the sound by its function, rather than by giving a specific path to a sound file, choices the user makes in designating particular sounds to be played for particular functions are honored by your application. Thus, for instance, if the user has specified that the crowing of a rooster is to be played whenever an alarm is triggered, that sound will be played if your application plays the ALP_SYS_SOUND_ALARM sound.
Table 4.4 lists the currently defined system sound values.
Table 4.4 Standard system sounds Â
In addition to the sound to be played, you also need to specify the audio stream through which the sound should be played, plus the volume level. The audio stream is a C string; valid strings are defined in the routing table, and thus can vary from device to device. Typically you would use "system_sounds" for system sounds, but certain sounds may be more appropriately played through one of the other stream types; see Table 4.5 for a list of the more common ones.
Table 4.5 Platform-defined sound stream playback typesÂ
The volume level is an integer value that ranges from 0 to 7.
Calling this function is a simple matter, as shown here:
alp_media_session_syssnd_play(ALP_SYS_SOUND_SOFTKEY_CLICK, Â Â Â Â "system_sounds", 7);
The first time you call either of the alp_media_session_syssnd_play... functions the function will initialize the audio subsystem and play the sound. Subsequent calls do not require the initialization step. This means that for the first call, there is a small delay before the sound is played. If minimizing this delay is important for your application, call alp_media_session_syssnd_init() earlier in your application; this initializes the audio subsystem so that it needn't be initialized when the first sound is played.
High-Performance Sounds
By calling alp_media_session_syssnd_init() before the first use of alp_media_session_syssnd_play(), you can reduce the delay between the call and when the sound is actually heard to about 0.1 seconds. In certain instances—largely when playing sounds to signify that a hardware or software button has been pressed—even this is too long of a delay. For these situations, the Audio Manager has a similar function that does nearly the same thing, although it operates much faster. alp_snd_syssnd_play()—the function that corresponds to alp_media_session_syssnd_play()—also takes a string identifying the sound, a stream identifier, and a volume level. However:
- The set of "system sounds" that this function will play is much smaller.
- The volume level you supply to this function should range from 0 to 100 (as opposed to from 0 to 7 for the Media Session equivalent of this function).
You should also supply an appropriate stream identifier depending upon the system sound you are playing.
Table 4.6 lists the system sounds that can be played with this function, and the recommended stream type to use when playing each sound.
Table 4.6 alp_snd_syssnd_play() supported sounds and recommended stream types
The sound that is produced when a key on the software keyboard is pressed. |
||
"Danger" sound, indicating that something bad could possibly happen. |
Playing a System Sound File
Instead of playing the user- or system-designated sound for a particular function, as was described in "Playing a System Sound by Name," if you instead need to play the sound stored in a specific system sound file, use alp_media_session_syssnd_play_file() instead. This function takes as its first argument the absolute path to a system sound file (system sound files are typically found in /usr/share/sounds/system/ or /usr/share/sounds/ringtones/).
As with alp_media_session_syssnd_play(), you also need to specify the audio stream through which the sound should be played, plus the volume level. The audio stream is a C string; valid strings are defined in the routing table, and thus can vary from device to device. For most true system sounds you would use "system_sounds", but certain sounds may be more appropriately played through one of the other stream types. See Table 4.5 for a list of the more common ones.
The volume level is an integer value that ranges from 0 to 7.
The following shows how you can use this function to play the contents of a system sound file:
alp_media_session_syssnd_play_file( Â Â Â Â "/usr/share/sounds/system/Low_Battery.mp3", Â Â Â Â "system_sounds", 7);
The first time you call either of the alp_media_session_syssnd_play... functions the function will initialize the audio subsystem and play the sound. Subsequent calls do not require the initialization step. This means that for the first call, there is a small delay before the sound is played. If minimizing this delay is important for your application, call alp_media_session_syssnd_init() earlier in your application; this initializes the audio subsystem so that it needn't be initialized when the first sound is played.
High-Performance Sounds
By calling alp_media_session_syssnd_init() before your first call to alp_media_session_syssnd_play_file(), you can reduce the delay between the call and when the sound is actually heard to about 0.1 seconds. In certain instances—largely when playing sounds to signify that a hardware or software button has been pressed—even this is too long of a delay. For these situations, the Audio Manager has a similar function that does much the same thing, although it operates much faster. alp_snd_syssnd_play_file()—the function that corresponds to alp_media_session_syssnd_play_file()—also takes an absolute path to the file containing the sound to be played, a stream identifier, and a volume level. However:
- The specified file must be in WAV format (the
alp_media_session_syssnd_play_file()function supports a wide range of formats). - The volume level you supply to this function should range from 0 to 100 (as opposed to from 0 to 7 for the Media Session equivalent of this function).
You should also supply an appropriate stream identifier depending upon the system sound you are playing. See Table 4.5 for the most common stream types.
1. A window that is transient to another "base" window will close when the base window is closed.










