openplanet-nl / vehiclestate

The VehicleState dependency plugin in Openplanet.
1 stars 4 forks source link

add support to show currently spectating ghost #3

Closed chipsTM closed 1 year ago

chipsTM commented 1 year ago

I threw this together rather quickly, but happy to discuss any concerns or edits you'd like to make

codecat commented 1 year ago

Please help me understand - I thought this already worked? I specifically remember being able to spectate players and seeing their vehicle state in Dashboard.

chipsTM commented 1 year ago

You're right that it does work already, however in the case of spectating ghosts you have to ensure there is only 1 vehicle state in order for dashboard to show up for ghost you're spectating. This is currently done by hiding the PB ghost(s)

Without PB ghosts hidden image

With PB ghosts hidden image

Sorry if images are a bit small was trying to show everything close together

What this aims to solve is always showing the dashboard for the "spectating" state no matter how many states are in memory image

Here is more than 1 ghost on image

I mostly mean this to be a quality of life, i.e. "it just works" no extra steps needed to show the dashboard

codecat commented 1 year ago

Ah, then this PR was labeled wrong, it's not the "spectating" in the traditional sense. 👍 I understand now.

Taking a quick look at this, your pattern does not bring up any results on my game - which version of the game are you using this on, and what exactly is being matched here?

chipsTM commented 1 year ago

I was afraid of that lol. From the "About Openplanet" it says I'm using TM Next 2023-01-26 09:32:08

So all I know right now is that there are pointers to the entity ids (and they work for me each time I start up the game). Like you mentioned previously, I can't rely on the base address and offsets, since they'll most likely change the next game update.

tbh I'm still learning/wrapping my head around how to translate this. I'll study this some more

XertroV commented 1 year ago

Dev::ReadUInt64(Dev::GetOffsetUint64(GetApp().GameScene, 0x1c8) + 0x1cc) appears to return the ID of the currently active vehicleVis.

When you load a level, it's usually 02000003 for me, then 02000004 when you spawn, and if you turn on multiple ghosts and spec one then it'll point to e.g., 04000097.

I found 2 paths to this particular value from GameScene: 0x1c8, 0x1cc and 0x608, 0x1cc. The pointers at 0x1c8 and 0x608 appear to point to the same object (not sure if they're ever different).

The test code I used:


    auto sceneVis = GetApp().GameScene;
    int offset1 = 0x1c8;
    int offset = 0x608;

    // auto vehicleVisMgr = Dev::GetOffsetNod(sceneVis, 0x10 + ix * 0x8);
    auto vehicleVisMgr = Dev::GetOffsetNod(sceneVis, offset);
    if (vehicleVisMgr is null) {
        return;
    }
    auto vehicleVisMgrPtr = Dev::GetOffsetUint64(sceneVis, offset);
    print('vehicleVisMgrPtr: ' + FmtPointer(vehicleVisMgrPtr));

    auto nod = vehicleVisMgr;
    auto ptr = vehicleVisMgrPtr;
    print("Next ptr: " + FmtPointer(ptr)); // + " of type: " + Reflection::TypeOf(nod).Name);

    ptr = Dev::ReadUInt64(ptr + 0x1cc);
    print("Next ptr: " + FmtPointer(ptr)); // + " of type: " + Reflection::TypeOf(nod).Name);
codecat commented 1 year ago

You'd be correct that there is 2 access points to this, as the managers always appear twice in ISceneVis. So the class you are looking at is NSmArenaVis_SMgr, which does indeed seem to contain the currently viewing ghost entity ID at that offset!

The offset is pretty large, but I'm down to just have a few safety checks, eg. (id & 0xFF000000) == 0x04000000 in case the offset ever changes (which is likely). Additionally, checking for 0x02000000 can give us a local player entity ID, but we technically don't really need that 🤔

Additionally, the manager class itself is at index 55 which is quite large, so this would have to be maintained as well. Maybe I'll have to write some proper API for vis state managers though, I think that could be nice.

codecat commented 1 year ago

I'll close this PR and implement this based on this information myself, thanks to both of you guys for the help! 🎉