diff --git a/code/WorkInProgress/surgery.dm b/code/WorkInProgress/surgery.dm index 404afdbb859..f07cf4b1f05 100644 --- a/code/WorkInProgress/surgery.dm +++ b/code/WorkInProgress/surgery.dm @@ -39,6 +39,16 @@ // evil infection stuff that will make everyone hate me var/can_infect = 0 + proc/isright(obj/item/tool) //is it is a required surgical tool for this step + return (istype(tool,required_tool)) + + proc/isacceptable(obj/item/tool) //is it is an accepted replacement tool for this step + if (allowed_tools) + for (var/T in allowed_tools) + if (istype(tool,T)) + return 1 + return 0 + // Build this list by iterating over all typesof(/datum/surgery_step) and sorting the results by priority @@ -1226,3 +1236,68 @@ proc/spread_germs_to_organ(datum/organ/external/E, mob/living/carbon/human/user) user:bloody_hands(target, 0) user:bloody_body(target) +////////////////////////////////////////////////////////////////// +// IMPLANT REMOVAL SURGERY // +////////////////////////////////////////////////////////////////// + +/datum/surgery_step/implant_removal + required_tool = /obj/item/weapon/hemostat + allowed_tools = list(/obj/item/weapon/wirecutters, /obj/item/weapon/kitchen/utensil/fork) + + min_duration = 80 + max_duration = 100 + + can_use(mob/user, mob/living/carbon/human/target, target_zone, obj/item/tool) + var/datum/organ/external/affected = target.get_organ(target_zone) + return affected.open == 2 && !(affected.status & ORGAN_BLEEDING) + + begin_step(mob/user, mob/living/carbon/human/target, target_zone, obj/item/tool) + var/datum/organ/external/affected = target.get_organ(target_zone) + user.visible_message("[user] starts poking around inside the incision on [target]'s [affected.display_name] with \the [tool].", \ + "You start poking around inside the incision on [target]'s [affected.display_name] with \the [tool]" ) + target.custom_pain("The pain in your chest is living hell!",1) + + end_step(mob/user, mob/living/carbon/human/target, target_zone, obj/item/tool) + var/datum/organ/external/chest/affected = target.get_organ("chest") + + var/find_prob = 0 + if (affected.implants.len) + var/obj/item/weapon/implant/imp = affected.implants[1] + if (imp.islegal()) + find_prob +=60 + else + find_prob +=40 + if (isright(tool)) + find_prob +=20 + + if (prob(find_prob)) + user.visible_message("\blue [user] takes something out of incision on [target]'s [affected.display_name] with \the [tool].", \ + "\blue You take something out of incision on [target]'s [affected.display_name]s with \the [tool]." ) + var/obj/item/weapon/implant/imp = affected.implants[1] + affected.implants -= imp + imp.loc = get_turf(target) + imp.imp_in = null + imp.implanted = 0 + else + user.visible_message("\blue [user] could not find anything inside [target]'s [affected.display_name], and pulls \the [tool] out.", \ + "\blue You could not find anything inside [target]'s [affected.display_name]." ) + if (ishuman(user) && prob(80)) user:bloody_hands(target, 0) + + fail_step(mob/user, mob/living/carbon/human/target, target_zone, obj/item/tool) + var/datum/organ/external/chest/affected = target.get_organ(target_zone) + user.visible_message("\red [user]'s hand slips, scraping tissue inside [target]'s [affected.display_name] with \the [tool]!", \ + "\red Your hand slips, scraping tissue inside [target]'s [affected.display_name] with \the [tool]!") + affected.createwound(CUT, 20) + if (affected.implants.len) + var/fail_prob = 10 + if (!isright(tool)) + fail_prob += 30 + if (prob(fail_prob)) + var/obj/item/weapon/implant/imp = affected.implants[1] + user.visible_message("\red Something beeps inside [target]'s [affected.display_name]!") + playsound(imp.loc, 'sound/weapons/armbomb.ogg', 75, 1, -3) + spawn(15) + imp.activate() + if (ishuman(user)) + user:bloody_hands(target, 0) + user:bloody_body(target) \ No newline at end of file diff --git a/code/datums/organs/organ_external.dm b/code/datums/organs/organ_external.dm index 06f46ed1927..167cbe6f0b1 100644 --- a/code/datums/organs/organ_external.dm +++ b/code/datums/organs/organ_external.dm @@ -34,6 +34,7 @@ var/open = 0 var/stage = 0 + var/list/implants = list() // INTERNAL germs inside the organ, this is BAD if it's greater 0 var/germ_level = 0 diff --git a/code/game/objects/items.dm b/code/game/objects/items.dm index b6c7cf8da8f..b2c9caaa15c 100644 --- a/code/game/objects/items.dm +++ b/code/game/objects/items.dm @@ -186,26 +186,21 @@ if (!istype(M)) // not sure if this is the right thing... return + if (can_operate(M)) //Checks if mob is lying down on table for surgery if(istype(M,/mob/living/carbon)) - if (user.a_intent != "harm") + if (user.a_intent != "harm") //check for Hippocratic Oath if(surgery_steps.len == 0) build_surgery_steps_list() for(var/datum/surgery_step/S in surgery_steps) - //check if tool is right or close enough - var/right = istype(src, S.required_tool) - if (!right && S.allowed_tools) - for (var/T in S.allowed_tools) - if (istype(src, T)) - right = 1 - if(right && S.can_use(user, M, user.zone_sel.selecting, src)) //is this step possible? - S.begin_step(user, M, user.zone_sel.selecting, src) - if(do_mob(user, M, rand(S.min_duration, S.max_duration))) - S.end_step(user, M, user.zone_sel.selecting, src) - else - S.fail_step(user, M, user.zone_sel.selecting, src) - return //don't want to do weapony things after surgery - if (is_surgery_tool(src)) - return + if( S.isright(src) || S.isacceptable(src) ) //check if tool is right or close enough + if(S.can_use(user, M, user.zone_sel.selecting, src)) //and if this step is possible + S.begin_step(user, M, user.zone_sel.selecting, src) //start on it + if(do_mob(user, M, rand(S.min_duration, S.max_duration))) //if user did nto move or changed hands + S.end_step(user, M, user.zone_sel.selecting, src) //finish successfully + else //or + S.fail_step(user, M, user.zone_sel.selecting, src) //malpractice~ + return //don't want to do weapony things after surgery + var/messagesource = M diff --git a/code/game/objects/items/weapons/implants/implant.dm b/code/game/objects/items/weapons/implants/implant.dm index 0ef3fa6bf1d..9f31412710b 100644 --- a/code/game/objects/items/weapons/implants/implant.dm +++ b/code/game/objects/items/weapons/implants/implant.dm @@ -1,7 +1,10 @@ /obj/item/weapon/implant name = "implant" + icon = 'device.dmi' + icon_state = "implant" var/implanted = null var/mob/imp_in = null + var/datum/organ/external/part = null color = "b" var/allow_reagents = 0 @@ -23,8 +26,8 @@ proc/hear(message, source as mob) return - - + proc/islegal() + return 0 /obj/item/weapon/implant/tracking name = "tracking" @@ -82,6 +85,8 @@ Implant Specifics:
"} if(src.imp_in) src.imp_in.gib() + islegal() + return 0 //BS12 Explosive /obj/item/weapon/implant/explosive name = "explosive implant" @@ -110,15 +115,18 @@ Implant Specifics:
"} var/list/replacechars = list("'" = "","\"" = "",">" = "","<" = "","(" = "",")" = "") msg = sanitize_simple(msg, replacechars) if(findtext(msg,phrase)) - if(istype(imp_in, /mob/)) - var/mob/T = imp_in - T.gib() - explosion(get_turf(imp_in), 1, 3, 4, 6, 3) - var/turf/t = get_turf(imp_in) - if(t) - t.hotspot_expose(3500,125) + activate() del(src) + activate() + if(istype(imp_in, /mob/)) + var/mob/T = imp_in + T.gib() + explosion(get_turf(imp_in), 1, 3, 4, 6, 3) + var/turf/t = get_turf(imp_in) + if(t) + t.hotspot_expose(3500,125) + implanted(mob/source as mob) phrase = input("Choose activation phrase:") as text var/list/replacechars = list("'" = "","\"" = "",">" = "","<" = "","(" = "",")" = "") @@ -127,6 +135,8 @@ Implant Specifics:
"} usr << "The implanted explosive implant in [source] can be activated by saying something containing the phrase ''[src.phrase]'', say [src.phrase] to attempt to activate." return 1 + islegal() + return 0 /obj/item/weapon/implant/chem name = "chem" @@ -266,14 +276,16 @@ the implant may become unstable and either pre-maturely inject the subject or si process() if (!implanted) return var/mob/M = imp_in - var/area/t = get_area(M) if(isnull(M)) // If the mob got gibbed - var/obj/item/device/radio/headset/a = new /obj/item/device/radio/headset(null) - a.autosay("[mobname] has died-zzzzt in-in-in...", "[mobname]'s Death Alarm") - del(a) - processing_objects.Remove(src) + activate() else if(M.stat == 2) + activate("death") + + activate(var/cause) + var/mob/M = imp_in + var/area/t = get_area(M) + if(cause == "death") var/obj/item/device/radio/headset/a = new /obj/item/device/radio/headset(null) if(istype(t, /area/syndicate_station) || istype(t, /area/syndicate_mothership) || istype(t, /area/shuttle/syndicate_elite) ) //give the syndies a bit of stealth @@ -282,7 +294,11 @@ the implant may become unstable and either pre-maturely inject the subject or si a.autosay("[mobname] has died in [t.name]!", "[mobname]'s Death Alarm") del(a) processing_objects.Remove(src) - + else + var/obj/item/device/radio/headset/a = new /obj/item/device/radio/headset(null) + a.autosay("[mobname] has died-zzzzt in-in-in...", "[mobname]'s Death Alarm") + del(a) + processing_objects.Remove(src) implanted(mob/source as mob) mobname = source.real_name @@ -314,13 +330,20 @@ the implant may become unstable and either pre-maturely inject the subject or si if (emote == src.activation_emote) source << "The air glows as \the [src.scanned.name] uncompresses." - var/turf/t = get_turf(source) - src.scanned.loc = t - del src + activate() + + activate() + var/turf/t = get_turf(src) + src.scanned.loc = t + if (part) part.implants -= src + del src implanted(mob/source as mob) src.activation_emote = input("Choose activation emote:") in list("blink", "blink_r", "eyebrow", "chuckle", "twitch_s", "frown", "nod", "blush", "giggle", "grin", "groan", "shrug", "smile", "pale", "sniff", "whimper", "wink") - source.mind.store_memory("Freedom implant can be activated by using the [src.activation_emote] emote, say *[src.activation_emote] to attempt to activate.", 0, 0) + if (source.mind) + source.mind.store_memory("Freedom implant can be activated by using the [src.activation_emote] emote, say *[src.activation_emote] to attempt to activate.", 0, 0) source << "The implanted freedom implant can be activated by using the [src.activation_emote] emote, say *[src.activation_emote] to attempt to activate." return 1 + islegal() + return 0 diff --git a/code/game/objects/items/weapons/implants/implanter.dm b/code/game/objects/items/weapons/implants/implanter.dm index 9cf12fe2478..ae21beff2d4 100644 --- a/code/game/objects/items/weapons/implants/implanter.dm +++ b/code/game/objects/items/weapons/implants/implanter.dm @@ -40,6 +40,11 @@ src.imp.loc = M src.imp.imp_in = M src.imp.implanted = 1 + if (ishuman(M)) + var/mob/living/carbon/human/H = M + var/datum/organ/external/affected = H.get_organ(user.zone_sel.selecting) + affected.implants += src.imp + imp.part = affected src.imp = null update() @@ -107,6 +112,10 @@ /obj/item/weapon/implanter/compressed/afterattack(atom/A, mob/user as mob) if(istype(A,/obj/item) && imp) + var/obj/item/weapon/implant/compressed/c = imp + if (c.scanned) + user << "\red Something is already scanned inside the implant!" + return imp:scanned = A A.loc.contents.Remove(A) update() diff --git a/icons/obj/device.dmi b/icons/obj/device.dmi index e57a75e0525..4831ad2ebf7 100644 Binary files a/icons/obj/device.dmi and b/icons/obj/device.dmi differ