Java ---自定义标签
本篇文章介绍自定义标签,可能在工作中很少涉及到自己来定义一个标签库,因为我们基本上都是使用的大神写的标签库,基本上直接使用即可,但是从自身的发展来看,通往高级程序员的道路上,开发框架就需要大量的使用到标签库技术。本文将从以下几个方面介绍自定义标签库的基本知识点:
- 背景以及作用
- 开发简单的标签
- 开发带属性的标签
- 开发带标签体的标签
- 以页面片段为属性的标签
- 具有动态属性的标签
一、标签库有什么作用
自定义标签库是一种优秀的表现层技术,之前介绍的MVC模式,我们使用jsp作为表现层,但是jsp语法嵌套在html页面,美工还是很难直接参与开发,并且jsp脚本和html代码耦合在一起,维护成本较高。我们能不能开发一套和html风格类似并且能完成jsp脚本功能的标签来解决这种低效的协作方式呢?于是标签库就诞生了。
这是Java中标签规范的继承体系,实现Tag接口的我们叫做传统式标签库开发,这种开发模式略显发复杂,基本已经被SimpleTag式的简单式开发标签库给取代了。Java中提供了一个默认的实现类SimpleTagSupport来实现自定义标签,我们只要继承此类即可。
二、开发一个最简单的标签库
开发一个自定义标签库的过程如下:
- 开发自定义标签处理类
- 创建*.tld文件,每个此文件对应一个标签库,标签库中可以由多个标签
- 在jsp页面使用标签
首先我们先从自定义标签处理类开始,正如上文所说,这个类只有继承了SimpleTagSupport这个类可以省去省去重写SimpleTag接口中的一些方法。我们说个doTag()这个方法很重要,这个方法类似于我么main方法一样,当jsp页面加载到我们定义的标签的时候就会过来调用这个方法。
public class MyTag extends SimpleTagSupport {
@Override
public void doTag() throws JspException, IOException {
getJspContext().getOut().write("hello walker");
}
}
这是一个简单的标签处理类,具体的细节暂时不用关心,只需要知道,它负责向jsp页面输出字符串即可。下面我们看看第二步,创建*tld文件。这个文件我们没有必要重新写一遍,到Tomcat服务器上的webapps/examples/WEB-INF/jsp2中复制一个过来,修改名字存放到我们的项目中WEB-INF的任意子路径下。删除一些标签成如下内容:
我们看到这是一个XML文件,根元素为taglib,而taglib主要有以下几个子元素:
- description //描述信息
- tlib-version //指定标签库的版本号,基本不用我们操心
- short-name //指定标签库的短名字,也是没什么用
- uri //这是一个重要的子元素,是该标签库的唯一标识
- tag //看名字就知道,这是定义标签的子元素,很重要
对于taglib这个根元素,我们主要关心他下面的uri和tag两个子元素,一个标签库可以由多个标签,也就是可以有多个tag标签。关于tag标签,主要有以下几个子元素:
- description //描述信息
- name //该标签的唯一标识,很重要
- tag-class //指定了处理该标签的类,也就是使用该标签谁给我返回结果
- body-content //标签体,后面详说,很重要
- attribute //属性,后面介绍,很重要
对于以上标签大家可能已经知道什么意思,但是具体用在什么地方可能不清楚,本小节的最后会综合三个步骤自定义一个简单的标签。接下来介绍在jsp页面是如何使用标签。
使用标签库也是有两个步骤,首先导入标签库,然后引用标签。我们使用taglib编译指令导入标签库,具体格式如下:
<%@ taglib uri="tld文件中指定的唯一标识" prefix="指定标签前缀"%>
我们看到这个导入标签库的编译指令主要有两个属性,一个是用于定位我们已经写好的标签库,定位的方法就是读取每个tld文件中的URI元素的值,prefix用于指定我们使用标签时的前缀,等用的时候就很容易理解了,现在解释反而不容易说清楚。我们使用标签的格式如下:
<刚刚指定的前缀 :标签名 />
标签名就是我们标签库中每个tag都会有的name的值,这指定了该语句是引用的那个标签。下面我们通过具体的例子直观感受下。
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<%@taglib uri="mytid" prefix="mytags"%>
<html>
<head>
<title></title>
</head>
<body>
<mytags:hello />
</body>
</html>
<taglib xmlns="http://java.sun.com/xml/ns/j2ee"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://java.sun.com/xml/ns/j2ee http://java.sun.com/xml/ns/j2ee/web-jsptaglibrary_2_0.xsd"
version="2.0">
<description>A tag library exercising SimpleTag handlers.</description>
<tlib-version>1.0</tlib-version>
<short-name>SimpleTagLibrary</short-name>
<uri>mytid</uri>
<tag>
<description>Outputs a colored tile</description>
<name>hello</name>
<tag-class>Test.MyTag</tag-class>
<body-content>empty</body-content>
</tag>
</taglib>
public class MyTag extends SimpleTagSupport {
@Override
public void doTag() throws JspException, IOException {
getJspContext().getOut().write("hello walker");
}
}
结果如下:
这就完成了一个最简单的标签库的定义和使用的过程,首先我们在index.jsp页面通过URI引入mytag标签库,指定了使用该标签库的前缀为mytags,然后<mytags:hello />引用name为hello的tag标签,然而在加载这条语句的时候会通过我们的tag中指定的处理类,找到它并执行,最后通过此标签处理类想我们的jsp页面输出了一个字符串。以上就是一个最简单的自定义标签的过程,为了更好的理解后续的较复杂的自定义标签方式,上述内容值得感受体会。
三、开发带属性的标签
假如我们通过拦截器获取了从数据库查出来的一个结果集,我们此处希望调用标签来将结果集以表格的形式输出来,此时我们的这个结果集又该如何传到标签处理类中呢?这时我们可以使用属性。具体看代码:
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<%@taglib uri="mytid" prefix="mytag"%>
<html>
<head>
<title></title>
</head>
<body>
<%
HashMap<String,Integer> maps = new HashMap<String, Integer>();
maps.put("李四",53);
maps.put("张三",23);
maps.put("walker",22);
pageContext.setAttribute("map",maps);
%>
<table>
<mytag:hello map="map"/>
</table>
</body>
</html>
<taglib xmlns="http://java.sun.com/xml/ns/j2ee"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://java.sun.com/xml/ns/j2ee http://java.sun.com/xml/ns/j2ee/web-jsptaglibrary_2_0.xsd"
version="2.0">
<description>A tag library exercising SimpleTag handlers.</description>
<tlib-version>1.0</tlib-version>
<short-name>SimpleTagLibrary</short-name>
<uri>mytid</uri>
<tag>
<description>Outputs a colored tile</description>
<name>hello</name>
<tag-class>Test.MyTag</tag-class>
<body-content>empty</body-content>
<attribute>
<name>map</name>
<required>true</required>
<fragment>true</fragment>
</attribute>
</tag>
</taglib>
public class MyTag extends SimpleTagSupport {
private String map;
public String getMap(){
return this.map;
}
public void setMap(String map){
this.map = map;
}
@Override
public void doTag() throws JspException, IOException {
HashMap<String,Integer> maps = (HashMap<String,Integer>)(getJspContext().getAttribute(map));
Object[] array = maps.keySet().toArray();
for (String str : maps.keySet()){
getJspContext().getOut().write("<tr>");
getJspContext().getOut().write("<td>");
getJspContext().getOut().write(str);
getJspContext().getOut().write("</td>");
getJspContext().getOut().write("<td>");
getJspContext().getOut().write(""+maps.get(str));
getJspContext().getOut().write("</td>");
getJspContext().getOut().write("</tr>");
}
}
}
我们首先先从index.jsp页面看起,首先我们定义了一个HashMap用来存放一个简单的个人信息,键为姓名值为年龄。最后我们设置共享范围为当前page。然后<mytag:hello map="map"/>,这里的map=“map”,第一个map是属性名,第二个只是一个字符串。下面进入到tld页面看,这个页面基本没有什么改动,只是多了个attribute元素,attribute中有几个子元素,第一个是name指定这个属性的唯一标识,第二个required指定该属性是否是必须属性。第三个fragment指定该属性是否支持jsp脚本。主要关心name这个元素。这个值和jsp页面调用标签时使用的属性名必须一样,并且这个属性值还必须和标签处理类中的私有属性名一样,这就是为了jsp页面的属性值能够自动的传入到标签处理类的属性中,我们看这个标签处理类
这个类定义了私有属性map,和我们的tld文件中的属性名是一致的。getJspContext().getAttribute(map),首先是获得了调用该标签的jsp页面的pageContext,这就是方法getJspContext的返回值,因为我们在jsp页面设置了一个共享数据(maps),于是我们同名名字获取该对象,这里的map就是我们的私有属性,他的值被自动赋值了,具体的值就是jsp页面传入的参数。后面的代码就很简单了,循环输出数据到jsp页面上。
稍微理一下思路,这种带属性的标签使用其实和无属性差不多,都是先引入了标签库,加载标签的的时候通过URI找到对应的标签库,只不过这次将一个字符串赋值给了tld中attribute元素中名为map的属性,然后跳向对应的标签处理类,顺便把map属性的值自动赋值处理类中的私有属性,然后执行输出代码。其中需要注意的是属性名一定要统一,另外,如果标签的属性值是8种基本数据类型,那么在JSP页面在传递字符串时,JSP引擎会自动转换成相应的类型,但如果标签的属性值是复合数据类型,那么JSP引擎是无法自动转换的。对于传递非基本数据类型的操作,后续文章会介绍。
为了篇幅不过于长,还剩下的内容留在下篇,如有错误,望指出!
Java ---自定义标签的更多相关文章
- java自定义标签 权限
<?xml version="1.0" encoding="UTF-8" ?> <taglib xmlns="http://java ...
- java 自定义标签 传值
<?xml version="1.0" encoding="UTF-8" ?> <taglib xmlns="http://ja ...
- Java ---自定义标签(二)
上篇文章的最后,我们自定义了一个带属性的标签,并使用它完成了一个简单的案例.其实到这我们已经可以看出来,前端jsp页面只需要写一个类似html语法的标签,就可以完成将集合中的数据取出来并展示这么相对复 ...
- [转][Java]自定义标签简介
作用:自定义标签主要用于移除 jsp 页面中的 java 代码. 实现:需要完成以下两个步骤: 编写一个实现 Tag 接口的 Java 类,把页面 java 代码移到这个 java 类中.(标签处理类 ...
- JSP2 自定义标签
实现步骤 实现自定义标签的处理类继承javax.servlet.jsp.tagext.SimpleTagSupport,并重写doTag方法 建立标签库配置文件 在jsp中使用自定义标签 一个简单的标 ...
- [Java] JSP笔记 - 自定义标签
自定义标签的创建步骤: 自定义标签的四大功能: 自定义标签的类结构: 在 1.0 中呢, 可以将 <body-content> 的值设置为 JSP, 2.0中则不允许在自定义标签体中出现j ...
- 12 自定义标签/JSTL标签库/web国际化/java web之设计模式和案例
EL应用 自定义一个标签,实现两个字符串的相加 1回顾 1.1servlet生命周期 init(ServletConfig) service ...
- Java自定义简单标签
Java自定义简单标签可以方便的在页面输出信息,并且对于权限的控制,和对于Jsp标签和servlet代码的分离有着很好的作用. 下面将以权限的控制为例自定义一个标签: 一.标签类型 <wxt: ...
- Java Spring Boot VS .NetCore (十一)自定义标签 Java Tag Freemarker VS .NetCore Tag TagHelper
Java Spring Boot VS .NetCore (一)来一个简单的 Hello World Java Spring Boot VS .NetCore (二)实现一个过滤器Filter Jav ...
随机推荐
- 简洁美观的Java博客系统Tale开源了,让每一个有故事的人更好的表达想法
Tale Tale的英文含义为故事,我相信每个坚持写Blog的人都是有故事的:中文你叫它 塌了 也无所谓 . Tale 使用了轻量级mvc框架 Blade 开发,默认主题使用了漂亮的 pinghsu, ...
- WPF移动Window窗体(鼠标点击左键移动窗体自定义行为)
XAML代码部分:1.引用System.Windows.Interactivity 2.为指定的控件添加一个拖动的行为 3.很简单的了解行为的作用和用法 <Window xmlns=" ...
- Java学习——用户界面的布局
使用布局管理器 FlowLayout管理器 面板的默认布局管理器是java.awt包中的FlowLayout类.使用FlowLayout时,像在页面中排列英文单词那样排组件:从左到右排列,当前行没有空 ...
- Oracle 重建控制文件
前些天在做Oracle数据库恢复测试时,因为一些异常操作导致控制文件出了问题,数据库无法正常使用,这里记录一下重建控制文件的操作 一.使用sysdba用户登入数据库 此时普通用户已无法链接数据库 二. ...
- 使用C#操作文件
读写文本文件 使用C#读写文本文件需要5个步骤: 1.创建文件流 2.创建阅读器或者写入器 3.执行读写操作 4.关闭阅读器或者写入器 5.关闭文件流 例 using System; using Sy ...
- C++ 构造函数或析构函数调用虚函数
构造函数和析构函数中的虚函数 在执行基类构造函数时,对象的派生类部分是未初始化的.实际上,此时对象还不是一个派生类对象. 为 了适应这种不完整,编译器将对象的类型视为在构造或析构期间发生了变化.在基类 ...
- Java的Date和Time入门教程
本文是一篇翻译文章,已取得原作者授权,原文地址是http://tutorials.jenkov.com/java-date-time/index.html Java语言的JDK中关于日期和时间的API ...
- 关于<context:property-placeholder>的一个有趣现象
转:http://stamen.iteye.com/blog/1926166 先来看下A和B两个模块 A模块和B模块都分别拥有自己的Spring XML配置,并分别拥有自己的配置文件: A模块 A模块 ...
- .Net轻量级ORM-NPoco的使用方法-摘自NPoco国外官方Wiki
文章引用自NPoco官方Wiki,地址:https://github.com/schotime/NPoco/wiki,因公司网络不稳定,有时无法访问,特将其摘抄. Home Adam Schroder ...
- webpack学习笔记(二)-- 初学者常见问题及解决方法
这篇文章是webpack学习第二篇,主要罗列了本人在实际操作中遇到的一些问题及其解决方法,仅供参考,欢迎提出不同意见. 注:本文假设读者已有webpack方面相关知识,故文中涉及到的专有名词不做另外解 ...