trying to use a minimalist mod to do big things

alright, what is the difference between:
You forgot the key info: what class does there methods belong to?

But I would guess that the only difference may be whether or what "game event" the method will trigger. So it may not be critical which you end up using - but you should of course test this in practice before settling with one of them.

One method might also be more convenient to use than another, but you should probably be happy with all the options! :king:

to eliminate any cities or units on any plots found in lPlotList?
Basically, yes. :king: But firstly you need to figure out what the values in lPlotList are. Because you may need to fetch a CyCity, CyPlot or CyPlayer (or even CyGame?) instance for the method you end up using. Alternatively you might need to get the ID (integer) of the CyCity instance.

This is somewhat tricky, at first, but you could start with figuring out what values you already have, what method you're gonna use, and finally what class instance or other value you need. I think you have your hands full for now. And I think you're actually learning this stuff now. :goodjob:
 
As a reference, I'm using CyCity.kill() and CyUnit.kill() within this context in PyScenario. But this might not be optimal for you.
 
VOID and void in the API means that the function does not return a result. This means you should not put the function call on the right side of an assignment operator (=) because there's no value to assign. It only does work; it doesn't tell you anything as a result.

In the API the stuff after a hyphen (-) is a comment that describes what the function does. Sadly, very few functions actually have this. Typically it's the functions that are obvious from their name that have the documentation and the complicated ones that lack it. :cry:
 
I'm guessing VOID is passed over from the C++ code in the SDK? Because it would be None if the API was actually written in Python, right?
 
oh, I knew that about the "void" I meant the several commands that looked like they all did basically the same thing.

also…before I go crazy with this…I want to take the opportunity to complicate matters.

I've been thinking about these spawns and how to balance history and choice, human and AI.

What do you think of the following spawn blueprint?




1) when a new AI civ spawns, the intended start plot and all adjacent plots are wiped (all units, culture, and cities) - no choice - this paves the way for the new capital. if the old civ is AI, no choice is given on step two, they automatically consent.

2) if the old civ is human, a popup then gives a choice whether or not the old civ wants to allow the flip (all cities, units and culture…simply taking whatever values are found and making them belong to the new civ).

3) If they say yes, the flip happens and the new civ starts with normal diplomacy. If they say no, the flip does not happen and the new civ begins in a state of war with the old civ. The starting units will be the same in any case.

4) if the new civ is human, the old civ automatically consents, even if it is human.


Does this sound equitable for players and like something you'd be willing to coach on without being driven to drink?
 
Yes and no. ;)

Yes, void comes from the C++ SDK is that is the declared return type of the function. The API is generated from a combination of the exported Boost::Python layer and the C++ code.

No, there is no value returned from the Python calls to those C++ functions. Any function that does not return a value in Python automatically evaluates to the None value when used in an expression.

I do not actually know if Python returns None for the function or substitutes None at the point where it is used in an expression. That would be an implementation detail left up to the interpreter.
 
I would hate to have a high level--or worse yet, a great general or other great person--on those tiles that got nuked. Perhaps move any units in those tiles into the closest tile that will remain under the original owner's control.
 
also…before I go crazy with this…I want to take the opportunity to complicate matters.
Good for you! :goodjob:

I've been thinking about these spawns and how to balance history and choice, human aand AI.

What do you think of the following spawn blueprint?
What you describe is basically doable - with Python. But you might have all these ideas on the back-burner and focus on getting some basic functionality in before you start messing around with popups and choices and stuff.

As long as you define things in separate functions it will be easy enough to add functionality going forward.

Does this sound equitable for players and like something you'd be willing to coach on without being driven to drink?
I'm sure I speak for other also when I say that this: As long as you don't try to do everything at once - and get ahead of yourself in general - we'll be here to coach you all the way. :D

Now figure out what the basic functionality is, exactly. Lets implement that! Then we can add checks for human player(s) and write alternate code for these instances. And lastly we can start to poke in the hornets nest that is multi-choice popups... (There are basically two alternate APIs for popups, and some of this is already covered in my tutorial.)
 
I would hate to have a high level--or worse yet, a great general or other great person--on those tiles that got nuked. Perhaps move any units in those tiles into the closest tile that will remain under the original owner's control.
Yeah, anything like this can be refined in absurdum. I'm not sure that units should be killed, period. But I do believe that changing tile ownership and spawning/founding a city will move any present units to a safe distance.
 
Rhye's simply nukes the box where the capital city spawn will take place. Of course, he (or is he a she?) gives the human player the opportunity to veto the flip entirely. I'm basically suggesting that cities in the 9x9 around what will be the spawn/capital get nuked. period. but you get the opportunity to veto anything else.

I would not be opposed to "moving" important units (or even all units) on those tiles, and would welcome the opportunity to replicate buildings/wonders/religions in the new city.

But, as Baldyr says, that is for another day.

Alright...I've defined country-wide flip zones, but i think I also need to define 9x9 city flip zones and work with them, as this will be the initial spawn and "nuke" space.
 
This is about the point that I like to remind you to make backups as you go. There's nothing worse than going down a road that turns out to be too complicated or just plain not what you want only to find you cannot get your mod back to a runnable state and having to start over.

Every so often, ZIP up your mod folder and keep a few backups. Give them meaningful names to go along with their creation date to remind you what's what.
 
alright...I am certain this is not correct, but I'm hoping it is principled enough to serve as a starting point. I know I'm not dealing with the list of plots correctly (and I'm sure the end is wrong, too, but I'm interested to see what the lesson is in this part of it.

Code:
#killboxes for spawns
tRoman = ((60, 45), (62, 47))
tPersian = ((80, 40), (82, 42))
tJapanese = ((114, 45), (116, 47))
tKorean = ((108, 45), (110, 47))
tArabian = ((74, 34), (76, 36))
tEnglish = ((54, 53), (56, 55))
tFrench = ((57, 50), (59, 52))
tSpanish = ((54, 44), (56, 46))
tGerman = ((62, 51), (64, 53))
tRussian = ((70, 53), (72, 55))
tAmerican = ((26, 44), (28, 46))


#compiles a list of plots
def getPlotList(tBL, tTR):
        lPlotList = []
        for x in range(tBL[0], tTR[0]+1):
                for y in range(tBL[1], tTR[1]+1):
                        lPlotList.append((x, y))
        return lPlotList


#kills all units, and cities in the plotlist, adds massive culture for the new civ
def killBox (self, lPlotlist):
	getMap().plot(lPlotList)
	changeCulture(eRome, 100, True):
		if isCity:
			raze()
		if isUnit:
			killUnits()

::ducks as Baldyr hurls a shoe::
 
hm...i just realized I never told it which set of coords from the defined tuples to use. nevermind...sigh...back to the drawing board...
 
alright, I understand now how to get the city on a plot and kill that city. I need to do this in a 9x9 box for each of these spawns (the city given below in the middle plot).

Now...I *could* simply define each of those 9 plots for each spawn, but I'd rather learn how to do it the proper way and scroll through them all (either using tuples I've defined in my constants giving the bottom left and top right of each 9x9 box, or by using the center tile and coding it similar to how Rhye appears to have used tCapital). I don't simply want to copy Rhye's code; I want to draft something from scratch that will do what I need it to do.

So...anybody well versed in this and willing to jump in with a bit of explanation? I know you do, Baldyr, but I also know it's the wee hours of the morning where you are, so when you see my solicitiation, don't feel left out, lol...


(the code below works...it reduces the city on the tile to rubble and spawns the units)
Spoiler :
Code:
#spawns the classical civs 800BC on the map (different date used for testing change before release)
def classicalSpawn():
	pRome = gc.getMap().plot(61, 46)
	pPersia = gc.getMap().plot(81, 41)
	pJapan = gc.getMap().plot(115, 46)
	pKorea = gc.getMap().plot(109, 46)
	if isDate(-3985):
		pRome.getPlotCity().kill()
		pPersia.getPlotCity().kill()
		pJapan.getPlotCity().kill()
		pKorea.getPlotCity().kill()
#Romans
		PyPlayer(7).initUnit(4, 61, 46, 3)
		PyPlayer(7).initUnit(5, 61, 46, 2)
		PyPlayer(7).initUnit(57, 61, 46, 15)
#Persians		
		PyPlayer(8).initUnit(4, 81, 41, 3)
		PyPlayer(8).initUnit(5, 81, 41, 2)
		PyPlayer(8).initUnit(57, 81, 41, 15)
#Japanese
		PyPlayer(9).initUnit(4, 115, 46, 3)
		PyPlayer(9).initUnit(5, 115, 46, 2)
		PyPlayer(9).initUnit(57, 115, 46, 15)
#Koreans
		PyPlayer(10).initUnit(4, 109, 46, 3)
		PyPlayer(10).initUnit(5, 109, 46, 2)
		PyPlayer(10).initUnit(57, 109, 46, 15)
 
alright, here goes:

I decided to eliminate a step. It struck me that I was overcomplicating things by trying to create a patch of culture for a civ with no cities while trying to spawn units on the spot and expecting it all to stay there long enough for the AI to build the capital city. Since these are later civs…why not just spawn the city?

So, that's what I did…the Classical civs spawn their historical capital, along with some extra settlers, workers and military units (colonies will just spawn units).

I still do need to figure out how to deal with culture flip zones and flipping cities and units for the optional area flips I suggested earlier (and the Americans won't get colonies, but "Manifest Destiny" in 1900, which will use that feature).

I also have to figure out how to use a loop to wipe that 3x3 box clean first, rather than individually inputting the nine tiles. I'll also have to figure out how to plant a loaded city (pre-loaded with some culture, population, and buildings, rather than a level 1, empty city)

And for the record, I did the city kill on my own using the API and looking at PyHelpers (the initCity was the same basic idea as initUnit) :king:.

the following code (the important part is called classicalSpawn) wipes a tile, and spawns a city on that tile as well as a bunch of units.

Spoiler :
Code:
#done by Antaine with great indebtedness to Baldyr, God-Emperor, and EmperorFool

from CvPythonExtensions import *
from Popup import PyPopup
from CvEventManager import *
from PyHelpers import *

gc = CyGlobalContext()
cyGame = CyGame()
cyMap = CyMap()
pyGame = PyGame()

#spawn zones
tRome = ((60, 43), (63, 48))
tPersia = ((80, 39), (86, 43))
tJapan = ((111, 41), (116, 51))
tKorea = ((107, 45), (111, 50))
tArabia = ((73, 31), (82, 38))
tEngland = ((53, 53), (56, 56))
tFrance = ((56, 47), (59, 52))
tSpain = ((52, 43), (57, 47))
tGermany = ((60, 50), (64, 64))
tRussia = ((65, 49), (80, 63))
tEastUS = ((24, 42), (34, 50))
tWestUS = ((11, 44), (23, 43))
tHawaii = ((112, 34), (6, 39))

#killboxes for spawns
tRoman = ((60, 45), (62, 47))
tPersian = ((80, 40), (82, 42))
tJapanese = ((114, 45), (116, 47))
tKorean = ((108, 45), (110, 47))
tArabian = ((74, 34), (76, 36))
tEnglish = ((54, 53), (56, 55))
tFrench = ((57, 50), (59, 52))
tSpanish = ((54, 44), (56, 46))
tGerman = ((62, 51), (64, 53))
tRussian = ((70, 53), (72, 55))
tAmerican = ((26, 44), (28, 46))

#units for later civ spawns
eSettler = 4
eWorker = 5
eArcher = 57
eLongbowman = 60
eMusketman = 42
eRifleman = 46

#for barbarian spawns
eGalley = 90
eViking = 36
eZulu = 38
eMongol = 68
eNative = 33
eAztec = 27
eInca = 25
eMaya = 39

#civs in the game (civ IDs, not WBS IDs)
eCeltia = 6
eEgypt = 8
eBabylon = 3
eGreece = 13
eIndia = 16
eChina = 7
eRome = 28
ePersia = 26
eJapan = 17
eKorea = 19
eArabia = 1
eEngland = 9
eFrance = 11
eSpain = 30
eGermany = 12
eRussia = 29
eAmerica = 0


cityNameDict = {
(55, 54): "London",
(55, 53): "London",
(56, 53): "London",
(56, 54): "London",
(63, 52): "Berlin",
(62, 52): "Berlin",
(62, 53): "Berlin",
(63, 53): "Berlin",
(51, 55): "Dublin",
(51, 56): "Dublin",
(55, 58): "Edinburgh",
(54, 57): "Edinburgh",
(54, 58): "Edinburgh",
(58, 51): "Paris",
(59, 51): "Paris",
(58, 52): "Paris",
(57, 51): "Paris",
(58, 50): "Paris",
(57, 50): "Paris",
(55, 45): "Madrid",
(55, 46): "Madrid",
(54, 46): "Madrid",
(54, 45): "Madrid",
(53, 45): "Lisbon",
(53, 44): "Lisbon",
(53, 46): "Lisbon",
(61, 46): "Rome",
(62, 45): "Rome",
(62, 46): "Rome",
(61, 47): "Rome",
(60, 47): "Rome",
(67, 43): "Athens",
(66, 42): "Athens",
(67, 44): "Athens",
(66, 44): "Athens",
(68, 46): "Byzantium",
(67, 46): "Byzantium",
(69, 45): "Byzantium",
(73, 40): "Jerusalem",
(73, 41): "Jerusalem",
(72, 39): "Jerusalem",
(72, 40): "Jerusalem",
(73, 42): "Antioch",
(73, 43): "Antioch",
(68, 39): "Alexandria",
(69, 39): "Alexandria",
(67, 39): "Alexandria",
(30, 47): "New York",
(31, 47): "New York",
(29, 47): "New York",
(29, 46): "New York",
(31, 48): "Boston",
(31, 49): "Boston",
(32, 49): "Boston",
(24, 43): "New Orleans",
(23, 43): "New Orleans",
(25, 43): "New Orleans",
(24, 48): "Chicago",
(24, 47): "Chicago",
(24, 49): "Chicago",
(25, 47): "Chicago",
(12, 48): "San Francisco",
(12, 47): "San Francisco",
(12, 49): "San Francisco",
(12, 50): "Seattle",
(12, 46): "Los Angeles",
(75, 35): "Mecca",
(74, 36): "Mecca",
(75, 34): "Mecca",
(74, 37): "Mecca",
(73, 37): "Mecca",
(76, 34): "Mecca",
(68, 57): "St. Petersburg",
(67, 56): "St. Petersburg",
(66, 56): "St. Petersburg",
(68, 56): "St. Petersburg",
(68, 58): "St. Petersburg",
(67, 58): "St. Petersburg",
(71, 54): "Moscow",
(71, 53): "Moscow",
(70, 53): "Moscow",
(72, 53): "Moscow",
(72, 54): "Moscow",
(70, 54): "Moscow",
(70, 56): "Moscow",
(71, 55): "Moscow",
(72, 55): "Moscow",
(69, 52): "Kiev",
(69, 51): "Kiev",
(70, 51): "Kiev",
(70, 50): "Odessa",
(71, 50): "Odessa",
(89, 35): "Bombay",
(89, 34): "Bombay",
(88, 35): "Bombay",
(88, 36): "Bombay",
(92, 34): "Pondicherry",
(91, 34): "Pondicherry",
(91, 33): "Pondicherry",
(102, 47): "Peking",
(101, 48): "Peking",
(102, 48): "Peking",
(103, 48): "Peking",
(101, 47): "Peking",
(103, 47): "Peking",
(101, 46): "Peking",
(102, 46): "Peking",
(103, 46): "Peking",
(115, 46): "Tokyo",
(115, 45): "Tokyo",
(114, 44): "Tokyo",
(106, 43): "Shanghai",
(106, 44): "Shanghai",
(106, 45): "Shanghai",
(107, 43): "Shanghai",
(107, 42): "Shanghai",
(105, 39): "Canton",
(105, 40): "Canton",
(106, 40): "Canton",
(106, 41): "Canton",
(103, 38): "Hong Kong",
(103, 39): "Hong Kong",
(104, 39): "Hong Kong",
(102, 38): "Hong Kong",
(102, 32): "Saigon",
(103, 33): "Saigon",
(102, 33): "Saigon",
(1, 38): "Honolulu",
(3, 37): "Honolulu",
(4, 35): "Hilo",
(5, 36): "Hilo",
(103, 14): "Perth",
(104, 14): "Perth",
(104, 13): "Perth",
(104, 12): "Perth",
(103, 12): "Perth",
(107, 19): "Darwin",
(107, 20): "Darwin",
(108, 20): "Darwin",
(108, 21): "Darwin",
(118, 13): "Sydney",
(117, 12): "Sydney",
(118, 15): "Sydney",
(118, 16): "Sydney",
(118, 17): "Sydney",
(114, 10): "Adelaide",
(114, 11): "Adelaide",
(113, 11): "Adelaide",
(115, 10): "Adelaide",
(77, 41): "Babylon",
(77, 40): "Babylon",
(76, 41): "Babylon",
(77, 42): "Babylon",
(76, 42): "Babylon",
(58, 47): "Marseilles",
(58, 48): "Marseilles",
(59, 48): "Marseilles",
(56, 48): "Bordeaux",
(56, 49): "Bordeaux",
(55, 51): "Brest",
(56, 51): "Brest",
(56, 44): "Gibraltar",
(54, 44): "Gibraltar",
(53, 54): "Cardiff",
(54, 54): "Cardiff",
(53, 55): "Cardiff",
(53, 53): "Cardiff",
(55, 56): "York",
(54, 56): "York",
(49, 54): "Cork",
(49, 56): "Galway",
(50, 56): "Galway",
(51, 54): "Waterford",
(50, 54): "Cashel",
(51, 57): "Belfast",
(50, 57): "Derry",
(50, 55): "Limerick",
(60, 55): "Copenhagen",
(60, 54): "Copenhagen",
(60, 53): "Copenhagen",
(62, 52): "Trondheim",
(63, 63): "Trondheim",
(64, 64): "Trondheim",
(60, 58): "Oslo",
(59, 57): "Oslo",
(58, 58): "Oslo",
(62, 58): "Uppsala",
(62, 59): "Uppsala",
(62, 60): "Uppsala",
(63, 58): "Stockholm",
(63, 57): "Stockholm",
(63, 56): "Stockholm",
(62, 56): "Stockholm",
(66, 59): "Helsinki",
(65, 59): "Helsinki",
(65, 58): "Helsinki",
(65, 58): "Vilnius",
(65, 55): "Vilnius",
(66, 54): "Vilnius",
(66, 55): "Vilnius",
(64, 53): "Vilnius",
(65, 53): "Vilnius",
(66, 53): "Vilnius",
(63, 50): "Vienna",
(64, 50): "Vienna",
(65, 50): "Vienna",
(65, 49): "Vienna",
(64, 49): "Vienna",
(63, 49): "Vienna",
(64, 52): "Warsaw",
(63, 51): "Warsaw",
(62, 48): "Venice",
(61, 48): "Venice",
(63, 48): "Venice",
(61, 43): "Palermo",
(62, 43): "Palermo",
(76, 32): "Sanaa",
(77, 32): "Sanaa",
(77, 33): "Sanaa",
(78, 33): "Sanaa",
(64, 12): "Cape Town",
(64, 13): "Cape Town",
(65, 13): "Cape Town",
(65, 12): "Cape Town",
(42, 18): "Rio De Janeiro",
(43, 19): "Rio De Janeiro",
(41, 18): "Rio De Janeiro",
(39, 15): "Montevideo",
(38, 14): "Montevideo",
(38, 13): "Montevideo",
(36, 13): "Buenos Aires",
(37, 13): "Buenos Aires",
(36, 12): "Buenos Aires",
(18, 39): "Mexico City",
(18, 38): "Mexico City",
(19, 39): "Mexico City",
(19, 40): "Mexico City",
(18, 49): "Mexico City",
(24, 45): "St. Louis",
(25, 45): "St. Louis",
(25, 46): "St. Louis",
(24, 46): "St. Louis",
(27, 38): "Havanna",
(28, 38): "Havanna",
(31, 37): "Port-au-Prince",
(31, 39): "Port-au-Prince",
(56, 50): "Nantes",
(59, 53): "Amsterdam",
(59, 52): "Amsterdam",
(28, 46): "Philadelphia",
(28, 45): "Philadelphia",
(27, 45): "Washington",
(27, 44): "Washington",
(58, 42): "Carthage",
(59, 42): "Carthage",
(59, 41): "Carthage",
(59, 40): "Carthage",
(60, 40): "Tripoli",
(61, 40): "Tripoli",
(62, 40): "Tripoli",
(47, 61): "Reykjavik",
(47, 62): "Reykjavik",
(48, 62): "Reykjavik",
(46, 63): "Reykjavik",
(69, 41): "Knossos",
(96, 39): "Calcutta"
}

#reads the date regardless of game speed
def isDate(iDate):
	return cyGame.getTurnYear(cyGame.getGameTurn() +1) > iDate and cyGame.getGameTurnYear() <= iDate

#compiles a list of plots
def getPlotList(tBL, tTR):
        lPlotList = []
        for x in range(tBL[0], tTR[0]+1):
                for y in range(tBL[1], tTR[1]+1):
                        lPlotList.append((x, y))
        return lPlotList

#searches in the dictionary to get a name for a key tile
def nameNorm(pCity):
   coord = (pCity.getX(), pCity.getY())
   if coord in cityNameDict:
      name = cityNameDict[coord]
      pCity.setName(name, True)
      return True
   else:
      return False


#colony spawn for Greeks and Celts 1600BC
def ancientSpawn():
	if isDate(-1600):
#Celts
		PyPlayer(0).initUnit(4, 51, 55, 1)
		PyPlayer(0).initUnit(5, 51, 55, 2)
		PyPlayer(0).initUnit(57, 51, 55, 3)
		PyPlayer(0).initUnit(4, 55, 54, 1)
		PyPlayer(0).initUnit(5, 55, 54, 2)
		PyPlayer(0).initUnit(57, 55, 54, 3)
		PyPlayer(0).initUnit(4, 55, 58, 1)
		PyPlayer(0).initUnit(5, 55, 58, 2)
		PyPlayer(0).initUnit(57, 55, 58, 3)
#Greeks
		PyPlayer(5).initUnit(4, 68, 46, 1)
		PyPlayer(5).initUnit(5, 68, 46, 2)
		PyPlayer(5).initUnit(57, 68, 46, 3)
		PyPlayer(5).initUnit(4, 69, 41, 1)
		PyPlayer(5).initUnit(5, 69, 41, 2)
		PyPlayer(5).initUnit(57, 69, 41, 3)
		PyPlayer(5).initUnit(4, 64, 47, 1)
		PyPlayer(5).initUnit(5, 64, 47, 2)
		PyPlayer(5).initUnit(57, 64, 47, 3)



#spawns the classical civs 800BC on the map (different date used for testing change before release)
def classicalSpawn():
	pRome = gc.getMap().plot(61, 46)
	pPersia = gc.getMap().plot(81, 41)
	pJapan = gc.getMap().plot(115, 46)
	pKorea = gc.getMap().plot(109, 46)
	if isDate(-3985):
		pRome.getPlotCity().kill()
		PyPlayer(7).initCity(61, 46)
		pPersia.getPlotCity().kill()
		PyPlayer(8).initCity(81, 41)
		pJapan.getPlotCity().kill()
		PyPlayer(9).initCity(115, 46)
		pKorea.getPlotCity().kill()
		PyPlayer(10).initCity(109, 46)
#Romans
		PyPlayer(7).initUnit(4, 61, 46, 2)
		PyPlayer(7).initUnit(5, 61, 46, 2)
		PyPlayer(7).initUnit(57, 61, 46, 15)
#Persians		
		PyPlayer(8).initUnit(4, 81, 41, 2)
		PyPlayer(8).initUnit(5, 81, 41, 2)
		PyPlayer(8).initUnit(57, 81, 41, 15)
#Japanese
		PyPlayer(9).initUnit(4, 115, 46, 2)
		PyPlayer(9).initUnit(5, 115, 46, 2)
		PyPlayer(9).initUnit(57, 115, 46, 15)
#Koreans
		PyPlayer(10).initUnit(4, 109, 46, 2)
		PyPlayer(10).initUnit(5, 109, 46, 2)
		PyPlayer(10).initUnit(57, 109, 46, 15)

#Roman colony spawn 1AD
def romeSpawn():
	if isDate(1):
#Lisbon
		PyPlayer(7).initUnit(4, 53, 45, 1)
		PyPlayer(7).initUnit(5, 53, 45, 2)
		PyPlayer(7).initUnit(57, 53, 45, 5)
#Carthage
		PyPlayer(7).initUnit(4, 58, 42, 1)
		PyPlayer(7).initUnit(5, 58, 42, 2)
		PyPlayer(7).initUnit(57, 58, 42, 5)
#Tripoli
		PyPlayer(7).initUnit(4, 60, 40, 1)
		PyPlayer(7).initUnit(5, 60, 40, 2)
		PyPlayer(7).initUnit(57, 60, 40, 5)

#spawns Arab civ 400AD
#def arabSpawn():
#	if isDate(400):

#spawns medieval civs 800AD
#def medievalSpawn():
#	if isDate(800):
#English
#French
#Spanish
#Germans
#Russians

#spawns German colonies in Scandinavia and Iceland 1200AD
#def scandiSpawn():
#	if isDate(1200):

#American spawn and flip of eastern US 1770AD
#def ameriSpawn():
#	if isDate(1770):

#American spawns and flip of western US and Hawaii 1900AD
#def ameriFlip():
#	if isDate(1900):

#colony spawns tied to discovery of Astronomy
#colonySpawn
#Arabs
#English
#French
#Spanish
#Russia

#spawns medieval barbarians 1000AD
#def barbSpawn():
#	if isDate(1000):
#Vikings
#Mongols

#spawns native Americans 1400AD
#def nativeSpawn():
#	if isDate(1400):
#North America
#Aztec
#Inca
 
Ok, here's two more PyScenario helper functions:
Code:
def getSquareList(tCoords, iDistance):
        return getPlotList((tCoords[0]-iDistance, tCoords[1]-iDistance), (tCoords[0]+iDistance, tCoords[1]+iDistance))

def getAdjacentList(tCoords):
        return getSquareList(tCoords, 1)
So instead of going through the trouble of mapping out the corner of 3x3 squares, you can use
Code:
getSquareList((61, 46), 1)
where the tCoords argument is replaced with the actual coordinates (in a tuple) of the center plot or "spawn tile" and the integer value 1 is how many tiles in each direction the plot list should expand from that tile.

But since you're doing a lot of these I've also supplied a convenient way of doing 3x3 squares:
Code:
getAdjacentList((61, 46))

Use them if you want. :king: This makes it really easy for you to skip the individual constants for each and every player, also. Just look at Rhye's tCapitals tuple!

Regarding:
Code:
	pRome = gc.getMap().plot(61, 46)
You realize that the plot() method is a CyMap method, right? And did you ever define a constant for CyMap()? I believe you did:
Code:
cyMap = CyMap()
So you can basically go:
Code:
	pRome = cyMap.plot(61, 46)
The pRome variable is also a bit confusing, as you might wanna use that for the CyPlayer instance of the Roman player later... But as I said - its your module and your naming conventions. At least you knew to use the p prefix so that you remember that its some sort of class instance. :)

Now, the return value of getPlotList(), getSquareList() and getAdjacentList() is a list value containing a set of tuples. Using getAdjacentList() will always get you 9 tuples with a pair of x/y coordinates each. You need a looping technique to access each tuple:
Code:
for tCoords in lPlotList:
This will make the following block of code be repeated as many times as there are entries in lPlotList (= nine times). The variable tCoords will change dynamically to each of the tuple values in order on iteration.

Then you need to extract the x and y values from the tuple:
Code:
x, y = tCoords
Now you have two separate variables, which is much easier to work with.

If you need to get the CyPlot instance of each you already know what to do:
Code:
pCurrentPlot = cyMap.plot(x, y)
And to kill any city you firstly need to check if there is a city present:
Code:
if pCurrentPlot.isCity():
And then get the CyCity instance:
Code:
pCity = pCurrentPlot.getPlotCity()
And finally, the kill:
Code:
pCity.kill()
This is basically how you program Python within the context of CivIV modding. You use iteration (looping) and conditional statements (if...) and assign return values of various methods to variables - until you reach your destination and the job is done.

Now, try to put what I wrote above together into a function! Check with the API to verify that I used the correct methods and that the return values and parameters check up.

ps. I'm off to work - see you in some 12 hours...
 
w00t...I've redeemed myself ;-) lol

Alright...since it's midnight here...all this tuple fun will have to wait until tomorrow and work its way in around some afternoon teaching (pfft...jobs...always getting in the way of priorities)
 
hmm...I'm having some problems. It isn't liking the tCoords definition, and even the other helper functions are arguing with me (not liking pRome, requiring extra parentheses so as not to count x and y as separate arguments if I use them directly, etc)

Code:
#spawns the classical civs 800BC on the map (different date used for testing change before release)
def classicalSpawn():
	pRome = cyMap.plot(61, 46)
	pPersia = cyMap.plot(81, 41)
	pJapan = cyMap.plot(115, 46)
	pKorea = cyMap.plot(109, 46)
	if isDate(-3985):
		getAdjacentList(pRome)
		x, y = tCoords
		for tCoords in lPlotList:
				pCurrentPlot = cyMap.plot(x, y)
				if pCurrentPlot.isCity():
						pCity = pCurrentPlot.getPlotCity()
						pCity.kill()
		PyPlayer(7).initCity(61, 46)
		pPersia.getPlotCity().kill()
		PyPlayer(8).initCity(81, 41)
		pJapan.getPlotCity().kill()
		PyPlayer(9).initCity(115, 46)
		pKorea.getPlotCity().kill()
		PyPlayer(10).initCity(109, 46)
#Romans
		PyPlayer(7).initUnit(4, 61, 46, 2)
		PyPlayer(7).initUnit(5, 61, 46, 2)
		PyPlayer(7).initUnit(57, 61, 46, 15)
 
Back
Top Bottom