Founding cities only on specific tiles

Lib.Spi't

Overlord of the Wasteland
Joined
Feb 12, 2009
Messages
3,708
Location
UK
Hi everybody out there.

Would it be possible to make a settler unit that can only found cities on specific tiles for example:

only on copper or only on a ruin or only on specific bonus tiles?

would it be an xml job or would it require the other types of code as well?

also while i'm here how do you go about making a settler that automatically build city buildings on founding, like the colonist and pioneer from 'Rise of Mankind' and could that also be tied in to what type of terrain or improvement the city is founded on.

I understand this might be a complex problem

any help would be much appreciated.

Thanks in advance.
 
By "build city buildings on founding", do you mean "free buildings in a city"? If you do, this is entirely XML, in CIV4CivilizationInfos.xml, under FreeBuildingClasses. But it's done "per Civilization", not "per Settler type."

The rest sounds like modding the DLL would be necessary.
 
Could be done though python...maybe.
There's a function "cannotFoundCity", which can prohibit founding one.
But there's no reference to a unit, so i guess, it would prevent all units (and not only the special one) from founding a city.
 
the free duildings i was referring to were in the rise of mankind mod where you havce advanced settlers that give 2 or 3 pop on founding as well as market and harbour and other things, was just wondering how it was done.

and if it could be done so that if a city was built on say coal it would found with something like a 'coal pit' building and from that you could build a number of specific buildings. thats the essence of the idea i'm trying to explore. as well as being limited to certain tiles for founding a city
 
In BTS, cannotFoundCity is one of the Python Callback defines. If you change the 0 to a 1, you can run this function anyway, but at the cost of performance.

I think you may be able to specify a unit in this function. Part of the variables defined for the function are the X and Y coordinate of the plot, so you can set them to a plot variable. Then, I know there's a way to get all the units on a plot and set it to a variable like pUnit (I can't remember the code, else I'd post it here), and then you can set up an if statement that runs if one of the units is a settler, or another type of settler.

From there, you can have the function return False when you want to found a city, and return True when you do not want to found a city.
 
TC01 just read your post and i am aa touch confused, my apologies.

I currently only have a knowledge of XML stuff not python.

Would your idea refer to a map reference, so one tile of that grid reference. Or would it be possible to define as a particular tile bonus e.g. iron or ruins?

Sorry I don't fully understand you like I said its a lack of understanding of the Python coding and mechanics.

But am I understanding that you would need python to achieve my aim?
 
TC01 just read your post and i am aa touch confused, my apologies.

I currently only have a knowledge of XML stuff not python.

Would your idea refer to a map reference, so one tile of that grid reference. Or would it be possible to define as a particular tile bonus e.g. iron or ruins?

Sorry I don't fully understand you like I said its a lack of understanding of the Python coding and mechanics.

But am I understanding that you would need python to achieve my aim?

Yeah, I meant to show the code, but I forgot and had to look up the functions. Sorry.

To make it so that a special settler unit can settle only on a certain plot, you'd have to use python, as well as XML.

First, you'd need to go into Assets/XML/PythonCallbackDefines.xml and change "USE_CANNOT_FOUND_CITY_CALLBACK" from 0 to 1. If it is set to 0, the game will never run this function. (As a note, if you do something in python and it doesn't do anything in game, you should check this file and make sure the function you are messing with isn't listed here with a "0".)

Then, you'd need to go into Assets/Python/CvGameUtils.py, search for cannotFoundCity, and change it into something like this...

Code:
	def cannotFoundCity(self,argsList):
		iPlayer, iPlotX, iPlotY = argsList
		pPlot = CyMap().plot(iPlotX, iPlotY)
		for i in range(pPlot.getNumUnits()):
			pUnit = pPlot.getUnit(i)
			if pUnit.getUnitType() == gc.getInfoTypeForString('UNIT_COPPER_SETTLER'):
				if pPlot.getBonusType() == gc.getInfoTypeForString('BONUS_COPPER'):
					return False
				return True
			return False

What this does is:

1. Sets "pPlot" to the coordinates (iPlotX, iPlotY). The lines above are the default function, everything below I've added.

2. The next two lines count all the units on pPlot and store them as a variable, pUnit, which is not one single unit but rather every unit on the plot at once. (I can do something similar to get all the plots on the map.)

3. The next line is an if-statement: if one of the units on the map has the Type UNIT_COPPER_SETTLER, a nonexistant unit that can only settle on Copper. If it does, it does the steps indented below it. Else, it simply returns False, meaning you can build a city.

4. The next line only triggers if the if statement above it is true. It asks whether the plot UNIT_COPPER_SETTLER is on has the Bonus (resource) Copper. If it does, it returns False (can build), but if it doesn't, it returns True (can't build).

If I wanted, I could change the "if pPlot.getBonusType()" line to "if pPlot.isHill", or "if pPlot.getImprovementType()", or "pPlot.getFeatureType()", allowing for other conditions.

You also need to create a "UNIT_COPPER_SETTLER", I didn't in a quick test I ran. However, using the normal Settler, I can still build cities anywhere I want, even with this code in the game. It might not work for UNIT_COPPER_SETTLER, though... if you can't get it to work, just ask.

(If someone sees a reason why this code won't work, please tell me- I'm not that great at python either...)
 
thanks very much for your speedy response

I'll see what I can do with everything you have given me, I may well have some more questions as I get my head around but I understand overall idea of what you've said.

cheers

You're welcome.

Glad I was able to help.
 
I like Notepad++ myself, as both an XML and Python editor, and a SDK viewer (I don't mess with the SDK).

But whatever works you should use... except for Windows Notepad, which, while it works, is a pretty bad program to use.
 
clearly I've done something slightly catastrophic???

it doesn't have the starting pop up screen either, where it says 'PlayerX you have been chosen to lead etc...'

but I don't understand what I could have done?
I've only changed that bit of python and added the COPPER_SETTLER unit into the game?
How could any of that have affected it?
 
EDIT: Never mind.

I'd suggest not making a starting settler only able to settle on copper, unless you are going to give that civ knowledge of all copper resources from the beginning of the game- no one actually knows where copper is. It was just an example.

Can you settle your Copper Settler on a tile with copper? (Use Worldbuilder to test).
 
Top Bottom