Custom Building for Custom Replacer District Not Buildable but can Purchase

kingchris20

Wisdom Seeker
Joined
Jul 30, 2012
Messages
1,343
Location
Resident of Heaven; Currently in the Waiting Room
I have 2 things. A custom district that replaces the harbor and a building for that district apart from the 3 normal ones for the harbor.

My district can build the lighthouse, shipyard, and seaport just fine. They are buildable once unlocked and purchasable, as expected.

However the additional building; once it is unlocked, it does not appear under the district as buildable. I can purchase it and it works fine once it is purchased, however I would like to make it buildable.

One thing I tried just to see if it could be build, I changed the prereq district to the city center instead of my district, and sure enough, I could build it once it was researched. But I would really like to have it as part of my district and have the option to build it rather than just buy it.

What can I do to make it buildable?

The coding:

Code:
<Types>
    <Row Type="KC20_DISTRICT_PIRATE_STRONGHOLD" Kind="KIND_DISTRICT"/>
    <Row Type="BUILDING_KC20_PIRATE_MUSEUM" Kind="KIND_BUILDING"/>
</Types>
<Buildings>
    <Row BuildingType="BUILDING_KC20_PIRATE_MUSEUM" Name="LOC_BUILDING_KC20_PIRATE_MUSEUM_NAME" 
    Description="LOC_BUILDING_KC20_PIRATE_MUSEUM_DESCRIPTION" PrereqCivic="CIVIC_CULTURAL_HERITAGE" 
    PrereqDistrict="KC20_DISTRICT_PIRATE_STRONGHOLD" PurchaseYield="YIELD_GOLD" Cost="600" 
    AdvisorType="ADVISOR_CULTURE" Maintenance="3" CitizenSlots="1"/>
</Buildings>
<Building_YieldChanges>
    <Row BuildingType="BUILDING_KC20_PIRATE_MUSEUM" YieldType="YIELD_CULTURE" YieldChange="2"/>
</Building_YieldChanges>
<Building_GreatPersonPoints>
    <Row BuildingType="BUILDING_KC20_PIRATE_MUSEUM" GreatPersonClassType="GREAT_PERSON_CLASS_MERCHANT" 
    PointsPerTurn="1"/>
</Building_GreatPersonPoints>
<Building_GreatWorks>
    <Row BuildingType="BUILDING_KC20_PIRATE_MUSEUM" GreatWorkSlotType="GREATWORKSLOT_ARTIFACT" 
    NumSlots="3" ThemingSameEras="true" ThemingUniqueCivs="true" ThemingYieldMultiplier="100" 
    ThemingTourismMultiplier="100" NonUniquePersonYield="1" NonUniquePersonTourism="1" 
    ThemingBonusDescription="LOC_BUILDING_THEMINGBONUS_ARCHAEOLOGY"/>
</Building_GreatWorks>
<DistrictReplaces>
    <Row CivUniqueDistrictType="KC20_DISTRICT_PIRATE_STRONGHOLD" ReplacesDistrictType="DISTRICT_HARBOR"/>
</DistrictReplaces>
<Districts>
    <Row DistrictType="KC20_DISTRICT_PIRATE_STRONGHOLD" Name="LOC_KC20_DISTRICT_PIRATE_STRONGHOLD_NAME" 
    Description="LOC_KC20_DISTRICT_PIRATE_STRONGHOLD_DESCRIPTION" PrereqTech="TECH_CELESTIAL_NAVIGATION" 
    PlunderType="PLUNDER_GOLD" PlunderAmount="50" AdvisorType="ADVISOR_CONQUEST" Cost="27" 
    CostProgressionModel="COST_PROGRESSION_NUM_UNDER_AVG_PLUS_TECH" CostProgressionParam1="40" 
    RequiresPlacement="true" Coast="true" Aqueduct="false" FreeEmbark="true" NoAdjacentCity="false" 
    AdjacentToLand="true" InternalOnly="false" ZOC="true" HitPoints="100" TradeEmbark="true" 
    CaptureRemovesBuildings="true" CaptureRemovesCityDefenses="false" MilitaryDomain="DOMAIN_SEA" 
    TravelTime="2" Appeal="1" CityStrengthModifier="2" 
    TraitType="TRAIT_CIVILIZATION_KC20_DISTRICT_PIRATE_STRONGHOLD"/>
</Districts>
<District_Adjacencies>
    <Row DistrictType="KC20_DISTRICT_PIRATE_STRONGHOLD" YieldChangeId="SeaResource_Gold"/>
    <Row DistrictType="KC20_DISTRICT_PIRATE_STRONGHOLD" YieldChangeId="District_Gold"/>
    <Row DistrictType="KC20_DISTRICT_PIRATE_STRONGHOLD" YieldChangeId="PirateStronghold_City_Gold"/>
</District_Adjacencies>
<District_GreatPersonPoints>
    <Row DistrictType="KC20_DISTRICT_PIRATE_STRONGHOLD" GreatPersonClassType="GREAT_PERSON_CLASS_ADMIRAL" 
    PointsPerTurn="2"/>
</District_GreatPersonPoints>
<District_TradeRouteYields>
    <Row DistrictType="KC20_DISTRICT_PIRATE_STRONGHOLD" YieldType="YIELD_PRODUCTION" 
    YieldChangeAsOrigin="0" YieldChangeAsDomesticDestination="1" YieldChangeAsInternationalDestination="0"/>
    <Row DistrictType="KC20_DISTRICT_PIRATE_STRONGHOLD" YieldType="YIELD_GOLD" 
    YieldChangeAsOrigin="0" YieldChangeAsDomesticDestination="0" YieldChangeAsInternationalDestination="3"/>
</District_TradeRouteYields>
<District_CitizenYieldChanges>
    <Row DistrictType="KC20_DISTRICT_PIRATE_STRONGHOLD" YieldType="YIELD_GOLD" YieldChange="2"/>
    <Row DistrictType="KC20_DISTRICT_PIRATE_STRONGHOLD" YieldType="YIELD_SCIENCE" YieldChange="1"/>
</District_CitizenYieldChanges>
<Adjacency_YieldChanges>
    <Row ID="PirateStronghold_Gold" Description="LOC_KC20_DISTRICT_PIRATE_STRONGHOLD_GOLD" 
    YieldType="YIELD_GOLD" YieldChange="2" TilesRequired="1" 
    AdjacentDistrict="KC20_DISTRICT_PIRATE_STRONGHOLD"/>
    <Row ID="PirateStronghold_City_Gold" Description="LOC_DISTRICT_CITY_CENTER_GOLD" 
    YieldType="YIELD_GOLD" YieldChange="2" TilesRequired="1" AdjacentDistrict="DISTRICT_CITY_CENTER"/>
</Adjacency_YieldChanges>
<DistrictModifiers>
    <Row>
        <DistrictType>KC20_DISTRICT_PIRATE_STRONGHOLD</DistrictType>
        <ModifierId>KC20_DISTRICT_PIRATE_STRONGHOLD_TRADE_ROUTE_CAPACITY</ModifierId>
    </Row>
</DistrictModifiers>
 
Edited: I think you have to add that building to Harbor itself, I think this is related to a "known bug".

I for instance tried to replace harbor, and then lighthouse and the others, which cant be built either, the 3 buildings replaced dont appear to build.

But I never tried to purchase! if this is true, maybe a problem in interface of building in city!

By the way my solution was to replicate suff (and not replace).
 
Last edited:
I tried it out, a real bug on interface of building in city, since I can purchase like you´ve said!!!

So can someone correct the interface of building in city for this case?

In my case, since I replaced lighthouse, regular default lighthouse appear to build instead of my one, but both appear in purchase!
 
I tried it out, a real bug on interface of building in city, since I can purchase like you´ve said!!!

So can someone correct the interface of building in city for this case?

In my case, since I replaced lighthouse, regular default lighthouse appear to build instead of my one, but both appear in purchase!


Well here is the LUA involved with populating the list in the production panel (productionpanel.lua) for Districts and Nested buildings. I am no good with LUA, but I am going to take a look....hoping that someone else might take a look as well.

Code:
-- Populate Districts ------------------------ CANNOT purchase districts
        districtList = listIM:GetInstance();
        districtList.Header:SetText(Locale.ToUpper(Locale.Lookup("LOC_HUD_DISTRICTS_BUILDINGS")));
        districtList.HeaderOn:SetText(Locale.ToUpper(Locale.Lookup("LOC_HUD_DISTRICTS_BUILDINGS")));
        local dL = districtList;    -- Due to lambda capture, we need to copy this for callback
        if ( districtList.districtListIM ~= nil ) then
            districtList.districtListIM:ResetInstances();
        else
            districtList.districtListIM = InstanceManager:new( "DistrictListInstance", "Root", districtList.List);   
        end

        -- In the interest of performance, we're keeping the instances that we created and resetting the data.
        -- This requires a little bit of footwork to remember the instances that have been modified and to manually reset them.
        for _,type in ipairs(m_TypeNames) do           
            if ( districtList[BUILDING_IM_PREFIX..type] ~= nil) then        --Reset the states for the building instance managers 
                districtList[BUILDING_IM_PREFIX..type]:ResetInstances();
            end
            if ( districtList[BUILDING_DRAWER_PREFIX..type] ~= nil) then    --Reset the states of the drawers
                districtList[BUILDING_DRAWER_PREFIX..type]:SetHide(true);
            end
        end

        for i, item in ipairs(data.DistrictItems) do
            local districtListing = districtList["districtListIM"]:GetInstance();
            ResetInstanceVisibility(districtListing);
            -- Check to see if this district item is one of the items that is recommended:
            for _,hash in ipairs( m_recommendedItems) do
                if(item.Hash == hash.BuildItemHash) then
                    districtListing.RecommendedIcon:SetHide(false);
                end
            end

            local nameStr = Locale.Lookup("{1_Name}", item.Name);
            if (item.Repair) then
                nameStr = nameStr .. "[NEWLINE]" .. Locale.Lookup("LOC_PRODUCTION_ITEM_REPAIR");
            end
            if (item.Contaminated) then
                nameStr = nameStr .. Locale.Lookup("LOC_PRODUCTION_ITEM_DECONTAMINATE");
            end
            districtListing.LabelText:SetText(nameStr);

            local turnsStrTT:string = "";
            local turnsStr:string = "";

            if(item.HasBeenBuilt and GameInfo.Districts[item.Type].OnePerCity == true and not item.Repair and not item.Contaminated and item.Progress == 0) then
                turnsStrTT = Locale.Lookup("LOC_HUD_CITY_DISTRICT_BUILT_TT");
                turnsStr = "[ICON_Checkmark]";
            else
                local numberOfTurns = item.TurnsLeft;
                if numberOfTurns == -1 then
                    numberOfTurns = "999+";
                    turnsStrTT = Locale.Lookup("LOC_HUD_CITY_WILL_NOT_COMPLETE");
                else
                    turnsStrTT = numberOfTurns .. Locale.Lookup("LOC_HUD_CITY_TURNS_TO_COMPLETE", item.TurnsLeft);
                end
                turnsStr = numberOfTurns .. "[ICON_Turn]";
            end

            if(item.Progress > 0) then
                districtListing.ProductionProgressArea:SetHide(false);
                local districtProgress = item.Progress/item.Cost;
                if (districtProgress < 1) then
                    districtListing.ProductionProgress:SetPercent(districtProgress);
                else
                    districtListing.ProductionProgressArea:SetHide(true);
                end
            else
                districtListing.ProductionProgressArea:SetHide(true);
            end
           
            districtListing.CostText:SetToolTipString(turnsStrTT);
            districtListing.CostText:SetText(turnsStr);
            districtListing.Button:SetToolTipString(item.ToolTip);
            districtListing.Disabled:SetToolTipString(item.ToolTip);
            districtListing.Icon:SetIcon(ICON_PREFIX..item.Type);

            local districtType = item.Type;
            -- Check to see if this is a unique district that will be substituted for another kind of district
            if(GameInfo.DistrictReplaces[item.Type] ~= nil) then
                districtType =     GameInfo.DistrictReplaces[item.Type].ReplacesDistrictType;
            end
            local uniqueBuildingIMName = BUILDING_IM_PREFIX..districtType;
            local uniqueBuildingAreaName = BUILDING_DRAWER_PREFIX..districtType;

            table.insert(m_TypeNames, districtType);
            districtList[uniqueBuildingIMName] = InstanceManager:new( "BuildingListInstance", "Root", districtListing.BuildingStack);
            districtList[uniqueBuildingAreaName] = districtListing.BuildingDrawer;
            districtListing.CompletedArea:SetHide(true);

            if (item.Disabled) then 
                if(item.HasBeenBuilt) then
                    districtListing.CompletedArea:SetHide(false);
                    districtListing.Disabled:SetHide(true);
                else
                    if(showDisabled) then
                        districtListing.Disabled:SetHide(false);
                        districtListing.Button:SetColor(COLOR_LOW_OPACITY);
                    else
                        districtListing.Root:SetHide(true);
                    end
                end
            else
                districtListing.Root:SetHide(false);
                districtListing.Disabled:SetHide(true);
                districtListing.Button:SetColor(0xFFFFFFFF);
            end
            districtListing.Button:SetDisabled(item.Disabled);
            districtListing.Button:RegisterCallback( Mouse.eLClick, function()
            districtListing.Button:RegisterCallback( Mouse.eMouseEnter,    function() UI.PlaySound("Main_Menu_Mouse_Over"); end);

                ZoneDistrict(data.City, item);
                Close();
            end);

            if(not IsTutorialRunning()) then
                districtListing.Button:RegisterCallback( Mouse.eRClick, function()
                    LuaEvents.OpenCivilopedia(item.Type);
                end);
            end

            districtListing.Root:SetTag(UITutorialManager:GetHash(item.Type));
        end

        districtList.List:CalculateSize();
        districtList.List:ReprocessAnchoring();

        if (districtList.List:GetSizeY()==0) then
            districtList.Top:SetHide(true);
        else
            m_maxProductionSize = m_maxProductionSize + HEADER_Y + SEPARATOR_Y;
            districtList.Header:RegisterCallback( Mouse.eLClick, function()
                OnExpand(dL);                   
                end);
            districtList.Header:RegisterCallback( Mouse.eMouseEnter,    function() UI.PlaySound("Main_Menu_Mouse_Over"); end);
            districtList.HeaderOn:RegisterCallback( Mouse.eLClick, function()
                OnCollapse(dL);                   
                end);
            districtList.HeaderOn:RegisterCallback(    Mouse.eMouseEnter,    function() UI.PlaySound("Main_Menu_Mouse_Over"); end);
        end

        prodDistrictList = dL;

        -- Populate Nested Buildings -----------------
           
        for i, buildingItem in ipairs(data.BuildingItems) do
            if(not buildingItem.IsWonder) then
                local uniqueDrawerName = BUILDING_DRAWER_PREFIX..buildingItem.PrereqDistrict;
                local uniqueIMName = BUILDING_IM_PREFIX..buildingItem.PrereqDistrict;
                if (districtList[uniqueIMName] ~= nil) then
                    local buildingListing = districtList[uniqueIMName]:GetInstance();   
                    ResetInstanceVisibility(buildingListing);   
                    -- Check to see if this is one of the recommended items
                    for _,hash in ipairs( m_recommendedItems) do
                        if(buildingItem.Hash == hash.BuildItemHash) then
                            buildingListing.RecommendedIcon:SetHide(false);
                        end
                    end
                    buildingListing.Root:SetSizeX(305);
                    buildingListing.Button:SetSizeX(305);
                    local districtBuildingAreaControl = districtList[uniqueDrawerName];
                    districtBuildingAreaControl:SetHide(false);

                    --Fill the meter if there is any progress, hide it if not
                    if(buildingItem.Progress > 0) then
                        buildingListing.ProductionProgressArea:SetHide(false);
                        local buildingProgress = buildingItem.Progress/buildingItem.Cost;
                        if (buildingProgress < 1) then
                            buildingListing.ProductionProgress:SetPercent(buildingProgress);
                        else
                            buildingListing.ProductionProgressArea:SetHide(true);
                        end
                    else
                        buildingListing.ProductionProgressArea:SetHide(true);
                    end

                    local nameStr = Locale.Lookup("{1_Name}", buildingItem.Name);
                    if (buildingItem.Repair) then
                        nameStr = nameStr .. "[NEWLINE]" .. Locale.Lookup("LOC_PRODUCTION_ITEM_REPAIR");
                    end
                    buildingListing.LabelText:SetText(nameStr);
                    local turnsStrTT:string = "";
                    local turnsStr:string = "";
                    local numberOfTurns = buildingItem.TurnsLeft;
                    if numberOfTurns == -1 then
                        numberOfTurns = "999+";
                        turnsStrTT = Locale.Lookup("LOC_HUD_CITY_WILL_NOT_COMPLETE");
                    else
                        turnsStrTT = numberOfTurns .. Locale.Lookup("LOC_HUD_CITY_TURNS_TO_COMPLETE", buildingItem.TurnsLeft);
                    end
                    turnsStr = numberOfTurns .. "[ICON_Turn]";
                    buildingListing.CostText:SetToolTipString(turnsStrTT);
                    buildingListing.CostText:SetText(turnsStr);
                    buildingListing.Button:SetToolTipString(buildingItem.ToolTip);
                    buildingListing.Disabled:SetToolTipString(buildingItem.ToolTip);
                    buildingListing.Icon:SetIcon(ICON_PREFIX..buildingItem.Type);
                    if (buildingItem.Disabled) then 
                        if(showDisabled) then
                            buildingListing.Disabled:SetHide(false);
                            buildingListing.Button:SetColor(COLOR_LOW_OPACITY);
                        else
                            buildingListing.Button:SetHide(true);
                        end
                    else
                        buildingListing.Button:SetHide(false);
                        buildingListing.Disabled:SetHide(true);
                        buildingListing.Button:SetSizeY(BUTTON_Y);
                        buildingListing.Button:SetColor(0xffffffff);
                    end
                    buildingListing.Button:SetDisabled(buildingItem.Disabled);
                    buildingListing.Button:RegisterCallback( Mouse.eMouseEnter,    function() UI.PlaySound("Main_Menu_Mouse_Over"); end);
                    buildingListing.Button:RegisterCallback( Mouse.eLClick, function()
                        BuildBuilding(data.City, buildingItem);
                        Close();
                    end);

                    if(not IsTutorialRunning()) then
                        buildingListing.Button:RegisterCallback( Mouse.eRClick, function()
                            LuaEvents.OpenCivilopedia(buildingItem.Type);
                        end);
                    end

                    buildingListing.Button:SetTag(UITutorialManager:GetHash(buildingItem.Type));
                   
                end
            end
        end
 
Top Bottom