From c47f99bc29f92fb4c52b2f001d01b7f4612c728d Mon Sep 17 00:00:00 2001 From: Leonid Pershin Date: Sun, 14 Jun 2026 12:42:09 +0300 Subject: [PATCH] Update engine subproject commit to 96e19c7. Remove obsolete gene, patch, pawn, plant, product, terrain, and world preset definitions from the Core mod. Enhance documentation to reflect new directory structure for Defs, improving clarity on file organization and localization paths. --- Mods/Core/Defs/Genes/Content.json | 29 ++++++ Mods/Core/Defs/Genes/Environment.json | 34 +++++++ Mods/Core/Defs/Genes/Growth.json | 24 +++++ Mods/Core/Defs/Genes/_Bases.json | 10 +++ .../{patches.json => Patches/Patches.json} | 0 .../Defs/{pawns.json => Pawns/Animals.json} | 9 +- Mods/Core/Defs/Pawns/Beings.json | 11 +++ Mods/Core/Defs/Pawns/_Bases.json | 8 ++ Mods/Core/Defs/Plants/Berries.json | 8 ++ Mods/Core/Defs/Plants/Bushes.json | 9 ++ Mods/Core/Defs/Plants/Cacti.json | 15 ++++ Mods/Core/Defs/Plants/Flowers.json | 12 +++ Mods/Core/Defs/Plants/Grass.json | 18 ++++ Mods/Core/Defs/Plants/Mushrooms.json | 11 +++ Mods/Core/Defs/Plants/Trees.json | 17 ++++ .../Defs/{plants.json => Plants/_Bases.json} | 90 +++++-------------- .../{products.json => Products/Products.json} | 0 .../{terrain.json => Terrain/Terrain.json} | 0 .../WorldPresets.json} | 0 Mods/Core/Defs/genes.json | 82 ----------------- docs/mods.md | 20 +++++ engine | 2 +- src/LittleSim/Content/GameDefs.cs | 10 +-- src/LittleSim/Content/PlantSet.cs | 4 +- src/LittleSim/Sim/PlantOrganism.cs | 2 +- 25 files changed, 257 insertions(+), 168 deletions(-) create mode 100644 Mods/Core/Defs/Genes/Content.json create mode 100644 Mods/Core/Defs/Genes/Environment.json create mode 100644 Mods/Core/Defs/Genes/Growth.json create mode 100644 Mods/Core/Defs/Genes/_Bases.json rename Mods/Core/Defs/{patches.json => Patches/Patches.json} (100%) rename Mods/Core/Defs/{pawns.json => Pawns/Animals.json} (62%) create mode 100644 Mods/Core/Defs/Pawns/Beings.json create mode 100644 Mods/Core/Defs/Pawns/_Bases.json create mode 100644 Mods/Core/Defs/Plants/Berries.json create mode 100644 Mods/Core/Defs/Plants/Bushes.json create mode 100644 Mods/Core/Defs/Plants/Cacti.json create mode 100644 Mods/Core/Defs/Plants/Flowers.json create mode 100644 Mods/Core/Defs/Plants/Grass.json create mode 100644 Mods/Core/Defs/Plants/Mushrooms.json create mode 100644 Mods/Core/Defs/Plants/Trees.json rename Mods/Core/Defs/{plants.json => Plants/_Bases.json} (53%) rename Mods/Core/Defs/{products.json => Products/Products.json} (100%) rename Mods/Core/Defs/{terrain.json => Terrain/Terrain.json} (100%) rename Mods/Core/Defs/{worldpresets.json => WorldPresets/WorldPresets.json} (100%) delete mode 100644 Mods/Core/Defs/genes.json diff --git a/Mods/Core/Defs/Genes/Content.json b/Mods/Core/Defs/Genes/Content.json new file mode 100644 index 0000000..17d9258 --- /dev/null +++ b/Mods/Core/Defs/Genes/Content.json @@ -0,0 +1,29 @@ +{ + "type": "Gene", + // Контент-гены (фаза G4+): плодоношение, добыча, цвет, производные и дискретные морфы. + "defs": [ + { "defName": "GeneFruitYield", "parent": "BaseNumericGene", "label": "gene.fruitYield", + "default": 0, "min": 0, "max": 12, "tags": ["fruiting"], + "effects": { "fruitYield": "value" } }, + { "defName": "GeneFruitSeason", "parent": "BaseNumericGene", "label": "gene.fruitSeason", + "default": 1, "min": 0, "max": 3, "spread": 0, "mutationChance": 0, "tags": ["fruiting"], + "effects": { "fruitSeason": "value" } }, + { "defName": "GeneHarvestAmount", "parent": "BaseNumericGene", "label": "gene.harvestAmount", + "default": 1, "min": 0, "max": 50, "tags": ["harvest"], + "effects": { "harvestAmount": "value" } }, + { "defName": "GeneLeafHue", "parent": "BaseNumericGene", "label": "gene.leafHue", + "default": 0.33, "min": 0, "max": 1, "spread": 0.04, "tags": ["morphology", "color"], + "effects": { "leafHue": "value" } }, + + // Производный ген: признак собирается группировкой по регэкспу — сумма всех генов-толерантностей + // (демонстрация gsom-функций фазы G5). Собственное значение гена не используется. + { "defName": "GeneHardiness", "parent": "BaseNumericGene", "label": "gene.hardiness", + "default": 0, "min": 0, "max": 1, "spread": 0, "mutationChance": 0, "tags": ["derived"], + "effects": { "hardiness": "gsum('Gene.*Tolerance')" } }, + + // Дискретный ген морфы: вариант 0 доминирует, 1 (рецессивный) виден только в гомозиготе. + { "defName": "GeneMorph", "kind": "Discrete", "label": "gene.morph", + "variants": 2, "variantWeights": [0.82, 0.18], "mutationChance": 0.05, "tags": ["morphology"], + "effects": { "variant": "value" } } + ] +} diff --git a/Mods/Core/Defs/Genes/Environment.json b/Mods/Core/Defs/Genes/Environment.json new file mode 100644 index 0000000..ca5fa61 --- /dev/null +++ b/Mods/Core/Defs/Genes/Environment.json @@ -0,0 +1,34 @@ +{ + "type": "Gene", + // Гены среды: свет, температура, почва. Покрывают экологические измерения генома растения, + // которые читают системы роста/жизненного цикла. + "defs": [ + { "defName": "GeneOptimalLight", "parent": "BaseNumericGene", "label": "gene.optimalLight", + "default": 0.6, "min": 0.0, "max": 1.0, "tags": ["environment", "light"], + "effects": { "optimalLight": "value" } }, + { "defName": "GeneLightTolerance", "parent": "BaseNumericGene", "label": "gene.lightTolerance", + "default": 0.5, "min": 0.05, "max": 1.0, "tags": ["environment", "light"], + "effects": { "lightTolerance": "value" } }, + { "defName": "GeneOptimalTemperature", "parent": "BaseNumericGene", "label": "gene.optimalTemperature", + "default": 14, "min": -20, "max": 45, "tags": ["environment", "temperature"], + "effects": { "optimalTemperature": "value" } }, + { "defName": "GeneTemperatureTolerance", "parent": "BaseNumericGene", "label": "gene.temperatureTolerance", + "default": 16, "min": 2, "max": 40, "tags": ["environment", "temperature"], + "effects": { "temperatureTolerance": "value" } }, + // Жёсткие края диапазона роста (модель RimWorld): на сколько °C ниже/выше плато оптимума рост + // спадает до нуля. Ниже (optimal-tolerance-coldHardiness) или выше (optimal+tolerance+heatHardiness) + // растение дормантно и копит температурный стресс. Асимметрично: вид может терпеть жару лучше холода. + { "defName": "GeneColdHardiness", "parent": "BaseNumericGene", "label": "gene.coldHardiness", + "default": 8, "min": 0, "max": 40, "tags": ["environment", "temperature"], + "effects": { "coldHardiness": "value" } }, + { "defName": "GeneHeatHardiness", "parent": "BaseNumericGene", "label": "gene.heatHardiness", + "default": 10, "min": 0, "max": 40, "tags": ["environment", "temperature"], + "effects": { "heatHardiness": "value" } }, + { "defName": "GeneOptimalFertility", "parent": "BaseNumericGene", "label": "gene.optimalFertility", + "default": 1.4, "min": 0.1, "max": 3.0, "tags": ["environment", "soil"], + "effects": { "optimalFertility": "value" } }, + { "defName": "GeneFertilityTolerance", "parent": "BaseNumericGene", "label": "gene.fertilityTolerance", + "default": 0.9, "min": 0.1, "max": 3.0, "tags": ["environment", "soil"], + "effects": { "fertilityTolerance": "value" } } + ] +} diff --git a/Mods/Core/Defs/Genes/Growth.json b/Mods/Core/Defs/Genes/Growth.json new file mode 100644 index 0000000..c382b81 --- /dev/null +++ b/Mods/Core/Defs/Genes/Growth.json @@ -0,0 +1,24 @@ +{ + "type": "Gene", + // Гены роста и размножения: бодрость, продолжительность жизни, расселение, репродукция. + "defs": [ + { "defName": "GeneVigor", "parent": "BaseNumericGene", "label": "gene.vigor", + "default": 1.0, "min": 0.1, "max": 3.0, "tags": ["growth"], + "effects": { "vigor": "value" } }, + { "defName": "GeneLifespan", "parent": "BaseNumericGene", "label": "gene.lifespan", + "default": 160, "min": 5, "max": 500, "tags": ["lifecycle"], + "effects": { "lifespan": "value" } }, + { "defName": "GeneDispersalRange", "parent": "BaseNumericGene", "label": "gene.dispersalRange", + "default": 2, "min": 1, "max": 8, "tags": ["lifecycle", "reproduction"], + "effects": { "dispersalRange": "value" } }, + { "defName": "GeneReproduceInterval", "parent": "BaseNumericGene", "label": "gene.reproduceInterval", + "default": 14, "min": 1, "max": 60, "tags": ["lifecycle", "reproduction"], + "effects": { "reproduceInterval": "value" } }, + { "defName": "GeneSelfPollination", "parent": "BaseNumericGene", "label": "gene.selfPollination", + "default": 0.2, "min": 0.0, "max": 1.0, "tags": ["reproduction"], + "effects": { "selfPollination": "value" } }, + { "defName": "GeneMutationRate", "parent": "BaseNumericGene", "label": "gene.mutationRate", + "default": 0.05, "min": 0.0, "max": 1.0, "tags": ["reproduction"], + "effects": { "mutationRate": "value" } } + ] +} diff --git a/Mods/Core/Defs/Genes/_Bases.json b/Mods/Core/Defs/Genes/_Bases.json new file mode 100644 index 0000000..19a0530 --- /dev/null +++ b/Mods/Core/Defs/Genes/_Bases.json @@ -0,0 +1,10 @@ +{ + "type": "Gene", + // Общие (абстрактные) гены: база наследования для конкретных генов. Каждый ген задаёт, как + // генерируются/мутируют аллели и как ген вкладывается в признаки (effects: имя признака → + // формула; value — выраженное значение гена). Конкретные гены лежат рядом по подтемам. + "defs": [ + { "defName": "BaseNumericGene", "abstract": true, "kind": "Numeric", + "spread": 0.08, "mutationChance": 0.05, "mutationMagnitude": 0.12 } + ] +} diff --git a/Mods/Core/Defs/patches.json b/Mods/Core/Defs/Patches/Patches.json similarity index 100% rename from Mods/Core/Defs/patches.json rename to Mods/Core/Defs/Patches/Patches.json diff --git a/Mods/Core/Defs/pawns.json b/Mods/Core/Defs/Pawns/Animals.json similarity index 62% rename from Mods/Core/Defs/pawns.json rename to Mods/Core/Defs/Pawns/Animals.json index dfcc2ce..b4a2662 100644 --- a/Mods/Core/Defs/pawns.json +++ b/Mods/Core/Defs/Pawns/Animals.json @@ -1,14 +1,7 @@ { "type": "Pawn", + // Животные. "defs": [ - { "defName": "BaseBeing", "abstract": true, "kind": "being", "sizeCells": 1.1 }, - { "defName": "BeingMale", "parent": "BaseBeing", "label": "pawn.being", "texture": "things/pawn/humanlike/bodies/FurCovered_Male_south" }, - { "defName": "BeingFemale", "parent": "BaseBeing", "label": "pawn.being", "texture": "things/pawn/humanlike/bodies/FurCovered_Female_south" }, - { "defName": "BeingThin", "parent": "BaseBeing", "label": "pawn.being", "texture": "things/pawn/humanlike/bodies/FurCovered_Thin_south" }, - { "defName": "BeingFat", "parent": "BaseBeing", "label": "pawn.being", "texture": "things/pawn/humanlike/bodies/FurCovered_Fat_south" }, - { "defName": "BeingHulk", "parent": "BaseBeing", "label": "pawn.being", "texture": "things/pawn/humanlike/bodies/FurCovered_Hulk_south" }, - - { "defName": "BaseAnimal", "abstract": true, "kind": "animal" }, { "defName": "Bear", "parent": "BaseAnimal", "label": "pawn.bear", "texture": "things/pawn/animal/bear/Bear_east", "sizeCells": 1.7 }, { "defName": "DeerDoe", "parent": "BaseAnimal", "label": "pawn.deer", "texture": "things/pawn/animal/deer/DeerFemale_east", "sizeCells": 1.4 }, { "defName": "DeerBuck", "parent": "BaseAnimal", "label": "pawn.deer", "texture": "things/pawn/animal/deer/DeerMale_east", "sizeCells": 1.6 }, diff --git a/Mods/Core/Defs/Pawns/Beings.json b/Mods/Core/Defs/Pawns/Beings.json new file mode 100644 index 0000000..7b206a3 --- /dev/null +++ b/Mods/Core/Defs/Pawns/Beings.json @@ -0,0 +1,11 @@ +{ + "type": "Pawn", + // Жители: варианты тел. + "defs": [ + { "defName": "BeingMale", "parent": "BaseBeing", "label": "pawn.being", "texture": "things/pawn/humanlike/bodies/FurCovered_Male_south" }, + { "defName": "BeingFemale", "parent": "BaseBeing", "label": "pawn.being", "texture": "things/pawn/humanlike/bodies/FurCovered_Female_south" }, + { "defName": "BeingThin", "parent": "BaseBeing", "label": "pawn.being", "texture": "things/pawn/humanlike/bodies/FurCovered_Thin_south" }, + { "defName": "BeingFat", "parent": "BaseBeing", "label": "pawn.being", "texture": "things/pawn/humanlike/bodies/FurCovered_Fat_south" }, + { "defName": "BeingHulk", "parent": "BaseBeing", "label": "pawn.being", "texture": "things/pawn/humanlike/bodies/FurCovered_Hulk_south" } + ] +} diff --git a/Mods/Core/Defs/Pawns/_Bases.json b/Mods/Core/Defs/Pawns/_Bases.json new file mode 100644 index 0000000..1cca457 --- /dev/null +++ b/Mods/Core/Defs/Pawns/_Bases.json @@ -0,0 +1,8 @@ +{ + "type": "Pawn", + // Общие (абстрактные) существа: база для жителей и животных. + "defs": [ + { "defName": "BaseBeing", "abstract": true, "kind": "being", "sizeCells": 1.1 }, + { "defName": "BaseAnimal", "abstract": true, "kind": "animal" } + ] +} diff --git a/Mods/Core/Defs/Plants/Berries.json b/Mods/Core/Defs/Plants/Berries.json new file mode 100644 index 0000000..fc594ab --- /dev/null +++ b/Mods/Core/Defs/Plants/Berries.json @@ -0,0 +1,8 @@ +{ + "type": "Plant", + // Ягодный почвопокров луга (еда). + "defs": [ + { "defName": "Strawberry", "parent": "BaseBerryBush", "label": "plant.strawberry", "sizeCells": 1.0, "texture": "things/plant/strawberryplant/StrawberryPlant" }, + { "defName": "Raspberry", "parent": "BaseBerryBush", "label": "plant.raspberry", "texture": "things/plant/raspberryplant/raspberrybusha" } + ] +} diff --git a/Mods/Core/Defs/Plants/Bushes.json b/Mods/Core/Defs/Plants/Bushes.json new file mode 100644 index 0000000..b42727d --- /dev/null +++ b/Mods/Core/Defs/Plants/Bushes.json @@ -0,0 +1,9 @@ +{ + "type": "Plant", + // Кусты: ягодный подлесок. Патч даёт им древесину при сборе (веточки) — см. Patches/Patches.json. + "defs": [ + { "defName": "BushA", "parent": "BaseBush", "texture": "things/plant/bush/BushA" }, + { "defName": "BushB", "parent": "BaseBush", "texture": "things/plant/bush/BushB" }, + { "defName": "BushC", "parent": "BaseBush", "texture": "things/plant/bush/BushC" } + ] +} diff --git a/Mods/Core/Defs/Plants/Cacti.json b/Mods/Core/Defs/Plants/Cacti.json new file mode 100644 index 0000000..a26bff3 --- /dev/null +++ b/Mods/Core/Defs/Plants/Cacti.json @@ -0,0 +1,15 @@ +{ + "type": "Plant", + // Пустыня: кактусы и агава на песке. Большинство без плодов; сагуаро/агава плодоносят. + "defs": [ + { "defName": "SaguaroCactusA", "parent": "BaseCactus", "label": "plant.saguaro", "sizeCells": 2.2, "trunkRadiusCells": 0.18, + "fruitProduct": "ProductBerry", "texture": "things/plant/saguarocactus/SaguaroCactusA" }, + { "defName": "SaguaroCactusB", "parent": "BaseCactus", "label": "plant.saguaro", "sizeCells": 2.2, "trunkRadiusCells": 0.18, + "fruitProduct": "ProductBerry", "texture": "things/plant/saguarocactus/SaguaroCactusB" }, + { "defName": "PebbleCactusA", "parent": "BaseCactus", "sizeCells": 1.0, "texture": "things/plant/pebblecactus/PebbleCactusA" }, + { "defName": "PebbleCactusB", "parent": "BaseCactus", "sizeCells": 1.0, "texture": "things/plant/pebblecactus/PebbleCactusB" }, + { "defName": "PincushionCactusA", "parent": "BaseCactus", "sizeCells": 0.9, "texture": "things/plant/pincushioncactus/PincushionCactusA" }, + { "defName": "AgaveA", "parent": "BaseCactus", "label": "plant.agave", "sizeCells": 1.3, "fruitProduct": "ProductBerry", "texture": "things/plant/agave/AgaveA" }, + { "defName": "AgaveB", "parent": "BaseCactus", "label": "plant.agave", "sizeCells": 1.3, "fruitProduct": "ProductBerry", "texture": "things/plant/agave/AgaveB" } + ] +} diff --git a/Mods/Core/Defs/Plants/Flowers.json b/Mods/Core/Defs/Plants/Flowers.json new file mode 100644 index 0000000..191e326 --- /dev/null +++ b/Mods/Core/Defs/Plants/Flowers.json @@ -0,0 +1,12 @@ +{ + "type": "Plant", + // Луг: декоративные цветы с быстрым расселением. + "defs": [ + { "defName": "DandelionA", "parent": "BaseFlower", "label": "plant.dandelion", "texture": "things/plant/dandelion/Dandelion" }, + { "defName": "DandelionB", "parent": "BaseFlower", "label": "plant.dandelion", "texture": "things/plant/dandelion/DandelionB" }, + { "defName": "DandelionC", "parent": "BaseFlower", "label": "plant.dandelion", "texture": "things/plant/dandelion/DandelionC" }, + { "defName": "DaylilyA", "parent": "BaseFlower", "label": "plant.daylily", "texture": "things/plant/daylily/DaylilyA" }, + { "defName": "DaylilyB", "parent": "BaseFlower", "label": "plant.daylily", "texture": "things/plant/daylily/DaylilyB" }, + { "defName": "RoseA", "parent": "BaseFlower", "label": "plant.rose", "sizeCells": 1.1, "texture": "things/plant/rose/RoseA" } + ] +} diff --git a/Mods/Core/Defs/Plants/Grass.json b/Mods/Core/Defs/Plants/Grass.json new file mode 100644 index 0000000..93bac6f --- /dev/null +++ b/Mods/Core/Defs/Plants/Grass.json @@ -0,0 +1,18 @@ +{ + "type": "Plant", + // Трава: быстрый почвопокров, основной скаттер лугов и леса. + "defs": [ + { "defName": "GrassA", "label": "plant.grass", "texture": "things/plant/grass/grassa", "sizeCells": 1.5, + "harvestProduct": "ProductGrass", + "genome": { "optimalLight": 0.85, "lightTolerance": 0.35, "optimalTemperature": 19, "temperatureTolerance": 8, + "coldHardiness": 9, "heatHardiness": 6, + "optimalFertility": 1.0, "fertilityTolerance": 1.0, "vigor": 1.3, + "lifespan": 22, "dispersalRange": 3, "reproduceInterval": 3, "selfPollination": 0.8, + "mutationRate": 0.06, "variantChance": 0.2, "spread": 0.1, + "harvestAmount": 2, "leafHue": 0.36 }, + "stages": [ + { "texture": "things/plant/seed_default", "sizeCells": 0.5, "growDays": 2, "label": "plant.stage.sprout" }, + { "sizeCells": 1.5, "label": "plant.stage.mature" } + ] } + ] +} diff --git a/Mods/Core/Defs/Plants/Mushrooms.json b/Mods/Core/Defs/Plants/Mushrooms.json new file mode 100644 index 0000000..60a8b49 --- /dev/null +++ b/Mods/Core/Defs/Plants/Mushrooms.json @@ -0,0 +1,11 @@ +{ + "type": "Plant", + // Грибы: подлесок леса, растут в тени крон. + "defs": [ + { "defName": "GlowstoolA", "parent": "BaseMushroom", "sizeCells": 0.9, "texture": "things/plant/glowstool/GlowstoolA" }, + { "defName": "GlowstoolB", "parent": "BaseMushroom", "sizeCells": 0.9, "texture": "things/plant/glowstool/GlowstoolB" }, + { "defName": "TimbershroomA", "parent": "BaseMushroom", "sizeCells": 1.1, "texture": "things/plant/timbershroom/TimbershroomA" }, + { "defName": "TimbershroomB", "parent": "BaseMushroom", "sizeCells": 1.1, "texture": "things/plant/timbershroom/TimbershroomB" }, + { "defName": "NutrifungusA", "parent": "BaseMushroom", "sizeCells": 0.9, "texture": "things/plant/nutrifungus/NutrifungusA" } + ] +} diff --git a/Mods/Core/Defs/Plants/Trees.json b/Mods/Core/Defs/Plants/Trees.json new file mode 100644 index 0000000..eae24ae --- /dev/null +++ b/Mods/Core/Defs/Plants/Trees.json @@ -0,0 +1,17 @@ +{ + "type": "Plant", + // Деревья: умеренные (BaseTree), тёплые (BaseWarmTree) и холодные (BaseColdTree) ниши. + "defs": [ + { "defName": "TreeOakA", "parent": "BaseTree", "label": "plant.oak", "texture": "things/plant/treeoak/TreeOakA" }, + { "defName": "TreeOakB", "parent": "BaseTree", "label": "plant.oak", "texture": "things/plant/treeoak/TreeOakB" }, + { "defName": "TreeBirchA", "parent": "BaseTree", "label": "plant.birch", "texture": "things/plant/treebirch/TreeBirchA" }, + { "defName": "TreeGrayPineA", "parent": "BaseTree", "label": "plant.pine", "texture": "things/plant/treegraypine/TreeGrayPineA" }, + { "defName": "TreeMapleA", "parent": "BaseTree", "label": "plant.maple", "texture": "things/plant/treemaple/TreeMapleA" }, + { "defName": "TreeMapleB", "parent": "BaseTree", "label": "plant.maple", "texture": "things/plant/treemaple/TreeMapleB" }, + { "defName": "TreePoplarA", "parent": "BaseTree", "label": "plant.poplar", "texture": "things/plant/treepoplar/TreePoplarA" }, + { "defName": "TreeTeakA", "parent": "BaseWarmTree", "label": "plant.teak", "texture": "things/plant/treeteak/TreeTeakA" }, + { "defName": "TreeTeakB", "parent": "BaseWarmTree", "label": "plant.teak", "texture": "things/plant/treeteak/TreeTeakB" }, + { "defName": "TreeCypressA", "parent": "BaseColdTree", "label": "plant.cypress", "texture": "things/plant/treecypress/TreeCypressA" }, + { "defName": "TreeCypressB", "parent": "BaseColdTree", "label": "plant.cypress", "texture": "things/plant/treecypress/TreeCypressB" } + ] +} diff --git a/Mods/Core/Defs/plants.json b/Mods/Core/Defs/Plants/_Bases.json similarity index 53% rename from Mods/Core/Defs/plants.json rename to Mods/Core/Defs/Plants/_Bases.json index 6d078c2..dbbda4c 100644 --- a/Mods/Core/Defs/plants.json +++ b/Mods/Core/Defs/Plants/_Bases.json @@ -1,5 +1,7 @@ { "type": "Plant", + // Общие (абстрактные) растения: базовые геномы по типам ниш. Конкретные виды наследуют их + // через "parent" и лежат рядом в файлах по семействам (Trees, Bushes, Cacti, …). "defs": [ { "defName": "BaseTree", "abstract": true, "sizeCells": 2.0, "trunkRadiusCells": 0.28, "harvestProduct": "ProductWood", "fruitProduct": "ProductAcorn", @@ -14,41 +16,8 @@ { "sizeCells": 1.2, "growDays": 9, "label": "plant.stage.sapling" }, { "sizeCells": 2.0, "label": "plant.stage.mature" } ] }, - { "defName": "TreeOakA", "parent": "BaseTree", "label": "plant.oak", "texture": "things/plant/treeoak/TreeOakA" }, - { "defName": "TreeOakB", "parent": "BaseTree", "label": "plant.oak", "texture": "things/plant/treeoak/TreeOakB" }, - { "defName": "TreeBirchA", "parent": "BaseTree", "label": "plant.birch", "texture": "things/plant/treebirch/TreeBirchA" }, - { "defName": "TreeGrayPineA", "parent": "BaseTree", "label": "plant.pine", "texture": "things/plant/treegraypine/TreeGrayPineA" }, - { "defName": "GrassA", "label": "plant.grass", "texture": "things/plant/grass/grassa", "sizeCells": 1.5, - "harvestProduct": "ProductGrass", - "genome": { "optimalLight": 0.85, "lightTolerance": 0.35, "optimalTemperature": 19, "temperatureTolerance": 8, - "coldHardiness": 9, "heatHardiness": 6, - "optimalFertility": 1.0, "fertilityTolerance": 1.0, "vigor": 1.3, - "lifespan": 22, "dispersalRange": 3, "reproduceInterval": 3, "selfPollination": 0.8, - "mutationRate": 0.06, "variantChance": 0.2, "spread": 0.1, - "harvestAmount": 2, "leafHue": 0.36 }, - "stages": [ - { "texture": "things/plant/seed_default", "sizeCells": 0.5, "growDays": 2, "label": "plant.stage.sprout" }, - { "sizeCells": 1.5, "label": "plant.stage.mature" } - ] }, - - { "defName": "BaseBush", "abstract": true, "label": "plant.bush", "sizeCells": 1.4, - "fruitProduct": "ProductBerry", - "genome": { "optimalLight": 0.6, "lightTolerance": 0.5, "optimalTemperature": 17, "temperatureTolerance": 9, - "coldHardiness": 10, "heatHardiness": 8, - "optimalFertility": 1.1, "fertilityTolerance": 1.0, "vigor": 1.0, - "lifespan": 60, "dispersalRange": 2, "reproduceInterval": 7, "selfPollination": 0.5, - "mutationRate": 0.05, "variantChance": 0.18, "spread": 0.1, - "fruitYield": 3, "fruitSeason": 1, "harvestAmount": 3, "leafHue": 0.32 }, - "stages": [ - { "texture": "things/plant/seed_default", "sizeCells": 0.6, "growDays": 3, "label": "plant.stage.sprout" }, - { "sizeCells": 1.4, "label": "plant.stage.mature" } - ] }, - { "defName": "BushA", "parent": "BaseBush", "texture": "things/plant/bush/BushA" }, - { "defName": "BushB", "parent": "BaseBush", "texture": "things/plant/bush/BushB" }, - { "defName": "BushC", "parent": "BaseBush", "texture": "things/plant/bush/BushC" }, - - // --- Деревья+: тёплая и холодная температурные ниши (showcase температурных генов) --- + // Деревья тёплой и холодной температурных ниш (showcase температурных генов). { "defName": "BaseWarmTree", "abstract": true, "sizeCells": 2.0, "trunkRadiusCells": 0.28, "harvestProduct": "ProductWood", "fruitProduct": "ProductAcorn", "genome": { "optimalLight": 0.65, "lightTolerance": 0.5, "optimalTemperature": 23, "temperatureTolerance": 9, @@ -75,16 +44,21 @@ { "sizeCells": 1.2, "growDays": 9, "label": "plant.stage.sapling" }, { "sizeCells": 2.0, "label": "plant.stage.mature" } ] }, - { "defName": "TreeMapleA", "parent": "BaseTree", "label": "plant.maple", "texture": "things/plant/treemaple/TreeMapleA" }, - { "defName": "TreeMapleB", "parent": "BaseTree", "label": "plant.maple", "texture": "things/plant/treemaple/TreeMapleB" }, - { "defName": "TreePoplarA", "parent": "BaseTree", "label": "plant.poplar", "texture": "things/plant/treepoplar/TreePoplarA" }, - { "defName": "TreeTeakA", "parent": "BaseWarmTree", "label": "plant.teak", "texture": "things/plant/treeteak/TreeTeakA" }, - { "defName": "TreeTeakB", "parent": "BaseWarmTree", "label": "plant.teak", "texture": "things/plant/treeteak/TreeTeakB" }, - { "defName": "TreeCypressA", "parent": "BaseColdTree", "label": "plant.cypress", "texture": "things/plant/treecypress/TreeCypressA" }, - { "defName": "TreeCypressB", "parent": "BaseColdTree", "label": "plant.cypress", "texture": "things/plant/treecypress/TreeCypressB" }, - // --- Пустыня: кактусы и агава на песке. Жаролюбивы, засухоустойчивы (низкий оптимум почвы), - // морозо-нестойки (tMin ≈ -2°C → гибнут в морозы). Большинство без плодов; сагуаро/агава плодоносят. --- + { "defName": "BaseBush", "abstract": true, "label": "plant.bush", "sizeCells": 1.4, + "fruitProduct": "ProductBerry", + "genome": { "optimalLight": 0.6, "lightTolerance": 0.5, "optimalTemperature": 17, "temperatureTolerance": 9, + "coldHardiness": 10, "heatHardiness": 8, + "optimalFertility": 1.1, "fertilityTolerance": 1.0, "vigor": 1.0, + "lifespan": 60, "dispersalRange": 2, "reproduceInterval": 7, "selfPollination": 0.5, + "mutationRate": 0.05, "variantChance": 0.18, "spread": 0.1, + "fruitYield": 3, "fruitSeason": 1, "harvestAmount": 3, "leafHue": 0.32 }, + "stages": [ + { "texture": "things/plant/seed_default", "sizeCells": 0.6, "growDays": 3, "label": "plant.stage.sprout" }, + { "sizeCells": 1.4, "label": "plant.stage.mature" } + ] }, + + // Кактусы: жаролюбивы, засухоустойчивы (низкий оптимум почвы), морозо-нестойки → гибнут в морозы. { "defName": "BaseCactus", "abstract": true, "label": "plant.cactus", "sizeCells": 1.2, "trunkRadiusCells": 0, "harvestProduct": "ProductFiber", "genome": { "optimalLight": 0.95, "lightTolerance": 0.35, "optimalTemperature": 26, "temperatureTolerance": 8, @@ -97,18 +71,9 @@ { "texture": "things/plant/seed_default", "sizeCells": 0.5, "growDays": 5, "label": "plant.stage.sprout" }, { "label": "plant.stage.mature" } ] }, - { "defName": "SaguaroCactusA", "parent": "BaseCactus", "label": "plant.saguaro", "sizeCells": 2.2, "trunkRadiusCells": 0.18, - "fruitProduct": "ProductBerry", "texture": "things/plant/saguarocactus/SaguaroCactusA" }, - { "defName": "SaguaroCactusB", "parent": "BaseCactus", "label": "plant.saguaro", "sizeCells": 2.2, "trunkRadiusCells": 0.18, - "fruitProduct": "ProductBerry", "texture": "things/plant/saguarocactus/SaguaroCactusB" }, - { "defName": "PebbleCactusA", "parent": "BaseCactus", "sizeCells": 1.0, "texture": "things/plant/pebblecactus/PebbleCactusA" }, - { "defName": "PebbleCactusB", "parent": "BaseCactus", "sizeCells": 1.0, "texture": "things/plant/pebblecactus/PebbleCactusB" }, - { "defName": "PincushionCactusA", "parent": "BaseCactus", "sizeCells": 0.9, "texture": "things/plant/pincushioncactus/PincushionCactusA" }, - { "defName": "AgaveA", "parent": "BaseCactus", "label": "plant.agave", "sizeCells": 1.3, "fruitProduct": "ProductBerry", "texture": "things/plant/agave/AgaveA" }, - { "defName": "AgaveB", "parent": "BaseCactus", "label": "plant.agave", "sizeCells": 1.3, "fruitProduct": "ProductBerry", "texture": "things/plant/agave/AgaveB" }, - // --- Грибы: подлесок леса. Низкий оптимум света (0.15) → растут в тени крон, где другим темно - // (showcase световой пригодности). Богатая почва, короткая жизнь, быстрое спороношение. --- + // Грибы: подлесок леса. Низкий оптимум света (0.15) → растут в тени крон, где другим темно + // (showcase световой пригодности). Богатая почва, короткая жизнь, быстрое спороношение. { "defName": "BaseMushroom", "abstract": true, "label": "plant.mushroom", "sizeCells": 0.9, "trunkRadiusCells": 0, "harvestProduct": "ProductMushroom", "genome": { "optimalLight": 0.15, "lightTolerance": 0.22, "optimalTemperature": 14, "temperatureTolerance": 11, @@ -121,13 +86,8 @@ { "texture": "things/plant/seed_default", "sizeCells": 0.4, "growDays": 2, "label": "plant.stage.sprout" }, { "label": "plant.stage.mature" } ] }, - { "defName": "GlowstoolA", "parent": "BaseMushroom", "sizeCells": 0.9, "texture": "things/plant/glowstool/GlowstoolA" }, - { "defName": "GlowstoolB", "parent": "BaseMushroom", "sizeCells": 0.9, "texture": "things/plant/glowstool/GlowstoolB" }, - { "defName": "TimbershroomA", "parent": "BaseMushroom", "sizeCells": 1.1, "texture": "things/plant/timbershroom/TimbershroomA" }, - { "defName": "TimbershroomB", "parent": "BaseMushroom", "sizeCells": 1.1, "texture": "things/plant/timbershroom/TimbershroomB" }, - { "defName": "NutrifungusA", "parent": "BaseMushroom", "sizeCells": 0.9, "texture": "things/plant/nutrifungus/NutrifungusA" }, - // --- Луг: цветы (декоративные, быстрое расселение) и ягодный почвопокров (еда). --- + // Луг: цветы (декоративные, быстрое расселение) и ягодный почвопокров (еда). { "defName": "BaseFlower", "abstract": true, "label": "plant.flower", "sizeCells": 1.0, "trunkRadiusCells": 0, "genome": { "optimalLight": 0.9, "lightTolerance": 0.35, "optimalTemperature": 20, "temperatureTolerance": 9, "coldHardiness": 8, "heatHardiness": 8, @@ -139,12 +99,6 @@ { "texture": "things/plant/seed_default", "sizeCells": 0.4, "growDays": 2, "label": "plant.stage.sprout" }, { "label": "plant.stage.mature" } ] }, - { "defName": "DandelionA", "parent": "BaseFlower", "label": "plant.dandelion", "texture": "things/plant/dandelion/Dandelion" }, - { "defName": "DandelionB", "parent": "BaseFlower", "label": "plant.dandelion", "texture": "things/plant/dandelion/DandelionB" }, - { "defName": "DandelionC", "parent": "BaseFlower", "label": "plant.dandelion", "texture": "things/plant/dandelion/DandelionC" }, - { "defName": "DaylilyA", "parent": "BaseFlower", "label": "plant.daylily", "texture": "things/plant/daylily/DaylilyA" }, - { "defName": "DaylilyB", "parent": "BaseFlower", "label": "plant.daylily", "texture": "things/plant/daylily/DaylilyB" }, - { "defName": "RoseA", "parent": "BaseFlower", "label": "plant.rose", "sizeCells": 1.1, "texture": "things/plant/rose/RoseA" }, { "defName": "BaseBerryBush", "abstract": true, "label": "plant.berrybush", "sizeCells": 1.2, "trunkRadiusCells": 0, "fruitProduct": "ProductBerry", @@ -157,8 +111,6 @@ "stages": [ { "texture": "things/plant/seed_default", "sizeCells": 0.5, "growDays": 3, "label": "plant.stage.sprout" }, { "label": "plant.stage.mature" } - ] }, - { "defName": "Strawberry", "parent": "BaseBerryBush", "label": "plant.strawberry", "sizeCells": 1.0, "texture": "things/plant/strawberryplant/StrawberryPlant" }, - { "defName": "Raspberry", "parent": "BaseBerryBush", "label": "plant.raspberry", "texture": "things/plant/raspberryplant/raspberrybusha" } + ] } ] } diff --git a/Mods/Core/Defs/products.json b/Mods/Core/Defs/Products/Products.json similarity index 100% rename from Mods/Core/Defs/products.json rename to Mods/Core/Defs/Products/Products.json diff --git a/Mods/Core/Defs/terrain.json b/Mods/Core/Defs/Terrain/Terrain.json similarity index 100% rename from Mods/Core/Defs/terrain.json rename to Mods/Core/Defs/Terrain/Terrain.json diff --git a/Mods/Core/Defs/worldpresets.json b/Mods/Core/Defs/WorldPresets/WorldPresets.json similarity index 100% rename from Mods/Core/Defs/worldpresets.json rename to Mods/Core/Defs/WorldPresets/WorldPresets.json diff --git a/Mods/Core/Defs/genes.json b/Mods/Core/Defs/genes.json deleted file mode 100644 index 5610511..0000000 --- a/Mods/Core/Defs/genes.json +++ /dev/null @@ -1,82 +0,0 @@ -{ - "type": "Gene", - // Организм-агностичные гены: каждый ген задаёт, как генерируются/мутируют аллели и как ген - // вкладывается в признаки (effects: имя признака → формула; value — выраженное значение гена). - // Этот набор покрывает измерения генома растения (его используют системы роста/жизненного цикла). - "defs": [ - { "defName": "BaseNumericGene", "abstract": true, "kind": "Numeric", - "spread": 0.08, "mutationChance": 0.05, "mutationMagnitude": 0.12 }, - - { "defName": "GeneOptimalLight", "parent": "BaseNumericGene", "label": "gene.optimalLight", - "default": 0.6, "min": 0.0, "max": 1.0, "tags": ["environment", "light"], - "effects": { "optimalLight": "value" } }, - { "defName": "GeneLightTolerance", "parent": "BaseNumericGene", "label": "gene.lightTolerance", - "default": 0.5, "min": 0.05, "max": 1.0, "tags": ["environment", "light"], - "effects": { "lightTolerance": "value" } }, - { "defName": "GeneOptimalTemperature", "parent": "BaseNumericGene", "label": "gene.optimalTemperature", - "default": 14, "min": -20, "max": 45, "tags": ["environment", "temperature"], - "effects": { "optimalTemperature": "value" } }, - { "defName": "GeneTemperatureTolerance", "parent": "BaseNumericGene", "label": "gene.temperatureTolerance", - "default": 16, "min": 2, "max": 40, "tags": ["environment", "temperature"], - "effects": { "temperatureTolerance": "value" } }, - // Жёсткие края диапазона роста (модель RimWorld): на сколько °C ниже/выше плато оптимума рост - // спадает до нуля. Ниже (optimal-tolerance-coldHardiness) или выше (optimal+tolerance+heatHardiness) - // растение дормантно и копит температурный стресс. Асимметрично: вид может терпеть жару лучше холода. - { "defName": "GeneColdHardiness", "parent": "BaseNumericGene", "label": "gene.coldHardiness", - "default": 8, "min": 0, "max": 40, "tags": ["environment", "temperature"], - "effects": { "coldHardiness": "value" } }, - { "defName": "GeneHeatHardiness", "parent": "BaseNumericGene", "label": "gene.heatHardiness", - "default": 10, "min": 0, "max": 40, "tags": ["environment", "temperature"], - "effects": { "heatHardiness": "value" } }, - { "defName": "GeneOptimalFertility", "parent": "BaseNumericGene", "label": "gene.optimalFertility", - "default": 1.4, "min": 0.1, "max": 3.0, "tags": ["environment", "soil"], - "effects": { "optimalFertility": "value" } }, - { "defName": "GeneFertilityTolerance", "parent": "BaseNumericGene", "label": "gene.fertilityTolerance", - "default": 0.9, "min": 0.1, "max": 3.0, "tags": ["environment", "soil"], - "effects": { "fertilityTolerance": "value" } }, - - { "defName": "GeneVigor", "parent": "BaseNumericGene", "label": "gene.vigor", - "default": 1.0, "min": 0.1, "max": 3.0, "tags": ["growth"], - "effects": { "vigor": "value" } }, - { "defName": "GeneLifespan", "parent": "BaseNumericGene", "label": "gene.lifespan", - "default": 160, "min": 5, "max": 500, "tags": ["lifecycle"], - "effects": { "lifespan": "value" } }, - { "defName": "GeneDispersalRange", "parent": "BaseNumericGene", "label": "gene.dispersalRange", - "default": 2, "min": 1, "max": 8, "tags": ["lifecycle", "reproduction"], - "effects": { "dispersalRange": "value" } }, - { "defName": "GeneReproduceInterval", "parent": "BaseNumericGene", "label": "gene.reproduceInterval", - "default": 14, "min": 1, "max": 60, "tags": ["lifecycle", "reproduction"], - "effects": { "reproduceInterval": "value" } }, - { "defName": "GeneSelfPollination", "parent": "BaseNumericGene", "label": "gene.selfPollination", - "default": 0.2, "min": 0.0, "max": 1.0, "tags": ["reproduction"], - "effects": { "selfPollination": "value" } }, - { "defName": "GeneMutationRate", "parent": "BaseNumericGene", "label": "gene.mutationRate", - "default": 0.05, "min": 0.0, "max": 1.0, "tags": ["reproduction"], - "effects": { "mutationRate": "value" } }, - - // --- Контент (фаза G4): плодоношение, добыча, цвет --- - { "defName": "GeneFruitYield", "parent": "BaseNumericGene", "label": "gene.fruitYield", - "default": 0, "min": 0, "max": 12, "tags": ["fruiting"], - "effects": { "fruitYield": "value" } }, - { "defName": "GeneFruitSeason", "parent": "BaseNumericGene", "label": "gene.fruitSeason", - "default": 1, "min": 0, "max": 3, "spread": 0, "mutationChance": 0, "tags": ["fruiting"], - "effects": { "fruitSeason": "value" } }, - { "defName": "GeneHarvestAmount", "parent": "BaseNumericGene", "label": "gene.harvestAmount", - "default": 1, "min": 0, "max": 50, "tags": ["harvest"], - "effects": { "harvestAmount": "value" } }, - { "defName": "GeneLeafHue", "parent": "BaseNumericGene", "label": "gene.leafHue", - "default": 0.33, "min": 0, "max": 1, "spread": 0.04, "tags": ["morphology", "color"], - "effects": { "leafHue": "value" } }, - - // Производный ген: признак собирается группировкой по регэкспу — сумма всех генов-толерантностей - // (демонстрация gsom-функций фазы G5). Собственное значение гена не используется. - { "defName": "GeneHardiness", "parent": "BaseNumericGene", "label": "gene.hardiness", - "default": 0, "min": 0, "max": 1, "spread": 0, "mutationChance": 0, "tags": ["derived"], - "effects": { "hardiness": "gsum('Gene.*Tolerance')" } }, - - // Дискретный ген морфы: вариант 0 доминирует, 1 (рецессивный) виден только в гомозиготе. - { "defName": "GeneMorph", "kind": "Discrete", "label": "gene.morph", - "variants": 2, "variantWeights": [0.82, 0.18], "mutationChance": 0.05, "tags": ["morphology"], - "effects": { "variant": "value" } } - ] -} diff --git a/docs/mods.md b/docs/mods.md index 1239330..cd9b52a 100644 --- a/docs/mods.md +++ b/docs/mods.md @@ -60,6 +60,26 @@ Mods/<Имя>/ вид — `being`/`animal`). CLR-классы — `src/LittleSim/Content/GameDefs.cs`; новый тип дефа = новый класс + `RegisterType` в `GameContent.Load`. +`Defs/` сканируется рекурсивно (`Defs/**/*.json`), и имя файла ни на что не влияет — +важны только `type` и `defName`. Поэтому контент Core разложен по подпапкам для удобства +поиска: одна папка на тип дефа, внутри — общие (абстрактные) дефы в `_Bases.json` и +конкретные, разбитые по семействам: + +``` +Defs/ + Genes/ _Bases.json, Environment.json, Growth.json, Content.json + Plants/ _Bases.json, Trees.json, Bushes.json, Grass.json, Cacti.json, + Mushrooms.json, Flowers.json, Berries.json + Pawns/ _Bases.json, Beings.json, Animals.json + Terrain/ Terrain.json + Products/ Products.json + Patches/ Patches.json + WorldPresets/ WorldPresets.json +``` + +`parent` разрешается после слияния всех файлов, так что ссылка на родителя из другого +файла/папки (`TreeOakA` → `BaseTree`) работает независимо от расположения. + ## Локализация `Languages/<код>/*.json` — плоские словари «ключ → строка»: diff --git a/engine b/engine index 38bdfbb..96e19c7 160000 --- a/engine +++ b/engine @@ -1 +1 @@ -Subproject commit 38bdfbbb81fa7e283d2908e097c94d16853bc0de +Subproject commit 96e19c7c6151152c29c5c5478d365983d3df4069 diff --git a/src/LittleSim/Content/GameDefs.cs b/src/LittleSim/Content/GameDefs.cs index 81b2442..1149a84 100644 --- a/src/LittleSim/Content/GameDefs.cs +++ b/src/LittleSim/Content/GameDefs.cs @@ -14,7 +14,7 @@ public sealed class ScatterEntry public List Options { get; init; } = []; } -/// Тип клетки рельефа (Defs/terrain.json): порог высоты, цвет, поверхность, скаттер растений. +/// Тип клетки рельефа (Defs/Terrain/): порог высоты, цвет, поверхность, скаттер растений. public sealed class TerrainDef : Def { /// Верхняя граница высоты (клетка относится к первому дефу, чей порог выше её высоты). @@ -67,7 +67,7 @@ public sealed class PlantGrowthStage } /// -/// Продукт (Defs/products.json): что растение даёт при сборе (древесина, трава) или плодоношении +/// Продукт (Defs/Products/): что растение даёт при сборе (древесина, трава) или плодоношении /// (ягоды, жёлудь). Источник истины — деф; растения ссылаются на него по имени, а количество /// определяют гены. — ключ локализации (product.*). /// @@ -145,7 +145,7 @@ public sealed class GenomeDef public float LeafHue { get; init; } = 0.33f; } -/// Растение (Defs/plants.json): текстура, размер, опциональный ствол-препятствие, стадии роста, геном. +/// Растение (Defs/Plants/): текстура, размер, опциональный ствол-препятствие, стадии роста, геном. public sealed class PlantDef : Def { /// Ключ текстуры (путь региона в атласах); база для стадий без своей текстуры. @@ -171,7 +171,7 @@ public sealed class PlantDef : Def } /// -/// Пресет размера мира (Defs/worldpresets.json): габариты сетки и население. Меню «Новый +/// Пресет размера мира (Defs/WorldPresets/): габариты сетки и население. Меню «Новый /// мир» строит список размеров из этих дефов — новая механика приходит данными мода, а не /// хардкодом. — ключ локализации (preset.*). /// @@ -190,7 +190,7 @@ public sealed class WorldPresetDef : Def public int Order { get; init; } } -/// Существо (Defs/pawns.json): текстура, размер и вид (житель/животное). +/// Существо (Defs/Pawns/): текстура, размер и вид (житель/животное). public sealed class PawnDef : Def { /// Вид существа: жители ("being") живут в мировой сцене, животные ("animal") — в террейне. diff --git a/src/LittleSim/Content/PlantSet.cs b/src/LittleSim/Content/PlantSet.cs index 0334af7..684b7a1 100644 --- a/src/LittleSim/Content/PlantSet.cs +++ b/src/LittleSim/Content/PlantSet.cs @@ -81,7 +81,7 @@ public sealed class PlantSet /// Индекс вида по дефу. public int IndexOf(PlantDef def) => _index[def]; - // Переводит базовый геном вида (числа из plants.json) в набор генов: каждое число — центр + // Переводит базовый геном вида (числа из Defs/Plants/) в набор генов: каждое число — центр // аллелей соответствующего общего GeneDef; морфа — дискретный ген с долей рецессива из вида. private static GenomeTemplate BuildTemplate( GenomeDef g, @@ -92,7 +92,7 @@ public sealed class PlantSet genes.TryGetValue(id, out var def) ? def : throw new KeyNotFoundException( - $"Gene def '{id}' not found — is Mods/Core/Defs/genes.json loaded?" + $"Gene def '{id}' not found — is Mods/Core/Defs/Genes/ loaded?" ); GenomeTemplate.Entry Numeric(string id, float baseValue) => diff --git a/src/LittleSim/Sim/PlantOrganism.cs b/src/LittleSim/Sim/PlantOrganism.cs index 78aaaca..b6e563b 100644 --- a/src/LittleSim/Sim/PlantOrganism.cs +++ b/src/LittleSim/Sim/PlantOrganism.cs @@ -5,7 +5,7 @@ using MrGameEng.Genetics; namespace LittleSim.Sim; /// -/// Растительные признаки (фенотип), вычисленные из генома формулами генов (см. genes.json): +/// Растительные признаки (фенотип), вычисленные из генома формулами генов (см. Defs/Genes/): /// готовые значения, которые читают системы роста и жизненного цикла, не касаясь генов напрямую. /// Имена полей соответствуют именам признаков в эффектах генов. ///