Using Phone Buttons and Function Keys

Now that we've looked at URLs and card navigation, let's examine some ways to add functionality for WAP devices.

Soft Keys

Although it's been established that WAP devices vary widely, on most WAP-enabled phones, you'll find two buttons just below the display that have arrows on them. With WML, you can program these buttons for a specific application and even make them function differently between applications, decks, and cards. After you have programmed such a button, it's called a soft key.

Soft keys are instrumental to navigation on WAP devices. These buttons give the user the ability to alter his path or jump to a different card without having to navigate a full list of options. For this reason, a programmer should always use these buttons to simplify the user experience when possible.

Tip

Use soft keys to allow the user quicker access to the most popular navigation paths.


In general, there are two soft keys per WAP device but this can vary, as some devices have full alphanumeric keypads. When you program for soft keys, keep in mind the screen constraints you are operating under. For example, if your caption for a soft key is "Get Quotes," like we did for one example, the screen resolution on some devices is exceeded and the soft key is not functional.

Tip

Soft key names should be very easily understood but short. Names like "Get Quotes" or "Press to operate" are poor choices due to screen and design constraints.


In some of the prior examples, we've been embedding soft keys without any explanation to the reader, and now we will elaborate on how to use these keys. In this example, a soft key has been created to present an additional soft key which would take the user to the previous card she had just viewed.

<card id="food" title="Food">
  <p>
        Burger World<br/>
        Food Menu<br/>
        <do type="options" label="Back">
            <prev/>
        </do>
        <a href="#drinks">Drinks</a><br/>
    </p>
   </card>

The <do> tag is particularly important here as it establishes the soft key. In this particular case, we added the label Back to the options list. This will put the caption Back above one of the soft keys on our WAP device. In general, most WAP devices only have two soft keys, so be sure to use them as effectively as possible.

Another way to create a soft key is for form submission. Earlier, we spoke of the card for BurgerWorld that listed food items and their prices. If we look at that card again, you'll note there is a <do> element in this card as well. We have set the type attribute for the <do> element to accept so that the user will have no option but to submit the form.

</card>
<!-- a continuing food menu card for BurgerWorld -->
    <card id="food2" title="Food Cont.">
    <p>
                            BurgerWorld<br/>
                               <b> Food Menu (cont.)</b><br/>
                            Hamburger $$1<br/>
                            Cheeseburger $$2<br/>
                            Chickenburger $$3<br/>
                            <do type="accept" label="More" optional="false">
                                     <go href="#food3"/>
                            </do>
   </p>
                            <p>
                             Select <b>More</b> for additional menu choices.
                            </p>

 </card>

In the preceding code, the card will establish a soft key with the label More. On most WAP devices, when an accept type is prompted to the user, the device will take the earliest soft key and give this label the highest priority for display. We can illustrate this by showing the card in two ways; one with the accept, the other with an options button.

Figure 4.4 shows the BurgerWorld menu with the type attribute set to accept (this is different from what was represented in the prior code example).

Figure 4.4. Using type=accept for navigation with a soft key.


Figure 4.5 shows the BurgerWorld menu using type=options.

Figure 4.5. Using type=options for navigation with a soft key.


With this basic understanding of soft keys and actions, we are now prepared to discuss more advanced WAP topics. Special attention should be given to that material we have learned in this chapter as it provides the framework for WML and a deep understanding of the code that is needed to continue.

Using Actions

Actions allow you to define processing instructions and expand your applications beyond static content viewing. Events and tasks are the two major types of actions that we will cover in the following section.

Events are processing instructions that are initiated by some kind of user input, like pressing a soft key (discussed in the Soft Keys section of this chapter), pressing a graphically generated button on a touch-sensitive display, or speaking a voice-activated command to the device. For example, a user hits the Select soft key on her phone and initiates an event that will navigate her to another card. Events can be navigational, but they can also trigger other kinds of processing, like initiating a timer, which we will explore a little further in the following section.

Tasks are actions that occur within an event, both figuratively, as a subset of that event's operations, and literally, within the code. The <go> element, which we already discussed in this chapter, is an example of a task. Tasks are coded within the opening and closing tags of the event action they reference. Before we dive into the broader context of events, let's examine the four tasks available within events in WML: noop, refresh, prev, and go.

  • noop noop is short for "no operation" and is the simplest task in WML. The noop task simply specifies that nothing should be done, and is most commonly used for overriding template <do> tags (see later in this chapter for an in-depth discussion of task overrides).

    <noop/>
    

Tip

Use the noop task when many cards in a deck contain identical actions, with one or two exceptions. You can save time by using a deck-level <do> tag in a template, and then use the noop task to override it on a particular card where the actions are different.


  • refresh The refresh task will refresh the device's current context as specified by the setvar attribute. Often, the refresh task is used with cards that contain a timer element, to be discussed further in Chapter 10, "Using Timers."

    <refresh>
           <setvar>
    </refresh>
    
  • prev The prev task performs a pop operation on the history stack and sends the user to the most recently listed URL in the history stack.

    <prev>
           <setvar>
    </prev>
    
  • go The <go> task is the most complicated task of the four WML tasks listed here, but also the one you will probably use the most because it lends WML much of its strength and scalability. It defines navigation to a URL and can point either to a new deck or card, using a URL fragment. The earlier example we showed of the <go> task was very simple, showing only the mandatory attributes. At its most complex, using all of the optional attributes, the <go> task looks like this:

    <go
         href="home.wml"
         method="get"
         sendreferer="false"
         accept-charset="string">
      <postfield>,<setvar>
    </go>
    

To show exactly what we did in the previous code sample, let's review each of the attributes used there.

  • href The href attribute is a required attribute that lists the destination URL for this action. In this case, we used a relative URL, "home.wml". This is a mandatory attribute; without it, the operation will fail.

  • method The method attribute specifies the HTTP submission method. It tells the application how to request the URL from the server. The HTTP submission method can either be set to get or post. By setting the method attribute to get, as in this example, the code will generate an HTTP GET request, which is the default setting. Whereas get implies only a simple request for information (such as a file, an image, or a database query), post implies the form processing can update information on the server (adding or changing information in a database, placing an order, and so on) The default setting is get. More information on the method attribute and how to use the post value appears after the discussion of the postfield element. Because the method attribute has a default setting, it is optional to code it.

  • sendreferer The sendreferer attribute can be set to either true or false. By setting the sendreferer attribute to true, the device must tell the WAP gateway (using an HTTP Referer request header) what the current deck's URL is, using the smallest URL possi ble (which is, in many cases, a relative URL). This tag is designed to give some flexibility to the server. If you set this value to true, the device will inform the server of its current deck and then express the new deck as a path from the current deck. The default setting is false; therefore the attribute is optional.

  • accept-charset The accept-charset attribute provides a valid character set encoding name. The default setting for accept-charset is unknown which tells the device it should use the same character set as the one identified to transmit the deck initially. This attribute is optional.

The postfield Element

The <postfield> element is really the glue that binds the cards together. A <postfield> creates an association between a variable and a value where the variable is some local piece of data stored in the WAP device. Syntactically, the <postfield> tag will occur in the <go> request block. The syntax is much like a standard programming language's assignment.

<postfield name="price" value="3">

In this example, the variable "price" will be set to "3" on the action list.

Therefore, if BurgerWorld wanted let its wireless users move from one deck to another and still keep track of the type of food someone was interested in, we might see a <go> tag that looks something like the following:

<go href="/orderfood.wml" method="get">
   <postfield name="food" value="bigburger">
</go>

The postfield element is quite versatile when it comes to guaranteeing data is properly formatted and assigned. When a WAP device encounters a <postfield> element in the code, the first thing it will do is identify the name and value pair and substitute values. Then, it will translate the name and value pairs to the correct character set (which includes properly escape-coding them into an appropriate MIME-content type), and then complete the task, based on the method defined in the <go> tag.

Let's take a look at a more powerful example of the <postfield> tag. In the following example, we ask the user who she is, what she thought of her BurgerWorld meal, and whether she will come back. This card actually prompts the user to fill in three text fields. When she completes the text fields, the values are stored into three user variables and passed to a dynamic file called logresults.cfm to be logged to a database. In this case we have used ColdFusion (hence the .cfm extension) to create our dynamic file, but any application server you choose can be run on the back end here.

<card id="comment" title="BurgerWorld Comments">

<do type="accept" label="Send">
     <go href="logresults.cfm" method="post">
              <postfield name="u_name" value="$message"/>
              <postfield name="u_thoughts" value="$subject"/>
              <postfield name="u_back" value="$comeback"/>
    </go>
</do>

<p>

Your Name: <input type="text" name="name"/><br/>
Thoughts: <input type="text" name="thoughts"/><br/>
Coming back? : <input type="text" name="comeback"/>

</p>
</card>

The preceding example demonstrates the power of the <postfield> tag. When the user presses the "Send" soft key, the <postfield> tag will associate the variable name to the values associated with all the text fields and pass them using the post method to the WAP Server. This example will only run if a logfile.cfm exists as a file on the server in the same path as the example code. Running the code without this file will cause an error.

Setting the method Attribute to post

Although mentioned earlier in this chapter, the method attribute in the <go> tag is analogous to the HTTP get/post element. If you elect to use the post element, the requested variables will be sent as URL-encoded. For example, suppose we are accessing a deck called burgers.wml and we are passing three variables: cheese=yes, mustard=no, mayonnaise=no. The syntax would resemble the following:

<go href="burgers.wml" method="[get|post]">
    <postfield name="cheese" value="yes"/>
    <postfield name="mustard" value="no/>
    <postfield name="mayonnaise" value="no/>
</go>

Based on the method chosen, the request to the WML server will look like the respective code in Table 4.1.

Table 4.1. Get Versus Post Requests to a Server
Get Post
GET burgers.wml?cheese=yes&mustard=no&mayonnaise=no HTTP/1.1 POST burgers.wml HTTP/1.1
(header information) Content-type="xxx- urlencoded"
 (header information)
 cheese=yes&mustard= no&mayonnaise=no

Tip

Use post as your method setting when submitting forms to a WML page. Get assigns a system environmental variable to the results that may be limited in the number of characters it can hold. With post there are no such limits.


Note

When the value of the method attribute is "post", an enctype attribute could be added to specify the content type used to submit the parameter to the server. The default value for this attribute is "application/x-www-form-urlencoded". At the present time, only this value or "multipart/form-data" can be specified for the enctype attribute.


The setvar Element

The setvar element is similar to the <postfield> element but it can be used in a single deck. Unlike HTML, WML has a built-in function that will allow a programmer to store values and plug those values into the WML code by simply referencing the variable. This is appealing because the user now has control over persisting data and maintaining state information between decks and cards. The <setvar> syntax is exactly the same as the <postfield> syntax:

<setvar name="price" value="3">

The important thing to remember is that these variables are case sensitive, so "price", "PRICE", and "PrIcE" all are different variables. Also, they are restricted in terms of naming conventions. A valid name will have the following characteristics:

  1. It will start with an ASCII letter followed by one or more ASCII letters, digits or underscores.

  2. It cannot start with a number.

  3. The variable name cannot be a reserved word.

Caution

Remember that variable names are extremely case sensitive. Therefore, it is a good idea to always use lowercase and stick to standard programming conventions.


Additionally valid values will be stored in a WML-compatible format, which means escape-coding could be added to your values unintentionally. Therefore, do not be surprised if you try to store the value "#98" and you receive a "%2398" back where %23 is the escape-code for the character "#".

When referencing a variable in your code, the value can be obtained in three ways:

$variable
$(variable)
$(variable:presentation)

The first method is the easiest to read. However, the second form is occasionally necessary if there is any ambiguity in the variable. The third format is used to specify how you want the variable to be presented. For example, let's use our "price" variable. By accessing a variable using the following syntax

$(price:escape)

the variable will be returned with escaping present in the variable. The other two supported formats are

$(price:unesc)

which will return an unescaped version of the variable, and

$(price:noesc)

which will return no escaping present in the variable.

Tip

In general, the WAP device will handle the formatting of the data; therefore, always using the $variable format will probably work best.


Now that we have defined all four tasks in WML (noop, refresh, prev, and go) as well as the postfield and setvar elements, we will learn how to "bind" tasks to events so that when a user triggers an event, tasks within that event are executed accordingly.

Creating Soft Keys with the do Element

The <do> tag is probably the most common event that you'll be working with. It's most often used to create soft keys—a primary source of input on WAP devices. The tag can also be used to attach actions to graphically rendered buttons on a touch-sensitive display or to a voice-command. Whatever kind of input the tag is using, the <do> tag is one of the most common ways to provide user interaction with your WML application.

The following code establishes a soft key, labeled "Menu", that takes the user to the card main. In this example, we "bound" the <go> task "inside" the <do> element, so that when the soft key is pressed, the user will navigate to main.

       <do type="options" label="Menu">
           <go href="#main"/>
       </do>

In the next example, the <do> tag establishes a soft key that returns the user back to the previous card he visited (we will discuss more on navigating with the history stack later in this chapter).

       <do type="prev" label="Back">
          <prev/>
       </do>

In the next example, we're going to walk through a piece of code and explain both its function and broader concepts as it relates to event binding. First, the code will allow the user to press a button on the phone to hyperlink to another card. That entire action constitutes an event that is triggered by the user when he presses the soft key. The hyperlink navigation action is a task carried out within the event, which has been automatically "bound" to the broader event. Binding a task, such as a hyperlink, within an event is relatively easy. We will bind the hyperlink to the button-pressing by nesting a "go" task inside the "do" event as seen in the following code example.

<!-- a continuing food menu card for BurgerWorld -->
    <card id="food2" title="Food Cont.">
    <p>
                            BurgerWorld<br/>
                               <b> Food Menu (cont.)</b><br/>
                            Hamburger $$1<br/>
                            Cheeseburger $$2<br/>
                            Chickenburger $$3<br/>
                            <do type="accept" label="More" optional="false">
                                     <go href="#food3"/>
                            </do>
   </p>
                            <p>
                             Select <b>More</b> for additional menu choices.
                            </p>

 </card>

The previous card is designed to show the users three menu items (a hamburger, a cheeseburger, and a chickenburger) and their prices and then offer the option to view additional menu selections on a separate card. To do this, we have placed the <do> tag within the card and set its type attribute to "accept" and its label attribute to "More". The word "More" will appear on the screen next to one of the device's buttons—this is our soft key. When that button is pressed, the application will accept the <go> task nested within the <do> event and hyperlink the user to the card with an ID of food3 where the user can view more menu items.

This example will only work if there is a card with the ID food3 in the deck.

Type Attributes: Accept Versus Option

In the prior example, we could have used a <do> tag and set the type attribute to options. Instead we chose to set the attribute to accept because we want the user to move through the menus successively, and prevent them from using the standard built-in soft keys which may appear on the device. Had we used the options type attribute, the code would have produced two soft keys: one that would allow the user to select the more soft key, and another that corresponds to the default actions for the card. In general, think of options as a way to give the user the ability to execute on your soft key, or do something else entirely. The accept attribute limits the user's paths, whereas the "options" merely gives them another option, or shortcut, to a location.


Finally, we set the optional attribute to false which tells the device that displaying this tag is not optional, but mandatory. False is the default setting for this attribute, so you could omit this attribute in your own code.

This example of the <do> tag used three attributes: type, label, and option, but there are lots of ways you can use the <do> element, so let's run through the syntax and give a brief description of the various attributes available with the <do> element.

The <do> tag syntax looks like this:

<do
     type="accept | prev | help | reset | options | delete | unknown"
     label="VDATA"
     name="NAME"
     optional="true | false"
>
    <noop> | <refresh> | <prev> | <go>

</do>

All totaled, there are four attributes which are commonly used in the <do> tag: type, label, option, and name.

The type attribute defines the kind of action that the "do" event will execute. The seven defined type values are listed in Table 4.2.

Table 4.2. Defined type Values for the <do> Tag
Type Values Type Attributes Descriptions
accept Affirms acknowledgement
prev Provides backward navigation through the history stack
help Requests for help (can be context-sensitive)
reset Clears and resets the current state
options Presents an option to the user that she can elect to use or ignore
delete Deletes the current choice or item
unknown Sets a generic <do> tag which is equivalent to an empty string

The label attribute provides a visual label for your action which the WAP device will render. If the label is too long for the device to render, the label might be ignored by devices which have very limited display sizes. In the preceding example, we used More as the label.

Caution

Assigning soft key labels that are too long for the target device will, in some cases, cause the device not to display your labels at all. To make sure they don't disappear on a particular device, keep your soft key labels under six characters!


The optional attribute can be set to either true or false. If the optional attribute is set to true you are telling the device that it is not required to display the tag. Because some devices have very limited room, this attribute allows some <do> tags to be considered optional, giving the device some flexibility in choosing what to display. As a result, if the optional attribute is set to true, the device might ignore the tag. The optional attribute is not mandatory; if you do not include it in your code, the default setting is false.

The name attribute specifies the unique name of the combined event and task binding in the <do> tag you've created. This becomes important when you have multiple <do> tags in a single card or deck. If no name value is specified, the name value defaults to the value of the type attribute. Duplicate names within a single card will produce an error.

Caution

If you have more than two <do> tags, and neither have been given a name value, you will produce an error.


Now that we've reviewed the relevant attributes for the <do> tag, we need to decide how we want to implement the tag in our application. You can implement the tag on both the card and deck levels of your application, depending on your needs.

card-level <do> tag To add a do element to a single, specific card, you can place the card-level tag anywhere within the text flow of a card. This does not guarantee placement of the <do> tag, however, as each device can display it differently.

Caution

The display of your <do> tags will depend entirely on the devices viewing your card! Because WML is displayed differently on different devices, your soft keys might not appear exactly according to your expectations. They may be cut off, or located somewhere unexpected on the device's screen. Plan accordingly!


deck-level <do> tag If your entire deck will be using the same actions on every card, you can place the action throughout the entire deck by creating the action within the deck's <template> tag. This way, the deck-level <do> tag will apply to each card in the deck. WAP-com patible devices will display deck-level <do> tags as if they are at the bottom of the card's text flow.

▸ For more on templates, see Chapter 3.

Tip

If your application is going to use the same soft keys on every card in a deck, you can save time by creating a deck template and putting your <do> tags in the template for every card.


Creating Intrinsic Events with the onevent Element

Intrinsic events are not triggered by the user, like we saw with the <do> element, but are instead triggered by the internal processing of the WAP device and browser. There are four types of intrinsic events, all created with the onevent tag, whose syntax looks like this:

<onevent
     type="onenterforward | onenterbackward | onpick | ontimer"
>
     <noop> | <refresh> | <prev> | <go>

</onevent>

Each of the following four types of the onevent element is triggered by an internal processing event on the device.

  • onenterforward (relevant to cards and templates) The onenterforward type is triggered when the user enters a card by way of a go task or other similar navigational mechanisms such as a script function or device-specific mechanism.

  • onenterbackward (relevant to cards and templates) The onenterbackward type is triggered when the user causes the device to navigate using a prev task, which retrieves a URL from the history stack—or any similar navigational mechanisms such as a script function or device-specific mechanism.

  • onpick (relevant to options) The onpick type is triggered when the user selects or deselects an item defined as an <option>.

  • ontimer (relevant to cards and templates) The ontimer type is triggered when a timer expires. For more about timers, see Chapter 10, "Using Timers."

Just like when we created user-triggered events, intrinsic events use the four tasks (noop, reset, prev, and go), nested inside the event, to bind the task to the event. In the following example, we created a Order Confirmation card that prevents the user from visiting the previous page and resubmitting his order for a World Burger, fries, and large soda to BurgerWorld.

<wml>
    <template>
       <do type="prev" label="Back">
          <prev/>
         </do>
    </template>

    <card id="confirm" title="Confirm">

      <onevent type="onenterbackward">
             <go href="main.wml"/>
      </onevent>
            <p>You have successfully ordered:<br/>
                    A World Burger<br/>
                    Fries<br/>
                    A Large Soda<br/>
                    Delivery within 10 minutes, or your order is free!<br/>
    </p>
     </card>
</wml>

This example will only function if a separate file, main.wml, is included.

The preceding example demonstrates how you can create events that are intrinsic to your application and don't rely on users input to be triggered. In the example, you also might have noticed that the code included a deck-level event (we used the do element in the <template> tag) and a card-level event (we used the onevent element within the card). In the example, the template provided the user with the ability to go to the previous card at any time while he was in the deck, whereas the card prevented the user from navigating to the previous card. Which one takes precedence, and how will you know when your code presents two conflicting events? The next section covers task overrides and gives you several simple principles by which you can determine the overriding task in your application.

Card and Deck Task Overrides

When you have multiple events and tasks in your deck, it is important to know which actions will override and take precedence over other actions when several are present in a deck. The following rules will help you determine which tasks take precedence when multiple tasks are involved.

  1. If a card-level event and a deck-level event both identify the same event, the card-level event will take precedence.

  2. If a deck and a card both have <do> tags with the same name attribute, the card's <do> tag will take precedence.

  3. If a deck and card both have <onevent> tags with the same type attribute, the card's <onevent> tag will take precedence.

  4. If a card-level event overrides a deck-level event, and the card level event elements specify the noop task, the noop task takes precedence and both card and deck-level events elements will be ignored, with no side effects on delivery.

The following example demonstrates these rules in action.

  • Card One displays the deck-level do element which originates in the <template> tag.

  • Card Two overrides the deck-level <do> element with the noop task, preventing the device from executing the deck-level <do> element. It may display the soft key, but won't execute the task.

  • Card Three, the final card, overrides the deck-level do element and replaces it with a card-level do element all its own.

<wml>
     <template>
          <do type="options" name="doit" label="Back">
               <prev/>
          </do>
     </template>
     <card id="card1">
          <p>Card One</p>
<!--the deck-level do tag will be displayed on this card-->
     </card>

     <card id="card2">
          <p>Card Two</p>
<!--the deck-level do tag is overridden with the noop
task. It is not displayed on this card-->
          <do type="options" name="doit">
               <noop/>
          </do>
     </card>

     <card id="card3">
          <p>Card Three</p>
<!--the deck-level do tag is overridden with the and
replaced with a card-level do element-->
          <do type="options" name="doit" label="Menu">
               <go href="/menu"/>
          </do>
     </card>
</wml>

..................Content has been hidden....................

You can't read the all page of ebook, please click here login for view all page.
Reset
13.59.100.42