什么是SiteMesh

SiteMesh 是一个网页布局和修饰的框架,利用它可以将网页的内容和页面结构分离,以达到页面结构共享的目的,它不仅仅能处理动态的内容,如jsp、asp等产生的内容,它也能处理静态页面HTML的内容,使得它的内容也符合你的页面结构的要求,甚至于它能将HTML文件象include那样将该文件作为一个面板的形式嵌入到别的文件中去。

简单来说就是我们使用sitemesh来指定一套模板页面来装饰其他非模板页面,让我们的web应用在展示时有一致的布局风格,可以类比于我们用的iframe布局。

这里引用一下官方的工作流程描述:

更多内容可以访问:http://wiki.sitemesh.org/wiki/display/sitemesh/Home

使用案例

引入依赖

下载sitemesh相关依赖jar包:http://wiki.sitemesh.org/display/sitemesh/Download

在IDEA中创建一个Web工程,在WEB-INF目录下创建一个lib目录,将sitemesh的jar包添加进去
/WEB-INF/lib/sitemesh.jar!/com/opensymphony/module/sitemesh/factory/sitemesh-default.xml这个路径可以看到sitemesh的默认配置文件,一般不需要去改动,特殊需求下也可以自定义规则。

<sitemesh>
    <property name="decorators-file" value="/WEB-INF/decorators.xml"/>
    <excludes file="${decorators-file}"/>

	<page-parsers>
		<parser content-type="text/html" class="com.opensymphony.module.sitemesh.parser.HTMLPageParser" />
	</page-parsers>
	<decorator-mappers>
		<mapper class="com.opensymphony.module.sitemesh.mapper.PageDecoratorMapper">
			<param name="property.1" value="meta.decorator" />
			<param name="property.2" value="decorator" />
		</mapper>
		<mapper class="com.opensymphony.module.sitemesh.mapper.FrameSetDecoratorMapper"/>
		<mapper class="com.opensymphony.module.sitemesh.mapper.PrintableDecoratorMapper">
			<param name="decorator" value="printable" />
			<param name="parameter.name" value="printable" />
			<param name="parameter.value" value="true" />
		</mapper>
		<mapper class="com.opensymphony.module.sitemesh.mapper.FileDecoratorMapper"/>
		<mapper class="com.opensymphony.module.sitemesh.mapper.ConfigDecoratorMapper">
			<param name="config" value="${decorators-file}" />
		</mapper>
	</decorator-mappers>
</sitemesh>

配置web.xml

然后在web.xml中配置sitemesh过滤器,因为我们的页面是要交给sitemesh来装饰,当然需要把需要装饰的页面交给sitemesh来处理。

  <!--配置sitemesh过滤器-->
    <filter>
        <filter-name>sitemesh</filter-name>
        <filter-class>com.opensymphony.sitemesh.webapp.SiteMeshFilter</filter-class>
    </filter>
    <filter-mapping>
        <filter-name>sitemesh</filter-name>
        <url-pattern>/*</url-pattern>
    </filter-mapping>

配置decorators.xml

sitemesh-default.xml描述了需要一个decorators-file,而且这个文件的路径在/WEB-INF/decorators.xml,这个文件的使用很简单,我们只需要定义装饰的模板文件路径和被装饰的文件就可以使用,还可以过滤哪些文件是不需要装饰的。

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE decorators>
<!--default dir 装饰模板文件的路径-->
<decorators defaultdir="/decorators">
	<!-- 用来定义装饰器要过滤的页面
		name:装饰器的名字 main
		page:使用default dir下面的哪个文件作为装饰器
		pattern:需要装饰的页面 /*表示所有页面都需要使用main来装饰
	-->
	<decorator name="main" page="main.jsp">
		<pattern>/*</pattern>
	</decorator>

	<!-- 此处用来定义不需要过滤的页面
		pattern:哪些页面不需要使用装饰器来装饰
	-->
	<excludes>
		<!--<pattern>/*</pattern>-->
	</excludes>
</decorators>

定义好装饰文件之后接下来就是如何使用,上面文件指出了我们定义的一个装饰文件叫main.jsp,当然针对不同的页面布局我们可以定义不同的装饰文件,只需要配置多个decorator标签即可。main.jsp的内容如下:

<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<%@ taglib prefix="decorator" uri="http://www.opensymphony.com/sitemesh/decorator" %>
<html>
<head>
    <title><decorator:title/></title>
</head>
<body>
<h2>我是头部内容</h2>
<hr/>
<decorator:body></decorator:body>
<hr/>
<h2>我是尾部内容</h2>
</body>
</html>

sitemesh自己定义一些标签库,在jsp文件中我们需要什么标签就引入这些标签库,首先引入sitemesh的标签库

<%@ taglib prefix="decorator" uri="http://www.opensymphony.com/sitemesh/decorator" %>

然后使用标签来定义我们需要装饰的部分,比如这里我们使用<decorator:title/>就可以需要装饰的页面的<title/>引用过来。

常用标签库

sitemesh的标签库总共分为两大类:

  • Decorate

    <decorator:title/>
    <decorator:head/>
    <decorator:body/>
    <decorator:getProperty property=""/>
    <decorator:usePage id=""/>
    <decorator:useHtmlPage id=""/>
    

    title: 引入原始页面<title>标签中的内容(不包括title标签本身)

    head: 引入原始页面的<head>标签中的内容(不包括head标签本身)

    body:引入原始页面的<body>标签中的内容(不包括body标签本身)

    getProperty: 引入原始页面的property属性指定的值同名的属性

    usePage & useHtmlPage:用来扩展title、head、body等标签,读取这些标签的属性值

  • Page

    <page:applyDecorator name="" page="" contentType="" encoding="" id="" title=""/>
    <page:param name=""/>
    

    applyDecorator:可以理解为将装饰器,嵌入到另一个装饰器,name:属性值为decorator中配置的装饰器名称,page:属性值为需要被嵌入的装饰器装饰的页面, title:覆盖被包含页面的title标签的内容

    应用场景:在主页面中,左侧布局一个菜单,这个菜单本身就是一个装饰器,再把菜单这个装饰器嵌入到我们的主装饰器。

    param:解析一个属性到装饰器,这个属性会覆盖原有页面中的的属性,name:指定要被重写属性的值

样例代码

具体案例代码:https://gitee.com/starslight/test/tree/master/sitemesh