LandSandBoat / server

:sailboat: LandSandBoat - a server emulator for Final Fantasy XI
https://landsandboat.github.io/server/
GNU General Public License v3.0
289 stars 576 forks source link

Airships cutscene/set player pos bug #216

Open ShiyoKozuki opened 3 years ago

ShiyoKozuki commented 3 years ago

Additional Information (Steps to reproduce/Expected behavior) :

All airships currently replay the cutscene of entering on the airship if you zone back into the current zone from your mog house and warp you to the airship dock if you previously used an airship before leaving that zone.

Take airship - > Go into mog house after docking - > leave moghouse to same zone.

Has something to do with this line of code in every airship zone file: https://github.com/LandSandBoat/server/blob/base/scripts/zones/Bastok-Jeuno_Airship/Zone.lua#L32

mrhappyasthma commented 3 years ago

This appears to be reproducible as a GM by just using !zone Port Bastok after arriving in Bastok from the airship. It plays the cut-scene and positions yourself every time.

The problem seems to actually be here: https://github.com/LandSandBoat/server/blob/base/scripts/zones/Port_Bastok/Zone.lua#L50

The if (prevZone == xi.zone.BASTOK_JEUNO_AIRSHIP) then check is still returning YES even after leaving the moghouse.

mrhappyasthma commented 3 years ago

I'm guessing PChar->loc.prevzone is not updated when zoning into/outof a mog house. I'm still trying to figure out where this is actually triggered from to see if I can test a fix.

mrhappyasthma commented 3 years ago

It looks like the last update to PChar->loc.prevzone comes from: https://github.com/LandSandBoat/server/blob/094ec9f022916bc86b8d0efee166b626ec560c2c/src/map/utils/charutils.cpp#L380

>   topaz_game_64.exe!charutils::LoadChar(CCharEntity * PChar) Line 381 C++
    topaz_game_64.exe!recv_parse(char * buff, unsigned __int64 * buffsize, sockaddr_in * from, map_session_data_t * map_session_data) Line 550  C++
    topaz_game_64.exe!do_sockets(fd_set * rfd, std::chrono::duration<__int64,std::ratio<1,10000000>> next) Line 410 C++
    topaz_game_64.exe!main(int argc, char * * argv) Line 277    C++
    [External Code] 

This packet seems to still contain the Airship value, even after zoning into/out of the mog house.

However we may need someone with a larger depth of knowledge to take over. I about exhausted my ability to debug further.

TeoTwawki commented 3 years ago

I'm guessing PChar->loc.prevzone is not updated when zoning into/outof a mog house. I'm still trying to figure out where this is actually triggered from to see if I can test a fix.

correct, because mog houses aren't a separate zone. So we need a binding that returns if the player just left a mog house ot add to that lua check. We have a flag we set and unset for players moving to/from mog houses.

TeoTwawki commented 3 years ago

or maybe we shoudl update prev to match current (both came FROM and went TO same zone) on exiting mog :thinking:

mrhappyasthma commented 3 years ago

My only concern with updating the prevzone would be if it breaks any assumptions from missions/quests. Are there any missions or quests that rely on the From zone being the airship?

Whether we set From to be 'Mog House' or From to match the zone (i.e. From = Port Bastok), it may cause trouble if any other logic relies on the From = Airship.

Perhaps a better idea is to update the checks to also check a cvar for whether the person left a moghouse or not. That way it's separate from messing with the zone logic?

What do you think?

mrhappyasthma commented 3 years ago

There's quite a few zones that check:

-- MOG HOUSE EXIT
--
 if player:getXPos() == 0 and player:getYPos() == 0 and player:getZPos() == 0 then

Which isn't entirely a reliable check, as we are seeing here. Since it also matches airship exits.

mrhappyasthma commented 3 years ago

Some random other info.

Confirmed we get an info output of Zoning from zone 236 to zone 236:.... (https://github.com/LandSandBoat/server/blob/094ec9f022916bc86b8d0efee166b626ec560c2c/src/map/packet_system.cpp#L3204)

The mhflag is never set and appears to be used for a different purpose and probably shouldn't be reused here.

We do have a Residential_Area/Zone.lua and the onZoneIn does seem to be called.

TeoTwawki commented 3 years ago

the mog house flag is used to tell if you were currently already in a mh, not if you just left one. I was thinking we could set a temporary thing anytime it gets removed to tell you just left one, if need be.

ShiyoKozuki commented 2 years ago

https://github.com/LandSandBoat/server/blob/2dbae3a1d7e3de544670f35051620660d5f9205f/src/map/utils/charutils.cpp#L5627

Should be: (PChar->m_moghouseID || PChar->loc.destination != PChar->getZone()) ? PChar->getZone() : PChar->loc.prevzone, PChar->loc.p.rotation, PChar->loc.p.x, PChar->loc.p.y, PChar->loc.p.z, PChar->m_moghouseID, PChar->loc.boundary, PChar->id);

kaincenteno commented 2 years ago

would adding a localvar affter the line that sets the position alleviate this bug? If so then it could check if the localvar exists to not play the arriving CS. What do you think @TeoTwawki ?