這篇博客,我想利用前面兩篇JSP標籤的內容實現一個可以選擇日期的自定義標籤。這篇博客會用到WdatePicker.js插件,這是一個日期選擇器。本篇博客主要是想利用前面兩篇博客的內容實現一些能用上的自定義標籤。關於WdatePicker.js的使用不會多說,重點還是自定義標籤。
首先看一下最終的結果是個什麼樣子:
通過自定義標籤生成一個輸入框,單擊這個輸入框則會調用WdatePicker.js讓用戶選擇日期。
這個實現還是很簡單,直接給代碼,在代碼中說明一下,需要注意的事項。
標籤處理器:
package myTag;
import java.io.IOException;
import javax.servlet.jsp.JspContext;
import javax.servlet.jsp.JspException;
import javax.servlet.jsp.JspWriter;
import javax.servlet.jsp.tagext.JspFragment;
import javax.servlet.jsp.tagext.JspTag;
import javax.servlet.jsp.tagext.SimpleTagSupport;
/** 繼承了SimpleTagSupport的全部方法 */
public class DateTag extends SimpleTagSupport {
private String dateValue; //值
private String format; //日期
private String id; //輸入框的ID
public String getDateValue() {
return dateValue;
}
public void setDateValue(String dateValue) {
System.out.println("得到的值:" + dateValue);
this.dateValue = dateValue;
}
public String getFormat() {
return format;
}
public void setFormat(String format) {
System.out.println("得到的格式:" + format);
this.format = format;
}
public String getId() {
return id;
}
public void setId(String id) {
System.out.println("得到的ID:" + id);
this.id = id;
}
/** 主要的方法,繪製標籤會調用 */
@Override
public void doTag() throws JspException, IOException {
/* 輸出JspWriter */
JspWriter out = getJspContext().getOut();
try {
String html = "<input type='text' id='" + getId() + "' class='css' onclick=\"showWdatePicker(\'" + getId() + "','" + getFormat() + "')\" ";
if(getDateValue() != null && !"".equals(getDateValue())) {
html += " value='" + getDateValue() + "' />";
} else {
html += "' />";
}
System.out.println(html);
out.println(html);
} catch(Exception e) {
e.printStackTrace();
}
}
/** JspContext的setter,getter方法,
* 容器在處理JSP頁面的中自定義標籤時會調用標籤處理器(本類),
* 這個時候容器會把頁面的JspContext傳遞個標籤處理器,就是通過這個方法
* 得到JspContext最主要的是要得到JspWriter
* 一般會把容器傳遞進來的JspContext保存在一個變量中,(本類沒有顯示這個變量,因爲在定義在SimpleTagSupport類中,直接使用就可以了)
* */
@Override
protected JspContext getJspContext() {
return super.getJspContext();
}
@Override
public void setJspContext(JspContext pc) {
super.setJspContext(pc);
}
/** JspFragment的setter, getter方法
* 如果標籤存在主體,則容器在調用這個標籤處理器的時候,會調用setJspBody()方法,將主體傳遞給標籤處理器
* 同樣建議使用變量保存起來,SimpleTagSupport類中存在這個變量:jspBody
* */
@Override
protected JspFragment getJspBody() {
return super.getJspBody();
}
@Override
public void setJspBody(JspFragment jspBody) {
super.setJspBody(jspBody);
}
/** Parent的setter,getter方法,如果當前標籤在另一個標籤之中
* 則容器在處理該標籤的時候會把父標籤傳遞及哪裏,SimpleTagSupport的:parentTag會保存這個變量
* */
@Override
public JspTag getParent() {
return super.getParent();
}
@Override
public void setParent(JspTag parent) {
super.setParent(parent);
}
}
tld文件:
<tag>
<name>dateTag</name>
<tag-class>myTag.DateTag</tag-class>
<body-content>empty</body-content>
<attribute>
<name>id</name>
<required>true</required>
<type>java.lang.String</type>
</attribute>
<attribute>
<name>format</name>
<required>true</required>
<type>java.lang.String</type>
</attribute>
<attribute>
<name>dateValue</name>
<rtexprvalue>true</rtexprvalue>
<type>java.lang.Date</type>
</attribute>
</tag>
jsp:
<%@ taglib uri="/WEB-INF/mytags.tld" prefix="easy" %>
<%@ page isELIgnored="false" %>
<%@ page contentType="text/html;charset=UTF-8" language="java" pageEncoding="UTF-8" %>
<%
String ctx = request.getContextPath();
request.getSession().setAttribute("dateValue", "2017-9-9");
/* 不寫後臺方法直接將值存在session中 */
%>
<html>
<head>
<script src="<%=ctx %>/resources/js/datepicker/WdatePicker.js" ></script>
<meta charset="UTF-8">
</head>
<body>
<h1>時間標籤</h1>
<easy:dateTag id="id" format="yyyy-MM-dd" dateValue="${dateValue}"/>
</body>
<script>
/** 顯示日曆控件 */
function showWdatePicker(objId,df){
WdatePicker({
el:objId,
isShowClear:false,
readOnly:true,
highLineWeekDay:true,
dateFmt:df
});
}
</script>
</html>
被容器處理過後的頁面:
<html>
<head>
<script src="/WebTest/resources/js/datepicker/WdatePicker.js" ></script>
<meta charset="UTF-8">
</head>
<body>
<h1>時間標籤</h1>
<input type='text' id='id' class='css' onclick="showWdatePicker('id','yyyy-MM-dd')" value='2017-9-9' />
</body>
<script>
/** 顯示日曆控件 */
function showWdatePicker(objId,df){
WdatePicker({
el:objId,
isShowClear:false,
readOnly:true,
highLineWeekDay:true,
dateFmt:df
});
}
</script>
</html>
對於上面的代碼沒有什麼特殊的,不過有一點需要提一下:如果在標籤處理器中使用Date作爲日期的值類型,那麼在頁面上使用EL表達式取值的時候,EL會強轉,這時候就會報錯:
上網百度過,網友也說跟環境有關的,我的環境是JDK1.7, Tomcat7.x的,出現這個問題,錯誤代碼就不貼了,如果是自己的標籤出現這個錯誤就改一下標籤,如果是第三方庫出現這個問題,就想辦法改一改實現方式。