#multiplayer
1 messages · Page 263 of 1
hmmm i think i will make a PoC at some point and will hit you up to reverse it you will have full access to anything you need from game client to memory read etc.
Sure go ahead
No, just checked. They use BattleEye now
but need to have some game for starters... so its usefull to make it
However they never removed the EAC files from the game installer. So it still is being installed on the system by the game even if they don't actively use it now.
Lazy Russian Devs be that way I guess. shrugs
¯_(ツ)_/¯
BE relies on kernel access too so if that's your concern it doesn't really matter
the files still can be there its not being launched unless they diditn removed it from the game exe
to be honest the only AC that "kinda" stops cheaters is ACE
but there is a bit BUT - its a rootkit, it doenloads whatever it wants from your pc on being prompted to do so - it screenshots your screens (not just the ones with a game) and doing some other malicious things "just to catch cheaters"
Yeeeah no thanks. That's a major privacy invasion in my books as well as a lawsuit of some sort waiting to happen.
its china so yea
Gross
and i heard that chinese version is even more invasive then international one
0_o oh jeez
about my thing
lets say this is the UObject class
UCLASS(Blueprintable)
class UObject
{
GENERATED_BODY()
public:
// Basic variables
UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "General")
FString ObjectName;
UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "General")
int32 ObjectID;
UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Stats")
float Health;
UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Stats")
float MaxHealth;
UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Configuration")
bool bIsActive;
UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "References")
AActor* OwnerActor;
UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Transform")
FVector Location;
UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Transform")
FRotator Rotation;
//... whatever there need to be below is below
};
My version
UCLASS(Blueprintable)
class UObject
{
GENERATED_BODY()
public:
// Basic variables
RANDOM_VARIABLE_PADDING(0,15)
UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "General")
FString ObjectName;
RANDOM_VARIABLE_PADDING(0,15)
UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "General")
int32 ObjectID;
RANDOM_VARIABLE_PADDING(0,15)
UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Stats")
float Health;
RANDOM_VARIABLE_PADDING(0,15)
UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Stats")
float MaxHealth;
RANDOM_VARIABLE_PADDING(0,15)
UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Configuration")
bool bIsActive;
RANDOM_VARIABLE_PADDING(0,15)
UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "References")
AActor* OwnerActor;
RANDOM_VARIABLE_PADDING(0,15)
UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Transform")
FVector Location;
RANDOM_VARIABLE_PADDING(0,15)
UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Transform")
FRotator Rotation;
RANDOM_VARIABLE_PADDING(0,15)
UObject(){
//.. whatever needs to be executed here
MACRO_POPULATE_ALL_HOLLOW_VARIABLES()
}
//... whatever there need to be below is below
};
Waste of time, write your code properly server authoritative and don't care about local instance spoofed values. If someone wants to cheat a local client they will cheat a local client, it's only time
Again, just changing offsets isn't going to neither make reversing difficult (or long) nor does it protect against anything else
In most games, offsets change every update and cheat developers still have automation for this or even just do it manually every update since it's a 5 minute thing, as I said
Like, say your ObjectName moves from [obj+0] to [obj+4] because you added a random int32 before it, there's still going to be code referencing the exact correct offset, so it's not exactly a magic tool
i wanted to stop esp and aimbot users not "server side exploits" xD
FOW is a good approach for that, not random padding offsets (some of which still fall into the boundary of implicit padding, rendering them useless)
For esp, aimbot is trickier for sure but some of the blatant stuff is easy to detect
Your padding here is pretty much cosmetic stuff to be honest
Great morning, realised I had a large 'consider actors' time from a load of procedurally generated ACTORS set as 'always relevant' and instead converted them all into locally spawned instanced static meshes (since that's all they were)... went from about 4ms 'consider actors' time to 1ms
Is transferring ownership of a UObject in a multi-player setting a no-no?
I use FFastArraySerializer to serialize item instances of inventory items being held by the player. Let's say I want to have the player "drop" the item, which means removing the item from the player's inventory and spawning an actor to represent the item in the world. I was thinking of maybe just transferring the UItemInstance* from the player's inventory to the spawning actor. I have never done that before. Normally I would just create a new UObject, copying over what I wanted, but I was just wondering about this potentially new approach.
its just trivial to write a cheat for any game when they rely entirely on anticheat
It's trivial to write cheats for any game in general, the impact is what's eventually down to the developers' hands
Though you never will be able to escape the aimbot/ESP mess for FPS games, etc, since those really are as trivial as reading memory and emulated mouse actions, so an anti-cheat's the only possible solution
Then there are also DMA based cheats which even kernel level anti cheat wont save you
I'm trying to get movement to replicate on a listen server, but the execute on server event never fires
it works on server but doesnt update at all on client
Is it better to override GetMaxSpeed or to update MaxWalkSpeed?
Hello, what might happen if you add the same UObject into two different SubObject lists? Is unreal smart enough to identify that an object was already replicated, or would it try to replicate it twice?
why can it be the subobject of two different things?
I think it crashes
I'm extending my current inventory implementation. Right now when an item is added to the inventory, it's added to the inventory component sub-object list.
However, now that I'm working on backpacks (which are also items) that add extra inventory components on the player when equipped. E.g. there's main inventory component, equipment inventory component (the inventory that makes items inside be considered as "equipped"), and dynamic inventory components that are added/removed when backpacks are equipped/unequipped respectively.
I want players to be able to move backpack from character to character (like looting) without losing items the backpack contains. Currently, when inventory is destroyed (backpack is unequipped) items simply disappear as there's nothing that replicates them (the sub-object list is gone).
What I thought is to let dynamic inventories know that they were created from an item instance (from a backpack). When that dynamic inventory would get/lose an item, it would tell the item instance that created that inventory about that, so that it'd know about all the contained items.
When the backpack would be removed, the backpack item instance would still have that list of items that it previously had, so that I would be able to dispatch that list the next time the backpack is equipped, e.g. the dynamic inventory that's created once the backpack is equipped would receive all of those items.
The reason I thought about referencing one UObject in two separate sub-object lists was related to that part where I tell the backpack item instance that an item was added/removed while the backpack is equipped to allow that back tracking once the backpack is unequipped. When it would notify about an item being added/removed, I thought that I would tell the inventory containing the backpack item (e.g. that equipment inventory component I mentioned at the beginning) about that, and that it would add it in its sub-object list as well.
However, now that I described all of that here, I think that I can do that only once the backpack is removed, so that backpack items would be replicated using dynamic inventory components when backpack is equipped, and by the inventory that stores the backpack once it's unequipped.
situation, I guess lol
Make inventory a UObject, InventoryComponent manages those UObjects, move the UObject from player's inventory component to the backpack actor's inventory component
easy peasy
Backpack is not an actor though
If it's dropped
Or well, you can move the backpack UObject from player A to player B
same logic
Make inventory just an array of structs and move them around as needed? sometimes helpful to separate the data from the actual actor
Well, yes, I can move the backpack UObject, but right now the backpack itself has no clue what it contains. It adds inventory components that store the items. Currently there's no logic to save those items once the backpack is removed
They're already UObjects, can't switch to structs
(Also I don't really like structs for inventories)
Just curious as to why?
I really like Lyra way of handling items. I like adding fragments to item instances to seamlessly extend item functionality. I'm either not aware of a way to do that using structs, or it's impossible to do that
I'm not really familiar with instanced structs though, it might be possible to do that using them. I'm using Lyra inventory since 5.1 though, so it wasn't really an option back then
Lyra is known to be massively overcomplicated though there is often a simpler and more elegant solution
But whatever works works!
You can use InstancedStructs as "fragments"
Done that in the past with an inventory system, worked great
They're a little on the heavy side but you can microoptimize bandwidth later heh
I agree that Lyra is often over-engineered, but I personally really like their way of handling inventory and equipment
Structs only replicate changed properties AFAIK so they aren't as heavy as one might think when first using them
Not instanced structs
Hmm, Lyra's fragments don't change on runtime though. They use them for item definitions, not for instances
They can't do delta updates
oh ok
I'd just use data assets for definitions
¯_(ツ)_/¯
That's what they kinda do. They use UObjects for a reason that I'm not really aware, but AFAIK they could've used PDAs the same way
my current inveneotry system uses UObjects but that was also because it was made before instanced structs were a thing
if i started from scratch today i'd probably use instanced structs
because structs have a fixed size and generally dont support polymorphism in unreal
instanced structs get around that by being dynamically allocated
PDA is not a struct though
never said it was
but PDAs are immutable
i guess im a little confused by what your issue is with your current setup?
Hmm, I don't get what you're saying. I was saying that they're using UObjects instead of PDAs, but I'm not sure on why. I haven't mentioned structs there
I think I know the solution by describing my problem in by first message after the question 
you basically have UObject for item instances, UObject for inventories, and a UObject for backpacks which themselves are items right?
UObject ItemInstance, UObject ItemDefinition, UActorComponent InventoryComponent, Backpack is an ItemInstance
I use UObject for inventories, ActorComponent for an InventoryManager that replicates those UObjects, and structs for item instances
InstancedStruct for custom data per item "class"
ok yeah thats roughly how i've handled it
its annoying having a uobject be a subobject of another subobject
UObject for inventory, huh? What's the difference between inventory manager and inventory?
probably inventory manager component handles transactions whereas the inventory just holds items
Interesting, when/how would you create/destroy inventories though?
Inventory holds item instances, InventoryManager just replicates the inventories as subobjects
Certain item types like backpacks have a list of inventory classes to spawn when they're created
changing ownership is the part I'm not sure about... I actually do not know if you can just pass over a subobject easily
if all else fails just destroying the instnace and making a new one imo would not be too bad
With replication? I know rename works on the local machine
It'll be recreated on clients, and tbf anything you do will cause it to be re-created, outside of having inventories be actors
I assumed you would need to do an extra cleanup of the subobject list
but the server will at least not have to re-create anything
that's fine
worst case is you have a dupe glitch I guess
huh, I don't do that, and it still works
static void SwapOwnership(FMESS_InventoryEntry& EntryA, FMESS_InventoryEntry& EntryB, UActorComponent* OwnerA, UActorComponent* OwnerB)
{
if (OwnerA == OwnerB)
{
// Avoid changing ownership between the same owner
return;
}
if (IsValid(EntryA.Instance))
{
OwnerA->RemoveReplicatedSubObject(EntryA.Instance);
OwnerB->AddReplicatedSubObject(EntryA.Instance);
}
if (IsValid(EntryB.Instance))
{
OwnerA->AddReplicatedSubObject(EntryB.Instance);
OwnerB->RemoveReplicatedSubObject(EntryB.Instance);
}
}
not really, server would just refuse the RPC
which is admittedly pretty bad
I don't think there's any "better" solution, every other solution is a sidegrade and kinda depends on what you wanna do
What's the outer of the item
because if you don't change the outer and the owning object is destroyed, your object goes with it
yeah I'm curious if it's okay to have the outer not be changed... that seems fishy
itll destroy
easily changed of course
You really really have to unless you wanna start debugging why your inventory suddenly explodes randomly
(been there, done that, remember to change the outer lol)
(with rename)
yeah it's easy
No risk of name collision, right?
just remember REN_ForceNoResetLoaders unless hitches are funny to you
I think it handles that internally depending on flags
i yearn for scenegraph
I got fed up and made my own lol
I don't have good editor support though
bold
I actually send them as uobjects over the network
which is actually not as hard as I thought it would be
mind you it involves a lot of Iris knowledge with a custom iris net object factory
(this is not a subobject, this is 100% raw root object that isn't an actor)
The inventory owner. I have some pickups in the game, and the item instances are created once the pickup is created. When player picks them up, the pickup is destroyed. I have never had any problems with it, even though it sounds like I should since the item should have no outer
I would rename to change the outer then ¯_(ツ)_/¯
The weird thing is that I'm not having any problems. I'll check what's the outer after GC
It might be you just happen to not ever destroy the other one yet
or its kept alive through other means and not marked pending kill?
Hm, so the outer is still the pickup, even though it's destroyed
well... that's probably no bueno
Surprised it works
yeah fix this immediately lol... this is waiting to explode
How do you rename exactly? I have to use UObject::Rename(), yes, but what arguments would I use?
For things you don't want to change, pass in nullptr
ObjectToChange->Rename(nullptr, MyNewOuter, REN_ForceNoResetLoaders);
the nullptr is to make it make its own name
I don't know which flags exactly are needed
Those look reasonable!
I do not know if REN_DoNotDirty dirties in what sense
What do you mean by "things you don't want to change"? Change in what way?
change the name of
Like the name.
you want to rename in the sense you are JUST changing the outer
not renaming and giving a new object name
Got it
Rename isn't really rename. It's "Move".
You can choose to move to a different container and/or to rename the thing itself.
What container are you referring to?
The outer.
Oh, got it
oh well there ya go
TIL
also if you have no idea wtf to make the outer
the general flow I think is to use the transient package?
I think for replication stuff just keep it simple and use the actual owning object though
Yeah, that's what I do
I really oughta do my inventory system idea one day.
What if instead of all those shenanigans you just had some global flat list of item instance data, and one property of an item can be the items it contains (and optionally it's containing parent)
Actors in the world can just reflect that item instance data, or the items can all be "virtual" and on the back end without ever meeting an actor
Good to know heh
struct ItemInstance
all the data
TArray<ItemInstance> EveryItemInTheWorld
TMap<int32, int32> IndexToParentIndex
TMultiMap<int32, int32> IndexToChildIndices
Couldn't you do some crazy stuff with a setup like this?
No reason you couldn't do it with objects assuming they exist on either end, what you need is the forward and backwards mapping of containing/contained in
Sounds like more of a pain in the ass than just having each "owner" contain its items
I personally don't really get the idea besides it being global. I don't see how you would know whose item it is, and how you would do any sorts of events in regards to an owner, e.g. gaining or losing an item
just update the mappings and you're done
me giving you an item is your inventory (which is an item) gaining it as a child and mine losing it.
an item without an outer is in the world, it would be mapped to by some actor.
A chest actor holds the id of the chest container/item id, and from there you can query for its children as deep as you want to go
A chest containing a chest containing a chest containing a gem would look like:
ChestActor:
InventoryID = 0
InventorySystem:
ItemsInWorld = Chest, Chest, Chest, Gem
IndexToParent = 3,2 2,1 1,0
IndexToChildren = 0,1 1,2 2,3
placing an item in the world is spawning an actor that holds its id, and removing from world (putting in a container) is the opposite. The actors in the world are just a view of the backend
and the performance would be incredible, you could probably do Factorio like this
Hey gang, I'm relatively new to unreal and running into a seemingly pretty basic issue but I cant figure it out for the life of me. Does anyone have a sec to hop on a call and take a quick look?
people usually don't call
I can explain the issue via text but might be more efficient via voice / screen share
When a round is over and I am trying to reset the map I am using ServerTravel MapWorld1 . When players login I start them as a spectator pawn and wait until atleast 2 are in before starting the game where I start a timer of 4 seconds then spawn all players into their expected blueprints and setup their HUD props and what not. The issue I'm having is when I test this with another person (not via the in engine multiplayer test flow which does not show this issue) the server player will aways load in and start as a spectator pawn but the clients will go to a black screen until they get spawned in as their expected blueprint but their props will not be set properly. IE their screen still says "spectating" but they have been spawned into the world as a character
is the 4 second timer intended to be after all players connect?
yeah but the issue is im not sure how many players I should expect to connect right since more could join? If they join after the round start then they would stay as spectators
anyone have experience making this? Ive been trying with overriding PhysWalking and adding an additive velocity but my velocity keeps oscilating
okay guys im back to working on my multiplayer prop hunt game. i want to remake my score system and need an easy to implement system for it. the way my game works is - once there are at least 3 players in the game, a 1 min timer starts before the game starts to allow more people to join. after that a 1 min timer starts for the prop to hide from the hunters, during which the hunter input is disabled. once the timer is over, another timer starts for the hunters to hunt the prop within that time. whenever any hunter kills the prop or the prop survives, the victory/loss widget pops up and a 10s timer until the next round starts and this cycle continues. i want the score system to work in such a manner that score is given to the hunter who kills the prop or to the prop if it manages to survive
i have already shared a video on the gameplay and the blueprints here
probably going to try making one based off moving deterministic meshes
Then get started on it and let us know when you hit a roadblock or a bug.
Or if you are stuck getting started, ask questions about smaller parts of the scoring system that you struggle with.
Low effort but easy results is having it run off an in-sync net clock (one that is a better than the default one in player state, I have a modified version of vori's one, it's pretty good for the most part), then it'll implicitly be in sync for the most part
https://vorixo.github.io/devtricks/non-destructive-synced-net-clock/
my doors already use something like that. the tricky part was figuring out what meshes to move
going to do something like this (gpt summarized)
🧱 Actor: ATravelator
RootComponent placed at Start - L
Two platform meshes of size (B + L)
↪ Pivot at X = B for smooth wraparound
On server BeginPlay set the replicated net-synced timestamp
🧮 Per Tick Movement (Server & Client)
float d = fmod((CurrentTime - StartTime) * Speed + InitialOffset, TravelatorLength);
FVector Pos = TravelatorDirection * d;
Platform->SetRelativeLocation(BaseOffset + Pos);
InitialOffset = 0 for A, TravelatorLength / 2 for B
i think gpt messed up the formula lol
gpt summarized
lost all interest lol
Please don't use AI, it'll severely hurt your ability to improve
And it'll feed you complete garbage
it's good for review/summary imo
Your message proves otherwise hah
I can't stand the emojis it tends to give when it explains or summarizes something, like I am a toddler who needs emojis to make it more engaging for me to read
I need to start prefixing my replies with a small gameplay clip of subway surfers
After reading the pinned material, i have understood that using a player state would be the way to go since i need to track the score of each individual player. but the issue that i'm currently facing is i dont know how to get started with it. i've come a long way with my project but this score system has been bothering me for around a week now
i have almost everything set up except for score, leaderboard and round system
Use game state as well
PlayerState can/should be used to store Player-specific data, that is correct.
Leaderboard is probably not so relevant at the start, as UI is only meant to show data and a leaderboard is usually not even featuring any controls to modify data. So you can tackle that at the end.
The score system is probably the bigger blockage?
@nova wasp @verbal ice @modest crater Smaller reminder: Please don't turn other channels into #programmer-hangout :P
Pointing out the flaw in AI when using it to learn and similar is fine, but the gifs are basically spam at that point. I removed those now.
Replication - Passing variables issue
Those are in theory relatively easy to make, even in Multiplayer. You don't even need to override a lot of stuff.
Whatever those things are called, you'd simply put a box collision along it.
The character will walk into the box collision on Server and AutoProxy during the same simulation frame, so you can freely apply some acceleration to the character's velocity.
You can probably overengineer this to be more generic, but in theory all you need to do is keep track of the overlapped actors in an Array on the character or the CMC (the actor can add itself to that on BeginOverlap and remove itself on EndOverlap to keep the character code cleaner) and then in PhysWalking or in CalcVelocity, access those and grab some Acceleration property that you set up on them, e.g., some float. Can multiply that float with the direction that the thing should move the character. Then multiply DeltaSeconds into it and add it to the Velocity.
If you make it more generic, maybe with a base class that you give some more generic name, you can also reuse this for like water that drags the character along. Or wind that pushes the character.
Yeah I feel stuck with the score system. It's not giving the score to the correct player and sometimes even gives the score to multiple players, maybe even all players at once
show code
I want to start fresh as it's already such a mess
The problem is, that barely anyone here will spend time on explaining you this in a way that it's almost a tutorial. If you don't have more specific questions about parts of it, then you'll only get "show code" answers.
If you show code we can at the very least give you pointers on doing it better
How you doing?
Trying to add Local Multiplayer (Split-Screen to my game).
All of the game logic and inputs is configured to work with multiple players.
Currently I just do CreateLocalPlayer on BeginPlay, and it works, the second player is added, and can be controlled with a 2nd controller.
Problem is, I don't want this to be on BeginPlay.
I want it, so that when the A key (Gamepad Face Down Button) is pressed on a 2nd Controller, only then the 2nd player is added.
No idea how to do this.
I can do things when the A key on the 1st controller is pressed, but that's not how I want this to be done. Can't get the A key input event to fire for a 2nd controller, when there is no second player.
You already explained that you want to grant score to Hunters that kill Props, and to Props that survive the full duration.
Let's assuming that score is the same for both cases for now, so 1 point for a kill and 1 point for surviving (you can adjust that later).
That means you have two different problems to solve:
- Grant score on kill.
- Grant score when timer is over.
Since you are already handling the timer stuff apparently, 2. should be relatively straight forward.
When the timer ends, grab all players that are part of the Prop team (assuming you have a properly managed team system) and add 1 to a score property that you can place on the PlayerState.
And the killing part is in theory also easy. Assuming you have the logic in place that Hunters can kill Props, whenever a Prop is killed, grab the killer and add 1 to the score property on the PlayerState.
And that's kinda it. You'll have to start coding it from this point on and report back if you run into specific problems.
Tried spawning an additional idle PlayerController with no pawn. The Gamepad Input event inside that player controller is still not firing for the second spawned (Additional) player controller.
So, I faced that same problem couple years ago and I can't tell you if there is a smarter way (honestly, there probably is with C++, as I assume one can get the input from the Gamepads even without a PlayerController somehow), but I solved it like this back in the day:
- Add the additional Player(Controller)s right from the start.
- Add a boolean to the PlayerController
bWantsToPlayand set that to false by default. - Whenever the A button is pressed, change the
bWantsToPlayboolean to true. - Later when you want to start playing, before switching the level, loop over the PlayerControllers (backwards fwiw) and remove every Player(Controller) that is either not the PrimaryPlayer (don't want to nuke the main player) or that has the
bWantsToPlayboolean false.
My first intuition as well, but doesn't seem to work for me.
I spawn an actor from class (on begin play), the class being the Player Controller.
The input events inside this spawned player controller don't fire for me.
You shouldn't manually spawn the PlayerController.
You should still use the CreatePlayer node.
But if I do that the screen splits. I want it to be Split Screen when there are 2 (or more) players, but when 1 player it shouldn't be split screen. A third person game.
Splitscreen can be toggled though?
How? Isn't it only in project settings? For this I would need to toggle it runtime. Is there a node?
Give me a minute.
/**
* Enables split screen
* @param bDisable Whether the viewport should split screen between local players or not
*/
UFUNCTION(BlueprintCallable, Category = "Viewport", meta = (WorldContext = "WorldContextObject"))
static ENGINE_API void SetForceDisableSplitscreen(const UObject* WorldContextObject, bool bDisable);
/**
* Returns the split screen state
* @return Whether the game viewport is split screen or not
*/
UFUNCTION(BlueprintPure, Category = "Viewport", meta = (WorldContext = "WorldContextObject"))
static ENGINE_API bool IsSplitscreenForceDisabled(const UObject* WorldContextObject);
Comment above it is a bit sh*t, but yeah
Those are static. Should be able to just call them from anywhere.
Thanks! Got the disable/enable split screen part working, but the main problem still stands.
If I set to true SpawnPlayerController in the screenshot, then a second player is spawned, with the pawn and everything. Don't want there to be a pawn.
If I set it to false, the pawn doesn't spawn, but the Input event inside the PlayerController is still not firing.
Can't I just have an Empty (non-pawn) player controller, that detects inputs, and spawn the pawn later when I want (When the A key is pressed)?
I can think of dirty solutions like teleporting additional player pawns somewhere until their key is pressed, but that is too dirty.
You'll need to tick that boolean. That node is kinda shit and had for a very long time even the boolean mislabeled.
There is something called a ULocalPlayer, that you don't really have access to in Blueprints. That is being created with that node.
But if you don't tick the PlayerController checkbox, you'll end up with a ULocalPlayer that has no PlayerController, and in Blueprints you have no way to get the PlayerController later created and attached.
In C++ you can probably use the ULocalPlayer for Input too, but well.
I already explained how you can have the PlayerController without the Pawn spawning.
The Pawn spawning is caused by your GameMode.
Hm, or did I not send that message? Strange.
Apparently not. I'm sure I typed it. Well, idk how your game is structured, but in theory you need to ensure that the GameMode, which is used when doing this "Press A" stuff doesn't spawn a Pawn for Controllers that don't want to play.
Do you want them to instantly get a Pawn spawned when they press the A button, or should that only happen "later"?
Yes, as soon as A pressed, a new player is added with the pawn and everything.
So I set the default pawn to None in gamemode, but still in that gamemode begin play I spawn my character pawn, and possess it with Controller 0.
Also on begin play create local player, disable split screen, then on button press, enable split screen, spawn a second pawn, possess with controller 1?
And how do I spawn a character pawn cleanly? Still just SpawnActorFromClass, with the class being the pawn? And the owner should be PlayerController I assume, Instigator None?
All right got all this working, with the Steps I mentioned.
Not sure if SpawnActorFromClass is the cleanest way to spawn a pawn, because with this I also need to get AllActorsOfClass PlayerSpawn and choose the one I need to get a Spawn Transform. But most important is it works now the way I wanted.
Thanks @thin stratus
You could override your GameModes "Get Pawn for Player", or whatever it is a called, function and check the boolean on the PlayerController there. Then return null if the boolean is false.
When you later press A, you can call "RestartPlayer" on the PlayerController after setting the boolean to true, which will run through the same code-path again, but this time with the boolean being true.
You shouldn't need the GameInstance for this. Also if a player renames themselve it would not be mapped correct anymore.
For the CopyProperties you need call SetPlayerScore on the casted "AsPSPropHunt" pin, as that's the new PlayerState.
And the bottom most RPC is not a good idea, both the Timer and the Killing should happen on the Server. You shouldn't have an RPC that modifies PlayerState.
Would it cause issues if I just define the AddScore event inside the player state and call it only on the GameMode, because it runs only on the server?
You don't need it to be a ServerRPC then.
I've removed the game instance and the add works correctly but it gets reset back to zero immediately after so when the server travel gets executed again, the score goes back to zero. I wonder if it has something to do with how I've set the OnRep
Make sure your CopyProperties function in the PlayerState is set up correctly.
am i doing this correctly? i have set up debug print strings which does show the increased score but not on the player HUD widget
That should be correct, yes.
Then it's a problem with the UI.
Calling UpdateScoreDisplay from within the OnRep of the PlayerState's PlayerScore looks a bit strange.
What are you updating there exactly?
I'm updating the score UI in the OnRep, the debug print shows the added score but then it sets back to zero somehow
But you have multiple PlayerStates
Setting the ScoreText will only display one value and only the last one that called the OnRep.
Should they only see their own Score?
Yeah that's what I'm trying to achieve. I also want to work on a leaderboard system after this too display after the end of the last round (i also need to work on the round system)
If you only want the local store to show, then you need to filter the OnRep a bit.
Since you are in the PlayerState, the "Owner" of the PlayerState will be the PlayerController.
So instead of doing "GetPlayerController0", you can do:
GetOwner -> IsValid -> CastToYourPlayerController -> IsLocalPlayerController -> UpdateUI
GetOwner will be invalid on SimProxy PlayerStates and IsLocalPlayerController ensures that the Server (if ListenServer) doesn't trigger this for other players, as it has access to all PlayerControllers and GetOwner won't be invalid for it.
is this what you meant? well it still didnt seen to change anything
Yeah
Where are you all setting the Score variable?
Server seems to be setting the Variable to 0 somewhere.
I have an OnDamage event inside my BP_PropCharacter, after the death logic of the prop and also after the EndTheGame event inside GameMode for the prop survival scoring
You might want to print the paths that can set it to 0. It shouldn't be magically set to 0
Oh wait, you are not Seamless Traveling.
CopyProperties requires seamless travel.
You have to enable that in the GameMode.
And if you want to try that in PIE, you need to set that console variable to true, cause PIE support for Seamless Travel is experimental.
It still gives the same results
Then not sure right now. You can try checking if it's a race condition of sorts, maybe the UI isn't valid yet when the OnRep calls. In your UI, in EventConstruct, you can get the OwningPlayer, from that the PlayerState. Check if the PlayerState is valid and if so, get the PlayerScore and update the text.
It's okay, I can't figure it out either. Probably best to just leave it like that. I tried the EventConstruct as well and it still doesn't work
Seems like my ue5 is not in a fighting mood
Hey everyone! I'm having a problem with advanced sessions in Unreal 5.5
I can perfectly host and join a session, and the server is able to control their player character. But every client that joins has no control whatsoever. When the server leaves the game the client gains full control. Does anyone know a solution to this?
That most likely has nothing to do with the sessions
Sounds more like Enhanced Input not being set up properly or the InputMode is still UI or something along those lines.
Hi, when it comes to high ping and packet loss I would need to implement a system that forces the player to disconnect if they're consistently hitting high pings/packet loss, I can track the players ping through the player state but is it possible to detect a players level of packet loss? I assume it won't be enough to just detect high ping since that doesn't account for low ping high packet loss situations and vice versa
sorry, i didn't read all, but I can quess that you dont have valid ui update on client. yes, its messed up after map change, either server calls to early and object isn't valid when binding or clients dont have it replicated yet. Best thing I found so far was to set timer on cast fail or variable validation failt to retry getting proper reference. or just simple delay until next tick
Yeah my whole project has been a mess, and it wasn't a surprise that this failed too just like a lot of other features that I tried implementing before
You can use APlayerController::NetConnection to get all the network-related data, including packet loss (UNetConnection::GetInLossPercentage() and UNetConnection::GetOutLossPercentage())
Things almost never work first time in game dev.
I've got everything wrong this past one week, it's frustrating
I assume none of that is exposed to bp's lol
nope. multiplayer dev with BPs is limited
I'm sure theres a plugin you can buy on fab that exposes it all though, or do it yourself
also I remember someone was saying something about a plugin that makes it so that debugging in rider shows whether the code is being run on a server or client? Does anyone know what it is?
I was gonna download it but didn't save it for later
I need some multiplayer architectural design tips. I want to create a 5-player coop space game where each player can be in a different star system (imagine smth like stellaris) or the players can be landed on a planet a 3D city.
Whenever a player changes system, it checks if it's one where another player exist and it jumps there, otherwise, generate a new star system replacing the current one (with a transition in between), the system's data is taken from the save file, system size, planets and their orbits and the objects inside.
I have this diagram with 5 star systems and 5 planets in a single world.
Is this something feasible in Unreal? Am I way over my head? I'm not looking to create ultra realistic levels like Star Citizen with tons of detail, it's all sort of simple with few things going on besides NPC ships flying around in each system.
its not a matter of if, its a matter of skill, time, and money
Sounds good, all i wanted to know is "unreal can't do that because of x"
Can totally do it. It kinda sounds like you want a different server spun up for each area, though. That'd make it a lot simpler. That or you're managing multiple levels within a single world.
well levels are proceduraly generated, not something static
What you could do is have each level be run locally by the "owning" co-op player. So the first one there becomes the server for that world. When you zone into another player's area, you join them or create a new server based on teh shared procedural data.
That'd be a bit more complicated, though.
Hey everyone! I’m working on a co-op game without dedicated servers, and I’m trying to figure out the best place to store a player’s private long-term stash (it's saved). I want each player to have their own stash that the host can’t access when they join a multiplayer game, to prevent cheaters from accessing other players' stash. I don't mind cheaters as long as it's about their own stash.
So what's the best approach for this? Should I use USaveGame or is there a better way?
I don't have any servers though, it's like other coop games like deep rock galactic etc
There's always a server if you have co-op.
Unless it's couch co-op.
If you have internet co-op without a dedicated server, then there's a player hosting a listen server.
Does anyone know how to disable UE's default net game driver? To disable its internal netcode stuff?
Doesn't seem like I can override
UWorld::Listen
And this is where it's called from UnrealEngine.cpp:
// Listen for clients.
if (Pending == NULL && (!GIsClient || URL.HasOption(TEXT("Listen"))))
{
if (!WorldContext.World()->Listen(URL))
{
UE_LOG(LogNet, Error, TEXT("LoadMap: failed to Listen(%s)"), *URL.ToString());
}
}
Seems like I'm stuck with it, or change the engine source code :/
Yes exactly that. By servers I mean dedicated / data servers
You'll get wrong info if your terminology is wrong 😛
Fuck ye, I found a hack, just pass a nonsense game net driver definition:
[/Script/Engine.GameEngine]
+NetDriverDefinitions=(DefName="GameNetDriver",DriverClassName="fodase",DriverClassNameFallback="fodase")
Causes:
[2025.07.13-19.01.51:028][ 0]LogNet: Error: UEngine::BroadcastNetworkFailure: FailureType = NetDriverCreateFailure, ErrorString = , Driver = NONE
[2025.07.13-19.01.51:029][ 0]LogNet: NetworkFailure: NetDriverCreateFailure, Error: ''
[2025.07.13-19.01.51:029][ 0]LogNet: Error: LoadMap: failed to Listen(/Game/Gabriel/LV_Gabriel?Name=Player)
I guess by having the stash in USaveGame, that would do it?
Yup. So you don't want the server to even have a read-only version of the player's stash?
@blazing bear Does the stash persist across matches?
To try to validate things?
You need a web server then
No, there is no need for the server to see it at all
Or maybe save on Steam, but it's sub-optimal
Do you want the stash to be accessible from 2 computers if the same player logs in from both?
Anything that you need to be saved across sessions, and I imagine you don't want it to be deleted when the user re-installs, will need some form of persistence
yo pt?
hell ye dude
Yes, well the stash will be saved both locally and through steam's own cloud
brazil more specifically
Yeah that's a tough one, that's the problem with P2P games
A host will inevitably be able to do a lot of stuff
Using P2P is explicitly making the compromise of not caring about cheating.
Ubisoft have tried with little success, unless you have a secret weapon lying around, you probably also won't be able to make it work
But I think having the stash on USaveGame will be enough, no?
Depends how your code is written
Just assume the host can manipulate "server" code, if "server" code can mess up the stash, so can the cheater
Obviously it would allow players to modify their own save, so cheating, but I'm fine with that
There you go, just keep stash related code client-only
Yeah that's right, I just need to have it completely local
How does this happen in the first place? They probably exposed that info to the network I guess
Pretty sure those are shared by players when they finish a run
Cheater probably just modified the amount and it gave it to everyone
Hello guys, Anybody else faced that {,,UnrealEditor-Engine.dll}::GPlayInEditorContextString is not working in 5.6 UE?
error: no member named 'GPlayInEditorContextString' in the global namespace
for me my module changed names to MyGameEditor-Engine.dll (replace MyGame with your project name)
Module 'MyGameEditor-engine.dll' not found
Do I need to set "mygame" as project name?
I mean replace Mygame with your project name
{,,BattlementEditor-Engine.dll}::GPlayInEditorContextString
in my case the project is called Battlement
ddin't worked for me 😦 shish... I will try to rebuild with debugGame editor configuration
ah yeah this will depend on having that module loaded
the module list should have it at least
still not working... insane those update with UE
I would say check the module list in your IDE
I need to have Editor module to be added as dependency?
no, I mean the loaded symbols while debugging
not sure if the dependencies affect loaded modules or not in debugging
should be all good. I can see the debug symbolls, additional removed compiler optimization.... I guess I have to just wait till somebody will post resolution somewhere 😦 thank you for help anyway!
I'm not sure what it is, but I implemented a target locking component, that will make the character face the target pawn.
This appears to work until I play a Montage, then it appears it is fighting the networking rotation or so.
I disabled UseControllerRotationYaw and OrientRotationToMovement and then in OnTick I'm setting the ActorRotation.
What I also noticed, when I have no target to lock onto, and play a montage, the characters rotation snaps back to it's origin.
When playing in Standalone, it appears to not have that issue.
Anybody any idea what the issue could be?
When dealing with net corrections, is the whole point to eliminate the jerkiness and teleportation of characters? Like lets say that every movement was net corrected but it looked normal, would that be acceptable?
yeah generally speaking the implication is moving with a jerky motion backwards is bad
is a root motion montage?
Ok cause I am setting up my movement and I am adding 250ms lag and trying to cause net corrections. I can only get it to happen if I am sprinting forward and then immediately stop sprinting and hit "S" to try to go backwards. I get about 10 corrections but it looks normal
and yeah I agree 100% that a correction that results in movement that doesn't feel like you are rubberbanding is the ideal
Appreciate your help.
yes
I'm not sure how root motion works with orientation but it should be possible to change that in the asset or the character
What I don't understand, if Use Controller Rotation Yaw is set to true, everything works fine.
But if I disabled it and manually do SetActorRotation, as soon as I play the montage it snaps back.
So what I've figured out so far, that the issue appears to be, that I'm playing the Montage from a Gameplay Ability, which also plays it on the server, but the rotation of the Character is not replicated to the server.
I don't really want to do it with a RPC, since I'm updating the rotation every tick.
Is there any way, to maybe update the rotation via the character movement, as if it was updated by the yaw movement of the mouse?
FYI: you was right, debug symbols were missing! have no idea how I was debugging all this time 
I'm a little confused what I'm doing wrong. I have logic on the Owning Client and setting a variable and it shows the variable is valid from the Client's Side. Then I send that variable through Run on Server. I check if the variable is valid on the server and it shows it is not
show what you are actually doing
it might help to make sure the rpc is even received
also this description does not include what you actually sent in the rpc
it's pretty hard for me to send a screen since it goes through the player blueprint, interfaces and then an item blueprint. I can try to explain it
I don't really need to see much except for the shape of the rpc and which object it is created in
if you are sending a reference variable you might need to make sure it's something you can send replicated
for example a locally created object will not work, but something like a static mesh asset (a loaded object) or a replicated object from the server would
What is a selected mag?
it is a blueprint that the client spawned on input
the server can't see a reference the client created local only
but you could describe what it means to be that magazine (for example, sending the type of item it is or some ID?) and reproduce it on the other side
set isn't the issue here
the issue is sending it as an rpc from client to server
the server has no concept of this object
so it arrives as empty
what is the actual information this magazine describes?
you COULD send the class of magazine becuse that is an asset both sides have
what I'm doing is the player holds a few magazines in front of them and they can cycle the magazines to reload them at an ammo box. I just wanted to have only the selected magazine on the server
if you created the magazines on the server originally they could exist as a networked object I guess
I don't know what "player holds a few magazines in front of them and they can cycle" means
on the logic of cycling through the magazines, I change the selected mag and wanted to send that to the server, but seems I can't do it that way
well no because you are sending an object only on the client
what is unique about each magazine?
If the server knows about the set of magazines you can choose from
you could index into that
or send the class that describes them etc
if this is that each magazine has stored X rounds left inside of it you might need to actually represent that information in a replicated way from the server
this is what I mean. This is the host running this so it works. Just not on the client
the information must be on the server to understand what it receives from the client
yeah of course it works when you are the authority
netcode stuff is hard to get into... with this I think it might be easier to just start with the magazines coming from the server
where they are a replicated object to begin with and this just represents them visually
if they were a replicated object in the first place they could be an rpc variable and show up on the server
assuming the server hasn't destroyed them of course
having the visuals for selecting magazines be client side is a good idea, but the information should be authoratative
you COULD be evil and just allow client side authority and they just send the information about their magazines as a dumb struct /class/asset ref if it's a co-op game
with not much concern of cheating
how would that work to allow client side authority?
So instead of sending the actor that the client spawned. I can just send information from that magazine to the server for things like bullets loaded and etc
I'll try that then
yeah, if you want
you could send the actor class for example or the static mesh etc
along with N bullets etc
thanks for the info. I'll try it out. Network Replication has been a pain lol
also depends on what the server needs to know (and other clients)
for example if other clients should see you considering each magazine or whatever
or if its just kind of local only
Hi guys, I'm currently creating a target locking system, that requires me to alter the characters rotation, to face the target.
The issue is, that I also need to pass that information to the server, but doing it via a RPC feels like it would put a strain on the network, additionally I'm not sure if this might fight with the movement predictions or not.
Is there a way, I could maybe replicate the rotation of the player, vie the character movement component or should i just use a RPC or do I run the target locking component on both server and client? What would be the best approach to that?
modify the control rotation client-side and you won't need to do anything
assuming this is default movement settings
Sorry maybe I should have added that part, but I want only the character to face the target, the camera should still be movable, by setting the controller rotation, this also locks the input.
You think there is a way for that too?
Depends how your setup works I guess. Commonly the character follows "control rotation", and you can just set that client-side and it naturally reaches the server via character movement component
If that's not how it works, you'll probably need to expand CMC to do what you need
The difficulty will be in how to handle the target not being in the same location, snce now your predicted movement is dependant on another actor which is not predicted.
Server may just have to accept the clients' rotation
I was just thinking, it should be the same as if i move the mouse, which is also dedicated by the client.
But i just want the character to face the target and the player still be able to look to the left and right
Also I'm not really sure, how to set the rotation with the CMC, is it also via FSavedMove_Character.
But maybe there is another way
have the camera NOT rely on control rotation
Control rotation is a rotation per controller that already has some networking backend for you, and various things can opt-in to using it
you can have control rotation drive the rotation of the character, and the camera can just be driven however you want
Do you think this would be the clean and right way?
I also thought that this might be nice, since I can leverage the things in place.
update on this: I ended up not doing this in CMC as a "wind push" sort of mechanic. There was a bug I couldn't fix but more importantly if the player gets "pushed", their velocity is non-zero. My animBP starts thinking the player is walking when they shouldn't be playing the walking animation. I could have fixed this by adding a flag to the animBP but I decided to go with the other approach
the approach i ended up using was using real moving meshes with deterministic movement (replicate a start time that is server-client synced). When a mesh reaches the end of the travelator, it teleports to the start. This approach also has it's flaws though:
- In real life, there is a decent amount of platforms on these machines. Moving 50+ platforms on each tick on the server is terrible for perf. I fixed this by only using 2 platforms for real collision. But the issue is that we must put the first platform at (-L,0) and the second platform at (0,0). So the first platform is sticking out. Not ideal but if it's underground and youre carving a hole for the travelator and covering X=-L to X=0, it's workable. If anyone has any input on a better way I would greatly appreciate 🙏
- When the mesh teleports and the player is stepping on it, the player also teleports. Im going to fix this by just covering up the section where the mesh teleports so the player cant be on the mesh when it teleports
heres the code if youre curious: https://pastebin.com/mw65Fa3m
You can absolutely do that in CMC
Override CalcVelocity not PhysWalking
Because movement is already predicted you don't need to predict when you are on/off it
You might get better de-sync results if you predict "bIsOnTravelator" or something but shouldn't need to
You can probably just modify acceleration with a TGuardValue before calling Super::CalcVelocity to get the behaviour you want, at least in a very basic form
thanks, I’ll try that since I plan to also have wind streams in my game. For travelators im gonna stick with real platforms since it makes more sense physics wise (and makes anim BP happy)
Hello. I'm trying to send an RPC from the client->server as early as possible after the client player/pawn is logged in and created but I'm having troubles with this RPC never making it to the server (and silently failing). What could cause this?
Using a listen server setup. My player pawn is automatically created using the "default pawn class" game mode override (so I am not spawning/controlling it manually). OnPostLogin the server is sending a RPC to the client player controller signaling "this client is all set up and net ready to send RPCs back to me". This works fine and this value gets replicated properly.
Then when the player pawn is created, in begin play (on the client, if they are locally controlling this pawn) I check if it has "isConfirmedReady" set from the server yet, and if so I fire off a server RPC from this client pawn. If it is not confirmed ready I wait 1s and try again, looping until it succeeds. This RPC is to set some initial data from the client (like the colour they chose for their player).
The problem I'm having is while the client has successfully received the "isConfirmedReady" RPC from the server (showing that RPCs are working fine from Server->Client), when the client tries to send the first RPC from client->server, this RPC is just never received by the server. No logs showing "no valid connection" or anything wrong. Just nothing. This only appears to happen if the client joins the server game very quickly after the server has started, so it's like something hasn't actually "settled" behind the scenes regarding net ready. Anyone have any suggestions? Banging my head against my desk for a few days trying to track down exactly what is going on, and where the proper entrypoint is for when it's safe to actually send an RPC.
I noticed I'm trying to send the RPC from client->server from the pawn class. On the Event call bp node it does say "Replicated To Server (if owning client)", so I thought maybe this is failing here because the pawn isn't owned by the client (or ownership just hasn't been replicated yet). But logging shows that the owner is the local controller... so it should work? (and it does except in this one edge case ... where the client joins the game too quickly?)
Marking the RPC's as reliable seems to improve things (still needs more rigorous testing..). Wonder if during startup the network is just so saturated, and those first RPC's are just getting dropped because they were not marked reliable? Hmmm...
the player is the owner of the pawn, right?
Yes, they should be. I'm not setting ownership manually , as I thought the default "spawn pawn for joined players" does that. Logging shows that the pawn is owned by the local controller yes. I also tried just routing this RPC through the player controller directly (which must have a connection to the server right?) and that RPC has the same issue. Says it's trying to be called, but it just never received by the server. And no errors or anything in the logs
Does the engine have tools to reset a level to how it was at the start, or do I have to implement that myself/seamless travel to the current level again
Look into AGameModeBase::ResetLevel
Sweet I felt like I knew something existed
Be aware though, its not like it handles much for you.
You need to implement Reset on all Actors you care to have restored to some "default" state.
I just reload the map personally.
Yeah, ive only really found ResetLevel useful in context with traditional round based modes like Search and Destroy.
should seamless travel be calling beginplay on my player controller again after the transition? I can see that after the properties are copied over the regular World->BeginPlay is called which leads to the game settings which does the regular iterate all actors and call beginplay on, I don't see any thing that would suggest travelled controllers are skipped but I thought I was informed that anything in a seamless travel does not have beginplay called again
Your assumption is incorrect. All Actors have BeginPlay called, regardless of travel type.
Okay thanks, that is not what was said here #multiplayer message and on various other forums but I appreciate you responding. I also couldnt see anything in code to suggest that it would be skipped, as I said it looked like the regular iterate all actors
Well the caveat would be that if the Actor has already begun play, it wont call it again.
So yeah, the Player Controller wont have it called after a Seamless Travel.
Unless the PlayerController type was changed by the GameMode.
But where does it copy it?
Sorry not sure what you mean?
The player controller copies properties over right, the actual one from map A doesnt exist in map B, it is just a copy so how would it know begin play has been called
Just trying to figure out why beginplay is called twice when it shouldnt
Called twice?
You sure your not talking about the PlayerState?
No, the player controller is having it called twice
if you follow the code in FSeamlessTravelHandler::Tick it appears to actually preserve the entire object edit: (apparently until it hits AGameModeBase::PostSeamlessTravel)
it does not recreate them
also not sure why beginplay being called after the travel is a bad thing here, that seems useful to me
check out the ActuallyKeptActors array in there
they get renamed
I have UEngine::TickWorldTravel calling the seamless seamless handler tick (like what you mentioned) which then ends up in AGameModeBase::PostSeamlessTravel which gets all the old controllers and calls HandleSeamlessTravelPlayer and in there its spawning a new controller
im not sure where you say its keeping it?
ah it handles controllers that way after the travel
I guess other things are kept as is
If its spawning a new Controller its because the GameMode of the new level has changed the Controller type
Which would be why its being called again, because it was changed.
The new Controller wouldnt have begun play.
Both levels have the same game mode and I havent overriden the controllers :/
AGameModeBase::PostSeamlessTravel seems to actually recreate them regardless
I'll keep looking into it if you're certain it should persist?
Yeah I was just looking at AGameModeBase::HandleSeamlessTravelPlayer
it looks like they might intend you to override SwapPlayerControllers
to handle forwarding the properties over
which is lame but... better than it being some evil reflection stuff
If you use AGameMode instead, it implements the class check for the PlayerController
if (PC && PC->GetClass() != PCClassToSpawn)
It does that
Where as AGameModeBase doesnt
ah lol of course they are arbitrarilly different here
I honestly never would have assumed it replaces this
He must be using AGameMode instead of AGameModeBase
Wait
Sorry
Other way around
Yes that is it I suppose, I inherit AModularGameModeBase here which only inherits the base
I kinda assumed the only difference was AGameMode having some scoring handling and the idea of a match
oh well
Yeah, GameMode is a bit of a mess TBH
I use GameModeBase personally.
yeah personally I would not see much point to not use base... it just doens't seem like you lose out on anything
confusing as this is
No you had it right to begin, I had the Base which didnt have that logic, the AGameMode does, I just copied that function from AGameMode and it's sorted
- correction tht was me misunderstanding you when you said other way around
sorted now, thanks again
I hope there isn't anything else that assumes this behaviour in the class though
I would give a cursory look just in case it has a different flow somewhere
im getting a warning from Iris
that a blob is split into multiple parts
never got this with non iris
it doesnt cause any issues, just a damn warning spam
Last I checked blendables can't be interpolated can they? It's either 1 or 0 depending on which volume has the highest alpha
Lots of PP settings can't interpolate
Or maybe they can now, IDK
FSceneView::OverridePostProcessSettings seems to interp
oh I thought i was on #materials, I apologize
Does the CMC do any checks on whether a char is possessed by the PC to determine if that player can add movement?
I can add movement input on the server, but not on any clients.
I have an array where I store the data for each gun magazine I am holding. I first set it to add the components to the array on begin play for the weapon I am holding. Everything worked normally and the server kept track of the bullets in each magazine. I wanted to change it to set the array in the item pick up itself (so dropping and picking up weapons will keep how many magazines/bullets they have) and then when the player picks up the weapon I expose it on spawn. For some reason, it's not working like it was before.
Is it because I destroy the pick up after I spawn the weapon I hold, therefore I am destroying the reference to the data?
Yop, Authority or AutoProxy only.
I'm just getting into multiplayer, so there is a lot of stuff new to me.
If i want to move a char that isn't possessed (with cmc ideally) what would i do?
Ask the Server to move it.
but then what the client sees on the screen is the response from the server, no?
Correct
Prediction of movement via CMC requires the Character to be possessed by said Player.
mhh, yeah that's what I feared.
Greetings
Can someone share guide about multiplayer laoding screen? It seems that clients on load (server travel and connect) see middle of the map for a sec before pawn spawned for no reason
I used semapless travel and transition map, but that not working
I believe that happens bcus the default cam is at 0,0 before the pawn spawns. I think you can fix this by 1: have a cam assigned to the players even if pawn does not exists. 2: extend the loading screen until pawn spawns.
Thanks, so I must create a camera that looks at the widget on every multiplayer map to avoid this?
im not 100% sure, but yeah something along those 2 examples is a way to fix it. I havnt bothered with it myself yet
We placed a sphere at the center of the level with a two sided black material to simulate a black screen
Oh
Is it really no other option?(
there's probably quite a number of tutorials out there on loading screens
Use a loading screen ?
We hold a loading screen up till the world begins play
At that point everything is normally ready
Why does the server only see the barricade destruction? Everything should be replicated correctly
this is the player bp
this is the barricaded door bp which is replicated, same with all the components
I don't understand how it doesn't work, the trace is done on the client then tells the server to destroy the barricade and play effects on the client??
In the BeginPlay of the HUD class create a loading screen
But how to start it? It's impossible to add a loading screen to the viewport until pawn is actually spawned
Level blueprint ?
we have loading screens, its just a widget that we adding to a viewport
but we cant add it until player spawn
Not working (
still see middle fo the map and after that a loading screen
You can implement it in a better way, client should only send a request to the server for doing the line trace, all the important logic should be done by the server
Did you set this HUD as your default HUD class in the game mode?
sure, because I see loading screen after seem middle of the map)
Add a print string to make sure it is visible
and test again
But I tried doing the line trace on the server and it still won't show the barricade being broken? is my other code correct?
yep, and this TRUE appears AFTER seeing middle of the map
You are using the result of the line trace from this function in another function
Server dont have access to the result of that line trace because it performed by the client
But I did all of this code in a server custom event too and it still didnt work?
Yes, for a couple of frames, especially on a bad internet connection, the client sees the center of the level because by default it uses the spectator pawn, that's why I recommend adding that black sphere
damn
is marvel rivals and other AAA UE games do a black sphere?))
There will always be a short delay like this. People usually hide this by either having a temporary overview camera or via UI.
I just told you the easiest solution
But how to tell the engine to use this camera? If I just put camera that looks at loading screen it will not posses
You are using way too many ServerRPCs. One ServerRPC initially is enough. Any other event called by that RPC is already on the Server.
PlayerCameraManager can help with that.
But the client still doesnt see the effects of the barricade being destroyed etc even with one server rpc at the start
In no world did you manage to undo all your RPCs in these few seconds after reading that comment.
And even then, your code is all over the place.
You are using way too many Event/Function Inputs in other Functions.
I did it before the first time..
Maybe any guide or use case? What I can do with this class?
If you create your own Child BP of it, you can assign it in your PlayerController Class Defaults.
It has functions to override (UpdateCamera or something like that) that allow returning the Location and Rotation of the Camera.
Simple solution:
Client does server rpc saying that it hit the thing
Server runs the logic to break the thing
Onrep variable changes to tell all clients that the thing is now in the broken state.
By default, it will stick to the ViewTarget + whatever active CameraComponent causes an offset.
You can get whatever you need in that function and decide if you want to show the overview camera.
It should be like this
E.g. if the ViewTarget is not your Character/Pawn.
so basically I need to add on every multiplayer map a loading screen place and then in player camera manager set location of the camera to it?
Well, no that's two different things.
The Camera stuff would be if you want some kind of "show the map while people are loading in" thing to cover the lag.
LoadingScreens that cover the screen with UI don't need the camera.
I just want to show loading screen before player see middle pf the map)
But adding it to viewport is only working after pawn is spawned
Are you adding the Widget in the PlayerController?
yep, on begin play
and I still see middle of the map, and only after a loading screen
BeginPlay could be too late, as that triggers from replication.
Hm. Good question. There are probably a ton of functions that could be used. Maybe something in the ULocalPlayer.
Or you use the more traditional LoadingScreens via the MoviePlayer, which can be shown across the whole travel and can be hidden "later" whe you want to hide them.
That not possible in blueprints, only in C++?
And if I will try movie player, we speaking about this plugin?
That's C++ yeah.
But you are developing a Multiplayer project. You shouldn't be using only BPs.
If you can't use C++, then that's your first reminder that C++ will probably be needed.
BPs can do a lot, but in Multiplayer projects you will quickly hit their limit.
And no, I don't mean that plugin.
You can google a bit, maybe someone made a plugin for the LoadingScreen stuff.
I know Lyra had one, but not sure if that works without Slate.
No worries, I can. But we are working with unreal game sync so Im trying to touch C++ only when it needeed)
(after every C++ change I need to build bineries for team manually)
UGS has nothing to do with that problem though.
Your problem is that you have no Build Machine.
UGS is even the opposite of the problem here. It's meant to solve this.
Hoping for a direction pointer, in my game im aiming for 4v4 or 5v5, players players generally will control 1 AI unit. sometimes however players may have a an additional pet or a 2 units. Based on this im thinking max 15 units in game at a time.
So wondering if its acceptable to do a get all actors of class on the character/unit class to build an action que? (Was told this node is bad before so hoping to clear it up)
Baksically im hoping to add units that have a valid action to an array to loop through to use later
Yep, but I didnt find any guide about it, Im not a devops guy. Even installing UGS was a big quest because Epic's didnt update some stuff in source engine so you will fail during UGS insatller preparations, and other stuff
HORDE looking very hard thing, tbh
Own manual build machine require some devops skills, my brain is melted
The node isn't as bad as it could be, as it uses some hashed container to find the objects based on the class.
However, using that node is often just a shortcut around properly setting up some manager that can keep track of the objects and hand them to you.
Now the server cant break the barricade but the client can
That what I asked here - any guide about multiplayer loading screen. I cant find nothing related on google, and AI is also talks about weird not existing stuff
Fair, but UGS itself is still meant to solve this. The Build Machine with automation is your problem then. Horde is also optional fwiw. People have used UGS years ago already.
But yeah, if you have no DevOps skills then that can get tricky really fast, understandable.
@thin stratus any pointers on where i should look for setting up this would be action manager. currently im getting all actors of class with tag and then if action is valid addint to the action que
thanks a lot, will check this
Third result on google searching for "Unreal Engine Loading Screen Plugin".
¯_(ツ)_/¯
Idk if that's good, but the code seems to be using the MoviePlayer. So it's probably enough to at least learn from.
I'm not too sure what your "action queue" is all about. But a manager of sorts can always be placed on the GameMode or GameState in form of an ActorComponent.
GameMode if server-only. GameState if needing replication (Server -> Client only).
That Manager can have an Array of "SomeClass", and "SomeClass" can use BeginPlay and EndPlay to add and remove itself to and from the array, cause the GameMode/GameState is easily gettable.
You need to redesign your system. Fixing this probably will cause another problem later, the client should only request a line trace from the server
I was doing this loop in the gamestate anyway
so ill look more into it around there
this happens once per phase in a turn the action just says if you will 'activate' in this phase this turn
hey can someone help me with this ?? im struggling days with this bug(btw in the game i show that when i fire a rocket on the first player and im second its just hit the controlled player(second player) but when i fire a rocket as a third player to the second it hits the second player)
You have some questionable code here. You're using GetPlayerController in a multiplayer environment for a start. And I don't know why the rockets need to know about the gamestat's player array.
Your rocket should do five things in order. Spawn. Move. Hit enemy. Apply damage. Destroy itself.
It should be able to infer what an enemy is based on it's instigator. If you didn't tell it what it's instigator is, you should.
Most of this logic sans some client side movement interpolation should be 100% server only.
You should literally never use GetPlayerController. There are always contextual ways to get a controller based on your needs. UI and AHUD have getters to get their owning player's controller. Most gameplay things do not need a controller for any reason.
I am unsure if I need to change this so wanted to double check. My Weapon has a bIsInPickupMode with an OnRep function to disable collision and some other stuff on all the clients. If I am spawning a weapon with SpawnActorDeferred on server from another class and I run:
NewWeapon->bIsInPickupMode = false;
NewWeapon->OnRep_bIsInPickupMode();```
before I call NewWeapon->FinishSpawning(...), will the collision and all that be disabled on clients or will the OnRep function not run on clients because spawning hasn't finished?
Edit: Kinda thinking I should just use Multicast instead as turning on/off isn't going to be running a whole lol. Not really sure why I was used OnRep originally aha.
yes ok,i know the player controller is not for multiplayer i just put it there for some tests i deleted it and replaced it with the get game state-get players array-for each and after that i cast to my player state but if you can please take a look on the other code and see if you can find any other problems that causes this to not work.
The node is fine, it's getting all actors of class actor on tick in a loop that would make it spendy.
Although you really should have some maintained data somewhere that lets you know who (player) owns which units (their units) and can just query that
MyUnits on Playerstate for example
You can create a widget that is spawned before you start loading into a game (like in your join game scene). Fade this to black during join, and then have it persist through the loading, and then fade it away once the character is loaded and "settled". I'm doing that for my game, hides the camera jumping. It's explained here: https://forums.unrealengine.com/t/multiplayer-how-to-set-a-persistent-loading-screen-while-connecting/371222/17 just needs a few small bits of code to expose it to BP. Spawn the widget through game instance or some persistant spot, and then you can access it between different maps
how can i make a host game/ join game menu system for my multiplayer prop hunt game? i want a waiting room until there are enough players to start the game (spawn them at the game level)
A waiting room would just be another level. When enough people join the server, you just transition the server to the play level.
Do anyone have experience working with multiplayer splitscreen? I'm having trouble to make the 2nd player listening to input. All inputs get redirected to player 1.
I wish it was that simple but my whole room system has been acting weird
none of my main menu buttons work for some reason and when i press the start game button on the lobby, it spawns all the players as if the entire level becomes black
can someone help me?
idk why but when i've set the server travel to the third person map instead of the demonstration map, all my players were spawned at the player starts, i wonder if there's a world setting that i need to change for my demonstration map that would allow my players to be spawned at the player starts rather than the level being all dark and acting all weird
but still my main menu buttons dont work as expected
i just need to fix my hosting/joining menu and my game technically works
Thank you for your update. I do store a reference to the player controller that is "commanding" the character on the character itself and a reference to the current character in the player controller (this can be moved to the player state if its preferred and probably makes sense to with how I've done the spawn tiles after previous feedback).
I was following a setup for the characters to be server owned but receive commands from a PlayerController. The idea was to then store a reference to an action for each phase in the AIController for each turn and on phase change within the turn, loop through all characters with a valid action for that phase and add them to an action que on the server and once the decision phase was over loop through that que to action each character. (It's a mix of turn-based and tabletop)
Thanks! On this forum people suggest creating a BP with "tick before begin play", or use C++
(To call this widget before pawn spawn)
Is that right?
Because it seems that we cant add loading screen to viewport if it calls that early
since server spawned actors have a bit of a delay before they send a client spawn info, if a server spawns a moving actor (like a projectile) it will move a bit before actually sending anything to the client, but it uses the spawn location instead of the most updated location... is there a way to make the spawn location the actors current location?
my work around is to have another location variable replicated with a initial only condition.. but it seems weird to replicate the location twice
RESOLVED!
Just use the Lyra "Common Loading Screen" plugin. It works perfectly in one click
Is it available on the market as a plugin?
Or did you migrate it your own
just copy it from lyra plugin folder, plugin called Common Loading Screen
Have a look at what UT4 does
It creates a fake clientside projectile that blends to the position of the serverside one
Actors owner is by default replicated uisng some onrep function, so why the onrep is not called? means the dedicated server is not taken into account?
void AActor::SetOwner(AActor* NewOwner)
{
if (Owner != NewOwner && IsValidChecked(this))
{
if (NewOwner != nullptr && NewOwner->IsOwnedBy(this))
{
UE_LOG(LogActor, Error, TEXT("SetOwner(): Failed to set '%s' owner of '%s' because it would cause an Owner loop"), *NewOwner->GetName(), *GetName());
return;
}
// Sets this actor's parent to the specified actor.
if (Owner != nullptr)
{
// remove from old owner's Children array
verifySlow(Owner->Children.Remove(this) == 1);
}
Owner = NewOwner;
MARK_PROPERTY_DIRTY_FROM_NAME(AActor, Owner, this);
if (Owner != nullptr)
{
// add to new owner's Children array
checkSlow(!Owner->Children.Contains(this));
Owner->Children.Add(this);
}
// mark all components for which Owner is relevant for visibility to be updated
if (bHasFinishedSpawning)
{
MarkOwnerRelevantComponentsDirty(this);
}
#if UE_WITH_IRIS
UpdateOwningNetConnection();
#endif // UE_WITH_IRIS
}
}
You can override SetOwner() and call it manually if you need it on the server side
void AMyActor::SetOwner(AActor* NewOwner)
{
Super::SetOwner(NewOwner);
OnRep_Owner();
}
Best approach
Hey everyone! Has anyone had any problems with spawning players in the server default map? I get this warning: LogGameMode: FindPlayerStart: PATHS NOT DEFINED or NO PLAYERSTART with positive rating. But I have a player start, I use seamless travel in the GameMode and everything should be correct. It works when I play in PIE, but packaged build as well as standalone game does not work, it just shows a black screen.
I'm using UE 5.6 by the way.
if i call a server RPC inside a server authority check its just gonna execute normally ? it wont send an rpc to itself and have any extra cost right?
yeah there's no networking involved, I'd expect the same impact as calling a BNE
and if it's not a BNE, you can always call the _Implementation function anyway
whats a BNE?
BlueprintNativeEvent
When a client connects to a listen server, does the server gain authority over the client's player controller?
Additionally, after a client connects to a listen server and then uses ClientTravel to load into the map the server is on, is the client's player controller expected to run OnPossess again? Our client used to run the OnPossess a 2nd time when it loaded into the Server's map, but we recently swapped to using pak files to house our maps and now, while I've figured out how to get it to load into the server's map, it's no longer running the player controller's OnPossess afterward like it used to, so I'm trying to establish expected behavior.
Greetings, weird question - its only me or disabling input for client player on spawn is kinda hard thing or possible only on C++?
If you put client RPC on Event Possesed - client will not be possesed at this moment and disable input wont work
If you will put a delay or onRepNotify variable for player controller, player still will have 0.5 sec to do smth on spawn
Authority is such a shitty concept to rely on honestly. I wish it was less recommended for general uses. Authority is nothing more than who spawned the actor in a sense. This gets muddled with client predictive spawned actors but if it's a replicated actor the server will still have authority. A client will only ever have authority singularly if their machine has spawned the actor, which means it will also have no networking capability.
So in the cases like a PlayerController a Server will always have authority over it since it's a replicated actor. The only time a client has authority over it is before they've travelled to the server's map.
I'd expect OnPossess to run any time the client gets a new pawn. So I'd definitely expect it to run after joining a server.
OnPossess only runs on the server if I recall
AcknowledgePossession runs on server and client
Thank you for this breakdown, this was great.
I always tell people to look at auth as "what machine spawned this actor"
For like 99% of actors, it is going to be the server. Which is why it is used as a way to do stuff on the server
Do you have any idea what could cause the client to skip its OnPossess call then? I'm worried I'm not connecting the client to the server correctly, but I'm not sure where I'm going wrong.
Because it doesn't get called on the client
You need AcknowledgePossession
Which is C++ only
Store a ref to all units a player owns in their playerstate or playercontroller (depending on if other people have to know)
This conflicts with this explanation: #multiplayer message
As well as the behavior the client exhibited prior to using maps loaded in via .pak files
Use ReceiveControllerChanged instead of Possessed
Prior to this change, the client ran OnPossess on the Player Controller twice, first when it launched, and a second time after it traveled to the server's map.
perfect, thanks)
I don't know what behavior you were experiencing, but it doesn't run on non-authority. Possess wiil early out if it is trying to run on something that doesn't have authority.
You could set that bCanPossessWithoutAuthority variable to true in a derived class, but I don't see many people doing that
So that is the only way for OnPossess to execute on the client
The playercontroller has AcknowledgePossession that you can override to handle local client possession stuff.
And AcknowledgePossession will execute towards the end of the OnPossess function execution (which again, only happens on the server)
Would it be correct to say that there should be a 2nd OnPossess call happening on the server after the client connects/travels? From there would I be able to use a Switch Has Authority to run my logic on the client?
If you are bringing the pawn with you on the seamless travel, then it might not execute again. Not sure though. But otherwise, I'd imagine it would because the controller is getting a new pawn.
Just have to trace the flow of the code.
Can you do seamless travel when calling ClientTravel? I know you can with ServerTravel, but I was of the understanding ClientTravel doesn't use seamless
When the client does its initial connection to the server, OnPossess should run.
I'm double checking this right now but this might be where my problem lies. I don't believe that OnPossess is running after the client's connection to the server, despite it connecting correctly (or so I thought)
Ok so OnPossess is being called twice - each time the server changes maps. Not when a client (allegedly) connects to it. The client is supposed to connect to the server shortly after the 2nd map is loaded in.
OnPossess gets called on server when a pawn is possessed
If I seamless travel to a map that has the same gamemode class as the current one, will the gamemode be kept or will it still be re-created?
I believe the GameMode is always recreated.
What about game state and its components?
The GameState is kept as part of AGameModeBase::GetSeamlessTravelActorList
So are all PlayerState and the GameSession
The GameMode is actually kept, but it gets replaced.
You can override AGameModeBase::GetSeamlessTravelActorList to add your own Actors to that list if you want them to be kept across level transitions.
You can keep Characters if you want
i see, thank you
Does EndPlay get called? We're using Lyra and I'm wondering if it will unload the current experience even though I kinda don't want it to
I see Lyra does it in ULyraExperienceManager::EndPlay, and it's a game state component
EndPlay will probably be called because it handles intermediate states, EndPlay isnt just for when the Actor is destroyed.
yeah and it has EEndPlayReason::LevelTransition
EndPlay is the opposite of BeginPlay
I know I know haha, was just wondering if persisted actors would have it called
A little annoying
Is it common to call OnReps or Server RPCs from one object to another? I am doing things on the CMC but keeping replication on the character.
Depends on how exposed you want those things to be to other classes.
I wouldnt typically call an OnRep function from another class directly no.
Id wrap it inside a setter that modifies the property as well.
this is how my menu system currently works rn. for some reason the server travel to the lobby map just doesnt happen but it shows the debug strings after all the hosting/joining/quitting code
i have fixed the transition from lobby to game map once there are enough players but main menu to lobby doesnt happen
Initial hosting isn't a Server Travel
Use OpenLevel with ?listen for that.
ServerTravel is after you are already hosting and doesn't require the ?listen part anymor
like this?
Yeah.
it still doesnt open the lobby map
After that, any travel that should keep the server listening and take clients with it should use ServerTravel. And also be seamless.
still shows the same debug strings as before
So it says Session Created but doesn't open the level?
it executes both the on success and on failure debug strings
Oh you are already playing connected in the main menu
You gotta change the play settings to Play As Standalone instead of ListenServer
After all you are in the main menu where people aren't connected yet
Or shouldn't be at least
i tried that but still shows the same, doesn't open the lobby level
and yes the players shouldn't be connected in the main menu but only when they are in the lobby level
So all 3 Windows show "Standalone" in the title instead of Server/Client?
yeah
Start with just one player for now and check what your output log says when you try to host
still the same
Yeah hence the output log part
i dont understand what i'm doing wrong with my code
Could you just share the output log after you try to host?
You still tested this as a Server.
The window title still shows you aren't playing as standalone
And your log shows that your Widget and your GameInstance are both doing something. Maybe duplicated code?
The GameInstance one is reporting an invalid PlayerState, which means you might be calling whatever you do there too early.
Please start as no Server and show the output log again.
i do have the code to show the main menu widget in both main menu player controller and also the level blueprint
Yeah. But the log shows that you print the failed to host stuff in your GameInstance
That's also where UE reports an invalid PlayerState
Why are you even creating the Menu widget in two places?
The MainMenu PC should be enough
The MainMenu PC also shouldn't need the whole authority and local controller stuff since you shouldn't be connected in the MainMenu
whats the standard way to remove ISMs on client and server? Im having a bit of an issue with the logic lol
Usually to keep track of what instances should exist in some replicated form
Okay I figured it out... it was that the player controller wasnt connected to the respective pin of the create session node and it works now, thanks!
Ya makes sense given the warnings
Didn't spot it from phone. Good catch
It just doesn't make much sense to host as a ListenServer
You are already hosting after all
It will probably work and kick the other 2 clients
But still nothing you want to test
Your PlayerController shouldn't even need the auth check etc in the MainMenu
You also shouldn't need the Level blueprint fwiw
Looks to me as if you create the menu twice atm
yeah i removed the level blueprint logic when you mentioned it and it works now
Now keep in mind that the traveling from lobby to game should be ServerTravel and the GameModes involved should be set to Seamless Travel
yeah i probably missed it while i was trying to figure out where exactly to call the widget, my bad
i usually call my widgets inside the controller but did it inside the level blueprint as well when some things didnt work as expected
Its a bit tricky as the indexes seem to be different between client and server, and keeping track of the ism component itself doesn't seem smart. idk im having trouble reasoning about how to approach it tbh
The indices are only different if you manage to desync it
Server should have authority over it
hmm i see
Hello all. I have a question about Epics Shooter Game 4.27 sample project. https://dev.epicgames.com/documentation/en-us/unreal-engine/shooter-game?application_version=4.27
Is it still considered like modern approach for multiplayer FPS or there are some better examples or solutions? Thank you in advance for any advice / help.
I mean C++ AShooterWeapon AShooterWeapon_Instant AShooterWeapon_Projectile
Hello. I have a situation where I spawn an actor which on begin play it sets some details about itself, like the mesh, text and other variables. It's set to replicated on server and everything works fine except the text render. Actor and each component is set to replicate. On the server side the text is showing properly, on clients it's just showing text. Any idea what's going on?
looks like set text isnt getting called for whatever reason on clients.. does it rely on another replicated value? might be a timing thing
Lyra replaced the shooter game
Replicating the TextRenderer component doesn't magically replicate the text. You usually barely replicate any of the standard native components.
You need to handle this via a RepNotify variable in the Actor
So it is better to use GAS for FPS like in Lyra?
It's an option fwiw
Up to you in the end
just to understand, the same actor has a static mesh component which is set through a variable on the actor that's set to replicate and that works just fine, for the text I need to rep notify and do something in the function of rep notify?
Yeah the StaticMesh should also be a RepNotify after all.
that's why I'm confused because the mesh and an ability class is replicated but just the text it's not and i've done the same thing with the text variable and component like with the rest
The Mesh and the Text are considered state. Those are supposed to be handled via OnRep/RepNotify if you need it to replicate
oh interesting... static mesh components DO replicate their static mesh variable.. TIL
skeletal mesh components dont though lol
IMO gas is ass for shooters, there is so much interdependence between stuff that it’s better if you develop a custom solution to networking a shooter, GAS maybe be fine for abilities but in my highly opinionated opinion, gas is not good for a shooter
If anyone is willing to help me out. I would love a small tutot session. Can compensate you. . . My game is basically just two physics balls that move around in a scene. Just need help understanding the assigning players to characters and how to correctly set things up with explanations. My reading abilities are very hard since dyslexia and such. I am an artist trying my hand at a simple project. Many thanks in advance. Please feel free to @ me or pm me
Personally I still really like it as it is so clean and self contained compared to Lyra. Each class does one thing and it's much easier to understand. You may need to upgrade to newer tools in UE such as the UI stuff as that is now outdated. It also had an audio update around the time of 4.27 so there are new things to learn there
These are both very solid in terms of simple and clean code to learn from. Just note the hit detection logic used in ShooterGame would need to be replaced if you were trying to make a competitive game as it trusts the client greatly
You can also look at UT4's source code for a more advanced version of both of these
The modern Lyra approach is moreso built for big teams with loads of logic separated out into tiny little sub blueprints or code snippets which makes actually working with it quite cumbersome
Lyra is too massive to be the platonic ideal template
Im almost certain the indexes for ISM instances are different between server and client. the client doesn't want to see the change no matter what i do 😮 not sure what to do tbh, I dont really want to use actors for interactable foliage lol
They are different yeah, nothing about ISM's is replicated
Partially dependant on how they are generated ofc
If they come from being pre-placed in the map, should be identical
How does it even work if the client and server are generating something different?
The hilarious part is that FN is a shooter 🤣
The gameplay effects are probably one of the more useful parts of GAS imo
Is there a way to mitigate jittering while moving (and sprinting specifically) with like 1%> packet loss percentage? (Everything is super smooth with only latency emulation, packet loss jitters a bit)
I don't really think it's any worse for shooters than anything else
At the end of the day shoot gun is just an ability
It's only flaw is that you need to hook into CMC somehow in a way that doesn't suck ass
ah that would make sense. I ended up copying the custom foliage instance static mesh component from the instanced foliage actor which isn't replicated, to another actor that was replicated. but I dont think its a very good solution lol. And the removed instances dont always update to the client -- its like a 90-95% working but otherwise sometimes buggy. So its a bit odd in such a regard. I looked at the network profiler but I haven't used it much so i dont have much of a benchmark to compare to lol.
I did place them using the procedural foliage tool then copy the component over to a new actor, so I guess maybe the indexes are identical in such a case then?
Im pretty sure I have to use a game instance to carry data through levels e.g. from a lobby to a gameplay and ive not found anything yet about doing this by passing a player struct through to the game instance in a map (im thinking player controller as key) but if i remember rightly you get assigned a new player controller on change so should the key be something else a little more unique? If so does any one have any reference for achieving it. I guess my question is, is the player controller ok to use as a key or should it be a name I set somewhere
Using the players Unique Net ID should cover it
Alternatively if you're using seamless travel, there is a handoff to the new controller, player state etc. from the previous ones
Have you ever wanted a new weapon to require 8 files? Have I got the solution for you.
They use it because they want to keep everything under one replication model as much as possible, for a stand alone shooter game I honestly personally believe GAS is not the right move
I could send 25 packed bytes per shot which is important given smgs or lmg fire up to like 40-60 bullets per second or I could use gas because it’s convenient and send way more than is needed and deal with all the quirks that come with weapon stats as ability sets, I just personally think gas wasn’t made for shooters and it shows
But you’re right it’s funny that Fortnite uses it and I have this take, as I said I think it just comes out of convenience and all being in the same replication model more than being the right tool for the job
Yeah - GAS sucks with fast firing stuff. For what its worth, I don't use attributes for weapon stats either. I just have 'em as regular ol' values. I have weapon bonuses as attributes though. So I could have a "assault rifle damage + 10%" and when I get damage, I just pull from the weapon and * it by the bonus.
It'd be really really nice if they'd do a GAS 2.0, because I'm sure they learned a crap ton in the like 10+ years they've been using this. But I doubt we'll ever get something like that. FN is too tied into it.
Just wait for fortnite 2 
so i wanted to replicate a comperessed rotation in a way that client update it and send to server for update main ly for hand sway
works perfectly fine on server but in autonomous proxie does not work
if needed the code base is big unable to share the full code need to show in vc
For data like that I wrap it in a common constantly updating struct (it also contains things like animation specific data, etc just things that change all the time from frame to frame) and the player sends it N amount of times per second in an unreliable rpc with it being as packed as I need it to be and then on the server I validate anything that might be funky and then I take that RPC received struct and set the servers local replicated variable of that same struct so it then sends to all clients through regular replication whenever it updates, in my case that works because its only "important" for the auth to have the latest data and clients I dont mind getting it late
just a few more things to fix and my game is somewhat done. im having issues sometimes with the pause menu system where the resume button just doesn't do its job and also the issue of not being able to host another game once the host leaves the game
i wonder why the pause menu sometimes acts weird and doesnt allow for the resume button to work
ello i hate asking for help but im struggling with saving data on client only in multiplayer game. could anyone proficient in datasaving and multiplayer assist me :)?
Can you be more specific what you are struggling with.
Saving data locally is as simple as calling the function on the target machine.
when ever i update the playerstate and save its saving on the server
Then you are calling the function in the server machine only.
If you need everyone to keep a .sav, you need each of machine to call the save function.
i understand. but i cant seem to figure out how to do the opposite
i am not a good programmer.
i use bp
You can do this in bp
How does the save get initiated?
At what point in the game does the save meant to happend?
Server initiated or just on each instance?
Does the server have to tell the client, go ahead and save?
Or client will just save after everytime it pick up without being told?
ummm im not sure if the server has to tell the client to save.
im pretty sure one of my issues is here where im trying to get game data from the game instance but thats the server.
clients will save after everytime its picked up. on rep?
Its your game you need to design the game flow
Game instance exist in every machine.
Everyone have their own.
If you try to do this in PIE you will have issues as I think they share the same GI.
yeah. i tried to do some settings change to make it its own instance and it seems to be working. as in, it shows the broken side of things
i've gotten it to work inside pie before
changed the settings to emulated best as it were on steam
Why do you even use GI to store data?
Gi is not replicated
If the data only available on server then client dont have access to that.
store each player data in player state
ONrep -> get data from player state -> save.
perhaps you would consider responding and adding me on discord and giving me a few moments when you are available
Can't do that, I have my own problem to deal with.
If you are trying to read object that you cant reach that will be the time you need to refactor your system.
No. They don't
All data should be readily available on client anyway.
can someone help me?
Destroy the session once you're done with it
This is what I get now, the resume button still doesn't work but when the host clicks on the leave game button, all players go back to the main menu and when i try to host another session, it only works for the player who hosted the previous session and even so, other players can't join that session
Hi, I would like to learn multiplayer programming. I have checked the pinned messages for resources but they have been posted years ago, so I am not sure if they are outdated or not. Therefore, I would appreciate any resource suggestions 😄
This really is the best place to start: https://dev.epicgames.com/documentation/en-us/unreal-engine/multiplayer-programming-quick-start-for-unreal-engine
& This entire category in general: https://dev.epicgames.com/documentation/en-us/unreal-engine/networking-and-multiplayer-in-unreal-engine
One of the few things in the Unreal Documentation that is actually well written :P
I was thinking of reading these but not sure about trusting the Unreal Doc
Thanks for the confirmation ❤️
Anywhere is a start. Replication hasn't changed though multiplayer it self is a can of worm.
I'll start fresh on my pause menu tomorrow, damn working on a multiplayer game has been taking a toll on me
I can imagine, i have the basic idea of how much more layered thinking multiplayer requires than single player.
How much have you consumed from the pinned material? Because you will be good to go to do simple mp game from there.
not much, I just checked the titles and dates they have been posted. I wasnt sure where to start until now.
My 2 cent, if you haven't publish a sp game, you probably should work on a complete game first.
Mp get complicated quickly depending on the game type
And certainly very limited if using bp only.
I worked on a published sp game and I have knowledge of C++ (limited, still improving)
I feel like its the right time to start learning multiplayer
The pinned material is not out of date, its the best source to start.
yeah even after an entirely new netcode backend
the actual substance of how it works on the game code side is mostly identical
this engine doesn't change a lot (with actor gameplay stuff) so old docs tend to be pretty close
I'll check them as well, thanks for letting me know they are not outdated ❤️
even though its printing correctly the sway is not visible here]
tried brute forcing it still in vain
any quick fix will help
Where is this placed?
The top right function
Tick
Why this prints Authority! two times?
PlayMeleeAttackMontage()
{
ServerPlayMeleeAttackMontage();
}
ServerPlayMeleeAttackMontage()
{
MulticastPlayAnimMontage_Implementation(AttackMontages[FMath::RandRange(0, AttackMontages.Num() - 1)]);
}
MulticastPlayAnimMontage_Implementation(UAnimMontage* NewMontage)
{
PlayAnimMontage(NewMontage);
}
MontageNotifyHandle(USkeletalMeshComponent* MeshPlayingMontage)
{
if(HasAuthority())
{
UE_LOG(LogTemp, Warning, TEXT("Authority!"));
}
else
{
UE_LOG(LogTemp, Warning, TEXT("Client!"));
}
}
LogTemp: Warning: Authority!
LogTemp: Warning: Authority!
LogTemp: Warning: Client!
im calling this line just for testing porpouses at the moment in the player controller, but the outline only shows on the server, i was under the impression that this code would run on every PC
thats inside a function thats inside a tick
ListenServer?
Why would you call that on Tick?
a the moment im just tryign to get it to work
but eventualy im gonna turn the outline on and off depending if ur behind things
Running as a single client in editor, not a packaged build
Server has all PCs (one for each Client/Player) and fwiw their own if ListenServer.
Clients only have their own (no instance of other player's PCs, despite maybe local coop ones).
so my autonomous proxies dont tick?
You might want to print in the other functions too, to see if any of them are called more times than you expect.
inside the PC that is
LocalClient and Server will tick the PC
I mean you can just print in the function and check for yourself
confirmed they are called once, and the montage also played once per click
Breakpoint the Notify and see what it calls from. Could be that this is just Notifies being as shite as they are.
> UnrealEditor-ARMA.dll!UOnMeleeHit::Notify(USkeletalMeshComponent * MeshComp, UAnimSequenceBase * Animation) Line 22 C++
UnrealEditor-Engine.dll!UAnimNotify::Notify(USkeletalMeshComponent * MeshComp, UAnimSequenceBase * Animation, const FAnimNotifyEventReference & EventReference) Line 40 C++
UnrealEditor-Engine.dll!UAnimInstance::TriggerSingleAnimNotify(FAnimNotifyEventReference & EventReference) Line 1620 C++
UnrealEditor-Engine.dll!UAnimInstance::TriggerAnimNotifies(float DeltaSeconds) Line 1521 C++
UnrealEditor-Engine.dll!UAnimInstance::DispatchQueuedAnimEvents() Line 748 C++
UnrealEditor-Engine.dll!USkeletalMeshComponent::ConditionallyDispatchQueuedAnimEvents() Line 1769 C++
UnrealEditor-Engine.dll!UCharacterMovementComponent::MoveAutonomous(float ClientTimeStamp, float DeltaTime, unsigned char CompressedFlags, const UE::Math::TVector<double> & NewAccel) Line 10269 C++
this is the notify i'm using:
UOnMeleeHit::Notify(USkeletalMeshComponent* MeshComp, UAnimSequenceBase* Animation)
{
if (!MeshComp) return;
AActor* Owner = MeshComp->GetOwner();
if (IsValid(Owner))
{
AArmaCharacter* Character = Cast<AArmaCharacter>(Owner);
if (IsValid(Character))
{
Character->MontageHitNotifyHandle(MeshComp);
}
}
}
in the callstack, about this i'm not sure why i have it
UnrealEditor-Engine.dll!UAnimNotify::Notify(USkeletalMeshComponent * MeshComp, UAnimSequenceBase * Animation, const FAnimNotifyEventReference & EventReference) Line 40 C++
I'm doing an aim offset using "Get Base Aim Rotation" and "Get Actor Rotation" this works fine locally, but on replicated clients, only the pitch seems to have a delta between aim and actor.
So I'm trying to figure out why only part of the Base Aim Rotation would be replicated. Is this expected because it is somehow handling vertical camera movement different from horizontal and decides only to replicate pitch?
this is the exact solution
#multiplayer message
Thanks a bunch, so if I understand and looking at the implementation of FRotator APawn::GetBaseAimRotation() const
It seems to only do stuff with pitch... did you ever try modifying this function or just do your own thing?
modifying engine functions will lead you to rebuild the engine and possibly other things can break
most of the times i just override things and use it with custom functionality
Hey everyone! Does anyone know how to manage two different lighting scenarios sub-levels in a multiplayer game?
I have two lighting levels and I switch between them using a trigger only for the one who is using this trigger, others should not be affected (aka goin in or out of the dungeon). When I switch on the client, everything works perfectly and doesn't affect other clients. However, when I stream a level with one light and unstream another on the server (non-dedicated), it affects all clients.
What I need is to change the lighting (stream the level) only locally on the client or on the server, without it affecting other clients. The event is not replicated and triggered only on the server (for the server).
Can someone explain to me why a blueprint based anim bluprint is cheaper than a native one?
I'm paying almost 1/2 a ms for the native update while the blueprint version doesn't have that cost. Making the blueprint version almost 2x faster on its overall work. The game thread time is not a big jump but the blueprint version is cheaper
aw hell this is multiplayer my bad lmao
off topic but just to respond quickly to save you some time: Measure in unreal Insights IMO with stat named events to see the actual time taken of each step
these stats are a bit too rough to make comparisons like this imo
Anyone recommend a good tutorial series for steam/advanced sessions with listen server. I am wanting to make a lobby where players join into and get assigned a proxy player and when pressing jump they spawn their character. I have most of this working already but clients aren't getting assigned to the servers local player slots (0-3). I am so lost and I can't figure out why. So I'm going to make a new project and start from scratch to see if I can learn something that I'm missing
Most of the tutorials that I've watched do pretty much the exact same thing and I have what they have but mine doesn't work with the default character etc
cpp or bp?
anyone able to tutor for $ multiplayer save and load data?
Breh, I have been banging my head on a wall for this thing for like 4 days straight and can't get it to work and I have no idea how to do it. and I have messaged all multiplayer people in freelance to help me with no reply. I have read all the documentations and watched all the tutorials that I have done the exact same thing in but trying to make it work in my specific case just will not for the love of god work, I need help, please someone Will pay money to teach me. litterally just a simple press A join in possess pawn
i can try and help you finn
I mean in what object.
In its simplest form, you can just use UE's save system to do a save file of the data you care about. Then you can send that data, after loading from it, to the client or server (whichever direction you need)
Hi, I've noticed a weird jitter when first interacting with doors where it appears to immediately open/close before playing the rest of the timeline animation, I assume its my MC_OpenDoor/MC_CloseDoor events clashing with the OnRep_IsOpen function setting the final open/close states of the door..?
What is the correct way to do this? The doors animation only needs to be played for players who are relevant hence the multicast but for players that become relevant later they just need to see the end result which is what the OnRep is doing, but how do I do it in the correct way without them clashing with eachother causing the jitter? OnInteraction runs on the server only so I figured this is the only place I should be setting IsOpen, I didn't want to set it on the Finished pin because its ran on a Multicast and I don't want clients being able to set the state of IsOpen.
one should not use Multicast for stateful behavior
including opening / closing a door
Multicast = Server telling clients to run X function.
so this meant that if the door is opened then a late joiners come. The door will stay shut for the late joiners as it never run the function.
relevancy or not I don't know why you want to introduce MC
The multicast is just to play the door animation, IsOpen OnRep sets the final states of the door so players who become relevant later are updated with the correct state of the door
Can i do it without the MC?
I don't know why you need the MC
Play the animation in the onrep
If i play the animation in the OnRep, wont it play the animation again when players become relevant to it later?
Yeah - but you shouldn't be marking them as relevant when they're right next to the door
you could also just include a simple timestamp and if it's very far from the local time just don't play it and snap to
Well that's what the MC's were for to avoid the animation being played for players that weren't relevant to it at the time, i suppose i can increase the relevancy range but still.. would rather it just didn't play the animation again lol
Megafunk laid out a neat solution imo.
you just add extra information like the time stamp.
Was just about to reply to that but ive not used any of those before so idk what they are lmao
When the door become relevant, you just check if the time stamp delta is more than the door animation time.
if it is, then assumed that no animation need to be played and snap.
what I mean is just the world time as a number
a timestamp usually refers to the world seconds or something similar
I would say it would be best to give it some leeway around ~3 seconds or so
where only big discreprencies mean you skip the anim
So wait, is this with keeping the code as it is now with the MC's or with running the animation in the OnRep instead?
I never played with relevancy but im pretty sure OnRep will get called when the actor become relevant.
MC shouldn't have a place in a stateful behavior.
it's a one time event
I haven't ever had it as a problem in practice
Yeah apart from the CanInteract's which i put there to stop it from being able to be spammed while the anim is playing, the MC doesn't set IsOpen the server does on the OnInteraction event, the MC was just to play the animation of the door opening/closing while IsOpen set the final state
No, I still think MC is a mistake here, it adds nothing but complication.
the state of the door can be interacted or not is solely belong to the server. Why does the client value even matter?
Client merely request to toggle the door.
if you want to stop spamming request, you can add some sort of cool down locally.
Cool so how do I set this up? So I wanna Get World Delta Seconds? then what from there? compare it to what?
delta seconds is not what you want
you just want world seconds
delta seconds is the time it took to make the frame
Corey, server executes the time line, then the location is multicasted
