Coverage Report - com.buckosoft.fibs.BuckoFIBS.ClientReceiveParser
 
Classes in this File Line Coverage Branch Coverage Complexity
ClientReceiveParser
0%
0/384
0%
0/143
5.833
ClientReceiveParser$Mode
0%
0/3
N/A
5.833
ClientReceiveParser$MyTimerTask
0%
0/9
N/A
5.833
ClientReceiveParser$MyTimerTaskSavedGames
0%
0/10
N/A
5.833
ClientReceiveParser$RegState
0%
0/5
N/A
5.833
 
 1  
 /******************************************************************************
 2  
  * ClientReceiveParser.java - Parse messages received from the network.
 3  
  * $Id$
 4  
  * 
 5  
  * BuckoFIBS - Backgammon by BuckoSoft
 6  
  * Copyright© 2009,2010 - Dick Balaska - BuckoSoft, Corp.
 7  
  * 
 8  
  * $Log$
 9  
  * Revision 1.28  2013/09/12 06:36:33  dick
 10  
  * Doubles dispatches gameEvents.
 11  
  *
 12  
  * Revision 1.27  2011/07/16 02:40:13  dick
 13  
  * Add CantWatchSelf.
 14  
  * YouDouble becomes a gameManager message.
 15  
  *
 16  
  * Revision 1.26  2011/07/04 03:39:16  dick
 17  
  * Route more messages through the GameManager.
 18  
  *
 19  
  * Revision 1.25  2011/06/22 05:53:58  dick
 20  
  * You Tell PlayerX is different than the other messages.
 21  
  * Add NobodyHeardYou.
 22  
  *
 23  
  * Revision 1.24  2011/06/18 19:30:32  dick
 24  
  * Resigning and new game messages.
 25  
  *
 26  
  * Revision 1.23  2011/06/14 19:13:52  dick
 27  
  * YouCantMove is a GameEvent.
 28  
  *
 29  
  * Revision 1.22  2011/06/13 04:43:19  dick
 30  
  * FIBS_PlayerWantsToResign is now a GameManager message.
 31  
  *
 32  
  * Revision 1.21  2011/06/05 06:57:46  dick
 33  
  * playerListPane becomes playerListTab.
 34  
  * Select the profile into the database upon login.
 35  
  *
 36  
  * Revision 1.20  2011/06/02 18:48:41  dick
 37  
  * 3 more FIBS messages become GameEvents.
 38  
  *
 39  
  * Revision 1.19  2011/05/31 19:35:54  dick
 40  
  * Fix new user registration.  FIBS_OneUserPerPerson is our cue to send the data.
 41  
  *
 42  
  * Revision 1.18  2011/05/22 22:58:59  dick
 43  
  * GAME_MOVE becomes GAME_EVENT.
 44  
  *
 45  
  * Revision 1.17  2011/05/22 05:10:16  dick
 46  
  * AcceptRejectDouble and BearingOff go to the GameManager.
 47  
  *
 48  
  * Revision 1.16  2011/05/21 04:56:42  dick
 49  
  * Work on integrating GUI game functions by routing them through the game manager now.
 50  
  * Particularly, YourMove and ResumeGame.
 51  
  *
 52  
  * Revision 1.15  2011/05/17 22:53:25  dick
 53  
  * FIBS_YouRoll gets dispatched to the GameManager.
 54  
  *
 55  
  * Revision 1.14  2011/05/15 02:18:18  dick
 56  
  * Gather the events to send to the GameManager.
 57  
  *
 58  
  * Revision 1.13  2011/05/14 04:43:01  dick
 59  
  * I needed to deal with some lightweight Boards.
 60  
  * So finally make the primary document Document
 61  
  * and demote just the Board handling to a domain object.
 62  
  *
 63  
  * Revision 1.12  2011/05/13 14:57:00  dick
 64  
  * Route game move messages through the GameManager so they can be animated.
 65  
  *
 66  
  * Revision 1.11  2011/05/11 22:22:42  dick
 67  
  * Working on animating moves.
 68  
  *
 69  
  * Revision 1.10  2011/05/10 16:08:20  dick
 70  
  * Fix the javadoc pointers to the source code.
 71  
  *
 72  
  * Revision 1.9  2011/01/04 17:31:45  dick
 73  
  * Update the player in the playlist when we get new whoinfo on him.
 74  
  *
 75  
  * Revision 1.8  2010/12/29 07:46:35  dick
 76  
  * Add WaitForLastInvitation and WaitForAcceptResign.
 77  
  *
 78  
  * Revision 1.7  2010/12/22 04:34:14  dick
 79  
  * Set the chatPane combobox before setting the player.
 80  
  *
 81  
  * Revision 1.6  2010/03/03 13:12:21  inim
 82  
  * Replaced (c) sign in comment mangled by CVS default encoding back to UTF-8
 83  
  *
 84  
  * Revision 1.5  2010/03/03 12:19:49  inim
 85  
  * Moved source to UTF8 encoding from CP1252 encoding. To this end all source files' (c) message was updated to "Copyright© 2009,2010 - Dick Balaska - BuckoSoft, Corp.". This replaces the (c) sign to UTF8, and adds the new year 2010.
 86  
  *
 87  
  * Revision 1.4  2010/02/15 09:22:22  dick
 88  
  * Play audio cues when Your opponent doubles or when he drops the match.
 89  
  *
 90  
  * Revision 1.3  2010/02/09 02:57:39  dick
 91  
  * Don't do autoGreedyBearoff if only watching a match.
 92  
  *
 93  
  * Revision 1.2  2010/02/08 09:14:13  dick
 94  
  * Add support for autoGreedyBearoff.  When the game turns to a race, enable greedy bearoffs.
 95  
  *
 96  
  * Revision 1.1  2010/02/04 05:57:53  inim
 97  
  * Mavenized project folder layout
 98  
  *
 99  
  * Revision 1.60  2010/01/25 21:09:58  dick
 100  
  * Remove the savedMatch icon from the playerList when the match is done.
 101  
  * Set the chatPane to "Tell (lastOpponent)".
 102  
  *
 103  
  * Revision 1.59  2010/01/23 06:14:35  dick
 104  
  * Handle removedFinishedMatch().  Handle youInvited().
 105  
  *
 106  
  * Revision 1.58  2009/05/09 03:42:27  dick
 107  
  * Add PlayerBannedWatch and Doesn'tWantYouToWatch.
 108  
  *
 109  
  * Revision 1.57  2009/03/16 18:52:17  dick
 110  
  * Play the YourTurn sound only if you can actually move.  (Respond to the "Please move" message.)
 111  
  *
 112  
  * Revision 1.56  2009/03/04 19:06:26  dick
 113  
  * Do message routing for the PlayerReportPane.
 114  
  *
 115  
  * Revision 1.55  2009/02/27 05:47:41  dick
 116  
  * Handle the whois "last logout" line.
 117  
  *
 118  
  * Revision 1.54  2009/02/25 09:41:12  dick
 119  
  * Handle ATTENTION messages from FIBS when it is shutting down.
 120  
  *
 121  
  * Revision 1.53  2009/02/25 07:42:54  dick
 122  
  * Calculate the duration of the match and store that with the FinishedMatch, will make a nice statistic someday.
 123  
  *
 124  
  * Revision 1.52  2009/02/24 05:48:47  dick
 125  
  * Handle connectionAborted() and ERROR from the ClientAdapter.
 126  
  *
 127  
  * Revision 1.51  2009/02/22 07:05:47  dick
 128  
  * if props.isDisplayRecv() then display them all.
 129  
  *
 130  
  * Revision 1.50  2009/02/21 17:59:42  dick
 131  
  * Update the RatingGraphPanel when a match is complete.
 132  
  *
 133  
  * Revision 1.49  2009/02/20 10:21:23  dick
 134  
  * Fill out a FinishedMatch and send it to the database.
 135  
  *
 136  
  * Revision 1.48  2009/02/17 21:12:56  dick
 137  
  * Display unknown messages as an error, not as an unhandled cookie.
 138  
  * (We know that the cookie is "unknown").
 139  
  *
 140  
  * Revision 1.47  2009/02/16 06:57:07  dick
 141  
  * Dispatch to ROLL_OR_DOUBLE instead of calling the methods directly.
 142  
  *
 143  
  * Revision 1.46  2009/02/14 12:19:15  dick
 144  
  * Between move work.
 145  
  *
 146  
  * Revision 1.45  2009/02/12 06:25:06  dick
 147  
  * Update the board when resuming a match.
 148  
  *
 149  
  * Revision 1.44  2009/02/11 09:05:48  dick
 150  
  * Better beginning and ending your turn.
 151  
  *
 152  
  * Revision 1.43  2009/02/09 22:44:28  dick
 153  
  * shutdown() cancels pending timers.
 154  
  * Handle resign (both ways).
 155  
  *
 156  
  * Revision 1.42  2009/02/06 07:56:48  dick
 157  
  * Working on doubles.
 158  
  *
 159  
  * Revision 1.41  2009/02/03 09:44:18  dick
 160  
  * Just give us a handle to MainDialog already.
 161  
  * Add some audio events.
 162  
  *
 163  
  * Revision 1.40  2009/02/02 08:42:24  dick
 164  
  * Several various message cleanups.
 165  
  *
 166  
  * Revision 1.39  2009/02/01 23:22:59  dick
 167  
  * FIBS_Done is an in-game message.
 168  
  *
 169  
  * Revision 1.38  2009/02/01 21:15:06  dick
 170  
  * Fire off a "show saved" message after we have finished who'ing.
 171  
  *
 172  
  * Revision 1.37  2009/01/31 08:46:25  dick
 173  
  * Fire off a 'who' 1 second after we finish the initial table.  FIBS doesn't send all the players across.
 174  
  * YourMove goes to the GameManager now.
 175  
  *
 176  
  * Revision 1.36  2009/01/31 06:08:49  dick
 177  
  * Dispatch board and double commands to the GameManager.
 178  
  *
 179  
  * Revision 1.35  2009/01/29 08:27:05  dick
 180  
  * Dispose of "waves" commands gracefully.
 181  
  *
 182  
  * Revision 1.34  2009/01/28 22:28:27  dick
 183  
  * Try a different Javadoc reference to the Mode.
 184  
  *
 185  
  * Revision 1.33  2009/01/28 22:26:22  dick
 186  
  * Javadoc.
 187  
  *
 188  
  * Revision 1.32  2009/01/28 19:42:47  dick
 189  
  * Prettier cvs link in the javadoc.
 190  
  *
 191  
  * Revision 1.31  2009/01/28 08:34:18  dick
 192  
  * If we get a FIBS_Unknown, then display the previous message too, because it's probably
 193  
  * a busted end-of-string detector from the previous message.
 194  
  *
 195  
  * Revision 1.30  2009/01/27 19:14:31  dick
 196  
  * Handle savedMatch as a warning.
 197  
  *
 198  
  * Revision 1.29  2009/01/27 06:54:23  dick
 199  
  * uninvite us if a player starts playing.
 200  
  *
 201  
  * Revision 1.28  2009/01/27 05:44:43  dick
 202  
  * public parseMessage becomes private dispatchMessage because the entry point is now the Adapter's dispatch().
 203  
  *
 204  
  * Revision 1.27  2009/01/26 17:35:15  dick
 205  
  * Push the CookieMonster down to the ClientConnection.  ClientAdapter now emits the cookie with the string.
 206  
  * There are many messages besides the known "BadBoard" messages that are a result of runon messages (missing crlf).
 207  
  * CookieMonster is going to need to do a full regexp scan and see if there is anything on the right that needs to be pushed back as another message.
 208  
  *
 209  
  * Revision 1.26  2009/01/26 07:22:51  dick
 210  
  * Process the "You Roll" command as a yourMove trigger.
 211  
  *
 212  
  * Revision 1.25  2009/01/24 17:05:05  dick
 213  
  * Add parseReplayMessage(s).
 214  
  *
 215  
  * Revision 1.24  2009/01/18 04:51:26  dick
 216  
  * add dispatch(YOUR_MOVE);
 217  
  * CommandDispatcher becomes CommandDispatcherImpl.
 218  
  * I should probably abstract out the methods that are being directly called in the Impl.
 219  
  *
 220  
  * Revision 1.23  2009/01/13 18:27:39  dick
 221  
  * Handle Ready To Play
 222  
  *
 223  
  * Revision 1.22  2009/01/12 21:59:39  dick
 224  
  * Javadoc.
 225  
  *
 226  
  * Revision 1.21  2009/01/12 20:08:29  dick
 227  
  * Implement ClientAdapter as part of the new ClientConnection decoupling.
 228  
  *
 229  
  * Revision 1.20  2009/01/10 05:04:02  dick
 230  
  * Handle match over messages special.  Fibs doesn't send a final board after the match is over, so we have to fake it out.
 231  
  *
 232  
  * Revision 1.19  2009/01/09 19:09:32  dick
 233  
  * Handle the FIBS_Timeout message.
 234  
  * Handle more game messages.
 235  
  *
 236  
  * Revision 1.18  2009/01/09 08:10:02  dick
 237  
  * Chat, game, and system message routing.
 238  
  *
 239  
  * Revision 1.17  2009/01/07 02:32:45  dick
 240  
  * Better resetting of our state between client connections.
 241  
  *
 242  
  * Revision 1.16  2009/01/06 08:05:28  dick
 243  
  * Handle registering a new user.
 244  
  *
 245  
  * Revision 1.15  2008/12/20 23:02:10  dick
 246  
  * Support for Own Info.
 247  
  *
 248  
  * Revision 1.14  2008/12/15 01:47:36  dick
 249  
  * Just echo FirstRoll and MakesFirstMove
 250  
  *
 251  
  * Revision 1.13  2008/12/14 06:43:23  dick
 252  
  * Add YouAreWatching (switch to board).
 253  
  * Only display a Cookie? if the pref says to.
 254  
  *
 255  
  * Revision 1.12  2008/12/13 06:57:11  dick
 256  
  * Move ClientConnection, CookieMonster, and FIBSMessages to their own network package.
 257  
  *
 258  
  * Revision 1.11  2008/12/13 06:20:49  dick
 259  
  * Dispatch NetworkConnected when we receive the welcome message.
 260  
  *
 261  
  * Revision 1.10  2008/12/11 20:27:33  dick
 262  
  * Handle CantInviteSelf, StartingNewGame, and Board.
 263  
  *
 264  
  * Revision 1.9  2008/12/11 09:58:50  dick
 265  
  * Display Network In messages in a different color.
 266  
  *
 267  
  * Revision 1.8  2008/12/11 08:46:19  dick
 268  
  * parse incoming Chat Message.
 269  
  *
 270  
  * Revision 1.7  2008/12/10 17:59:25  dick
 271  
  * Display system messages in color.
 272  
  *
 273  
  * Revision 1.6  2008/12/09 19:32:36  dick
 274  
  * Add Goodbye and NewMatchRequest handling.
 275  
  *
 276  
  * Revision 1.5  2008/12/09 01:48:55  dick
 277  
  * Early CookieMonster integration.
 278  
  *
 279  
  * Revision 1.4  2008/12/07 22:52:27  dick
 280  
  * Start playing with the cookie monster.
 281  
  *
 282  
  * Revision 1.3  2008/04/05 01:42:11  dick
 283  
  * Add eol when outputting the motd.
 284  
  *
 285  
  * Revision 1.2  2008/04/01 04:21:26  dick
 286  
  * Handle player logging out.
 287  
  *
 288  
  * Revision 1.1  2008/03/31 07:08:00  dick
 289  
  * Parse messages received from the network.
 290  
  *
 291  
  */
 292  
 
 293  
 /* 
 294  
  * This program is free software: you can redistribute it and/or modify
 295  
  * it under the terms of the GNU General Public License as published by
 296  
  * the Free Software Foundation, either version 3 of the License, or
 297  
  * (at your option) any later version.
 298  
  *
 299  
  * This program is distributed in the hope that it will be useful,
 300  
  * but WITHOUT ANY WARRANTY; without even the implied warranty of
 301  
  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 302  
  * GNU General Public License for more details.
 303  
  *
 304  
  * You should have received a copy of the GNU General Public License
 305  
  * along with this program.  If not, see <http://www.gnu.org/licenses/>.
 306  
  *
 307  
  * The Original Code is BuckoFIBS, <http://www.buckosoft.com/BuckoFIBS/>.
 308  
  * The Initial Developer of the Original Code is Dick Balaska and BuckoSoft, Corp.
 309  
  * 
 310  
  */
 311  
 package com.buckosoft.fibs.BuckoFIBS;
 312  
 
 313  
 import java.util.Date;
 314  
 import java.util.Timer;
 315  
 import java.util.TimerTask;
 316  
 
 317  
 import com.buckosoft.fibs.BuckoFIBS.AudioManager.Cue;
 318  
 import com.buckosoft.fibs.BuckoFIBS.gui.MainDialog;
 319  
 import com.buckosoft.fibs.BuckoFIBS.gui.SystemMessagesTextPane;
 320  
 import com.buckosoft.fibs.BuckoFIBS.gui.chatWindow.ChatPane;
 321  
 import com.buckosoft.fibs.domain.CookieString;
 322  
 import com.buckosoft.fibs.domain.FinishedMatch;
 323  
 import com.buckosoft.fibs.domain.Player;
 324  
 import com.buckosoft.fibs.net.ClientAdapter;
 325  
 import com.buckosoft.fibs.net.ClientConnection;
 326  
 import com.buckosoft.fibs.net.FIBSMessages;
 327  
 
 328  
 
 329  
 /** Parse and dispatch messages received from the network.
 330  
  * @author Dick Balaska
 331  
  * @since 2008/03/31
 332  
  * @version $Revision$ <br> $Date$
 333  
  * @see <a href="http://cvs.buckosoft.com/Projects/BuckoFIBS/BuckoFIBS/src/main/java/com/buckosoft/fibs/BuckoFIBS/ClientReceiveParser.java">cvs ClientReceiveParser.java</a>
 334  
  */
 335  0
 public class ClientReceiveParser implements FIBSMessages, ClientAdapter {
 336  
         private        final static boolean DEBUG = false;
 337  
 
 338  
         /** We connect to fibs in either normal communications mode, or a special "Register new user" mode.
 339  
          */
 340  0
         public enum Mode {
 341  
                 /** Default, normal fibs connection */
 342  0
                 Run,
 343  
                 /** Special register new user commands are needed. */
 344  0
                 Register
 345  
         }
 346  
         private        MainDialog                mainDialog;
 347  0
         private        CommandDispatcher        commandDispatcher = null;
 348  0
         private        BFProperties                properties = null;
 349  0
         private ClientConnection clientConnection = null;
 350  0
         private        Mode                        mode = Mode.Run;
 351  
         private        final static String eol = "\r\n";
 352  
 
 353  0
         private        String lastInviter = null;
 354  
         private        String lastMessage0;
 355  
         private        String lastMessage1;
 356  
         private int                lastCookie0;
 357  
         private int                lastCookie1;
 358  
         
 359  0
         private        boolean        whoVirgin = true;
 360  0
         private        boolean needSavedGames = true;
 361  0
         private        Date        matchStartTime = null;
 362  
 //        private        boolean        matchResuming = false;
 363  0
         private        boolean        matchResumingYourTurn = false;
 364  
 
 365  0
         private        FinishedMatch                finishedMatch = null;
 366  
 
 367  
         /** Set the reference to the instance of MainDialog
 368  
          * @param mainDialog The MainDialog that is running
 369  
          */
 370  
         public        void setMainDialog(MainDialog mainDialog) {
 371  0
                 this.mainDialog = mainDialog;
 372  0
         }
 373  
 
 374  
         /** Set the reference to our CommandDispatcher
 375  
          * @param commandDispatcher The CommandDispatcher
 376  
          */
 377  
         public void setCommandDispatcher(CommandDispatcher commandDispatcher) {
 378  0
                 this.commandDispatcher = commandDispatcher;
 379  0
         }
 380  
 
 381  
         /** Set the reference to our ClientConnection
 382  
          * @param clientConnection The ClientConnection
 383  
          */
 384  
         public void setClientConnection(ClientConnection clientConnection) {
 385  0
                 this.clientConnection = clientConnection;
 386  0
         }
 387  
 
 388  
         /** Set the Properties/User preferences
 389  
          * @param properties The loaded properties
 390  
          */
 391  
         public        void setProperties(BFProperties properties) {
 392  0
                 this.properties = properties;
 393  0
         }
 394  
 
 395  
         /** We connect to fibs in either normal communications mode, or a special "Register new user" mode.
 396  
          * @param mode The mode that we should parse messages in
 397  
          * @see com.buckosoft.fibs.BuckoFIBS.ClientReceiveParser.Mode
 398  
          */
 399  
         public void setMode(Mode mode) {
 400  0
                 this.mode = mode;
 401  0
                 clientConnection.resetFIBSCookieMonster();
 402  0
         }
 403  
 
 404  
         /** Kill all timers and tasks this object owns as we prepare to go bye-bye.
 405  
          */
 406  
         public void shutdown() {
 407  0
                 if (this.myTimer != null) {
 408  0
                         this.myTimer.cancel();
 409  0
                         this.myTimer = null;
 410  
                 }
 411  0
                 if (this.myTimerSavedGames != null) {
 412  0
                         this.myTimerSavedGames.cancel();
 413  0
                         this.myTimerSavedGames = null;
 414  
                 }
 415  0
                 if (this.myTimerTaskSavedGames != null) {
 416  0
                         this.myTimerTaskSavedGames.cancel();
 417  0
                         this.myTimerTaskSavedGames = null;
 418  
                 }
 419  0
         }
 420  
 
 421  
         private void dispatchMessage(int cookie, String s) {
 422  
                 CookieString gl;
 423  0
                 lastMessage1 = lastMessage0;
 424  0
                 lastMessage0 = s;
 425  0
                 lastCookie1 = lastCookie0;
 426  0
                 lastCookie0 = cookie;
 427  
                 if (DEBUG)
 428  
                         System.out.println("cookie = " + cookie);
 429  0
                 if (this.properties.isDisplayRecv())
 430  0
                         this.commandDispatcher.writeSystemMessageln(SystemMessagesTextPane.NETWORKMSG, s);
 431  0
                 if (mode == Mode.Register) {
 432  0
                         parseMessageRegister(s, cookie);
 433  0
                         return;
 434  
                 }
 435  0
                 switch (cookie) {
 436  
                 // These do nothing here.
 437  
                 case CLIP_MOTD_END:
 438  
                 case FIBS_BoardstyleSetTo:
 439  
                 case FIBS_SavedMatchesHeader:
 440  
                 case FIBS_Empty:
 441  
                 case FIBS_UsersHeardYou:        // JavaFIBS puts this in the status bar, which i don't have
 442  
                 case FIBS_YouAlreadyRolled:
 443  0
                         break;
 444  
                 case CLIP_OWN_INFO:
 445  0
                         this.commandDispatcher.dispatch(CommandDispatcher.Command.OWN_INFO, s);
 446  0
                         break;
 447  
                 case CLIP_WHO_INFO:
 448  0
                         parseWhoInfo(s);
 449  0
                         break;
 450  
                 case CLIP_WHO_END:
 451  0
                         handleWhoEnd();
 452  0
                         break;
 453  
                 case FIBS_SavedMatchPlaying:
 454  
                 case FIBS_SavedMatchReady:
 455  
                 case FIBS_SavedMatch:
 456  
                         //if (DEBUG)
 457  0
                                 System.out.println(s);
 458  0
                         this.commandDispatcher.dispatch(CommandDispatcher.Command.SAVED_MATCH, s);
 459  0
                         break;
 460  
                 case FIBS_NoSavedMatch:
 461  0
                         showErrorMessage(s);
 462  0
                         this.commandDispatcher.dispatch(CommandDispatcher.Command.SAVED_MATCH, s);
 463  0
                         break;
 464  
                 case FIBS_LoginPrompt:
 465  0
                         whoVirgin = true;
 466  0
                         this.commandDispatcher.writeSystemMessageln(s);
 467  0
                         this.mainDialog.getDB().setActiveProfile(this.properties.getSelectedProfile());
 468  0
                         this.mainDialog.updateRatingPanel();
 469  0
                         this.mainDialog.setPlayerListTabVisible();
 470  0
                         clientConnection.sendLogin();
 471  0
                         break;
 472  
                 case CLIP_LOGIN:
 473  0
                         parsePlayerLoggedIn(s);
 474  0
                         break;
 475  
                 case CLIP_LOGOUT:
 476  0
                         parsePlayerLoggedOut(s);
 477  0
                         break;
 478  
                 case FIBS_OpponentLogsOut:
 479  
                 case FIBS_OpponentLeftGame:
 480  0
                         parseAbortMatch(s);
 481  0
                         break;
 482  
                 case FIBS_Goodbye:
 483  0
                         disconnectFromServer();
 484  0
                         break;
 485  
                 case FIBS_Timeout:
 486  0
                         this.commandDispatcher.writeSystemMessageln(SystemMessagesTextPane.NETWORKMSG, s);
 487  0
                         disconnectFromServer();
 488  0
                         break;
 489  
                 case CLIP_WELCOME:
 490  0
                         this.commandDispatcher.dispatch(CommandDispatcher.Command.NETWORK_CONNECTED);
 491  0
                         break;
 492  
                 case FIBS_YouAreWatching:
 493  0
                         this.commandDispatcher.writeSystemMessageln(SystemMessagesTextPane.NETWORKMSG, s);
 494  0
                         this.commandDispatcher.dispatch(CommandDispatcher.Command.WATCHING);
 495  0
                         break;
 496  
                 case CLIP_SAYS:
 497  0
                         if (s.startsWith("12 RepBotNG ")) {
 498  0
                                 this.mainDialog.getPlayerReportPane().receiveLine(s, cookie);
 499  0
                                 return;
 500  
                         }
 501  0
                         parseChatMessage(s, cookie);
 502  0
                         break;
 503  
                 case CLIP_WHISPERS:
 504  
                 case CLIP_KIBITZES:
 505  0
                         parseChatMessage(s, cookie);
 506  0
                         break;
 507  
                 case CLIP_SHOUTS:
 508  0
                         if (s.startsWith("13 MissManners"))
 509  0
                                 this.commandDispatcher.dispatch(CommandDispatcher.Command.MISS_MANNERS, s);
 510  0
                         if(!properties.isMsgIgnoreShouts())
 511  0
                                 parseChatMessage(s, cookie);
 512  
                         break;
 513  
                 case CLIP_YOU_SAY:
 514  0
                         parseChatMessage(s, cookie);
 515  0
                         break;
 516  
                 case CLIP_YOU_SHOUT:
 517  
                 case CLIP_YOU_WHISPER:
 518  
                 case CLIP_YOU_KIBITZ:
 519  0
                         parseYouChatMessage(s, cookie);
 520  0
                         break;
 521  
                 case FIBS_NobodyHeardYou:
 522  0
                         this.commandDispatcher.writeChatMessageln(null, cookie, s);
 523  
                 case FIBS_Waves:
 524  
                 case FIBS_WavesAgain:
 525  0
                         if(!properties.isMsgIgnoreShouts())
 526  0
                                 parseWavesMessage(s);
 527  
                         break;
 528  
                 case FIBS_NewMatchRequest:
 529  
                 case FIBS_ResumeMatchRequest:
 530  0
                         parseInvite(s);
 531  0
                         break;
 532  
                 case FIBS_CantInviteSelf:
 533  
                 case FIBS_CantWatchSelf:
 534  
                 case FIBS_NotInteresting:
 535  
                 case FIBS_PlayerNotPlaying:
 536  
                 case FIBS_PlayerRefusingGames:
 537  
                 case FIBS_NotYourTurnToRoll:
 538  
                 case FIBS_NotYourTurnToMove:
 539  
                 case FIBS_PlayerBannedWatch:
 540  
                 case FIBS_DoesntWantYouToWatch:
 541  0
                         showErrorMessage(s);
 542  0
                         break;
 543  
                 case FIBS_ResumeMatchAck0:
 544  
                 case FIBS_ResumeMatchAck5:
 545  0
                         displayGameMessage(s);
 546  0
                         startNewGame(true);
 547  
 //                        this.matchResuming = true;
 548  0
                         break;
 549  
                 case FIBS_Turn:
 550  0
                         displayGameMessage(s);
 551  0
                         parseResumeMatchTurn(s, cookie);
 552  0
                         break;
 553  
                 case FIBS_MatchLength:
 554  0
                         displayGameMessage(s);
 555  0
                         parseResumeMatchLength(s);
 556  0
                         break;
 557  
                 case FIBS_Board:
 558  
                         if (DEBUG)
 559  
                                 System.out.println(s);
 560  0
                         this.mainDialog.getDocument().getBoard().parseFibsBoard(s);
 561  0
                         gl = new CookieString(cookie, s);
 562  0
                         this.commandDispatcher.dispatch(CommandDispatcher.Command.GAME_EVENT, gl);
 563  0
                         if (this.matchResumingYourTurn) {
 564  0
                                 if (this.mainDialog.getDocument().getBoard().isYouMayDouble()) {
 565  0
                                         if (this.mainDialog.getDocument().getBoard().getDice()[0][0] == 0) {
 566  0
                                                 this.commandDispatcher.dispatch(CommandDispatcher.Command.ROLL_OR_DOUBLE);
 567  
                                         }
 568  
                                 }
 569  0
                                 this.matchResumingYourTurn = false; 
 570  
                         }
 571  0
                         doAutoGreedyBearoff();
 572  0
                         break;
 573  
                 case FIBS_NewMatchAck10:
 574  0
                         this.commandDispatcher.writeSystemMessageln(SystemMessagesTextPane.NETWORKMSG, s);
 575  0
                         this.mainDialog.setGameMessagesTabVisible();
 576  0
                         break;
 577  
                 case FIBS_NewMatchAck2:
 578  
                 case FIBS_FirstRoll:
 579  
                 case FIBS_MakesFirstMove:
 580  
                 case FIBS_PlayerRolls:
 581  
                 case FIBS_YouRoll:
 582  
                 case FIBS_PlayerMoves:
 583  
                 case FIBS_CantMove:
 584  
                 case FIBS_OnlyPossibleMove:
 585  
                 case FIBS_PleaseMove:
 586  
                 case FIBS_YourTurnToMove:
 587  
                 case FIBS_AcceptRejectDouble:
 588  
                 case FIBS_WatchResign:
 589  
                 case FIBS_ResignRefused:
 590  
                 case FIBS_AcceptWins:
 591  
                 case FIBS_PlayerWantsToResign:
 592  
                 case FIBS_YouCantMove:
 593  
                 case FIBS_BearingOff:
 594  
                 case FIBS_YouAcceptAndWin:
 595  
                 case FIBS_YouResign:
 596  
                 case FIBS_YouReject:
 597  
                 case FIBS_YouDouble:
 598  0
                         displayGameMessage(s);
 599  0
                         gl = new CookieString(cookie, s);
 600  0
                         this.commandDispatcher.dispatch(CommandDispatcher.Command.GAME_EVENT, gl);
 601  0
                         break;
 602  
                 case FIBS_StartingNewGame:
 603  0
                         startNewGame(false);
 604  0
                         displayGameMessage(s);
 605  0
                         gl = new CookieString(cookie, s);
 606  0
                         this.commandDispatcher.dispatch(CommandDispatcher.Command.GAME_EVENT, gl);
 607  0
                         break;
 608  
                 case FIBS_YouWinMatch:
 609  
                 case FIBS_PlayerWinsMatch:
 610  0
                         parseMatchOverMessage(s, cookie);
 611  0
                         displayGameMessage(s);
 612  0
                         break;
 613  
                 case FIBS_ReadyTrue:
 614  
                 case FIBS_ReadyFalse:
 615  0
                         parseReadyMessage(cookie);
 616  0
                         break;
 617  
 //                case FIBS_AcceptRejectDouble:
 618  
 //                        handleAcceptRejectDouble();
 619  
 //                        break;
 620  
                 case FIBS_JoinNextGame: 
 621  0
                         this.commandDispatcher.writeNetworkMessageln("join");
 622  0
                         break;
 623  
                 case FIBS_PlayerWinsGame:
 624  
                 case FIBS_ScoreUpdate:
 625  
                 case FIBS_ResignWins:
 626  
                 case FIBS_PlayerStartsWatching:
 627  
                 case FIBS_PointsFor:
 628  
                 case FIBS_YouWinGame:
 629  
                 case FIBS_CantMoveFirstMove:
 630  
                 case FIBS_RollBeforeMove:
 631  
                 case FIBS_Done:
 632  
                 case FIBS_GreedyTrue:                        // XXX: Someday, change the icon on this state
 633  
                 case FIBS_GreedyFalse:
 634  
                 case FIBS_ResignYouWin:
 635  
                 case FIBS_PleaseWaitForJoin:
 636  
                 case FIBS_YouGiveUp:
 637  
                 case FIBS_MustMove:
 638  0
                         displayGameMessage(s);
 639  0
                         break;
 640  
                 case FIBS_PlayerAcceptsDouble:
 641  0
                         gl = new CookieString(cookie, s);
 642  0
                         this.commandDispatcher.dispatch(CommandDispatcher.Command.GAME_EVENT, gl);
 643  0
                         this.mainDialog.getDocument().setYouDouble(false);
 644  0
                         displayGameMessage(s);
 645  0
                         break;
 646  
                 case FIBS_DidntDoubleOrResign:
 647  0
                         displayGameError(s);
 648  0
                         break;
 649  
                 case FIBS_PlayersStartingMatch:
 650  
                 case FIBS_PlayerStopsWatching:
 651  
                 case FIBS_PlayersStartingUnlimitedMatch:
 652  
                 case FIBS_ResumingLimitedMatch:
 653  
                 case FIBS_ResumingUnlimitedMatch:
 654  
                 case FIBS_MatchResult:
 655  0
                         parseOtherMatchMessage(s);
 656  0
                         break;
 657  
                 case FIBS_PlayerInfoStart:
 658  
                 case FIBS_LastLogin:
 659  
                 case FIBS_StillLoggedIn:
 660  
                 case FIBS_NotLoggedIn:
 661  
                 case FIBS_ReadyWatchingPlaying:
 662  
                 case FIBS_RatingExperience:
 663  
                 case FIBS_NoEmail:
 664  
                 case FIBS_EmailAddress:
 665  
                 case FIBS_IsPlayingWith:
 666  
                 case FIBS_HasSavedGames:
 667  
                 case FIBS_HasNoSavedGames:
 668  
                 case FIBS_NoInfo:
 669  0
                         this.mainDialog.getPlayerReportPane().receiveLine(s, cookie);
 670  
 //                        this.commandDispatcher.writeSystemMessageln(SystemMessagesTextPane.NETWORKMSG, s);
 671  0
                         break;
 672  
                 // Just echo the message to the window
 673  
                 case FIBS_PreLogin:
 674  
                 case CLIP_MOTD_BEGIN:
 675  
                 case FIBS_TypeJoin:
 676  
                 case FIBS_YouStopWatching:
 677  
                 case FIBS_YouAlreadyPlaying:
 678  
                 case FIBS_AlreadyPlaying:
 679  
                 case FIBS_LastLogout:
 680  
                 case FIBS_NotPlaying:
 681  
                 case FIBS_NoUser:
 682  
                 case FIBS_EchoJunk:
 683  
                 case FIBS_WaitForLastInvitation:
 684  
                 case FIBS_WaitForAcceptResign:
 685  
                 case FIBS_YourEmailChanged:
 686  0
                         this.commandDispatcher.writeSystemMessageln(SystemMessagesTextPane.NETWORKMSG, s);
 687  0
                         break;
 688  
                 case FIBS_DidntInvite:
 689  
                 case FIBS_NotWatchingPlaying:
 690  
                 case FIBS_NoSavedGames:
 691  0
                         this.commandDispatcher.writeSystemMessageln(SystemMessagesTextPane.NETWORKMSG, s);
 692  0
                         this.mainDialog.setSystemMessagesTabVisible();
 693  0
                         break;
 694  
                 case FIBS_WARNINGSavedMatch:
 695  0
                         parseInviteWarning(s);
 696  0
                         break;
 697  
                 case FIBS_DoubleTrue:
 698  0
                         parseDoublesOnOff(true);
 699  0
                         displayGameMessage(s);
 700  0
                         break;
 701  
                 case FIBS_DoubleFalse:
 702  0
                         parseDoublesOnOff(false);
 703  0
                         displayGameMessage(s);
 704  0
                         break;
 705  
                 case FIBS_Doubles:
 706  0
                         parseDoubles(s);
 707  0
                         gl = new CookieString(cookie, s);
 708  0
                         this.commandDispatcher.dispatch(CommandDispatcher.Command.GAME_EVENT, gl);
 709  0
                         displayGameMessage(s);
 710  0
                         break;
 711  
                 case FIBS_YouAcceptDouble:
 712  0
                         displayGameMessage(s);
 713  0
                         this.mainDialog.getDocument().setYouDouble(false);
 714  0
                         this.mainDialog.updateBoard();
 715  0
                         break;
 716  
                 case FIBS_RollOrDouble:
 717  0
                         this.commandDispatcher.dispatch(CommandDispatcher.Command.ROLL_OR_DOUBLE);
 718  0
                         break;
 719  
 //                case FIBS_YourTurnToMove:        // First roll of the game, always 2 moves
 720  
 //                        this.commandDispatcher.dispatch(CommandDispatcher.Command.YOUR_MOVE, "2");
 721  
 //                        break;
 722  
                 case FIBS_YouInvited:
 723  0
                         parseYouInvited(s);
 724  0
                         break;
 725  
 //                case FIBS_PleaseMove:
 726  
 //                        parsePleaseMove(s);
 727  
 //                        this.mainDialog.playSound(Cue.YourTurn);
 728  
 //                        displayGameMessage(s);
 729  
 //                        break;
 730  
                 case FIBS_ATTENTION:
 731  
                 case FIBS_ShuttingDown:
 732  
                 case FIBS_Rebooting:
 733  0
                         this.mainDialog.playSound(Cue.FibsAttention);
 734  
                 case FIBS_GamesWillBeSaved:
 735  
                 case FIBS_UnknownCommand:
 736  
                 case FIBS_GameWasSaved:
 737  0
                         this.commandDispatcher.writeSystemMessageln(SystemMessagesTextPane.ERROR, s);
 738  0
                         break;
 739  
                 case FIBS_Unknown:
 740  0
                         this.commandDispatcher.writeSystemMessageln(SystemMessagesTextPane.ERROR, "Unknown message from FIBS: '" + s + "'");
 741  0
                         this.commandDispatcher.writeSystemMessageln(SystemMessagesTextPane.ERROR, "First char is " + new Integer(s.charAt(0)));
 742  0
                         break;
 743  
                 default:
 744  0
                         if (this.commandDispatcher.getProperties().isDEBUG_ShowUnhandledCookies()) {
 745  0
                                 String t = "Cookie? " + cookie + " '" + s + "'";
 746  0
                                 this.commandDispatcher.writeSystemMessageln(SystemMessagesTextPane.ERROR, t);
 747  0
                                 System.out.println(t);
 748  0
                                 t = "Last message was " + lastCookie1 + " '" + lastMessage1 + "'";
 749  0
                                 if (cookie == FIBS_Unknown) {
 750  0
                                         this.commandDispatcher.writeSystemMessageln(SystemMessagesTextPane.ERROR, t);
 751  0
                                         System.out.println(t);
 752  
                                 }
 753  
                         }
 754  
                         break;
 755  
                 }
 756  0
         }
 757  
 
 758  
 //        /** Replay a message from a saved game or a previous move in this game
 759  
 //         * @param s
 760  
 //         */
 761  
 /*        public void parseReplayMessage(int cookie, String s) {
 762  
                 if (DEBUG)
 763  
                         System.out.println("cookie = " + cookie);
 764  
                 switch (cookie) {
 765  
                 case FIBS_Board:
 766  
                         this.commandDispatcher.dispatch(CommandDispatcher.Command.FIBS_BOARD, s);
 767  
                         break;
 768  
                 default:
 769  
 //                        if (this.commandDispatcher.getProperties().isDEBUG_ShowUnhandledCookies())
 770  
                                 this.commandDispatcher.writeSystemMessageln(SystemMessagesTextPane.ERROR, "Replay? " + cookie + " '" + s + "'");
 771  
                         break;
 772  
                 }
 773  
         }
 774  
 */
 775  0
         private enum RegState {
 776  0
                 name,
 777  0
                 password,
 778  0
                 password1,
 779  0
                 done
 780  
         }
 781  0
         private RegState regState = RegState.name;
 782  
         
 783  
         private void parseMessageRegister(String s, int fibsCookie) {
 784  0
                 int profileId = this.commandDispatcher.getProperties().getSelectedProfile();
 785  
                 String password;
 786  0
                 switch (fibsCookie) {
 787  
                 case FIBS_LoginPrompt:
 788  0
                         this.commandDispatcher.writeRegisterUserMessage("Logging in...");
 789  0
                         this.commandDispatcher.writeSystemMessageln(s);
 790  0
                         clientConnection.sendMessage("guest" + eol);
 791  0
                         break;
 792  
                 case FIBS_OneUserPerPerson:
 793  0
                         String userName = this.commandDispatcher.getProperties().getUserName(profileId);
 794  0
                         this.commandDispatcher.writeRegisterUserMessage("Registering user " + userName);
 795  0
                         this.clientConnection.sendMessage("name " + userName + eol);
 796  0
                         regState = RegState.password;
 797  0
                         break;
 798  
 
 799  
                 case FIBS_GivePassword:
 800  0
                         password = this.commandDispatcher.getProperties().getPassword(profileId);
 801  0
                         this.clientConnection.sendMessage(password + eol);
 802  0
                         break;
 803  
                 case FIBS_RetypePassword:
 804  0
                         password = this.commandDispatcher.getProperties().getPassword(profileId);
 805  0
                         this.clientConnection.sendMessage(password + eol);
 806  0
                         break;
 807  
                 case FIBS_YouAreRegistered:
 808  0
                         this.commandDispatcher.writeRegisterUserMessage("Success!");
 809  
 //                        this.clientConnection.sendMessage("bye" + eol);
 810  0
                         this.commandDispatcher.dispatch(CommandDispatcher.Command.CONNECT_TO_SERVER);
 811  0
                         break;
 812  
                 case FIBS_UseAnotherName:
 813  0
                         this.commandDispatcher.dispatch(CommandDispatcher.Command.BAD_NEW_USER, s);
 814  0
                         break;
 815  
                 case CLIP_MOTD_BEGIN:
 816  0
                         if (regState == RegState.password) {
 817  0
                                 password = this.commandDispatcher.getProperties().getPassword(profileId);
 818  0
                                 this.clientConnection.sendMessage(password + eol);
 819  0
                                 regState = RegState.password1;
 820  0
                                 break;
 821  
                         }
 822  0
                         if (regState == RegState.password1) {
 823  0
                                 password = this.commandDispatcher.getProperties().getPassword(profileId);
 824  0
                                 this.clientConnection.sendMessage(password + eol);
 825  0
                                 regState = RegState.done;
 826  
                                 break;
 827  
                         }
 828  
                 }
 829  0
         }
 830  
 
 831  
         private void showErrorMessage(String s) {
 832  0
                 this.commandDispatcher.writeSystemMessageln(SystemMessagesTextPane.ERROR, s);
 833  0
         }
 834  
 
 835  
         private void disconnectFromServer() {
 836  0
                 this.commandDispatcher.dispatch(CommandDispatcher.Command.SHUTTING_DOWN);
 837  0
                 this.clientConnection.resetFIBSCookieMonster();
 838  0
         }
 839  
 
 840  
         private        void parseWhoInfo(String s) {
 841  0
                 Player p = new Player();
 842  0
                 p.parsePlayer(s);
 843  0
                 if (this.finishedMatch != null && p.getName().equals(this.mainDialog.getDocument().getName())) {
 844  0
                         this.finishedMatch.setRatingAfterMatch(p.getRating());
 845  0
                         this.mainDialog.getDB().store(this.finishedMatch);
 846  0
                         this.finishedMatch = null;
 847  0
                         this.mainDialog.updateRatingPanel();
 848  0
                         this.mainDialog.getDB().updateOpponent(p);
 849  0
                         this.mainDialog.getPlayerListTab().getPlayerTableModel().playerChanged(p);
 850  
                 }
 851  0
                 this.commandDispatcher.dispatch(CommandDispatcher.Command.PLAYER_CHANGED, p);
 852  0
         }
 853  
 
 854  
         private void handleWhoEnd() {
 855  0
                 if (this.whoVirgin) {
 856  0
                         sendDelayedWhoCommand();
 857  0
                 } else if (this.needSavedGames) {
 858  0
                         sendDelayedSavedGamesCommand();
 859  0
                         this.needSavedGames = false;
 860  
                 }
 861  0
         }
 862  
 
 863  
         private        void parsePlayerLoggedOut(String s) {
 864  0
                 String[] ss = s.split(" ");
 865  0
                 this.commandDispatcher.dispatch(CommandDispatcher.Command.PLAYER_GONE, ss[1]);
 866  0
                 if (this.properties.isMsgLoginsAndOuts())
 867  0
                         this.commandDispatcher.writeSystemMessageln(SystemMessagesTextPane.NORMAL, ss[2] + " " + ss[3] + " " + ss[4]);
 868  0
         }
 869  
 
 870  
         private        void parseAbortMatch(String s) {
 871  0
                 this.commandDispatcher.writeSystemMessageln(SystemMessagesTextPane.ERROR, s);
 872  0
                 this.mainDialog.playSound(Cue.MatchAborted);
 873  0
                 this.commandDispatcher.writeNetworkMessageln("show saved");
 874  0
         }
 875  
 
 876  
         /** Just log the player to the messages list.
 877  
          * Adding the player to the table comes with the CLIP_WHO_INFO message
 878  
          * @param s The Login message
 879  
          */
 880  
         private void parsePlayerLoggedIn(String s) {
 881  0
                 String[] ss = s.split(" ");
 882  0
                 if (this.properties.isMsgLoginsAndOuts())
 883  0
                         this.commandDispatcher.writeSystemMessageln(SystemMessagesTextPane.NORMAL, ss[2] + " " + ss[3] + " " + ss[4]);
 884  0
         }
 885  
 
 886  
         private void parseOtherMatchMessage(String s) {
 887  0
                 if (this.properties.isMsgOtherMatchInfo())
 888  0
                         this.commandDispatcher.writeSystemMessageln(SystemMessagesTextPane.NORMAL, s);
 889  0
         }
 890  
 
 891  
         private void parseInvite(String s) {
 892  0
                 String[] ss = s.split(" ");
 893  0
                 this.commandDispatcher.dispatch(CommandDispatcher.Command.INVITED, 
 894  
                                 ss[0], 
 895  0
                                 ss[3].equals("resume") ? ss[3] : ss[5]);
 896  0
                 lastInviter = ss[0];
 897  0
         }
 898  
 
 899  
         private void parseInviteWarning(String s) {
 900  0
                 if (lastInviter != null) {
 901  0
                         this.commandDispatcher.dispatch(CommandDispatcher.Command.INVITE_WARNING, lastInviter, s);
 902  
                 }
 903  0
         }
 904  
 
 905  
         private        void parseYouInvited(String s) {
 906  0
                 String[] ss = s.split(" ");
 907  0
                 this.commandDispatcher.dispatch(CommandDispatcher.Command.YOU_INVITED, ss[3]);
 908  0
                 this.commandDispatcher.writeSystemMessageln(SystemMessagesTextPane.NORMAL, s);
 909  0
         }
 910  
 
 911  
         private        void parseDoubles(String s) {
 912  0
                 this.commandDispatcher.writeNetworkMessageln("board");
 913  0
         }
 914  
 
 915  
         private        void startNewGame(boolean resume) {
 916  0
                 if (this.matchStartTime == null)
 917  0
                         this.matchStartTime = new Date();
 918  0
                 if (!resume)
 919  0
                         this.commandDispatcher.dispatch(CommandDispatcher.Command.START_GAME);
 920  
                 else
 921  0
                         this.commandDispatcher.dispatch(CommandDispatcher.Command.RESUME_GAME);
 922  
                         
 923  0
         }
 924  
 
 925  
         private void displayGameMessage(String s) {
 926  0
                 this.commandDispatcher.writeGameMessageln(s);
 927  0
         }
 928  
         private void displayGameError(String s) {
 929  0
                 this.commandDispatcher.writeGameErrorln(s);
 930  0
         }
 931  
 
 932  
         private void parseMatchOverMessage(String s, int cookie) {
 933  0
                 String[] ss = s.split(" ");
 934  0
                 this.commandDispatcher.dispatch(CommandDispatcher.Command.MATCH_OVER, ss[0], ss[6]);
 935  0
                 String opponentName = this.mainDialog.getDocument().getBoard().getPlayerName()[1];
 936  0
                 int[] scores = this.mainDialog.getDocument().getBoard().getMatchScore();
 937  0
                 if (this.mainDialog.getDocument().getBoard().isYouPlaying()) {
 938  0
                         this.finishedMatch = new FinishedMatch();
 939  0
                         this.finishedMatch.setMatchPoints(Integer.parseInt(ss[3]));
 940  0
                         this.finishedMatch.setYourScore(scores[0]);
 941  0
                         this.finishedMatch.setOpponentScore(scores[1]);
 942  0
                         Date endDate = new Date();
 943  0
                         this.finishedMatch.setDate(endDate);
 944  0
                         this.finishedMatch.setDuration((int)((endDate.getTime()-this.matchStartTime.getTime())/1000));
 945  0
                         this.matchStartTime = null;
 946  0
                         this.mainDialog.getDocument().removeSavedMatch(opponentName);
 947  0
                         Player op = this.mainDialog.getDB().getPlayer(opponentName);
 948  0
                         if (op == null) {
 949  0
                                 op = this.mainDialog.getPlayerTableModel().getPlayer(opponentName);
 950  0
                                 this.mainDialog.getDB().store(op);
 951  
                         }
 952  0
                         op.setSavedMatch(null);                                                // remove the icon from the player list
 953  0
                         this.finishedMatch.setOpponentId(op.getId());
 954  0
                         this.commandDispatcher.dispatch(CommandDispatcher.Command.PLAYER_CHANGED, op);
 955  
 
 956  0
                         this.mainDialog.getChatPane().setupComboBoxCommand(ChatPane.Command.Tell);
 957  0
                         this.mainDialog.getChatPane().maybeAddPlayer(opponentName);
 958  
                 }
 959  0
         }
 960  
 
 961  
         private void parseDoublesOnOff(boolean onoff) {
 962  0
                 this.commandDispatcher.dispatch(CommandDispatcher.Command.TOGGLE_DOUBLE, new Boolean(onoff));
 963  
                 
 964  0
         }
 965  
 
 966  
         private void parseReadyMessage(int cookie) {
 967  0
                 boolean b = false;
 968  0
                 if (cookie == FIBS_ReadyTrue)
 969  0
                         b = true;
 970  0
                 this.commandDispatcher.dispatch(CommandDispatcher.Command.READY_TO_PLAY, new Boolean(b));
 971  0
         }
 972  
 
 973  
         private void parseChatMessage(String s, int cookie) {
 974  0
                 int i = s.indexOf(' ', 3);
 975  0
                 if (i == -1)
 976  0
                         return;
 977  0
                 String name = s.substring(3, i);
 978  0
                 String text = s.substring(i+1);
 979  0
                 this.mainDialog.playSound(Cue.ChatReceived);
 980  0
                 this.commandDispatcher.writeChatMessageln(name, cookie, text);
 981  0
         }
 982  
 
 983  
         private void parseYouChatMessage(String s, int cookie) {
 984  0
                 this.mainDialog.playSound(Cue.ChatReceived);
 985  0
                 this.commandDispatcher.writeChatMessageln(null, cookie, s.substring(3));
 986  0
         }
 987  
         
 988  
         private void parseWavesMessage(String s) {
 989  0
                 this.commandDispatcher.writeSystemMessageln(s);
 990  0
         }
 991  
 
 992  
         private void parseResumeMatchTurn(String s, int cookie) {
 993  0
                 String t = s.substring(6, s.length()-1);
 994  0
                 if (this.mainDialog.getDocument().getName().equals(t)) {
 995  0
                         this.matchResumingYourTurn = true;
 996  0
                         CookieString cs = new CookieString(cookie, s);
 997  0
                         this.commandDispatcher.dispatch(CommandDispatcher.Command.GAME_EVENT, cs);
 998  
                 }
 999  0
         }
 1000  
 
 1001  
         private void parseResumeMatchLength(String s) {
 1002  
                 
 1003  0
         }
 1004  
 
 1005  
 //        private void handleAcceptRejectDouble() {
 1006  
 //                this.commandDispatcher.dispatch(CommandDispatcher.Command.ACCEPT_OR_DECLINE_DOUBLE);
 1007  
 //        }
 1008  
 
 1009  
         private void doAutoGreedyBearoff() {
 1010  0
                 if (!this.mainDialog.getDocument().getBoard().isYouPlaying())
 1011  0
                         return;
 1012  0
                 if (!this.properties.isAutoGreedyBearOff())
 1013  0
                         return;
 1014  0
                 if (this.mainDialog.getDocument().isGreedy())
 1015  0
                         return;
 1016  0
                 if (this.mainDialog.getDocument().getBoard().isRace())
 1017  0
                         this.commandDispatcher.dispatch(CommandDispatcher.Command.TOGGLE_GREEDY_BEAROFF);
 1018  0
         }
 1019  
 
 1020  
         /* (non-Javadoc)
 1021  
          * @see com.buckosoft.fibs.net.ClientAdapter#dispatch(java.lang.String)
 1022  
          */
 1023  
         @Override
 1024  
         public void dispatch(int cookie, String s) {
 1025  0
                 this.dispatchMessage(cookie, s);
 1026  0
         }
 1027  
 
 1028  
         /* (non-Javadoc)
 1029  
          * @see com.buckosoft.fibs.net.ClientAdapter#writeSystemMessageln(com.buckosoft.fibs.net.ClientAdapter.MessageRoute, java.lang.String)
 1030  
          */
 1031  
         @Override
 1032  
         public void writeSystemMessageln(MessageRoute route, String s) {
 1033  0
                 this.writeSystemMessage(route, s + eol);
 1034  0
         }
 1035  
 
 1036  
         /* (non-Javadoc)
 1037  
          * @see com.buckosoft.fibs.net.ClientAdapter#writeSystemMessage(com.buckosoft.fibs.net.ClientAdapter.MessageRoute, java.lang.String)
 1038  
          */
 1039  
         @Override
 1040  
         public void writeSystemMessage(MessageRoute route, String s) {
 1041  0
                 if (route == ClientAdapter.MessageRoute.NETWORKOUT)
 1042  0
                         this.commandDispatcher.writeSystemMessage(SystemMessagesTextPane.NETWORKOUT, s);
 1043  0
                 else if (route == ClientAdapter.MessageRoute.DEBUG)
 1044  0
                         this.commandDispatcher.writeSystemMessage(SystemMessagesTextPane.DEBUG, s);
 1045  0
                 else if (route == ClientAdapter.MessageRoute.SYSTEM)
 1046  0
                         this.commandDispatcher.writeSystemMessage(SystemMessagesTextPane.NORMAL, s);
 1047  0
                 else if (route == ClientAdapter.MessageRoute.ERROR)
 1048  0
                         this.commandDispatcher.writeSystemMessage(SystemMessagesTextPane.ERROR, s);
 1049  0
         }
 1050  
 
 1051  
         
 1052  
         @Override
 1053  
         public void connectionAborted() {
 1054  0
                 this.commandDispatcher.dispatch(CommandDispatcher.Command.DISCONNECT_FROM_NETWORK);
 1055  0
         }
 1056  
 
 1057  
 
 1058  
         //////////////////////////////////////////////////////////////////////////
 1059  
         // Timer task which does a "who" after a couple of seconds in order to grab
 1060  
         // more of the players on FIBS.
 1061  0
         private        Timer        myTimer = null;
 1062  0
         private        TimerTask        myTimerTask = null;
 1063  
 
 1064  
         private        void        sendDelayedWhoCommand() {
 1065  0
                 if (myTimer != null) {
 1066  0
                         return;
 1067  
                 }
 1068  0
                 myTimer = new Timer();
 1069  
                 try {
 1070  0
                         myTimerTask = new MyTimerTask(this);
 1071  0
                         myTimer.schedule(myTimerTask, 2000);
 1072  0
                 } catch (IllegalStateException e) {
 1073  0
                         e.printStackTrace();
 1074  0
                 }
 1075  0
         }
 1076  
 
 1077  
         private class MyTimerTask extends TimerTask {
 1078  
                 private        ClientReceiveParser crp;
 1079  
 
 1080  0
                 MyTimerTask(ClientReceiveParser crp) {
 1081  0
                         super();
 1082  0
                         this.crp = crp;
 1083  0
                 }
 1084  
                 /* (non-Javadoc)
 1085  
                  * @see java.util.TimerTask#run()
 1086  
                  */
 1087  
                 @Override
 1088  
                 public void run() {
 1089  0
                         this.crp.commandDispatcher.writeNetworkMessageln("who");
 1090  0
                         this.crp.whoVirgin = false;
 1091  0
                         this.crp.myTimer.cancel();
 1092  0
                         this.crp.myTimer = null;
 1093  0
                 }
 1094  
         }
 1095  
 
 1096  
         //////////////////////////////////////////////////////////////////////////
 1097  
         // Timer task which does a "who" after a couple of seconds in order to grab
 1098  
         // more of the players on FIBS.
 1099  0
         private        Timer        myTimerSavedGames = null;
 1100  0
         private        TimerTask        myTimerTaskSavedGames = null;
 1101  
 
 1102  
         private        void        sendDelayedSavedGamesCommand() {
 1103  0
                 if (myTimerSavedGames != null) {
 1104  0
                         return;
 1105  
                 }
 1106  0
                 myTimerSavedGames = new Timer();
 1107  
                 try {
 1108  0
                         myTimerTaskSavedGames = new MyTimerTaskSavedGames(this);
 1109  0
                         myTimerSavedGames.schedule(myTimerTaskSavedGames, 1000);
 1110  0
                 } catch (IllegalStateException e) {
 1111  0
                         e.printStackTrace();
 1112  0
                 }
 1113  0
         }
 1114  
 
 1115  
         private class MyTimerTaskSavedGames extends TimerTask {
 1116  
                 private        ClientReceiveParser crp;
 1117  
 
 1118  0
                 MyTimerTaskSavedGames(ClientReceiveParser crp) {
 1119  0
                         super();
 1120  0
                         this.crp = crp;
 1121  0
                 }
 1122  
                 /* (non-Javadoc)
 1123  
                  * @see java.util.TimerTask#run()
 1124  
                  */
 1125  
                 @Override
 1126  
                 public void run() {
 1127  0
                         this.crp.commandDispatcher.writeNetworkMessageln("show saved");
 1128  0
                         this.crp.myTimerSavedGames.cancel();
 1129  0
                         this.crp.myTimerSavedGames = null;
 1130  0
                         this.crp.myTimerTaskSavedGames.cancel();
 1131  0
                         this.crp.myTimerTaskSavedGames = null;
 1132  0
                 }
 1133  
         }
 1134  
 
 1135  
 }