No matter if it's an FPS, RTS, or driving game we're making, we'll want to be able to load different kinds of environments for the players to roam around in. How can we do that easily?
In this recipe, we'll add functionalities to the networked FPS game we outlined previously in this chapter. The principle will work for any kind of already networked game, although it might differ depending on how the game implements the level. Here, we'll assume it uses jMonkeyEngine scenes or .j3o
scenes.
Perform the following set of steps to load a level:
LoadLevelMessage
. It extends GameMessage
since it might be useful to know the gameId
. Apart from that, it has one field levelName
.Game
class so that it can keep track of which level it's running.levelNode
field on our server, which we can load our level into, as follows:private Node loadLevel(String levelName){ return (Node) assetManager.loadModel("Scenes/"+levelName + ".j3o"); }
levelNode = loadLevel("TestScene"); rootNode.attachChild(levelNode); game.setLevelName("TestScene");
simpleInitApp
method, we'll tell the application to load TestScene
from Chapter 1, SDK Game Development Hub:LoadLevelMessage levelMessage = new LoadLevelMessage(); levelMessage.setLevelName(game.getLevelName()); server.broadcast(Filters.in(conn), levelMessage);
addPlayer
method, we need to create and send the message to the connecting client. That's all for the server side of things.levelNode
field and a loadLevel
method, but it's a little bit different:public void loadLevel(final String levelName){ enqueue(new Callable(){ public Object call() throws Exception { if(rootNode.hasChild(levelNode)){ rootNode.detachChild(levelNode); } levelNode = (Node) assetManager.loadModel("Scenes/"+levelName + ".j3o"); rootNode.attachChild(levelNode); return null; } }); }
enqueue
block.MessageListener
picks up LoadLevelMessage
as follows:else if (m instanceof LoadLevelMessage){ gameClient.loadLevel(((LoadLevelMessage)m).getLevelName()); game.setLevelName(((LoadLevelMessage)m).getLevelName()); }
When a client joins, the server creates a LoadLevelMessage
class and populates it with the name of the level currently loaded. The server doesn't supply the level itself, but the client must have the levels supplied previously. The LoadLevelMessage
class only provides a name in this case, which is probably enough in many cases. For some games, it's a good idea to support a custom path when loading levels, since it allows for greater customization options.
3.15.182.62