tiles用来定义界面布局,瓦片 的意思,可能认为一个网页是有好多瓦片搭建而成吧
去 http://tiles.apache.org/download.html 把他的源代码下载下来
unzip -x tiles-2.1.2-src.zip
cd tiles-2.1.2
mv src src2
mv src2/* .
rmdir src2
mvn compile dependency:sources # 等吧,要几分钟
mvn eclipse:configure-workspace -Declipse.workspace=web
mv web/* .
mvn eclipse:eclipse
这就算编译完了,而后用eclipse启动tiles-2.1.2中的workspace就好,不明白mvn也没什么,
也不太需要看 tiles 的代码,想知道mvn是怎么回事,看我以前的介绍
看了看 http://tiles.apache.org/framework/tutorial/index.html,感觉还好,
tiles 的功能就是进行页面布局,下面也就是看看tutorial这中如何定义 tiles-defs.xml
中的<definition>元素,还有如何使用tiles提供的<tiles:insertDefinition> 和
<tiles:insertTemplate>标签
tiles tutorial :
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Basic Usage/Creating Pages:
web.xml template.jsp tiles-defs.xml userpage.jsp中的<tiles:insertDefinition>标签
1. 在 web.xml 中注册 tiles初始化servlet
<servlet>
<servlet-name>tiles</servlet-name>
<servlet-class>org.apache.tiles.servlet.startup.TilesServlet</servlet-class>
<init-param>
<param-name>org.apache.tiles.impl.BasicTilesContainer.DEFINITIONS_CONFIG
</param-name>
<param-value>/WEB-INF/tiles-defs.xml</param-value>
</init-param>
<load-on-startup>2</load-on-startup>
</servlet>
2. 定义模板的布局 layout/classic.jsp
<%@ taglib uri="http://tiles.apache.org/tags-tiles" prefix="tiles" %>
<html>
<head>
<title><tiles:getAsString name="title"/></title>
</head>
<body>
<table>
<tr>
<td colspan="2">
<tiles:insertAttribute name="header" />
</td>
</tr>
<tr>
<td>
<tiles:insertAttribute name="menu" />
</td>
<td>
<tiles:insertAttribute name="body" />
</td>
</tr>
<tr>
<td colspan="2">
<tiles:insertAttribute name="footer" />
</td>
</tr>
</table>
</body>
</html>
2. 在 tiles-defs.xml 中注册模板
<?xml version="1.0" encoding="ISO-8859-1" ?>
<!DOCTYPE tiles-definitions PUBLIC
"-//Apache Software Foundation//DTD Tiles Configuration 2.1//EN"
"http://tiles.apache.org/dtds/tiles-config_2_1.dtd">
<tiles-definitions>
<definition name="myapp.homepage" template="/layouts/classic.jsp">
<put-attribute name="title" value="Tiles tutorial homepage" />
<put-attribute name="header" value="/tiles/banner.jsp" />
<put-attribute name="menu" value="/tiles/common_menu.jsp" />
<put-attribute name="body" value="/tiles/home_body.jsp" />
<put-attribute name="footer" value="/tiles/credits.jsp" />
</definition>
</tiles-definitions>
3. 在所有页面中,都可以使用该 <tiles:insertDefinition> 来使用布局
<%@ taglib uri="http://tiles.apache.org/tags-tiles" prefix="tiles" %>
<tiles:insertDefinition name="myapp.homepage" />
z或者在 servlet 中通过以下代码使用 tiles
TilesContainer container = ServletUtil.getContainer(
request.getSession().getServletContext());
container.render("myapp.homepage", request, response);
Advanced Topic/Rendering Utilities中介绍了如何使用 TilesDispatchSevlet 显示
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Advanced Topics/Nesting and Extending
tiles-defs.xml 中 <definition> 元素的使用方法
在 tiles-defs.xml 配置文件中,一个<definition>1的定义中,通过<put-attribue>嵌套引用另
一个<definition>2,这时将 <definition>2 称为 <definiton>1的 subdefinition;
也可以让一个<definition>继承另一个<definition>
在 tiles-defs.xml 中使用 subdefinition:
<!-- subdefiniton也就是一个普通的 definition,可以作为其他 definition 的属性 -->
<definition name="myapp.homepage.body" template="/layouts/three_rows.jsp">
<put-attribute name="one" value="/tiles/headlines.jsp" />
<put-attribute name="two" value="/tiles/topics.jsp" />
<put-attribute name="one" value="/tiles/comments.jsp" />
</definition>
<definition name="myapp.homepage" template="/layouts/classic.jsp">
<put-attribute name="title" value="Tiles tutorial homepage" />
<put-attribute name="header" value="/tiles/banner.jsp" />
<put-attribute name="menu" value="/tiles/common_menu.jsp" />
<!-- 在这里使用已经定义的 myapp.home.body 作为属性 -->
<put-attribute name="body" value="myapp.homepage.body" />
<put-attribute name="footer" value="/tiles/credits.jsp" />
</definition>
也可以把 subdefinition 不显示的定义在 tiles-defs.xml中,匿名使用:
<definition name="myapp.homepage" template="/layouts/classic.jsp">
<put-attribute name="title" value="Tiles tutorial homepage" />
<put-attribute name="header" value="/tiles/banner.jsp" />
<put-attribute name="menu" value="/tiles/common_menu.jsp" />
<put-attribute name="body">
<definition template="/layouts/three_rows.jsp">
<put-attribute name="one" value="/tiles/headlines.jsp" />
<put-attribute name="two" value="/tiles/topics.jsp" />
<put-attribute name="one" value="/tiles/comments.jsp" />
</definition>
</put-attribute>
<put-attribute name="footer" value="/tiles/credits.jsp" />
</definition>
所谓 层叠属性cascade-attribute:将定义在<definition>1中的属性<tiles:insertAttribute>1
标记为cascade,那么<definition>1 的subdefinition <definition>2的template包含的所有
<tiles:insertAttribute>中,如果 <tiles:insertAttribute>x的name属性 与
<tiles:insertAttribute>1的name 相同的,<definiton>2 就可以使用定义在 <definiton>1中的
<tiles:insertAttribute>1 作为 <definiton>2 的 <tiles:insertAttribute>x,例如:
z模板文件为:
/layout/def-template.jsp
<tiles:insertAttribute name="def-attr-name1"/><br> <!-- ^^^^ -->
<tiles:insertAttribute name="def-attr-name2"/><br>
/layout/subdef-template.jsp
<tiles:insertAttribute name="subdef-attr-name"/><br>
<tiles:insertAttribute name="def-attr-name1"/><br> <!-- ^^^^ -->
tiles-defs.xml 为:
<definition name="definition1" template="/layout/def-template">
<put-attribute name="def-attr-name1" value="/xxx.jsp" cascade="true"/>
<put-attribute name="def-attr-name2" value="/yyy.jsp"/>
<put-attribute name="def-attr-name3" value="definition2"/>
</definition>
<definition name="definition2" template="/layout/subdef-template.jsp"/>
<put-attribute name="subdef-attr-name" value="/zzz.jsp"/>
<!--
z无须设置<put-attribute name='def-attr-name1'.../>,
z使用 definition1 中定义的内容即可,认为不太常用
-->
</definiiton>
<definition>的继承,例如,myapp.homepage 继承 myapp.page.common :
<definition name="myapp.page.common" template="/layouts/classic.jsp">
<put-attribute name="header" value="/tiles/banner.jsp" />
<put-attribute name="menu" value="/tiles/common_menu.jsp" />
<put-attribute name="footer" value="/tiles/credits.jsp" />
</definition>
<definition name="myapp.homepage" extends="myapp.page.common">
<put-attribute name="title" value="Tiles tutorial homepage" />
<put-attribute name="body" value="myapp.homepage.body" />
</definition>
<definiton>在继承时,也可以进行覆盖,例如:
<definition name="myapp.homepage.alternate" extends="myapp.homepage"
template="/layouts/alternate.jsp" > <!-- 覆盖模板属性 -->
<!-- 覆盖 put-attribute 元素 -->
<put-attribute name="menu" value="/tiles/common_menu_for_customers.jsp" />
</definition>
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Advanced Topics/Runtime Composition:
tiles提供的标签:<tiles:insertTemplate>
直接在.jsp中定义界面布局,这样就无须在 tiles-defs.xml 中再配置 <definition>元素,例如:
user-page.jsp:
<tiles:insertTemplate template="/layouts/classic.jsp">
<tiles:putAttribute name="title" value="Tiles tutorial homepage" />
<tiles:putAttribute name="header" value="/tiles/banner.jsp" />
<tiles:putAttribute name="menu" value="/tiles/common_menu.jsp" />
<tiles:putAttribute name="body">
<tiles:insertTemplate template="/layouts/variable_rows.jsp">
<tiles:putListAttribute name="items">
<tiles:addAttribute value="/tiles/banner.jsp" />
<tiles:addAttribute value="/tiles/common_menu.jsp" />
<tiles:addAttribute value="/tiles/credits.jsp" />
</tiles:putListAttribute>
</tiles:insertTemplate>
</tiles:putAttribute
<tiles:putAttribute name="footer" value="/tiles/credits.jsp" />
</tiles:insertTemplate>
也可以在 .jsp 中继承已经在 tiles-defs.xml 中配置的 <definition>,并覆盖template属性和
<tiles:putAttribute> 属性
<tiles:insertDefinition name="myapp.homepage.customer"
template="/layouts/alternative_layout.jsp">
<tiles:putAttribute name="menu" value="/tiles/common_menu_for_customers.jsp"/>
</tiles:insertDefinition>
myapp.homepage.customer 为:
<definition name="myapp.homepage" extends="myapp.page.common">
<put-attribute name="title" value="Tiles tutorial homepage" />
<put-attribute name="body" value="myapp.homepage.body" />
</definition>
被 myapp.homepage.customer 继承的 myapp.page.common 为:
<definition name="myapp.page.common" template="/layouts/classic.jsp">
<put-attribute name="header" value="/tiles/banner.jsp" />
<put-attribute name="menu" value="/tiles/common_menu.jsp" />
<put-attribute name="footer" value="/tiles/credits.jsp" />
</definition>
<tiles:insertDefinition>标签可以让.jsp使用 已经注册在tiles-defs.xml中的模板 指定 .jsp页
的展现形式,<tiles:insertDefinition> 可以搞定基本全部页面的展现形式,但有些页面的展现形式
还是与 tiles-defs.xml中配置的模板 有些出入的,使用 <tiles:insertDefinition> 可以在jsp页
中直接设置页面的展现所使用的模板
使用以下代码来指定 servlet 显示时使用的模板,类似于jsp中的<tiles:insertTemplet>
// 获取tiles容器
TilesContainer container = ServletUtil.getContainer(
request.getSession().getServletContext());
// 创建body属性
Attribute bodyAttribute = new Attribute("body");
bodyAttribute.setValue("/tiles/body_customer.jsp");
// 重新创建属性上下文
AttributeContext attributeContext = container.startContext(request,
response);
// 将属性添加到上下文中
attributeContext.setTemplateAttribute(bodyAttribute);
// 根据属性上下文attributeContext,显示页面
container.render("myapp.homepage", request, response);
container.endContext(request, response);
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Advanced Topics/View Prepares
jsp 按照 tiles定义的模板显示前,会先调用注册在该模板上的preparer来完成init
定义ViewPreparer,例如:
package tiles.viewpreparer;
import org.apache.tiles.preparer.PreparerException;
import org.apache.tiles.preparer.ViewPreparer;
import org.apache.tiles.context.TilesRequestContext;
import org.apache.tiles.AttributeContext;
import org.apache.tiles.Attribute;
public class CustomViewPreparer implements ViewPreparer {
public void execute(TilesRequestContext tilesContext,
AttributeContext attributeContext) throws PreparerException {
attributeContext.putAttribute("body",
new Attribute("This is the value added by the ViewPreparer"));
}
}
在 tiles-defs.xml 中为 <definition> 配置 preparer:
<definition name="preparer.definition"
preparer="tiles.viewpreparer.CustomViewPreparer">
<put-attribute name="foo" value="/bar/foo.jsp" />
</definition>
tiles的默认实现中以单态的形式创建ViewPreparer,参考BasicPreparerFactory
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Advanced Topics/EL Support
可以在 tiles-defs.xml 中,配置<definition>元素时加入EL表达式
支持EL表达式的<definition>定义,通过EL指定界面显示时使用的 模板 和 内容,例如:
<definition name="test.composite.el.definition"
templateExpression="${layout}"> <!-- 显示时使用的模板 -->
<put-attribute name="title" value="String title, not a jsp."/>
<put-attribute name="header" value="/header.jsp"/>
<!-- 显示时的内容 -->
<put-attribute name="body" expression="${requestScope.body}"/>
</definition>
在<definition>中使用EL时,需要进行如下配置:
web.xml:
<servlet>
<servlet-name>tiles-init</servlet-name>
<servlet-class>org.apache.tiles.web.startup.TilesServlet</servlet-class>
<init-param>
<param-name>org.apache.tiles.evaluator.AttributeEvaluator</param-name>
<param-value>org.apache.tiles.evaluator.el.ELAttributeEvaluatr</param-value>
</init-param>
</servlet>
当然也可以通过在jsp中指定:
<tiles:insertDefinition name="myapp.homepage.customer"
template="/layouts/alternative_layout.jsp">
<tiles:putAttribute name="someAttr" value="${requestScope.myBean.attr}"/>
</tiles:insertDefinition>