Terry.Li-彬

虚其心,可解天下之问;专其心,可治天下之学;静其心,可悟天下之理;恒其心,可成天下之业。

  BlogJava :: 首页 :: 新随笔 :: 联系 :: 聚合  :: 管理 ::
  143 随笔 :: 344 文章 :: 130 评论 :: 0 Trackbacks

FreeMarker概述

  • FreeMarker是一个模板引擎,一个基于模板生成文本输出的通用工具,使用纯Java编写
  • Template + data model = output
  • Hello world

  • FreeMarkerTest.java
 
import java.io.StringWriter;import java.util.HashMap;import java.util.Locale;
 
import freemarker.template.Configuration;import freemarker.template.Template;
 
publicclass FreeMarkerTest {
 
publicstaticvoid main(String[] args){
FreeMarkerTest test = new FreeMarkerTest();
test.sayHello("Hermit");
}
 
publicvoid sayHello(String name){
Configuration freemarkerCfg = new Configuration();
freemarkerCfg.setClassForTemplateLoading(this.getClass(), "/");
 
freemarkerCfg.setEncoding(Locale.getDefault(), "UTF-8");
Template template;
Locale.setDefault(Locale.ENGLISH);
try{
template = freemarkerCfg.getTemplate("Hello.ftl");
template.setEncoding("UTF-8");
HashMap root = newHashMap();
root.put("user", name);
 
StringWriter writer = newStringWriter();
template.process(root, writer);
System.out.println(writer.toString());
}catch(Exception e){
e.printStackTrace();
}}
 
 
 
}
 
  • Hello.ftl
 
 
Hello ${user}!
 
 
  • 输出

Hello Hermit!


空值的处理

在我们的程序中难免会碰到值为空的时候,如果用一个空值直接去替换模板中的标记,freemarker会毫不犹豫的抛出异常,并把错误信息直接写到输出结果里。为了对付这种情况我们有两种写法

  • 模板
 
Hello ${user!}!
Hello ${user?if_exists}
Hello ${user!'your name'}!
Hello ${user?default('your name')}
 
  • 程序
 
test.sayHello(null);
 
  • 输出
 
Hello !
Hello your name!
Hello
Hello your name
 

freemarker国际化模板

freemarker支持多语言国际化,只要把模板名称按照java资源文件的写法就可以了,也就是name_语言_国家地区.ftl 如果找不到对应的语言,就会用默认语言的模板。

  • 程序
 
import java.io.StringWriter;import java.util.HashMap;import java.util.Locale;
 
import freemarker.template.Configuration;import freemarker.template.Template;
 
publicclass FreeMarkerTest {
 
publicstaticvoid main(String[] args){
FreeMarkerTest test = new FreeMarkerTest();
test.sayHello("hermit",Locale.CHINA);
test.sayHello("hermit",Locale.ENGLISH);
}
 
publicvoid sayHello(String name,Locale locale){
Configuration freemarkerCfg = new Configuration();
freemarkerCfg.setClassForTemplateLoading(this.getClass(), "/");
 
freemarkerCfg.setEncoding(Locale.getDefault(), "UTF-8");
Template template;
Locale.setDefault(Locale.ENGLISH);
try{
template = freemarkerCfg.getTemplate("Hello.ftl",locale);
template.setEncoding("UTF-8");
HashMap root = newHashMap();
root.put("user", name);
 
StringWriter writer = newStringWriter();
template.process(root, writer);
System.out.println(writer.toString());
}catch(Exception e){
e.printStackTrace();
}
}

  
}
 
  • 默认语言模版:Hello.ftl
Hello ${user!}! 
中文模版:Hello_zh_CN.ftl
你好 ${user!}!

输出
你好 hermit!
Hello hermit!
 

在struts项目中使用freemarker

1、引入freemarker.jar
2、web.xml加入
	<!-- FreeMarker view servlet (to replace JSP) -->
<servlet>
<servlet-name>freemarker</servlet-name><servlet-class>
freemarker.ext.servlet.FreemarkerServlet
</servlet-class>
 
<!-- FreemarkerServlet settings: -->
<init-param>
<param-name>TemplatePath</param-name>
<param-value>
/</param-value>
</init-param>
<init-param>
<param-name>NoCache</param-name>
<param-value>true</param-value>
</init-param>
<init-param>
<param-name>ContentType</param-name>
<param-value>text/html</param-value>
</init-param>

 
<!-- FreeMarker settings: --><init-param><param-name>template_update_delay</param-name><param-value>0</param-value>
<!-- 0 is for development only! Use higher value otherwise. -->

</init-param>
<init-param><param-name>default_encoding</param-name>
<param-value>
utf-8</param-value></init-param>
<init-param><param-name>locale</param-name><param-value>en_US</param-value></init-param>
<init-param>
<param-name>number_format</param-name><param-value>0.##########</param-value></init-param>
 
<load-on-startup>1</load-on-startup></servlet>
 
<servlet-mapping><servlet-name>freemarker</servlet-name><url-pattern>*.ftl</url-pattern></servlet-mapping>
 
3、一个示例页面
 
<html><head><title>Say Hello</title><METAHTTP-EQUIV="Content-Type"CONTENT="text/html; charset=utf-8"></head><body><h1>Hello ${user}!</h1></body></html>
 

我们完全可以用freemarker的模板取代JSP页面。用freemarker的模板看起更简洁,可读性更强。比如现在struts2的UI标签就是用freemarker做的。

freemarker用struts标签做国际化

  • 示例模板
<#assign  html =JspTaglibs["/WEB-INF/struts-html.tld"]><#assign  bean =JspTaglibs["/WEB-INF/struts-bean.tld"]><#assign  logic =JspTaglibs["/WEB-INF/struts-logic.tld"]><html><head><title> FreeMarker Struts Example </title><metahttp-equiv ="Content-type"content ="text/html; charset=utf-8"></ head ><body><@bean.message key ="hello"  arg0 ="hermit"/></body></html> 

主要是引入标签的时候要这样写:

<#assign  html =JspTaglibs["/WEB-INF/struts-html.tld"]> 

freemarker直接使用资源文件进行多语言国际化

  • 程序
import java.io.StringWriter;import java.util.HashMap;import java.util.Locale;import java.util.ResourceBundle;
 
import freemarker.ext.beans.BeansWrapper;import freemarker.ext.beans.ResourceBundleModel;import freemarker.template.Configuration;import freemarker.template.Template;
 
publicclass FreeMarkerTest {
 
publicstaticvoid main(String[] args){
FreeMarkerTest test = new FreeMarkerTest();
test.sayHello("hermit",Locale.CHINA);
test.sayHello("hermit",Locale.ENGLISH);
}
 
publicvoid sayHello(String name,Locale locale){
Configuration freemarkerCfg = new Configuration();
freemarkerCfg.setClassForTemplateLoading(this.getClass(), "/");
 
freemarkerCfg.setEncoding(Locale.getDefault(), "UTF-8");
Template template;
Locale.setDefault(Locale.ENGLISH);
try{
template = freemarkerCfg.getTemplate("Hello.ftl");
template.setEncoding("UTF-8");
HashMap root = newHashMap();
root.put("user", name);
ResourceBundle RESOURCE_BUNDLE = ResourceBundle.getBundle("ApplicationResources",locale);
ResourceBundleModel rsbm = new ResourceBundleModel(RESOURCE_BUNDLE,new BeansWrapper());
root.put("bundle", rsbm);
StringWriter writer = newStringWriter();
template.process(root, writer);
System.out.println(writer.toString());
}catch(Exception e){
e.printStackTrace();
}}
 
 
 
}

模板
${bundle("hello","hermit")} 

默认语言资源文件
hello=Hello {0}\! 

中文资源文件

hello=你好 {0}\!
  • 输出
你好 hermit!
Hello hermit!

关键的地方就是用ResourceBundleModel把ResourceBundle转换一下。

常用的2种加载模板的方式

  • 普通java类根据当前class上下文环境加载模板
cfg.setClassForTemplateLoading(this.getClass(), "/");
  • 在web项目中根据servlet上下文环境加载模板
cfg.setServletContextForTemplateLoading(this.getServlet().getServletContext(), "/");
posted on 2009-01-28 23:17 礼物 阅读(1755) 评论(0)  编辑  收藏 所属分类: 模板