mirror of
https://github.com/Bubberstation/Bubberstation.git
synced 2026-01-28 01:51:46 +00:00
* When any object is hit by an explosion, we no longer always call ex_act() on all its contents indiscriminately. The default contents_explosion() does nothing and it's overriden for certain objects only like storage items, machines with occupants, mechs. I've also overriden handle_atom_del() for many objects so that any sudden deletion of an object referenced in an object var of its container properly nullifies such references, avoiding potential runtime and updating the container's icon_state (e.g. admin-delete a mixer's beaker and the mixer's sprite updates immediately). I've tweaked bomb effect on worn clothes, having some armor but not 100% now still protects your clothes somewhat. Fixes some arguments of ex_act in living/ex_act() and other mobs. * derp and map fixes. * dem map fixes, man. * More work on code that use implants, simplified now that we can use the "implants" carbon var. * some fixes * more typos and fixes.
366 lines
11 KiB
Plaintext
366 lines
11 KiB
Plaintext
/*
|
|
* Data HUDs have been rewritten in a more generic way.
|
|
* In short, they now use an observer-listener pattern.
|
|
* See code/datum/hud.dm for the generic hud datum.
|
|
* Update the HUD icons when needed with the appropriate hook. (see below)
|
|
*/
|
|
|
|
/* DATA HUD DATUMS */
|
|
|
|
/atom/proc/add_to_all_human_data_huds()
|
|
for(var/datum/atom_hud/data/human/hud in huds) hud.add_to_hud(src)
|
|
|
|
/atom/proc/remove_from_all_data_huds()
|
|
for(var/datum/atom_hud/data/hud in huds) hud.remove_from_hud(src)
|
|
|
|
/datum/atom_hud/data
|
|
|
|
/datum/atom_hud/data/human/medical
|
|
hud_icons = list(STATUS_HUD, HEALTH_HUD)
|
|
|
|
/datum/atom_hud/data/human/medical/basic
|
|
|
|
/datum/atom_hud/data/human/medical/basic/proc/check_sensors(mob/living/carbon/human/H)
|
|
if(!istype(H)) return 0
|
|
var/obj/item/clothing/under/U = H.w_uniform
|
|
if(!istype(U)) return 0
|
|
if(U.sensor_mode <= 2) return 0
|
|
return 1
|
|
|
|
/datum/atom_hud/data/human/medical/basic/add_to_single_hud(mob/M, mob/living/carbon/H)
|
|
if(check_sensors(H))
|
|
..()
|
|
|
|
/datum/atom_hud/data/human/medical/basic/proc/update_suit_sensors(mob/living/carbon/H)
|
|
check_sensors(H) ? add_to_hud(H) : remove_from_hud(H)
|
|
|
|
/datum/atom_hud/data/human/medical/advanced
|
|
|
|
/datum/atom_hud/data/human/security
|
|
|
|
/datum/atom_hud/data/human/security/basic
|
|
hud_icons = list(ID_HUD)
|
|
|
|
/datum/atom_hud/data/human/security/advanced
|
|
hud_icons = list(ID_HUD, IMPTRACK_HUD, IMPLOYAL_HUD, IMPCHEM_HUD, WANTED_HUD)
|
|
|
|
/datum/atom_hud/data/diagnostic
|
|
hud_icons = list (DIAG_HUD, DIAG_STAT_HUD, DIAG_BATT_HUD, DIAG_MECH_HUD, DIAG_BOT_HUD)
|
|
|
|
/* MED/SEC/DIAG HUD HOOKS */
|
|
|
|
/*
|
|
* THESE HOOKS SHOULD BE CALLED BY THE MOB SHOWING THE HUD
|
|
*/
|
|
|
|
/***********************************************
|
|
Medical HUD! Basic mode needs suit sensors on.
|
|
************************************************/
|
|
|
|
//HELPERS
|
|
|
|
//called when a carbon changes virus
|
|
/mob/living/carbon/proc/check_virus()
|
|
var/threat = 0
|
|
for(var/datum/disease/D in viruses)
|
|
if(!(D.visibility_flags & HIDDEN_SCANNER))
|
|
if (D.severity != NONTHREAT) //a buffing virus gets an icon
|
|
threat = 2
|
|
return threat //harmful viruses have priority
|
|
else
|
|
threat = 1 //aka good virus
|
|
|
|
return threat
|
|
|
|
//helper for getting the appropriate health status
|
|
/proc/RoundHealth(mob/living/M)
|
|
if(M.stat == DEAD || (M.status_flags & FAKEDEATH))
|
|
return "health-100" //what's our health? it doesn't matter, we're dead, or faking
|
|
var/maxi_health = M.maxHealth
|
|
if(iscarbon(M) && M.health < 0)
|
|
maxi_health = 100 //so crit shows up right for aliens and other high-health carbon mobs; noncarbons don't have crit.
|
|
var/resulthealth = (M.health / maxi_health) * 100
|
|
switch(resulthealth)
|
|
if(100 to INFINITY)
|
|
return "health100"
|
|
if(90.625 to 100)
|
|
return "health93.75"
|
|
if(84.375 to 90.625)
|
|
return "health87.5"
|
|
if(78.125 to 84.375)
|
|
return "health81.25"
|
|
if(71.875 to 78.125)
|
|
return "health75"
|
|
if(65.625 to 71.875)
|
|
return "health68.75"
|
|
if(59.375 to 65.625)
|
|
return "health62.5"
|
|
if(53.125 to 59.375)
|
|
return "health56.25"
|
|
if(46.875 to 53.125)
|
|
return "health50"
|
|
if(40.625 to 46.875)
|
|
return "health43.75"
|
|
if(34.375 to 40.625)
|
|
return "health37.5"
|
|
if(28.125 to 34.375)
|
|
return "health31.25"
|
|
if(21.875 to 28.125)
|
|
return "health25"
|
|
if(15.625 to 21.875)
|
|
return "health18.75"
|
|
if(9.375 to 15.625)
|
|
return "health12.5"
|
|
if(1 to 9.375)
|
|
return "health6.25"
|
|
if(-50 to 1)
|
|
return "health0"
|
|
if(-85 to -50)
|
|
return "health-50"
|
|
if(-99 to -85)
|
|
return "health-85"
|
|
else
|
|
return "health-100"
|
|
return "0"
|
|
|
|
//HOOKS
|
|
|
|
//called when a human changes suit sensors
|
|
/mob/living/carbon/proc/update_suit_sensors()
|
|
var/datum/atom_hud/data/human/medical/basic/B = huds[DATA_HUD_MEDICAL_BASIC]
|
|
B.update_suit_sensors(src)
|
|
|
|
var/turf/T = get_turf(src)
|
|
if (T) crewmonitor.queueUpdate(T.z)
|
|
|
|
//called when a living mob changes health
|
|
/mob/living/proc/med_hud_set_health()
|
|
var/image/holder = hud_list[HEALTH_HUD]
|
|
holder.icon_state = "hud[RoundHealth(src)]"
|
|
var/icon/I = icon(icon, icon_state, dir)
|
|
holder.pixel_y = I.Height() - world.icon_size
|
|
|
|
//for carbon suit sensors
|
|
/mob/living/carbon/med_hud_set_health()
|
|
..()
|
|
|
|
var/turf/T = get_turf(src)
|
|
if(T)
|
|
crewmonitor.queueUpdate(T.z)
|
|
|
|
//called when a carbon changes stat, virus or XENO_HOST
|
|
/mob/living/proc/med_hud_set_status()
|
|
var/image/holder = hud_list[STATUS_HUD]
|
|
var/icon/I = icon(icon, icon_state, dir)
|
|
holder.pixel_y = I.Height() - world.icon_size
|
|
if(stat == DEAD || (status_flags & FAKEDEATH))
|
|
holder.icon_state = "huddead"
|
|
else
|
|
holder.icon_state = "hudhealthy"
|
|
|
|
/mob/living/carbon/med_hud_set_status()
|
|
var/image/holder = hud_list[STATUS_HUD]
|
|
var/icon/I = icon(icon, icon_state, dir)
|
|
var/virus_state = check_virus()
|
|
holder.pixel_y = I.Height() - world.icon_size
|
|
if(status_flags & XENO_HOST)
|
|
holder.icon_state = "hudxeno"
|
|
else if(stat == DEAD || (status_flags & FAKEDEATH))
|
|
holder.icon_state = "huddead"
|
|
else if(virus_state == 2)
|
|
holder.icon_state = "hudill"
|
|
else if(virus_state == 1)
|
|
holder.icon_state = "hudbuff"
|
|
else
|
|
holder.icon_state = "hudhealthy"
|
|
|
|
|
|
/***********************************************
|
|
Security HUDs! Basic mode shows only the job.
|
|
************************************************/
|
|
|
|
//HOOKS
|
|
|
|
/mob/living/carbon/human/proc/sec_hud_set_ID()
|
|
var/image/holder = hud_list[ID_HUD]
|
|
var/icon/I = icon(icon, icon_state, dir)
|
|
holder.pixel_y = I.Height() - world.icon_size
|
|
holder.icon_state = "hudno_id"
|
|
if(wear_id)
|
|
holder.icon_state = "hud[ckey(wear_id.GetJobName())]"
|
|
sec_hud_set_security_status()
|
|
|
|
var/turf/T = get_turf(src)
|
|
if (T) crewmonitor.queueUpdate(T.z)
|
|
|
|
/mob/living/carbon/human/proc/sec_hud_set_implants()
|
|
var/image/holder
|
|
for(var/i in list(IMPTRACK_HUD, IMPLOYAL_HUD, IMPCHEM_HUD))
|
|
holder = hud_list[i]
|
|
holder.icon_state = null
|
|
for(var/obj/item/weapon/implant/I in implants)
|
|
if(istype(I,/obj/item/weapon/implant/tracking))
|
|
holder = hud_list[IMPTRACK_HUD]
|
|
var/icon/IC = icon(icon, icon_state, dir)
|
|
holder.pixel_y = IC.Height() - world.icon_size
|
|
holder.icon_state = "hud_imp_tracking"
|
|
else if(istype(I,/obj/item/weapon/implant/mindshield))
|
|
holder = hud_list[IMPLOYAL_HUD]
|
|
var/icon/IC = icon(icon, icon_state, dir)
|
|
holder.pixel_y = IC.Height() - world.icon_size
|
|
holder.icon_state = "hud_imp_loyal"
|
|
else if(istype(I,/obj/item/weapon/implant/chem))
|
|
holder = hud_list[IMPCHEM_HUD]
|
|
var/icon/IC = icon(icon, icon_state, dir)
|
|
holder.pixel_y = IC.Height() - world.icon_size
|
|
holder.icon_state = "hud_imp_chem"
|
|
|
|
/mob/living/carbon/human/proc/sec_hud_set_security_status()
|
|
var/image/holder = hud_list[WANTED_HUD]
|
|
var/icon/I = icon(icon, icon_state, dir)
|
|
holder.pixel_y = I.Height() - world.icon_size
|
|
var/perpname = get_face_name(get_id_name(""))
|
|
if(perpname)
|
|
var/datum/data/record/R = find_record("name", perpname, data_core.security)
|
|
if(R)
|
|
switch(R.fields["criminal"])
|
|
if("*Arrest*")
|
|
holder.icon_state = "hudwanted"
|
|
return
|
|
if("Incarcerated")
|
|
holder.icon_state = "hudincarcerated"
|
|
return
|
|
if("Parolled")
|
|
holder.icon_state = "hudparolled"
|
|
return
|
|
if("Discharged")
|
|
holder.icon_state = "huddischarged"
|
|
return
|
|
holder.icon_state = null
|
|
|
|
/***********************************************
|
|
Diagnostic HUDs!
|
|
************************************************/
|
|
|
|
//For Diag health and cell bars!
|
|
/proc/RoundDiagBar(value)
|
|
switch(value * 100)
|
|
if(95 to INFINITY)
|
|
return "max"
|
|
if(80 to 100)
|
|
return "good"
|
|
if(60 to 80)
|
|
return "high"
|
|
if(40 to 60)
|
|
return "med"
|
|
if(20 to 40)
|
|
return "low"
|
|
if(1 to 20)
|
|
return "crit"
|
|
else
|
|
return "dead"
|
|
return "dead"
|
|
|
|
//Sillycone hooks
|
|
/mob/living/silicon/proc/diag_hud_set_health()
|
|
var/image/holder = hud_list[DIAG_HUD]
|
|
var/icon/I = icon(icon, icon_state, dir)
|
|
holder.pixel_y = I.Height() - world.icon_size
|
|
if(stat == DEAD)
|
|
holder.icon_state = "huddiagdead"
|
|
else
|
|
holder.icon_state = "huddiag[RoundDiagBar(health/maxHealth)]"
|
|
|
|
/mob/living/silicon/proc/diag_hud_set_status()
|
|
var/image/holder = hud_list[DIAG_STAT_HUD]
|
|
var/icon/I = icon(icon, icon_state, dir)
|
|
holder.pixel_y = I.Height() - world.icon_size
|
|
switch(stat)
|
|
if(CONSCIOUS)
|
|
holder.icon_state = "hudstat"
|
|
if(UNCONSCIOUS)
|
|
holder.icon_state = "hudoffline"
|
|
else
|
|
holder.icon_state = "huddead2"
|
|
|
|
//Borgie battery tracking!
|
|
/mob/living/silicon/robot/proc/diag_hud_set_borgcell()
|
|
var/image/holder = hud_list[DIAG_BATT_HUD]
|
|
var/icon/I = icon(icon, icon_state, dir)
|
|
holder.pixel_y = I.Height() - world.icon_size
|
|
if(cell)
|
|
var/chargelvl = (cell.charge/cell.maxcharge)
|
|
holder.icon_state = "hudbatt[RoundDiagBar(chargelvl)]"
|
|
else
|
|
holder.icon_state = "hudnobatt"
|
|
|
|
/*~~~~~~~~~~~~~~~~~~~~
|
|
BIG STOMPY MECHS
|
|
~~~~~~~~~~~~~~~~~~~~~*/
|
|
/obj/mecha/proc/diag_hud_set_mechhealth()
|
|
var/image/holder = hud_list[DIAG_MECH_HUD]
|
|
var/icon/I = icon(icon, icon_state, dir)
|
|
holder.pixel_y = I.Height() - world.icon_size
|
|
holder.icon_state = "huddiag[RoundDiagBar(obj_integrity/max_integrity)]"
|
|
|
|
|
|
/obj/mecha/proc/diag_hud_set_mechcell()
|
|
var/image/holder = hud_list[DIAG_BATT_HUD]
|
|
var/icon/I = icon(icon, icon_state, dir)
|
|
holder.pixel_y = I.Height() - world.icon_size
|
|
if(cell)
|
|
var/chargelvl = cell.charge/cell.maxcharge
|
|
holder.icon_state = "hudbatt[RoundDiagBar(chargelvl)]"
|
|
else
|
|
holder.icon_state = "hudnobatt"
|
|
|
|
|
|
/obj/mecha/proc/diag_hud_set_mechstat()
|
|
var/image/holder = hud_list[DIAG_STAT_HUD]
|
|
var/icon/I = icon(icon, icon_state, dir)
|
|
holder.pixel_y = I.Height() - world.icon_size
|
|
holder.icon_state = null
|
|
if(internal_damage)
|
|
holder.icon_state = "hudwarn"
|
|
|
|
/*~~~~~~~~~
|
|
Bots!
|
|
~~~~~~~~~~*/
|
|
/mob/living/simple_animal/bot/proc/diag_hud_set_bothealth()
|
|
var/image/holder = hud_list[DIAG_HUD]
|
|
var/icon/I = icon(icon, icon_state, dir)
|
|
holder.pixel_y = I.Height() - world.icon_size
|
|
holder.icon_state = "huddiag[RoundDiagBar(health/maxHealth)]"
|
|
|
|
/mob/living/simple_animal/bot/proc/diag_hud_set_botstat() //On (With wireless on or off), Off, EMP'ed
|
|
var/image/holder = hud_list[DIAG_STAT_HUD]
|
|
var/icon/I = icon(icon, icon_state, dir)
|
|
holder.pixel_y = I.Height() - world.icon_size
|
|
if(on)
|
|
holder.icon_state = "hudstat"
|
|
else if(stat) //Generally EMP causes this
|
|
holder.icon_state = "hudoffline"
|
|
else //Bot is off
|
|
holder.icon_state = "huddead2"
|
|
|
|
/mob/living/simple_animal/bot/proc/diag_hud_set_botmode() //Shows a bot's current operation
|
|
var/image/holder = hud_list[DIAG_BOT_HUD]
|
|
var/icon/I = icon(icon, icon_state, dir)
|
|
holder.pixel_y = I.Height() - world.icon_size
|
|
if(client) //If the bot is player controlled, it will not be following mode logic!
|
|
holder.icon_state = "hudsentient"
|
|
return
|
|
|
|
switch(mode)
|
|
if(BOT_SUMMON, BOT_RESPONDING) //Responding to PDA or AI summons
|
|
holder.icon_state = "hudcalled"
|
|
if(BOT_CLEANING, BOT_REPAIRING, BOT_HEALING) //Cleanbot cleaning, Floorbot fixing, or Medibot Healing
|
|
holder.icon_state = "hudworking"
|
|
if(BOT_PATROL, BOT_START_PATROL) //Patrol mode
|
|
holder.icon_state = "hudpatrol"
|
|
if(BOT_PREP_ARREST, BOT_ARREST, BOT_HUNT) //STOP RIGHT THERE, CRIMINAL SCUM!
|
|
holder.icon_state = "hudalert"
|
|
if(BOT_MOVING, BOT_DELIVER, BOT_GO_HOME, BOT_NAV) //Moving to target for normal bots, moving to deliver or go home for MULES.
|
|
holder.icon_state = "hudmove"
|
|
else
|
|
holder.icon_state = "" |