这次我们来一步一步的仿造一个google的搜索栏,由于本人学的也很浅相信大家不会看得很迷糊,由于我们没有链接数据库,我采用一个硬编码来编写被匹配的内容,正常情况下应该是从数据库中取出一个表的”被搜索最多次数”的10个内容然后进行匹配 import java.util.ArrayList; import java.util.List;
public class ListFactory { public static List getList(){ List list = new ArrayList(); list.add("ibm"); list.add("hp"); list.add("dell"); list.add("desk"); return list; }
}
这个工厂生成了一个list,里面存储了需要匹配的内容 有了匹配信息我们还需要一个servlet来对它进行匹配
新建一个servlet 映射地址 searchAction
import java.io.IOException; import java.io.PrintWriter; import java.util.List;
import javax.servlet.ServletException; import javax.servlet.http.HttpServlet; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse;
public class SearchAction extends HttpServlet {
/** * Constructor of the object. */ public SearchAction() { super(); }
/** * Destruction of the servlet. <br> */ public void destroy() { super.destroy(); // Just puts "destroy" string in log // Put your code here }
/** * The doGet method of the servlet. <br> * * This method is called when a form has its tag value method equals to get. * * @param request the request send by the client to the server * @param response the response send by the server to the client * @throws ServletException if an error occurred * @throws IOException if an error occurred */ public void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException { //转发至doPost(); doPost(request,response); }
/** * The doPost method of the servlet. <br> * * This method is called when a form has its tag value method equals to post. * * @param request the request send by the client to the server * @param response the response send by the server to the client * @throws ServletException if an error occurred * @throws IOException if an error occurred */ public void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException { //用于缓存匹配对象的字符串,正常应该是个数组 String temps=""; response.setContentType("text/html"); PrintWriter out = response.getWriter(); //从工厂类中取出要匹配的list List list = ListFactory.getList(); //ajax发送过来的请求值,也就是页面上现在输入的内容 String inputtext = request.getParameter("inputtext"); //遍历list for(int i=0;i<list.size();i++){ String temp = (String) list.get(i); //如果在匹配内容头中找到当前输入的字符串,且输入不是空串 //indexOf 返回字串的位置,为0 则表示 123中找到了12 ,而找不到23因为23的indexOf //为1 if(temp.indexOf(inputtext)==0 && inputtext!=null && inputtext.trim().length()!=0){ //将匹配上的list内容添加到缓存字符串 temps=temps+temp+"<br>"; } } //输出缓存字符串 out.write(temps); out.flush(); out.close(); }
/** * Initialization of the servlet. <br> * * @throws ServletException if an error occure */ public void init() throws ServletException { // Put your code here }
}
有了工厂类(替代数据库),有了控制器,现在开始写前台的页面和ajax
<%@ page language="java" import="java.util.*" pageEncoding="utf-8"%> <% String path = request.getContextPath(); String basePath = request.getScheme()+"://"+request.getServerName()+":"+request.getServerPort()+path+"/"; %>
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"> <html> <head> <base href="<%=basePath%>"> <title>My JSP 'index.jsp' starting page</title> <meta http-equiv="pragma" content="no-cache"> <meta http-equiv="cache-control" content="no-cache"> <meta http-equiv="expires" content="0"> <meta http-equiv="keywords" content="keyword1,keyword2,keyword3"> <meta http-equiv="description" content="This is my page"> <!-- <link rel="stylesheet" type="text/css" href="styles.css"> --> </head> <script src="js/prototype.js"></script> <script src="js/test.js" ></script> <body> <table width="100%" border="1" bordercolor="#000000"> <tr> <td> <input name="text" type="text" id="itext" onKeyUp="getXML()"/> <input name="button" type="button" value="搜索"/> <div id="outdiv" style=" display:none; width:119px; height:20; position:absolute; left: 16px; top: 41px; background-color:#ECEDFF">111</div> </td> </tr> <tr> <td> </td> </tr> </table> </body> </html>
这个页面中唯一需要注意的是 作为输出匹配框的 div 层 <div id="outdiv" style=" display:none; width:119px; height:20; position:absolute; left: 16px; top: 41px; background-color:#ECEDFF">111</div> 此层一开始被设置为隐藏,111可以不写,其实写什么都看不到,因为它根本没有被显示 Display:none 类似的属性还有 visible,它们的区别在此不说了,百度一下,你就知道 文本框设置一个键盘事件 onKeyUp="getXML()" 每次键盘抬起就调用一次函数
在开始写脚本文件之前需要先导入prototype库,在我的ajax入门3 里有提及
正常导入它以后我们就开始 编写 test.js 文件
//键盘抬起时激活的函数 function getXML(){ //局部请求地址 var url="searchAction"; //获取用户当前输入的内容 var inputvalue=$("itext").value; //使用prototype函数构造xmlhttprequest对象 var myAjax = new Ajax.Request( url, { //请求方法为post method:'post', //设置参数为 inputtext=inputvalue parameters:"inputtext="+inputvalue, //设置回调函数 onComplete:showResponse, //是否异步 asynchronous:true } ); }
function showResponse(xmlrequest){ //还是需要注意回调函数的参数,使用此参数的responseText属性获取服务器//servlet返回的文本内容,要取得XML请参考我之前的 ajax 入门文章 var text = xmlrequest.responseText; //如果返回的被匹配上的内容不为空 if(text!=""){ //显示该层,关于element.show也是prototype的函数 Element.show("outdiv"); }else{ //如果没匹配上就隐藏该层,注意我们的思路是每次键盘抬起都进行一次请求, //然后进行判断,不匹配就隐藏 Element.hide("outdiv"); } //将匹配的内容输出到 div 层 $("outdiv").innerHTML=xmlrequest.responseText; }
以下内容为更新:
这里我们可以再稍微丰富一下比如将servlet的doPost改写成
public void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException { String temps=""; response.setContentType("text/html"); PrintWriter out = response.getWriter(); List list = ListFactory.getList(); String inputtext = request.getParameter("inputtext"); for(int i=0;i<list.size();i++){ String temp = (String) list.get(i); if(temp.indexOf(inputtext)==0 && inputtext!=null && inputtext.trim().length()!=0){ temps=temps+temp+"$"; } } out.write(temps); out.flush(); out.close(); }
也就是使用"$"字符来将返回的几个匹配分割
然后在javascript中对其进行解析
function showResponse(xmlrequest){ var text = xmlrequest.responseText; var texts = text.split("$"); if(text!=""){ Element.show("outdiv"); }else{ Element.hide("outdiv"); } var temp = ""; var outdiv = $("outdiv"); for(var i = 0;i < texts.length-1;i++){ temp = temp + "<span style=cursor:hand onclick='inMessage(this)'>" +texts[i]+ "</span>" +"<br>"; } outdiv.innerHTML = temp; }
function inMessage(obj){ //alert(obj.innerHTML); $(itext).value = obj.innerHTML; Element.hide("outdiv"); }
这样每次出现下拉列表之后列表中的项目都可以被选择,点击之后内容就会录入到搜索框中了
|
|