Java基於UDP協定完成簡略的聊天室法式。本站提示廣大學習愛好者:(Java基於UDP協定完成簡略的聊天室法式)文章只能為提供參考,不一定能成為您想要的結果。以下是Java基於UDP協定完成簡略的聊天室法式正文
比來比擬閒,一向在抽閒回想一些Java方面的技巧運用。
明天沒甚麼事做,基於UDP協定,寫了一個異常簡略的聊天室法式。
如今的任務,很罕用到socket,也算是對Java收集編程方面的一個簡略回想。
先看一下後果:
完成的後果可以說長短常異常簡略,但照樣可以簡略的看到一個完成道理。
“聊天室001”的用戶,小紅和小綠互相聊了兩句,“聊天室002”的小黑無人理睬,在一旁孤單著。
看一下代碼完成:
1、起首是新聞辦事器的完成,功效很簡略:
•將客戶真個信息(進入了哪個聊天室等)停止掛號;
•結構UDP協定套接字對象,接收各個客戶端發送的新聞;
•解析新聞內容,將聊天信息推送回對應聊天室的各個客戶端;
package com.tsr.simplechat.receive_server; import java.io.IOException; import java.net.DatagramPacket; import java.net.DatagramSocket; import java.net.SocketException; import java.util.ArrayList; import java.util.HashMap; import com.谷歌.gson.Gson; import com.tsr.simplechat.bean.MessageEntity; import com.tsr.simplechat.client.ChatClient; //聊天辦事器 public class ChatServer extends Thread { // 法式占用端標語 private static final int PORT = 10000; // 新聞接收套接字對象 private static DatagramSocket server = null; // 字典對象(Key:聊天室ID,Value:該聊天室下的客戶端用戶聚集); private static HashMap<String, ArrayList<ChatClient>> groups = new HashMap<String, ArrayList<ChatClient>>(); // 結構器 public ChatServer() { try { // 新聞接收套接字對象的結構初始化 server = new DatagramSocket(PORT); } catch (SocketException e) { e.printStackTrace(); } } // 注冊聊天室新登錄用戶 public static void logInGroup(String groupID, ChatClient client) { // 經由過程聊天室ID,獲得該聊天室的一切在線用戶 ArrayList<ChatClient> clients = groups.get(groupID); if (clients == null) { clients = new ArrayList<ChatClient>(); } // 將此次進入聊天室的用戶掛號 clients.add(client); // 更新聊天室信息 groups.put(groupID, clients); } // 輪回吸收新聞 @Override public void run() { while (true) { receiveMessage(); } } private void receiveMessage() { // UDP數據包 byte[] buf = new byte[1024]; DatagramPacket packet = new DatagramPacket(buf, buf.length); while (true) { try { // 接收數據包 server.receive(packet); } catch (IOException e) { // TODO Auto-generated catch block e.printStackTrace(); } // 解析數據包,獲得聊天信息 String content = new String(packet.getData(), 0, packet.getLength()); // 經由過程第三方包解析json數據 Gson gson = new Gson(); MessageEntity me = gson.fromJson(content, MessageEntity.class); // 解析新聞內容,經由過程聊天室ID,獲得該聊天室的一切在線用戶 ArrayList<ChatClient> clients = groups.get(me.getGroupId()); // 將吸收到的新聞推送回該聊天室的各個用戶 for (ChatClient client : clients) { client.pushBackMessage(me); } } } }
2、客戶端法式,仍然很簡略:
•簡略的界說客戶端聊天室界面。
•結構新聞發送套接字對象。
•獲得聊天信息框的內容,發送到辦事器。
package com.tsr.simplechat.client; import java.awt.Button; import java.awt.Event; import java.awt.Frame; import java.awt.TextArea; import java.awt.TextField; import java.awt.event.WindowAdapter; import java.awt.event.WindowEvent; import java.io.IOException; import java.net.DatagramPacket; import java.net.DatagramSocket; import java.net.InetAddress; import java.net.SocketException; import java.net.UnknownHostException; import com.tsr.simplechat.bean.MessageEntity; import com.tsr.simplechat.receive_server.ChatServer; //客戶端法式 public class ChatClient extends Frame { private static final long serialVersionUID = 1L; // 聊天室ID private String groupID; // 客戶端用戶名 private String clientName; // 客戶端新聞發送辦事套接字 private DatagramSocket msg_send; // 辦事端口 private final int PORT = 10000; // 辦事器IP地址 private InetAddress ip; // 客戶端控件 TextField tf = new TextField(20); TextArea ta = new TextArea(); Button send = new Button("send"); // 客戶端結構器 public ChatClient(String groupID, String clientName) { super("聊天室:" + groupID + "/" + clientName); this.clientName = clientName; this.groupID = groupID; // 設置客戶端界面款式 add("North", tf); add("Center", ta); add("South", send); setSize(250, 250); show(); // 聊天相干辦事器初始化 init(); // 監督器 addWindowListener(new WindowAdapter() { public void windowClosing(WindowEvent e) { // 封閉新聞發送辦事 msg_send.close(); // 封閉客戶端法式 dispose(); System.exit(0); } }); } // 聊天相干辦事器初始化 private void init() { // 注冊以後用戶及地點聊天室信息注冊到辦事器 ChatServer.logInGroup(groupID, this); try { // 初始化新聞發送套接字對象 msg_send = new DatagramSocket(); // 指定新聞辦事器 try { ip = InetAddress.getByName("127.0.0.1"); } catch (UnknownHostException e) { System.out.println("未知的主機異常.."); } } catch (SocketException e) { System.out.println("套接字銜接異常.."); } } // 新聞發送按鈕時光監聽 public boolean action(Event evt, Object arg) { if (evt.target.equals(send)) { try { // 獲得輸出內容 String content = tf.getText(); // 發送新聞 send_message(content); // 清空聊天框 tf.setText(null); } catch (Exception ioe) { System.out.print(ioe.getMessage()); } } return true; } // 新聞發送 private void send_message(String content) { // 新聞格局化(json格局) String message = messageFormat(content); // 將新聞封裝成UDP數據包 byte[] buf = message.getBytes(); DatagramPacket packet = new DatagramPacket(buf, buf.length, ip, PORT); try { // 經由過程UDP協定發送新聞 msg_send.send(packet); } catch (IOException e) { System.out.println("IO異常.."); } } // 新聞格局化 private String messageFormat(String content) { StringBuffer buffer = new StringBuffer(); buffer.append("{\"groupId\":").append("\"").append(groupID).append( "\","); buffer.append("\"userName\":\"").append(clientName).append("\","); buffer.append("\"text\":\"").append(content).append("\"}"); return buffer.toString(); } // 從辦事器獲得以後聊天室最新新聞(回調..) public void pushBackMessage(MessageEntity me) { ta.append(me.getUserName() + ":" + me.getText()); ta.append("\n"); } }
3、新聞實體類
重要就是用於將新聞封裝成對象,包括:聊天室ID、新聞發送者昵稱,新聞內容。應用json格局解析。
package com.tsr.simplechat.bean; //新聞實體 public class MessageEntity { private String groupId; private String userName; private String text; public String getGroupId() { return groupId; } public void setGroupId(String groupId) { this.groupId = groupId; } public String getUserName() { return userName; } public void setUserName(String userName) { this.userName = userName; } public String getText() { return text; } public void setText(String text) { this.text = text; } }
4、OK,到了這裡就根本弄定了,樹立一個測試類。
•開啟新聞辦事器。
•開啟三個客戶端,個中兩個進入“聊天室001”,另外一個進入“聊天室002”。
import com.tsr.simplechat.client.ChatClient; import com.tsr.simplechat.receive_server.ChatServer; public class Test { public static void main(String[] args) { ChatServer r = new ChatServer(); r.start(); ChatClient c1 = new ChatClient("001", "小紅"); ChatClient c2 = new ChatClient("001", "小綠"); ChatClient c3 = new ChatClient("002", "小黑"); } }
以上就是本文的全體內容,願望對年夜家的進修有所贊助,也願望年夜家多多支撐。