java 聊天室

时间:2024.4.20

《Java之聊天室制作》总结报告

姓    名                       

学    号______             _____

班    级                    ____

二〇##年十二月二十一日


目录

1,    设计目的

为了强化基础知识,结合多个模块的知识 综合应用。巩固基础,使java编程思想充分应用,主要了解及使用 I/O 网络通信,和图形用户界面。,掌握使用Java语言进行面向对象设计的基本方法,提高运用面向对象知识分析实际问题、解决实际问题的能力。

2,    设计内容

基本实现java聊天室的功能:

1,     实现服务器端

2,     实现客户端

3,     实现多用户聊天功能

4,     实现聊天记录的保存

3,    所用知识

1,     I/O

2,     多线程

3,     网络通信

  ServerSocket Socket

4,     图形用户界

5,     监听事件

4,设计思想

    通过用户名进行用户登录  然后等待其他用户的登录,然后再选定聊天用户进行聊天 在文本框里面输入文字 按发送按钮 或按ENTER键进行消息的发送,接收方式为自动接收 实现一个简易的即时聊天工具,同时利用java的跨平台性实现不同平台下的聊天

5,软件截图

服务器端:

客户端:

聊天记录:

6,主要代码

服务器端:

publicclassMyServerextends JFrame {

    private JTextArea ta_info;

    private ServerSocket server; // 声明ServerSocket对象

    private Socket socket; // 声明Socket对象socket

    private Hashtable<String, Socket> map = new Hashtable<String, Socket>();// 用于存储连接到服务器的用户和客户端套接字对象

   

    publicvoid createSocket() {

        try {

            server = new ServerSocket(3000);// 创建服务器套接字对象

            while (true) {

                ta_info.append("waitting......\n");

                socket = server.accept();// 获得套接字对象

                ta_info.append("Client sueessful。" + socket + "\n");

                new ServerThread(socket).start();// 创建并启动线程对象

            }

        } catch (IOException e) {

            e.printStackTrace();

        }

    }

   

    class ServerThread extends Thread {

        Socket socket;

        public ServerThread(Socket socket) {

            this.socket = socket;

        }

        publicvoid run() {

            try {

                ObjectInputStream ins = new ObjectInputStream(socket

                        .getInputStream());

                while (true) {

                    Vector v = null;

                    try {

                        v = (Vector) ins.readObject();

                    } catch (ClassNotFoundException e) {

                        e.printStackTrace();

                    }

                    if (v != null && v.size() > 0) {

                        for (int i = 0; i < v.size(); i++) {

                            String info = (String) v.get(i);// 读取信息

                            String key = "";

                            if (info.startsWith("用户:")) {// 添加登录用户到客户端列表

                                key = info.substring(3, info.length());// 获得用户名并作为键使用

                                map.put(key, socket);// 添加键值对

                                Set<String> set = map.keySet();// 获得集合中所有键的Set视图

                                Iterator<String> keyIt = set.iterator();// 获得所有键的迭代器

                                while (keyIt.hasNext()) {

                                    String receiveKey = keyIt.next();// 获得表示接收信息的键

                                    Socket s = map.get(receiveKey);// 获得与该键对应的套接字对象

                                    PrintWriter out = new PrintWriter(s

                                            .getOutputStream(), true);// 创建输出流对象

                                    Iterator<String> keyIt1 = set.iterator();// 获得所有键的迭代器

                                    while (keyIt1.hasNext()) {

                                        String receiveKey1 = keyIt1.next();// 获得键,用于向客户端添加用户列表

                                        out.println(receiveKey1);// 发送信息

                                        out.flush();// 刷新输出缓冲区

                                    }

                                }

                            } elseif (info.startsWith("退出:")) {

                                key = info.substring(3);// 获得退出用户的键

                                map.remove(key);// 添加键值对

                                Set<String> set = map.keySet();// 获得集合中所有键的Set视图

                                Iterator<String> keyIt = set.iterator();// 获得所有键的迭代器

                                while (keyIt.hasNext()) {

                                    String receiveKey = keyIt.next();// 获得表示接收信息的键

                                    Socket s = map.get(receiveKey);// 获得与该键对应的套接字对象

                                    PrintWriter out = new PrintWriter(s

                                            .getOutputStream(), true);// 创建输出流对象

                                    out.println("退出:" + key);// 发送信息

                                    out.flush();// 刷新输出缓冲区

                                }

                            } else {// 转发接收的消息

                                key = info.substring(info.indexOf(":发送给:") + 5,

                                        info.indexOf(":的信息是:"));// 获得接收方的key值,即接收方的用户名

                                String sendUser = info.substring(0, info

                                        .indexOf(":发送给:"));// 获得发送方的key值,即发送方的用户名

                                Set<String> set = map.keySet();// 获得集合中所有键的Set视图

                                Iterator<String> keyIt = set.iterator();// 获得所有键的迭代器

                                while (keyIt.hasNext()) {

                                    String receiveKey = keyIt.next();// 获得表示接收信息的键

                                    if (key.equals(receiveKey) && !sendUser.equals(receiveKey)) {// 与接受用户相同,但不是发送用户

                                        Socket s = map.get(receiveKey);// 获得与该键对应的套接字对象

                                        PrintWriter out = new PrintWriter(s.getOutputStream(), true);// 创建输出流对象

                                        out.println("MSG:" + info);// 发送信息

                                        out.flush();// 刷新输出缓冲区

                                    }

                                }

                            }

                        }

                    }

                }

            } catch (IOException e) {

                ta_info.append(socket + "已经退出。\n");

            }

        }

    }

   

    publicstaticvoid main(String args[]) {

      MyServer my=new MyServer();

        my.setVisible(true);

        my.createSocket();

    }

   

    /**

     * Create the frame

     */

    public MyServer() {

        super();

        addWindowListener(new WindowAdapter() {

            publicvoid windowIconified(final WindowEvent e) {

                setVisible(false);

            }

        });

        setTitle("服务器端");

        setBounds(100, 100, 385, 266);

       

        final JScrollPane scrollPane = new JScrollPane();

        getContentPane().add(scrollPane, BorderLayout.CENTER);

       

        ta_info = new JTextArea();

        scrollPane.setViewportView(ta_info);

    }       

    publicvoid showFrame(){

        this.setVisible(true);                                              // 显示窗体

        this.setState(Frame.NORMAL);

        this.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);

    }

}

客户端:

package Day20121209;

       import java.awt.*;

import java.awt.event.*;

import java.io.*;

import java.net.*;

import java.text.DateFormat;

import java.util.Date;

import java.util.Vector;

import javax.swing.*;

       publicclass Mycilent  {

              private JFrame jf;

           private JTextField tf_newUser;

           privateJList user_list;

           private JTextArea ta_info;

           private JTextField tf_send;

           private ObjectOutputStream out;// 声明输出流对象

           privateboolean loginFlag = false;// 为true时表示已经登录,为false时表示未登录

           private JButton save;

           publicstaticvoid main(String args[]) {

               EventQueue.invokeLater(new Runnable() {

                   publicvoid run() {

                       try {

                       Mycilent client=new Mycilent();

                          client.jf.setVisible(true);

                           client.createClientSocket();// 调用方法创建套接字对象

                       } catch (Exception e) {

                           e.printStackTrace();

                       }

                   }

               });

           }

          

           publicvoid createClientSocket() {

               try {

                   Socket socket = new Socket("127.0.0.1", 3000);// 创建套接字对象

                   out = new ObjectOutputStream(socket.getOutputStream());// 创建输出流对象

                   new ClientThread(socket).start();// 创建并启动线程对象

               } catch (UnknownHostException e) {

                   e.printStackTrace();

               } catch (IOException e) {

                   e.printStackTrace();

               }

           }

          

           class ClientThread extends Thread {

               Socket socket;

               public ClientThread(Socket socket) {

                   this.socket = socket;

               }

               publicvoid run() {

                   try {

                       BufferedReader in = new BufferedReader(new InputStreamReader(

                               socket.getInputStream()));// 创建输入流对象

                       DefaultComboBoxModel model = (DefaultComboBoxModel) user_list

                               .getModel();// 获得列表框的模型

                       while (true) {

                           String info = in.readLine().trim();// 读取信息

                           if (!info.startsWith("MSG:")) {// 接收到的不是消息

                               if (info.startsWith("退出:")) {// 接收到的是退出消息

                                   model.removeElement(info.substring(3));// 从用户列表中移除用户

                               } else {// 接收到的是登录用户

                                   boolean itemFlag = false;// 标记是否为列表框添加列表项,为true不添加,为false添加

                                   for (int i = 0; i < model.getSize(); i++) {// 对用户列表进行遍历

                                       if (info.equals((String) model.getElementAt(i))) {// 如果用户列表中存在该用户名

                                           itemFlag = true;// 设置为true,表示不添加到用户列表

                                           break;// 结束for循环

                                       }

                                   }

                                   if (!itemFlag) {

                                           model.addElement(info);// 将登录用户添加到用户列表

                                   }

                               }

                           } else {// 如果获得的是消息,则在文本域中显示接收到的消息

                               DateFormat df = DateFormat.getDateInstance();// 获得DateFormat实例

                               String dateString = df.format(new Date());         // 格式化为日期

                               df = DateFormat.getTimeInstance(DateFormat.MEDIUM);// 获得DateFormat实例

                               String timeString = df.format(new Date());         // 格式化为时间

                               String sendUser = info.substring(4,info.indexOf(":发送给:"));// 获得发送信息的用户

                               String receiveInfo = info.substring(info.indexOf(":的信息是:")+6);// 获得接收到的信息

                               ta_info.append("  "+sendUser + "    " +dateString+"  "+timeString+"\n  "+receiveInfo+"\n");// 在文本域中显示信息

                               ta_info.setSelectionStart(ta_info.getText().length()-1);// 设置选择起始位置

                               ta_info.setSelectionEnd(ta_info.getText().length());// 设置选择的结束位置

//        

                           }

                       }

                   } catch (IOException e) {

                       e.printStackTrace();

                   }

               }

           }

          

           privatevoid send() {

               if (!loginFlag) {

                   JOptionPane.showMessageDialog(null, "请先登录。");

                   return;// 如果用户没登录则返回

               }

               String sendUserName = tf_newUser.getText().trim();// 获得登录用户名

               String info = tf_send.getText();// 获得输入的发送信息

               if (info.equals("")) {

                   return;// 如果没输入信息则返回,即不发送

               }

               Vector<String> v = new Vector<String>();// 创建向量对象,用于存储发送的消息

               Object[] receiveUserNames = user_list.getSelectedValues();// 获得选择的用户数组

               if (receiveUserNames.length <= 0) {

                   return;// 如果没选择用户则返回

               }

               for (int i = 0; i < receiveUserNames.length; i++) {

                   String msg = sendUserName + ":发送给:" + (String) receiveUserNames[i]

                           + ":的信息是: " + info;// 定义发送的信息

                   v.add(msg);// 将信息添加到向量

               }

               try {

                   out.writeObject(v);// 将向量写入输出流,完成信息的发送

                   out.flush();// 刷新输出缓冲区

               } catch (IOException e) {

                   e.printStackTrace();

               }

               DateFormat df = DateFormat.getDateInstance();// 获得DateFormat实例

               String dateString = df.format(new Date());         // 格式化为日期

               df = DateFormat.getTimeInstance(DateFormat.MEDIUM);// 获得DateFormat实例

               String timeString = df.format(new Date());         // 格式化为时间

               String sendUser = tf_newUser.getText().trim();// 获得发送信息的用户

               String receiveInfo = tf_send.getText().trim();// 显示发送的信息

               ta_info.append("  "+sendUser + "    " +dateString+"  "+timeString+"\n  "+receiveInfo+"\n");// 在文本域中显示信息

               tf_send.setText(null);// 清空文本框

               ta_info.setSelectionStart(ta_info.getText().length()-1);// 设置选择的起始位置

               ta_info.setSelectionEnd(ta_info.getText().length());// 设置选择的结束位置

           }

          

           publicvoid Save(){//聊天记录保存

           File file=new File("D:\\qq.txt");//保存位置

           if(file.exists()){//判断文件是否存在

           FileOutputStream fo=null;//定义输出流

           String s=ta_info.getText()+"\n";//得到文本框内容

          

                            try {

                                   fo=new FileOutputStream("D:\\qq.txt",true);

                                   fo.write(s.getBytes());//写进文件

                            } catch (FileNotFoundException e) {

                                   // TODO Auto-generated catch block

                                   e.printStackTrace();

                            } catch (IOException e) {

                                   // TODO Auto-generated catch block

                                   e.printStackTrace();

                            }finally{

                                   try {

                                          fo.close();//关闭流

                                   } catch (IOException e) {

                                          // TODO Auto-generated catch block

                                          e.printStackTrace();

                                   }

                            }

           }else{

                   try {

                                   file.createNewFile();//创建文件

                            } catch (IOException e) {

                                   // TODO Auto-generated catch block

                                   e.printStackTrace();

                            }

           }

                 }

           /**

            * Create the frame

            */

           public Mycilent() {

               super();

               jf=new JFrame("客户端");

               save=new JButton("聊天记录");

               jf.setBounds(100, 100, 485, 388);

              

               final JPanel panel = new JPanel();

               jf.getContentPane().add(panel, BorderLayout.SOUTH);

              

               final JLabel label = new JLabel();

               label.setText("输入聊天内容:");

               panel.add(label);

              

               tf_send = new JTextField();

               tf_send.addActionListener(new ActionListener() {

                   publicvoid actionPerformed(final ActionEvent e) {

                       send();// 调用方法发送信息

                   }

               });

              

               tf_send.addKeyListener(new KeyListener() {

                           

                            @Override

                            publicvoid keyTyped(KeyEvent e) {

                                   // TODO Auto-generated method stub

                                   int n=e.getKeyCode();

                                   if(n==KeyEvent.VK_ENTER){

                                          send();

                                   }

                            }

                           

                            @Override

                            publicvoid keyReleased(KeyEvent e) {

                                   // TODO Auto-generated method stub

                                  

                            }

                           

                            @Override

                            publicvoid keyPressed(KeyEvent e) {

                                   // TODO Auto-generated method stub

                                  

                            }

                     });

              

               tf_send.setPreferredSize(new Dimension(180, 25));

               panel.add(tf_send);

              

               final JButton button = new JButton();

               button.addActionListener(new ActionListener() {

                   publicvoid actionPerformed(final ActionEvent e) {

                       send();// 调用方法发送信息

                   }

               });

               button.setText("发  送");

               panel.add(button);

               save.addActionListener(new ActionListener() {

                           

                            @Override

                            publicvoid actionPerformed(ActionEvent arg0) {

                                   // TODO Auto-generated method stub

                                   Save();//调用保存方法

                                          JDialog jd=new JDialog();//生成对话框

                                          jd.setLayout(new FlowLayout());

                                          JTextArea jt=new JTextArea(20,30);

                                          JScrollPane js=new JScrollPane(jt);

                                          jd.setTitle("聊天记录");

                                          jd.add(js);

                                          jd.pack();

                                          jd.setVisible(true);

                                          jd.setLocation(200, 300);

                                          BufferedReader br=null;

                                     try {

                                             br= new BufferedReader(new FileReader("d://qq.txt"));   //读入文件

                                              String line = "";  

                                              while((line=br.readLine()) != null) {  

                                                jt.append(line+"\n");//添加到文本域

                                              }

                                   } catch (FileNotFoundException e) {

                                          // TODO Auto-generated catch block

                                          e.printStackTrace();

                                   } catch (IOException e) {

                                          // TODO Auto-generated catch block

                                          e.printStackTrace();

                                   }   finally{

                                          try {

                                                 br.close();//关闭流

                                          } catch (IOException e) {

                                                 // TODO Auto-generated catch block

                                                 e.printStackTrace();

                                          }

                                   }

                            }

                     });

               panel.add(save);

               final JSplitPane splitPane = new JSplitPane();

               splitPane.setDividerLocation(100);

               jf.getContentPane().add(splitPane, BorderLayout.CENTER);

               

               final JScrollPane scrollPane = new JScrollPane();

               splitPane.setRightComponent(scrollPane);

              

               ta_info = new JTextArea();

               scrollPane.setViewportView(ta_info);

              

               final JScrollPane scrollPane_1 = new JScrollPane();

               splitPane.setLeftComponent(scrollPane_1);

              

               user_list = newJList();

               user_list.setModel(new DefaultComboBoxModel(new String[] { "" }));

               scrollPane_1.setViewportView(user_list);

              

               final JPanel panel_1 = new JPanel();

              jf. getContentPane().add(panel_1, BorderLayout.NORTH);

              

               final JLabel label_1 = new JLabel();

               label_1.setText("用户名称:");

               panel_1.add(label_1);

              

               tf_newUser = new JTextField();

               tf_newUser.setPreferredSize(new Dimension(140, 25));

               panel_1.add(tf_newUser);

              

               final JButton button_1 = new JButton();

               button_1.addActionListener(new ActionListener() {

                   publicvoid actionPerformed(final ActionEvent e) {

                       if (loginFlag) {// 已登录标记为true

                           JOptionPane.showMessageDialog(null, "在同一窗口只能登录一次。");

                           return;

                       }

                       String userName = tf_newUser.getText().trim();// 获得登录用户名

                       Vector v = newVector();// 定义向量,用于存储登录用户

                       v.add("用户:" + userName);// 添加登录用户

                       try {

                           out.writeObject(v);// 将用户向量发送到服务器

                           out.flush();// 刷新输出缓冲区

                       } catch (IOException ex) {

                           ex.printStackTrace();

                       }

                       tf_newUser.setEnabled(false);// 禁用用户文本框

                       loginFlag = true;// 将已登录标记设置为true

                   }

               });

               button_1.setText("登  录");

               panel_1.add(button_1);

               final JButton button_2 = new JButton();

               button_2.addActionListener(new ActionListener() {

                   publicvoid actionPerformed(final ActionEvent e) {

                       String exitUser = tf_newUser.getText().trim();

                       Vector v = newVector();

                       v.add("退出:" + exitUser);

                       try {

                           out.writeObject(v);

                           out.flush();// 刷新输出缓冲区

                       } catch (IOException ex) {

                           ex.printStackTrace();

                       }

                       System.exit(0);                                     // 退出系统

                   }

               });

               button_2.setText("退  出");

               panel_1.add(button_2);

         

           }

           publicvoid showFrame(){

           jf.setVisible(true);                                              // 显示窗体

            jf.setState(Frame.NORMAL);

               jf.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);

           }

       }

更多相关推荐:
java局域聊天室实践总结

河北科技师范学院JAVA程序设计课程设计个人实习总结实习类型课程设计实习单位指导教师所在院系信息技术系班级姓名学号一实习时间和地点时间20xx31720xx414地点F310F311二实习的内容我所开发的系统是...

java聊天室设计总结

JAVA聊天室程序设计总结大二第一学期末我们进行了为期两周的java实习这次的实习内容是设计一个多人聊天室在网络越来越发达的今天人们对网络的依赖越来越多越来越离不开网络由此而产生的聊天工具越来越多类似QQMSN...

java聊天室项目设计书

Java项目设计聊天室设计设计人XXX指导老师XXX设计时间20xx417到20xx424目录第一部分项目概况1项目说明42项目背景4第二部分项目计划1项目目标42项目范围43项目策略44项目开发周期45每项任...

java项目总结

DBHelp类packagecomxunpoitprodbimportjavasqlConnectionimportjavasqlDriverManagerimportjavasqlSQLExceptionim...

《Java程序设计基础》项目设计报告

Java程序设计基础项目设计报告题目求三角形面积的实现专业班级学号姓名完成时间成绩课程设计说明书论文第I页目录1设计的目的111设计的目的112内容要求12系统基本框架结构图23系统功能设计331系统主界面设计...

Java Me 小项目报告

手机应用程序开发JavaME项目报告学院信息科学与技术班级学号姓名主要功能屏幕上有一个小球上下弹动按左键向左移动按右键向右移送按上键减速按下键加速中间的确定键变大其他键改变颜色在红绿蓝色之间变化右软件可以暂停或...

java计算器项目课程设计报告(包涵源文件与类图)

计算机网络技术专业专业代码590102动态网站基础程序设计课程设计班级网站1101班学号20xx352220xx184220xx221520xx515320xx352820xx289320xx352320xx3...

Java雷电游戏项目报告模板

北京青年政治学院小学期达内JAVA课程项目报告项目题目专业班级学生姓名学生学号雷电游戏的设计与实现指导教师姓名目录一系统目标X二系统设计思路X三系统详细设计X四系统实现X五系统设计总结XX六参考文献XX1一系统...

Java EE项目开发实验报告

实验一Struts框架技术及应用一实验目的掌握Struts框架技术的原理及其在项目中的应用掌握MVC开发模式二实验内容创建一个用于本次和后续JavaEE项目的名为test的数据库并在数据库中创建一个名为user...

java个人记事本总结报告

计算机学院工程实践总结报告个人记事本小组序号组员姓名年级班级指导教师姓名提交日期目录12引言2项目需求分析及方案2212223243程序的基本功能2输入输出要求3测试数据3设计方案3项目概要设计4313233抽...

Java项目报告模版

Java程序设计项目报告班级姓名学号指导教师20xx年06月3日1选题概述题目javaXX应用程序简介通过本程序可以实现XX的基本功能程序是Frame类的子类使用GridLayout的布局方式对组件进行布局用P...

Java小项目报告

HUNANUNIVERSITYJava小项目报告题目:学生成绩管理系统学生姓名吕良学生学号***专业班级计算机科学与技术(3)班指导老师文佳宝完成日期20**.12.23Java小项目:学生成绩管理系统一、项目…

java聊天室项目总结(4篇)