ValveSoftware / Source-1-Games

Source 1 based games such as TF2 and Counter-Strike: Source
635 stars 74 forks source link

[TF2] Dropped wearables spawns from stale origins due to being outside PVS. #5090

Open zxz41 opened 1 year ago

zxz41 commented 1 year ago

When a player dies somewhere in the world, the player calls a function called DropWearable on the client realm. This function takes in a wearable cosmetic (C_TFWearable) and some breakable parameters (breakablepropparams_t)

Later this function calls to either GetRootBone (which is later used for MatrixGetColumn) or GetAbsOrigin.

Both these functions calls to CalcAbsolutePosition. But since we're on the client realm we'll only be able to retrieve where they were last seen (going dormant from being outside the PVS.) This is why it's common to see this bug in action around teleporter entrances, near observer points, visleaf splits etc.

image A poor engineer meeting his doom. Observe how his hat spawns at the teleporter rather than at his demise.

One solution is to wrap the GetRootBone else GetAbsOrigin in a if ( !pWearable->IsDormant() ) statement, and then else into setting the position to the breakable params origin (or m_vecRagdollOrigin if the param origin weren't set up.) and then offsetting it with GetClassEyeHeight.

Something like this

if( !pWearable->IsDormant() )
{
    if( /*didn't bother &&*/ pWearable->GetRootBone( rootBone ) )
    {
        MatrixGetColumn( rootBone, 3, vecPos );
    }
    else
    {
        vecPos = pWearable->GetAbsOrigin();
    }
}
else
{
    position = breakparams.origin + GetClassEyeHeight();
}

You could also calculate the offset from the player, but since there's semirare instances of players going dormant but not the wearable, and vise versa. And it's something nobody will notice since the wearable gets thrown in a random direction.

Platina6978 commented 1 year ago

Is this way you sometime see hats etc. spawn from your face? That glitch feels as ancient as can be in this game hah. Is this perhaps also the cause for gibs sometimes spawning seemingly in the middle of nowhere?

zxz41 commented 1 year ago

Is this way you sometime see hats etc. spawn from your face? That glitch feels as ancient as can be in this game hah.

I'm not entirely sure why that happens to be honest. Might be due to people in observer mode spectating players, since (iirc) their entity follows the player around and could be updating their position everyone in that PVS. Although I've never seen wearables spawning from observer camera entities.

Is this perhaps also the cause for gibs sometimes spawning seemingly in the middle of nowhere?

The bombinomicon seems to cause this. Probably having the same issue of using the dormant/stale origin.