diff --git a/code/datums/organs/organ_external.dm b/code/datums/organs/organ_external.dm index aba465b3a14..641d1b7c061 100644 --- a/code/datums/organs/organ_external.dm +++ b/code/datums/organs/organ_external.dm @@ -186,10 +186,19 @@ src.update_damages() proc/bandage() + var/rval = 0 status |= ORGAN_BANDAGED for(var/datum/wound/W in wounds) + rval |= !W.bandaged W.bandaged = 1 + return rval + proc/salve() + var/rval = 0 + for(var/datum/wound/W in wounds) + rval |= !W.salved + W.salved = 1 + return rval proc/get_damage() //returns total damage return max(brute_dam + burn_dam - perma_injury, perma_injury) //could use health? diff --git a/code/game/machinery/bots/medbot.dm b/code/game/machinery/bots/medbot.dm index 82c1e38836b..d987a34f41e 100644 --- a/code/game/machinery/bots/medbot.dm +++ b/code/game/machinery/bots/medbot.dm @@ -6,16 +6,16 @@ /obj/machinery/bot/medbot name = "Medibot" desc = "A little medical robot. He looks somewhat underwhelmed." - icon = 'icons/obj/aibots.dmi' + icon = 'aibots.dmi' icon_state = "medibot0" layer = 5.0 - density = 0 + density = 1 anchored = 0 health = 20 maxhealth = 20 req_access =list(access_medical) var/stunned = 0 //It can be stunned by tasers. Delicate circuits. -//var/emagged = 0 + var/obj/machinery/camera/cam = null var/list/botcard_access = list(access_medical, access_morgue, access_genetics, access_robotics) var/obj/item/weapon/reagent_containers/glass/reagent_glass = null //Can be set to draw from this for reagents. var/skin = null //Set to "tox", "ointment" or "o2" for the other two firstaid kits. @@ -27,27 +27,29 @@ var/last_found = 0 var/last_newpatient_speak = 0 //Don't spam the "HEY I'M COMING" messages var/currently_healing = 0 - var/injection_amount = 15 //How much reagent do we inject at a time? + var/injection_amount = 5 //How much reagent do we inject at a time? var/heal_threshold = 15 //Start healing when they have this much damage in a category - var/use_beaker = 0 //Use reagents in beaker instead of default treatment agents. + var/use_beaker = 1 //Use reagents in beaker instead of default treatment agents. //Setting which reagents to use to treat what by default. By id. var/treatment_brute = "bicaridine" var/treatment_oxy = "dexalin" var/treatment_fire = "kelotane" var/treatment_tox = "anti_toxin" var/treatment_virus = "spaceacillin" + var/reagent_id = "inaprovaline" var/shut_up = 0 //self explanatory :) + var/always_inject = 0 /obj/machinery/bot/medbot/mysterious name = "Mysterious Medibot" desc = "International Medibot of mystery." skin = "bezerk" - treatment_oxy = "dexalinp" + reagent_id = "dexalinp" /obj/item/weapon/firstaid_arm_assembly name = "first aid/robot arm assembly" desc = "A first aid kit with a robot arm permanently grafted to it." - icon = 'icons/obj/aibots.dmi' + icon = 'aibots.dmi' icon_state = "firstaid_arm" var/build_step = 0 var/created_name = "Medibot" //To preserve the name if it's a unique medbot I guess @@ -58,7 +60,7 @@ ..() spawn(5) if(src.skin) - src.overlays += image('icons/obj/aibots.dmi', "kit_skin_[src.skin]") + src.overlays += image('aibots.dmi', "kit_skin_[src.skin]") /obj/machinery/bot/medbot/New() @@ -67,13 +69,16 @@ spawn(4) if(src.skin) - src.overlays += image('icons/obj/aibots.dmi', "medskin_[src.skin]") + src.overlays += image('aibots.dmi', "medskin_[src.skin]") src.botcard = new /obj/item/weapon/card/id(src) if(isnull(src.botcard_access) || (src.botcard_access.len < 1)) src.botcard.access = get_access("Medical Doctor") else src.botcard.access = src.botcard_access + src.cam = new /obj/machinery/camera(src) + src.cam.c_tag = src.name + src.cam.network = "Medbay" /obj/machinery/bot/medbot/turn_on() . = ..() @@ -101,7 +106,6 @@ var/dat dat += "Automatic Medical Unit v1.0

" dat += "Status: [src.on ? "On" : "Off"]
" - dat += "Maintenance panel panel is [src.open ? "opened" : "closed"]
" dat += "Beaker: " if (src.reagent_glass) dat += "Loaded \[[src.reagent_glass.reagents.total_volume]/[src.reagent_glass.reagents.maximum_volume]\]" @@ -126,6 +130,9 @@ dat += "Reagent Source: " dat += "[src.use_beaker ? "Loaded Beaker (When available)" : "Internal Synthesizer"]
" + dat += "Inject: " + dat += "[src.always_inject ? "Always" : "If loaded chemical is known to help"]
" + dat += "The speaker switch is [src.shut_up ? "off" : "on"]. Toggle" user << browse("Medibot v1.0 controls[dat]", "window=automed") @@ -161,13 +168,12 @@ else if((href_list["use_beaker"]) && (!src.locked)) src.use_beaker = !src.use_beaker + else if((href_list["toggle_inject"]) && (!src.locked)) + src.always_inject = !src.always_inject else if (href_list["eject"] && (!isnull(src.reagent_glass))) - if(!src.locked) - src.reagent_glass.loc = get_turf(src) - src.reagent_glass = null - else - usr << "You cannot eject the beaker because the panel is locked." + src.reagent_glass.loc = get_turf(src) + src.reagent_glass = null else if ((href_list["togglevoice"]) && (!src.locked)) src.shut_up = !src.shut_up @@ -177,30 +183,22 @@ /obj/machinery/bot/medbot/attackby(obj/item/weapon/W as obj, mob/user as mob) if (istype(W, /obj/item/weapon/card/id)||istype(W, /obj/item/device/pda)) - if (src.allowed(user) && !open && !emagged) + if (src.allowed(user)) src.locked = !src.locked - user << "Controls are now [src.locked ? "locked." : "unlocked."]" + user << "Controls are now [src.locked ? "locked." : "unlocked."]" src.updateUsrDialog() else - if(emagged) - user << "ERROR" - if(open) - user << "Please close the access panel before locking it." - else - user << "Access denied." + user << "\red Access denied." else if (istype(W, /obj/item/weapon/reagent_containers/glass)) - if(src.locked) - user << "You cannot insert a beaker because the panel is locked." - return if(!isnull(src.reagent_glass)) - user << "There is already a beaker loaded." + user << "There is already a beaker loaded!" return user.drop_item() W.loc = src src.reagent_glass = W - user << "You insert [W]." + user << "You insert [W]." src.updateUsrDialog() return @@ -211,20 +209,19 @@ /obj/machinery/bot/medbot/Emag(mob/user as mob) ..() - if(open && !locked) - if(user) user << "You short out [src]'s reagent synthesis circuits." - spawn(0) - for(var/mob/O in hearers(src, null)) - O.show_message("\red [src] buzzes oddly!", 1) - flick("medibot_spark", src) - src.patient = null - if(user) src.oldpatient = user - src.currently_healing = 0 - src.last_found = world.time - src.anchored = 0 - src.emagged = 2 - src.on = 1 - src.icon_state = "medibot[src.on]" + if(user) user << "\red You short out [src]'s reagent synthesis circuits." + spawn(0) + for(var/mob/O in hearers(src, null)) + O.show_message("\red [src] buzzes oddly!", 1) + flick("medibot_spark", src) + src.patient = null + if(user) src.oldpatient = user + src.currently_healing = 0 + src.last_found = world.time + src.anchored = 0 + src.emagged = 1 + src.on = 1 + src.icon_state = "medibot[src.on]" /obj/machinery/bot/medbot/process() set background = 1 @@ -254,7 +251,7 @@ src.path = new() if(!src.patient) - if(!src.shut_up && prob(1)) + if(prob(1) && (!src.shut_up)) var/message = pick("Radar, put a mask on!","There's always a catch, and it's the best there is.","I knew it, I should've been a plastic surgeon.","What kind of medbay is this? Everyone's dropping like dead flies.","Delicious!") src.speak(message) @@ -265,6 +262,9 @@ if ((C == src.oldpatient) && (world.time < src.last_found + 100)) continue + if(C.getOxyLoss() < 5 && reagent_id == "inaprovaline" && !src.emagged && !src.reagent_glass) + continue + if(src.assess_patient(C)) src.patient = C src.oldpatient = C @@ -324,7 +324,7 @@ if(C.suiciding) return 0 //Kevorkian school of robotic medical assistants. - if(src.emagged == 2) //Everyone needs our medicine. (Our medicine is toxins) + if(src.emagged) //Everyone needs our medicine. (Our medicine is toxins) return 1 //If they're injured, we're using a beaker, and don't have one of our WONDERCHEMS. @@ -335,25 +335,18 @@ continue //They're injured enough for it! - if((C.getBruteLoss() >= heal_threshold) && (!C.reagents.has_reagent(src.treatment_brute))) + if(C.getBruteLoss() >= heal_threshold) return 1 //If they're already medicated don't bother! - if((C.getOxyLoss() >= (15 + heal_threshold)) && (!C.reagents.has_reagent(src.treatment_oxy))) + if(C.getOxyLoss() >= (15 + heal_threshold)) return 1 - if((C.getFireLoss() >= heal_threshold) && (!C.reagents.has_reagent(src.treatment_fire))) + if(C.getFireLoss() >= heal_threshold) return 1 - if((C.getToxLoss() >= heal_threshold) && (!C.reagents.has_reagent(src.treatment_tox))) + if(C.getToxLoss() >= heal_threshold) return 1 - - for(var/datum/disease/D in C.viruses) - if((D.stage > 1) || (D.spread_type == AIRBORNE)) - - if (!C.reagents.has_reagent(src.treatment_virus)) - return 1 //STOP DISEASE FOREVER - return 0 /obj/machinery/bot/medbot/proc/medicate_patient(mob/living/carbon/C as mob) @@ -376,40 +369,37 @@ src.last_found = world.time return - var/reagent_id = null - - //Use whatever is inside the loaded beaker. If there is one. + //See if we have anything inside the beaker to help. if((src.use_beaker) && (src.reagent_glass) && (src.reagent_glass.reagents.total_volume)) - reagent_id = "internal_beaker" + if(always_inject) + reagent_id = "internal_beaker" + else if (C.getBruteLoss() >= heal_threshold && reagent_glass.reagents.has_reagent(src.treatment_brute)) + reagent_id = "internal_beaker" - if(src.emagged == 2) //Emagged! Time to poison everybody. + else if (C.getOxyLoss() >= (15 + heal_threshold) && reagent_glass.reagents.has_reagent(src.treatment_oxy)) + reagent_id = "internal_beaker" + + else if (C.getFireLoss() >= heal_threshold && reagent_glass.reagents.has_reagent(src.treatment_fire)) + reagent_id = "internal_beaker" + + else if (C.getToxLoss() >= heal_threshold && reagent_glass.reagents.has_reagent(src.treatment_tox)) + reagent_id = "internal_beaker" + + else if (100 - C.health >= heal_threshold && reagent_glass.reagents.has_reagent("tricordrazine")) + reagent_id = "internal_beaker" + + + if(src.emagged) //Emagged! Time to poison everybody. reagent_id = "toxin" - var/virus = 0 - for(var/datum/disease/D in C.viruses) - virus = 1 + if(reagent_id == "internal_beaker" && \ + src.patient.reagents.has_reagent(src.reagent_glass.reagents.get_master_reagent_id()) ) + if(prob(10)) + var/message = pick("Oops, that's an overdose!", "You're going to be just fine!") + src.speak(message) + return - if (!reagent_id && (virus)) - if(!C.reagents.has_reagent(src.treatment_virus)) - reagent_id = src.treatment_virus - - if (!reagent_id && (C.getBruteLoss() >= heal_threshold)) - if(!C.reagents.has_reagent(src.treatment_brute)) - reagent_id = src.treatment_brute - - if (!reagent_id && (C.getOxyLoss() >= (15 + heal_threshold))) - if(!C.reagents.has_reagent(src.treatment_oxy)) - reagent_id = src.treatment_oxy - - if (!reagent_id && (C.getFireLoss() >= heal_threshold)) - if(!C.reagents.has_reagent(src.treatment_fire)) - reagent_id = src.treatment_fire - - if (!reagent_id && (C.getToxLoss() >= heal_threshold)) - if(!C.reagents.has_reagent(src.treatment_tox)) - reagent_id = src.treatment_tox - - if(!reagent_id) //If they don't need any of that they're probably cured! + if(C.getOxyLoss() < 10 && reagent_id == "inaprovaline") //If they don't need any of that they're probably cured! src.oldpatient = src.patient src.patient = null src.currently_healing = 0 @@ -433,10 +423,9 @@ src.icon_state = "medibot[src.on]" src.currently_healing = 0 + reagent_id = "inaprovaline" return -// src.speak(reagent_id) - reagent_id = null return @@ -452,6 +441,11 @@ src.stunned = min(stunned+10,20) ..() +/obj/machinery/bot/medbot/emp_act(severity) + if (cam) + cam.emp_act(severity) + ..() + /obj/machinery/bot/medbot/explode() src.on = 0 for(var/mob/O in hearers(src, null)) @@ -478,53 +472,24 @@ return /obj/machinery/bot/medbot/Bump(M as mob|obj) //Leave no door unopened! - if ((istype(M, /obj/machinery/door)) && (!isnull(src.botcard))) - var/obj/machinery/door/D = M - if (!istype(D, /obj/machinery/door/firedoor) && D.check_access(src.botcard)) - D.open() + spawn(0) + if ((istype(M, /obj/machinery/door)) && (!isnull(src.botcard))) + var/obj/machinery/door/D = M + if (!istype(D, /obj/machinery/door/firedoor) && D.check_access(src.botcard)) + D.open() + src.frustration = 0 + else if ((istype(M, /mob/living/)) && (!src.anchored)) + src.loc = M:loc src.frustration = 0 - else if ((istype(M, /mob/living/)) && (!src.anchored)) - src.loc = M:loc - src.frustration = 0 + + return return -/* terrible /obj/machinery/bot/medbot/Bumped(atom/movable/M as mob|obj) spawn(0) if (M) var/turf/T = get_turf(src) M:loc = T -*/ - -/* - * Pathfinding procs, allow the medibot to path through doors it has access to. - */ - -//Pretty ugh -/* -/turf/proc/AdjacentTurfsAllowMedAccess() - var/L[] = new() - for(var/turf/t in oview(src,1)) - if(!t.density) - if(!LinkBlocked(src, t) && !TurfBlockedNonWindowNonDoor(t,get_access("Medical Doctor"))) - L.Add(t) - return L - - -//It isn't blocked if we can open it, man. -/proc/TurfBlockedNonWindowNonDoor(turf/loc, var/list/access) - for(var/obj/O in loc) - if(O.density && !istype(O, /obj/structure/window) && !istype(O, /obj/machinery/door)) - return 1 - - if (O.density && (istype(O, /obj/machinery/door)) && (access.len)) - var/obj/machinery/door/D = O - for(var/req in D.req_access) - if(!(req in access)) //doesn't have this access - return 1 - - return 0 -*/ /* * Medbot Assembly -- Can be made out of all three medkits. @@ -538,7 +503,7 @@ //Making a medibot! if(src.contents.len >= 1) - user << "You need to empty [src] out first." + user << "\red You need to empty [src] out first!" return var/obj/item/weapon/firstaid_arm_assembly/A = new /obj/item/weapon/firstaid_arm_assembly @@ -548,44 +513,48 @@ A.skin = "tox" else if(istype(src,/obj/item/weapon/storage/firstaid/o2)) A.skin = "o2" + else if(istype(src,/obj/item/weapon/storage/firstaid/adv)) + A.skin = "adv" + A.loc = user + if (user.r_hand == S) + user.u_equip(S) + user.r_hand = A + else + user.u_equip(S) + user.l_hand = A + A.layer = 20 + user << "You add the robot arm to the first aid kit" del(S) - user.put_in_hands(A) - user << "You add the robot arm to the first aid kit." - user.drop_from_inventory(src) del(src) /obj/item/weapon/firstaid_arm_assembly/attackby(obj/item/weapon/W as obj, mob/user as mob) ..() - if(istype(W, /obj/item/weapon/pen)) - var/t = stripped_input(user, "Enter new robot name", src.name, src.created_name) + if((istype(W, /obj/item/device/healthanalyzer)) && (!src.build_step)) + src.build_step++ + user << "You add the health sensor to [src]!" + src.name = "First aid/robot arm/health analyzer assembly" + src.overlays += image('aibots.dmi', "na_scanner") + del(W) + + else if((isprox(W)) && (src.build_step == 1)) + src.build_step++ + user << "You complete the Medibot! Beep boop." + var/obj/machinery/bot/medbot/S = new /obj/machinery/bot/medbot + S.skin = src.skin + S.loc = get_turf(src) + S.name = src.created_name + del(W) + del(src) + + else if(istype(W, /obj/item/weapon/pen)) + var/t = input(user, "Enter new robot name", src.name, src.created_name) as text + t = copytext(sanitize(t), 1, MAX_NAME_LEN) if (!t) return if (!in_range(src, usr) && src.loc != usr) return + src.created_name = t - else - switch(build_step) - if(0) - if(istype(W, /obj/item/device/healthanalyzer)) - user.drop_item() - del(W) - src.build_step++ - user << "You add the health sensor to [src]." - src.name = "First aid/robot arm/health analyzer assembly" - src.overlays += image('icons/obj/aibots.dmi', "na_scanner") - - if(1) - if(isprox(W)) - user.drop_item() - del(W) - src.build_step++ - user << "You complete the Medibot! Beep boop." - var/turf/T = get_turf(src) - var/obj/machinery/bot/medbot/S = new /obj/machinery/bot/medbot(T) - S.skin = src.skin - S.name = src.created_name - user.drop_from_inventory(src) - del(src) diff --git a/code/game/machinery/telecomms/broadcaster.dm b/code/game/machinery/telecomms/broadcaster.dm index ee411b7e785..3833e3f8048 100644 --- a/code/game/machinery/telecomms/broadcaster.dm +++ b/code/game/machinery/telecomms/broadcaster.dm @@ -366,6 +366,7 @@ var/message_delay = 0 // To make sure restarting the recentmessages list is kept // --- Filter the message; place it in quotes apply a verb --- + if(!M) return var/quotedmsg = M.say_quote(message) // --- This following recording is intended for research and feedback in the use of department radio channels --- diff --git a/code/game/objects/items/stacks/medical.dm b/code/game/objects/items/stacks/medical.dm index 57ffa477306..1b5403d3282 100644 --- a/code/game/objects/items/stacks/medical.dm +++ b/code/game/objects/items/stacks/medical.dm @@ -62,11 +62,21 @@ else if(affecting.name == "l_leg") child = H.get_organ("l_foot") - if (affecting.heal_damage(src.heal_brute, src.heal_burn) || child.heal_damage(src.heal_brute, src.heal_burn)) - H.UpdateDamageIcon() + if(src.heal_brute) + if(!affecting.bandage() && !child.bandage()) + user << "\red The wounds on this limb have already been bandaged." + else if(src.heal_burn) + if(!affecting.salve() && !child.salve()) + user << "\red The wounds on this limb have already been salved." else - if (affecting.heal_damage(src.heal_brute, src.heal_burn)) - H.UpdateDamageIcon() + if(src.heal_brute) + if(!affecting.bandage()) + user << "\red The wounds on this limb have already been bandaged." + else if(src.heal_burn) + if(!affecting.salve()) + user << "\red The wounds on this limb have already been salved." + + H.UpdateDamageIcon() M.updatehealth() else M.heal_organ_damage((src.heal_brute/2), (src.heal_burn/2)) diff --git a/code/modules/mob/living/carbon/human/examine.dm b/code/modules/mob/living/carbon/human/examine.dm index 39136deb07b..824062cf039 100644 --- a/code/modules/mob/living/carbon/human/examine.dm +++ b/code/modules/mob/living/carbon/human/examine.dm @@ -212,30 +212,8 @@ else//Brain is gone, doesn't matter if they are AFK or present msg += "It appears that [t_his] brain is missing...\n" - var/temp_dam = getBruteLoss() //no need to calculate each of these twice - msg += "" - if(temp_dam) - if(temp_dam < 30) - msg += "[t_He] [t_has] minor bruising.\n" - else - msg += "[t_He] [t_has] severe bruising!\n" - - temp_dam = getFireLoss() - if(temp_dam) - if(temp_dam < 30) - msg += "[t_He] [t_has] minor burns.\n" - else - msg += "[t_He] [t_has] severe burns!\n" - - temp_dam = getCloneLoss() - if(temp_dam) - if(temp_dam < 30) - msg += "[t_He] [t_has] minor genetic deformities.\n" - else - msg += "[t_He] [t_has] severe genetic deformities.\n" - if(nutrition < 100) msg += "[t_He] [t_is] severely malnourished.\n" else if(nutrition >= 500) diff --git a/code/modules/mob/living/say.dm b/code/modules/mob/living/say.dm index b822cd09c05..5858188d2a2 100644 --- a/code/modules/mob/living/say.dm +++ b/code/modules/mob/living/say.dm @@ -253,9 +253,14 @@ var/list/department_radio_keys = list( return if ("department") - if (src:ears) - src:ears.talk_into(src, message, message_mode) - used_radios += src:ears + if(istype(src, /mob/living/carbon)) + if (src:ears) + src:ears.talk_into(src, message, message_mode) + used_radios += src:ears + else if(istype(src, /mob/living/silicon/robot)) + if (src:radio) + src:radio.talk_into(src, message, message_mode) + used_radios += src:radio message_range = 1 italics = 1 diff --git a/code/modules/mob/living/silicon/robot/robot.dm b/code/modules/mob/living/silicon/robot/robot.dm index e3e8b0d823f..d9ea6ff9fda 100644 --- a/code/modules/mob/living/silicon/robot/robot.dm +++ b/code/modules/mob/living/silicon/robot/robot.dm @@ -177,7 +177,7 @@ icon_state = "landmate" modtype = "Eng" feedback_inc("cyborg_engineering",1) - channels = list("Engineering" = 0) + channels = list("Engineering" = 1) if("Janitor") updatename(mod) diff --git a/code/modules/mob/living/silicon/say.dm b/code/modules/mob/living/silicon/say.dm index 39c80bc7b02..3753a118ba1 100644 --- a/code/modules/mob/living/silicon/say.dm +++ b/code/modules/mob/living/silicon/say.dm @@ -24,7 +24,7 @@ message = copytext(message, 3) message = trim(copytext(sanitize(message), 1, MAX_MESSAGE_LEN)) robot_talk(message) - else if ((copytext(message, 1, 3) == ":h") || (copytext(message, 1, 3) == ":H")) + else if (isAI(src) && ((copytext(message, 1, 3) == ":h") || (copytext(message, 1, 3) == ":H"))) if(isAI(src)&&client)//For patching directly into AI holopads. var/mob/living/silicon/ai/U = src message = copytext(message, 3) diff --git a/code/modules/mob/new_player/new_player.dm b/code/modules/mob/new_player/new_player.dm index 7233cc2d813..6c43e58b0b0 100644 --- a/code/modules/mob/new_player/new_player.dm +++ b/code/modules/mob/new_player/new_player.dm @@ -363,9 +363,13 @@ proc/AnnounceArrival(var/mob/living/carbon/human/character, var/rank) if (ticker.current_state == GAME_STATE_PLAYING) + var/mob/living/silicon/ai/announcer = new (null) var/obj/item/device/radio/intercom/a = new /obj/item/device/radio/intercom(null)// BS12 EDIT Arrivals Announcement Computer, rather than the AI. - a.autosay("\"[character.real_name],[character.wear_id.assignment ? " [character.wear_id.assignment]," : "" ] has arrived on the station.\"", "Arrivals Announcement Computer") + announcer.name = "Arrivals Announcement Computer" + announcer.real_name = "Arrivals Announcement Computer" + a.autosay("\"[character.real_name],[character.wear_id.assignment ? " [character.wear_id.assignment]," : "" ] has arrived on the station.\"", announcer) del(a) + del(announcer) proc/LateChoices() var/mills = world.time // 1/10 of a second, not real milliseconds but whatever