#multiplayer

1 messages Β· Page 290 of 1

verbal ice
#

Which (from what I gather) aims to provide what NPP would've

#

So that GMC can be used for non-movement prediction too

quasi tide
#

That'd be a welcome addition

verbal ice
#

tbf it already is

#

but more native support would be nice

quasi tide
#

Yeah, but it feels weird currently

nova wasp
#

I feel like Mover kind of eats that plugin's lunch so trying to make it more generic is a good idea

quasi tide
#

Nah

#

What Cyn is talking about is routing all of your networked stuff through GMC replication stuff

verbal ice
#

GMC has a community made GAS replacement plugin too so

quasi tide
#

So no more CMC fighting GAS for prediction and rollback and stuff

verbal ice
#

Which supports server applied but client "predicted" gameplay effects

nova wasp
#

so not just for movement but a psuedo-gas thing

quasi tide
#

Oh, you're talking GMC, not Mover being more generic

nova wasp
#

GAS prediction being separate from the CMC is a huge footgun people get burned by over and over

#

so it being 1 thing is a good idea (as a plugin)

verbal ice
#

Most annoying thing about GAS is how deep routed it is with ACharacter and the CMC

fossil spoke
#

I just wished they did NPP and then just integrated it into GAS, CMC etc etc

quasi tide
#

It'd be nice. But the needs of Fortnite win.

#

And Fortnite works fine

#

Remember when Epic made games?

nova wasp
#

Fortnite is multiple games now I guess

fossil spoke
nova wasp
#

a lot of the chaos replication code is due to the needs of lego fortnite etc

fossil spoke
#

With UEFN and how FN is going to be Roblox, I feel like they will need to make things more generic and play nicely together.

summer tide
#

How do you test multiplayer sounds on a single pc? Such as footsteps

verbal ice
#

Spawn multiple clients?

short arrow
#

So no matter which client you're controlling it'll always only return sound from that first client or something like that

#

Its in the settings

north jacinth
#

what's the recommended method, when using chaos for physics networking, to handle weapons that add impulses to other pawns?

north jacinth
chrome bay
#

Having spent a lot of time with both GAS and NPP, IMO they are fundamentally incompatible. NPP is built around the idea that you can save and send the entire state of your system at high frequency. Also rollback/resim for ability logic when it can reach out to any part of your game is incredibly non-trivial.

fallen fossil
#

Should I worry about race condition?
I do have Array and Iiterate it once per second. So its rare, but if some RPC comes and asks one actor to add some element to it.

Does it happen after global tick, before, is it async? πŸ€”

fallen fossil
#

Im just asking how unreal works, I don't have any async setup yet

dark parcel
#

Not sure whats that got to do with rpc

fallen fossil
#

Servers iterates array, and some actor asks to be part of that array, or no longer wants to be there

#

so it breaks

nova wasp
#

async has multiple actual meanings

dark parcel
#

Why would inserting or removing element breaks the game?

nova wasp
#

async can refer to just doing something later, or doing it on another thread

#

in this case it is almost certainly the former

fallen fossil
nova wasp
#

also yeah this question is not possible to understand

#
I do have Array and Iiterate it once per second. So its rare, but if some RPC comes and asks one actor to add some element to it.

Does it happen after global tick, before, is it async
#

what would race here?

dark parcel
#

@fallen fossil just a tip when it comes to networking.

I would say most of the tine like 90% of the time. Client always just request stuff.

Server always hold the truth and the correct data.

nova wasp
#

they are both on the same thread? why would one happening before the other matter?

#

the race would be the order of things not being what you expect, but I don't know why the order here matters at all

fallen fossil
nova wasp
#

what are you doing from a task thread for this? you just said "every second" as if it's a regular timer?

#

unreal doesn't thread random things without you telling it to generally speaking aside from animation graphs

fallen fossil
#

it it regular tick

dark parcel
#

I think if you can provide an actual use case / objective you can get clearer answer.

nova wasp
#

when would that execute on another thread without being marked to do so?

#

you really should just use insights at least once with stat named events on to see when each thing happens

#

it's really important to have a basic understanding of the engine tick flow to see when things happen on the game thread

fallen fossil
nova wasp
#

it's on the main thread

#

before anything ticks rpcs and replicated data are received

#

the order that this happens is of course not so simple but it's on the main thread

#

with networking the race condition issue is mostly in regards to things being split into DIFFERENT PACKETS that do not show up in the same game frame's network channel read

fallen fossil
nova wasp
#

you really REALLY should use insights at least once, please just look at the frame graph

#

it is absurdly powerful to see what happens in the frame. you don't need to understand 100% of what is happening but having a basic understanding will help avoid doubts like this

#

and even if it did happen on another therad you could just add 1 critical section and call it a day lol

#

locking stuff about just 1 variable isn't that tough

#

also to be clear because of rpcs and replication being sent and received on the game thread this means that if your overall FPS is lower the rate of sent/received data will be more spread out as well

fallen fossil
nova wasp
#

because there is more time between sending them

#

when something takes longer to do, the amount of time between doing it over and over increases

#

this generally matters more for data that is something that changes over time, like a player's transform etc

fallen fossil
#

found it

#

;d

nova wasp
#

take note that literally everything you add from normal gameplay code is on the same thread

#

besides maybe some anim graph work etc

fallen fossil
#

found my RPC, pretty neat tool

nova wasp
#

I guess you can try to find the 1 second timer as well but it might need to have a cpuprofiler trace macro or a named event (only visible in traces during stat named events)

fallen fossil
#

but then, again, how would I know if its sending or receiving? πŸ€” , I guess it is only tracing main window?

nova wasp
#

and it goes without saying the actual event must happen while tracing took place

nova wasp
#

is this single process PIE? multiple processes? which network mode?

fallen fossil
#

, Im just asking if its tracing multiple windows πŸ˜„

nova wasp
#

read my message again

fallen fossil
#

pie

nova wasp
#

is this single process PIE or multiple instances?

#

PIE can optionally create multiple processes to have each client be in a distinct program instead of just making multiple worlds tick under one uengine

#

you can also optionally have the different PIE instances tick at different rates to simulate the server hz being like 30 fps etc

fallen fossil
#

okok

#

ok, I got one mroe question, more simple :D, how do I close this middle tab, which highlights my selected timer? πŸ˜„

nova wasp
#

that should be G I think for main graph... I forget lol

fallen fossil
#

yes πŸ˜„

#

thanks

nova wasp
#

the options and keybindings are under the view options and tracks dropdowns

#

be careful because you can accidentally hit C and go into compact mode, just hit C again to undo it

fallen fossil
#

I was there, but checked wrong tab

nova wasp
#

the button for it is here

#

If you see multiple game worlds under Tick_Engine it's running multiple instances in 1 process

#

if you are using multiple processes you will need to trace those processes separately afaik

fallen fossil
#

thats add up

#

πŸ‘Œ πŸ™†β€β™‚οΈ

#

never test performance on single process for more players noted

nova wasp
#

yeah it's kind of impossible to run well with 4 uworlds at once lol... the render time is just too much

#

you can crank down the resolution a lot but you can safely expect it to just be fairly slow

nova wasp
#

r.screenprecentage will let you go above 100% so yes

dark edge
dark edge
#

also hilarious that 10 iterations of a tire model costs less time than reading position and velocity or writing out forces.

#

I don't recall for sure but I think this was for like 512 or 1k tires

nova wasp
#

why not just run it inside of a chaos sim callback if it's going to be right there (some things will be much easier on the main thread that interact with main thread stuff though)

#

if you do a separate read lock for each physics particle of course it's going to be somewhat slow

#

depending on what other threads are doing it might even need to wait on those

dark edge
#

Right now I'm just going through the component velocity and add force api, I'll investigate skipping that and going straight to the source later.

nova wasp
#

I guess you can look at modular vehicles as an example

#

not for how to make vehicles, but how to make them live right inside of chaos

dark edge
#

I'll probably get it to run on chaos sim step but not right now

#

It's incredibly complicated and not necessarily related to chaos so that'll have to be an option

thin stratus
#

Chaos Mover might also be something that shows how to do this, btw.

dark edge
#

Hell yeah, FFastArraySerializer is great. This is after spamming additions and removals of device models in a subsystem with bad network emulation. Order doesn't matter, just that the same IDs map to the same device models in the dense array at the end of the day.

#

ah shit nvm its getting out of sync somewhere

nova wasp
#

what does "out of sync" mean

#

also keep in mind "bad" emulation is beyond the pale

#

5% packet loss is insane

dark edge
# nova wasp what does "out of sync" mean

Final topology on server and client disagree. There's a device model on server that doesn't exist on clients, or vice versa, or mappings from ID to device data aren't aligned

nova wasp
#

what does that mean in fast array terms

#

is an entire element missing? not up to date after a second etc?

#

also make sure to not rely on fast array order

#

fast array order is not meaningful

#

you can use the fast array indexes of each element as a key if you need to

dark edge
#

So here I'm using a fastarray of {ID, Data} and I build a sparse set on either end that maps ID to a packed array Data

#

I think the problem is when addition and removal end up in the same update as a modify

#

Yeah I haven't handled the case where fast additions and removals can result in a PostReplicatedChange as it all gets batched together, gotta handle that

#

I'm basically using a fastarray of {ID, T} to keep this in sync on both ends

template<typename T>
struct TSLMDeviceContainer
{
    FSLMHandle Add(const T& Value)
    {
        const int32 Index = Dense.Add(Value);
        int32 ID;
        if (FreeList.Num() > 0)
        {
            ID = FreeList.Pop();
            IDToIndex[ID] = Index;
        }
        else
        {
            ID = IDToIndex.Add(Index);
        }
        IndexToID.Add(ID);
        return {ID};
    }
    
    void AddWithExplicitHandle(const T& Value, const FSLMHandle ExplicitHandle)
    {
        while (IDToIndex.Num() <= ExplicitHandle.ID)
        {
            IDToIndex.Add(INDEX_NONE);
        }
        if (IDToIndex[ExplicitHandle.ID] != INDEX_NONE)
        {
            Remove(ExplicitHandle);
        }
        FreeList.Remove(ExplicitHandle.ID);
        const int32 Index = Dense.Add(Value);
        IDToIndex[ExplicitHandle.ID] = Index;
        IndexToID.Add(ExplicitHandle.ID);
    }

    bool Remove(const FSLMHandle Handle)
    {
        if (!IsValid(Handle))
        {
            return false;
        }
        
        const int32 ID = Handle.ID;
        const int32 Index = IDToIndex[ID];
        const int32 LastIndex = Dense.Num() - 1;
        
        Dense[Index] = Dense[LastIndex];
        const int32 MovedID = IndexToID[LastIndex];
        IndexToID[Index] = MovedID;
        IDToIndex[MovedID] = Index;
        
        Dense.Pop();
        IndexToID.Pop();
        IDToIndex[ID] = INDEX_NONE;
        FreeList.Add(ID);
        return true;
    }

    bool IsValid(const FSLMHandle Handle) const
    {
        return IDToIndex.IsValidIndex(Handle.ID) && IDToIndex[Handle.ID] != INDEX_NONE;
    }

    T& Get(const FSLMHandle Handle)
    {
        check(IsValid(Handle));
        return Dense[IDToIndex[Handle.ID]];
    }

    const T& Get(const FSLMHandle Handle) const
    {
        check(IsValid(Handle));
        return Dense[IDToIndex[Handle.ID]];
    }

    int32 Num() const
    {
        return Dense.Num();
    }

    TArray<T>::RangedForIteratorType begin()
    {
        return Dense.begin();
    }
    
    TArray<T>::RangedForIteratorType end()
    {
        return Dense.end();
    }
    
    TArray<T>::RangedForConstIteratorType begin() const
    {
        return Dense.begin();
    }
    
    TArray<T>::RangedForConstIteratorType end() const
    {
        return Dense.end();
    }
    
private:
    TArray<T> Dense;
    TArray<int32> IndexToID;
    TArray<int32> IDToIndex;
    TArray<int32> FreeList;
};

I don't have ID versions implemented rn but will add them later probably. Handle just wraps ID right now but will later wrap {ID, Version}

nova wasp
#

removal silently allowing an index none to stick around?

#

if it helps there is a built in struct called FInstanceIdIndexMap now that helps make doing this easier

#

(I don't know if it's fully exported though as it was made for isms)

dark edge
#

The FastArray is staying in sync, just not the thing I'm modifying on its callbacks

chrome bay
#

You can set the ReplicationID of the inner items of FastArray directly. I do that a lot when I want the ID to match something I already have, or if I want to control the ID's myself. Actually a very useful feature

#

FastArray will only modify it if it's the default value of INDEX_NONE - but if you set it before calling MarkItemDirty, it won't do anything to it

#

No need to maintain your own mappings then, it becomes native. Gives you a way to persistently ID things

#

(so long as you don't need an INDEX_NONE ID)

fallen fossil
#

Server must spawn actors for them to be replicated to clients.

So my simple question is, spawning anything via RPC on client will have different Pointers and it won't replicate right? each copy will be local.

chrome bay
#

Replicated objects will resolve to the local object on the local machine

#

The object either needs to be net-addressable (resolvable by name, like objects in the map) or replicated down from the Server

dark edge
#

oh shit yeah that's actually useful I think.

dark edge
nova wasp
#

A really common thing to do is have replicated data on one object create other objects locally. This is good because you can keep the raw replicated data super simple but have a complex actor locally to mess with

#

For example equipping a gun could spawn the gun actor (only locally) while it's just from an onrep of a struct or a fast array being added/removed

#

so you keep the benefits of a nice visual actor but without the extra overhead and complexity of a new replicated object

dark edge
halcyon ore
#

I'm unsure wether to post this in #packaging or not.
Given I feel like it must be some tiny checkbox, or like config entry...

How do you setup your dedicated steam server, to not require the full steam client to be installed?

(If I install the steam client and login, my server works fine
(If I don't have it installed, or uninstall it, then the server throws some generic steam, subsystem errors, that says it has no appid)

slate phoenix
#

Hello everyone, I’ve been thinking about this for the past 3 hours:
Should inventory slots and hotbar slots remain separate, or should the hotbar be derived directly from the inventory?

If I make the hotbar a separate slot system, I’ll need to create a separate table for it in MySQL. I’m not sure whether that’s a good or bad design choice.
If I don’t separate them, I’ll just use a single table instead of two.

Which approach do you think is better: a separate slot system or a unified one?

fossil spoke
#

Logically I would think they are part of the same inventory system.

slate phoenix
dark edge
#

Is something in your backpack and on your hotbar, or is the hotbar like its own container?

chrome bay
# dark edge Do you know if there's a way to access the before value in PostReplicatedChange?

Sadly no πŸ™ It is kind of possible but you'd have to reimplement the fast array replication to get the base delta state before it serializes, you could mayyyyybe do that in NetDeltaSerialize but I've not tried tbh..

When you say the inner items, you mean the array? The array uses RemoveSwap during serialize so there won't be gaps in it when items are removed etc.

dark edge
#

RIght now I have a fastarray that is used as the replicated state to keep a derived data struct in sync on either end

chrome bay
#

Yeah it won't have gaps or anything, item order isn't preserved though, could be different between server/clients etc.

#

the main thing is adds/removes/changes are bound to the ReplicationID - so if you remove an item with a replication ID, then add a new one with the same replication ID on Server, that's detected as a 'change' on the client not a distinct remove/add.

#

And generally you wanna be careful reusing ID's because the other properties 'ArrayReplicationKey' and 'ReplicationKey' may need to be incremented to ensure it replicates too

dark edge
#

Basically I hand out handles to things, the core container looks like this:

template<typename T>
struct TSLMDeviceContainer
{
    FSLMHandle Add(const T& Value)
    {
        const int32 Index = Dense.Add(Value);
        int32 ID;
        if (FreeList.Num() > 0)
        {
            ID = FreeList.Pop();
            IDToIndex[ID] = Index;
        }
        else
        {
            ID = IDToIndex.Add(Index);
        }
        IndexToID.Add(ID);
        return {ID};
    }
    
    void AddWithExplicitHandle(const T& Value, const FSLMHandle ExplicitHandle)
    {
        while (IDToIndex.Num() <= ExplicitHandle.ID)
        {
            IDToIndex.Add(INDEX_NONE);
        }
        if (IDToIndex[ExplicitHandle.ID] != INDEX_NONE)
        {
            Remove(ExplicitHandle);
        }
        FreeList.Remove(ExplicitHandle.ID);
        const int32 Index = Dense.Add(Value);
        IDToIndex[ExplicitHandle.ID] = Index;
        IndexToID.Add(ExplicitHandle.ID);
    }

    bool Remove(const FSLMHandle Handle)
    {
        if (!IsValid(Handle))
        {
            return false;
        }
        
        const int32 ID = Handle.ID;
        const int32 Index = IDToIndex[ID];
        const int32 LastIndex = Dense.Num() - 1;
        
        Dense[Index] = Dense[LastIndex];
        const int32 MovedID = IndexToID[LastIndex];
        IndexToID[Index] = MovedID;
        IDToIndex[MovedID] = Index;
        
        Dense.Pop();
        IndexToID.Pop();
        IDToIndex[ID] = INDEX_NONE;
        FreeList.Add(ID);
        return true;
    }

    bool IsValid(const FSLMHandle Handle) const
    {
        return IDToIndex.IsValidIndex(Handle.ID) && IDToIndex[Handle.ID] != INDEX_NONE;
    }

    T& Get(const FSLMHandle Handle)
    {
        check(IsValid(Handle));
        return Dense[IDToIndex[Handle.ID]];
    }

    const T& Get(const FSLMHandle Handle) const
    {
        check(IsValid(Handle));
        return Dense[IDToIndex[Handle.ID]];
    }

    int32 Num() const
    {
        return Dense.Num();
    }

    TArray<T>::RangedForIteratorType begin()
    {
        return Dense.begin();
    }
    
    TArray<T>::RangedForIteratorType end()
    {
        return Dense.end();
    }
    
    TArray<T>::RangedForConstIteratorType begin() const
    {
        return Dense.begin();
    }
    
    TArray<T>::RangedForConstIteratorType end() const
    {
        return Dense.end();
    }
    
    const TArray<T>& GetDense() const
    {
        return Dense;
    }
    
    const TArray<int32>& GetIndexToID() const
    {
        return IndexToID;
    }
    
    const TArray<int32>& GetIDToIndex() const
    {
        return IDToIndex;
    }
    
    const TArray<int32>& GetFreeList() const
    {
        return FreeList;
    }
    
private:
    TArray<T> Dense;
    TArray<int32> IndexToID;
    TArray<int32> IDToIndex;
    TArray<int32> FreeList;
};

The Fastarray is just an array of {ID, Data} pairs.

dark edge
chrome bay
#

You have any UObject refs in there or anything? Could be getting changes flagged as UObject GUID's are resolved

#

Works the same way as OnReps in that regard

dark edge
#

Basically i have a fastarray of {ID,Data} which is used to sync a sparse set on either end.

dark edge
#

I think it's a networking race condition that gets bundled up and called a change

chrome bay
#

Yeah, could be multiple packets combining or something. Would be strange though if you aren't changing ReplicationID yourself and just adding/removing elements

#

Normally ReplicationID is just an incrementing counter

#

Also you're not adding/removing items client side by accident or anything?

dark edge
#

This is what it looks like when it happens. Red is serverside logging before adding/removing from fastarray

chrome bay
#

Ahh I see, so ordering issue

dark edge
#

Nope all I'm doing is adding/removing from fastarray on server and recieving callbacks

#

ID xx is my id, replication ID is from fastarray

chrome bay
#

hmm yeah ID 6 getting a postrepchange is unexpected

#

Oh, unless fast array also flags items that moved in the array as changed.. but I don't think it does

dark edge
#

It's rare and my removal test function just removes a random element, you'd think I'd see it all the time if that was the case

#

I'll check if I can just treat postrepchange as an add if not existing and call it a day.

nova wasp
#

what is the top level of the engine callstack that actually calls change

dark edge
#

Played StepMania for a bit with add/remove commands and got the desync. Yeah it looks like client always misses something, it must be an add masquerading as a change.

nova wasp
#

huh, that is kinda freaky that it misses the add

#

I'm not sure if that is actually getting missed

#

or if you are expecting an intermediate value of a replicated property to arrive on a client or what

nova wasp
#

I still don't know why IsValid(Handle) just early outs on a dead entry that is index_none

#

that is your code

#

that should hard ensure

#

that is not a nice thing to happen

dark edge
#

Change gets called all the time but a change with indices to work with is what we're talking about.

dark edge
nova wasp
#

so they can just desync on their own? oh

dark edge
#

Just like timer, you can hold a timer handle beyond the lifespan of the timer it maps to

nova wasp
#

but that is not tied to replicating data

#

this is not the same thing

#

what happens if they just yeet a real entry from the server?

dark edge
#

I'll later version handles, or I can just monotonically increment the IDs

nova wasp
#

having a way they can tearoff a handle might be useful to keep it around if that makes sense but imo it's easier to just have a separate local only container

dark edge
#

The handle is how you get sim state, the sim lives in this opaque system. All you have publicly is basically a CRUD interface

chrome bay
#

Only other thing I can think of is if the client is the server/client sorting the array client-side or something, causing the internal ItemMap fast array keeps to be out of sync.

#

But doesn't sound like you're doing that

#

Be worth logging which ReplicationID's get added/removed server side too

nova wasp
#

could enable LogNetFastTArray to use log or verbose

#

that way it would log the reason for each changed indice

#

you can see there is a path that a new element is a changed indice

chrome bay
#

The other thing is that removes are always processed befored adds - so that second bit of client logging is two different updates

nova wasp
#

this kind of logging is easier if you add a framecounter imo

#

but the default log might have that already with a timestamp

#

for example BuildChangedAndDeletedBuffers

#

new elements are changed indices

#

at least in that path

#

this is indeed pretty annoying to follow but it's not impossible

chrome bay
#

yeah, probably need to log the hell out of it to figure it out. I mean personally at least I've not yet had a fast array that desync'd because of high frequency updates etc, but obviously updates do get "missed"

nova wasp
#

LogNetFastTArray

#

there are already logs

#

there is no need for new logs

#

you just need to turn them on with a console command

chrome bay
#

ye

nova wasp
#

it might be weird if there are other fast arrays active at the same time though

#

I'll admit I'm 50/50 on how I feel about the added elements marked as changed

#

I think skipping an added callback is nasty either way... that is super unexpected to me

#

I guess if all you have to do is just have a fallback in changed it's not that bad but still... I feel like that's kind of breaking the contract

dark edge
#

I'm testing the lognetfasttarray rn

#

So here's a write with a numchanged

FastArrayDeltaSerialize_DeltaSerializeStruct for SLMFastArrayItemSimpleGearbox. SLMFastArrayItemSimpleGearbox. Writing
LogNetFastTArray: Current: 30 [12/0], [14/0], [15/0], [16/0], [17/0], [18/0], 
LogNetFastTArray: Client: 29 [12/0], [14/0], [15/0], [16/0], [17/0], 
LogNetFastTArray: NetSerializeItemDeltaFast: FastArray. DeleteCount: -1
LogNetFastTArray:     Array[0] - ID 12. CL 0.
LogNetFastTArray:        Stayed The Same - Skipping
LogNetFastTArray:     Array[1] - ID 14. CL 0.
LogNetFastTArray:        Stayed The Same - Skipping
LogNetFastTArray:     Array[2] - ID 15. CL 0.
LogNetFastTArray:        Stayed The Same - Skipping
LogNetFastTArray:     Array[3] - ID 16. CL 0.
LogNetFastTArray:        Stayed The Same - Skipping
LogNetFastTArray:     Array[4] - ID 17. CL 0.
LogNetFastTArray:        Stayed The Same - Skipping
LogNetFastTArray:     Array[5] - ID 18. CL 0.
LogNetFastTArray:        New! Element ID: 18. 
LogNetFastTArray:    Writing Bunch. NumChange: 1. NumDel: 0 [30/29]
#

might be an add tho, lemme find a read with a numchanged

nova wasp
#

so they just mark the changed elements and if they are added it just decides that later?

#

I guess why not if it's fast to check

dark edge
#

OK i found this on the reading end, big chunk of changes, i'll try find the writing end

#
LogNetFastTArray: FastArrayDeltaSerialize_DeltaSerializeStruct for SLMFastArrayItemSimpleGearbox. SLMFastArrayItemSimpleGearbox. Reading
LogNetFastTArray: Received [65/57].
LogNetFastTArray: Read NumChanged: 5 NumDeletes: 1.
LogNetFastTArray:    Adding ElementID: 15 for deletion
LogNetFastTArray:    Changed. ID: 34 -> Idx: 9
LogNetFastTArray:    Changed. ID: 35 -> Idx: 10
LogNetFastTArray:    Changed. ID: 36 -> Idx: 11
LogNetFastTArray:    Changed. ID: 37 -> Idx: 12
LogNetFastTArray:    Changed. ID: 38 -> Idx: 13
LogNetFastTArray: Adding implicit delete for ElementID: 39. MostRecentArrayReplicationKey: 64. Current Payload: [65/57]
LogTemp: Warning: PreReplicatedRemove ID 4 at index 4 with replication ID 15
LogTemp: Warning: PreReplicatedRemove ID 13 at index 14 with replication ID 39
LogTemp: Warning: PostReplicatedChange ID 4 at index 9 with replication ID 34
LogTemp: Warning: PostReplicatedChange ID 9 at index 10 with replication ID 35
LogTemp: Warning: PostReplicatedChange ID 10 at index 11 with replication ID 36
LogTemp: Warning: PostReplicatedChange ID 11 at index 12 with replication ID 37
LogTemp: Warning: PostReplicatedChange ID 12 at index 13 with replication ID 38
LogNetFastTArray:    Deleting: 14
LogNetFastTArray:    Deleting: 4
LogNetFastTArray: FastArrayDeltaSerialize: Recreating Items map. Struct: SLMFastArrayItemSimpleGearbox, Items.Num: 13 Map.Num: 0
LogNetFastTArray: FastArrayDeltaSerialize_DeltaSerializeStruct for SLMFastArrayItemSimpleGearbox. SLMFastArrayItemSimpleGearbox. GatherGuidReferences
nova wasp
#

I wonder what 65/57 means here

#

ah it's ArrayReplicationKey vs BaseReplicationKey which I assume is the delta baseline

dark edge
#

Anyway if anything about this approach seems baffling this might help.
I think I can get away with detecting when a "change" is really a funky add. As long as the derived high freq state lines up on either end it's fine.

nova wasp
#

those separate arrows are going to introduce some fun race conditions (not to say this is poorly thought out, I just think it's inevitable here... you would probably not get away with fitting the whole thing in 1 atomic thing either way)

#

you might need an incrementing change generation id

#

unless state showing up before the handle is okay and vice versa

dark edge
#

"What's the RPM of the engine for this widget?"
"IDK the engine ain't here yet, so 0 I suppose?"

nova wasp
#

it might be kind of nasty to have a partial incomplete state in some cases but you can only really find out by triyng it I suppose

#

mostly when new stuff appears but it might be fine

dark edge
#

It's the same thing as replicated actor vs a replicated pointer to it really

#

You got the thing, then references to it in some way which can be held by various consumers

verbal field
#

Hello, create widget is returning unkown on client, I'm doing this on BeginPlay on a "Character" based blueprint, any one knows why?

exotic wasp
verbal field
exotic wasp
#

Because if this actor is replicated, a client won't have authority

#

And it seems like you're missing the owning player input

verbal field
sinful tree
dark parcel
#

Begin play is too early, most likely it will always just spawn on server since the character isn't owned yet by the client at Begin Play.

#

@verbal field Begin play would not be the right place to setup U.I most of the time. Also if you are planning to have one radar per player, you should use IsLocallyControlled,
otherwise you get duplicates.

verbal field
sinful tree
# verbal field I'm assigning the widget to a variable, but the client player will have the vari...

Widgets aren't replicated.
Creating a widget on Begin Play of a Character blueprint means that every single instance of the game will end up creating their own copy of that widget for every single Character.

So if you and I are in a game, Begin Play will fire on my end for my character and for your character. On your end, it'll fire for your character and my character. That's 4 instances of a character and each has their own widget being created.

#

Your problem may be that it's coming up invalid because you're attempting to access it on the server (if you're running as dedicated server)

sinful tree
# verbal field

Widgets don't replicate, so setting w/Notify does nothing.

verbal field
#

when a client validates it on the same Caharcter it shows null half of the times

dark parcel
#

it's utterly pointless, widget don't replicate.

#

a machine need to create it's own widget on it's own.

#

Replication in object means that when a server create the object, clients will also get a copy.

#

when it comes to widget, widget does not replicate.

viscid geyser
#

I know Mover has better replication and network prediction out of the box compared to cmc, can I for example have a pawn with two separate collision capsule components properly replicated and network predicted without having to modify any of the components through cpp?

verbal field
dark parcel
#

and afterall it doesn't replicate, so it's irrelevant.

#

You need to ensure that the create widget node is executed in target machines.

#

and I repeat, BEGIN PLAY is the WRONG place if you required to have the U.I in client.

verbal field
#

Thanks

dark parcel
# verbal field Thanks

perhaps you can show us the visual of your widget. Hard to give pointer without knowing the objective.

verbal field
#

The widget is irrelevant, I have multiple widgets with the same problem, all I need is to save each players individual widgets into variables to call them in gameplay

dark parcel
#

the problem is you may unintentionally get duplicates if you don't know how to filter net code.

#

for example if you spawn at begin play of character without filter. If there are 4 players, your Player 2 will end up with 4 radars when the intention was just to spawn one.

dark parcel
#

I don't know what event you can hook into in blueprint though... I use AcknowledgePossession to setup my U.I on client.

#

may able to do reliable client RPC after server Possess but not sure if that's 100% reliable.

#

can maybe do on the OnRep_PlayerState but it sound nasty.

nova wasp
#

OnRep_PlayerState would be helpful if they need to be aware of the playerstate set locally

#

which is often the case, so that's not a bad idea at all

#

if it needs to read and bind to properties from the playerstate etc

#

In this case it might be useful to use something like ReceivePossess on the controller or pawn

#

that way you can see when it's a local player controller and keep the logic relevant to the pawn

#

ah wait, that's server only

#

I've been away from stuff like this too long... I think the playerstate's OnPawnSet would work okay

willow adder
#

Server get loaded Character from Cleint(Super), but Client not get loaded Character form Server, i try everything but no success i am near it must be a small fix for this?

dark parcel
#

Are you the person that ask about "loading" save file in multiplayer game?

willow adder
#

Yes Coldsummer

dark parcel
#

As client, you load the save data then you send the data to server.

Server then set the replicated variable and replicate it to all client. Its as simple as that.

For example you have a save file in the client machine to dictate hair color.

As client, load the save data then send that FColor data to server via server RPC.

Server then set the hair color (replicated). Client will get the update via OnRep -> set hair color.

dark parcel
#

need to see more code

willow adder
#

Because it is MP and i can only see the Result if it is working when i package to Steam and test on 2 Machiene this make things more Time Consuming and complicated( like Matt Botswain says here: MP is not a walk in a Park πŸ˜‚ for sure)

dark parcel
#

@willow adder You can test by making dummy data too instead of loading from save file.

#

the point here is that as client, you need to send data for the server to acknowledge and replicate.

#

Where the data is pulled from, e.g from code or save file. It doesn't really matter in the context of testing.

#

having to package everytime you want to test functionality is a pain.

willow adder
dark parcel
#

so the save file, where does it exist?

#

wdym by Server Save File

#

I thought the client store their own .sav in your project

willow adder
#

when i start Steam as you know Matchmaking Listener Server 1 gets the Server and 1 the Client both have its own Local Save

#

Even if i Switch from my Alt Pc and Back the same Result

willow adder
dark parcel
#

Can you show the code again, where you have the IsServer branch

#

where is it called.

dark parcel
#

what event is called prior to this branch

willow adder
#

Begin Play

#

With a 3 Sec Delay

dark parcel
#

lol

#

that's not ideal, if your player have high latency the game will break.

#

I haven't seen your loading code yet, did you send the data to the server as client?

willow adder
dark parcel
#

try to do this in
OnRep_PlayerState->IsLocallyControlled->Switch Has Authority -> Load SaveGameFile -> Set things
-> Client -> Load SaveGame File -> Server RPC (Data) -> Set replicated things.

willow adder
#

Did i must Cast to MainChar or to that Component

dark parcel
#

when the Playerstate is replicated. You need to know these objects, they are crucial in MP.

Game Mode, Game State, Player Controller, and Player State.

heady nacelle
#

Hi! I ran into a problem that makes me wanna pull out my hair and thought maybe I'm missing something very obvious that someone can point out.

The following code is being called on some players from the game mode, the problem happens only on the joined clients and not on the hosting player:

In example 1: I print the value of pos (1000, 0, 40), the client moves nowhere.

In example 2: I hardcode the exact same value as in the other example and the client moves to that spot.

Why does it behave differently by passing in a vector even though the value is exactly the same?? πŸ₯²

short arrow
heady nacelle
short arrow
formal path
#

so if you print the value of the vector it's printing a correct value on both client & server or whereever you need it ?

heady nacelle
formal path
#

it sounds like the value might not be replicated to all clients ?

#

since you said its only an issue for connecting clients

#

print everything

heady nacelle
short arrow
#

Is this in your character class?

heady nacelle
short arrow
heady nacelle
short arrow
#

and can you also show how you are setting the array

short arrow
#

where are you setting the replicated array

heady nacelle
short arrow
# heady nacelle

All of this seems right, are you making sure the variable is being set before calling the MoveToMinigameArea event?

#

it's a really interesting way of doing it but the code doesn't raise any flags, I'm guessing it's a race condition

#

make sure you're only calling MoveToMinigameArea event after the vector array has been set

#

to test if this is the problem you can add a 1 or 2 second delay before calling MoveToMinigameArea

heady nacelle
#

yea I'll do some more tests before I try something else

short arrow
#

The thing is it looks like clients are calling an RPC to the server to set the vector location array, that can cause a race condition

#

It explains why it works fine on the server but not the others. I bet SetActorLocation isn't being reached

short arrow
surreal hornet
#

I created a custom phy function that generally replicates phys walking and pushes the character at a certain speed and than i play a montage ontop of. This has been working really well and will replace this instead of using root motion to fix all the corrections for networking. I have created animation cancel notifiers for each montage to cancel into other montages. Now the issue i am facing is as sim proxies the distance and speed traveled is fine but at higher ping the animations don't match up and if you were to spam dodge roll animations for example it will cut the animations due to high ping. I am wondering what would be the best solution to resolve this? This is due to server rpc delay issues and wondering what can I do to have it where for sim proxies their animations play in order and don't look like they are cutting off completely.

nova wasp
#

is a server rpc what makes the sim proxies animate?

#

sim proxy characters are almost entirely just some onreps and local interpolation/extrapolation + some local sim

surreal hornet
#

Sorry if i confused you but basically I play a montage locally and than right after a server rpc call with a multi cast

nova wasp
#

in that case it's entirely random when it will show up more or less

#

relative to other properties

#

is it reliable or unreliable?

surreal hornet
#

Reliable

nova wasp
#

for this kind of thing it's really context specific and to make it "perfect" might involve buffering things or sending timestamps etc

#

I can't tell what is actually being sent or received or skipped

surreal hornet
#

Just montages

#

Thats all with no root motion or anything

nova wasp
#

that's not descriptive of what is happening here

#

the montage is a "roll anymation"

#

is it playing with root motion? does it just follow the player moving?

#

oh okay no root motion

#

also FWIW network emulation will make for some bad situations that are rarely going to happen in a real game... if you are testing with 1 second of ping and 5% packet loss of course it will be nasty pretty much no matter what

surreal hornet
#

Yeah i have a custom phy function that drives the chatacter. Im just playing an animation ontop. My issue isnt with corrections or moving the chatacter that all works really well. Just that the animations themselves are not playing as clean in higher ping.

kindred widget
surreal hornet
nova wasp
#

in order to make it perfect 1:1 with the OTHER replicated properties IMO the only thing you can really do is have the onrep that triggers sim proxy movement include the information about the roll... this requires C++ but I imagine you could probably cheese this in bp somehow
you don't need to do this but otherwise properties/rpcs will always have a chance of showing up on different frames from the normal transform replication

#

and yeah is this listen server etc?

surreal hornet
#

Host and other clients

nova wasp
#

listen servers only update their cmc's animations when an rpc is received with a new saved move (to support root motion) and disabling this behaviour might involve some C++ or just having a second mesh on top of the normal one

dark parcel
#

So are you saying the clients see the animation jaggy too?

#

because those artifact normally visually visible on listen server only for the reason Megafunk said above.

kindred widget
#

There's a boolean that disables it I recall.

#

Had it in RS2's lobby. πŸ˜„

dark parcel
#
GetMesh()->bOnlyAllowAutonomousTickPose = true;

this one?

kindred widget
#

Looks familiar.

dark parcel
#

hmm actually he said the montage is clunky, not the normal anim?

nova wasp
#

yeah fwiw this person seems to be seeing this on clients as well

#

but that listen server thing is still worth pointing out

dark parcel
#

yeah that may not be the case then.

#

My montage playing pretty bad when I use GAS to do it under high ping.

#

haven't test in packaged yet but that's the behavior on editor.

nova wasp
#

GAS montage replication is just an onrep that sends timing and section info with some error margin

dark parcel
#

Yeah, it kinda skips some of the time.

surreal hornet
#

Oh no that is something else i already did that. Im not talking about if host sees it like skipping. Im talking about animations at higher ping cutting off.

More of i want the animation to be more in sync with the movement.

Sorry when I come home I can give more details had to head out somewhere. I can show video examples of what I am talking about.

nova wasp
#

in order to get perfect timing for a series of montages that aren't locally following you might need to simulate the work locally but this is probably just 1 montage for rolling

nova wasp
#

is it starting too late and getting overwritten? is it starting too soon and getting stopped?

#

oh okay yeah videos would help

#

all good

surreal hornet
nova wasp
#

but yeah either way I think my personal favorite way would be with a custom onrep for your cmc that replaces onrep replicated transform... this will involve some c++ but it is pretty much the most complete way to remove this problem

#

if 1-frame offsets cause jitter from separate properties/rpcs arriving at random times it can help

brave yew
#

Going with this, how would i work with a root motion animation for a dodge? Using RPC I have gotten it to look perfect on other clients but the owning client has huge jitter

#

Same goes for a quick and dirty running code i made in blueprints, which will be easy enough to add to the CMC, but i think they seem from the same issue

#

I can also make it relatively smooth by playing the animation on the client and the server, but then the other clients fail to see it

dark parcel
#

are you using montage? If you do, you shouldn't get jitter.

surreal hornet
#

Sorry about the delay I was with family but here is the video @nova wasp

i am testing around 400 ping with like 5 percent packet loss.

so the window on the right side is the client i am controlling. On that side everything is playing fine and no corrections. My issue is what it looks like to others. Becuase of the rpc delay time if i keep spaming attacks it gets cut off. I know these conditions are not realistic and wont happen but I only did this to stress test and show clearly the issue i am having. I asked claude on solutions and it talked about some sort of queuing while multi casting and stuff and dont know if that is the best possible solution and was hoping if there is a better way to handle this.

thin stratus
surreal hornet
# thin stratus Just in general I would not test with package loss, especially not that high val...

it plays and looks fine at around that ping with some occasional animation getting cut off like in the video. I know that those values arent realistic but i set those values to show more of what I am talking about. I am handling rotation and speed using custom cmc code with safe and saved and compressed bools. Issue is i am playing montages with an rpc ontop of those movements. so movement is being handled perfectly fine just animations lag behind.

nova wasp
#

you might need to get into predicting them continuing to attack if you really really can't accept missing one animation

#

I feel like the 5% packet loss case even for demonstration here is too extreme

surreal hornet
nova wasp
#

the actual real life ping values

#

one friend with bad internet hovering around 200 ping

#

I am going to venture a guess that their loss did not exceed 1%

#

even 1% is absurdly high imo

surreal hornet
#

oh really??!?! why the hell am i testing with 10 percent and stuff loool

nova wasp
#

the "bad" settings are to see if the game even works under the worst case scenario

#

not to compare with just "bad internet"

surreal hornet
#

Oh I guess i spent alot of time on this when it wasnt as bad as i thought lol.

nova wasp
#

it's worth trying out just to see if something outright breaks with it on I suppose

#

for example someone could have their internet cut out for like a split second or something... shit happens

surreal hornet
#

on the bright side I did improve my netcode alot and testing with my friend really proved how solid it is so it wasnt a waste.

surreal hornet
brave yew
dark parcel
brave yew
#

Sure! 1 sec

#

Which of the 3 I mentioned?

dark parcel
#

anything related to playing the montage and the network emulation settings.

dark parcel
#

I don't think you can expect to have something look allright with packet lost

#

5% is extremly bad too.

#

even 2% is too much already.

nova wasp
#

yeah I am starting to think they need a really big caveat there

#

5% packet loss is ABSURD

#

that preset is not just a "bad" connection... it is the worst case

dark parcel
#

1% packet lost in dota and i just stop playing.

brave yew
#

this works almost flawlessly on the client but other clients don't see the anim

#

this works almost flawlessly on other clients but there is jitter on the character

nova wasp
#

what does "there is jitter on the character" mean

#

what actual data is representing the jitter?

brave yew
#

i can show you

nova wasp
#

that looks like a movement correction

dark parcel
#

yup, looks like movement correction.

brave yew
dark parcel
#

what's the command again to visualize correction?

nova wasp
#

p.NetVisualizeSimulatedCorrections iirc

#

ah yeah p.NetShowCorrections is more correct

dark parcel
#

but you never play it on the other clients.

nova wasp
#

but yeah the first one is simply missing something replicating it down to clients

dark parcel
brave yew
#

nvm actually

dark parcel
#

with this picture, 100% input delay.

brave yew
#

you were refering to that one

#

my bad

nova wasp
#

also if this is a co-op game as always I would say consider turning off network corrections entirely... you do not need to suffer the madness of extending the cmc correctly that way

dark parcel
#

the first one you are predicting but you are only playing on the calling machine + the server.

dark parcel
#

you never tell other client to play the anim.

brave yew
#

that's the part I am lost at

nova wasp
#

you literally do so in the second picture?

dark parcel
#

try this. But I don't know if this cover all edge cases.

Personally I use GAS play Montage and Wait.

brave yew
dark parcel
brave yew
dark parcel
#

MC_Roll -> If Is NOT locally Controlled -> Play Montage

brave yew
nova wasp
#

you could also consider sending it is an onrep of a value but that would involve dealing with some math to prevent timing issues and incrementing it etc

dark parcel
#

@nova wasp So corrections are driving me crazy too. It's been constant ongoing battle.

#

like just bumping into another player already cause unwanted correction.

#

I can just turn it off, but would there be a lot of margin of error as the time goes by?

nova wasp
#

well, bumping into another player sucks for corrections because the cmc only thinks about itself for the most part

dark parcel
#

like off by 200 units for example.

brave yew
nova wasp
#

the margin of error would only exist if the server never ever accepted the state but only the input (in a way that diverges)

#

the server does accept the state though afaik

dark parcel
nova wasp
#

GAS PlayMontage is 100% just an onrep of the montage and some timing

#

it is really really simple and they kind of make it look fancier than it really is

#

it's not some magic external thing either, the onrep exists right on the GAS component

#

the task exists mainly to hold callbacks and keep the replicated property updating until the montage is over

#

that said yes it is quite effective at what it does

#

it's not good enough for things sensitive to frame-by-frame timings but it's great for most things

#

I guess the montage slot timing and the serialization is somewhat fancier than just a basic onrep but I guess it's just... not doing much beyond sending a montage and a time

#

the best thing about it is that it's stateful in a way that late-joiners will resolve state and relevancy pop-ins will fix themselves

#

but 90% of game anims like montages are so short it's not that important

#

(also I just wanted to say that game environment looks neat... I like the style)

heady nacelle
brave yew
short arrow
nova wasp
# brave yew How??

it involves a variety of cvar settings including AGameNetworkManager::ClientAuthorativePosition

;defaultgame ini:
[/Script/Engine.GameNetworkManager]
ClientAuthorativePosition=true
brave yew
#

If you start flying all over the place? Sure, yer a wizard now

nova wasp
#

you can also get away with accepting client positions temporarily which can be helpful if you just have certain situations that are difficult for the server/client to agree on

dark parcel
#

that was the advise given though when doing something "fast". πŸ€”

heady nacelle
tardy fossil
#

hmmm i got the strangest issue after switching to Iris... after a good amount of actors have been spawned/destroyed, a random actor being spawned will just not replicate anything (other than its initial data, so no replicated vars or RPC's) and the ONLY hint i get in the logs is:

LogActor: Warning: AActor::PostNetInit InteriorShape_0 Remoterole: 0

this is gonna be fun to track down 😭 although while writing this i notice the name of the actor is _0 and its definitely NOT the first InteriorShape actor that has been spawned

hybrid zodiac
#

Hi everyone. For seamless travel I believe the process will destroy all actors like game mode, game state, player state etc, create new ones and allow you to copy over some properties from the old to the new.

Is the sequence in which these actors are replaced guaranteed? For example, can I guarantee that when the player state's CopyProperties or BeginPlay functions are called, the new game mode is already active, or is it uncertain?

dark lance
#

Hi everyone, hope you’re all doing well.
I’m running into a replication issue with head movement and would really appreciate some advice.
I’m trying to replicate head rotation (offset) so players can see each other’s head movement in multiplayer.

Current issue;
The Main PC (Listen Server) can see the Client’s head movement.
But the Client cannot see the Main PC’s head movement.

Important details:
The head movement logic is inside the Animation Blueprint.
I’m using control rotation to drive a spine/head offset.
Jumping and other movement replicate correctly.
The rotation is being calculated locally in the AnimBP.
Has anyone run into this before

dark parcel
#

@dark lance where is this?

dark lance
dark parcel
#

so no point making a replicated variable in your anim bp.

dark lance
mystic estuary
dark parcel
#

If the head points where the player is looking at, then just use GetBaseAimRotation.

#

or is it GetAimRotation 0o?

mystic estuary
#

Not sure

#

πŸ™Œ

dark parcel
#
void AAGPlayerCharacter::AimOffset(float DeltaTime)
{
    if (IsLocallyControlled())
        AO_Pitch = GetBaseAimRotation().Pitch;
    
    /** Gets proxies characters in server that server don't control. */
    if (GetBaseAimRotation().Pitch > 90.f && !IsLocallyControlled())
    {
        /** map pitch from [270, 360] to [-90, 0] because of compression */
        const FVector2D InRange(270.f, 360.f);
        const FVector2d OutRange(-90.f, 0.f);
        float L_AO_Pitch = FMath::GetMappedRangeValueClamped(InRange, OutRange, GetBaseAimRotation().Pitch);
        AO_Pitch = FMath::FInterpTo(AO_Pitch, L_AO_Pitch, DeltaTime, 15.0f);
    }
    else
    {
        AO_Pitch = FMath::FInterpTo(AO_Pitch, GetBaseAimRotation().Pitch, DeltaTime, 15.0f);
    }
}
#

remapping bonus because iirc, the pitch value is optimized.

dark lance
#

wow okay thank you @mystic estuary @dark parcel I will try this and let you know thank you for the help appreciate it

dark lance
#

I’ve got the pitch (up/down) working on both client and server. However, when the server (main PC) looks left/right (yaw), the client doesn’t see that yaw movement. Any ideas why yaw isn’t showing on the client side

#

I did use Get base aim rotation and it worked

slow wing
#

Is there a "best practice" way to delete default subobjects only on the server?

mystic estuary
# dark lance I’ve got the pitch (up/down) working on both client and server. However, when th...

Looking at your footage it appears that your character capsule isn't actually rotating when you're looking left/right slightly. GetAimRotation predicts the yaw based on capsule rotation replicated by CMC.

In this case you would need to replicate yaw manually. Simply create a replicated variable that you update on the server using server RPC on tick, and use that to replace base aim rotation yaw

grand kestrel
#

There's never any need to replicate anything extra for aim offsets

#

@dark lance on simulated proxy you'll want to add interpolation to your aim offset because it's byte compressed, it'll look jerky without it

tame kraken
#

hey, did anyone encounter this issue where the charactermovementcomponent's smoothing doesn't work in the listen server compared to the dedicated server?

#

i did this test side by side with network emulation
in the listen server i get the correction debugs and the experience is bad, like if there is no smoothing
while in the dedicated server, i also get the correction debugs, but it's much smoother like the system is actually working

grand kestrel
#

There is no extrapolation on listen server, epic confirmed via udn, and suggested attempting to implement it manually the same way they do for sim proxy. Never tried it myself nor was any outcome posted

#

Epic don't care about listen server and haven't since 2014

#

Fortnite doesn't need it

grand kestrel
nova wasp
#

it also only ticks their skm animations by default when a new rpc is received (mostly to try to resimulate root motion afaik)

grand kestrel
#

In case it's not clear, it's used for mesh smoothing

tardy fossil
#

has anyone used filtering classes for Iris? is there any way to get the internal index that the filter class uses from a FNetHandle? from what I can see from source the main way is through FNetRefHandleManager but that is completely private...

tardy fossil
#

oh the UNetObjectFilter class has a GetObjectIndex() function

halcyon ore
#

When you find out the game state isn't always replicated/ ready for use
I know it has to be networked, but I assumed given its a core actor, it would be forced to be first or something

willow adder
tardy fossil
verbal ice
#

If that helps

#

Simply because the game state is the one that routes begin play.

runic lily
#

Anyone got any tips for reducing RAM usage in editor, so that it's easier to launch multiple editor instances?

formal path
#

dont have any levels open / open an empty level is the only thing you can probably do

tardy fossil
verbal ice
#

They change the API a lot

meager spade
halcyon ore
verbal ice
#

no

#

For RPCs it's the owning connection yes but the PC doesn't handle the low level networking stuff

halcyon ore
verbal ice
#

the game state routes begin play so you quite literally cannot have a begin play call without it being available

halcyon ore
verbal ice
#

However rep notifies can call before begin play, that might be your problem

halcyon ore
#

Yeah.
But at least for this test on rep shouldn’t be an issue.

Has me curious if I did something weird without realizing.

tardy fossil
meager spade
tardy fossil
# meager spade anyone? πŸ˜›

cant say i've ever seen that before... looks like LogIris throws out some logs when protocol verification fails though.. i'd try searching for "FReplicationProtocolManager::ValidateReplicationProtocol" with LogIris turned on and see if anything pops up in either server/client logs

formal path
#

could be different build version on client and server i guess

harsh cloak
#

Anyone know if there is a delegate for when a playercontroller disconnects? I'm struggling to find something but I need to bind to this so I can do some cleanup in some of my container logic

verbal ice
#

gamemode logout

#

endplay of the pc

harsh cloak
#

cheers I'll take a look

halcyon ore
quasi spear
dark lance
quartz star
#

Hi, I have a fast array that contains a replicated uobject ptr.
For some reason, when I add an entry to the fast array, assign its uobject ptr to a new replicated uobject (which I also added to the replicated subobject list) and mark it as dirty, the fast array first calls PostReplicatedAdd with an invalid uobject ptr and then PostReplicatedChange with a valid one.
But in both calls the replication ID is identical.

Does anyone know what could cause that?

meager spade
#

cause the uobject is replicating slower that the fast array did, PostAdd has no replicated uobject on the client

#

when it does resolve, postchange gets called

#

this is a typical race condition

#

and if your making the object the same time you update the array, something has to arrive first.

dark edge
meager spade
#

yeah

#

might be anything tbh

#

never really took notice if it happens on say a replkciated TArray of objects

dark edge
#

I've only used fastarray on POD structs but I've noticed some changes that seem to be packet ordering based. I basically route Add and Change to the same code

quartz star
modest swallow
#

Hi guys, I'm making a Local coop couch party game and I've run into some problems, I am running ue5.6 using blueprints . I either need a way to toggle the project setting that sets the a gamepad to controller 1 instead of 0. Or I need a way to add more than 4 local players. Preferably I would like to add up to 8 but tbh I'm ok with whichever is available to do with blueprint or a plugin.

quasi spear
chrome bay
meager spade
#

to refire the onreps

crystal verge
#

hey guys, i am trying to do a server travel in blueprint and it does not work on the package project when tested.
I am doing OnPostLogin in game mode, and also set "Use seamless travel travel to true" but still no result. have tested the server travel in editor it worked but when i package it does not. please any one with experience in this ?

kindred widget
crystal verge
neon verge
#

So I'm a bit confused by knockback with GAS. I'm trying to, inside my ability after I detect a hit, to apply knockback via impulse or launch character (tried both). On listen server knockback is executed properly, but when I swap over and play as client I don't see any KB. This is after a few authority checks. IF I remove my authority checks I do see knockback but then there is some desync where I'm running into an invisible character.

How are we supposed to implement KB inside of GAS as I feel like I'm missing something here. My flow is basically : Execute Ability -> Play Montage -> Start trace via gameplay event inisde the ability -> Apply knockback and damage if we hit something

crystal verge
latent heart
#

Names for identifiers. Strings are text values. Text are user-facing text values.

#

Send whichever is appropriate.

#

FText is the input you get from text entries, so probably FText.

#

It probably makes very little difference. You may lose some encoding data if you convert to fstring.

#

May

#

I believe the limit is over a thousand per packet, so you can send pretty hefty strings.

#

100 would be fine.

#

I'm not sure honestly, I haven't looked into the internals of ftext.

#

No. Definitely not for user chat messages.

#

You should try to stick to fnames, but only where they are appropriate. Is it an identifier for something? Use an FName.

verbal ice
#

For user chat messages I'd go FString

#

Since they're arbitrary strings

#

Not localized and not identifiers

latent heart
#

Still remember the day someone said, "you should use FName instead of FString because sizeof(FName) < sizeof(FString)".

verbal ice
#

pocket dimension ram

latent heart
#

It was probably Mistty. We all know they're PC is a magic black box.

verbal ice
#

we're just all living in the past

prisma snow
minor arrow
#

can anyone please help with dedicated server stuff. im having an issue where it wont launch right

rare cloud
verbal ice
#

I'd still go FString just for what it represents

queen escarp
#

Why would this cause issues on Client side ?

#

(Controller BP)

lost inlet
#

if it's a controller BP why do you need GetPlayerController?

#

and what issues?

tardy fossil
#

well the thing that stands out to me is that the client is calling a client rpc

dark parcel
#

Well the function name kinda weird too. Client spawn character on client.

#

So i guess he doesnt want to spawn a replicated character??

queen escarp
#

nevermind i solved it

dark parcel
# queen escarp nevermind i solved it

Its common etiquete to explain briefly how you solve it so people with simmiliar problem can find resolution.

Also its mp we r talking about. You may miss a thing or two and that may be picked up if you share your solution.

queen escarp
#

Ah your right, well the problem was not this code, it originated from the game mode that rann the spawn character to soon really

#

so the code shown worked as intended

dark parcel
#

I am kinda worried about the client rpc call inside the controller.

#

Very much doubt that is the actual intention.

#

If you are aiming to spawn a replicated actor then it has to be done by the server.

A client running client rpc will only run the function locally at best.

So what ever you spawn will never be in sync and only exist in the client machine that execute the code.

queen escarp
#

Hmm i dont remeber, but if im playing as listen server then playing a montage with RPC will make it play twice once on client and once on server, i dont rember how to set it up x)

#

iΒ΄ve set this up before and it worked like a charm

formal path
queen escarp
#

well since im playing as listen then the host playes the montages twice

#

wich runs the code twice basicly

formal path
#

so it plays twice on server?

queen escarp
#

yeah

#

so even as a listen it should only play on the "client side" of the host

formal path
#

so you never want it to play on the server?

#

or what do you mean with client side of the server

#

or is there no dedicated server and is it one of your players that is hosting

queen escarp
#

i dont want it to run twice for the host .P

#

yeah exactly

#

no dedicated

#

P2p

formal path
#

maybe the server has a local and remote controller and is calling it twice

#

have you tried logging all the calls to the function and what object is calling it

tardy fossil
#

if you add a print node just before playing the montage, and you launch the game as listen server with no clients, does it print twice?

queen escarp
#

yeah

queen escarp
#

or on the client side its printing for the client and server .. hm

drifting estuary
#

Should clients ever be manually adjusting their Role? I came across code that's manually adjusting the Role of Pawns on clients in order to mimic Possession so that both a mounted unit and the player are both still AutonomousProxy. This doesn't seem like the expected path and that maybe it'd be better to just set the mounted unit as the Owner of the player Pawn when they're on it, or let the Controller own the player Pawn. EIther way it seems like the server should be in control of determining roles. Thoughts?

unique forge
#

having problem with online subsystem steam

#

it doesnt pop up

#

enabled online subsystem in plugins

sinful tree
sinful tree
# queen escarp this is the listen server player if fires the code twice...

The Multicast would trigger once on all clients and once on the server. If the problem you're having has to deal with the amount of damage being dealt, it could be because you're doing that down the line in your code.

Also, it's probably not a good idea to allow a client to tell the server what animation montage to play and then let that multicast out to everyone, as that could allow clients to play animations they shouldn't be allowed to play.

queen escarp
#

how would i play a montage without RPCΒ΄ing it then :/ ?

sinful tree
#

You let the server decide what montage should be playing. don't have the client send an RPC to the server with the montage and blindly multicast it out to everyone else.

queen escarp
#

hm,

queen escarp
#

and i get "why" it dose that

#

im not sure how to sole it tho

sinful tree
#

You should only be doing the damage on the server πŸ™‚

#

You're probably doing damage on both the server and the client.

queen escarp
#

but it always shows for the listen server host also..

dark parcel
#

Stop using the getter with index

queen escarp
#

aye ignore that part already removed it <)

dark parcel
#

Info are missing so cant help without knowing more.

#

Like what actually calls the event. Whos executing the code.

queen escarp
#

ok i have a widget componenet (healthbar) when a unit takes damage i want it to "show" the hp bar for that client

dark parcel
#

So how is the client informed when server deal damage?

queen escarp
#

since its not rpc or on server its handled locally id say

dark parcel
#

Nothing that you show tells me client gets any feedback.

queen escarp
#

well the player pawn is casting to the damaged npc telling it to show the widget

#

so basicly its like singelplayer but i though since i only want it to be played locally it would work the same way basicly

#

oh..

dark parcel
#

Wdym by locally? One pc?

queen escarp
#

your right again as always

dark parcel
#

Then why do you have rpc again at all.

queen escarp
#

im dealing the damage via rpc

#

and applying damage via server

#

so the server gets the info also

dark parcel
#

The server need the info unless you take 0 info from the client.

#

But normally to compensatw for latency server trust client to certain degree.

#

Like if client says i hit this person. Server can check if the hitbox is close enough.

queen escarp
#

aye

#

but but let put it like this

dark parcel
#

But at the end, server the one that deal the damage.

#

Client just say i hit this thing, go verify.

queen escarp
#

yeah

#

but based on this if i have the triggering Actor how owuld i tell it to show it to that client

dark parcel
#

By knowing how coms are done in multiplayer.

#

I have a feeling you dont fully grasp rpcs yet.

#

Server rpc = hey server run this function.

#

Client rpc = hey client go run this function.

#

Normal workflow is when server deal damage it will inform client that the damage is done.

#

Client can then display txt damage etc. Based on that info.

queen escarp
#

i took a breake with mp for like 2 years so yeah forgot almost everything ...>.<

dark parcel
#

ApplyDamage(server side) -> set attribute.

Client OnRep->Attribute -> get delta between old and new value -> show damage text

queen escarp
#

hm

#

ok but i should be able to rpc this then

dark parcel
#

Damage is also done on the server. Server have context (which player deal the damage, etc.)

So server can just send info to the client that deal the damage if neccesary.

queen escarp
#

i got the actor (owner) i tell all clients "are you this owner" if owner play for him only ?

dark parcel
# queen escarp

But you said you only want to show the text to the player that deal damage. So why multicast?

#

Can just do a client rpc

#

Either that or OnRep when the attribute gets replicated

#

And check if the text should be shown.

queen escarp
#

can just do a client rpc

#

wdym

dark parcel
#

What does a client rpc do?

queen escarp
#

client rpc= talks with all clients ?

#

or client rpc do you mean just tell the server ?

dark parcel
dark parcel
#

Client rpc when executed by the server (as it should) tells the owning client of the actor to execute the function.

queen escarp
#

oh okey, so how do i do a client rpc whycry

dark parcel
#

So you can just get the damage causer-> client rpc -> show damage text.

dark parcel
queen escarp
#

are you talking about run on owning client ??

dark parcel
#

That is indeed client rpc

queen escarp
#

oh... yeah now i get it just confusing with the labeling yeah i know that

#

but doing it with a client rpc im still getting the server getting the code

dark parcel
#

I need to see code

queen escarp
dark parcel
#

This should be done when applying damage

#

I dont know what calls that event prior

#

Or whos even executing it.

#
  1. When server deal damage

  2. Server tell the player (damage causer) to execute a function that show the health bar.

#

Its as simple as that

#

A neater way to deal with this is to use GAS and the gameplay effect.

formal path
#

or the health bar just shows the player HP and that is a replicated variable ?

dark parcel
#

Same thing but can just add more stuff like sfx, vfx, etc.

formal path
#

you probably still need a RPC call to trigger the damage effect vfx tho

dark parcel
#

Yeah but thats done under the hood with gameplay effect.

formal path
#

does using gameplay effects require gas

dark parcel
#

Yea its part of GAS

formal path
#

finally a reason to use it πŸ˜‚

queen escarp
#

you know what i think i know why its not working

#

im jsut not sure how to workaround it

#

the damage is dealt with a RPC since its playing a montage then tracing for hits if hit only server deals damage so it only happens once,

#

but the damage it run from that code so therefor its running on all clients...

dark parcel
#

So make a system for it. How its done depend on how you want to design the game.

queen escarp
#

yeah..

dark parcel
#

Easiest way is just to let server be the only one checking.

#

But since movement is predicted this can cause a scenario where player hit something on their screen but the damage is not valid as in server the hit is missed.

#

But if you gonna go with this then just make sure only server runs the damage thingy in the montage

queen escarp
#

yeah i se the problem now..

#

hmmm

dark parcel
#

Anim notify -> get owner -> has authority -> deal the damage

dark parcel
#

-> get damage causer -> ClientRPC_showDamage

queen escarp
#

well since the tracing is related to the montage...

#

oh wait!

#

if i do this authority check in the montage thats being RPCΒ΄d

#

will that work ? will it run once on the server

#

or X client times on the server ... hmm

dark parcel
#

You can make sure that client doesnt do the tracing logic at all

#

Just filter with has authority

queen escarp
#

i did ? middle of the image

#

or is that wrong ?

dark parcel
#

Doesnt look wrong but never know when i can only take a glimpse.

#

Also regardless of the trace, unless the client send a server rpc to inform about the damage then this is unrelated.

#

You gotta make a choice on the degree of trusting the client or no trust at all.

queen escarp
#

hmm

dark parcel
#

Something is hit -> has authority (is the server executing the code?) -> apply damage -> damage causer -> client rpc show damage text.

queen escarp
#

yeah thats exacly what im doing

#

this runs the print on server tho

dark parcel
#

In plain english.

Something is hit. If we are the server, apply damage then tell the owner of the damage causer to show text.

dark parcel
# queen escarp

I dont understsnd what this is doing. Ive been telling you about showing text upon server apply damage.

#

That server rpc you showed makes absolute no sense to me.

queen escarp
#

this is the whole line

dark parcel
#

Cant c on my phone other than the text that says trace multicast which sound super wrong.

#

I dont see why you need to tell every player to trace.

#

Also multicast means server telling every client to run X function.

queen escarp
#

well since its tracing from a montage wich has to be RpcΒ΄d form what im told thats the only way i could do it

dark parcel
#

You can rpc the montage but why the trace?

#

Anywayy i cant debug this further for you.

My advise would be to ensure that apply damage is run on server only.

queen escarp
#

that is ensured

#

100%

dark parcel
#

Then all you gotta do from that apply damsge function is to run a client rpc of the damage causer to show text

#

There shouldnt be server rpc or w.e u trying to do.

All you gotta do when applying damage (server) is to tell the client (in this case the player of the damsge causer) to run a function to show the text.

#

Apply damage -> get damage causer -> client rpc ShowDamageText

queen escarp
#

hm should the widget be replicated :/ ?

#

just to clarify its no text thats shown its a widget component on the actor itsefl that i set visiblity on/off

dark parcel
#

Widget dont replicate

queen escarp
#

this shouldent be printed for server right ??

dark parcel
#

It will be printed on the owner of the actor

#

If the owner is the server then it will be printed on thr server.

queen escarp
#

well on clients its printed on server

#

this is from a client side*

dark parcel
#

Example, a listen server gets a pawn. The listen server is also a player.

queen escarp
#

yeah i know that

dark parcel
#

The only way for client to communicate with server is thru server rpc.

dark parcel
#

A client calling a client rpc will just execute the function locally at best.

dark parcel
formal path
queen escarp
#

hmm

dark parcel
dark parcel
#

On phone, screen shoot only pls.

queen escarp
#

so 2nd picture is the montage thats being played on RPC but since the trace checks for authority the event on hit actor is played on server and from that i deal damage first the after calling that function

#

this trace is acctualy a pluggin so i guess it might be something with that causing it

formal path
#

you absolutely do not need a plugin to trace between 2 socket locations

queen escarp
#

true i did it myself before* but i saw this free pluggin and wanted to try a more "advance one" and test it

dark parcel
#

Like what its derived from.

queen escarp
#

or do you mean from what class, its the player character BP

#

this is the root from where the montage starts*

dark parcel
queen escarp
#

yeah

#

or its a parentclass of caracter BP

#

or its the char bp* i jsut have 5 different child classes from it so yes

dark parcel
#

If the unit base bp is owned by a client then it will print on client.

#

The only time it will print Server is when the owner is the listen server.

queen escarp
#

i agree this is news for me to

#

you know what

#

im dumb

#

or

#

This code ir run on the NPC wich hold the HP bar so the printing comes from a NPC = Server

#

even if its Client RPC then its still the Npc thats printing it

#

so i need to run the code from my player bp to tell it to show…

dark parcel
#

Isnt the damage dealer the player?

queen escarp
#

well yeah but the code is running on a npc wich is server owned

#

so that wont work*

dark parcel
#

The show damage text needs to be in player owned actor. In this case the character the player possess.

#

It doesnt matter where you call it. You are the server.

#

(Server)where ever -> the player character that deal the damage -> show damage text.

queen escarp
#

yeah i noticed my misstake

#

thanks as always 🫑

still blaze
#

Hey guys, did anyone know how fix this:
in my dash ability, even I only commit ability on server, but when my client dash, the remaining cooldown time might be strange (I have a GE_Dash_CD, used as the cd class in my GA_Dash, it's only 2 secs, but sometimes the widget says it's 5 secs for example(i literally watch the float value from my ability object!!))
can anyone fix it, private chat if u r willing to help
please +crying
using UE5.6

still blaze
sinful tree
still blaze
still blaze
sinful tree
queen escarp
#

Hi, Advice
if im to spawn Npc or stuff on the level ingame whats the most common way to spawn them, from game mode or just call it from a parent or ?

sinful tree
#

If it's just an actor you'd place and they're static in the world... Probably just place them in the level.

queen escarp
#

ah like a "manager simpleton"

#

gotcha

meager spade
#

yeah we have directors in the world

#

like AIDirector

#

SpawnDirector

unique forge
#

huanson

nocturne quail
#

onrep has issues with previous state of a TArray?
I want to read the PreviousContainers

void OnRep_InventoryContainers(TArray<FInventoryContainers> PreviousContainers);
#

this works for simple properties perfectly but not with container property

kindred widget
#

I'd start by turning that into a const ref.

nocturne quail
#

I changed it now to single property

fossil spoke
#

Why arent you using a Fast Array?

#

As soon you need previous state of a replicated TArray, your first thought should be considering moving it over to a Fast Array.

dark edge
fossil spoke
nocturne quail
fossil spoke
#

Which gives you the opportunity to extract the previous state.

dark edge
#

How do you keep the orders synced? I thought the array ordering was only valid during that call.

#

I suppose you could just have shadow unreplicated fields in the array entry too

fossil spoke
#

Generally I find it good practice to always generate a UID for each element.

#

When using FAs

#

So to avoid ordering issues

neon stone
#

Is there any kind of rollback netcode solution on the market or elsewhere? UE5 doesn't have one by default.

thin stratus
#

Most peeps are fine with what the CMC offers. Other tried their luck with the Network Prediction Plugin (either on Independent mode, or on Fixed Tick). Epic itself is more leaning into Chaos Replication by now, I think.

#

If you need anything more complex or specific, I wouldn't know what's on the market. If searching for it online hasn't brought up anything, then I would guess that most of those solutions remain hidden in studios that needed them.

formal path
#

we just had client auth physics & hit detection and snapped things into place if they diverged too much

#

so it really depends on what you wanne achieve

thin stratus
#

Rollback is usually asked for when wanting to make a fighting game and that is usually not support out of the box I would say.

#

There are probably several convention (e.g. GDC) talks that brush over the topic, but if there is none available you'd be stuck coding your own.

#

Or at least adding a third party one

slate phoenix
#

Guys, I’m currently using data coming from the real server, but I’m experiencing a problem.

When I jump while running, the character gets pulled back (rubberbanding).

If I jump normally, there is no problem.
Walking or running also works fine.

However, when I run and jump at the same time, the character gets pulled back.
My ping is good, so I’m not sure what could be causing this.

exotic wasp
#

Then I just make a sorted array when needed. It's trivial to sort by index because it's a 1:1 mapping

trim onyx
#

Guys, I’m currently using data coming

slate phoenix
dark parcel
#

Well that doesnt say much.

If the system uses character movement component. The data has to be packed and send using the movement struct.

#

Cpp only btw since you said your project is bp only.

#

At least for server auth movement.

grand axle
#

has anyone managed to get gamepads to spawn local players correctly with "Skip assigning gamepad to player 0" without a player controller and directly geting the gamepad that pressed the button to control the local player that is spawned? I can get it to work with "Skip assigning gamepad to player 0" off but it's only when it's enabled I can't get it to work? any ideas?

slate phoenix
# grand axle has anyone managed to get gamepads to spawn local players correctly with "Skip a...

The issue is that with "Skip Assigning Gamepad to Player 0" enabled, gamepad indices shift by 1 (gamepad 0 maps to controller ID 1). When you call CreatePlayer, the new PlayerController gets a sequential ID that doesn't match the gamepad.
Solution: After CreatePlayer returns the new PlayerController, manually call SetControllerId on it with the actual gamepad index that triggered the join. You'll need to track which gamepad pressed the button (via Enhanced Input's GetLastInputDevice or listening to InputDeviceConnectionChange), then force-assign that ID to the spawned controller.
You can't fully avoid PlayerControllers for local players β€” UE requires them. But you can keep them minimal and route all gameplay logic through your Pawn/Character directly.

lost inlet
#

copying and pasting your LLM answer isn't particularly helpful

#

the modern day lmgtfy

slate phoenix
lost inlet
#

do you even understand it yourself?

slate phoenix
#

yes if want can do

neon stone
stiff pine
#

Scratch the previous questions. Stranger and more detailed new one. What you see here is the output of ShowDebug INPUT, and printing out the name of the controller returned by "Get Local Viewing Player Controller." It looks to me like ShowDebug INPUT says that Player 1 DOES have a controller attached to them. This is backed up by the fact that they can recieve inputs. And, if I were to use the player index to access the player controller instead, it would find Player 1's controller. I'm very confused over this behavior. Any explanation would be appreciated.

nocturne quail
#

Any idea why I am getting this line of warning on tick in the logs?

OldMap size (0) does not match item count (4) for struct (VehicleSeatItem), missing a MarkArrayDirty on element add/remove?
A4WBase::A4WBase() : AVehicleBase()
{
    if (SeatComponent)
    {
        SeatComponent->AddSeat(0, ESeatRole::Driver, "Seat_Driver");
        SeatComponent->AddSeat(1, ESeatRole::Passenger, "Seat_FR");
        SeatComponent->AddSeat(2, ESeatRole::Passenger, "Seat_RR");
        SeatComponent->AddSeat(3, ESeatRole::Passenger, "Seat_RL");
    }

    VehicleType = EVehicleType::Car;
}
USTRUCT()
struct FVehicleSeatItem : public FFastArraySerializerItem
{
    GENERATED_BODY()

    UPROPERTY()
    uint8 SeatIndex = 0;

    UPROPERTY()
    ESeatRole SeatRole = ESeatRole::Passenger;

    UPROPERTY()
    FName SeatSocket;

    UPROPERTY()
    TObjectPtr<APlayerState> OccupantPlayerState = nullptr;

    UPROPERTY(NotReplicated)
    TWeakObjectPtr<ACharacter> CachedCharacter;
};
USTRUCT()
struct FVehicleSeatArray : public FFastArraySerializer
{
    GENERATED_BODY()

    UPROPERTY()
    TArray<FVehicleSeatItem> Items;

    UPROPERTY(NotReplicated)
    class UVehicleSeatComponent* OwnerComponent;

    bool NetDeltaSerialize(FNetDeltaSerializeInfo& DeltaParms)
    {
        return FFastArraySerializer::FastArrayDeltaSerialize<FVehicleSeatItem, FVehicleSeatArray>(Items, DeltaParms, *this);
    }

    void PostReplicatedAdd(const TArrayView<int32> AddedIndices, int32 FinalSize);
    void PostReplicatedChange(const TArrayView<int32> ChangedIndices, int32 FinalSize);

private:

    void HandleSeatChanged(FVehicleSeatItem& Seat);
};
void UVehicleSeatComponent::AddSeat(uint8 SeatIndex, ESeatRole Role, const FName& Socket)
{
    if (!GetOwner()->HasAuthority())
        return;

    FVehicleSeatItem Seat;
    Seat.SeatIndex = SeatIndex;
    Seat.SeatRole = Role;
    Seat.SeatSocket = Socket;

    SeatArray.Items.Add(Seat);
}
stiff pine
#

No server.

#

It is possible this is a 5.6 local multiplayer bug. I've already found one. But I don't know nearly enough about multiplayer systems to figure that out alone.

slate phoenix
#

What do you mean by "starting with"? I didn't understand the question. Are there 4 clients or just one Pie client?

dark parcel
#

Have you actually do that?

nocturne quail
dark parcel
#

After SeatArray.Items.Add

nocturne quail
#

SeatArray.MarkArrayDirty();

dark parcel
# slate phoenix will help her understand

Not really, also LLM hallucinate a lot. At the very least you can mention that your answer was from LLM.

Presenting it as a solution as if you know if its right will end up shooting others in the foot more.

stiff pine
shrewd ginkgo
#

I have a multiplayer project in Unreal Engine 5. The character movement itself is perfectly smooth, but the camera appears to stutter or jitter while moving. This issue only happens on the client side; the server view is smooth.

The camera is attached directly to the character’s head (to the mesh/head bone), not to a spring arm. There is no camera lag enabled. Settings like β€œAlways Tick Pose and Refresh Bones” are already enabled on the mesh, and the character rotation settings (Use Controller Rotation Yaw / Orient Rotation to Movement) are configured correctly.

Despite this, the camera still moves in a slightly jittery or choppy way while the character walks, but only on the client in multiplayer. I'm trying to understand what could cause camera stutter when the camera is attached to the head bone in a networked character.

sinful tree
shrewd ginkgo
#

I didn't understand what you meant

nocturne quail
sinful tree
shrewd ginkgo
#

There's no problem with the editor, but when I package it and play with my friends, there's an issue.

sinful tree
shrewd ginkgo
#

How can I control it?

dark edge
#

That would differentiate if it's the editor build or just the fact that you have zero latency

dark parcel
dark parcel
#

@nocturne quail why fast array for seats? Iirc you get more overhead than regular array for something with small length.

shrewd ginkgo
#

I tested it and I think that's the cause. But why does this problem occur when I walk? It doesn't happen when I just turn around. and How can I fix this?

minor arrow
#

looking for help with setting up a dedicated lobby server setup

nocturne quail
shrewd ginkgo
#

The problem isn't as noticeable on a different computer in the same house, but it appears like this on a computer on a different network. The camera only malfunctions when walking

dark edge
#

cuz that's the only part that wasn't a stuttering mess

dark edge
shrewd ginkgo
#

It spins smoothly while staying stationary.

dark edge
shrewd ginkgo
dark edge
# shrewd ginkgo

Are you doing anything funky with setting max speed or anything like that?

shrewd ginkgo
#

I change my maximum speed while walking or running.

dark edge
#

show how

shrewd ginkgo
dark edge
#

that won't work btw, not butter smooth anyway

shrewd ginkgo
#

He is running and walking in the video, but even if he just walks straight, there is jitter

dark edge
#

If sprinting isn't a thing, is the only code that touches the CMC the AddMovementInput?

shrewd ginkgo
#

Yes, I didn't add anything else.

dark edge
#

Could be mesh interpolation shenanigans

shrewd ginkgo
#

The reason I put on the mesh was to attach it to head and use the aimoffset.

#

I removed the other variables from the CMC and am packaging them.

shrewd ginkgo
#

When I asked AI, it said this was related to the network smoothing mode. My current settings are as follows:

nocturne quail
# shrewd ginkgo

don't ever directly modify the max speed, it will be desynced and you get jitters

shrewd ginkgo
#

I removed the motion speed modifiers from the image you quoted. Only the changes I made here remain.

nocturne quail
#

you should modify max speed before it returns in the same tick frame

shrewd ginkgo
dark edge
#

Add a new default character and compare the settings

grand axle
# slate phoenix The issue is that with "Skip Assigning Gamepad to Player 0" enabled, gamepad ind...

Without skip assigning "gamepad to player 0" I have already skipped the player controller part which works when any one of my controllers press face button down. So It is possible to detect gamepad id and which gamepad pressed it. It only gets weird when skipped is enabled. I can spawn all the players when I have it true but they wont be assigned to the gamepad that pressed it. Which is weird behavior

#

It's done in c++ btw. Bps don't expose the data

#

I tried making proxi PCs that detect gp input but that wigs out my online multiplayer part. The goal here is to have a dynamic load in for local + online players to play together eg, computer one joins and then creates 3 local players and server also has 3 local players so it'd be a 6 player game with two computers, one client, one host. Which I have working. It's just a little funky is all. It's just skip assigning gp to p0 that screws it up

slate phoenix
dark parcel
#

No LLM stuff pls

slate phoenix
# dark parcel No LLM stuff pls

I already mentioned that I would send it privately, and the issue is not related to you. He can also write himself. Anyone reading the messages can already see that the first message describes the problem and the second one suggests a possible solution. The person himself is also aware of the situation. I’m just trying to help. Since nobody knows the details of the project, no one can give a direct or definitive solution.

dark parcel
nocturne quail
nocturne quail
#

I thougt disabling movement component will disable it automatically, but its not

#

so have to add it

queen escarp
#

Hi, This might be a dumb player but creating widgets for each palyer/client should be done with Client RPC on controller or such right ?

#

there is no reason to RPC the creation of the widget right ?

#

it cant detect the player hud from the player pawn

lusty palm
#

Hey guys my NetDeltaSerialize seems to be called every tick, is this intentional? cpp bool FInventory::NetDeltaSerialize(FNetDeltaSerializeInfo& DeltaParms) { UE_LOG(LogTemp, Warning, TEXT("FastArray NetDeltaSerialize called")); return FFastArraySerializer::FastArrayDeltaSerialize<FInventorySlot, FInventory>(Slots, DeltaParms, *this); }

dark edge
#

WHEN do you want this widget created?

queen escarp
#

its created at start

nocturne quail