Dorado 7 : 06. 实做AJAX(SEFC)

下面我们通过实做AJAX对Dorado7中的AJAX操作做一定的了解。

页面功能描述:
首先我们设计一个Spring的JavaBean:

package com.bstek.dorado.sample.basic;

import java.util.Properties;
import org.springframework.stereotype.Component;
import com.bstek.dorado.annotation.Expose;
import com.bstek.dorado.core.DoradoAbout;

@Component
public class Ajax {

	@Expose
	public String toUpperCase(String str) {
		return "input:\n" + str + "\n\n" + "output:\n"
				+ str.toUpperCase();
	}

	@Expose
	public int multiply(int num1, int num2) {
		return num1 * num2;
	}

	@Expose
	public Properties getSystemInfo() {
		Properties info = new Properties();
		info.setProperty("product", DoradoAbout.getProductTitle());
		info.setProperty("vendor", DoradoAbout.getVendor());
		info.setProperty("version", DoradoAbout.getVersion());
		return info;
	}
}

页面上放置三个按钮:button1, button2, button3

  • 单击button1的时候,调用spring中的一个bean的方法toUpperCase,并将我们传入的字符串转换为大写,并返回到前台浏览器中;
  • 单击button2的时候,调用spring中的一个bean的方法multiply,并将我们传入Map对象(含多个key)中的两个数字相乘,并将计算结果返回到前台浏览器中;
  • 单击button1的时候,调用spring中的一个bean的方法getSystemInfo,并将Java中的一个Map对象返回到前台浏览器中;

如果完成了以上的三个功能,我们就很容易解决这些AJAX技术问题:

  • 如何调用Spring中bean中指定的业务方法;
  • 如何传入一个单值给后台,并将调用结果为单值的值如何返回到前台;
  • 如何传入一个map到后台,并将运算结果返回到前台;
  • 如何调用后台的业务方法,并将计算结果为map的值返回到前台;
    掌握了以上基本技术之后,再将它们综合应用一下,如JS中指定map参数,ajax调用结束之后返回map对象,并在前端使用。这样我们就可以解决大部分的ajax调用问题了。

toUpperCase

下面我们还是在HelloWorld中实做这个范例,由于HelloWorld中已经定义过Ajax这个Bean了,我们不再重复定义,我们在com.bstek.dorado.sample.training目录中新建一个名称为Ajax的View,并在其中添加一个AjaxAction控件和Button控件,其中AjaxAction是Action的一种,我们在控件的基础知识中简单介绍过它代表了页面上的一种动作,是不可见的对象。但是它可以被其他可见控件使用,例如单击按钮时触发Action。

我们设置AjaxAction控件的相关属性:

属性

id

toUpperCaseAction

caption

To UpperCase

parameter

Hello World!

service

ajax#toUpperCase

其中我们特别关注其service属性,"ajax#toUpperCase"是一个服务名称,根据Dorado中的服务定位表达式,它最终代表的含义是调用Ajax这个类的toUpperCase方法,至于服务表达式的概念我们后面再讲,这儿我们只要记住这个字符串最终会调用到Ajax这个类的toUpperCase方法就可以。而parameter的值就代表了调用toUpperCase方法传入的参数值。
再设置Button控件的相关属性:

属性

action

toUpperCaseAction

定义action属性的效果是,单击按钮的时候自动触发toUpperCaseAction。我们可以注意到Button上的显示内容我们都没有定义,该处根据Action的绑定规则它会自动显示action对应的caption,而toUpperCaseAction中我们已经定义了caption了。
另外,当Ajax这个类的toUpperCase方法执行结束之后,我们希望在浏览器中看到最终的返回值,那么我们定义toUpperCaseAction的onSuccess事件:


在当前目录下新建Ajax.js文件,输入如下代码:

// @Bind #toUpperCaseAction.onSuccess
!function(self){
    dorado.MessageBox.alert(self.get("returnValue"));
}

在action的onSuccess事件中,self代表了action本身,returnValue表示Ajax调用结束后Java层返回的结果。该处关于JS代码的写法后面我们会有专门的章节进行说明,此处我们记住self.get("returnValue")的含义就是获得ajax调用返回的结果就可以。
这样我们就完成了第一个按钮的开发,在浏览器中打开这个页面(http://localhost:8080/sample-center/com.bstek.dorado.sample.training.Ajax.d)查看效果:

multiply

下面我们接着做multiply的ajax调用,同样我们再添加一个AjaxAction和一个Button。

我们设置AjaxAction控件的相关属性:

属性

id

multiplyAction

executingMessage

Computing...

service

ajax#multiply

通过toUpperCase实例的制作,我们知道了"ajax#multiply",它最终代表的含义是调用Ajax这个类的multiply方法。executingMessage是用于在Ajax调用时给客户一个提示信息,在Ajax调用结束之后会自动消失,这样对于某些耗时的ajax调用来说这种显示效果更为人性化。
再设置Button控件的相关属性:

属性

idmultiplyButton

action

multiplyAction

caption

Ajax Multiply

定义action属性的效果是,单击按钮的时候自动触发toUpperCaseAction。另外与toUpperCase范例不同,这次我们直接在Button上定义caption,其实这几种定义caption的方式都可行,根据实际场景灵活运用就是了。例如我们希望动态改变按钮绑定的action时,我们就可以考虑将caption定义在action中。

另外,当Ajax这个类的multiply方法被调用时需要两个参数,我们希望给用户一个自定义输入参数的机会,而不是toUpperCase用例中直接定义在parameter属性中,如下图:

则我们在Ajax.js中给button1的onClick代码中添加如下的JS:

// @Bind #multiplyButton.onClick
!function(){
    var action = view.get("#action1");
    dorado.MessageBox.prompt("Please input two numbers here",{
        defaultText: "3,5",
        callback: function(text){
            var nums = text.split(",");
            var parameter = {
                num1: nums[0],
                num2: nums[1]
            };
            action.set("parameter", parameter).execute(function(result){
                dorado.MessageBox.alert(nums[0] + " * "+ nums[1] + " = " + result);
            });
        }
    });
}

其中我们通过Dorado提供的MessageBox做用户输入界面,MessageBox的具体用法参考:http://www.bsdn.org/projects/dorado7/deploy/jsdoc/class.html?symbol=dorado.MessageBox.
我们将用户输入的值利用js的split拆分为两个数字,num1和num2封装到parameter中(可以想象成一个Map),并将这个parameter设置给action去调用服务器端的multiply方法。
我们回过头在看看multiply方法:

@Expose
public int multiply(int num1, int num2) {
	return num1 * num2;
}

当map对象传到Ajax类的时候,发现没有匹配的方法,这个时候Dorado的自动方法适配机制会自动的将map拆为num1和num2,从而调用到multiply方法。有关自动方法适配我们后面还会再讲。multiply做的工作就是将num1和num2相乘,并将结果返回。我们在Button的onClick代码中利用了一个回调函数将计算结果显示出来(回调函数用法会在后面的JavaScript基础中进一步说明)。

这样我们就完成了第二个按钮的开发,在浏览器中打开这个页面(http://localhost:8080/sample-center/com.bstek.dorado.sample.training.Ajax.d)查看效果:

getSystemInfo

下面我们做getSystemInfo的ajax调用,同样我们再添加一个AjaxAction和一个Button。

我们设置AjaxAction控件的相关属性:

属性

id

getSystemInfoAction

caption

Retrieve Dorado7 System Information

service

ajax#getSystemInfo

通过toUpperCase实例的制作,我们知道了"ajax#getSystemInfo",它最终代表的含义是调用Ajax这个类的getSystemInfo方法。
再设置Button控件的相关属性:

属性

action

getSystemInfoAction

定义action属性的效果是,单击按钮的时候自动触发getSystemInfo。

另外,当Ajax这个类的getSystemInfo方法调用成功后返回的是一个Properties对象,这也是一个Map对象,我们希望在浏览器中看到最终的返回值,那么我们在Ajax.js中定义getSystemInfoAction的onSuccess事件:

// @Bind #getSystemInfoAction.onSuccess
!function(self){
    var info = self.get("returnValue");
    dorado.MessageBox.alert("product : " + info.product + "\n" +
        "vendor : " + info.vendor + "\n" +
        "version : " + info.version);
}

在action的onSuccess事件中,self代表了action本身,returnValue表示Ajax调用结束后Java层返回的结果。由于返回的是一个Map对象,在浏览器中接受的时候会自动转为JSON对象,这样我们就可以直接通过info.product,info.veneor,info.version范围map中的内容。
这样我们就完成了第三个按钮的开发,在浏览器中打开这个页面(http://localhost:8080/sample-center/com.bstek.dorado.sample.training.Ajax.d)查看效果:

Attachments: