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

📄 ch19.htm

📁 对于程序员来说可以利用JAVA来开发网络游戏!
💻 HTM
📖 第 1 页 / 共 5 页
字号:
<TT><FONT FACE="Courier">private synchronized void sendStatus(Connect4Player
me, int message) {<BR>
&nbsp;&nbsp;Vector theirVector = ((me == player1) ?&nbsp;&nbsp;p2Queue
: p1Queue);<BR>
&nbsp;&nbsp;theirVector.addElement(new Integer(message));<BR>
&nbsp;&nbsp;notify();<BR>
}</FONT></TT>
</BLOCKQUOTE>
<P>
The integer status message passed in as the second parameter to
<TT><FONT FACE="Courier">sendStatus</FONT></TT> is added to the
player's event queue. The <TT><FONT FACE="Courier">notify</FONT></TT>
method is then called, which causes the <TT><FONT FACE="Courier">wait</FONT></TT>
call in <TT><FONT FACE="Courier">getStatus</FONT></TT> to return.
This shows the synchronized nature of these two methods: <TT><FONT FACE="Courier">getStatus</FONT></TT>
waits until <TT><FONT FACE="Courier">sendStatus</FONT></TT> provides
the information it needs.
<P>
That sums up the code for the server. At this point, you have
half a game. Too bad you can't do much with it yet; you still
need a client. Knowing that, let's take a look at the code involved
in making the client side work.
<H4><B>The Client</B></H4>
<P>
The client side of NetConnect4 consists of four classes, three
of which you've seen before:
<UL>
<LI><TT><FONT FACE="Courier">Connect4State</FONT></TT>
<LI><TT><FONT FACE="Courier">Connect4Engine</FONT></TT>
<LI><TT><FONT FACE="Courier">Connect4</FONT></TT>
<LI><TT><FONT FACE="Courier">Connect4ClientConnection</FONT></TT>
</UL>
<P>
The first two classes, <TT><FONT FACE="Courier">Connect4State</FONT></TT>
and <TT><FONT FACE="Courier">Connect4Engine</FONT></TT>, come
directly from the original Connect4 game. They provide the core
logic for establishing the rules of the game and determining whether
the game has been won, lost, or tied. These two classes require
no modification for NetConnect4, so refer to <A HREF="ch16.htm" >Day 16</A>
if you need to refresh your memory on how they work.
<P>
The <TT><FONT FACE="Courier">Connect4</FONT></TT> applet class
should also be familiar from the original game. A few modifications
have been made to this version of <TT><FONT FACE="Courier">Connect4</FONT></TT>
to accommodate the fact that the game is running over a network.
The primary changes to the <TT><FONT FACE="Courier">Connect4</FONT></TT>
class are in the <TT><FONT FACE="Courier">run</FONT></TT> method,
which handles establishing a server connection and coordinating
the state of the game with the graphics and user interface. Listing
19.5 contains the source code for the <TT><FONT FACE="Courier">run</FONT></TT>
method.
<HR>
<BLOCKQUOTE>
<B>Listing 19.5. The </B><TT><B><FONT FACE="Courier">Connect4</FONT></B></TT><B>
class's </B><TT><B><FONT FACE="Courier">run</FONT></B></TT><B>
method.<BR>
</B>
</BLOCKQUOTE>
<BLOCKQUOTE>
<TT><FONT FACE="Courier">public void run() {<BR>
&nbsp;&nbsp;// Track the images<BR>
&nbsp;&nbsp;int gameState = 0;<BR>
&nbsp;&nbsp;newGame();<BR>
&nbsp;&nbsp;try {<BR>
&nbsp;&nbsp;&nbsp;&nbsp;tracker.waitForID(0);<BR>
&nbsp;&nbsp;}<BR>
&nbsp;&nbsp;catch (InterruptedException e) {<BR>
&nbsp;&nbsp;&nbsp;&nbsp;return;<BR>
&nbsp;&nbsp;}<BR>
<BR>
&nbsp;&nbsp;try {<BR>
&nbsp;&nbsp;&nbsp;&nbsp;// Create the connection<BR>
&nbsp;&nbsp;&nbsp;&nbsp;connection = new Connect4ClientConnection(this);
<BR>
&nbsp;&nbsp;&nbsp;&nbsp;while (connection.isConnected()) {<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;int istatus = connection.getTheirMove();
<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;if (istatus == Connect4ClientConnection.GAMEOVER)
{<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;myMove = false;
<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;gameState = 0;
<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;return;<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;// Wait for the other player
<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;else if (istatus == Connect4ClientConnection.PLSWAIT)
{<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;if (gameState
== 0) {<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;gameState
= Connect4ClientConnection.PLSWAIT;<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;status
= new String(&quot;Wait for player&quot;);<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;repaint();
<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;} else {<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;System.out.println(&quot;Gameflow
error!&quot;);<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;return;
<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;else if (istatus == Connect4ClientConnection.THEIRTURN)
{<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;status = new String(&quot;Their
turn.&quot;);<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;myMove = false;
<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;gameState = Connect4ClientConnection.THEIRTURN;
<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;repaint();<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;else if (istatus == Connect4ClientConnection.YOURTURN)
{<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;gameState = Connect4ClientConnection.YOURTURN;
<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;status = new String(&quot;Your
turn.&quot;);<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;repaint();<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;myMove = true;
<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;else if (istatus == Connect4ClientConnection.THEYWON)
{<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;gameState = Connect4ClientConnection.THEYWON;
<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;else if (istatus == Connect4ClientConnection.THEYQUIT)
{<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;gameState = Connect4ClientConnection.THEYQUIT;
<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;status = new String(&quot;Opponent
Quit!&quot;);<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;myMove = false;
<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;repaint();<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;return;<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;else if (istatus == Connect4ClientConnection.THEYTIED)
{<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;gameState = Connect4ClientConnection.THEYTIED;
<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;else if (istatus == Connect4ClientConnection.ERROR)
{<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;System.out.println(&quot;error!&quot;);
<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;gameState = Connect4ClientConnection.ERROR;
<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;status = new String(&quot;Error!
Game Over&quot;);<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;myMove = false;
<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;repaint();<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;return;<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;else {<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;if (gameState
== Connect4ClientConnection.THEIRTURN) {<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;//
Note that we make the move, but wait for the *server*<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;//
to say YOURTURN before we change the status. Otherwise,<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;//
we have a race condition - if the player moves before<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;//
the server says YOURTURN, we go back into that mode,<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;//
allowing the player to make two turns in a row!<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Point
pos = gameEngine.makeMove(1, istatus);<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;blueSnd.play();
<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;repaint();
<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;else if (gameState
== Connect4ClientConnection.THEYWON) {<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;status
= new String(&quot;Sorry, you lose!&quot;);<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;myMove
= false;<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;gameOver
= true;<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;repaint();
<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;sadSnd.play();
<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;return;
<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;else if (gameState
== Connect4ClientConnection.THEYTIED) {<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;status
= new String(&quot;Tie game!&quot;);<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;myMove
= false;<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;gameOver
= true;<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;repaint();
<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;sadSnd.play();
<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;return;
<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;else {<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;System.out.println(&quot;Gameflow
error!&quot;);<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;return;
<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<BR>
&nbsp;&nbsp;&nbsp;&nbsp;}<BR>
&nbsp;&nbsp;}<BR>
&nbsp;&nbsp;catch (IOException e) {<BR>
&nbsp;&nbsp;&nbsp;&nbsp;System.out.println(&quot;IOException:
&quot;+e);<BR>
&nbsp;&nbsp;}<BR>
}</FONT></TT>
</BLOCKQUOTE>
<HR>
<P>
The logic used in the <TT><FONT FACE="Courier">run</FONT></TT>
method flows directly from the logic you just learned about in
the <TT><FONT FACE="Courier">Game</FONT></TT> class. This logic
revolves around handling whose turn it is, along with communicating
whether a game has been won, lost, or tied.
<P>
The <TT><FONT FACE="Courier">mouseDown</FONT></TT> method also
has been modified a little to accommodate sending game information
to the server. Listing 19.6 shows the source code for the <TT><FONT FACE="Courier">mouseDown</FONT></TT>
method.
<HR>
<BLOCKQUOTE>
<B>Listing 19.6. The </B><TT><B><FONT FACE="Courier">Connect4</FONT></B></TT><B>
class's </B><TT><B><FONT FACE="Courier">mouseDown</FONT></B></TT><B>
method.<BR>
</B>
</BLOCKQUOTE>
<BLOCKQUOTE>
<TT><FONT FACE="Courier">public boolean mouseDown(Event evt, int
x, int y) {<BR>
&nbsp;&nbsp;if (gameOver) {<BR>
&nbsp;&nbsp;&nbsp;&nbsp;thread = null;<BR>
&nbsp;&nbsp;&nbsp;&nbsp;thread = new Thread(this);<BR>
&nbsp;&nbsp;&nbsp;&nbsp;thread.start();<BR>
&nbsp;&nbsp;}<BR>
&nbsp;&nbsp;else if (myMove) {<BR>
&nbsp;&nbsp;&nbsp;&nbsp;// Make sure the move is valid<BR>
&nbsp;&nbsp;&nbsp;&nbsp;Point pos = gameEngine.makeMove(0, x /
28);<BR>
&nbsp;&nbsp;&nbsp;&nbsp;if (pos.y &gt;= 0) {<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;if (!gameEngine.isWinner(0))
<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;if (!gameEngine.isTie())
{<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;redSnd.play();
<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;status
= new String(&quot;Their turn.&quot;);<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;connection.sendMove(pos.x);
<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;myMove
= false;<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;else {<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;sadSnd.play();
<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;status
= new String(&quot;It's a tie!&quot;);<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;gameOver
= true;<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;connection.sendITIED();
<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;connection.sendMove(pos.x);
<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;else {<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;applauseSnd.play();
<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;status

⌨️ 快捷键说明

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