自定义标签的步骤:
1.写一个类实现SimpleTag接口或者继承SimpleTagSupport
2.写一个tld文件,描述写好的类
3.在jsp页面引入tld文件,就可以在jsp页面中使用自定义标签
执行原理:
当jsp在执行的过程中,每当遇到一个简单标签时都会创建一个处理类对象.
调用setJspContext传入当前jsp页面的PageContext对象.
如果当前标签有父标签则调用setParent方法将父标签传入,如果没有父标签则这个方法不会被调用.
如果该标签具有属性,调用属性的setXXX方法将属性的值传入
如果当前标签具有标签体,则会调用setJspBody将封装了标签体信息的JspFragment传入,如果没有标签体,这个方法不执行
最后调用doTag方法,在这个方法里我们可以书写处理标签事件的java代码
当自定义标签执行完成后,简单标签对象就销毁掉了.
案例1.概念性知识
SimpleDemo1类:
package cn.itheima.simpleTag;
import java.io.IOException;
import javax.servlet.jsp.JspException;
import javax.servlet.jsp.SkipPageException;
import javax.servlet.jsp.tagext.JspFragment;
import javax.servlet.jsp.tagext.SimpleTagSupport;
public class SimpleDemo1 extends SimpleTagSupport {
private int times;
public void setTimes(int times) {
this.times = times;
}
@Override
public void doTag() throws JspException, IOException {
//1.控制表前提的内容要不要执行
//--控制标签体不执行,什么都不做标签体的内容就不会执行
//--控制表前提执行,只要调用封装着标签体JSPFragment对象的invoke方法即可
JspFragment fragment = getJspBody();
fragment.invoke(getJspContext().getOut());
//2.控制标签体之后的内容要不要执行
//标签之后的内容执行,什么都不做,就会执行
//标签之的内容不执行,抛出一个异常SkipPgageException
// throw new SkipPageException();
//3.控制标签体重复执行
for(int i=0;i<times;i++){
getJspBody().invoke(null);
}
}
}
如果要使用属性:则需要在类中的成员属性中定义,并需要set方法,然后再tld文件中配置。
配置文件:
name:要使用的标签的名字。
tag-class:定义的那个类。
body-content:JSP:简单标签中不能使用这个属性,因为不支持java代码
empty:标签体内容是空。
scriptless:标签体可以有内容
rtexprvalue
attribute:
name:类中定义的属性名(必须实现se方法)
required:是否为必须属性,true表示是必须属性。
rtexprvalue:是否支持EL表达式。true表示支持EL表达式。
type:类中定义的属性的类型。int,String,bolean...等
<tag>
<name>bodyInvoke</name>
<tag-class>cn.itheima.simpleTag.SimpleDemo1</tag-class>
<body-content>scriptless</body-content>
<attribute>
<name>times</name>
<required>true</required>
<rtexprvalue>true</rtexprvalue>
<type>int</type>
</attribute>
</tag>
在jsp页面是导入tld文件.
<%@ page language="java" import="java.util.*" pageEncoding="UTF-8"%>
<%@ taglib uri="http://www.itheima.com/simples" prefix="t"%>
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
<html>
<head>
<title></title>
<meta http-equiv=" pragma" content="no-cache">
<meta http-equiv="cache-control" content="no-cache">
<meta http-equiv="expires" content="0">
</head>
<body>
<t:bodyInvoke times="4">标签体的内容执行了</t:bodyInvoke>after
</body>
</html>
运行结果:
案例2:模拟防盗链功能的标签:
1.定义的类:
package cn.itheima.simpleTag;
import java.io.IOException;
import javax.servlet.ServletResponse;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.jsp.JspException;
import javax.servlet.jsp.PageContext;
import javax.servlet.jsp.tagext.SimpleTagSupport;
public class SimpleDemo3 extends SimpleTagSupport{
@Override
public void doTag() throws JspException, IOException {
PageContext pc=(PageContext) getJspContext();
String ref = pc.getRequest().getParameter("Referer");
if("".endsWith(ref)||ref==null||!ref.startsWith("http://localhost")){
HttpServletRequest request=(HttpServletRequest) pc.getRequest();
HttpServletResponse response = (HttpServletResponse) pc.getResponse();
response.sendRedirect(request.getContextPath()+"/index.jsp");
return;
}
}
}
2.tld文件:
<tag>
<name>referer</name>
<tag-class>cn.itheima.simpleTag.SimpleDemo3</tag-class>
<body-content>empty</body-content>
</tag>