How to check every city?

NotSoGood

Emperor
Joined
Jan 25, 2009
Messages
1,077
Location
Finland
I'm trying to change Manhattan Project into national wonder and remove the global effect allowing to build nukes. So when you build the Manhattan Project you can train nukes and receive bomb shelters in every cities. It also allows you to build bomb shelters later. Right now I have changed it to national wonder and allowed it to build nukes. But now I have run into a problem, how can I check in python every single city that someone has? I would apreciate help.
 
If you are still interested in using Python to check every city owned by a player, this function should work. You should pass a pointer to a CyPlayer object.

Code:
# Returns a list of CyCity pointers.
def GetCities(player):
	cities = [ ]
	city, iter = player.firstCity(False)
	while city:
		cities += [ city ]
		city, iter = player.nextCity(iter, false)
	return cities
 
I think python would be the best way in this. But because I'm still just trying to learn python could you explain me that code? Where to use it and what it does?

EDIT: Just noticed, this is a fuction (or something like that) in python isn't it? Any way to check the cities after you build a building? It would be able to be used in CvEventManager in onBuildingBuilt.
 
I'm don't know exactly what you want to do. Could you give me some more detail?
 
I'm don't know exactly what you want to do. Could you give me some more detail?

:) Sorry if you didn't understand me. I'm not the best at English so it is sometimes quite hard to read. Mayby some examples...
So I intented to use it in CvEventManager under onBuildingBuilt. If I'm right your code cannot be added as it's under onBuildingBuilt, like this:
Code:
	def onBuildingBuilt(self, argsList):
		'Building Completed'
		pCity, iBuildingType = argsList
		game = gc.getGame()
		
		[B]# Returns a list of CyCity pointers.
		def GetCities(player):
			cities = [ ]
			city, iter = player.firstCity(False)
			while city:
				cities += [ city ]
				city, iter = player.nextCity(iter, false)
			return cities[/B]
		
		if ((not gc.getGame().isNetworkMultiPlayer()) and (pCity.getOwner() == gc.getGame().getActivePlayer()) and isWorldWonderClass(gc.getBuildingInfo(iBuildingType).getBuildingClassType())):
			# If this is a wonder...
			popupInfo = CyPopupInfo()
			popupInfo.setButtonPopupType(ButtonPopupTypes.BUTTONPOPUP_PYTHON_SCREEN)
			popupInfo.setData1(iBuildingType)
			popupInfo.setData2(pCity.getID())
			popupInfo.setData3(0)
			popupInfo.setText(u"showWonderMovie")
			popupInfo.addPopup(pCity.getOwner())

		CvAdvisorUtils.buildingBuiltFeats(pCity, iBuildingType)

		if (not self.__LOG_BUILDING):
			return
		CvUtil.pyPrint('%s was finished by Player %d Civilization %s' 
			%(PyInfo.BuildingInfo(iBuildingType).getDescription(), pCity.getOwner(), gc.getPlayer(pCity.getOwner()).getCivilizationDescription(0)))
So is there anyway to use it that when you build the building it checks all the cities you have and gains acces for you to those cities? Like check or add buildings, population, etc...
 
Technically You could do it that way as long as you added a call to the function.

However, why would you want to cycle thru the player's cities within onBuildingBuilt? You already have a city pointer (pCity) that points to the city where the building was built. The iBuildingType variable contains the building type for the building that was just built. For example if you want to do something every time a city builds a bunker you could do this.....

Code:
if iBuilding == BuildingType.BUILDING_BUNKER:
	# Place your code here.

If you want to cycle thru a player's cities and do something that depends on the current status of each city, you probably would want to do that somewhere other than onBuildingBuilt, since your test would only occur when a building is built.
 
If you want to cycle thru a player's cities and do something that depends on the current status of each city, you probably would want to do that somewhere other than onBuildingBuilt, since your test would only occur when a building is built.

This made me actually think more about what I want to do. I took a closer look into API and found the function countNumBuildings (BuildingType eBuilding). This will do what I want about being able to build bomb shelters after building the Manhattan Project and you don't even have to check every cities. I tried using it like this:
Code:
	def canConstruct(self,argsList):
		pCity = argsList[0]
		eBuilding = argsList[1]
		bContinue = argsList[2]
		bTestVisible = argsList[3]
		bIgnoreCost = argsList[4]
		
		## Manhattan Project start ##
		iManhattanProject = gc.getInfoTypeForString('BUILDING_MANHATTAN_PROJECT')
		iBombShelter = gc.getInfoTypeForString('BUILDING_BOMB_SHELTER')
		cityOwner = pCity.getOwner
		if eBuilding == iBombShelter:
			if cityOwner.countNumBuildings(iManhattanProject) == 1:
				return True
		## Manhattan Project end ##		
		
		return False
but got python error:
Code:
Traceback (most recent call last):

  File "CvGameInterface", line 150, in canConstruct

  File "CvGameUtils", line 195, in canConstruct

AttributeError: 'Boost.Python.function' object has no attribute 'countNumBuildings'
ERR: Python function canConstruct failed, module CvGameInterface
What is wrong there?
 
replace cityowner with this. getOwner() only returns an int.

Code:
		ePlayer = pCity.getOwner()
		pPlayer = gc.getPlayer(ePlayer)
 
replace cityowner with this. getOwner() only returns an int.

Code:
		ePlayer = pCity.getOwner()
		pPlayer = gc.getPlayer(ePlayer)

Thanks Sephi, that was it. :goodjob:
Now the bomb shelter is able to be built after you construct the Mahattan Project. I quess I can use the same code for enabling training nukes. I'll check the API if I find something interesting about giving buildings. BTW I'll have to check did the original Manhattan Project even give you free bomb shelters...
 
Back
Top Bottom