#multiplayer
1 messages ยท Page 235 of 1
you need to pass the reference at the time of the widget creation
iuh
Create a variable, call it Owner . The type is Actor
Make it instance editable and expose on spawn
On the create widget node, set the owner (The character that you spawn)
Would it be possible to create a data asset at runtime or a data table?
Not even sure if either of those would fit my needs but Iโm thinking to create a system that would allow a player to make a very simple mini quest and have it exist for another player to do at a later time. I suppose I could do this outside the engine like storing the info somewhere else and then reimporting / loading that back to get in the game again but yea curious if there are any suggestions on this concept
I could make a BP loaded with variables that could be set (this sounds like a data asset lol) and then just have that BP saved as an actor but idk Iโm just thinking through ideas rn
With all the discussion about getplayercontroller above, I kind of got lost.
If you have a game that combines split screen with online multiplayer, for example 2 players splitscreen in a lobby with 2 other players (not splitscreen).
If you wanted an enemy that picked a random player to target with an attack, what is the best practice to get that list of players?
I've seen a half dozen different ways, including tracking it yourself by building it when players connect/disconnect, and using the various built in player lists, I can't tell which one is best to use.
right, so I made a new project to get my head around this "get player controller" concept right,
- made a custom game mode and custom player controller, player controller has a int variable to keep track of.
- so in game mode, on handleStartingNewPlayer, I cast it to player controller, set a number to the variable and spawn the default third person character and posses it.
then to simulate the scenario, just made a simple input action that spawn an actor bp_actor_on_client. I know some will say I should at this spawn point, set a reference to the player controller, but that is the thing right, we want to get it without having such hard reference, since pcg does not make any reference it just spawns.
So this actor will after some time call server and ask to be spawn, and the server will choose a color based on the owner player, branching on the int variable we set at the start.
So this works fine PIE when
- stand alone
- as listening server
and also works in stand alone multiplayer out of the editor.
In a split screen however, it always runs as player 1, spawining the redish ball instead another color, because of the fixed index in get player controller at 0.
But I don't think there is a way around this for split screen right? So if the actor does not have a reference to who owns it, there is not way to call the server with the correct info.
But at the same time, actor spawn in split screen is visible regardless of who spawns it, so we do not have the server/client problem.
Then the question would go to how to identify if it is a local split or client server, can call game mode directly from the actor, but still can't know who should owns it.
that is exactly my question now ๐คฃ. I'll mess with a split screen that plays online, like 2 people on the same pc, and two others in a different pc.
I guess we handle this as 2 online players, and internally handle two local players ๐ตโ๐ซ
I guess to summarize is there a built in player list somewhere that accurately tracks all the players, ranging from all local, to all online, and any combination within, or does that need to be implemented by the dev
Yeah that looks like it does exactly what I said.
It sounds like your pcg setup spawns something for each player then?
The PlayerArray on the GameState has each player's PlayerState.
Only thing with that array is that the order is not guaranteed to be the same on server and clients. As it's filled locally. But it will contain each player's PlayerState. Even AIs if you mark them as bWantsPlayerState
pcg in split screen duplicate everything, since is the "same instance".
so for split screen, one needs to handle it as stand alone I guess, only 1 can run pcg,
it is the same instance for both screen,
well in my initial setup, i have pcg populating most of the visual, trees and some buildings, but at those buildings, some of them I want to spawn an npc, so that is where the spawn from server comes in. For this scenario, I don't really care who spawns it, so its fine.
Converting this to a splitscreen, there is no need to control any of that, as it alls runs as a single instance.
But just out of curiosity, I think it is impossible to get a player controller from a loose actor in a splitscreen, it simple doesn't have any. But it is also not needed since any controller can direct call it
on the pcg side, I do think I already have a solution, I'm passing the "seed" variable, which is just a random number from the graph, at the pcg spawn actor node, the graph runs on the client, the client can pass a parameter to the graph, and then spawn the actor with this parameter, like the count variable, index or whatever. It won't be a hard reference to the player controller, but it will be enough to get one in case its needed.
Unfortunately there is just no solution for local split screen, impossible to know which character trigger the pcg
like this, in online, the only visible actor in server is the white ball, everything else is client. Everythng is pcg generated here, including the server balls
but local split screen, it runs both. Balls are spawn with "get player controller at 0" which call server spawn.
in split screen, the pcg is literally the same instance, so there is no way to know who triggered the pcg generation from walking, this is a grid based pcg, that loads around player. But shouldn't have any need to know either, everything is a single instance.
Well, anyways, thanks for all the effort in explaining it, that really help me get a better view of it
@thin stratus can you think of any reason not to do a net predicted launch character stack?
Just prototyping the idea atm
In this case it came about because characters needed a boost during some of their air attacks but root motion sources acting like forces instead of impulse didn't cut it
But its still just a 'try it and see'
if i have custom settings for a game ie. gravity multiplier, damage, multiplier, would it be better to store them in the game mode, gamestate, or it doesnt matter which one
if they were in the gamemode they would not be able to replicate to players
they may need to be in the game state here or some other actor replicated to all clients
Recommendations on how to replicate an elevator that an chaos vehicle can drive on?
I imagine there is a way to have the elevator be predictive?
My assumption would be having the elevator move on the fixed async physics update somehow
unsure if the default callbacks work in the sim, I would insights trace to see
I mean, the pending stuff in the CMC might already be doing what you want or not?
Not sure it needs to be a stack if they can't be offset with a delay anyway. Could just combine them into one vector.
Also, side note, that gameplay tag could be pretty expensive to replicate, so make sure to only send a bit if it's empty.
so setting up a river where i can enter i can start swimming. the start swimming works fine but when i exit the water all players are stopping swimming not just the player that has exited the river
it was my first thing I couldn't fix in unreal and I couldn''t find any solution for it. You are operating on GLOBAL physics volume, for the whole world. Make a specific one for your river, and check is water volume at that specific
and why are you sending RPC when you already separated server logic with hasAuthority branch. Overlap functions are executed on server and clients so rpc is not needed here I think
ahh okay i was trying to achive a way to automate the water volume so i am not having to place heaps of physics volumes as i dont believe i can do this in blueprint
ill have to go back to the drawing board for this
hello, what's the correct way to replicate damage in a first person shooter?
(it's a PvE game to play with a party of friends, not competitively, so i'm fine with some client authority)
what i mean is, let's say i have a client firing 20 rounds per second, hitting the enemy with all of them
the absolute easiest way to replicate this that i can think of would be to call the damage event from the client to the server, for each bullet hit
however even with my little experience i can tell that it sounds like a bad idea, especially since every RPC would need to be reliable
a different solution could be to go with server authority which makes the replication problem nonexistent since i can just replicate the enemy's health variable, given all damage is called and applied directly by the server without having to be called by a client first
the problem this introduces, which is what i'm stuck on, is how do you replicate the firing from a client? just start/stop firing RPC events?
and then, wouldnt the positions be desynced between client and server leading to confusing misses or hits?
Server auth is usually the way to go. And as you noticed, it's not straightforward
The position could indeed be different. As the thing the client is aiming at is already somewhere else on the server and even further gone once the RPC arrives on the server to start firing.
But that's only solvable by storing information about the targets and having a timestamp to send along to the server so it can do the hit tracing against an older position
Which all in all isn't easy and if you make a coop game is probably overkill
yeah, it is a co-op game and honestly im not even sure i could do all of that with my current knowledge yet
if its overkill, that means there are different solutions right? if so, could you give some insight into which ones i should look into?
The "different solution" is just not caring about the delay and potential lag.
You either send each shot as an RPC, or you send start and end.
start and end as the total damage values?
Start and End as the StartFire EndFire
You should always only RPC what the Server can't know about
In this case the button press and release
The rest is all authority stuff
i see
why doesn't Execute Console Command with the command of viewmode unlit work for player 2 when testing in editor w/ listen server mode?
I tried both client & server authority calling it from player 2 character input
the only way to achieve this is via c++ and overriding corresponding functions. Still not hard but need some c++ knowledge
I mean, the pending stuff in the CMC might already be doing what you want or not?
LaunchCharacter and pending forces typically desyncs, it's not in saved moves if that's what you mean, might be misunderstanding you tho
Not sure it needs to be a stack if they can't be offset with a delay anyway. Could just combine them into one vector.
Generally the stack wouldn't be used beyond a single count outside of edge cases, but it would represent different launches, so the vector would be unique to each one
Also, side note, that gameplay tag could be pretty expensive to replicate, so make sure to only send a bit if it's empty.
Yup
I'm mostly just making sure I'm not wasting time reinventing the wheel, but doesn't seem like I am if I can get a stable/accurate version of LaunchCharacter
@pallid mesa you got any insight? ^
guys, I connect to my game server like:
ClientTravel("someurl:20001?character=MyChar&token=MySessionId", TRAVEL_Absolute);
How can I simulate it in PIE? Like In game instance do ClientTravel with these additional params right after start? Or maybe there's some project settings for it?
additional startup args in advanced settings for play perhaps
but I'm not sure how to make the client not auto join
My dumb temp solution would be to have the client disconnect after starting PIE to a local level and then call this after
well, yea, actually it's not a big issue to emulate it. another thing is where on the server I can access these parameters? like somewhere in postlogin in gamemode?
the startup arguments?
or do you mean the editor PIE settings?
It kind of depends ... GEditor can obtain some PIE arguments I guess but I'm not sure what you want to get exectly
nono, I'm talking more about real world example. I basically login on my login map and get signed character Id I want to load once client travels to game map. So I have session Id and character Id in game instance, but how do I transfer it to server now, so the right character is loaded for given player controller?
I click the button and it moves to the controller,Then the controller calls the event in the gamestate, The gamestate increments an interger then moves on to the final stage where its supposed to tell everyone who got the vote, The problem is the clients are not getting to this final part of the code and Iโm not sure why any help would be great!
You can't send RPCs on actors that aren't owned by a client. GameState isn't owned by clients so you cannot have them call an RPC on the GameState.
Your multicast will also not be guaranteed to be received when the replicated value is received on clients. Make that "Player Vote" variable a "Rep w/ Notify" and you'll get an OnRep function that will be called when a new value is received which you can then use to update whatever you want to update when the new value comes in.
you can override the prelogin or login functions in a custom gamemode class and one of the arguments passed to those funtions is the ?var=value option string
in that specific example you could override the login function and create the player controller by calling the super function, parse the options string and set the variables on the player controller before returning it
Ive been messing around with your suggestion and the number doesnt go up unless i start with the server client otherwise when it is incremented it doesnt show
That's because replicated variables only replicate when executing on the server.
If you want to adjust something for everyone to see, you need to be executing on the server, but in order to have a client tell the server to do something you need to RPC on an actor that is owned by the client, and then the server can do whatever it needs to.... So you could RPC on their player controller, playerstate, controlled pawn, or a replicated component owned by one of these actors, and then when executing on the server, go to the gamestate and increment your variable.
thats brings up a good question then should i just run this in the gm
GameMode only exists on the server, so any variables on there won't be replicated to anyone.
ok should be the last thing but now its just returning 0 i attached it to a variable to increase but its not increasing by one
Don't use the OnRep to set the on rep variable... you set replicated variables on the server. The OnRep function triggers for everyone when a new value is received in that variable for clients.
So if you wanted a click of something on a client to increment a variable on the gamestate and for everyone to see a print when the value is received:
Clicked Button on Widget > RPC to server on PlayerController > Get GameState > Call "Vote Count" function on GameState.
Vote Count Function > Increments "Player Vote" OnRep variable +1
OnRepPlayerVote function > Print "PlayerVote" variable.
how are projectiles ( bullets ) supposed to be replicated? currently the template i use only seem to have the damage running on server and the muzzle flash in some other function. But not the projectile itself.
The projectile is spawned locally from my bp_rifle
Anyone have an idea why my actor that I'm spawning in my GameInstanceSubsystem isn't being replicated to clients?
I'm making sure the game instance spawning the actor is on the server, and the actor is set to replicate. Is spawning an actor from this non-replicating subsystem an issue?
Hello, I have a random puzzle system that stores answers in a map. Since the system randomly generates answers and spawns them, it works on the server without replication using the "Switch Has Authority" node. When I try to display the answers in a widget, only the integer part of the map is visible on the client, and the string part does not appear on the client.
Is there a reason you are using a GameInstanceSubsystem instead of a WorldSubsystem?
Maps do not support Replication.
Instead, create a Struct type that holds the 2 data types you need.
And replicate it with an Array.
Because the configs that are supposed to be managed should ideally be shared across any levels
The reason I went with spawning an actor as a manager was because I read that subsystems aren't really meant to handle replication as UObjects so it's safer to use an actor
is posible use this with struct (Its in for each loop)
Only Actors support replication out of the Box, so that would be the main reason.
You would have to modify it slightly, but yes, thats fine.
Also the fact that the game instance / it's subsystems are auto created on clients, I think replication might get a little weird (I at least ran into problems when trying, but maybe I was doing something wrong)
Is there any costs involved with calling an RPC function in an offline game? Asking because I'm trying to make a plugin that needs to support both single player and multiplayer. Wondering if I should separate any RPC stuff in a different class to maximise the performance of the singleplayer code.
How do you know the Actor isnt being replicated on the Client?
There is a tiny tiny tiny bit of extra overhead. But it is nothing to worry about.
Thanks
What modification should I make?
I think you should try and implement it yourself first. I gave you the answer to what you need to try and do to get it working.
My other game instance subsystems are running UGameplayStatics::GetActorOfClass to try to find it when they're on the client but are returning nullptr
When do they do this? Replication is not instant, so depending on when you call that/how often you call it could be giving you a false indication, since the Actor might not have replicated yet.
The best way to tell
Is to use the BeginPlay function
On the Actor itself
Because that will always be called for both Server and Clients
Yeah I was doing that actually, I was only getting breakpoints on the server
So I guess that's a better indication that I forgot to mention that it's not replicating lol
Okey i ill trying
And you are 100% sure? PrintStrings will give you the Network Context, so its much easier to identify than trying to guess from a breakpoint.
Since its usually very odd that an Actor thats set to Replicate and is spawned on the Server would not be replicated.
Typically its user error
I just had some stupid code to make it easier to breakpoint and inspect the data
Yeah let me double check
Should I use a struct like that or an index for every answer?
This isnt a #multiplayer question anymore, perhaps ask in #blueprint
@meager heart Just my two cents but usually the workaround I have for these kinds of issues is that I usually have an actor that handles world-based stuff that reads from the subsystem. That way you don't need to drive world-based logic directly from the subsystem itself.
The issue I think is that I need to propagate the subsystem info to the clients, because if the client actors are reading from the subsystem they aren't getting correct data
Does that make sense? Or am I misinterpreting what you're saying
Yeah it's only ever firing on the server, which is why I'm wondering if there's some exception for if a replicated actor is spawned by a non-replicated UObject? Idk if that's a thing
Otherwise maybe I'm replicating it wrong
The World Spawns the Actor
So it doesnt matter from where you call the function
Are you actually running PIE with a Client attached? Lol
So a breakpoint on line 71 doesnt get hit?
Unfortunately not, function only fires once, but I can verify the actor exists on the server
It is odd then, have you restarted the Editor?
I hope you arent using HotReload or LiveCoding wrong
It doesn't appear in the outliner, I think there's some uclass specifier I'm missing for that but can't remember rn
Yeah I have but I'll give it a try again. I use LiveCoding sparingly and will restart generally if I modify anything in a header
Yeah still not firing after a restart
What happens if you delay the spawning for a bit?
I wonder if OnWorldInitialized is a bit to early
True, let me try that out
No problem, still gonna try to figure it out the discord is just a good place to get quick answers when there's something basic I'm forgetting about but if it's something weird I can debug it
Thanks for the help ๐
Same thing happens after a delay lol, very weird
Spawn that Actor form GameMode's BeginPlay or similar. Just to verify Actor itself is correctly setup
you can use GetDebugStringForWorld
e.g. UE_LOG(LogTemp, Warning, TEXT("[%s][%s] Hello World!"), *GetDebugStringForWorld(GetWorld()), *GetName());
Great point, let me check
at debugging (breakpoint) you can use watches with following value:
{,,UnrealEditor-Engine.dll} GPlayInEditorContextString
to distinguish Server/Client/Standalone etc
though your way with incremented int is funny, haha
thanks lol just needed some arbitrary code and sometimes debugging on a log macro is weird
Yeah it's actually just never firing begin play logic on the client when spawned from the gamemode, I think something's set up wrong with the actor then... I'm not sure what else I need to add, I haven't set up replicated actors from C++ before but I thought it was only that bool in their constructor. I can look it up and see if I'm missing anything else
maybe it's about actor's owner
Isn't the owner the world if I just spawn it?
I guess the owner is an actor so it's not...
what net mode selected in PIE? "Client"? Can you see running character on the second screen?
or just two actors together in one frame
maybe you just spawned 2 standalone windows 
Yeah I'm using a listen server and 1 client, the server is running in the viewport and the client is in another window
don't remember the exact nomenclature because I'm restarting rn
Make fresh new Actor in BP, add Cube Mesh to it, mark Actor replicated. Spawn it in gamemode . Check if it replicates 
|| ah, GameMode do not exist no clients, so it's even simplier, no HasAuthority needed||
Was able to spawn a replicated BP actor from gamemode, made my class blueprintable to see what happens if I reparent that new class to it
Yeah using that reparented BP made it hit ๐ค
Very weird, the child BP class doesn't override anything
Maybe it's the fact it has a component it actually registers with the world or something, idk
Gonna go to sleep for tonight, thanks for the help everyone 
And thanks for the idea of spawning it separately in the gamemode, much quicker way of debugging
Is possible get overlaping actor player controller in sphere collision?
Entity
what do you even mean by that
As Index 0 right?
Yeah if client the one calling it
since only an instance of local controller is available to them
but then what are you actually trying to do?
Does the server know itself as Index 0?
might be doing it wrong
as dedicated server, index 0 will give you the first client controller probably
anyway you don't want the index
what will that server?
you already have the reference to the character
as server you can just get the controller of the charcter
Server usually do logic in response to smth, not just by "get PC 0 and do shit"
Overlap -> Switch has Authority -> Cast to Player Character -> Get Controller
Im trying damage system with ai but problem is health values is replicated is but if client dies system restart game but we got debug healh decrase in player controller if try with that works with no problem
e.g. when collision happens, then you have input params/context to deduce correct PC, or if Client had send RPC, then it will be handled in corresponding instance of PC of that client
what's the actual problem? I failed to comperhend
Damage is server only
just make sure everything is run in server, client simply receive the result (the replicated health)
Problem is If client dies from AI our system restarting game but anyone dies from health debug in player controller (run on server event damage) its not restarting until everyone dies
you just need to make sure that the function that restart the game is run on the server
(and @little pumice ) Did one final test based on the fact that the BP child worked, turns out that actors need a root component to be replicated. Adding this made it replicate properly when spawned in C++
Which kind of makes sense I guess, considering it wouldn't really be anywhere in the world without a root component
if you have health in PC you are doing it wrong too, as client will only know their own controller.
so it will not be aware of other player's health
use player state for such property
no its in character only debug in pc
not sure I get what the issue is when you said debug in player controller
death is also handled on the server
so client shouldn't die unless the server tell them to die
it says the function isnt callable
What function isn't callable?
You're not supposed to be calling it yourself.
It gets called automatically when a replicated variable receives a new value on clients.
You define what happens in that function when that new value is received.
oh i read call the function so i misinterpreted mb
ok i feel like i followed your guide to the letter but it is still only working on the server
That should be correct. The print string in the OnRep should print on clients.
I don't think ++ and -- nodes work correctly with onrep variables
Does in 5.5, at least for clients. The server doesn't seem to trigger the onrep unless it gets set.
Oh I wasn't aware of that they fixed it. Just had the same issue on 5.3 last week though
oh im on 4.7 lol so might not work
if thats the case
Yea so in that case, just set the Player Vote C1 to the output from the ++ node and it'll probably show up fine.
Well I would try a regular assignment just to be safe
what do you mean a regular assignment? Like this?
Yep, you might want to see that replicated variable bubble when you assign/set your variables to trigger OnRep fn
Arrays also had a similar problem iirc, requiring to set it to itself after element addition/removal to trigger the OnRep (for BP), not sure if it got fixed as well though
ok so this works if i start with the "server client" first if i initiate with the player client it stays at one lol
i might need to upgrade to 5 atp lol
Well I don't see any other problems with the setup either, so maybe something else is broken wrong/missing?
going to check the output logs for a bit
Yeah that would do it. The RootComponent of an Actor is what gives it it's Transform in the World. Without it, it wouldnt be able to spawn normally.
Not something thats usually considered, given that you just assume you have made one lol
what would be the best approach to make breakable props, like chair, table, crates etc. Chaos destruction with replicated force fields? These props must:
- be able to be spawned run-time or be placed inscene (so I need replicated actor).
- I want to create and bind to them events like OnDamaged, OnBreaked etc.
- and the most puzzling part: how to code that debirs of destructed prop make noise, impacts, scrape etc. (I have coded it on my static mesh physics objects but I wonder if it even would be possible to code it for debirs)
I see that another problem would be with replicating it. I can replicate static mesh physics but geometry collection not
Something that bugs me. Let's say before the game starts I give players choice to choose Starting Resources amount (50/50/50 or 25/100/25 for example). I can store this choice in the Game Instance and when Player Controller get's created just Get GameInstance from each player and take this Starting Resources variable and add to the Player State (where they store resources). Just out of curiosity I don't expect people to cheat because I don't plan ranked ladder, but it feels like it would actually be easy to ''hack''? And so because of that there is question. What is actually better place to do it? ''StartingManager'' that receives it, spawned by GameMode? Spawned for each PlayerController? The current flow is Game Instance calls to open level, Game Mode spawns Player Controller. So maybe GameMode would spawn Manager? but then it cannot access GameInstance, so how to ''feed'' data to GameMode for this exact player. What I'm missing? What can I create so gamemode or playercontroller can access it without user beeing able to ''hack''. Or do I just lock the choices, so in the worst case if player tries to hack it's gonna set starting resources as default or something like that? I'm missing some class where I could feed the data safely so the game can take it and use. What is that?
You are letting the player chose their own starting resource before they join the game?
not the one that respawns around him, just the amounts like 50 wood 100 gold for example
I kinda lost the plot, do you want the player to chose starting resource before they join someone's game?
why do you need game instance
it would be probably in the lobby
then all the choice can be stored in the server
okay so that would be after the session is made or something like that?
I think you are overthingking it
you simply need to ask the player what choice they made
you don't ask them, how many lumber did you chose
you ask them the choice ID
and you map the ID with the resource in the server
if Choice 1 -> Wood = 50, Gold = 5
if every choice is valid then doesn't matter if they "hack"
unless you impose restriction where some choice is not valid. Then you do handle this on the lobby and accept people request to selec tan id if it's valid
okay, but more or less flow in the blueprints would look like how? I'm missing that ''bridge''. If I ask from server, then I ask to where? Player Controller?
so it means I should put that choice to be set in player controller?
Am I picturing instance where people join a server where they are presented with a Widget that have buttons where they can make choices on starting resources?
If other player needs to know or see what choices other people make
you do store that in game state
as that is replicated
Client joins
As Client -> Click button (Server RPC, hey I select option 1)
Server : Ok option one valid, set Player 1 choice to 1 (choice being a replicated variable)
ohh, Game State... so game state opens already when we are in ''lobby'' and waiting for everyone to be ready? and then we can access it from GameMode and give choices to each player?
ok, that got me closer to what I wanted, but for singleplayer I guess Game Instance will be completly fine for ''missions'' and then for multiplayer I will just do different logic, or will abbadon the idea of resource selection ๐
I mean the idea of selecting starting resource is very simple
you can just prototype a button where if a player click, it will represents the player that clicks it
If you are going to make multiplayer then you do have to make it multiplayer ready
don't do a single player game and change your mind in the middle
the architecture is different
You don't even need to do different logic as Multiplayer logic will work just fine for single player
but not vice versa
im scared of multiplayer because of how much things take longer to debug and do things but yeah just trying to conceptualize how things would be if
well ngl, sometime I don't know how much I can push multiplayer
it's just by some miracle at the verge of giving up, I got the solution on what I thought is impossible to do with my current skill
must feel good and scary at the same time ๐
my plan is to make basic prototype so you can play, and then give it a bit of time to try and make it multiplayer, but systems are quite simple, if its not gonna work then its gonna be a good lesson but at least game in single will work
now after thinking a bit, since we are in lobby, there is already player state and player controller, so player clicking on the button it would just Set Resources Amount to Player State of that player... holy shit that was simple? each button would Set different amount... correct?
now I just need to fill my knowledge about sessions, lobbys and ''starting game'' .. step by step well get there
thanks for help ColdSummer
I was gonna comment on hacking stuff but now I have a question, is it possible to fake/send RPCs with hacky ways?
Not like mingling with the data being sent with it but like triggering it
Anybody know if the FArchive passed to Struct::NetSerialize's size is only the size of serialization data of that particular struct? Reason I ask is I'd like to pack an optional value and use the size of the FArchive to determine whether it's serialized or not, instead of an extra bit
Definitely possible yeah
How is that possible though, is there a different tech behind RPCs than using the open sockets between my pc and server?
If it would be a http request, I can understand that you can just duplicate the payload and send another request from outside, but shouldn't RPCs use the connection that we already have with server?
If they do use it, is it some kind of copying instructions to execute the RPC call again or something like that?
That's partly why the ownership system exists. If a client machine does manage to send an RPC for an actor they don't own, the server would reject it
So even if a client manages to push one through, nout will happen server side
The ownership test is done at both ends
Yeah I was going to give an example of an RPC that would increment a resource for the above question. So since we're owner of our PlayerState, if we don't put checks it could be incremented infinitely, is that correct?
yeah for sure
A client machine could basically call any function they want at anytime outside of normal code execution
So whatever the server is receiving should be validated and checked
Is there any recommended resource on hacking or hack prevention to learn more about this kind of stuff? I always felt myself missing on this side
I just think the RPC as a request, in the end server will check if the request is valid or not
Like client say ,. Hey I want to open this door.
Server gonna check if the client have the key or not in it's machine
so doesn't matter what the client say they have
nothing sticks out, just as soon as you realise a client machine can do literally anything it wants with some simple tools, the potential exploits become clearer
if client by some chance allowed to say, I have this much resource,
Then they can just do memory manipulation and change their resource.
You can design the game like, client values is but mere illusions. Their resource in their tab is just a representation what could be true.
But the real value is always on the server
basically: client requests to do things, server does things
Yeah I was going to give an example of just storing the variables in server itself is not enough to prevent hacks. Server side logic should cover abusive or edge cases to prevent anything go out of order as well.
Like having presets and saying to server "Hey I want this index" is probably the best way as ColdSummer recommended. Although it still requires index check in server too.
But if it would be "Okay you have X amount of points, each point is 50 resource, now select which resource you want", and the widget button click would say "Hey server add point to this resource" that would require the server to check if any client's total spent points are exceeding the limit or not.
Just wanted to add my bit, since the initial question kind of included that
A simple example would be firing a weapon or something. You can make an RPC called FireWeapon(Orign, Direction) - and do a simple check to make sure the client is near that origin, roughly facing that direction etc.
BUT, the client machine could spam that RPC to the Server as often as it likes. It's up to you to implement a heuristic to check the rate of fire they client is expecting, the number of shots fired etc.. That's a little more complicated to do.
I am on the verge to think that I shouldn't care about hack too much
for someone to hack my game, my game need player base first
if I am not working for a company, then meh
simple checks will do
Well that's a valid concern as well. Me trying my best with listen server games here.. (with the hope of it growing and requiring dedicated servers some day)
Pretty much. Like it helps to maintain good practices either way because then it becomes natural, but hackers are only going to hack a game that people widely care about
and if we are doing listen server, that's doomed already too
Ideally players who host servers and DO want to play normally shouldn't be penalised for that though. It's also a good reason to support both listen + dedicated. It's not super hard to do outside of a few edge areas, and if you're writing cheat-resistant code for one you get it for the other too.
Listen server is not self sufficient as many might think. It still requires NAT 
not with steam lobbies ๐
Being bound to a subsystem is still better than paying for a server that hosts less than 10 players monthly I believe ๐ฅฒ
Using AWS fleet, you can create an instance on demand
they can be terminated when there's no more player too
@dark parcel I realized what part of puzzle I was missing. In my ''Level Selection'' because after clicking Start Game I was opening new level, everything would get resetedso I setting anything in Player State didn't make sense for me. The missing puzzle is that I need to travel to the next level without reseting PlayerState for example. I don't know how yet(i'm watching tutorials and reading), but I think this is it. That way player can click things in mission selection and set them, and then travel to level with these settings. Game Instance would be fine for the singleplayer in 100% but I guess it's better to it with this way.
The player state holds the choice so it can be replicated to client. Which in turn show the selection they made in their machine (through widget or w.e you like)
The same selection should be stored on server game instance or any presistence object.
So it can be carried over to the next level and any data gets replicated to client if needed ( you don't in this case)
As client you request the server what choice you make.
Server check the request and set the choice if request valid.
Client On rep choice -> update widget.
When game is ready to move to the next level with server travel.
Server store all the data it needs from the lobby (e.g player choice).
Once all the players travelled to the next map.
Server read player choices it stored in persistent object and grant resources to players based on their choice.
You should make a custom player state for your lobby
As choice doesn't mean anything outside your "character screen"
FString ServerAddressWithToken = FString::Printf(
TEXT("127.0.0.1:20002?character=%s&token=%s"),
*CharacterSheet,
*SessionId
);
ClientTravel(ServerAddressWithToken, TRAVEL_Absolute, false);
guys, how do I properly pass parameters to server?
When I pass like that I have some strange things in InitNewPlayer Options parameter, it has something like:
?character=taiko&token=QUE1N0NERDJGQzUxNTZBQzRCMDg4QTRBMDRFQkI4QjJFOTQ2NDFEMQ==?Name=computername?SplitscreenCount=1 taiko&token=QUE1N0NERDJGQzUxNTZBQzRCMDg4QTRBMDRFQkI4QjJFOTQ2NDFEMQ== RDNERDU0MDI2OUZDMjQxNThCRkEzNjFEOTJFODA1MjYxMzI5QzJFMg==
why it's so ruined? ๐
FString ServerAddressWithToken = FString::Printf(
TEXT("127.0.0.1:20002?character=%s?token=%s"),
*CharacterSheet,
*SessionId
);
oh, so it's not like http url thingy! okay ๐
also if you override something like ULocalPlayer::GetGameLoginOptions then they'll also get added
not yet ๐
can someone help me understand what is going on with my projcetile in terms of replication? The damage is replicated correctly but the projectile itself is only visible on the shooting client
1st pic
2nd pic
3rd pic
4th pic
Well, you're supposed to spawn the actor server-side, not spawn it client side then ask the server to deal damage
Where do you call FireBullet? Is it possible only on the client hence spawning the projectile only on the client? And I can't see the owner is set but if it is, then calling the server RPC would still make server run the damage logic and make health reduced on everyone
Oh wait, if it's spawned only on the client, how would server RPC work?
RPC belongs to the weapon it looks like
Ah right, okay then it makes sense
But yea, the setup is backwards
Also, not related with the problem or wouldn't result any different but ApplyDamage interface should already include all the parameters you're passing with your BPI, there shouldn't be need for it ๐ค
i think this setup is this way to prevent latency that would come with spawning it on server no?
wouldnt i need to just spawn a fake bullet to other clients
and have the actual bullet only visible to the shooting client
I'm not so much experienced with this stuff but I feel like the local client should have the fake bullet while others have the replicated one (and maybe even correct your fake after the actual replicated one spawns in local player as well). And have your actual bullet on your server
At least the damage logic should be on the server, that I can say I guess Well that kind of depends actually
that would be the same as spawning the bullet on the server with extra steps
im aware of the server side spawning but wouldnt that come with latency issues
Currently you're giving the authority of saying "Hey I hit something" entirely to the client, which can work but not safe regarding to cheats and consistency.
And preventing latency should be like faking to your local player by saying "Yes good boi, you pressed the input and now you're doing this" as soon as input comes and waiting for server approval to continue or revoke the action if needed I believe
yes, but the waiting for the server approval is what causes latency and the feeling of not being responsive no?
That's why you create a fake bullet to make it responsive, without waiting for anything and correct/destroy it whenever you get info back from server to make it consistent
yeah i guess that makes sense, would i need to rework that damage event or can i keep that?
You shouldn't have an RPC a client can call which just applies damage either way
Nothing stopping them calling that whenever they want
you mean i could make the projectile spawn on the server then just connect that to the existing damage event as now only the server could call it?
To keep things simple, for now yeah, do the damage server side
Projectile prediction is no joke to implement generally
does that look something like this? I got this from a tutorial video
the class itself would essentially be the same as before, which would call the damage event
I have a question about Delta Replication in regards to replicated structs: when changing the struct, if I use a local FMyStruct variable as a placeholder and fill it with the global replicated FMyStruct fields, then apply all requested changes to the local FMyStruct variable, then finally overwrite the global replicated FMyStruct variable with the local FMyStruct - this is where delta replication comes in to save my butt, correct? It shouldnโt send the entire struct over the network since some of the fields may/likely will be the same?
And to piggy back off of that, letโs say one of the fields is an array and some elements are added/removed. Does the entire array get replicated or only the delta between the original and new array?
Do you guys know what is the exact command to type in the Open Level to use ServerTravel? I'm using Advanced Session Plugin so I can get ServerTravel node, but I read somewhere that because of that plugin I can use Options in the Open Level node, just cannot find exact command there, since I already have Level from Object Reference, is ServerTravel enough?
Not exactly sure what your problem is.
The Options String is usually appended to the URL anyway.
SomeMapName?Key1=Value1?Key2=Value2
The top node you have can just use an AppendString node to add the KeyValue pairs
The only other way to get a server travel going is by using ExecuteConsoleCommand, and there you'd also append the string together for the same
The first ServerTravel node works, but I wish I could use OpenLevel (byObjectReference) and add to it ServerTravel.
E.g. ServerTravel SomeMapName?Key1=Value1?Key2=Value2
Why
That's not possible fwiw
ServerTravel != OpenLevel
even with the Avanced Session Plugin?
Don't know what that would have to do with it
Internally in C++ OpenLevel is != ServerTravel
You do either or
Ok, I just read comment somewhere that said it's possible that is why I'm confused or I understand it wrong
Not to my knowledge
I would need to check for that
Can be that it is indeed possible, but I know the code paths are different
If that could be possible it would be sso good
I'm creating buttons to ''Enter Level'' and I have Level Reference so It would be so much usefull connecting this than taking name of the level converting to string etc.
You can just code your own if that's what you want though
so like 50 buttons, each would pass different Level Reference
hehe maybe not 50 but yeah
Doesn't seem like it's possible
OpenLevel call SetClientTravel
And that handles just a Client Traveling
You'd need to code your own node
Or you load the level and grab the name from it
yeah I mean it's not big deal, just was confused and looking whole internet for it because this comment said it's possible haha
thanks for help โค๏ธ
idk what the soft ref of the level can all give you
But you might be lucky and it can offer you the path/name of the level asset
So you can just use that with the ServerTravel node
Then you don't need to change the StartGame node
So I have Data Asset for each '"Level/Episode" as I call it. I have there Level Name and Level(Object Reference). I will just change to take Level_name instead of Level(Object Reference) so it's not big deal I guess.
Honestly. change it to the Asset
That makes it easier for you in the future to change it without changing the callsite
so pass whole asset and take name from it inside GameMode for the opening of the level?
Yeah, then in the future if you want to you just have to change what StartGame does and take the reference of the level instead of the name if you want to change it
You might also want to pass options in the future, so might make sense to just handle "Level" as the DataAsset
makes sense, thanks for feedback!
@upbeat basin @sinful tree almost forgot but thanks for the help its still a little goofy but it could boil down to im not doing it in standalone mode nonetheless I appreciate the help!
@thin stratus
Doing LaunchCharacter from a GA isn't de-syncing, I'm guessing that's because its fired from a predicted ability and the velocity itself is predicted by CMC, that probably suffices
So yeah I probably don't need to do anything custom there
I did notice though, it doesn't get applied while a root motion montage is active, even if its additive, the root motion overrides it
So for my own purpose I probably need to have a separate predicted velocity that is added onto root motion, for launches during root motion
Using a custom root motion source that mimics this would be the same, without reinventing the wheel
does this count as spawning the projectile on the server? trying to figure out how i would do what you mentioned
What this would be doing is allowing a client to spawn basically any actor at any time at any location_ and since you're multicasting it, it's spawning that actor individually on all clients that have this actor relevant at the time of the multicast (so they'd all have local copies of the actor), while also spawning it on the server. You want to limit what information you allow clients to tell the server. If you want to spawn something on the server, then spawn it when "Executing on Server" and if you want others to also see it, make sure it's a replicated actor.
I've never done local prediction of projectiles myself but understand what would be required, and it's somewhat complicated to get it to look right since you effectively would have a projectile that you spawned locally on the client that moves slower than what your projectile normally would and another projectile that you spawn on the server that is replicated out to everyone and moves at full speed, and you end up having to make them link up by using an ID that you create on the client and tell the server to use. When the replicated projectile comes to the client that originally spawned the predicted projectile, you'd have to have the replicated projectile be invisible for that client and since it moves faster, it would "catch up" to the predicted version, at which point you can make the replicated version visible and then destroy the client predicted vesion, and in the case that the server rejects the client shooting, have a means of destroying the client predicted actor (likely via a Client RPC) by sending that ID number back and the client finding the local projoectile and destroying it.
What.
your client is telling the server to spawn an actor of the clients choosing. this means they can spawn literally anything
Here's basically what needs to happen:
You need to have two projectiles spawned, one locally on the client when they press the button and another on the server when they receive the RPC from the client requesting to shoot, after the server accepts that the client can shoot.
The client predicted shot needs to be moving slower than the server projectile.
You need some way of being able to link the client predicted projectile and the replicated projectile which is where the ID comes in.
If the server rejects the player shooting, it needs to tell the client to destroy their locally predicted projectile.
If the server allows the shot, then the server needs to spawn a replicated version of the projectile that will then exist on all clients.
The client that predicted the shot should not see the replicated version until it has "caught up" to the local predicted version (the replicated version will be moving faster than the predicted version) at which point the locally predicted version should be destroyed.
The logic of the replicated projectile would be handled by the server, so what it hits or where it continues to travel would all be based on how the server sees the world.
This also doesn't account for things like if the player is close to a wall or some other actor in which case there may not even be enough time to handle all of this in which case you'd need to handle the logic a bit differently.
There is an example of how to do predicted projectiles in Unreal Tournament's source code as well.
Anybody know why FPredictionKeyDelegates::BroadcastRejectedDelegate and BroadcastCaughtUpDelegate don't clear/Move the delegate list? They make copies, but surely once the events are broadcast they are no longer needed?
Quick question if I run in the editor client mode with two clients I will create 3 world representations
I assume all these world exist on separate threads or no?
One question, on my LyraCharacterComponent, I have Safe_bWantsToSprint and this works with the CMC streucture.
But after setting up my GE_Sprint and GA_Sprint. Nothing happens. I know the input is working because of print nodes.
The only logical reason, is that Safe_bWantsToSprint is never true. Because the variable is not linked to the input (so set true when pressed, set false when released.
Before using Lyra, I used to just set the input in the character.
But now I want to work with GE so any idea how can I linked this behavior?
It might be if the array changes from a delegate
So they copy to avoid changing during iteration
Why do you have has authority check for toggling sprint?
Also tranek gas github implement sprint. You can look how it's done.
shouldnt it first check if it has authority?
Why? The point of toggling the FSavedMove is to do prediction
i like yout pfp haha
yeah u r right
But anyway tranek implement a sprinting on his gas documentation.
Also multiplayer ready, it toggle the bits in FSavedMove, you should be able to get what you need.
ty
guys, what is the best way to never miss to log any dedicated server crash? ๐
use a crash reporter?
"best" I wouldn't want to comment on, but you can try setting up "Sentry".
wise Cedric, can I ask you to point me in right direction? I already finished my prototype, but still can't solve issue with syncronizing of character rotation. I tried to control it by adding yawn on client and server, it works in editor, but in shipping package it's not synced at all and makes character simulated proxies rotate randomly.
I need to programatically rotate character, like for example when ability is used I need to face the opponent(SetActorRotation(LookAtTheOpponentVector) e.g.). CMC is ruining all fun here along with PlayerController.
What is the proper way to do it? How to rotate in sync? ๐
I now use a component like:
// Fill out your copyright notice in the Description page of Project Settings.
#include "Components/COR_ControllerRotationComponent.h"
#include "Kismet/KismetMathLibrary.h"
UCOR_ControllerRotationComponent::UCOR_ControllerRotationComponent()
{
PrimaryComponentTick.bCanEverTick = true;
SetIsReplicatedByDefault(true);
bIsRotating = false;
}
void UCOR_ControllerRotationComponent::BeginPlay()
{
Super::BeginPlay();
}
void UCOR_ControllerRotationComponent::TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction)
{
Super::TickComponent(DeltaTime, TickType, ThisTickFunction);
if (bIsRotating)
{
RotateToFaceCoordinate(DeltaTime);
}
}
void UCOR_ControllerRotationComponent::StartRotatingToFaceCoordinateInternal(const FVector& InTargetLocation,
bool bIsRecursiveCall)
{
APlayerController* PlayerController = Cast<APlayerController>(GetOwner());
APawn* ControlledPawn = PlayerController->GetPawn();
ControlledPawn->bUseControllerRotationYaw = true;
TargetLocation = InTargetLocation;
bIsRotating = true;
if(!bIsRecursiveCall)
{
if(!GetOwner()->HasAuthority())
{
StartRotatingToFaceCoordinate_Server(InTargetLocation);
}
else
{
StartRotatingToFaceCoordinate_Client(InTargetLocation);
}
}
}
void UCOR_ControllerRotationComponent::StartRotatingToFaceCoordinate(const FVector& InTargetLocation)
{
StartRotatingToFaceCoordinateInternal(InTargetLocation, false);
}
void UCOR_ControllerRotationComponent::StartRotatingToFaceCoordinate_Client_Implementation(
const FVector& InTargetLocation)
{
StartRotatingToFaceCoordinateInternal(InTargetLocation, true);
}
void UCOR_ControllerRotationComponent::StartRotatingToFaceCoordinate_Server_Implementation(
const FVector& InTargetLocation)
{
StartRotatingToFaceCoordinateInternal(InTargetLocation, true);
}
void UCOR_ControllerRotationComponent::RotateToFaceCoordinate(float DeltaSeconds)
{
APlayerController* PlayerController = Cast<APlayerController>(GetOwner());
APawn* ControlledPawn = PlayerController->GetPawn();
FVector MyLocation = ControlledPawn->GetActorLocation();
FVector DirectionToTarget = (TargetLocation - MyLocation).GetSafeNormal();
FRotator CurrentRotation = ControlledPawn->GetActorRotation();
FRotator TargetRotation = DirectionToTarget.Rotation();
float DesiredYaw = TargetRotation.Yaw;
float CurrentYaw = CurrentRotation.Yaw;
float YawDifference = DesiredYaw - CurrentYaw;
YawDifference = FMath::Wrap(YawDifference, -180.0f, 180.0f);
ControlledPawn->AddControllerYawInput(YawDifference * DeltaSeconds * 10);
if (FMath::Abs(YawDifference) < 1.0f)
{
bIsRotating = false;
ControlledPawn->bUseControllerRotationYaw = false;
}
}
I wouldn't call myself "wise", but thanks :P
The Rotation of the PlayerController should already be in sync.
HOLY MOTHER OF WALL OF TEXT
Vertical screen doesn't help that message.
well, it's just to keep it short. That's how it doesn't work right now xD
Yeah that part I understand, but what I don't get is why they don't actually move the current list out of the static map, since presumably once broadcast you don't need em anymore and they should clear. Prediction Key stuff went through a lot of changes in 5.5 so is quite interesting
The CMC is already sending the ControlRotation to the Server. @subtle kernel
There isn't really a need to go beyond that.
okay. but, how do I say CMC to rotate to face specific vector?
When I rotate with player input it's all good and fine. But as soon as I try to do it programatically, nothing I tried works so far
Right, so you have to understand a bit how the CMC and prediction likes to work.
If it's a Character that is actively controlled by the Client and you have the Yaw of the Character use the Control Yaw (checkbox), then rotating the Character to face something might get overridden by the CMC. Or rather by the ControlRotation the player sends.
Which means if you rotate the Character, you also need to rotate the ControlRotation to the same direction.
At least in a naive first approach.
How do you control the ControlRotation? Currently I do rotation like:
ControlledPawn->AddControllerYawInput(YawDifference * DeltaSeconds * 10);
You can just set it
If there is no setter on the APawn class, then there should be one on the AController class.
So I don't need to manually replicate rotation, like I do it now? I just need to do it either on server or client changing yaw along with ControlRotation in sync?
In theory, yes. For something like your Ability I would probably look into RootMotionSources.
GAS exposed them to GameplayAbilities, but you can use them without GAS too.
I'm neck deep in GAS
Then you'd usually just use RootMotionSources in the GAS Ability.
There should be some that can also Rotate. If not you can make your own.
They are just structs that ultimately provide the CMC with a "fake" RootMotionTransform.
But those are usually for fixed movements.
If you need a dynamic, constant rotation to a target, then you might want to handle this differently.
nah, I don't want dynamic
RootMotionParams.SetRotationalAcceleration(CurrentRotation - StartRotation);
gpt says something like that
GAS has nodes for it
You use them in your Predicted GAs
Check RootMotionSource.h
There is a huge comment in it explaining them
okay
I don't think there is one that does just rotation
These are the default ones that exist
You can inherit from FRootMotionSource and make your own, following how they are done.
It's not really rocket science.
You can check the first one, the ConstantForce one for an example.
Most of the function are boilerplate code
::PrepareRootMotion is the one that ultimately does the heavy lifting
At the end it calls RootMotionParams.Set(NewTransform) where the existing ones almost all just pass a vector in, but you can do some rotation stuff
No worries
I tried it out and it works now, thank you very much for the help
Anyway to access the FProperty chain being serialized within an Iris net Serializer anybody know?
what kind of net serializer?
the member descriptor should be accessible from the offset
Basically I've got an item that's inside a fast array, and I want to change what the item serializes based on settings of the fast array container property
So I've declared a net serializer for the item type, but can't see anyway to get the outer fast array from inside it
either from within Serialize or Quantize etc.
pass some meta info to the item when it is added to array (haven't tried that though
)
though it will not work if object was added to multiple arrays 
you may use wrapper struct for items 
The other option sadly is duplicate information into all those items, which I don't wanna do. Upsets the alignment etc.
ugh the property descriptors can sometimes contain an fproperty
the owner is in the instance descriptors too
Hell I don't even know how to get them 
Looking now at FGameplayAbilityTargetingLocationInfoNetSerializer which seems to do some shenanigans with descriptors but reading through this code is giving me PTSD
setting something's visibility to hidden breaks/disable replications for the hidden object?
like if i am in ADS mode and want to hide the head without propagating to childrens for local controller, and the head is the root of the modular body
after doing this baseaimrotation and controllrotation stops working
Yep, if it's hidden and has no collision then by default the Server marks it not relevant for anybody
You can override IsNetRelevantFor to change it
Thank U it helps alot
also found another way to sovle it, visibilitybasedanimtick in character class
need to be always tick pose and refresh bones
not sure if it will effect optimizations but it works
That doesn't have any effect on relevancy
Just means you'll be running animations on the server and when it's not actually rendered
Does ChaosVehicle have good integration with replication? According to the docs, Modular Vehicles should have decent implementation, but I can't get that one up and running.
@thin stratus I've noticed the client is receiving incorrect stamina value, i.e. not what the server sends
I've set breakpoint there without condition and its always 100.f
The breakpoint in that screenshot is never hit, so its sending the correct value
I'm making a merged branch for PredictedMovement (for sake of BP users primarily) so maybe I managed to miss/break something but I can't see what
I was using the predicted movement plugin, and i noticed that the stamina you send to server is one 'tick' behind, cause you are not updating it in PostUpdate.
You should have two stamina values in SavedMove:
- StartStamina, used as you use stamina now
- SavedStamina, only set in PostUpdate and sent to server
Else it is always gonna desync if a change is over the set threshold
Yeah I think Stamina could use some updating in general
I actually cover that here: https://github.com/Vaei/PredictedMovement/wiki/Move-Containers#delayed-moves
But I haven't updated Stamina with this new info yet
I assume that is what you're referring to
Yup
If you notice anything else like that feel free to ping me here or create issue on git
I'm working on v2 now, its very close, I accidentally updated main a little early lol so its temporarily in a non-ideal state
But the main feature in v2 are modifiers
If you were making something not QUITE RTS but close, with maybe a few dozen characters running around with no direct control, would you use CMC?
That's kind of on the threshold of yes/no
Sounds unnecessary tho, in fact Mover might be able to handle those simpler characters very well
We used Mover for Critters because we needed lightweight pawns
Its not ready for player-controlled characters but it worked well for that
Yeah I might want to play with Mover a bit
What's the TL:DR on Mover nowadays? Not quite ready for prime time but worth messing with?
We're about to release a game into EA with those critters and they're fine
Mind you at this point they mostly just sit there due to time constraints, but they do work
If you need root motion anim/sources then abort abort abort (ask Cedric how much work that takes)
But specifically because yours aren't going to be directly controlled, I suspect it is an option worth investigating for you
Is it as much boilerplate and tightly coupled as CMC or more of a generic movement system?
Hey I'm wondering if people are using Iris in their projects, or if it's something to avoid
I'm looking to start a new multiplayer project in 5.5.2 and I heard it's better than the default system. But it's still marked as experimental as far as i know so I'm not sure if it's just not feature complete or if there are actual issues
Honestly its a bit scattered
But its workable
How does PlayerState.PlayerId UniqueID work?
Is it fine to rely on that and match up certain data stored longer term for that?
Like if a player disconnects and joins a server a week later, will it be their same PlayerId UniqueID?
Or should I assign my own UUIDs based on login instead?
I'm trying to find a better resource to learn about the PlayerState.PlayerIdUniqueID. I went back through cedric's multiplayer compendium (which I'm surprised didnt mention it)
Use the UniqueID instead
PlayerId is just an identifier for that Session.
UniqueID is a globally unique identifier for that Player on the running platform.
Errr, I realize I meant to type UniqueID.
Is it a hash function or something of their hardware specs/install that creates this, so it won't change?
The UniqueID is dictated by the OnlineSubsystem.
If you are using Steam, it will be your SteamID for example.
No problem.
guys, what do you use for logging in dedicated server shipping builds?
Might need more context there
But... the log ๐ You just have to enable it in shipping
Also, Sentry
ah, enable logging in shipping okay, it's great advice ๐ thanks!
need to look at this sentry, is it epic product?
https://docs.sentry.io/platforms/unreal/
https://sentry.io/welcome/
Its free for 1 user
oh, okay, thanks
I'm all alone here, yea xD
btw, it shouldn't be possible to connect from shipping client to dev dedicated server?
Why not? They are separate programs, so long as you don't gate the connection yourself
oh, okay, that's nice
now I have a problem with shipping client won't show anything at all after loading screen ๐ I wonder how to debug it xD
Assuming you're building from source engine I'd recommend enabling logging in shipping.
how do you do it, can I ask?
is it this one?
seems like it will rebuild everything from scratch 
Yes, I'm afraid so.
i have these three things, and these 3 server functions. for some reason the transform doesnt update in multiplayer, while the 2 bool properties do when im on clients.
anyone know why that might be?
You marked only bHasNecessaryResources as replicated, other two shouldn't update on clients. So it's normal that transform doesn't update. Real question here should be how the bCanPlaceObject updates on clients ๐ค
i did that for testing. the Replicated doesnt matter, as im not even doing a DOREPNOTIFY for them
Isn't your question why your variables don't update on clients? It sounds like replication matter
it is, but both of the bools replicate
only the transform doesnt
right now the way my code works is that the client is doing some work, and is sending updates to the server
not back and forth
So in the actual code they are all marked as replicated and have DOREPNOTIFY?
and then the server updates the world
no, none of them are Replicated in that manner. im manually updating the server's version of the property with a Server designated function
Okay and what do you expect to happen that doesn't afterwards?
im doing a builder system. so the client has a phantom object mesh, and has a soft class reference to an actual object. on the clients screen, they can move the mesh around. that works fine. the checks also happen on the client for if they can place or not (these are updated by the server in a different location). these all work
now, im trying to send the mesh's position to the server, so that the server can spawn an object into the world at that location
it is instead spawning at 0,0,0
so everything is working except this transform for some reason
and i tested this before trying to implement replication, and it does spawn in the proper position in that case
i could try to do the dorepnotify thing and do this more properly, but im too lazy right now and i thought this would work, especially considering part of it does work
and i think in theory it should work just fine
Do you see that Transform variable in this server rpc when you debug? it's not 0,0,0?
Is it possible your issue is with the spawn logic or the spawned actor maybe? Have you debugged your functions?
ive done much printing in various places. im not positive i read the logs correctly actually. its hard to see what the server is doing when so many logs go through. as far as i can tell the server never gets updated.
ill just try an RPC tomorrow
and yes that does say relative transform but it doesnt work either way. i forgot to change that from my testing
go get some sleep xD
Rider is so bad at it, yea
Yeah thats ue shit + rider, it does suggest _Implementations for autocomplete
implementation calls work on native functions too...bit inconsistent
It might be possible that you call them as a regular function, so just running locally without nothing to do with RPC
possibly. changing that hasnt yet fixed it. i may need to do it tomorrow anyway. good catch though, thank you
we are so back baby
i love you
i sleep now
Hi all,
Iโve a dedicated server and a client game (UE5) and I want to change the tick rates on them.
For client:
I am able to go in project settings and under frame rate click to smooth or fixed and set it to a value under frame rate.
For server:
I tried updating script .ini files and add values such as t.MAXFPS or NetServerMaxTickRate and set it to a value
But then I launch the server with the -log parameter
I get one line which says:
bringing world up for play .. (max tick rate 30)
Even though I clearly set this up to be a different value
Any ideas what am doing wrong ?
any tutorials on how to create an auction house
what kind of multiplayer challenges you see here? isn't it quite simple task if we're talking about client/server interaction?
well i never done anything associated with multiplayer , i need some resources
well, there're many resources regarding general multiplayer ๐
And 0 about making auction houses on UE ๐ i'm almost 100% certain
im want to build an idle game where only multiplayer features would be a global chat and an auction house
you can begin here probably:
This compendium is meant to give you a good start into multiplayer programming for Unreal Engine.
you're probably not going to find a piecemeal tutorial on that, learn the concepts
it's all down to RPCs and replication in your case
and that above link is a good place to start
thnx
IF the client triggers an event and sends at that moment GetWorld()->GetGameState->GetWorldTimeInSeconds() and when the server receive the server compares the delta ...do I get the 1/2 RTT ?
Your world and server world seconds are not the same. RTT should be calculated by sending a timestamp, waiting for response with the same timestamp (which should be the "R" in RTT) where you obtained it and calculating the delta from that timestamp again where you obtained it, as far as I know
well use a standard ping and divide by 2. There is no way for the server to know exactly how far back the client sent the instruction
Round trip time is just the time it takes for the client to send data to server and back
you can use RPC to send the data
As client -> Send Server RPC (Client Time Stamp)
Server send data back to client
I know that , but when firing an ability such as a projectile I can't have fun by passing multiple timestamp back & forth
I don't think that's what you are suppose to do
The ServerWorldTimeSeconds feature in AGameState is very rough
Not really meant for accurate prediction etc.
if you need sync clock, then just implement network clock
or get the one in player state, I heard it's good enough
just up the update value
ServerTime wasn't even in the consideration there, it was client world time comparison with server world time
Yeah, they are unrelated
But the ServerWorldTimeSeconds in AGameState gives you a very, very rough approximation of the current server world time
Good enough for some things
ServerDeltaTime = GetWorld()->GetGameState()->GetServerWorldTimeSeconds() - ExecutionTime;
that's what I'm doing
when writing the question I just use the standard time
Oh I thought it was different worlds' time comparison since it was GetWorld()->GetGameState->GetWorldTimeInSeconds() there
So the GetPingInMilliseconds from playerstate is better
I just want to spawn a projectile server side that catches up to the client position
Take the ping from the player state and halve it, that's your starting delta time
Although why server would fast-forward I'm not sure
Is it still better to make our own rather than using the builtin one, as in resulting with significant difference?
that was my question, because I'm having a hard time figuring my print ๐
I did my own only because I wanted more utility, but for fairly loose timers it's ok
they really jacked up the default update frequency in AGameState
I just ping-pong RPCs back and forth via player controller, that works good enough for me
(unreliable and infrequently)
pretty sure I nicked it from UT actually
UT uses that method but the engine doesn't have it? ๐ค
Well UT is pretty specialized twitchy shooter I guess, and targeted very high tick rate servers (like 120hz IIRC)
They also really didn't care about making the game "modular" or abstract, they specifically had the goal of making UT - so separation of concerns etc wasn't really a big deal
hence weapons and characters being extremely tightly coupled
worked well though.. must be nice to have highly specific goals 
https://forums.unrealengine.com/t/severe-lag-ping-in-an-empty-ue5-project-in-local-standalone-any-net-mode/1787863 might experience this based on my measurement.. ping says 300 but serverdeltatime says "300" also...
Steps: create a new project from FPS template. print ping from player state in character BP. launch as Standalone with 2 players in Client net mode (with a dedicated server) this happens with a listen server too. basically any mode which makes the server run outside of the editor. ping will be 120-200ms with noticable lag. Other notes: turn...
any reason why repnotify replicates after aprox. 10 sec?
Could be a whole lot of stuff
First thing that comes to my mind is, assuming you're in editor without any network emulation and 10 secs is exaggration, if that's a variable in PlayerState, it has a low net update frequency
Well, actually checking the PlayerState, it does seem like it's similar to Character now
Is this changed at any time? I feel like I remember I was dealing with why clients were receiving updates on player state a bit late and default frequency was way too low
I was comparing MinNetUpdateFrequency, Character is still 100x more frequent than PlayerState
Anyways, to come back to the question, it could be a whole lot of things like from having high ping to forgetting a timer to set the replicated variable or something, so it might need some debugging or more context to answer it
its gamestate, net update is frequency is 10. i tried to add force net update, no changes
Well I don't have any specific idea about that sorry
Not sure if makes a difference but seems like a lot of replicated variables though
Is it just these variables that replicate late or any other side effects you can see during quest changes?
these are only that need and are replicated in GS
custom ones ofc
no, they only are set and replicated on quest start and end
and client side just triggers event dispatchers for UI elements and level blueprint to load proper dungeon
I want to ask if it's possible that your quest struct is too big but I don't think that alone could result that much delay
it never had any problems, also it started recently, i'm checking 1 thing that I changed recently and see if it hels
yes, i got the culprit... network saturation for sure but now I need to adjust it somehow
dungeon was generating (asside of meshes) actor that's interactable and replicated. That caused saturation, I need to rework the actor or spawn logic
Hey folks!
We are experiencing some roadblocks with getting two clients to interact with a shared entity and doing the prediction etc required for that.
Imagine having two players steering the same vehicle, one controlling the wheel and the other taking care of throttle.
Looking to chat, and maybe pay a bit for some consultancy ๐
Ok I've been stuck at this problem for a week. Since this only happens when I test in multiplayer, I'll ask here. For some reason the object nullifies inside a struct that I assign to an array. I first create a new object, add it to the replication list, also ensure that's it's supported for replication and then assign it to the struct before adding that struct to an array (multiple times on different indexes). All this happens in a server RPC. After I do all that, when I debug it, it shows that the object still exists in the structs, but when I check in the editor they are not there. Why is this happening? Here's the code: https://paste.ofcode.org/AuFGCg3TtCrgmTmgPazpe5
Also an error that I get when it calls that is in the log file.
Might know why actually
the ensure message is practically telling you what to do
yep
also it's a great help to have engine symbols installed for debugging
I looked at the error message many times but I didn't really know what that meant
is it a plugin?
no, it's just debug symbols
you install them from the epic launcher as an option
and if you launch via the IDE (with a debugger) it'll actually allow you to interact with the callstack
which will help see the issue better
interesting. I'll see
Also that was the issue
I just had to enable it and that's all
Crazy how I spent almost a week trying to debug this
and it's just a boolean I forgot to enable
well if you do those things, the next time shouldn't be a week
hopefully
I usually don't look at the output log errors that often since I always thought that they don't tell anything useful but it seems I was wrong
is it this?
oh yeah right
srry
Sorry for interrupting. Is there any way (if yes I'll look myself) to test Multiplayer for 2 people but using Standalone Mode?
How do people test Level Travel (from ''Session/Lobby'' Level to the Target Level if so far I cannot join the session when I use Standalone mode. The thing I want to test is passing the data that I saved on Player State, and ''passing'' it to the ''new'' Player State (CopyProperties) works only when tested in Standalone Mode.
That's probably outside of the typical Unreal multiplayer system. You'd have some sort of global server or service that you can talk to directly. Each "client" would be playing in standalone.
You can enable seamless travel for PIE if your aim is only testing CopyProperties
Are you setting the listen option upon host opening the initial level/lobby?
Hmm. Just out of passerby curiosity... do you think it would be possible to do what he wants or similar, at least on a small scale, utilizing beacons?
guys, I'm seeing strange, I run my client like:
CubesOfRealityProtoClient.exe 127.0.0.1:20001 -log
Here's shipping package logs:
[2025.01.29-16.10.34:457][ 0]LogInit: Display: Game Engine Initialized.
[2025.01.29-16.10.34:459][ 0]LogInit: Display: Starting Game.
[2025.01.29-16.10.34:459][ 0]LogGlobalStatus: UEngine::Browse Started Browse: "/Game/TopDown/Maps/Login?Name=Player"
[2025.01.29-16.10.34:459][ 0]LogNet: Browse: /Game/TopDown/Maps/Login?Name=Player
Here's dev package logs:
[2025.01.29-16.07.46:614][ 0]LogInit: Display: Game Engine Initialized.
[2025.01.29-16.07.46:616][ 0]LogInit: Display: Starting Game.
[2025.01.29-16.07.46:616][ 0]LogGlobalStatus: UEngine::Browse Started Browse: "127.0.0.1:20001/Game/TopDown/Maps/Login?Name=Player"
[2025.01.29-16.07.46:616][ 0]LogNet: Browse: 127.0.0.1:20001/Game/TopDown/Maps/Login?Name=Player
It seems that shipping trying to open local map for some reason, when dev travels to server.
Why it happen that way? What can be fixed?
I want to make a game whith procedurally generated maps. I want to make it like a 3d cube grid. The parts are almost always the same size, some are bigger, but it always aligns with the grid. Now I want to know:
What is the smartest and most multiplayer-viable method to do this?
for anyone who is concerned - you cannot override startup map in shipping build via command line
same seed, same map
Ok, but what about building the level? Are they supposed to be like actors
Or is there a special class for this?
they can be actors
but what I'm saying is you don't replicate the actors, you replicate the seed that placed them there
When you play Minecraft, the server isn't sending you all the blocks, that's way too much data
you just have the same seed, and the server sends you the diff vs the generated level from that seed. On a fresh level, the server has to send you pretty much nothing
Ok thank you very much
But lighting will be worse?
how would that make any difference?
it has nothing to do with it
your options are:
Server runs the procgen, replicates the results
or
Server and clients run the procgen, getting the same result
for something with as much data as you're talking about, you want the first approach
You cant have built lighting on actors
As far as I know
you can't have built lighting with procedural generated maps
how the hell would that work
The parts that get added in are like 20m x 20m x 20m cubes
does the game ship with the maps as static maps, or are they generated when you play?
They are already rooms
you can maybe have baked lighting within each room but that has nothing to do with what we're talking about anyway
how many cubes are you talking about?
The rooms are premade, but always end up in different configuration
I will use seeds
I just wasn't sure about how to handle rooms.
I thought doing them as normal actors could be bad for Performance
Considering there are also actors within these rooms
how many rooms?
That trigger certain events
So many I will use seeds
Like 15ร7ร5
5 in height
So less than 525 rooms, because some rooms can be as big as 25
Then one room has the scale 5x5x5
For the beta, I will go down to 7x3x3
Have you successfully spawned a room at runtime yet?
Yes
What is a room then, an actor BP with childactorcomponents?
Rn, yes
or is it a level instance
They are actor BPs
random sanity check q, maybe someone can answer.
player has a 'sheath', basically just an overlap component.
in multiplayer, the player makes a server RPC call which directly calls AttachActorToComponent.
the pickup actor is replicated, the sheath is replicated.
does the attachment automatically replicate, or do you need to multicast from the server RPC? i feel like i have only gotten this to work multicasting, but my understanding is attachment is replicated by the server automatically provided the actors involved are replicated.
Hey guys I have an actor that is replicated, I am trying to use RPC run on server and run on owner only however these aren't firing, I've set each ones owner to the player controller however still not working, anyone know the right way of doing this?
what is this actor?
Hello, how can I use level streaming in multiplayer so that load and unload events only affect the event owner?
I don't actually have any engine sample for float comparison here
Do you think it should be !FMath::IsNearlyEqual() or != for PostUpdate()?
I believe it would be better to use IsNearlyEqual like is done in CanCombineWith.
But in my project i decided to skip this check, and block combining only if in post update the stamina drain state changed from the beginning of the move.
This is because otherwise it will always prevent combining if you have constant stamina regeneration
Ooh yeah that makes sense
@twin vessel sorry I just realized -- we're not checking stamina in CanCombineWith
We're only checking bStaminaDrained
@twin vessel sanity check this for me
I would skip the check for stamina value difference in CanDelaySendingMove and PostUpdate for the reason explained before. Other then that seems right.
Probably (but i am not sure) putting the check also in CanDelaySendingMove is redundant since you are forcing no combine in PostUpdate
It is the value you send to server in network move
Could you show me your implementation?
Look at XMUFoundationMovement
My reasoning is that since ServerCheckClientError is run at the end of the server's move, we need to check the current stamina value with the stamina value at the end of client's move
I do notice you don't have Start/Saved stamina drained state, was that not a consideration , or a reason for that?
I do think that should delay sending moves and disable combining
Hmm yeah I have borked something here
@twin vessel have you tested using p.netshowcorrections 1
I'm getting intermittent corrections at similar intervals so I've set something up wrong
Yes, i get no issues with my setup
In PostUpdate i directly compare the movement component's drain state with the value saved in the SavedMove
Hello, how can I use level streaming in multiplayer so that load and unload events only affect the event owner?
Noob here,I'm trying to replicate my dialogue tree.But it isnt work properly.
Widgets don't replicate.
Widget displays but the task dont works
It might display, but any of the RPCs and replicated properties you're using are not replicated.
So how to fix that
Anything that happens in a behavior tree also do not replicate, they usually only happen on the server where the AI Controller associated to the behavior tree resides.
Widgets are local only meaning they can only be used to display data that the client has already. That means you need to use some other replicated actor or component that the client has relevant at the time to handle what information needs to be sent or received from the client.
Like you might want a "Dialog Component" that is attached to say your PlayerController.... This component you can then use to send RPCs through, and have specific dialog windows pop up with whatever information you want for that paritcular player. If the player needs to send some kind of choice to the server, then you'd put the RPC in there as well.
Thanks for the response.I'll check and give an update @sinful tree
Can anyone tell me why unreal makes u write _implementation at the end of RPCโs definitions in cpp
because you don't call the _Implementation to make the RPC replicate
you call the ufunction which is defined in the generated header which actually queues up the RPC
so they are two distinct functions
you can call _Implementation and Onreps etc directly if you need to or even override them from parents if they are virtual
Interesting thank you for the explanation
notably this is similar in BlueprintNativeEvents
where the regular non-implementation function is optionally sending the call to the blueprint if one overrides the function
you can call
_ImplementationandOn_Reps etc directly if you need to
it's an edge case though.
There is extra step in calling RPC or BlueprintNativeEvents due to straight forward nature of C++ language:
- When you call a function, it literally executes it's body, while
- For
RPCyou want that code to be executed on a different machine. - The idea of
BlueprintNativeEventsis to giveBlueprintsa chance to handle(consume) call instead of C++.
So in both cases you can't just call original function, an indirection is required.
but you CAN and there are many cases where you need to call an onrep directly on the server to do work intended for responding to changing data... It's rarely needed unless something is a bit spaghetti but I'm trying to convey that they are not magic
it's definitely not the common case I guess
agree, but it's a good thing to learn when you already confident in base functionality, I find it confusing for beginners to dive into such details 
Ah so it's basically preprocessor / UHT magic that glues the two together?
any tips on using motion warping in multiplayer settings?
I let client calculate the final position and have server use that data for the warp location.
it's still correcting however
might be because there is a collision and what the server sees not the same? but then how do I go around this
Any tips ๐ฆ ?
unity or unreal?
sever-side?
Would really appreciate 2 cents here ๐ญ
Client send the location
idc much about cheating for this game
did you disable server correction?
bIgnoreClientMovement.... = true
and what is value of "NetUpdateFrequency"?
default is 30
Yeah that's what I end up doing atm... but feels wrong
enabled after the ability end
NetUpdateFrequency is 100 for character
I think there are some unnecessary interpolations.
Hey, I'm just trying to replicate an INT. What am I missing here? I just want the INT to change on both systems when one player clicks.
@mild creek you already set it for one of the character
Append string and print object and you will know what im talking about
you have 2 characters in the world
As client you RPC from character_1 , server set the int to 2 then it replicate back to the client's character_1
so now server's character_1 and client's character_1 int is 2
where character_2 remain 0 since you never trigger the RPC on character_2
ahh okay, thank you very much!
hi there am kinda stuck. am using a cable component and i want to replicate it but i can seem to get it to work right
So to translate that print string
Server: Character_1 int is 2
Client: Character_1 int is 2
Server: Character_0 int is 0
CLient: Character_0 int is 0
Okay I think I don't understand something. I'm spawning actors after actors which is probably the problem it self (one actor gets spawned, then the one that spawned spawns again other 2, but i don't think it matters).
Player Controller spawns Faction Manager (as Owner I plug Self so as Player Controller)
Faction Manager spawns Hero (as Owner I first Get Owner (of Faction Manager) then I cast to Player Controller, and I past that Player Controller as Owner of Hero.
Inside Hero I again need Player Controller reference, so I take Get Owner of the Hero, cast to Player Controller, but it turns out it's a AIC_Unit ?
Yes, Hero set to AI Controller Class, but I don't get (like I read so many articles I never saw that AI Controller can steal my ownership?)
Now I'm kinda confused what the I need because i cannot test if my logic will work.
Basically the context is i'm trying to let the Hero reveal fog of map for THE ''client''/''player controller'' (i'm lost in naming these things because) that owns it. and yes I use AI mostly to move units so far? but i'm going to scrap this logic and put it inside units blueprint.
and from Faction Manager as I spawn hero, sorry for mishmash but I'm trying things before i clean them up nicely
Is your BP_Caravan a pawn?
yes, it's child of BP_Unit and these are pawns that can be moved by player (top down rts like controlls)
Can you check the Auto posses AI of the caravan BP
If you don't possess a pawn and auto possession settings are set, they can get automatically possessed by a player or AI controller, which eventually changes to owner as well
Yup, you might want to disable it
Or set to placed in world in case you want any pawn in scene to become an AI
Or just possess the caravan with your controller after spawn and let the settings be as it is
I manually put Player Controller variable on spawn from the Faction Manager(for now) and I can use it inside caravan so for now it's fine, just was confused that Get Owner suddenly changes when there is AI Controller involved. I have some logic on AIC_Unit for moving but I'll check if I can disable itetc.
It's not an AI specific behavior. Possess function calls Pawn->SetOwner(this)
I don't know where Spawn exposed variables are set but probably order is like Spawn -> Set exposed variables -> Check for auto possession -> Possess -> SetOwner so your parameter is overridden
What does bAllowJoinViaPresence in FOnlineSessionSettings actually means? Presences for me is status kind of a thing like "listening to spotify" in discord or "playing x for y minutes" in steam, is it something different for online subsystem context? What else can it use and what difference is there to use it or not?
For example, I'm testing with null subsystem and if I don't set it to true, I can't find the session from another player. Why is this required and are there any other stuff that could be used to make the session discoverable?
Is it possible to have a client join a running listen-server session in the UE editor at a later time, not when I start playing the level in PIE? I would love to be able to test scenarios where another player joins the game later into the session. Is that easily achievable?
yes, but I think you would need to open the windowd for it before, just not join him straight away
and usually people make lobbys like levels where you can click to host session and then join session
you should be able to join match that is already ''live'' when players already went trough lobby to the match level
How do I stop the server from replicating rotation to clients?
When I call "Set Actor Rotation", just on the server side, this is arbitrarily replicated to all players clientes
This did not happen in Unreal Engine version 4.27.2, this was put into the code in version 5.
These events are also replicating even though I'm calling them outside of an RPC
Hey there!
I just want to drop something out of my inventory, so basically replicating "Spawn Actor". As you can see I juse RPCs as usual, but it doesnt work? Am I being dump?
Playercontrollers are only on server and owning players machines
so if you have 1 client and 1 listen server, both playercontrollers exist on listen server but only clients exists on their machine
Anyone has idea what setting Auto Poses AI does extra that my logic that w as working just stops? and i have no idea how it's even related. When I set it to Disable, players spawn, they got their units, they only see their own ''fog of war'' and when I set this to Posses suddenly 1 player doesn't see anything. The thing is if I don't possess I cannot move with AI MoveTo? Can I use something else?
It doesnt even work from Server to Client wtf?
Hmm, so when Possesing is disabled my character mov component max speed is set to 0, and when I posses its the one I actually set.
Is there an easy way to find the nasty RPC that something calls on tick and is marked as reliable?
I found one, but I wouldn't be surprised if there are more (client's project)
I feel like I saw somewhere that would show you all objects that are ticking. Like a cmdlet thing you would run. As for detecting the RPC - idk
dump ticks
It might be enough to breakpoint where a reliable rpc is progressed
Ticking Actors might not give me much
Thing could run on a timer
Only other thing that I can think of is profiling and seeing which area is filling up fast.
ยฏ_(ใ)_/ยฏ
NetDriver.cpp:2671 (UE5.4) has a Bunch.bReliable = 1; line I can breakpoint
Hey there!
are there any tutorials or courses that cover replication for dedicated servers and NOT listen servers.
It will be the same
guys, I tried to implement my own FRootMotionSource_ConstantRotation for synced rotation in multiplayer, it works okay when call it on client, but when I call it on server it gives me:
checkf(false, TEXT("Serializing RootMotionSource without NetSerializeNative - not supported!"));
not sure what it is. there's no such method as NetSerializeNative in FRootMotionSource
Only thing to keep in mind is visual stuff doesn't happen on dedicated servers
Thats weird, because I made some multiplayer abilities that are working on listen server, but not on dedicated server (when i click on play as clients)
You have to elaborate more than that
And that sounds like the issue is not about dedicated server
More like clients can't get the ability to work
So playing with 2 players as listen server mode ( 1 server and 1 client ) as client might produce the same result.
Hey, Cedric, I tried to implement custom root motion source and it seems to be working okay. But it's not getting replicated at all :/ I'm using it like:
TSharedPtr<FCOR_RootMotionSource_ConstantRotation> RotationSource = MakeShared<
FCOR_RootMotionSource_ConstantRotation>();
RotationSource->InstanceName = FName("RotateToFaceCoordinate");
RotationSource->AccumulateMode = ERootMotionAccumulateMode::Override;
RotationSource->Priority = 900;
RotationSource->TargetDirection = DirectionToTarget;
RotationSource->RotationSpeed = RotationSpeed;
RotationSource->Duration = RotationDuration;
RotationSource->SpeedOverTime = SpeedOverTimeCurve;
CharacterMovement->ApplyRootMotionSource(RotationSource);
So I either run in on server or client and I think it should be replicated automatically from both sides, right? :/
Or maybe I actually need to run it on autonomous proxy as well as on server. Because I see rotation on simulated proxies now, when I do rotation on owning player. Okay okay. I will test it.
I've implemented rotation root motion too, and It needed a engine mod. At least in 5.3.
Basically, IIRC, Rotation is not taken in account alone. It needs to be associated with translation too, which sucks.
And there was something associated with the accumulate mode ...
All in all, it was a bit of a mess like "What if we didn't care about rotation?"
Plus, make sure your structure has ALL the correct override for serialization, and check the one used by default in the engine. Some are missing for rotation IIRC
(FUN)
Needs to be added on both sides.
Well Server can add it alone ,but then you get a correction i assume
Hello, how can I use level streaming in multiplayer so that load and unload events only affect the event owner?
I do add it both sides too.
Corrections are very minimal, almost inexistent with an acceptable ping.
quick sanity check question: is it normal that calling ClientTravel after joining a server for the first time causes unreal to first load the default map before loading the map that the server is actually hosting?
everything is otherwise working fine ๐
when ServerTraveling, before you join destination map, you travel trough transition map which you can set in the settings, if nothing is t hen then either some map is used or new one is created
Are Structs not properly replicated? Do I have to mark somewhere in C++ to be replicatable? im trying to figure out why my system is not updating the health bars for clients meanwhile for server it works. If it's not only because of structs I can post more data so many someone can help.
@normal viper The only reason a Struct wont replicate its values, is if they are not marked as UPROPs.
Or, the Actor itself is not Replicated.
Hmm,
- I have component on unit with Health Bar
- Icreate Health Widget inside Damageable Component, then I take it and assign in the unit (i tried delay to see if maybe here is fault, but that is not the case).
- In Damageable I initialize widget, for testing purposes I put ne Health and Max Health and they replicate.
- Inside W_Health I bind to Damageable On Health Update event ..
with the numbers everything works because I can see printing good amounts after I take all actors and damage them by server in the player controller, just widgets are not updating on the client, theyare always 100/100 (default value od Widget).
I even was about to do something on repNotify but im not sure if that is the problem.
Is the Component set to Replicate as well?
Client: 100/100
Server 156/234
Damage: (these are numbers actually from Damageable Struct as I didnt change it in the Take Damage function
and also replicated as it's added on the unit
maybe when I'm initializing component and i take Data Asset it's not replicated?
How is damage applied? Why does the client tell the server they get damaged?
That's kinda a flaw imo
Hmm, so 1 more thing maybe it will help. I removed W_health from the Widget Component that is on Unit. but i'm setting it here, and so it actually still works but only for the server. So I guess the problem is with how I initialize it?
this is the start of this ''flow''
What is w health? Widget health?
You are trying to replicate a widget? Well you cant
it's widget component put on unit
Why does widget component hold health?
I would rework a lot of this tbh. Decouple your widget and your attribute
which one? i think you are misunderstanding, there is Widget Component put on unit, and then there is another WHealth that was created on AC DAmageable
widget doesn't hold health variables
just receives them with bind from the damageable component
i guess i have to change the flow and just create widget on units from player component on each client ?
Make an actor component that hold your attribute at the very least if you don't want to use GAS
Widget is local, other player will never know someone else widget. And that's good because you shouldn't be thingking about widget in networking. What you need to focus on is the internal data (hp, damage, etc.)
And your widget in turn just read those variable
Do I correctly understand that calling a multicast function on the client actually runs the function locally? And that generally you want to gate it to the server unless you really want that multicast call to run on the client?
And fyi structs is deffinitly replicated, I used it all the time
It will call the function locally at best but you probably doing it wrong already
Mc only meaningful if called by server
Server will then tell the client to run the functions on everyone's copy of the actor
i more or less know the ideas but what does it mean in practice? do i call player controller so it will run event for it self to ''create widget'' for this client (himself?) and then data is replicated so it will just update it?
Roger, thank you.
You create the widget whenever you want. Then just bind the variable.
OnRep Hp -> broadcast ValueChanged
Widget on construct get my character attribute component-> bind value changed
so in case of 30 units I have to basically create these widgets not on them, but maybe on them but trough the client for the client? ๐
Why do you even think about networking when it comes to widget
i mean I think the binding is fine? it should work..
The widget only read the internal variable
It gets updated when it gets updated
Take for example an hp bar
It just read the character hp
i dont know because it feels weird when i have unit on the ground and in my mind it should have 1 health over himself and everyone just read it, meanwhile it turns out i have to create 4 widgets for him for 4 players so each of them has own health bar of this unit
RTS game?
yes
btw it works for server.. everything is updating you know
Because server is the server, it's no different than playing it single player
Multiplayer is about communication
there was confusion maybe with wrong numbers on bar and on printing, it's jsut that 2nd player doesn't see this widget of the unit
@chrome bay Hey! I read back up on HLL's projectile implementation, using the manager to "simulate" them just as data. I have a question, since clients are a little behind, how do you handle long-distance projectiles with travel time & bullet drop? If a player is walking perpendicular from you, wouldn't you never hit it because you're seeing in the past?
Or do clients also tell the server when a "long distance" projectile hit a player?
You create widget for every unit.
For simplicity can just add a widget component to the character. And no, don't make it replicated that would be pointless.
Begin play -> get health widget component -> get my attribute component-> bind value changed
Widget on construct -> get owner -> set text to owner hp
So you get the initial hp variable to display on your widget and update whenever your value changed is called
Ofc doing it on begin play mean there is an instance where variable may not be replicated yet
So you can see 0 for a few frame for example
But you can work it out from there
get my attribute component is what in this context?
Your hit point or what ever variable you want the widget to represent
also just taking widget component that is added as component, it does nothing to it
Not sure what you mean
like this component itself doesnt have any variables yet
or i cannot bind to it, i first have to create widget somewhere and then set it as it? ithhink at least its like that
Is that not widget component?
You can add a widget to widget component
An instance will be created
Look into the detail tab
Gtg for now
you can only put class, is this it..?
Yes
How does the damage take place? How does it happend?
Going b to work now but I can write sample code to demonstrate showing hp and taking damage after work
I have problem with showing up widget to the 2nd client, not really with taking damage (it works more or less) ๐ , and this is usually called by interface first on BP_Unit which then calls to component on himself
so i modified the starting thing a bit, and now its shows actually proper starting values on server and client,
rn it just doesn't update the client
and widget itself:
If you read your own code, take damage is executed on server
So what do you think happend with call on health update? Do you think the client magically knows?
That delegate will only be called on the machine that execute it. In this case the server.
I can show you an example code later but the solution was given above if you want to try it your self.
Basically take damage should just deal damage
Don't call widget to do anything. You can broadcast but bear in mind that's only get called on the machine that execute it.
Take damage (server) -> set hp = hp - damage
OnRep_hp -> call value change
Make sense? On rep gets called on client ( and server if using blueprint )
So since you are using bp, move the on call value changed on the OnRep function.
On rep is literary a function that fire when the variable updates ( e.g when server update the client value )
OnRep damageable data -> call value changed
. Get rid of the call value changed inside the execute on server block
Ok so I found a response from @thin stratus from a while back about how to manually create and join sessions, and it works ok with a packaged build, but I'm still hoping there's a way to do this from the editor itself. Any clever creative solutions y'all might have tried in the past?
https://forums.unrealengine.com/t/how-do-i-launch-a-server/310995/2
The point of this exercise it to test clients joining later in the game
Doesn't the editor by now have a late join button?
Oh shoot, you're right. It's an experimental feature.
Yeah it should create a button at the top next to the normal play buttons once you started playing iirc
It did, thank you!
oh wow
for now only way to do it was "open mapname?listen" and then on client "open 127.0.0.1" ๐
Yus, I also only learned about it from a Client's Project
What is the recommended way to create a simple plane with client-side prediction? I think FN had those like 7 years ago.
I tried
- Vanilla Chaos Vehicle Replication
- Chaos Vehicle Replication with Physics Prediction (experimental)
- Chaos Modular Vehicle (experimental)
I have not tried this but is a backup - Code flying physics in a cmc and pretend the plane is a sphere shaped capsule
All the chaos replication really didn't perform well in my testing.
Modular vehicles is the best IMO but it still has lots of bugs
Like bad jittering
Also if you hit something too fast you will crash lol
Like the whole game.. not crash the vehicle lol
Although once they fix the jitter and crashes it will be superior to the old vehicle movement system
I will try again the modular vehicles, thanks for the direction.
physics prediction and async physics needs to be on for it to work
even offline mode it needs physics prediction enabled for some reason
probably uses callbacks for both cases
yea i assumed it has something to do with that
kind of seems silly as there's surely no real reason it can't be active in direct variable tickrate physics but I guess most of the reason for the existence of that plugin is predicted physics
- I deleted the call from inside Server Take Damage.
- I moved the call logic to the Rep Notify
- Right now it updates only for the client and not for the server.
Is this because that what you said, this broad cast call is only called on machine that execute it? so that is why it's on client 1?
So either I have to bind or just inside widget create custom event Update Health and pass these variables from rep notify?
Is there any trick to make the Modular Vehicle example use replication? I enabled the phys prediction in settings and it works in standalone, but switching to 2 clients with dedicated server lets client 1 drive around but client 2 sees the client 1 at spawn location.
OnRep is called on server too in Blueprint
do you have tick physics async enabled in your project settings? with just tick async physics on and physics replication and everything else default the example map works fine for me with 2 players
Ah, I was missing those! Thanks!
Just out of curiosity, how did you find out that those two options need to be enabled? Just reading source code or is there a documentation I have missed.
so in BP_Unit when I call on Begin Play to update it updates for everyone.. then when (probably here is mistake) I take all actors of class and damage them f rom Player Controller (i call TakeDamage Server on the component) it only updates for the clients at the moment, and not for the server.
I also changed to call just event and not binded call. What I'm missing out?
@normal viper got friends atm but maybe we can go on a 5 min call later. As far as I can see your begin play seems fine to me
What I'm doing wrong that it doesn't update for server now... hmm the worst part it's just guessing game until it clicks you know... like i wish I knew what I was doing haha xd
The on rep looks fine too
I will check it later
Just remember that changing a value on client will only change for it self
In one tutorial I saw someone just Bind from inside Widget
to the value from the component/actor
Yeah that sounds fine
You can bind whenever you want. In most cases just do it on widget construct
they used binding here will test it right now
uhh, it works
isn't this on tick though or something?
im gonna try 1 more thing because I think it may be problem how I initialized widget from the unit, it should just be on construct
Onrep Is called whenever the value is updated
So when you set the damageable struct on server
The server will then replicate the data to client on the next net update