Java velocity开发学习

申明

本文章主要借鉴于:http://sakyone.iteye.com/blog/524289

介绍

Velocity是一基于java语言的模板引擎,使用这个简单、功能强大的开发工具,可以很容易的将数据对象灵活的与格式化文档组装到一起;

引用

在pom.xml中增加依赖:

        <dependency>
            <groupId>org.apache.velocity</groupId>
            <artifactId>velocity</artifactId>
            <version>1.7</version>
        </dependency>

一个简单的例子

使用Velocity模版引擎,一般通过如下步骤:
1、第一步是要初始化Velocity,Velocity.init().
2、创建一个Context object.
3、将你的数据对象加入到Context对象中.
4、使用Velocity选择一个模板.
5、合并模板和数据导出到输出流.

代码如下:

public class VelocityTest {
    /**
     * @param args
     */
    public static void main(String[] args) {
        try {
            // 初始化
            Velocity.init();
            // 取得VelocityContext对象
            VelocityContext context = new VelocityContext();
            // 向context中放入要在模板中用到的数据对象
            context.put("name", new String("Velocity"));
            Template template = Velocity.getTemplate("hello.vm");//hello.vm放入工程主目录下
            StringWriter writer = new StringWriter();
            template.merge(context, writer);
            System.out.println(writer.toString());
        } catch (Exception e) {
            e.printStackTrace();
        }
    }
}


hello.vm内容如下:

<html>  
    <head></head>  
    <body>  
        HELLO! $name,Welcome to velocity!  
    </body>  
</html>

程序执行结果,将$name换成了Velocity

<html>  
    <head></head>  
    <body>  
        HELLO! Velocity,Welcome to velocity!  
    </body>  
</html>


进阶介绍

单便和多例

单例模式

前面的例子就是使用的单例模式,这是系统默认的模式, 这样在jvm(应用程序)或web aplication(一个web程序)中只存在一个Velocity engine实例共享使用。. 这对于配置和共享资源来说非常方便. 比如, 这非常适合用于支持 Servlet 2.2+ 的web application中,每一个web app持有它自己的唯一Velocity实例, 它们可以共享templates, a logger等资源. Singleton可以直接通过使用org.apache.velocity.app.Velocity 类。

  try {
            // 初始化
            Velocity.init();
            // 取得VelocityContext对象
            VelocityContext context = new VelocityContext();
            // 向context中放入要在模板中用到的数据对象
            context.put("name", new String("Velocity"));
            Template template = Velocity.getTemplate("hello.vm");//hello.vm放入工程主目录下
            StringWriter writer = new StringWriter();
            template.merge(context, writer);
            System.out.println(writer.toString());
        }

多例模式

在1.2版本以后, 可以在 JVM (or web application.)创建,配置,使用多个Velocity实例;当你希望在同一程序中,对每个实例独立配置时它们的 template directories, loggers等资源时,这是非常方便的. 多实例化时,我们要用到 org.apache.velocity.app.VelocityEngine类.

try {
            VelocityEngine ve = new VelocityEngine();
            ve.init();
            // 取得VelocityContext对象
            VelocityContext context = new VelocityContext();
            // 向context中放入要在模板中用到的数据对象
            context.put("name", new String("Velocity"));
            Template template = Velocity.getTemplate("hello.vm");
            StringWriter writer = new StringWriter();
            template.merge(context, writer);
            System.out.println(writer.toString());
        } catch (Exception e) {

无论是使用单例模式还是使用多例模式,程序员都无须改变程序的结构,而且非常简单的就在两者之间进行转换。


content

1.The Basics
'context' 是Velocity中的一个核心概念, 这是一个从系统的”数据容器(a container of data)”引出的一个常见概念. 这里的context在java程序层和模板视图层(template layer ( or the designer ))之间扮演着一个”数据对象传送者”'(carrier')的角色.
做为程序员,你可以将你程序生成的不同类型的数据对象放入context中,对于视图设计来说,这些对象(包含它们的数据域和命令)将在模板元素中被引用到(references)。一般来说,你将和视图设计者一起决定应用需要哪些数据,可以说,你放入context中的数据对象在这里成为一种”API”,由视图设计者在模板中来访问.因此,在向context中决定放放哪些数据对象时,程序的设计者需要仔细分析视图表现所需的数据内容。
虽然Velocity中你可以创建自己的Context类来支持一些个性化的应用(比如,一个访问,保存LDAP Server服务的context),你可以实现VelocityContext这个己封装较为完务的基类。
VelocityContext对象基本上可满足大多的应用, 我们强烈建议你除非在特别的情况下,否则不要创建自己的Context实现!
VelocityContext用法十分简单,类似于Hashtable class.下面是这个接口提供的两个基本用法:
public Object put(String key, Object value);
public Object get(String key);
很像Hashtable吧,这里的value必须是一个java.lang.Object类(不能是原始类型,像int,boolean), 也不能是null值. 原始类型(Fundamental types like int or float)必须被包装为一个适当对应的Object型.
2.在模板中用#foreach指令支持迭代对象
在放入context前,你对对象有着全面的操作自由. 但就像所有的自由一样, 你必须遵守一些规则,承担一些责任,因此,你必须理解Velocity是如何使用对象的,Velocity的VTL支持多种类型的集合类型(collection types) 使用#foreach().
Object [] 一般对象数组. Velocity将内功能会将它包装成功之为一个实现Iterator interface对象, 这个转换是不需要程序员或视图设计者参与.
java.util.Collection :Velocity会使用他们的标准iterator() 得到一个可以迭代中使用的 Iterator对象,如果你使用自己的实现了Collection interface的对象,要确保它的iterator() 命令返回一个可用的Iterator.
java.util.Map接口对象,Velocity 使用其顶层接口的values() 命令得到一个实现 Collection interface的对象, 应用其iterator()再返回一个Iterator.
java.util.Iterator使用特别注意 : 如果一个Iterator对象被放置到context中,当在模板中有多个 #foreach()指令中,这些#foreach() 将顺序执行,如果第一个调用失败,后面的将阻塞且不能重置.
java.util.Enumeration USE WITH CAUTION : 如同java.util.Iterator一样的道理,Velocity将使用的是一个不能重置('non-resettablity')或者说一个final型的对象.
因此,仅当在不得己的情况下,Iterator and Enumeration 对象才有必要放入context中---也许你有更好的办法不使用他们.

3.Context Chaining
另外一个新引入的概念是context chaining.有时也叫做context wrapping(有点类似与servlet中的chain), 这个高级特性让你可以连结多个独立的Velocity的contexts,以便在template中使用.

例子

传多个参数

代码:

           context.put("name", "wangxiaoyu");
            context.put("age", "20");
            Template template = Velocity.getTemplate("helloCollection.vm");


helloCollection.vm的内容:

<html>  
    <head></head>  
    <body>  
        HELLO! $name,you are only $age years old!  
    </body>  
</html>

传对象

定义一个对象:

public class Person {

    public Person(String name, Integer age) {
        this.name = name;
        this.age = age;
    }

    private String name;

    private Integer age;

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public Integer getAge() {
        return age;
    }

    public void setAge(Integer age) {
        this.age = age;
    }
}

代码:

            context.put("person", new Person("wangxiaoyu", 20));
            Template template = Velocity.getTemplate("helloCollection.vm");

helloCollection.vm的内容:

<html>  
    <head></head>  
    <body>  
        HELLO! $person.name,you are only $person.age years old!  
    </body>  
</html>

传集合

代码:

List<Person> persons = new ArrayList<Person>();
            persons.add(new Person("wangxiaoyu", 20));
            persons.add(new Person("zhoushuyan", 20));
            context.put("persons", persons);

helloCollection.vm的内容:

<html>  
    <body>  
        #foreach($person in $persons)
                  <tr bgcolor="#f3f3f3">  
                    <td height="32px">${person.name}</td>  
                    <td height="32px">${person.age}</td>
                </tr>  
        #end
    </body>  
</html>

代码运行结果:

<html>  
    <body>  
                          <tr bgcolor="#f3f3f3">  
                    <td height="32px">wangxiaoyu</td>  
                    <td height="32px">20</td>
                </tr>  
                          <tr bgcolor="#f3f3f3">  
                    <td height="32px">zhoushuyan</td>  
                    <td height="32px">20</td>
                </tr>  
            </body>  
</html>

将content传入另一个content

代码:

    // 向context中放入要在模板中用到的数据对象
            context1.put("name", "wangxiaoyu");
            context1.put("age", "20");
            context1.put("duplicate", "I am in context1");
            VelocityContext context2 = new VelocityContext(context1);

            context2.put("anotherName", "zhoushuyan");
            context2.put("anotherAge", "20");
            context2.put("duplicate", "I am in context2");


helloCollection.vm的内容:

<html>  
    <body>  
          $name,$age
          $anotherName,$anotherAge
          $duplicate
    </body>  
</html>

代码运行结果:

<html>  
    <body>  
          wangxiaoyu,20
          zhoushuyan,$anotherAge
          I am in context2
    </body>  
</html>

在模版引擎中可以任意使用context1和context2中的对象,如果context1和context2中都加入了某个对象,则显示后加入的数据。

在servlet中使用velocity



  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值