前言
继上一篇「WAP的应用,发展工具的介绍,WML基础篇」里中的小小例子(编按:请参见本刊2000.5月号72期第84页「WML教室(一):如何架构一个自己专属的WAP网站」),我们已经学到了在整个WML的网页中许多重要之组件,如:卷标、card及段落(Paragraph)等,在之后的文章,笔者会带领各位读者陆续进入到WML语言较进阶的部分,而本章中主要会以例子来带领用户更加之熟悉WML网页之建置。在本篇的第一个例子中,笔者将介绍在WML组件中如何从一个CARD链结到另外一个CARD。
程序开始
<?xml version="1.0"?>
<!DOCTYPE wml PUBLIC "-//WAPFORUM//DTD WML 1.1//EN" "http://www.wapforum.org/DTD/wml_1.1.xml">
<wml xml:lang="en-us"> <!-- 1 -->
<card id="card1" title="Card 1"> <!-- 2 -->
<do type="accept" label="OK"> <!-- 3 -->
<go href="#card2"/> <!-- 4 -->
</do>
<p> <!-- 5 -->
Hello everybody! <!-- 6 -->
This is the first card... <!-- 7 -->
</p>
</card>
<card id="card2" title="Card 2"> <!-- 8 -->
<p> <!-- 9 -->
This is My second card. <!-- 10 -->
Goodbye. <!-- 11 -->
</p>
</card>
</wml>
笔者先以前一篇所提过的Nokia Toolkit这套工具来操作。首先,将档案load进来,单击左边窗口左下角的Show按键,手机就会出现如(图一)之图案。
此时我们可以利用功能键按下Options,便会出现如(图二)的画面,让我们可以选取「OK」之选项。
利用上下键选择钮来选择「OK」键之后,按下「Select」后,浏览器就会跳至第二个Card,如(图三):
这样的动作就相当于我们在Internet上浏览web pages时可以用鼠标点选链结以连到不同的地方,现在笔者就为各位读者来解释一下如何让WML网页有这样的功能。在程序的第1行:
<wml xml:lang="en-us">
指的是此份WML文件所采用之语言为「英语」。在上例中的Deck包含两个Card,而当手机读取此Deck时,会先显示第一个Card。若是用户进一步对第一个画面作动作时,也就是按「OK」键后,就会显示第二个Card。
在第一行的后面,我们可以发现到程序代码中包含着<!-- 1 -->的字符串。其主要之用意为在WML的网页中作批注之用,而批注之语法为:
<!-- 批注之内容 -->
批注主要之目的为增加WML程序的可读性,帮助WML网页撰写者更加了解文件的内容,但批注的内容并不会显示在手机上。值得注意的是在WML的语言中并不支持「巢状」形式的批注,也就是不能够在批注中还有批注的意思。
接下来就是如何做到CARD之间链结的重头戏了,在第3行的:
<do type="accept" label="OK">
中定义了用户的动作,而label就是显示在手机上提示用户的文字,因此在之前的操作中,当我们按下了Options之后,会出现OK这样的选项,而当这个按键被按下的时候,便会去执行在<do>这个组件中所指定的动作,而这儿的动作就是:
<go href="#card2"/>
也就是会跳到一个id为card2的CARD去,其中WML以#来代表一个CARD,所以如果我们要跳到其他的WML网页时,只需要在href中指定档名即可。
接下来,让我们来看更进阶的一个小例子,带领大家更了解知道WML语言。其程序代码如下:
<wml>
<template>
<do type="accept" name="exit" label="EXIT">
<prev/>
</do>
</template>
<card id="card_1" title="Welcome" newcontext="true">
<p>
Hello World!
</p>
</card>
</wml>
我们来操作看看,看在我们的手机屏幕上会出现什么画面,出现之画面如(图四):
在这程序中,我们遇到许多我们第一次见到之组件,首先,在第2行到第6行之间,我们看到程序代码中的卷标:
<template>
. . .
</template>
样板(template)组件指定在一个Deck中所有之Card所做的事情,换句话说,在之前第一篇文章中,我们知道,一个Deck可能包含数个Card,若是我们在每个Card都有相同的动作,例如:「离开」。则我们可以将「离开」这个动作定义在样板(template)中,定义在样板中的动作就如同定义在「每个」Card里的动作一般。所以利用样板之组件可以省去许多我们写网页的时间,使得程序代码更有效率及可读性。
再接下来的范例,我们会进一步专注在用户之接口中,包含画面中含有用户的数据输入,以及如何在WML里使用变量等等。
首先,下一个例子里包含了变量的读取及设定,而所用到之卷标组件包函了以下几种:
card
do
go
prev
setvar
onevent
refresh
其程序代码如下:
1. <?xml version="1.0"?>
2. <!DOCTYPE wml PUBLIC "-//WAPFORUM//DTD WML 1.1//EN" "http://www.wapforum.org/DTD/wml_1.1.xml">
3. <wml>
4. <card id="card1" title="First Card" newcontext="true">
5. <p>
6. Card 1 ... <br/>
7. <!-- The following variables will not be defined until the other cards in this deck are entered. -->
8. card1 var1 = $(card1_var1) <br/>
9. card2 var1 = $(card2_var1) <br/>
10. card3 var1 = $(card3_var1) <br/>
11. <do type="accept" label="Next Card">
12. <go href="#card2">
13. <setvar name="card1_var1" value="val_1"/>
14. </go>
15. </do>
16. </p>
17. </card>
18. <card id="card2" title="Second Card">
19. <p>
20. Card 2 ... <br/>
21. card1 var1 = $(card1_var1) <br/>
22. card2 var1 = $(card2_var1) <br/>
23. card3 var1 = $(card3_var1) <br/>
24. <do type="accept" label="First Card">
25. <go href="#card1"/>
26. </do>
27. <do type="accept" label="Third Card">
28. <go href="#card3">
29. <setvar name="card2_var1" value="val_2"/>
30. </go>
31. </do>
32. <do type="prev" label="Previous Card">
33. <prev/>
34. </do>
35. </p>
36. </card>
37. <card id="card3" title="Third Card">
38. <onevent type="onenterforward">
39. <refresh>
40. <setvar name="card3_var1" value="val_3"/>
41. </refresh>
42. </onevent>
43. <p>
44. Card 3 ... <br/>
45. card1 var1 = $(card1_var1) <br/>
46. card2 var1 = $(card2_var1) <br/>
47. card3 var1 = $(card3_var1) <br/>
48. <do type="prev" label="Previous">
49. <prev/>
50. </do>
51. </p>
52. </card>
53. </wml>
在程序代码的第4行中,我们可以发现到,在Card卷标里的属性部分包含了「newcontext='true'」之字符串,其功用为告知浏览器(即一般手机)去做初始化,并将以前浏览过网页的纪录清除。
在程序执行到第8行时,我们发现到字符串$(card1_var1)之字样。其意义代表宣告变量$(card1_var1),而其值是空的。所以当程序执行至8,9,10行时,会出现如(图五)之画面。
《图五 由画面可看出card1 var1及card2 var1和card3 var1变量之值皆为空的》 |
|
从Options里选择Next Card并按下Select之按键。如(图六)所示:
之后浏览器会进入第2个Card之程序代码,是在程序代码第18行至36行。值得注意的是在程序代码第11行到第14行之间:
11. <do type="accept" label="Next Card">
12. <go href="#card2">
13. <setvar name="card1_var1" value="val_1"/>
14. </go>
即刚刚我们在图六中按下Select之按键就会执行程序代码第13行之位置,将变量card1_var1之值设成「val_1」。设定变量之方式必须使用「setvar」之卷标,其格式如下:
<setvar name = "XXXX" value = "kkk"/>
其中name的字段代表要设定变量值之名称,而value代表要设定之值。
之后执行按键之结果画面如(图七):
《图七 在画面中可发现card var1之变量其值已经设为val_1》 |
|
选择Options之功能键之后会出现(图八)之画面,在图八之画面中,读者可以利用上下选取键在窗体中选择回到第1个Card或到第3个Card。
《图八 选单中可选择回第1个Card或到第3个Card》 |
|
若是我们选择了第3个Card时会出现画面如(图九)的图案:
若是我们连续在画面中连双击Back时,我们可以发现到,画面回到第1个Card并在第1个Card中,其变量之值并非为空,而是已经皆有特定之值存在。而这些特定之直接是我们在程序代码中第13行,第29行和第40行中,我们利用setvar之卷标来给于我们的变量特定之值。
在第38行我们可以发现我们位成使用过之卷标,其形式如下:
<onevent type="onenterforward">
<onevent>之卷标是立即的去做在<onevent>卷标里所指定的特定组件,而在此例中,此特定之组件为「onenterforward」,若是所指定之特定组件不为合法之元建时,浏览器会忽略进而不去执行此段程序代码。而在刚刚程序代码中所指定之「onenterforward」又是代表什么呢?即代表若是用户利用forward时会特定去做某些特定之事件。
举个小小的例子让读者更容易知道这段程序代码的功用,下面的例子里,当用户利用forward到此网页时,会自动的启动「onenterforward」之事件,而在card之所撰写之讯息不会出现,原因是因为浏览器会直接去读取在wapertech网域中good.wml之网页。若是用户利用backward之方式读取此网页时,会显示网页之内容而不会链接读取good.wml之网页。
<card>
<onenvent type="onenterforward">
<go href="http://www.wapertech.com.tw/good.wml"/>
</onevent>
<p>
Welcome to a new age!
</p>
</card>
在程序代码中第39行里,有我们未曾见过的卷标<refresh>,其功用为何呢?
<refresh>之卷标其功用为更新所指定card中所定义变量之值。而在执行<refresh>卷标时就会立即的更新所有变量之值,而用户也可在屏幕上发现变量之值已经更改了。
上述的范例即在让读者了解到WML语言里变量的使用方法,在某些之情况中用户可能需要纪录到用户的设定或者是偏好等习性,这些都是可以利用变量的方式来储存用户的设定等。
结语
以上范例主要是想藉由简单之程序,让读者更容易在程序代码中学习到定义繁杂的卷标的概念。在上述几个范例程序中,读者可以加以融会贯通,进而转写出功能强大之网页。在下期的篇幅中,笔者将带领用户进入更深入的WML语言世界中,包含利用WML Script和相关之用户接口,进而做出更人性化及更加丰富之WML网页。(待续)
(作者为威波科技资深工程师)