From 1cd94cda23516df002d5dae06450b38890912825 Mon Sep 17 00:00:00 2001 From: Asdow <20314541+Asdow@users.noreply.github.com> Date: Sat, 16 Nov 2024 16:05:14 +0200 Subject: [PATCH] Fix inventory cloning bug (#338) - If we have a sector already loaded (eg. Drassen airport) - Squad in a different sector encounters enemies and goes to autoresolve - After pressing DONE in autoresolve screen -> we miss calling the TrashWorld() function in CheckAndHandleUnloadingOfCurrentWorld() due to battle sector not being the same as loaded sector. - Selected sector gets reset from Drassen airport to invalid values by same function - Now we have the loaded sector's whole inventory existing in gWorldItems - Enter any other sector in tactical mode and the gWorldItems gets added into its sector inventory in EnterSector() Because the TrashItems() work in a way where it only sets gWorldItems elements to not existing if it finds them in a loaded map's structure data, we will pretty much always have that original bugged out set of items present in gWorlItems and they will constantly be added to sector inventories from then on once the bug has been triggered. --- Strategic/strategicmap.cpp | 22 ++++++++++------------ 1 file changed, 10 insertions(+), 12 deletions(-) diff --git a/Strategic/strategicmap.cpp b/Strategic/strategicmap.cpp index 5708dfc7..801bda22 100644 --- a/Strategic/strategicmap.cpp +++ b/Strategic/strategicmap.cpp @@ -6665,18 +6665,16 @@ BOOLEAN CheckAndHandleUnloadingOfCurrentWorld( ) if ( guiCurrentScreen == AUTORESOLVE_SCREEN ) { - if ( gWorldSectorX == sBattleSectorX && gWorldSectorY == sBattleSectorY && gbWorldSectorZ == sBattleSectorZ ) - { //Yes, this is and looks like a hack. The conditions of this if statement doesn't work inside - //TrashWorld() or more specifically, TacticalRemoveSoldier() from within TrashWorld(). Because - //we are in the autoresolve screen, soldiers are internally created different (from pointers instead of - //the MercPtrs[]). It keys on the fact that we are in the autoresolve screen. So, by switching the - //screen, it'll delete the soldiers in the loaded world properly, then later on, once autoresolve is - //complete, it'll delete the autoresolve soldiers properly. As you can now see, the above if conditions - //don't change throughout this whole process which makes it necessary to do it this way. - guiCurrentScreen = MAP_SCREEN; - TrashWorld( ); - guiCurrentScreen = AUTORESOLVE_SCREEN; - } + //Yes, this is and looks like a hack. The conditions of this if statement doesn't work inside + //TrashWorld() or more specifically, TacticalRemoveSoldier() from within TrashWorld(). Because + //we are in the autoresolve screen, soldiers are internally created different (from pointers instead of + //the MercPtrs[]). It keys on the fact that we are in the autoresolve screen. So, by switching the + //screen, it'll delete the soldiers in the loaded world properly, then later on, once autoresolve is + //complete, it'll delete the autoresolve soldiers properly. As you can now see, the above if conditions + //don't change throughout this whole process which makes it necessary to do it this way. + guiCurrentScreen = MAP_SCREEN; + TrashWorld( ); + guiCurrentScreen = AUTORESOLVE_SCREEN; } else {