//This will automatically update obsolete map versions to the new ones. This will even //work in the game itself, but would require conversion to happen every time. This is completely //transparent to the rest of the game, but in the editor, obsolete versions will be updated upon //loading and won't be permanently updated until the map is saved, regardless of changes. void UpdateOldVersionMap() { #if 0 //This code is no longer needed since the major version update from 1.0 to 4.0 //However, I am keeping it in for reference. SOLDIERINITNODE *curr; INT32 i; LEVELNODE *pStruct; //VERSION 0 -- obsolete November 14, 1997 if( gMapInformation.ubMapVersion == 0 ) { //Soldier information contained two fixable bugs. gMapInformation.ubMapVersion++; curr = gSoldierInitHead; while( curr ) { //Bug #01) Nodes without detailed slots weren't initialized. if( !curr->pBasicPlacement->fDetailedPlacement ) curr->pDetailedPlacement = NULL; //Bug #02) The attitude variable was accidentally being generated like attributes // which put it completely out of range. if( curr->pBasicPlacement->bAttitude > 7 ) curr->pBasicPlacement->bAttitude = (INT8)Random(8); //go to next node curr = curr->next; } } //VERSION 1 -- obsolete January 7, 1998 if( gMapInformation.ubMapVersion == 1 ) { gMapInformation.ubMapVersion++; //Bug #03) Removing all wall decals from map, because of new changes to the slots // as well as certain decals found commonly in illegal places. for( i = 0; i < WORLD_MAX; i++ ) { RemoveAllStructsOfTypeRange( i, FIRSTWALLDECAL, LASTWALLDECAL ); RemoveAllStructsOfTypeRange( i, FIFTHWALLDECAL, SIXTHWALLDECAL ); } } //VERSION 2 -- obsolete February 3, 1998 if( gMapInformation.ubMapVersion == 2 ) { gMapInformation.ubMapVersion++; curr = gSoldierInitHead; while( curr ) { //Bug #04) Assign enemy mercs default army color code if applicable if( curr->pBasicPlacement->bTeam == ENEMY_TEAM && !curr->pBasicPlacement->ubSoldierClass ) { if( !curr->pDetailedPlacement ) { curr->pBasicPlacement->ubSoldierClass = SOLDIER_CLASS_ARMY; } else if( curr->pDetailedPlacement && curr->pDetailedPlacement->ubProfile == NO_PROFILE ) { curr->pBasicPlacement->ubSoldierClass = SOLDIER_CLASS_ARMY; curr->pDetailedPlacement->ubSoldierClass = SOLDIER_CLASS_ARMY; } } curr = curr->next; } } //VERSION 3 -- obsolete February 9, 1998 if( gMapInformation.ubMapVersion == 3 ) { gMapInformation.ubMapVersion++; //Bug #05) Move entry points down if necessary. ValidateEntryPointGridNo( &gMapInformation.sNorthGridNo ); ValidateEntryPointGridNo( &gMapInformation.sEastGridNo ); ValidateEntryPointGridNo( &gMapInformation.sSouthGridNo ); ValidateEntryPointGridNo( &gMapInformation.sWestGridNo ); } //VERSION 4 -- obsolete February 25, 1998 if( gMapInformation.ubMapVersion == 4 ) { gMapInformation.ubMapVersion++; //6) Change all doors to FIRSTDOOR for( i = 0; i < WORLD_MAX; i++ ) { //NOTE: Here are the index values for the various doors //DOOR OPEN CLOSED //FIRST 916 912 //SECOND 936 932 //THIRD 956 952 //FOURTH 976 972 pStruct = gpWorldLevelData[ i ].pStructHead; while( pStruct ) { //outside topleft if( pStruct->usIndex == 932 || pStruct->usIndex == 952 || pStruct->usIndex == 972 ) { ReplaceStructIndex( i, pStruct->usIndex, 912 ); break; } else if( pStruct->usIndex == 936 || pStruct->usIndex == 956 || pStruct->usIndex == 976 ) { ReplaceStructIndex( i, pStruct->usIndex, 916 ); break; } //outside topright else if( pStruct->usIndex == 927 || pStruct->usIndex == 947 || pStruct->usIndex == 967 ) { ReplaceStructIndex( i, pStruct->usIndex, 907 ); break; } else if( pStruct->usIndex == 931 || pStruct->usIndex == 951 || pStruct->usIndex == 971 ) { ReplaceStructIndex( i, pStruct->usIndex, 911 ); break; } //inside topleft else if( pStruct->usIndex == 942 || pStruct->usIndex == 962 || pStruct->usIndex == 982 ) { ReplaceStructIndex( i, pStruct->usIndex, 922 ); break; } else if( pStruct->usIndex == 946 || pStruct->usIndex == 966 || pStruct->usIndex == 986 ) { ReplaceStructIndex( i, pStruct->usIndex, 926 ); break; } //inside topright else if( pStruct->usIndex == 937 || pStruct->usIndex == 957 || pStruct->usIndex == 977 ) { ReplaceStructIndex( i, pStruct->usIndex, 917 ); break; } else if( pStruct->usIndex == 941 || pStruct->usIndex == 961 || pStruct->usIndex == 981 ) { ReplaceStructIndex( i, pStruct->usIndex, 921 ); break; } pStruct = pStruct->pNext; } } } //VERSION 5 -- obsolete March 4, 1998 if( gMapInformation.ubMapVersion == 5 ) { gMapInformation.ubMapVersion++; //Bug 7) Remove all exit grids (the format has changed) for( i = 0; i < WORLD_MAX; i++ ) RemoveExitGridFromWorld( i ); } //VERSION 6 -- obsolete March 9, 1998 if( gMapInformation.ubMapVersion == 6 ) { //Bug 8) Change droppable status of merc items so that they are all undroppable. gMapInformation.ubMapVersion++; curr = gSoldierInitHead; while( curr ) { //Bug #04) Assign enemy mercs default army color code if applicable if( curr->pDetailedPlacement ) { for( i = 0; i < curr->pDetailedPlacement->Inv.size(); i++ ) { //make all items undroppable, even if it is empty. This will allow for //random item generation, while empty, droppable slots are locked as empty //during random item generation. curr->pDetailedPlacement->Inv[ i ].fFlags |= OBJECT_UNDROPPABLE; } } curr = curr->next; } } //VERSION 7 -- obsolete April 14, 1998 if( gMapInformation.ubMapVersion == 7 ) { gMapInformation.ubMapVersion++; //Bug 9) Priority placements have been dropped in favor of splitting it into two categories. // The first is Detailed placements, and the second is priority existance. So, all // current detailed placements will also have priority existance. curr = gSoldierInitHead; while( curr ) { if( curr->pDetailedPlacement ) { curr->pBasicPlacement->fPriorityExistance = TRUE; } curr = curr->next; } } if( gMapInformation.ubMapVersion == 14 ) { //Toast all of the ambiguous road pieces that ended up wrapping the byte. LEVELNODE *pStruct, *pStruct2; INT32 i; for( i = 0; i < WORLD_MAX; i++ ) { pStruct = gpWorldLevelData[ i ].pObjectHead; if( pStruct && pStruct->usIndex == 1078 && i < WORLD_MAX-2 && i >= 320 ) { //This is the only detectable road piece that we can repair. pStruct2 = gpWorldLevelData[ i+1 ].pObjectHead; if( pStruct2 && pStruct2->usIndex == 1081 ) { RemoveObject( i, pStruct->usIndex ); RemoveObject( i+1, pStruct->usIndex+1 ); RemoveObject( i+2, pStruct->usIndex+2 ); RemoveObject( i-160, pStruct->usIndex-160 ); RemoveObject( i-159, pStruct->usIndex-159 ); RemoveObject( i-158, pStruct->usIndex-158 ); RemoveObject( i-320, pStruct->usIndex-320 ); RemoveObject( i-319, pStruct->usIndex-319 ); RemoveObject( i-318, pStruct->usIndex-318 ); AddObjectToTail( i, 1334 ); AddObjectToTail( i-160, 1335 ); AddObjectToTail( i-320, 1336 ); AddObjectToTail( i+1, 1337 ); AddObjectToTail( i-159, 1338 ); AddObjectToTail( i-319, 1339 ); AddObjectToTail( i+2, 1340 ); AddObjectToTail( i-158, 1341 ); AddObjectToTail( i-318, 1342 ); } } else if( pStruct && pStruct->usIndex >= 1079 && pStruct->usIndex < 1115 ) { RemoveObject( i, pStruct->usIndex ); } } } if( gMapInformation.ubMapVersion <= 7 ) { if( gfEditMode ) { #ifdef JA2TESTVERSION ScreenMsg( FONT_MCOLOR_RED, MSG_ERROR, L"Currently loaded map is corrupt! Allowing the map to load anyway!" ); #endif } else { if( gbWorldSectorZ ) { AssertMsg( 0, String( "Currently loaded map (%c%d_b%d.dat) is invalid -- less than the minimum supported version.", gWorldSectorY + 'A' - 1, gWorldSectorX, gbWorldSectorZ ) ); } else if( !gbWorldSectorZ ) { AssertMsg( 0, String( "Currently loaded map (%c%d.dat) is invalid -- less than the minimum supported version.", gWorldSectorY + 'A' - 1, gWorldSectorX ) ); } } } //VERSION 8 -- obsolete April 18, 1998 if( gMapInformation.ubMapVersion == 8 ) { gMapInformation.ubMapVersion++; //Bug 10) Padding on detailed placements is uninitialized. Clear all data starting at // fKillSlotIfOwnerDies. curr = gSoldierInitHead; while( curr ) { if( curr->pDetailedPlacement ) { //The size 120 was hand calculated. The remaining padding was 118 bytes //and there were two one byte fields cleared, fKillSlotIfOwnerDies and ubScheduleID memset( &curr->pDetailedPlacement->fKillSlotIfOwnerDies, 0, 120 ); } curr = curr->next; } } //Version 9 -- Kris -- obsolete April 27, 1998 if( gMapInformation.ubMapVersion == 9 ) { gMapInformation.ubMapVersion++; curr = gSoldierInitHead; while( curr ) { //Bug 11) Convert all wheelchaired placement bodytypes to cows. Result of change in the animation database. if( curr->pDetailedPlacement && curr->pDetailedPlacement->bBodyType == CRIPPLECIV ) { curr->pDetailedPlacement->bBodyType = COW; curr->pBasicPlacement->bBodyType = COW; } curr = curr->next; } } if( gMapInformation.ubMapVersion < 12 ) { gMapInformation.ubMapVersion = 12; gMapInformation.sCenterGridNo = -1; } if( gMapInformation.ubMapVersion < 13 ) { //replace all merc ammo inventory slots status value with the max ammo that the clip can hold. INT32 i, cnt; OBJECTTYPE *pItem; gMapInformation.ubMapVersion++; //Bug 10) Padding on detailed placements is uninitialized. Clear all data starting at // fKillSlotIfOwnerDies. curr = gSoldierInitHead; while( curr ) { if( curr->pDetailedPlacement ) { for ( i = 0; i < curr->pDetailedPlacement->Inv.size(); i++ ) { pItem = &curr->pDetailedPlacement->Inv[ i ]; if( Item[ pItem->usItem ].usItemClass & IC_AMMO ) { for( cnt = 0; cnt < pItem->ubNumberOfObjects; cnt++ ) { pItem->shots.ubShotsLeft[ cnt ] = Magazine[ Item[ pItem->usItem ].ubClassIndex ].ubMagSize; } } } } curr = curr->next; } } if( gMapInformation.ubMapVersion < 14 ) { gMapInformation.ubMapVersion++; if( !gfCaves && !gfBasement ) { ReplaceObsoleteRoads(); } } if( gMapInformation.ubMapVersion < 15 ) { //Do nothing. The object layer was expanded from 1 byte to 2 bytes, effecting the //size of the maps. This was due to the fact that the ROADPIECES tileset contains //over 300 pieces, hence requiring a size increase of the tileset subindex for this //layer only. } #endif //end of MAJOR VERSION 3.0 obsolete code if( gMapInformation.ubMapVersion < 15 ) { AssertMsg( 0, "Map is less than minimum supported version." ); } if( gMapInformation.ubMapVersion < 16 ) { gMapInformation.ubMapVersion = 16; gMapInformation.sIsolatedGridNo = -1; } if( gMapInformation.ubMapVersion < 17 ) { gMapInformation.ubMapVersion = 17; //EliminateObjectLayerRedundancy(); } if( gMapInformation.ubMapVersion < 18 ) { // replace useless crowbars with proper ones UINT32 i; gMapInformation.ubMapVersion = 18; for ( i = 0; i < guiNumWorldItems; i++ ) { if ( gWorldItems[ i ].object.usItem == JAR_ELIXIR ) { gWorldItems[ i ].object.usItem = CROWBAR; } } } if( gMapInformation.ubMapVersion < 19 ) { //Do nothing, this is used to force regenerate the map edgepoints in map edgepoints.c gMapInformation.ubMapVersion = 19; } if( gMapInformation.ubMapVersion < 20 ) { //validate the map entry points as the world boundaries have changed. gMapInformation.ubMapVersion = 20; ValidateEntryPointGridNo( &gMapInformation.sNorthGridNo ); ValidateEntryPointGridNo( &gMapInformation.sEastGridNo ); ValidateEntryPointGridNo( &gMapInformation.sSouthGridNo ); ValidateEntryPointGridNo( &gMapInformation.sWestGridNo ); ValidateEntryPointGridNo( &gMapInformation.sCenterGridNo ); ValidateEntryPointGridNo( &gMapInformation.sIsolatedGridNo ); } if( gMapInformation.ubMapVersion < 21 ) { SOLDIERINITNODE *curr; //override any item slots being locked if there is no item in that slot. //Laymen terms: If any items slots are locked to be empty, make them empty but available //for random item generation. gMapInformation.ubMapVersion = 21; curr = gSoldierInitHead; while( curr ) { if( curr->pDetailedPlacement ) { for( UINT32 i = 0; i < curr->pDetailedPlacement->Inv.size(); i++ ) { if( !curr->pDetailedPlacement->Inv[ i ].usItem ) { if( curr->pDetailedPlacement->Inv[ i ].fFlags & OBJECT_UNDROPPABLE ) { if( curr->pDetailedPlacement->Inv[ i ].fFlags & OBJECT_NO_OVERWRITE ) { curr->pDetailedPlacement->Inv[ i ].fFlags &= ~OBJECT_NO_OVERWRITE; } } } } } curr = curr->next; } } if( gMapInformation.ubMapVersion < 22 ) { //Allow map edgepoints to be regenerated as new system has been reenabled. gMapInformation.ubMapVersion = 22; } if( gMapInformation.ubMapVersion < 23 ) { //Allow map edgepoints to be regenerated as new system has been reenabled. SOLDIERINITNODE *curr; gMapInformation.ubMapVersion = 23; if( giCurrentTilesetID == 1 ) //cave/mine tileset only { //convert all civilians to miners which use uniforms and more masculine body types. curr = gSoldierInitHead; while( curr ) { if( curr->pBasicPlacement->bTeam == CIV_TEAM && !curr->pDetailedPlacement ) { curr->pBasicPlacement->ubSoldierClass = SOLDIER_CLASS_MINER; curr->pBasicPlacement->bBodyType = -1; } curr = curr->next; } } } if( gMapInformation.ubMapVersion < 25 ) { gMapInformation.ubMapVersion = 25; if( gfCaves ) { LightSetBaseLevel( 13 ); } } if( gMapInformation.ubMapVersion < 26 ) { //Allow map edgepoints to be regenerated as new system has been reenabled. gMapInformation.ubMapVersion = 26; } if( gMapInformation.ubMapVersion < 27 ) { //Allow map edgepoints to be regenerated as new system has been reenabled. gMapInformation.ubMapVersion = 27; } if( gMapInformation.ubMapVersion < 29 ) { gMapInformation.ubMapVersion = 29; } }
//Because loading and saving the map takes a few seconds, we want to post a message //on the screen and then update it which requires passing the screen back to the main loop. //When we come back for the next frame, we then actually save or load the map. So this //process takes two full screen cycles. UINT32 ProcessFileIO() { INT16 usStartX, usStartY; CHAR8 ubNewFilename[50]; BOOLEAN fAltMap;//dnl ch31 150909 switch( gbCurrentFileIOStatus ) { case INITIATE_MAP_SAVE: //draw save message StartFrameBufferRender( ); SaveFontSettings(); SetFont( HUGEFONT ); SetFontForeground( FONT_LTKHAKI ); SetFontShadow( FONT_DKKHAKI ); SetFontBackground( 0 ); swprintf( zOrigName, L"Saving map: %s", gzFilename ); usStartX = iScreenWidthOffset + 320 - StringPixLength( zOrigName, LARGEFONT1 ) / 2; usStartY = iScreenHeightOffset + 180 - GetFontHeight( LARGEFONT1 ) / 2; mprintf( usStartX, usStartY, zOrigName ); InvalidateScreen( ); EndFrameBufferRender( ); gbCurrentFileIOStatus = SAVING_MAP; return LOADSAVE_SCREEN; case SAVING_MAP: //save map sprintf( ubNewFilename, "%S", gzFilename ); RaiseWorldLand(); if( gfShowPits ) RemoveAllPits(); OptimizeSchedules(); ShowHighGround(4);//dnl ch41 210909 //dnl ch33 091009 BOOLEAN fRet; if(gfVanillaMode && iNewMapWorldRows == OLD_WORLD_ROWS && iNewMapWorldCols == OLD_WORLD_COLS) fRet = SaveWorld(ubNewFilename, VANILLA_MAJOR_MAP_VERSION, VANILLA_MINOR_MAP_VERSION); else fRet = SaveWorld(ubNewFilename); if(!fRet) { //dnl ch37 150909 gfSaveError = TRUE; if(gfErrorCatch) { InitErrorCatchDialog(); return(EDIT_SCREEN); } gbCurrentFileIOStatus = IOSTATUS_NONE; CreateMessageBox((STR16)(_BS(L" Error saving ") << (const char*)ubNewFilename << L" file. Try another filename? " << _BS::wget).c_str() ); return(guiCurrentScreen); } if( gfShowPits ) AddAllPits(); GetSectorFromFileName(gzFilename, gWorldSectorX, gWorldSectorY, gbWorldSectorZ, fAltMap);//dnl ch31 140909 if( gfGlobalSummaryExists ) UpdateSectorSummary( gzFilename, gfUpdateSummaryInfo ); else//dnl ch30 150909 ReEvaluateWorld(ubNewFilename); iCurrentAction = ACTION_NULL; gbCurrentFileIOStatus = IOSTATUS_NONE; gfRenderWorld = TRUE; gfRenderTaskbar = TRUE; fEnteringLoadSaveScreen = TRUE; RestoreFontSettings(); if( gfErrorCatch ) { InitErrorCatchDialog(); return EDIT_SCREEN; } fNewMapSaved = TRUE; return EDIT_SCREEN; case INITIATE_MAP_LOAD: //draw load message SaveFontSettings(); gbCurrentFileIOStatus = LOADING_MAP; if( gfEditMode && iCurrentTaskbar == TASK_MERCS ) IndicateSelectedMerc( SELECT_NO_MERC ); SpecifyItemToEdit( NULL, -1 ); return LOADSAVE_SCREEN; case LOADING_MAP: //load map DisableUndo(); sprintf( ubNewFilename, "%S", gzFilename ); RemoveMercsInSector( ); // Want to override crash, so user can do something else. if(!ReEvaluateWorld(ubNewFilename) || !LoadWorld(ubNewFilename))//dnl ch36 140909 { EnableUndo(); gbCurrentFileIOStatus = IOSTATUS_NONE; gfGlobalError = FALSE; gfLoadError = TRUE; CreateMessageBox((STR16)(_BS(L" Error loading ") << (const char*)ubNewFilename << L" file. Try another filename? " << _BS::wget).c_str()); return(guiCurrentScreen); } //ADB these are NOT set yet! but they need to be, duh CompileWorldMovementCosts(); GetSectorFromFileName(gzFilename, gWorldSectorX, gWorldSectorY, gbWorldSectorZ, fAltMap);//dnl ch31 140909 RestoreFontSettings(); //Load successful, update necessary information. //ATE: Any current mercs are transfered here... //UpdateMercsInSector( gWorldSectorX, gWorldSectorY, gbWorldSectorZ ); AddSoldierInitListTeamToWorld( ENEMY_TEAM, 255 ); AddSoldierInitListTeamToWorld( CREATURE_TEAM, 255 ); AddSoldierInitListTeamToWorld( MILITIA_TEAM, 255 ); AddSoldierInitListTeamToWorld( CIV_TEAM, 255 ); iCurrentAction = ACTION_NULL; gbCurrentFileIOStatus = IOSTATUS_NONE; if( !gfCaves && !gfBasement ) { gusLightLevel = 12; if( ubAmbientLightLevel != 4 ) { ubAmbientLightLevel = 4; LightSetBaseLevel( ubAmbientLightLevel ); } } else gusLightLevel = (UINT16)(EDITOR_LIGHT_MAX - ubAmbientLightLevel ); gEditorLightColor = gpLightColors[ 0 ]; gfRenderWorld = TRUE; gfRenderTaskbar = TRUE; fEnteringLoadSaveScreen = TRUE; InitJA2SelectionWindow(); ShowEntryPoints(); EnableUndo(); RemoveAllFromUndoList(); SetEditorSmoothingMode( gMapInformation.ubEditorSmoothingType ); if( gMapInformation.ubEditorSmoothingType == SMOOTHING_CAVES ) AnalyseCaveMapForStructureInfo(); AddLockedDoorCursors(); gubCurrRoomNumber = gubMaxRoomNumber; UpdateRoofsView(); UpdateWallsView(); ShowLightPositionHandles(); SetMercTeamVisibility( ENEMY_TEAM, gfShowEnemies ); SetMercTeamVisibility( CREATURE_TEAM, gfShowCreatures ); SetMercTeamVisibility( MILITIA_TEAM, gfShowRebels ); SetMercTeamVisibility( CIV_TEAM, gfShowCivilians ); BuildItemPoolList(); gpItemPool = NULL;//dnl ch26 210909 fShowHighGround = FALSE;//dnl ch2 210909 fRaiseWorld = FALSE;//dnl ch3 210909 ShowHighGround(4);//dnl ch41 210909 SetRenderCenter(WORLD_COLS/2, WORLD_ROWS/2);//dnl ch43 280909 if( gfShowPits ) AddAllPits(); if( iCurrentTaskbar == TASK_MAPINFO ) { //We have to temporarily remove the current textinput mode, //update the disabled text field values, then restore the current //text input fields. SaveAndRemoveCurrentTextInputMode(); UpdateMapInfoFields(); RestoreSavedTextInputMode(); } return EDIT_SCREEN; } gbCurrentFileIOStatus = IOSTATUS_NONE; return LOADSAVE_SCREEN; }
void ExtractAndUpdateMapInfo() { UINT16 str[10]; INT32 temp; BOOLEAN fUpdateLight1 = FALSE; //extract light1 colors temp = min( GetNumericStrictValueFromField( 1 ), 255 ); if( temp != -1 && temp != gEditorLightColor.peRed ) { fUpdateLight1 = TRUE; gEditorLightColor.peRed = (UINT8)temp; } temp = min( GetNumericStrictValueFromField( 2 ), 255 ); if( temp != -1 && temp != gEditorLightColor.peGreen ) { fUpdateLight1 = TRUE; gEditorLightColor.peGreen = (UINT8)temp; } temp = min( GetNumericStrictValueFromField( 3 ), 255 ); if( temp != -1 && temp != gEditorLightColor.peBlue ) { fUpdateLight1 = TRUE; gEditorLightColor.peBlue = (UINT8)temp; } if( fUpdateLight1 ) { gfEditorForceShadeTableRebuild = TRUE; LightSetColors( &gEditorLightColor, 1 ); gfEditorForceShadeTableRebuild = FALSE; } //extract radius temp = max( min( GetNumericStrictValueFromField( 4 ), 8 ), 1 ); if( temp != -1 ) gsLightRadius = (INT16)temp; temp = max( min( GetNumericStrictValueFromField( 5 ), 15 ), 1 ); if( temp != -1 && temp != gusLightLevel ) { gusLightLevel = (UINT16)temp; gfRenderWorld = TRUE; ubAmbientLightLevel = (UINT8)(EDITOR_LIGHT_MAX - gusLightLevel); LightSetBaseLevel( ubAmbientLightLevel ); LightSpriteRenderAll(); } temp = (INT8)GetNumericStrictValueFromField( 6 ); if( temp == -1 ) gMapInformation.ubRestrictedScrollID = 0; else gMapInformation.ubRestrictedScrollID = (UINT8)temp; //set up fields for exitgrid information Get16BitStringFromField( 7, str ); if( str[0] >= 'a' && str[0] <= 'z' ) str[0] -= 32; //uppercase it! if( str[0] >= 'A' && str[0] <= 'Z' && str[1] >= '0' && str[1] <= '9' ) { //only update, if coordinate is valid. gExitGrid.ubGotoSectorY = (UINT8)(str[0] - 'A' + 1); gExitGrid.ubGotoSectorX = (UINT8)(str[1] - '0'); if( str[2] >= '0' && str[2] <= '9' ) gExitGrid.ubGotoSectorX = (UINT8)(gExitGrid.ubGotoSectorX * 10 + str[2] - '0' ); gExitGrid.ubGotoSectorX = (UINT8)max( min( gExitGrid.ubGotoSectorX, 16 ), 1 ); gExitGrid.ubGotoSectorY = (UINT8)max( min( gExitGrid.ubGotoSectorY, 16 ), 1 ); } gExitGrid.ubGotoSectorZ = (UINT8)max( min( GetNumericStrictValueFromField( 8 ), 3 ), 0 ); gExitGrid.usGridNo = (UINT16)max( min( GetNumericStrictValueFromField( 9 ), 25600 ), 0 ); UpdateMapInfoFields(); }
//Because loading and saving the map takes a few seconds, we want to post a message //on the screen and then update it which requires passing the screen back to the main loop. //When we come back for the next frame, we then actually save or load the map. So this //process takes two full screen cycles. UINT32 ProcessFileIO() { INT16 usStartX, usStartY; UINT8 ubNewFilename[50]; switch( gbCurrentFileIOStatus ) { case INITIATE_MAP_SAVE: //draw save message StartFrameBufferRender( ); SaveFontSettings(); SetFont( HUGEFONT ); SetFontForeground( FONT_LTKHAKI ); SetFontShadow( FONT_DKKHAKI ); SetFontBackground( 0 ); swprintf( zOrigName, L"Saving map: %s", gzFilename ); usStartX = 320 - StringPixLength( zOrigName, LARGEFONT1 ) / 2; usStartY = 180 - GetFontHeight( LARGEFONT1 ) / 2; mprintf( usStartX, usStartY, zOrigName ); InvalidateScreen( ); EndFrameBufferRender( ); gbCurrentFileIOStatus = SAVING_MAP; return LOADSAVE_SCREEN; case SAVING_MAP: //save map sprintf( ubNewFilename, "%S", gzFilename ); RaiseWorldLand(); if( gfShowPits ) RemoveAllPits(); OptimizeSchedules(); if ( !SaveWorld( ubNewFilename ) ) { if( gfErrorCatch ) { InitErrorCatchDialog(); return EDIT_SCREEN; } return ERROR_SCREEN; } if( gfShowPits ) AddAllPits(); SetGlobalSectorValues( gzFilename ); if( gfGlobalSummaryExists ) UpdateSectorSummary( gzFilename, gfUpdateSummaryInfo ); iCurrentAction = ACTION_NULL; gbCurrentFileIOStatus = IOSTATUS_NONE; gfRenderWorld = TRUE; gfRenderTaskbar = TRUE; fEnteringLoadSaveScreen = TRUE; RestoreFontSettings(); if( gfErrorCatch ) { InitErrorCatchDialog(); return EDIT_SCREEN; } if( gMapInformation.ubMapVersion != gubMinorMapVersion ) ScreenMsg( FONT_MCOLOR_RED, MSG_ERROR, L"Map data has just been corrupted!!! What did you just do? KM : 0" ); return EDIT_SCREEN; case INITIATE_MAP_LOAD: //draw load message SaveFontSettings(); gbCurrentFileIOStatus = LOADING_MAP; if( gfEditMode && iCurrentTaskbar == TASK_MERCS ) IndicateSelectedMerc( SELECT_NO_MERC ); SpecifyItemToEdit( NULL, -1 ); return LOADSAVE_SCREEN; case LOADING_MAP: //load map DisableUndo(); sprintf( ubNewFilename, "%S", gzFilename ); RemoveMercsInSector( ); if( !LoadWorld( ubNewFilename ) ) { //Want to override crash, so user can do something else. EnableUndo(); SetPendingNewScreen( LOADSAVE_SCREEN ); gbCurrentFileIOStatus = IOSTATUS_NONE; gfGlobalError = FALSE; gfLoadError = TRUE; //RemoveButton( iTempButton ); CreateMessageBox( L" Error loading file. Try another filename?" ); return LOADSAVE_SCREEN; } SetGlobalSectorValues( gzFilename ); RestoreFontSettings(); //Load successful, update necessary information. //ATE: Any current mercs are transfered here... //UpdateMercsInSector( gWorldSectorX, gWorldSectorY, gbWorldSectorZ ); AddSoldierInitListTeamToWorld( ENEMY_TEAM, 255 ); AddSoldierInitListTeamToWorld( CREATURE_TEAM, 255 ); AddSoldierInitListTeamToWorld( MILITIA_TEAM, 255 ); AddSoldierInitListTeamToWorld( CIV_TEAM, 255 ); iCurrentAction = ACTION_NULL; gbCurrentFileIOStatus = IOSTATUS_NONE; if( !gfCaves && !gfBasement ) { gusLightLevel = 12; if( ubAmbientLightLevel != 4 ) { ubAmbientLightLevel = 4; LightSetBaseLevel( ubAmbientLightLevel ); } } else gusLightLevel = (UINT16)(EDITOR_LIGHT_MAX - ubAmbientLightLevel ); gEditorLightColor = gpLightColors[ 0 ]; gfRenderWorld = TRUE; gfRenderTaskbar = TRUE; fEnteringLoadSaveScreen = TRUE; InitJA2SelectionWindow(); ShowEntryPoints(); EnableUndo(); RemoveAllFromUndoList(); SetEditorSmoothingMode( gMapInformation.ubEditorSmoothingType ); if( gMapInformation.ubEditorSmoothingType == SMOOTHING_CAVES ) AnalyseCaveMapForStructureInfo(); AddLockedDoorCursors(); gubCurrRoomNumber = gubMaxRoomNumber; UpdateRoofsView(); UpdateWallsView(); ShowLightPositionHandles(); SetMercTeamVisibility( ENEMY_TEAM, gfShowEnemies ); SetMercTeamVisibility( CREATURE_TEAM, gfShowCreatures ); SetMercTeamVisibility( MILITIA_TEAM, gfShowRebels ); SetMercTeamVisibility( CIV_TEAM, gfShowCivilians ); BuildItemPoolList(); if( gfShowPits ) AddAllPits(); if( iCurrentTaskbar == TASK_MAPINFO ) { //We have to temporarily remove the current textinput mode, //update the disabled text field values, then restore the current //text input fields. SaveAndRemoveCurrentTextInputMode(); UpdateMapInfoFields(); RestoreSavedTextInputMode(); } return EDIT_SCREEN; } gbCurrentFileIOStatus = IOSTATUS_NONE; return LOADSAVE_SCREEN; }