Constant Replication without excessive Remote Calls (REDOING)

Just as simple to make a function that excludes a player:

function FireExcluding( RemoteEvent, Plr, ... )
    local Plrs = game.Players:GetPlayers( )
    for a = 1, #Plrs do
        if Plrs[ a ] ~= Plr then RemoteEvent:FireClient( Plrs[ a ], ... ) end
    end
end
1 Like

To be fair the title of the tutorial is “Constant replication without excessive remote calls”, so maybe this change should be made :grin:

1 Like

:stuck_out_tongue_winking_eye: yeah alright i concede defeat

You’re not firing it with the NetworkPlayer as the first argument

Also, if you’re worried about speed don’t use pairs/ipairs as it’s slower then just for i = 1, #x do

Yeah, I only just woke up when I wrote that :stuck_out_tongue: thanks for pointing out

Also again, I’ll keep it using the pairs() function as it is easier for people to understand

In Method A, What prevents Player B from deleting the bullet locally, thus dealing no damage?

Nothing, which is why in practice you’d add some extra security specific to your game.

Can you give an example of this extra security? Having Player B handle hit detection on himself just sounds like a bad idea to me.

Wouldn’t this make it extremely difficult to hit players with high latency? Not even regarding cheats here, just like, what if Player B lives in thailand? Them actually receiving the shot might happen like, upwards of a second after Player A fires, at which point they might be 16 feet or more away. This is the exact opposite of favor the shooter.

Another potential issue is that Player B could conceivably delete the remote event, or the script which responds to it, or write a script which deletes bullets as they’re created, and now they’re completely invulnerable. I don’t think there’s any server side solution for this. Any client side solution is a just a band-aid which is easily circumvented via a little reverse engineering.

You could handle hit detection on the server, instead of passing that job onto B, and that sounds substantially more reasonable. Yes there are potential latency problems, but it makes cheating harder. Plus you could potentially implement backwards reconciliation to maximize responsiveness.

I understand that this is largely about minimizing network requirements, but you’re giving away a lot of control to players. I don’t know if this practice is worth the security cost.

1 Like

Handling hit detection on the server just makes even more lag. However, here is how I do things:

  1. Make a ray on the sending client, send that origin + position over a RemoteFunction, and get a key returned
  2. Do hit calculation clientsided
  3. Fire Server, with the part hit, and the ray
  4. The server will use ray:ClosestPoint() to see if the player was close to the client. If so, do damage, otherwise, nothing. Also do checks to see if the ray origin is near where the player was, etc etc. Generally, pretty secure.

That’s how I do stuff in practice (alongside the Replication), however I didn’t want to include that at the time of writing as it was probably too complex for the kind of person who would be at the stage of needing this tutorial.

However again, I am (eventually) rewriting, so I’ll keep that into account :stuck_out_tongue:

1 Like

Handling hit detection on the server results in less network overhead though. In your solution there is one command (CMD) coming from player A, and then there’s a Remote Procedure Call (RPC) for every single player. If you have a game with, say, 24 players, that’s 25 remote calls for every pellet. Yes, FireAllClients is less expensive computationally than calling FireClient on a loop, but the networking cost is the same. Something like a 5 pellet shotgun on a 24 player server firing once would be 5 CMDs and 120 RPCs.

If you do the hit detection server side there is only a CMD for every shot fired (assuming you are doing client side prediction for the weapons). Raytracing is not the most expensive thing in the world (part creation is far worse in my experience), and reducing complexity is more important than efficiency in a lot of cases (so that way upkeep is easier). If your weapons are so computationally expensive that it’s slowing down the server then you should probably rework your weapons (halve the number of pellets fired, double damage, reduce fire rate, etc.), come up with a queueing system, live with the consequences, or switch to a different engine, instead of trying to push all your calculations onto the clients who may actually have worse computers than the server. So long as you aren’t reaching enormous processor usage levels on ROBLOX’s servers your players won’t notice at all.

Sometimes it helps me to start from first principles and work my way up from there when I’m dealing with messy network stuff.

Say that we’re making a hitscan gun

Assumptions:

  • Raycasts are fast
  • Networks are slow
  • The server is roughly omnipotent

Requirements:

  • Feedback to the shooter must be immediate
  • Hits must be verified by the server

The following procedure meets those requirements:

  1. Client shoots
  2. Client figures out who it hit
  3. Client shows hit animation
  4. Client tells the server who it hit
  5. Server validates
  6. Server deals damage

Thoughts?

47 Likes

Exactly how it should be done.
^ My thoughts.

3 Likes

So great that I bookmarked it

Yeah, that’s exactly how I do it in practice.

(I’m going to rewrite this, plus add an advanced version)

1 Like

I don’t get it, you didn’t even solve this example problem and your methods given do not solve the bad practice of repeatedly firing remote events.

I think you’ve misunderstood the topic here - the method being used here in the example does solve the problem, because rather than having to move an object every step to replicate it (for example, a turret on a tank), setting network ownership of it will produce a smoother result with fewer calls. It’s okay though - I can understand how this could be a challenging topic.

Just a reminder, that you should look at this “last post” date before commenting - you can find it on the top right of posts :slightly_smiling_face: (this post was last updated over 2 years ago!)

I replicate the bullets for both the server and the client, so the client just sees the bullets as cosmetics whilst the server casts the actual bullet and deals damage. I think doing this is better as people sometimes have slower connections and it might be used for their own advantage. That’s just my assumption please correct me if I’m wrong.

1 Like

I don’t see where the code solves this given bad practice example, all it relates to is properly replicating a Object’s movement, not the Mouse move. I think I might be confused here, but could you explain further and give an example of code of solving that bad practice example?

The code example doesn’t intend to solve the Mouse problem … they’re not the same problem?
The topic being discussed is “Constant replication without excessive remote calls” - the mouse problem is just an example of a poor workaround if the user was not aware of the full potential of Network Ownership.

You keep saying “this” but what exactly are you confused about? There are several points regarding reasons as to why excessive remote calls are considered bad practice. You should provide a more explicit concern so that OP or someone else can help you address your confusion.

As far as the point brought up that I can see, I think you’re slightly mistaken there. Mouse movement is completely different from replication although the two can be interlinked. Mouse movement should not be replicated, that’s a pointless practice. The point is to replicate something based on user input, including the mouse’s location.

Are you confused about the network ownership, or the allowing of clients to handle visuals on their end, or the concept in general? Do you have a specific scenario regarding excessive remote calls that can be plucked at?