From 5ccd8241c45e7a1d97eea0c234ba1b94de3bf173 Mon Sep 17 00:00:00 2001
From: Charlie <69320440+hal9000PR@users.noreply.github.com>
Date: Mon, 24 Jul 2023 15:52:17 +0100
Subject: [PATCH] homing projectiles + wizard spell (#21752)
---
code/datums/spells/wizard_spells.dm | 10 ++++
code/game/gamemodes/wizard/spellbook.dm | 6 +++
.../mob/living/carbon/human/human_defense.dm | 1 -
.../projectile/homing_projectiles.dm | 52 +++++++++++++++++++
code/modules/surgery/organs/organ_external.dm | 1 +
paradise.dme | 1 +
6 files changed, 70 insertions(+), 1 deletion(-)
create mode 100644 code/modules/projectiles/projectile/homing_projectiles.dm
diff --git a/code/datums/spells/wizard_spells.dm b/code/datums/spells/wizard_spells.dm
index b3ba4757cbb..61e5b013eaf 100644
--- a/code/datums/spells/wizard_spells.dm
+++ b/code/datums/spells/wizard_spells.dm
@@ -358,6 +358,16 @@
return TRUE
+/obj/effect/proc_holder/spell/fireball/toolbox
+ name = "Homing Toolbox"
+ desc = "This spell summons and throws a magical homing toolbox at your opponent."
+ sound = 'sound/weapons/smash.ogg'
+ fireball_type = /obj/item/projectile/homing/magic/toolbox
+ invocation = "ROBUSTIO!"
+
+ selection_activated_message = "Your prepare to cast your homing toolbox! Left-click to cast at a target!"
+ selection_deactivated_message = "You unrobust your toolbox...for now."
+
/obj/effect/proc_holder/spell/aoe/repulse
name = "Repulse"
desc = "This spell throws everything around the user away."
diff --git a/code/game/gamemodes/wizard/spellbook.dm b/code/game/gamemodes/wizard/spellbook.dm
index dddf1605f34..cca639f9a9a 100644
--- a/code/game/gamemodes/wizard/spellbook.dm
+++ b/code/game/gamemodes/wizard/spellbook.dm
@@ -137,6 +137,12 @@
spell_type = /obj/effect/proc_holder/spell/fireball
category = "Offensive"
+/datum/spellbook_entry/summon_toolbox
+ name = "Homing Toolbox"
+ spell_type = /obj/effect/proc_holder/spell/fireball/toolbox
+ category = "Offensive"
+ cost = 1
+
/datum/spellbook_entry/fleshtostone
name = "Flesh to Stone"
spell_type = /obj/effect/proc_holder/spell/touch/flesh_to_stone
diff --git a/code/modules/mob/living/carbon/human/human_defense.dm b/code/modules/mob/living/carbon/human/human_defense.dm
index 4f93df03dbd..803a408b2d2 100644
--- a/code/modules/mob/living/carbon/human/human_defense.dm
+++ b/code/modules/mob/living/carbon/human/human_defense.dm
@@ -578,7 +578,6 @@ emp_act
if(((throwingdatum ? throwingdatum.speed : I.throw_speed) >= EMBED_THROWSPEED_THRESHOLD) || I.embedded_ignore_throwspeed_threshold)
if(can_embed(I))
if(prob(I.embed_chance) && !HAS_TRAIT(src, TRAIT_PIERCEIMMUNE))
- throw_alert("embeddedobject", /obj/screen/alert/embeddedobject)
var/obj/item/organ/external/L = pick(bodyparts)
L.add_embedded_object(I)
I.add_mob_blood(src)//it embedded itself in you, of course it's bloody!
diff --git a/code/modules/projectiles/projectile/homing_projectiles.dm b/code/modules/projectiles/projectile/homing_projectiles.dm
new file mode 100644
index 00000000000..b97afec55d4
--- /dev/null
+++ b/code/modules/projectiles/projectile/homing_projectiles.dm
@@ -0,0 +1,52 @@
+/obj/item/projectile/homing
+ name = "smart bullet"
+ icon_state = "bullet"
+ var/homing_active = TRUE
+
+/obj/item/projectile/homing/pixel_move(trajectory_multiplier)
+ . = ..()
+ if(!homing_active)
+ return
+
+ var/turf/current_turf = get_turf(src)
+ var/turf/target_turf = get_turf(original)
+ if(current_turf == target_turf)
+ homing_active = FALSE
+ return
+
+ if(!current_turf || !target_turf)
+ return
+
+ var/dx = target_turf.x - current_turf.x
+ var/dy = target_turf.y - current_turf.y
+ var/angle = ATAN2(dy, dx)
+ set_angle(angle)
+
+/obj/item/projectile/homing/magic
+ name = "bolt of nothing"
+ icon_state = "energy"
+ damage = 0
+ damage_type = OXY
+ nodamage = 1
+ armour_penetration_percentage = 100
+ flag = MAGIC
+
+/obj/item/projectile/homing/magic/toolbox
+ name = "magic toolbox"
+ icon = 'icons/obj/storage.dmi'
+ icon_state = "toolbox_default"
+ hitsound = 'sound/weapons/smash.ogg'
+ damage = 30
+ damage_type = BRUTE
+
+/obj/item/projectile/homing/magic/toolbox/on_range()
+ . = ..()
+ new /obj/item/storage/toolbox(get_turf(src))
+
+/obj/item/projectile/homing/magic/toolbox/on_hit(atom/target, blocked, hit_zone)
+ . = ..()
+ var/obj/item/storage/toolbox/T = new /obj/item/storage/toolbox(get_turf(src))
+ if(ishuman(target))
+ var/mob/living/carbon/human/H = target
+ var/obj/item/organ/external/E = pick(H.bodyparts)
+ E.add_embedded_object(T)
diff --git a/code/modules/surgery/organs/organ_external.dm b/code/modules/surgery/organs/organ_external.dm
index 0f7d385a746..2d56706c846 100644
--- a/code/modules/surgery/organs/organ_external.dm
+++ b/code/modules/surgery/organs/organ_external.dm
@@ -871,6 +871,7 @@ Note that amputating the affected organ does in fact remove the infection from t
forceMove(T)
/obj/item/organ/external/proc/add_embedded_object(obj/item/I)
+ owner.throw_alert("embeddedobject", /obj/screen/alert/embeddedobject)
embedded_objects += I
I.forceMove(owner)
RegisterSignal(I, COMSIG_MOVABLE_MOVED, PROC_REF(remove_embedded_object))
diff --git a/paradise.dme b/paradise.dme
index 30f214fd036..26bb79cc001 100644
--- a/paradise.dme
+++ b/paradise.dme
@@ -2405,6 +2405,7 @@
#include "code\modules\projectiles\projectile\bullets.dm"
#include "code\modules\projectiles\projectile\energy_projectiles.dm"
#include "code\modules\projectiles\projectile\force.dm"
+#include "code\modules\projectiles\projectile\homing_projectiles.dm"
#include "code\modules\projectiles\projectile\magic_projectiles.dm"
#include "code\modules\projectiles\projectile\reusable.dm"
#include "code\modules\projectiles\projectile\special_projectiles.dm"