<%@ page language="java" contentType="text/html; charset=UTF-8" pageEncoding="UTF-8"%>

<!-- 引入标签库: prefix是必须含有的不可缺少 -->    
<%@ taglib uri="/ssgao" prefix="ssgao" %>

<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>Insert title here</title>
</head>
<body>
输出标签信息
<!-- 在JSp页面中使用自定义标签gs,gs标签是带有标签体的,其标签体的内容是:我的宝贝是笑笑 -->
<ssgao:aouo>
我的宝贝是笑笑
</ssgao:aouo>
</body>
</html>

JspTag接口*

     该接口是所有自定义标签的父接口,是jsp2.0中新定义的标记接口,没有任何属性和方法。JspTag的接口有Tag和SimpleTag两个直接子接口,jsp2.0之前的版本只有Tag接口,所以实现Tag接口的自定义标签页叫做传统标签把实现SimpleTag接口的自定义标签叫做简单标签

Tag接口

     Tag接口是所有传统标签的父接口,其中定义了两个重要的方法(doStartTag,doEndTag)方法和四个常量(EVAL_BODY_INCLUDE,SKIP_BODY,EVAL_PAGE.SKIP_PAGE)这两个方法和四个常量的作用如下:
     从WEB容器在解释执行JSP页面的过程中,遇到自定义的标签的开始标记就会去调用标签处理器的doStartTag方法,doStartTag方法执行完后可以向WEB容器返回常量EVAL_BODY_INCLUDE或SKIP_BODY。如果doStartTag方法返回EVAL_BODY_INCLUDE,WEB容器就会接着执行自定义标签的标签体。如果doStartTag方法返回SKIP_BODY,WEB容器就会忽略自定义标签的标签体,直接解释执行自定义标签的结束标记。
     WEB容器解释执行到自定义标签的结束标记时,就会调用标签处理器的doEndTag方法,doEndTag方法执行完后可以向WEB容器返回常量EVAL_PAGE或KIP_PAGE。如果doEndTag方法返回常量EVAL_PAGE,WEB容器就会接着执行JSP页面中位于结束标记后面的JSP代码;如果doEndTag方法返回SKIP_TAG,WEB容器就会忽略JSP页面中位于标记后面的所有内容。
     从doStartTag和doEndTag方法的作用和返回值的作用可以看出,开发自定义的标签时,可以在doStartTag方法和doEndTag方法体内编写适合Java程序代码来实现具体的功能。通过控制doStartTag方法和doEndTag方法的返回值,还可以告诉WEB容器是否执行自定义标签中的标签体内容和JSP页面中位于自定义标签结束标记后面的内容。

Iteration Tag接口

   IterationTag接口继承了Tag接口,并在Tag接口的基础上增加一个doAfterBody的方法和一个EVAL_BODY_AGAIN常量。实现IterationTag接口的标签除了可以完成Tag接口所能完成功能外,还能够通知WEB容器是否重复执行标签体内容。对于实现了ITerationTag接口的自定义标签,WEB容器在执行完自定义标签的标签体后,将调用标签处理器的doAfterBody方法,doAfterBody方法可以向WEB容器返回常量EVAL_BODY_AGAIN或SKIP_BODY。如果doAfterBody方法返回EVAL_BODY_AGAIN,WEB容器就会把标签体内容重复执行一次,执行完后接着在调用doAfterBody方法,如此往复,直到doAfterBody方法返回常量SKIP_BODY.WEB容器才会开始处理标签的结束标记和调用doEndTag方法。
     可见,开发自定义标签时,可以通过控制doAfterBody方法的返回值来告诉WEB容器是否重复执行标签体内容,从而达到循环处理标签体内容的效果。例如,可以通过一个实现IterationTag接口的标签来迭代输出一个集合中所有元素,在标签体部分指定元素的输出格式。

BodyTag接口

BodyTag接口继承了IterationTag接口,并在IterationTag接口的基础上增加了两个方法(setBodyContent、doInitBody)和一个EVAL_BODY_BUFFERED常量。实现BodyTag接口的标签除了可以完成IterationTag接口所能完成的功能,还可以对标签体内容进行修改。对于实现了BodyTag接口的自定义标签,标签处理器的doStartTag方法不仅可以返回前面讲解的常量EVAL_BODY_INCLUDE或SKIP_BODY,还可以返回常量EVAL_BODY_BUFFERED。如果doStartTag方法返回EVAL_BODY_BUFFERED,WEB容器就会创建一个专用于捕获标签体运行结果的BodyContent对象,然后调用标签处理器的setBodyContent方法将BodyContent对象的引用传递给标签处理器,WEB容器接着将标签体的执行结果写入到BodyContent对象中。在标签处理器的后续事件方法中,可以通过先前保存的BodyContent对象的引用来获取标签体的执行结果,然后调用BodyContent对象特有的方法对BodyContent对象中的内容(即标签体的执行结果)进行修改和控制其输出。
在JSP API中也提供了BodyTag接口的实现类BodyTagSupport,我们在编写能够修改标签体内容的自定义标签的标签处理器类时,可以继承和扩展BodyTagSupport类,这相比实现BodyTag接口将简化开发工作

SimpleTag 接口

  SimpleTag接口是JSP2.0中新增的一个标签接口。由于传统标签使用三个标签接口来完成不同的功能,显得过于繁琐,不利于标签技术的推广,因此,SUN公司为降低标签技术的学习难度,在JSP 2.0中定义了一个更为简单、便于编写和调用的SimpleTag接口。SimpleTag接口与传统标签接口最大的区别在于,SimpleTag接口只定义了一个用于处理标签逻辑的doTag方法,该方法在WEB容器执行自定义标签时调用,并且只被调用一次。那些使用传统标签接口所完成的功能,例如是否执行标签体、迭代标签体、对标签体内容进行修改等功能都可以在doTag方法中完成。
   在JSP API中也提供了SimpleTag接口的实现类SimpleTagSupport,我们在编写简单标签时,可以继承和扩展SimpleTagSupport类,这相比实现SimpleTag接口将简化开发工作

传统标签接口中的各个方法可以返回返回值得说明

返回值和方法名 EVAL_BODY_INCLUDE SKIP_BODY EVAL_BODY_BUFFEREDY EVAL_BODY_AGAIN EVAL_PAGE SKIP_PAGE
doStartTag 将标签体的执行结果插入到输出流中 忽略标签体部分 将标签提的执行接口放入到一个BodyContent对象中 X X X
doAfterBody X 不在重复执行标签体内容 X 重复执行标签内容 X X
doEndTag X X X X 继续处理结果标签后面的所有JSP代码 忽略结束标签后面的所有JSP代码

传统标签实现页面逻辑

控制jsp页面某一部分内容是否执行
控制整个jsp页面是否执行
控制jsp页面内容重复执行
修改jsp页面内容输出

控制jsp页面的自定义标签体是否执行

    编写一个类实现tag接口,控制doStartTag()方法的返回值,如果整个方法返回EVAL_BODY_INCLUDE,则执行标签体,如果返回SKIP_BODY则不执行
    SUN公司针对tag接口提供了一个默认的实现类TagSupport,TagSupport类中实现了tag接口的所有方法,因此我们可以编写一个类集成TagSupport,然后在重写doStartTag方法
    
package demo.tag;
import java.io.IOException;
import javax.servlet.jsp.JspException;
import javax.servlet.jsp.JspWriter;
import javax.servlet.jsp.tagext.Tag;
import javax.servlet.jsp.tagext.TagSupport;

/**
* TagSupport类实现了Tag接口,TagtwoDemo继承了TagSupport
* @author ssgao
*
*/
public class TagtwoDemo extends TagSupport{

/** */
private static final long serialVersionUID = 7332955146947736164L;
/**
* 重写doStartTag方法,来控制标签提是否执行
*/
@Override
public int doStartTag() throws JspException {
JspWriter jw =pageContext.getOut();
try {
jw.write("自定义标签->");
} catch (IOException e) {
e.printStackTrace();
}
/**
* 如果返回EVAL_BODY_INCLDE,则执行标签体
* 如果返回SKIP_BODY 则不执行标签体
*/
return Tag.EVAL_BODY_INCLUDE;
} } 在WEB-INF目录下tld文件中添加对该标签处理的描述 <?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE taglib PUBLIC "-//Sun Microsystems, Inc.//DTD JSP Tag Library 1.2//EN" "http://java.sun.com/dtd/web-jsptaglibrary_1_2.dtd" >
<taglib>
 <tlib-version>tlib-version</tlib-version>
 <jsp-version>jsp-version</jsp-version>
 <short-name>short-name</short-name>
 
 <uri>/ssgao</uri>
 
 <tag>
   <name>aouo</name>
   <tag-class>demo.tag.TagtwoDemo</tag-class>
   <body-content>JSP</body-content>
 </tag>
</taglib> 在JSP页面中引入标签库
<%@ page language="java" contentType="text/html; charset=UTF-8" pageEncoding="UTF-8"%>

<!-- 引入标签库: prefix是必须含有的不可缺少 -->    
<%@ taglib uri="/ssgao" prefix="ssgao" %>


<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>Insert title here</title>
</head>
<body>
输出标签信息
<!-- 在JSp页面中使用自定义标签gs,gs标签是带有标签体的,其标签体的内容是:我的宝贝是笑笑 -->
<ssgao:aouo>
我的宝贝是笑笑
</ssgao:aouo>
</body>
</html>

控制整个JSP页面是否执行

编写一个类实现Tag接口,控制doEndTag方法的返回值,如果这个方法返回EVAL_PAGE,则执行标签下的JSP页面,如果返回SKIP_PAGE则不执行余下的JSP

package demo.tag;

import javax.servlet.jsp.JspException;
import javax.servlet.jsp.tagext.Tag;
import javax.servlet.jsp.tagext.TagSupport;

/**
* TagSupport类实现了Tag接口,TagtwoDemo继承了TagSupport
* @author ssgao
*
*/
public class EndTagDemo extends TagSupport{

/** */
private static final long serialVersionUID = 7332955146947736164L;

/**
* 重写doEndTag方法控制JSP页面是否执行
*/
public int doEndTag() throws JspException { /**
* 如果返回EVAL_PAGE,则执行标签余下的JSP页面
* 如果返回SKIP_PAGE,则不执行余下的JSP页面
*/
return Tag.SKIP_PAGE;
}
} 在WEB-INF目录下tld文件中添加对该标签处理的描述
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE taglib PUBLIC "-//Sun Microsystems, Inc.//DTD JSP Tag Library 1.2//EN" "http://java.sun.com/dtd/web-jsptaglibrary_1_2.dtd" >
<taglib>
 <tlib-version>tlib-version</tlib-version>
 <jsp-version>jsp-version</jsp-version>
 <short-name>short-name</short-name>  
 <uri>/end</uri>
 
 <tag>
   <name>end</name>
   <tag-class>demo.tag.EndTagDemo</tag-class>
   <body-content>empty</body-content>
 </tag>
</taglib> 在JSP页面中引入标签库
<%@ page language="java" contentType="text/html; charset=UTF-8" pageEncoding="UTF-8"%>

<!-- 引入标签库: prefix是必须含有的不可缺少 -->    
<%@ taglib uri="/end" prefix="gs" %>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>Insert title here</title>
</head>
<body>
<!-- 在JSp页面中使用自定义标签gs,gs标签是带有标签体的,其标签体的内容是:我的宝贝是笑笑 -->
<gs:end/>
输出标签信息
</body>
</html>

JSP页面内容重复执行

编写一个类实现Iterationtag接口控制doAfterBody()方法的返回值,如果这个方法返回EVAL_BODY_AGAIN,则web服务器重复执行一次标签体,一次类推,知道doAfterBody方法返回SKIP_BODY
则标签体才不会重复执行
package demo.tag;

import java.io.IOException;

import javax.servlet.jsp.JspException;
import javax.servlet.jsp.JspWriter;
import javax.servlet.jsp.tagext.IterationTag;
import javax.servlet.jsp.tagext.Tag;
import javax.servlet.jsp.tagext.TagSupport;

/**
* TagSupport类实现了Tag接口,TagtwoDemo继承了TagSupport
* @author ssgao
*
*/
public class AfterTagDemo extends TagSupport{

/** */
private static final long serialVersionUID = 7332955146947736164L;
static int no;
static{
no=5;
} /**
* 重写doStartTag方法,来控制标签提是否执行
*/
@Override
public int doStartTag() throws JspException {
/**
* 如果返回EVAL_BODY_INCLDE,则执行标签体
* 如果返回SKIP_BODY 则不执行标签体
*/
return Tag.EVAL_BODY_INCLUDE;
}
@Override
public int doAfterBody() throws JspException {
no--;
while(no>0){
return IterationTag.EVAL_BODY_AGAIN;
}
return IterationTag.SKIP_BODY;
}
} 在WEB-INF目录下tld文件中添加对该标签处理的描述
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE taglib PUBLIC "-//Sun Microsystems, Inc.//DTD JSP Tag Library 1.2//EN" "http://java.sun.com/dtd/web-jsptaglibrary_1_2.dtd" >
<taglib>
 <tlib-version>tlib-version</tlib-version>
 <jsp-version>jsp-version</jsp-version>
 <short-name>short-name</short-name>
 <uri>/after</uri>
 <tag>
   <name>after</name>
   <tag-class>demo.tag.AfterTagDemo</tag-class>
   <body-content>JSP</body-content>
 </tag>
</taglib>

在JSP页面中引入标签库

<%@ page language="java" contentType="text/html; charset=UTF-8" pageEncoding="UTF-8"%>

<!-- 引入标签库: prefix是必须含有的不可缺少 -->    
<%@ taglib uri="/after" prefix="ssgao" %>

<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>Insert title here</title>
</head>
<body>
输出标签信息
<!-- 在JSp页面中使用自定义标签gs,gs标签是带有标签体的,其标签体的内容是:我的宝贝是笑笑 -->
<ssgao:after>
我的宝贝是笑笑
</ssgao:after>
</body>
</html>

修改JSP页面内容输出

编写一个类实现BodyTag接口,控制doStartTag方法返回EVAL_BODY_BUFFERED,则WEB服务器会创建BodyContent对象捕获标签体,然后在doEndTag()方法体内,得到代表标签体的bodyContent对象
从而就可以对标签体进行修改操作
sun公司针对BodyTag接口提供一个默认的实现类BodyTagSupport,BodyTagSupport类中实现了BodyTag接口的所有方法,因此我们可以编写一个类继承BodyTagSupport类,然后在根据需要重写doStartTag方法和doEndTag方法。
package demo.tag;

import javax.servlet.jsp.JspException;
import javax.servlet.jsp.tagext.BodyContent;
import javax.servlet.jsp.tagext.BodyTag;
import javax.servlet.jsp.tagext.BodyTagSupport;
import javax.servlet.jsp.tagext.Tag;
/**
* BodyTagSupport类实现了BodyTag接口接口,EditTagDemo继承 BodyTagSupport类
* @author ssgao
*
*/
public class EditTagDemo extends BodyTagSupport{

/** */
private static final long serialVersionUID = -3814095430415404149L;

/**
* 控制doStartTag()方法返回EVAL_BODY_BUFFERED
*/
@Override
public int doStartTag() throws JspException {
return BodyTag.EVAL_BODY_BUFFERED;
}

@Override
public int doEndTag() throws JspException {
/**this.getBodyContent()得到代表标签体的bodyContent对象 */
BodyContent bodyContent=this.getBodyContent();
//拿到标签体
String content = bodyContent.getString();
//修改标签体里面的内容,将小写转换为大写
String result = content.toUpperCase();
try {
/** 输出修改后的内容*/
this.pageContext.getOut().write(result);
} catch (Exception e) {
e.printStackTrace();
}
return Tag.EVAL_PAGE;
}
} 在WEB-INF目录下tld文件中添加对该标签处理的描述
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE taglib PUBLIC "-//Sun Microsystems, Inc.//DTD JSP Tag Library 1.2//EN" "http://java.sun.com/dtd/web-jsptaglibrary_1_2.dtd" >
<taglib>
 <tlib-version>tlib-version</tlib-version>
 <jsp-version>jsp-version</jsp-version>
 <short-name>short-name</short-name>
 <uri>/edit</uri>  
 <tag>
   <name>edit</name>
   <tag-class>demo.tag.EditTagDemo</tag-class>
   <body-content>JSP</body-content>
 </tag>
</taglib>

在JSP页面中引入标签库

<%@ page language="java" contentType="text/html; charset=UTF-8" pageEncoding="UTF-8"%>

<!-- 引入标签库: prefix是必须含有的不可缺少 -->    
<%@ taglib uri="/edit" prefix="ssgao" %>

<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>Insert title here</title>
</head>
<body>
输出标签信息
<ssgao:edit>
sadasd
</ssgao:edit>
</body>
</html>

jsp jsp传统标签开发的更多相关文章

  1. javaweb学习总结(二十四)——jsp传统标签开发

    一.标签技术的API 1.1.标签技术的API类继承关系 二.标签API简单介绍 2.1.JspTag接口 JspTag接口是所有自定义标签的父接口,它是JSP2.0中新定义的一个标记接口,没有任何属 ...

  2. javaweb(二十四)——jsp传统标签开发

    一.标签技术的API 1.1.标签技术的API类继承关系 二.标签API简单介绍 2.1.JspTag接口 JspTag接口是所有自定义标签的父接口,它是JSP2.0中新定义的一个标记接口,没有任何属 ...

  3. 深入分析JavaWeb Item23 -- jsp自己定义标签开发入门

    一.自己定义标签的作用 自己定义标签主要用于移除Jsp页面中的java代码. 二.自己定义标签开发和使用 2.1.自己定义标签开发步骤 1.编写一个实现Tag接口的Java类(标签处理器类) 要编写一 ...

  4. JSP传统标签开发

    1.标签技术的API类继承关系 1).JspTag接口是所有自定义标签的父接口 该接口中没有任何属性和方法,只有两个直接子接口,Tag接口和SimpleTag接口,把实现Tag接口的自定义标签叫做传统 ...

  5. 【JSP】自定义标签开发入门

    JSP 自定义标签 自定义标签是用户定义的JSP语言元素.当JSP页面包含一个自定义标签时将被转化为servlet,标签转化为对被 称为tag handler的对象的操作,即当servlet执行时We ...

  6. javaweb基础(24)_jsp一般的标签开发

    一.标签技术的API 1.1.标签技术的API类继承关系 二.标签API简单介绍 2.1.JspTag接口 JspTag接口是所有自定义标签的父接口,它是JSP2.0中新定义的一个标记接口,没有任何属 ...

  7. 08.十分钟学会JSP传统标签编程

    一.认识标签 1,说明:传统标签编程在开发中基本用不到,学习标签编程主要还是为了完善知识体系. 2,标签的主要作用:移除或减少jsp中的java代码 3,标签的主要组成部分及运行原理 4,简单标签示例 ...

  8. 【jsp】JSTL标签大全详解

    一.JSTL标签介绍 1.什么是JSTL? JSTL是apache对EL表达式的扩展(也就是说JSTL依赖EL),JSTL是标签语言!JSTL标签使用以来非常方便,它与JSP动作标签一样,只不过它不是 ...

  9. JSP简单标签开发

    一.继承自SimpleTag接口的自定义标签实现类称为简单标签,接口中5个方法 1.setJspContext方法 用于把JSP页面的PageContext对象传递给标签处理器对象 2.setPare ...

随机推荐

  1. canvas压缩图片

    1.canvas.toDataUrl压缩图片 canvas的toDataUrl方法可以将内容导出为base64编码格式的图片,采用base64编码将比源文件大1/3,但是该方法可以指定导出图片质量,所 ...

  2. noip2010 真题练习 2017.2.18

    第一题比较简单,用exist数组判断是否在循环队列中,就可实现线性算法. Code #include<iostream> #include<cstdio> #include&l ...

  3. Linux内核同步机制--自旋锁【转】

    本文转载自:http://www.cppblog.com/aaxron/archive/2013/04/12/199386.html 自旋锁与互斥锁有点类似,只是自旋锁不会引起调用者睡眠,如果自旋锁已 ...

  4. (转)Nuts and Bolts of Applying Deep Learning

    Kevin Zakka's Blog About Nuts and Bolts of Applying Deep Learning Sep 26, 2016 This weekend was very ...

  5. navicat Window . MAC版常用快捷键

    navicat 结合快捷键 1.ctrl+q 打开查询窗口 2.ctrl+/ 注释sql语句 3.ctrl+shift +/ 解除注释 4.ctrl+r 运行查询窗口的sql语句 5.ctrl+shi ...

  6. MVC ---- 无法将类型"System.Data.EntityState"隐式转换为"System.Data.Entity.EntityState"

    1.EF 5.0解决方法 先卸载EF:Uninstall-Package EntityFramework -Force 在安装EF5.0:Install-Package EntityFramework ...

  7. 字典重复key的合并

    from collections import defaultdict d=defaultdict(set) s=[("001","A"),("001 ...

  8. Linux 安装iostat命令

    首先跟你的Linux系统有关 我用的是Red hat系统 记录下最快的安装iostat命令的方式 起初想查看iostat, 提示 iostat: command not found 于是,通过yum ...

  9. 汇编语言调用Linux系统调用read和write

    .section .data UserMsg: .ascii "Please input the message:" LenOfUserMsg: .equ lenMsg, LenO ...

  10. 【Golang 接口自动化00】为什么要用Golang做自动化?

    为什么使用Golang做自动化 顺应公司的趋势学习了Golang之后,因为没有开发那么多的时间和项目来实践,怕步此前学习Java缺少练习遗忘殆尽的后尘,决定利用工作之余的时间把此前用Python的写的 ...