diff --git a/data/json/monsters/zed-pupating.json b/data/json/monsters/zed-pupating.json index acaa191d0df8d..818076d941c7a 100644 --- a/data/json/monsters/zed-pupating.json +++ b/data/json/monsters/zed-pupating.json @@ -5,6 +5,7 @@ "name": { "str": "pupating zombie crawler" }, "description": "This half of a human corpse is wrapped in sticky black fibers that cover everything from the neck down. Beneath the wrapping there is a strange rhythmic movement, grotesque to behold.", "copy-from": "mon_zombie_crawler", + "species": [ "ZOMBIE" ], "delete": { "categories": [ "CLASSIC" ] }, "bleed_rate": 50, "regenerates": 10, @@ -33,6 +34,7 @@ "name": { "str": "pupating zombie" }, "description": "This human corpse is wrapped in sticky black fibers that cover everything from the neck down. Beneath the wrapping there is a strange rhythmic movement, grotesque to behold.", "copy-from": "mon_zombie_fat", + "species": [ "ZOMBIE" ], "harvest": "zombie_pupating", "delete": { "categories": [ "CLASSIC" ] }, "bleed_rate": 50, @@ -62,6 +64,7 @@ "name": { "str": "pupating brute" }, "description": "This muscular human corpse is wrapped in sticky black fibers that cover everything from the neck down. Beneath the wrapping there is a strange rhythmic movement, grotesque to behold.", "copy-from": "mon_zombie_brute", + "species": [ "ZOMBIE" ], "delete": { "categories": [ "CLASSIC" ] }, "harvest": "zombie_pupating", "speed": 95, @@ -90,6 +93,7 @@ "name": { "str": "hive hulk" }, "description": "The bloated torso of this gigantic corpse is wrapped in sticky black fibers. Beneath the wrapping there is a strange rhythmic movement, grotesque to behold.", "copy-from": "mon_zombie_hulk", + "species": [ "ZOMBIE" ], "hp": 300, "speed": 85, "color": "white_magenta", @@ -124,6 +128,7 @@ "name": { "str": "shady pupating zombie" }, "description": "An uncanny shadow envelops this creature. You can make out the outline of what once may have been a human being, but its edges bulge rhythmically in places that are not anatomically possible for humans.", "copy-from": "mon_zombie_fat", + "species": [ "ZOMBIE" ], "delete": { "categories": [ "CLASSIC" ] }, "special_attacks": [ { "type": "bite", "cooldown": 3 } ], "regenerates": 5, diff --git a/data/json/monsters/zed-winged.json b/data/json/monsters/zed-winged.json index 6cf6ebfd8fa53..c153de2526c49 100644 --- a/data/json/monsters/zed-winged.json +++ b/data/json/monsters/zed-winged.json @@ -5,6 +5,7 @@ "name": { "str": "batwing zombie" }, "description": "This zombie's arms have stretched far beyond human limits, the skin lengthened into a gruesome, fleshy membrane. The mutation does not suit it well: it moves clumsily, even compared to other zombies, but can occasionally leap a significant distance.", "copy-from": "mon_zombie_base", + "species": [ "ZOMBIE" ], "weight": "65200 g", "hp": 64, "color": "light_green", @@ -41,6 +42,7 @@ "name": { "str": "garghoul" }, "description": "This zombie's arms have stretched far beyond human limits, the skin lengthened into a gruesome, fleshy membrane. The rest has become emaciated, with thin, rope-like muscles ripping through taut flesh. While it doesn't appear to be able to fly, it uses its mutated arms to make shockingly fast leaps through the air.", "copy-from": "mon_zombie_base", + "species": [ "ZOMBIE" ], "diff": 2, "volume": "52 L", "weight": "41 kg", @@ -82,7 +84,7 @@ "type": "MONSTER", "name": { "str": "flesh-raptor" }, "description": "This small, winged predator darts through the air on three thinly-haired wings that look like stretched human hands. A sheer, jagged spike juts out from the point where the wings meet. It looks like nothing you've seen on Earth, and yet strangely like it is made of human parts.", - "species": [ "ZOMBIE", "HUMAN" ], + "species": [ "ZOMBIE" ], "default_faction": "zombie", "diff": 1, "volume": "4 L", diff --git a/data/json/monsters/zed_acid.json b/data/json/monsters/zed_acid.json index 7838261a5a50e..d97779160eeb0 100644 --- a/data/json/monsters/zed_acid.json +++ b/data/json/monsters/zed_acid.json @@ -21,6 +21,7 @@ "name": { "str": "corrosive zombie" }, "description": "This zombie has swollen to immense proportions, but still manages to hold itself together with semi-congealed acid all over its bloated, leathery body. It moves clumsily, but spits from a large reserve of acid with uncanny accuracy.", "copy-from": "mon_zombie_base", + "species": [ "ZOMBIE" ], "diff": 15, "volume": "108500 ml", "weight": "120 kg", diff --git a/data/json/monsters/zed_burned.json b/data/json/monsters/zed_burned.json index 4be6bc7b78dc2..b692da6f7681c 100644 --- a/data/json/monsters/zed_burned.json +++ b/data/json/monsters/zed_burned.json @@ -72,6 +72,7 @@ "name": { "str": "fiend" }, "description": "A monstrous burnt vaguely humanoid creature, walking around on its knuckles like a gorilla. Tattered and blackened strands of muscle fibers dangle all around its body, with patches of fused melded skin and bone visible between. Its forelimbs end in lengthy skeletal claws.", "copy-from": "mon_zombie_base", + "species": [ "ZOMBIE" ], "volume": "875 L", "weight": "200 kg", "hp": 275, @@ -108,6 +109,7 @@ "type": "MONSTER", "description": "An oversized charred human form. The remains of its burnt and blackened musculature are clearly visible between the cracks of the shell formed from its melted skin. This one appears to have metal fragments sticking out of its body.", "copy-from": "mon_zombie_scorched_brute", + "species": [ "ZOMBIE" ], "harvest": "zombie_rust", "decay": "zombie_decay_bone_human_skull_rust" } diff --git a/data/json/monsters/zed_command.json b/data/json/monsters/zed_command.json index 8f9e1ab06eef6..dfef111b0f9ac 100644 --- a/data/json/monsters/zed_command.json +++ b/data/json/monsters/zed_command.json @@ -5,6 +5,7 @@ "name": { "str": "skeletal master" }, "description": "A strange zombie covered in bone plates from face to toe. Despite the added weight on its body, its movements are coordinated, almost as if capable of analyzing your movements.", "copy-from": "mon_zombie_master", + "species": [ "ZOMBIE" ], "hp": 90, "speed": 60, "material": [ "bone" ], @@ -26,6 +27,7 @@ "name": { "str": "zombie lich", "str_pl": "zombie liches" }, "description": "A twisted visage of the human body decked in bone from head to toe. Its vague shape is reminiscent of some tabletop monster, and it walks and watches your actions with a cold and calculating demeanor.", "copy-from": "mon_zombie_necro", + "species": [ "ZOMBIE" ], "speed": 70, "material": [ "bone" ], "color": "dark_gray", diff --git a/data/json/monsters/zed_ferrous.json b/data/json/monsters/zed_ferrous.json index 5fda3c9e22298..e676a00e99f13 100644 --- a/data/json/monsters/zed_ferrous.json +++ b/data/json/monsters/zed_ferrous.json @@ -67,6 +67,7 @@ "name": { "str": "rust urchin" }, "description": "A spiked horror of a zombie covered in long, rusty spikes. A walking tetanus infection waiting to happen.", "copy-from": "mon_zombie_base", + "species": [ "ZOMBIE" ], "weight": "90 kg", "hp": 100, "speed": 60, diff --git a/data/json/monsters/zed_fusion.json b/data/json/monsters/zed_fusion.json index 5344b2859fa58..f7575b55cd131 100644 --- a/data/json/monsters/zed_fusion.json +++ b/data/json/monsters/zed_fusion.json @@ -153,7 +153,7 @@ "default_faction": "zombie", "volume": "875000 ml", "weight": "200 kg", - "species": [ "ZOMBIE", "HUMAN" ], + "species": [ "ZOMBIE" ], "diff": 35, "hp": 500, "speed": 100, @@ -186,7 +186,7 @@ "description": "Covered in grievous wounds, this wretch's gray skin has bloated to near-rupture with putrid gas. Between lumps of unrecognizable gore, a human head lamely follows your movements with empty, black eyes.", "default_faction": "zombie", "bodytype": "human", - "species": [ "ZOMBIE", "HUMAN" ], + "species": [ "ZOMBIE" ], "diff": 5, "volume": "62500 ml", "weight": "81500 g", @@ -218,7 +218,7 @@ "description": "A nightmarish, spidery abomination born from human gore. It deftly crawls between the walls and ceiling with limbs grown from its own disjointed ribs.", "default_faction": "zombie", "bodytype": "spider", - "species": [ "ZOMBIE", "HUMAN" ], + "species": [ "ZOMBIE" ], "diff": 5, "volume": "62500 ml", "weight": "81500 g", @@ -251,7 +251,7 @@ "description": "A corpse hideously twisted into an insect-like form. A hollow tendril reaches out from its open thorax.", "default_faction": "zombie", "bodytype": "spider", - "species": [ "ZOMBIE", "HUMAN" ], + "species": [ "ZOMBIE" ], "diff": 14, "volume": "30000 ml", "weight": "40750 g", @@ -298,7 +298,7 @@ "description": "A nightmarish spider of gore standing tall among the ruins, keeping silent watch of the blighted landscape. Its spindly limbs of bone slip between the rubble with otherworldly speed.", "default_faction": "zombie", "bodytype": "spider", - "species": [ "ZOMBIE", "HUMAN" ], + "species": [ "ZOMBIE" ], "diff": 5, "volume": "122500 ml", "weight": "81500 g", @@ -329,7 +329,7 @@ "description": "Great snakes of flesh hang from the ceiling above, madly thrashing and reaching about.", "default_faction": "zombie", "bodytype": "spider", - "species": [ "ZOMBIE", "HUMAN" ], + "species": [ "ZOMBIE" ], "diff": 5, "volume": "122500 ml", "weight": "81500 g", @@ -368,7 +368,7 @@ "default_faction": "zombie", "volume": "875000 ml", "weight": "200 kg", - "species": [ "ZOMBIE", "HUMAN" ], + "species": [ "ZOMBIE" ], "diff": 1, "hp": 3, "speed": 100, @@ -392,7 +392,7 @@ "default_faction": "zombie", "volume": "875000 ml", "weight": "200 kg", - "species": [ "ZOMBIE", "HUMAN" ], + "species": [ "ZOMBIE" ], "diff": 1, "hp": 3, "speed": 100, diff --git a/data/json/monsters/zed_misc.json b/data/json/monsters/zed_misc.json index 2bf82c9007275..5883691506d35 100644 --- a/data/json/monsters/zed_misc.json +++ b/data/json/monsters/zed_misc.json @@ -152,6 +152,7 @@ "name": { "str": "zombie wrestler" }, "description": "A slab of festering muscle the size of a well-toned bodybuilder. With popping and cracking sounds its arm muscles constantly lengthen and contract as it reaches out with deformed muscular hands the size of dinner plates.", "copy-from": "mon_zombie_brute", + "species": [ "ZOMBIE" ], "diff": 3, "volume": "108500 ml", "weight": "94500 g", @@ -210,6 +211,7 @@ "name": { "str": "zombie prowler" }, "description": "Enveloped in darkness is the outline of what used to be a person, quick and spindly - and nigh invisible in the shadows. Even with the unnatural camouflage hiding its features you can make out large teeth and even larger claws.", "copy-from": "mon_zombie_base", + "species": [ "ZOMBIE" ], "looks_like": "mon_zombie_brute_ninja", "diff": 2, "hp": 160, @@ -249,6 +251,7 @@ "//": "Upgraded version of brainless. Regenerating Skull with huge ears.", "description": "This zombie's head was once obviously destroyed, the gaps in its scraps of face now filling with a peculiar gray goo. Human ears hang from the sides, enormous and unsettling. Thin slits at the front suggest it may have a (very limited) sense of sight.", "copy-from": "mon_zombie_base", + "species": [ "ZOMBIE" ], "volume": "62275 ml", "weight": "79800 g", "//2": "Weight and volume changed to reflect a (mostly) lack of head.", @@ -271,6 +274,7 @@ "name": { "str": "relentless hulk" }, "description": "A hulking zombie swollen to the size of six men. Its inky black eyes are locked on you. No matter how far you run, it always seems to find you.", "copy-from": "mon_zombie_base", + "species": [ "ZOMBIE" ], "diff": 5, "volume": "875000 ml", "weight": "1000 kg", @@ -361,6 +365,7 @@ "name": { "str": "zombie hollow" }, "description": "This zombie's hollow black eyes survey its surroundings as it stretches and bends in ways that whoever the original body belonged to never could. The only things that seem solid on this flexible, black-veined body are the rows of sharp, black teeth. You get the feeling that the only human thing remaining is the skin, worn as one might wear clothes.", "copy-from": "mon_zombie_base", + "species": [ "ZOMBIE" ], "hp": 100, "color": "black_white", "scents_tracked": [ "sc_human", "sc_fetid" ], @@ -388,6 +393,7 @@ "name": { "str": "zombie hulk" }, "description": "A human corpse swollen to the size of six men, with arms as wide as trash cans.", "copy-from": "mon_zombie_base", + "species": [ "ZOMBIE" ], "diff": 5, "volume": "875 L", "weight": "1000 kg", @@ -421,6 +427,7 @@ "name": { "str": "zombie hunter" }, "description": "You're barely able to believe this thing was ever human; it scrambles about on all fours, its nails and teeth sharpened into dangerous-looking spikes.", "copy-from": "mon_zombie_base", + "species": [ "ZOMBIE" ], "hp": 90, "speed": 110, "color": "brown", @@ -455,6 +462,7 @@ "name": { "str": "zombie snapper" }, "description": "With a crocodile-like snout and rows of protruding teeth, this swimwear-clad zombie lurks in the water.", "copy-from": "mon_zombie_base", + "species": [ "ZOMBIE" ], "hp": 120, "speed": 100, "color": "light_green_cyan", @@ -522,6 +530,7 @@ "name": { "str": "zombie necromancer" }, "description": "A twisted mockery of the human form, emaciated, with jet-black skin and glowing red eyes. It is somehow painful to look at, awakening fears deep within your psyche, and even the surrounding air seems more sinister, somehow darker and more dangerous.", "copy-from": "mon_zombie_base", + "species": [ "ZOMBIE" ], "diff": 20, "hp": 100, "speed": 100, @@ -605,6 +614,7 @@ "name": { "str": "fleshy hunter" }, "description": "A zombie prowling around on all fours; its exposed muscles churn and snake, unraveling before restitching themselves elsewhere along its red-raw figure.", "copy-from": "mon_zombie_hunter", + "species": [ "ZOMBIE" ], "regenerates": 12, "color": "red_cyan", "upgrades": { "half_life": 35, "into": "mon_zombie_regenerating_final" }, @@ -647,6 +657,7 @@ "name": { "str": "zombie predator" }, "description": "With its joints in odd places and angles, this humanoid creature prowls across the landscape with surprising speed. Its teeth and arms are sharpened into fine points, and black ooze seeps out from cuts between its muscles.", "copy-from": "mon_zombie_hunter", + "species": [ "ZOMBIE" ], "speed": 140, "color": "brown_green", "melee_skill": 5, @@ -704,6 +715,7 @@ "name": { "str": "shady zombie" }, "description": "An uncanny shadow envelops this creature, as if light itself were too repulsed to touch it. All you can make out is its shambling, human-shaped outline.", "copy-from": "mon_zombie_base", + "species": [ "ZOMBIE" ], "color": "light_gray", "scents_tracked": [ "sc_human", "sc_fetid" ], "vision_day": 3, diff --git a/data/json/monsters/zed_skeletal.json b/data/json/monsters/zed_skeletal.json index 931e304b400c0..651259232e4e4 100644 --- a/data/json/monsters/zed_skeletal.json +++ b/data/json/monsters/zed_skeletal.json @@ -5,6 +5,7 @@ "name": { "str": "skeletal zombie" }, "description": "A monstrous overgrowth of ossified tissue has replaced this zombie's rotting skin with an organic armor of dense bone. Large clumps of black goo seep from its joints as it shambles aimlessly, with sickening crackling sounds filling the surrounding air.", "copy-from": "mon_zombie_base", + "species": [ "ZOMBIE" ], "speed": 60, "material": [ "bone" ], "color": "white", @@ -25,6 +26,7 @@ "name": { "str": "skeletal brute" }, "description": "Distorted outgrowths of calcified bone plates cover this zombie's rotten skin. Joints and cracks around its body ooze with black goo.", "copy-from": "mon_zombie_brute", + "species": [ "ZOMBIE" ], "volume": "108500 ml", "weight": "120 kg", "hp": 175, @@ -58,6 +60,7 @@ "name": { "str": "skeletal shocker" }, "description": "Heavy, jagged bone plates have grown out of the surface of this zombie's skin. Underneath, its flesh glows and crackles with the occasional jolt of electricity.", "copy-from": "mon_zombie_base", + "species": [ "ZOMBIE" ], "diff": 15, "hp": 105, "speed": 60, @@ -89,6 +92,7 @@ "name": { "str": "skeletal juggernaut" }, "description": "This hideous golem of plated bones and misshapen flesh drags its heavy, pointed limbs behind it like an unwanted burden. Formerly soft and vulnerable, bones grew around its form to protect it - only, they kept growing. And growing. And growing.", "copy-from": "mon_zombie_hulk", + "species": [ "ZOMBIE" ], "speed": 60, "material": [ "bone" ], "color": "white", diff --git a/data/json/monsters/zed_soldiers.json b/data/json/monsters/zed_soldiers.json index dae316e36c4cb..1fb27453faf69 100644 --- a/data/json/monsters/zed_soldiers.json +++ b/data/json/monsters/zed_soldiers.json @@ -312,6 +312,7 @@ "id": "mon_bestial_stalker", "type": "MONSTER", "copy-from": "mon_zombie_marine_upgrade", + "species": [ "ZOMBIE" ], "looks_like": "mon_zombie_marine_upgrade", "//": "This is a variation which will drop default military equipment, rather than specific naval uniforms and gear.", "description": "Lumbering about on all fours, this mutated beast's dagger-like claws clack against the ground as it predatorially moves: thick strands of exposed muscle tissue running across its rotting body. The addition of its new bulk has caused the skin along its arms and back to split, and the brute's teeth have extended into spikes of bone. The military insignias on the remains of the creature's pulverized gear are the only testaments to the soldier that this hulking abomination used to be.", diff --git a/data/json/monsters/zed_tentacle.json b/data/json/monsters/zed_tentacle.json index 293ceb0fd63c4..b64c0a650af7e 100644 --- a/data/json/monsters/zed_tentacle.json +++ b/data/json/monsters/zed_tentacle.json @@ -54,6 +54,7 @@ "name": { "str": "zombie strider" }, "description": "In front of you lies the most disgusting rendition of a starfish you've ever seen. Not just the arms, but the legs and even the head have been horrendously deformed and stretched several meters long. It walks around hunchback, looking through the remains of its head for its next victim.", "copy-from": "mon_zombie_base", + "species": [ "ZOMBIE" ], "diff": 10, "hp": 180, "speed": 60, diff --git a/data/json/recipes/recipe_music_instruments.json b/data/json/recipes/recipe_music_instruments.json index bcc4d0f656120..5d8800ca82f73 100644 --- a/data/json/recipes/recipe_music_instruments.json +++ b/data/json/recipes/recipe_music_instruments.json @@ -10,7 +10,7 @@ "time": "620 m", "autolearn": true, "qualities": [ { "id": "LUTHIER", "level": 1 }, { "id": "SAW_W", "level": 2 }, { "id": "CHISEL_WOOD", "level": 1 } ], - "proficiencies": [ { "proficiency": "prof_carpentry_basic" } ], + "proficiencies": [ { "proficiency": "prof_carpentry_basic" }, { "proficiency": "prof_luthier_basic" } ], "byproducts": [ [ "splinter", 68 ] ], "components": [ [ [ "tonewood", 2 ] ], @@ -31,7 +31,7 @@ "time": "420 m", "autolearn": true, "qualities": [ { "id": "LUTHIER", "level": 1 }, { "id": "SAW_W", "level": 2 }, { "id": "CHISEL_WOOD", "level": 1 } ], - "proficiencies": [ { "proficiency": "prof_carpentry_basic" } ], + "proficiencies": [ { "proficiency": "prof_carpentry_basic" }, { "proficiency": "prof_luthier_basic" } ], "byproducts": [ [ "splinter", 68 ] ], "components": [ [ [ "tonewood", 3 ] ], @@ -52,7 +52,7 @@ "time": "720 m", "autolearn": true, "qualities": [ { "id": "LUTHIER", "level": 1 }, { "id": "SAW_W", "level": 2 }, { "id": "CHISEL_WOOD", "level": 1 } ], - "proficiencies": [ { "proficiency": "prof_carpentry_basic" } ], + "proficiencies": [ { "proficiency": "prof_carpentry_basic" }, { "proficiency": "prof_luthier_basic" } ], "byproducts": [ [ "splinter", 89 ] ], "components": [ [ [ "tonewood", 2 ] ], diff --git a/data/mods/Aftershock/EOC/monster_weakpoint_eocs.json b/data/mods/Aftershock/EOC/monster_weakpoint_eocs.json new file mode 100644 index 0000000000000..ee807b2281ea5 --- /dev/null +++ b/data/mods/Aftershock/EOC/monster_weakpoint_eocs.json @@ -0,0 +1,19 @@ +[ + { + "type": "effect_on_condition", + "id": "EOC_AFS_INSTANT_DEATH", + "condition": "has_beta", + "effect": [ "npc_die" ] + }, + { + "type": "effect_on_condition", + "id": "EOC_AFS_REACTOR_MELTDOWN", + "condition": "has_beta", + "effect": [ + { "npc_location_variable": { "context_val": "loc" } }, + { "map_spawn_item": "afs_reactor_unstable", "loc": { "context_val": "loc" } }, + { "npc_add_effect": "effect_robot_immobilized", "duration": "PERMANENT" }, + { "u_message": "The malfunctioning reactor is ejected." } + ] + } +] diff --git a/data/mods/Aftershock/effects.json b/data/mods/Aftershock/effects.json index 0af0100fafd60..7af4b265ae16f 100644 --- a/data/mods/Aftershock/effects.json +++ b/data/mods/Aftershock/effects.json @@ -243,6 +243,16 @@ "flags": [ "LEVITATION" ], "show_in_info": true }, + { + "type": "effect_type", + "id": "effect_robot_immobilized", + "name": [ "Immobilized" ], + "desc": [ "You are completely immobile" ], + "rating": "bad", + "show_in_info": true, + "remove_message": "You can move again.", + "flags": [ "CANNOT_ATTACK", "CANNOT_MOVE" ] + }, { "type": "effect_type", "id": "afs_medigel_eff_trigger" @@ -331,5 +341,12 @@ "id": "afs_cureall", "removes_effects": [ "afs_badpoison" ], "base_mods": { "pkill_min": [ 5 ] } + }, + { + "type": "effect_type", + "id": "afs_ai_defensive", + "name": [ "Defensive Stance" ], + "show_in_info": true, + "desc": [ { "str": "This creature is actively defending itself." } ] } ] diff --git a/data/mods/Aftershock/emit.json b/data/mods/Aftershock/emit.json index 1b27b3a3cc446..3508d2c4370de 100644 --- a/data/mods/Aftershock/emit.json +++ b/data/mods/Aftershock/emit.json @@ -22,5 +22,13 @@ "intensity": 3, "chance": 70, "qty": 70 + }, + { + "id": "weak_rad_glimmer", + "type": "emit", + "field": "fd_rad_glimmer", + "intensity": 3, + "chance": 100, + "qty": 12 } ] diff --git a/data/mods/Aftershock/itemgroups/weapons/armories.json b/data/mods/Aftershock/itemgroups/weapons/armories.json index 7575acae309b0..742e2385fe9dd 100644 --- a/data/mods/Aftershock/itemgroups/weapons/armories.json +++ b/data/mods/Aftershock/itemgroups/weapons/armories.json @@ -21,7 +21,7 @@ "id": "afs_grenade_armory", "type": "item_group", "subtype": "distribution", - "items": [ { "group": "afs_any_hand_grenade", "prob": 3 } ] + "items": [ { "group": "afs_any_hand_grenade", "prob": 3 }, { "group": "afs_any_mine", "prob": 2 } ] }, { "id": "afs_energy_weapon_armory", diff --git a/data/mods/Aftershock/itemgroups/weapons/grenade_groups.json b/data/mods/Aftershock/itemgroups/weapons/grenade_groups.json index 24c0c8bb191d2..15f603f499257 100644 --- a/data/mods/Aftershock/itemgroups/weapons/grenade_groups.json +++ b/data/mods/Aftershock/itemgroups/weapons/grenade_groups.json @@ -15,6 +15,12 @@ { "item": "grenade_emp", "count": [ 1, 3 ] } ] }, + { + "id": "afs_any_mine", + "type": "item_group", + "subtype": "distribution", + "entries": [ { "item": "bot_shock_mine", "count": [ 3, 5 ] } ] + }, { "id": "afs_anti_robot_grenades", "type": "item_group", diff --git a/data/mods/Aftershock/items/corpses.json b/data/mods/Aftershock/items/corpses.json index ee6f05eb58104..df3566a511905 100644 --- a/data/mods/Aftershock/items/corpses.json +++ b/data/mods/Aftershock/items/corpses.json @@ -342,6 +342,40 @@ "flags": [ "TRADER_AVOID", "NO_REPAIR" ], "melee_damage": { "bash": 6, "cut": 6 } }, + { + "type": "GENERIC", + "id": "broken_shock_mine", + "symbol": ",", + "color": "green", + "name": { "str": "spent shock-mine" }, + "category": "other", + "description": "A spent shock-mine, inert and harmless. Cannot be recharged, but some of its components could be recycled.", + "price": "100 USD", + "price_postapoc": "100 USD", + "material": [ "qt_steel", "plastic" ], + "volume": "1 L", + "weight": "1200 g", + "to_hit": -3, + "flags": [ "TRADER_AVOID", "NO_REPAIR" ], + "melee_damage": { "bash": 4, "cut": 1 } + }, + { + "type": "GENERIC", + "id": "broken_zenit", + "symbol": ",", + "color": "green", + "name": { "str": "broken zenit drone" }, + "category": "other", + "description": "A broken zenit security drone. Could be disassembled for robotic components and heavy armor.", + "price": "100 USD", + "price_postapoc": "100 USD", + "material": [ "qt_steel", "vacuum_carbide" ], + "volume": "60 L", + "weight": "120 kg", + "to_hit": -3, + "flags": [ "TRADER_AVOID", "NO_REPAIR" ], + "melee_damage": { "bash": 4, "cut": 1 } + }, { "type": "GENERIC", "id": "afs_broken_copbot", diff --git a/data/mods/Aftershock/items/grenades.json b/data/mods/Aftershock/items/grenades.json index a43395f22456d..881568e822714 100644 --- a/data/mods/Aftershock/items/grenades.json +++ b/data/mods/Aftershock/items/grenades.json @@ -245,5 +245,25 @@ "name": "active oxygen bomb", "price": "0 USD", "description": "This bomb's fuse is lit, and it will explode any second now. Throw it immediately!" + }, + { + "id": "afs_reactor_unstable", + "type": "TOOL", + "category": "weapons", + "name": "unstable fusion reactor", + "looks_like": "c4armed", + "description": "A pressurized plasma reactor that is on the verge of a catastrophic explosion.", + "weight": "4400 g", + "volume": "10 L", + "price": "0 cent", + "to_hit": -5, + "material": [ "steel" ], + "symbol": "(", + "color": "light_red", + "countdown_interval": "3 seconds", + "explode_in_fire": true, + "explosion": { "power": 28000, "max_noise": 150, "distance_factor": 0.15 }, + "countdown_action": { "type": "explosion", "explosion": { "power": 28000, "max_noise": 150, "distance_factor": 0.15 } }, + "flags": [ "BOMB", "TRADER_AVOID", "SPAWN_ACTIVE" ] } ] diff --git a/data/mods/Aftershock/items/gun/40mm_grenade.json b/data/mods/Aftershock/items/gun/40mm_grenade.json new file mode 100644 index 0000000000000..a99ffcc931d2f --- /dev/null +++ b/data/mods/Aftershock/items/gun/40mm_grenade.json @@ -0,0 +1,17 @@ +[ + { + "id": "afs_launcher_salvaged", + "copy-from": "m320", + "looks_like": "m79", + "type": "GUN", + "name": { "str": "vatforged grenade launcher" }, + "description": "A crude grenade launcher that's been either ripped from a broken robot or built using a hacked template. The remnants of a loading rack allow it to hold three 40mm grenades at once.", + "price": "300 USD", + "price_postapoc": "300 USD", + "clip_size": 3, + "reload": 200, + "extend": { "flags": [ "RELOAD_ONE" ] }, + "pocket_data": [ { "pocket_type": "MAGAZINE", "rigid": true, "ammo_restriction": { "40x46mm": 3 } } ], + "melee_damage": { "bash": 6 } + } +] diff --git a/data/mods/Aftershock/items/gun/voltaic.json b/data/mods/Aftershock/items/gun/voltaic.json index b11b2c1a90b35..24303efcef336 100644 --- a/data/mods/Aftershock/items/gun/voltaic.json +++ b/data/mods/Aftershock/items/gun/voltaic.json @@ -80,5 +80,28 @@ ], "ammo_effects": [ "BEANBAG" ], "flags": [ "NEVER_JAMS", "NON_FOULING", "NEEDS_NO_LUBE" ] + }, + { + "id": "afs_mine_shocker", + "type": "GUN", + "symbol": "%", + "color": "blue", + "name": { "str": "mine shocker", "//~": "NO_I18N" }, + "description": { "str": "How shocking!", "//~": "NO_I18N" }, + "material": [ "qt_steel" ], + "flags": [ "PSEUDO", "NEVER_JAMS", "NONCONDUCTIVE", "NO_REPAIR", "WATERPROOF_GUN", "NO_SALVAGE", "NO_UNLOAD", "NO_TURRET" ], + "skill": "pistol", + "ammo_effects": [ "LIGHTNING" ], + "ranged_damage": { "damage_type": "electric", "amount": 4 }, + "weight": "12 g", + "volume": "12 ml", + "longest_side": "25 cm", + "to_hit": 1, + "reload_noise_volume": 2, + "loudness": 2, + "range": 12, + "dispersion": 150, + "durability": 8, + "melee_damage": { "bash": 2 } } ] diff --git a/data/mods/Aftershock/items/inactiverobot.json b/data/mods/Aftershock/items/inactiverobot.json index 7fe0121892fbe..dc0e6462f7f84 100644 --- a/data/mods/Aftershock/items/inactiverobot.json +++ b/data/mods/Aftershock/items/inactiverobot.json @@ -277,6 +277,23 @@ "is_pet": true } }, + { + "id": "bot_shock_mine", + "type": "TOOL", + "copy-from": "bot_hack_base", + "name": "inactive shock-mine", + "description": "A less-than-lethal mine that emits a powerful electrical shock when triggered. Activate this item to deploy the mine, which will have a lifetime of 10 hours after activation.", + "color": "yellow", + "volume": "1 L", + "weight": "1200 g", + "use_action": { + "type": "place_monster", + "monster_id": "mon_shock_mine", + "difficulty": 1, + "moves": 100, + "skills": [ "traps", "computer" ] + } + }, { "abstract": "bot_medibot_base", "type": "TOOL", diff --git a/data/mods/Aftershock/items/vehicle_items.json b/data/mods/Aftershock/items/vehicle_items.json index 877c1f7a4ef6b..870b63e991979 100644 --- a/data/mods/Aftershock/items/vehicle_items.json +++ b/data/mods/Aftershock/items/vehicle_items.json @@ -16,6 +16,25 @@ "use_action": "CAPTURE_MONSTER_VEH", "flags": [ "TRADER_AVOID" ] }, + { + "type": "GENERIC", + "id": "afs_mil_ship_plate", + "name": { "str": "military ablative plating" }, + "description": "A segment of thick armor plating that would normally be found mounted on a spaceship. Incredibly heavy.", + "weight": "28500 g", + "to_hit": -1, + "color": "green", + "symbol": "]", + "material": [ "qt_steel", "vacuum_carbide" ], + "volume": "10 L", + "category": "veh_parts", + "price": "160 USD", + "price_postapoc": "7 USD 50 cent", + "flags": [ "NO_REPAIR" ], + "qualities": [ [ "COOK", 1 ] ], + "use_action": [ "HEAT_SOLID_ITEMS" ], + "melee_damage": { "bash": 8 } + }, { "type": "GENERIC", "id": "exo_gantry", diff --git a/data/mods/Aftershock/mobs/monster_attacks/zenit.json b/data/mods/Aftershock/mobs/monster_attacks/zenit.json new file mode 100644 index 0000000000000..bcfba036f6b0f --- /dev/null +++ b/data/mods/Aftershock/mobs/monster_attacks/zenit.json @@ -0,0 +1,137 @@ +[ + { + "type": "effect_on_condition", + "id": "EOC_ZENIT_CONTROL", + "effect": [ + { + "run_eocs": [ + { + "id": "zenit_setup", + "condition": { "math": [ "u_setup != 1" ] }, + "effect": [ + { "math": [ "u_setup = 1" ] }, + { "math": [ "u_timer_zenit_shock_mines = 0" ] }, + { "math": [ "u_timer_zenit_shock_att = 0" ] }, + { "math": [ "u_timer_zenit_smoke = 0" ] } + ] + } + ] + }, + { "u_location_variable": { "context_val": "my_loc" } }, + { "npc_location_variable": { "context_val": "t_loc" } }, + { "math": [ "_distance = distance('u', 'npc')" ] }, + { + "switch": { "math": [ "_distance" ] }, + "cases": [ + { + "case": 0, + "effect": [ + { "run_eocs": [ "eoc_zenit_shock_mines" ] }, + { "run_eocs": [ "eoc_zenit_smoke" ], "variables": { "tar": { "context_val": "my_loc" } } } + ] + }, + { + "case": 6, + "effect": [ { "run_eocs": [ "eoc_zenit_shock_att" ], "variables": { "tar": { "context_val": "t_loc" } } } ] + }, + { "case": 12, "effect": [ { "run_eocs": [ "eoc_zenit_def" ] } ] }, + { + "case": 25, + "effect": [ { "run_eocs": [ "eoc_zenit_smoke", "eoc_zenit_def" ], "variables": { "tar": { "context_val": "t_loc" } } } ] + } + ] + } + ] + }, + { + "id": "eoc_zenit_def", + "type": "effect_on_condition", + "condition": { "not": { "npc_has_any_effect": [ "afs_ai_defensive" ] } }, + "effect": [ + { "u_add_effect": "afs_ai_defensive", "duration": "10 minutes" }, + { + "run_eocs": [ + { + "id": "avatar_sees_zenit_def", + "condition": "player_see_u", + "effect": [ { "message": "The Zenit crouches forward, hiding most of its body behind its upper armor plate." } ] + } + ] + } + ] + }, + { + "id": "eoc_zenit_undef", + "type": "effect_on_condition", + "condition": { "and": [ { "u_has_any_effect": [ "afs_ai_defensive" ] } ] }, + "effect": [ + { "u_lose_effect": "afs_ai_defensive" }, + { + "run_eocs": [ + { + "id": "avatar_sees_zenit_undef", + "condition": "player_see_u", + "effect": [ { "message": "The Zenit raises its body." } ] + } + ] + } + ] + }, + { + "id": "eoc_zenit_shock_att", + "type": "effect_on_condition", + "condition": { "and": [ { "expects_vars": [ "tar" ] }, { "math": [ "time_since(u_timer_zenit_shock_att) > time(' 12 s')" ] } ] }, + "effect": [ + { "run_eocs": [ "eoc_zenit_undef" ], "alpha_talker": "u" }, + { "math": [ "u_timer_zenit_shock_att = time('now')" ] }, + { "u_cast_spell": { "id": "spell_electric_chain_2" }, "loc": { "context_val": "tar" } }, + { + "run_eocs": [ + { + "id": "avatar_sees_zenit_shock_att", + "condition": "player_see_u", + "effect": [ { "message": "The Zenit emits an explosion of arcing electricity." } ] + } + ] + } + ] + }, + { + "id": "eoc_zenit_shock_mines", + "type": "effect_on_condition", + "condition": { "and": [ { "math": [ "time_since(u_timer_zenit_shock_mines) > time(' 5 m')" ] } ] }, + "effect": [ + { "run_eocs": [ "eoc_zenit_undef" ], "alpha_talker": "u" }, + { "math": [ "u_timer_zenit_shock_mines = time('now')" ] }, + { "u_spawn_monster": "mon_shock_mine", "real_count": 30, "min_radius": 5, "max_radius": 13 }, + { + "run_eocs": [ + { + "id": "avatar_sees_zenit_shock_mines", + "condition": "player_see_u", + "effect": [ { "message": "Several mines are expelled from the Zenit's munitions bay" } ] + } + ] + } + ] + }, + { + "id": "eoc_zenit_smoke", + "type": "effect_on_condition", + "condition": { "and": [ { "expects_vars": [ "tar" ] }, { "math": [ "time_since(u_timer_zenit_smoke) > time(' 40 s')" ] } ] }, + "effect": [ + { "run_eocs": [ "eoc_zenit_undef" ], "alpha_talker": "u" }, + { "math": [ "u_timer_zenit_smoke = time('now')" ] }, + { "u_cast_spell": { "id": "quadraphract_smoke_mortar" }, "loc": { "context_val": "tar" } }, + { + "run_eocs": [ + { + "id": "avatar_sees_zenit_smoke", + "condition": "player_see_u", + "effect": [ { "message": "Several bomblets are expelled from the Zenit's munitions bay" } ] + } + ] + } + ] + } +] diff --git a/data/mods/Aftershock/mobs/monster_groups/robot_monster_groups.json b/data/mods/Aftershock/mobs/monster_groups/robot_monster_groups.json index 3de8db8ce76e0..b3ca1f6b0338a 100644 --- a/data/mods/Aftershock/mobs/monster_groups/robot_monster_groups.json +++ b/data/mods/Aftershock/mobs/monster_groups/robot_monster_groups.json @@ -59,6 +59,7 @@ "name": "GROUP_ROBOT_COPS_HOSTILE", "default": "mon_manhack", "monsters": [ + { "monster": "mon_zenit", "weight": 50, "cost_multiplier": 100 }, { "monster": "mon_skitterbot", "weight": 200, "cost_multiplier": 20 }, { "monster": "mon_afs_eyebot", "weight": 200, "cost_multiplier": 4 }, { "monster": "mon_afs_copbot", "weight": 100, "cost_multiplier": 70 }, diff --git a/data/mods/Aftershock/mobs/monster_weakpoints/robot_weakpoints.json b/data/mods/Aftershock/mobs/monster_weakpoints/robot_weakpoints.json new file mode 100644 index 0000000000000..2f7c188b5a217 --- /dev/null +++ b/data/mods/Aftershock/mobs/monster_weakpoints/robot_weakpoints.json @@ -0,0 +1,213 @@ +[ + { + "type": "weakpoint_set", + "id": "afs_wps_robot", + "weakpoints": [ + { + "id": "power_plant", + "name": "the main power plant", + "coverage": 1, + "difficulty": { "melee": 10, "ranged": 5 }, + "coverage_mult": { "melee": 0 }, + "armor_mult": { "all": 1.5 }, + "effects": [ + { + "effect_on_conditions": [ "EOC_AFS_INSTANT_DEATH" ], + "message": "The %s power plants sparks and smokes.", + "chance": 100, + "damage_required": [ 1, 100 ] + } + ] + }, + { + "id": "cpu", + "name": "the AI core", + "coverage": 1, + "difficulty": { "melee": 10, "ranged": 5 }, + "coverage_mult": { "melee": 0 }, + "armor_mult": { "all": 2 }, + "effects": [ + { + "effect_on_conditions": [ "EOC_AFS_INSTANT_DEATH" ], + "message": "The %s processor is completely destroyed!", + "chance": 100, + "damage_required": [ 1, 100 ] + } + ] + }, + { + "id": "governor", + "name": "the motive governor", + "coverage": 1, + "difficulty": { "melee": 10, "ranged": 5 }, + "coverage_mult": { "melee": 0 }, + "armor_mult": { "all": 2 }, + "effects": [ + { "effect": "downed", "duration": [ 5, 10 ], "message": "The %s stumbles", "damage_required": [ 1, 2 ] }, + { + "effect": "effect_robot_immobilized", + "permanent": true, + "duration": 86400, + "chance": 100, + "message": "The %s collapses to the ground as its limbs fail!", + "damage_required": [ 2, 100 ] + } + ] + }, + { + "id": "main_sensor", + "name": "the main sensory array", + "coverage": 5, + "difficulty": { "melee": 4, "ranged": 7 }, + "coverage_mult": { "melee": 3 }, + "armor_mult": { "all": 0.1 }, + "effects": [ + { "effect": "blind", "duration": [ 1, 2 ], "chance": 40, "message": "The %s is blinded!", "damage_required": [ 1, 1 ] }, + { + "effect": "blind", + "permanent": true, + "duration": 86400, + "chance": 100, + "message": "The %s sensor mount is completely destroyed!", + "damage_required": [ 1, 100 ] + } + ] + }, + { + "id": "weak_point", + "name": "a lightly armored segment", + "coverage": 20, + "difficulty": { "melee": 3, "ranged": 7 }, + "coverage_mult": { "ranged": 0.05 }, + "armor_mult": { "all": 1 } + }, + { + "id": "heavy_armor", + "name": "a segment of sloped armor", + "is_good": false, + "armor_mult": { "all": 3 }, + "coverage_mult": { "melee": 1.5 }, + "coverage": 30 + } + ] + }, + { + "type": "weakpoint_set", + "id": "afs_wps_robot_explode", + "weakpoints": [ + { + "id": "power_plant", + "name": "the exposed reactor", + "coverage": 5, + "difficulty": { "melee": 4, "ranged": 5 }, + "condition": { "npc_has_any_effect": [ "maimed_armor" ] }, + "coverage_mult": { "melee": 0 }, + "armor_mult": { "all": 2 }, + "effects": [ + { + "effect_on_conditions": [ "EOC_AFS_REACTOR_MELTDOWN" ], + "chance": 100, + "message": "The %s sounds a nuclear alarm horn as its power plant detunes! Run!", + "damage_required": [ 2, 100 ] + } + ] + } + ] + }, + { + "type": "weakpoint_set", + "id": "afs_wps_zenit", + "weakpoints": [ + { + "id": "joint_servo", + "name": "an exposed servo", + "condition": { "not": { "npc_has_any_effect": [ "blind", "afs_ai_defensive" ] } }, + "coverage": 5, + "difficulty": { "melee": 6, "ranged": 8 }, + "coverage_mult": { "melee": 2 }, + "armor_mult": { "all": 0.1 } + }, + { + "id": "heavy_armor", + "name": "an armored limb", + "armor_mult": { "all": 5 }, + "is_good": false, + "coverage_mult": { "melee": 0.5 }, + "coverage": 20 + }, + { + "id": "main_sensor", + "name": "the oculus", + "coverage": 6, + "difficulty": { "melee": 4, "ranged": 7 }, + "coverage_mult": { "melee": 2 }, + "condition": { "not": { "npc_has_any_effect": [ "blind", "afs_ai_defensive" ] } }, + "armor_mult": { "all": 0.1 }, + "effects": [ + { "effect": "blind", "duration": [ 1, 2 ], "chance": 40, "message": "The %s is blinded!", "damage_required": [ 1, 1 ] }, + { + "effect": "blind", + "permanent": true, + "chance": 100, + "duration": 86400, + "message": "The oculus shatters", + "damage_required": [ 1, 100 ] + } + ] + }, + { + "id": "main_sensor_broken", + "name": "the oculus fixture", + "coverage": 6, + "difficulty": { "melee": 4, "ranged": 7 }, + "coverage_mult": { "melee": 2 }, + "condition": { "and": [ { "npc_has_any_effect": [ "blind" ] }, { "not": { "npc_has_any_effect": [ "afs_ai_defensive" ] } } ] }, + "armor_mult": { "all": 0.1 } + }, + { + "id": "upper_armor", + "name": "the upper armor disk", + "coverage": 30, + "coverage_mult": { "melee": 0.5 }, + "armor_mult": { "all": 10 }, + "condition": { "not": { "npc_has_any_effect": [ "maimed_armor", "afs_ai_defensive" ] } }, + "effects": [ + { + "effect": "maimed_armor", + "duration": 86400, + "chance": 100, + "message": "The Zenit's armor disk is shredded!", + "damage_required": [ 5, 100 ] + } + ] + }, + { + "id": "upper_armor_defensive", + "name": "the upper armor disk", + "coverage": 60, + "is_good": false, + "coverage_mult": { "melee": 0.5 }, + "difficulty": { "melee": 6, "ranged": 10 }, + "armor_mult": { "all": 10 }, + "condition": { "and": [ { "npc_has_any_effect": [ "afs_ai_defensive" ] }, { "not": { "npc_has_any_effect": [ "maimed_armor" ] } } ] }, + "effects": [ + { + "effect": "maimed_armor", + "duration": 86400, + "chance": 100, + "message": "The Zenit's armor disk is shredded!", + "damage_required": [ 5, 100 ] + } + ] + }, + { + "id": "upper_armor_weak", + "name": "the exposed circuitry", + "coverage": 60, + "armor_mult": { "all": 0.1 }, + "condition": { "npc_has_any_effect": [ "maimed_armor" ] }, + "effects": [ { "effect_on_conditions": [ "EOC_AFS_INSTANT_DEATH" ], "chance": 100, "damage_required": [ 1, 100 ] } ] + } + ] + } +] diff --git a/data/mods/Aftershock/mobs/robots.json b/data/mods/Aftershock/mobs/robots.json index 5111c55bd25d8..e839ce66548a8 100644 --- a/data/mods/Aftershock/mobs/robots.json +++ b/data/mods/Aftershock/mobs/robots.json @@ -419,6 +419,42 @@ "special_attacks": [ { "id": "smash", "throw_strength": 96 } ], "extend": { "flags": [ "BASHES", "DESTROYS", "ATTACKMON" ] } }, + { + "id": "mon_zenit", + "type": "MONSTER", + "name": { "str_sp": "TsKBEM Zenit", "//~": "Its in Russian. Not a typo." }, + "looks_like": "mon_hazmatbot", + "description": "An ancient security drone intended to safeguard extractive outposts in hostile environments. Its construction vaguely recalls an alien crustacean, with a single sensory oculus and four spade-like legs mounted underneath a disk of space-ship grade armor. Zenit units can mount a wide variety of \"deterrent\" weapon modules, and its difficult to tell what this rogue unit is capable of.", + "default_faction": "rampant_machine", + "species": [ "ROBOT" ], + "volume": "62 L", + "weight": "81500 g", + "hp": 1200, + "speed": 70, + "material": [ "steel" ], + "symbol": "M", + "color": "yellow", + "morale": 80, + "aggression": 50, + "anger_triggers": [ "HURT", "PLAYER_CLOSE", "FRIEND_ATTACKED" ], + "vision_day": 50, + "bleed_rate": 0, + "death_function": { "corpse_type": "BROKEN" }, + "special_attacks": [ { "id": "zenit_control", "cooldown": 5 } ], + "weakpoint_sets": [ "afs_wps_robot", "afs_wps_robot_explode", "afs_wps_zenit" ], + "death_drops": { "groups": [ [ "broken_robots", 3 ] ] }, + "flags": [ + "SEES", + "HEARS", + "ELECTRONIC", + "BIOLOGICALPROOF", + "NO_BREATHE", + "PRIORITIZE_TARGETS", + "PATH_AVOID_DANGER", + "STUN_IMMUNE" + ], + "armor": { "bash": 15, "cut": 30, "acid": 100, "bullet": 25, "heat": 20, "afs_plasma": 1 } + }, { "id": "mon_utilibot_fire", "type": "MONSTER", @@ -827,6 +863,49 @@ } ] }, + { + "id": "mon_shock_mine", + "type": "MONSTER", + "name": { "str": "shock-mine" }, + "//": "A monster so that the player and other monsters can shoot at it without the need of custom AI.", + "description": "A bulky device that will constantly discharge electricity in a small radius around it.", + "default_faction": "rampant_machine", + "species": [ "ROBOT" ], + "diff": 12, + "volume": "1 L", + "weight": "1200 g", + "hp": 5, + "speed": 100, + "material": [ "steel" ], + "symbol": "i", + "color": "light_gray", + "aggression": 100, + "morale": 100, + "bleed_rate": 0, + "vision_night": 4, + "luminance": 10, + "emit_fields": [ { "emit_id": "emit_spark", "delay": "1 s" } ], + "special_attacks": [ + { + "type": "gun", + "cooldown": 1, + "gun_type": "afs_mine_shocker", + "fake_skills": [ [ "gun", 2 ], [ "rifle", 3 ] ], + "ranges": [ [ 0, 5, "DEFAULT" ] ] + }, + { + "type": "spell", + "spell_data": { "id": "shock_mine_control", "min_level": 1, "hit_self": true }, + "allow_no_target": true, + "monster_message": "", + "cooldown": 3 + } + ], + "death_function": { "corpse_type": "BROKEN" }, + "//2": "Deliberatedly electric and not electronic, so it can be immune to electric damageand EMP.", + "flags": [ "SEES", "NOHEAD", "ELECTRIC", "BIOLOGICALPROOF", "COLDPROOF", "IMMOBILE", "NO_BREATHE" ], + "armor": { "bash": 5, "cut": 2, "bullet": 3, "stab": 0, "electric": 100 } + }, { "id": "mon_afs_eyebot", "type": "MONSTER", diff --git a/data/mods/Aftershock/monster_attacks.json b/data/mods/Aftershock/monster_attacks.json index 38da6648685c8..90b4d7e46f257 100644 --- a/data/mods/Aftershock/monster_attacks.json +++ b/data/mods/Aftershock/monster_attacks.json @@ -4,7 +4,7 @@ "attack_type": "melee", "id": "hypo_pkill", "cooldown": 5, - "move_cost": 150, + "move_cost": 0, "damage_max_instance": [ { "damage_type": "stab", "amount": 5, "armor_penetration": 15, "armor_multiplier": 0.2 } ], "effects": [ { "id": "pkill3", "duration": 300 }, { "id": "pkill2", "duration": 600 } ], "hit_dmg_u": "%1$s injects you with a syringe!", @@ -12,6 +12,49 @@ "no_dmg_msg_u": "%1$s tries to inject you, but fails to penetrate your armor!", "no_dmg_msg_npc": "%1$s tries to inject , but fails to penetrate their armor!" }, + { + "type": "monster_attack", + "attack_type": "melee", + "id": "zenit_control", + "cooldown": 3, + "move_cost": 0, + "range": 35, + "dodgeable": false, + "blockable": false, + "damage_max_instance": [ { "damage_type": "bash", "amount": 0 } ], + "eoc": [ "EOC_ZENIT_CONTROL" ], + "hit_dmg_u": "", + "hit_dmg_npc": "", + "miss_msg_u": "", + "miss_msg_npc": "", + "no_dmg_msg_u": "", + "no_dmg_msg_npc": "" + }, + { + "id": "shock_mine_control", + "type": "SPELL", + "name": { "str": "Sock mine control", "//~": "NO_I18N" }, + "description": { "str": "Shock mines control themselves using this one.", "//~": "NO_I18N" }, + "valid_targets": [ "self" ], + "flags": [ "SILENT", "NO_EXPLOSION_SFX" ], + "shape": "blast", + "min_range": 1, + "max_range": 1, + "message": "", + "effect": "effect_on_condition", + "effect_str": "EOC_SHOCK_MINE_CONTROL" + }, + { + "id": "EOC_SHOCK_MINE_CONTROL", + "type": "effect_on_condition", + "effect": [ + { + "if": { "math": [ "has_var(u_death_timer)" ] }, + "then": [ { "if": { "math": [ "time_since(u_death_timer) > time(' 8 h')" ] }, "then": [ "u_die" ] } ], + "else": [ { "math": [ "u_death_timer = time('now')" ] } ] + } + ] + }, { "type": "monster_attack", "attack_type": "melee", diff --git a/data/mods/Aftershock/npcs/Augustmoon_Salvors/augustmoon_gun_trader.json b/data/mods/Aftershock/npcs/Augustmoon_Salvors/augustmoon_gun_trader.json index 0b2e04d3a65f8..671a0edd04f76 100644 --- a/data/mods/Aftershock/npcs/Augustmoon_Salvors/augustmoon_gun_trader.json +++ b/data/mods/Aftershock/npcs/Augustmoon_Salvors/augustmoon_gun_trader.json @@ -46,7 +46,8 @@ { "group": "afs_augustmoon_guntrader_military_gun", "count": [ 1, 2 ] }, { "group": "afs_augustmoon_guntrader_military_ammo", "count": [ 4, 12 ] }, { "item": "UPS_OFF", "charges": 1000 }, - { "group": "afs_any_hand_grenade", "count": [ 4, 8 ] } + { "group": "afs_any_hand_grenade", "count": [ 4, 8 ] }, + { "group": "afs_any_mine", "count": [ 2, 3 ] } ] }, { diff --git a/data/mods/Aftershock/recipes/deconstruction/robot.json b/data/mods/Aftershock/recipes/deconstruction/robot.json index afffb4381c9a0..e43a12432b2ec 100644 --- a/data/mods/Aftershock/recipes/deconstruction/robot.json +++ b/data/mods/Aftershock/recipes/deconstruction/robot.json @@ -91,5 +91,54 @@ [ [ "solar_cell", 2 ] ], [ [ "canister_empty", 1 ] ] ] + }, + { + "result": "broken_zenit", + "type": "uncraft", + "activity_level": "LIGHT_EXERCISE", + "skill_used": "electronics", + "difficulty": 2, + "time": "240 m", + "using": [ [ "soldering_standard", 3 ] ], + "qualities": [ { "id": "SCREW", "level": 1 } ], + "components": [ + [ [ "ai_module", 1 ] ], + [ [ "self_monitoring_module", 1 ] ], + [ [ "sensor_module", 1 ] ], + [ [ "memory_module", 1 ] ], + [ [ "pathfinding_module", 1 ] ], + [ [ "identification_module", 1 ] ], + [ [ "spidery_legs_big", 1 ] ], + [ [ "targeting_module", 1 ] ], + [ [ "afs_magnet_3", 4 ] ], + [ [ "afs_circuitry_3", 1 ] ], + [ [ "afs_material_1", 10 ] ], + [ [ "afs_material_3", 1 ] ], + [ [ "afs_material_4", 1 ] ], + [ [ "gun_module", 1 ] ], + [ [ "afs_heat_2_salvage", 2 ] ], + [ [ "afs_energy_storage_4", 1 ] ], + [ [ "afs_launcher_salvaged", 1 ] ], + [ [ "bot_shock_mine", 10 ] ], + [ [ "afs_mil_ship_plate", 3 ] ] + ] + }, + { + "result": "broken_shock_mine", + "type": "uncraft", + "activity_level": "LIGHT_EXERCISE", + "skill_used": "electronics", + "difficulty": 2, + "time": "30 m", + "using": [ [ "soldering_standard", 3 ] ], + "qualities": [ { "id": "SCREW", "level": 1 } ], + "components": [ + [ [ "sensor_module", 1 ] ], + [ [ "afs_material_1", 10 ] ], + [ [ "scrap", 2 ] ], + [ [ "afs_heat_1", 1 ] ], + [ [ "afs_energy_storage_3", 1 ] ], + [ [ "canister_empty", 1 ] ] + ] } ] diff --git a/data/mods/Aftershock/recipes/robot_recipes.json b/data/mods/Aftershock/recipes/robot_recipes.json index dbdc9f595ea7d..130ad77dc5e4d 100644 --- a/data/mods/Aftershock/recipes/robot_recipes.json +++ b/data/mods/Aftershock/recipes/robot_recipes.json @@ -117,6 +117,35 @@ [ [ "lens", 1 ] ] ] }, + { + "result": "bot_shock_mine", + "type": "recipe", + "activity_level": "LIGHT_EXERCISE", + "category": "CC_ELECTRONIC", + "subcategory": "CSC_ELECTRONIC_OTHER", + "skill_used": "electronics", + "decomp_learn": 6, + "reversible": true, + "difficulty": 4, + "time": "30 m", + "using": [ [ "soldering_standard", 3 ] ], + "qualities": [ + { "id": "SCREW", "level": 1 }, + { "id": "SCREW_FINE", "level": 1 }, + { "id": "WRENCH", "level": 2 }, + { "id": "WRENCH_FINE", "level": 1 } + ], + "components": [ + [ [ "sensor_module", 1 ] ], + [ [ "afs_material_1", 10 ] ], + [ [ "scrap", 2 ] ], + [ [ "power_supply", 1 ] ], + [ [ "afs_energy_storage_3", 1 ] ], + [ [ "canister_empty", 1 ] ], + [ [ "cable", 60 ] ], + [ [ "afs_heat_1", 1 ] ] + ] + }, { "type": "recipe", "activity_level": "BRISK_EXERCISE", diff --git a/data/mods/Aftershock/vehicles/vehicle_parts.json b/data/mods/Aftershock/vehicles/vehicle_parts.json index 8f0655c61f5cd..a24ec476c341d 100644 --- a/data/mods/Aftershock/vehicles/vehicle_parts.json +++ b/data/mods/Aftershock/vehicles/vehicle_parts.json @@ -36,6 +36,39 @@ "damage_reduction": { "all": 4 }, "variants": [ { "symbols": ")", "symbols_broken": ")" } ] }, + { + "type": "vehicle_part", + "id": "plating_ship", + "name": { "str": "heavy ablative plating" }, + "categories": [ "warfare" ], + "color": "dark_gray", + "broken_color": "light_gray", + "durability": 1600, + "item": "afs_mil_ship_plate", + "location": "armor", + "//": "300 cm weld to install", + "requirements": { + "install": { + "skills": [ [ "mechanics", 6 ] ], + "time": "60 m", + "using": [ [ "welding_standard", 300 ], [ "vehicle_bolt_install", 4 ] ] + }, + "removal": { + "skills": [ [ "mechanics", 4 ] ], + "time": "30 m", + "using": [ [ "vehicle_weld_removal_cut_resistant", 1 ], [ "vehicle_wrench_2", 1 ] ] + } + }, + "flags": [ "ARMOR", "NO_REPAIR" ], + "breaks_into": [ + { "item": "afs_material_1", "count": [ 8, 10 ] }, + { "item": "afs_material_2", "count": [ 4, 6 ] }, + { "item": "afs_material_3", "count": [ 0, 2 ] }, + { "item": "afs_material_4", "count": [ 0, 1 ] } + ], + "damage_reduction": { "all": 450 }, + "variants": [ { "symbols": ")", "symbols_broken": ")" } ] + }, { "type": "vehicle_part", "id": "afs_control_station", diff --git a/data/mods/DinoMod/monster_factions.json b/data/mods/DinoMod/monster_factions.json index 9f53fb244d0a3..aab3c4e1d3222 100644 --- a/data/mods/DinoMod/monster_factions.json +++ b/data/mods/DinoMod/monster_factions.json @@ -582,6 +582,25 @@ "base_faction": "very_small_mixed", "friendly": [ "mosasaurus", "mosasaurus_juvenile" ] }, + { + "type": "MONSTER_FACTION", + "name": "shonisaurus", + "base_faction": "mixed_dino", + "friendly": [ "shonisaurus_juvenile", "shonisaurus_hatchling" ], + "by_mood": [ "shonisaurus" ] + }, + { + "type": "MONSTER_FACTION", + "name": "shonisaurus_juvenile", + "base_faction": "small_mixed", + "friendly": [ "shonisaurus", "shonisaurus_hatchling" ] + }, + { + "type": "MONSTER_FACTION", + "name": "shonisaurus_hatchling", + "base_faction": "very_small_mixed", + "friendly": [ "shonisaurus", "shonisaurus_juvenile" ] + }, { "type": "MONSTER_FACTION", "name": "plesiosaurus", diff --git a/data/mods/DinoMod/monstergroups/wilderness.json b/data/mods/DinoMod/monstergroups/wilderness.json index 3ad40955c7c50..2289a5bc30081 100644 --- a/data/mods/DinoMod/monstergroups/wilderness.json +++ b/data/mods/DinoMod/monstergroups/wilderness.json @@ -84,6 +84,11 @@ { "monster": "mon_zosasaurus", "cost_multiplier": 25, "starts": "14 days" }, { "monster": "mon_zosasaurus", "cost_multiplier": 25, "starts": "28 days" }, { "monster": "mon_zosasaurus", "cost_multiplier": 25, "starts": "90 days" }, + { "monster": "mon_shonisaurus", "weight": 1, "cost_multiplier": 25, "starts": "3 days" }, + { "monster": "mon_zonisaurus", "cost_multiplier": 25, "starts": "7 days" }, + { "monster": "mon_zonisaurus", "cost_multiplier": 25, "starts": "14 days" }, + { "monster": "mon_zonisaurus", "cost_multiplier": 25, "starts": "28 days" }, + { "monster": "mon_zonisaurus", "cost_multiplier": 25, "starts": "90 days" }, { "monster": "mon_plesiosaurus", "weight": 1, "cost_multiplier": 25, "pack_size": [ 1, 2 ] }, { "monster": "mon_zlesiosaurus", "cost_multiplier": 25, "starts": "7 days" }, { "monster": "mon_zlesiosaurus", "cost_multiplier": 25, "starts": "14 days" }, @@ -144,6 +149,11 @@ { "monster": "mon_zosasaurus", "cost_multiplier": 25, "starts": "14 days" }, { "monster": "mon_zosasaurus", "cost_multiplier": 25, "starts": "28 days" }, { "monster": "mon_zosasaurus", "cost_multiplier": 25, "starts": "90 days" }, + { "monster": "mon_shonisaurus", "weight": 1, "cost_multiplier": 25, "starts": "3 days" }, + { "monster": "mon_zonisaurus", "cost_multiplier": 25, "starts": "7 days" }, + { "monster": "mon_zonisaurus", "cost_multiplier": 25, "starts": "14 days" }, + { "monster": "mon_zonisaurus", "cost_multiplier": 25, "starts": "28 days" }, + { "monster": "mon_zonisaurus", "cost_multiplier": 25, "starts": "90 days" }, { "monster": "mon_plesiosaurus", "weight": 4, "cost_multiplier": 25, "pack_size": [ 1, 2 ] }, { "monster": "mon_zlesiosaurus", "cost_multiplier": 25, "starts": "7 days" }, { "monster": "mon_zlesiosaurus", "cost_multiplier": 25, "starts": "14 days" }, @@ -162,6 +172,11 @@ { "monster": "mon_zosasaurus", "cost_multiplier": 25, "starts": "14 days" }, { "monster": "mon_zosasaurus", "cost_multiplier": 25, "starts": "28 days" }, { "monster": "mon_zosasaurus", "cost_multiplier": 25, "starts": "90 days" }, + { "monster": "mon_shonisaurus", "weight": 1, "cost_multiplier": 25, "starts": "3 days" }, + { "monster": "mon_zonisaurus", "cost_multiplier": 25, "starts": "7 days" }, + { "monster": "mon_zonisaurus", "cost_multiplier": 25, "starts": "14 days" }, + { "monster": "mon_zonisaurus", "cost_multiplier": 25, "starts": "28 days" }, + { "monster": "mon_zonisaurus", "cost_multiplier": 25, "starts": "90 days" }, { "monster": "mon_plesiosaurus", "weight": 4, "cost_multiplier": 25, "pack_size": [ 1, 2 ] }, { "monster": "mon_zlesiosaurus", "cost_multiplier": 25, "starts": "7 days" }, { "monster": "mon_zlesiosaurus", "cost_multiplier": 25, "starts": "14 days" }, diff --git a/data/mods/DinoMod/monsters/dinosaur.json b/data/mods/DinoMod/monsters/dinosaur.json index e838a74ae1533..8aa37a0225b3d 100644 --- a/data/mods/DinoMod/monsters/dinosaur.json +++ b/data/mods/DinoMod/monsters/dinosaur.json @@ -2755,6 +2755,7 @@ "aggression": -10, "morale": 10, "speed": 110, + "attack_cost": 110, "melee_skill": 6, "melee_dice": 2, "melee_dice_sides": 6, @@ -2799,6 +2800,7 @@ "aggression": 9, "morale": 50, "speed": 200, + "attack_cost": 200, "zombify_into": "mon_zteranodon", "description": "A large feathered flying reptile, with a long pointed toothless beak and a long pointy head crest.", "reproduction": { "baby_type": { "baby_egg": "egg_pteranodon" }, "baby_count": 3, "baby_timer": 24 }, @@ -2821,6 +2823,7 @@ "aggression": 9, "morale": 80, "speed": 150, + "attack_cost": 150, "zombify_into": "mon_zuetzalcoatlus", "description": "A huge feathered flying reptile, with a long pointed toothless beak and a long stiff neck.", "reproduction": { "baby_type": { "baby_egg": "egg_quetzalcoatlus" }, "baby_count": 3, "baby_timer": 24 }, @@ -2861,6 +2864,7 @@ "aggression": 9, "morale": 90, "speed": 30, + "attack_cost": 30, "melee_skill": 8, "melee_dice": 3, "melee_dice_sides": 8, @@ -2869,10 +2873,62 @@ "weakpoint_sets": [ "wps_mosasaur_body" ], "hp": 400, "zombify_into": "mon_zosasaurus", - "description": "A huge aquatic reptile about the size of a small house, with a ferocious crocodile-like head and powerful swimming fins.", + "description": "A huge aquatic reptile about the size of a house, with a ferocious crocodile-like head and powerful swimming fins.", "reproduction": { "baby_type": { "baby_monster": "mon_mosasaurus_hatchling" }, "baby_count": 1, "baby_timer": 343 }, "baby_flags": [ "SPRING", "SUMMER", "AUTUMN" ], - "biosignature": { "biosig_item": "feces_dino", "biosig_timer": 1 }, + "grab_strength": 50, + "special_attacks": [ { "id": "bite_grab", "cooldown": 7 }, [ "LUNGE", 10 ], [ "EAT_CARRION", 60 ] ], + "flags": [ + "SEES", + "HEARS", + "ANIMAL", + "PATH_AVOID_DANGER", + "GRABS", + "BASHES", + "DESTROYS", + "WARM", + "SWIMS", + "AQUATIC", + "WATER_CAMOUFLAGE", + "PUSH_MON", + "EATS" + ], + "harvest": "dino_large_pred", + "dissect": "dissect_mosasaurus_large", + "anger_triggers": [ "PLAYER_WEAK", "HURT", "FRIEND_ATTACKED", "PLAYER_CLOSE" ], + "categories": [ "DINOSAUR", "WILDLIFE" ], + "armor": { "bash": 4, "cut": 4, "bullet": 6 } + }, + { + "type": "MONSTER", + "id": "mon_shonisaurus", + "name": { "str_sp": "shonisaurus" }, + "looks_like": "mon_zhark", + "species": "REPTILE", + "default_faction": "shonisaurus", + "symbol": "D", + "color": "red_white", + "volume": "1000 L", + "weight": "1000 kg", + "//": "When large weights and volumes are fixed this should be 81500 L and 81500 kg", + "bodytype": "fish", + "material": [ "flesh" ], + "stomach_size": 180000, + "aggression": 9, + "morale": 90, + "speed": 35, + "attack_cost": 35, + "melee_skill": 8, + "melee_dice": 2, + "melee_dice_sides": 8, + "melee_damage": [ { "damage_type": "cut", "amount": 10 } ], + "families": [ "prof_gross_anatomy", "prof_intro_biology", "prof_physiology" ], + "weakpoint_sets": [ "wps_mosasaur_body" ], + "hp": 380, + "zombify_into": "mon_zonisaurus", + "description": "A huge aquatic reptile about the size of a house, with a long snout and swimming fins, similar to a swordfish.", + "reproduction": { "baby_type": { "baby_monster": "mon_shonisaurus_hatchling" }, "baby_count": 1, "baby_timer": 343 }, + "baby_flags": [ "SPRING", "SUMMER", "AUTUMN" ], "grab_strength": 50, "special_attacks": [ { "id": "bite_grab", "cooldown": 7 }, [ "LUNGE", 10 ], [ "EAT_CARRION", 60 ] ], "flags": [ @@ -2912,7 +2968,8 @@ "stomach_size": 22000, "aggression": -5, "morale": 50, - "speed": 20, + "speed": 33, + "attack_cost": 33, "melee_skill": 6, "melee_dice": 2, "melee_dice_sides": 6, @@ -2924,7 +2981,6 @@ "description": "A large aquatic reptile about the size of a car, with a ferocious crocodile-like head, a long neck, and four powerful swimming fins.", "reproduction": { "baby_type": { "baby_monster": "mon_plesiosaurus_hatchling" }, "baby_count": 1, "baby_timer": 343 }, "baby_flags": [ "SPRING", "SUMMER", "AUTUMN" ], - "biosignature": { "biosig_item": "feces_dino", "biosig_timer": 1 }, "grab_strength": 10, "special_attacks": [ { "id": "bite_grab", "cooldown": 50 }, [ "LUNGE", 10 ], [ "EAT_CARRION", 60 ] ], "flags": [ "SEES", "HEARS", "ANIMAL", "PATH_AVOID_DANGER", "GRABS", "BASHES", "WARM", "SWIMS", "AQUATIC", "PUSH_MON", "EATS" ], diff --git a/data/mods/DinoMod/monsters/fungus.json b/data/mods/DinoMod/monsters/fungus.json index 4b99e21de06a8..8ea1c39974985 100644 --- a/data/mods/DinoMod/monsters/fungus.json +++ b/data/mods/DinoMod/monsters/fungus.json @@ -1367,6 +1367,25 @@ "upgrades": false, "flags": [ "SEES", "HEARS", "DESTROYS", "WARM", "SWIMS", "AQUATIC", "POISON", "STUMBLES", "NO_BREATHE", "FILTHY" ] }, + { + "id": "mon_zonisaurus_fungus", + "type": "MONSTER", + "name": { "str": "fungal shonisaurus zombie" }, + "description": "This was once a huge aquatic dinosaur the size of a house, with a long snout and swimming fins. Fungal tendrils now sprout from its mouth, eyes, and other orifices, holding together a foul mass of mold-covered scales and teeth.", + "copy-from": "mon_zonisaurus", + "default_faction": "fungus", + "species": [ "FUNGUS" ], + "diff": 2, + "proportional": { "hp": 0.75, "speed": 0.65 }, + "color": "light_gray", + "relative": { "melee_skill": -1, "melee_dice": -1, "melee_dice_sides": 3, "armor": { "bash": 3 } }, + "bleed_rate": 0, + "vision_day": 5, + "vision_night": 5, + "special_attacks": [ [ "FUNGUS", 200 ], [ "scratch", 10 ], { "type": "bite", "cooldown": 5 } ], + "upgrades": false, + "flags": [ "SEES", "HEARS", "DESTROYS", "WARM", "SWIMS", "AQUATIC", "POISON", "STUMBLES", "NO_BREATHE", "FILTHY" ] + }, { "id": "mon_zlesiosaurus_fungus", "type": "MONSTER", diff --git a/data/mods/DinoMod/monsters/hatchling.json b/data/mods/DinoMod/monsters/hatchling.json index 76de870b45ffe..634c374bb0acb 100644 --- a/data/mods/DinoMod/monsters/hatchling.json +++ b/data/mods/DinoMod/monsters/hatchling.json @@ -810,6 +810,19 @@ "petfood": { "food": [ "DINOFOOD_B" ] }, "extend": { "flags": [ "AQUATIC", "WATER_CAMOUFLAGE" ] } }, + { + "id": "mon_shonisaurus_hatchling", + "type": "MONSTER", + "copy-from": "mon_spinosaurus_hatchling", + "name": "shonisaurus neonate", + "description": "A tiny aquatic reptile neonate with huge shiny eyes and pointy little teeth.", + "default_faction": "shonisaurus_hatchling", + "harvest": "mammal_tiny", + "upgrades": { "age_grow": 30, "into": "mon_shonisaurus_juvenile" }, + "death_function": { "effect": { "id": "death_guilt", "min_level": 3 } }, + "petfood": { "food": [ "DINOFOOD_B" ] }, + "extend": { "flags": [ "AQUATIC", "WATER_CAMOUFLAGE" ] } + }, { "id": "mon_plesiosaurus_hatchling", "type": "MONSTER", diff --git a/data/mods/DinoMod/monsters/juvenile.json b/data/mods/DinoMod/monsters/juvenile.json index 08dd4ae08f917..a78fb56d5e2cd 100644 --- a/data/mods/DinoMod/monsters/juvenile.json +++ b/data/mods/DinoMod/monsters/juvenile.json @@ -969,6 +969,21 @@ "petfood": { "food": [ "DINOFOOD_B" ] }, "flags": [ "SEES", "HEARS", "ANIMAL", "PATH_AVOID_DANGER", "CANPLAY", "NO_BREED", "SWIMS", "AQUATIC" ] }, + { + "id": "mon_shonisaurus_juvenile", + "type": "MONSTER", + "name": "shonisaurus juvenile", + "description": "A juvenile predatory aquatic reptile with large pointy teeth and a long snout.", + "default_faction": "shonisaurus_juvenile", + "copy-from": "mon_shonisaurus", + "volume": "750 L", + "weight": "750 kg", + "aggression": 50, + "hp": 100, + "upgrades": { "age_grow": 365, "into": "mon_shonisaurus" }, + "petfood": { "food": [ "DINOFOOD_B" ] }, + "flags": [ "SEES", "HEARS", "ANIMAL", "PATH_AVOID_DANGER", "CANPLAY", "NO_BREED", "SWIMS", "AQUATIC" ] + }, { "id": "mon_plesiosaurus_juvenile", "type": "MONSTER", diff --git a/data/mods/DinoMod/monsters/zed-dinosaur.json b/data/mods/DinoMod/monsters/zed-dinosaur.json index c799071ade6f0..9b1692b229b96 100644 --- a/data/mods/DinoMod/monsters/zed-dinosaur.json +++ b/data/mods/DinoMod/monsters/zed-dinosaur.json @@ -1867,6 +1867,21 @@ ], "armor": { "bash": 5, "cut": 7, "bullet": 7 } }, + { + "type": "MONSTER", + "id": "mon_zonisaurus", + "name": { "str": "shonisaurus zombie" }, + "copy-from": "mon_zosasaurus", + "speed": 30, + "attack_cost": 30, + "melee_dice": 2, + "melee_damage": [ { "damage_type": "cut", "amount": 10 } ], + "hp": 400, + "description": "The ragged bloated corpse of a huge aquatic dinosaur the size of a house, with a long snout and swimming fins.", + "burn_into": "mon_zonisaurus_scorched", + "fungalize_into": "mon_zonisaurus_fungus", + "upgrades": false + }, { "type": "MONSTER", "id": "mon_zlesiosaurus", diff --git a/data/mods/DinoMod/monsters/zinosaur_burned.json b/data/mods/DinoMod/monsters/zinosaur_burned.json index d80841d90a886..ef15240fd7c44 100644 --- a/data/mods/DinoMod/monsters/zinosaur_burned.json +++ b/data/mods/DinoMod/monsters/zinosaur_burned.json @@ -1364,6 +1364,7 @@ "aggression": 100, "morale": 100, "speed": 125, + "attack_cost": 125, "melee_skill": 3, "melee_dice": 2, "melee_dice_sides": 5, @@ -1393,6 +1394,7 @@ "volume": "190 L", "weight": "250 kg", "speed": 100, + "attack_cost": 100, "hp": 40, "fungalize_into": "mon_zuetzalcoatlus_fungus", "description": "A heavily-burned, birdlike zombie pterosaur that still reeks of charred meat. Its flesh has mended into a leathery shell." @@ -1405,6 +1407,7 @@ "looks_like": "mon_zhark", "bodytype": "fish", "speed": 12, + "attack_cost": 12, "melee_skill": 3, "melee_dice": 3, "melee_dice_sides": 7, @@ -1437,6 +1440,17 @@ ], "armor": { "bash": 7, "cut": 16, "acid": 3, "heat": 15, "bullet": 14 } }, + { + "type": "MONSTER", + "id": "mon_zonisaurus_scorched", + "name": { "str": "scorched shonisaurus zombie" }, + "copy-from": "mon_zosasaurus_scorched", + "speed": 15, + "attack_cost": 15, + "melee_dice": 2, + "melee_damage": [ { "damage_type": "stab", "amount": 10 } ], + "fungalize_into": "mon_zonisaurus_fungus" + }, { "type": "MONSTER", "id": "mon_zlesiosaurus_scorched", @@ -1445,6 +1459,7 @@ "looks_like": "mon_zhark", "bodytype": "gator", "speed": 10, + "attack_cost": 10, "melee_skill": 3, "melee_dice": 2, "melee_dice_sides": 5, diff --git a/data/mods/Magiclysm/Spells/monsterspells.json b/data/mods/Magiclysm/Spells/monsterspells.json index 91c3ec7fc8d91..2983d73c0981a 100644 --- a/data/mods/Magiclysm/Spells/monsterspells.json +++ b/data/mods/Magiclysm/Spells/monsterspells.json @@ -516,6 +516,28 @@ "max_duration": 30000, "duration_increment": 2400 }, + { + "id": "necrotic_gaze_monster", + "type": "SPELL", + "name": { "str": "Necrotic Gaze Monster", "//~": "NO_I18N" }, + "description": { "str": "Like the animist spell, but for monsters", "//~": "NO_I18N" }, + "valid_targets": [ "hostile" ], + "effect": "attack", + "shape": "line", + "flags": [ "NO_LEGS", "RANDOM_DAMAGE", "NO_PROJECTILE", "NO_HANDS", "SPLIT_DAMAGE" ], + "min_damage": 30, + "max_damage": 80, + "min_range": 3, + "max_range": 5, + "range_increment": 0.1, + "max_level": 25, + "difficulty": 3, + "base_casting_time": 100, + "min_aoe": 1, + "max_aoe": 3, + "aoe_increment": 0.1, + "damage_type": "necrotic" + }, { "id": "ethereal_grasp_monster", "type": "SPELL", diff --git a/data/mods/Magiclysm/monsters/monsters.json b/data/mods/Magiclysm/monsters/monsters.json index 04554435f9c2d..9a5bdce17a556 100644 --- a/data/mods/Magiclysm/monsters/monsters.json +++ b/data/mods/Magiclysm/monsters/monsters.json @@ -83,11 +83,11 @@ "color": "dark_gray", "type": "MONSTER", "flags": [ "SEES", "HEARS", "SMELLS", "KEENNOSE", "HAS_MIND", "PATH_AVOID_DANGER", "WARM" ], - "harvest": "mutant_human", + "harvest": "gozu", "material": [ "hflesh" ], "bodytype": "human", "default_faction": "magical_beast", - "species": [ "MAGICAL_BEAST", "HUMAN" ], + "species": [ "MAGICAL_BEAST" ], "volume": "62500 ml", "weight": "81500 g", "hp": 60, @@ -95,9 +95,8 @@ "aggression": 30, "morale": 100, "melee_skill": 3, - "melee_damage": [ { "damage_type": "cut", "amount": 20 } ], - "melee_dice": 3, - "melee_dice_sides": 10, + "melee_dice": 2, + "melee_dice_sides": 6, "dodge": 6, "vision_night": 30, "vision_day": 30, @@ -114,7 +113,7 @@ }, { "type": "spell", - "spell_data": { "id": "necrotic_gaze" }, + "spell_data": { "id": "necrotic_gaze_monster", "min_level": 6 }, "cooldown": 5, "monster_message": "The krabgek gazes at %3$s!" } diff --git a/data/mods/Magiclysm/obsolete/camp_placement.json b/data/mods/Magiclysm/obsolete/camp_placement.json index 2497399f684ab..01e5772978bdd 100644 --- a/data/mods/Magiclysm/obsolete/camp_placement.json +++ b/data/mods/Magiclysm/obsolete/camp_placement.json @@ -4,10 +4,6 @@ "type": "camp_migration", "camp_migrations": { "name": "Forge of Wonders", "overmap_terrain": "forge_3A", "faction": "forge_lords" } }, - { - "type": "camp_migration", - "camp_migrations": { "name": "Healer's respite", "overmap_terrain": "magic_shop", "faction": "healers_grey" } - }, { "type": "camp_migration", "camp_migrations": { "name": "Old Wizard", "overmap_terrain": "lake_retreat_z3", "faction": "wizards_ancient" } diff --git a/data/mods/Magiclysm/traps.json b/data/mods/Magiclysm/traps.json index 3e5c0318bb5c6..1375f808254e0 100644 --- a/data/mods/Magiclysm/traps.json +++ b/data/mods/Magiclysm/traps.json @@ -45,5 +45,25 @@ "type": "effect_on_condition", "id": "EOC_TRAPS_SUMMON_BLADES", "effect": [ { "u_spawn_monster": "mon_animated_blade_feral", "real_count": [ 1, 2 ], "min_radius": 1, "max_radius": 1 } ] + }, + { + "type": "trap", + "id": "tr_rune_trap_summon_krabgek", + "name": "glowing runes", + "color": "red", + "symbol": "o", + "visibility": 15, + "avoidance": 13, + "difficulty": 99, + "action": "eocs", + "eocs": [ "EOC_TRAPS_SUMMON_KRABGEK" ], + "trigger_weight": "50000 g", + "trigger_message_u": "As you step forward, runes begin glowing brightly!", + "trigger_message_npc": "As steps forward, runes begin glowing brightly!" + }, + { + "type": "effect_on_condition", + "id": "EOC_TRAPS_SUMMON_KRABGEK", + "effect": [ { "u_spawn_monster": "mon_krabgek", "real_count": 1, "min_radius": 1, "max_radius": 1 } ] } ] diff --git a/data/mods/Magiclysm/worldgen/magic_shop.json b/data/mods/Magiclysm/worldgen/city_specials/magic_shop.json similarity index 95% rename from data/mods/Magiclysm/worldgen/magic_shop.json rename to data/mods/Magiclysm/worldgen/city_specials/magic_shop.json index 488d979aa19eb..c312888cc4eed 100644 --- a/data/mods/Magiclysm/worldgen/magic_shop.json +++ b/data/mods/Magiclysm/worldgen/city_specials/magic_shop.json @@ -196,9 +196,15 @@ "K": { "item": "allclothes", "chance": 20, "repeat": [ 1, 2 ] }, "B": { "item": "magic_shop_books", "chance": 20, "repeat": [ 1, 2 ] } }, - "place_npcs": [ { "class": "healer_priest", "x": 10, "y": 10 } ] + "place_nested": [ { "chunks": [ [ "NPC_healer_priest", 20 ], [ "null", 80 ] ], "x": 10, "y": 10 } ] } }, + { + "type": "mapgen", + "method": "json", + "nested_mapgen_id": "NPC_healer_priest", + "object": { "mapgensize": [ 1, 1 ], "rows": [ " " ], "place_npcs": [ { "class": "healer_priest", "x": 0, "y": 0 } ] } + }, { "type": "mapgen", "method": "json", diff --git a/data/mods/Magiclysm/worldgen/multitile_city_buildings.json b/data/mods/Magiclysm/worldgen/multitile_city_buildings.json index 059167bfc9f1c..3767a55c23ed3 100644 --- a/data/mods/Magiclysm/worldgen/multitile_city_buildings.json +++ b/data/mods/Magiclysm/worldgen/multitile_city_buildings.json @@ -4,7 +4,7 @@ "id": "magic_shop", "locations": [ "land" ], "overmaps": [ - { "point": [ 0, 0, 0 ], "overmap": "magic_shop_north", "camp": "healers_grey", "camp_name": "Healer's respite" }, + { "point": [ 0, 0, 0 ], "overmap": "magic_shop_north" }, { "point": [ 0, 0, 1 ], "overmap": "magic_shop_2ndfloor_north" }, { "point": [ 0, 0, 2 ], "overmap": "magic_shop_roof_north" } ] diff --git a/data/mods/Magiclysm/worldgen/used_bookstore.json b/data/mods/Magiclysm/worldgen/used_bookstore.json index b25926c824c47..cf06bc7f56b84 100644 --- a/data/mods/Magiclysm/worldgen/used_bookstore.json +++ b/data/mods/Magiclysm/worldgen/used_bookstore.json @@ -14,8 +14,8 @@ ",#N NNN NNN N#******", ",#NNN NNNN N N#******", ",#NNN NN$$$$D$#W##******", - ",W $Mz $#d*G******", - ",W NNN$MOz $#d********", + ",W $MO z$#d*G******", + ",W NNN$M O $#d********", ",#N ###$MMMM$#d********", ",#N +s&$$$$$$#*********", ",##############********,", @@ -54,8 +54,15 @@ "d": "f_dumpster", "C": "f_counter" }, - "monster": { "O": { "monster": "mon_krabgek", "chance": 100 }, "z": { "monster": "mon_krabgek", "chance": 33 } }, + "traps": { + "z": [ [ "tr_null", 1 ], [ "tr_rune_trap_summon_krabgek", 4 ] ], + "O": [ [ "tr_null", 2 ], [ "tr_rune_trap_summon_krabgek", 1 ] ] + }, "toilets": { "&": { } }, + "place_monster": [ + { "group": "GROUP_VANILLA", "x": [ 2, 8 ], "y": [ 2, 12 ], "repeat": [ 1, 5 ] }, + { "group": "GROUP_VANILLA", "x": [ 9, 15 ], "y": [ 2, 5 ], "repeat": [ 1, 2 ] } + ], "items": { "M": { "item": "spellbook_loot_1", "chance": 60 }, "N": { "item": "novels", "chance": 60, "repeat": [ 1, 3 ] } } } }, diff --git a/data/mods/TEST_DATA/items.json b/data/mods/TEST_DATA/items.json index c1900c6057073..d63d31793df7a 100644 --- a/data/mods/TEST_DATA/items.json +++ b/data/mods/TEST_DATA/items.json @@ -1589,6 +1589,31 @@ } ] }, + { + "id": "test_xl_waist_apron_long", + "type": "GENERIC", + "name": { "str": "long waist apron" }, + "copy-from": "test_waist_apron_long", + "extend": { "flags": [ "OVERSIZE", "PREFIX_XL" ] }, + "//": "the variants are not copy-from'd at the time of writing so let's make some", + "variants": [ + { + "id": "generic_apron_cotton", + "name": { "str": "long waist apron" }, + "description": "It's colored white, like the ones commonly used by chefs, professional or otherwise.", + "weight": 50, + "append": true + }, + { + "id": "pink_apron_cotton", + "name": { "str": "pink long waist apron" }, + "description": "It's colored neon pink, commonly used by women or men who like pink.", + "color": "pink", + "weight": 3, + "append": true + } + ] + }, { "id": "test_umbrella", "type": "GENERIC", diff --git a/data/mods/TEST_DATA/recipes.json b/data/mods/TEST_DATA/recipes.json index ec1aec7526be5..651f391018d05 100644 --- a/data/mods/TEST_DATA/recipes.json +++ b/data/mods/TEST_DATA/recipes.json @@ -280,6 +280,12 @@ "autolearn": true, "using": [ [ "tailoring_cotton_patchwork", 6 ] ] }, + { + "//": "Variant version with XL prefix", + "result": "test_xl_waist_apron_long", + "type": "recipe", + "copy-from": "test_waist_apron_long_pink_apron_cotton" + }, { "result": "test_200_kcal", "type": "recipe", diff --git a/data/mods/Xedra_Evolved/items/alchemy.json b/data/mods/Xedra_Evolved/items/alchemy.json index 13eab7aebdf9d..c3e031f843b14 100644 --- a/data/mods/Xedra_Evolved/items/alchemy.json +++ b/data/mods/Xedra_Evolved/items/alchemy.json @@ -293,19 +293,22 @@ "healthy": 7, "fun": -30, "flags": [ "NO_INGEST", "WATER_DISSOLVE", "EDIBLE_FROZEN" ], - "use_action": { - "type": "effect_on_conditions", - "description": "Drink the potion.", - "effect_on_conditions": [ - { - "id": "extend_life", - "effect": [ - { "u_message": "You imbibed the concoction and you feel your chakras align and your DNA de-age." }, - { "u_add_trait": "EXTEND_LIFE" } - ] - } - ] - } + "consumption_effect_on_conditions": [ "extend_life" ] + }, + { + "type": "effect_on_condition", + "id": "extend_life", + "condition": { "not": { "u_has_trait": "EXTEND_LIFE" } }, + "effect": [ + { "u_message": "You imbibed the concoction and you feel your chakras align and your DNA de-age." }, + { "u_add_trait": "EXTEND_LIFE" } + ], + "false_effect": [ + { + "u_message": "This was a very valuable elixir that you just wasted drinking yourself. You can't become more unaging.", + "type": "neutral" + } + ] }, { "id": "potion_dex", @@ -342,21 +345,24 @@ "id": "hyde_formula", "name": { "str_sp": "Hyde Formula" }, "description": "This is a transmutation potion that will bring your best attributes to the forefront.", - "use_action": { - "type": "effect_on_conditions", - "description": "Drink the formula.", - "effect_on_conditions": [ - { - "id": "hyde_formula", - "effect": [ { "u_message": "You imbibed the concoction and you feel your inner self unleashed." }, { "u_add_trait": "HYDE" } ] - } - ] - }, + "consumption_effect_on_conditions": [ "hyde_formula" ], "type": "COMESTIBLE", "color": "green_yellow", "calories": 50, "copy-from": "life_extension_potion" }, + { + "type": "effect_on_condition", + "id": "hyde_formula", + "condition": { "not": { "u_has_trait": "HYDE" } }, + "effect": [ { "u_message": "You imbibed the concoction and you feel your inner self unleashed." }, { "u_add_trait": "HYDE" } ], + "false_effect": [ + { + "u_message": "If this was a just world choosing to drink this concotion more than once would send you into an uncontrollable rage state where you rampaged until your inevitable death. This is not a just world.", + "type": "neutral" + } + ] + }, { "id": "plant_imbuement", "type": "COMESTIBLE", @@ -375,11 +381,7 @@ "healthy": 7, "fun": -30, "flags": [ "NO_INGEST", "WATER_DISSOLVE", "EDIBLE_FROZEN" ], - "use_action": { - "type": "effect_on_conditions", - "description": "Drink the potion. Will not work on those too distant from humanity already.", - "effect_on_conditions": [ "become_plant_fae" ] - } + "consumption_effect_on_conditions": [ "become_plant_fae" ] }, { "id": "earth_imbuement", @@ -399,11 +401,7 @@ "healthy": 7, "fun": -30, "flags": [ "NO_INGEST", "WATER_DISSOLVE", "EDIBLE_FROZEN" ], - "use_action": { - "type": "effect_on_conditions", - "description": "Drink the potion. Will not work on those too distant from humanity already.", - "effect_on_conditions": [ "become_earth_fae" ] - } + "consumption_effect_on_conditions": [ "become_earth_fae" ] }, { "id": "water_imbuement", @@ -423,11 +421,7 @@ "healthy": 7, "fun": -30, "flags": [ "NO_INGEST", "WATER_DISSOLVE", "EDIBLE_FROZEN" ], - "use_action": { - "type": "effect_on_conditions", - "description": "Drink the potion. Will not work on those too distant from humanity already.", - "effect_on_conditions": [ "become_water_fae" ] - } + "consumption_effect_on_conditions": [ "become_water_fae" ] }, { "id": "air_imbuement", @@ -447,11 +441,7 @@ "healthy": 7, "fun": -30, "flags": [ "NO_INGEST", "WATER_DISSOLVE", "EDIBLE_FROZEN" ], - "use_action": { - "type": "effect_on_conditions", - "description": "Drink the potion. Will not work on those too distant from humanity already.", - "effect_on_conditions": [ "become_air_fae" ] - } + "consumption_effect_on_conditions": [ "become_air_fae" ] }, { "id": "fire_imbuement", @@ -471,11 +461,7 @@ "healthy": 7, "fun": -30, "flags": [ "NO_INGEST", "WATER_DISSOLVE", "EDIBLE_FROZEN" ], - "use_action": { - "type": "effect_on_conditions", - "description": "Drink the potion. Will not work on those too distant from humanity already.", - "effect_on_conditions": [ "become_fire_fae" ] - } + "consumption_effect_on_conditions": [ "become_fire_fae" ] }, { "id": "doll_imbuement", @@ -495,10 +481,6 @@ "healthy": 7, "fun": -30, "flags": [ "NO_INGEST", "WATER_DISSOLVE", "EDIBLE_FROZEN" ], - "use_action": { - "type": "effect_on_conditions", - "description": "Drink the potion. Will not work on those too distant from humanity already.", - "effect_on_conditions": [ "become_doll_fae" ] - } + "consumption_effect_on_conditions": [ "become_doll_fae" ] } ] diff --git a/data/mods/Xedra_Evolved/items/comestibles/med.json b/data/mods/Xedra_Evolved/items/comestibles/med.json index c3ba0ac5e8cb7..d5b01d2ed69d2 100644 --- a/data/mods/Xedra_Evolved/items/comestibles/med.json +++ b/data/mods/Xedra_Evolved/items/comestibles/med.json @@ -67,24 +67,24 @@ "vitamins": [ ], "material": [ "water" ], "freezing_point": -8, - "use_action": { - "type": "effect_on_conditions", - "description": "Drink the blood.", - "effect_on_conditions": [ - { - "id": "learn_blood_of_saints", - "condition": { "u_has_effect": "vampire_virus_post_mortal" }, - "effect": [ - { "u_add_effect": "poisoned_blood2", "duration": "2 hours" }, - { - "u_message": "Your veins burn and ache. What were you thinking trying this? You are already one of the damned!", - "type": "bad" - } - ], - "false_effect": [ { "run_eocs": "learn_blood_of_saints_2" } ] - } - ] - } + "consumption_effect_on_conditions": [ "learn_blood_of_saints" ] + }, + { + "type": "effect_on_condition", + "id": "learn_blood_of_saints", + "condition": { "u_has_effect": "vampire_virus_post_mortal" }, + "effect": [ + { "u_add_effect": "poisoned_blood2", "duration": "2 hours" }, + { + "u_message": "Your veins burn and ache. What were you thinking trying this? You are already one of the damned!", + "type": "bad" + } + ], + "false_effect": [ + { "u_message": "You imbibed the concoction and you feel your veins flex in a warm glow.", "type": "good" }, + { "u_add_trait": "BLOOD_OF_SAINTS" }, + { "u_add_effect": "blood_treatment", "duration": "PERMANENT" } + ] }, { "type": "effect_on_condition", diff --git a/data/mods/Xedra_Evolved/items/drugs.json b/data/mods/Xedra_Evolved/items/drugs.json index eff71549cd476..0ad49b51a63a0 100644 --- a/data/mods/Xedra_Evolved/items/drugs.json +++ b/data/mods/Xedra_Evolved/items/drugs.json @@ -80,11 +80,7 @@ "stack_size": 4, "symbol": "!", "color": "magenta", - "use_action": { - "type": "effect_on_conditions", - "description": "Inject the treatment.", - "effect_on_conditions": [ "EOC_CONSUMED_BLOOD_TREATMENT" ] - }, + "consumption_effect_on_conditions": [ "EOC_CONSUMED_BLOOD_TREATMENT" ], "flags": [ "NPC_SAFE", "TRADER_AVOID" ], "vitamins": [ [ "meat_allergen", 1 ] ] }, diff --git a/data/mods/Xedra_Evolved/items/gracken_trait_improvements.json b/data/mods/Xedra_Evolved/items/gracken_trait_improvements.json index 15bb79fed32af..22c070b7ecc67 100644 --- a/data/mods/Xedra_Evolved/items/gracken_trait_improvements.json +++ b/data/mods/Xedra_Evolved/items/gracken_trait_improvements.json @@ -20,16 +20,14 @@ "name": { "str_sp": "Gracken Shade Arms" }, "looks_like": "offal", "description": "An organ that allows a mature Gracken to convert their arms back to a base state.", - "use_action": { - "type": "effect_on_conditions", - "description": "Exchanged the limb back to a base model.", - "effect_on_conditions": [ - { - "id": "shade_arms", - "effect": [ { "u_message": "You exchanged your previous arms for these." }, { "u_add_trait": "SHADE_ARMS" } ] - } - ] - } + "consumption_effect_on_conditions": [ "shade_arms" ] + }, + { + "type": "effect_on_condition", + "id": "shade_arms", + "condition": { "not": { "u_has_trait": "SHADE_ARMS" } }, + "effect": [ { "u_message": "You exchanged your previous arms for this." }, { "u_add_trait": "SHADE_ARMS" } ], + "false_effect": [ { "u_message": "You are already have Gracken arms.", "type": "neutral" } ] }, { "id": "gracken_strong_arms", @@ -38,16 +36,14 @@ "name": { "str_sp": "Gracken Strong Arms" }, "looks_like": "offal", "description": "An organ that allows a mature Gracken to convert their arms to a stronger form.", - "use_action": { - "type": "effect_on_conditions", - "description": "Exchanged the limb back for a stronger form factor.", - "effect_on_conditions": [ - { - "id": "strong_arms", - "effect": [ { "u_message": "You exchanged your previous arms for these." }, { "u_add_trait": "SHADE_STRONG_ARMS" } ] - } - ] - } + "consumption_effect_on_conditions": [ "strong_arms" ] + }, + { + "type": "effect_on_condition", + "id": "strong_arms", + "condition": { "not": { "u_has_trait": "SHADE_STRONG_ARMS" } }, + "effect": [ { "u_message": "You exchanged your previous arms for this." }, { "u_add_trait": "SHADE_STRONG_ARMS" } ], + "false_effect": [ { "u_message": "You are already have strong arms.", "type": "neutral" } ] }, { "id": "gracken_long_arms", @@ -56,16 +52,14 @@ "name": { "str_sp": "Gracken Long Arms" }, "looks_like": "offal", "description": "An organ that allows a mature Gracken to convert their arms to a longer form.", - "use_action": { - "type": "effect_on_conditions", - "description": "Exchanged the limb back for a longer form factor.", - "effect_on_conditions": [ - { - "id": "long_arms", - "effect": [ { "u_message": "You exchanged your previous arms for these." }, { "u_add_trait": "SHADE_LONG_ARMS" } ] - } - ] - } + "consumption_effect_on_conditions": [ "long_arms" ] + }, + { + "type": "effect_on_condition", + "id": "long_arms", + "condition": { "not": { "u_has_trait": "SHADE_LONG_ARMS" } }, + "effect": [ { "u_message": "You exchanged your previous arms for this." }, { "u_add_trait": "SHADE_LONG_ARMS" } ], + "false_effect": [ { "u_message": "You are already have long arms.", "type": "neutral" } ] }, { "id": "gracken_shade_hands", @@ -74,16 +68,14 @@ "name": { "str_sp": "Gracken Shade Hands" }, "looks_like": "offal", "description": "An organ that allows a mature Gracken to convert their hands back to a base state.", - "use_action": { - "type": "effect_on_conditions", - "description": "Exchanged the limb back to a base model.", - "effect_on_conditions": [ - { - "id": "shade_hands", - "effect": [ { "u_message": "You exchanged your previous arms for these." }, { "u_add_trait": "SHADE_ARMS" } ] - } - ] - } + "consumption_effect_on_conditions": [ "shade_hands" ] + }, + { + "type": "effect_on_condition", + "id": "gracken_shade_hands", + "condition": { "not": { "u_has_trait": "SHADE_HANDS" } }, + "effect": [ { "u_message": "You exchanged your previous arms for this." }, { "u_add_trait": "SHADE_HANDS" } ], + "false_effect": [ { "u_message": "You are already have normal Gracken hands.", "type": "neutral" } ] }, { "id": "gracken_sharp_nails", @@ -92,16 +84,14 @@ "name": { "str_sp": "Gracken Sharp Nails" }, "looks_like": "offal", "description": "An organ that allows a mature Gracken to convert their hands to a sharper form.", - "use_action": { - "type": "effect_on_conditions", - "description": "Exchanged the limb back for a sharper form factor.", - "effect_on_conditions": [ - { - "id": "sharp_nails", - "effect": [ { "u_message": "You exchanged your previous hands for these." }, { "u_add_trait": "SHADE_SHARP_NAILS" } ] - } - ] - } + "consumption_effect_on_conditions": [ "sharp_nails" ] + }, + { + "type": "effect_on_condition", + "id": "sharp_nails", + "condition": { "not": { "u_has_trait": "SHADE_SHARP_NAILS" } }, + "effect": [ { "u_message": "You exchanged your previous hands for this." }, { "u_add_trait": "SHADE_SHARP_NAILS" } ], + "false_effect": [ { "u_message": "You are already have sharpened nails.", "type": "neutral" } ] }, { "id": "gracken_dextrous_hands", @@ -110,16 +100,14 @@ "name": { "str_sp": "Gracken Dextrous Hands" }, "looks_like": "offal", "description": "An organ that allows a mature Gracken to convert their hands to a more agile form.", - "use_action": { - "type": "effect_on_conditions", - "description": "Exchanged the limb back for a longer form factor.", - "effect_on_conditions": [ - { - "id": "dextrous_hands", - "effect": [ { "u_message": "You exchanged your previous hands for these." }, { "u_add_trait": "SHADE_DEXTROUS_HANDS" } ] - } - ] - } + "consumption_effect_on_conditions": [ "dextrous_hands" ] + }, + { + "type": "effect_on_condition", + "id": "dextrous_hands", + "condition": { "not": { "u_has_trait": "SHADE_DEXTROUS_HANDS" } }, + "effect": [ { "u_message": "You exchanged your previous hands for this." }, { "u_add_trait": "SHADE_DEXTROUS_HANDS" } ], + "false_effect": [ { "u_message": "You are already have dextrous hands.", "type": "neutral" } ] }, { "id": "gracken_herbivorous_stomach", @@ -128,16 +116,14 @@ "name": { "str_sp": "Gracken Herbivorous Stomach" }, "looks_like": "offal", "description": "An organ that allows a mature Gracken to convert their diet to an herbivorous one.", - "use_action": { - "type": "effect_on_conditions", - "description": "Changed your diet to eating only plants.", - "effect_on_conditions": [ - { - "id": "herbivorous_stomach", - "effect": [ { "u_message": "You exchanged your previous stomach for this." }, { "u_add_trait": "SHADE_HERBIVORE" } ] - } - ] - } + "consumption_effect_on_conditions": [ "herbivorous_stomach" ] + }, + { + "type": "effect_on_condition", + "id": "herbivorous_stomach", + "condition": { "not": { "u_has_trait": "SHADE_HERBIVORE" } }, + "effect": [ { "u_message": "You exchanged your previous stomach for this." }, { "u_add_trait": "SHADE_HERBIVORE" } ], + "false_effect": [ { "u_message": "You are already an herbivore.", "type": "neutral" } ] }, { "id": "gracken_omnivorous_stomach", @@ -146,16 +132,14 @@ "name": { "str_sp": "Gracken Dextrous Hands" }, "looks_like": "offal", "description": "An organ that allows a mature Gracken to convert their diet to an omnivorous one.", - "use_action": { - "type": "effect_on_conditions", - "description": "Changed your diet to eating most things.", - "effect_on_conditions": [ - { - "id": "omnivorous_stomach", - "effect": [ { "u_message": "You exchanged your previous stomach for this." }, { "u_add_trait": "SHADE_OMNIVORE" } ] - } - ] - } + "consumption_effect_on_conditions": [ "omnivorous_stomach" ] + }, + { + "type": "effect_on_condition", + "id": "omnivorous_stomach", + "condition": { "not": { "u_has_trait": "SHADE_OMNIVORE" } }, + "effect": [ { "u_message": "You exchanged your previous stomach for this." }, { "u_add_trait": "SHADE_OMNIVORE" } ], + "false_effect": [ { "u_message": "You are already an omnivore.", "type": "neutral" } ] }, { "id": "gracken_carnivorous_stomach", @@ -164,15 +148,13 @@ "name": { "str_sp": "Gracken Dextrous Hands" }, "looks_like": "offal", "description": "An organ that allows a mature Gracken to convert their diet to an carnivorous one.", - "use_action": { - "type": "effect_on_conditions", - "description": "Changed your diet to meat eating.", - "effect_on_conditions": [ - { - "id": "carnivorous_stomach", - "effect": [ { "u_message": "You exchanged your previous stomach for this." }, { "u_add_trait": "SHADE_CARNIVORE" } ] - } - ] - } + "consumption_effect_on_conditions": [ "carnivorous_stomach" ] + }, + { + "type": "effect_on_condition", + "id": "carnivorous_stomach", + "condition": { "not": { "u_has_trait": "SHADE_CARNIVORE" } }, + "effect": [ { "u_message": "You exchanged your previous stomach for this." }, { "u_add_trait": "SHADE_CARNIVORE" } ], + "false_effect": [ { "u_message": "You are already a carnivore.", "type": "neutral" } ] } ] diff --git a/data/mods/Xedra_Evolved/items/hedge_magic_items.json b/data/mods/Xedra_Evolved/items/hedge_magic_items.json index a98812c385bc7..438cf2d18be2a 100644 --- a/data/mods/Xedra_Evolved/items/hedge_magic_items.json +++ b/data/mods/Xedra_Evolved/items/hedge_magic_items.json @@ -237,11 +237,7 @@ "color": "blue", "flags": [ "EATEN_COLD", "HEDGE_ENCHANTED" ], "phase": "solid", - "use_action": { - "type": "effect_on_conditions", - "description": "Rub the paste on your eyes.", - "effect_on_conditions": [ "EOC_HEDGE_SEE_NETHER_EYE_PASTE" ] - } + "consumption_effect_on_conditions": [ "EOC_HEDGE_SEE_NETHER_EYE_PASTE" ] }, { "type": "COMESTIBLE", diff --git a/data/mods/Xedra_Evolved/spells/hedge_magic_eocs.json b/data/mods/Xedra_Evolved/spells/hedge_magic_eocs.json index 994ebfe380b54..6e20239d1064e 100644 --- a/data/mods/Xedra_Evolved/spells/hedge_magic_eocs.json +++ b/data/mods/Xedra_Evolved/spells/hedge_magic_eocs.json @@ -133,7 +133,10 @@ { "type": "effect_on_condition", "id": "EOC_HEDGE_SEE_NETHER_EYE_PASTE", - "effect": [ { "u_add_effect": "effect_hedge_nether_eye_paste", "duration": { "math": [ "1800 * rng(0.6,1.4)" ] } } ] + "effect": [ + { "u_add_effect": "effect_hedge_nether_eye_paste", "duration": { "math": [ "1800 * rng(0.6,1.4)" ] } }, + { "u_message": "You rub the paste on your eyes and feel it tingle." } + ] }, { "type": "effect_on_condition", diff --git a/doc/JSON_INFO.md b/doc/JSON_INFO.md index fe49bd55d8b41..965f98d01ba80 100644 --- a/doc/JSON_INFO.md +++ b/doc/JSON_INFO.md @@ -156,7 +156,6 @@ Use the `Home` key to return to the top. - [Connect group definitions](#connect-group-definitions) - [Furniture](#furniture) - [`type`](#type-1) - - [`move_cost_mod`](#move_cost_mod) - [`keg_capacity`](#keg_capacity) - [`deployed_item`](#deployed_item) - [`lockpick_result`](#lockpick_result) @@ -173,7 +172,6 @@ Use the `Home` key to return to the top. - [`surgery_skill_multiplier`](#surgery_skill_multiplier) - [Terrain](#terrain) - [`type`](#type-2) - - [`move_cost`](#move_cost) - [`heat_radiation`](#heat_radiation) - [`light_emitted`](#light_emitted-1) - [`lockpick_result`](#lockpick_result-1) @@ -199,6 +197,7 @@ Use the `Home` key to return to the top. - [`connects_to`](#connects_to) - [`rotates_to`](#rotates_to) - [`symbol`](#symbol) + - [`move_cost_mod`](#move_cost_mod) - [`comfort`](#comfort) - [`floor_bedding_warmth`](#floor_bedding_warmth) - [`fall_damage_reduction`](#fall_damage_reduction) diff --git a/src/item.cpp b/src/item.cpp index d97521755db83..1add17d56ff70 100644 --- a/src/item.cpp +++ b/src/item.cpp @@ -5854,6 +5854,24 @@ void item::properties_info( std::vector &info, const iteminfo_query *p } +// Cache for can_craft in final_info. +static std::unordered_map can_craft_recipe_cache; +static time_point cache_valid_turn; + +static bool can_craft_recipe( const recipe *r, const inventory &crafting_inv ) +{ + if( cache_valid_turn != calendar::turn ) { + cache_valid_turn = calendar::turn; + can_craft_recipe_cache.clear(); + } + if( can_craft_recipe_cache.count( r ) > 0 ) { + return can_craft_recipe_cache.at( r ); + } + can_craft_recipe_cache[r] = r->deduped_requirements().can_make_with_inventory( crafting_inv, + r->get_component_filter() ); + return can_craft_recipe_cache.at( r ); +} + void item::final_info( std::vector &info, const iteminfo_query *parts, int batch, bool /* debug */ ) const { @@ -6085,7 +6103,7 @@ void item::final_info( std::vector &info, const iteminfo_query *parts, // with the inventory display allowing you to select items, showing the things you could make with contained items could be confusing. const itype_id &tid = typeId(); const inventory &crafting_inv = player_character.crafting_inventory(); - const recipe_subset available_recipe_subset = player_character.get_group_available_recipes(); + const recipe_subset &available_recipe_subset = player_character.get_group_available_recipes(); const std::set &item_recipes = available_recipe_subset.of_component( tid ); insert_separation_line( info ); @@ -6093,11 +6111,10 @@ void item::final_info( std::vector &info, const iteminfo_query *parts, info.emplace_back( "DESCRIPTION", _( "You know of nothing you could craft with it." ) ); } else { std::vector crafts; + crafts.reserve( item_recipes.size() ); for( const recipe *r : item_recipes ) { - const bool can_make = r->deduped_requirements() - .can_make_with_inventory( crafting_inv, r->get_component_filter() ); - - // Endarken recipes that can't be constructed with the survivor's inventory + const bool can_make = can_craft_recipe( r, crafting_inv ); + // Endarken recipes that can't be crafted with the survivor's inventory const std::string name = r->result_name( /* decorated = */ true ); crafts.emplace_back( can_make ? name : string_format( "%s", name ) ); } diff --git a/src/item_tname.h b/src/item_tname.h index cdee759dfe120..3b8e405e92923 100644 --- a/src/item_tname.h +++ b/src/item_tname.h @@ -111,16 +111,26 @@ constexpr uint64_t tname_conditional_bits = // TODO: fine grain? 1ULL << static_cast( tname::segments::COMPONENTS ) | 1ULL << static_cast( tname::segments::TAGS ) | 1ULL << static_cast( tname::segments::VARS ); -constexpr uint64_t item_name_bits = // item prefix + item name + item suffix +constexpr uint64_t base_item_name_bits = 1ULL << static_cast( tname::segments::CUSTOM_ITEM_PREFIX ) | 1ULL << static_cast( tname::segments::TYPE ) | 1ULL << static_cast( tname::segments::CUSTOM_ITEM_SUFFIX ); +constexpr uint64_t variant_bits = + 1ULL << static_cast( tname::segments::VARIANT ); constexpr segment_bitset default_tname( default_tname_bits ); constexpr segment_bitset unprefixed_tname( default_tname_bits & ~tname_prefix_bits ); constexpr segment_bitset tname_sort_key( default_tname_bits & ~tname_unsortable_bits ); constexpr segment_bitset tname_contents( tname_contents_bits ); constexpr segment_bitset tname_conditional( tname_conditional_bits ); -constexpr segment_bitset item_name( item_name_bits ); +// Name for an abstract base item of a given class, not any specific one. +// Often used in crafting UI and similar. +// For example in the sentence "To make some 'XL socks' I will need to cut up a 'blanket'", +// when we don't care which color (read: variant) 'XL socks' we want or 'blanket' we have. +constexpr segment_bitset base_item_name( base_item_name_bits ); +// Name of a specific item in the game world, carries the item identity, and will not +// change in a normal playthrough except through exordinary means (e.g. via `iuse_transform`). +// E.g. "XL green socks" (notably, not "|. XL green socks (filthy)") +constexpr segment_bitset item_identity_name( base_item_name_bits | variant_bits ); } // namespace tname diff --git a/src/recipe.cpp b/src/recipe.cpp index 48c1a427e928c..b902993479435 100644 --- a/src/recipe.cpp +++ b/src/recipe.cpp @@ -1218,17 +1218,21 @@ std::string recipe::result_name( const bool decorated ) const { std::string name; if( !name_.empty() ) { + // if the recipe has an explicit name (such as for proficiency training) - use that name = name_.translated(); - } else if( !variant().empty() ) { - auto iter_var = std::find_if( result_->variants.begin(), result_->variants.end(), - [this]( const itype_variant_data & itvar ) { - return itvar.id == variant(); - } ); - if( iter_var != result_->variants.end() ) { - name = iter_var->alt_name.translated(); - } } else { - name = item::tname( result_, 1, tname::item_name ); + // Names are tricky, so we have to create a temporary fake result item to get one. + // As of 2025-01-01 there's no better way around this. + item temp_item( result_ ); + // Use generic item name by default. + tname::segment_bitset segs = tname::base_item_name; + if( !variant().empty() ) { + // ..but if the recipe calls for a specific varaint - then use that variant. + // Note that `temp_item` is likely to already have a random variant set at the time of creation. + temp_item.set_itype_variant( variant() ); + segs = tname::item_identity_name; + } + name = temp_item.tname( 1, segs ); } if( decorated && uistate.favorite_recipes.find( this->ident() ) != uistate.favorite_recipes.end() ) { diff --git a/src/requirements.cpp b/src/requirements.cpp index 43956bd07897f..8e289bfaf5868 100644 --- a/src/requirements.cpp +++ b/src/requirements.cpp @@ -158,9 +158,9 @@ std::string tool_comp::to_string( const int batch, const int ) const //~ %1$s: tool name, %2$d: charge requirement return string_format( npgettext( "requirement", "%1$s (%2$d charge)", "%1$s (%2$d charges)", charge_total ), - item::tname( type, 1, tname::item_name ), charge_total ); + item::tname( type, 1, tname::base_item_name ), charge_total ); } else { - return item::tname( type, std::abs( count ), tname::item_name ); + return item::tname( type, std::abs( count ), tname::base_item_name ); } } @@ -176,16 +176,16 @@ std::string item_comp::to_string( const int batch, const int avail ) const return string_format( npgettext( "requirement", "%2$d %1$s (have infinite)", "%2$d %1$s (have infinite)", c ), - item_temp.tname( 1, tname::item_name ), c ); + item_temp.tname( 1, tname::base_item_name ), c ); } else if( avail > 0 ) { //~ %1$s: item name, %2$d: charge requirement, %3%d: available charges return string_format( npgettext( "requirement", "%2$d %1$s (have %3$d)", "%2$d %1$s (have %3$d)", c ), - item_temp.tname( 1, tname::item_name ), c, avail ); + item_temp.tname( 1, tname::base_item_name ), c, avail ); } else { //~ %1$s: item name, %2$d: charge requirement return string_format( npgettext( "requirement", "%2$d %1$s", "%2$d %1$s", c ), - item_temp.tname( 1, tname::item_name ), c ); + item_temp.tname( 1, tname::base_item_name ), c ); } } else { if( avail == item::INFINITE_CHARGES ) { @@ -193,16 +193,16 @@ std::string item_comp::to_string( const int batch, const int avail ) const return string_format( npgettext( "requirement", "%2$d %1$s (have infinite)", "%2$d %1$s (have infinite)", c ), - item_temp.tname( c, tname::item_name ), c ); + item_temp.tname( c, tname::base_item_name ), c ); } else if( avail > 0 ) { //~ %1$s: item name, %2$d: required count, %3%d: available count return string_format( npgettext( "requirement", "%2$d %1$s (have %3$d)", "%2$d %1$s (have %3$d)", c ), - item_temp.tname( c, tname::item_name ), c, avail ); + item_temp.tname( c, tname::base_item_name ), c, avail ); } else { //~ %1$s: item name, %2$d: required count return string_format( npgettext( "requirement", "%2$d %1$s", "%2$d %1$s", c ), - item_temp.tname( c, tname::item_name ), c ); + item_temp.tname( c, tname::base_item_name ), c ); } } } diff --git a/tests/crafting_test.cpp b/tests/crafting_test.cpp index 373183b7aaeb2..de598b0f437fa 100644 --- a/tests/crafting_test.cpp +++ b/tests/crafting_test.cpp @@ -112,6 +112,8 @@ static const recipe_id recipe_test_tallow2( "test_tallow2" ); static const recipe_id recipe_test_waist_apron_long( "test_waist_apron_long" ); static const recipe_id recipe_test_waist_apron_long_pink_apron_cotton( "test_waist_apron_long_pink_apron_cotton" ); +static const recipe_id +recipe_test_xl_waist_apron_long_pink_apron_cotton( "test_xl_waist_apron_long_pink_apron_cotton" ); static const recipe_id recipe_vambrace_larmor( "vambrace_larmor" ); static const recipe_id recipe_water_clean( "water_clean" ); @@ -2247,11 +2249,12 @@ TEST_CASE( "variant_crafting_recipes", "[crafting][slow]" ) tools.emplace_back( "scissors" ); tools.insert( tools.end(), 10, item( "sheet_cotton" ) ); tools.insert( tools.end(), 10, item( "thread" ) ); - prep_craft( recipe_test_waist_apron_long, tools, true ); - actually_test_craft( recipe_test_waist_apron_long, INT_MAX, 10 ); + const recipe_id apron_recipe = recipe_test_waist_apron_long; + prep_craft( apron_recipe, tools, true ); + actually_test_craft( apron_recipe, INT_MAX, 10 ); item_location apron = player_character.get_wielded_item(); - REQUIRE( apron->type->get_id() == recipe_test_waist_apron_long->result() ); + REQUIRE( apron->type->get_id() == apron_recipe->result() ); REQUIRE( apron->has_itype_variant() ); if( variant_counts.count( apron->itype_variant().id ) == 0 ) { @@ -2275,11 +2278,12 @@ TEST_CASE( "variant_crafting_recipes", "[crafting][slow]" ) tools.emplace_back( "scissors" ); tools.insert( tools.end(), 10, item( "sheet_cotton" ) ); tools.insert( tools.end(), 10, item( "thread" ) ); - prep_craft( recipe_test_waist_apron_long_pink_apron_cotton, tools, true ); - actually_test_craft( recipe_test_waist_apron_long_pink_apron_cotton, INT_MAX, 10 ); + const recipe_id apron_recipe = recipe_test_xl_waist_apron_long_pink_apron_cotton; + prep_craft( apron_recipe, tools, true ); + actually_test_craft( apron_recipe, INT_MAX, 10 ); item_location apron = player_character.get_wielded_item(); - REQUIRE( apron->type->get_id() == recipe_test_waist_apron_long_pink_apron_cotton->result() ); + REQUIRE( apron->type->get_id() == apron_recipe->result() ); REQUIRE( apron->has_itype_variant() ); if( apron->itype_variant().id == "pink_apron_cotton" ) { @@ -2288,6 +2292,14 @@ TEST_CASE( "variant_crafting_recipes", "[crafting][slow]" ) } CHECK( specific_variant_count == max_iters ); } + SECTION( "recipe names" ) { + const recipe_id basic_recipe = recipe_test_waist_apron_long; + CHECK( basic_recipe.obj().result_name() == "long waist apron" ); + const recipe_id variant_recipe = recipe_test_waist_apron_long_pink_apron_cotton; + CHECK( variant_recipe.obj().result_name() == "pink long waist apron" ); + const recipe_id variant_prefix_recipe = recipe_test_xl_waist_apron_long_pink_apron_cotton; + CHECK( variant_prefix_recipe.obj().result_name() == "XL pink long waist apron" ); + } } TEST_CASE( "pseudo_tools_in_crafting_inventory", "[crafting][tools]" ) diff --git a/tools/spell_checker/dictionary.txt b/tools/spell_checker/dictionary.txt index 797d1b40db012..a003f24c41c48 100644 --- a/tools/spell_checker/dictionary.txt +++ b/tools/spell_checker/dictionary.txt @@ -5567,6 +5567,7 @@ shoggoth shoggoths shogi Shoki +shonisaurus shootable shopkeep shorthair