There is another xml possibility:
Make a second tech for an hero unit. Make that second tech require TECH_GERMANY AND other techs.
Then you can use firstfreeunitclass for that second tech - OR: Make the hero require that second tech.
tech acquired?
1A. no --> do nothing
1B. yes --> by Germany?
2A. no --> do nothing
2B. yes --> Physics?
3A. no --> do nothing
3B. yes --> give a Red Baron to Germany
note to you: every enabled python callback slows your game. I'm always doing it in xml when I don't need python.
note to you: every enabled python callback slows your game. I'm always doing it in xml when I don't need python.
you probably don't need a callback for your work
this should work. you will get the unit in your capital city. I don't know how to check for your empire, else I could do it for you.
//edit: you need to add a Help tag to the technology which gives you the unit. else you won't see it on the tech tree when using python.
UnboundLocalError: local variable 'pPID' referenced before assignment
ERR: Python function onEvent failed, module CvEventInterface
def onTechAcquired(self, argsList):
'Tech Acquired'
iTechType, iTeam, iPlayer, bAnnounce = argsList
###this part here
if iTechType == gc.getInfoTypeForString("TECH_WHATEVER"):
TheCivForTheUnit = gc.getInfoTypeForString("CIVILIZATION_WHATEVER")
pPlayer = gc.getPlayer(iPlayer)
myName = pPlayer.getCivilizationType ()
if myName == TheCivForTheUnit:
pCity= pPlayer.getCapitalCity()
iX =pCity.getX()
iY = pCity.getY()
newUnit = pPlayer.initUnit(gc.getInfoTypeForString( 'UNIT_WHATEVER' ), iX, iY, UnitAITypes.UNITAI_GENERAL, DirectionTypes.NO_DIRECTION)
Instead of pPID use pLoser.getOwner()
For the tech+civ:
PHP:def onTechAcquired(self, argsList): 'Tech Acquired' iTechType, iTeam, iPlayer, bAnnounce = argsList ###this part here if iTechType == gc.getInfoTypeForString("TECH_WHATEVER"): TheCivForTheUnit = gc.getInfoTypeForString("CIVILIZATION_WHATEVER") pPlayer = gc.getPlayer(iPlayer) myName = pPlayer.getCivilizationType () if myName == TheCivForTheUnit: pCity= pPlayer.getCapitalCity() iX =pCity.getX() iY = pCity.getY() newUnit = pPlayer.initUnit(gc.getInfoTypeForString( 'UNIT_WHATEVER' ), iX, iY, UnitAITypes.UNITAI_GENERAL, DirectionTypes.NO_DIRECTION)
For the position, i just took the capital.
Instead of pPID use pLoser.getOwner()
For the tech+civ:
PHP:def onTechAcquired(self, argsList): 'Tech Acquired' iTechType, iTeam, iPlayer, bAnnounce = argsList ###this part here if iTechType == gc.getInfoTypeForString("TECH_WHATEVER"): TheCivForTheUnit = gc.getInfoTypeForString("CIVILIZATION_WHATEVER") pPlayer = gc.getPlayer(iPlayer) myName = pPlayer.getCivilizationType () if myName == TheCivForTheUnit: pCity= pPlayer.getCapitalCity() iX =pCity.getX() iY = pCity.getY() newUnit = pPlayer.initUnit(gc.getInfoTypeForString( 'UNIT_WHATEVER' ), iX, iY, UnitAITypes.UNITAI_GENERAL, DirectionTypes.NO_DIRECTION)
For the position, i just took the capital.
def onTechAcquired(self, argsList):
'Tech Acquired'
iTechType, iTeam, iPlayer, bAnnounce = argsList
# Note that iPlayer may be NULL (-1) and not a refer to a player object
# Show tech splash when applicable
if (iPlayer > -1 and bAnnounce and not CyInterface().noTechSplash()):
if (gc.getGame().isFinalInitialized() and not gc.getGame().GetWorldBuilderMode()):
if ((not gc.getGame().isNetworkMultiPlayer()) and (iPlayer == gc.getGame().getActivePlayer())):
popupInfo = CyPopupInfo()
popupInfo.setButtonPopupType(ButtonPopupTypes.BUTTONPOPUP_PYTHON_SCREEN)
popupInfo.setData1(iTechType)
popupInfo.setText(u"showTechSplash")
popupInfo.addPopup(iPlayer)
def onTechAcquired(self, argsList):
'Tech Acquired'
iTechType, iTeam, iPlayer, bAnnounce = argsList
# Note that iPlayer may be NULL (-1) and not a refer to a player object
### Hero Mod Start ##
if iTechType == gc.getInfoTypeForString("TECH_WHATEVER"):
TheCivForTheUnit = gc.getInfoTypeForString("CIVILIZATION_WHATEVER")
pPlayer = gc.getPlayer(iPlayer)
myName = pPlayer.getCivilizationType ()
if myName == TheCivForTheUnit:
pCity= pPlayer.getCapitalCity()
iX =pCity.getX()
iY = pCity.getY()
newUnit = pPlayer.initUnit(gc.getInfoTypeForString( 'UNIT_WHATEVER' ), iX, iY, UnitAITypes.UNITAI_GENERAL, DirectionTypes.NO_DIRECTION)
## Hero Mod End ##
# Show tech splash when applicable
if (iPlayer > -1 and bAnnounce and not CyInterface().noTechSplash()):
if (gc.getGame().isFinalInitialized() and not gc.getGame().GetWorldBuilderMode()):
if ((not gc.getGame().isNetworkMultiPlayer()) and (iPlayer == gc.getGame().getActivePlayer())):
popupInfo = CyPopupInfo()
popupInfo.setButtonPopupType(ButtonPopupTypes.BUTTONPOPUP_PYTHON_SCREEN)
popupInfo.setData1(iTechType)
popupInfo.setText(u"showTechSplash")
popupInfo.addPopup(iPlayer)
Do a search for "onTechAcquired", you will find this:
Code:def onTechAcquired(self, argsList): 'Tech Acquired' iTechType, iTeam, iPlayer, bAnnounce = argsList # Note that iPlayer may be NULL (-1) and not a refer to a player object # Show tech splash when applicable if (iPlayer > -1 and bAnnounce and not CyInterface().noTechSplash()): if (gc.getGame().isFinalInitialized() and not gc.getGame().GetWorldBuilderMode()): if ((not gc.getGame().isNetworkMultiPlayer()) and (iPlayer == gc.getGame().getActivePlayer())): popupInfo = CyPopupInfo() popupInfo.setButtonPopupType(ButtonPopupTypes.BUTTONPOPUP_PYTHON_SCREEN) popupInfo.setData1(iTechType) popupInfo.setText(u"showTechSplash") popupInfo.addPopup(iPlayer)
replace this with
Code:def onTechAcquired(self, argsList): 'Tech Acquired' iTechType, iTeam, iPlayer, bAnnounce = argsList # Note that iPlayer may be NULL (-1) and not a refer to a player object ### Hero Mod Start ## if iTechType == gc.getInfoTypeForString("TECH_WHATEVER"): TheCivForTheUnit = gc.getInfoTypeForString("CIVILIZATION_WHATEVER") pPlayer = gc.getPlayer(iPlayer) myName = pPlayer.getCivilizationType () if myName == TheCivForTheUnit: pCity= pPlayer.getCapitalCity() iX =pCity.getX() iY = pCity.getY() newUnit = pPlayer.initUnit(gc.getInfoTypeForString( 'UNIT_WHATEVER' ), iX, iY, UnitAITypes.UNITAI_GENERAL, DirectionTypes.NO_DIRECTION) ## Hero Mod End ## # Show tech splash when applicable if (iPlayer > -1 and bAnnounce and not CyInterface().noTechSplash()): if (gc.getGame().isFinalInitialized() and not gc.getGame().GetWorldBuilderMode()): if ((not gc.getGame().isNetworkMultiPlayer()) and (iPlayer == gc.getGame().getActivePlayer())): popupInfo = CyPopupInfo() popupInfo.setButtonPopupType(ButtonPopupTypes.BUTTONPOPUP_PYTHON_SCREEN) popupInfo.setData1(iTechType) popupInfo.setText(u"showTechSplash") popupInfo.addPopup(iPlayer)
def onTechAcquired(self, argsList):
'Tech Acquired'
iTechType, iTeam, iPlayer, bAnnounce = argsList
# Note that iPlayer may be NULL (-1) and not a refer to a player object
### Hero Mod Start - code by The J##
if iTechType == gc.getInfoTypeForString("TECH_BOATING"):
TheCivForTheUnit = gc.getInfoTypeForString("CIVILIZATION_NETHERLANDS")
pPlayer = gc.getPlayer(iPlayer)
pPID = pPlayer.getID()
myName = pPlayer.getCivilizationType ()
if myName == TheCivForTheUnit:
pCity= pPlayer.getCapitalCity()
iX =pCity.getX()
iY = pCity.getY()
newUnit = pPlayer.initUnit(gc.getInfoTypeForString( 'UNIT_TANK' ), iX, iY, UnitAITypes.UNITAI_GENERAL, DirectionTypes.NO_DIRECTION)
newUnit.setHasPromotion(gc.getInfoTypeForString( 'PROMOTION_HERO' ), true)
newUnit.setHasPromotion(gc.getInfoTypeForString( 'PROMOTION_FREEUPGRADE' ), true)
newUnit.setName("Tank the Terrible")
## Display message
CyInterface().addMessage(pPID,false,15,CyTranslator().getText("TXT_KEY_HERO_EMERGE_NETHERLANDS",()),'',0,'Art/Interface/Buttons/Units/HeroNetherlands.dds',ColorTypes(11), iX, iY, True,True)
## Hero Mod End ##
Just one minor question: how can I spawn two units? Just copy the last command?
Thx but if i wanted ALL civs to receive this upon getting a coliseum (but only the first built one), then what?
def onBuildingBuilt(self, argsList):
'Building Completed'
pCity, iBuildingType = argsList
game = gc.getGame()
###from here###
thisBuilding = gc.getBuildingInfo(iBuildingType)
BuildingClass = thisBuilding.getBuildingClassType ()
if BuildingClass == gc.getInfoTypeForString("BUILDINGCLASS_COLOSSEUM"):
if game.getBuildingClassCreatedCount(BuildingClass)==1:
iX = pCity.getX()
iY = pCity.getY()
newUnit = pPlayer.initUnit(gc.getInfoTypeForString( 'UNIT_WHATEVER' ), iX, iY, UnitAITypes.UNITAI_GENERAL, DirectionTypes.NO_DIRECTION)
####to here###
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)))
Got it working the way I want it to work, big thanks to the J
Here's the example Pythoncode:
Yes, that will do it.
The first colloseum, which is built, should spawn a unit?
This needs some changes...
Spoiler :PHP:def onBuildingBuilt(self, argsList): 'Building Completed' pCity, iBuildingType = argsList game = gc.getGame() ###from here### thisBuilding = gc.getBuildingInfo(iBuildingType) BuildingClass = thisBuilding.getBuildingClassType () if BuildingClass == gc.getInfoTypeForString("BUILDINGCLASS_COLOSSEUM"): if game.getBuildingClassCreatedCount(BuildingClass)==1: iX = pCity.getX() iY = pCity.getY() newUnit = pPlayer.initUnit(gc.getInfoTypeForString( 'UNIT_WHATEVER' ), iX, iY, UnitAITypes.UNITAI_GENERAL, DirectionTypes.NO_DIRECTION) ####to here### 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) [/SPOILER] 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)))
nice to see it.
Do i copy all the spoiler under def onBuildingBuilt(self, argsList):? exactly like you have it?
You do know this belongs to the Spartacus HEROES part right??
All, what is after "####to here###" and before "###from here### "should already be somewhere there, so you don't need that part.
## BTS HEROS - Spartacus Capture Event Start ##
if pWinner.getUnitClassType() == gc.getInfoTypeForString('UNITCLASS_SPARTACUS'):
pPlayer = gc.getPlayer(pWinner.getOwner())
## Capture % Random # 0 to 3 or 25% ##
self.iNewGladiatorNumber = self.getRandomNumber( 3 )
if self.iNewGladiatorNumber == 0:
iGladiator = CvUtil.findInfoTypeNum(gc.getUnitInfo,gc.getNumUnitInfos(),'UNIT_GLADIATOR')
pClearPlot = self.findClearPlot(pLoser)
if (pLoser.plot().getNumUnits() == 1 and pClearPlot != -1):
pPlot = pLoser.plot()
pLoser.setXY(pClearPlot.getX(), pClearPlot.getY(), false, true, true)
else:
pPlot = pWinner.plot()
newUnit = pPlayer.initUnit(iGladiator, pPlot.getX(), pPlot.getY(), UnitAITypes.NO_UNITAI, DirectionTypes.DIRECTION_NORTH)
pLoser.setDamage(75, False)
newUnit.convert(pLoser)
pLoser.setDamage(100, False)
newUnit.finishMoves()
iXa = pLoser.getX()
iYa = pLoser.getY()
CyInterface().addMessage(pPID,false,15,CyTranslator().getText("TXT_KEY_SPARTACUS_CAPTURE_SUCCESS",()),'',0,',Art/Interface/Buttons/Units/ICBM.dds,Art/Interface/Buttons/Warlords_Atlas_1.dds,3,11',ColorTypes(44), iXa, iYa, True,True)
## BTS HEROS - Spartacus Capture End ##
You don't have to place the code in that section, you have to place it in CvEventManager after onBuildingBuilt (you see that in the code).
def onBuildingBuilt(self, argsList):
'Building Completed'
pCity, iBuildingType = argsList
game = gc.getGame()
###water start part 3####
###from here###
thisBuilding = gc.getBuildingInfo(iBuildingType)
BuildingClass = thisBuilding.getBuildingClassType ()
if BuildingClass == gc.getInfoTypeForString("BUILDINGCLASS_COLOSSEUM"):
if game.getBuildingClassCreatedCount(BuildingClass)==1:
iX = pCity.getX()
iY = pCity.getY()
newUnit = pPlayer.initUnit(gc.getInfoTypeForString( 'UNIT_WHATEVER' ), iX, iY, UnitAITypes.UNITAI_GENERAL, DirectionTypes.NO_DIRECTION)
####to here###
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)
@Strat:
I like the concept of giving a unit to the first civ that builds a certain building i.e. first civ that builds a colosseum receives Spartacus.
I'm quite sure the AI is totally oblivious of this. How do you intend to get the AIs actively going after building, in this case, the first colosseum?
Otherwise human players can easily exploit this