java课程设计
简介
利用socket实现了网络通信,模拟了一个低配版的qq游戏大厅。
具体地说,实现的功能有
上线下线
群发消息
私聊消息
五子棋对战
效果图片
文件结构
核心代码如下
1 客户端部分
CharClient.java
package com.nsd.charClient;
import java.awt.BorderLayout;
import java.awt.Graphics;
import java.awt.Image;
import java.awt.TextArea;
import java.awt.TextField;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.MouseEvent;
import java.awt.event.MouseListener;
import java.io.BufferedReader;
import java.io.File;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.PrintWriter;
import java.net.Socket;
import java.net.UnknownHostException;
import javax.imageio.ImageIO;
import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JPanel;
import net.sf.json.JSONObject;
public class CharClient extends JFrame {
private Socket socket = null;
private JButton btSend = new JButton("Send");
private JButton btPrivateSend = new JButton("PrivateSend");
private JButton btLogOut = new JButton("LogOut");
private JButton btShowAllUsers = new JButton("ShowAllUsers(execptSelf)");
private TextArea txtMessageShow = new TextArea(30, 26);
private TextField txtMessage = new TextField(40);
private TextField txtPrivateTarget = new TextField(40);
private TextField txtPrivateMessage = new TextField(40);
private JButton btSolo = new JButton("Solo");
private TextField opponentID = new TextField(40);
public final int maxSize = 10 + 5;
public final int n = 10;
public int chessBoard[][];
private boolean inSolo = false;
private boolean canMove = false;
public class MyPanel extends JPanel implements MouseListener {
Image image = null;
Image image1 = null;
Image image2 = null;
public MyPanel() {
AddListener();
}
private void AddListener() {
this.setFocusable(true);
this.addMouseListener(this);
}
public void paint(Graphics g) {
super.paint(g);
try {
image = ImageIO.read(new File(
"D:\\信息竞赛\\cpp\\vijoslong\\java\\charClient\\src\\com\\nsd\\charClient\\chessBoard.jpg"));
image1 = ImageIO.read(
new File("D:\\信息竞赛\\cpp\\vijoslong\\java\\charClient\\src\\com\\nsd\\charClient\\black.jpg"));
image2 = ImageIO.read(
new File("D:\\信息竞赛\\cpp\\vijoslong\\java\\charClient\\src\\com\\nsd\\charClient\\white.jpg"));
g.drawImage(image, 0, 0, null);
for (int i = 1; i <= n; i++) {
for (int j = 1; j <= n; j++) {
if (chessBoard[i][j] == 0)
continue;
int x = 30 + (i - 1) * 44;
int y = 30 + (j - 1) * 44;
if (chessBoard[i][j] == 1) {
g.drawImage(image1, x, y, null);
}
if (chessBoard[i][j] == 2) {
g.drawImage(image2, x, y, null);
}
}
}
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
@Override
public void mouseClicked(MouseEvent e) {
// TODO Auto-generated method stub
if (canMove == false) {
// if(inSolo == true) txtMessageShow.setText(txtMessageShow.getText() + "\n" + "【尚未轮到你落子】");
return;
}
int x = e.getX();
int y = e.getY();
SendMoveMessage(x, y);
}
@Override
public void mousePressed(MouseEvent e) {
// TODO Auto-generated method stub
}
@Override
public void mouseReleased(MouseEvent e) {
// TODO Auto-generated method stub
}
@Override
public void mouseEntered(MouseEvent e) {
// TODO Auto-generated method stub
}
@Override
public void mouseExited(MouseEvent e) {
// TODO Auto-generated method stub
}
}
public static void main(String[] args) {
// TODO Auto-generated method stub
new CharClient();
}
public CharClient() {
chessBoard = new int[maxSize][maxSize];
for (int i = 1; i <= n; i++) {
for (int j = 1; j <= n; j++) {
chessBoard[i][j] = 0;
}
}
// init 设置框架,设置容器,增加监听,增加菜单,增加业务处理,增加线程
/*
* setFrame(); setPanel();
*/
setSize(730, 750);
setTitle("QQ聊天室");
setLocationRelativeTo(null);
// 框架分为上下二个部分,
this.setLayout(new BorderLayout(8, 8));
this.add(txtMessageShow, BorderLayout.WEST);
this.add(setButtonPanel(), BorderLayout.NORTH);
this.add(setSoloPanel(), BorderLayout.CENTER);
this.add(setButtonPanel2(), BorderLayout.SOUTH);
//
btSend.addActionListener(new ActionListener() {
@Override
public void actionPerformed(ActionEvent arg0) {
// TODO Auto-generated method stub
SendMessage();
}
});
btPrivateSend.addActionListener(new ActionListener() {
@Override
public void actionPerformed(ActionEvent arg0) {
// TODO Auto-generated method stub
SendPrivateMessage();
}
});
btLogOut.addActionListener(new ActionListener() {
@Override
public void actionPerformed(ActionEvent e) {
// TODO Auto-generated method stub
LogOut();
}
});
btShowAllUsers.addActionListener(new ActionListener() {
@Override
public void actionPerformed(ActionEvent e) {
// TODO Auto-generated method stub
ShowAllUsers();
}
});
btSolo.addActionListener(new ActionListener() {
@Override
public void actionPerformed(ActionEvent e) {
// TODO Auto-generated method stub
if (inSolo == false)
Solo();
}
});
// addMenu();
addSocket();
setVisible(true);
}
private void Solo() {
String opponent = opponentID.getText().trim();
try {
// 获取客户端和服务器相连的socket,选择输出端口,转为字符输入流
PrintWriter out = new PrintWriter(socket.getOutputStream());
// 依照协议,设置json数据
JSONObject jo = new JSONObject();
jo.put("state", "solo");
jo.put("targetID", opponent);
// System.out.println(jo.toString()); // {"state":"private","targetID":"WWW"}
// 发送到服务器端 println
out.println(jo.toString());
out.flush();
inSolo = true;
canMove = true;
// out.close();
} catch (Exception e) {
e.printStackTrace();
}
}
private void SendPrivateMessage() {
String target = txtPrivateTarget.getText().trim();
String message = txtPrivateMessage.getText().trim();
try {
// 获取客户端和服务器相连的socket,选择输出端口,转为字符输入流
PrintWriter out = new PrintWriter(socket.getOutputStream());
// 依照协议,设置json数据
JSONObject jo = new JSONObject();
jo.put("state", "private");
jo.put("targetID", target);
jo.put("Note", message);
// System.out.println(jo.toString()); // {"state":"private","targetID":","Note":"wwwwww"}
// 发送到服务器端 println
out.println(jo.toString());
out.flush();
// out.close();
} catch (Exception e) {
e.printStackTrace();
}
}
private void SendMessage() {
String message = txtMessage.getText().trim();
try {
// 获取客户端和服务器相连的socket,选择输出端口,转为字符输入流
PrintWriter out = new PrintWriter(socket.getOutputStream());
// 依照协议,设置json数据
JSONObject jo = new JSONObject();
jo.put("state", "public");
jo.put("Note", message);
// System.out.println(jo.toString()); // {"state":"public","Note":"wwwwww"}
// 发送到服务器端 println
out.println(jo.toString());
out.flush();
// out.close();
} catch (Exception e) {
e.printStackTrace();
}
}
private void LogOut() {
// TODO Auto-generated method stub
String message = txtMessage.getText().trim();
try {
// 获取客户端和服务器相连的socket,选择输出端口,转为字符输入流
PrintWriter out = new PrintWriter(socket.getOutputStream());
// 依照协议,设置json数据
JSONObject jo = new JSONObject();
jo.put("state", "leave");
jo.put("Note", message);
// System.out.println(jo.toString()); // {"state":"leave","Note":"wwwwww"}
// 发送到服务器端 println
out.println(jo.toString());
out.flush();
System.exit(0);
// out.close();
} catch (Exception e) {
e.printStackTrace();
}
}
private void ShowAllUsers() {
// TODO Auto-generated method stub
String message = txtMessage.getText().trim();
try {
// 获取客户端和服务器相连的socket,选择输出端口,转为字符输入流
PrintWriter out = new PrintWriter(socket.getOutputStream());
// 依照协议,设置json数据
JSONObject jo = new JSONObject();
jo.put("state", "show");
jo.put("Note", message);
// System.out.println(jo.toString()); // {"state":"show","Note":"wwwwww"}
// 发送到服务器端 println
out.println(jo.toString());
out.flush();
// out.close();
} catch (Exception e) {
e.printStackTrace();
}
}
private void SendMoveMessage(int x, int y) {
// 棋盘左上角第一个格子(32,32)
// 格子间距40
// System.out.println(""+x+" "+y);
int X = (y - 30) / 44 + 1; // 换算到棋盘坐标 xy颠倒
int Y = (x - 30) / 44 + 1;
try {
// 获取客户端和服务器相连的socket,选择输出端口,转为字符输入流
PrintWriter out = new PrintWriter(socket.getOutputStream());
// 依照协议,设置json数据
JSONObject jo = new JSONObject();
jo.put("state", "move");
jo.put("x", X + "");
jo.put("y", Y + "");
// System.out.println(jo.toString()); // {"state":"public","x":"ww","y":"ww"}
// 发送到服务器端 println
out.println(jo.toString());
out.flush();
// out.close();
} catch (Exception e) {
e.printStackTrace();
}
}
private void addSocket() {
try {
socket = new Socket("localhost", 30088);
// System.out.println(socket);
// Socket[addr=localhost/127.0.0.1,port=30088,localport=64332]
this.setTitle("[" + socket.getLocalPort() + "]");
//
// 创建线程,用于客户端循环等待接受服务器的数据
new Thread(new ClientRunnable(socket)).start();
// st.getInputStream()
} catch (Exception e) {
e.printStackTrace();
}
}
private JPanel setButtonPanel() {
JPanel jp = new JPanel(new BorderLayout(4, 4));
// 群发
JPanel jp1 = new JPanel(new BorderLayout(4, 4));
jp1.add(new JLabel("Message"), BorderLayout.WEST);
jp1.add(txtMessage, BorderLayout.CENTER);
jp1.add(btSend, BorderLayout.EAST);
jp.add(jp1, BorderLayout.NORTH);
// JPanel jp2 = new JPanel(new BorderLayout(4, 4));
jp.add(new JLabel("id"), BorderLayout.WEST);
jp.add(txtPrivateTarget, BorderLayout.EAST);
JPanel jp3 = new JPanel(new BorderLayout(4, 4));
jp3.add(new JLabel("Message"), BorderLayout.WEST);
jp3.add(txtPrivateMessage, BorderLayout.CENTER);
jp3.add(btPrivateSend, BorderLayout.EAST);
// jp3.add(jp2, BorderLayout.NORTH);
jp.add(jp3, BorderLayout.SOUTH);
return jp;
}
private JPanel setButtonPanel2() {
JPanel jp = new JPanel(new BorderLayout(4, 4));
jp.add(btShowAllUsers, BorderLayout.NORTH);
jp.add(new JLabel("opponentID"), BorderLayout.WEST);
jp.add(opponentID, BorderLayout.CENTER);
jp.add(btSolo, BorderLayout.EAST);
jp.add(btLogOut, BorderLayout.SOUTH);
return jp;
}
private MyPanel setSoloPanel() { // 创建棋盘画布 在棋盘画布上的点击会向服务器发送move信息
MyPanel jp = new MyPanel();
return jp;
}
class ClientRunnable implements Runnable {
private BufferedReader br = null;
public ClientRunnable(Socket socket) throws IOException {
// 从socket获取输入流,再强转为BufferedReader流
// this.br = br;
br = new BufferedReader(new InputStreamReader(socket.getInputStream()));
}
@Override
public void run() {
// TODO Auto-generated method stub
try {
while (true) {
// 缓冲字符流,readLine
String str = br.readLine();
// str的解析。
int res = analyseStr(str);
if (res == 0)
txtMessageShow.setText(txtMessageShow.getText() + "\n" + str);
// RunStep();
}
} catch (Exception e) {
e.printStackTrace();
}
}
}
private int analyseStr(String s) {
if (s == null)
return 1;
if (s.charAt(0) == '%') {
inSolo = false; // 比赛结束
for (int i = 1; i <= n; i++) {
for (int j = 1; j <= n; j++) {
chessBoard[i][j] = 0;
}
}
repaint();
return 1;
}
if (s.charAt(0) == '&') {
// System.out.println("s'len is "+s.length());
for (int i = 1; i <= n; i++) {
for (int j = 1; j <= n; j++) {
chessBoard[j][i] = s.charAt((i - 1) * n + j - 1 + 1) - '0'; // 横纵坐标需要颠倒
// 最后的 +1 是因为要考虑&
}
}
if (canMove == false)
canMove = true; // 交换移动权
else
canMove = false;
repaint();
return 1;
}
return 0;
}
}
GomokuBoard.java
package com.nsd.charServer;
public class GomokuBoard {
public final int maxSize = 10 + 5;
public final int n = 10;
public int p1, p2;
public int moveFlag, drawFlag, winFlag;
public int chessBoard[][];
GomokuBoard(int _p1, int _p2) {
p1 = _p1;
p2 = _p2;
moveFlag = 1;
drawFlag = 0;
winFlag = 0;
chessBoard = new int[maxSize][maxSize];
for (int i = 1; i <= n; i++) {
for (int j = 1; j <= n; j++) {
chessBoard[i][j] = 0;
}
}
}
public void show() {
for (int i = 1; i <= n; i++) {
for (int j = 1; j <= n; j++) {
System.out.print(chessBoard[i][j]);
}
System.out.println();
}
}
public int checkEnd() {
int drawFlag = 1, winFlag = 0; // 平局 或者 当前moveFlag者获胜
for (int i = 1; i <= n; i++) {
if (drawFlag == 0)
break;
for (int j = 1; j <= n; j++) {
if (chessBoard[i][j] == 0) { // 有空位 不算平局
drawFlag = 0;
break;
}
}
}
for (int i = 1; i <= n; i++) {
if (winFlag == 1)
break;
for (int j = 1; j <= n; j++) { // 枚举中心点(i,j)
if (chessBoard[i][j] != moveFlag)
continue;
// 竖
if (i >= 3 && i <= n - 2) {
if (chessBoard[i - 1][j] == moveFlag && chessBoard[i - 2][j] == moveFlag
&& chessBoard[i + 1][j] == moveFlag && chessBoard[i + 2][j] == moveFlag) {
winFlag = 1;
break;
}
}
// 横
if (j >= 3 && j <= n - 2) {
if (chessBoard[i][j - 1] == moveFlag && chessBoard[i][j - 2] == moveFlag
&& chessBoard[i][j + 1] == moveFlag && chessBoard[i][j + 2] == moveFlag) {
winFlag = 1;
break;
}
}
// 斜
if (i >= 3 && i <= n - 2 && j >= 3 && j <= n - 2) {
if (chessBoard[i - 1][j - 1] == moveFlag && chessBoard[i - 2][j - 2] == moveFlag
&& chessBoard[i + 1][j + 1] == moveFlag && chessBoard[i + 2][j + 2] == moveFlag) {
winFlag = 1;
break;
}
if (chessBoard[i + 1][j - 1] == moveFlag && chessBoard[i + 2][j - 2] == moveFlag
&& chessBoard[i - 1][j + 1] == moveFlag && chessBoard[i - 2][j + 2] == moveFlag) {
winFlag = 1;
break;
}
}
}
}
if (drawFlag == 1 || winFlag == 1)
return 1;
return 0;
}
}
2 服务器代码
CharServer.java
package com.nsd.charServer;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.OutputStream;
import java.io.PrintWriter;
import java.net.ServerSocket;
import java.net.Socket;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import javax.swing.JOptionPane;
import net.sf.json.JSONObject;
import com.google.gson.JsonObject;
public class CharServer {
private List<Socket> lstSocket = new ArrayList<>();
private List<GomokuBoard> lstSoloTables = new ArrayList<>();
public static void main(String[] args) {
// TODO Auto-generated method stub
new CharServer();
}
// alt+/
public CharServer() {
// init
try {
// 创建一个30088端口的服务器
// 终止服务器进程方法:cmd中输入netstat -p tcp -ano | findstr :30088
// 找到对应的pid(最后一列数),使用任务管理器结束任务
ServerSocket ss = new ServerSocket(30088);
// 创建线程,用于不断循环等待客户端上线,
new Thread(new SocketAcceptThread(ss)).start();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
class SocketAcceptThread implements Runnable {
private ServerSocket serverSocket = null;
public SocketAcceptThread() {
// TODO Auto-generated constructor stub
}
public SocketAcceptThread(ServerSocket ss) {
this.serverSocket = ss;
}
@Override
public void run() {
// TODO Auto-generated method stub
while (true) {
try {
// accept是阻塞的过程,有客户上线,才能往下执行。
Socket st = serverSocket.accept();
// 将和客户端连接的Socket对象st保存。
lstSocket.add(st);
// 服务器端将这个用户信息获取,用该用户的端口号作为信息。
String strPort = "" + st.getPort();
System.out.println("Server: " + strPort);
System.out.println("Server: " + st);
// 服务器端将这个用户发布在群里,告知大家,该用户上线。
// SendAllUser(str, "up");
SendWelcomeUser(strPort);
// 当前的 Socket对象 需要接受对应这个对象客户端的数据,不断的接受数据
new ServerClientThread(st).start();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
}
class ServerClientThread extends Thread {
// 缓冲输入字符流
private BufferedReader br = null;
private Socket socket = null;
private boolean exit = false;
public ServerClientThread(Socket st) throws IOException {
// TODO Auto-generated constructor stub
socket = st;
InputStream is = st.getInputStream();
// 缓冲输入字符流 <= InputStream
br = new BufferedReader(new InputStreamReader(is));
}
@Override
public void run() {
// TODO Auto-generated method stub
try {
while (!exit) {
// io , readline 阻塞状态,缓冲输入字符流
String str = br.readLine();
// 对str进行解析, {"state":"public","Note":"wwwwww"}
DoClient(str, socket.getPort());
}
} catch (Exception e) {
e.printStackTrace();
}
}
}
private void DoClient(String str, int port) throws IOException {
// 对客户端的str数据进行解析
JSONObject jo = JSONObject.fromObject(str);
String state = jo.get("state").toString();
switch (state) {
case "public":
// 群发的消息
for (int i = 0; i < lstSocket.size(); i++) {
Socket st = lstSocket.get(i);
OutputStream os = st.getOutputStream();
PrintWriter out = new PrintWriter(os);
// 状态,数据
// 服务器端发送到客户端的数据,仅是一个字符串。下行消息
out.println("【" + port + "】" + jo.get("Note").toString());
out.flush();
}
break;
case "private":
// 私发的消息
int flag = -1;
int sender = -1;
String targetID = jo.get("targetID").toString();
int targetIDInt = Integer.parseInt(targetID);
for (int i = 0; i < lstSocket.size(); i++) {
Socket st = lstSocket.get(i);
if (st.getPort() == port)
sender = i;
// System.out.println("st.getPort():"+st.getPort());
// System.out.println("targetID:"+targetID);
// if(st.getPort() + "" != targetID) continue;
if (targetIDInt != st.getPort())
continue;
// System.out.println("success");
flag = i;
OutputStream os = st.getOutputStream();
PrintWriter out = new PrintWriter(os);
// 状态,数据
// 服务器端发送到客户端的数据,仅是一个字符串。下行消息
out.println("【" + port + "】私聊你的消息:" + jo.get("Note").toString());
out.flush();
}
if (flag == -1) {
Socket st = lstSocket.get(sender);
OutputStream os = st.getOutputStream();
PrintWriter out = new PrintWriter(os);
out.println("【" + targetID + "】不存在或已下线");
out.flush();
}
break;
case "leave":
// 下线消息
for (int i = 0; i < lstSocket.size(); i++) {
Socket st = lstSocket.get(i);
OutputStream os = st.getOutputStream();
PrintWriter out = new PrintWriter(os);
// 状态,数据
/*
* JSONObject jo = new JSONObject(); jo.put("state", state); jo.put("Name",
* str); out.println(jo.toString());
*/
out.println("【" + port + "】用户已离线");
out.flush();
}
// 从socket列表中清除用户
for (int i = 0; i < lstSocket.size(); i++) {
Socket st = lstSocket.get(i);
if (st.getPort() == port) {
lstSocket.remove(i);
break;
}
}
break;
case "show":
// 显示所有在线用户
int sender1 = -1;
for (int i = 0; i < lstSocket.size(); i++) {
Socket st = lstSocket.get(i);
if (st.getPort() == port) {
sender1 = i;
break;
}
}
Socket st = lstSocket.get(sender1);
OutputStream os = st.getOutputStream();
PrintWriter out = new PrintWriter(os);
out.println("【" + "current users list" + "】");
for (int j = 0; j < lstSocket.size(); j++) {
if (sender1 == j)
continue;
Socket st2 = lstSocket.get(j);
out.println("【" + st2.getPort() + "】");
}
out.flush();
break;
case "solo":
// 棋类比赛
int flag1 = -1;
int sender11 = -1;
String targetID1 = jo.get("targetID").toString();
int targetIDInt1 = Integer.parseInt(targetID1);
for (int i = 0; i < lstSocket.size(); i++) {
Socket st1 = lstSocket.get(i);
if (st1.getPort() == port) {
sender11 = i;
break;
}
}
Socket st1 = lstSocket.get(sender11);
for (int i = 0; i < lstSocket.size(); i++) {
if (i == sender11)
continue; // 不允许和自身solo
Socket st2 = lstSocket.get(i);
// System.out.println("st.getPort():"+st.getPort());
// System.out.println("targetID:"+targetID);
// if(st.getPort() + "" != targetID) continue;
if (targetIDInt1 != st2.getPort())
continue;
flag1 = i;
int x = st1.getPort(), y = st2.getPort();
OutputStream os1 = st1.getOutputStream();
PrintWriter out1 = new PrintWriter(os1);
OutputStream os2 = st2.getOutputStream();
PrintWriter out2 = new PrintWriter(os2);
boolean isInSolo = false;
for (int j = 0; j < lstSoloTables.size(); j++) {
GomokuBoard temp = lstSoloTables.get(j);
if (x == temp.p1 || x == temp.p2) {
out1.println("【你已处于对局中,不可开始新的对局】");
out1.flush();
isInSolo = true;
break;
}
if (y == temp.p1 || y == temp.p2) {
out1.println("【对手已处于对局中,不可开始新的对局】");
out1.flush();
isInSolo = true;
break;
}
}
if (isInSolo == false) {
createSoloTables(st1.getPort(), st2.getPort());
// 服务器端发送到客户端的数据
out1.println("即将开始你和【" + targetID1 + "】的solo");
out1.flush();
out2.println("【" + port + "】发起了对你的solo");
out2.flush();
}
break;
}
if (flag1 == -1) {
// Socket st1 = lstSocket.get(sender11);
OutputStream os1 = st1.getOutputStream();
PrintWriter out1 = new PrintWriter(os1);
out1.println("【" + targetID1 + "】不存在或已下线");
out1.flush();
}
break;
case "move":
// 下棋动作
// x y为处理后的棋盘坐标
// p1 p2为游戏双方端口号(其中p1为这一步下棋的人)
String x = jo.get("x").toString();
String y = jo.get("y").toString();
int X = Integer.parseInt(x);
int Y = Integer.parseInt(y); // 坐标
int P1 = port; // P1为当前落子者 数值为端口号
int P2 = -1;
for (int i = 0; i < lstSoloTables.size(); i++) {
GomokuBoard gb = lstSoloTables.get(i);
if (gb.p1 == P1) {
P2 = gb.p2;
break;
}
if (gb.p2 == P1) {
P2 = gb.p1;
break;
}
}
int s1 = -1, s2 = -1;
for (int i = 0; i < lstSocket.size(); i++) {
Socket temp = lstSocket.get(i);
if (temp.getPort() == P1) {
s1 = i;
}
if (temp.getPort() == P2) {
s2 = i;
}
}
// System.out.println(""+s1+" "+s2);
if (s1 == -1 || s2 == -1)
break; // 有人不在棋局之中
Socket St1 = lstSocket.get(s1);
Socket St2 = lstSocket.get(s2);
OutputStream Os1 = St1.getOutputStream();
PrintWriter Out1 = new PrintWriter(Os1);
OutputStream Os2 = St2.getOutputStream();
PrintWriter Out2 = new PrintWriter(Os2);
for (int i = 0; i < lstSoloTables.size(); i++) {
GomokuBoard gb = lstSoloTables.get(i);
if ((gb.p1 == P1 && gb.p2 == P2) || (gb.p1 == P2 && gb.p2 == P1)) {
if (gb.chessBoard[X][Y] != 0) {
Out1.println("【落子位置已有棋子】");
Out1.flush();
break;
}
gb.chessBoard[X][Y] = gb.moveFlag;
Out1.print("&");
for (int i1 = 1; i1 <= gb.n; i1++) {
for (int j = 1; j <= gb.n; j++) {
Out1.print(gb.chessBoard[i1][j]);
}
// Out1.println();
}
Out1.println("&");
Out1.flush();
// Out1.close();
Out2.print("&");
for (int i1 = 1; i1 <= gb.n; i1++) {
for (int j = 1; j <= gb.n; j++) {
Out2.print(gb.chessBoard[i1][j]);
}
// Out2.println();
}
Out2.println("&"); // 这边输出要换行 因为客户端的读取是readline
Out2.flush();
// gb.show();
if (gb.checkEnd() == 1) {
if (gb.moveFlag == 1 || gb.moveFlag == 2) {
if (gb.drawFlag == 1) {
Out1.println("【平局】");
Out2.println("【平局】");
Out1.flush();
Out2.flush();
}
if (gb.drawFlag == 0) {
Out1.println("【你胜利了】");
Out2.println("【你失败了】");
Out1.flush();
Out2.flush();
}
}
try {
Thread.sleep(5000); // 游戏结束时停止5s
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
endSolo(i, s1, s2);
}
gb.moveFlag = 3 - gb.moveFlag; // 交换
break;
}
}
break;
}
System.out.println("Server data : " + str);
}
private void createSoloTables(int x, int y) { // 创建lstSocket中两个socket的临时对战
// TODO Auto-generated method stub
GomokuBoard gb = new GomokuBoard(x, y);
lstSoloTables.add(gb);
}
private void endSolo(int x, int s1, int s2) { // 删除lstSoloTables中的第x个棋盘,并结束对战窗口
lstSoloTables.remove(x);
// 加入在客户端结束对战窗口的代码
Socket St1 = lstSocket.get(s1);
Socket St2 = lstSocket.get(s2);
OutputStream Os1 = null;
try {
Os1 = St1.getOutputStream();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
PrintWriter Out1 = new PrintWriter(Os1);
OutputStream Os2 = null;
try {
Os2 = St2.getOutputStream();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
PrintWriter Out2 = new PrintWriter(Os2);
Out1.println("%"); // %表示结束
Out1.flush();
Out2.println("%");
Out2.flush();
}
private void SendWelcomeUser(String strPort) throws IOException {
// 新客户上线,群发欢迎的消息
for (int i = 0; i < lstSocket.size(); i++) {
Socket st = lstSocket.get(i);
OutputStream os = st.getOutputStream();
PrintWriter out = new PrintWriter(os);
// 状态,数据
out.println("欢迎【" + strPort + "】用户上线");
out.flush();
}
}
}