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

jsp2.0自定义标签Tag

    博客分类:
  • Java
阅读更多

JSP2.0 中,对于自定义的标签有两种实现方法,实现接口或者继承现有的类

如下图,标注蓝色的是接口,其它是标签类(SimpleTagSupport 只在JSP2.0 中才有)

 

tag2.JPG  

在以上接口和类中,定义了一些静态常量,如下:

Tag 中定义:

SKIP_BODY = 0;          // 不处理标签体,直接调用doEndTag() 方法

EVAL_BODY_INCLUDE = 1;   // 解析标签体, 但绕过 doInitBody () setBodyContent () 方法

SKIP_PAGE = 5;          // 不解析标签后面的JSP 内容

EVAL_PAGE = 6;          // 解析标签后, 继续解析标签后面的JSP 内容

 

IterationTag 中定义:

EVAL_BODY_AGAIN = 2;

 

BodyTag 中定义:

EVAL_BODY_TAG = 2;          // deprecated

EVAL_BODY_BUFFERED = 2;    //

 

特别的,对于EVAL_BODY_AGAINEVAL_BODY_BUFFERED

doAferBody 中返回SKIP_BODY ,表示终止标记正文处理 ;若返回的是 EVAL_BODY_BUFFERED ,将会再一次调用 doAferBody 方法,重新处理标记正文,直到返回SKIP_BODY 为止。  //

 

TagSupport 默认doStartTag()/doAfterBody() 返回SKIP_BODY

BodyTagSupport 默认doStartTag() 返回EVAL_BODY_BUFFERED / doInitBody() 什么也不做 /doAfterBody() 返回SKIP_BODY

下面是自定义tag 的执行过程(由上至下),对于以上各常量的实际运用为:

注意其中的 doInitBody/setBodyContent 方法在自定义标签实现了 BodyTag 接口或继承BodyTagSupport 才可以使用

Tag 方法

可返回的静态常量

doStartTag

SKIP_BODY EVAL_BODY_INCLUDE

EVAL_BODY_AGAIN/EVAL_BODY_BUFFERED

doInitBody

做标签一些初始化工作,无返回值

setBodyContent

doInitBody 之后执行,使用setBodyContent 得到JSP 页面中标签体之间内容

doAfterBody

最终必须返回SKIP_BODY ,否则可能导致OutOfMemoryError ,可参考上面

doEndTag

SKIP_PAGE/EVAL_PAGE

 

示例代码如下:

public int doAfterBody() throws JspException {

  try {

   this.pageContext.getOut().write("<br>");

  } catch (IOException e) {

      e.printStackTrace();

  }

  if(cou>1){

   cou--;

   return this.EVAL_BODY_AGAIN;

  }else{

   return this.SKIP_BODY;   // 最终必须返回SKIP_BODY

  }

  }

 

自定义标签的开发包括:

1.  开发标签的处理程序(java 类)

2.  .tld 文件中指定标签使用的类

3.  web.xml 中指定JSP 中使.tld( 标签库描述文件) 文件的位置。

 

.tld 文件中

<tag>

    <name>out</name>

    <tag-class>org.apache.taglibs.standard.tag.el.core.OutTag</tag-class>

<body-content >JSP</body-content>

<attribute>

        <name>value</name>

        <required>true</required>

        <rtexprvalue >false</rtexprvalue>

  </attribute>

  </tag>

 

body-content

根据web-jsptaglibrary_2_0.xsd (位于servlet-api.jar 包($TOMCAT_HOME\common\lib )中的\javax\servlet\resources 下,其中web.xml 验证时所需要的xsd 文件都位于此resources 目录下), body-content 的值有下面4 种:

<xsd:enumeration value="tagdependent "/>

    <xsd:enumeration value="JSP "/>

    <xsd:enumeration value="empty "/>

    <xsd:enumeration value="scriptless "/>

 

 

tagdependent 标签体内容 直接被写入BodyContent ,由自定义标签类来进行处理,而不被JSP 容器解释

如下:

<test:myList>

select name,age from users

</test:myList>

 

JSP 接受所有JSP 语法,如定制的或内部的tagscripts 、静态HTML 、脚本元素、JSP 指令和动作。如:

<my:test>

    <%=request.getProtocol()%>      //

</my:test>

具体可参考后面附源码。

 

empty 空标记,即起始标记和结束标记之间没有内容。

下面几种写法都是有效的,

<test:mytag />

<test:mytag uname="Tom" />

<test:mytag></test:mytag>

 

scriptless 接受文本、ELJSP 动作。如上述 使用<body-content> scriptless </body-content> 报错 ,具体可参考后面附源码。

 

rtexprvalue:

由请求时表达式来指定属性的值,默认为false ,如下必须设置为true

<test:welcome uname="<%=request.getParameter("username") %>" />

 

 

body-content JSP/scriptless 时标签体可以接受的代码(jasper-compiler.jar $TOMCAT_HOME\common\lib )中 \org\apache\jasper\compiler\Parser.java 中):

JSP:

private void parseElements(Node parent)

        throws JasperException

    {

        if( scriptlessCount > 0 ) {

            // vc: ScriptlessBody

            // We must follow the ScriptlessBody production if one of

            // our parents is ScriptlessBody.

            parseElementsScriptless( parent );

            return;

        }

       

        start = reader.mark();

        if (reader.matches("<%--")) {

            parseComment(parent);

        } else if (reader.matches("<%@")) {

            parseDirective(parent);

        } else if (reader.matches("<jsp:directive.")) {

            parseXMLDirective(parent);

        } else if (reader.matches("<%!")) {

            parseDeclaration(parent);

        } else if (reader.matches("<jsp:declaration")) {

            parseXMLDeclaration(parent);

        } else if (reader.matches("<%=")) {

            parseExpression(parent);

        } else if (reader.matches("<jsp:expression")) {

            parseXMLExpression(parent);

        } else if (reader.matches("<%")) {

            parseScriptlet(parent);

        } else if (reader.matches("<jsp:scriptlet")) {

            parseXMLScriptlet(parent);

        } else if (reader.matches("<jsp:text")) {

            parseXMLTemplateText(parent);

        } else if (reader.matches("${")) {

            parseELExpression(parent);

        } else if (reader.matches("<jsp:")) {

            parseStandardAction(parent);

        } else if (!parseCustomTag(parent)) {

            checkUnbalancedEndTag();

            parseTemplateText(parent);

        }

}

Scriptless:

private void parseElementsScriptless(Node parent)

        throws JasperException

    {

        // Keep track of how many scriptless nodes we've encountered

        // so we know whether our child nodes are forced scriptless

        scriptlessCount++;

       

        start = reader.mark();

        if (reader.matches("<%-- ")) {

            parseComment(parent);

        } else if (reader.matches("<%@ ")) {

            parseDirective(parent);

        } else if (reader.matches("<jsp:directive. ")) {

            parseXMLDirective(parent);

        } else if (reader.matches("<%!")) {

            err.jspError( reader.mark(), "jsp.error.no.scriptlets" );

        } else if (reader.matches("<jsp:declaration")) {

            err.jspError( reader.mark(), "jsp.error.no.scriptlets" );

        } else if (reader.matches("<%=")) {

            err.jspError( reader.mark(), "jsp.error.no.scriptlets" );

         } else if (reader.matches("<jsp:expression")) {

            err.jspError( reader.mark(), "jsp.error.no.scriptlets" );

        } else if (reader.matches("<%")) {

            err.jspError( reader.mark(), "jsp.error.no.scriptlets" );

        } else if (reader.matches("<jsp:scriptlet")) {

            err.jspError( reader.mark(), "jsp.error.no.scriptlets" );

        } else if (reader.matches("<jsp:text ")) {

            parseXMLTemplateText(parent);

        } else if (reader.matches("${ ")) {

            parseELExpression(parent);

        } else if (reader.matches("<jsp: ")) {

            parseStandardAction(parent);

        } else if (!parseCustomTag(parent)) {

            checkUnbalancedEndTag();

            parseTemplateText(parent);

        }

       

         scriptlessCount--;

}

 

由上面可以看出,局限性比较小,在body-content 可以使用 Scriptless 的地方都可以用 JSP 代替,反之则不可。

(转自: http://www.blogjava.net/xiaodaoxiaodao/archive/2007/01/05/103438.html)

分享到:
评论

相关推荐

    jsp2.0 自定义标签和自定标签函数

    "jsp 2.0自定义标签.doc"文件很可能包含了一个关于如何创建和使用自定义标签的详细教程。它可能涵盖了从创建TLD文件,编写标签处理类,到在JSP页面上实际使用自定义标签的全过程。同时,这个文档可能会提供一些实际...

    Web2.0体系学习(自定义标签)

    - JSP 2.0引入了Facelets,它支持XML-based的视图层,可以更方便地创建自定义组件,包括自定义标签。 - Spring Web Flow、JSF等框架也提供了自定义标签的机制,进一步丰富了Web2.0开发中的自定义标签应用。 通过...

    JSP2.0 Tag 使用

    JSP2.0提供的Tag Files机制是一种新的自定义标签开发方式。这种方式使得开发者可以编写自己的JSP文件作为标签处理器,这个JSP文件被称为标签文件。标签文件通过定义简单的标记来执行操作,使得创建自定义标签变得...

    Tag的使用<JSP 2.0新特性>

    JSP 2.0版本引入了一个新的特性,即自定义Tag的支持,这使得开发者能够创建自己的标签库,以更符合HTML语法的方式来编写业务逻辑。本实例将深入探讨`Tag`的使用,以及如何通过JSP 2.0新特性来简化自定义标签的开发...

    《JSP2.0技术手册》

    2. **标准标签库(JSTL)**:JSTL(JavaServer Pages Standard Tag Library)是JSP 2.0推荐的标准标签库,它包含了一系列用于处理常见任务的标签,如循环、条件判断、XML操作等,使得页面更易于阅读和维护。...

    JSP2.0技术手册完整版附源码.rar

    3. **JSP标签和自定义标签**:学习如何创建和使用自定义标签,提高代码复用性。 4. **错误处理和调试**:学会设置和处理异常,以及如何在JSP中进行调试。 5. **MVC设计模式**:理解MVC模式并应用到JSP项目中,使代码...

    JSP2.0大学教程-覃华

    8. **标签文件**:JSP 2.0允许开发者将自定义标签封装在单独的`.tag`文件中,提高了代码的重用性和模块化。 9. **自动注册Servlet和JSP**:不再需要在`web.xml`中手动配置每个Servlet或JSP,这简化了部署过程。 10...

    JSP自定义标签实例与详细讲解

    在JavaServer Pages (JSP) 技术中,自定义标签是实现页面逻辑和视图分离的一种重要方式,它允许开发者创建可重用的组件,提高代码的可维护性和复用性。本教程将深入探讨JSP自定义标签的实例与详细讲解。 一、JSP...

    jsp的自定义标签

    2. **创建标签处理类(Tag Handler Class)**:这是自定义标签的核心,它是一个实现了`javax.servlet.jsp.tagext.Tag`接口或者其子接口的Java类。在这个类中,你可以编写处理标签生命周期的方法,如`doStartTag()`和...

    JSP2.0 API chm

    **JSP 2.0 API 知识点详解** ...JSP 2.0是其一个重要版本,带来了许多改进和新特性,提升了开发效率...共享的“JSP2.0 API chm”帮助文档无疑是一个宝贵的资源,有助于开发者在实践中进一步探索和提升JSP 2.0的技术水平。

    jsp2.0 学习笔记+完整源码

    - **自定义标签的改进**:引入了新的标签库描述符(TLD, Tag Library Descriptor),使得创建和管理自定义标签更加方便。 **2. JSP 2.0核心概念** - **JSP元素**:包括指令(directives)、声明(declarations)、...

    JSP2.0技术手册完整版+源码

    3. **自定义标签库(Tag Libraries)**:JSP2.0支持自定义标签,允许开发者创建自己的标签库,使得代码更加模块化和可扩展。 4. **页面指令简化**:`&lt;jsp:include&gt;`和`&lt;jsp:forward&gt;`等指令变得更简洁,同时引入了`...

    jsp 2.0技术手册中文版

    - **自定义标签**:通过实现Tag接口或SimpleTag接口,可以创建可重用的自定义标签库。 3. **EL表达式语言** - EL表达式的语法:${expression},用于输出Java对象的值。 - EL的变量解析:访问作用域中的对象,如...

    JSP自定义标签的开发及使用

    本篇文章将深入探讨JSP自定义标签的开发与使用,以及如何通过实例`Demo1_JspTag`来理解这一过程。 首先,我们需要了解自定义标签的基本概念。自定义标签是JSP的一种扩展机制,它允许我们封装复杂的Java代码或业务...

    jsp2.0_技术手册

    - **指令(Directives)**: JSP 2.0中包含`page`、`include`和`taglib`三种指令,用于设置页面属性、导入其他文件和定义自定义标签库。 - **脚本元素(Scripting Elements)**: 包括`!%&gt;`(声明)、`&lt;%= %&gt;`...

    JSP自定义标签之日期显示

    在Java服务器页面(JSP)开发中,自定义标签是一种扩展JSP功能的强大方式,它允许我们封装复杂的逻辑或重复使用的代码片段,提高代码的可读性和可维护性。本篇将深入探讨“JSP自定义标签之日期显示”,以及如何通过...

    JSP2.0大学教程 覃华 教学PPT

    **JSP2.0大学教程 覃华 教学PPT** JSP(JavaServer Pages)是Java平台上的一个重要技术,它允许开发者在HTML、XML或其他任何支持的标记语言中嵌入Java代码,用于创建动态网页。JSP2.0版本引入了许多改进和新特性,...

    权威实用jsp自定义标签demo<select,checkbox,radio>

    在JSP中,自定义标签通常由两部分组成:标签库描述文件(TLD,Tag Library Descriptor)和标签处理类(Tag Handler Class)。TLD用于定义标签的元数据,包括标签名称、属性、导出的标签库等信息;而标签处理类则实现...

    jsp2.0 技术手册

    JSP2.0通过JSP Tag Library Descriptor (TLD)文件支持自定义标签,使得开发人员可以创建自己的标签库,提高代码复用性和可维护性。 6. **标准标签库(JSTL)** JSTL是JSP2.0的一个重要补充,提供了一系列标准标签...

Global site tag (gtag.js) - Google Analytics