Jump to content
  • Advertisement


  • Content Count

  • Joined

  • Last visited

Community Reputation

1 Neutral

About willepj

  • Rank

Personal Information

  • Role
  • Interests


  • Github
  • Steam
  1. Thank you very much. I now realise what mistakes I've been making. In the Console class (which is common code) I've replaced variable.setValue(value) with user.setVariable(variable, value). user is an argument that is passed to the Console.run(...) method. LocalUser will send a packet to the server if connected. ServerUser will set the variable. Same thing for commands - if the command is a server only command, LocalUser will send a packet and ServerUser will execute the command. I've got a minor problem with weapons (as that is common code). On the client side, should I decrease the ammo count when firing? I'm thinking that I shouldn't as it is logic and so it should be server-side, right? Firing is sent as part of the PlayerMovementPacket. Once again, thank you for your help.
  2. Sorry. I should have made myself more clear Engine#broadcast will send a message to all clients on the server, and on the client, it will send a message to the server. I do have a system which tracks variable changes and when it detects a change, it calls Engine#onMonitorValueChange. Let's use the example of commands and game variables. Let's create an IGameVariablePermissionManager or something like that. When we call GameVariable#setValue(..) if GameVariableManager.permissionManager.canSet(this) returns false, then return and don't set the variable. However, should I have an IGameVariablePermissionManager for the server and client or should it look at some variables (like sv_running or sv_dedicated) in order to work out if it a client, integrated server or dedicated server? I will be splitting up my Engine class soon though.
  3. I did something not too dissimilar in an old engine of mine. Although, the only places where I call Engine.isClientSide() and Engine.isServerSide() is when setting game variables (like sv_cheats 1), running a command (like noclip) and shooting a weapon. These variables and commands should be accessible from both the server and the client (if running on a listen server), and so it wouldn't be possible to instantiate them with an Engine instance. i.e engine.setVariable(var, value) rather than var.setValue(value). The whole point of the Engine class (which can be found here) is to allow common code (code in the Engine project - like weapons, variables, commands) to access client or server side code. When the game is launched, the client sets Engine.instance to new ClientEngine(), which allows GameVariable#setValue(...) to send a packet telling all clients connected or the server its connected to that the variable has changed (via Engine#broadcast). Other things it does is events - onEntitySpawn, onComponentAdd, onMonitorValueChange, etc. and ServerEngine can override these and send a packet whenever a component is added or changed or an entity is spawned. Furthermore, it also acts as a Scene object, allowing common code to add an entity to the scene, or find all entities with a specific component. Thanks for your quote. It got me thinking. I'll see if I can use an event bus instead of relying on polymorphism. Do you think I should create AddEntityToSceneEvents and GameVariableUpdateEvents? The former would do the same as Engine.getEntities().add(...) and the latter would replace Engine.getInstance().broadcast(...). Whilst writing this reply, I also noticed that I use the Engine class in the Client, Editor and Server projects a lot. The code in these projects have access to GameClient, GameEditor and GameServer respectively, which are singletons all contain a Scene instance and BaseNetworkable as well. Before I start implementing this, I'd just like to know your opinion on adding an event system (of course with the ability to add multiple listeners to an event), and therefore (hopefully) reduce complexity and allow for the Engine class to be a singleton.
  4. That is probably the best. My only problem with that is then I'll have to pass engine objects around and having a dependency like that can be a pain. I could have an instance of the Engine per thread/group of threads? One group for the client; one group for the server. By dedicated, I mean remote server (i.e a server that is its own process and always running). It was a question about networking in general (not just listen servers). Thank you so much for your advice. I'll try to implement it once/if I can separate my singletons. I'm also using component-based entities and each frame I track certain variables and if they've changed, I send an update to the client. In step 3, do you just check which modules are enabled and then return based on that? i.e passing an Engine object to methods when running them? I'll see if that is an option.
  5. Whenever you launch singleplayer, most games will run an integrated server (Minecraft, Quake, CS:GO, etc.). How should I go about this? Should I just launch a new server process and connect my client to that once the server's launched? Should I run a server in a separate thread? My only problem with the latter is that my (Java) code uses methods such as if (Engine.isClientSide()) ... Should I use the Thread.currentThread() or new Exception.getStackTrace()[1].getClassName() to work out what part of code is running my method? Furthermore, should I share entities and assets between the client and server? I do a physics simulation on the client as well - should that be disabled? How much logic should a client do when connected to a dedicated server? For example, pressing E to open a door. Should the client play the animation as well or just tell the server that a user interacted with a door? Also, what about shooting an arrow - at the moment the code only runs on the server because there would be two arrows; one spawned on the server and one on the client. Sorry for all the questions and a thanks for reading, William
  6. willepj

    Duplicating a VAO

    It's written in Java, and so it uses JFrames and JPanels. The look and feel is Substance's Graphite skin. I made a few changes to the theme, which can be found here. Unfortunately, it's a "hard" fork and I can't remember what I changed.
  7. willepj

    Duplicating a VAO

    I've got it working. It turns out the vertices, texture coordinates and normals array was being truncated (the arrays were much longer than I expected). Just for some clarification, I wanted to copy the VBOs/data from an existing VAO into a new one, so then I could modify that VAO and its VBOs, without affecting the other models in the scene. For example, I could "clone" a cube's VAO, then skew and stretch that to make the handle for a staircase, and use cubes for steps. If they had the same VAO, then the steps, of course, will also be skewed and stretched. I'm mainly going to be using this system to prototype/blockmesh in the editor, then export to 3ds max to UV map and clean up, then import back into the engine as an OBJ, and that way I won't have to worry about scales.
  8. I'm currently working on a level editor, which will support editing meshes. I've been trying to duplicate a VAO and its VBOs, so I can then modify it, however, I'm stuck trying to duplicate the VAO's index buffer. I can copy the other VBOs just fine. The first VBO is the first attribute (and the index buffer is created before any buffers for the attributes are, and so that is why I'm subtracting one from the first VBO). int vao = Loader.getInstance().createVAO(); int firstVBO = 0; int[] vbos = new int[meshComponent.model.getMesh().getDimensions()]; int count = meshComponent.model.getMesh().getVertexCount(); { GL15.glBindBuffer(GL31.GL_COPY_READ_BUFFER, meshComponent.model.getMesh().getFirstVBO() - 1); int size = GL15.glGetBufferParameteri(GL31.GL_COPY_READ_BUFFER, GL15.GL_BUFFER_SIZE); int vbo = Loader.getInstance().createEmptyIndexBuffer(size / 4); GL15.glBindBuffer(GL31.GL_COPY_WRITE_BUFFER, vbo); GL31.glCopyBufferSubData(GL31.GL_COPY_READ_BUFFER, GL31.GL_COPY_WRITE_BUFFER, 0, 0, size); } for (int i = 0; i < vbos.length; i++) { int mul = 3; // the dimensions of the VBO if (i == 1) mul = 2; // texture coordinates int vbo = Loader.getInstance().createEmptyVBO(meshComponent.model.getMesh().getVertexCount() * mul); if (i == 0) firstVBO = vbo; GL15.glBindBuffer(GL15.GL_ARRAY_BUFFER, vbo); GL20.glVertexAttribPointer(i, mul, GL11.GL_FLOAT, false, mul * 4, 0); GL15.glBindBuffer(GL15.GL_ARRAY_BUFFER, 0); GL15.glBindBuffer(GL31.GL_COPY_READ_BUFFER, meshComponent.model.getMesh().getFirstVBO() + i); GL15.glBindBuffer(GL31.GL_COPY_WRITE_BUFFER, vbo); GL31.glCopyBufferSubData(GL31.GL_COPY_READ_BUFFER, GL31.GL_COPY_WRITE_BUFFER, 0, 0, meshComponent.model.getMesh().getVertexCount() * mul); } GL15.glBindBuffer(GL31.GL_COPY_READ_BUFFER, 0); GL15.glBindBuffer(GL31.GL_COPY_WRITE_BUFFER, 0); Loader.getInstance().unbindVAO(); When I try to clone a cube, only the top and bottom faces are rendered (even with backface culling disabled). Here is a picture of the bug. If I divide size by 4 (as 4 bytes is an int) in the glCopyBufferSubData call, then only 3 triangles are copied (one is missing on the top face as well as all of the triangles on the side - picture here). Furthermore, using glGetBufferSubData on the index buffer (of both the copied and original VAOs) fails silently, however, it works on the attributes. Thank you in advance for any help.
  • Advertisement

Important Information

By using GameDev.net, you agree to our community Guidelines, Terms of Use, and Privacy Policy.

GameDev.net is your game development community. Create an account for your GameDev Portfolio and participate in the largest developer community in the games industry.

Sign me up!