基于Java编写的网络五子棋

需求分析:

对于网络五子棋而言,在普通五子棋的基础上需要添加以下功能:

1.拥有服务器端和客户端,用户通过客户端登录服务器后可与其他登录的用户进行对弈

2.服务器支持多组用户同时进行对弈

3.用户可以在服务器上创建新游戏或加入已创建的游戏

4.用户在下棋的时候可以进行聊天交流

由上可以知道需要实现的功能:

·提供服务器和客户端的功能

·服务器将监听客户端的登录情况并允许多个客户端进行登录

·用户通过客户端可以登录服务器,之后可以看到服务器当前在线的其他用户,并与他们进行聊天等

·用户登录服务器后,可以创建新的五子棋游戏或加入已创建的五子棋游戏

·用户通过客户端可以像普通五子棋那样与其他用户对弈

根据功能将网络五子棋分为4个模块:即用户面板模块、棋盘面板模块、五子棋服务器模块、五子棋客户端模块


下面我们开始进行编译用户面板模块:

1.开发用户列表面板

import java.awt.*;

/**
 * Created by Administrator on 2016/11/21.
 */
//初始状态下将添加10个名称为“无用户“的信息到列表中,说明服务器最多支持10个用户同时在线
//该列表被添加到面板中,使用“BorderLayout”布局格式
public class UserListPad extends Panel{
    public List userList=new List(10);

    public UserListPad(){
        setLayout(new BorderLayout());
        for(int i=0;i<10;i++){
            userList.add(i+"."+"无用户");
        }
        add(userList,BorderLayout.CENTER);
    }
}

2.开发用户聊天面板

import javax.swing.*;
import java.awt.*;

/**
 * Created by Administrator on 2016/11/21.
 */
//聊天面板为一个TextArea视图控件,拥有一个垂直方向的滚动条。
//该TextArea被添加到面板中,使用“BorderLayout”布局格式。
public class UserChatPad extends JPanel{
    public JTextArea chatTextArea=new JTextArea("命令区域",18,20);
    public UserChatPad(){
        setLayout(new BorderLayout());
        chatTextArea.setAutoscrolls(true);
        chatTextArea.setLineWrap(true);
        add(chatTextArea,BorderLayout.CENTER);
    }
}

3.开发用户输入面板

import javax.swing.*;
import java.awt.*;

/**
 * Created by Administrator on 2016/11/21.
 */
//面板包含两个视图控件
//contentInpitted为TextField控件,用户可以在其中输入聊天信息
public class UserInputPad extends JPanel{
    public JTextField contentInputted = new JTextField("",26);
    public JComboBox userChoice = new JComboBox();

    public UserInputPad(){
        setLayout(new FlowLayout(FlowLayout.LEFT));
        for(int i=0;i<50;i++){
            userChoice.addItem(i+"."+"无用户");
        }
        userChoice.setSize(60,24);
        add(userChoice);
        add(contentInputted);
    }
}

4.开发用户操作面板

import javax.swing.*;
import java.awt.*;

/**
 * Created by Administrator on 2016/11/21.
 */
public class UserControlPad extends JPanel {
    public JLabel ipLabel = new JLabel("IP",JLabel.LEFT);
    public JTextField ipInputted = new JTextField("localhost",10);
    public JButton connectButton = new JButton("连接到服务器");
    public JButton createButton = new JButton("创建游戏");
    public JButton joinButton = new JButton("加入游戏");
    public JButton cancelButton = new JButton("放弃游戏");
    public JButton exitButton = new JButton("退出游戏");
    public UserControlPad(){
        setLayout(new FlowLayout(FlowLayout.LEFT));
        setBackground(Color.LIGHT_GRAY);
        add(ipLabel);
        add(ipInputted);
        add(connectButton);
        add(createButton);
        add(joinButton);
        add(cancelButton);
        add(exitButton);
    }
}

下面开始开发棋盘面板模块

1.开发黑棋类

import java.awt.*;

/**
 * Created by Administrator on 2016/11/21.
 */
public class FIRPointBlack extends Canvas {
    FIRPad padBelonged; // 黑棋所属的棋盘

    public FIRPointBlack(FIRPad padBelonged)
    {
        setSize(20, 20); // 设置棋子大小
        this.padBelonged = padBelonged;
    }

    public void paint(Graphics g)
    { // 画棋子
        g.setColor(Color.black);
        g.fillOval(0, 0, 14, 14);
    }
}

2.开发白棋类

import java.awt.*;

/**
 * Created by Administrator on 2016/11/21.
 */
public class FIRPointWhite extends Canvas{
    FIRPad padBelonged; // 白棋所属的棋盘

    public FIRPointWhite(FIRPad padBelonged)
    {
        setSize(20, 20);
        this.padBelonged = padBelonged;
    }

    public void paint(Graphics g)
    { // 画棋子
        g.setColor(Color.white);
        g.fillOval(0, 0, 14, 14);
    }
}

3.开发棋盘面板

import java.awt.*;
import java.awt.event.*;
import java.io.*;
import java.net.*;

import javax.swing.JTextField;


/**
 * Created by Administrator on 2016/11/21.
 */
public class FIRPad extends Panel implements MouseListener,ActionListener{
    // 鼠标是否能使用
    public boolean isMouseEnabled = false;
    // 是否胜利
    public boolean isWinned = false;
    // 是否在下棋中
    public boolean isGaming = false;
    // 棋子的x轴坐标位
    public int chessX_POS = -1;
    // 棋子的y轴坐标位
    public int chessY_POS = -1;
    // 棋子的颜色
    public int chessColor = 1;
    // 黑棋x轴坐标位数组
    public int chessBlack_XPOS[] = new int[200];
    // 黑棋y轴坐标位数组
    public int chessBlack_YPOS[] = new int[200];
    // 白棋x轴坐标位数组
    public int chessWhite_XPOS[] = new int[200];
    // 白棋y轴坐标位数组
    public int chessWhite_YPOS[] = new int[200];
    // 黑棋数量
    public int chessBlackCount = 0;
    // 白棋数量
    public int chessWhiteCount = 0;
    // 黑棋获胜次数
    public int chessBlackVicTimes = 0;
    // 白棋获胜次数
    public int chessWhiteVicTimes = 0;
    // 套接口
    public Socket chessSocket;
    public DataInputStream inputData;
    public DataOutputStream outputData;
    public String chessSelfName = null;
    public String chessPeerName = null;
    public String host = null;
    public int port = 4331;
    public TextField statusText = new TextField("请连接服务器!");
    public FIRThread firThread = new FIRThread(this);

    public FIRPad()
    {
        setSize(440, 440);
        setLayout(null);
        setBackground(Color.LIGHT_GRAY);
        addMouseListener(this);
        add(statusText);
        statusText.setBounds(new Rectangle(40, 5, 360, 24));
        statusText.setEditable(false);
    }

    // 连接到主机
    public boolean connectServer(String ServerIP, int ServerPort) throws Exception
    {
        try
        {
            // 取得主机端口
            chessSocket = new Socket(ServerIP, ServerPort);
            // 取得输入流
            inputData = new DataInputStream(chessSocket.getInputStream());
            // 取得输出流
            outputData = new DataOutputStream(chessSocket.getOutputStream());
            firThread.start();
            return true;
        }
        catch (IOException ex)
        {
            statusText.setText("连接失败! \n");
        }
        return false;
    }

    // 设定胜利时的棋盘状态
    public void setVicStatus(int vicChessColor)
    {
        // 清空棋盘
        this.removeAll();
        // 将黑棋的位置设置到零点
        for (int i = 0; i <= chessBlackCount; i++)
        {
            chessBlack_XPOS[i] = 0;
            chessBlack_YPOS[i] = 0;
        }
        // 将白棋的位置设置到零点
        for (int i = 0; i <= chessWhiteCount; i++)
        {
            chessWhite_XPOS[i] = 0;
            chessWhite_YPOS[i] = 0;
        }
        // 清空棋盘上的黑棋数
        chessBlackCount = 0;
        // 清空棋盘上的白棋数
        chessWhiteCount = 0;
        add(statusText);
        statusText.setBounds(40, 5, 360, 24);
        if (vicChessColor == 1)
        { // 黑棋胜
            chessBlackVicTimes++;
            statusText.setText("黑方胜,黑:白 " + chessBlackVicTimes + ":" + chessWhiteVicTimes
                    + ",游戏重启,等待白方...");
        }
        else if (vicChessColor == -1)
        { // 白棋胜
            chessWhiteVicTimes++;
            statusText.setText("白方胜,黑:白 " + chessBlackVicTimes + ":" + chessWhiteVicTimes
                    + ",游戏重启,等待黑方...");
        }
    }

    // 取得指定棋子的位置
    public void setLocation(int xPos, int yPos, int chessColor)
    {
        if (chessColor == 1)
        { // 棋子为黑棋时
            chessBlack_XPOS[chessBlackCount] = xPos * 20;
            chessBlack_YPOS[chessBlackCount] = yPos * 20;
            chessBlackCount++;
        }
        else if (chessColor == -1)
        { // 棋子为白棋时
            chessWhite_XPOS[chessWhiteCount] = xPos * 20;
            chessWhite_YPOS[chessWhiteCount] = yPos * 20;
            chessWhiteCount++;
        }
    }

    // 判断当前状态是否为胜利状态
    public boolean checkVicStatus(int xPos, int yPos, int chessColor)
    {
        int chessLinkedCount = 1; // 连接棋子数
        int chessLinkedCompare = 1; // 用于比较是否要继续遍历一个棋子的相邻网格
        int chessToCompareIndex = 0; // 要比较的棋子在数组中的索引位置
        int closeGrid = 1; // 相邻网格的位置
        if (chessColor == 1)
        { // 黑棋时
            chessLinkedCount = 1; // 将该棋子自身算入的话,初始连接数为1
            //以下每对for循环语句为一组,因为下期的位置能位于中间而非两端
            for (closeGrid = 1; closeGrid <= 4; closeGrid++)
            { // 遍历相邻4个网格
                for (chessToCompareIndex = 0; chessToCompareIndex <= chessBlackCount; chessToCompareIndex++)
                { // 遍历棋盘上所有黑棋子
                    if (((xPos + closeGrid) * 20 == chessBlack_XPOS[chessToCompareIndex])
                            && ((yPos * 20) == chessBlack_YPOS[chessToCompareIndex]))
                    { // 判断当前下的棋子的右边4个棋子是否都为黑棋
                        chessLinkedCount = chessLinkedCount + 1; // 连接数加1
                        if (chessLinkedCount == 5)
                        { // 五子相连时,胜利
                            return true;
                        }
                    }
                }
                if (chessLinkedCount == (chessLinkedCompare + 1)) {
                    chessLinkedCompare++;
                }
                else {// 若中间有一个棋子非黑棋,则会进入此分支,此时无需再遍历
                    break;
                }
            }
            for (closeGrid = 1; closeGrid <= 4; closeGrid++)
            {
                for (chessToCompareIndex = 0; chessToCompareIndex <= chessBlackCount; chessToCompareIndex++)
                {
                    if (((xPos - closeGrid) * 20 == chessBlack_XPOS[chessToCompareIndex])
                            && (yPos * 20 == chessBlack_YPOS[chessToCompareIndex]))
                    { // 判断当前下的棋子的左边4个棋子是否都为黑棋
                        chessLinkedCount++;
                        if (chessLinkedCount == 5)
                        {
                            return true;
                        }
                    }
                }
                if (chessLinkedCount == (chessLinkedCompare + 1)) {
                    chessLinkedCompare++;
                }
                else {
                    break;
                }
            }
            // 进入新的一组for循环时要将连接数等重置
            chessLinkedCount = 1;
            chessLinkedCompare = 1;
            for (closeGrid = 1; closeGrid <= 4; closeGrid++)
            {
                for (chessToCompareIndex = 0; chessToCompareIndex <= chessBlackCount; chessToCompareIndex++)
                {
                    if ((xPos * 20 == chessBlack_XPOS[chessToCompareIndex])
                            && ((yPos + closeGrid) * 20 == chessBlack_YPOS[chessToCompareIndex]))
                    { // 判断当前下的棋子的上边4个棋子是否都为黑棋
                        chessLinkedCount++;
                        if (chessLinkedCount == 5)
                        {
                            return true;
                        }
                    }
                }
                if (chessLinkedCount == (chessLinkedCompare + 1)) {
                    chessLinkedCompare++;
                }
                else {
                    break;
                }
            }
            for (closeGrid = 1; closeGrid <= 4; closeGrid++)
            {
                for (chessToCompareIndex = 0; chessToCompareIndex <= chessBlackCount; chessToCompareIndex++)
                {
                    if ((xPos * 20 == chessBlack_XPOS[chessToCompareIndex])
                            && ((yPos - closeGrid) * 20 == chessBlack_YPOS[chessToCompareIndex]))
                    { // 判断当前下的棋子的下边4个棋子是否都为黑棋
                        chessLinkedCount++;
                        if (chessLinkedCount == 5)
                        {
                            return true;
                        }
                    }
                }
                if (chessLinkedCount == (chessLinkedCompare + 1)) {
                    chessLinkedCompare++;
                }
                else {
                    break;
                }
            }
            chessLinkedCount = 1;
            chessLinkedCompare = 1;
            for (closeGrid = 1; closeGrid <= 4; closeGrid++)
            {
                for (chessToCompareIndex = 0; chessToCompareIndex <= chessBlackCount; chessToCompareIndex++)
                {
                    if (((xPos - closeGrid) * 20 == chessBlack_XPOS[chessToCompareIndex])
                            && ((yPos + closeGrid) * 20 == chessBlack_YPOS[chessToCompareIndex]))
                    { // 判断当前下的棋子的左上方向4个棋子是否都为黑棋
                        chessLinkedCount++;
                        if (chessLinkedCount == 5)
                        {
                            return true;
                        }
                    }
                }
                if (chessLinkedCount == (chessLinkedCompare + 1)) {
                    chessLinkedCompare++;
                }
                else {
                    break;
                }
            }
            for (closeGrid = 1; closeGrid <= 4; closeGrid++)
            {
                for (chessToCompareIndex = 0; chessToCompareIndex <= chessBlackCount; chessToCompareIndex++)
                {
                    if (((xPos + closeGrid) * 20 == chessBlack_XPOS[chessToCompareIndex])
                            && ((yPos - closeGrid) * 20 == chessBlack_YPOS[chessToCompareIndex]))
                    { // 判断当前下的棋子的右下方向4个棋子是否都为黑棋
                        chessLinkedCount++;
                        if (chessLinkedCount == 5)
                        {
                            return true;
                        }
                    }
                }
                if (chessLinkedCount == (chessLinkedCompare + 1)) {
                    chessLinkedCompare++;
                }
                else {
                    break;
                }
            }
            chessLinkedCount = 1;
            chessLinkedCompare = 1;
            for (closeGrid = 1; closeGrid <= 4; closeGrid++)
            {
                for (chessToCompareIndex = 0; chessToCompareIndex <= chessBlackCount; chessToCompareIndex++)
                {
                    if (((xPos + closeGrid) * 20 == chessBlack_XPOS[chessToCompareIndex])
                            && ((yPos + closeGrid) * 20 == chessBlack_YPOS[chessToCompareIndex]))
                    { // 判断当前下的棋子的右上方向4个棋子是否都为黑棋
                        chessLinkedCount++;
                        if (chessLinkedCount == 5)
                        {
                            return true;
                        }
                    }
                }
                if (chessLinkedCount == (chessLinkedCompare + 1)) {
                    chessLinkedCompare++;
                }
                else {
                    break;
                }
            }
            for (closeGrid = 1; closeGrid <= 4; closeGrid++)
            {
                for (chessToCompareIndex = 0; chessToCompareIndex <= chessBlackCount; chessToCompareIndex++)
                {
                    if (((xPos - closeGrid) * 20 == chessBlack_XPOS[chessToCompareIndex])
                            && ((yPos - closeGrid) * 20 == chessBlack_YPOS[chessToCompareIndex]))
                    { // 判断当前下的棋子的左下方向4个棋子是否都为黑棋
                        chessLinkedCount++;
                        if (chessLinkedCount == 5)
                        {
                            return true;
                        }
                    }
                }
                if (chessLinkedCount == (chessLinkedCompare + 1)) {
                    chessLinkedCompare++;
                }
                else {
                    break;
                }
            }
        }
        else if (chessColor == -1)
        { // 白棋时
            chessLinkedCount = 1;
            for (closeGrid = 1; closeGrid <= 4; closeGrid++)
            {
                for (chessToCompareIndex = 0; chessToCompareIndex <= chessWhiteCount; chessToCompareIndex++)
                {
                    if (((xPos + closeGrid) * 20 == chessWhite_XPOS[chessToCompareIndex])
                            && (yPos * 20 == chessWhite_YPOS[chessToCompareIndex]))
                    {// 判断当前下的棋子的右边4个棋子是否都为白棋
                        chessLinkedCount++;
                        if (chessLinkedCount == 5)
                        {
                            return true;
                        }
                    }
                }
                if (chessLinkedCount == (chessLinkedCompare + 1)) {
                    chessLinkedCompare++;
                }
                else {
                    break;
                }
            }
            for (closeGrid = 1; closeGrid <= 4; closeGrid++)
            {
                for (chessToCompareIndex = 0; chessToCompareIndex <= chessWhiteCount; chessToCompareIndex++)
                {
                    if (((xPos - closeGrid) * 20 == chessWhite_XPOS[chessToCompareIndex])
                            && (yPos * 20 == chessWhite_YPOS[chessToCompareIndex]))
                    {// 判断当前下的棋子的左边4个棋子是否都为白棋
                        chessLinkedCount++;
                        if (chessLinkedCount == 5)
                        {
                            return true;
                        }
                    }
                }
                if (chessLinkedCount == (chessLinkedCompare + 1)) {
                    chessLinkedCompare++;
                }
                else {
                    break;
                }
            }
            chessLinkedCount = 1;
            chessLinkedCompare = 1;
            for (closeGrid = 1; closeGrid <= 4; closeGrid++)
            {
                for (chessToCompareIndex = 0; chessToCompareIndex <= chessWhiteCount; chessToCompareIndex++)
                {
                    if ((xPos * 20 == chessWhite_XPOS[chessToCompareIndex])
                            && ((yPos + closeGrid) * 20 == chessWhite_YPOS[chessToCompareIndex]))
                    {// 判断当前下的棋子的上边4个棋子是否都为白棋
                        chessLinkedCount++;
                        if (chessLinkedCount == 5)
                        {
                            return true;
                        }
                    }
                }
                if (chessLinkedCount == (chessLinkedCompare + 1)) {
                    chessLinkedCompare++;
                }
                else {
                    break;
                }
            }
            for (closeGrid = 1; closeGrid <= 4; closeGrid++)
            {
                for (chessToCompareIndex = 0; chessToCompareIndex <= chessWhiteCount; chessToCompareIndex++)
                {
                    if ((xPos * 20 == chessWhite_XPOS[chessToCompareIndex])
                            && ((yPos - closeGrid) * 20 == chessWhite_YPOS[chessToCompareIndex]))
                    {// 判断当前下的棋子的下边4个棋子是否都为白棋
                        chessLinkedCount++;
                        if (chessLinkedCount == 5)
                        {
                            return true;
                        }
                    }
                }
                if (chessLinkedCount == (chessLinkedCompare + 1)) {
                    chessLinkedCompare++;
                }
                else {
                    break;
                }
            }
            chessLinkedCount = 1;
            chessLinkedCompare = 1;
            for (closeGrid = 1; closeGrid <= 4; closeGrid++)
            {
                for (chessToCompareIndex = 0; chessToCompareIndex <= chessWhiteCount; chessToCompareIndex++)
                {
                    if (((xPos - closeGrid) * 20 == chessWhite_XPOS[chessToCompareIndex])
                            && ((yPos + closeGrid) * 20 == chessWhite_YPOS[chessToCompareIndex]))
                    {// 判断当前下的棋子的左上方向4个棋子是否都为白棋
                        chessLinkedCount++;
                        if (chessLinkedCount == 5)
                        {
                            return true;
                        }
                    }
                }
                if (chessLinkedCount == (chessLinkedCompare + 1)) {
                    chessLinkedCompare++;
                }
                else {
                    break;
                }
            }
            for (closeGrid = 1; closeGrid <= 4; closeGrid++)
            {
                for (chessToCompareIndex = 0; chessToCompareIndex <= chessWhiteCount; chessToCompareIndex++)
                {
                    if (((xPos + closeGrid) * 20 == chessWhite_XPOS[chessToCompareIndex])
                            && ((yPos - closeGrid) * 20 == chessWhite_YPOS[chessToCompareIndex]))
                    {// 判断当前下的棋子的右下方向4个棋子是否都为白棋
                        chessLinkedCount++;
                        if (chessLinkedCount == 5)
                        {
                            return true;
                        }
                    }
                }
                if (chessLinkedCount == (chessLinkedCompare + 1)) {
                    chessLinkedCompare++;
                }
                else {
                    break;
                }
            }
            chessLinkedCount = 1;
            chessLinkedCompare = 1;
            for (closeGrid = 1; closeGrid <= 4; closeGrid++)
            {
                for (chessToCompareIndex = 0; chessToCompareIndex <= chessWhiteCount; chessToCompareIndex++)
                {
                    if (((xPos + closeGrid) * 20 == chessWhite_XPOS[chessToCompareIndex])
                            && ((yPos + closeGrid) * 20 == chessWhite_YPOS[chessToCompareIndex]))
                    {// 判断当前下的棋子的右上方向4个棋子是否都为白棋
                        chessLinkedCount++;
                        if (chessLinkedCount == 5)
                        {
                            return true;
                        }
                    }
                }
                if (chessLinkedCount == (chessLinkedCompare + 1)) {
                    chessLinkedCompare++;
                }
                else {
                    break;
                }
            }
            for (closeGrid = 1; closeGrid <= 4; closeGrid++)
            {
                for (chessToCompareIndex = 0; chessToCompareIndex <= chessWhiteCount; chessToCompareIndex++)
                {
                    if (((xPos - closeGrid) * 20 == chessWhite_XPOS[chessToCompareIndex])
                            && ((yPos - closeGrid) * 20 == chessWhite_YPOS[chessToCompareIndex]))
                    {// 判断当前下的棋子的左下方向4个棋子是否都为白棋
                        chessLinkedCount++;
                        if (chessLinkedCount == 5)
                        {
                            return (true);
                        }
                    }
                }
                if (chessLinkedCount == (chessLinkedCompare + 1)) {
                    chessLinkedCompare++;
                }
                else {
                    break;
                }
            }
        }
        return false;
    }

    // 画棋盘
    public void paint(Graphics g)
    {
        for (int i = 40; i <= 380; i = i + 20)
        {
            g.drawLine(40, i, 400, i);
        }
        g.drawLine(40, 400, 400, 400);
        for (int j = 40; j <= 380; j = j + 20)
        {
            g.drawLine(j, 40, j, 400);
        }
        g.drawLine(400, 40, 400, 400);
        g.fillOval(97, 97, 6, 6);
        g.fillOval(337, 97, 6, 6);
        g.fillOval(97, 337, 6, 6);
        g.fillOval(337, 337, 6, 6);
        g.fillOval(217, 217, 6, 6);
    }

    // 画棋子
    public void paintFirPoint(int xPos, int yPos, int chessColor)
    {
        FIRPointBlack firPBlack = new FIRPointBlack(this);
        FIRPointWhite firPWhite = new FIRPointWhite(this);
        if (chessColor == 1 && isMouseEnabled)
        { // 黑棋
            // 设置棋子的位置
            setLocation(xPos, yPos, chessColor);
            // 取得当前局面状态
            isWinned = checkVicStatus(xPos, yPos, chessColor);
            if (isWinned == false)
            { // 非胜利状态
                firThread.sendMessage("/" + chessPeerName + " /chess "
                        + xPos + " " + yPos + " " + chessColor);
                this.add(firPBlack); // 将棋子添加到棋盘中
                firPBlack.setBounds(xPos * 20 - 7,
                        yPos * 20 - 7, 16, 16); // 设置棋子边界
                statusText.setText("黑(第" + chessBlackCount + "步)"
                        + xPos + " " + yPos + ",轮到白方.");
                isMouseEnabled = false; // 将鼠标设为不可用
            }
            else
            { // 胜利状态
                firThread.sendMessage("/" + chessPeerName + " /chess "
                        + xPos + " " + yPos + " " + chessColor);
                this.add(firPBlack);
                firPBlack.setBounds(xPos * 20 - 7,
                        yPos * 20 - 7, 16, 16);
                setVicStatus(1); // 调用胜利方法,传入参数为黑棋胜利
                isMouseEnabled = false;
            }
        }
        else if (chessColor == -1 && isMouseEnabled)
        { // 白棋
            setLocation(xPos, yPos, chessColor);
            isWinned = checkVicStatus(xPos, yPos, chessColor);
            if (isWinned == false)
            {
                firThread.sendMessage("/" + chessPeerName + " /chess "
                        + xPos + " " + yPos + " " + chessColor);
                this.add(firPWhite);
                firPWhite.setBounds(xPos * 20 - 7,
                        yPos * 20 - 7, 16, 16);
                statusText.setText("白(第" + chessWhiteCount + "步)"
                        + xPos + " " + yPos + ",轮到黑方.");
                isMouseEnabled = false;
            }
            else
            {
                firThread.sendMessage("/" + chessPeerName + " /chess "
                        + xPos + " " + yPos + " " + chessColor);
                this.add(firPWhite);
                firPWhite.setBounds(xPos * 20 - 7,
                        yPos * 20 - 7, 16, 16);
                setVicStatus(-1); // 调用胜利方法,传入参数为白棋
                isMouseEnabled = false;
            }
        }
    }

    // 画网络棋盘
    public void paintNetFirPoint(int xPos, int yPos, int chessColor)
    {
        FIRPointBlack firPBlack = new FIRPointBlack(this);
        FIRPointWhite firPWhite = new FIRPointWhite(this);
        setLocation(xPos, yPos, chessColor);
        if (chessColor == 1)
        {
            isWinned = checkVicStatus(xPos, yPos, chessColor);
            if (isWinned == false)
            {
                this.add(firPBlack);
                firPBlack.setBounds(xPos * 20 - 7,
                        yPos * 20 - 7, 16, 16);
                statusText.setText("黑(第" + chessBlackCount + "步)"
                        + xPos + " " + yPos + ",轮到白方.");
                isMouseEnabled = true;
            }
            else
            {
                firThread.sendMessage("/" + chessPeerName + " /victory "
                        + chessColor);//djr
                this.add(firPBlack);
                firPBlack.setBounds(xPos * 20 - 7,
                        yPos * 20 - 7, 16, 16);
                setVicStatus(1);
                isMouseEnabled = true;
            }
        }
        else if (chessColor == -1)
        {
            isWinned = checkVicStatus(xPos, yPos, chessColor);
            if (isWinned == false)
            {
                this.add(firPWhite);
                firPWhite.setBounds(xPos * 20 - 7,
                        yPos * 20 - 7, 16, 16);
                statusText.setText("白(第" + chessWhiteCount + "步)"
                        + xPos + " " + yPos + ",轮到黑方.");
                isMouseEnabled = true;
            }
            else
            {
                firThread.sendMessage("/" + chessPeerName + " /victory "
                        + chessColor);
                this.add(firPWhite);
                firPWhite.setBounds(xPos * 20 - 7,
                        yPos * 20 - 7, 16, 16);
                setVicStatus(-1);
                isMouseEnabled = true;
            }
        }
    }

    // 捕获下棋事件
    public void mousePressed(MouseEvent e)
    {
        if (e.getModifiers() == InputEvent.BUTTON1_MASK)
        {
            chessX_POS = (int) e.getX();
            chessY_POS = (int) e.getY();
            int a = (chessX_POS + 10) / 20, b = (chessY_POS + 10) / 20;
            if (chessX_POS / 20 < 2 || chessY_POS / 20 < 2
                    || chessX_POS / 20 > 19 || chessY_POS / 20 > 19)
            {
                // 下棋位置不正确时,不执行任何操作
            }
            else
            {
                paintFirPoint(a, b, chessColor); // 画棋子
            }
        }
    }

    public void mouseReleased(MouseEvent e){}
    public void mouseEntered(MouseEvent e){}
    public void mouseExited(MouseEvent e){}
    public void mouseClicked(MouseEvent e){}
    public void actionPerformed(ActionEvent e){}
}

4.开发棋盘线程

import java.util.StringTokenizer;
import java.io.IOException;

/**
 * Created by Administrator on 2016/11/21.
 */
public class FIRThread extends Thread{
    FIRPad currPad; // 当前线程的棋盘

    public FIRThread(FIRPad currPad)
    {
        this.currPad = currPad;
    }

    // 处理取得的信息
    public void dealWithMsg(String msgReceived)
    {
        if (msgReceived.startsWith("/chess "))
        { // 收到的信息为下棋
            StringTokenizer userMsgToken = new StringTokenizer(msgReceived, " ");
            // 表示棋子信息的数组、0索引为:x坐标;1索引位:y坐标;2索引位:棋子颜色
            String[] chessInfo = { "-1", "-1", "0" };
            int i = 0; // 标志位
            String chessInfoToken;
            while (userMsgToken.hasMoreTokens())
            {
                chessInfoToken = (String) userMsgToken.nextToken(" ");
                if (i >= 1 && i <= 3)
                {
                    chessInfo[i - 1] = chessInfoToken;
                }
                i++;
            }
            currPad.paintNetFirPoint(Integer.parseInt(chessInfo[0]), Integer
                    .parseInt(chessInfo[1]), Integer.parseInt(chessInfo[2]));
        }
        else if (msgReceived.startsWith("/yourname "))
        { // 收到的信息为改名
            currPad.chessSelfName = msgReceived.substring(10);
        }
        else if (msgReceived.equals("/error"))
        { // 收到的为错误信息
            currPad.statusText.setText("用户不存在,请重新加入!");
        }
    }

    // 发送信息
    public void sendMessage(String sndMessage)
    {
        try
        {
            currPad.outputData.writeUTF(sndMessage);
        }
        catch (Exception ea)
        {
            ea.printStackTrace();;
        }
    }

    public void run()
    {
        String msgReceived = "";
        try
        {
            while (true)
            { // 等待信息输入
                msgReceived = currPad.inputData.readUTF();
                dealWithMsg(msgReceived);
            }
        }
        catch (IOException es){}
    }
}

下面开始开发服务器模块

1.开发服务器信息面板

import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.FlowLayout;
import java.awt.Label;
import java.awt.Panel;
import java.awt.TextArea;

import javax.swing.JLabel;

/**
 * Created by Administrator on 2016/11/21.
 */
public class ServerMsgPanel extends Panel {
    public TextArea msgTextArea = new TextArea("", 22, 50,
            TextArea.SCROLLBARS_VERTICAL_ONLY);
    public JLabel statusLabel = new JLabel("当前连接数:", Label.LEFT);
    public Panel msgPanel = new Panel();
    public Panel statusPanel = new Panel();
    public ServerMsgPanel()
    {
        setSize(350, 300);
        setBackground(Color.LIGHT_GRAY);
        setLayout(new BorderLayout());
        msgPanel.setLayout(new FlowLayout());
        msgPanel.setSize(210, 210);
        statusPanel.setLayout(new BorderLayout());
        statusPanel.setSize(210, 50);
        msgPanel.add(msgTextArea);
        statusPanel.add(statusLabel, BorderLayout.WEST);
        add(msgPanel, BorderLayout.CENTER);
        add(statusPanel, BorderLayout.NORTH);
    }

}

2.开发服务器进程

import java.io.DataInputStream;
import java.io.DataOutputStream;
import java.io.IOException;
import java.net.Socket;
import java.util.Enumeration;
import java.util.Hashtable;
import java.util.StringTokenizer;

/**
 * Created by Administrator on 2016/11/21.
 */
public class FIRServerThread extends Thread{
    Socket clientSocket; // 保存客户端套接口信息
    Hashtable clientDataHash; // 保存客户端端口与输出流对应的Hash
    Hashtable clientNameHash; // 保存客户端套接口和客户名对应的Hash
    Hashtable chessPeerHash; // 保存游戏创建者和游戏加入者对应的Hash
    ServerMsgPanel serverMsgPanel;
    boolean isClientClosed = false;

    public FIRServerThread(Socket clientSocket, Hashtable clientDataHash,
                           Hashtable clientNameHash, Hashtable chessPeerHash,
                           ServerMsgPanel server)
    {
        this.clientSocket = clientSocket;
        this.clientDataHash = clientDataHash;
        this.clientNameHash = clientNameHash;
        this.chessPeerHash = chessPeerHash;
        this.serverMsgPanel = server;
    }

    public void dealWithMsg(String msgReceived)
    {
        String clientName;
        String peerName;
        if (msgReceived.startsWith("/"))
        {
            if (msgReceived.equals("/list"))
            { // 收到的信息为更新用户列表
                Feedback(getUserList());
            }
            else if (msgReceived.startsWith("/creatgame [inchess]"))
            { // 收到的信息为创建游戏
                String gameCreaterName = msgReceived.substring(20); //取得服务器名
                synchronized (clientNameHash)
                { // 将用户端口放到用户列表中
                    clientNameHash.put(clientSocket, msgReceived.substring(11));
                }
                synchronized (chessPeerHash)
                { // 将主机设置为等待状态
                    chessPeerHash.put(gameCreaterName, "wait");
                }
                Feedback("/yourname " + clientNameHash.get(clientSocket));
                sendGamePeerMsg(gameCreaterName, "/OK");
                sendPublicMsg(getUserList());
            }
            else if (msgReceived.startsWith("/joingame "))
            { // 收到的信息为加入游戏时
                StringTokenizer userTokens = new StringTokenizer(msgReceived, " ");
                String userToken;
                String gameCreatorName;
                String gamePaticipantName;
                String[] playerNames = { "0", "0" };
                int nameIndex = 0;
                while (userTokens.hasMoreTokens())
                {
                    userToken = (String) userTokens.nextToken(" ");
                    if (nameIndex >= 1 && nameIndex <= 2)
                    {
                        playerNames[nameIndex - 1] = userToken; // 取得游戏者命
                    }
                    nameIndex++;
                }
                gameCreatorName = playerNames[0];
                gamePaticipantName = playerNames[1];
                if (chessPeerHash.containsKey(gameCreatorName)
                        && chessPeerHash.get(gameCreatorName).equals("wait"))
                { // 游戏已创建
                    synchronized (clientNameHash)
                    { // 增加游戏加入者的套接口与名称的对应
                        clientNameHash.put(clientSocket,
                                ("[inchess]" + gamePaticipantName));
                    }
                    synchronized (chessPeerHash)
                    { // 增加或修改游戏创建者与游戏加入者的名称的对应
                        chessPeerHash.put(gameCreatorName, gamePaticipantName);
                    }
                    sendPublicMsg(getUserList());
                    // 发送信息给游戏加入者
                    sendGamePeerMsg(gamePaticipantName,
                            ("/peer " + "[inchess]" + gameCreatorName));
                    // 发送游戏给游戏创建者
                    sendGamePeerMsg(gameCreatorName,
                            ("/peer " + "[inchess]" + gamePaticipantName));
                }
                else
                { // 若游戏未创建则拒绝加入游戏
                    sendGamePeerMsg(gamePaticipantName, "/reject");
                    try
                    {
                        closeClient();
                    }
                    catch (Exception ez)
                    {
                        ez.printStackTrace();
                    }
                }
            }
            else if (msgReceived.startsWith("/[inchess]"))
            { // 收到的信息为游戏中时
                int firstLocation = 0, lastLocation;
                lastLocation = msgReceived.indexOf(" ", 0);
                peerName = msgReceived.substring((firstLocation + 1), lastLocation);
                msgReceived = msgReceived.substring((lastLocation + 1));
                if (sendGamePeerMsg(peerName, msgReceived))
                {
                    Feedback("/error");
                }
            }
            else if (msgReceived.startsWith("/giveup "))
            { // 收到的信息为放弃游戏时
                String chessClientName = msgReceived.substring(8);
                if (chessPeerHash.containsKey(chessClientName)
                        && !((String) chessPeerHash.get(chessClientName))
                        .equals("wait"))
                { // 胜利方为游戏加入者,发送胜利信息
                    sendGamePeerMsg((String) chessPeerHash.get(chessClientName),
                            "/youwin");
                    synchronized (chessPeerHash)
                    { // 删除退出游戏的用户
                        chessPeerHash.remove(chessClientName);
                    }
                }
                if (chessPeerHash.containsValue(chessClientName))
                { // 胜利方为游戏创建者,发送胜利信息
                    sendGamePeerMsg((String) getHashKey(chessPeerHash,
                            chessClientName), "/youwin");
                    synchronized (chessPeerHash)
                    {// 删除退出游戏的用户
                        chessPeerHash.remove((String) getHashKey(chessPeerHash,
                                chessClientName));
                    }
                }
            }
            else
            { // 收到的信息为其它信息时
                int lastLocation = msgReceived.indexOf(" ", 0);
                if (lastLocation == -1)
                {
                    Feedback("无效命令");
                    return;
                }
            }
        }
        else
        {
            msgReceived = clientNameHash.get(clientSocket) + ">" + msgReceived;
            serverMsgPanel.msgTextArea.append(msgReceived + "\n");
            sendPublicMsg(msgReceived);
            serverMsgPanel.msgTextArea.setCaretPosition(serverMsgPanel.msgTextArea.getText()
                    .length());
        }
    }

    // 发送公开信息
    public void sendPublicMsg(String publicMsg)
    {
        synchronized (clientDataHash)
        {
            for (Enumeration enu = clientDataHash.elements(); enu
                    .hasMoreElements();)
            {
                DataOutputStream outputData = (DataOutputStream) enu.nextElement();
                try
                {
                    outputData.writeUTF(publicMsg);
                }
                catch (IOException es)
                {
                    es.printStackTrace();
                }
            }
        }
    }

    // 发送信息给指定的游戏中的用户
    public boolean sendGamePeerMsg(String gamePeerTarget, String gamePeerMsg)
    {
        for (Enumeration enu = clientDataHash.keys(); enu.hasMoreElements();)
        { // 遍历以取得游戏中的用户的套接口
            Socket userClient = (Socket) enu.nextElement();
            if (gamePeerTarget.equals((String) clientNameHash.get(userClient))
                    && !gamePeerTarget.equals((String) clientNameHash
                    .get(clientSocket)))
            { // 找到要发送信息的用户时
                synchronized (clientDataHash)
                {
                    // 建立输出流
                    DataOutputStream peerOutData = (DataOutputStream) clientDataHash
                            .get(userClient);
                    try
                    {
                        // 发送信息
                        peerOutData.writeUTF(gamePeerMsg);
                    }
                    catch (IOException es)
                    {
                        es.printStackTrace();
                    }
                }
                return false;
            }
        }
        return true;
    }

    // 发送反馈信息给连接到主机的人
    public void Feedback(String feedBackMsg)
    {
        synchronized (clientDataHash)
        {
            DataOutputStream outputData = (DataOutputStream) clientDataHash
                    .get(clientSocket);
            try
            {
                outputData.writeUTF(feedBackMsg);
            }
            catch (Exception eb)
            {
                eb.printStackTrace();
            }
        }
    }

    // 取得用户列表
    public String getUserList()
    {
        String userList = "/userlist";
        for (Enumeration enu = clientNameHash.elements(); enu.hasMoreElements();)
        {
            userList = userList + " " + (String) enu.nextElement();
        }
        return userList;
    }

    // 根据value值从Hashtable中取得相应的key
    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 sendInitMsg()
    {
        sendPublicMsg(getUserList());
        Feedback("/yourname " + (String) clientNameHash.get(clientSocket));
        Feedback("Java 五子棋客户端");
        Feedback("/list --更新用户列表");
        Feedback("/<username> <talk> --私聊");
        Feedback("注意:命令必须对所有用户发送");
    }

    public void closeClient()
    {
        serverMsgPanel.msgTextArea.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");
            }
        }
        synchronized (clientDataHash)
        { // 删除客户数据
            clientDataHash.remove(clientSocket);
        }
        synchronized (clientNameHash)
        { // 删除客户数据
            clientNameHash.remove(clientSocket);
        }
        sendPublicMsg(getUserList());
        serverMsgPanel.statusLabel.setText("当前连接数:" + clientDataHash.size());
        try
        {
            clientSocket.close();
        }
        catch (IOException exx)
        {
            exx.printStackTrace();
        }
        isClientClosed = true;
    }

    public void run()
    {
        DataInputStream inputData;
        synchronized (clientDataHash)
        {
            serverMsgPanel.statusLabel.setText("当前连接数:" + clientDataHash.size());
        }
        try
        {	// 等待连接到主机的信息
            inputData = new DataInputStream(clientSocket.getInputStream());
            sendInitMsg();
            while (true)
            {
                String message = inputData.readUTF();
                dealWithMsg(message);
            }
        }
        catch (IOException esx){}
        finally
        {
            if (!isClientClosed)
            {
                closeClient();
            }
        }
    }
}

3.开发服务器端

import java.io.*;
import java.net.*;
import java.awt.*;
import java.util.*;
import java.awt.event.*;

import javax.swing.JButton;
/**
 * Created by Administrator on 2016/11/21.
 */
public class FIRServer extends Frame implements ActionListener{
    JButton clearMsgButton = new JButton("清空列表");
    JButton serverStatusButton = new JButton("服务器状态");
    JButton closeServerButton = new JButton("关闭服务器");
    Panel buttonPanel = new Panel();
    ServerMsgPanel serverMsgPanel = new ServerMsgPanel();
    ServerSocket serverSocket;
    Hashtable clientDataHash = new Hashtable(50); //将客户端套接口和输出流绑定
    Hashtable clientNameHash = new Hashtable(50); //将客户端套接口和客户名绑定
    Hashtable chessPeerHash = new Hashtable(50); //将游戏创建者和游戏加入者绑定

    public FIRServer()
    {
        super("Java 五子棋服务器");
        setBackground(Color.LIGHT_GRAY);
        buttonPanel.setLayout(new FlowLayout());
        clearMsgButton.setSize(60, 25);
        buttonPanel.add(clearMsgButton);
        clearMsgButton.addActionListener(this);
        serverStatusButton.setSize(75, 25);
        buttonPanel.add(serverStatusButton);
        serverStatusButton.addActionListener(this);
        closeServerButton.setSize(75, 25);
        buttonPanel.add(closeServerButton);
        closeServerButton.addActionListener(this);
        add(serverMsgPanel, BorderLayout.CENTER);
        add(buttonPanel, BorderLayout.SOUTH);

        addWindowListener(new WindowAdapter()
        {
            public void windowClosing(WindowEvent e)
            {
                System.exit(0);
            }
        });
        pack();
        setVisible(true);
        setSize(400, 300);
        setResizable(false);
        validate();

        try
        {
            createServer(4331, serverMsgPanel);
        }
        catch (Exception e)
        {
            e.printStackTrace();
        }
    }

    // 用指定端口和面板创建服务器
    public void createServer(int port, ServerMsgPanel serverMsgPanel) throws IOException
    {
        Socket clientSocket; // 客户端套接口
        long clientAccessNumber = 1; // 连接到主机的客户数量
        this.serverMsgPanel = serverMsgPanel; // 设定当前主机
        try
        {
            serverSocket = new ServerSocket(port);
            serverMsgPanel.msgTextArea.setText("服务器启动于:"
                    + InetAddress.getLocalHost() + ":" //djr
                    + serverSocket.getLocalPort() + "\n");
            while (true)
            {
                // 监听客户端套接口的信息
                clientSocket = serverSocket.accept();
                serverMsgPanel.msgTextArea.append("已连接用户:" + clientSocket + "\n");
                // 建立客户端输出流
                DataOutputStream outputData = new DataOutputStream(clientSocket
                        .getOutputStream());
                // 将客户端套接口和输出流绑定
                clientDataHash.put(clientSocket, outputData);
                // 将客户端套接口和客户名绑定
                clientNameHash
                        .put(clientSocket, ("新玩家" + clientAccessNumber++));
                // 创建并运行服务器端线程
                FIRServerThread thread = new FIRServerThread(clientSocket,
                        clientDataHash, clientNameHash, chessPeerHash, serverMsgPanel);
                thread.start();
            }
        }
        catch (IOException ex)
        {
            ex.printStackTrace();
        }
    }

    public void actionPerformed(ActionEvent e)
    {
        if (e.getSource() == clearMsgButton)
        { // 清空服务器信息
            serverMsgPanel.msgTextArea.setText("");
        }
        if (e.getSource() == serverStatusButton)
        { // 显示服务器信息
            try
            {
                serverMsgPanel.msgTextArea.append("服务器信息:"
                        + InetAddress.getLocalHost() + ":"
                        + serverSocket.getLocalPort() + "\n");
            }
            catch (Exception ee)
            {
                ee.printStackTrace();
            }
        }
        if (e.getSource() == closeServerButton)
        { // 关闭服务器
            System.exit(0);
        }
    }

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

下面开始编写客户端模块

1.开发客户端

import java.awt.*;
import java.awt.event.*;
import java.io.*;
import java.net.*;

import javax.swing.JFrame;

import djr.chess.gui.UserChatPad;
import djr.chess.gui.UserControlPad;
import djr.chess.gui.UserInputPad;
import djr.chess.gui.UserListPad;
import djr.chess.pad.FIRPad;

/**
 * Created by Administrator on 2016/11/21.
 */
public class FIRClient extends Frame implements ActionListener,KeyListener {
    // 客户端套接口
    Socket clientSocket;
    // 数据输入流
    DataInputStream inputStream;
    // 数据输出流
    DataOutputStream outputStream;
    // 用户名
    String chessClientName = null;
    // 主机地址
    String host = null;
    // 主机端口
    int port = 4331;
    // 是否在聊天
    boolean isOnChat = false;
    // 是否在下棋
    boolean isOnChess = false;
    // 游戏是否进行中
    boolean isGameConnected = false;
    // 是否为游戏创建者
    boolean isCreator = false;
    // 是否为游戏加入者
    boolean isParticipant = false;
    // 用户列表区
    UserListPad userListPad = new UserListPad();
    // 用户聊天区
    UserChatPad userChatPad = new UserChatPad();
    // 用户操作区
    UserControlPad userControlPad = new UserControlPad();
    // 用户输入区
    UserInputPad userInputPad = new UserInputPad();
    // 下棋区
    FIRPad firPad = new FIRPad();
    // 面板区
    Panel southPanel = new Panel();
    Panel northPanel = new Panel();
    Panel centerPanel = new Panel();
    Panel eastPanel = new Panel();

    // 构造方法,创建界面
    public FIRClient()
    {
        super("Java 五子棋客户端");
        setLayout(new BorderLayout());
        host = userControlPad.ipInputted.getText();

        eastPanel.setLayout(new BorderLayout());
        eastPanel.add(userListPad, BorderLayout.NORTH);
        eastPanel.add(userChatPad, BorderLayout.CENTER);
        eastPanel.setBackground(Color.LIGHT_GRAY);

        userInputPad.contentInputted.addKeyListener(this);

        firPad.host = userControlPad.ipInputted.getText();
        centerPanel.add(firPad, BorderLayout.CENTER);
        centerPanel.add(userInputPad, BorderLayout.SOUTH);
        centerPanel.setBackground(Color.LIGHT_GRAY);
        userControlPad.connectButton.addActionListener(this);
        userControlPad.createButton.addActionListener(this);
        userControlPad.joinButton.addActionListener(this);
        userControlPad.cancelButton.addActionListener(this);
        userControlPad.exitButton.addActionListener(this);
        userControlPad.createButton.setEnabled(false);
        userControlPad.joinButton.setEnabled(false);
        userControlPad.cancelButton.setEnabled(false);

        southPanel.add(userControlPad, BorderLayout.CENTER);
        southPanel.setBackground(Color.LIGHT_GRAY);

        addWindowListener(new WindowAdapter()
        {
            public void windowClosing(WindowEvent e)
            {
                if (isOnChat)
                { // 聊天中
                    try
                    {  // 关闭客户端套接口
                        clientSocket.close();
                    }
                    catch (Exception ed){}
                }
                if (isOnChess || isGameConnected)
                { // 下棋中
                    try
                    {   // 关闭下棋端口
                        firPad.chessSocket.close();
                    }
                    catch (Exception ee){}
                }
                System.exit(0);
            }
        });

        add(eastPanel, BorderLayout.EAST);
        add(centerPanel, BorderLayout.CENTER);
        add(southPanel, BorderLayout.SOUTH);
        pack();
        setSize(670, 560);
        setVisible(true);
        setResizable(false);
        this.validate();
    }

    // 按指定的IP地址和端口连接到服务器
    public boolean connectToServer(String serverIP, int serverPort) throws Exception
    {
        try
        {
            // 创建客户端套接口
            clientSocket = new Socket(serverIP, serverPort);
            // 创建输入流
            inputStream = new DataInputStream(clientSocket.getInputStream());
            // 创建输出流
            outputStream = new DataOutputStream(clientSocket.getOutputStream());
            // 创建客户端线程
            FIRClientThread clientthread = new FIRClientThread(this);
            // 启动线程,等待聊天信息
            clientthread.start();
            isOnChat = true;
            return true;
        }
        catch (IOException ex)
        {
            userChatPad.chatTextArea
                    .setText("不能连接!\n");
        }
        return false;
    }

    // 客户端事件处理
    public void actionPerformed(ActionEvent e)
    {
        if (e.getSource() == userControlPad.connectButton)
        { // 连接到主机按钮单击事件
            host = firPad.host = userControlPad.ipInputted.getText(); // 取得主机地址
            try
            {
                if (connectToServer(host, port))
                {   // 成功连接到主机时,设置客户端相应的界面状态
                    userChatPad.chatTextArea.setText("");
                    userControlPad.connectButton.setEnabled(false);
                    userControlPad.createButton.setEnabled(true);
                    userControlPad.joinButton.setEnabled(true);
                    firPad.statusText.setText("连接成功,请等待!");
                }
            }
            catch (Exception ei)
            {
                userChatPad.chatTextArea
                        .setText("不能连接!\n");
            }
        }
        if (e.getSource() == userControlPad.exitButton)
        { // 离开游戏按钮单击事件
            if (isOnChat)
            {  // 若用户处于聊天状态中
                try
                { // 关闭客户端套接口
                    clientSocket.close();
                }
                catch (Exception ed){}
            }
            if (isOnChess || isGameConnected)
            { // 若用户处于游戏状态中
                try
                { // 关闭游戏端口
                    firPad.chessSocket.close();
                }
                catch (Exception ee){}
            }
            System.exit(0);
        }
        if (e.getSource() == userControlPad.joinButton)
        { // 加入游戏按钮单击事件
            String selectedUser = (String)userListPad.userList.getSelectedItem(); // 取得要加入的游戏
            if (selectedUser == null || selectedUser.startsWith("[inchess]") ||
                    selectedUser.equals(chessClientName))
            { // 若未选中要加入的用户,或选中的用户已经在游戏,则给出提示信息
                firPad.statusText.setText("必须选择一个用户!");
            }
            else
            { // 执行加入游戏的操作
                try
                {
                    if (!isGameConnected)
                    { // 若游戏套接口未连接
                        if (firPad.connectServer(firPad.host, firPad.port))
                        { // 若连接到主机成功
                            isGameConnected = true;
                            isOnChess = true;
                            isParticipant = true;
                            userControlPad.createButton.setEnabled(false);
                            userControlPad.joinButton.setEnabled(false);
                            userControlPad.cancelButton.setEnabled(true);
                            firPad.firThread.sendMessage("/joingame "
                                    + (String)userListPad.userList.getSelectedItem() + " "
                                    + chessClientName);
                        }
                    }
                    else
                    { // 若游戏端口连接中
                        isOnChess = true;
                        isParticipant = true;
                        userControlPad.createButton.setEnabled(false);
                        userControlPad.joinButton.setEnabled(false);
                        userControlPad.cancelButton.setEnabled(true);
                        firPad.firThread.sendMessage("/joingame "
                                + (String)userListPad.userList.getSelectedItem() + " "
                                + chessClientName);
                    }
                }
                catch (Exception ee)
                {
                    isGameConnected = false;
                    isOnChess = false;
                    isParticipant = false;
                    userControlPad.createButton.setEnabled(true);
                    userControlPad.joinButton.setEnabled(true);
                    userControlPad.cancelButton.setEnabled(false);
                    userChatPad.chatTextArea
                            .setText("不能连接: \n" + ee);
                }
            }
        }
        if (e.getSource() == userControlPad.createButton)
        { // 创建游戏按钮单击事件
            try
            {
                if (!isGameConnected)
                { // 若游戏端口未连接
                    if (firPad.connectServer(firPad.host, firPad.port))
                    { // 若连接到主机成功
                        isGameConnected = true;
                        isOnChess = true;
                        isCreator = true;
                        userControlPad.createButton.setEnabled(false);
                        userControlPad.joinButton.setEnabled(false);
                        userControlPad.cancelButton.setEnabled(true);
                        firPad.firThread.sendMessage("/creatgame "
                                + "[inchess]" + chessClientName);
                    }
                }
                else
                { // 若游戏端口连接中
                    isOnChess = true;
                    isCreator = true;
                    userControlPad.createButton.setEnabled(false);
                    userControlPad.joinButton.setEnabled(false);
                    userControlPad.cancelButton.setEnabled(true);
                    firPad.firThread.sendMessage("/creatgame "
                            + "[inchess]" + chessClientName);
                }
            }
            catch (Exception ec)
            {
                isGameConnected = false;
                isOnChess = false;
                isCreator = false;
                userControlPad.createButton.setEnabled(true);
                userControlPad.joinButton.setEnabled(true);
                userControlPad.cancelButton.setEnabled(false);
                ec.printStackTrace();
                userChatPad.chatTextArea.setText("不能连接: \n"
                        + ec);
            }
        }
        if (e.getSource() == userControlPad.cancelButton)
        { // 退出游戏按钮单击事件
            if (isOnChess)
            { // 游戏中
                firPad.firThread.sendMessage("/giveup " + chessClientName);
                firPad.setVicStatus(-1 * firPad.chessColor);
                userControlPad.createButton.setEnabled(true);
                userControlPad.joinButton.setEnabled(true);
                userControlPad.cancelButton.setEnabled(false);
                firPad.statusText.setText("请创建或加入游戏!");
            }
            if (!isOnChess)
            { // 非游戏中
                userControlPad.createButton.setEnabled(true);
                userControlPad.joinButton.setEnabled(true);
                userControlPad.cancelButton.setEnabled(false);
                firPad.statusText.setText("请创建或加入游戏!");
            }
            isParticipant = isCreator = false;
        }
    }

    public void keyPressed(KeyEvent e)
    {
        TextField inputwords = (TextField) e.getSource();
        if (e.getKeyCode() == KeyEvent.VK_ENTER)
        { // 处理回车按键事件
            if (userInputPad.userChoice.getSelectedItem().equals("所有用户"))
            { // 给所有人发信息
                try
                {
                    // 发送信息
                    outputStream.writeUTF(inputwords.getText());
                    inputwords.setText("");
                }
                catch (Exception ea)
                {
                    userChatPad.chatTextArea
                            .setText("不能连接到服务器!\n");
                    userListPad.userList.removeAll();
                    userInputPad.userChoice.removeAll();
                    inputwords.setText("");
                    userControlPad.connectButton.setEnabled(true);
                }
            }
            else
            { // 给指定人发信息
                try
                {
                    outputStream.writeUTF("/" + userInputPad.userChoice.getSelectedItem()
                            + " " + inputwords.getText());
                    inputwords.setText("");
                }
                catch (Exception ea)
                {
                    userChatPad.chatTextArea
                            .setText("不能连接到服务器!\n");
                    userListPad.userList.removeAll();
                    userInputPad.userChoice.removeAll();
                    inputwords.setText("");
                    userControlPad.connectButton.setEnabled(true);
                }
            }
        }
    }

    public void keyTyped(KeyEvent e) {}
    public void keyReleased(KeyEvent e) {}

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

2.开发客户端线程

import java.io.IOException;
import java.util.StringTokenizer;

import javax.swing.DefaultListModel;
import javax.swing.ListModel;

/**
 * Created by Administrator on 2016/11/21.
 */
public class FIRClientThread extends Thread{
    public FIRClient firClient;

    public FIRClientThread(FIRClient firClient)
    {
        this.firClient = firClient;
    }

    public void dealWithMsg(String msgReceived)
    {
        if (msgReceived.startsWith("/userlist "))
        { // 若取得的信息为用户列表
            StringTokenizer userToken = new StringTokenizer(msgReceived, " ");
            int userNumber = 0;
            // 清空客户端用户列表
            firClient.userListPad.userList.removeAll();
            // 清空客户端用户下拉框
            firClient.userInputPad.userChoice.removeAll();
            // 给客户端用户下拉框添加一个选项
            firClient.userInputPad.userChoice.addItem("所有用户");
            while (userToken.hasMoreTokens())
            { // 当收到的用户信息列表中存在数据时
                String user = (String) userToken.nextToken(" "); // 取得用户信息
                if (userNumber > 0 && !user.startsWith("[inchess]"))
                { // 用户信息有效时
                    firClient.userListPad.userList.add(user);// 将用户信息添加到用户列表中
                    firClient.userInputPad.userChoice.addItem(user); // 将用户信息添加到用户下拉框中
                }
                userNumber++;
            }
            firClient.userInputPad.userChoice.setSelectedIndex(0);// 下拉框默认选中所有人
        }
        else if (msgReceived.startsWith("/yourname "))
        { // 收到的信息为用户本名时
            firClient.chessClientName = msgReceived.substring(10); // 取得用户本名
            firClient.setTitle("Java 五子棋客户端 " + "用户名:"
                    + firClient.chessClientName); // 设置程序Frame的标题
        }
        else if (msgReceived.equals("/reject"))
        { // 收到的信息为拒绝用户时
            try
            {
                firClient.firPad.statusText.setText("不能加入游戏!");
                firClient.userControlPad.cancelButton.setEnabled(false);
                firClient.userControlPad.joinButton.setEnabled(true);
                firClient.userControlPad.createButton.setEnabled(true);
            }
            catch (Exception ef)
            {
                firClient.userChatPad.chatTextArea
                        .setText("Cannot close!");
            }
            firClient.userControlPad.joinButton.setEnabled(true);
        }
        else if (msgReceived.startsWith("/peer "))
        { // 收到信息为游戏中的等待时
            firClient.firPad.chessPeerName = msgReceived.substring(6);
            if (firClient.isCreator)
            { // 若用户为游戏建立者
                firClient.firPad.chessColor = 1; // 设定其为黑棋先行
                firClient.firPad.isMouseEnabled = true;
                firClient.firPad.statusText.setText("黑方下...");
            }
            else if (firClient.isParticipant)
            { // 若用户为游戏加入者
                firClient.firPad.chessColor = -1; // 设定其为白棋后性
                firClient.firPad.statusText.setText("游戏加入,等待对手.");
            }
        }
        else if (msgReceived.equals("/youwin"))
        { // 收到信息为胜利信息
            firClient.isOnChess = false;
            firClient.firPad.setVicStatus(firClient.firPad.chessColor);
            firClient.firPad.statusText.setText("对手退出");
            firClient.firPad.isMouseEnabled = false;
        }
        else if (msgReceived.equals("/OK"))
        { // 收到信息为成功创建游戏
            firClient.firPad.statusText.setText("游戏创建等待对手");
        }

        else if (msgReceived.equals("/error"))
        { // 收到信息错误
            firClient.userChatPad.chatTextArea.append("错误,退出程序.\n");
        }
        else
        {
            firClient.userChatPad.chatTextArea.append(msgReceived + "\n");
            firClient.userChatPad.chatTextArea.setCaretPosition(
                    firClient.userChatPad.chatTextArea.getText().length());
        }
    }

    public void run()
    {
        String message = "";
        try
        {
            while (true)
            {
                // 等待聊天信息,进入wait状态
                message = firClient.inputStream.readUTF();
                dealWithMsg(message);
            }
        }
        catch (IOException es){}
    }
}

至此,网络版五子棋就算是开发完成了。关于这么多类和包的关系如下图:


  • 9
    点赞
  • 66
    收藏
    觉得还不错? 一键收藏
  • 4
    评论
评论 4
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值