From b91bc7b209db33d350c84912c3beaa67d2a5583b Mon Sep 17 00:00:00 2001 From: Kriplo Date: Sun, 3 Nov 2013 16:26:30 +0000 Subject: [PATCH] Brief: //dnl ch75 - More map editor fixes and map inventory pool performance improvement for big maps. Details: - Fix not showing expected messagebox on exit (ALT+x) which also throw exception and goes to improper mapeditor exit. - Fix second annoying sticky message which shouldn't popup during map loading and performing RemoveProhibitedAttachments. - Fix CTD when delete all enemies or civilians or all of them in map. - Fix some std exception when reporting for missing optional xml file. - Fix memory and map corruption in old mapeditors if loaded old map has item with invalid attachment and we try to attach something else. - As years ago pInventoryPoolList had migrated from WORLDITEM* array to std::vector it was time to do that with gWorldItems too, all necessary functions which need to be adopted to gWorldItems std::vector type are also changed. - Resize code for gWorldItems is changed hoping will lead into less corruption problems as now could occur in mapeditor and game when code automatically doing attachment changes. - Change code for handling map inventory which now should be fast enough to support AIMNAS project which will probably deal with thousands of items per map. git-svn-id: https://ja2svn.mooo.com/source/ja2/trunk/GameSource/ja2_v1.13/Build@6554 3b4a5df2-a311-0410-b5c6-a8a6f20db521 --- Editor/EditorMercs.cpp | 2 +- Editor/Item Statistics.cpp | 3 + Editor/editscreen.cpp | 8 +- Strategic/Assignments.cpp | 26 +- Strategic/Hourly Update.cpp | 4 +- .../Map Screen Interface Map Inventory.cpp | 828 ++++++++---------- .../Map Screen Interface Map Inventory.h | 4 +- Strategic/Queen Command.cpp | 13 +- Strategic/Strategic Event Handler.cpp | 18 +- Strategic/Strategic Town Loyalty.cpp | 7 +- Strategic/XML_ExtraItems.cpp | 2 + Strategic/mapscreen.cpp | 43 +- Tactical/Handle Items.cpp | 22 - Tactical/Inventory Choosing.cpp | 34 +- Tactical/Item Types.cpp | 6 +- Tactical/Items.cpp | 60 +- Tactical/Items.h | 2 + Tactical/Soldier Create.cpp | 2 +- Tactical/Tactical Save.cpp | 107 +-- Tactical/Tactical Save.h | 6 +- Tactical/Turn Based Input.cpp | 30 +- Tactical/World Items.cpp | 68 +- Tactical/World Items.h | 7 +- TileEngine/Explosion Control.cpp | 2 +- 24 files changed, 593 insertions(+), 711 deletions(-) diff --git a/Editor/EditorMercs.cpp b/Editor/EditorMercs.cpp index 4f48a51c..981da0a5 100644 --- a/Editor/EditorMercs.cpp +++ b/Editor/EditorMercs.cpp @@ -1680,7 +1680,7 @@ void IndicateSelectedMerc( INT16 sID ) } } //if we made it this far, then we have a new merc cursor indicator to draw. - if( gpSelected == NULL || gpSelected->pSoldier ) + if( gpSelected && gpSelected->pSoldier )//dnl ch75 261013 gsSelectedMercGridNo = gpSelected->pSoldier->sGridNo; else { diff --git a/Editor/Item Statistics.cpp b/Editor/Item Statistics.cpp index e23aeeb9..ec52c648 100644 --- a/Editor/Item Statistics.cpp +++ b/Editor/Item Statistics.cpp @@ -1430,6 +1430,7 @@ void ToggleAttachment( GUI_BUTTON *btn, INT32 reason ) { INT32 i; UINT16 usAttachment = 0; + ResizeWorldItems();//dnl ch75 021113 to prevent memory corruption during resize if somehow in created item we manage to put invalid attachment (DRAGUNOV with SNIPERCOPE problem in older mapeditors) for( i = 0; i < NUM_ATTACHMENT_BUTTONS; i++ ) { //Loop through and find the button that was just modified switch( i ) @@ -1469,6 +1470,7 @@ void ToggleCeramicPlates( GUI_BUTTON *btn, INT32 reason ) { if( reason & MSYS_CALLBACK_REASON_LBUTTON_UP ) { + ResizeWorldItems();//dnl ch75 021113 just precaution to prevent eventual memory corruption during resize if somehow AttachObject find invalid attachment gfCeramicPlates ^= TRUE; if( gfCeramicPlates ) { @@ -1490,6 +1492,7 @@ void ToggleDetonator( GUI_BUTTON *btn, INT32 reason ) { if( reason & MSYS_CALLBACK_REASON_LBUTTON_UP ) { + ResizeWorldItems();//dnl ch75 021113 just precaution to prevent eventual memory corruption during resize if somehow AttachObject find invalid attachment if( !gfDetonator ) { gfDetonator = TRUE; diff --git a/Editor/editscreen.cpp b/Editor/editscreen.cpp index 0ac8682b..27762e16 100644 --- a/Editor/editscreen.cpp +++ b/Editor/editscreen.cpp @@ -2051,7 +2051,6 @@ void HandleKeyboardShortcuts( ) if( gfEditingDoor ) KillDoorEditing(); iCurrentAction = ACTION_QUIT_GAME; - return; } break; case 'z': @@ -2313,7 +2312,7 @@ UINT32 PerformSelectedAction( void ) break; case ACTION_QUIT_GAME: - gfProgramIsRunning = FALSE; + //gfProgramIsRunning = FALSE;//dnl ch75 251013 throw exception on exit without showing message box case ACTION_EXIT_EDITOR: if( EditModeShutdown( ) ) { @@ -2741,6 +2740,11 @@ UINT32 ProcessEditscreenMessageBoxResponse() { gfConfirmExitFirst = FALSE; iEditorToolbarState = TBAR_MODE_EXIT_EDIT; + if(iCurrentAction == ACTION_QUIT_GAME)//dnl ch75 251013 + { + iEditorToolbarState = TBAR_MODE_QUIT_GAME; + gfProgramIsRunning = FALSE; + } } return EDIT_SCREEN; } diff --git a/Strategic/Assignments.cpp b/Strategic/Assignments.cpp index 085d064b..e01d5759 100644 --- a/Strategic/Assignments.cpp +++ b/Strategic/Assignments.cpp @@ -6105,7 +6105,7 @@ void HandleEquipmentMove( INT16 sMapX, INT16 sMapY, INT8 bZ ) CHAR16 wSectorName[ 64 ]; GetShortSectorString( sMapX, sMapY, wSectorName ); - WORLDITEM* pWorldItem_Target = NULL; + std::vector pWorldItem_Target;//dnl ch75 271013 // now loop over all sectors from which we take stuff, and move the equipment std::map::iterator itend = sectormercmap.end(); @@ -6136,11 +6136,7 @@ void HandleEquipmentMove( INT16 sMapX, INT16 sMapY, INT8 bZ ) UINT32 uiTotalNumberOfRealItems_Target = 0; // use the new map - if ( pWorldItem_Target ) - { - delete[] pWorldItem_Target; - pWorldItem_Target = NULL; - } + pWorldItem_Target.clear();//dnl ch75 021113 if( ( gWorldSectorX == targetX )&&( gWorldSectorY == targetY ) && (gbWorldSectorZ == bZ ) ) { @@ -6157,8 +6153,8 @@ void HandleEquipmentMove( INT16 sMapX, INT16 sMapY, INT8 bZ ) if( uiTotalNumberOfRealItems_Target > 0 ) { // allocate space for the list - pWorldItem_Target = new WORLDITEM[ uiTotalNumberOfRealItems_Target ]; - + pWorldItem_Target.resize(uiTotalNumberOfRealItems_Target);//dnl ch75 271013 + // now load into mem LoadWorldItemsFromTempItemFile( targetX, targetY, bZ, pWorldItem_Target ); } @@ -6236,7 +6232,7 @@ void HandleEquipmentMove( INT16 sMapX, INT16 sMapY, INT8 bZ ) WORLDITEM* pWorldItem_tmp = NULL; if( ( gWorldSectorX != targetX ) || ( gWorldSectorY != targetY ) || (gbWorldSectorZ != bZ ) ) { - pWorldItem_tmp = new WORLDITEM[ uiTotalNumberOfRealItems_Target ]; + std::vector pWorldItem_tmp(uiTotalNumberOfRealItems_Target);//dnl ch75 271013 // copy over old inventory UINT32 newcount = 0; @@ -6250,11 +6246,7 @@ void HandleEquipmentMove( INT16 sMapX, INT16 sMapY, INT8 bZ ) } // use the new map - if ( pWorldItem_Target ) - { - delete[] pWorldItem_Target; - pWorldItem_Target = NULL; - } + pWorldItem_Target.clear();//dnl ch75 021113 pWorldItem_Target = pWorldItem_tmp; } @@ -6270,12 +6262,6 @@ void HandleEquipmentMove( INT16 sMapX, INT16 sMapY, INT8 bZ ) //Save the Items to the the file SaveWorldItemsToTempItemFile( targetX, targetY, bZ, uiTotalNumberOfRealItems_Target, pWorldItem_Target ); } - - if ( pWorldItem_tmp ) - { - delete[] pWorldItem_tmp; - pWorldItem_tmp = NULL; - } // award a bit of experience to the movers UINT16 itemsperperson = moveditems / (*it).second; diff --git a/Strategic/Hourly Update.cpp b/Strategic/Hourly Update.cpp index cbe777e3..78ebb6d1 100644 --- a/Strategic/Hourly Update.cpp +++ b/Strategic/Hourly Update.cpp @@ -457,7 +457,7 @@ void HourlyStealUpdate() // we loop over this sector's inventory and look for something shiny. We will pick it up if we hae enough space in our inventory // open sector inv UINT32 uiTotalNumberOfRealItems = 0; - WORLDITEM* pWorldItem = NULL; + std::vector pWorldItem;//dnl ch75 271013 BOOLEAN fReturn = FALSE; if( ( gWorldSectorX == pSoldier->sSectorX ) && ( gWorldSectorY == pSoldier->sSectorY ) && (gbWorldSectorZ == pSoldier->bSectorZ ) ) @@ -479,7 +479,7 @@ void HourlyStealUpdate() if( uiTotalNumberOfRealItems > 0 ) { // allocate space for the list - pWorldItem = new WORLDITEM[ uiTotalNumberOfRealItems ]; + pWorldItem.resize(uiTotalNumberOfRealItems);//dnl ch75 271013 if ( !uiTotalNumberOfRealItems ) continue; diff --git a/Strategic/Map Screen Interface Map Inventory.cpp b/Strategic/Map Screen Interface Map Inventory.cpp index c96f5d9c..87f54541 100644 --- a/Strategic/Map Screen Interface Map Inventory.cpp +++ b/Strategic/Map Screen Interface Map Inventory.cpp @@ -60,8 +60,6 @@ std::vector pInventoryPoolListQ[INVPOOLLISTNUM]; INT32 iCurrentInventoryPoolPageQ[INVPOOLLISTNUM]={ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }; INT32 iLastInventoryPoolPageQ[INVPOOLLISTNUM]={ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }; -extern BOOLEAN SaveWorldItemsToTempItemFile( INT16 sMapX, INT16 sMapY, INT8 bMapZ, UINT32 uiNumberOfItems, WORLDITEM* pData ); - #define MAP_INV_X_OFFSET (((SCREEN_WIDTH - 261) - 380) / 2) // status bar colors @@ -157,7 +155,6 @@ INT8 sObjectSourseSoldierID = -1; // number of unseen items in sector UINT32 uiNumberOfUnSeenItems = 0; - // the inventory slots //MOUSE_REGION MapInventoryPoolSlots[ MAP_INVENTORY_POOL_SLOT_COUNT ]; MOUSE_REGION MapInventoryPoolSlots[ MAP_INVENTORY_POOL_MAX_SLOTS ]; @@ -173,11 +170,13 @@ BOOLEAN gfMapInventoryItemToZoom[ MAP_INVENTORY_POOL_MAX_SLOTS ]; BOOLEAN fChangedInventorySlots = FALSE; // the unseen items list...have to save this -WORLDITEM *pUnSeenItems = NULL; - +std::vector pUnSeenItems;//dnl ch75 271013 +#ifdef INVFIX_Moa//dnl ch75 311013 // save list to write to temp file -WORLDITEM *pSaveList = NULL; - +std::vector pSaveList; +#else +std::vector& pSaveList = pUnSeenItems; +#endif INT32 giFlashHighlightedItemBaseTime = 0; //INT32 giCompatibleItemBaseTime = 0;//Moa: removed (see HandleMouseInCompatableItemForMapSectorInventory) @@ -293,7 +292,7 @@ void DrawTextOnSectorInventory( void ); INT32 GetTotalNumberOfItemsInSectorStash( void ); void HandleMapSectorInventory( void ); void ResetMapSectorInventoryPoolHighLights( void ); -void ReBuildWorldItemStashForLoadedSector( INT32 iNumberSeenItems, INT32 iNumberUnSeenItems, WORLDITEM *pSeenItemsList, WORLDITEM *pUnSeenItemsList ); +void ReBuildWorldItemStashForLoadedSector( INT32 iNumberSeenItems, INT32 iNumberUnSeenItems, std::vector& pSeenItemsList, std::vector& pUnSeenItemsList );//dnl ch75 271013 BOOLEAN IsMapScreenWorldItemVisibleInMapInventory( WORLDITEM *pWorldItem ); BOOLEAN IsMapScreenWorldItemInvisibleInMapInventory( WORLDITEM *pWorldItem ); void CheckGridNoOfItemsInMapScreenMapInventory(); @@ -344,6 +343,22 @@ void MapInventoryFilterToggle( UINT32 uiFlags ); void MapInventoryFilterSet( UINT32 uiFlags ); void HandleSetFilterButtons(); +//dnl ch75 271013 ClearAllItemPools and RefreshItemPools are relocated from "Handle Items.cpp" +void ClearAllItemPools() +{ + for(INT32 cnt=0; cnt& pItemList, INT32 iNumberOfItems) +{ + ClearAllItemPools(); + RefreshWorldItemsIntoItemPools(pItemList, iNumberOfItems); +} + // Flugente: show wether an item is set to be ignored by the 'move item' assignment. This can be toggled in strategic inventory. static BOOLEAN fShowMoveItem = TRUE; BOOLEAN IsShowMoveItem() @@ -812,7 +827,7 @@ void CreateDestroyMapInventoryPoolButtons( BOOLEAN fExitFromMapScreen ) BuildStashForSelectedSector( sSelMapX, sSelMapY, ( INT16 )( iCurrentMapSectorZ ) ); //Moa: added the handling function instead of SectorInventoryCooldown, which has loaded the items from the tempfile (loading also done in BuildStashForSelectedSector) - HandleSectorCooldownFunctions( sSelMapX, sSelMapY, (INT8)iCurrentMapSectorZ, (WORLDITEM*) &(*pInventoryPoolList.begin()) , pInventoryPoolList.size(), TRUE ); + HandleSectorCooldownFunctions( sSelMapX, sSelMapY, (INT8)iCurrentMapSectorZ, pInventoryPoolList, pInventoryPoolList.size(), TRUE );//dnl ch75 271013 //SetLastTimePlayerWasInSector( sSelMapX, sSelMapY, (INT8)iCurrentMapSectorZ ); //SaveWorldItemsToTempItemFile( sSelMapX, sSelMapY, (INT8)iCurrentMapSectorZ, pInventoryPoolList.size(), (WORLDITEM*) &(*pInventoryPoolList.begin()) ); @@ -861,10 +876,10 @@ void CreateDestroyMapInventoryPoolButtons( BOOLEAN fExitFromMapScreen ) // Reset number of desired slots so we recalculate page size entirely on the next open. giDesiredNumMapInventorySlots = -1; - +#ifdef INVFIX_Moa//dnl ch75 311013 // clear up unseen list ClearUpTempUnSeenList( ); - +#endif // undo item decay (will be saved once and only when entering sector) // HandleSectorCooldownFunctions( sSelMapX, sSelMapY, (INT8)iCurrentMapSectorZ, (WORLDITEM*) &(*pInventoryPoolList.begin()) , pInventoryPoolList.size(), TRUE , TRUE); @@ -874,9 +889,9 @@ void CreateDestroyMapInventoryPoolButtons( BOOLEAN fExitFromMapScreen ) // now save results SaveSeenAndUnseenItems( ); - +#ifdef INVFIX_Moa//dnl ch75 311013 DestroyStash( ); - +#endif // HEADROCK HAM 5: Filters! guiMapInventoryFilter = IC_MAPFILTER_ALL; @@ -917,19 +932,14 @@ void CancelSectorInventoryDisplayIfOn( BOOLEAN fExitFromMapScreen ) -void ClearUpTempUnSeenList( void ) +void ClearUpTempUnSeenList( void )//dnl ch75 271013 { // save these items and all the others - if( pUnSeenItems == NULL ) - { + if(pUnSeenItems.empty()) return; - } - // build the list based on this pSaveList = pUnSeenItems; - pUnSeenItems = NULL; - - return; + pUnSeenItems.clear(); } ////////////////////////////////////// @@ -960,6 +970,7 @@ void ClearUpTempUnSeenList( void ) ////////////////////////////////////// void SaveSeenAndUnseenItems( void ) { +#ifdef INVFIX_Moa//dnl ch75 291013 std::vector worldItemsSaveList; //exists() on front and exists() && visible != 0 on back. UINT32 iExistingItems = 0; //fExists @@ -1003,127 +1014,59 @@ void SaveSeenAndUnseenItems( void ) if( ( gWorldSectorX == sSelMapX ) && ( gWorldSectorY == sSelMapY ) && ( gbWorldSectorZ == ( INT8 ) ( iCurrentMapSectorZ ) ) ) { //handle in existing function - ReBuildWorldItemStashForLoadedSector( iExistingItems, uiNumberOfUnSeenItems, &(*worldItemsSaveList.begin()), pSaveList ); + ReBuildWorldItemStashForLoadedSector( iExistingItems, uiNumberOfUnSeenItems, worldItemsSaveList, pSaveList );//dnl ch75 271013 } else { //copy remaining unseen items into savelist - if ( uiNumberOfUnSeenItems > 0 && pSaveList != NULL) - worldItemsSaveList.insert( worldItemsSaveList.end(), pSaveList, pSaveList + uiNumberOfUnSeenItems ); + if ( uiNumberOfUnSeenItems > 0 && !pSaveList.empty() )//dnl ch75 271013 + worldItemsSaveList.insert( worldItemsSaveList.end(), pSaveList.begin(), pSaveList.end() ); //save the items to file (skipping all checks of AddWorldItemsToUnLoadedSector(), allready done here!, also we do not delete the file before we overwrite) - if ( !SaveWorldItemsToTempItemFile( sSelMapX, sSelMapY, ( INT8 ) iCurrentMapSectorZ, uiNumberOfUnSeenItems + iExistingItems, &(*worldItemsSaveList.begin()) ) ) + if ( !SaveWorldItemsToTempItemFile( sSelMapX, sSelMapY, ( INT8 ) iCurrentMapSectorZ, uiNumberOfUnSeenItems + iExistingItems, worldItemsSaveList ) )//dnl ch75 271013 { ScreenMsg( FONT_MCOLOR_LTYELLOW, MSG_BETAVERSION, L"Error: Could not save %d seen and %d unseen items to disc! Please Report.", iExistingItems, uiNumberOfUnSeenItems ); return; } } uiNumberOfUnSeenItems = 0; - if( pSaveList != NULL ) + pSaveList.clear();//dnl ch75 271013 +#else + UINT32 i, uiTotalNumberOfVisibleItems, uiNumOfSlots, uiNumberOfSeenItems; + + uiNumOfSlots = min(MAP_INVENTORY_POOL_SLOT_COUNT * ((UINT32)iLastInventoryPoolPage + 1), pInventoryPoolList.size());// Best guess if all without going into loop + uiNumberOfSeenItems = 0; + uiTotalNumberOfVisibleItems = 0; + for(i=0; i 0 ) - { - pSeenItemsList = new WORLDITEM[ iTotalNumberItems ]; - - // copy - for( iCounter = 0; iCounter < pInventoryPoolList.size(); iCounter++ ) + if(pInventoryPoolList[i].fExists && pInventoryPoolList[i].object.ubNumberOfObjects) { - if( pInventoryPoolList[ iCounter ].object.exists() == true ) - { - // copy object stuff - pSeenItemsList[ iItemCount ] = pInventoryPoolList[ iCounter ]; - - // check if item actually lives at a gridno - // if not, check predicessor, iItemCount is not 0 - if( pSeenItemsList[ iItemCount ].sGridNo == 0 ) - { - if( iItemCount > 0 ) - { - // borrow from predicessor - pSeenItemsList[ iItemCount ].sGridNo = pSeenItemsList[ iItemCount - 1 ].sGridNo; - } - else - { - // get entry grid location - } - } - pSeenItemsList[ iItemCount ].fExists = TRUE; - pSeenItemsList[ iItemCount ].bVisible = TRUE; - iItemCount++; - } + uiTotalNumberOfVisibleItems += pInventoryPoolList[i].object.ubNumberOfObjects; + if(i > uiNumberOfSeenItems) + pInventoryPoolList[uiNumberOfSeenItems++] = pInventoryPoolList[i]; + else + uiNumberOfSeenItems++; } } - - // if this is the loaded sector handle here - if( ( gWorldSectorX == sSelMapX ) && ( gWorldSectorY == sSelMapY ) && ( gbWorldSectorZ == ( INT8 ) ( iCurrentMapSectorZ ) ) ) + uiNumOfSlots = ((uiNumberOfSeenItems + uiNumberOfUnSeenItems) / MAP_INVENTORY_POOL_SLOT_COUNT + 1) * MAP_INVENTORY_POOL_SLOT_COUNT; + if(pInventoryPoolList.size() < uiNumOfSlots) + pInventoryPoolList.resize(uiNumOfSlots); + for(i=0; i 0 ) - { - // over write file and copy unseen - AddWorldItemsToUnLoadedSector( sSelMapX, sSelMapY, ( INT8 )( iCurrentMapSectorZ ), 0, uiNumberOfUnSeenItems, pSaveList, TRUE ); - - // check if seen items exist too - if( iItemCount > 0 ) - { - AddWorldItemsToUnLoadedSector( sSelMapX, sSelMapY, ( INT8 )( iCurrentMapSectorZ ), 0, iItemCount, pSeenItemsList, FALSE ); - } - - } - else if( iItemCount > 0 ) - { - // copy only seen items - AddWorldItemsToUnLoadedSector( sSelMapX, sSelMapY, ( INT8 )( iCurrentMapSectorZ ), 0, iItemCount, pSeenItemsList, TRUE ); - } - else - { - // get rid of the file - SaveWorldItemsToTempItemFile( sSelMapX, sSelMapY, ( INT8 )( iCurrentMapSectorZ ), 0, NULL ); - return; - } + Assert(SaveWorldItemsToTempItemFile(sSelMapX, sSelMapY, iCurrentMapSectorZ, uiNumberOfSeenItems + uiNumberOfUnSeenItems, pInventoryPoolList, FALSE)); + SetNumberOfVisibleWorldItemsInSectorStructureForSector(sSelMapX, sSelMapY, iCurrentMapSectorZ, uiTotalNumberOfVisibleItems); } - - // now clear out seen list - if( pSeenItemsList != NULL ) - { - delete[]( pSeenItemsList ); - pSeenItemsList = NULL; - } - - // clear out unseen list - if( pSaveList != NULL ) - { - delete[]( pSaveList ); - pSaveList = NULL; - } - - uiNumberOfUnSeenItems = 0; - iItemCount = 0; +#endif } - - // the screen mask bttn callaback...to disable the inventory and lock out the map itself void MapInvenPoolScreenMaskCallback(MOUSE_REGION * pRegion, INT32 iReason ) { @@ -1932,175 +1875,6 @@ void DestroyMapInventoryButtons( void ) return; } -INT32 GetSizeOfStashInSector_OLD( INT16 sMapX, INT16 sMapY, INT16 sMapZ, BOOLEAN fCountStacksAsOne ); -void BuildStashForSelectedSector_OLD( INT16 sMapX, INT16 sMapY, INT16 sMapZ ) -{ - INT32 iSize = 0; - UINT32 uiItemCount = 0; - UINT32 uiTotalNumberOfItems = 0, uiTotalNumberOfRealItems = 0; - WORLDITEM * pTotalSectorList = NULL; - INT32 iCounter = 0; - UINT32 uiTotalNumberOfSeenItems=0; - -// #ifdef _DEBUG - BOOLEAN fReturn = TRUE; -// #endif - - // get size of the current stash in sector (count stacks as one item) - iSize = GetSizeOfStashInSector_OLD( sMapX, sMapY, sMapZ, TRUE ); - - // round off .. we want at least 1 free page of space... - iSize = ((iSize / MAP_INVENTORY_POOL_SLOT_COUNT) + 1) * MAP_INVENTORY_POOL_SLOT_COUNT; - - // allocate space for list - pInventoryPoolList.clear(); - pInventoryPoolList.resize( iSize ); - - iLastInventoryPoolPage = ( ( iSize - 1 ) / MAP_INVENTORY_POOL_SLOT_COUNT ); - - - uiNumberOfUnSeenItems = 0; - - // now laod these items into memory, based on fact if sector is in fact loaded - if( ( sMapX == gWorldSectorX )&&( gWorldSectorY == sMapY ) &&(gbWorldSectorZ == sMapZ ) ) - { - // sector loaded, just copy from list - for( iCounter = 0; ( UINT32 )( iCounter ) < guiNumWorldItems; iCounter++ ) - { - // check if visible, if so, then copy over object type - // if visible to player, then state fact - -/* - if( gWorldItems[ iCounter].bVisible == 1 && - gWorldItems[ iCounter ].fExists && - gWorldItems[ iCounter ].object.usItem != SWITCH && - gWorldItems[ iCounter ].object.bTrap <= 0 ) -*/ - if( IsMapScreenWorldItemVisibleInMapInventory( &gWorldItems[ iCounter ] ) ) - { - // one more item - pInventoryPoolList[ uiItemCount ] = gWorldItems[ iCounter ]; - uiItemCount++; - } - } - - - uiTotalNumberOfSeenItems = uiItemCount; - - - // now allocate space for all the unseen items - if( guiNumWorldItems > uiItemCount ) - { - pUnSeenItems = new WORLDITEM[ guiNumWorldItems - uiItemCount ]; - - uiItemCount = 0; - - // now copy over - for( iCounter = 0; ( UINT32 )iCounter < guiNumWorldItems; iCounter++ ) - { - if( IsMapScreenWorldItemInvisibleInMapInventory( &gWorldItems[ iCounter ] ) ) - { - // one more item - pUnSeenItems[ uiItemCount ] = gWorldItems[ iCounter ]; - - uiItemCount++; - } - } - - // copy over number of unseen - uiNumberOfUnSeenItems = uiItemCount; - } - } - else - { - // not loaded, load - // get total number, visable and invisible - fReturn = GetNumberOfWorldItemsFromTempItemFile( sMapX, sMapY, ( INT8 )( sMapZ ), &( uiTotalNumberOfItems ), FALSE ); - Assert( fReturn ); - - fReturn = GetNumberOfActiveWorldItemsFromTempFile( sMapX, sMapY, ( INT8 )( sMapZ ), &( uiTotalNumberOfRealItems ) ); - Assert( fReturn ); - - if( uiTotalNumberOfRealItems > 0 ) - { - // allocate space for the list - pTotalSectorList = new WORLDITEM[ uiTotalNumberOfItems ]; - - - // now load into mem - LoadWorldItemsFromTempItemFile( sMapX, sMapY, ( INT8 ) ( sMapZ ), pTotalSectorList ); - - } - - - // now run through list and - for( iCounter = 0; ( UINT32 )( iCounter )< uiTotalNumberOfRealItems; iCounter++ ) - { - // if visible to player, then state fact -/* - if( pTotalSectorList[ iCounter].bVisible == 1 && - pTotalSectorList[ iCounter].fExists && - pTotalSectorList[ iCounter].object.usItem != SWITCH && - pTotalSectorList[ iCounter].object.bTrap <= 0 ) -*/ - - - //TEST!! If the item exists, and is NOT VALID, report it - if( pTotalSectorList[ iCounter].fExists && pTotalSectorList[ iCounter].object.usItem > MAXITEMS ) - { - ScreenMsg( FONT_MCOLOR_LTYELLOW, MSG_BETAVERSION, L"The %d item in the list is NOT valid. Please send save. DF 1.", iCounter ); - } - - - if( IsMapScreenWorldItemVisibleInMapInventory( &pTotalSectorList[ iCounter] ) ) - { - // one more item - pInventoryPoolList[ uiItemCount ] = pTotalSectorList[ iCounter ]; - - uiItemCount++; - } - } - - uiTotalNumberOfSeenItems = uiItemCount; - - // now allocate space for all the unseen items - if( uiTotalNumberOfRealItems > uiItemCount ) - { - pUnSeenItems = new WORLDITEM[ uiTotalNumberOfRealItems - uiItemCount ]; - - uiItemCount = 0; - - // now copy over - for( iCounter = 0; ( UINT32 )iCounter < uiTotalNumberOfItems; iCounter++ ) - { - if( IsMapScreenWorldItemInvisibleInMapInventory( &pTotalSectorList[ iCounter] ) ) - { - // one more item - pUnSeenItems[ uiItemCount ] = pTotalSectorList[ iCounter ]; - - uiItemCount++; - } - } - - // copy over number of unseen - uiNumberOfUnSeenItems = uiItemCount; - } - - // if anything was alloced, then get rid of it - if( uiTotalNumberOfRealItems > 0 ) - { - delete[]( pTotalSectorList ); - } - } - - //Check to see if any of the items in the list have a gridno of NOWHERE and the entry point flag NOT set - CheckGridNoOfItemsInMapScreenMapInventory(); - - //Sort the sector invenrtory - SortSectorInventory( pInventoryPoolList, uiTotalNumberOfSeenItems ); -} - - //////////////////////////// // @brief: Creates filtered and unfiltered lists for stash and stores them in global variables. // @@ -2125,7 +1899,7 @@ void BuildStashForSelectedSector_OLD( INT16 sMapX, INT16 sMapY, INT16 sMapZ ) //////////////////////////// void BuildStashForSelectedSector( INT16 sMapX, INT16 sMapY, INT16 sMapZ ) { - +#ifdef INVFIX_Moa//dnl ch75 301013 UINT32 fNumTotal = 0, fNumShown = 0, fNumFiltered = 0, fNumFlagsSet = 0; //itemstack count std::vector fFilteredItems; //store filtered items to be converted later to an array. std::vector fWorldItems; //store everything here what we can get (WORLDITEM.fExists == TRUE) @@ -2146,7 +1920,6 @@ void BuildStashForSelectedSector( INT16 sMapX, INT16 sMapY, INT16 sMapZ ) // sector loaded, just copy from list for( UINT32 i = 0; i < guiNumWorldItems; i++ ) { - if( IsMapScreenWorldItemVisibleInMapInventory( &gWorldItems[ i ] ) ) { if( ( gWorldItems[i].object.exists() == true ) && ( TileIsOutOfBounds(gWorldItems[ i ].sGridNo) ) && !( gWorldItems[ i ].usFlags & WORLD_ITEM_GRIDNO_NOT_SET_USE_ENTRY_POINT ) ) @@ -2218,7 +1991,7 @@ void BuildStashForSelectedSector( INT16 sMapX, INT16 sMapY, INT16 sMapZ ) pInventoryPoolList.clear( ); // load items into fWorldItems vector - if ( !LoadWorldItemsFromTempItemFile( sMapX, sMapY, (INT8) sMapZ, &(*fWorldItems.begin()) ) ) + if ( !LoadWorldItemsFromTempItemFile( sMapX, sMapY, (INT8) sMapZ, fWorldItems ) )//dnl ch75 271013 { DebugMsg( TOPIC_JA2, DBG_LEVEL_3, String("LoadWorldItemsFromTempItemFile: failed in BuildStashForSelectedSector()" ) ); return; @@ -2293,8 +2066,9 @@ void BuildStashForSelectedSector( INT16 sMapX, INT16 sMapY, INT16 sMapZ ) // to copy fFilteredItems (vector) to global (array) if (uiNumberOfUnSeenItems > 0) { - pUnSeenItems = new WORLDITEM[uiNumberOfUnSeenItems];//gets passed to pSaveList in ClearUpTempUnSeenList() and deleted by SaveSeenAndUnseenItems() - std::copy(fFilteredItems.begin(), fFilteredItems.end(), pUnSeenItems ); + //dnl ch75 271013 + pUnSeenItems.resize(uiNumberOfUnSeenItems);//gets passed to pSaveList in ClearUpTempUnSeenList() and deleted by SaveSeenAndUnseenItems() + std::copy(fFilteredItems.begin(), fFilteredItems.end(), pUnSeenItems.begin()); } //resize globallist to a multiple of MAP_INVENTORY_POOL_SLOT_COUNT + one element (some other code does expect that) pInventoryPoolList.resize(MAP_INVENTORY_POOL_SLOT_COUNT * (iLastInventoryPoolPage+1) ); @@ -2311,16 +2085,85 @@ void BuildStashForSelectedSector( INT16 sMapX, INT16 sMapY, INT16 sMapZ ) //Sort the sector inventory SortSectorInventory( pInventoryPoolList, fNumShown ); +#else + UINT32 i, uiTotalNumberOfItems, uiNumberOfSeenItems, uiNumOfSlots; + WORLDITEM *pwi, *pipl, *pusi; + if(sMapX == gWorldSectorX && gWorldSectorY == sMapY && gbWorldSectorZ == sMapZ)// if map is already loaded use gWorldItems[] and guiNumWorldItems to build lists + { + uiTotalNumberOfItems = guiNumWorldItems; + uiNumOfSlots = (uiTotalNumberOfItems / MAP_INVENTORY_POOL_SLOT_COUNT + 1) * MAP_INVENTORY_POOL_SLOT_COUNT; + if(pInventoryPoolList.size() < uiNumOfSlots) + pInventoryPoolList.resize(uiNumOfSlots); + if(pUnSeenItems.size() < uiNumOfSlots) + pUnSeenItems.resize(uiNumOfSlots); + uiNumberOfSeenItems = 0; + uiNumberOfUnSeenItems = 0; + pwi = &gWorldItems.front(); + pipl = &pInventoryPoolList.front(); + pusi = &pUnSeenItems.front(); + for(i=0; ifExists) + { + *pusi++ = *pwi; + uiNumberOfUnSeenItems++; + } + } + } + else// if map not loaded, use tempfile to build lists + { + Assert(GetNumberOfWorldItemsFromTempItemFile(sMapX, sMapY, (INT8)sMapZ, &uiTotalNumberOfItems, FALSE)); + uiNumOfSlots = (uiTotalNumberOfItems / MAP_INVENTORY_POOL_SLOT_COUNT + 1) * MAP_INVENTORY_POOL_SLOT_COUNT; + if(pInventoryPoolList.size() < uiNumOfSlots) + pInventoryPoolList.resize(uiNumOfSlots); + if(pUnSeenItems.size() < uiNumOfSlots) + pUnSeenItems.resize(uiNumOfSlots); + Assert(LoadWorldItemsFromTempItemFile(sMapX, sMapY, (INT8)sMapZ, pInventoryPoolList)); + uiNumberOfSeenItems = uiTotalNumberOfItems; + uiNumberOfUnSeenItems = 0; + for(i=0; ifExists = FALSE; + pipl->object.usItem = NONE; + pipl->object.ubNumberOfObjects = 0; + pipl++; + } + SortSectorInventory(pInventoryPoolList, uiNumberOfSeenItems); +#endif } -void ReBuildWorldItemStashForLoadedSector( INT32 iNumberSeenItems, INT32 iNumberUnSeenItems, WORLDITEM *pSeenItemsList, WORLDITEM *pUnSeenItemsList ) +void ReBuildWorldItemStashForLoadedSector( INT32 iNumberSeenItems, INT32 iNumberUnSeenItems, std::vector& pSeenItemsList, std::vector& pUnSeenItemsList )//dnl ch75 271013 { INT32 iTotalNumberOfItems = 0; INT32 iCurrentItem = 0; INT32 iCounter = 0; INT32 iRemainder = 0; UINT32 uiTotalNumberOfVisibleItems=0; - WORLDITEM * pTotalList = NULL; + std::vector pTotalList;//dnl ch75 271013 // clear out the list TrashWorldItems( ); @@ -2337,7 +2180,7 @@ void ReBuildWorldItemStashForLoadedSector( INT32 iNumberSeenItems, INT32 iNumber } // allocate space for items - pTotalList = new WORLDITEM[ iTotalNumberOfItems ]; + pTotalList.resize(iTotalNumberOfItems);//dnl ch75 271013 // place seen items in the world for( iCounter = 0; iCounter < iNumberSeenItems; iCounter++ ) @@ -2363,14 +2206,6 @@ void ReBuildWorldItemStashForLoadedSector( INT32 iNumberSeenItems, INT32 iNumber //reset the visible item count in the sector info struct SetNumberOfVisibleWorldItemsInSectorStructureForSector( gWorldSectorX, gWorldSectorY, gbWorldSectorZ , uiTotalNumberOfVisibleItems ); - - // clear out allocated space for total list - delete[]( pTotalList ); - - // reset total list - pTotalList = NULL; - - return; } void DestroyStash( void ) @@ -2379,96 +2214,6 @@ void DestroyStash( void ) pInventoryPoolList.clear(); } -//Moa: merged into BuildStashForSelectedSector -INT32 GetSizeOfStashInSector_OLD( INT16 sMapX, INT16 sMapY, INT16 sMapZ, BOOLEAN fCountStacksAsOne ) -{ - // get # of items in sector that are visible to the player - UINT32 uiTotalNumberOfItems = 0, uiTotalNumberOfRealItems = 0; - WORLDITEM * pTotalSectorList = NULL; - UINT32 uiItemCount = 0; - INT32 iCounter = 0; - BOOLEAN fReturn = TRUE; - - if( ( sMapX == gWorldSectorX ) && ( sMapY == gWorldSectorY) && ( sMapZ == gbWorldSectorZ ) ) - { - uiTotalNumberOfItems = guiNumWorldItems; - - // now run through list and - for( iCounter = 0; ( UINT32 )( iCounter )< uiTotalNumberOfItems; iCounter++ ) - { - // if visible to player, then state fact -// if( gWorldItems[ iCounter ].bVisible == 1 && gWorldItems[ iCounter ].fExists ) - if( IsMapScreenWorldItemVisibleInMapInventory( &gWorldItems[ iCounter ] ) ) - { - // add it - if ( fCountStacksAsOne ) - { - uiItemCount++; - } - else - { - uiItemCount += gWorldItems[ iCounter ].object.ubNumberOfObjects; - } - } - } - } - else - { - // get total number, visable and invisible - fReturn = GetNumberOfActiveWorldItemsFromTempFile( sMapX, sMapY, ( INT8 )( sMapZ ), &( uiTotalNumberOfRealItems ) ); - Assert( fReturn ); - - fReturn = GetNumberOfWorldItemsFromTempItemFile( sMapX, sMapY, ( INT8 )( sMapZ ), &( uiTotalNumberOfItems ), FALSE ); - Assert( fReturn ); - - if( uiTotalNumberOfItems > 0 ) - { - // allocate space for the list - pTotalSectorList = new WORLDITEM[ uiTotalNumberOfItems ]; - - // now load into mem - LoadWorldItemsFromTempItemFile( sMapX, sMapY, ( INT8 ) ( sMapZ ), pTotalSectorList ); - } - - // now run through list and - for( iCounter = 0; ( UINT32 )( iCounter )< uiTotalNumberOfRealItems; iCounter++ ) - { - // if visible to player, then state fact -// if( pTotalSectorList[ iCounter ].bVisible == 1 && pTotalSectorList[ iCounter ].fExists ) - if( IsMapScreenWorldItemVisibleInMapInventory( &pTotalSectorList[ iCounter ] ) ) - { - // add it - if ( fCountStacksAsOne ) - { - uiItemCount++; - } - else - { - uiItemCount += pTotalSectorList[ iCounter ].object.ubNumberOfObjects; - } - } - } - - // if anything was alloced, then get rid of it - if( pTotalSectorList != NULL ) - { - delete[]( pTotalSectorList ); - pTotalSectorList = NULL; - - #ifdef JA2BETAVERSION - if( uiTotalNumberOfItems == 0 ) - { - ScreenMsg( FONT_MCOLOR_LTYELLOW, MSG_BETAVERSION, L"pTotalSectorList is NOT NULL when uiTotalNumberOfRealItems is %d.", uiTotalNumberOfRealItems ); - } - #endif - } - } - - - return( uiItemCount ); -} - - void BeginInventoryPoolPtr( OBJECTTYPE *pInventorySlot ) { @@ -3290,6 +3035,7 @@ void ResizeInventoryList( void ) // to reduce the size of the inventory while we work, but that would require more wizardry - and is not actually // necessary to begin with. It's actually better and safer this way! BOOLEAN fExtraPage = FALSE; +#ifdef INVFIX_Moa//dnl ch75 311013 if (iNumEmptySlotsAtEnd >= 3 ) { // Lots of empty slots at the end, so we don't need to increase the number of pages. @@ -3301,6 +3047,23 @@ void ResizeInventoryList( void ) pInventoryPoolList.resize( __max(iOptimalSizeWithExtraEmptySlots + MAP_INVENTORY_POOL_SLOT_COUNT, giDesiredNumMapInventorySlots ) ); fExtraPage = TRUE; } +#else + if(iNumEmptySlotsAtEnd >= 3) + { + // Lots of empty slots at the end, so we don't need to increase the number of pages. + giDesiredNumMapInventorySlots = max(iOptimalSizeWithExtraEmptySlots, giDesiredNumMapInventorySlots); + } + else + { + // We want 1 extra blank page at the end, so we add the number of slots required to make that page. + giDesiredNumMapInventorySlots = max(iOptimalSizeWithExtraEmptySlots + MAP_INVENTORY_POOL_SLOT_COUNT, giDesiredNumMapInventorySlots); + fExtraPage = TRUE; + } + if(giDesiredNumMapInventorySlots > (INT32)pInventoryPoolList.size()) + pInventoryPoolList.resize(giDesiredNumMapInventorySlots); + if(giDesiredNumMapInventorySlots > (INT32)pUnSeenItems.size()) + pUnSeenItems.resize(giDesiredNumMapInventorySlots); +#endif // Set this value so that the inventory does not shrink later. If we zoom or close the inventory, this will be // automatically reset to force a complete recalculation - which is ok because we're recalculating everything in @@ -3734,6 +3497,7 @@ void CheckGridNoOfItemsInMapScreenMapInventory() void SortSectorInventory( std::vector& pInventory, UINT32 uiSizeOfArray ) { +#if 0//dnl ch75 011113 return code from v1.12 as current one is terrible slow //first, compress the inventory by stacking like items that are reachable, while moving empty items towards the back for (std::vector::iterator iter = pInventory.begin(); iter != pInventory.end(); ++iter) { //if object exists, we want to try to stack it @@ -3799,6 +3563,9 @@ void SortSectorInventory( std::vector& pInventory, UINT32 uiSizeOfArr pInventory.resize(x * MAP_INVENTORY_POOL_SLOT_COUNT); } } +#else + qsort( (LPVOID)&pInventory.front(), (size_t) uiSizeOfArray, sizeof(WORLDITEM), MapScreenSectorInventoryCompare ); +#endif } @@ -3810,15 +3577,27 @@ INT32 MapScreenSectorInventoryCompare( const void *pNum1, const void *pNum2) UINT16 usItem2Index; UINT16 ubItem1Quality; UINT16 ubItem2Quality; -/* - if(gGameExternalOptions.fEnableInventoryPoolQ)//dnl??? ch51 081009 + + //dnl ch75 011113 without this fix sort will create mess when use empty slots with improper flags settings created badly somewhere else in code + if(!(pFirst->fExists && pFirst->object.ubNumberOfObjects && pFirst->object.usItem)) { - if(pFirst->object.usItem == 0) - return(1); - else if(pSecond->object.usItem == 0) - return(-1); + pFirst->fExists = FALSE; + pFirst->object.ubNumberOfObjects = 0; + pFirst->object.usItem = NONE; + return(1); } -*/ + if(!(pSecond->fExists && pSecond->object.ubNumberOfObjects && pSecond->object.usItem)) + { + pSecond->fExists = FALSE; + pSecond->object.ubNumberOfObjects = 0; + pSecond->object.usItem = NONE; + return(-1); + } + if(!pFirst->fExists) + return(1); + if(!pSecond->fExists) + return(-1); + usItem1Index = pFirst->object.usItem; usItem2Index = pSecond->object.usItem; @@ -3830,10 +3609,11 @@ INT32 MapScreenSectorInventoryCompare( const void *pNum1, const void *pNum2) BOOLEAN CanPlayerUseSectorInventory( SOLDIERTYPE *pSelectedSoldier ) { - INT16 sSectorX, sSectorY, sSectorZ; - - if(gGameExternalOptions.fEnableInventoryPoolQ)//dnl ch51 200813 +#ifdef _DEBUG//dnl ch75 021113 + if(gGameExternalOptions.fEnableInventoryPoolQ) return(TRUE); +#endif + INT16 sSectorX, sSectorY, sSectorZ; //Get the sector that has a battle BOOLEAN fInCombat = GetCurrentBattleSectorXYZAndReturnTRUEIfThereIsABattle( &sSectorX, &sSectorY, &sSectorZ ); @@ -3953,6 +3733,8 @@ BOOLEAN SaveInventoryPoolQ(UINT8 ubSaveGameID) ret = FALSE; CreateSavedGameFileNameFromNumber(ubSaveGameID, tmpbuf); strcat(tmpbuf, ".IPQ"); + if(FileExists(tmpbuf))//dnl ch75 021113 + FileDelete(tmpbuf); hFile = FileOpen(tmpbuf, FILE_ACCESS_WRITE|FILE_OPEN_ALWAYS, FALSE); if(hFile == 0) goto ERR; @@ -3982,6 +3764,7 @@ BOOLEAN SortInventoryPoolQ(void) { if(pInventoryPoolList.size() > 0) { +#if 0//dnl ch75 311013 for(INT32 iSlotCounter=0; iSlotCounter<(INT32)pInventoryPoolList.size(); iSlotCounter++) if(pInventoryPoolList[iSlotCounter].object.usItem == NOTHING && pInventoryPoolList[iSlotCounter].object.exists() == false) { @@ -3992,30 +3775,84 @@ BOOLEAN SortInventoryPoolQ(void) iLastInventoryPoolPage = (pInventoryPoolList.size() - 1) / MAP_INVENTORY_POOL_SLOT_COUNT; if(iCurrentInventoryPoolPage > iLastInventoryPoolPage) iCurrentInventoryPoolPage = iLastInventoryPoolPage; +#else + SortSectorInventory(pInventoryPoolList, pInventoryPoolList.size()); +#endif } fMapPanelDirty = TRUE; return(TRUE); } -BOOLEAN SwitchToInventoryPoolQ(UINT8 newidx) +BOOLEAN SwitchToInventoryPoolQ(UINT8 newidx)//dnl ch75 021113 { - UINT8 curidx; - - curidx = gInventoryPoolIndex & 0x0F; + UINT8 curidx = gInventoryPoolIndex & 0x0F; + newidx &= 0x0F; + if(curidx == newidx) + return(FALSE); + MapInventoryFilterSet(IC_MAPFILTER_ALL); +#if 0 pInventoryPoolListQ[curidx] = pInventoryPoolList; +#else + UINT32 uiNumOfSlots = (iLastInventoryPoolPage + 1) * MAP_INVENTORY_POOL_SLOT_COUNT; + if(pInventoryPoolListQ[curidx].size() != uiNumOfSlots) + pInventoryPoolListQ[curidx].resize(uiNumOfSlots); + WORLDITEM *pwiQ1 = &pInventoryPoolListQ[curidx].front(); + WORLDITEM *pwiQ2 = &pInventoryPoolListQ[curidx].back(); + WORLDITEM *pwi1 = &pInventoryPoolList.front(); + WORLDITEM *pwi2 = &pInventoryPoolList.back(); + int cnt = 0; + while(pwi1 <= pwi2) + { + if(pwi1->fExists) + { + *pwiQ1 = *pwi1; + pwiQ1++; + } + pwi1++; + cnt++; + } + while(pwiQ1 <= pwiQ2) + { + pwiQ1->fExists = FALSE; + pwiQ1->object.ubNumberOfObjects = 0; + pwiQ1++; + } +#endif iCurrentInventoryPoolPageQ[curidx] = iCurrentInventoryPoolPage; iLastInventoryPoolPageQ[curidx] = iLastInventoryPoolPage; - - newidx &= 0x0F; - if (pInventoryPoolListQ[newidx].empty() == true) + if(pInventoryPoolListQ[newidx].empty() == true) pInventoryPoolListQ[newidx].resize(MAP_INVENTORY_POOL_SLOT_COUNT); +#if 0 pInventoryPoolList = pInventoryPoolListQ[newidx]; +#else + if(pInventoryPoolList.size() < pInventoryPoolListQ[newidx].size()) + pInventoryPoolList.resize(pInventoryPoolListQ[newidx].size()); + pwiQ1 = &pInventoryPoolListQ[newidx].front(); + pwiQ2 = &pInventoryPoolListQ[newidx].back(); + pwi1 = &pInventoryPoolList.front(); + pwi2 = &pInventoryPoolList.back(); + cnt = 0; + while(pwiQ1 <= pwiQ2) + { + if(pwiQ1->fExists) + { + *pwi1 = *pwiQ1; + pwi1++; + } + pwiQ1++; + cnt++; + } + while(pwi1 <= pwi2) + { + pwi1->fExists = FALSE; + pwi1->object.ubNumberOfObjects = 0; + pwi1++; + } +#endif iCurrentInventoryPoolPage = iCurrentInventoryPoolPageQ[newidx]; iLastInventoryPoolPage = iLastInventoryPoolPageQ[newidx]; - gInventoryPoolIndex = newidx | 0x30; fMapPanelDirty = TRUE; - return(TRUE); } @@ -4024,7 +3861,7 @@ BOOLEAN CopySectorInventoryToInventoryPoolQ(UINT8 idx) INT32 iSlotCounter, iSlotCounterQ; idx = gInventoryPoolIndex & 0x0F; - if(idx <= 0 || idx >= INVPOOLLISTNUM) + if(idx <= 0 || idx >= INVPOOLLISTNUM || !(gWorldSectorX == sSelMapX && gWorldSectorY == sSelMapY && gbWorldSectorZ == iCurrentMapSectorZ))//dnl ch75 021113 return(FALSE); SwitchToInventoryPoolQ('0'); iSlotCounterQ = 0; @@ -4054,37 +3891,38 @@ BOOLEAN CopySectorInventoryToInventoryPoolQ(UINT8 idx) return(TRUE); } -BOOLEAN CopySectorInventoryToInventoryPoolQs(UINT8 idx) +BOOLEAN CopySectorInventoryToInventoryPoolQs(UINT8 idx)//dnl ch75 021113 { - UINT8 defaultidx; - INT32 iSlotCounter, iSlotCounterQ[INVPOOLLISTNUM]; + UINT32 iSlotCounter, iSlotCounterQ[INVPOOLLISTNUM], usItemClass; + WORLDITEM *pipl; - idx = gInventoryPoolIndex & 0x0F; - if(!(idx == 0 || idx == 8 || idx == 9))// Only from these inventories items could be separate to 1-7 + if(!(gWorldSectorX == sSelMapX && gWorldSectorY == sSelMapY && gbWorldSectorZ == iCurrentMapSectorZ)) return(FALSE); - defaultidx = idx; memset(iSlotCounterQ, 0, sizeof(iSlotCounterQ)); for(iSlotCounter=0; iSlotCounter<(INT32)pInventoryPoolList.size(); iSlotCounter++) { - if(pInventoryPoolList[iSlotCounter].bVisible==1 && pInventoryPoolList[iSlotCounter].fExists && pInventoryPoolList[iSlotCounter].usFlags&WORLD_ITEM_REACHABLE && pInventoryPoolList[iSlotCounter].object.usItem != NOTHING) + pipl = &pInventoryPoolList[iSlotCounter]; + if(pipl->fExists) { - UINT32 usItemClass = Item[pInventoryPoolList[iSlotCounter].object.usItem].usItemClass; - if(usItemClass == IC_GUN || usItemClass == IC_LAUNCHER) + usItemClass = Item[pipl->object.usItem].usItemClass; + if(usItemClass & IC_MAPFILTER_GUN) idx = 1; - else if(usItemClass == IC_AMMO || usItemClass == IC_BELTCLIP) + else if(usItemClass & IC_MAPFILTER_AMMO) idx = 2; - else if(usItemClass == IC_BOMB || usItemClass == IC_GRENADE) + else if(usItemClass & IC_MAPFILTER_EXPLOSV) idx = 3; - else if(usItemClass == IC_BLADE || usItemClass == IC_THROWING_KNIFE || usItemClass == IC_THROWN || usItemClass == IC_PUNCH) + else if(usItemClass & IC_MAPFILTER_MELEE) idx = 4; - else if(usItemClass == IC_ARMOUR || usItemClass == IC_LBEGEAR) + else if(usItemClass & IC_MAPFILTER_ARMOR) idx = 5; - else if(usItemClass == IC_MEDKIT || usItemClass == IC_KIT || usItemClass == IC_APPLIABLE) + else if(usItemClass & IC_MAPFILTER_LBE) idx = 6; - else if(usItemClass == IC_NONE || usItemClass == IC_FACE || usItemClass == IC_KEY || usItemClass == IC_MISC || usItemClass == IC_MONEY || usItemClass == IC_TENTACLES) + else if(usItemClass & IC_MAPFILTER_KIT) idx = 7; else - idx = defaultidx; + idx = 8; + if((gInventoryPoolIndex & 0x0F) == idx) + continue; while(1) { if(iSlotCounterQ[idx] >= (INT32)pInventoryPoolListQ[idx].size()) @@ -4092,12 +3930,13 @@ BOOLEAN CopySectorInventoryToInventoryPoolQs(UINT8 idx) pInventoryPoolListQ[idx].resize(pInventoryPoolListQ[idx].size() + MAP_INVENTORY_POOL_SLOT_COUNT); iLastInventoryPoolPageQ[idx] = (pInventoryPoolListQ[idx].size() - 1) / MAP_INVENTORY_POOL_SLOT_COUNT; } - if(pInventoryPoolListQ[idx][iSlotCounterQ[idx]].object.usItem == NOTHING) + if(pInventoryPoolListQ[idx][iSlotCounterQ[idx]].object.usItem == NONE) { - pInventoryPoolListQ[idx][iSlotCounterQ[idx]] = pInventoryPoolList[iSlotCounter]; - DeleteObj(&pInventoryPoolList[iSlotCounter].object); - pInventoryPoolList[iSlotCounter].fExists = FALSE; - pInventoryPoolList[iSlotCounter].bVisible = FALSE; + pInventoryPoolListQ[idx][iSlotCounterQ[idx]] = *pipl; + pipl->object.ubNumberOfObjects = 0; + pipl->object.usItem = NONE; + pipl->fExists = FALSE; + pipl->bVisible = FALSE; iSlotCounterQ[idx]++; break; } @@ -4109,23 +3948,26 @@ BOOLEAN CopySectorInventoryToInventoryPoolQs(UINT8 idx) return(TRUE); } -BOOLEAN DisplaySectorItemsInfo(void)//dnl ch51 090913 +BOOLEAN DisplaySectorItemsInfo(void)//dnl ch51 090913 //dnl ch75 021113 { - INT32 iCounter, iItemCount, iItemTraps; - WORLDITEM *pWorldItem; - - iItemCount = 0; - iItemTraps = 0; - for(iCounter=0; (UINT32)iCounterfExists) + continue; pWorldItem = &gWorldItems[iCounter]; - if(pWorldItem->bVisible<=0 && pWorldItem->fExists && !(pWorldItem->object.usItem==NOTHING || pWorldItem->object.usItem==SWITCH || pWorldItem->object.usItem==ACTION_ITEM || pWorldItem->object.usItem==OWNERSHIP || pWorldItem->object.usItem==SYRINGE_3 || pWorldItem->object.usItem==SYRINGE_4 || pWorldItem->object.usItem==SYRINGE_5)) + if(pWorldItem->bVisible<=0 && pWorldItem->fExists && !(pWorldItem->object.usItem==NOTHING || pWorldItem->object.usItem==SWITCH || pWorldItem->object.usItem==ACTION_ITEM || pWorldItem->object.usItem==OWNERSHIP/* || pWorldItem->object.usItem==SYRINGE_3 || pWorldItem->object.usItem==SYRINGE_4 || pWorldItem->object.usItem==SYRINGE_5*/)) iItemCount++; - if(/*pWorldItem->object[0]->data.bTrap > 0 && (pWorldItem->usFlags & WORLD_ITEM_ARMED_BOMB) && */pWorldItem->object[0]->data.misc.usBombItem) + if(pWorldItem->object[0]->data.bTrap > 0) + { iItemTraps++; -// SendFmtMsg("Item%.4d:%4d %d %.4X %.4X %.2X %.2X %.2X %d", iCounter, pWorldItem->bVisible, pWorldItem->fExists, pWorldItem->sGridNo, pWorldItem->usFlags, pWorldItem->object[0]->data.bTrap, pWorldItem->object[0]->data.fUsed, pWorldItem->object[0]->data.misc.usBombItem, pWorldItem->object.usItem); + if(pWorldItem->object[0]->data.misc.usBombItem) + iItemBombs++; + } +//SendFmtMsg("Item%.4d:%4d %d %.4X %.4X %.2X %.2X %.2X %d", iCounter, pWorldItem->bVisible, pWorldItem->fExists, pWorldItem->sGridNo, pWorldItem->usFlags, pWorldItem->object[0]->data.bTrap, pWorldItem->object[0]->data.fUsed, pWorldItem->object[0]->data.misc.usBombItem, pWorldItem->object.usItem); } - ScreenMsg(FONT_MCOLOR_LTYELLOW, MSG_INTERFACE, L"%d unseen items and %d boobytraps left.", iItemCount, iItemTraps); + ScreenMsg(FONT_MCOLOR_LTYELLOW, MSG_INTERFACE, L"%d unseen items and %d boobytraps left with %d/%d bombs.", iItemCount, iItemTraps, iItemBombs, guiNumWorldBombs); return(TRUE); } //dnl ch51 081009 finish @@ -5095,11 +4937,12 @@ void SortSectorInventoryStackAndMerge(bool ammoOnly ) // NOTE: Never run this function when the pool is closed or not yet created! void RefreshSeenAndUnseenPools() { +#ifdef INVFIX_Moa//dnl ch75 011113 INT32 iItemCount = 0; // Create a new itemlist to contain all items in the sector. This is a CPU-cheap alternative to saving them // into the tempfile WorldItems list. - WORLDITEM *pItemsList = NULL; + std::vector pItemsList;//dnl ch75 271013 // What is the number of items currently seen in the Sector Inventory? INT32 iTotalNumberSeenItems = GetTotalNumberOfItems( ); // The number of Unseen items is stored in a global, so lets use it to figure out how many items are in @@ -5110,7 +4953,7 @@ void RefreshSeenAndUnseenPools() if( iTotalNumItems > 0 ) { // Point to a new array that will hold all these items. - pItemsList = new WORLDITEM[ iTotalNumItems ]; + pItemsList.resize(iTotalNumItems);//dnl ch75 271013 /////////////////// // Copy all items from the SEEN inventory @@ -5156,7 +4999,6 @@ void RefreshSeenAndUnseenPools() // Clear both the SEEN and UNSEEN lists. pInventoryPoolList.clear(); - pUnSeenItems = NULL; INT32 iCurItem = 0; INT32 iNumUnseenItems = 0; @@ -5196,7 +5038,7 @@ void RefreshSeenAndUnseenPools() // Put them in the UNSEEN list. // Create a new UNSEEN pool of this size. - pUnSeenItems = new WORLDITEM[ iNumUnseenItems ]; + pUnSeenItems.resize(iNumUnseenItems);//dnl ch75 271013 iCurItem = 0; @@ -5225,7 +5067,85 @@ void RefreshSeenAndUnseenPools() // Finally, resort the inventory. SortSectorInventory( pInventoryPoolList, pInventoryPoolList.size() ); - +#else + UINT32 i, j, uiNumOfSlots, uiUnSeenSlots; + WORLDITEM *pipl, *pusi, *pwi; + // Move previously unseen items from pUnSeenItems to pInventoryPoolList from the end as there are probably most free slots + uiNumOfSlots = pInventoryPoolList.size(); + pipl = &pInventoryPoolList.back(); + j = uiNumberOfUnSeenItems; + pusi = &pUnSeenItems.front(); + while(uiNumOfSlots && j) + { + if(pipl->fExists) + { + uiNumOfSlots--, pipl--; + continue; + } + while(j) + { + if(IsMapScreenWorldItemVisibleInMapInventory(pusi)) + { + *pipl = *pusi; + pusi->fExists = FALSE; + pusi->object.usItem = NONE; + pusi->object.ubNumberOfObjects = 0; + uiNumOfSlots--, pipl--; + j--, pusi++; + break; + } + j--, pusi++; + } + } + // Move previously seen items from pInventoryPoolList to pUnSeenItems + i = 0; + pipl = &pInventoryPoolList.front(); + j = 0; + pusi = &pUnSeenItems.front(); + uiUnSeenSlots = pUnSeenItems.size(); + while(j < uiUnSeenSlots && i < uiNumOfSlots) + { + if(pusi->fExists && j < uiNumberOfUnSeenItems) + { + j++, pusi++; + continue; + } + while(i < uiNumOfSlots) + { + if(IsMapScreenWorldItemInvisibleInMapInventory(pipl)) + { + *pusi = *pipl; + pipl->fExists = FALSE; + pipl->object.usItem = NONE; + pipl->object.ubNumberOfObjects = 0; + if(j >= uiNumberOfUnSeenItems) + uiNumberOfUnSeenItems++; + j++, pusi++; + i++, pipl++; + break; + } + i++, pipl++; + } + } + // Move empty slots to the end of pUnSeenItems and recalculate number of uiNumberOfUnSeenItems + while(j < uiNumberOfUnSeenItems) + { + if(pusi->fExists) + { + j++, pusi++; + continue; + } + pwi = &pUnSeenItems[uiNumberOfUnSeenItems-1]; + if(pwi->fExists) + { + *pusi = *pwi; + j++, pusi++; + } + uiNumberOfUnSeenItems--; + } + SortSectorInventory(pInventoryPoolList, pInventoryPoolList.size()); + fMapPanelDirty = TRUE; +#endif } void CreateMapInventoryFilterMenu( ) @@ -5496,13 +5416,15 @@ void MapInventoryFilterToggle( UINT32 uiFlags ) void MapInventoryFilterSet( UINT32 uiFlags ) { + if(guiMapInventoryFilter != uiFlags)//dnl ch75 021113 + { // Alter the filter based on the flags we want. This is a XOR operation, so we're basically // toggling the correct bits in the filter on-and-off. The bits correspond to the various // item classes - though they are often toggled in groups (i.e. Guns + Launchers, Kits + Medkits + Camokits, etc.) guiMapInventoryFilter = uiFlags; // The refresh function moves the necessary items from the Seen to the Unseen inventories, and vice versa. RefreshSeenAndUnseenPools(); - + } BlitInventoryPoolGraphic( ); HandleSetFilterButtons(); @@ -5760,7 +5682,7 @@ void HandleItemCooldownFunctions( OBJECTTYPE* itemStack, INT32 deltaSeconds, UI // if fWithMinutes = true, adjust cooldown for time since sector was last entered // otherwise its used for a turn-precise cooldown //Moa: code inside pWorldItem loop moved to HandleItemCooldownFunctions, added optional fUndo flag to undecay items (default = FALSE) -void HandleSectorCooldownFunctions( INT16 sMapX, INT16 sMapY, INT8 sMapZ, WORLDITEM* pWorldItem, UINT32 size, BOOLEAN fWithMinutes, BOOLEAN fUndo ) +void HandleSectorCooldownFunctions( INT16 sMapX, INT16 sMapY, INT8 sMapZ, std::vector& pWorldItem, UINT32 size, BOOLEAN fWithMinutes, BOOLEAN fUndo )//dnl ch75 271013 { // if not using overheating or food system, no point in all this if ( !gGameExternalOptions.fWeaponOverheating && !gGameExternalOptions.fDirtSystem && !gGameOptions.fFoodSystem ) diff --git a/Strategic/Map Screen Interface Map Inventory.h b/Strategic/Map Screen Interface Map Inventory.h index 61c14b84..3b97350f 100644 --- a/Strategic/Map Screen Interface Map Inventory.h +++ b/Strategic/Map Screen Interface Map Inventory.h @@ -84,5 +84,5 @@ BOOLEAN SwitchToInventoryPoolQ(UINT8 newidx); // Flugente: handle various cooldown functions over an array of items in a specific sector. // if fWithMinutes = true, adjust cooldown for time since sector was last entered // otherwise its used for a turn-precise cooldown -void HandleSectorCooldownFunctions( INT16 sMapX, INT16 sMapY, INT8 sMapZ, WORLDITEM* pWorldItem, UINT32 size, BOOLEAN fWithMinutes, BOOLEAN fUndo = FALSE); -void HandleItemCooldownFunctions( OBJECTTYPE* itemStack, INT32 deltaSeconds, UINT16 naturalDirt = 100, BOOLEAN isUnderground = FALSE); \ No newline at end of file +void HandleSectorCooldownFunctions( INT16 sMapX, INT16 sMapY, INT8 sMapZ, std::vector& pWorldItem, UINT32 size, BOOLEAN fWithMinutes, BOOLEAN fUndo = FALSE);//dnl ch75 271013 +void HandleItemCooldownFunctions( OBJECTTYPE* itemStack, INT32 deltaSeconds, UINT16 naturalDirt = 100, BOOLEAN isUnderground = FALSE); diff --git a/Strategic/Queen Command.cpp b/Strategic/Queen Command.cpp index ba680f3f..9f937cc7 100644 --- a/Strategic/Queen Command.cpp +++ b/Strategic/Queen Command.cpp @@ -2162,6 +2162,7 @@ void EnemyCapturesPlayerSoldier( SOLDIERTYPE *pSoldier ) RemoveCharacterFromSquads( pSoldier ); WORLDITEM WorldItem; + std::vector pWorldItem(1);//dnl ch75 271013 // Is this the first one..? if ( gubQuest[ QUEST_HELD_IN_ALMA ] == QUESTNOTSTARTED ) @@ -2186,9 +2187,9 @@ void EnemyCapturesPlayerSoldier( SOLDIERTYPE *pSoldier ) WorldItem.bVisible = FALSE; WorldItem.bRenderZHeightAboveLevel = 0; pSoldier->inv[ i ].MoveThisObjectTo(WorldItem.object); - - AddWorldItemsToUnLoadedSector( gModSettings.ubInitialPOWSectorX, gModSettings.ubInitialPOWSectorY, 0, - gModSettings.iInitialPOWItemGridNo[ gStrategicStatus.ubNumCapturedForRescue ], 1, &WorldItem, FALSE ); + //dnl ch75 271013 + pWorldItem[0] = WorldItem; + AddWorldItemsToUnLoadedSector( gModSettings.ubInitialPOWSectorX, gModSettings.ubInitialPOWSectorY, 0, gModSettings.iInitialPOWItemGridNo[ gStrategicStatus.ubNumCapturedForRescue ], 1, pWorldItem, FALSE ); } } @@ -2219,9 +2220,9 @@ void EnemyCapturesPlayerSoldier( SOLDIERTYPE *pSoldier ) WorldItem.bVisible = FALSE; WorldItem.bRenderZHeightAboveLevel = 0; pSoldier->inv[ i ].MoveThisObjectTo(WorldItem.object); - - AddWorldItemsToUnLoadedSector( gModSettings.ubMeanwhileInterrogatePOWSectorX, gModSettings.ubMeanwhileInterrogatePOWSectorY, 0, - gModSettings.iMeanwhileInterrogatePOWItemGridNo[ gStrategicStatus.ubNumCapturedForRescue ], 1, &WorldItem, FALSE ); + //dnl ch75 271013 + pWorldItem[0] = WorldItem; + AddWorldItemsToUnLoadedSector( gModSettings.ubMeanwhileInterrogatePOWSectorX, gModSettings.ubMeanwhileInterrogatePOWSectorY, 0, gModSettings.iMeanwhileInterrogatePOWItemGridNo[ gStrategicStatus.ubNumCapturedForRescue ], 1, pWorldItem, FALSE ); } } diff --git a/Strategic/Strategic Event Handler.cpp b/Strategic/Strategic Event Handler.cpp index 81a1b9f6..9f76e483 100644 --- a/Strategic/Strategic Event Handler.cpp +++ b/Strategic/Strategic Event Handler.cpp @@ -423,12 +423,9 @@ void HandleDelayedItemsArrival( UINT32 uiReason ) INT32 sStartGridNo; UINT32 uiNumWorldItems, uiLoop; BOOLEAN fOk; - WORLDITEM * pTemp = 0; + std::vector pTemp;//dnl ch75 271013 UINT8 ubLoop; - - -//#if 0 if (uiReason == NPC_SYSTEM_EVENT_ACTION_PARAM_BONUS + NPC_ACTION_RETURN_STOLEN_SHIPMENT_ITEMS ) { if ( gMercProfiles[ PABLO ].bMercStatus == MERC_IS_DEAD ) @@ -504,11 +501,7 @@ void HandleDelayedItemsArrival( UINT32 uiReason ) { return; } - pTemp = new WORLDITEM[ uiNumWorldItems]; - if (!pTemp) - { - return; - } + pTemp.resize(uiNumWorldItems);//dnl ch75 271013 fOk = LoadWorldItemsFromTempItemFile( BOBBYR_SHIPPING_DEST_SECTOR_X, BOBBYR_SHIPPING_DEST_SECTOR_Y, BOBBYR_SHIPPING_DEST_SECTOR_Z, pTemp ); if (fOk) { @@ -522,13 +515,6 @@ void HandleDelayedItemsArrival( UINT32 uiReason ) AddWorldItemsToUnLoadedSector( BOBBYR_SHIPPING_DEST_SECTOR_X, BOBBYR_SHIPPING_DEST_SECTOR_Y, BOBBYR_SHIPPING_DEST_SECTOR_Z, 0, uiNumWorldItems, pTemp, TRUE ); } } - - if (pTemp) { - delete [] pTemp; - } - -//#endif - } void AddSecondAirportAttendant( void ) diff --git a/Strategic/Strategic Town Loyalty.cpp b/Strategic/Strategic Town Loyalty.cpp index a29f64d4..4019f910 100644 --- a/Strategic/Strategic Town Loyalty.cpp +++ b/Strategic/Strategic Town Loyalty.cpp @@ -1111,7 +1111,7 @@ void RemoveRandomItemsInSector( INT16 sSectorX, INT16 sSectorY, INT16 sSectorZ, { // remove random items in sector UINT32 uiNumberOfItems = 0, iCounter = 0; - WORLDITEM *pItemList; + std::vector pItemList;//dnl ch75 271013 UINT32 uiNewTotal = 0; CHAR16 wSectorName[ 128 ]; @@ -1138,7 +1138,7 @@ void RemoveRandomItemsInSector( INT16 sSectorX, INT16 sSectorY, INT16 sSectorZ, return; } - pItemList = new WORLDITEM[ uiNumberOfItems ]; + pItemList.resize(uiNumberOfItems);//dnl ch75 271013 // now load items LoadWorldItemsFromTempItemFile( sSectorX, sSectorY, ( UINT8 )sSectorZ, pItemList ); @@ -1167,9 +1167,6 @@ void RemoveRandomItemsInSector( INT16 sSectorX, INT16 sSectorY, INT16 sSectorZ, { AddWorldItemsToUnLoadedSector( sSectorX, sSectorY, ( UINT8 )sSectorZ, 0, uiNumberOfItems, pItemList, TRUE ); } - - // mem free - delete[]( pItemList ); } else // handle a loaded sector { diff --git a/Strategic/XML_ExtraItems.cpp b/Strategic/XML_ExtraItems.cpp index c7be4a6e..6c327bc2 100644 --- a/Strategic/XML_ExtraItems.cpp +++ b/Strategic/XML_ExtraItems.cpp @@ -209,6 +209,8 @@ void AddExtraItems(UINT8 x, UINT8 y, UINT8 z, bool sectorIsLoaded) } strcat(fileName, ".xml"); + if(!FileExists(fileName))//dnl ch75 261013 just to avoid sdd::exception under debug from VFS when file not exist + return; // Open extra items file HWFILE hFile; diff --git a/Strategic/mapscreen.cpp b/Strategic/mapscreen.cpp index e87d4fc6..99dd51d0 100644 --- a/Strategic/mapscreen.cpp +++ b/Strategic/mapscreen.cpp @@ -7394,8 +7394,29 @@ void GetMapKeyboardInput( UINT32 *puiNewEvent ) case ')': SelectAllCharactersInSquad( 19 ); // internal squad #s start at 0 break; - - + case '\''://dnl ch75 021113 +#ifdef _DEBUG + // temporary add soldiers to your list for equipment inspection and general testing + for(UINT32 ubLoop=0; ubLoopbTeam == ENEMY_TEAM && MercSlots[ubLoop]->bActive) + { + for(int i=0; iubID) + break; + if(gCharactersList[i].usSolID == 0 && gCharactersList[i].fValid == FALSE) + { + gCharactersList[i].usSolID = MercSlots[ubLoop]->ubID; + gCharactersList[i].fValid = TRUE; + break; + } + } + } + } + fTeamPanelDirty = TRUE; +#endif + break; case 'a': if( fAlt ) { @@ -7881,6 +7902,24 @@ void GetMapKeyboardInput( UINT32 *puiNewEvent ) } #endif break; + case 'Q'://dnl ch75 021113 +#ifdef _DEBUG + extern UINT8 gInventoryPoolIndex; + if(fShowMapInventoryPool == TRUE && gInventoryPoolIndex == '0') + { + if(gGameExternalOptions.fEnableInventoryPoolQ) + { + gGameExternalOptions.fEnableInventoryPoolQ = FALSE; + ScreenMsg(FONT_MCOLOR_LTYELLOW, MSG_INTERFACE, L"InventoryPoolQ disabled."); + } + else + { + gGameExternalOptions.fEnableInventoryPoolQ = TRUE; + ScreenMsg(FONT_MCOLOR_LTYELLOW, MSG_INTERFACE, L"InventoryPoolQ enabled."); + } + } +#endif + break; case 'r': if( gfPreBattleInterfaceActive ) { //activate autoresolve in prebattle interface. diff --git a/Tactical/Handle Items.cpp b/Tactical/Handle Items.cpp index 9cf39cf1..c2f00af4 100644 --- a/Tactical/Handle Items.cpp +++ b/Tactical/Handle Items.cpp @@ -6207,28 +6207,6 @@ BOOLEAN ContinuePastBoobyTrapInMapScreen( OBJECTTYPE *pObject, SOLDIERTYPE *pSol return( TRUE ); } -// Well, clears all item pools -void ClearAllItemPools( ) -{ - INT32 cnt; - - for ( cnt = 0; cnt < WORLD_MAX; cnt++ ) - { - RemoveItemPool( cnt, 0 ); - RemoveItemPool( cnt, 1 ); - } -} - - -// Refresh item pools -void RefreshItemPools( WORLDITEM * pItemList, INT32 iNumberOfItems ) -{ - ClearAllItemPools( ); - - RefreshWorldItemsIntoItemPools( pItemList, iNumberOfItems ); -} - - INT32 FindNearestAvailableGridNoForItem( INT32 sSweetGridNo, INT8 ubRadius ) { INT32 sTop, sBottom; diff --git a/Tactical/Inventory Choosing.cpp b/Tactical/Inventory Choosing.cpp index ba6827b3..2e054c88 100644 --- a/Tactical/Inventory Choosing.cpp +++ b/Tactical/Inventory Choosing.cpp @@ -3671,7 +3671,7 @@ UINT32 ItemFitness_WithAmmo( OBJECTTYPE* pObj, UINT8 idx, UINT32 uiBullets ) } // retreives the next free slot in pWorldItem (we want to keep it short and not add too many items) -UINT32 GetNextFreeIndex( WORLDITEM* pWorldItem, UINT32 uiMaxCount, UINT32 uiCount ) +UINT32 GetNextFreeIndex( std::vector& pWorldItem, UINT32 uiMaxCount, UINT32 uiCount )//dnl ch75 271013 { for( ; uiCount < uiMaxCount; ++uiCount ) { @@ -3711,10 +3711,10 @@ struct ItemSearchStruct { }; // evaluate an object an remember it if it is the best so far -void EvaluateObjForItem( WORLDITEM* pWorldItem, OBJECTTYPE* pObj, UINT32 uiCount, ItemSearchStruct* pSi ) +void EvaluateObjForItem( std::vector& pWorldItem, OBJECTTYPE* pObj, UINT32 uiCount, ItemSearchStruct* pSi )//dnl ch75 271013 { // safety first - if ( !pWorldItem || !pObj || !pSi ) + if ( pWorldItem.empty() || !pObj || !pSi ) // THIS SHOULDN'T HAPPEN! return; @@ -3732,10 +3732,10 @@ void EvaluateObjForItem( WORLDITEM* pWorldItem, OBJECTTYPE* pObj, UINT32 uiCount } // special version of EvaluateObjForItem(): we take the existing ammo count into consideration -void EvaluateObjForItem_WithAmmo( WORLDITEM* pWorldItem, OBJECTTYPE* pObj, UINT32 uiCount, ItemSearchStruct* pSi, UINT32 uiBullets ) +void EvaluateObjForItem_WithAmmo( std::vector& pWorldItem, OBJECTTYPE* pObj, UINT32 uiCount, ItemSearchStruct* pSi, UINT32 uiBullets )//dnl ch75 271013 { // safety first - if ( !pWorldItem || !pObj || !pSi ) + if ( pWorldItem.empty() || !pObj || !pSi ) // THIS SHOULDN'T HAPPEN! return; @@ -3754,10 +3754,10 @@ void EvaluateObjForItem_WithAmmo( WORLDITEM* pWorldItem, OBJECTTYPE* pObj, UINT3 // forward declaration for default parameter // if pSi has an entry, move gun from pWorldItem into pp -void SearchItemRetrieval( WORLDITEM* pWorldItem, ItemSearchStruct* pSi, SOLDIERCREATE_STRUCT *pp, UINT8 usTake = 1 ); +void SearchItemRetrieval( std::vector& pWorldItem, ItemSearchStruct* pSi, SOLDIERCREATE_STRUCT *pp, UINT8 usTake = 1 );//dnl ch75 271013 // if pSi has an entry, move gun from pWorldItem into pp -void SearchItemRetrieval( WORLDITEM* pWorldItem, ItemSearchStruct* pSi, SOLDIERCREATE_STRUCT *pp, UINT8 usTake ) +void SearchItemRetrieval( std::vector& pWorldItem, ItemSearchStruct* pSi, SOLDIERCREATE_STRUCT *pp, UINT8 usTake )//dnl ch75 271013 { if ( pSi->found && !pSi->done ) { @@ -3869,7 +3869,7 @@ void MoveOneMilitiaEquipmentSet(INT16 sSourceX, INT16 sSourceY, INT16 sTargetX, BOOLEAN fReturn = FALSE; UINT32 uiTotalNumberOfRealItems = 0; UINT32 uiNumOriginalItems = 0; - WORLDITEM* pWorldItem = NULL; + std::vector pWorldItem;//dnl ch75 271013 SOLDIERCREATE_STRUCT tmp; UINT32 uiCount = 0; INT32 dummygridno = NOWHERE; @@ -3895,8 +3895,8 @@ void MoveOneMilitiaEquipmentSet(INT16 sSourceX, INT16 sSourceY, INT16 sTargetX, if( uiTotalNumberOfRealItems > 0 ) { // allocate space for the list - pWorldItem = new WORLDITEM[ uiTotalNumberOfRealItems ]; - + pWorldItem.resize(uiTotalNumberOfRealItems);//dnl ch75 271013 + // now load into mem LoadWorldItemsFromTempItemFile( sTargetX, sTargetY, 0, pWorldItem ); } @@ -3939,8 +3939,8 @@ void MoveOneMilitiaEquipmentSet(INT16 sSourceX, INT16 sSourceY, INT16 sTargetX, UINT32 uiNewInvSize = max(uiTotalNumberOfRealItems, existingitemsfound + numnewitems); // create a bigger inventory wit big enough size - WORLDITEM* pWorldItem_tmp = new WORLDITEM[ uiNewInvSize ]; - + std::vector pWorldItem_tmp(uiNewInvSize);//dnl ch75 271013 + // copy over old inventory for( uiCount = 0; uiCount < uiTotalNumberOfRealItems; ++uiCount ) { @@ -3976,7 +3976,6 @@ void MoveOneMilitiaEquipmentSet(INT16 sSourceX, INT16 sSourceY, INT16 sTargetX, // use the new map uiTotalNumberOfRealItems = uiNewInvSize; - delete[] pWorldItem; pWorldItem = pWorldItem_tmp; /////////////////////////////// ADD ITEMS FROM STRUCT TO SECTOR ///////////////////////////////////////////////////// @@ -4053,7 +4052,7 @@ void TakeMilitiaEquipmentfromSector( INT16 sMapX, INT16 sMapY, INT8 sMapZ, SOLDI { BOOLEAN fReturn = FALSE; UINT32 uiTotalNumberOfRealItems = 0; - WORLDITEM* pWorldItem = NULL; + std::vector pWorldItem;//dnl ch75 271013 UINT32 uiCount = 0; INT32 dummygridno = NOWHERE; // this gridno will be the new position of items we create (ammo crates) BOOLEAN fNightTime = NightTime(); @@ -4105,7 +4104,7 @@ void TakeMilitiaEquipmentfromSector( INT16 sMapX, INT16 sMapY, INT8 sMapZ, SOLDI if( uiTotalNumberOfRealItems > 0 ) { // allocate space for the list - pWorldItem = new WORLDITEM[ uiTotalNumberOfRealItems ]; + pWorldItem.resize(uiTotalNumberOfRealItems);//dnl ch75 271013 if ( !uiTotalNumberOfRealItems ) return; @@ -4629,7 +4628,7 @@ void TakeMilitiaEquipmentfromSector( INT16 sMapX, INT16 sMapY, INT8 sMapZ, SOLDI for(INT16 i = 0; i < pObj->ubNumberOfObjects; ++i) newammo += (*pObj)[i]->data.ubShotsLeft; - UINT32 addammo = min(usSelectedGunBulletsNeeded - usSelectedGunBulletCount, newammo); + UINT32 addammo = min((UINT32)(usSelectedGunBulletsNeeded - usSelectedGunBulletCount), newammo);//dnl ch75 271013 SpawnFittingAmmo( pp, &(pp->Inv[ HANDPOS ]), ammotype, addammo ); @@ -4726,7 +4725,7 @@ void TakeMilitiaEquipmentfromSector( INT16 sMapX, INT16 sMapY, INT8 sMapZ, SOLDI UINT32 uiNewInvSize = uiTotalNumberOfRealItems + 1; // create a bigger inventory wit big enough size - WORLDITEM* pWorldItem_tmp = new WORLDITEM[ uiNewInvSize ]; + std::vector pWorldItem_tmp(uiNewInvSize);//dnl ch75 271013 // copy over old inventory for( uiCount = 0; uiCount < uiTotalNumberOfRealItems; ++uiCount ) @@ -4747,7 +4746,6 @@ void TakeMilitiaEquipmentfromSector( INT16 sMapX, INT16 sMapY, INT8 sMapZ, SOLDI // use the new map uiTotalNumberOfRealItems = uiNewInvSize; - delete[] pWorldItem; pWorldItem = pWorldItem_tmp; } ///////////////////////////////// 3rd loop afterwork ///////////////////////////////////////////////////////// diff --git a/Tactical/Item Types.cpp b/Tactical/Item Types.cpp index 5ae4a219..f9b01a8a 100644 --- a/Tactical/Item Types.cpp +++ b/Tactical/Item Types.cpp @@ -483,9 +483,13 @@ LBENODE* OBJECTTYPE::GetLBEPointer(unsigned int index) bool OBJECTTYPE::exists() { +#if 0//dnl ch75 011113 if(this == NULL) return(FALSE); return (ubNumberOfObjects > 0 && usItem != NOTHING); +#else + return(this && ubNumberOfObjects && usItem); +#endif } void OBJECTTYPE::SpliceData(OBJECTTYPE& sourceObject, unsigned int numToSplice, StackedObjects::iterator beginIter) @@ -1671,7 +1675,7 @@ OBJECTTYPE& OBJECTTYPE::operator=(const OLD_OBJECTTYPE_101& src) (*this)[x]->attachments.resize(usAttachmentSlotIndexVector.size()); } }*/ - RemoveProhibitedAttachments(NULL, this, this->usItem); + AttachDefaultAttachments(this);//RemoveProhibitedAttachments(NULL, this, this->usItem);//dnl ch75 261013 //just a precaution //ADB ubWeight has been removed, see comments in OBJECTTYPE //this->ubWeight = CalculateObjectWeight(this); diff --git a/Tactical/Items.cpp b/Tactical/Items.cpp index e9d3483e..fcaed665 100644 --- a/Tactical/Items.cpp +++ b/Tactical/Items.cpp @@ -2448,7 +2448,7 @@ BOOLEAN ValidItemAttachment( OBJECTTYPE * pObj, UINT16 usAttachment, BOOLEAN fAt } else { - if ( fAttemptingAttachment && ValidAttachmentClass( usAttachment, pObj->usItem ) ) + if ( fAttemptingAttachment && fDisplayMessage && ValidAttachmentClass( usAttachment, pObj->usItem ) )//dnl ch75 251013 { // well, maybe the player thought he could CHAR16 zTemp[ 100 ]; @@ -5594,7 +5594,7 @@ IMPORTANT: If you use AttachObject/RemoveAttachment with fRemoveProhibited TRUE */ void RemoveProhibitedAttachments(SOLDIERTYPE* pSoldier, OBJECTTYPE* pObj, UINT16 usItem, BOOLEAN fOnlyRemoveWhenSlotsChange) { - if(!pObj->exists()) + if(!pObj->exists() || !(*pObj)[0]->AttachmentListSize())//dnl ch75 261013 return; if(UsingNewAttachmentSystem()==true){ @@ -5708,20 +5708,26 @@ void RemoveProhibitedAttachments(SOLDIERTYPE* pSoldier, OBJECTTYPE* pObj, UINT16 } else { - // put it on the ground - INT32 sGridNo = 1; - - if(guiCurrentItemDescriptionScreen == MAP_SCREEN && fShowMapInventoryPool) + // put it on the ground //dnl ch75 281013 + INT32 sGridNo = NOWHERE; + UINT8 ubLevel = 0; + for(int i=0; iAttachObject(NULL,&defaultAttachment, FALSE); } #else - if(gGameOptions.ubAttachmentSystem || gfEditMode) - { - for(UINT8 cnt=0; cntdata.gun.bGunStatus, &defaultAttachment); - pObj->AttachObject(NULL, &defaultAttachment, FALSE); - } - } + AttachDefaultAttachments(pObj);//dnl ch75 261013 #endif } @@ -15328,4 +15324,22 @@ UINT8 GetInventorySleepModifier( SOLDIERTYPE *pSoldier ) } return( modifier ); +} + +void AttachDefaultAttachments(OBJECTTYPE *pObj, BOOLEAN fAllDefaultAttachments)//dnl ch75 261013 +{ + if(pObj->usItem && gGameOptions.ubAttachmentSystem) + { + RemoveProhibitedAttachments(NULL, pObj, pObj->usItem); + //Madd: ok, so this drives me nuts -- why bother with default attachments if the map isn't going to load them for you? + //this should fix that... + for(UINT8 cnt=0; cntusItem].defaultattachments[cnt] == NONE || !(gGameOptions.ubAttachmentSystem && Item[Item[pObj->usItem].defaultattachments[cnt]].inseparable || fAllDefaultAttachments)) + break; + OBJECTTYPE defaultAttachment; + CreateItem(Item[pObj->usItem].defaultattachments[cnt], (*pObj)[0]->data.gun.bGunStatus, &defaultAttachment); + pObj->AttachObject(NULL, &defaultAttachment, FALSE); + } + } } \ No newline at end of file diff --git a/Tactical/Items.h b/Tactical/Items.h index faf214c0..f5e1b9ed 100644 --- a/Tactical/Items.h +++ b/Tactical/Items.h @@ -524,6 +524,8 @@ INT32 GetPercentRangeBonus( OBJECTTYPE * pObj ); // silversurfer: returns the SleepModifier from the characters inventory UINT8 GetInventorySleepModifier( SOLDIERTYPE *pSoldier ); +void AttachDefaultAttachments(OBJECTTYPE *pObj, BOOLEAN fAllDefaultAttachments=TRUE);//dnl ch75 261013 + #endif diff --git a/Tactical/Soldier Create.cpp b/Tactical/Soldier Create.cpp index dfd42937..a603dc74 100644 --- a/Tactical/Soldier Create.cpp +++ b/Tactical/Soldier Create.cpp @@ -2621,7 +2621,7 @@ void CreateDetailedPlacementGivenStaticDetailedPlacementAndBasicPlacementInfo( { pp->Inv[ i ] = spp->Inv[ i ]; //WarmSteel - if someone in the map editor placed a wrong attachment on this gun, fix it. - RemoveProhibitedAttachments(NULL, &pp->Inv[i], pp->Inv[i].usItem); + AttachDefaultAttachments(&pp->Inv[i]);//RemoveProhibitedAttachments(NULL, &pp->Inv[i], pp->Inv[i].usItem);//dnl ch75 261013 //return; } } diff --git a/Tactical/Tactical Save.cpp b/Tactical/Tactical Save.cpp index 4b0bc461..b9551bf8 100644 --- a/Tactical/Tactical Save.cpp +++ b/Tactical/Tactical Save.cpp @@ -570,7 +570,7 @@ BOOLEAN LoadMapTempFilesFromSavedGameFile( HWFILE hFile ) BOOLEAN UpdateWorldItemsTempFile( INT16 sMapX, INT16 sMapY, INT8 bMapZ ) { UINT32 uiTotalNumberOfItems=0; - WORLDITEM* pTotalSectorList = NULL; + std::vector pTotalSectorList;//dnl ch75 271013 BOOLEAN fReturn = GetNumberOfWorldItemsFromTempItemFile( sMapX, sMapY, bMapZ, &( uiTotalNumberOfItems ), FALSE ); if (fReturn == false) { @@ -581,7 +581,7 @@ BOOLEAN UpdateWorldItemsTempFile( INT16 sMapX, INT16 sMapY, INT8 bMapZ ) if( uiTotalNumberOfItems > 0 ) { // allocate space for the list - pTotalSectorList = new WORLDITEM[ uiTotalNumberOfItems ]; + pTotalSectorList.resize(uiTotalNumberOfItems);//dnl ch75 271013 LoadWorldItemsFromTempItemFile( sMapX, sMapY, bMapZ, pTotalSectorList ); int backup = guiCurrentSaveGameVersion; @@ -590,15 +590,6 @@ BOOLEAN UpdateWorldItemsTempFile( INT16 sMapX, INT16 sMapY, INT8 bMapZ ) guiCurrentSaveGameVersion = backup; } - - - // if anything was alloced, then get rid of it - if( pTotalSectorList != NULL ) - { - delete[]( pTotalSectorList ); - pTotalSectorList = NULL; - } - return TRUE; } @@ -626,7 +617,7 @@ BOOLEAN UpdateCIVTempFile( INT16 sMapX, INT16 sMapY, INT8 bMapZ ) } */ -BOOLEAN SaveWorldItemsToTempItemFile( INT16 sMapX, INT16 sMapY, INT8 bMapZ, UINT32 uiNumberOfItems, WORLDITEM *pData ) +BOOLEAN SaveWorldItemsToTempItemFile( INT16 sMapX, INT16 sMapY, INT8 bMapZ, UINT32 uiNumberOfItems, std::vector& pData, BOOLEAN fUpdateVisibleItems )//dnl ch75 271013 { HWFILE hFile; UINT32 uiNumBytesWritten=0; @@ -668,14 +659,15 @@ BOOLEAN SaveWorldItemsToTempItemFile( INT16 sMapX, INT16 sMapY, INT8 bMapZ, UINT SetSectorFlag( sMapX, sMapY, bMapZ, SF_ITEM_TEMP_FILE_EXISTS ); - SynchronizeItemTempFileVisbleItemsToSectorInfoVisbleItems( sMapX, sMapY, bMapZ, FALSE ); + if( fUpdateVisibleItems )//dnl ch75 311013 + SynchronizeItemTempFileVisbleItemsToSectorInfoVisbleItems( sMapX, sMapY, bMapZ, FALSE ); return( TRUE ); } -BOOLEAN LoadWorldItemsFromTempItemFile( INT16 sMapX, INT16 sMapY, INT8 bMapZ, WORLDITEM *pData ) +BOOLEAN LoadWorldItemsFromTempItemFile( INT16 sMapX, INT16 sMapY, INT8 bMapZ, std::vector& pData )//dnl ch75 271013 { UINT32 uiNumBytesRead=0; HWFILE hFile; @@ -817,7 +809,7 @@ BOOLEAN GetNumberOfWorldItemsFromTempItemFile( INT16 sMapX, INT16 sMapY, INT8 bM BOOLEAN AddItemsToUnLoadedSector( INT16 sMapX, INT16 sMapY, INT8 bMapZ, INT32 sGridNo, UINT32 uiNumberOfItemsToAdd, OBJECTTYPE *pObject, UINT8 ubLevel, UINT16 usFlags, INT8 bRenderZHeightAboveLevel, INT8 bVisible, BOOLEAN fReplaceEntireFile ) { UINT32 uiNumberOfItems=0; - WORLDITEM *pWorldItems; + std::vector pWorldItems;//dnl ch75 271013 UINT32 cnt; UINT32 uiLoop1=0; @@ -834,18 +826,12 @@ BOOLEAN AddItemsToUnLoadedSector( INT16 sMapX, INT16 sMapY, INT8 bMapZ, INT32 sG } //Allocate memeory for the item - pWorldItems = new WORLDITEM[uiNumberOfItems]; - if( pWorldItems == NULL ) - { - //Error Allocating memory for the temp item array - return( FALSE ); - } + pWorldItems.resize(uiNumberOfItems); //Load in the sectors Item Info if( !LoadWorldItemsFromTempItemFile( sMapX, sMapY, bMapZ, pWorldItems ) ) { //error reading in the items from the Item mod file - delete[] pWorldItems; return( FALSE ); } @@ -876,6 +862,7 @@ BOOLEAN AddItemsToUnLoadedSector( INT16 sMapX, INT16 sMapY, INT8 bMapZ, INT32 sG if( cnt == ( uiNumberOfItems ) ) { +#if 0//dnl ch75 271013 //Error, there wasnt a free spot. Reallocate memory for the array WORLDITEM* pTemp = new WORLDITEM[uiNumberOfItems + 1]; if( pTemp == NULL ) @@ -894,6 +881,9 @@ BOOLEAN AddItemsToUnLoadedSector( INT16 sMapX, INT16 sMapY, INT8 bMapZ, INT32 sG //set the spot were the item is to be added cnt = uiNumberOfItems - 1; +#else + pWorldItems.resize(++uiNumberOfItems); +#endif } pWorldItems[ cnt ].fExists = TRUE; @@ -931,10 +921,6 @@ BOOLEAN AddItemsToUnLoadedSector( INT16 sMapX, INT16 sMapY, INT8 bMapZ, INT32 sG //Save the Items to the the file SaveWorldItemsToTempItemFile( sMapX, sMapY, bMapZ, uiNumberOfItems, pWorldItems ); - - //Free the memory used to load in the item array - delete[]( pWorldItems ); - return( TRUE ); } @@ -1497,9 +1483,9 @@ UINT32 GetLastTimePlayerWasInSector(INT16 sMapX, INT16 sMapY, INT8 sMapZ) BOOLEAN LoadAndAddWorldItemsFromTempFile( INT16 sMapX, INT16 sMapY, INT8 bMapZ ) { UINT32 uiNumberOfItems=0; - WORLDITEM *pWorldItems = NULL; + std::vector pWorldItems;//dnl ch75 271013 UINT32 cnt; - INT32 sNewGridNo; + INT32 sNewGridNo; //Get the number of items from the file if( !GetNumberOfWorldItemsFromTempItemFile( sMapX, sMapY, bMapZ, &uiNumberOfItems, TRUE ) ) @@ -1510,12 +1496,7 @@ BOOLEAN LoadAndAddWorldItemsFromTempFile( INT16 sMapX, INT16 sMapY, INT8 bMapZ ) if( uiNumberOfItems ) { - pWorldItems = new WORLDITEM[ uiNumberOfItems ]; - if( pWorldItems == NULL ) - { - //Error Allocating memory for the temp item array - return( FALSE ); - } + pWorldItems.resize(uiNumberOfItems);//dnl ch75 271013 } else { @@ -1540,7 +1521,6 @@ BOOLEAN LoadAndAddWorldItemsFromTempFile( INT16 sMapX, INT16 sMapY, INT8 bMapZ ) //Load the World Items from the file if( !LoadWorldItemsFromTempItemFile( sMapX, sMapY, bMapZ, pWorldItems ) ) { - delete[]( pWorldItems ); return( FALSE ); } @@ -1593,8 +1573,6 @@ BOOLEAN LoadAndAddWorldItemsFromTempFile( INT16 sMapX, INT16 sMapY, INT8 bMapZ ) } } - delete[]( pWorldItems ); - return( TRUE ); } @@ -1925,12 +1903,12 @@ BOOLEAN LoadRottingCorpsesFromTempCorpseFile( INT16 sMapX, INT16 sMapY, INT8 bMa // Rewritten to load the temp file once, update with the list, and then write it. This was getting insane as items piled up in sectors. // A few dozen read, update, writes was okay but a few hundred is pushing it. -BOOLEAN AddWorldItemsToUnLoadedSector( INT16 sMapX, INT16 sMapY, INT8 bMapZ, INT32 sGridNo, UINT32 uiNumberOfItemsToAdd, WORLDITEM *pWorldItem, BOOLEAN fOverWrite ) +BOOLEAN AddWorldItemsToUnLoadedSector( INT16 sMapX, INT16 sMapY, INT8 bMapZ, INT32 sGridNo, UINT32 uiNumberOfItemsToAdd, std::vector& pWorldItem, BOOLEAN fOverWrite )//dnl ch75 271013 { UINT32 uiLoop; UINT32 uiLastItemPos; UINT32 uiNumberOfItems; - WORLDITEM *pWorldItems; + std::vector pWorldItems;//dnl ch75 271013 if( !GetNumberOfWorldItemsFromTempItemFile( sMapX, sMapY, bMapZ, &uiNumberOfItems, TRUE ) ) { @@ -1939,22 +1917,15 @@ BOOLEAN AddWorldItemsToUnLoadedSector( INT16 sMapX, INT16 sMapY, INT8 bMapZ, INT } //Allocate memory for the item - pWorldItems = new WORLDITEM[ uiNumberOfItems ]; - if( pWorldItems == NULL ) - { - //Error Allocating memory for the temp item array - return( FALSE ); - } + pWorldItems.resize(uiNumberOfItems);//dnl ch75 271013 //Load in the sectors Item Info if( !LoadWorldItemsFromTempItemFile( sMapX, sMapY, bMapZ, pWorldItems ) ) { //error reading in the items from the Item mod file - delete[] pWorldItems; return( FALSE ); } - //if we are to replace the entire file if( fOverWrite ) { @@ -1983,6 +1954,7 @@ BOOLEAN AddWorldItemsToUnLoadedSector( INT16 sMapX, INT16 sMapY, INT8 bMapZ, INT if( uiLastItemPos == ( uiNumberOfItems ) ) { +#if 0//dnl ch75 271013 //Error, there wasnt a free spot. Reallocate memory for the array WORLDITEM* pTemp; pTemp = new WORLDITEM [uiNumberOfItems + 1]; @@ -1999,6 +1971,9 @@ BOOLEAN AddWorldItemsToUnLoadedSector( INT16 sMapX, INT16 sMapY, INT8 bMapZ, INT //Increment the total number of item in the array uiNumberOfItems++; +#else + pWorldItems.resize(++uiNumberOfItems); +#endif } pWorldItems[ uiLastItemPos ].fExists = TRUE; @@ -2025,10 +2000,6 @@ BOOLEAN AddWorldItemsToUnLoadedSector( INT16 sMapX, INT16 sMapY, INT8 bMapZ, INT //Save the Items to the the file SaveWorldItemsToTempItemFile( sMapX, sMapY, bMapZ, uiNumberOfItems, pWorldItems ); - - //Free the memory used to load in the item array - delete[]( pWorldItems ); - #if 0 // The old excruciatingly inefficient code for( uiLoop=0; uiLoop pWorldItems;//dnl ch75 271013 UINT32 cnt; UINT32 uiNumberOfActive=0; BOOLEAN fFileLoaded = FALSE; @@ -2300,12 +2271,7 @@ BOOLEAN GetNumberOfActiveWorldItemsFromTempFile( INT16 sMapX, INT16 sMapY, INT8 //If there items in the data file if( uiNumberOfItems != 0 ) { - pWorldItems = new WORLDITEM[ uiNumberOfItems ]; - if( pWorldItems == NULL ) - { - //Error Allocating memory for the temp item array - return( FALSE ); - } + pWorldItems.resize(uiNumberOfItems);//dnl ch75 271013 //Load the World Items from the file if( !LoadWorldItemsFromTempItemFile( sMapX, sMapY, bMapZ, pWorldItems ) ) @@ -2317,7 +2283,6 @@ BOOLEAN GetNumberOfActiveWorldItemsFromTempFile( INT16 sMapX, INT16 sMapY, INT8 if( pWorldItems[cnt].fExists ) uiNumberOfActive++; } - delete[]( pWorldItems ); } *pNumberOfData = uiNumberOfActive; } @@ -2834,7 +2799,7 @@ BOOLEAN GetSectorFlagStatus( INT16 sMapX, INT16 sMapY, UINT8 bMapZ, UINT32 uiFla BOOLEAN AddDeadSoldierToUnLoadedSector( INT16 sMapX, INT16 sMapY, UINT8 bMapZ, SOLDIERTYPE *pSoldier, INT32 sGridNo, UINT32 uiFlags ) { UINT32 uiNumberOfItems; - WORLDITEM *pWorldItems=NULL; + std::vector pWorldItems;//dnl ch75 271013 UINT i; UINT8 bCount=0; UINT16 uiFlagsForWorldItems=0; @@ -2903,12 +2868,7 @@ BOOLEAN AddDeadSoldierToUnLoadedSector( INT16 sMapX, INT16 sMapY, UINT8 bMapZ, S if( uiNumberOfItems ) { //allocate memory for the world item array - pWorldItems = new WORLDITEM[ uiNumberOfItems ]; - if( pWorldItems == NULL ) - { - //Error Allocating memory for the temp item array - return( FALSE ); - } + pWorldItems.resize(uiNumberOfItems);//dnl ch75 271013 //loop through all the soldiers items and add them to the world item array bCount = 0; @@ -2999,10 +2959,6 @@ BOOLEAN AddDeadSoldierToUnLoadedSector( INT16 sMapX, INT16 sMapY, UINT8 bMapZ, S //Add the rotting corpse info to the sectors unloaded rotting corpse file AddRottingCorpseToUnloadedSectorsRottingCorpseFile( sMapX, sMapY, bMapZ, &Corpse); - //FRee the memory used for the pWorldItem array - delete[]( pWorldItems ); - pWorldItems = NULL; - return( TRUE ); } @@ -3375,7 +3331,7 @@ void SetNumberOfVisibleWorldItemsInSectorStructureForSector( INT16 sMapX, INT16 void SynchronizeItemTempFileVisbleItemsToSectorInfoVisbleItems( INT16 sMapX, INT16 sMapY, INT8 bMapZ, BOOLEAN fLoadingGame ) { UINT32 uiTotalNumberOfItems = 0;//, uiTotalNumberOfRealItems = 0; - WORLDITEM * pTotalSectorList = NULL; + std::vector pTotalSectorList;//dnl ch75 271013 UINT32 uiItemCount = 0; UINT32 iCounter = 0; BOOLEAN fReturn; @@ -3399,7 +3355,7 @@ void SynchronizeItemTempFileVisbleItemsToSectorInfoVisbleItems( INT16 sMapX, INT if( uiTotalNumberOfItems > 0 ) { // allocate space for the list - pTotalSectorList = new WORLDITEM[ uiTotalNumberOfItems ]; + pTotalSectorList.resize(uiTotalNumberOfItems);//dnl ch75 271013 // now load into mem LoadWorldItemsFromTempItemFile( sMapX, sMapY, bMapZ, pTotalSectorList ); @@ -3416,13 +3372,6 @@ void SynchronizeItemTempFileVisbleItemsToSectorInfoVisbleItems( INT16 sMapX, INT } } - // if anything was alloced, then get rid of it - if( pTotalSectorList != NULL ) - { - delete[]( pTotalSectorList ); - pTotalSectorList = NULL; - } - #ifdef JA2BETAVERSION if( fLoadingGame && guiCurrentSaveGameVersion >= 86 ) { diff --git a/Tactical/Tactical Save.h b/Tactical/Tactical Save.h index 4a3da993..393ef88d 100644 --- a/Tactical/Tactical Save.h +++ b/Tactical/Tactical Save.h @@ -47,9 +47,9 @@ BOOLEAN SaveCurrentSectorsInformationToTempItemFile( ); BOOLEAN LoadCurrentSectorsInformationFromTempItemsFile(); // Loads a World Item array from that sectors temp item file -BOOLEAN LoadWorldItemsFromTempItemFile( INT16 sMapX, INT16 sMapY, INT8 bMapZ, WORLDITEM *pData ); +BOOLEAN LoadWorldItemsFromTempItemFile( INT16 sMapX, INT16 sMapY, INT8 bMapZ, std::vector& pData );//dnl ch75 271013 -BOOLEAN SaveWorldItemsToTempItemFile( INT16 sMapX, INT16 sMapY, INT8 bMapZ, UINT32 uiNumberOfItems, WORLDITEM *pData ); +BOOLEAN SaveWorldItemsToTempItemFile( INT16 sMapX, INT16 sMapY, INT8 bMapZ, UINT32 uiNumberOfItems, std::vector& pData, BOOLEAN fUpdateVisibleItems=TRUE );//dnl ch75 271013 //When the savegame version changes, load the temp files, then immediately save them again in the new format BOOLEAN UpdateWorldItemsTempFile( INT16 sMapX, INT16 sMapY, INT8 bMapZ ); @@ -59,7 +59,7 @@ BOOLEAN UpdateWorldItemsTempFile( INT16 sMapX, INT16 sMapY, INT8 bMapZ ); BOOLEAN AddItemsToUnLoadedSector( INT16 sMapX, INT16 sMapY, INT8 bMapZ, INT32 sGridNo, UINT32 uiNumberOfItems, OBJECTTYPE *pObject, UINT8 ubLevel, UINT16 usFlags, INT8 bRenderZHeightAboveLevel, INT8 bVisible, BOOLEAN fReplaceEntireFile ); -BOOLEAN AddWorldItemsToUnLoadedSector( INT16 sMapX, INT16 sMapY, INT8 bMapZ, INT32 sGridNo, UINT32 uiNumberOfItems, WORLDITEM *pWorldItem, BOOLEAN fOverWrite ); +BOOLEAN AddWorldItemsToUnLoadedSector( INT16 sMapX, INT16 sMapY, INT8 bMapZ, INT32 sGridNo, UINT32 uiNumberOfItems, std::vector& pWorldItem, BOOLEAN fOverWrite );//dnl ch75 271013 //Deletes all the Temp files in the Maps\Temp directory BOOLEAN InitTacticalSave( BOOLEAN fCreateTempDir ); diff --git a/Tactical/Turn Based Input.cpp b/Tactical/Turn Based Input.cpp index 28990dd6..5d410d70 100644 --- a/Tactical/Turn Based Input.cpp +++ b/Tactical/Turn Based Input.cpp @@ -113,9 +113,9 @@ #include "connect.h" #include "fresh_header.h" - #include "IMP Skill Trait.h" // added by Flugente #include "SkillMenu.h" // added by Flugente +#include "Map Screen Interface Map Inventory.h"//dnl ch75 021113 //forward declarations of common classes to eliminate includes class OBJECTTYPE; @@ -2368,7 +2368,14 @@ void GetKeyboardInput( UINT32 *puiNewEvent ) ClearDisplayedListOfTacticalStrings( ); } break; - +#if 0//dnl ch75 021113 + case '\"': + Testing(1); + break; + case '\'': + Testing(2); + break; +#endif case '1': if( fAlt ) @@ -2496,6 +2503,9 @@ void GetKeyboardInput( UINT32 *puiNewEvent ) break; case '$': + if(fCtrl && gGameExternalOptions.fEnableInventoryPoolQ)//dnl ch75 021113 + DisplaySectorItemsInfo(); + else { // Flugente: trait skill selection menu. Yes, screw squad 13 INT32 usMapPos; @@ -3416,23 +3426,21 @@ void GetKeyboardInput( UINT32 *puiNewEvent ) } break; case 'I': - //CHRISL: This will create a large number of objects for checking overloading - if( fAlt && fCtrl ) + //CHRISL: This will create a large number of objects for checking overloading //dnl ch75 251013 + if(fAlt && fCtrl) { - INT32 tempMapPos = usMapPos; - if( CHEATER_CHEAT_LEVEL( ) ) + if(CHEATER_CHEAT_LEVEL()) { - for(UINT16 i = 1; i < 1300; i++) + for(UINT16 i=FIRST_WEAPON; i gWorldItems;//dnl ch75 261013 UINT32 guiNumWorldItems = 0; WORLDBOMB * gWorldBombs = NULL; @@ -393,43 +393,16 @@ void FindPanicBombsAndTriggers( void ) } } -INT32 GetFreeWorldItemIndex( void ) +UINT32 GetFreeWorldItemIndex(void)//dnl ch75 271013 { UINT32 uiCount; - WORLDITEM *newWorldItems; - UINT32 uiOldNumWorldItems; - - for(uiCount=0; uiCount < guiNumWorldItems; uiCount++) - { - if ( gWorldItems[ uiCount ].fExists == FALSE ) - return( (INT32)uiCount ); - } - - uiOldNumWorldItems = guiNumWorldItems; - // grow by 3/2 as a better strategy, minimum 10 - guiNumWorldItems = max(10, guiNumWorldItems * 3 / 2); - //Allocate new table with max+10 items. - newWorldItems = new WORLDITEM [ guiNumWorldItems ]; - if (newWorldItems == NULL) - { - return( -1 ); - } - - if (gWorldItems) - { - for (unsigned int x = 0; x < uiOldNumWorldItems; ++x) - { - newWorldItems[x] = gWorldItems[x]; - } - delete[] gWorldItems; - } - gWorldItems = newWorldItems; - - // Return uiCount..... - return( uiCount ); + for(uiCount=0; uiCount& pItemList, INT32 iNumberOfItems )//dnl ch75 271013 { INT32 i; diff --git a/Tactical/World Items.h b/Tactical/World Items.h index 2a3f4b6a..a8e5b550 100644 --- a/Tactical/World Items.h +++ b/Tactical/World Items.h @@ -102,7 +102,7 @@ public: #define SIZEOF_WORLDITEM_POD (offsetof(WORLDITEM, endOfPod)) #define _OLD_SIZEOF_WORLDITEM_POD (offsetof(_OLD_WORLDITEM, endOfPod)) -extern WORLDITEM *gWorldItems; +extern std::vector gWorldItems;//dnl ch75 261013 extern UINT32 guiNumWorldItems; INT32 AddItemToWorld( INT32 sGridNo, OBJECTTYPE *pObject, UINT8 ubLevel, UINT16 usFlags, INT8 bRenderZHeightAboveLevel, INT8 bVisible, INT8 soldierID ); @@ -133,7 +133,8 @@ extern INT32 FindWorldItemForBombInGridNo( INT32 sGridNo, INT8 bLevel); // Flugente: is there a planted tripwire at this gridno? fKnown = TRUE: only return true if we know of that one already extern INT32 FindWorldItemForTripwireInGridNo( INT32 sGridNo, INT8 bLevel, BOOLEAN fKnown = TRUE ); -void RefreshWorldItemsIntoItemPools( WORLDITEM * pItemList, INT32 iNumberOfItems ); +void ResizeWorldItems(void);//dnl ch75 271013 +void RefreshWorldItemsIntoItemPools( std::vector& pItemList, INT32 iNumberOfItems );//dnl ch75 271013 void CoolDownWorldItems( ); // Flugente: Cool/decay down all items in this sector -#endif \ No newline at end of file +#endif diff --git a/TileEngine/Explosion Control.cpp b/TileEngine/Explosion Control.cpp index 38728071..f1097a60 100644 --- a/TileEngine/Explosion Control.cpp +++ b/TileEngine/Explosion Control.cpp @@ -3893,7 +3893,7 @@ void HandleExplosionQueue( void ) uiCurrentTime = GetJA2Clock(); // WDS 07/25/2008 - Avoid error where gWorldItems and/or gWorldBombs is nil - if (gWorldBombs && gWorldItems) { + if (gWorldBombs && !gWorldItems.empty()) {//dnl ch75 271013 for ( uiIndex = 0; uiIndex < gubElementsOnExplosionQueue; uiIndex++ ) { if ( gExplosionQueue[ uiIndex ].fExists && uiCurrentTime >= gExplosionQueue[ uiIndex ].uiTimeStamp )