Images
Visible Capitol

Visible Capitol

The original purpose of this script was another bugfix to the game, where the AI forgot to build a new capitol when the original one was destroyed.

I then added the Visible Capitol extension: A visible capitol (tile improvement) is placed next to each player’s capital.

If the capital is captured, the capitol turns into a governor’s residence for the conqueror. If the capital is destroyed, the capitol turns into ruins.

Since the original issue should be fixed by the Apolyton Edition the remaining purpose of this script consists in providing an additional eye-candy.

1The Script1

//--------------------------------------------------------------------------
// MoT Mod for CTP2 (Apolyton Edition) by BureauBert
// v1.1
// http://motmod.ctp2.info
//--------------------------------------------------------------------------
////////////////////////////////////////////////////////////////////////////
// Visible Capital Code
// by BureauBert
// The original code by Wouter Snijders (aka Locutus) was made to make
// the AI build a new capitol when they lost their original one.
// Since this is no longer needed with the Apolyton Edition, the remaining
// purpose of this script consists in adding a visible representation
// to the city improvement.
////////////////////////////////////////////////////////////////////////////

// AE changelog 2008-10-08: Fixed: The AI does rebuild its capitol if it has lost its capitol.

///////////////////////////////////
// Functions
///////////////////////////////////

// create visible capitol (tile improvement)

void_f CreateVisibleCapital(int_t thePlayer, location_t theLocation, int_t theReason) {
        int_t capVisiPlayer;
        location_t capVisiCityLoc;
        int_t capCountB;
        int_t capCountC;
        int_t capVisiToBuild;
        location_t capVisiTmpLoc;
        location_t capVisiBuildLoc;
        int_t capLookLoc;
        location_t capCheckLoc;
        int_t capVisiReason;

        capVisiPlayer = thePlayer;
        capVisiCityLoc = theLocation;
        capVisiReason = theReason;
        capVisiToBuild = -1;

        // Reasons for building tileimp:
        // 1 - player's first city
        // 2 - rebuild capital
        // 3 - capital to ruins upon destruction
        // 4 - capital to governor's residence upon capture and gift
        // 5 - remove governor's residence upon destruction

        if(capVisiReason == 1) {
                if(capVisiPlayer > 0) {
                        capVisiToBuild = TerrainImprovementDB(TILEIMP_ANCIENT_CAPITOL);
                }
                if(capVisiPlayer == 0) {
                        capVisiToBuild = TerrainImprovementDB(TILEIMP_BARB_HQ);
                }
        }
        if(capVisiReason == 2){
                if(capVisiPlayer == 0) {
                        capVisiToBuild = TerrainImprovementDB(TILEIMP_BARB_HQ);
                }
                if(capVisiPlayer > 0 && !HasAdvance(capVisiPlayer, AdvanceDB(ADVANCE_ELECTRICITY))) {
                        capVisiToBuild = TerrainImprovementDB(TILEIMP_ANCIENT_CAPITOL);
                }
                if(capVisiPlayer > 0 && HasAdvance(capVisiPlayer, AdvanceDB(ADVANCE_ELECTRICITY))) {
                        capVisiToBuild = TerrainImprovementDB(TILEIMP_MODERN_CAPITOL);
                }
        }
        if(capVisiReason == 3) {
                for(capLookLoc = 0; capLookLoc <= 7; capLookLoc = capLookLoc + 1) {
                        if(GetNeighbor(capVisiCityLoc, capLookLoc, capCheckLoc)) {
                                if(TileHasImprovement(capCheckLoc, TerrainImprovementDB(TILEIMP_ANCIENT_CAPITOL))) {
                                        Event:CutImprovements(capCheckLoc);
                                        capVisiBuildLoc = capCheckLoc;
                                        capVisiToBuild = TerrainImprovementDB(TILEIMP_ANCIENT_CAPITOL_RUINS);
                                        capLookLoc = 7;
                                }
                                if(TileHasImprovement(capCheckLoc, TerrainImprovementDB(TILEIMP_MODERN_CAPITOL))) {
                                        Event:CutImprovements(capCheckLoc);
                                        capVisiBuildLoc = capCheckLoc;
                                        capVisiToBuild = TerrainImprovementDB(TILEIMP_MODERN_CAPITOL_RUINS);
                                        capLookLoc = 7;
                                }
                                if(TileHasImprovement(capCheckLoc, TerrainImprovementDB(TILEIMP_COLONIAL))) {
                                        Event:CutImprovements(capCheckLoc);
                                        capVisiBuildLoc = capCheckLoc;
                                        capVisiToBuild = -1;
                                        capLookLoc = 7;
                                }
                        }
                }
        }
        if(capVisiReason == 4) {
                for(capLookLoc = 0; capLookLoc <= 7; capLookLoc = capLookLoc + 1) {
                        if(GetNeighbor(capVisiCityLoc, capLookLoc, capCheckLoc)) {

                                // split into 2 if-clauses just in case we want to introduce a modern colonial bldg. later

                                if(TileHasImprovement(capCheckLoc, TerrainImprovementDB(TILEIMP_ANCIENT_CAPITOL))
                                || TileHasImprovement(capCheckLoc, TerrainImprovementDB(TILEIMP_ANCIENT_CAPITOL_RUINS))) {
                                        Event:CutImprovements(capCheckLoc);
                                        capVisiBuildLoc = capCheckLoc;
                                        capVisiToBuild = TerrainImprovementDB(TILEIMP_COLONIAL);
                                        capLookLoc = 7;
                                }
                                if(TileHasImprovement(capCheckLoc, TerrainImprovementDB(TILEIMP_MODERN_CAPITOL))
                                || TileHasImprovement(capCheckLoc, TerrainImprovementDB(TILEIMP_MODERN_CAPITOL_RUINS))) {
                                        Event:CutImprovements(capCheckLoc);
                                        capVisiBuildLoc = capCheckLoc;
                                        capVisiToBuild = TerrainImprovementDB(TILEIMP_COLONIAL);
                                        capLookLoc = 7;
                                }
                                // if it was the barb's capital, just destroy their headquarters
                                if(TileHasImprovement(capCheckLoc, TerrainImprovementDB(TILEIMP_BARB_HQ))) {
                                        Event:CutImprovements(capCheckLoc);
                                        capVisiBuildLoc = capCheckLoc;
                                        capVisiToBuild = -1;
                                        capLookLoc = 7;
                                }
                        }
                }
        }
        if(capVisiReason == 5) {
                for(capLookLoc = 0; capLookLoc <= 7; capLookLoc = capLookLoc + 1) {
                        if(GetNeighbor(capVisiCityLoc, capLookLoc, capCheckLoc)) {
                                if(TileHasImprovement(capCheckLoc, TerrainImprovementDB(TILEIMP_COLONIAL))
                                || TileHasImprovement(capCheckLoc, TerrainImprovementDB(TILEIMP_BARB_HQ))) {
                                        Event:CutImprovements(capCheckLoc);
                                        capVisiBuildLoc = capCheckLoc;
                                        capVisiToBuild = -1;
                                        capLookLoc = 7;
                                }
                        }
                }
        }
        if(capVisiReason == 6) {
                for(capLookLoc = 0; capLookLoc <= 7; capLookLoc = capLookLoc + 1) {
                        if(GetNeighbor(capVisiCityLoc, capLookLoc, capCheckLoc)) {
                                if(TileHasImprovement(capCheckLoc, TerrainImprovementDB(TILEIMP_ANCIENT_CAPITOL))
                                || TileHasImprovement(capCheckLoc, TerrainImprovementDB(TILEIMP_MODERN_CAPITOL))
                                || TileHasImprovement(capCheckLoc, TerrainImprovementDB(TILEIMP_BARB_HQ))) {
                                        Event:CutImprovements(capCheckLoc);
                                        capVisiBuildLoc = capCheckLoc;
                                        capVisiToBuild = -1;
                                        capLookLoc = 7;
                                }
                        }
                }
        }
        if(capVisiReason == 1 || capVisiReason == 2){
                int_t check;
                int_t timp;
                int_t rand;

                capVisiBuildLoc = capVisiCityLoc;

                for(capCountB = 7; capCountB > -1; capCountB = capCountB - 1){
                        if(GetNeighbor(capVisiCityLoc, capCountB, capVisiTmpLoc)) {
                                timp = 0;
                                if(TerrainType(capVisiTmpLoc) == TerrainDB(TERRAIN_PLAINS)
                                || TerrainType(capVisiTmpLoc) == TerrainDB(TERRAIN_GRASSLAND)
                                || TerrainType(capVisiTmpLoc) == TerrainDB(TERRAIN_DESERT)
                                || TerrainType(capVisiTmpLoc) == TerrainDB(TERRAIN_TUNDRA)
                                || TerrainType(capVisiTmpLoc) == TerrainDB(TERRAIN_HILL)
                                || TerrainType(capVisiTmpLoc) == TerrainDB(TERRAIN_FOREST)
                                || TerrainType(capVisiTmpLoc) == TerrainDB(TERRAIN_JUNGLE)
                                ){
                                        for(capCountC = 0; capCountC < MOD_NUMOFTILEIMPS; capCountC = capCountC + 1) {
                                                if(TileHasImprovement(capVisiTmpLoc, capCountC) && capCountC != TerrainImprovementDB(TILEIMP_TERRAFORM_GRASSLAND)) {
                                                        timp = timp + 1;
                                                }
                                                if(TileHasWonder(capVisiTmpLoc) || TileHasNaturalWonder(capVisiTmpLoc) || TileHasMonument(capVisiTmpLoc)) {
                                                        timp = timp + 10;
                                                }
                                                if(HasGood(capVisiTmpLoc) > -1) {
                                                        timp = timp + 10;
                                                }
                                        }
                                        if(timp < 1) {
                                                capVisiBuildLoc = capVisiTmpLoc;
                                                capCountB = -1;
                                        }
                                }
                        }
                }
                if(capVisiBuildLoc == capVisiCityLoc) {
                        for(capCountB = 7; capCountB > -1; capCountB = capCountB - 1){
                                if(GetNeighbor(capVisiCityLoc, capCountB, capVisiTmpLoc)) {
                                        timp = 0;
                                        if(TerrainType(capVisiTmpLoc) == TerrainDB(TERRAIN_MOUNTAIN)
                                        || TerrainType(capVisiTmpLoc) == TerrainDB(TERRAIN_BROWN_HILL)
                                        || TerrainType(capVisiTmpLoc) == TerrainDB(TERRAIN_BROWN_MOUNTAIN)
                                        || TerrainType(capVisiTmpLoc) == TerrainDB(TERRAIN_WHITE_HILL)
                                        || TerrainType(capVisiTmpLoc) == TerrainDB(TERRAIN_WHITE_MOUNTAIN)
                                        || TerrainType(capVisiTmpLoc) == TerrainDB(TERRAIN_GLACIER)
                                        || TerrainType(capVisiTmpLoc) == TerrainDB(TERRAIN_SWAMP)
                                        ){
                                                for(capCountC = 0; capCountC < MOD_NUMOFTILEIMPS; capCountC = capCountC + 1) {
                                                        if(TileHasImprovement(capVisiTmpLoc, capCountC) && capCountC != TerrainImprovementDB(TILEIMP_TERRAFORM_GRASSLAND)) {
                                                                timp = timp + 1;
                                                        }
                                                        if(TileHasWonder(capVisiTmpLoc) || TileHasNaturalWonder(capVisiTmpLoc) || TileHasMonument(capVisiTmpLoc)) {
                                                                timp = timp + 10;
                                                        }
                                                        if(HasGood(capVisiTmpLoc) > -1) {
                                                                timp = timp + 10;
                                                        }
                                                }
                                                if(timp < 1) {
                                                        capVisiBuildLoc = capVisiTmpLoc;
                                                        capCountB = -1;
                                                }
                                        }
                                }
                        }
                }
                if(capVisiBuildLoc == capVisiCityLoc){
                        check = 0;
                        GetRandomNeighbor(capVisiCityLoc, capVisiTmpLoc);
                        while(check < 8) {
                                timp = 0;
                                if(IsWater(capVisiTmpLoc) || TileHasWonder(capVisiTmpLoc) || TileHasMonument(capVisiTmpLoc) || HasGood(capVisiTmpLoc) > -1) {
                                        timp = timp + 1;
                                }
                                if(timp == 0){
                                        for(capCountB = 0; capCountB < MOD_NUMOFTILEIMPS; capCountB = capCountB + 1) {
                                                if(TileHasImprovement(capVisiTmpLoc, capCountB)) {
                                                        Event:CutImprovements(capVisiTmpLoc);
                                                }
                                        }
                                        capVisiBuildLoc = capVisiTmpLoc;
                                        check = 8;
                                }
                                else {
                                        GetRandomNeighbor(capVisiCityLoc, capVisiTmpLoc);
                                        check = check + 1;
                                }
                        }
                }
                if(capVisiBuildLoc != capVisiCityLoc) {
                        rand = Random(2);
                        if(rand == 1) {
                                Terraform(capVisiBuildLoc, TerrainDB(TERRAIN_PLAINS));
                        }
                        elseif(rand==0) {
                                Terraform(capVisiBuildLoc, TerrainDB(TERRAIN_GRASSLAND));
                        }
                }
        }
        if(capVisiBuildLoc != capVisiCityLoc) {
                if(capVisiToBuild > -1) {
                        VIS_VisiStuffPlacement = 1;
                        GrantAdvance(capVisiPlayer, AdvanceDB(ADVANCE_SUBNEURAL_ADS));
                        Event:CreateImprovement(capVisiPlayer, capVisiBuildLoc, capVisiToBuild, 0);
                }
                FinishImprovements(capVisiBuildLoc);
        }
}

///////////////////////////////////
// Event Handlers
///////////////////////////////////

// create visible capitol next to first capital (AIs and HUMANs)

HandleEvent(CreateCity) 'FirstCapital' post {
        city_t capNewCity;
        location_t capNewCityLoc;
        int_t capNewPlayer;
        int_t capNewPlayersCities;

        if(GetCityByLocation(location[0], capNewCity)) {
                if(CityIsValid(capNewCity)) {
                        // capNewCity = city[0];
                        capNewCityLoc = capNewCity.location;
                        capNewPlayer = capNewCity.owner;
                        capNewPlayersCities = PlayerCityCount(capNewPlayer);
                        if(capNewPlayersCities == 1) {
                                CreateVisibleCapital(capNewPlayer, capNewCityLoc, 1);
                        }
                }
        }
}

// turn existing visible capitol into governor's residence upon capture (AIs and HUMANs)

HandleEvent(CaptureCity) 'TurnCapitolIntoResidenceCapture' post {
        int_t capCapturePlayer;
        location_t capCaptureLoc;
        int_t capCapturePlayersCities;

        capCapturePlayer = city[0].owner;
        capCaptureLoc = city[0].location;
        capCapturePlayersCities = PlayerCityCount(capCapturePlayer);

        CreateVisibleCapital(capCapturePlayer, capCaptureLoc, 4);
        // in the case of a splinter civ, create a brand new capitol:
        if(capCapturePlayersCities == 1) {
                CreateVisibleCapital(capCapturePlayer, capCaptureLoc, 1);
        }
}

// turn existing visible capitol into governor's residence upon gift (AIs and HUMANs)

HandleEvent(GiveCity) 'TurnCapitolIntoResidenceSurrender' post {
        int_t capVictoryPlayer;
        location_t capVictoryLoc;

        capVictoryPlayer = city[0].owner;
        capVictoryLoc = city[0].location;
       
        CreateVisibleCapital(capVictoryPlayer, capVictoryLoc, 4);
}

// detect the destruction of a Capital,
// call CreateCapital (AIs only) and CreateVisibleCapital (AIs and HUMANs) functions

HandleEvent(KillCity) 'CapitalKilled' pre {
        int_t capTmpPlayer1;
        city_t capTmpCity1;
        location_t capTmpCityLoc1;

        capTmpCity1 = city[0];
        capTmpPlayer1 = capTmpCity1.owner;
        capTmpCityLoc1 = capTmpCity1.location;

        if(capTmpPlayer1 > -1) {
                if(CityHasBuilding(capTmpCity1, "IMPROVE_CAPITOL")) {
                        CreateVisibleCapital(capTmpPlayer1, capTmpCityLoc1, 3);
                }
                else {
                        CreateVisibleCapital(capTmpPlayer1, capTmpCityLoc1, 5);
                }
        }
        return CONTINUE;
}

// detect the removal of the capitol in case the city has not been killed
// (capitol sold, lost during an assault ...), call CreateVisibleCapital for removal of tileimp

HandleEvent(BuildingRemoved) 'CapitalRemoved' pre {
        int_t capTmpPlayer1;
        int_t capBuildIdx;
        city_t capTmpCity1;
        location_t capTmpCityLoc1;

        capTmpCity1 = city[0];
        capTmpPlayer1 = capTmpCity1.owner;
        capTmpCityLoc1 = capTmpCity1.location;
        capBuildIdx = value[0].value;

        if(CityIsValid(capTmpCity1)) {
                if(capBuildIdx == BuildingDB(IMPROVE_CAPITOL)) {
                        CreateVisibleCapital(capTmpPlayer1, capTmpCityLoc1, 6);
                }
        }
        return CONTINUE;
}

// detect the disbandment of a Capital,
// call CreateCapital (AIs only) and CreateVisibleCapital (AIs and HUMANs) functions

HandleEvent(DisbandCity) 'CapitalDisbanded' pre {
        int_t capTmpPlayer3;
        city_t capTmpCity3;
        location_t capTmpCityLoc3;
       
        capTmpCity3 = city[0];
        capTmpPlayer3 = capTmpCity3.owner;
        capTmpCityLoc3 = capTmpCity3.location;

        if(CityHasBuilding(capTmpCity3, "IMPROVE_CAPITOL")) {
                CreateVisibleCapital(capTmpPlayer3, capTmpCityLoc3, 3);
        }
        return CONTINUE;
}

// detect the park creation of a Capital,
// call CreateCapital (AIs only) and CreateVisibleCapital (AIs and HUMANs) functions

HandleEvent(CreatePark) 'CapitalToPark' pre {
        int_t capTmpPlayer4;
        city_t capTmpCity4;
        location_t capTmpCityLoc4;

        capTmpCity4 = city[0];
        capTmpPlayer4 = capTmpCity4.owner;
        capTmpCityLoc4 = capTmpCity4.location;

        if(CityHasBuilding(capTmpCity4, "IMPROVE_CAPITOL")) {
                CreateVisibleCapital(capTmpPlayer4, capTmpCityLoc4, 3);
        }
        return CONTINUE;
}

// create visible capitol upon building of new capitol (AI's and HUMANs)

HandleEvent(CreateBuilding) 'NewCapital' post {
        city_t capNewCity;
        location_t capNewCityLoc;
        int_t capNewPlayer;
        int_t capNewBuilding;

        capNewBuilding = value[0].value;
        capNewPlayer = city[0].owner;
        capNewCity = city[0];
        capNewCityLoc = capNewCity.location;

        if(capNewBuilding == BuildingDB(IMPROVE_CAPITOL)) {
                CreateVisibleCapital(capNewPlayer, capNewCityLoc, 2);        // create new visiCap
        }
}

// prevent overbuilding of capitol ti's, except for other capitol ti's
               
HandleEvent(CreateImprovement) 'CapitolMayorProtection' pre {       
        if(TileHasCapital(location[0])) {
                if(value[0] == TerrainImprovementDB(TILEIMP_ANCIENT_CAPITOL)
                || value[0] == TerrainImprovementDB(TILEIMP_MODERN_CAPITOL)
                || value[0] == TerrainImprovementDB(TILEIMP_BARB_HQ)
                || value[0] == TerrainImprovementDB(TILEIMP_ANCIENT_CAPITOL_RUINS)
                || value[0] == TerrainImprovementDB(TILEIMP_MODERN_CAPITOL_RUINS)
                || value[0] == TerrainImprovementDB(TILEIMP_COLONIAL)
                // || value[0] == TerrainImprovementDB(TILEIMP_ROAD)
                // || value[0] == TerrainImprovementDB(TILEIMP_RAILROAD)
                // || value[0] == TerrainImprovementDB(TILEIMP_MAGLEV)
                ) {
                        return CONTINUE;               
                }
                else {
                        return STOP;
                }
        }
        else {
                return CONTINUE;
        }
}

// prevent pillaging of capitol ti's

HandleEvent(PillageOrder) 'CapitolPillageProtectionA' pre {
        location_t capTmpLoc;

        capTmpLoc = army[0].location;

        if(TileHasCapital(capTmpLoc)) {
                return STOP;
        }
        else {
                return CONTINUE;
        }
}

HandleEvent(PillageUnit) 'CapitolPillageProtectionB' pre {
        location_t capTmpLoc;
       
        capTmpLoc = unit[0].location;

        if(TileHasCapital(capTmpLoc)) {
                return STOP;
        }
        else {
                return CONTINUE;
        }
}