日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 前端技术 > javascript >内容正文

javascript

Head First JSP---随笔八(传统标记)

發布時間:2025/3/15 javascript 21 豆豆
生活随笔 收集整理的這篇文章主要介紹了 Head First JSP---随笔八(传统标记) 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

傳統標記處理器

也許我們很幸運,我們的公司采用了JSP 2.0。但也可能很糟糕,用的是2.0以前的版本。


Tag處理器API

我們只要擴展其中一個類就行了。


一個非常小傳統標記處理器

這個例子太極除了,它與SimpleTag處理器的doTag()方法幾乎沒有什么區別。


有兩個方法的傳統標記處理器


標記有體時:簡單標記和傳統標記的比較


這里思考一個問題:如果我們要循環一個體呢?這里是return,我們該如何做呢?后面有答案!


傳統標記的生命周期是不同的


這樣的生命周期很有意思。


傳統標記生命周期取決于返回值

doStartTag()和doEndTag()方法返回一個int。這個int告訴容器下一步要做什么。

對于doStartTag(),容器的問題是“我該計算體嗎?”。

對于doEndTag(),容器的問題是“我要繼續計算調用頁面的余下部分嗎?”。

如圖:


IterationTag允許體重復執行

TagSupport的UML:

通過重寫doAfterBody()方法達到重復執行體的功能

例子:
簡單標記實現:

傳統標記實現:


TagSupport的默認返回值

如果沒有覆蓋返回一個整數的TagSupport生命周期方法,要當心TagSupport方法實現返回的默認值


需要注意的點,給你一個例子

要注意,doAfterBody()方法在已經處理一次體后才開始運行,看看上面的調用“流程圖”

這里還要注意:容器可以重用傳統標記處理器,也就是說,我們要注意全局變量


實例

還記得第三章的啤酒案例嗎?現在來實現動態獲取!

開發環境:

初始化頁面(init.jsp):

<%@ page import="java.util.*" %>> <html> <body><% List<String> optionsList = new ArrayList<String>();optionsList.add("light");optionsList.add("amber");optionsList.add("brown");optionsList.add("dark");getServletContext().setAttribute("colorList", optionsList);%><jsp:forward page="beer.jsp"/> </body> </html>

我們的表單頁面(beer.jsp):

<%@ taglib prefix="formTags" uri="http://example.com/tags/forms" %> <%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %> <html> <body><form method="post" action="SelectBeer.do"><p>Select beer characteristics:</p>Color:<c:catch><formTags:select name="color" size="1"optionsList="${applicationScope.colorList}"/><br><br></c:catch><input type="submit" value="submit"></form> </body> </html>

我們的簡單標記處理器類(SelectTagHandler.java):

package com.example.taglib;import java.io.IOException; import java.util.List;import javax.servlet.jsp.JspException; import javax.servlet.jsp.JspWriter; import javax.servlet.jsp.PageContext; import javax.servlet.jsp.tagext.SimpleTagSupport;public class SelectTagHandler extends SimpleTagSupport{private List<String> optionsList;private String name;private int size;public void setOptionsList(List<String> optionsList) {this.optionsList = optionsList;}public void setName(String name) {this.name = name;}public void setSize(int size) {this.size = size;}@Overridepublic void doTag() throws JspException, IOException {PageContext pageContext = (PageContext) getJspContext();JspWriter out = pageContext.getOut();out.println("<select name='"+name+"' size='"+size+"'>");for(int i=0;i<optionsList.size();i++) {String s = optionsList.get(i);out.println("<option value='"+s+"'> "+s+" </option>");}out.println("</select>");} }

我們的標記文件(demo.tld):

<?xml version="1.0" encoding="ISO-8859-1" ?> <!DOCTYPE taglibPUBLIC "-//Sun Microsystems, Inc.//DTD JSP Tag Library 1.2//EN""http://java.sun.com/j2ee/dtds/web-jsptaglibrary_1_2.dtd"><taglib><tlib-version>1.2</tlib-version><jsp-version>1.2</jsp-version><short-name>Forms Taglib</short-name><uri>http://example.com/tags/forms</uri><description>An example tab library of replacements for the HTML form tags.</description><tag><name>select</name><tag-class>com.example.taglib.SelectTagHandler</tag-class><body-content>empty</body-content><attribute><name>optionsList</name><type>java.util.List</type><required>true</required><rtexprvalue>true</rtexprvalue></attribute><attribute><name>name</name><required>true</required><rtexprvalue>true</rtexprvalue></attribute><attribute><name>size</name><required>true</required><rtexprvalue>true</rtexprvalue></attribute></tag> </taglib>

我們的部署文件(DD):

<?xml version="1.0" encoding="UTF-8"?> <web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"xmlns="http://java.sun.com/xml/ns/javaee"xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_3_0.xsd"id="WebApp_ID" version="3.0"><welcome-file-list><welcome-file>init.jsp</welcome-file></welcome-file-list></web-app>

實驗結果:


select標記還不完善

我們HTML的<select>標記有更多的屬性

我們需要在標記處理器類添加些能夠設置它們的方法:

看完之后…呵呵,tld也要配置這些屬性。太恐怖了!!

幸好!JSP規范專門針對這個目的提供了一個API,那就是我們的DynamicAttributes接口


標記處理器代碼使用DynamicAttribute接口

使用3張圖搞定這個部分:

首先看看setXxx()該如何解決(因為這里是鍵/值對,所以用HashMap是最好的選擇,當然也可以用別的):

接下來是doTag()方法:

最后是TLD中的配置:

最后就完成了。這簡直是神器

這里指出:這個接口對傳統標記也是適用的


標記文件的dynamic-attributes

這里要注意,tagAttrs是一個頁面作用域變量

一個實例:

首先是.tag文件:

<%@ tag body-content="empty" dynamic-attributes="tagAttrs"%> <%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %> <c:forEach var="attr" items="${tagAttrs}">${attr.key} = ${attr.value} </c:forEach>

其次是測試的.jsp文件:

<%@ taglib prefix="myTags" tagdir="/WEB-INF/tags" %> <html> <body><myTags:header name="123" value="111"/> </body> </html>

實驗結果:

帥呆了!!


DynamicAttributes接口的要點

  • DynamicAttributes接口允許標記處理器類接收任意數目的標記屬性。
  • TLD中的標記聲明必須包含<dynamic-attribute>元素。
  • 顯式標記屬性必須有一個設置方法。
  • 一般會使用setDynamicAttribute()方法利用一個hashmap存儲動態屬性名/值對。
  • 標記文件也可以使用動態屬性。
  • 標記要使用tag指令的dynamic-attributes屬性。
  • dynamic-attributes的值包含動態屬性的一個hashmap。
  • 一般地,會使用JSTL forEach定制動作迭代處理這個映射。

  • 如果要訪問體內容!

    如果我們能直接訪問具體的體內容,就可以做很多事情了,比如在表達式中使用體內容,或者以某種方式過濾或修改。為此可以擴展BodyTagSupport而不是TagSupport,這樣你就能訪問BodyTag接口方法。


    基于BodyTag,你會獲得兩個新方法

    注意:默認值改變為EVAL_BODY_BUFFERED

    還有一個需要注意的地方(如果沒有體,需要return SKIP_BODY):


    傳統標記方法的生命周期返回值


    標記可以調用其父標記

    SimpleTag和Tag都有一個getParent()方法(注意返回值存在區別)。


    簡單標記的父標記可以是傳統標記

    簡單標記的父標記可以是傳統標記的原因,是因為Tag is-like-a JspTag。因此,簡單標記不能是傳統標記的父標記


    父標記從子標記獲取信息

    我們知道,只有getParent()方法而沒有getChild()方法,也就是說,只能獲取到父標記不能得到子標記。那我們如何獲取到信息呢?

    一個例子:

    這樣就很巧妙的讓父標記知道子標記的信息。下面是測試:

    結果與我們想象的一樣


    得到一個任意的祖先


    使用findAncestorWithClass()方法向上查找到一個特定的祖先,返回第一個找到的祖先(也就是如果這顆樹有多個我們要查找的節點,返回深度最深的節點并且這個節點是this的祖先)。


    簡單標記和傳統標記的重要區別


    使用標記處理器的PageContext API(復習)


    本章完。。

    總結

    以上是生活随笔為你收集整理的Head First JSP---随笔八(传统标记)的全部內容,希望文章能夠幫你解決所遇到的問題。

    如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。