`
Flory
  • 浏览: 23504 次
  • 性别: Icon_minigender_1
  • 来自: 上海
社区版块
存档分类
最新评论

JSP自定义标签开发入门

 
阅读更多

JSP自定义标签开发入门,简单标签的开发我们只要实现Tag接口即可,为了简单起见可以直接继承实现了此接口的TagSupport类。


一般情况下开发jsp自定义标签需要引用以下两个包

import javax.servlet.jsp.*;

import javax.servlet.jsp.tagext.*;

首先我们需要大致了解开发自定义标签所涉及到的接口与类的层次结构(其中SimpleTag接口与SimpleTagSupport类是JSP2.0中新引入的)。

目标1:自定义一个用表格显示用户信息的简单标签

效果图:

在jsp页面使用此自定义标签:

假设我们有一个UserInfo的javabean,那么在JSP页面使用此标签只需调用此标签即可

  1. <!-- 创建需要展现UserInfo的实例(用于测试数据) -->
  2. <%
  3. UserInfo user = new UserInfo();
  4. user.setUserName("Xuwei");
  5. user.setAge(33);
  6. user.setEmail("test@test.test");
  7. pageContext.setAttribute("userinfo", user);
  8. %>
  9. <!-- 给标签设置user属性绑定要展现的UserInfo对象 -->
  10. <cc:showUserInfo user="${pageScope.userinfo }" />

开发步骤:

简单标签的开发我们只要实现Tag接口即可,为了简单起见可以直接继承实现了此接口的TagSupport类

1 创建自定义标签类

  1. public class UserInfoTag extends TagSupport {
  2. private UserInfo user;
  3. @Override
  4. public int doStartTag() throws JspException {
  5. try {
  6. JspWriter out = this.pageContext.getOut();
  7. if(user == null) {
  8. out.println("No UserInfo Found...");
  9. return SKIP_BODY;
  10. }
  11. out.println("<table width='500px' border='1' align='center'>");
  12. out.println("<tr>");
  13. out.println("<td width='20%'>Username:</td>");
  14. out.println("<td>" + user.getUserName() + "</td>");
  15. out.println("</tr>");
  16. out.println("<tr>");
  17. out.println("<td>Age:</td>");
  18. out.println("<td>" + user.getAge() + "</td>");
  19. out.println("</tr>");
  20. out.println("<tr>");
  21. out.println("<td>Email:</td>");
  22. out.println("<td>" + user.getEmail() + "</td>");
  23. out.println("</tr>");
  24. out.println("</table>");
  25. } catch(Exception e) {
  26. throw new JspException(e.getMessage());
  27. }
  28. return SKIP_BODY;
  29. }
  30. @Override
  31. public int doEndTag() throws JspException {
  32. return EVAL_PAGE;
  33. }
  34. @Override
  35. public void release() {
  36. super.release();
  37. this.user = null;
  38. }
  39. //getter and setters
  40. public UserInfo getUser() {
  41. return user;
  42. }
  43. public void setUser(UserInfo user) {
  44. this.user = user;
  45. }
  46. }

2 在Web-Inf创建标签库描述文件.tdl(Tag Library Description)

  1. <?xml version="1.0" encoding="UTF-8"?>
  2. <taglib version="2.0" xmlns="http://java.sun.com/xml/ns/j2ee"
  3. xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
  4. xsi:schemaLocation="http://java.sun.com/xml/ns/j2ee web-jsptaglibrary_2_0.xsd">
  5. <tlib-version>1.0</tlib-version>
  6. <jsp-version>2.0</jsp-version>
  7. <short-name>cc</short-name>
  8. <uri>/mytaglib</uri>
  9. <tag>
  10. <name>showUserInfo</name>
  11. <tag-class>com.mytags.UserInfoTag</tag-class>
  12. <body-content>empty</body-content>
  13. <attribute>
  14. <name>user</name>
  15. <required>false</required>
  16. <rtexprvalue>true</rtexprvalue>
  17. </attribute>
  18. </tag>
  19. </taglib>

3 配置web.xml

  1. <jsp-config>
  2. <taglib>
  3. <taglib-uri>/mytaglib</taglib-uri>
  4. <taglib-location>/WEB-INF/mytaglib.tld</taglib-location>
  5. </taglib>
  6. </jsp-config>

4 在需要使用此标签的jsp页面头部引入

  1. <%@ taglib uri="/mytaglib" prefix="cc"%>

5 使用(参照上面的使用步骤)

此致,一个简单的JSP标签开发完成

标签类说明:

我们创建的UserInfoTag类继承了TagSupport类,而它又实现了Tag接口,Tag接口的生命周期由其所在的容器控制,如下图:

setPageContext() 将所在jsp页面的pageContext注入进来,目的是为了在后面的方法中可以访问到jsp页面对象的pageContext属性

setParent() 设置此标签的父标签

setAttribute() 将标签中的属性注入到此class的属性,不需要自己实现但要提供属性的get与set方法

doStartTag() 在开始标签属性设置后调用,如果返回SKIP_BODY则忽略标签之中的内容,如果返回EVAL_BODY_INCLUDE则将标签体的内容进行输出

doEndTag() 在结束标签之前调用,返回SKIP_PAGE跳过整个jsp页面后面的输出,返回EVAL_PAGE执行页面余下部分

release() 生命周期结束时调用

特别说明:在tomcat4.1之后的版本中默认开启了标签缓冲池(websphere和weblogic并不会这么做),所以执行完标签后并不会执行release()方法(_jspDestroy()时才释放),也就是说同一个jsp页面自定义标签不管使用多少次只会存在一个实例,但也并不是每一个标签都会为其创建一个缓冲池,要根据参数来判断,例如:

  1. <cc:UserInfoTag user=”…” />
  2. <cc:UserInfoTag />

上面例子中由于参数不同就会创建两个标签缓冲池。

这个问题可以通过设定tomcat的配置文件加以解决:

在%tomcat%\conf\web.xml加入enablePooling参数,并设置为false(不缓存自定义标签)。

  1. <init-param>
  2. <param-name>enablePooling</param-name>
  3. <param-value>false</param-value>
  4. </init-param>

清空%tomcat%\conf\目录

TagSupport类已经为我们实现并扩展了一些方法(比如在上述方法中我们可以直接使用pageContext对象,调用父标签getParent()等),所以一般情况下我们只需重写doStartTag(),doEndTag() 即可

TLD文件说明:

<!--版本号-->
<tlib-version>1.0</tlib-version>
<jsp-version>2.0</jsp-version>
<short-name>cc</short-name>
<tag>
<!—指定标签名 -->
<name>showUserInfo</name>
<!—指定标签类文件的全路径 -->
<tag-class>com.mytags.UserInfoTag</tag-class>
<!--如果不需要标签体则设置empty,反之设定jsp -->
<body-content>empty</body-content>
<!—设定属性(如果有的话) -->
<attribute>
<!—指定标签名 -->
<name>user</name>
<!—是否是必须,如果非必须没设置则为空 -->
<required>false</required>
<rtexprvalue>true</rtexprvalue><!—是否可在属性中使用表达式 -->
</attribute>
</tag>

Web.xml文件说明:

<jsp-config>
<taglib>
<!--

标签库的uri路径
即jsp头文件中声明<%@ taglib uri="/mytaglib" prefix="cc"%>
的uri
-->
<taglib-uri>/mytaglib</taglib-uri>
<!—tld文件所在的位置-->
<taglib-location>/WEB-INF/mytaglib.tld</taglib-location>
</taglib>
</jsp-config>

目标2:自定义一个类似于Asp.Net中的Reapter控件的标签

效果图:

在jsp页面使用此自定义标签:

  1. <!-- 创建需要展现javabean(UserInfo)集合的实例(用于测试数据) -->
  2. <%
  3. List<UserInfo> users = new ArrayList<UserInfo>();
  4. users.add(new UserInfo("Zhangsan", 12, "Zhangsan@163.com"));
  5. users.add(new UserInfo("Lisi", 22, "Lisi@sina.com"));
  6. users.add(new UserInfo("Wangwu", 33, "Wangwu@qq.com"));
  7. pageContext.setAttribute("users", users);
  8. %>
  9. <!-- 给标签绑定数据源 -->
  10. <table width='500px' border='1' align='center'>
  11. <tr>
  12. <td width='20%'>UserName</td>
  13. <td width='20%'>Age</td>
  14. <td>Email</td>
  15. </tr>
  16. <cc:repeater var="item" items="${pageScope.users }">
  17. <tr>
  18. <td>${item.userName }</td>
  19. <td>${item.age }</td>
  20. <td>${item.email }</td>
  21. </tr>
  22. </cc:repeater>
  23. </table>

开发步骤:

要完成此控件我们需要实现一个迭代接口,即IterationTag,由于TagSupport同样实现了此接口,所以我们继承此类

1 创建自定义标签类

  1. public class Repeater extends TagSupport {
  2. private Collection items;
  3. private Iterator it;
  4. private String var;
  5. @Override
  6. public int doStartTag() throws JspException {
  7. if(items == null || items.size() == 0) return SKIP_BODY;
  8. it = items.iterator();
  9. if(it.hasNext()) {
  10. pageContext.setAttribute(var, it.next());
  11. }
  12. return EVAL_BODY_INCLUDE;
  13. }
  14. @Override
  15. public int doAfterBody() throws JspException {
  16. if(it.hasNext()) {
  17. pageContext.setAttribute(var, it.next());
  18. return EVAL_BODY_AGAIN;
  19. }
  20. return SKIP_BODY;
  21. }
  22. @Override
  23. public int doEndTag() throws JspException {
  24. return EVAL_PAGE;
  25. }
  26. public void setItems(Collection items) {
  27. this.items = items;
  28. }
  29. public void setVar(String var) {
  30. this.var = var;
  31. }
  32. }

2在Web-Inf创建标签库描述文件.tdl(Tag Library Description)由于目标1种已经创建了此文件,我们只需增加此标签的配置即可

  1. <tag>
  2. <name>repeater</name>
  3. <tag-class>com.mytags.Repeater</tag-class>
  4. <body-content>jsp</body-content>
  5. <attribute>
  6. <name>items</name>
  7. <required>false</required>
  8. <rtexprvalue>true</rtexprvalue>
  9. </attribute>
  10. <attribute>
  11. <name>var</name>
  12. <required>true</required>
  13. <rtexprvalue>true</rtexprvalue>
  14. </attribute>
  15. </tag>

3 配置web.xml (目标1中已完成,无需修改)

4 在需要使用此标签的jsp页面头部引入

  1. <%@ taglib uri="/mytaglib" prefix="cc"%>

5 使用(参照上面的使用步骤)

标签类说明:

我们用到了迭代接口,以下是容器处理此接口的流程

作为目标1中的补充: 在doAfterBody()如果返回值是EVAL_BODY_AGAIN那么将重新执行此方法

目标3:使用BodyTagSupport

此目标并不会使用实际例子进行显示,主要是说明为什么,什么情况下需要使用到BodyTag接口或者BodyTagSupport类?

如果我们需要在 …. 之间的标签体的头部和尾部加上一些标记或者是其他处理,一般的处理方法是在doStartTag和doEndTag方法中进行, 但是如果是个迭代标签,标签体的每段内容在循环输出时每次都需要在头部和尾部加上一些标记,我们使用BodyTagSupport就很方便了,

此接口在doStartTag()方法返回值多了一个EVAL_BODY_BUFFERED,它将对主体进行计算,并输出到缓冲区(注:此处是缓冲区并非直接输出到客户端,需要我们手动(this.bodyContent.getEnclosingWriter().write(this.bodyContent.getString());)进行输出客户端的调用,否则主体内容不会进行显示)

标签类说明:

关于BodyTagSupport接口的说明

目标4:自定义的函数库

1 创建函数库类

  1. public class MyFunctions {
  2. public static String formatMyName(String name) {
  3. return "your name is " + name;
  4. }
  5. public static int add(int a, int b) {
  6. return a+b;
  7. }
  8. }

2 在TLD文件中配置 (引用于目标1中的tld文件)

  1. <function>
  2. <name>formatMyName</name>
  3. <function-class>com.taglib.MyFunctions</function-class>
  4. <function-signature>java.lang.String formatMyName(java.lang.String)</function-signature>
  5. </function>
  6. <function>
  7. <name>add</name>
  8. <function-class>com.taglib.MyFunctions</function-class>
  9. <function-signature>java.lang.String add(int, int)</function-signature>
  10. </function>

3 JSP中调用

  1. ${cc:formatMyName("wangfei") }
  2. ${cc:add(12, 34) }

分享到:
评论

相关推荐

    JSP自定义标签入门学习

    本文为大家分享了JSP自定义标签入门学习教程,希望大家喜欢。 1.JSP自定义标签: 自定义标签是用户定义的JSP语言元素。当JSP页面包含一个自定义标签时将被转化为servlet,标签转化为对被 称为tag handler的对象的操作...

    完整版Java JSP web开发教程 10_自定义标签(共20页).ppt

    完整版Java JSP web开发教程 10_自定义标签(共20页).ppt 完整版Java JSP web开发教程 11_JSP 标准标签库(共21页).ppt 完整版Java JSP web开发教程 12_过滤器(共20页).ppt 完整版Java JSP web开发教程 13_MVC ...

    完整版Java JSP web开发教程 11_JSP 标准标签库(共21页).ppt

    完整版Java JSP web开发教程 10_自定义标签(共20页).ppt 完整版Java JSP web开发教程 11_JSP 标准标签库(共21页).ppt 完整版Java JSP web开发教程 12_过滤器(共20页).ppt 完整版Java JSP web开发教程 13_MVC ...

    完整版Java JSP web开发教程 02_Servlet使用入门(共23页).ppt

    完整版Java JSP web开发教程 10_自定义标签(共20页).ppt 完整版Java JSP web开发教程 11_JSP 标准标签库(共21页).ppt 完整版Java JSP web开发教程 12_过滤器(共20页).ppt 完整版Java JSP web开发教程 13_MVC ...

    jsp中自定义Taglib详解

    自定义标签类都必须继承一个父类:javax.servlet.jsp.tagext.SimpleTagSupport,或者TagSupport除此之外,JSP自定义标签类还有如下要求。 如果标签类包含属性,每个属性都有对应的getter和setter方法。 重写doTag()...

    完整版Java JSP web开发教程 全套PPT课件资料 共13个章节.rar

    完整版Java JSP web开发教程 10_自定义标签(共20页).ppt 完整版Java JSP web开发教程 11_JSP 标准标签库(共21页).ppt 完整版Java JSP web开发教程 12_过滤器(共20页).ppt 完整版Java JSP web开发教程 13_MVC ...

    JSP开发技术大全 源码

    mail组件、程序日志组件、JavaScript脚本语言、CSS样式、XML入门技术、在JSP中应用Ajax技术、在JSP中应用DOM解析XML、在JSP中应用JDOM解析XML、在JSP中应用SAX解析XML、EL表达式、JSTL标签库、自定义标签、Hibernate...

    完整版Java JSP web开发教程 05_JSP简介(共17页).ppt

    完整版Java JSP web开发教程 10_自定义标签(共20页).ppt 完整版Java JSP web开发教程 11_JSP 标准标签库(共21页).ppt 完整版Java JSP web开发教程 12_过滤器(共20页).ppt 完整版Java JSP web开发教程 13_MVC ...

    完整版Java JSP web开发教程 07_JSP隐式对象(共32页).ppt

    完整版Java JSP web开发教程 10_自定义标签(共20页).ppt 完整版Java JSP web开发教程 11_JSP 标准标签库(共21页).ppt 完整版Java JSP web开发教程 12_过滤器(共20页).ppt 完整版Java JSP web开发教程 13_MVC ...

    完整版Java JSP web开发教程 09_JSP表达式语言(共23页).ppt

    完整版Java JSP web开发教程 10_自定义标签(共20页).ppt 完整版Java JSP web开发教程 11_JSP 标准标签库(共21页).ppt 完整版Java JSP web开发教程 12_过滤器(共20页).ppt 完整版Java JSP web开发教程 13_MVC ...

    完整版Java JSP web开发教程 08_JavaBean和JSP中(共26页).ppt

    完整版Java JSP web开发教程 10_自定义标签(共20页).ppt 完整版Java JSP web开发教程 11_JSP 标准标签库(共21页).ppt 完整版Java JSP web开发教程 12_过滤器(共20页).ppt 完整版Java JSP web开发教程 13_MVC ...

    完整版Java JSP web开发教程 06_JSP脚本和指令的使用(共22页).ppt

    完整版Java JSP web开发教程 10_自定义标签(共20页).ppt 完整版Java JSP web开发教程 11_JSP 标准标签库(共21页).ppt 完整版Java JSP web开发教程 12_过滤器(共20页).ppt 完整版Java JSP web开发教程 13_MVC ...

    JSP开发技术大全 JSP

    mail组件、程序日志组件、JavaScript脚本语言、CSS样式、XML入门技术、在JSP中应用Ajax技术、在JSP中应用DOM解析XML、在JSP中应用JDOM解析XML、在JSP中应用SAX解析XML、EL表达式、JSTL标签库、自定义标签、Hibernate...

    jsp 开发技术大全

    mail组件、程序日志组件、JavaScript脚本语言、CSS样式、XML入门技术、在JSP中应用Ajax技术、在JSP中应用DOM解析XML、在JSP中应用JDOM解析XML、在JSP中应用SAX解析XML、EL表达式、JSTL标签库、自定义标签、Hibernate...

    完整版Java JSP web开发教程 01_web概述(共18页).ppt

    完整版Java JSP web开发教程 10_自定义标签(共20页).ppt 完整版Java JSP web开发教程 11_JSP 标准标签库(共21页).ppt 完整版Java JSP web开发教程 12_过滤器(共20页).ppt 完整版Java JSP web开发教程 13_MVC ...

    完整版Java JSP web开发教程 12_过滤器(共20页).ppt

    完整版Java JSP web开发教程 10_自定义标签(共20页).ppt 完整版Java JSP web开发教程 11_JSP 标准标签库(共21页).ppt 完整版Java JSP web开发教程 12_过滤器(共20页).ppt 完整版Java JSP web开发教程 13_MVC ...

    完整版Java JSP web开发教程 04_JavaMail和Servlet(共22页).ppt

    完整版Java JSP web开发教程 10_自定义标签(共20页).ppt 完整版Java JSP web开发教程 11_JSP 标准标签库(共21页).ppt 完整版Java JSP web开发教程 12_过滤器(共20页).ppt 完整版Java JSP web开发教程 13_MVC ...

    完整版Java JSP web开发教程 03_会话跟踪简介(共22页).ppt

    完整版Java JSP web开发教程 10_自定义标签(共20页).ppt 完整版Java JSP web开发教程 11_JSP 标准标签库(共21页).ppt 完整版Java JSP web开发教程 12_过滤器(共20页).ppt 完整版Java JSP web开发教程 13_MVC ...

    完整版Java JSP web开发教程 13_MVC 设计模式(共22页).ppt

    完整版Java JSP web开发教程 10_自定义标签(共20页).ppt 完整版Java JSP web开发教程 11_JSP 标准标签库(共21页).ppt 完整版Java JSP web开发教程 12_过滤器(共20页).ppt 完整版Java JSP web开发教程 13_MVC ...

Global site tag (gtag.js) - Google Analytics