Bazaar developer reference

CvEconomicAI::DoReconState()

Defined in
CvEconomicAI.cpp, line 2053
Class
CvEconomicAI
Hook name
CivHooks::CvEconomicAI_DoReconState

Hooks

static bool BeforeCvEconomicAI_DoReconState(CvEconomicAI* self);static void AfterCvEconomicAI_DoReconState(CvEconomicAI* self);static void ReplaceCvEconomicAI_DoReconState(void (*original)(CvEconomicAI*), CvEconomicAI* self);CivRegisterBefore<CivHooks::CvEconomicAI_DoReconState>(host, &BeforeCvEconomicAI_DoReconState);CivRegisterAfter<CivHooks::CvEconomicAI_DoReconState>(host, &AfterCvEconomicAI_DoReconState);CivRegisterReplace<CivHooks::CvEconomicAI_DoReconState>(host, &ReplaceCvEconomicAI_DoReconState);

Code

2052/// Determine how our recon efforts are going2053void CvEconomicAI::DoReconState()2054{2055	int iPlotLoop, iDirectionLoop, iUnitLoop;2056	CvPlot* pPlot;2057	CvPlot* pAdjacentPlot;2058	CvUnit* pLoopUnit;2059	bool bIsLand;2060	bool bIsCoastalWater;20612062	if(GetPlayer()->isMinorCiv())2063	{2064		m_eReconState = RECON_STATE_ENOUGH;2065		m_eNavalReconState = RECON_STATE_ENOUGH;2066		return;2067	}20682069	// Start at 1 so we don't get divide-by-0 errors2070	//   Land recon counters2071	int iNumLandPlotsRevealed = 1;2072	int iNumLandPlotsWithAdjacentFog = 1;20732074	//   Naval recon counters2075	int iNumCoastalTilesRevealed = 1;2076	int iNumCoastalTilesWithAdjacentFog = 1;20772078	bool bNeedToLookAtDeepWaterAlso = GET_TEAM(m_pPlayer->getTeam()).canEmbarkAllWaterPassage();20792080	// Look at map size and gauge how much of it we know about2081	for(iPlotLoop = 0; iPlotLoop < GC.getMap().numPlots(); iPlotLoop++)2082	{2083		pPlot = GC.getMap().plotByIndexUnchecked(iPlotLoop);20842085		if(pPlot->isRevealed(m_pPlayer->getTeam()))2086		{2087			bIsLand = false;2088			bIsCoastalWater = false;20892090			// Count Revealed Land Plots2091			if(!pPlot->isWater())2092			{2093				bIsLand = true;2094				iNumLandPlotsRevealed++;2095			}2096			else if(pPlot->isShallowWater() || bNeedToLookAtDeepWaterAlso)2097			{2098				bIsCoastalWater = true;2099				iNumCoastalTilesRevealed++;2100			}21012102			// Check adjacent Plots for THEIR visibility2103			for(iDirectionLoop = 0; iDirectionLoop < NUM_DIRECTION_TYPES; ++iDirectionLoop)2104			{2105				pAdjacentPlot = plotDirection(pPlot->getX(), pPlot->getY(), ((DirectionTypes)iDirectionLoop));21062107				if(pAdjacentPlot != NULL)2108				{2109					// Check to see if adjacent Tile is land or water...2110					if(pAdjacentPlot->isWater())2111					{2112						// This is a slight cheat (because the AI rules out water tiles) but helps prevents the AI from building too many Land explorers2113						if((bNeedToLookAtDeepWaterAlso || pAdjacentPlot->isShallowWater()) && !pAdjacentPlot->isRevealed(m_pPlayer->getTeam()))2114						{2115							iNumCoastalTilesWithAdjacentFog++;2116							break;2117						}2118					}2119					else2120					{2121						// This is a slight cheat (because the AI rules out water tiles) but helps prevents the AI from building too many Land explorers2122						if(!pAdjacentPlot->isRevealed(m_pPlayer->getTeam()))2123						{2124							iNumLandPlotsWithAdjacentFog++;2125							break;2126						}2127					}2128				}2129			}2130		}2131	}21322133	// RECON ON OUR HOME CONTINENT21342135	// How many Units do we have exploring or being trained to do this job? The more Units we have the less we want this Strategy2136	int iNumExploringUnits = m_pPlayer->GetNumUnitsWithUnitAI(UNITAI_EXPLORE, true, false) + m_iExplorersDisbanded;2137	int iStrategyWeight = /*100*/ GC.getAI_STRATEGY_EARLY_EXPLORATION_STARTING_WEIGHT();2138	int iWeightThreshold = 110;  // So result is a number from 10 to 1002139	iWeightThreshold -= m_pPlayer->GetGrandStrategyAI()->GetPersonalityAndGrandStrategy((FlavorTypes)GC.getInfoTypeForString("FLAVOR_RECON")) *2140	                    /*10*/ GC.getAI_STRATEGY_EARLY_EXPLORATION_WEIGHT_PER_FLAVOR();21412142	// Safety check even if personality flavor is higher than expected2143	if(iWeightThreshold > 100)2144	{2145		iWeightThreshold = 100;2146	}21472148	iStrategyWeight *= iNumLandPlotsWithAdjacentFog;2149	int iNumExplorerDivisor = iNumExploringUnits + /*1*/ GC.getAI_STRATEGY_EARLY_EXPLORATION_EXPLORERS_WEIGHT_DIVISOR();2150	iStrategyWeight /= (iNumExplorerDivisor * iNumExplorerDivisor);2151	iStrategyWeight /= (int)sqrt((double)iNumLandPlotsRevealed);21522153	if(iStrategyWeight > iWeightThreshold)2154	{2155		m_eReconState = RECON_STATE_NEEDED;2156	}2157	else2158	{2159		if(iStrategyWeight > (iWeightThreshold / 4))2160		{2161			m_eReconState = RECON_STATE_NEUTRAL;2162		}2163		else2164		{2165			m_eReconState = RECON_STATE_ENOUGH;21662167			// Return all/most warriors/spears to normal unit AI since have enough recon.  Keep at least 1 explorer through Turn 100.2168			bool bSkipFirst = GC.getGame().getGameTurn() < 100;2169			for(pLoopUnit = m_pPlayer->firstUnit(&iUnitLoop); pLoopUnit != NULL; pLoopUnit = m_pPlayer->nextUnit(&iUnitLoop))2170			{2171				if(pLoopUnit->AI_getUnitAIType() == UNITAI_EXPLORE && pLoopUnit->getUnitInfo().GetUnitAIType(UNITAI_ATTACK))2172				{2173					if(bSkipFirst)2174					{2175						bSkipFirst = false;2176					}2177					else2178					{2179						pLoopUnit->AI_setUnitAIType(UNITAI_ATTACK);2180						if(GC.getLogging() && GC.getAILogging())2181						{2182							CvString strLogString;2183							strLogString.Format("Assigning exploring %s back to attack AI, X: %d, Y: %d", pLoopUnit->getName().GetCString(), pLoopUnit->getX(), pLoopUnit->getY());2184							m_pPlayer->GetHomelandAI()->LogHomelandMessage(strLogString);2185						}2186					}2187				}2188			}2189		}2190	}21912192	// NAVAL RECON ACROSS THE ENTIRE MAP21932194	// No coastal cities?  Moot point...2195	CvCity* pLoopCity;2196	int iCityLoop;2197	bool bFoundCoastalCity = false;2198	for(pLoopCity = m_pPlayer->firstCity(&iCityLoop); pLoopCity != NULL && !bFoundCoastalCity; pLoopCity = m_pPlayer->nextCity(&iCityLoop))2199	{2200		if(pLoopCity->isCoastal())2201		{2202			bFoundCoastalCity = true;2203		}2204	}22052206	if(!bFoundCoastalCity)2207	{2208		m_eNavalReconState = RECON_STATE_ENOUGH;2209	}22102211	else2212	{2213		// How many Units do we have exploring or being trained to do this job? The more Units we have the less we want this Strategy2214		iNumExploringUnits = m_pPlayer->GetNumUnitsWithUnitAI(UNITAI_EXPLORE_SEA, true, true);2215		iStrategyWeight = /*100*/ GC.getAI_STRATEGY_EARLY_EXPLORATION_STARTING_WEIGHT();2216		iWeightThreshold = 110;  // So result is a number from 10 to 1002217		iWeightThreshold -= m_pPlayer->GetGrandStrategyAI()->GetPersonalityAndGrandStrategy((FlavorTypes)GC.getInfoTypeForString("FLAVOR_NAVAL_RECON")) *2218		                    /*10*/ GC.getAI_STRATEGY_EARLY_EXPLORATION_WEIGHT_PER_FLAVOR();22192220		// Safety check even if personality flavor is higher than expected2221		if(iWeightThreshold > 100)2222		{2223			iWeightThreshold = 100;2224		}22252226		iStrategyWeight *= iNumCoastalTilesWithAdjacentFog;2227		iNumExplorerDivisor = iNumExploringUnits + /*1*/ GC.getAI_STRATEGY_EARLY_EXPLORATION_EXPLORERS_WEIGHT_DIVISOR();2228		iStrategyWeight /= (iNumExplorerDivisor * iNumExplorerDivisor);2229		iStrategyWeight /= (int)sqrt((double)iNumCoastalTilesRevealed);22302231		if(iStrategyWeight > iWeightThreshold/* || iNumExploringUnits == 0 && iNumCoastalTilesWithAdjacentFog > 50*/)2232		{2233			m_eNavalReconState = RECON_STATE_NEEDED;2234		}2235		else2236		{2237			if(iStrategyWeight > (iWeightThreshold / 4))2238			{2239				m_eNavalReconState = RECON_STATE_NEUTRAL;2240			}2241			else2242			{2243				m_eNavalReconState = RECON_STATE_ENOUGH;22442245				// Return all/most boats to normal unit AI since have enough recon2246				bool bSkipFirst = (m_eNavalReconState == RECON_STATE_NEUTRAL);2247				for(pLoopUnit = m_pPlayer->firstUnit(&iUnitLoop); pLoopUnit != NULL; pLoopUnit = m_pPlayer->nextUnit(&iUnitLoop))2248				{2249					if(pLoopUnit->AI_getUnitAIType() == UNITAI_EXPLORE_SEA && pLoopUnit->getUnitInfo().GetUnitAIType(UNITAI_ATTACK_SEA))2250					{2251						if(bSkipFirst)2252						{2253							bSkipFirst = false;2254						}2255						else2256						{2257							pLoopUnit->AI_setUnitAIType(UNITAI_ATTACK_SEA);2258							if(GC.getLogging() && GC.getAILogging())2259							{2260								CvString strLogString;2261								strLogString.Format("Assigning naval explorer back to attack sea AI to %s, X: %d, Y: %d", pLoopUnit->getName().GetCString(), pLoopUnit->getX(), pLoopUnit->getY());2262								m_pPlayer->GetHomelandAI()->LogHomelandMessage(strLogString);2263							}2264						}2265					}2266				}2267			}2268		}2269	}2270}

Calls

Called by