8.7 从Lobby移动到实际游戏
问题
创建了会话后,你想给所有玩家时间用来聚集、聊天、让他们可以示意已经准备好可以进行游戏了。
解决方案
XNA在会话状态和玩家的IsReady属性中带有基本的lobby功能。
会话开始于Lobby状态。只有主机可以调用NetworkSession. StartGame方法,这个方法将会话移动到Playing状态。主机可以基于所有玩家的IsReady状态做出决定。
工作原理
当会话创建后,会话的SessionState属性会拥有Lobby值。 当在这个状态时,你需要让所有在这个会话中的玩家可以示意他们已经做好了准备,这可以通过将他们的IsReady设为true做到。这个值可以被会话中的所有玩家读取:
case GameState.InSession: { switch (networkSession.SessionState) { case NetworkSessionState.Lobby: { if (keybState != lastKeybState) { if (keybState.IsKeyDown(Keys.R)) { LocalNetworkGamer localGamer = networkSession.LocalGamers[0]; localGamer.IsReady = !localGamer.IsReady; } } } break; case NetworkSessionState.Playing: { } break; } networkSession.Update(); }
主机需要检测是否所有玩家都将IsReady设为了true。最简单的方法是检查NetworkSess ion.IsEveryoneReady的值,如果所有人都准备好了,主机会调用NetworkSession.StartGame方法,这个方法将状态从Lobby移动到Playing:
case NetworkSessionState.Lobby: { if (keybState != lastKeybState) { if (keybState.IsKeyDown(Keys.R)) { LocalNetworkGamer localGamer = networkSession.LocalGamers[0]; localGamer.IsReady = !localGamer.IsReady; } } if (networkSession.IsHost) { if (networkSession.AllGamers.Count > 1) { if (networkSession.IsEveryoneReady) { networkSession.StartGame(); log.Add("All players ready -- start the game!"); } } } } break;
当状态改变至Playing时,会话会引发GameStarted事件,这个事件所有玩家都会进行监听。这样可以让他们绘制游戏屏幕并开始发送和接收游戏数据。
当主机决定结束游戏时,需要调用NetworkSession.EndGame方法,这个方法将所有玩家的IsReady重置为false并返回Lobby状态。
case NetworkSessionState.Playing: { if (networkSession.IsHost) { if (keybState != lastKeybState) { if (keybState.IsKeyDown(Keys.E)) { networkSession.EndGame(); } } } } break;
这会引发会话的GameEnded事件,所有玩家都可以监听这个事件,这样他们就可以,例如,绘制lobby图像。
代码
InSession状态包含大多数基本代码让多个玩家表示他们的IsReady,让主机从Lobby状态移动到Playing状态或返回:
case GameState.InSession: { switch (networkSession.SessionState) { case NetworkSessionState.Lobby: { if (keybState != lastKeybState) { if (keybState.IsKeyDown(Keys.R)) { LocalNetworkGamer localGamer = networkSession.LocalGamers[0]; localGamer.IsReady = !localGamer.IsReady; } } if (networkSession.IsHost) { if (networkSession.AllGamers.Count > 1) { if (networkSession.IsEveryoneReady) { networkSession.StartGame(); log.Add("All players ready -- start the game!"); } } } } break; case NetworkSessionState.Playing: { if (networkSession.IsHost) { if (keybState != lastKeybState) { if (keybState.IsKeyDown(Keys.E)) { networkSession.EndGame(); } } } } break; } networkSession.Update(); } break;
发布时间:2009/11/11 上午11:42:03 阅读次数:5090