请高手帮忙,看看这个程序,关于聊天室的

[复制链接]
查看11 | 回复9 | 2006-9-7 10:14:43 | 显示全部楼层 |阅读模式
下面是服务端代码,也是在网上找的。
不过运行有问题,我改了些,不过还是不行,请DX帮忙看看!
Server.java
import java.io.*;
import java.util.Vector;
import java.net.*;
public class Server extends ServerSocket {
private static int port = 8989;
private static Vector allSocket = new Vector();

public Server() throws IOException{
super(port);
}

public void startService() throws IOException{
try{

System.out.println("服务已经启动。。。");

while(true){

new SocketThread(accept()).start();

}
} catch (Exception e) {

e.printStackTrace();
} finally {

this.close();
}
}
class SocketThreadextends Thread {//implements Runnable {
Socket socket=null;
public SocketThread(Socket s) {

socket = s;
}
public void run() {

try {


ClientUser newClient = new ClientUser(1,socket.getInetAddress().getHostAddress(),socket.getPort());

//向客户端发送已有的所有用户连接

PrintWriter out = new PrintWriter(socket.getOutputStream(),true);

for(int i=0;i "+msg);

}

}

else if(msg.startsWith("QUIT")) {


System.out.println(newClient.getDescription()+" 退出聊天室");

allSocket.removeElement(socket);

//向其它用户重新发送退出信息

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

Socket s = (Socket)allSocket.elementAt(i);


out = new PrintWriter(s.getOutputStream(),true);

out.println("QUIT: "+newClient.getDescription());


}
//
if(in != null)
//
in.close();
//
if(out != null)
//
out.close();
//
if(socket != null)
//
socket.close();

//allSocket.remove(socket);

return;


}

}

}

}

catch(Exception e) {

e.printStackTrace();

}
}
}

public static void main(String[] args) {
try {

new Server().startService();
}
catch(IOException e) {

e.printStackTrace();
}
}

}


class ClientUser {
private int status;
private String ip;
private int port;
public ClientUser(int status,String ip,int port) {
setStatus(status);
setIP(ip);
setPort(port);
}
public void setStatus(int s) {
status = s;
}
public void setIP(String ip) {
this.ip = ip;
}
public void setPort(int port) {
this.port = port;
}
public int getStatus() {
return status;
}
public String getIP() {
return ip;
}
public int getPort() {
return port;
}
public String getStatusDesp() {
returnstatus!=0?"已连接":"断开";
}
public String getDescription() {
return ip+":"+port;//+"("+getStatusDesp()+")";
}
}
回复

使用道具 举报

千问 | 2006-9-7 10:14:43 | 显示全部楼层
接下来是客户端的代码,主要是这个类!
帮忙分析下,多个客户端连接后,莫个客户端断开连接后,登录的user信息list有时总为空呢?为什么啊?
Client.java
import java.awt.*;
import java.awt.event.*;
import javax.swing.*;
import java.io.*;
import java.util.*;
import java.net.*;
public class Client extends JFrame {
private JButton topButton = null;
private JList userList = null;
private JTextArea msgShowArea = null;
private JTextField msgInputField = null;
private JButton sendButton = null;
private JPanel topPanel = null;
private JPanel bottomPanel = null;
private String ipAddr = "localhost";
private int serverPort = 8989;
private boolean isConnected = false;
MsgRecvThread socketThread = null;
Socket client = null;
BufferedReader socketIn = null;
PrintWriter socketOut = null;
DataModel dm;
Vector users;
public Client(String title) {
super(title);
Container c = this.getContentPane();
c.setLayout(new BorderLayout());
topButton = new JButton("连接服务器");
//users = new Vector();
dm = new DataModel();
userList = new JList(dm);
userList.setSize(40, 400);
msgShowArea = new JTextArea(160, 80);
msgInputField = new JTextField(40);
sendButton = new JButton("发送");
topPanel = new JPanel(new FlowLayout(FlowLayout.CENTER));
topPanel.add(topButton);
c.add(topPanel, BorderLayout.NORTH);
c.add(new JScrollPane(userList), BorderLayout.WEST);
c.add(new JScrollPane(msgShowArea), BorderLayout.CENTER);
bottomPanel = new JPanel(new FlowLayout(FlowLayout.RIGHT));
bottomPanel.add(msgInputField);
bottomPanel.add(sendButton);
c.add(bottomPanel, BorderLayout.SOUTH);
this.setBounds(200, 200, 600, 400);
//this.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
this.addWindowListener(new WindowAdapter() {

public void windowClosing(WindowEvent e) {

stopConnect();

System.exit(0);

}
});
this.setVisible(true);
topButton.addActionListener(new ActionListener() {

public void actionPerformed(ActionEvent e) {

if (!isConnected)

startConnect();

else

stopConnect();

}
});
sendButton.addActionListener(new ActionListener() {

public void actionPerformed(ActionEvent e) {

if (isConnected)

sendMsg();

}
});
}
public static void main(String[] args) {
new Client("简易多人聊天室");
}
public void startConnect() {
try {

topButton.setEnabled(false);

client = new Socket(ipAddr, serverPort);

socketIn = new BufferedReader(new InputStreamReader(client.getInputStream()));

socketOut = new PrintWriter(client.getOutputStream(), true);

msgShowArea.append("--- 连接服务器成功 --- \n");

topButton.setText("断开连接");

topButton.setEnabled(true);

isConnected = true;

//(new Thread(new MsgRecvThread())).start();

socketThread = new MsgRecvThread();

socketThread.start();
} catch (IOException e) {

msgShowArea.append("--- 连接服务器失败! --- \n");

isConnected = false;

topButton.setText("连接服务器");

topButton.setEnabled(true);
}
}
public void stopConnect() {
try {

//socketThread.stop=true;

if (socketOut != null) {

socketOut.println("QUIT");

socketOut.close();

isConnected = false;

topButton.setText("连接服务器");

topButton.setEnabled(true);

//users = new Vector();

//
for(int i=0;i<dm.getSize();i++){

//
dm.removeIndex(i);

//
}

dm.clearAll();

userList.updateUI();

msgShowArea.append(" --- 与服务器的连接已断开 --- \n");

}

socketThread.stop = true;

//
if (socketIn != null)

//
socketIn.close();

//
if (client != null)

//
client.close();
} catch (Exception e) {

msgShowArea.append(" ---操作失败! --- \n");
}
}
public void sendMsg() {
String msg = msgInputField.getText();
try {

socketOut.println("MESG: " + msg);

msgShowArea.append(" --- 信息已发出! --- \n");
} catch (Exception e) {

msgShowArea.append(" --- 发送失败! ---\n");
}
}
class MsgRecvThread extends Thread {
boolean stop = false;
public void run() {

try {

String rcvStr = "";

while (true) {//!(rcvStr = socketIn.readLine()).equals("")

if (stop) {

if (socketIn != null)

socketIn.close();

if (client != null)

client.close();

return;

}

rcvStr = socketIn.readLine();

if (rcvStr.startsWith("USER: ")) {

System.out.println("好友上线" + rcvStr.substring("USER: ".length()));

dm.addData(rcvStr.substring("USER: ".length()));

userList.updateUI();

//Client.super.repaint();

} else if (rcvStr.startsWith("MESG: ")) {

msgShowArea.append(rcvStr.substring("MESG: ".length()) + "\n");

} else if (rcvStr.startsWith("QUIT: ")) {

System.out.println("好友下线" + rcvStr.substring("QUIT: ".length()));

dm.removeData(rcvStr.substring("QUIT: ".length()));

userList.updateUI();

msgShowArea.append(rcvStr.substring("QUIT: ".length()) + "退出聊天\n");

}

//rcvStr = "";

}

} catch (Exception e) {

e.printStackTrace();

}
}
}
}
class DataModel extends AbstractListModel {
private Vector data = new Vector();
//public DataModel(Object[] listData) {
public DataModel() {
//data = new Vector();
//for (int i = 0; i < listData.length; i++) {
//
data.add(listData);
//}
}
public void removeData(Object o) {
data.remove(o);
}
public void clearAll() {
data.clear();
}
public void addData(Object o) {
data.add(o);
}
public void removeIndex(int index) {
data.remove(index);
}
public int getSize() {
return data.size();
}
public Object getElementAt(int index) {
return data.get(index);
}
}
[ 本帖最后由 hanjs 于 2008-1-24 19:33 编辑 ]
回复

使用道具 举报

千问 | 2006-9-7 10:14:43 | 显示全部楼层
下面是程序运行时的界面
[ 本帖最后由 hanjs 于 2008-1-24 19:37 编辑 ]
回复

使用道具 举报

千问 | 2006-9-7 10:14:43 | 显示全部楼层
理想的状态下应该是这样的!
[ 本帖最后由 hanjs 于 2008-1-24 19:39 编辑 ]
回复

使用道具 举报

千问 | 2006-9-7 10:14:43 | 显示全部楼层
up

大家帮忙看看啊,这个问题困扰我一天了,小弟在此多谢了!
回复

使用道具 举报

千问 | 2006-9-7 10:14:43 | 显示全部楼层
晕,弄java的真的没有数据库的多啊?
论坛也没有人给答疑


回复

使用道具 举报

千问 | 2006-9-7 10:14:43 | 显示全部楼层
你是指第一个登录的客户端没有看到后登录的用户信息?
回复

使用道具 举报

千问 | 2006-9-7 10:14:43 | 显示全部楼层
对啊,按理都应该显示的啊!
反复连接-断开-连接-断开总是显示不对!
回复

使用道具 举报

千问 | 2006-9-7 10:14:43 | 显示全部楼层
这种管理应该是服务端在接收用户上下线时有个统计的,然后
1。服务端开放一个接口,客户端隔一段时间去查询一下当前的列表,然后刷新显示
2。服务端向所有在线的用户发送通知事件,客户端根据用户名和上下线标志刷新列表
或者按你目前的流程分析一下是哪里出了问题,看看哪里维护这个列表的
回复

使用道具 举报

千问 | 2006-9-7 10:14:43 | 显示全部楼层
这个列表是client端维护的。
当有用户上线,server会将新用户信息发给已连接的客户端,在将所有上线的用户发给新登录的用户端
当有用户下线,也会发给客户端进行刷新,可是并不是都能刷新成功呢?有时会出现list列表中为空的情况,看上面的图片
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

主题

0

回帖

4882万

积分

论坛元老

Rank: 8Rank: 8

积分
48824836
热门排行