Dummy Buildings, and Building-Class Structure Issues with Certain Building Effects

LeeS

Imperator
Joined
Jul 23, 2013
Messages
7,241
Location
Illinois, USA
Support Issues Related to the Impending Release of Civ6:
  1. Other than to clean up any small whoopses or typos that may exist in the information presented I have no intentions of adding to the information nor of making any great changes to format of how the info is presented
  2. I am attempting to wind-down my Civ5 modding in preperation for the release of 6.
  3. I am not abandoning the Civ5 modding forum, I am just winding down the stuff I have in the works and that I can reasonably expect to put to bed prior to the release of 6.
  4. I intend to move on to 6 modding for the most part (or for the all part), assuming 6 is not a mess or a BE

-----------------------------------------------------------------------------------------------------------------------------------------------------



Some Advice and Guidance on <BuildingClass> Table Structure for Proper Hook-up to Certain Building Effects


&

Some Guidance on <Buildings> Table Structure for Dummy and Hidden Buildings

With Particular Attention to Dummy and Hidden Buildings
When Using Either XML or SQL Methods to Insert Such Buildings and Building-Classes Into the Game's Database​



Note on Usage of the terms "Dummy Building" and "Hidden Building":
  • I tend to differentiate between a "Dummy" building and a "Hidden" building only in that in the way I define them a "hidden" building is hidden from sight of the mod-user, whereas a "dummy" building is not hidden from sight of the mod-user. This is not, I think, anything like the way most mod-creators think of the distinction between a "dummy" building and a "hidden" building.
Note on Examples of code that may be included with this reference:
  • When I show examples of code within tutorials or references I am never interested in whether or not the effects such code would create are balanced in-game. I am only interested in using an example of code and coding methods to illustrate a point or present a method to achieve a goal.
----------------------------------------------------------------------------------------------------------------------------------------------------------------------

Guidance on <BuildingClass> Table Structure for Proper Hook-up to Certain Building Effects

Introduction: <BuildingClass> Table Structuring

As many more-experienced Mod-Creators already know, there are certain limitations to successfully getting Buildings to have an expected or anticipated effect in-game. Most of these limitations can be directly traced back to how a building is inserted into its corresponding Building-Class. In essence, without LUA intervention, the game will not allow certain kinds of building effects to "stack", or to be given at all via a building to which a specific civilization is not entitled from within a specific Building-Class. So, for purposes of this "guidance", the structure of a Building-Class includes not only the setting of the Default Building within such a class, but also the settings of all unique buildings from within the class that have been specified in <Rows> within the <Civilization_BuildingClassOverrides> table. Any building that has been inserted into a specific Building-Class, and which is neither the DefaultBuilding, nor has been assigned to a specific civilization (via the <Civilization_BuildingClassOverrides> table), will fail to give the effects to be discussed in this guidance.

Consider the following 'Mock-Up' Building-Class and the Buildings Assigned:

BUILDINGCLASS_TAVERN
Building Kind | Building | Correct Civilization(s) | Extra Effect
Default Building | BUILDING_TAVERN | ALL BUT GERMANY | NONE
Unique Building | BUILDING_ALE_HOUSE | CIVILIZATION_GERMANY | +1 Tourism

Only Germany would be able to make use of the Tourism effect within such a structure. By "such a structure" I mean that the <BuildingClass> Table and the <Civilization_BuildingClassOverrides> table are entered as follows:
Code:
<BuildingClasses>
	<Row>
		<Type>BUILDINGCLASS_TAVERN</Type>
		<DefaultBuilding>BUILDING_TAVERN</DefaultBuilding>
		<Description>TXT_KEY_BUILDING_TAVERN</Description>
	</Row>
</BuildingClasses>
<Civilization_BuildingClassOverrides>
	<Row>
		<CivilizationType>CIVILIZATION_GERMANY</CivilizationType>
		<BuildingClassType>BUILDINGCLASS_TAVERN</BuildingClassType>
		<BuildingType>BUILDING_ALE_HOUSE</BuildingType>
	</Row>
</Civilization_BuildingClassOverrides>
It would still be possible to assign via LUA a BUILDING_ALE_HOUSE to a city not belonging to Germany, but there would be no Tourism effect in that non-German city coming from the BUILDING_ALE_HOUSE. The opposite is also true: adding a BUILDING_TAVERN to a German city would not have the correct effects for such things as Tourism.

If the structure of the 'mock' building-class were as this:

BUILDINGCLASS_TAVERN
Building Kind | Building | Correct Civilization(s) | Extra Effect
Default Building | BUILDING_TAVERN | ALL BUT GERMANY | +1 Tourism
Unique Building | BUILDING_ALE_HOUSE | CIVILIZATION_GERMANY | +2 Tourism

Germany would get 2 Tourism for every BUILDING_ALE_HOUSE constructed, and every other civilization would get 1 Tourism for every BUILDING_TAVERN constructed. Contrary to some conclusions drawn and discussed elsewhere on the internet (and here on CivFanatics) it does not matter how many buildings within a class give Tourism (or the other effects that will be discussed later), it only matters if the building is correct for the civilization in question.

Important Definition for Further Reference within this Guidance:

It is important to note that hereinafter whenever I refer to a civilization being "normally entitled" to a particular building within a class, or that the building is "correct for a particular civilization" , I mean by such a structuring of the Building-Class as it appears within the Database after all mods have loaded and made thier respective changes.

-----------------------------------------------------------------------------------------------------------------------------------------------------------------------

The Two Issues Involved:

There are two main issues involved in the way a Building-Class' structure will affect the way buildings within the class function in-game: "Stacking" and "Refusal".

These may seem like they are the same issue, but they are not.
  • The difference lies in that for "Stacking" issues, the 1st building from within a class that is added to a city will implement all of the effects assigned to the building via XML or SQL, but the second, third, fourth, and so on copies of the same building within the same city will not create all of the assigned effects.
  • For "Refusals", the game simply will not add any of certain kinds of effects when a building is added to a city. "Refusals" are all based on whether or not a building within a class is correct for the city-owner's civilization.
  • "Stacking" problems apply regardless of whether the building is correct for the city-owner's civilization.

-----------------------------------------------------------------------------------------------------------------------------------------------------------------------

Issues With Effect "Stacking":
  • Certain effects, most notably Tourism, will not "stack" for multiple buildings added within a city. The game simply refuses to assign the tourism effect of the 2nd+ building added to a city from within a single building-class. The inclusion of <NoLimit>true</NoLimit> within the definition of a building-class has no effect on this stacking limitation. This is the primary example of the "stacking" issue. A work-around for this limitation with regards to Tourism can be found here.
  • In discussing those building effects that are "stack-limited", a clear distinction must be drawn between those effects that stack from multiple cities having a copy of the same building, and whether the effects stack for multiple copies of the same building within the same city. For the purposes of this Guidance, we are only interested in whether or not the effects stack for multiple copies of the same building within the same city.
  • Tourism does not appear to be the only problem-effect so limited, but at the current time I do not have an exhaustive list to offer of what effects refuse to stack. The following tables, however, have been tested for the effects shown as "VERIFIED". "X" shown in the "Stacks" column of these two tables means I have not as yet had an opportunity to make a good test of the <Buildings> table for that column, or of the game-table specified. "GAME RULES AFFECTED" means that there are additional game-rules that come into play, so the effect may or may not appear to be immediate, but the effect does stack. The two tables shown are based on whether a building has these columns set with values in the <Buildings> table, whether a building has <Row> entries for it as the <BuildingType> in the various <Building_Something> tables, or whether the building's <BuildingClassType> is specified in the various <Belief_BuildingClassSomething> or <Policy_BuildingClassSomething> tables:
<Buildings> Table Columns:
Spoiler :
<Buildings> Column | Stacks | Verified by Test/Comment
<TechEnhancedTourism> | FALSE | VERIFIED
<UnmoddedHappiness> | TRUE | VERIFIED (1)
<BuildingProductionModifier> | TRUE | VERIFIED
<WonderProductionModifier> | TRUE | VERIFIED
<GreatPeopleRateChange> | X | NOT VERIFIED
<Defense> | TRUE | VERIFIED
<ExtraCityHitPoints> | TRUE | VERIFIED
<GlobalPlotCultureCostModifier> | X | NOT VERIFIED
<GlobalPlotBuyCostModifier> | X | NOT VERIFIED
<PlotCultureCostModifier> | TRUE | VERIFIED
<PlotBuyCostModifier> | TRUE | VERIFIED
<TradeRouteSeaGoldBonus> | FALSE | VERIFIED
<TradeRouteLandGoldBonus> | FALSE | VERIFIED
<TradeRouteLandDistanceModifier> | X | NOT VERIFIED
<TradeRouteSeaDistanceModifier> | X | NOT VERIFIED
<TradeRouteTargetBonus> | X | NOT VERIFIED
<TradeRouteRecipientBonus> | X | NOT VERIFIED
<CityConnectionTradeRouteModifier> | X | NOT VERIFIED
<NumTradeRouteBonus> | X | NOT VERIFIED
<EspionageModifier> | X | NOT VERIFIED
<GlobalEspionageModifier> | X | NOT VERIFIED
<ExtraSpies> | X | NOT VERIFIED
<SpyRankChange> | X | NOT VERIFIED
<InstantSpyRankChange> | X | NOT VERIFIED
<Happiness> | TRUE | GAME RULES AFFECTED (1)
<UnhappinessModifier> | TRUE | VERIFIED
<HappinessPerCity> | X | NOT VERIFIED
<HappinessPerXPolicies> | FALSE | VERIFIED (3)
<CityCountUnhappinessMod> | X | NOT VERIFIED
<MilitaryProductionModifier> | TRUE | VERIFIED
<SpaceProductionModifier> | X | NOT VERIFIED
<GlobalSpaceProductionModifier> | X | NOT VERIFIED
<GlobalGreatPeopleRateModifier> | X | NOT VERIFIED
<GreatGeneralRateModifier> | X | NOT VERIFIED
<GreatPeopleRateModifier> | X | NOT VERIFIED
<GreatPersonExpendGold> | X | NOT VERIFIED
<GreatScientistBeakerModifier> | X | NOT VERIFIED
<FreeGreatPeople> | X | NOT VERIFIED
<CultureRateModifier> | TRUE | VERIFIED
<GlobalCultureRateModifier> | X | NOT VERIFIED
<ReligiousPressureModifier> | X | NOT VERIFIED
<ExtraMissionarySpreads> | X | NOT VERIFIED
<GoldenAgeModifier> | X | NOT VERIFIED
<PolicyCostModifier> | X | NOT VERIFIED
<FreePolicies> | X | NOT VERIFIED
<UnitUpgradeCostMod> | X | NOT VERIFIED
<GlobalDefenseMod> | X | NOT VERIFIED
<MinorFriendshipChange> | X | NOT VERIFIED
<CityStateTradeRouteProductionModifier> | X | NOT VERIFIED
<LandmarksTourismPercent> | X | NOT VERIFIED
<GreatWorksTourismModifier> | X | NOT VERIFIED
<GlobalPopulationChange> | X | NOT VERIFIED
<NukeModifier> | X | NOT VERIFIED
<FoodKept> | X | NOT VERIFIED
<Gold> | TRUE | VERIFIED
<MedianTechPercentChange> | X | NOT VERIFIED
<ExtraLeagueVotes> | TRUE | VERIFIED
<FreeTechs> | TRUE | VERIFIED
<WorkerSpeedModifier> | X | NOT VERIFIED
<AirModifier> | FALSE | VERIFIED (2)
<CapturePlunderModifier> | X | NOT VERIFIED
<Experience> | X | NOT VERIFIED
(1): Negative numbers in these columns are ignored
(2): <AirModifier> will not stack regardless of how the building is defined within its class. There is no condition in which the Firaxis-supplied dll allows the effect to be implemented for any copy of the building beyond the first copy of the building within a single city
(3): Only the last building added to a city that has <HappinessPerXPolicies> will have any effect. This includes dummy or hidden buildings.​
Building-Related Tables:
Spoiler :
Buildings-Related Table | Stacks | Verified by Test/Comment
<Building_YieldChanges> | TRUE | VERIFIED
<Building_BuildingClassYieldChanges> 1 | FALSE | VERIFIED
<Building_BuildingClassHappiness> | FALSE | VERIFIED
<Policy_BuildingClassYieldChanges> | TRUE | VERIFIED
<Policy_BuildingClassCultureChanges> | TRUE | VERIFIED
<Policy_BuildingClassHappiness> | TRUE | GAME RULES AFFECTED
<Building_YieldModifiers> | TRUE | VERIFIED
<Building_GlobalYieldModifiers> | TRUE | NOT VERIFIED
<Building_AreaYieldModifiers> | TRUE | VERIFIED
<Building_HurryModifiers> | TRUE | VERIFIED
<Building_SpecialistYieldChanges> | X | NOT VERIFIED
<Building_YieldChangesPerPop> | TRUE | VERIFIED
<Building_YieldChangesPerReligion> | FALSE | VERIFIED
<Building_RiverPlotYieldChanges> | TRUE | VERIFIED
<Building_SeaPlotYieldChanges> | TRUE | VERIFIED
<Building_LakePlotYieldChanges> | TRUE | VERIFIED
<Building_SeaResourceYieldChanges> | TRUE | VERIFIED
<Building_ResourceYieldChanges> | TRUE | NOT VERIFIED
<Building_FeatureYieldChanges> | TRUE | VERIFIED
<Building_TerrainYieldChanges> | TRUE | VERIFIED
<Building_TechEnhancedYieldChanges> | X | NOT VERIFIED
<Building_FreeUnits> | TRUE | VERIFIED
<Building_DomainFreeExperiences> | TRUE | VERIFIED
<Building_UnitCombatFreeExperiences> | TRUE | VERIFIED
<Building_UnitCombatProductionModifiers> | TRUE | VERIFIED
<Building_DomainProductionModifiers> | TRUE | VERIFIED
<Building_ResourceQuantity> | TRUE | GAME RULES AFFECTED
<Belief_BuildingClassYieldChanges> 2 | FALSE | FAITH STACKS
<Belief_BuildingClassHappiness> | INDETERMINATE | NOT VERIFIED
<Belief_BuildingClassTourism> | FALSE | AS FROM RELIGIOUS ART BELIEF
<Policy_BuildingClassTourismModifiers> | FALSE | VERIFIED
<Policy_BuildingClassYieldModifiers> | TRUE | VERIFIED
  • 1some people have misunderstood -- it does in fact stack across multiple copies of the same building in different cities but it does not stack for multiple copies of the same building within the same city.
  • 2 the only "YIELD" that appears to stack is Faith. All other valid yields for the <Belief_BuildingClassYieldChanges> do not appear to stack.
  • "Stacking" effects are most commonly used with hidden or dummy buildings, and to generate unique ability effects.
  • Whether or not the building is hidden, or is a dummy, or a hidden-dummy, does not matter as regards the way the game treats "stacking" effects.
  • So far as the game's internal code is concerned regarding these effects a building is a building is a building. And a wonder is a building.


---------------------------------------------------------------------------------------------------------------------------------------------------------------------

Issues With Effects "Refusals":

Certain effects, most notably Tourism, will be "refused" by the game where a building is not correct from within a given building-class for a given civilization. The building will be accepted as a valid building by the game, but all of the effects will not be implemented within a city that is not owned by the correct civilization for that building.

<Buildings> Table Columns:
Spoiler :
<Buildings> Column | Works for Incorrect | Verified by Test/Comment
<TechEnhancedTourism> | FALSE | VERIFIED
<TradeRouteLandDistanceModifier> | FALSE | NOT VERIFIED
<TradeRouteSeaDistanceModifier> | FALSE | NOT VERIFIED
<UnmoddedHappiness> | TRUE | VERIFIED (1)
<BuildingProductionModifier> | TRUE | VERIFIED
<WonderProductionModifier> | TRUE | VERIFIED
<GreatPeopleRateChange> | X | NOT VERIFIED
<Defense> | TRUE | VERIFIED
<ExtraCityHitPoints> | TRUE | VERIFIED
<GlobalPlotCultureCostModifier> | X | NOT VERIFIED
<GlobalPlotBuyCostModifier> | X | NOT VERIFIED
<PlotCultureCostModifier> | TRUE | VERIFIED
<PlotBuyCostModifier> | TRUE | VERIFIED
<TradeRouteSeaGoldBonus> | X | NOT VERIFIED
<TradeRouteLandGoldBonus> | X | NOT VERIFIED
<TradeRouteTargetBonus> | X | NOT VERIFIED
<TradeRouteRecipientBonus> | X | NOT VERIFIED
<CityConnectionTradeRouteModifier> | X | NOT VERIFIED
<NumTradeRouteBonus> | X | NOT VERIFIED
<EspionageModifier> | X | NOT VERIFIED
<GlobalEspionageModifier> | X | NOT VERIFIED
<ExtraSpies> | X | NOT VERIFIED
<SpyRankChange> | X | NOT VERIFIED
<InstantSpyRankChange> | X | NOT VERIFIED
<Happiness> | TRUE | GAME RULES AFFECTED (1)
<UnhappinessModifier> | X | NOT VERIFIED
<HappinessPerCity> | X | NOT VERIFIED
<CityCountUnhappinessMod> | X | NOT VERIFIED
<MilitaryProductionModifier> | TRUE | VERIFIED
<SpaceProductionModifier> | X | NOT VERIFIED
<GlobalSpaceProductionModifier> | X | NOT VERIFIED
<GlobalGreatPeopleRateModifier> | X | NOT VERIFIED
<GreatGeneralRateModifier> | X | NOT VERIFIED
<GreatPeopleRateModifier> | X | NOT VERIFIED
<GreatPersonExpendGold> | X | NOT VERIFIED
<GreatScientistBeakerModifier> | X | NOT VERIFIED
<FreeGreatPeople> | X | NOT VERIFIED
<CultureRateModifier> | TRUE | VERIFIED
<GlobalCultureRateModifier> | X | NOT VERIFIED
<ReligiousPressureModifier> | X | NOT VERIFIED
<ExtraMissionarySpreads> | X | NOT VERIFIED
<GoldenAgeModifier> | X | NOT VERIFIED
<PolicyCostModifier> | X | NOT VERIFIED
<FreePolicies> | X | NOT VERIFIED
<UnitUpgradeCostMod> | X | NOT VERIFIED
<GlobalDefenseMod> | X | NOT VERIFIED
<MinorFriendshipChange> | X | NOT VERIFIED
<CityStateTradeRouteProductionModifier> | X | NOT VERIFIED
<LandmarksTourismPercent> | X | NOT VERIFIED
<GreatWorksTourismModifier> | X | NOT VERIFIED
<GlobalPopulationChange> | X | NOT VERIFIED
<NukeModifier> | X | NOT VERIFIED
<FoodKept> | X | NOT VERIFIED
<Gold> | TRUE | VERIFIED
<MedianTechPercentChange> | X | NOT VERIFIED
<ExtraLeagueVotes> | X | NOT VERIFIED
<FreeTechs> | TRUE | VERIFIED
<WorkerSpeedModifier> | X | NOT VERIFIED
<AirModifier> | X | NOT VERIFIED
<CapturePlunderModifier> | X | NOT VERIFIED
<Experience> | X | NOT VERIFIED
(1): Negative numbers in these columns are ignored​
Building-Related Tables:
Spoiler :
Buildings-Related Table | Works for Incorrect | Verified by Test/Comment
<Building_BuildingClassYieldChanges> | TRUE | VERIFIED
<Building_BuildingClassHappiness> | FALSE | VERIFIED
<Building_YieldChanges> | TRUE | VERIFIED
<Building_YieldModifiers> | TRUE | VERIFIED
<Building_GlobalYieldModifiers> | TRUE | VERIFIED
<Building_AreaYieldModifiers> | TRUE | VERIFIED
<Building_HurryModifiers> | TRUE | VERIFIED
<Building_SpecialistYieldChanges> | X | NOT VERIFIED
<Building_YieldChangesPerPop> | TRUE | VERIFIED
<Building_YieldChangesPerReligion> | TRUE | NOT VERIFIED
<Building_RiverPlotYieldChanges> | TRUE | VERIFIED
<Building_SeaPlotYieldChanges> | TRUE | VERIFIED
<Building_LakePlotYieldChanges> | TRUE | NOT VERIFIED
<Building_SeaResourceYieldChanges> | TRUE | NOT VERIFIED
<Building_ResourceYieldChanges> | TRUE | VERIFIED
<Building_FeatureYieldChanges> | TRUE | VERIFIED
<Building_TerrainYieldChanges> | TRUE | VERIFIED
<Building_TechEnhancedYieldChanges> | X | NOT VERIFIED
<Building_FreeUnits> | TRUE | VERIFIED
<Building_DomainFreeExperiences> | TRUE | VERIFIED
<Building_UnitCombatFreeExperiences> | TRUE | VERIFIED
<Building_UnitCombatProductionModifiers> | TRUE | VERIFIED
<Building_DomainProductionModifiers> | TRUE | VERIFIED
<Building_ResourceQuantity> | TRUE | VERIFIED
<Policy_BuildingClassTourismModifiers> | FALSE | VERIFIED
<Policy_BuildingClassYieldModifiers> | FALSE | VERIFIED
<Policy_BuildingClassYieldChanges> | FALSE | VERIFIED
<Policy_BuildingClassCultureChanges> | FALSE | VERIFIED
<Belief_BuildingClassYieldChanges> | FALSE | VERIFIED
<Belief_BuildingClassHappiness> | FALSE | VERIFIED
<Belief_BuildingClassTourism> | FALSE | Shows 0 from RELIGIOUS ART belief
 
Last edited:
Structuring of <BuildingClasses> with Reference to the Issues of "Stacking" and "Refusal" as Previously Covered:

The issues touched upon earlier with regard to "stacking" and "refusal" effects previously noted apply whether or not a building-class contains only dummy, hidden, or "normal" buildings. These issues apply as much to the game's pre-existing building-classes (such as the Castle Class of Buildings) as they do to any new class of buildings added to the game. This should be borne in mind in the following discussion of building-class structuring, which will generally take a form of discussing a building-class that is made up of dummy or hidden buildings, since these are so commonly used by mod-creators.

Assume for purposes of discussion that I am adding a new Class of Buildings to the game called BUILDINGCLASS_DUMMY, that the default building will be BUILDING_BASIC_DUMMY, and that I have added this new class with the following code as shown in XML:
Code:
<BuildingClasses>
	<Row>
		<Type>BUILDINGCLASS_DUMMY</Type>
		<DefaultBuilding>BUILDING_BASIC_DUMMY</DefaultBuilding>
		<Description>TXT_KEY_BUILDING_BASIC_DUMMY</Description>
		<NoLimit>true</NoLimit>
	</Row>
</BuildingClasses>
I choose not to bury the reader with piles of code to decipher, so assume that I also add a <Buildings> table (and any related required tables) to have several dummy or hidden buildings inserted into this new class of buildings called BUILDINGCLASS_DUMMY, so that if I chart what each of these buildings within the BUILDINGCLASS_DUMMY do in-game, I would have the following:

Building | Effects
BUILDING_BASIC_DUMMY | +1 Gold
BUILDING_TOURISM_DUMMY | +1 Tourism
BUILDING_FAITH_DUMMY | +1 Faith
BUILDING_FOOD_DUMMY | +1 Food
BUILDING_HAPPINESS_DUMMY | +2 "regular" happiness
BUILDING_POLICY_LIBERTY_DUMMY | +1 Culture if the player adopts the Liberty policy branch
BUILDING_BELIEF_INITIATION_RITES_DUMMY | +1 Faith if the Player chooses Inititation Rites

An examination of this chart with reference back to the previous tables showing which affects cannot stack, and which affects are not implemented by the game for buildings that are not correct from within a building-class for a particular city's owner should highlight several problems in getting all of these dummies to work properly, even when "forced" upon a city via an lua method for placing buildings into cities. A (not necessarily complete) listing of these issues is:
  1. BUILDING_TOURISM_DUMMY will not only not "stack", it will have no effect whatsoever.
    • It is not the default building within the class, and I have not made a <Civilization_BuildingClassOverrides> table to make it the unique within this class for any civilization, so BUILDING_TOURISM_DUMMY will be a completely useless building.
    • The fact that it might be hidden using the <GreatWorkCount>-1</GreatWorkCount> method does not affect the uselessness of this building one way or the other. It is the placing of this building within its building-class that makes it a useless building.
  2. BUILDING_POLICY_LIBERTY_DUMMY and BUILDING_BELIEF_INITIATION_RITES_DUMMY will also have no effect because the relevant tables are <Policy_BuildingClassCultureChanges> and <Belief_BuildingClassYieldChanges> repectively.
    • Since <Policy_BuildingClassCultureChanges> and <Belief_BuildingClassYieldChanges> are designated in terms of <BuildingClassType> the game would default to making these effects apply to BUILDING_BASIC_DUMMY, and would not apply them to either BUILDING_POLICY_LIBERTY_DUMMY and BUILDING_BELIEF_INITIATION_RITES_DUMMY.
    • Since most dummy or hidden buildings are added to cities via lua programs, and the effects would be applied to BUILDING_BASIC_DUMMY, the end result of a player adopting the Liberty Policy Branch or the Initiation Rites Belief might be wildly different than intended.
  3. Only BUILDING_BASIC_DUMMY, BUILDING_FAITH_DUMMY, BUILDING_FOOD_DUMMY, and BUILDING_HAPPINESS_DUMMY will be completely successful in terms of adding multiple copies of the building within the same city.
    • BUILDING_HAPPINESS_DUMMY will be dependant on city population, especially if multiple copies of it are added to the same city.
One solution alluded to earlier might seem to be to add a <Civilization_BuildingClassOverrides> table to the XML that will make BUILDING_TOURISM_DUMMY the correct building within the class for the desired civilization. But this is not an actual solution due to the following:
  1. While this would certainly allow the BUILDING_TOURISM_DUMMY to operate correctly in all cases, it merely shifts the issues related to the correct building within the class from BUILDING_BASIC_DUMMY to BUILDING_TOURISM_DUMMY.
  2. Does not in fact get around the stacking issues with relation to tourism for multiple copies of the same building within the same city.


-----------------------------------------------------------------------------------------------------------------------------------------------------------------------


Solution to the Issues Related to Structuring of <BuildingClasses> with Reference to the Issues of "Stacking" and "Refusal" as Previously Covered:

The only real solution to most of the "stacking" asnd "refusal" issues previously discussed is to assign every hidden or dummy building to its own independant building-class. For issues such as the "stacking" of Tourism, the only real solution is the one found by UltimatePotatoe.

Instead of inserting the BUILDING_POLICY_LIBERTY_DUMMY into a larger building-class with other dummy and/or hidden buildings, I would ctreate its own building-class, and structure <BuildingClass>, <Buildings>, <Policy_BuildingClassCultureChanges>, and <Language_en_US> as follows:
Spoiler :
Code:
<GameData>
	<Language_en_US>
		<Row Tag="TXT_KEY_BUILDING_POLICY_LIBERTY_DUMMY">
			<Text>Liberty Extra Culture</Text>
		</Row>
	</Language_en_US>

	<Buildings>
		<Row>
			<Type>BUILDING_POLICY_LIBERTY_DUMMY</Type>
			<BuildingClass>BUILDINGCLASS_POLICY_LIBERTY_DUMMY</BuildingClass>
			<Cost>-1</Cost>
			<FaithCost>-1</FaithCost>
			<PrereqTech>NULL</PrereqTech>
			<GreatWorkCount>-1</GreatWorkCount>
			<MinAreaSize>-1</MinAreaSize>
			<NeverCapture>true</NeverCapture>
			<IconAtlas>BW_ATLAS_1</IconAtlas>
			<PortraitIndex>19</PortraitIndex>
			<Description>TXT_KEY_BUILDING_POLICY_LIBERTY_DUMMY</Description>
		</Row>
	</Buildings>

	<BuildingClasses>
		<Row>
			<Type>BUILDINGCLASS_POLICY_LIBERTY_DUMMY</Type>
			<DefaultBuilding>BUILDING_POLICY_LIBERTY_DUMMY</DefaultBuilding>
			<Description>TXT_KEY_BUILDING_POLICY_LIBERTY_DUMMY</Description>
			<NoLimit>true</NoLimit>
		</Row>
	</BuildingClasses>

	<Policy_BuildingClassCultureChanges>
		<Row>
			<PolicyType>POLICY_LIBERTY</PolicyType>
			<BuildingClassType>BUILDINGCLASS_POLICY_LIBERTY_DUMMY</BuildingClassType>
			<CultureChange>1</CultureChange>
		</Row>
	</Policy_BuildingClassCultureChanges>
</GameData>
  • If I assign such a building to every city of CIVILIZATION_X through a <Traits> table <FreeBuilding> column, then when a player playing as CIVILIZATION_X adopts the Liberty Policy Branch, they would get +2 Culture in every city instead of the usual +1 Culture per city.
  • If I instead assign multiple copies of the same BUILDING_POLICY_LIBERTY_DUMMY to the same city via some lua method, and based on meeting certain other conditions I might determine are necessary before each of these copies is added to the same city, then for every copy of the building in every city owned by CIVILIZATION_X an increase in culture of +1 will occur so long as the player has adopted the Liberty Policy Branch.

[side notes]You should always include both a valid <Description> tag and a valid <IconAtlas> & <PortraitIndex> specification. Inclusion of these will not affect the hidden-building method.
  • The <Description> tag should be included because for certain effects the game will look for the <Description> tag for all valid buildings with such effects, and if it fails to find a <Description> tag, will result in game-fatal results (such as locking the Espionage Spy-Assignment pop-up where an <EspionageModifier> has been included in a building that lacks a <Description> tag).
  • <IconAtlas> & <PortraitIndex> specifications should be included because the civilopedia opener-page for buildings randomly selects an icon to display from the list of valid registered buildings, even those that are hidden. If a hidden or dummy building lacks a valid set of Icon Specifications this will cause the ugly "no icon" icon to be displayed. You will then be plagued by meaningless bug reports from users of your mod.

------------------------------------------------------------------------------------------------------------------------------------------------------------------------

Guidance on <Buildings> Table Structure for Dummy and Hidden Buildings

Introduction: <Buildings> Table and <BuildingClass> table Structuring for Dummy and Hidden Buildings

  • Often, dummy buildings are used for no more complex purpose than as markers that can be added to cities and then later "checked-for" in an lua program. If a city has a specific dummy building, then the lua program will take certain actions as defined by the maker of the mod. If the dummy is not present, the action is not taken, or an alternative set of actions are taken by the lua program.
  • Dummy buildings are often also used directly to create a Civilization's Unique Ability effects not normally accessible within the <Traits> table, or those secondary tables that rely on the <Traits> primary table. In such cases (at least for BNW) the dummy building can be hidden, and usually is.
  • As mentioned earlier, a dummy building does not have to be hidden in order to accomplish the desired result. But with BNW it is more "seamless" from the point-of-view of the mod-user to hide the building so that it does not show in the city display.
  • In order to make a dummy building, nothing special is required in terms of XML/SQL. To hide it for BNW, nothing especially dramatic in terms of XML/SQL code is required either.

Creating a Dummy Building

Usually, when you add a building to the game, you need to have a default building, and any buildings that are given only to a specific civilization are in addition to that default building. In the case of hidden buildings this strategy for adding the building and its class to the game is neither necessary or desired. It is better to simply create only the building that will be given via a Leader Trait, or through LUA or some other method of "handing-out" the building, and to set that building as the default for the building class. So, at the minimum, you need to add the dummy building to the <Buildings> table, and you need to add the CLASS of the building to the <BuildingClasses> table.

(1) Create the Building Class

To add the BuildingClass, you need a <BuildingClasses> table within your XML/SQL, such as the following example where a simple "marker" building will be created:
Code:
<BuildingClasses>
	<Row>
		<Type>BUILDINGCLASS_MARKER_LRS</Type>
		<DefaultBuilding>BUILDING_MARKER_LRS</DefaultBuilding>
		<Description>TXT_KEY_BUILDING_MARKER_LRS</Description>
	</Row>
</BuildingClasses>
  • Note that the name of the BuildingClass for the marker is BUILDINGCLASS_MARKER_LRS as opposed to just BUILDINGCLASS_MARKER. This is because there is a fairly high probability that some other mod-maker will use a name such as BUILDINGCLASS_MARKER, and two such exactly-duplicative names will cause mod-conflict issues, whereas a name such as BUILDINGCLASS_MARKER_LRS is much less likely to result in such conflicts. I learned this precautionary trick from JFD, and it is a good one to follow.
  • Note that <NoLimit>true</NoLimit> is not included in this Building-Class since it would only be ever added as a marker, rather than use to give additive effects when multiple copies of the building are added to a single city.
  • The default building specified will be the marker building, and as with the Building-Class name, BUILDING_MARKER_LRS has been used instead of just BUILDING_MARKER.
  • Always include a <Description> tag, and make it the same as the one you will use for the dummy building within the <Buildings> table. As noted earlier, omission of the <Description> tag is a bad habit to get into.
(2) Create the Building

To create the dummy building, you use the <Buildings> table just as if you were creating a "real" building, but in the case of dummy buildings less information is required than normal:
Code:
<Buildings>
	<Row>
		<Type>BUILDING_MARKER_LRS</Type>
		<BuildingClass>BUILDINGCLASS_MARKER_LRS</BuildingClass>
		<Cost>-1</Cost>
		<PrereqTech>NULL</PrereqTech>
		<MinAreaSize>-1</MinAreaSize>
		<NeverCapture>true</NeverCapture>
		<NukeImmune>true</NukeImmune>
		<PortraitIndex>19</PortraitIndex>
		<IconAtlas>BW_ATLAS_1</IconAtlas>
		<Description>TXT_KEY_BUILDING_MARKER_LRS</Description>
	</Row>
</Buildings>
  • The use of <Cost>-1</Cost> makes the building unbuildable. Theoretically, since the building is the default one within its class, every civilization should be able to build BUILDING_MARKER_LRS in any city, but the setting of the <Cost> in this way forbids any player from constructing or buying the building.
  • The use of <PrereqTech>NULL</PrereqTech> removes the building from showing in the tech tree.
  • The use of <NeverCapture>true</NeverCapture> ensures that the building cannot be captured if the city is conquered by an enemy.
  • The use of <NukeImmune>true</NukeImmune> ensures that the marker building will survive a nuke attack on the city by an enemy.
  • <IconAtlas> & <PortraitIndex> specifications should be included because the civilopedia opener-page for buildings randomly selects an icon to display from the list of valid registered buildings, even those that are hidden. If a hidden or dummy building lacks a valid set of Icon Specifications this will cause the ugly "no icon" icon to be displayed. You will then be plagued by meaningless bug reports from users of your mod. The two settings I have used will make the Palace icon be used for the building.
  • Always include a <Description> tag. As noted earlier, omission of the <Description> tag is a bad habit to get into.
  • As structured this building will not be hidden. It will show in the city view as a building belonging to the city, but it won't have any effects.

(3) Define the Text to be Displayed for the <Description> tag

You need to follow through and actually give the game an in-game text-string to use for the <Description> tag, as like this:
Code:
<Language_en_US>
	<Row Tag="TXT_KEY_BUILDING_MARKER_LRS">
		<Text>LeeS Marker</Text>
	</Row>
</Language_en_US>

(4) The Finished XML for the Marker Building

The complete finished code for the dummy marker building would be as follows:
Spoiler :
Code:
<GameData>
	<BuildingClasses>
		<Row>
			<Type>BUILDINGCLASS_MARKER_LRS</Type>
			<DefaultBuilding>BUILDING_MARKER_LRS</DefaultBuilding>
			<Description>TXT_KEY_BUILDING_MARKER_LRS</Description>
		</Row>
	</BuildingClasses>
	<Buildings>
		<Row>
			<Type>BUILDING_MARKER_LRS</Type>
			<BuildingClass>BUILDINGCLASS_MARKER_LRS</BuildingClass>
			<Cost>-1</Cost>
			<PrereqTech>NULL</PrereqTech>
			<MinAreaSize>-1</MinAreaSize>
			<NeverCapture>true</NeverCapture>
			<NukeImmune>true</NukeImmune>
			<PortraitIndex>19</PortraitIndex>
			<IconAtlas>BW_ATLAS_1</IconAtlas>
			<Description>TXT_KEY_BUILDING_MARKER_LRS</Description>
		</Row>
	</Buildings>
	<Language_en_US>
		<Row Tag="TXT_KEY_BUILDING_MARKER_LRS">
			<Text>LeeS Marker</Text>
		</Row>
	</Language_en_US>
</GameData>

  • As shown, the marker doesn't really do anything. This is intentional, because in the case of a marker this is very often what we want.
  • The building is not hidden, it would show in the city view. For G&K and Vanilla, this will be the case for dummy buildings, without relying on methods involving somewhat more complicated lua or dll code-gymnastics.
  • <FaithCost>-1</FaithCost> is not shown even though it is generally included in a dummy building for G&K. The reason is that Vanilla has no such column as <FaithCost>.

(5) Hiding the Building for BNW:

  • In order to hide the building for BNW, it is only necessary to add a couple of lines of code to the definition of the building within the <Buildings> table:
Spoiler :
Code:
<GameData>
	<BuildingClasses>
		<Row>
			<Type>BUILDINGCLASS_MARKER_LRS</Type>
			<DefaultBuilding>BUILDING_MARKER_LRS</DefaultBuilding>
			<Description>TXT_KEY_BUILDING_MARKER_LRS</Description>
		</Row>
	</BuildingClasses>
	<Buildings>
		<Row>
			<Type>BUILDING_MARKER_LRS</Type>
			<BuildingClass>BUILDINGCLASS_MARKER_LRS</BuildingClass>
			<Cost>-1</Cost>
			<PrereqTech>NULL</PrereqTech>
			[COLOR="Blue"]<GreatWorkCount>-1</GreatWorkCount>
			<FaithCost>-1</FaithCost>[/COLOR]
			<MinAreaSize>-1</MinAreaSize>
			<NeverCapture>true</NeverCapture>
			<NukeImmune>true</NukeImmune>
			<PortraitIndex>19</PortraitIndex>
			<IconAtlas>BW_ATLAS_1</IconAtlas>
			<Description>TXT_KEY_BUILDING_MARKER_LRS</Description>
		</Row>
	</Buildings>
	<Language_en_US>
		<Row Tag="TXT_KEY_BUILDING_MARKER_LRS">
			<Text>LeeS Marker</Text>
		</Row>
	</Language_en_US>
</GameData>
  • Again, the marker doesn't really do anything. Nothing in what was done between the Vanilla/G&K dummy and the BNW hidden building has changed in terms of the building's use: it is still just intended as a marker for easement of LUA programming methods.
  • The building is now hidden, and requires BNW. The inclusion of <GreatWorkCount>-1</GreatWorkCount> hides the building in the city view.
  • <FaithCost>-1</FaithCost> is generally included in a hidden building for BNW, although it is not really necessary.
  • Even though they now will not show anywhere, the same reasons as given earlier for including <PortraitIndex>, <IconAtlas>, and <Description> still apply.


AUTHOR'S NOTE: More to come, I just haven't finished writing it yet.
 
Last edited:
Hooking-Up a Dummy Building Via an LUA method

The most common method for adding dummy buildings into cities is to do what can be called a "hook-up" to an event that runs every turn for all players, human and AI. Then, when certain conditions are met, the lua program adds the dummy building to a specific city (usually a player's capital for convenience) or to any and all cities where the required conditions are met.

I am going to use a recent mod I made and offered on Steam as an example. In this mod, called "OP Human Players", I add a variety of effects to make the human player in a single-player game outrageously over-powered. It's not a "seriously-serious" mod in any sense, but it functions properly and is a handy example of using a dummy building. I have more than one dummy building operating in "OP Human Players", but for the sake of simplicity I have removed all but one of them from the lua code I will show.

The XML for the building was done in two parts, to give compatibility to both Gods & Kings and Brave New World. The first part was the basic definition of the dummy building, its building-class, and the language description-tag info. The dummy building adds +5 Unmodded Happiness to the empire for each copy of the dummy building added to the empire's capital city.
Spoiler OP_Buildings.xml :
Code:
<GameData>
	<Buildings>
		<!-- Happiness Dummy -->
		<Row>
			<Type>BUILDING_HAPPINESS_DUMMY_LRS</Type>
			<BuildingClass>BUILDINGCLASS_HAPPINESS_DUMMY_LRS</BuildingClass>
			<Cost>-1</Cost>
			<FaithCost>-1</FaithCost>
			<PrereqTech>NULL</PrereqTech>
			<ArtDefineTag>NONE</ArtDefineTag>
			<MinAreaSize>-1</MinAreaSize>
			<NeverCapture>true</NeverCapture>
			<HurryCostModifier>-1</HurryCostModifier>
			<UnmoddedHappiness>5</UnmoddedHappiness>
			<IconAtlas>BW_ATLAS_1</IconAtlas>
			<PortraitIndex>19</PortraitIndex>
			<Description>TXT_KEY_HAPPINESS_DUMMY_LRS</Description>
		</Row>
	</Buildings>

	<BuildingClasses>
		<Row>
			<Type>BUILDINGCLASS_HAPPINESS_DUMMY_LRS</Type>
			<DefaultBuilding>BUILDING_HAPPINESS_DUMMY_LRS</DefaultBuilding>
			<Description>TXT_KEY_HAPPINESS_DUMMY_LRS</Description>
			<NoLimit>true</NoLimit>
		</Row>
	</BuildingClasses>

	<Language_en_US>
		<Row Tag="TXT_KEY_HAPPINESS_DUMMY_LRS">
			<Text>Happiness Dummy</Text>
		</Row>
	</Language_en_US>
</GameData>
Then in a second file, that is added to the database after the previous code, I added an update to this basic definition to "hide" the buildings from view for BNW. This update succeeds for BNW, but is rejected when a user only has G&K:
Spoiler BNW_Updates.xml :
Code:
<GameData>
	<Buildings>
		<!-- Happiness Dummy -->
		<Update>
			<Where Type="BUILDING_HAPPINESS_DUMMY_LRS" />
			<Set>
				<GreatWorkCount>-1</GreatWorkCount>
			</Set>
		</Update>
	</Buildings>
</GameData>
My ModBuddy "Actions" tab therefore looks like this:

Spoiler :


I then need the actual LUA function that will run every turn. But 1st I have some preliminary code I generally include when writing functions like these. And also, before I can write the code I need to add an lua file to the mod in ModBuddy. And it needs to be specified as an InGameUIAddin under the "Content" tab of ModBuddy, so it should look like this:

Spoiler :


The actual code I start with in the lua file OP_Units.lua is as follows. Note that I have added line numbers that would not normally be included, shown in red:
Code:
[COLOR="Red"]01)[/COLOR]	gHappyDummy = GameInfoTypes.BUILDING_HAPPINESS_DUMMY_LRS
[COLOR="red"]02)[/COLOR]	gHappyFloor = 1
[COLOR="red"]03)[/COLOR]	gHappyRoof = 15
  • Line 01) creates a variable within the lua program called gHappyDummy and grabs the building ID# from the <Buildings> table for BUILDING_HAPPINESS_DUMMY_LRS. I find it easier to code this way by first grabbing the ID# of any element within the game's database that I am going to use before doing anything else in my lua programs. Also, as I understand it, this speeds the execution of the lua program somewhat since the game only has to do the look-up once instead of multiple times.
  • Line 02) creates a variable within the lua program called gHappyFloor and assigns it an integer value of "1". Later on in the code of the lua I will use this as a target value for the human player's happiness "score". A Happiness score of "1" is the least acceptable before the lua program will take action and add an additional happiness dummy building to the human player's capital city.
  • Line 03) creates a variable within the lua program called gHappyRoof and assigns it an integer value of "15". If the human player's happiness "score" exceeds 15 positive happiness, the lua will look to see if there are any happiness dummy buildings in the human player's capital city, and if so, will eliminate one of those happiness buildings.
Now I make the actual function that will perform the desired actions, and again I have added line numbers in red that would not normally be included:
Code:
[COLOR="Red"]01)[/COLOR]	GameEvents.PlayerDoTurn.Add(function(iPlayer)
[COLOR="red"]02)[/COLOR]	local pPlayer = Players[iPlayer]
[COLOR="red"]03)[/COLOR]	if not pPlayer:IsHuman() then return end
[COLOR="red"]04)[/COLOR]		local iPlayerHappiness = pPlayer:GetExcessHappiness()
[COLOR="red"]05)[/COLOR]		local pCapitalCity = pPlayer:GetCapitalCity()

[COLOR="red"]06)[/COLOR]		local iNumCapitalHappyBuildings = 0
[COLOR="red"]07)[/COLOR]		if pCapitalCity:IsHasBuilding(gHappyDummy) then
[COLOR="red"]08)[/COLOR]			iNumCapitalHappyBuildings = pCapitalCity:GetNumRealBuilding(gHappyDummy)
[COLOR="red"]09)[/COLOR]		end

[COLOR="red"]10)[/COLOR]		if iPlayerHappiness < gHappyFloor then
[COLOR="red"]11)[/COLOR]			pCapitalCity:SetNumRealBuilding(gHappyDummy, iNumCapitalHappyBuildings + 1)
[COLOR="red"]12)[/COLOR]			print("adding 1 happy building")
[COLOR="red"]13)[/COLOR]		else 
[COLOR="red"]14)[/COLOR]			if iPlayerHappiness > gHappyRoof then
[COLOR="red"]15)[/COLOR]				if iNumCapitalHappyBuildings > 0 then
[COLOR="red"]16)[/COLOR]					pCapitalCity:SetNumRealBuilding(gHappyDummy, iNumCapitalHappyBuildings - 1)
[COLOR="red"]17)[/COLOR]					print("subtracting 1 happy building")
[COLOR="red"]18)[/COLOR]				end
[COLOR="red"]19)[/COLOR]			else print("not addjusting number happy building")
[COLOR="red"]20)[/COLOR]			end
[COLOR="red"]21)[/COLOR]		end
[COLOR="red"]22)[/COLOR]	end)
  • Line Number 01) Tells the game to add a new lua function to those that run on the GameEvents.PlayerDoTurn event. Essentially, this tells the game to run the added function during turn processing for every player, human, AI, City-State, or Barbarian.
  • Line Number 02) creates a local variable called pPlayer and sets it to the current player's ID # from the lua table called Players. The iPlayer info was passed automatically by the game to the GameEvents.PlayerDoTurn. This game event PlayerDoTurn runs once-per-turn for all valid players in the game, so by "current player", is meant the player the game is processing commands for at the time it runs through the lua program. At one point in the "turn", this will be for the human player, at another point during the same turn, this will be for Barbarians, and at other points during the same turn this will be for City-States and Adversary AI players.
  • Line Number 03) looks to see whether the current player the lua is running for is the human player. If not, it ends the rest of the function. This not only keeps the rest of the lua from running for any except the human player, it also saves processing time between turns by returning back out of the function at the earliest possible time.
  • Line Number 04) creates a local variable called iPlayerHappiness and sets it to the human player's "ExcessHappiness" happiness amount. This will be an integer value, and will be the same (positive, 0, or negative) as is showing on the game's top panel display for the player's current happiness "score".
  • Line Number 05) creates a local variable called pCapitalCity and sets it to the city ID info for the human player's capital city. Often you will want to add dummy buildings to a player's capital city, and this is an easy method to "get" the reference info the game needs for the player's capital.
  • Line Number 06) creates a local variable called iNumCapitalHappyBuildings and sets it to 0, as a default value for this local variable.
  • Line Number 07) starts a conditional-check lua programming block, so that line number 08) only runs if the human player's capital city has at least one copy of the happiness dummy building.
  • Line Number 08) resets the integer value of local variable iNumCapitalHappyBuildings to however many are present in the human player's capital city.
  • Line Number 09) end the conditional-check lua programming block started in line number 07).
  • Line Number 10) starts a conditional-check lua programming block, so that line numbers 11) & 12) only run if the player's current happiness score is less than the limit value originally specified for the variable gHappyFloor.
  • Line Number 11) sets the number of gHappyDummy buildings in the human player's capital city equal to the previous number detected plus one more happiness dummy building. Remember that variable gHappyDummy was previously set to the ID# from the <Buildings> table for the happiness dummy building BUILDING_HAPPINESS_DUMMY_LRS. This line is, in essence, the "meat" of how you add dummy buildings to cities using lua.
  • Line Number 12) merely prints a confirmation note into the lua.log file that a happiness dummy building was added to the human player's capital city.
  • Line Number 13) "else" is used to give the lua something literally "else" it can do when the condition in the original "if" line (number 10)) was not met. It is used as an "entry-point" or "jump-point" for the lua program to move to when the original condition was not met.
  • Line Number 14) starts a new conditional-check lua programming block to be executed when the original condition in line number 10) was not met. In this case, the condition needed to run lines 15) to 18) is for the human player's happiness score to be greater than the pre-defined limit stored in variable gHappyRoof.
  • Line Number 15) starts a new conditional-check lua programming block to be executed when the number of Happiness Dummy Buildings in the human player's capital city is greater than "0". Lines 16) & 17) will only run if both of the following conditions are met: (a) the human player's happiness score is greater than 15, and (b), there are Happiness Dummy Buildings in the human player's capital city.
  • Line Number 16) reduces the number of Happiness Dummy Buildings in the human player's capital city by one building.
  • Line Number 17) prints a confirmation to the lua.log that one happiness dummy building was subtracted from the human player's capital city.
  • Line Number 18) terminates the conditional-check lua programming block started on line number 15).
  • Line Number 19) prints a confirmation to the lua.log that no action was taken as regards adjusting the number of happiness dummy buildings in the human player's capital city. The only way the lua can reach this line is if no action was taken to either add or subtract happiness dummy buildings.
  • Line Number 20) terminates the conditional-check lua programming block started on line number 14).
  • Line Number 21) terminates the conditional-check lua programming block started on line number 10).
  • Line Number 22) terminates the function.
The whole lua file, without the line numbers, looks like this, as one unified piece of code:
Spoiler the whole lua :
Code:
gHappyDummy = GameInfoTypes.BUILDING_HAPPINESS_DUMMY_LRS
gHappyFloor = 1
gHappyRoof = 15

GameEvents.PlayerDoTurn.Add(function(iPlayer)
local pPlayer = Players[iPlayer]
if not pPlayer:IsHuman() then return end
	local iPlayerHappiness = pPlayer:GetExcessHappiness()
	local pCapitalCity = pPlayer:GetCapitalCity()

	local iNumCapitalHappyBuildings = 0
	if pCapitalCity:IsHasBuilding(gHappyDummy) then
		iNumCapitalHappyBuildings = pCapitalCity:GetNumRealBuilding(gHappyDummy)
	end

	if iPlayerHappiness < gHappyFloor then
		pCapitalCity:SetNumRealBuilding(gHappyDummy, iNumCapitalHappyBuildings + 1)
		print("adding 1 happy building")
	else 
		if iPlayerHappiness > gHappyRoof then
			if iNumCapitalHappyBuildings > 0 then
				pCapitalCity:SetNumRealBuilding(gHappyDummy, iNumCapitalHappyBuildings - 1)
				print("subtracting 1 happy building")
			end
		else print("not addjusting number happy building")
		end
	end
end)
 

Attachments

  • actions_tab.jpg
    actions_tab.jpg
    78.7 KB · Views: 4,319
  • Content_Tab.jpg
    Content_Tab.jpg
    109.1 KB · Views: 4,450
Compatibility Issues Between Expansion Levels

There are several building-related issues for compatibility between Vanilla, Gods&Kings, and BNW. These are not primarily dummy-building issues, but they do affect compatibility for dummy buildings. The info presented here for compatibility for the three expansion levels affect "normal" buildings as much as they do dummy or hidden buildings.

Spoiler <Buildings> table compatibilities :

Buildings Column | Expansion(s)
Culture | Vanilla only*
DiplomaticVoting | Vanilla and G&K
TradeRouteModifier | Vanilla and G&K
VictoryPrereq | Vanilla and G&K
AffectSpiesNow | G&K and BNW
Espionage | G&K and BNW
EspionageModifier | G&K and BNW
GlobalEspionageModifier | G&K and BNW
ExtraSpies | G&K and BNW
SpyRankChange | G&K and BNW
InstantSpyRankChange | G&K and BNW
FaithCost | G&K and BNW
UnlockedByBelief | G&K and BNW
HolyCity | G&K and BNW
ExtraMissionarySpreads | G&K and BNW
ReligiousPressureModifier | G&K and BNW
ThemingBonusHelp | BNW only
NullifyInfluenceModifier | BNW only
UnlockedByLeague | BNW only
CityConnectionTradeRouteModifier | BNW only
CityConnectionTradeRouteModifier | replaces TradeRouteModifier
AllowsFoodTradeRoutes | BNW only
AllowsProductionTradeRoutes | BNW only
TradeRouteRecipientBonus | BNW only
TradeRouteTargetBonus | BNW only
NumTradeRouteBonus | BNW only
LandmarksTourismPercent | BNW only
InstantMilitaryIncrease | BNW only
GreatWorksTourismModifier | BNW only
XBuiltTriggersIdeologyChoice | BNW only
TradeRouteSeaDistanceModifier | BNW only
TradeRouteSeaGoldBonus | BNW only
TradeRouteLandDistanceModifier | BNW only
TradeRouteLandGoldBonus | BNW only
CityStateTradeRouteProductionModifier | BNW only
GreatScientistBeakerModifier | BNW only
TechEnhancedTourism | BNW only
PolicyBranchType | BNW only
GreatWorkSlotType | BNW only
FreeGreatWork | BNW only
GreatWorkCount | BNW only
ExtraLeagueVotes | BNW only
* The <Culture> column is completely removed from G&K and BNW, and will cause file-discard if included in a G&K and BNW building. To add a Culture yield to a building in G&K and BNW, <Building_YieldChanges> is used with a YIELD_CULTURE.

Spoiler Building-Related Game-Table Expansion Compatibilities :

Building-Related Table | Expansion(s)
Building_ResourceCultureChanges | Vanilla only*
Building_ResourceFaithChanges | G&K and BNW
Building_YieldChangesPerReligion | BNW only
Building_ThemingBonuses | BNW only
Belief_BuildingClassTourism | BNW only
Policy_BuildingClassTourismModifiers | BNW only

* the table is actually still valid in the definitions of game-tables, but you should use <Building_ResourceYieldChanges> with YIELD_CULTURE for G&K and BNW.



------------------------------------------------------------------------------------------------------------------------------------------------------------------------

XML-only Strategies to Circumvent Issues Between Expansion Levels

  • Most if not all of the expansion compatibility issues that are related to buildings can be circumvented via XML-only methods, assuming that it is aesthetically acceptable to you as a mod-creator to have dummy buildings that actually show in the player's city-view for Vanilla and G&K.
  • The method(s) that will be shown do require a bit more work within ModBuddy in that "sandboxed" XML files are created in ModBuddy, and have to be given separate "OnModActivated > UpdateDatabase" entries in the mod's "Actions" tab.

The method that will be shown (with a few different examples) will be one where:
  1. A basic definition of the dummy building is created in a "stand-alone" XML-file.
    • The basic building definition will be highest-up in ModBuddy on the list of "UpdateDatabase" files.
    • This definition of the building within the <Buildings> table will often in and of itself not actually create any effect in-game.
  2. A "Sandboxed" Update XML-file will be created for Vanilla-expansion code
    • The Vanilla-expansion update will be second highest-up in ModBuddy on the list of "UpdateDatabase" files. IE, it should be placed in the "Actions" tab directly below the ModBuddy "OnModActivated" > "UpdateDatabase" for the basic definition of the building.
    • This Update XML-file of the building will add all of the code needed to make it work properly in Vanilla. What this means is that <Buildings> columns that are only used in Vanilla should always be placed here, followed by data for the building-related tables that are only effective in Vanilla, and all of this placed within the same "Vanilla" update file. Code that cannot be used for G&K or BNW will be discarded, but this is OK and intentional, as it will tend to cause the Vanilla update to succeed for Vanilla, but fail for G&K and BNW.
    • In many cases there will be no difference between what is available to Vanilla and what is available to G&K. In such cases you should simply choose which of the two updates to skip including in your mod.
  3. A "Sandboxed" Update XML-file will be created for G&K-expansion code
    • The G&K-expansion update will be third highest-up in ModBuddy on the list of "UpdateDatabase" files. IE, it should be placed in the "Actions" tab directly below the ModBuddy "OnModActivated" > "UpdateDatabase" for the Vanilla update of the building.
    • This Update XML-file of the building will add all of the code needed to make it work properly in G&K. What this means is that <Buildings> columns that are only used in G&K should always be placed here, followed by data for the building-related tables that are only effective in G&K, and all of this placed within the same "G&K" update file. Code that cannot be used for Vanilla or BNW will be discarded, but this is OK and intentional, as it will tend to cause the G&K update to succeed for G&K, but fail for Vanilla and BNW.
    • Code that will be accepted for both both G&K and BNW should be placed in the G&K update to avoid problems with repeat code-strings that would otherwise occur while loading the BNW-only code.
  4. A "Sandboxed" Update XML-file will be created for BNW-expansion code
    • The BNW-expansion update will be fourth highest-up in ModBuddy on the list of "UpdateDatabase" files. IE, it should be placed in the "Actions" tab directly below the ModBuddy "OnModActivated" > "UpdateDatabase" for the G&K update of the building.
    • This Update XML-file of the building will add all of the code needed to make it work properly in BNW. What this means is that <Buildings> columns that are only used in BNW should always be placed here, followed by data for the building-related tables that are only effective in BNW, and all of this placed within the same "BNW" update file. Code that cannot be used for G&K or Vanilla will be discarded, but this is OK and intentional, as it will tend to cause the BNW update to succeed for BNW, but fail for G&K and Vanilla.
As an example of this method, here are the XML-files for a dummy building that would add +1 Culture for each dummy building added to a city:
Spoiler Basic Dummy Building Definition :

Code:
<GameData>
	<BuildingClasses>
		<Row>
			<Type>BUILDINGCLASS_CULTURE_LRS</Type>
			<DefaultBuilding>BUILDING_CULTURE_LRS</DefaultBuilding>
			<Description>TXT_KEY_BUILDING_CULTURE_LRS</Description>
			<NoLimit>true</NoLimit>
		</Row>
	</BuildingClasses>
	<Buildings>
		<Row>
			<Type>BUILDING_CULTURE_LRS</Type>
			<BuildingClass>BUILDINGCLASS_CULTURE_LRS</BuildingClass>
			<Cost>-1</Cost>
			<PrereqTech>NULL</PrereqTech>
			<MinAreaSize>-1</MinAreaSize>
			<NeverCapture>true</NeverCapture>
			<NukeImmune>true</NukeImmune>
			<PortraitIndex>19</PortraitIndex>
			<IconAtlas>BW_ATLAS_1</IconAtlas>
			<Description>TXT_KEY_BUILDING_CULTURE_LRS</Description>
		</Row>
	</Buildings>
	<Language_en_US>
		<Row Tag="TXT_KEY_BUILDING_CULTURE_LRS">
			<Text>LeeS Culture</Text>
		</Row>
	</Language_en_US>
</GameData>
Spoiler Vanilla update of the Dummy Building to add the Culture :

Code:
<GameData>
	<Buildings>
		<!-- Culture Dummy Vanilla Update -->
		<Update>
			<Where Type="BUILDING_CULTURE_LRS" />
			<Set>
				<Culture>1</Culture>
			</Set>
		</Update>
	</Buildings>
</GameData>
Spoiler G&K and BNW Update to add the Culture :

Code:
<GameData>
	<!-- Culture Dummy G&K and BNW Update -->

	<Buildings>
		<Update>
			<Where Type="BUILDING_CULTURE_LRS" />
			<Set>
				<FaithCost>-1</FaithCost>
			</Set>
		</Update>
	</Buildings>

	<Building_YieldChanges>
		<!--	Not an <Update> because no such building already has a <Row> in this table with YIELD_CULTURE as the <YieldType>	-->
		<!--	This <Row> entry would actually "work" for Vanilla in the sense that the file would not be rejected, but Vanilla has no
				"hook-up" for culture in the <Building_YieldChanges> table	-->
		<Row>
			<BuildingType>BUILDING_CULTURE_LRS</BuildingType>
			<YieldType>YIELD_CULTURE</YieldType>
			<Yield>1</Yield>
		</Row>
	</Building_YieldChanges>
</GameData>
Spoiler BNW Update to Hide the Building in BNW :

Code:
<GameData>
	<Buildings>
		<!-- Culture Dummy BNW Update -->
		
		<Update>
			<Where Type="BUILDING_CULTURE_LRS" />
			<Set>
				<GreatWorkCount>-1</GreatWorkCount>
			</Set>
		</Update>
	</Buildings>
</GameData>
 
Last edited:
So I'd like to add a bit of information about building stacking:

The HUD doesn't treat the Great People Points from dummy building as stacking, so Cities with stacked GPP Dummy buildings will count only 1, but the Great People Points themselves do stack, and this is without Community Patch.
 
So I'd like to add a bit of information about building stacking:

The HUD doesn't treat the Great People Points from dummy building as stacking, so Cities with stacked GPP Dummy buildings will count only 1, but the Great People Points themselves do stack, and this is without Community Patch.
The User Interface doesn't treat stacking *most* dummy buildings at all despite their stacks are still in effect.
 
None of the in-game displays are designed to deal with more than one copy of a building within the same city.

Stacking refers to whether or not the effects of multiple copies of the same building in the same city are implemented fully or not, regardless of the shortcomings of the city display.
 
Top Bottom