Images
Natural Wonders
Ayers Rock
Grand Canyon
Angel Falls
Great Barrier Reef
Guillin Hills
Lake Baikal
Urgup Cones

Natural Wonders

Implementation of The Immortal Wombat’s Mod:

“This mod makes the world a little more interesting by adding up to 7 new features onto the map — seven of the most beautiful natural features of earth (in theory at least. my art’s not up to much).

They are: Ayers Rock, the Great Barrier Reef, the Grand Canyon, Angel Falls, Lake Baikal, the Guillin Hill, the Urgup Cones.”

The Script

//--------------------------------------------------------------------------
// MoT Mod for CTP2 (Apolyton Edition) by BureauBert
// v1.1
// http://motmod.ctp2.info
//--------------------------------------------------------------------------
//=========================================================
// Natural Wonders
// Another tile mod by the Immortal Wombat
//
// Thanks to Dale for the idea, and Martin Gühmann, for  
// GoodMod, from which the idea of using 'special' tile
// improvements and from which some of this code came.
//=========================================================


HandleEvent (CreateImprovement)'IWN_TimpOnNaturalWonderStop' pre {
        int_t IWN_tilimpcreate;
        location_t tmpLoc;
        IWN_tilimpcreate = value[0];
        tmpLoc = location[0];
       
        if (!IsHumanPlayer(player[0])&&(GetCurrentRound () > 1)) {
                if (TileHasNaturalWonder(tmpLoc)){
                        return STOP;
                }
        }
        return CONTINUE;
}


//---------------------------------------
// Plant the wonders on the map
//

int_f DoNW(location_t NWonderLoc) {
        location_t        tmpLoc;
        unit_t        BarbUnit;
        tmpLoc = NWonderLoc;
        CreateUnit(0, UnitDB(UNIT_BOMBER), tmpLoc, 1, BarbUnit);
        Event:CreateImprovement(0,tmpLoc, TerrainImprovementDB(TILEIMP_BORDER), 0);
        Event: DisbandUnit(BarbUnit);
        return 1;
}

int_f IWN_AllDone(int_t tilecounter) {
        if(IWN_AYERS && IWN_REEF && IWN_CANYON && IWN_FALL && IWN_GUILLIN && IWN_BAIKAL && IWN_URGUP) {
                return 1;
        }
        if(tilecounter >= GetMapWidth() * GetMapHeight()) {
                return 1;
        }
        else {
                return 0;
        }
}

HandleEvent(BeginTurn) 'IWN_placeborders' pre {
        int_t i;
        int_t j;
        int_t k;
        int_t rnd;
        int_t count;
        int_t total;
        location_t tmpLoc;
        location_t tmp2Loc;
        location_t tmp3Loc;
        location_t BorderLoc;

        IWN_AYERS = 0;
        IWN_REEF = 0;
        IWN_CANYON = 0;
        IWN_FALL = 0;
        IWN_GUILLIN = 0;
        IWN_BAIKAL = 0;
        IWN_URGUP = 0;

        if(GetCurrentRound () == 0) {
                if(!HasAdvance(0, ID_ADVANCE_SUBNEURAL_ADS)) {
                        GrantAdvance(0, AdvanceDB(ADVANCE_SUBNEURAL_ADS));
                }
                total = 0;
                while(!IWN_AllDone(total)) {
                        i = random(GetMapWidth() - 1);
                        j = random(GetMapHeight() - 1);
                        MakeLocation(tmpLoc, i, j);
                       
                        total = total + 1;

                        if(TerrainType(tmpLoc) == TerrainDB(TERRAIN_WATER_BEACH) && IWN_BAIKAL == 0) {
                                count = 0;
                                for(k = 0; k < 8; k = k + 1){
                                        if(GetNeighbor(tmpLoc, k, tmp2Loc)) {
                                                if(IsWater(tmp2Loc)){
                                                        count = count + 1;
                                                }
                                        }
                                }
                                if(count == 0){
                                        if(GetNeighbor(tmpLoc, 7, BorderLoc)) {
                                                IWN_BAIKAL_LOC = tmpLoc;
                                                IWN_BAIKAL = DoNW(BorderLoc);
                                        }
                                }
                        }
                        // Find any single tile of beach surrounded by land
                        //
                        elseif(TerrainType(tmpLoc) == TerrainDB(TERRAIN_PLAINS) && UnitsInCell(tmpLoc) < 1 && IWN_AYERS == 0 && !TileHasImprovement(tmpLoc, TerrainImprovementDB(TILEIMP_NW_CANYON))) {
                                if(GetNeighbor(tmpLoc, 7, BorderLoc)) {
                                        IWN_AYERS_LOC = tmpLoc;
                                        IWN_AYERS = DoNW(BorderLoc);
                                }
                        }
                        // any plains tile
                        //
                        elseif(TerrainType(tmpLoc) == TerrainDB(TERRAIN_PLAINS) && UnitsInCell(tmpLoc) < 1 && IWN_CANYON == 0 && !TileHasImprovement(tmpLoc, TerrainImprovementDB(TILEIMP_NW_AYERS))) {
                                if(GetNeighbor(tmpLoc, 7, BorderLoc)) {
                                        IWN_CANYON_LOC = tmpLoc;
                                        IWN_CANYON = DoNW(BorderLoc);
                                }
                        }
                        // any plains tile
                        //
                        elseif(TerrainType(tmpLoc) == TerrainDB(TERRAIN_WATER_REEF) && IWN_REEF == 0) {
                                if(GetNeighbor(tmpLoc, 7, BorderLoc)) {
                                        for(k = 0; k < 8; k = k + 1) {
                                                if(GetNeighbor(tmpLoc, k, tmp2Loc)) {
                                                        if(TerrainType(tmp2Loc) == TerrainDB(TERRAIN_WATER_REEF)) {
                                                                IWN_REEF_DIR = k;
                                                                IWN_REEF_LOC = tmpLoc;
                                                                IWN_REEF = DoNW(BorderLoc);
                                                        }
                                                }
                                        }
                                }
                        }
                        // start on any reef tile, then move in a random direction, placing up to 4 more reef tile imps,
                        // to create a line of them
                        //
                        elseif(TerrainType(tmpLoc) == TerrainDB(TERRAIN_GRASSLAND) && UnitsInCell(tmpLoc) < 1 && IWN_GUILLIN == 0) {
                                if(GetNeighbor(tmpLoc, 7, BorderLoc)) {
                                        IWN_GUILLIN_LOC = tmpLoc;
                                        IWN_GUILLIN = DoNW(BorderLoc);
                                }
                        }
                        // any grassland tile
                        //
                        elseif(TerrainType(tmpLoc) == TerrainDB(TERRAIN_HILL) && UnitsInCell(tmpLoc) < 1 && IWN_FALL == 0 && HasRiver(tmpLoc)) {
                                if(GetNeighbor(tmpLoc, 6, tmp2Loc)) {
                                        if(HasRiver(tmp2Loc)) {
                                                count = 0;
                                                for(k = 1; k < 5; k = k + 1) {
                                                        if(GetNeighbor(tmpLoc, k, tmp3Loc)) {
                                                                if(k != 2 && HasRiver(tmp3Loc)) {
                                                                        count = count + 1;
                                                                }
                                                        }
                                                        if(count == 0){
                                                                if(GetNeighbor(tmpLoc, 7, BorderLoc)) {
                                                                        IWN_FALL_LOC = tmpLoc;
                                                                        IWN_FALL = DoNW(BorderLoc);
                                                                }
                                                        }
                                                }
                                        }
                                }
                        }
                        //
                        // Complicated one. Only creates falls when the neighbouring tile to the south west has a river, and
                        // the other surrounding tiles do not. This creates the falls as an end-point at the source of a river
                        // hence the placement in the hills.
                        //
                        elseif(TerrainType(tmpLoc) == TerrainDB(TERRAIN_DESERT) && UnitsInCell(tmpLoc) < 1 && IWN_URGUP == 0) {
                                if(GetNeighbor(tmpLoc, 7, BorderLoc)) {
                                        IWN_URGUP_LOC = tmpLoc;
                                        IWN_URGUP = DoNW(BorderLoc);
                                }
                        }
                        // any desert tile
                        //
                }
                Disabletrigger('IWN_placeborders');
                return CONTINUE;
        }
}

HandleEvent(BeginTurnProduction)'IWN_finishborders' post {
        int_t i;
        int_t j;
        location_t tmpLoc;
        location_t BorderLoc;

        for(i = 0; i < GetMapWidth() - 1; i = i + 1) {
                for(j = 0; j < GetMapHeight() - 1; j = j + 1) {
                        MakeLocation(tmpLoc, i, j);
                        if(tmpLoc == IWN_AYERS_LOC ||
                        tmpLoc == IWN_REEF_LOC ||
                        tmpLoc == IWN_CANYON_LOC ||
                        tmpLoc == IWN_FALL_LOC ||
                        tmpLoc == IWN_GUILLIN_LOC ||
                        tmpLoc == IWN_BAIKAL_LOC ||
                        tmpLoc == IWN_URGUP_LOC) {
                                if(GetNeighbor(tmpLoc, 7, BorderLoc)) {
                                        FinishImprovements(BorderLoc);
                                }
                        }
                }
        }
        Disabletrigger('IWN_finishborders');
}

HandleEvent(BeginTurnImprovements) 'IWN_place_nw' pre{
        int_t k;
        location_t BorderLoc;
        location_t tmp2Loc;
        location_t tmpLoc;

        if(GetCurrentRound () <= 1) {
                if(IWN_BAIKAL) {
                        Event:CreateImprovement(0, IWN_BAIKAL_LOC, TerrainImprovementDB(TILEIMP_NW_BAIKAL), 0);
                        if(GetNeighbor(IWN_BAIKAL_LOC, 7, BorderLoc)) {
                                Event:CutImprovements(BorderLoc);
                        }
                }
                if(IWN_AYERS) {
                        Event:CreateImprovement(0, IWN_AYERS_LOC, TerrainImprovementDB(TILEIMP_NW_AYERS), 0);
                        if(GetNeighbor(IWN_AYERS_LOC, 7, BorderLoc)) {
                                Event:CutImprovements(BorderLoc);
                        }
                }
                if(IWN_CANYON) {
                        Event:CreateImprovement(0, IWN_CANYON_LOC, TerrainImprovementDB(TILEIMP_NW_CANYON), 0);
                        if(GetNeighbor(IWN_CANYON_LOC, 7, BorderLoc)) {
                                Event:CutImprovements(BorderLoc);
                        }
                }
                if(IWN_REEF) {
                        Event:CreateImprovement(0, IWN_REEF_LOC, TerrainImprovementDB(TILEIMP_NW_REEF), 0);
                        tmpLoc = IWN_REEF_LOC;
                        for(k=0; k < 4; k = k + 1) {
                                if(GetNeighbor(tmpLoc, IWN_REEF_DIR, tmp2Loc)) {
                                        tmpLoc = tmp2Loc;
                                        if(TerrainType(tmpLoc) == TerrainDB(TERRAIN_WATER_REEF)) {
                                                Event:CreateImprovement(0, tmpLoc, TerrainImprovementDB(TILEIMP_NW_REEF), 0);
                                        } else {
                                                k = 4;
                                        }
                                }
                        }
                        if(GetNeighbor(IWN_REEF_LOC, 7, BorderLoc)) {
                                Event:CutImprovements(BorderLoc);
                        }
                }
                if(IWN_GUILLIN) {
                        Event:CreateImprovement(0, IWN_GUILLIN_LOC, TerrainImprovementDB(TILEIMP_NW_GUILLIN), 0);
                        if(GetNeighbor(IWN_GUILLIN_LOC, 7, BorderLoc)) {
                                Event:CutImprovements(BorderLoc);
                        }
                }
                if(IWN_FALL) {
                        Event:CreateImprovement(0, IWN_FALL_LOC, TerrainImprovementDB(TILEIMP_NW_FALL), 0);
                        if(GetNeighbor(IWN_FALL_LOC, 7, BorderLoc)) {
                                Event:CutImprovements(BorderLoc);
                        }
                }
                if(IWN_URGUP) {
                        Event:CreateImprovement(0, IWN_URGUP_LOC, TerrainImprovementDB(TILEIMP_NW_URGUP), 0);
                        if(GetNeighbor(IWN_URGUP_LOC, 7, BorderLoc)) {
                                Event:CutImprovements(BorderLoc);
                        }
                }
        }
        Disabletrigger('IWN_place_nw');
        return CONTINUE;
}

//---------------------------------------------------------
// finish imp and remove advance functions have to fire
// on separate handlers to place tile imp and grant advance
//

HandleEvent(BeginTurn) 'IWN_remove_sub_ads' post {
        int_t i;
        int_t j;
        location_t tmpLoc;

        if(HasAdvance(player[0], ID_ADVANCE_SUBNEURAL_ADS)) {
                RemoveAdvance(player[0], AdvanceDB(ADVANCE_SUBNEURAL_ADS));
        }
        for(i = 0; i < GetMapWidth() - 1; i = i + 1){
                for(j = 0; j < GetMapHeight() - 1; j = j + 1){
                        MakeLocation(i, j, tmpLoc);
                        if(TileHasNaturalWonder(tmpLoc)) {
                                FinishImprovements(tmpLoc);
                        }
                }
        }
}