來寫個AJAX版的聊天室吧!先看看直接使用AJAX要如何做到,首先需要一個簡單的聊天室Servlet…
|
onlyfun.caterpillar; java.io.IOException; java.io.PrintWriter; java.util.LinkedList; java.util.List; javax.servlet.ServletException; javax.servlet.http.HttpServletRequest; javax.servlet.http.HttpServletResponse; ChatRoomServlet javax.servlet.http.HttpServlet javax.servlet.Servlet LinkedList<Message> messages = LinkedList<Message>();
ChatRoomServlet() ();
List<Message> addMessage(String text) (text != && text.trim().length() > 0) messages.addFirst( Message(text)); (messages.size() > 10) messages.removeLast();
messages;
List<Message> getMessages() messages;
doPost(HttpServletRequest request, HttpServletResponse response) ServletException, IOException List<Message> list = ;
(.equals(request.getParameter())) list = addMessage(request.getParameter());
(.equals(request.getParameter())) list = getMessages();
PrintWriter out = response.getWriter(); response.setContentType(); response.setHeader(, ); out.println(); ( i = 0; i < list.size(); i++) String msg = list.get(i).getText(); out.println( + msg + );
out.println();
|
Message物件如下…
|
onlyfun.caterpillar; Message id = System.currentTimeMillis(); String text;
Message(String newtext) text = newtext; (text.length() > 256) text = text.substring(0, 256);
text = text.replace(, ); text = text.replace(, );
getId() id;
String getText() text;
|
Servlet接受訊息新增與查詢,判斷的方式是檢查請求引數task是send或query。
Servlet會以XML傳回目前List當中的訊息,客戶端可以查詢或插入新訊息時,取得目前List中的訊息,接著在web.xml中設定一下…
|
<?xml version= encoding=?> <web-app id= version= xmlns= xmlns:xsi= xsi:schemaLocation=> <servlet> <description> </description> <display-name> ChatRoomServlet</display-name> <servlet-name>ChatRoomServlet</servlet-name> <servlet-class> onlyfun.caterpillar.ChatRoomServlet</servlet-class> </servlet> <servlet-mapping> <servlet-name>ChatRoomServlet</servlet-name> <url-pattern>/ChatRoomServlet</url-pattern> </servlet-mapping> <session-config> <session-timeout> 30 </session-timeout> </session-config> </web-app>
|
在網頁中,使用者可以在輸入訊息後按下按鈕送出資訊,並在XML回應取得時,將訊息以一列一列的表格方式顯示出來,另外還設定了週期性的輪詢,即使不輸入新訊息,也可以週期性的取得新的聊天訊息…
|
<!DOCTYPE HTML PUBLIC > <html> <head> <meta http-equiv= content=> <title>Chat Room</title> <script type=> var xmlHttp; function createXMLHttpRequest() (window.ActiveXObject) xmlHttp = ActiveXObject(); (window.XMLHttpRequest) xmlHttp = XMLHttpRequest();
function sendMessage() var msg = document.getElementById().value;
(msg == ) refreshMessage(); ;
var param = + msg; ajaxRequest(param); document.getElementById().value = ;
function queryMessage() var param = ; ajaxRequest(param);
function ajaxRequest(param) var url = + Date().getTime(); createXMLHttpRequest(); xmlHttp.onreadystatechange = refreshMessage; xmlHttp.open(, url, ); xmlHttp.setRequestHeader(, ); xmlHttp.send(param);
function refreshMessage() (xmlHttp.readyState == 4) (xmlHttp.status == 200) var messages = xmlHttp.responseXML.getElementsByTagName();
var table_body = document.getElementById(); var length = table_body.childNodes.length; (var i = 0; i < length; i++) table_body.removeChild(table_body.childNodes[0]);
var length = messages.length; (var i = length - 1; i >= 0 ; i--) var message = messages[i].firstChild.data; var row = createRow(message);
table_body.appendChild(row);
setTimeout(, 2000);
function createRow(message) var row = document.createElement(); var cell = document.createElement(); var cell_data = document.createTextNode(message); cell.appendChild(cell_data); row.appendChild(cell); row;
</script> </head> <body> <p> Your Message: <input id=/> <input type= value= onclick=/> </p> <p>Messages:</p> <table align=> <tbody id=></tbody> </table> </body> </html>
|
簡單抓個畫面…
直接用AJAX,後端用JSP/Servlet,您要對請求引數做些判斷,看看是新增訊息或查詢,並要自行輸出XML,有的沒的…
改成DWR的話,就很簡單了,寫個簡單的Java物件…
|
onlyfun.caterpillar; java.util.LinkedList; java.util.List; Chat LinkedList<Message> messages = LinkedList<Message>(); List addMessage(String text) (text != && text.trim().length() > 0) messages.addFirst( Message(text)); (messages.size() > 10) messages.removeLast();
messages;
List getMessages() messages;
|
接著…在dwr.xml中開放一下…
|
<?xml version= encoding=?> <!DOCTYPE dwr PUBLIC >
<dwr> <allow> <create creator= javascript=> <param name= value=/> </create>
<convert converter= match=/> </allow> </dwr>
|
使用者取得訊息時,是直接傳回List物件,而List中裝的是Message物件,Message物件是自訂物件,conterver設定為 bean,表示DWR會自動將Message的getter名稱轉換為傳回客戶端的JavaScript物件中的屬性,例如Message中有 getText(),則在客戶端可以用message.text這樣的方式來存取。
接著是簡單的客戶端網頁…
|
<!DOCTYPE HTML PUBLIC > <html> <head> <meta http-equiv= content=> <title>Insert title here</title> <script src= type=></script> <script src= type=></script> <script src= type=></script> <script type=> function sendMessage() var text = DWRUtil.getValue(); DWRUtil.setValue(, ); Chat.addMessage(text, gotMessages);
function gotMessages(messages) var chatlog = ; (var data in messages) chatlog = + messages[data].text + + chatlog;
DWRUtil.setValue(, chatlog); setTimeout(, 2000);
function queryMessage() Chat.getMessages(gotMessages);
</script> </head> <body> <p> Your Message: <input id=/> <input type= value= onclick=/> </p> <p>Messages:</p> <div id=></div> </body> </html>
|
當List物件傳回時,它成為gotMessages(messages)中的messages物件,而messages物件中包括 Message物件轉換後對應的JavaScript物件,由於我們已經設定了Converter,所以可以用messages[data].text來 取得傳回的訊息…
簡單抓個畫面…