Optimal way to handle bullets being created in a FE game

I released a game today named Ball Blast which includes automatic rifles as the starter weapon people get when they join the game. However I noticed that in larger servers there was a significant amount of network lag when a lot of people were firing their ARs at once. I’ve seen games like Phantom Forces handle bullet creation no problem.

What I’m currently doing is firing a remote event on the client who shot the gun which tells the server to tell the other clients to build a bullet following the same trajectory. (The client who fired the bullet creates a bullet for itself instantly).

This might not be the optimal way obviously which is why I’m asking for advice from anyone who has ton this before.

6 Likes

I am also interested in learning the proper methods for projectile replication, I’ve been stuck on the subject for over two weeks now. :neutral_face:

I am positive it is the best to automatically give response to the firing client. I think it is also proper to do hit detection on the client, and also have solid sanity checks on the server afterwards to verify the hit.

Things I’m uncertain of:

  1. Missing a hit while replicating to other clients. For example, updating the projectile on its path by 0.8 seconds on the non-firing clients to sync with the firing client, but within that 0.8 seconds there was a possible collision.

  2. Do I sync the projectile from the firing client to the other clients? The reason I ask this is cause the time to communicate between client - server - client usually exceeds the projectile travel time; so I guess the answer to this is no? So in that case just sync the non-firing clients projectiles together?

1 Like

Can’t give an exact answer, but I can tell you that rendering the bullet trail server-side for all of the other clients to see is a major cause of lag to do with FE weapons, at least from experience.

The client of the player who fired the weapon creates a bullet for itself, then tells the server to tell the other clients to create bullets for themselves. Probably didn’t make this clear in OP, so I edited it.

2 Likes

I have done this before in a game I was working on with EndorsedModel called, “Sniper!” We simply had the client call a RemoteEvent to the server when they clicked to shoot, and then it registered on the server, checked if they had the ammo and needed to reload, and if they didn’t, it generated the bullet, the drop, and the trail on the server.

It worked for us and we didn’t have any issues, but the game wasn’t really big enough to have a problem with people being lagged down if it caused any lag. So I’m about 75% sure this won’t cause lag, but I could be wrong.

This solution may work for a simple game with small maps, but for more complex games it will result in a choppy projectile path.

In the last game I made I actually handled the projectile visualization on the server, mainly cause the projectile path was updated every 1 stud, so it didn’t need to be smooth. For the new game I’m working on though I am rendering a smooth ballistic path, so it is paramount that it be rendered on the client. I am just unsure on how to properly handle everything as mentioned in my above post…

1 Like

If you have a large map, check clientside when the event is fired how far away the bullet is from the player, or try drawing a raycast from the player to the bullet and then using this data decide whether or not they need to render the bullet’s trajectory or not. This should save on lag a lot since they wont be rendering bullets that aren’t even near or visible.

Perhaps you could try making a lower detail version just for bullets that you think the player cant see or are very far away, that updates it’s position less often, using less processing. Even this would likely significantly reduce lag.

I made a system that renders the shot locally for both the shooter and everyone else. The shooter and the server both simulate the shot though, which is entirely separate from rendering. The server also keeps track of all player positions for 20 “cycles” (10Hz right now but that can be adjusted) and each player’s latency.

When the client simulates a shot, it determines if it hit another character. If it did, it reports that to the server, and the server then verifies it by rolling the hit player’s position back by the shooter’s most recent network latency. This means that the server is effectively simulating the shot from the shooter’s perspective, even though the server received word of the shot later when everything has moved.

With this, you can separate your rendering logic and make it just resemble what actually happened. You can expand this to not just hit-scan projectiles, but even projectiles that follow a parabolic trajectory over time. As long as the server is simulating it in the right context, it’ll work. Other clients only need enough information to show the right thing, like the originating point and endpoint.

Note that this isn’t perfect, though. If the shooter has much higher latency than other players, it’s entirely possible that they’re seeing the “wrong” thing according to the server’s truth. Being shot also can look kind of weird, since the shot might not necessarily come from where the shooter’s gun actually is now, or it might not look like it actually hit you when the server says it did. Just some tradeoffs you have to make. You can expand on this system to try to solve some of it.

21 Likes

Did a similar thing for cannon projectiles. Seems to be the best way to do it without going borderline overkill on it

1 Like