freemarker实现通用分页,首页静态化,通用select,通用文章显示
freemarker工具类:
package org.konghao.freemarker;import java.io.File;import java.io.FileWriter;import java.io.IOException;import java.io.PrintWriter;import java.util.Map;import freemarker.template.Configuration;import freemarker.template.Template;import freemarker.template.TemplateException;public class FreemarkerUtil {//getTemplate("01.ftl")public Template getTemplate(String name) {try {//通过Freemaker的Configuration读取相应的ftlConfiguration cfg = new Configuration();//设定去哪里读取相应的ftl模板文件cfg.setClassForTemplateLoading(this.getClass(),"/ftl");//在模板文件目录中找到名称为name的文件Template temp = cfg.getTemplate(name);return temp;} catch (IOException e) {e.printStackTrace();}return null;}public void print(String name,Map<String,Object> root) {try {//通过Template可以将模板文件输出到相应的流Template temp = this.getTemplate(name);temp.process(root, new PrintWriter(System.out));} catch (TemplateException e) {e.printStackTrace();} catch (IOException e) {e.printStackTrace();}}public void fprint(String name,Map<String,Object> root,String outFile) {FileWriter out = null;try {//通过一个文件输出流,就可以写到相应的文件中out = new FileWriter(new File("D:\\webservice\\ftl\"+outFile));Template temp = this.getTemplate(name);temp.process(root, out);} catch (IOException e) {e.printStackTrace();} catch (TemplateException e) {e.printStackTrace();} finally {try {if(out!=null) out.close();} catch (IOException e) {e.printStackTrace();}}}}
package org.konghao.freemarker.test;import java.util.Arrays;import java.util.Date;import java.util.HashMap;import java.util.List;import java.util.Map;import org.junit.Before;import org.junit.Test;import org.konghao.freemarker.FreemarkerUtil;import org.konghao.freemarker.model.Article;import org.konghao.freemarker.model.Channel;import org.konghao.freemarker.model.Student;import org.konghao.freemarker.model.User;public class TestFreemarker {FreemarkerUtil fu;Map<String,Object> root = null;@Beforepublic void setUp() {fu = new FreemarkerUtil();root = new HashMap<String,Object>();}@Testpublic void test01() {//1、创建数据模型Map<String,Object> root = new HashMap<String,Object>();//2、为数据模型添加值root.put("username", "张三");//3、将数据模型和模板组合的数据输出到控制台fu.print("01.ftl", root);fu.fprint("02.ftl", root, "01.html");}@Testpublic void test02() {//freemarker还可以输出相应的对象root.put("user", new User(1,"李四",16));sprint("03.ftl");fprint("03.ftl","03.html");}@Testpublic void test04() {List<User> users = Arrays.asList(new User(1,"张三",22),new User(2,"李四",33));root.put("users",users);sprint("04.ftl");fprint("04.ftl","04.html");}@Testpublic void test05() {root.put("username", "管理员");List<User> users = Arrays.asList(new User(1,"张三",22),new User(2,"李四",33));root.put("users",users);sprint("05.ftl");fprint("05.ftl","05.html");}@Testpublic void test06() {//此时user对象并没有group的值,这时如果在页面显示group直接报错//freemarker不会处理空值root.put("user",new User(1,"地点",22));sprint("06.ftl");}@Testpublic void test07() {root.put("now",new Date());root.put("username", "李四");sprint("07.ftl");fprint("07.ftl", "07.html");}@Testpublic void test08() {sprint("08.ftl");}@Testpublic void test09() {sprint("09.ftl");}@Testpublic void test10() {root.put("username","张三");sprint("10.ftl");}@Testpublic void test11() {sprint("11.ftl");}@Testpublic void test12() {List<User> users = Arrays.asList(new User(1,"张三",22),new User(2,"李四",33),new User(3,"王五",44));root.put("users",users);List<Student> stus = Arrays.asList(new Student("123123", "地点"),new Student("11111","方法"));root.put("stus", stus);sprint("12.ftl");fprint("12.ftl","12.html");}@Testpublic void test13() {sprint("13.ftl");fprint("13.ftl","13.html");}@Testpublic void test14() {Map<String,List<Article>> arts = new HashMap<String,List<Article>>();List<Article> a1 = Arrays.asList(new Article("说给焦点方法各家阿斯顿发贺卡就是地方贺卡设计", new Channel(1, "多对多")),new Article("看似简单干净啊", new Channel(1, "多对多")),new Article("阿斯达卡说得好斯蒂芬斯蒂芬", new Channel(1, "多对多")),new Article("阿阿斯顿撒上所说的话", new Channel(1, "多对多")),new Article("是地方贺卡设计", new Channel(1, "多对多")),new Article("斯诺克打击***建设的", new Channel(1, "多对多")));arts.put("1", a1);List<Article> a2 = Arrays.asList(new Article("你说的就是公司根据阿卡什打电话", new Channel(1, "多对多")),new Article("个撒旦发撒旦发的时候", new Channel(1, "多对多")),new Article("个很好的方法斯蒂芬斯蒂芬个", new Channel(1, "多对多")),new Article("阿撒旦发撒旦发上所说的话", new Channel(1, "多对多")),new Article("是地方贺卡设计阿斯达卡的方法撒旦发撒旦发", new Channel(1, "多对多")),new Article("阿斯顿发撒旦发撒旦发撒旦和斯诺克打击***建设的", new Channel(1, "多对多")));arts.put("2", a2);root.put("arts",arts);sprint("14.ftl");fprint("14.ftl","14.html");}private void sprint(String name) {fu.print(name, root);}private void fprint(String name,String filename) {fu.fprint(name, root, filename);}}
<html><head><meta http-equiv="Content-Type" content="text/html; charset=UTF-8"><title>Insert title here</title></head><body><#macro showArt cid titleNum><#nested><#local articles=arts[cid]/><#list articles as art><li><span><a href=""><#if (art.title?length>titleNum)>${art.title[0..titleNum]}...<#else>${art.title}</#if></span></a></li></#list></#macro><@showArt cid="1" titleNum=7><h1>水水水水水水</h1></@showArt><@showArt cid="2" titleNum=10><h1>活活后发货后会</h1></@showArt></body></html>
<html><head><meta http-equiv="Content-Type" content="text/html; charset=UTF-8"><title>Insert title here</title></head><body><#import "/inc/pager.ftl" as my/><@my.pager url="#" totalPage=150 curPage=14 showPageNum=20/></body></html>
<html><head><meta http-equiv="Content-Type" content="text/html; charset=UTF-8"><title>Insert title here</title></head><body><#import "/inc/select.ftl" as my/><@my.select id="address" datas=["北京","天津","上海"]/><@my.select id="sex" datas=["选择性别","男","女"] value="男"/><@my.select id="username" datas=users key="id" text="name" headkey="-1" headtext="请选择用户"/><@my.select id="stu" datas=stus key="no" text="name" headkey="-1" headtext="请选择学生"/><@my.select id="sex" datas={"0":"男","1":"女"} value="1"/></body></html>
<html><head><meta http-equiv="Content-Type" content="text/html; charset=UTF-8"><title>Insert title here</title></head><body><#--使用incldue可能会出现覆盖的问题,可以使用import来完成导入,并且加入名称空间<#include "/inc/inc1.ftl"/><#include "/inc/inc2.ftl"/>--><#import "/inc/inc2.ftl" as inc2/><#import "/inc/inc1.ftl" as inc1/>${inc2.username}${inc1.username}<#--将一个变量定义到名称空间中--><#assign age=12 in inc2/>${inc2.age}<#--访问名称空间中的自定义指令--><@inc1.test/></body></html>
<html><head><meta http-equiv="Content-Type" content="text/html; charset=UTF-8"><title>Insert title here</title></head><body><#assign username="李四"><#--此时模板中的变量的名称和模型中的变量名称一致,不是覆盖,而是隐藏-->${username}<#--使用.globals可以访问模型中的变量-->${.globals.username}<#macro test><#--此时当调用该指令之后,会将模板中的变量username覆盖为王五所以这种方式存在风险,所以一般不使用这种方式在指令中定义变量--><#--<#assign username="王五"/>--><#--使用local可以声明局部变量,所以在marco中非特殊使用局部变量--><#local username="王五"/>${username}</#macro><@test/>${username}<#list 1..3 as username><#--循环中的变量出了循环就消失-->${username}</#list>${username}</body></html>
<html><head><meta http-equiv="Content-Type" content="text/html; charset=UTF-8"><title>Insert title here</title></head><body><#--对于hello这个自定义指令而言,hello后的都是参数,有两个参数一个是num一个是ok--><#macro hello num ok><#list 1..num as n><h1>Hello${ok}${n}</h1></#list></#macro><#--<@hello/>会报错,因为hello有两个参数,在定义参数的值的时候参数名不能省略--><@hello num=3 ok="World"/><#--为repeat的两个参数定义了初始值,此时在调用该指令就可以省略参数,如果省略会使用默认值--><#macro repeat num=10 ok="World"><#list 1..num as n><h1>Hello${ok}${n}</h1></#list></#macro><@repeat/><#macro test><#--nested会输出指令中的内容--><#nested 12 33/><#nested 11 22/><#nested 22 33/></#macro><@test;x,y><h1>你好啊--${x}--${y}</h1></@test></body></html>
<html><head><meta http-equiv="Content-Type" content="text/html; charset=UTF-8"><title>Insert title here</title></head><body><#assign nums=[1,3,4,56,33,43]/>${nums?first}<#--特别注意,以下定义不使用[12..200]--><#assign nums=12..200/><#--定义了一个连续的序列从12到199--><#--序列的拆分--><#assign nums1=nums[1..10]><#list nums1 as num>${num}</#list>${"你好,你来了吗今天看书了吗!"[0..8]}...<#assign maps={"1":"张三","2":"李四"}>${maps["1"]}<#--以下代码可以将map的key转换为相应的序列--><#assign keys=maps?keys><#list keys as key>${key}---${maps[key]}<#assign users={"username":"张三","password":"123"}>${users.username}---${users["password"]}</#list></body></html>
<html><head><meta http-equiv="Content-Type" content="text/html; charset=UTF-8"><title>Insert title here</title></head><body><#--定义变量--><#assign username="张三"/>${username}<#--定义了一个数字--><#assign num=10>${num+11}<#assign str="10"/>${str+11}<#--值会完成覆盖--><#assign str=33/>${str+11}<#assign b=true/><#--不能直接输出数字或者字符串以外的类型,否则都会报错,需要转换为字符串才能输出使用xxx?string可以完成对字符串的转换--><#--${b}-->${b?string}${(a.d)???string}<#--日期也不能直接输出,需要转换为字符串-->${now?string("yyyy-MM-dd HH:mm:ss")}<#--${now?string}没有为日期设定格式也会报错--><#--以下显示了使用字符链接和插值的方式连接字符串-->${"hello"+username}${"hello${username}"}<#--字符串转换为日期data用来转换日期,datatime用来转换日期和时间,time用来转换时间--><#assign bir="1979-12-02 12:22:33"?date("yyyy-MM-dd HH:mm:ss")><#assign bir="1979-12-02 12:22:33"?datetime("yyyy-MM-dd HH:mm:ss")>${bir}${"<br/>"?html}[${"abcde"?left_pad(10,"--")}]${1.4?string(0)}${1.8?int}</body></html>
<html><head><meta http-equiv="Content-Type" content="text/html; charset=UTF-8"><title>Insert title here</title></head><body>${user.id}-------${user.name}------${user.group!}<#--${user.group.name!}--><#-- 按照以上的方式加! freemarker仅仅只会判断group.name是不是空值 -->${(user.group.name)!"没有任何值存在"}${(a.b)!"没有a.b元素"}<#if (a.b)??>不为空<#else>为空</#if></body></html>
<html><head><meta http-equiv="Content-Type" content="text/html; charset=UTF-8"><title>Insert title here</title></head><body><#include "/inc/top.ftl"/><hr/><#list users as user>${user.id}---------${user.name}-------${user.age}<br/></#list></body></html>
<html><head><meta http-equiv="Content-Type" content="text/html; charset=UTF-8"><title>Insert title here</title></head><body><#list users as user>${user.id}---------${user.name}-------${user.age}<br/></#list></body></html>
<html><head><meta http-equiv="Content-Type" content="text/html; charset=UTF-8"><title>Insert title here</title></head><body><h1>${user.id}-----${user.name}-----${user.age}</h1><#if user.age lt 12>${user.name}还是一个小孩<#elseif user.age lt 18>${user.name}快成年<#else>${user.name}已经成年</#if></body></html>
<html><head><meta http-equiv="Content-Type" content="text/html; charset=UTF-8"><title>Insert title here</title></head><body><h1>${username}</h1></body></html>
你好:${username}
<#assign username="张三"><#macro test>hello world</#macro>
<#assign username="李四">
<#macro pager url totalPage curPage=1 showPageNum=15><#local halfPage=(showPageNum/2)?int/>${halfPage}<#if (halfPage>=curPage)><@showPage start=1 end=curPage url=url class=class curPage=curPage/><@showPage start=curPage+1 end=showPageNum curPage=curPage url=url class=class/><#else><@showPage start=curPage-halfPage end=curPage url=url class=class curPage=curPage/><#if (curPage+halfPage>totalPage)><#local endPage=totalPage/><#else><#local endPage=curPage+halfPage/></#if><@showPage start=curPage+1 end=endPage url=url class=class curPage=curPage/></#if></#macro><#macro showPage start end curPage url class><#list start..end as page><#if curPage==page>[${page}]<#else><a href="${url}" name="code"><#macro select id datas value="" key="" text="" headkey="" headtext=""><select id="${id}" name="${id}"><#if headkey!=""><option value="${headkey}">${headtext}</option></#if><#if datas?is_hash_ex><#local keys=datas?keys/><#list keys as key><#if key==value><option value="${key}" selected>${datas[key]}</option><#else><option value="${key}">${datas[key]}</option></#if></#list><#else><#list datas as data><#if key!=""><#if value==data[key]?string><option value="${data[key]}" selected>${data[text]}</option><#else><option value="${data[key]}">${data[text]}</option></#if><#else><#if value==data><option value="${data}" selected>${data}</option><#else><option value="${data}">${data}</option></#if></#if></#list></#if></select></#macro>
<h1>欢迎${username}访问我们的系统</h1>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd"> <modelVersion>4.0.0</modelVersion> <groupId>org.konghao.freemarker</groupId> <artifactId>freemarker-hello</artifactId> <version>0.0.1-SNAPSHOT</version> <packaging>jar</packaging> <name>freemarker-hello</name> <url>http://maven.apache.org</url> <properties> <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding> </properties> <dependencies> <dependency> <groupId>junit</groupId> <artifactId>junit</artifactId> <version>4.7</version> <scope>test</scope> </dependency> <dependency> <groupId>org.freemarker</groupId> <artifactId>freemarker</artifactId> <version>2.3.19</version></dependency> </dependencies></project>
<?xml version="1.0" encoding="UTF-8"?><beans xmlns="http://www.springframework.org/schema/beans"xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:context="http://www.springframework.org/schema/context"xmlns:mvc="http://www.springframework.org/schema/mvc"xsi:schemaLocation="http://www.springframework.org/schema/mvc http://www.springframework.org/schema/mvc/spring-mvc-3.1.xsdhttp://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-3.0.xsdhttp://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-3.0.xsd"><mvc:annotation-driven /><context:component-scan base-package="org.konghao.fre.controller"></context:component-scan><mvc:resources location="/resources/" mapping="/resources/**" /><bean id="freemarkerConfig" value="/WEB-INF/ftl/"/></bean><bean id="viewResolver" value="true"/> <property name="prefix" value=""/> <property name="suffix" value=".ftl"/> <property name="contentType" value="text/html; charset=UTF-8"></property></bean><bean/><property name="prefix" value="/WEB-INF/jsp/"></property><property name="suffix" value=".jsp"></property></bean><bean value="application/json" /><entry key="xml" value="text/xml" /><entry key="htm" value="text/html" /></map></property><property name="defaultContentType" value="text/html" /></bean></beans>