project_files/Android-build/SDL-android-project/src/org/hedgewars/hedgeroid/netplay/Netplay.java
changeset 7461 38acbfdb484f
parent 7358 57a508884052
child 7476 2fb781bbdd51
equal deleted inserted replaced
7458:fec6fa1e460e 7461:38acbfdb484f
     3 import java.io.File;
     3 import java.io.File;
     4 import java.io.FileNotFoundException;
     4 import java.io.FileNotFoundException;
     5 
     5 
     6 import org.hedgewars.hedgeroid.R;
     6 import org.hedgewars.hedgeroid.R;
     7 import org.hedgewars.hedgeroid.Utils;
     7 import org.hedgewars.hedgeroid.Utils;
       
     8 import org.hedgewars.hedgeroid.netplay.JnaFrontlib.BoolCallback;
     8 import org.hedgewars.hedgeroid.netplay.JnaFrontlib.IntStrCallback;
     9 import org.hedgewars.hedgeroid.netplay.JnaFrontlib.IntStrCallback;
     9 import org.hedgewars.hedgeroid.netplay.JnaFrontlib.MetaschemePtr;
    10 import org.hedgewars.hedgeroid.netplay.JnaFrontlib.MetaschemePtr;
    10 import org.hedgewars.hedgeroid.netplay.JnaFrontlib.NetconnPtr;
    11 import org.hedgewars.hedgeroid.netplay.JnaFrontlib.NetconnPtr;
    11 import org.hedgewars.hedgeroid.netplay.JnaFrontlib.RoomArrayPtr;
    12 import org.hedgewars.hedgeroid.netplay.JnaFrontlib.RoomArrayPtr;
    12 import org.hedgewars.hedgeroid.netplay.JnaFrontlib.RoomCallback;
    13 import org.hedgewars.hedgeroid.netplay.JnaFrontlib.RoomCallback;
    38 	
    39 	
    39 	// Extras in broadcasts
    40 	// Extras in broadcasts
    40 	public static final String EXTRA_PLAYERNAME = "playerName";
    41 	public static final String EXTRA_PLAYERNAME = "playerName";
    41 	public static final String EXTRA_MESSAGE = "message";
    42 	public static final String EXTRA_MESSAGE = "message";
    42 	public static final String EXTRA_HAS_ERROR = "hasError";
    43 	public static final String EXTRA_HAS_ERROR = "hasError";
       
    44 	public static final String EXTRA_REASON = "reason";
    43 	
    45 	
    44 	private static final String ACTIONPREFIX = "org.hedgewars.hedgeroid.netconn.";
    46 	private static final String ACTIONPREFIX = "org.hedgewars.hedgeroid.netconn.";
    45 	public static final String ACTION_DISCONNECTED = ACTIONPREFIX+"DISCONNECTED";
    47 	public static final String ACTION_DISCONNECTED = ACTIONPREFIX+"DISCONNECTED";
    46 	public static final String ACTION_CONNECTED = ACTIONPREFIX+"CONNECTED";
    48 	public static final String ACTION_CONNECTED = ACTIONPREFIX+"CONNECTED";
    47 	public static final String ACTION_PASSWORD_REQUESTED = ACTIONPREFIX+"PASSWORD_REQUESTED";
    49 	public static final String ACTION_PASSWORD_REQUESTED = ACTIONPREFIX+"PASSWORD_REQUESTED";
       
    50 	public static final String ACTION_ENTERED_ROOM_FROM_LOBBY = ACTIONPREFIX+"ENTERED_ROOM";
       
    51 	public static final String ACTION_LEFT_ROOM = ACTIONPREFIX+"LEFT_ROOM";
       
    52 	public static final String ACTION_STATE_CHANGED = ACTIONPREFIX+"STATE_CHANGED";
    48 	
    53 	
    49 	public static final String DEFAULT_SERVER = "netserver.hedgewars.org";
    54 	public static final String DEFAULT_SERVER = "netserver.hedgewars.org";
    50 	public static final int DEFAULT_PORT = 46631;
    55 	public static final int DEFAULT_PORT = 46631;
    51 		
    56 		
    52 	private final Context appContext;
    57 	private final Context appContext;
    53 	private final LocalBroadcastManager broadcastManager;
    58 	private final LocalBroadcastManager broadcastManager;
    54 	private final FromNetHandler fromNetHandler = new FromNetHandler();
    59 	private final FromNetHandler fromNetHandler = new FromNetHandler();
    55 	
    60 	
    56 	private State state;
    61 	private State state;
    57 	private int foregroundUsers = 0;
    62 	private int foregroundUsers = 0;	// Reference counter of clients requesting foreground tick speed (fast ticks)
       
    63 	private boolean chief;				// Do we control the current room?
    58 	
    64 	
    59 	// null if there is no running connection (==state is NOT_CONNECTED)
    65 	// null if there is no running connection (==state is NOT_CONNECTED)
    60 	private ThreadedNetConnection connection;
    66 	private ThreadedNetConnection connection;
    61 	
    67 	
    62 	public final PlayerList playerList = new PlayerList();
    68 	public final Playerlist playerList = new Playerlist();
    63 	public final RoomList roomList = new RoomList();
    69 	public final Roomlist roomList = new Roomlist();
    64 	public final MessageLog lobbyChatlog;
    70 	public final MessageLog lobbyChatlog;
    65 	public final MessageLog roomChatlog;
    71 	public final MessageLog roomChatlog;
    66 	
    72 	
    67 	public Netplay(Context appContext) {
    73 	public Netplay(Context appContext) {
    68 		this.appContext = appContext;
    74 		this.appContext = appContext;
    94 		if(state != State.NOT_CONNECTED) {
   100 		if(state != State.NOT_CONNECTED) {
    95 			throw new IllegalStateException("Attempt to start a new connection while the old one was still running.");
   101 			throw new IllegalStateException("Attempt to start a new connection while the old one was still running.");
    96 		}
   102 		}
    97 		
   103 		
    98 		clearState();
   104 		clearState();
    99 		state = State.CONNECTING;
   105 		changeState(State.CONNECTING);
   100 		connection = ThreadedNetConnection.startConnection(appContext, fromNetHandler, name, host, port);
   106 		connection = ThreadedNetConnection.startConnection(appContext, fromNetHandler, name, host, port);
   101 		connection.setFastTickRate(foregroundUsers > 0);
   107 		connection.setFastTickRate(foregroundUsers > 0);
   102 	}
   108 	}
   103 	
   109 	
   104 	public void sendNick(String nick) { sendToNet(ThreadedNetConnection.ToNetHandler.MSG_SEND_NICK, nick); }
   110 	public void sendNick(String nick) { sendToNet(ThreadedNetConnection.ToNetHandler.MSG_SEND_NICK, nick); }
   105 	public void sendPassword(String password) { sendToNet(ThreadedNetConnection.ToNetHandler.MSG_SEND_PASSWORD, password); }
   111 	public void sendPassword(String password) { sendToNet(ThreadedNetConnection.ToNetHandler.MSG_SEND_PASSWORD, password); }
   106 	public void sendQuit(String message) { sendToNet(ThreadedNetConnection.ToNetHandler.MSG_SEND_QUIT, message); }
   112 	public void sendQuit(String message) { sendToNet(ThreadedNetConnection.ToNetHandler.MSG_SEND_QUIT, message); }
   107 	public void sendRoomlistRequest() { sendToNet(ThreadedNetConnection.ToNetHandler.MSG_SEND_ROOMLIST_REQUEST); }
   113 	public void sendRoomlistRequest() { sendToNet(ThreadedNetConnection.ToNetHandler.MSG_SEND_ROOMLIST_REQUEST); }
   108 	public void sendPlayerInfoQuery(String name) { sendToNet(ThreadedNetConnection.ToNetHandler.MSG_SEND_PLAYER_INFO_REQUEST, name); }
   114 	public void sendPlayerInfoQuery(String name) { sendToNet(ThreadedNetConnection.ToNetHandler.MSG_SEND_PLAYER_INFO_REQUEST, name); }
   109 	public void sendChat(final String s) { sendToNet(ThreadedNetConnection.ToNetHandler.MSG_SEND_CHAT, s); }
   115 	public void sendChat(String s) { sendToNet(ThreadedNetConnection.ToNetHandler.MSG_SEND_CHAT, s); }
       
   116 	public void sendFollowPlayer(String nick) { sendToNet(ThreadedNetConnection.ToNetHandler.MSG_SEND_FOLLOW_PLAYER, nick); }
       
   117 	public void sendJoinRoom(String name) { sendToNet(ThreadedNetConnection.ToNetHandler.MSG_SEND_JOIN_ROOM, name); }
       
   118 	public void sendCreateRoom(String name) { sendToNet(ThreadedNetConnection.ToNetHandler.MSG_SEND_CREATE_ROOM, name); }
       
   119 	public void sendLeaveRoom(String message) { sendToNet(ThreadedNetConnection.ToNetHandler.MSG_SEND_LEAVE_ROOM, message); }
       
   120 	
   110 	public void disconnect() { sendToNet(ThreadedNetConnection.ToNetHandler.MSG_DISCONNECT, "User Quit"); }
   121 	public void disconnect() { sendToNet(ThreadedNetConnection.ToNetHandler.MSG_DISCONNECT, "User Quit"); }
   111 	
   122 	
   112 	private static Netplay instance;
   123 	private static Netplay instance;
   113 	
   124 	
   114 	/**
   125 	/**
   131 
   142 
   132 	public State getState() {
   143 	public State getState() {
   133 		return state;
   144 		return state;
   134 	}
   145 	}
   135 	
   146 	
       
   147 	private void changeState(State newState) {
       
   148 		if(newState != state) {
       
   149 			state = newState;
       
   150 			broadcastManager.sendBroadcastSync(new Intent(ACTION_STATE_CHANGED));
       
   151 		}
       
   152 	}
       
   153 	
       
   154 	public boolean isChief() {
       
   155 		return chief;
       
   156 	}
       
   157 	
   136 	/**
   158 	/**
   137 	 * Indicate that you want network messages to be checked regularly (several times per second).
   159 	 * Indicate that you want network messages to be checked regularly (several times per second).
   138 	 * As long as nobody requests fast ticks, the network is only checked once every few seconds
   160 	 * As long as nobody requests fast ticks, the network is only checked once every few seconds
   139 	 * to conserve battery power.
   161 	 * to conserve battery power.
   140 	 * Once you no longer need fast updates, call unrequestFastTicks.
   162 	 * Once you no longer need fast updates, call unrequestFastTicks.
   189 	 * Processes messages from the networking system. Always runs on the main thread.
   211 	 * Processes messages from the networking system. Always runs on the main thread.
   190 	 */
   212 	 */
   191 	final class FromNetHandler extends Handler {
   213 	final class FromNetHandler extends Handler {
   192 		public static final int MSG_LOBBY_JOIN = 0;
   214 		public static final int MSG_LOBBY_JOIN = 0;
   193 		public static final int MSG_LOBBY_LEAVE = 1;
   215 		public static final int MSG_LOBBY_LEAVE = 1;
   194 		public static final int MSG_CHAT = 2;
   216 		public static final int MSG_ROOM_JOIN = 2;
   195 		public static final int MSG_MESSAGE = 3;
   217 		public static final int MSG_ROOM_LEAVE = 3;
   196 		public static final int MSG_ROOM_ADD = 4;
   218 		public static final int MSG_CHAT = 4;
   197 		public static final int MSG_ROOM_UPDATE = 5;
   219 		public static final int MSG_MESSAGE = 5;
   198 		public static final int MSG_ROOM_DELETE = 6;
   220 		public static final int MSG_ROOM_ADD = 6;
   199 		public static final int MSG_ROOMLIST = 7;
   221 		public static final int MSG_ROOM_UPDATE = 7;
   200 		public static final int MSG_CONNECTED = 8;
   222 		public static final int MSG_ROOM_DELETE = 8;
   201 		public static final int MSG_DISCONNECTED = 9;
   223 		public static final int MSG_ROOMLIST = 9;
   202 		public static final int MSG_PASSWORD_REQUEST = 10;
   224 		public static final int MSG_CONNECTED = 10;
       
   225 		public static final int MSG_DISCONNECTED = 11;
       
   226 		public static final int MSG_PASSWORD_REQUEST = 12;
       
   227 		public static final int MSG_ENTER_ROOM_FROM_LOBBY = 13;
       
   228 		public static final int MSG_LEAVE_ROOM = 14;
   203 		
   229 		
   204 		public FromNetHandler() {
   230 		public FromNetHandler() {
   205 			super(Looper.getMainLooper());
   231 			super(Looper.getMainLooper());
   206 		}
   232 		}
   207 		
   233 		
   219 				Pair<String, String> args = (Pair<String, String>)msg.obj;
   245 				Pair<String, String> args = (Pair<String, String>)msg.obj;
   220 				playerList.removePlayer(args.first);
   246 				playerList.removePlayer(args.first);
   221 				lobbyChatlog.appendPlayerLeave(args.first, args.second);
   247 				lobbyChatlog.appendPlayerLeave(args.first, args.second);
   222 				break;
   248 				break;
   223 			}
   249 			}
       
   250 			case MSG_ROOM_JOIN: {
       
   251 				String name = (String)msg.obj;
       
   252 				// TODO roomPlayerList.addPlayerWithNewId(name);
       
   253 				roomChatlog.appendPlayerJoin(name);
       
   254 				break;
       
   255 			}
       
   256 			case MSG_ROOM_LEAVE: {
       
   257 				Pair<String, String> args = (Pair<String, String>)msg.obj;
       
   258 				// TODO roomPlayerList.removePlayer(args.first);
       
   259 				roomChatlog.appendPlayerLeave(args.first, args.second);
       
   260 				break;
       
   261 			}
   224 			case MSG_CHAT: {
   262 			case MSG_CHAT: {
   225 				Pair<String, String> args = (Pair<String, String>)msg.obj;
   263 				Pair<String, String> args = (Pair<String, String>)msg.obj;
   226 				getCurrentLog().appendChat(args.first, args.second);
   264 				getCurrentLog().appendChat(args.first, args.second);
   227 				break;
   265 				break;
   228 			}
   266 			}
   246 			case MSG_ROOMLIST: {
   284 			case MSG_ROOMLIST: {
   247 				roomList.updateList((Room[])msg.obj);
   285 				roomList.updateList((Room[])msg.obj);
   248 				break;
   286 				break;
   249 			}
   287 			}
   250 			case MSG_CONNECTED: {
   288 			case MSG_CONNECTED: {
   251 				state = State.LOBBY;
   289 				changeState(State.LOBBY);
   252 				broadcastManager.sendBroadcast(new Intent(ACTION_CONNECTED));
   290 				broadcastManager.sendBroadcast(new Intent(ACTION_CONNECTED));
   253 				break;
   291 				break;
   254 			}
   292 			}
   255 			case MSG_DISCONNECTED: {
   293 			case MSG_DISCONNECTED: {
   256 				Pair<Boolean, String> args = (Pair<Boolean, String>)msg.obj;
   294 				Pair<Boolean, String> args = (Pair<Boolean, String>)msg.obj;
   257 				state = State.NOT_CONNECTED;
   295 				changeState(State.NOT_CONNECTED);
   258 				connection = null;
   296 				connection = null;
   259 				Intent intent = new Intent(ACTION_DISCONNECTED);
   297 				Intent intent = new Intent(ACTION_DISCONNECTED);
   260 				intent.putExtra(EXTRA_HAS_ERROR, args.first);
   298 				intent.putExtra(EXTRA_HAS_ERROR, args.first);
   261 				intent.putExtra(EXTRA_MESSAGE, args.second);
   299 				intent.putExtra(EXTRA_MESSAGE, args.second);
   262 				broadcastManager.sendBroadcastSync(intent);
   300 				broadcastManager.sendBroadcastSync(intent);
   264 			}
   302 			}
   265 			case MSG_PASSWORD_REQUEST: {
   303 			case MSG_PASSWORD_REQUEST: {
   266 				Intent intent = new Intent(ACTION_PASSWORD_REQUESTED);
   304 				Intent intent = new Intent(ACTION_PASSWORD_REQUESTED);
   267 				intent.putExtra(EXTRA_PLAYERNAME, (String)msg.obj);
   305 				intent.putExtra(EXTRA_PLAYERNAME, (String)msg.obj);
   268 				broadcastManager.sendBroadcast(intent);
   306 				broadcastManager.sendBroadcast(intent);
       
   307 				break;
       
   308 			}
       
   309 			case MSG_ENTER_ROOM_FROM_LOBBY: {
       
   310 				roomChatlog.clear();
       
   311 				changeState(State.ROOM);
       
   312 				chief = (Boolean)msg.obj;
       
   313 				Intent intent = new Intent(ACTION_ENTERED_ROOM_FROM_LOBBY);
       
   314 				broadcastManager.sendBroadcastSync(intent);
       
   315 				break;
       
   316 			}
       
   317 			case MSG_LEAVE_ROOM: {
       
   318 				changeState(State.LOBBY);
       
   319 				Intent intent = new Intent(ACTION_LEFT_ROOM);
       
   320 				intent.putExtra(EXTRA_MESSAGE, (String)msg.obj);
       
   321 				intent.putExtra(EXTRA_REASON, msg.arg1);
       
   322 				broadcastManager.sendBroadcastSync(intent);
   269 				break;
   323 				break;
   270 			}
   324 			}
   271 			default: {
   325 			default: {
   272 				Log.e("FromNetHandler", "Unknown message type: "+msg.what);
   326 				Log.e("FromNetHandler", "Unknown message type: "+msg.what);
   273 				break;
   327 				break;
   330 						shutdown(true, appContext.getString(R.string.error_connection_failed));
   384 						shutdown(true, appContext.getString(R.string.error_connection_failed));
   331 						return;
   385 						return;
   332 					}
   386 					}
   333 					FLIB.flib_netconn_onLobbyJoin(conn, lobbyJoinCb, null);
   387 					FLIB.flib_netconn_onLobbyJoin(conn, lobbyJoinCb, null);
   334 					FLIB.flib_netconn_onLobbyLeave(conn, lobbyLeaveCb, null);
   388 					FLIB.flib_netconn_onLobbyLeave(conn, lobbyLeaveCb, null);
       
   389 					FLIB.flib_netconn_onRoomJoin(conn, roomJoinCb, null);
       
   390 					FLIB.flib_netconn_onRoomLeave(conn, roomLeaveCb, null);
   335 					FLIB.flib_netconn_onChat(conn, chatCb, null);
   391 					FLIB.flib_netconn_onChat(conn, chatCb, null);
   336 					FLIB.flib_netconn_onMessage(conn, messageCb, null);
   392 					FLIB.flib_netconn_onMessage(conn, messageCb, null);
   337 					FLIB.flib_netconn_onRoomAdd(conn, roomAddCb, null);
   393 					FLIB.flib_netconn_onRoomAdd(conn, roomAddCb, null);
   338 					FLIB.flib_netconn_onRoomUpdate(conn, roomUpdateCb, null);
   394 					FLIB.flib_netconn_onRoomUpdate(conn, roomUpdateCb, null);
   339 					FLIB.flib_netconn_onRoomDelete(conn, roomDeleteCb, null);
   395 					FLIB.flib_netconn_onRoomDelete(conn, roomDeleteCb, null);
   340 					FLIB.flib_netconn_onConnected(conn, connectedCb, null);
   396 					FLIB.flib_netconn_onConnected(conn, connectedCb, null);
   341 					FLIB.flib_netconn_onRoomlist(conn, roomlistCb, null);
   397 					FLIB.flib_netconn_onRoomlist(conn, roomlistCb, null);
   342 					FLIB.flib_netconn_onDisconnected(conn, disconnectCb, null);
   398 					FLIB.flib_netconn_onDisconnected(conn, disconnectCb, null);
   343 					FLIB.flib_netconn_onPasswordRequest(conn, passwordRequestCb, null);
   399 					FLIB.flib_netconn_onPasswordRequest(conn, passwordRequestCb, null);
       
   400 					FLIB.flib_netconn_onEnterRoom(conn, enterRoomCb, null);
       
   401 					FLIB.flib_netconn_onLeaveRoom(conn, leaveRoomCb, null);
       
   402 					
   344 					FLIB.flib_metascheme_release(meta);
   403 					FLIB.flib_metascheme_release(meta);
   345 					tickHandler.start();
   404 					tickHandler.start();
   346 				}
   405 				}
   347 			});
   406 			});
   348 		}
   407 		}
   373 			public void callback(Pointer context, String name, String msg) {
   432 			public void callback(Pointer context, String name, String msg) {
   374 				sendFromNet(FromNetHandler.MSG_LOBBY_LEAVE, Pair.create(name, msg));
   433 				sendFromNet(FromNetHandler.MSG_LOBBY_LEAVE, Pair.create(name, msg));
   375 			}
   434 			}
   376 		};
   435 		};
   377 		
   436 		
       
   437 		private final StrCallback roomJoinCb = new StrCallback() {
       
   438 			public void callback(Pointer context, String name) {
       
   439 				sendFromNet(FromNetHandler.MSG_ROOM_JOIN, name);
       
   440 			}
       
   441 		};
       
   442 		private final StrStrCallback roomLeaveCb = new StrStrCallback() {
       
   443 			public void callback(Pointer context, String name, String message) {
       
   444 				sendFromNet(FromNetHandler.MSG_ROOM_LEAVE, Pair.create(name, message));
       
   445 			}
       
   446 		};
   378 		private final StrStrCallback chatCb = new StrStrCallback() {
   447 		private final StrStrCallback chatCb = new StrStrCallback() {
   379 			public void callback(Pointer context, String name, String msg) {
   448 			public void callback(Pointer context, String name, String msg) {
   380 				sendFromNet(FromNetHandler.MSG_CHAT, Pair.create(name, msg));
   449 				sendFromNet(FromNetHandler.MSG_CHAT, Pair.create(name, msg));
   381 			}
   450 			}
   382 		};
   451 		};
   423 			public void callback(Pointer context, String nickname) {
   492 			public void callback(Pointer context, String nickname) {
   424 				sendFromNet(FromNetHandler.MSG_PASSWORD_REQUEST, playerName);
   493 				sendFromNet(FromNetHandler.MSG_PASSWORD_REQUEST, playerName);
   425 			}
   494 			}
   426 		};
   495 		};
   427 		
   496 		
       
   497 		private final BoolCallback enterRoomCb = new BoolCallback() {
       
   498 			public void callback(Pointer context, boolean isChief) {
       
   499 				sendFromNet(FromNetHandler.MSG_ENTER_ROOM_FROM_LOBBY, Boolean.TRUE);
       
   500 			}
       
   501 		};
       
   502 		
       
   503 		private final IntStrCallback leaveRoomCb = new IntStrCallback() {
       
   504 			public void callback(Pointer context, int reason, String message) {
       
   505 				sendFromNet(FromNetHandler.MSG_LEAVE_ROOM, reason, message);
       
   506 			}
       
   507 		};
       
   508 		
   428 		private void shutdown(boolean error, String message) {
   509 		private void shutdown(boolean error, String message) {
   429 			if(conn != null) {
   510 			if(conn != null) {
   430 				FLIB.flib_netconn_destroy(conn);
   511 				FLIB.flib_netconn_destroy(conn);
   431 				conn = null;
   512 				conn = null;
   432 			}
   513 			}
   446 		private static String createDisconnectUserMessage(Resources res, int reason, String message) {
   527 		private static String createDisconnectUserMessage(Resources res, int reason, String message) {
   447 			switch(reason) {
   528 			switch(reason) {
   448 			case JnaFrontlib.NETCONN_DISCONNECT_AUTH_FAILED:
   529 			case JnaFrontlib.NETCONN_DISCONNECT_AUTH_FAILED:
   449 				return res.getString(R.string.error_auth_failed);
   530 				return res.getString(R.string.error_auth_failed);
   450 			case JnaFrontlib.NETCONN_DISCONNECT_CONNLOST:
   531 			case JnaFrontlib.NETCONN_DISCONNECT_CONNLOST:
   451 				return res.getString(R.string.error_connection_lost, message);
   532 				return res.getString(R.string.error_connection_lost);
   452 			case JnaFrontlib.NETCONN_DISCONNECT_INTERNAL_ERROR:
   533 			case JnaFrontlib.NETCONN_DISCONNECT_INTERNAL_ERROR:
   453 				return res.getString(R.string.error_unexpected, message);
   534 				return res.getString(R.string.error_unexpected, message);
   454 			case JnaFrontlib.NETCONN_DISCONNECT_SERVER_TOO_OLD:
   535 			case JnaFrontlib.NETCONN_DISCONNECT_SERVER_TOO_OLD:
   455 				return res.getString(R.string.error_server_too_old);
   536 				return res.getString(R.string.error_server_too_old);
   456 			default:
   537 			default:
   474 			public static final int MSG_SEND_PASSWORD = 1;
   555 			public static final int MSG_SEND_PASSWORD = 1;
   475 			public static final int MSG_SEND_QUIT = 2;
   556 			public static final int MSG_SEND_QUIT = 2;
   476 			public static final int MSG_SEND_ROOMLIST_REQUEST = 3;
   557 			public static final int MSG_SEND_ROOMLIST_REQUEST = 3;
   477 			public static final int MSG_SEND_PLAYER_INFO_REQUEST = 4;
   558 			public static final int MSG_SEND_PLAYER_INFO_REQUEST = 4;
   478 			public static final int MSG_SEND_CHAT = 5;
   559 			public static final int MSG_SEND_CHAT = 5;
   479 			public static final int MSG_DISCONNECT = 6;
   560 			public static final int MSG_SEND_FOLLOW_PLAYER = 6;
       
   561 			public static final int MSG_SEND_JOIN_ROOM = 7;
       
   562 			public static final int MSG_SEND_CREATE_ROOM = 8;
       
   563 			public static final int MSG_SEND_LEAVE_ROOM = 9;
       
   564 			
       
   565 			public static final int MSG_DISCONNECT = 10;
   480 			
   566 			
   481 			public ToNetHandler(Looper looper) {
   567 			public ToNetHandler(Looper looper) {
   482 				super(looper);
   568 				super(looper);
   483 			}
   569 			}
   484 			
   570 			
   509 					if(FLIB.flib_netconn_send_chat(conn, (String)msg.obj) == 0) {
   595 					if(FLIB.flib_netconn_send_chat(conn, (String)msg.obj) == 0) {
   510 						sendFromNet(FromNetHandler.MSG_CHAT, Pair.create(playerName, (String)msg.obj));
   596 						sendFromNet(FromNetHandler.MSG_CHAT, Pair.create(playerName, (String)msg.obj));
   511 					}
   597 					}
   512 					break;
   598 					break;
   513 				}
   599 				}
       
   600 				case MSG_SEND_FOLLOW_PLAYER: {
       
   601 					FLIB.flib_netconn_send_playerFollow(conn, (String)msg.obj);
       
   602 					break;
       
   603 				}
       
   604 				case MSG_SEND_JOIN_ROOM: {
       
   605 					FLIB.flib_netconn_send_joinRoom(conn, (String)msg.obj);
       
   606 					break;
       
   607 				}
       
   608 				case MSG_SEND_CREATE_ROOM: {
       
   609 					FLIB.flib_netconn_send_createRoom(conn, (String)msg.obj);
       
   610 					break;
       
   611 				}
       
   612 				case MSG_SEND_LEAVE_ROOM: {
       
   613 					if(FLIB.flib_netconn_send_leaveRoom(conn, (String)msg.obj) == 0) {
       
   614 						sendFromNet(FromNetHandler.MSG_LEAVE_ROOM, -1, "");
       
   615 					}
       
   616 					break;
       
   617 				}
   514 				case MSG_DISCONNECT: {
   618 				case MSG_DISCONNECT: {
   515 					FLIB.flib_netconn_send_quit(conn, (String)msg.obj);
   619 					FLIB.flib_netconn_send_quit(conn, (String)msg.obj);
   516 					shutdown(false, "User quit");
   620 					shutdown(false, "User quit");
   517 					break;
   621 					break;
   518 				}
   622 				}