diff --git a/code/_onclick/item_attack.dm b/code/_onclick/item_attack.dm
index 9ab4aa159d0..22c85ec85b0 100644
--- a/code/_onclick/item_attack.dm
+++ b/code/_onclick/item_attack.dm
@@ -30,9 +30,9 @@
return 0
var/messagesource = M
- if (can_operate(M)) //Checks if mob is lying down on table for surgery
- if (do_surgery(M,user,src))
- return 0
+ //if (can_operate(M)) //Checks if mob is lying down on table for surgery
+ // if (do_surgery(M,user,src))
+ // return 0
if (istype(M,/mob/living/carbon/brain))
messagesource = M:container
diff --git a/code/game/objects/items/stacks/medical.dm b/code/game/objects/items/stacks/medical.dm
index 83043ed7770..d6197c416a6 100644
--- a/code/game/objects/items/stacks/medical.dm
+++ b/code/game/objects/items/stacks/medical.dm
@@ -112,11 +112,11 @@
affecting.heal_damage(src.heal_brute, src.heal_burn, 0)
use(1)
else
- if (can_operate(H)) //Checks if mob is lying down on table for surgery
- if (do_surgery(H,user,src))
- return
- else
- user << "The [affecting.name] is cut open, you'll need more than some ointment!"
+ //if (can_operate(H)) //Checks if mob is lying down on table for surgery
+ // if (do_surgery(H,user,src))
+ // return
+ //else
+ user << "The [affecting.name] is cut open, you'll need more than some ointment!"
/obj/item/stack/medical/bruise_pack/comfrey
name = "\improper Comfrey leaf"
@@ -177,11 +177,11 @@
affecting.heal_damage(heal_brute,0)
use(1)
else
- if (can_operate(H)) //Checks if mob is lying down on table for surgery
- if (do_surgery(H,user,src))
- return
- else
- user << "The [affecting.name] is cut open, you'll need more than a bandage!"
+ //if (can_operate(H)) //Checks if mob is lying down on table for surgery
+ // if (do_surgery(H,user,src))
+ // return
+ //else
+ user << "The [affecting.name] is cut open, you'll need more than a bandage!"
/obj/item/stack/medical/advanced/ointment
name = "advanced burn kit"
@@ -210,11 +210,11 @@
affecting.heal_damage(0,heal_burn)
use(1)
else
- if (can_operate(H)) //Checks if mob is lying down on table for surgery
- if (do_surgery(H,user,src))
- return
- else
- user << "The [affecting.name] is cut open, you'll need more than a bandage!"
+ //if (can_operate(H)) //Checks if mob is lying down on table for surgery
+ // if (do_surgery(H,user,src))
+ // return
+ //else
+ user << "The [affecting.name] is cut open, you'll need more than a bandage!"
/obj/item/stack/medical/splint
name = "medical splints"
diff --git a/code/game/objects/items/stacks/nanopaste.dm b/code/game/objects/items/stacks/nanopaste.dm
index fea0281c9b8..7da3d2935ba 100644
--- a/code/game/objects/items/stacks/nanopaste.dm
+++ b/code/game/objects/items/stacks/nanopaste.dm
@@ -27,9 +27,9 @@
var/mob/living/carbon/human/H = M
var/obj/item/organ/external/S = H.get_organ(user.zone_sel.selecting)
- if(can_operate(H))
- if (do_surgery(H,user,src))
- return
+ //if(can_operate(H))
+ // if (do_surgery(H,user,src))
+ // return
if (S && (S.status & ORGAN_ROBOT))
if(S.get_damage())
diff --git a/code/game/objects/items/weapons/kitchen.dm b/code/game/objects/items/weapons/kitchen.dm
index 64a5ad53948..2fbd6589562 100644
--- a/code/game/objects/items/weapons/kitchen.dm
+++ b/code/game/objects/items/weapons/kitchen.dm
@@ -63,8 +63,8 @@
overlays.Cut()
return
- if (can_operate(M))
- do_surgery(M, user, src)
+ //if (can_operate(M))
+ // do_surgery(M, user, src)
/obj/item/weapon/kitchen/utensil/fork
name = "fork"
diff --git a/code/modules/client/preferences.dm b/code/modules/client/preferences.dm
index bc28c88ee2f..7a0f81b3bb4 100644
--- a/code/modules/client/preferences.dm
+++ b/code/modules/client/preferences.dm
@@ -1565,7 +1565,7 @@ var/global/list/special_role_times = list( //minimum age (in days) for accounts
else
O.robotize()
else
- var/obj/item/organ/I = character.internal_organs_by_name[name]
+ var/obj/item/organ/internal/I = character.get_int_organ(name)
if(I)
if(status == "assisted")
I.mechassist()
diff --git a/code/modules/hydroponics/grown.dm b/code/modules/hydroponics/grown.dm
index b39ca263d02..2704ef7dded 100644
--- a/code/modules/hydroponics/grown.dm
+++ b/code/modules/hydroponics/grown.dm
@@ -298,7 +298,7 @@
// This is being copypasted here because reagent_containers (WHY DOES FOOD DESCEND FROM THAT) overrides it completely.
// TODO: refactor all food paths to be less horrible and difficult to work with in this respect. ~Z
- if(!istype(M) || (can_operate(M) && do_surgery(M,user,src))) return 0
+ if(!istype(M)) return 0
if(!def_zone)
def_zone = check_zone(user.zone_sel.selecting)
diff --git a/code/modules/mob/living/carbon/alien/special/alien_embryo.dm b/code/modules/mob/living/carbon/alien/special/alien_embryo.dm
index 5ffe45a8123..d56593f2206 100644
--- a/code/modules/mob/living/carbon/alien/special/alien_embryo.dm
+++ b/code/modules/mob/living/carbon/alien/special/alien_embryo.dm
@@ -2,7 +2,7 @@
// It functions almost identically (see code/datums/diseases/alien_embryo.dm)
var/const/ALIEN_AFK_BRACKET = 450 // 45 seconds
-/obj/item/alien_embryo
+/obj/item/organ/internal/body_egg/alien_embryo
name = "alien embryo"
desc = "All slimy and yuck."
icon = 'icons/mob/alien.dmi'
@@ -10,30 +10,49 @@ var/const/ALIEN_AFK_BRACKET = 450 // 45 seconds
var/mob/living/affected_mob
var/stage = 0
-/obj/item/alien_embryo/New()
- if(istype(loc, /mob/living))
- affected_mob = loc
- affected_mob.status_flags |= XENO_HOST
- if(istype(affected_mob,/mob/living/carbon))
- var/mob/living/carbon/H = affected_mob
- H.med_hud_set_status()
- processing_objects.Add(src)
- spawn(0)
- AddInfectionImages(affected_mob)
+/obj/item/organ/internal/body_egg/alien_embryo/on_find(mob/living/finder)
+ ..()
+ if(stage < 4)
+ finder << "It's small and weak, barely the size of a foetus."
else
- qdel(src)
+ finder << "It's grown quite large, and writhes slightly as you look at it."
+ if(prob(10))
+ AttemptGrow(0)
-/obj/item/alien_embryo/Destroy()
- if(affected_mob)
- affected_mob.status_flags &= ~(XENO_HOST)
- if(istype(affected_mob,/mob/living/carbon))
- var/mob/living/carbon/H = affected_mob
- H.med_hud_set_status()
- spawn(0)
- RemoveInfectionImages(affected_mob)
- return ..()
+/obj/item/organ/internal/body_egg/alien_embryo/prepare_eat()
+ var/obj/S = ..()
+ S.reagents.add_reagent("sacid", 10)
+ return S
-/obj/item/alien_embryo/process()
+/obj/item/organ/internal/body_egg/alien_embryo/on_life()
+ switch(stage)
+ if(2, 3)
+ if(prob(2))
+ owner.emote("sneeze")
+ if(prob(2))
+ owner.emote("cough")
+ if(prob(2))
+ owner << "Your throat feels sore."
+ if(prob(2))
+ owner << "Mucous runs down the back of your throat."
+ if(4)
+ if(prob(2))
+ owner.emote("sneeze")
+ if(prob(2))
+ owner.emote("cough")
+ if(prob(4))
+ owner << "Your muscles ache."
+ if(prob(20))
+ owner.take_organ_damage(1)
+ if(prob(4))
+ owner << "Your stomach hurts."
+ if(prob(20))
+ owner.adjustToxLoss(1)
+ if(5)
+ owner << "You feel something tearing its way out of your stomach..."
+ owner.adjustToxLoss(10)
+
+/obj/item/organ/internal/body_egg/alien_embryo/egg_process()
if(!affected_mob) return
if(loc != affected_mob)
affected_mob.status_flags &= ~(XENO_HOST)
@@ -51,38 +70,15 @@ var/const/ALIEN_AFK_BRACKET = 450 // 45 seconds
spawn(0)
RefreshInfectionImage()
- switch(stage)
- if(2, 3)
- if(prob(1))
- affected_mob.emote("sneeze")
- if(prob(1))
- affected_mob.emote("cough")
- if(prob(1))
- affected_mob << "Your throat feels sore."
- if(prob(1))
- affected_mob << "Mucous runs down the back of your throat."
- if(4)
- if(prob(1))
- affected_mob.emote("sneeze")
- if(prob(1))
- affected_mob.emote("cough")
- if(prob(2))
- affected_mob << "Your muscles ache."
- if(prob(20))
- affected_mob.take_organ_damage(1)
- if(prob(2))
- affected_mob << "Your stomach hurts."
- if(prob(20))
- affected_mob.adjustToxLoss(1)
- affected_mob.updatehealth()
- if(5)
- affected_mob << "You feel something tearing its way out of your stomach..."
- affected_mob.adjustToxLoss(10)
- affected_mob.updatehealth()
- if(prob(50))
- AttemptGrow()
-/obj/item/alien_embryo/proc/AttemptGrow(var/gib_on_success = 1)
+ if(stage == 5 && prob(50))
+ //for(var/datum/surgery/S in owner.surgeries)
+ // if(S.location == "chest" && istype(S.get_surgery_step(), /datum/surgery_step/manipulate_organs))
+ // AttemptGrow(0)
+ // return
+ AttemptGrow()
+
+/obj/item/organ/internal/body_egg/alien_embryo/proc/AttemptGrow(var/gib_on_success = 1)
var/list/candidates = get_candidates(ROLE_ALIEN,ALIEN_AFK_BRACKET,1)
var/client/C = null
@@ -123,7 +119,7 @@ var/const/ALIEN_AFK_BRACKET = 450 // 45 seconds
Proc: RefreshInfectionImage()
Des: Removes the current icons located in the infected mob adds the current stage
----------------------------------------*/
-/obj/item/alien_embryo/proc/RefreshInfectionImage()
+/obj/item/organ/internal/body_egg/alien_embryo/RefreshInfectionImage()
RemoveInfectionImages()
AddInfectionImages()
@@ -131,7 +127,7 @@ Des: Removes the current icons located in the infected mob adds the current stag
Proc: AddInfectionImages(C)
Des: Adds the infection image to all aliens for this embryo
----------------------------------------*/
-/obj/item/alien_embryo/proc/AddInfectionImages()
+/obj/item/organ/internal/body_egg/alien_embryo/AddInfectionImages()
for(var/mob/living/carbon/alien/alien in player_list)
if(alien.client)
var/I = image('icons/mob/alien.dmi', loc = affected_mob, icon_state = "infected[stage]")
@@ -141,7 +137,7 @@ Des: Adds the infection image to all aliens for this embryo
Proc: RemoveInfectionImage(C)
Des: Removes all images from the mob infected by this embryo
----------------------------------------*/
-/obj/item/alien_embryo/proc/RemoveInfectionImages()
+/obj/item/organ/internal/body_egg/alien_embryo/RemoveInfectionImages()
for(var/mob/living/carbon/alien/alien in player_list)
if(alien.client)
for(var/image/I in alien.client.images)
diff --git a/code/modules/mob/living/carbon/human/update_icons.dm b/code/modules/mob/living/carbon/human/update_icons.dm
index faa638f401e..b768039ac29 100644
--- a/code/modules/mob/living/carbon/human/update_icons.dm
+++ b/code/modules/mob/living/carbon/human/update_icons.dm
@@ -381,6 +381,9 @@ var/global/list/damage_icon_parts = list()
else
//warning("Invalid f_style for [species.name]: [f_style]")
+ if(!get_int_organ(/obj/item/organ/internal/brain))
+ face_standing += icon("icon"='icons/mob/human_face.dmi', "icon_state" = "debrained_s")
+
if(h_style && !(head && (head.flags & BLOCKHEADHAIR) && !(isSynthetic())))
var/datum/sprite_accessory/hair_style = hair_styles_list[h_style]
if(hair_style && hair_style.species_allowed)
@@ -393,9 +396,6 @@ var/global/list/damage_icon_parts = list()
else
//warning("Invalid h_style for [species.name]: [h_style]")
- if(!get_int_organ(/obj/item/organ/internal/brain))
- face_standing += icon("icon"='icons/mob/human_face.dmi', "icon_state" = "debrained_s")
-
overlays_standing[HAIR_LAYER] = image(face_standing)
if(update_icons) update_icons()
diff --git a/code/modules/reagents/reagent_containers.dm b/code/modules/reagents/reagent_containers.dm
index 7f9c3ee3c98..3fa08e42a03 100644
--- a/code/modules/reagents/reagent_containers.dm
+++ b/code/modules/reagents/reagent_containers.dm
@@ -46,10 +46,10 @@
/obj/item/weapon/reagent_containers/attack_self(mob/user as mob)
return
-/obj/item/weapon/reagent_containers/attack(mob/M as mob, mob/user as mob, def_zone)
- if (can_operate(M)) //Checks if mob is lying down on table for surgery
- if (do_surgery(M,user,src))
- return
+///obj/item/weapon/reagent_containers/attack(mob/M as mob, mob/user as mob, def_zone)
+// if (can_operate(M)) //Checks if mob is lying down on table for surgery
+// if (do_surgery(M,user,src))
+// return
// this prevented pills, food, and other things from being picked up by bags.
// possibly intentional, but removing it allows us to not duplicate functionality.
diff --git a/code/modules/surgery/helpers.dm b/code/modules/surgery/helpers.dm
index 9340099a1bb..52d68c4fbd7 100644
--- a/code/modules/surgery/helpers.dm
+++ b/code/modules/surgery/helpers.dm
@@ -1,46 +1,61 @@
/proc/attempt_initiate_surgery(obj/item/I, mob/living/M, mob/user)
+ world << "[istype(M)]"
if(istype(M))
var/mob/living/carbon/human/H
var/obj/item/organ/external/affecting
var/selected_zone = user.zone_sel.selecting
-
+ world << "line 8"
if(istype(M, /mob/living/carbon/human))
H = M
+ world <<"line 10"
affecting = H.get_organ(check_zone(selected_zone))
- if(can_operate(M)) //if they're prone or a slime
+ if(can_operate(H)) //if they're prone or a slime
var/datum/surgery/current_surgery
+ world << "line 15"
for(var/datum/surgery/S in M.surgeries)
if(S.location == selected_zone)
current_surgery = S
+ world << "[S]"
if(!current_surgery)
var/list/all_surgeries = surgeries_list.Copy()
var/list/available_surgeries = list()
+ world << "line 24"
for(var/datum/surgery/S in all_surgeries)
if(!S.possible_locs.Find(selected_zone))
+ world << "line 29"
+ world << "[selected_zone]"
continue
if(affecting && S.requires_organic_bodypart && affecting.status == ORGAN_ROBOT)
+ world << "line 30"
continue
if(!S.can_start(user, M))
+ world << "line 31"
continue
for(var/path in S.allowed_species)
+ world << "[path]"
+ world << "[M]"
if(istype(M, path))
+ world << "line 32"
+ world << "[path]"
available_surgeries[S.name] = S
break
var/P = input("Begin which procedure?", "Surgery", null, null) as null|anything in available_surgeries
if(P && user && user.Adjacent(M) && (I in user))
+ world << "line 40"
var/datum/surgery/S = available_surgeries[P]
var/datum/surgery/procedure = new S.type
if(procedure)
procedure.location = selected_zone
M.surgeries += procedure
procedure.organ_ref = affecting
- //just use the scalpel cut message
+ user.visible_message("[user] prepares to operate on [M]'s [parse_zone(selected_zone)].", \
+ "You prepare to operate on [M]'s [parse_zone(selected_zone)].")
else if(!current_surgery.step_in_progress)
if(current_surgery.status == 1)
diff --git a/code/modules/surgery/organs_internal.dm b/code/modules/surgery/organs_internal.dm
index 0e18d6a357c..6e9d1228ecd 100644
--- a/code/modules/surgery/organs_internal.dm
+++ b/code/modules/surgery/organs_internal.dm
@@ -125,12 +125,8 @@
var/obj/item/organ/internal/body_egg/alien_embryo/A = target.get_int_organ(/obj/item/organ/internal/body_egg/alien_embryo)
if(A)
user << "You found an unknown alien organism in [target]'s chest!"
- if(A.stage < 4)
- user << "It's small and weak, barely the size of a foetus."
- else
- user << "It's grown quite large, and writhes slightly as you look at it."
- if(prob(10))
- A.AttemptGrow()
+ if(prob(10))
+ A.AttemptGrow()
A.remove(target)
A.loc = get_turf(target)
@@ -154,7 +150,7 @@
allowed_tools = list(/obj/item/organ/internal = 100, /obj/item/weapon/reagent_containers/food/snacks/organ = 0)
var/implements_extract = list(/obj/item/weapon/hemostat = 100, /obj/item/weapon/crowbar = 55)
- var/implements_mend = list(/obj/item/stack/medical/advanced/bruise_pack= 100,/obj/item/stack/medical/bruise_pack = 20
+ var/implements_mend = list(/obj/item/stack/medical/advanced/bruise_pack= 100,/obj/item/stack/nanopaste = 100,/obj/item/stack/medical/bruise_pack = 20
)
var/current_type
var/obj/item/organ/internal/I = null
@@ -222,16 +218,21 @@
tool_name = "regenerative membrane"
else if (istype(tool, /obj/item/stack/medical/bruise_pack))
tool_name = "the bandaid"
+ else if (istype(tool, /obj/item/stack/nanopaste))
+ tool_name = "\the [tool]" //what else do you call nanopaste medically?
if (!hasorgans(target))
return
for(var/obj/item/organ/internal/I in affected.internal_organs)
if(I && I.damage > 0)
- if(I.robotic < 2)
+ if(I.robotic < 2 && !istype (tool, /obj/item/stack/nanopaste))
if(!I.sterile)
spread_germs_to_organ(I, user)
user.visible_message("[user] starts treating damage to [target]'s [I.name] with [tool_name].", \
"You start treating damage to [target]'s [I.name] with [tool_name]." )
+ else if(I.robotic > 2 && istype(tool, /obj/item/stack/nanopaste))
+ user.visible_message("[user] starts treating damage to [target]'s [I.name] with [tool_name].", \
+ "You start treating damage to [target]'s [I.name] with [tool_name]." )
target.custom_pain("The pain in your [affected.name] is living hell!",1)
else if(istype(tool, /obj/item/weapon/reagent_containers/food/snacks/organ))
@@ -253,7 +254,11 @@
if(I)
I.surgeryize()
if(I && I.damage > 0)
- if(I.robotic < 2)
+ if(I.robotic < 2 && !istype (tool, /obj/item/stack/nanopaste))
+ user.visible_message("\blue [user] treats damage to [target]'s [I.name] with [tool_name].", \
+ "\blue You treat damage to [target]'s [I.name] with [tool_name]." )
+ I.damage = 0
+ else if(I.robotic > 2 && istype (tool, /obj/item/stack/nanopaste))
user.visible_message("\blue [user] treats damage to [target]'s [I.name] with [tool_name].", \
"\blue You treat damage to [target]'s [I.name] with [tool_name]." )
I.damage = 0
@@ -282,7 +287,7 @@
user.visible_message("[user] can't seem to extract anything from [target]'s [parse_zone(target_zone)]!",
"You can't extract anything from [target]'s [parse_zone(target_zone)]!")
return 0
- ..()
+
//////////////////////////////////////////////////////////////////
// CHEST INTERNAL ORGAN SURGERY //
diff --git a/code/modules/surgery/robotics.dm b/code/modules/surgery/robotics.dm
index 2a8fb4758e1..d0fe89dcd41 100644
--- a/code/modules/surgery/robotics.dm
+++ b/code/modules/surgery/robotics.dm
@@ -5,10 +5,17 @@
/datum/surgery/cybernetic_repair
name = "Cybernetic Repair"
- steps = list(/datum/surgery_step/robotics/external/unscrew_hatch,/datum/surgery_step/robotics/external/open_hatch,/datum/surgery_step/robotics/fix_organ_robotic,/datum/surgery_step/robotics/external/close_hatch)
+ steps = list(/datum/surgery_step/robotics/external/unscrew_hatch,/datum/surgery_step/robotics/external/open_hatch,/datum/surgery_step/robotics/external/repair_brute,/datum/surgery_step/robotics/external/repair_burn,/datum/surgery_step/robotics/external/close_hatch)
possible_locs = list("chest","head","l_arm", "l_hand","r_arm","r_hand","r_leg","r_foot","l_leg","l_foot","groin")
requires_organic_bodypart = 0
+/datum/surgery/cybernetic_repair
+ name = "Cybernetic Mainpulation"
+ steps = list(/datum/surgery_step/robotics/external/unscrew_hatch,/datum/surgery_step/robotics/external/open_hatch,/datum/surgery_step/robotics/manipulate_robotic_organs)
+ possible_locs = list("chest","head","groin")
+ requires_organic_bodypart = 0
+
+
//to do, moar surgerys or condense down ala mainpulate organs.
/datum/surgery_step/robotics
can_infect = 0
@@ -214,31 +221,122 @@
"\red You cause a short circuit in [target]'s [affected.name]!")
target.apply_damage(rand(5,10), BURN, affected)
-/datum/surgery_step/robotics/fix_organ_robotic //For artificial organs
- allowed_tools = list(
- /obj/item/stack/nanopaste = 100, \
- /obj/item/weapon/bonegel = 30, \
- /obj/item/weapon/screwdriver = 70, \
- )
+///////condenseing remove/extract/repair here. /////////////
+/datum/surgery_step/robotics/manipulate_robotic_organs
+ allowed_tools = list(/obj/item/device/mmi = 100)
+ var/implements_extract = list(/obj/item/device/multitool = 100)
+ var/implements_mend = list( /obj/item/stack/nanopaste = 100,/obj/item/weapon/bonegel = 30, /obj/item/weapon/screwdriver = 70)
+ var/implements_insert = list(/obj/item/weapon/screwdriver = 100)
+ var/current_type
+ var/obj/item/organ/internal/I = null
+ var/obj/item/organ/external/affected = null
min_duration = 70
max_duration = 90
- can_use(mob/living/user, mob/living/carbon/human/target, target_zone, obj/item/tool,datum/surgery/surgery)
+/datum/surgery_step/robotics/manipulate_robotic_organs/New()
+ ..()
+ allowed_tools = allowed_tools + implements_extract + implements_mend + implements_insert
- if (!hasorgans(target))
- return
- var/obj/item/organ/external/affected = target.get_organ(target_zone)
- if(!affected) return
- var/is_organ_damaged = 0
- for(var/obj/item/organ/internal/I in affected.internal_organs)
- if(I.damage > 0 && I.robotic >= 2)
- is_organ_damaged = 1
- break
- return affected.open_enough_for_surgery() && is_organ_damaged
- begin_step(mob/living/user, mob/living/carbon/human/target, target_zone, obj/item/tool,datum/surgery/surgery)
+
+/datum/surgery_step/robotics/manipulate_robotic_organs/begin_step(mob/living/user, mob/living/carbon/human/target, target_zone, obj/item/tool,datum/surgery/surgery)
+
+ I = null
+ affected = target.get_organ(target_zone)
+ if(tool in implements_insert)
+ current_type = "insert"
+ //I = tool
+ var/off_tool = user.get_inactive_hand()
+
+ if(!off_tool || !istype(off_tool,/obj/item/organ/internal))
+ user << "You need a replacement internal part in your off hand."
+ return -1
+ I = off_tool //and please god let it be an organ...
+ if(target_zone != I.parent_organ || target.get_organ_slot(I.slot))
+ user << "There is no room for [I] in [target]'s [parse_zone(target_zone)]!"
+ return -1
+
+ if(I.damage > (I.max_damage * 0.75))
+ user << " \The [I] is in no state to be transplanted."
+ return -1
+
+ if(target.get_int_organ(I))
+ user << "\red \The [target] already has [I]."
+ return -1
+
+ user.visible_message("[user] begins reattaching [target]'s [tool] with \the [tool].", \
+ "You start reattaching [target]'s [surgery.current_organ] with \the [tool].")
+ target.custom_pain("Someone's rooting around in your [affected.name]!",1)
+ else if(istype(tool,/obj/item/device/mmi/))
+ current_type = "install"
+
+ if(target_zone != "chest")
+ user << " You must target the chest cavity."
+
+ return -1
+ var/obj/item/device/mmi/M = tool
+
+
+ if(!(affected && affected.open_enough_for_surgery()))
+ return -1
+
+ if(!istype(M))
+ return -1
+
+ if(!M.brainmob || !M.brainmob.client || !M.brainmob.ckey || M.brainmob.stat >= DEAD)
+ user << "That brain is not usable."
+ return -1
+
+ if(!(affected.status & ORGAN_ROBOT))
+ user << "You cannot install a computer brain into a meat enclosure."
+ return -1
+
+ if(!target.species)
+ user << "You have no idea what species this person is. Report this on the bug tracker."
+ return -1
+
+ if(!target.species.has_organ["brain"])
+ user << "You're pretty sure [target.species.name_plural] don't normally have a brain."
+ return -1
+
+ if(target.get_int_organ(/obj/item/organ/internal/brain/))
+ user << "Your subject already has a brain."
+ return -1
+
+ user.visible_message("[user] starts installing \the [tool] into [target]'s [affected.name].", \
+ "You start installing \the [tool] into [target]'s [affected.name].")
+
+ else if(tool in implements_extract)
+ current_type = "extract"
+ var/list/organs = target.get_organs_zone(target_zone)
+ if(!(affected && (affected.status & ORGAN_ROBOT)))
+ return -1
+ if(!affected.open_enough_for_surgery())
+ return -1
+ if(!organs.len)
+ user << "There is no removeable organs in [target]'s [parse_zone(target_zone)]!"
+ return -1
+ else
+ for(var/obj/item/organ/internal/O in organs)
+ O.on_find(user)
+ organs -= O
+ organs[O.name] = O
+
+ I = input("Remove which organ?", "Surgery", null, null) as null|anything in organs
+ if(I && user && target && user.Adjacent(target) && user.get_active_hand() == tool)
+ I = organs[I]
+ if(!I) return -1
+ user.visible_message("[user] starts to decouple [target]'s [I] with \the [tool].", \
+ "You start to decouple [target]'s [I] with \the [tool]." )
+
+ target.custom_pain("The pain in your [affected.name] is living hell!",1)
+ else
+ return -1
+
+ else if(tool in implements_mend)
+ current_type = "mend"
if (!hasorgans(target))
return
var/obj/item/organ/external/affected = target.get_organ(target_zone)
@@ -250,24 +348,69 @@
"You start mending the damage to [target]'s [I.name]'s mechanisms." )
target.custom_pain("The pain in your [affected.name] is living hell!",1)
- ..()
- end_step(mob/living/user, mob/living/carbon/human/target, target_zone, obj/item/tool,datum/surgery/surgery)
+ ..()
+
+/datum/surgery_step/robotics/manipulate_robotic_organs/end_step(mob/living/user, mob/living/carbon/human/target, target_zone, obj/item/tool,datum/surgery/surgery)
+ if(current_type == "mend")
if (!hasorgans(target))
return
- var/obj/item/organ/external/affected = target.get_organ(target_zone)
-
for(var/obj/item/organ/internal/I in affected.internal_organs)
-
if(I && I.damage > 0)
if(I.robotic >= 2)
user.visible_message("\blue [user] repairs [target]'s [I.name] with [tool].", \
"\blue You repair [target]'s [I.name] with [tool]." )
I.damage = 0
+ return 1
+ else if(current_type == "insert")
+ var/obj/item/organ/internal/I = target.get_int_organ(surgery.current_organ)
- fail_step(mob/living/user, mob/living/carbon/human/target, target_zone, obj/item/tool,datum/surgery/surgery)
+ var/off_tool = user.get_inactive_hand()
+ I = off_tool
+ user.drop_item()
+ I.insert(target)
+ user.visible_message("\blue [user] has reattached [target]'s [I] with \the [tool]." , \
+ "\blue You have reattached [target]'s [I] with \the [tool].")
+ if(I && istype(I))
+ I.status &= ~ORGAN_CUT_AWAY
+ else if (current_type == "install")
+ user.visible_message("\blue [user] has installed \the [tool] into [target]'s [affected.name].", \
+ "\blue You have installed \the [tool] into [target]'s [affected.name].")
+
+ var/obj/item/device/mmi/M = tool
+ var/obj/item/organ/internal/brain/mmi_holder/holder = new()
+ if (istype(M, /obj/item/device/mmi/posibrain))
+ holder.robotize()
+
+ holder.insert(target)
+ user.unEquip(tool)
+ tool.forceMove(holder)
+ holder.stored_mmi = tool
+ holder.update_from_mmi()
+
+ if(M.brainmob && M.brainmob.mind)
+ M.brainmob.mind.transfer_to(target)
+
+ else if(current_type == "extract")
+ if(I && I.owner == target)
+ user.visible_message("\blue [user] has decoupled [target]'s [surgery.current_organ] with \the [tool]." , \
+ "\blue You have decoupled [target]'s [surgery.current_organ] with \the [tool].")
+
+ add_logs(user, target, "surgically removed [I.name] from", addition="INTENT: [uppertext(user.a_intent)]")
+ spread_germs_to_organ(I, user)
+ I.status |= ORGAN_CUT_AWAY
+ I.remove(target)
+ I.loc = get_turf(target)
+ else
+ user.visible_message("[user] can't seem to extract anything from [target]'s [parse_zone(target_zone)]!",
+ "You can't extract anything from [target]'s [parse_zone(target_zone)]!")
+ return 0
+
+/datum/surgery_step/robotics/manipulate_robotic_organs/fail_step(mob/living/user, mob/living/carbon/human/target, target_zone, obj/item/tool,datum/surgery/surgery)
+
+ if(current_type == "mend")
if (!hasorgans(target))
return
var/obj/item/organ/external/affected = target.get_organ(target_zone)
@@ -282,108 +425,21 @@
if(I)
I.take_damage(rand(3,5),0)
-/datum/surgery_step/robotics/detatch_organ_robotic
-
- allowed_tools = list(
- /obj/item/device/multitool = 100
- )
-
- min_duration = 90
- max_duration = 110
-
- can_use(mob/living/user, mob/living/carbon/human/target, target_zone, obj/item/tool, datum/surgery/surgery)
-
- var/obj/item/organ/external/affected = target.get_organ(target_zone)
- if(!(affected && (affected.status & ORGAN_ROBOT)))
- return 0
- if(!affected.open_enough_for_surgery())
- return 0
-
- surgery.current_organ = null
- surgery.organ_ref = null
-
- var/list/attached_organs = list()
- for(var/organ in affected.internal_organs)
- var/obj/item/organ/internal/I = organ
- if(I && istype(I) && !(I.status & ORGAN_CUT_AWAY) && I.parent_organ == target_zone)
- attached_organs[I.organ_tag] = I
-
- var/organ_to_remove = input(user, "Which organ do you want to prepare for removal?") as null|anything in attached_organs
- if(!organ_to_remove)
- return 0
-
- surgery.current_organ = organ_to_remove
- surgery.organ_ref = attached_organs[organ_to_remove]
-
- return ..() && organ_to_remove
-
- begin_step(mob/living/user, mob/living/carbon/human/target, target_zone, obj/item/tool,datum/surgery/surgery)
- user.visible_message("[user] starts to decouple [target]'s [surgery.current_organ] with \the [tool].", \
- "You start to decouple [target]'s [surgery.current_organ] with \the [tool]." )
- ..()
-
- end_step(mob/living/user, mob/living/carbon/human/target, target_zone, obj/item/tool,datum/surgery/surgery)
- user.visible_message("\blue [user] has decoupled [target]'s [surgery.current_organ] with \the [tool]." , \
- "\blue You have decoupled [target]'s [surgery.current_organ] with \the [tool].")
-
- var/obj/item/organ/internal/I = target.get_int_organ(surgery.current_organ)
- if(I && istype(I))
- I.status |= ORGAN_CUT_AWAY
-
- fail_step(mob/living/user, mob/living/carbon/human/target, target_zone, obj/item/tool,datum/surgery/surgery)
+ else if(current_type == "insert")
user.visible_message("\red [user]'s hand slips, disconnecting \the [tool].", \
"\red Your hand slips, disconnecting \the [tool].")
-/datum/surgery_step/robotics/attach_organ_robotic
- allowed_tools = list(
- /obj/item/weapon/screwdriver = 100,
- )
-
- min_duration = 100
- max_duration = 120
-
- can_use(mob/living/user, mob/living/carbon/human/target, target_zone, obj/item/tool,datum/surgery/surgery)
-
- var/obj/item/organ/external/affected = target.get_organ(target_zone)
- if(!(affected && (affected.status & ORGAN_ROBOT)))
- return 0
- if(!affected.open_enough_for_surgery())
- return 0
-
- surgery.current_organ = null
- surgery.organ_ref = null
-
- var/list/removable_organs = list()
- for(var/organ in affected.internal_organs)
- var/obj/item/organ/internal/I = organ
- if(I && istype(I) && (I.status & ORGAN_CUT_AWAY) && (I.status & ORGAN_ROBOT) && I.parent_organ == target_zone)
- removable_organs[I.organ_tag] = I
-
- var/organ_to_replace = input(user, "Which organ do you want to reattach?") as null|anything in removable_organs
- if(!organ_to_replace)
- return 0
-
- surgery.current_organ = organ_to_replace
- surgery.organ_ref = removable_organs[organ_to_replace]
- return ..()
-
- begin_step(mob/living/user, mob/living/carbon/human/target, target_zone, obj/item/tool,datum/surgery/surgery)
- user.visible_message("[user] begins reattaching [target]'s [surgery.current_organ] with \the [tool].", \
- "You start reattaching [target]'s [surgery.current_organ] with \the [tool].")
- ..()
-
- end_step(mob/living/user, mob/living/carbon/human/target, target_zone, obj/item/tool,datum/surgery/surgery)
- user.visible_message("\blue [user] has reattached [target]'s [surgery.current_organ] with \the [tool]." , \
- "\blue You have reattached [target]'s [surgery.current_organ] with \the [tool].")
-
- var/obj/item/organ/internal/I = target.get_int_organ(surgery.current_organ)
- if(I && istype(I))
- I.status &= ~ORGAN_CUT_AWAY
-
- fail_step(mob/living/user, mob/living/carbon/human/target, target_zone, obj/item/tool,datum/surgery/surgery)
+ else if(current_type == "extract")
user.visible_message("\red [user]'s hand slips, disconnecting \the [tool].", \
"\red Your hand slips, disconnecting \the [tool].")
+ else if (current_type == "install")
+ user.visible_message("\red [user]'s hand slips!.", \
+ "\red Your hand slips!")
+ return -1
+
+
+
/datum/surgery_step/robotics/install_mmi
allowed_tools = list(
/obj/item/device/mmi = 100
diff --git a/code/modules/surgery/surgery.dm b/code/modules/surgery/surgery.dm
index f1cb16f138c..2c9570dab9b 100644
--- a/code/modules/surgery/surgery.dm
+++ b/code/modules/surgery/surgery.dm
@@ -3,11 +3,13 @@
var/name = "surgery"
var/status = 1
var/list/steps = list()
+ /*
var/eyes = 0
var/face = 0
var/appendix = 0
var/ribcage = 0
var/head_reattach = 0 //Steps in a surgery
+ */
var/can_cancel = 1
var/step_in_progress = 0
@@ -17,7 +19,7 @@
var/list/possible_locs = list() //Multiple locations -- c0
var/obj/item/organ/organ_ref //Operable body part
var/current_organ = "organ"
- var/list/allowed_species = null
+ var/list/allowed_species = list(/mob/living/carbon/human)
var/list/disallowed_species = null
/datum/surgery/proc/can_start(mob/user, mob/living/carbon/target)
@@ -31,7 +33,7 @@
var/datum/surgery_step/S = get_surgery_step()
if(S)
- if(S.begin_step(user, target, user.zone_sel.selecting, user.get_active_hand(), src))
+ if(S.try_op(user, target, user.zone_sel.selecting, user.get_active_hand(), src))
return 1
return 0
@@ -51,13 +53,15 @@
// type path referencing tools that can be used for this step, and how well are they suited for it
var/list/allowed_tools = null
- // type paths referencing mutantraces that this step applies to.
+ var/implement_type = null
// duration of the step
var/min_duration = 0
var/max_duration = 0
var/name
+ var/accept_hand = 0 //does the surgery step require an open hand? If true, ignores implements. Compatible with accept_any_item.
+ var/accept_any_item = 0
// evil infection stuff that will make everyone hate me
var/can_infect = 0
@@ -67,15 +71,42 @@
var/list/allowed_species = null
var/list/disallowed_species = null
+/datum/surgery_step/proc/try_op(mob/user, mob/living/carbon/target, target_zone, obj/item/tool, datum/surgery/surgery)
+ var/success = 0
+ if(accept_hand)
+ if(!tool)
+ success = 1
+ if(accept_any_item)
+ if(tool && tool_quality(tool))
+ success = 1
+ else
+ for(var/path in allowed_tools)
+ if(istype(tool, path))
+ implement_type = path
+ if(tool_quality(tool))
+ success = 1
+
+ if(success)
+ if(target_zone == surgery.location)
+ initiate(user, target, target_zone, tool, surgery)
+ return 1//returns 1 so we don't stab the guy in the dick or wherever.
+ if(isrobot(user) && user.a_intent != I_HARM) //to save asimov borgs a LOT of heartache
+ return 1
+ return 0
+
/datum/surgery_step/proc/initiate(mob/user, mob/living/carbon/target, target_zone, obj/item/tool, datum/surgery/surgery)
surgery.step_in_progress = 1
+ if(begin_step(user, target, target_zone, tool, surgery) == -1)
+ surgery.step_in_progress = 0
+ return
+
if(do_after(user, max_duration, target = target))
var/advance = 0
var/prob_chance = 100
- if(tool) //this means it isn't a require nd or any item step.
- prob_chance = allowed_tools[tool]
+ if(implement_type) //this means it isn't a require nd or any item step.
+ prob_chance = allowed_tools[implement_type]
prob_chance *= get_location_modifier(target)
if(prob(prob_chance) || isrobot(user))
@@ -176,7 +207,7 @@
S.fail_step(user, M, zone, tool) //malpractice~
else // This failing silently was a pain.
user << "You must remain close to your patient to conduct surgery."
- surgery.step_in_progress -= zone // Clear the in-progress flag.
+ surgery.step_in_progress = 0 // Clear the in-progress flag.
return 1 //don't want to do weapony things after surgery
if (user.a_intent == I_HELP)