⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 chessserver.java

📁 Eclipse 编程技术与实例,讲解了Eclipse编辑器的使用方法
💻 JAVA
📖 第 1 页 / 共 2 页
字号:

	}
   /**
    * 发送公共消息的函数,将消息向每个客户端都发送一份
    */
	public void publicTalk(String publicTalkMessage) {

		synchronized (clientDataHash) {
			for (Enumeration enu = clientDataHash.elements(); enu
					.hasMoreElements();) {
				DataOutputStream outData = (DataOutputStream) enu.nextElement();
				try {
					outData.writeUTF(publicTalkMessage);
				} catch (IOException es) {
					es.printStackTrace();
				}
			}
		}

	}
  /**
   * 选择对象发送消息,参数peerTalk为发送的用户名,后面的参数为发送的消息
   */
	public boolean peerTalk(String peerTalk, String talkMessage) {
        //
		for (Enumeration enu = clientDataHash.keys(); enu.hasMoreElements();) {
			Socket userClient = (Socket) enu.nextElement();
           //找到发送消息的对象,获取它的输出流以发送消息
			if (peerTalk.equals((String) clientNameHash.get(userClient))
					&& !peerTalk.equals((String) clientNameHash
							.get(clientSocket))) {
				synchronized (clientDataHash) {
					DataOutputStream peerOutData = (DataOutputStream) clientDataHash
							.get(userClient);
					try {
						peerOutData.writeUTF(talkMessage);
					} catch (IOException es) {
						es.printStackTrace();
					}
				}
				Feedback(talkMessage);
				return (false);
			} 
			//如果是发给自己的,直接回馈
			else if (peerTalk.equals((String) clientNameHash
					.get(clientSocket))) {
				Feedback(talkMessage);
				return (false);
			}
		}

		return (true);

	}
   /**
    * 此函数也用于选择发送消息,但不能发送给自己。
    */
	public boolean chessPeerTalk(String chessPeerTalk, String chessTalkMessage) {

		for (Enumeration enu = clientDataHash.keys(); enu.hasMoreElements();) {
			Socket userClient = (Socket) enu.nextElement();

			if (chessPeerTalk.equals((String) clientNameHash.get(userClient))
					&& !chessPeerTalk.equals((String) clientNameHash
							.get(clientSocket))) {
				synchronized (clientDataHash) {
					DataOutputStream peerOutData = (DataOutputStream) clientDataHash
							.get(userClient);
					try {
						peerOutData.writeUTF(chessTalkMessage);
					} catch (IOException es) {
						es.printStackTrace();
					}
				}
				return (false);
			}
		}
		return (true);
	}
  /**
   * 用于处理消息回馈的函数
   */
	public void Feedback(String feedbackString) {
		synchronized (clientDataHash) {
			DataOutputStream outData = (DataOutputStream) clientDataHash
					.get(clientSocket);
			try {
				outData.writeUTF(feedbackString);
			} catch (Exception eb) {
				eb.printStackTrace();
			}
		}

	}
   /**
    * 获取用户列表的函数,此函数读取clientNameHash获取用户列表,
    * 然后将其保存在一个字符串userList中。
    */
	public String getUserList() {
		String userList = "/userlist";

		for (Enumeration enu = clientNameHash.elements(); enu.hasMoreElements();) {
			userList = userList + " " + (String) enu.nextElement();
		}
		return userList;
	}
    /**
     * 给出HashTable和值对象,获取相对应得键值的函数。
     */
	public Object getHashKey(Hashtable targetHash, Object hashValue) {
		Object hashKey;
		for (Enumeration enu = targetHash.keys(); enu.hasMoreElements();) {
			hashKey = (Object) enu.nextElement();
			if (hashValue.equals((Object) targetHash.get(hashKey)))
				return (hashKey);
		}
		return (null);
	}

	public void firstCome() {
		publicTalk(getUserList());
		Feedback("/yourname " + (String) clientNameHash.get(clientSocket));
		Feedback("Java五子棋聊天客户端");
		Feedback("/changename <你的名字> --更改名字");
		Feedback("/list --更新用户列表");
		Feedback("/<用户名> <要说的话> --私聊");
		Feedback("注意:用命令的时候,先把谈话的对象定为所有人");
	}
    /**
     * 用于和客户端断开的函数。
     */
	public void clientClose() {
		server.messageBoard.append("用户断开:" + clientSocket + "\n");
		//如果是游戏客户端主机
		synchronized (chessPeerHash) {
			if (chessPeerHash.containsKey(clientNameHash.get(clientSocket))) {
				chessPeerHash.remove((String) clientNameHash.get(clientSocket));
			}
			if (chessPeerHash.containsValue(clientNameHash.get(clientSocket))) {
				chessPeerHash.put((String) getHashKey(chessPeerHash,
						(String) clientNameHash.get(clientSocket)),
						"tobeclosed");
			}
		}
		//将保留的HashTable里的数据清除
		synchronized (clientDataHash) {
			clientDataHash.remove(clientSocket);
		}
		synchronized (clientNameHash) {
			clientNameHash.remove(clientSocket);
		}
		publicTalk(getUserList());
		//计算当前连接数,并显示在状态框中
		server.statusLabel.setText("当前连接数:" + clientDataHash.size());
		try {
			clientSocket.close();
		} catch (IOException exx) {
		}

		isClientClosed = true;

	}

	public void run() {
		DataInputStream inData;
		synchronized (clientDataHash) {
			server.statusLabel.setText("当前连接数:" + clientDataHash.size());
		}
		try {
			inData = new DataInputStream(clientSocket.getInputStream());
			firstCome();
			while (true) {
				String message = inData.readUTF();
				messageTransfer(message);
			}
		} catch (IOException esx) {
		} finally {
			if (!isClientClosed) {
				clientClose();
			}
		}
	}

}

/**
 * @author wufenghanren
 * 服务器端框架类
 */
public class chessServer extends Frame implements ActionListener {

	Button messageClearButton = new Button("清除显示");

	Button serverStatusButton = new Button("服务器状态");

	Button serverOffButton = new Button("关闭服务器");

	Panel buttonPanel = new Panel();

	MessageServerPanel server = new MessageServerPanel();

	ServerSocket serverSocket;

	Hashtable clientDataHash = new Hashtable(50);

	Hashtable clientNameHash = new Hashtable(50);

	Hashtable chessPeerHash = new Hashtable(50);
    /**
     *框架类的构造函数 
     */
	chessServer() {
		super("Java五子棋服务器");
		setBackground(new Color(204,204,204));

		buttonPanel.setLayout(new FlowLayout());
		messageClearButton.setSize(60, 25);
		buttonPanel.add(messageClearButton);
		messageClearButton.addActionListener(this);
		serverStatusButton.setSize(75, 25);
		buttonPanel.add(serverStatusButton);
		serverStatusButton.addActionListener(this);
		serverOffButton.setSize(75, 25);
		buttonPanel.add(serverOffButton);
		serverOffButton.addActionListener(this);

		add(server, BorderLayout.CENTER);
		add(buttonPanel, BorderLayout.SOUTH);
        //退出窗口的监听器
		addWindowListener(new WindowAdapter() {
			public void windowClosing(WindowEvent e) {
				System.exit(0);
			}
		});
		setVisible(true);
		setSize(400, 450);
		setResizable(false);
		validate();
		try {
			makeMessageServer(4331, server);
		} catch (Exception e) {
			System.out.println("e");
		}
	}
    /**
     * 初始化消息服务器的类
     */
	public void makeMessageServer(int port, MessageServerPanel server)
			throws IOException {
		Socket clientSocket;
		long clientAccessNumber = 1;
		this.server = server;

		try {
			//输出服务器的启动信息
			serverSocket = new ServerSocket(port);
			server.messageBoard.setText("服务器开始于:"
					+ serverSocket.getInetAddress().getLocalHost() + ":"
					+ serverSocket.getLocalPort() + "\n");

			while (true) {
				clientSocket = serverSocket.accept();
				server.messageBoard.append("用户连接:" + clientSocket + "\n");

				DataOutputStream outData = new DataOutputStream(clientSocket
						.getOutputStream());

				clientDataHash.put(clientSocket, outData);
				clientNameHash
						.put(clientSocket, ("新来客" + clientAccessNumber++));

				ServerThread thread = new ServerThread(clientSocket,
						clientDataHash, clientNameHash, chessPeerHash, server);

				thread.start();
			}
		} catch (IOException ex) {
			System.out.println("已经有服务器在运行. \n");
		}

	}
 /**
  * 按钮的事件监听器,响应按钮点击事件
  */
	public void actionPerformed(ActionEvent e) {
		if (e.getSource() == messageClearButton) {
			server.messageBoard.setText("");
		}
		//当“服务器状态”按钮点击时,显示服务器状态
		if (e.getSource() == serverStatusButton) {
			try {
				server.messageBoard.append("服务器信息:"
						+ serverSocket.getInetAddress().getLocalHost() + ":"
						+ serverSocket.getLocalPort() + "\n");
			} catch (Exception ee) {
				System.out
						.println("serverSocket.getInetAddress().getLocalHost() error \n");
			}
		}
		if (e.getSource() == serverOffButton) {
			System.exit(0);
		}
	}

	public static void main(String args[]) {
		chessServer chessServer = new chessServer();
	}
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -