Python Snippets

It is often times better to get things done your way when you do them yourself, instead of relying on other people.

Granted, not all of us are coders, but if you've tried then that counts for something. As long as you're not one of those lazy people that don't try to do anything for themselves and expect others to do everything for them.

But I would recommend giving it another shot, assuming you've got the patience. There are some good tutorials on the forums that can help get you started.
 
It is often times better to get things done your way when you do them yourself, instead of relying on other people.

Granted, not all of us are coders, but if you've tried then that counts for something. As long as you're not one of those lazy people that don't try to do anything for themselves and expect others to do everything for them.

But I would recommend giving it another shot, assuming you've got the patience. There are some good tutorials on the forums that can help get you started.

Considering the amount of work I've put into my sole and only mod (and first attempt at anything like that thus far), I've accomplished and learned far more than I though I would ever in that field.

Python remains totally confusing to me and I doubt I'll be able to accomplish much in that area anytime soon. On the other hand, if Zebra9 gets tired of my ideas, I'm sure he's a big boy and can tell me himself -- no offense meant or taken on my part. ;)
 
I'll let you know if I get tired of getting tons of credit for your ideas HeHe. lol :lol:

I think I've got the "Thumbtack" ability workin g I'll get it up tomorrow. :thumbsup:

I'll start working on the promo idea as an expansion for zPromotions.
 
I'll let you know if I get tired of getting tons of credit for your ideas HeHe. lol :lol:

Indeed, and you're welcome! :lol:

I think I've got the "Thumbtack" ability workin g I'll get it up tomorrow. :thumbsup:

I'll start working on the promo idea as an expansion for zPromotions.

Thanks alot for doing, as some might put it, everything for me! :mischief:
 
Zebra 9, I was wondering if you could tell me what exactly is the Python call that determines a Great Person's type (artist, prophet...)

I am looking to update my Civ-Specific Great People mod to Python-only (much cleaner) using TheLopez's No-Name Great Person Renamer mod. However, there is no distinction in his code among great person type.
http://forums.civfanatics.com/showthread.php?t=168367

EDIT: Let me be more specific...

What I want the game to do is look at the unit, get its type, and select a name based on that type. For example I have:
Code:
...
	def onGreatPersonBorn(self, argsList):
		'Great Person Born'
		pUnit, iPlayer, pCity = argsList
		player = PyPlayer(iPlayer)
		infoUnit = pUnit.getUnitClassType()
		# Check if we should even show the popup:
		if pUnit.isNone() or pCity.isNone():
			return
		
		if(len(pUnit.getNameNoDesc()) == 0):
				
			iCivilizationType = player.player.getCivilizationType()
				
			pUnit.setName(NameUtils.getCivilizationName(iCivilizationType, infoUnit))
...

which calls

Code:
	if (infoUnit == gc.getInfoTypeForString("UNITCLASS_PROPHET")):
		if(len(civilizationNameHash[strCivilizationType]["GP"]) > 0):
			strGP = civilizationNameHash[strCivilizationType]["GP"][gc.getGame().getMapRand().get(len(civilizationNameHash[strCivilizationType]["GP"]), "Random Name")]
			strName = string.capwords(strGP)

			return strName

for a Great Prophet. There's something going wrong here, but I can't see where. At first I thought it was in the comparison check, but that seems to work.

Sorry for any thread hijack. :D
 
At first I thought it was in the comparison check, but that seems to work.

Sorry to hijack your hijack, but this part is unclear to me. Your code to check the UnitClass seems fine, but if it's not detecting the type of GP correctly, you could go off of the UnitType instead.

Code:
unitType = pUnit.getUnitType()
...
if (unitType == gc.getInfoTypeForString("UNIT_PROPHET")):
    ...

But again, you said this part is actually working. How have you tested it? Did you print out debug statements inside the if-test? If so, also print out the len of the hash (list) of names and the random number you get.

I don't know how you're printing stuff for debug, but assume you have a function on NameUtils called debug().

Code:
if (...):
    self.debug("Profit!!!")
    nameList = civilizationNameHash[strCivilizationType]["GP"]
    if (nameList):
        self.debug("Found %d names" %len(nameList))
        rand = gc.getGame().getMapRand().get(len(nameList), "Random Name")
        self.debug("Got random # %d" %rand)
        strGP = nameList[rand]
        self.debug("Chose name %s" %strGP)
        strName = string.capwords(strGP)
        return strName

The other thing I noticed is that you pass iCivilizationType to NameUtils, but you use a variable called strCivilizationType to look up the correct list of names. Is there a conversion/lookup I'm missing, perhaps InfoType -> String?

You also have

Code:
player.player.getCivilizationType()

Is that a typo? If so, is it in your code or only your post?
 
Thanks for the response. I don't have the debug printout here right now, but I'll try to get it later.

That last "player.player" looked fishy to me, too. That's how it was in TheLopez's mod, which worked. I also originally had Unit Type, not Unit Class, but then it occurred to me that class would be better since you might have multiple kinds of great people per class (long story).
 
I agree that testing against unit class is the better option, but I wasn't sure if you meant that part was or was not working. If it wasn't working, I'd try unit type just to verify sanity. :)

I see that you are using

Code:
player = PyPlayer(iPlayer)

I haven't used PyPlayer before so I'm unfamiliar with it. I assume it's a Python wrapper for the player # (since that's what you give it when creating it). It probably exposes "player" as the CyPlayer obtained using something like

Code:
player = gc.getPlayer(iPlayer)

I wish there was more extensive documentation on the API. I'd have no chance without all the mods already out there from which to scavenge example code. I still can't find any information on the GUI toolkit functions. :(
 
The PyPlayer returns a player object that contains alot of stuff that is not in the SDK but is actally in python. When someone uses player.player I believe it's the same as using gc.getPlayer(iPlayer). So I think you should change the PyPlayer(iPlayer) to gc.getPlayer(iPlayer), but of course I don't know what your code looks like. Now from what you are saying you want to change the units type, right? If so you will have to change the SDK so that it does it or makes a python call.

P.S I think I just thought of some way it can be done from python.
 
Actually, I'm not looking to change the UnitType, just the individual name, e.g. so a Great Scientist born to England will be named Isaac Newton, Stephen Hawking and so on, instead of Plato or other non-English.

I'll try to fiddle around with it some more today and once it's working I'll post it here. :D This has lots of possibilities outside of great people. Suppose you wanted to give any unit a unique name. Normally, you'd just add the names in the <UniqueName> tag in XML. But this isn't civ-specific--suppose you want to have ship names like the Yamato or Nagato for the Japanese, and the Arizona and Missouri for America. You can't do that in XML, because any name will go for any civ.
 
Actually, I'm not looking to change the UnitType, just the individual name, e.g. so a Great Scientist born to England will be named Isaac Newton, Stephen Hawking and so on, instead of Plato or other non-English.

I'll try to fiddle around with it some more today and once it's working I'll post it here. :D This has lots of possibilities outside of great people. Suppose you wanted to give any unit a unique name. Normally, you'd just add the names in the <UniqueName> tag in XML. But this isn't civ-specific--suppose you want to have ship names like the Yamato or Nagato for the Japanese, and the Arizona and Missouri for America. You can't do that in XML, because any name will go for any civ.

I see where you're going with this. It's very exciting! I had toyed with a "France 1940" scenario before getting "AD1640 North America" underway. The reason for the switch was that I wanted to identify all the divisions and generals by name/number to provide a startup as historical as possible. After failing miserably in this respect (and having a hopelessly-pacifistic AI foiling my most-bellicose-expectations for the blitzkrieg), I sailed for the New World. Sigh... :lol:
 
I just tested TheLopez's "No-Name Renamer" mod for Great People in Warlords, and it worked. (It was written for Vanilla 1.61, so I was afraid it might just be Warlords.) Since I did not change the fundamental mechanism except for adding the unit type check, I assume something's going wrong there.

I'll be back. ;)

BTW, Ambreville, there is a way to get around this problem in XML only... just create a bunch of new units like "French Battleship" and give them the civ-specific names. :D Of course, this'll add about 100 new units to the game... :crazyeye: You can see why I'm eager to switch to Python.
 
BTW, Ambreville, there is a way to get around this problem in XML only... just create a bunch of new units like "French Battleship" and give them the civ-specific names. :D Of course, this'll add about 100 new units to the game... :crazyeye: You can see why I'm eager to switch to Python.

Thanks for the tip. Can I do that for great generals too?

And how do I make sure a specific unit on the map has "the" correct name out of the list??
 
Yes. This is I how I currently have the Great People mod set up. Each civ gets a UU for each great person. However, there is a bug in SDK that prevents GG's from using this properly, but luckily Mexico found it and squashed it.

I've had a lot of problems renaming units in worldbuilder, too. In my WWII mod, I originally had all the units named, but once I saved it they all disappeared. :( Unfortunately, in Warlords, there is no way to make sure that units will have the "correct" name, as they are assigned randomly from the <uniquenames> list when they are built. Mexico also developed a mod that goes back to Vanilla's sequential ordering (meaning the first one in the list is the first to be used, and so on) but I don't know if that will solve your problem.


EDIT: Never mind, Zebra! Thanks to everybody for the advice. I finally got it to work!

You'll never believe what one of the problems was: I'd renamed the file to CivSpecificGreatPeopleModNameUtils instead of CvCivSpecificGreatPeopleModNameUtils. :wallbash: I swear, I do silly things like this all the time...
 
I've had a lot of problems renaming units in worldbuilder, too. In my WWII mod, I originally had all the units named, but once I saved it they all disappeared. :(

Yup. Same here.

Unfortunately, in Warlords, there is no way to make sure that units will have the "correct" name, as they are assigned randomly from the <uniquenames> list when they are built. Mexico also developed a mod that goes back to Vanilla's sequential ordering (meaning the first one in the list is the first to be used, and so on) but I don't know if that will solve your problem.

I could see doing it this way, if there were a way to keep track of the order in which I placed unit types on the map. This could be hellishly complicated! :eek:

No chance this will be improved in BtS? :confused:
 
Theoretically, you should be able to see the new names once you place them on the map, which would make keeping track of them easier. But it's still complicated.

Okay, another question for the wise Zebra 9... ;)
The unit renamer now works, but it does not rename the event message in the upper left corner, "Great Scientist has been born in Washington!" The actual Great Scientist was correctly renamed to Albert Einstein (or whatever). How do I change the event display to reflect the new name? What's the command for passing it back to the event manager?

What we really need is an index of Python functions in Civ 4.
 
Congrats on getting it working!. :goodjob:

The unit renamer now works, but it does not rename the event message in the upper left corner, "Great Scientist has been born in Washington!"

I can't say for sure, but I suspect you may be stuck with this unless you want to modify the C++ DLL. The problem is that you're intercepting an event telling you that a great person was born and placed on the map. It's likely already displayed the message.

What we really need is an index of Python functions in Civ 4.

This site contains the API for most of the Python objects exposed to you. It's lacking some (like the GUI widgets), but it's a start. I learned most everything from Ruff Hi's Cobbled SG Mod. Working code is a great instructor. In fact, that mod -- a collection of a ton of other modpacks -- includes a unit renamer so you get things like "Warrior 3 from Calcutta".
 
Top Bottom