OK, I figured it out. Noticed the last thing to report in PythonDbg.log was that my capital grew. Looking at my capital, I realized they were just about to complete the Nature's Revolt ritual. As soon as I switched production to something else, the turn completed like normal. Does anyone know where Nature's Revolt is handled? I can take a look at the script and maybe figure it out.
Mostly, I just really NEED those Heroic Attack/Defense II hawks to feed to my flesh golems. The consistent diet of vampires and wyvern riders I have been feeding them just isn't enough. Maybe I just banked too many hawks and the game is breaking trying to make sense of it all.
OK, I figured it out. Noticed the last thing to report in PythonDbg.log was that my capital grew. Looking at my capital, I realized they were just about to complete the Nature's Revolt ritual. As soon as I switched production to something else, the turn completed like normal. Does anyone know where Nature's Revolt is handled? I can take a look at the script and maybe figure it out.
Mostly, I just really NEED those Heroic Attack/Defense II hawks to feed to my flesh golems. The consistent diet of vampires and wyvern riders I have been feeding them just isn't enough. Maybe I just banked too many hawks and the game is breaking trying to make sense of it all.
Ah right, I remember pre-emptively editing that ritual after reading in this thread that it was fatally bugged (see https://forums.civfanatics.com/threads/magistermodmod.455111/page-189#post-16299102 , changed it to Magister's code to apply for animals owned for everyone). Building the ritual worked fine with the modified code in place
Ah right, I remember pre-emptively editing that ritual after reading in this thread that it was fatally bugged (see https://forums.civfanatics.com/threads/magistermodmod.455111/page-189#post-16299102 , changed it to Magister's code to apply for animals owned for everyone). Building the ritual worked fine with the modified code in place
Righteous, thank you! Yeah, that while loop won’t ever complete. Classic example of forgetting to reset the killswitch. It will just keep adding a unit each time through the loop, the barbarian unit list will keep growing, and therefore the while conditional will always be true. Correct way would be either reset bValid to false or use a while loop to make a list of units, then iterate through with a for loop. Looks like the latter was the eventual approach.
Anyway, much appreciated. My even-more-broken flesh golems thank you as well!
EDIT: I’m wrong about the loop. Unclear why it didn’t work in its original implementation.
Now that I’m up and running again, a few questions about this mod:
1. I have all the requirements for Stir from Slumber (at least the listed ones) but cannot cast the ritual. Also, it hasn’t been cast by anyone else as far as I can tell in the World Builder. Do I also need Cult of the Dragon in a city? Is it dependent on AC?
2. Can you not evangelize arcane or disciple units? Seems like my arcane units always resist (as well as ANY unit with Divine I/II) and disciples aren’t even valid targets.
3. Can Laeran Cord not be spread to cities with other religions present? Seems like I can add other religions after LC, but it doesn’t like to spread when other religions are there first.
4. Is the only way to transform Gaelan into the Burnt Priest to miscast Share Memories, also making him a barbarian and losing Circle of Gaelan from everyone? The civilopedia entry seems to indicate he can be upgraded at level 10 in a city with The Undertow religion, but the option does not appear for me.
5. For miscasting, will a spell with a built-in 25% miscast chance (lesser haste, for instance) always have AT LEAST that much miscast chance, even if you get tons of -% miscast chance?
6. Generic question about FFH: what does +X spell damage do? Does that mean if a spell says “about 15% damage to a maximum of 30%” and the unit has +10 spell damage then the spell will do about 25% damage but not be able to damage units past 30% (70% health remaining)?
I'm wondering now if maybe I should just make the hostile versions of the temples share a BUILDINGCLASS, as they can kind of clutter up the pedia, tech tree, and the tech popups.
In my test games so far I have not often found myself building the harmful versions of the temples (except in a Calabim game when I wanted extra unhappiness to produce more from the Governor's Manors, which didn't really feel right), and am not sure I want the AI wasting on buildings with negative effects either.
Priests would still be able to found temples even when they would become the hostile versions, which you may want to do in rival territory even more.
I'm thinking of expanding the "without arda" mechanic to use multiple promotions indicating multiple levels of divine favor. The "hostile" versions of a temple could then make enemy priests of that religion less likely to miscast. A Rescuer might not have much chance of guiding Refugees out of oppression unless there is a Safehouse there to shelter them. A Profane's spells might be useless attacking the Empyrean holy city of the goodly Malakim, unless someone managed to set up a Demons Altar there to invite evil into the city.
This would of course incentivize a lot more Inquisitions.
Now that I’m up and running again, a few questions about this mod:
1. I have all the requirements for Stir from Slumber (at least the listed ones) but cannot cast the ritual. Also, it hasn’t been cast by anyone else as far as I can tell in the World Builder. Do I also need Cult of the Dragon in a city? Is it dependent on AC?
I cannot remember whether there have been any changes since the last release, but currently Stir from Slumber can be completed multiple times one you know Divine Essense, but there are some restrictions in python.
It requires the Cult of the Dragon be present in the city, unless you are playing as the Kuriotates or Sheaim civilizations.
The specific dragons and Wyrmholds created by the ritual depend on your effective mana supply (your actual number of sources of mana plus or minus some modifiers specific to your civilization, leader, state religion, and alignment.)
The ritual will not create any sort of Wyrmhold that already exists on the map, or any belonging to a species of dragon that the barbarian state already has living.
If there is no possible type of Wyrmhold for the ritual to create, then you cannot create the ritual.
Spoiler:
CvGameUtils.py
Code:
if eProject == gc.getInfoTypeForString('PROJECT_STIR_FROM_SLUMBER'):
if not pCity.isHasReligion(gc.getInfoTypeForString('RELIGION_CULT_OF_THE_DRAGON')):
if pPlayer.getCivilizationType() not in [ gc.getInfoTypeForString('CIVILIZATION_KURIOTATES'), gc.getInfoTypeForString('CIVILIZATION_SHEAIM')]:
return True
iNumWyrmholds = 0
listWyrmholds = [ gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_FEATHERED'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_BLOOD'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_SIEGE'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_GOLD'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_GRAVE'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_OBSIDIAN'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_FANG'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_RUNE'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_PIT'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_FURNACE'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_ELDER'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_WINTER'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_SHIELD'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_CORAL'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_VAULT'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_SEED'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_SHADOW'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_SHIMMERING'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_DAWN'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_SCALED')
]
if eTeam.isHasTech(gc.getInfoTypeForString('TECH_OMNISCIENCE')):
listWyrmholds.append(gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_SPIRE'))
if eTeam.isHasTech(gc.getInfoTypeForString('TECH_MALEVOLENT_DESIGNS')) and eTeam.isBuildingClassMaxedOut(gc.getInfoTypeForString('BUILDINGCLASS_TOWER_OF_NECROMANCY'),0):
if pPlayer.getCivilizationType() != gc.getInfoTypeForString('CIVILIZATION_SIDAR') and pPlayer.countNumBuildings(gc.getInfoTypeForString('BUILDING_SOUL_SHROUD')) < 1:
listWyrmholds.append(gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_DRACOLICH'))
for iWyrmhold in listWyrmholds:
infoWyrmhold = gc.getImprovementInfo(iWyrmhold)
iBonus = infoWyrmhold.getBonusConvert()
if iBonus != -1:
if cf.getNumBonusEffective(iPlayer, iBonus) < 1:
continue
if cf.findImprovement(iWyrmhold) != -1:
continue
iDragon = infoWyrmhold.getSpawnUnitType()
if iDragon !=-1:
if bPlayer.isUnitClassMaxedOut(gc.getUnitInfo(iDragon).getUnitClassType(), 1):continue
iNumWyrmholds += 1
return False
if iNumWyrmholds < 1:
return True
CvEventManager.py
Code:
elif iProjectType == gc.getInfoTypeForString('PROJECT_STIR_FROM_SLUMBER'):
pCity.setHasReligion(gc.getInfoTypeForString('RELIGION_CULT_OF_THE_DRAGON'),True,True,True)
listWyrmholds = [ gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_FEATHERED'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_BLOOD'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_SIEGE'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_GOLD'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_GRAVE'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_OBSIDIAN'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_FANG'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_RUNE'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_PIT'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_FURNACE'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_ELDER'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_WINTER'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_SHIELD'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_CORAL'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_VAULT'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_SEED'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_SHADOW'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_SHIMMERING'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_DAWN'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_SCALED')
]
if eTeam.isHasTech(gc.getInfoTypeForString('TECH_OMNISCIENCE')):
listWyrmholds.append(gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_SPIRE'))
if eTeam.isHasTech(gc.getInfoTypeForString('TECH_MALEVOLENT_DESIGNS')) and eTeam.isBuildingClassMaxedOut(gc.getInfoTypeForString('BUILDINGCLASS_TOWER_OF_NECROMANCY'),0):
if pPlayer.getCivilizationType() != gc.getInfoTypeForString('CIVILIZATION_SIDAR') and pPlayer.countNumBuildings(gc.getInfoTypeForString('BUILDING_SOUL_SHROUD')) < 1:
listWyrmholds.append(gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_DRACOLICH'))
for iWyrmhold in listWyrmholds:
infoWyrmhold = gc.getImprovementInfo(iWyrmhold)
iBonus = infoWyrmhold.getBonusConvert()
if iBonus != -1:
if cf.getNumBonusEffective(iPlayer, iBonus) < 1:
continue
iDragon = infoWyrmhold.getSpawnUnitType()
if iDragon !=-1:
if bPlayer.isUnitClassMaxedOut(gc.getUnitInfo(iDragon).getUnitClassType(), 0):
continue
if pPlayer.isUnitClassMaxedOut(gc.getUnitInfo(iDragon).getUnitClassType(), 0):
continue
pWyrmholdPlot = cf.findImprovement(iWyrmhold)
if pWyrmholdPlot == -1:
pWyrmholdPlot = cf.addLair(iWyrmhold)
self.onImprovementBuilt([iWyrmhold, pWyrmholdPlot.getX(), pWyrmholdPlot.getY()])
# elif iDragon !=-1:
# if not bPlayer.isUnitClassMaxedOut(gc.getUnitInfo(iDragon).getUnitClassType(), 0):
# newUnit = bPlayer.initUnit(iDragon, pWyrmholdPlot.getX(), pWyrmholdPlot.getY(), UnitAITypes.NO_UNITAI, DirectionTypes.DIRECTION_SOUTH)
# newUnit.setHasPromotion(gc.getInfoTypeForString('PROMOTION_LAIR_GUARDIAN'), True)
2. Can you not evangelize arcane or disciple units? Seems like my arcane units always resist (as well as ANY unit with Divine I/II) and disciples aren’t even valid targets.
You cannot evangelize units that have a religion type set in their xml defines. That includes the disciples, priests, and high priests of each religion, but it is not linked to UNITCOMBAT_DISCIPLE. It also includes religious heroes and champions like Radiant Guards.
(Note that the Luonnotar's Enlighten Units ability is similar to Evangelize units but can change the religion type of any living unit, including priests of other religions. Disciple units whose owners have adopted the Matronae as their state religion have a spell that removes their religion and divine promotions and then transforms them into Apostates, the clerics of Morrigan who specialize in killing clerics of the old gods.)
The only unitcombats on which you cannot use Evangelize are Animals and Beasts, although since the targets must be living units I cannot think of any Siege or Naval units that would be eligible either.
You can evangelize arcane units, but they may have promotions that make them more likely to resist spells.
Spoiler:
CvSpellInterface.py
Code:
def reqEvangelizeUnits(pCaster, eSpell=-1):
iRel = pCaster.getReligion()
if iRel != -1:
lAnimal = [gc.getInfoTypeForString('UNITCOMBAT_ANIMAL'), gc.getInfoTypeForString('UNITCOMBAT_BEAST')]
iX = pCaster.getX()
iY = pCaster.getY()
for iiX in xrange(iX-1, iX+2, 1):
for iiY in xrange(iY-1, iY+2, 1):
pPlot = CyMap().plot(iiX, iiY)
if pPlot.isNone():continue
for i in xrange(pPlot.getNumUnits()):
pUnit = pPlot.getUnit(i)
if pUnit.isAlive():
if pCaster is pUnit:continue
if pCaster.getID() == pUnit.getID():continue
if pUnit.getReligion() == iRel:continue
if pUnit.getUnitCombatType() in lAnimal:continue
if pUnit.isAvatarOfCivLeader():continue
if gc.getUnitInfo(pUnit.getUnitType()).getReligionType() == -1:
return True
return False
def helpEvangelizeUnits(lpUnits, eSpell = -1):
szBuffer = ''
pCaster = lpUnits[0]
iTeam = pCaster.getTeam()
lTargets = []
iCount = 0
iRel = pCaster.getReligion()
if iRel != -1:
infoRel = gc.getReligionInfo(iRel)
szBuffer += localText.getText("TXT_KEY_SPELL_SPREAD_RELIGION", (u"%c " %(infoRel.getChar()) + infoRel.getDescription(), ))
lAnimal = [gc.getInfoTypeForString('UNITCOMBAT_ANIMAL'), gc.getInfoTypeForString('UNITCOMBAT_BEAST')]
iX = pCaster.getX()
iY = pCaster.getY()
for iiX in xrange(iX-1, iX+2, 1):
for iiY in xrange(iY-1, iY+2, 1):
pPlot = CyMap().plot(iiX, iiY)
if pPlot.isNone():continue
for i in xrange(pPlot.getNumUnits()):
pUnit = pPlot.getUnit(i)
if pUnit.isInvisible(iTeam, False):continue
if pUnit.getReligion() == iRel:continue
if pUnit in lpUnits:continue
if pUnit.getUnitCombatType() in lAnimal:continue
if pUnit.isAvatarOfCivLeader():continue
if pUnit.isAlive():
if gc.getUnitInfo(pUnit.getUnitType()).getReligionType() == -1:
iCount += 1
lTargets.append(pUnit)
lTargets = list(set(lTargets))
iCount = len(lTargets)
if iCount == 1:
pUnit = lTargets.pop(0)
pPlayer = gc.getPlayer(pUnit.getOwner())
if pPlayer != -1:
sList = "<color=%d,%d,%d,%d>%s</color>" %(pPlayer.getPlayerTextColorR(), pPlayer.getPlayerTextColorG(), pPlayer.getPlayerTextColorB(), pPlayer.getPlayerTextColorA(), pUnit.getName() )
szBuffer += localText.getText("TXT_KEY_HELP_SPELL_TARGETS_THIS", ( sList, ))
elif iCount > 0:
sList = ''
while len(lTargets) > 0:
pUnit = lTargets.pop(0)
pPlayer = gc.getPlayer(pUnit.getOwner())
if pPlayer != -1:
sList += "<color=%d,%d,%d,%d>%s</color>" %(pPlayer.getPlayerTextColorR(), pPlayer.getPlayerTextColorG(), pPlayer.getPlayerTextColorB(), pPlayer.getPlayerTextColorA(), pUnit.getName() )
if len(lTargets) > 0:
if len(lTargets) == 1:
sList += " and "
else:
sList += ", "
szBuffer += localText.getText("TXT_KEY_HELP_SPELL_TARGETS_THESE_COUNT_LIST", (iCount, sList, ))
if eSpell != -1:
if eSpell == gc.getInfoTypeForString('SPELL_ENLIGHTEN_UNITS'):
szBuffer += helpTogglePromotions(lpUnits, eSpell, [], ['PROMOTION_ZEAL', 'PROMOTION_UNHOLY_TAINT', 'PROMOTION_CHANNELING4'], 1, True)
if eSpell == gc.getInfoTypeForString('SPELL_EVANGELIZE_UNITS_DRAGON_CULT'):
szBuffer += helpTogglePromotions(lpUnits, eSpell, [], ['PROMOTION_LOYALTY'], 1, True)
return szBuffer
def spellEvangelizeUnits(pCaster, eSpell=-1):
iRel = pCaster.getReligion()
if iRel != -1:
lAnimal = [gc.getInfoTypeForString('UNITCOMBAT_ANIMAL'), gc.getInfoTypeForString('UNITCOMBAT_BEAST')]
iX = pCaster.getX()
iY = pCaster.getY()
for iiX in xrange(iX-1, iX+2, 1):
for iiY in xrange(iY-1, iY+2, 1):
pPlot = CyMap().plot(iiX, iiY)
if pPlot.isNone():continue
for i in xrange(pPlot.getNumUnits()):
pUnit = pPlot.getUnit(i)
if pUnit.isAlive():
if pCaster.getID() == pUnit.getID():continue
if pUnit.getReligion() == iRel:continue
if pUnit.getUnitCombatType() in lAnimal:continue
if pUnit.isAvatarOfCivLeader():continue
if gc.getUnitInfo(pUnit.getUnitType()).getReligionType() == -1:
if not effectResisted(pUnit, pCaster, eSpell):
pUnit.setReligion(iRel)
3. Can Laeran Cord not be spread to cities with other religions present? Seems like I can add other religions after LC, but it doesn’t like to spread when other religions are there first.
There shouldn't be anything special preventing that religion from spreading. It has a conflict with the Stewards of Inequity, but that is no different from how other faiths like the Runes and Foxmen conflict.
4. Is the only way to transform Gaelan into the Burnt Priest to miscast Share Memories, also making him a barbarian and losing Circle of Gaelan from everyone? The civilopedia entry seems to indicate he can be upgraded at level 10 in a city with The Undertow religion, but the option does not appear for me.
Without resorting to Worldbuilder, the only way to transform Gaelan into the Burnt priest is to miscast Trade Memories. That removes the Circle of Gaelan from everyone and deals psychic damage to all units, dealing more damage and adding negative promotions to all units who were in the circle. It may make the Burnt Priest a barbarian, but does not have to. The Burnt Priest will remain under your control if you have switched to the Undertow or Stewards of Inequity state religion before he miscasts.
I was thinking that for his miscasting to transform him into Gaelan required he be high level, but looking at the code I see I had changed a conditional statement to "if True:" in order to test something and had not changed it back yet. I might change that to "if pCaster.getLevel() >= 10:" to make it fit closer to the pedia.
Note that if the Burnt Priest is slain, that a Life 3 archmage could resurrect him under your control if you have the Undertow as your state religion.
Spoiler:
CvSpellInterface.py
Code:
def miscastTradeMemories(pCaster, eSpell):
pCaster.doDamageNoCaster(15, 100, gc.getInfoTypeForString('DAMAGE_PSYCHIC'), False)
lPromotions = [ gc.getInfoTypeForString('PROMOTION_CRAZED'),
gc.getInfoTypeForString('PROMOTION_CHARMED'),
gc.getInfoTypeForString('PROMOTION_ENRAGED'),
gc.getInfoTypeForString('PROMOTION_FATIGUED'),
gc.getInfoTypeForString('PROMOTION_WITHERED'),
gc.getInfoTypeForString('PROMOTION_PARANOID'),
gc.getInfoTypeForString('PROMOTION_MUTATED')
]
if len(lPromotions) > 0:
iProm = lPromotions.pop(CyGame().getSorenRandNum(len(lPromotions), "Trade Memory"))
pCaster.setHasPromotion(iProm, True)
if pCaster.getUnitType() == gc.getInfoTypeForString('UNIT_GAELAN'):
if True:#not pCaster.canAcquirePromotionAny() or CyGame().getSorenRandNum(18, "Memory Palace Destroyed") + pCaster.getLevel > 13:
iCircle = gc.getInfoTypeForString('PROMOTION_CIRCLE_OF_GAELAN')
iCircleC = gc.getInfoTypeForString('BUILDING_CIRCLE_OF_CONJURERS')
pCaster.setHasPromotion(iCircle, False)
pPlot = pCaster.plot()
iPlayer = pCaster.getOwner()
pPlayer = gc.getPlayer(iPlayer)
if pPlayer.getStateReligion() not in [gc.getInfoTypeForString('RELIGION_OCTOPUS_OVERLORDS'),gc.getInfoTypeForString('RELIGION_STEWARDS_OF_INEQUITY')]:
pPlayer = gc.getPlayer(gc.getBARBARIAN_PLAYER())
pPlot = findClearPlot(-1, pPlot)
iUnit = gc.getInfoTypeForString('UNIT_BURNT_PRIEST')
pNewUnit = pPlayer.initUnit(iUnit,pPlot.getX(), pPlot.getY(), UnitAITypes.UNITAI_HERO, DirectionTypes.DIRECTION_SOUTH)
pNewUnit.convert(pCaster)
iPsychic = gc.getInfoTypeForString('DAMAGE_PSYCHIC')
for iPlayer in xrange(gc.getMAX_PLAYERS()):
pPlayer = gc.getPlayer(iPlayer)
if pPlayer.isAlive():
for pyCity in PyPlayer(iPlayer).getCityList() :
pCity = pyCity.GetCy()
pCity.setNumRealBuilding(iCircleC, 0)
for loopUnit in PyPlayer(iPlayer).getUnitList():
if loopUnit.isHasPromotion(iCircle):
loopUnit.doDamage(30, 100, pNewUnit, iPsychic, False)
loopUnit.setHasPromotion(iCircle, False)
for iProm in lPromotions:
loopUnit.setHasPromotion(iProm, True)
else:
loopUnit.doDamage(0, 20, pNewUnit, iPsychic, False)
5. For miscasting, will a spell with a built-in 25% miscast chance (lesser haste, for instance) always have AT LEAST that much miscast chance, even if you get tons of -% miscast chance?
No, that is the base chance for the spell to miscast. That number gets added together with the miscasting modifiers for the unit type and all of its promotions.
Archmages are less likely to miscast than adepts, High Priests less likely than Priests. Conjurers of the Circle of Gaelan are more likely to miscast.
The Arcane, Spiritual, Channeling, and metamagic promotions make miscasting less likely. Priests operating in lands ruled by a different state religion get the hidden "Without Arda" promotion making them a lot more likely to miscast.
In the next version the Crown of Akharien will reduce the miscasting chance by 100%, instead of allowing free upgrades.
I believe the mouseover tooltip for a unit casting a spell includes all the modifiers, but the way it is shown in the pedia does not.
6. Generic question about FFH: what does +X spell damage do? Does that mean if a spell says “about 15% damage to a maximum of 30%” and the unit has +10 spell damage then the spell will do about 25% damage but not be able to damage units past 30% (70% health remaining)?
Now that I’m up and running again, a few questions about this mod:
1. I have all the requirements for Stir from Slumber (at least the listed ones) but cannot cast the ritual. Also, it hasn’t been cast by anyone else as far as I can tell in the World Builder. Do I also need Cult of the Dragon in a city? Is it dependent on AC?
2. Can you not evangelize arcane or disciple units? Seems like my arcane units always resist (as well as ANY unit with Divine I/II) and disciples aren’t even valid targets.
3. Can Laeran Cord not be spread to cities with other religions present? Seems like I can add other religions after LC, but it doesn’t like to spread when other religions are there first.
4. Is the only way to transform Gaelan into the Burnt Priest to miscast Share Memories, also making him a barbarian and losing Circle of Gaelan from everyone? The civilopedia entry seems to indicate he can be upgraded at level 10 in a city with The Undertow religion, but the option does not appear for me.
5. For miscasting, will a spell with a built-in 25% miscast chance (lesser haste, for instance) always have AT LEAST that much miscast chance, even if you get tons of -% miscast chance?
6. Generic question about FFH: what does +X spell damage do? Does that mean if a spell says “about 15% damage to a maximum of 30%” and the unit has +10 spell damage then the spell will do about 25% damage but not be able to damage units past 30% (70% health remaining)?
Yes, it requires the Cult in the city. That makes it easy for Kuriotates to found (due to Legends) and somewhat easy for Tebryn (due to the free Fanatic) but otherwise the only reliable way to get it is to basically invade Acheron's city and perform it there (or build a Fanatic from it and spread it to a more desirable city).
Arcane units can be converted for sure; as far as i know there's no inbuilt extra resistance they have compared to other units. Magic Resistance and similar features does reduce the change of being converted, which seems like a downside (possibly unintentional). As for disciples, i assume the general disciple-class can be converted but there's a buttload of units in there with a specific religious requirement (ai disciples like Acolytes, Savants and their priest/high priest upgrades) that probably can't be. At least i have never seen them be evangelized and i think they are straight up immune to attempts to convert them (Children / Matronae "conversion" nonwithstanding).
Laeran can be spread like usual, although it will conflict with Stewards of Inequity. I don't know if there's a difference in spread rate between religions though, but at very least it can be reliably spread (as well as most other religions that is) via a Scribe.
I don't remember the requirements of keeping Gaelan but i know i've made him into a Burnt Priest before - specifically via miscasting. He has to be a certain level before that can happen though. Controlling him might've required training him then converting to Undertow? I am hazy on the details. Unlike high priests or some other religious heroes, he won't abandon you for changing state religion.
Spell damage increases will benefit the damage of Maelstrom. I just tested it out on a unit with multiple + damage sources (Meta affinity, Spellstaff, Infernal Tome), but i am not sure how the calculation works. A unit with +85 spell damage increases the basic Maelstrom max damage from 50% to 70%, whereas Air Affinity Maelstrom goes from max 90% to 95%, with no listed change in average damage (both unaltered and the improved damages can be seen in the tooltip).
However, other % damage spells (Wither, Earthquake, Call of the Grave) does not gain any listed increase in damage, whether it is the Affinity version or not.
As for miscasting, there seems to be a minimum miscast chance but i don't know if it is always equal to what the spell says or it is affected by promotions. I tested spawning a few dozen archmages who all cast the basic Floating Eye and around 20% miscast, so it seems to be tied to the spell (since the Channeling promotions alone should've brought it far below 0%, and it doesn't seem to be capped to 1% in this anecdotal testing).
I'm wondering now if maybe I should just make the hostile versions of the temples share a BUILDINGCLASS, as they can kind of clutter up the pedia, tech tree, and the tech popups.
In my test games so far I have not often found myself building the harmful versions of the temples (expect in a Calabim game when I wanted extra unhappiness to produce more from the Governor's Manors, which didn't really feel right), and am not sure I want the AI wasting on buildings with negative effects either.
Priests would still be able to found temples even when they would become the hostile versions, which you may want to do in rival territory even more.
I'm thinking of expanding the "without arda" mechanic to use multiple promotions indicating multiple levels of divine favor. The "hostile" versions of a temple could then make enemy priests of that religion less likely to miscast. A Profane's spells might be useless attacking the Empyrean holy city of the goodly Malakim, unless someone managed to set up a Demons Altar there to invite evil into the ity. A Rescuer might not have much chance of guiding Refugees out of oppression unless there is a Safehouse there to shelter them.
This would of course incentivize a lot more Inquisitions.
I cannot remember whether there has been any changes since the last release, but currently Stir from Slumber can be completed multiple times one you know Divine Essense, but there are some restrictions in python.
It requires the Cult of the Dragon be present in the city, unless you are playing as the Kuriotates or Sheaim civilizations.
The specific dragons and Wyrmholds created by the ritual depend on your effective mana supply (your actual number of sources of mana plus or minus some modifiers specific to your civilization, leader, state religion, and alignment.)
The ritual will not create any sort of Wyrmhold that already exists on the map, or any belonging to a species of dragon that the barbarian state already has living.
If there is no possible type of Wyrmhold for the ritual to create, then you cannot create the ritual.
Spoiler:
CvGameUtils.py
Code:
if eProject == gc.getInfoTypeForString('PROJECT_STIR_FROM_SLUMBER'):
if not pCity.isHasReligion(gc.getInfoTypeForString('RELIGION_CULT_OF_THE_DRAGON')):
if pPlayer.getCivilizationType() not in [ gc.getInfoTypeForString('CIVILIZATION_KURIOTATES'), gc.getInfoTypeForString('CIVILIZATION_SHEAIM')]:
return True
iNumWyrmholds = 0
listWyrmholds = [ gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_FEATHERED'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_BLOOD'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_SIEGE'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_GOLD'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_GRAVE'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_OBSIDIAN'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_FANG'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_RUNE'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_PIT'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_FURNACE'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_ELDER'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_WINTER'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_SHIELD'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_CORAL'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_VAULT'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_SEED'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_SHADOW'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_SHIMMERING'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_DAWN'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_SCALED')
]
if eTeam.isHasTech(gc.getInfoTypeForString('TECH_OMNISCIENCE')):
listWyrmholds.append(gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_SPIRE'))
if eTeam.isHasTech(gc.getInfoTypeForString('TECH_MALEVOLENT_DESIGNS')) and eTeam.isBuildingClassMaxedOut(gc.getInfoTypeForString('BUILDINGCLASS_TOWER_OF_NECROMANCY'),0):
if pPlayer.getCivilizationType() != gc.getInfoTypeForString('CIVILIZATION_SIDAR') and pPlayer.countNumBuildings(gc.getInfoTypeForString('BUILDING_SOUL_SHROUD')) < 1:
listWyrmholds.append(gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_DRACOLICH'))
for iWyrmhold in listWyrmholds:
infoWyrmhold = gc.getImprovementInfo(iWyrmhold)
iBonus = infoWyrmhold.getBonusConvert()
if iBonus != -1:
if cf.getNumBonusEffective(iPlayer, iBonus) < 1:
continue
if cf.findImprovement(iWyrmhold) != -1:
continue
iDragon = infoWyrmhold.getSpawnUnitType()
if iDragon !=-1:
if bPlayer.isUnitClassMaxedOut(gc.getUnitInfo(iDragon).getUnitClassType(), 1):continue
iNumWyrmholds += 1
return False
if iNumWyrmholds < 1:
return True
CvEventManager.py
Code:
elif iProjectType == gc.getInfoTypeForString('PROJECT_STIR_FROM_SLUMBER'):
pCity.setHasReligion(gc.getInfoTypeForString('RELIGION_CULT_OF_THE_DRAGON'),True,True,True)
listWyrmholds = [ gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_FEATHERED'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_BLOOD'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_SIEGE'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_GOLD'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_GRAVE'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_OBSIDIAN'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_FANG'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_RUNE'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_PIT'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_FURNACE'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_ELDER'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_WINTER'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_SHIELD'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_CORAL'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_VAULT'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_SEED'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_SHADOW'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_SHIMMERING'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_DAWN'),
gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_SCALED')
]
if eTeam.isHasTech(gc.getInfoTypeForString('TECH_OMNISCIENCE')):
listWyrmholds.append(gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_SPIRE'))
if eTeam.isHasTech(gc.getInfoTypeForString('TECH_MALEVOLENT_DESIGNS')) and eTeam.isBuildingClassMaxedOut(gc.getInfoTypeForString('BUILDINGCLASS_TOWER_OF_NECROMANCY'),0):
if pPlayer.getCivilizationType() != gc.getInfoTypeForString('CIVILIZATION_SIDAR') and pPlayer.countNumBuildings(gc.getInfoTypeForString('BUILDING_SOUL_SHROUD')) < 1:
listWyrmholds.append(gc.getInfoTypeForString('IMPROVEMENT_WYRMHOLD_DRACOLICH'))
for iWyrmhold in listWyrmholds:
infoWyrmhold = gc.getImprovementInfo(iWyrmhold)
iBonus = infoWyrmhold.getBonusConvert()
if iBonus != -1:
if cf.getNumBonusEffective(iPlayer, iBonus) < 1:
continue
iDragon = infoWyrmhold.getSpawnUnitType()
if iDragon !=-1:
if bPlayer.isUnitClassMaxedOut(gc.getUnitInfo(iDragon).getUnitClassType(), 0):
continue
if pPlayer.isUnitClassMaxedOut(gc.getUnitInfo(iDragon).getUnitClassType(), 0):
continue
pWyrmholdPlot = cf.findImprovement(iWyrmhold)
if pWyrmholdPlot == -1:
pWyrmholdPlot = cf.addLair(iWyrmhold)
self.onImprovementBuilt([iWyrmhold, pWyrmholdPlot.getX(), pWyrmholdPlot.getY()])
# elif iDragon !=-1:
# if not bPlayer.isUnitClassMaxedOut(gc.getUnitInfo(iDragon).getUnitClassType(), 0):
# newUnit = bPlayer.initUnit(iDragon, pWyrmholdPlot.getX(), pWyrmholdPlot.getY(), UnitAITypes.NO_UNITAI, DirectionTypes.DIRECTION_SOUTH)
# newUnit.setHasPromotion(gc.getInfoTypeForString('PROMOTION_LAIR_GUARDIAN'), True)
You can evangelize arcane units, but they may have promotions that make them more likely to resist spells.
You cannot evangelize units that have a religion type set in their xml defines, at least not if the Evangelist follows most religions. The Matronae and Luonnotar have special abilities for evangelizing priests and making them abandon the gods.
Disciples typically do have religions defined in the xml, but so do religious champions of other unitcombats.
You cannot evangelize units of the animal or beast unitcombats.
Spoiler:
CvSpellInterface.py
Code:
def reqEvangelizeUnits(pCaster, eSpell=-1):
iRel = pCaster.getReligion()
if iRel != -1:
lAnimal = [gc.getInfoTypeForString('UNITCOMBAT_ANIMAL'), gc.getInfoTypeForString('UNITCOMBAT_BEAST')]
iX = pCaster.getX()
iY = pCaster.getY()
for iiX in xrange(iX-1, iX+2, 1):
for iiY in xrange(iY-1, iY+2, 1):
pPlot = CyMap().plot(iiX, iiY)
if pPlot.isNone():continue
for i in xrange(pPlot.getNumUnits()):
pUnit = pPlot.getUnit(i)
if pUnit.isAlive():
if pCaster is pUnit:continue
if pCaster.getID() == pUnit.getID():continue
if pUnit.getReligion() == iRel:continue
if pUnit.getUnitCombatType() in lAnimal:continue
if pUnit.isAvatarOfCivLeader():continue
if gc.getUnitInfo(pUnit.getUnitType()).getReligionType() == -1:
return True
return False
def helpEvangelizeUnits(lpUnits, eSpell = -1):
szBuffer = ''
pCaster = lpUnits[0]
iTeam = pCaster.getTeam()
lTargets = []
iCount = 0
iRel = pCaster.getReligion()
if iRel != -1:
infoRel = gc.getReligionInfo(iRel)
szBuffer += localText.getText("TXT_KEY_SPELL_SPREAD_RELIGION", (u"%c " %(infoRel.getChar()) + infoRel.getDescription(), ))
lAnimal = [gc.getInfoTypeForString('UNITCOMBAT_ANIMAL'), gc.getInfoTypeForString('UNITCOMBAT_BEAST')]
iX = pCaster.getX()
iY = pCaster.getY()
for iiX in xrange(iX-1, iX+2, 1):
for iiY in xrange(iY-1, iY+2, 1):
pPlot = CyMap().plot(iiX, iiY)
if pPlot.isNone():continue
for i in xrange(pPlot.getNumUnits()):
pUnit = pPlot.getUnit(i)
if pUnit.isInvisible(iTeam, False):continue
if pUnit.getReligion() == iRel:continue
if pUnit in lpUnits:continue
if pUnit.getUnitCombatType() in lAnimal:continue
if pUnit.isAvatarOfCivLeader():continue
if pUnit.isAlive():
if gc.getUnitInfo(pUnit.getUnitType()).getReligionType() == -1:
iCount += 1
lTargets.append(pUnit)
lTargets = list(set(lTargets))
iCount = len(lTargets)
if iCount == 1:
pUnit = lTargets.pop(0)
pPlayer = gc.getPlayer(pUnit.getOwner())
if pPlayer != -1:
sList = "<color=%d,%d,%d,%d>%s</color>" %(pPlayer.getPlayerTextColorR(), pPlayer.getPlayerTextColorG(), pPlayer.getPlayerTextColorB(), pPlayer.getPlayerTextColorA(), pUnit.getName() )
szBuffer += localText.getText("TXT_KEY_HELP_SPELL_TARGETS_THIS", ( sList, ))
elif iCount > 0:
sList = ''
while len(lTargets) > 0:
pUnit = lTargets.pop(0)
pPlayer = gc.getPlayer(pUnit.getOwner())
if pPlayer != -1:
sList += "<color=%d,%d,%d,%d>%s</color>" %(pPlayer.getPlayerTextColorR(), pPlayer.getPlayerTextColorG(), pPlayer.getPlayerTextColorB(), pPlayer.getPlayerTextColorA(), pUnit.getName() )
if len(lTargets) > 0:
if len(lTargets) == 1:
sList += " and "
else:
sList += ", "
szBuffer += localText.getText("TXT_KEY_HELP_SPELL_TARGETS_THESE_COUNT_LIST", (iCount, sList, ))
if eSpell != -1:
if eSpell == gc.getInfoTypeForString('SPELL_ENLIGHTEN_UNITS'):
szBuffer += helpTogglePromotions(lpUnits, eSpell, [], ['PROMOTION_ZEAL', 'PROMOTION_UNHOLY_TAINT', 'PROMOTION_CHANNELING4'], 1, True)
if eSpell == gc.getInfoTypeForString('SPELL_EVANGELIZE_UNITS_DRAGON_CULT'):
szBuffer += helpTogglePromotions(lpUnits, eSpell, [], ['PROMOTION_LOYALTY'], 1, True)
return szBuffer
def spellEvangelizeUnits(pCaster, eSpell=-1):
iRel = pCaster.getReligion()
if iRel != -1:
lAnimal = [gc.getInfoTypeForString('UNITCOMBAT_ANIMAL'), gc.getInfoTypeForString('UNITCOMBAT_BEAST')]
iX = pCaster.getX()
iY = pCaster.getY()
for iiX in xrange(iX-1, iX+2, 1):
for iiY in xrange(iY-1, iY+2, 1):
pPlot = CyMap().plot(iiX, iiY)
if pPlot.isNone():continue
for i in xrange(pPlot.getNumUnits()):
pUnit = pPlot.getUnit(i)
if pUnit.isAlive():
if pCaster.getID() == pUnit.getID():continue
if pUnit.getReligion() == iRel:continue
if pUnit.getUnitCombatType() in lAnimal:continue
if pUnit.isAvatarOfCivLeader():continue
if gc.getUnitInfo(pUnit.getUnitType()).getReligionType() == -1:
if not effectResisted(pUnit, pCaster, eSpell):
pUnit.setReligion(iRel)
There shouldn't be anything special preventing that religion from spreading. It has a conflict with the Stewards of Inequity, but that is no different from how other faiths like the Runes and Foxmen conflict.
Without resulting to Worldbuilder, the only way to transform Gaelan into the Burnt priest is to miscast Trade Memories. That removes the Circle of Gaelan from everyone and deals psychic damage to all units, dealing more damage and adding negative promotions to all units who were in the circle. It may make the Burnt Priest a barbarian, but does not have to. The Burnt Priest will remain under your control if you have switched to the Undertow or Stewards of Inequity state religion before he miscasts.
I was thinking that for his miscasting to transform him into Gaelan required he be high level, but looking at the code I see I had changed a conditional statement to "if True:" in order to test something and had not changed it back yet. I might change that to "if pCaster.getLevel >= 10:" to make it fit closer to the pedia.
Note that if the Burnt Priest is slain, that a Life 3 archmage could resurrect him under your control if you have the Undertow as your state religion.
Spoiler:
CvSpellInterface.py
Code:
def miscastTradeMemories(pCaster, eSpell):
pCaster.doDamageNoCaster(15, 100, gc.getInfoTypeForString('DAMAGE_PSYCHIC'), False)
lPromotions = [ gc.getInfoTypeForString('PROMOTION_CRAZED'),
gc.getInfoTypeForString('PROMOTION_CHARMED'),
gc.getInfoTypeForString('PROMOTION_ENRAGED'),
gc.getInfoTypeForString('PROMOTION_FATIGUED'),
gc.getInfoTypeForString('PROMOTION_WITHERED'),
gc.getInfoTypeForString('PROMOTION_PARANOID'),
gc.getInfoTypeForString('PROMOTION_MUTATED')
]
if len(lPromotions) > 0:
iProm = lPromotions.pop(CyGame().getSorenRandNum(len(lPromotions), "Trade Memory"))
pCaster.setHasPromotion(iProm, True)
if pCaster.getUnitType() == gc.getInfoTypeForString('UNIT_GAELAN'):
if True:#not pCaster.canAcquirePromotionAny() or CyGame().getSorenRandNum(18, "Memory Palace Destroyed") + pCaster.getLevel > 13:
iCircle = gc.getInfoTypeForString('PROMOTION_CIRCLE_OF_GAELAN')
iCircleC = gc.getInfoTypeForString('BUILDING_CIRCLE_OF_CONJURERS')
pCaster.setHasPromotion(iCircle, False)
pPlot = pCaster.plot()
iPlayer = pCaster.getOwner()
pPlayer = gc.getPlayer(iPlayer)
if pPlayer.getStateReligion() not in [gc.getInfoTypeForString('RELIGION_OCTOPUS_OVERLORDS'),gc.getInfoTypeForString('RELIGION_STEWARDS_OF_INEQUITY')]:
pPlayer = gc.getPlayer(gc.getBARBARIAN_PLAYER())
pPlot = findClearPlot(-1, pPlot)
iUnit = gc.getInfoTypeForString('UNIT_BURNT_PRIEST')
pNewUnit = pPlayer.initUnit(iUnit,pPlot.getX(), pPlot.getY(), UnitAITypes.UNITAI_HERO, DirectionTypes.DIRECTION_SOUTH)
pNewUnit.convert(pCaster)
iPsychic = gc.getInfoTypeForString('DAMAGE_PSYCHIC')
for iPlayer in xrange(gc.getMAX_PLAYERS()):
pPlayer = gc.getPlayer(iPlayer)
if pPlayer.isAlive():
for pyCity in PyPlayer(iPlayer).getCityList() :
pCity = pyCity.GetCy()
pCity.setNumRealBuilding(iCircleC, 0)
for loopUnit in PyPlayer(iPlayer).getUnitList():
if loopUnit.isHasPromotion(iCircle):
loopUnit.doDamage(30, 100, pNewUnit, iPsychic, False)
loopUnit.setHasPromotion(iCircle, False)
for iProm in lPromotions:
loopUnit.setHasPromotion(iProm, True)
else:
loopUnit.doDamage(0, 20, pNewUnit, iPsychic, False)
No, that is the base chance for the spell to miscast. That number gets added together with the miscasting modifiers for the unit type and all of its promotions.
Archmages are less likely to miscast than adepts, High Priests less likely than Priests. Conjurers of the Circle of Gaelan are more likely to miscast.
The Arcane, Spiritual, Channeling, and metamagic promotions make miscasting less likely. Priests operating in lands ruled by a different state religion get the hidden "Without Arda" promotion making them a lot more likely to miscast.
In the next version the Crown of Akharien will reduce the miscasting chance by 100%, instead of allowing free upgrades.
I believe the mouseover tooltip for a unit casting a spell includes all the modifiers, but the way it is shown in the pedia does not.
Thanks for the detailed response, and for putting the code in there as well, that is very helpful.
I need to go brainwash a dragon priest dude, that was the one missing element for stir from slumber!
Regarding evangelize, that makes sense for the Brujah as I bet they are Anointed in the XML, the others were Sapere (Laeran Cord) turned Mage - does the XML Laeran Cord designation follow the Sapere unit even if it switches class?
Laeran Cord not spreading makes sense as I think Stewards of Inequity were in all those cities.
The miscast tooltip for a lesser spell on an archmage still says 25% even with Channeling I-IV, Metamagic III, and a spellstaff. Is this just a case of the tooltip not reflecting the mechanics?
I’ll need to look more into the magic damage thing. Sometimes the limit number seems like an absolute limit (i.e. cannot damage units more than that amount ever) and sometimes it seems like a per casting limit. For example, I have seen Crown of Brilliance reduce units to very low health but not kill them even after multiple castings/ticks, but I yeeted a full stack with two castings of pillar of flames the other day.
P.S. this mod is fantastic. An improvement on one of the best mods for any game I’ve ever played, FFH2. So way to go!
I cannot remember whether there have been any changes since the last release, but currently Stir from Slumber can be completed multiple times one you know Divine Essense, but there are some restrictions in python.
It requires the Cult of the Dragon be present in the city, unless you are playing as the Kuriotates or Sheaim civilizations.
The specific dragons and Wyrmholds created by the ritual depend on your effective mana supply (your actual number of sources of mana plus or minus some modifiers specific to your civilization, leader, state religion, and alignment.)
The ritual will not create any sort of Wyrmhold that already exists on the map, or any belonging to a species of dragon that the barbarian state already has living.
If there is no possible type of Wyrmhold for the ritual to create, then you cannot create the ritual.
I recall that I also couldn't build Stir from Slumber, despite meeting the listed requirements; until after I edited CIV4ProjectInfo.xml -- it has <iMaxGlobalInstances>-1</iMaxGlobalInstances> in the June 22 version; changing that to 1 (or a higher positive number) was needed (in addition to Cult in the city, Divine Essence etc).
On a related note; can Spire Dragons ever spawn (from their symbolic "wyrmhold" or otherwise), or is that unit more intended for use in previous-age, pre-extinction scenarios?
I think I figured out why Evangelist was not working for me. Both Nullstone Citadel and Ring of Force (the affinity version) indicate that units in the given city receive magic resistance, but also have an entry that says “+% for units to resist magic.” Does this latter effect apply to the whole team regardless of geographic location?
Seems like a bug: when I upgrade a Sapere to a Hierophant, they lose their Arcane promotion. Happens when going Mage -> Hierophant too. New Hierophants, whether from Theology or the world builder, start with Arcane though.
I was sure I remembered the mouseovers showing the miscast chance with modifiers, but it doesn't seem to be doing that now.
I'm still playing around with divine casters odds of miscating spells being influenced by a variety of different "Arda" promotions. Ideally I'd like it if I could give specific spells a python call that controls just its own miscast chance, but the best the game engine let me to is to use a passive python effect to swap out promotions that chance a unit's miscast chance for all spells. I wanted it to be influenced by the owner's state religion, the state religion of the owner of the plot, the religions present in the closest city, temples in the city, etc. I thought about having it be influenced by the religions of nearby units, but for code that gets called as often as this cycling through huge stacks could get very inefficient.
This morning I realized I could use CyGame().calculateReligionPercent(iReligion) to quickly check how much influence a religion has in the world as a whole, which could allow some interesting strategic motivations to try to spread your religion and prevent the spread of others. If almost everyone follows your religion then your priest's spells would never fail, but if no one believes in your god then the spells become useless.
Right now I'm working with a system that works with larger numbers and then translates that into choosing one of 10 different levels of Arda promotions ranging from +200% to - 100% chance of miscasting.
(Arda is what Kael calls the divine power that a god extends to his priests and angels. Due to the Compact, how much power he shares is limited by not only the recipient's faith but the faith of others nearby. Agares cannot do much to help a Profane attack a city full of saints that follow Sirona, but could give him almost limitless power against Savants and enough to kill a high priest of a good god when he is dwelling among the wicked. The Matronae are working to eliminate the believers of the 21 Gods because if no one believes in any of them anymore then the Compact would prevent them from sharing their Arda with anyone. In the Age of Innovation, the Matronae faith becomes so widespread that even the remnants who still believe in the old gods cannot accept a literal interpretation of stories of miracles that had been worked in earlier ages.)
I just added a "Monotheist Meetinghouse" as a temple of the Luonnotar, which turns into a hostile version if you follow any state religion, which can further protect against priest spells being cast nearby. I made the friendly Grigori version grant happiness nearby cities, a GPP bonus, and happiness from every mana type.
I'm still debating whether to add a temple for the Cult of the Dragon or the Matronae. Canonically the only religions buildings we know exist for the Matronae as the 3 wonders already in the game, so they probably won't get temples. I could add dragon shrines for each type of dragon, but that seems like overkill. One shrine with free specialists from any Wyrmhold would be easier.
The Luonnatar, Matronae, and Dragon Fanatics would not have any divine units who could gain any Arda promotions, as they do not serve gods who can grant miracles or are bound by The Compact. Those who worship them instead of the gods would however weaken the ardas of true priests.
For the names of the Esus clerics, I'm now leaning towards "Swindler" => "Thief" = > "Propogandist"
I'm thinking of giving arda bonuses based on resources on the tile too. I found I could use iBonusModifer = gc.getUnitInfo(pCaster.getUnitType()).getBonusProductionModifier(iBonus) to modify the Arda counter based on the resources for which a unit's xml defines have a production modifier. I'd already given most disciples such modifiers based on their patron mana sphere, plus gave Druids a bonus for Fruit of the Yggdrasil and Cultists a bonus for Jeteye. Giving bonuses for hell resources for Ritualsist would make sense. Now that I think of it, the plotcounter should probably be used to make evil spells stronger in Hell.
I recall that I also couldn't build Stir from Slumber, despite meeting the listed requirements; until after I edited CIV4ProjectInfo.xml -- it has <iMaxGlobalInstances>-1</iMaxGlobalInstances> in the June 22 version; changing that to 1 (or a higher positive number) was needed (in addition to Cult in the city, Divine Essence etc).
On a related note; can Spire Dragons ever spawn (from their symbolic "wyrmhold" or otherwise), or is that unit more intended for use in previous-age, pre-extinction scenarios?
That doesn't make sense to me. A <iMaxGlobalInstances>-1</iMaxGlobalInstances> should allow unlimited instances, and it does when I just playtested it. It may appear not work if you don't have the python prereqs, but I suspect changing that tag making it work was just a coincidence.
I have not yet added an ability for Spire dragons to spawn from their lair. it is really juts a flavor thing, which can also give an extra source of metamagic mana.
Seems like a bug: when I upgrade a Sapere to a Hierophant, they lose their Arcane promotion. Happens when going Mage -> Hierophant too. New Hierophants, whether from Theology or the world builder, start with Arcane though.
I think that must be due to the Arcane promotion having the bValidate tag and due to the only allowed unitcombat being UNITCOMBAT_ADEPT. I think it checks when upgrading units but not when initializing new ones.
The issue probably effects the Arcane promotion when granted to vampire spawns of vampiric mages under Alexis too.
I guess the easiest solution would just be to remove bValidate.
I was sure I remembered the mouseovers showing the miscast chance with modifiers, but it doesn't seem to be doing that now.
I'm still playing around with divine casters odds of miscating spells being influenced by a variety of different "Arda" promotions. Ideally I'd like it if I could give specific spells a python call that controls just its own miscast chance, but the best the game engine let me to is to use a passive python effect to swap out promotions that chance a unit's miscast chance for all spells. I wanted it to be influenced by the owner's state religion, the state religion of the owner of the plot, the religions present in the closest city, temples in the city, etc. I thought about having it be influenced by the religions of nearby units, but for code that gets called as often as this cycling through huge stacks could get very inefficient.
This morning I realized I could use CyGame().calculateReligionPercent(iReligion) to quickly check how much influence a religion has in the world as a whole, which could allow some interesting strategic motivations to try to spread your religion and prevent the spread of others. If almost everyone follows your religion then your priest's spells would never fail, but if no one believes in your god then the spells become useless.
Right now I'm working with a system that works with larger numbers and then translates that into choosing one of 10 different levels of Arda promotions ranging from +200% to - 100% chance of miscasting.
(Arda is what Kael calls the divine power that a god extends to his priests and angels. Due to the Compact, how much power he shares is limited by not only the recipient's faith but the faith of others nearby. Agares cannot do much to help a Profane attack a city full of saints that follow Sirona, but could give him almost limitless power against Savants and enough to kill a high priest of a good god when he is dwelling among the wicked. The Matronae are working to eliminate the believers of the 21 Gods because if no one believes in any of them anymore then the Compact would prevent them from sharing their Arda with anyone. In the Age of Innovation, the Matronae faith becomes so widespread that even the remnants who still believe in the old gods cannot accept a literal interpretation of stories of miracles that had been worked in earlier ages.)
I just added a "Monotheist Meetinghouse" as a temple of the Luonnotar, which turns into a hostile version if you follow any state religion, which can further protect against priest spells being cast nearby. I made the friendly Grigori version grant happiness nearby cities, a GPP bonus, and happiness from every mana type.
I'm still debating whether to add a temple for the Cult of the Dragon or the Matronae. Canonically the only religions buildings we know exist for the Matronae as the 3 wonders already in the game, so they probably won't get temples. I could add dragon shrines for each type of dragon, but that seems like overkill. One shrine with free specialists from any Wyrmhold would be easier.
The Luonnatar, Matronae, and Dragon Fanatics would not have any divine units who could gain any Arda promotions, as they do not serve gods who can grant miracles or are bound by The Compact. Those who worship them instead of the gods would however weaken the ardas of true priests.
For the names of the Esus clerics, I'm now leaning towards "Swindler" => "Thief" = > "Propogandist"
That doesn't make sense to me. A <iMaxGlobalInstances>-1</iMaxGlobalInstances> should allow unlimited instances, and it does when I just playtested it. It may appear not work if you don't have the python prereqs, but I suspect changing that tag making it work was just a coincidence.
I have not yet added an ability for Spire dragons to spawn from their lair. it is really juts a flavor thing, which can also give an extra source of metamagic mana.
I think that must be due to the Arcane promotion having the bValidate tag and due to the only allowed unitcombat being UNITCOMBAT_ADEPT. I think it checks when upgrading units but not when initializing new ones.
The issue probably effects the Arcane promotion when granted to vampire spawns of vampiric mages under Alexis too.
I guess the easiest solution would just be to remove bValidate.
Regarding the mouse overs and modifiers: it does show them if it brings the chance above the base chance. For instance, my Brujah casting Rage in another’s territory or if my religion is not Anointed is sky high, likewise, my Saperes with Circle of Gaelan show a bigger chance as well. It just never goes below the base chance on the tooltip. Also, I think the actual miscast chance never goes below the base chance (that is, the tooltip is correct). I had a Vampire Lord, calculated his miscast reduction at -120% (-75% from Channeling II & III, -25% base on the unit, -20% spellstaff), and he still miscasts Wraith all the time and I have to fight them.
Fun fact, Arda is also the name of the planet Middle Earth is on. Getting a lot of use in fantasy!
For adjusting specific spells, could you have the religious environment cause the spell itself to be replaced with a version with a different base miscast chance? Or swap the Divine promotion for a version with higher miscast chance spells attached? Seems like whatever trigger you are using to add/remove Without Arda could maybe do that. But I am speculating as I’m not familiar with the modding capabilities on Civ4.
Also, I’m spending way too much time reading the hundreds of compiled lore posts from you and Kael on Google drive. FfH is a pretty darn good bit of fantasy world-building.
That doesn't make sense to me. A <iMaxGlobalInstances>-1</iMaxGlobalInstances> should allow unlimited instances, and it does when I just playtested it. It may appear not work if you don't have the python prereqs, but I suspect changing that tag making it work was just a coincidence.
Yeah, I think you're right about that having been a coincidence. Changed the tag back and tried loading an old save from when I had just taken Acheron's city; and the ritual is buildable at that time, so I guess it was a fluke that simply reloading would've sufficed to solve.
Unrelated; I've noticed that some arcane units gain no (more) xp from channelling/arcane/etc promotions if raised as undead; while of course liches don't have that problem, so I guess it's not specifically due to the Undead tag. Example: adept is fed to a vampire in a city with Mokka's Cauldron, comes out an undead Imp who gains no more free XP from its promotions. Same with undead "pseudo-hero" Mokka, no free XP gain even holding Spellstaff, Infernal Grimoire and having Arcane trait from his summoner/raiser (luckily his Undeath Affinity lets him get XP other ways, like raising a settler from city ruins and getting some of its "xp" when that unit joins a city ). Maybe it's as intended, but in any case am curious about what mechanic is blocking the xp gain.
Another note: Rescue Refugees is extremely powerful even without Wardens as state religion; a single rescuer can take any city down to a single pop in a single turn, by sending the refugees ahead out of the city when rescuer capacity is full. And of course, if you do it to an AI civ, they don't understand or recognise that you're taking virtually their whole population while ostensibly at peace. Miscast rate from not having Wardens as state religion isn't really an issue since there's no limit to how many times you can try in a turn, and neither is the limit to the number of rescuers when, again, a single one can drain at least one city per turn. Maybe limit the rescue ability to Wardens state religion? Or make it usable only in fewer, more specific contexts (e.g. city in disorder, unhappiness from vampire feasting, sacrifice the weak civic, theocracy if religious minority present in city etc), rather than Liberty civic being (seemingly) the only safe way to block rescuers.
Yeah, I think you're right about that having been a coincidence. Changed the tag back and tried loading an old save from when I had just taken Acheron's city; and the ritual is buildable at that time, so I guess it was a fluke that simply reloading would've sufficed to solve.
Unrelated; I've noticed that some arcane units gain no (more) xp from channelling/arcane/etc promotions if raised as undead; while of course liches don't have that problem, so I guess it's not specifically due to the Undead tag. Example: adept is fed to a vampire in a city with Mokka's Cauldron, comes out an undead Imp who gains no more free XP from its promotions. Same with undead "pseudo-hero" Mokka, no free XP gain even holding Spellstaff, Infernal Grimoire and having Arcane trait from his summoner/raiser (luckily his Undeath Affinity lets him get XP other ways, like raising a settler from city ruins and getting some of its "xp" when that unit joins a city ). Maybe it's as intended, but in any case am curious about what mechanic is blocking the xp gain.
Another note: Rescue Refugees is extremely powerful even without Wardens as state religion; a single rescuer can take any city down to a single pop in a single turn, by sending the refugees ahead out of the city when rescuer capacity is full. And of course, if you do it to an AI civ, they don't understand or recognise that you're taking virtually their whole population while ostensibly at peace. Miscast rate from not having Wardens as state religion isn't really an issue since there's no limit to how many times you can try in a turn, and neither is the limit to the number of rescuers when, again, a single one can drain at least one city per turn. Maybe limit the rescue ability to Wardens state religion? Or make it usable only in fewer, more specific contexts (e.g. city in disorder, unhappiness from vampire feasting, sacrifice the weak civic, theocracy if religious minority present in city etc), rather than Liberty civic being (seemingly) the only safe way to block rescuers.
The ability units to get free caster xp from promotions like arcane or channeling depends on tag in their unit xml defines. I'll have to check whether imps and mokka have that tag after I get back home
I haven't tested it yet but I expect that the new expanded arda mechanic will nerf Rescue Refugees more than enough. The cities where it can be used would all be those with modifiers making Miscasting much more likely.
Before adding that mechanic, I was leaning towards making Rescue Refugees require a Safehouse (hostile) and/or making the Refugees ability to settle in a city bringing their xp over as culture or production require a friendly Safehouse there. I might still do that, but right now I'm guessing I'll need to make the spell much less likely to miscast.
Note that shortly after the last release I changed the ignore has cast tag to a has cast tag, so each caster could only use it once per turn unless it has a spell staff.
I think I have a potential unintended consequence of Mutation/Chaos Affinity to report: the adjustment to attack/defense/moves can be applied repeatedly, whereas the random promotions can only happen once. I noticed that my Gaelan unit would always be astronomically stronger after leaving him to sit for like 100 turns. This happened in 3 different games. For example, he currently has a strength of 34/32 (base, before affinities) and 3 moves (with no mobility promotions), and his starting strength was 3! This is because the mutation from Chaos Affinity procs multiple times while he sits.
The problem is that the code uses 2*current value as the range for setting the new value for attack/defense/moves. This makes the odds of getting a better or worse score about 50/50 for a single roll (actually a bit in favor of lower values since basic python ranges are 0:n-1, inclusive), but across multiple rolls, the probability curve will always skew more and more in favor of greater (even much greater) numbers as the number of castings increases. Mathematically this is because, as the range is doubled on each roll, the effect of subsequent "good" rolls is enhanced (larger and larger ranges wherein the previous range accounts for less of the new range) while the effect of subsequent "bad" rolls is mitigated (the range gets compressed, still encompassing a relatively higher and higher portion of the previous range). Another issue (maybe, unless this is intended behavior) is that it is possible to roll a zero making the unit completely useless for combat forever after, or forever immobile, as the case may be.
EDIT: I made some python code to check this, and it appears there are several ways to go. If you run it as is, the probability of increasing the values goes up until about 10 casts but then actually starts to go down as the probability of rolling a zero increases, and a zero is permanent (had not considered this previously). If you correct for rolling zeroes (again, unless this is intentional) with a code like this:
Python:
value = random.randint(0,value*2) + 1
you will get random values between 1 and twice the value. The creep upwards is very pronounced in this scenario. After 10,000 trials with a starting value of 6 and doing 10 casts per trial, the average final value for a given unit is ~16.
On the other hand, this code:
Python:
value = random.randint(0,value*2)
if value == 0:
value = 1
will not permabork units when a zero is rolled, but the creep upward is less pronounced as the probability of rolling a 1 is twice that of all other numbers. After 10,000 trials with a starting value of 6 and doing 10 casts per trial, the average final value for a given unit is ~7.75.
Code is python3, but I think it should make sense what I was doing in python2.
On startup.
I enabled all of the logging available, and looking through the logs, there doesn't seem to be any errors in there. I think it's failing to load these files before the mod even initializes. (I can send the logs if you want, but I doubt they will be of help)
I installed it as normal, FFH2, then o patch, then I copied the zip over. I also tried copying a working version from a friend, which also gave the same error. I load the mod by opening vanilla Civ IV, then loading the mod.
Any help you can offer on this issue would be appreciated!
On startup.
I enabled all of the logging available, and looking through the logs, there doesn't seem to be any errors in there. I think it's failing to load these files before the mod even initializes. (I can send the logs if you want, but I doubt they will be of help)
I installed it as normal, FFH2, then o patch, then I copied the zip over. I also tried copying a working version from a friend, which also gave the same error. I load the mod by opening vanilla Civ IV, then loading the mod.
Any help you can offer on this issue would be appreciated!
I am using PlayonLinux (manjaro distro) but mine is running without errors. Can you load other mods, including base FFH?
You specified vanilla Civ IV; that is including Beyond the Sword right? If the game boots without the expansions it won't work. On that note, make sure the mod is installed in Beyond the Sword's mod folder, not the base game's one.
I am using PlayonLinux (manjaro distro) but mine is running without errors. Can you load other mods, including base FFH?
You specified vanilla Civ IV; that is including Beyond the Sword right? If the game boots without the expansions it won't work. On that note, make sure the mod is installed in Beyond the Sword's mod folder, not the base game's one.
Yeah, I misspoke, sorry, I'm loading it from Beyond The Sword. I can load FFH + O patch just fine, and a few other mods as well. It's in the correct directory, same as FFH.
Yeah, I misspoke, sorry, I'm loading it from Beyond The Sword. I can load FFH + O patch just fine, and a few other mods as well. It's in the correct directory, same as FFH.
Strange; checking my own file path to the XML files the only difference i note in Assets/XML/Gameinfo/ is the presence of the Civ4PlayerOptionInfos.xml file in the Mmm copy, though perhaps it is only created as a result of changing settings. Have you veriified the Magister installation didn't create duplicate folders? I recall having an issue with that when i installed it on another setup a long time ago, and i had to manually rename folders to merge them. It should've replaced a few files when installing the submod, rather than existing as a seperate folder in the FFH one.
Strange; checking my own file path to the XML files the only difference i note in Assets/XML/Gameinfo/ is the presence of the Civ4PlayerOptionInfos.xml file in the Mmm copy, though perhaps it is only created as a result of changing settings. Have you veriified the Magister installation didn't create duplicate folders? I recall having an issue with that when i installed it on another setup a long time ago, and i had to manually rename folders to merge them. It should've replaced a few files when installing the submod, rather than existing as a seperate folder in the FFH one.
So, the files exist where they're supposed to, I can see them. I copied FFH w/the O patch into a folder called "Magister Modmod for FfH2", then copied the zip over it, and overwrote the files. For some reason, it's not loading them, even though they exist.
This site uses cookies to help personalise content, tailor your experience and to keep you logged in if you register.
By continuing to use this site, you are consenting to our use of cookies.