Abling Disability (#4485)

This PR implements a system for manipulating a client's color safely and also ports a prioritization system for sorting client color from /tg/. Currently this PR also implements client coloration in the form of color blindness, namely:
Monochromacy
Deuteranopia
Tritanopia
Protanopia

DTP are mild brain traumas, whereas monocrhomacy is a severe brain trauma.
Furthermore, this PR removes the Needs Glasses prompt in character creation, and replaces it with a disability selector, allowing people to more closely refine their special little snowflakes.
Current disabilities available:
Nervousness
Nearsightedness
Deuteranopia
Tritanopia
Protanopia
Deafness
Muteness
This commit is contained in:
LordFowl
2018-04-05 21:57:50 +03:00
committed by Erki
parent b39269225e
commit 64e386785c
31 changed files with 272 additions and 15 deletions
+71
View File
@@ -0,0 +1,71 @@
/datum/client_color
var/client_color = "" //Any client.color-valid value
var/priority = 1 //Since only one client.color can be rendered on screen, we take the one with the highest priority value:
//eg: "Bloody screen" > "goggles color" as the former is much more important
/mob
var/list/client_colors = list()
/*
Adds an instance of color_type to the mob's client_colors list
color_type - a typepath (subtyped from /datum/client_color)
*/
/mob/proc/add_client_color(color_type)
if(!ispath(/datum/client_color))
return
var/datum/client_color/CC = new color_type()
client_colors |= CC
sortTim(client_colors, /proc/cmp_clientcolor_priority)
update_client_color()
/*
Removes an instance of color_type from the mob's client_colors list
color_type - a typepath (subtyped from /datum/client_color)
*/
/mob/proc/remove_client_color(color_type)
if(!ispath(/datum/client_color))
return
for(var/cc in client_colors)
var/datum/client_color/CC = cc
if(CC.type == color_type)
client_colors -= CC
qdel(CC)
break
update_client_color()
/*
Resets the mob's client.color to null, and then sets it to the highest priority
client_color datum, if one exists
*/
/mob/proc/update_client_color()
if(!client)
return
client.color = ""
if(!client_colors.len)
return
var/datum/client_color/CC = client_colors[1]
if(CC)
animate(client, color = CC.client_color)
/datum/client_color/monochrome
client_color = list(0.33,0.33,0.33, 0.33,0.33,0.33, 0.33,0.33,0.33)
priority = INFINITY
/datum/client_color/deuteranopia
client_color = list(0.47,0.38,0.15, 0.54,0.31,0.15, 0,0.3,0.7)
priority = 100
/datum/client_color/protanopia
client_color = list(0.51,0.4,0.12, 0.49,0.41,0.12, 0,0.2,0.76)
priority = 100
/datum/client_color/tritanopia
client_color = list(0.95,0.07,0, 0,0.44,0.52, 0.05,0.49,0.48)
priority = 100
@@ -103,7 +103,7 @@ var/global/list/valid_bloodtypes = list("A+", "A-", "B+", "B-", "AB+", "AB-", "O
"facial_style" = pref.f_style,
"eyes_colour" = rgb(pref.r_eyes, pref.g_eyes, pref.b_eyes),
"b_type" = pref.b_type,
"disabilities" = pref.disabilities,
"disabilities" = json_encode(pref.disabilities),
"organs_data" = list2params(pref.organ_data),
"organs_robotic"= list2params(pref.rlimb_data),
"body_markings" = json_encode(pref.body_markings),
@@ -135,8 +135,6 @@ var/global/list/valid_bloodtypes = list("A+", "A-", "B+", "B-", "AB+", "AB-", "O
pref.g_eyes = GetGreenPart(pref.eyes_colour)
pref.b_eyes = GetBluePart(pref.eyes_colour)
pref.disabilities = text2num(pref.disabilities)
if (istext(pref.organ_data))
pref.organ_data = params2list(pref.organ_data)
if (istext(pref.rlimb_data))
@@ -148,6 +146,13 @@ var/global/list/valid_bloodtypes = list("A+", "A-", "B+", "B-", "AB+", "AB-", "O
catch (var/exception/e)
log_debug("BODY MARKINGS: Caught [e]. Initial value: [before]")
pref.body_markings = list()
if (istext(pref.disabilities))
var/before = pref.disabilities
try
pref.disabilities = json_decode(pref.disabilities)
catch (var/exception/e)
log_debug("DISABILITIES: Caught [e]. Initial value: [before]")
pref.disabilities = list()
pref.r_hair = sanitize_integer(pref.r_hair, 0, 255, initial(pref.r_hair))
pref.g_hair = sanitize_integer(pref.g_hair, 0, 255, initial(pref.g_hair))
@@ -166,13 +171,14 @@ var/global/list/valid_bloodtypes = list("A+", "A-", "B+", "B-", "AB+", "AB-", "O
pref.b_eyes = sanitize_integer(pref.b_eyes, 0, 255, initial(pref.b_eyes))
pref.b_type = sanitize_text(pref.b_type, initial(pref.b_type))
pref.disabilities = sanitize_integer(pref.disabilities, 0, 65535, initial(pref.disabilities))
if (!pref.organ_data || !islist(pref.organ_data))
pref.organ_data = list()
if (!pref.rlimb_data || !islist(pref.rlimb_data))
pref.rlimb_data = list()
if (!pref.body_markings || !islist(pref.body_markings))
pref.body_markings = list()
if (!pref.disabilities || !islist(pref.disabilities))
pref.disabilities = list()
/datum/category_item/player_setup_item/general/body/content(var/mob/user)
var/list/out = list()
@@ -189,7 +195,9 @@ var/global/list/valid_bloodtypes = list("A+", "A-", "B+", "B-", "AB+", "AB-", "O
out += "Blood Type: <a href='?src=\ref[src];blood_type=1'>[pref.b_type]</a><br>"
if(has_flag(mob_species, HAS_SKIN_TONE))
out += "Skin Tone: <a href='?src=\ref[src];skin_tone=1'>[-pref.s_tone + 35]/220</a><br>"
out += "Needs Glasses: <a href='?src=\ref[src];disabilities=[NEARSIGHTED]'><b>[pref.disabilities & NEARSIGHTED ? "Yes" : "No"]</b></a><br>"
out += "Disabilities: <a href='?src=\ref[src];trait_add=1'>Adjust</a><br>"
for(var/M in pref.disabilities)
out += " [M] <a href='?src=\ref[src];trait_remove=[M]'>-</a><br>"
if(!(has_flag(mob_species, HAS_FBP)))
out += "Limbs: <a href='?src=\ref[src];limbs=1'>Adjust</a><br>"
out += "Internal Organs: <a href='?src=\ref[src];organs=1'>Adjust</a><br>"
@@ -622,9 +630,17 @@ var/global/list/valid_bloodtypes = list("A+", "A-", "B+", "B-", "AB+", "AB-", "O
return TOPIC_REFRESH
else if(href_list["disabilities"])
var/disability_flag = text2num(href_list["disabilities"])
pref.disabilities ^= disability_flag
else if(href_list["trait_add"])
var/list/available_disabilities = pref.disabilities ^ chargen_disabilities_list
var/new_trait = input(user, "Choose a disability:", "Character Preference") as null|anything in available_disabilities
if(new_trait && CanUseTopic(user))
pref.disabilities += new_trait
return TOPIC_REFRESH
else if(href_list["trait_remove"])
var/M = href_list["trait_remove"]
pref.disabilities -= M
return TOPIC_REFRESH
else if(href_list["toggle_clothing"])
+4 -2
View File
@@ -116,7 +116,7 @@ datum/preferences
var/exploit_record = ""
var/ccia_record = ""
var/list/ccia_actions = list()
var/disabilities = 0
var/list/disabilities = list()
var/nanotrasen_relation = "Neutral"
@@ -369,6 +369,8 @@ datum/preferences
// Destroy/cyborgize organs & setup body markings
character.sync_organ_prefs_to_mob(src)
character.sync_trait_prefs_to_mob(src)
character.underwear = underwear
character.undershirt = undershirt
@@ -535,7 +537,7 @@ datum/preferences
flavour_texts_robot = list()
ccia_actions = list()
disabilities = 0
disabilities = list()
nanotrasen_relation = "Neutral"
@@ -0,0 +1,57 @@
//Character trait system. Currently geared only for disabilities but a refactor to make it trait neutral would be trivial.
/datum/character_disabilities
var/name = "Enigma"
var/desc = "This trait was not meant to be seen by mortal minds."
/datum/character_disabilities/proc/apply_self(var/mob/living/carbon/human/H)
return
/datum/character_disabilities/nearsighted
name = "Nearsightedness"
desc = "Without prescription glasses your vision is impaired."
/datum/character_disabilities/nearsighted/apply_self(var/mob/living/carbon/human/H)
H.disabilities |= NEARSIGHTED
/datum/character_disabilities/nervous
name = "Nervousness"
desc = "You are prone to stuttering and bouts of anxiety."
/datum/character_disabilities/nervous/apply_self(var/mob/living/carbon/human/H)
H.disabilities |= NERVOUS
/datum/character_disabilities/deuteranomaly
name = "Deuteranopia"
desc = "You have difficulty perceiving green."
/datum/character_disabilities/deuteranomaly/apply_self(var/mob/living/carbon/human/H)
H.add_client_color(/datum/client_color/deuteranopia)
/datum/character_disabilities/protanopia
name = "Protanopia"
desc = "You have difficulty perceiving red."
/datum/character_disabilities/protanopia/apply_self(var/mob/living/carbon/human/H)
H.add_client_color(/datum/client_color/protanopia)
/datum/character_disabilities/tritanopia
name = "Tritanopia"
desc = "You have difficulty perceiving green and yellow."
/datum/character_disabilities/tritanopia/apply_self(var/mob/living/carbon/human/H)
H.add_client_color(/datum/client_color/tritanopia)
/datum/character_disabilities/mute
name = "Muteness"
desc = "You are unable to form coherent speech."
/datum/character_disabilities/mute/apply_self(var/mob/living/carbon/human/H)
H.sdisabilities |= MUTE
/datum/character_disabilities/deaf
name = "Deafness"
desc = "You are unable to percieve sound."
/datum/character_disabilities/deaf/apply_self(var/mob/living/carbon/human/H)
H.sdisabilities |= DEAF
@@ -135,6 +135,12 @@
LAZYINITLIST(O.temporary_markings)
O.temporary_markings[M] = attr
/mob/living/carbon/human/proc/sync_trait_prefs_to_mob(datum/preferences/prefs)
var/list/traits = prefs.disabilities
for(var/M in traits)
var/datum/character_disabilities/trait = chargen_disabilities_list[M]
trait.apply_self(src)
// Helper proc that grabs whatever organ this humantype uses to see.
// Usually eyes, but can be something else.
// If `no_synthetic` is TRUE, returns null for mobs that are mechanical, or for mechanical eyes.
@@ -41,6 +41,7 @@
var/can_repair = 0
var/health_prefix = ""
appearance_flags = NO_CLIENT_COLOR
/mob/living/simple_animal/construct/cultify()
@@ -11,6 +11,7 @@
slot_flags = SLOT_BELT
origin_tech = list(TECH_BLUESPACE = 4, TECH_MATERIAL = 4)
var/imprinted = "empty"
appearance_flags = NO_CLIENT_COLOR
//////////////////////////////Capturing////////////////////////////////////////////////////////
@@ -88,6 +89,7 @@
return
/obj/structure/constructshell/cult
appearance_flags = NO_CLIENT_COLOR
icon_state = "construct-cult"
desc = "This eerie contraption looks like it would come alive if supplied with a missing ingredient."
@@ -74,6 +74,7 @@
faction = "cult"
supernatural = 1
tameable = FALSE
appearance_flags = NO_CLIENT_COLOR
/mob/living/simple_animal/hostile/scarybat/cult/cultify()
return
@@ -32,6 +32,7 @@
minbodytemp = 0
supernatural = 1
appearance_flags = NO_CLIENT_COLOR
/mob/living/simple_animal/hostile/creature/cult/cultify()
return
@@ -55,6 +55,7 @@
/mob/living/simple_animal/hostile/faithless/cult
faction = "cult"
appearance_flags = NO_CLIENT_COLOR
/mob/living/simple_animal/hostile/faithless/cult/cultify()
return
@@ -28,6 +28,7 @@
faction = "cult"
status_flags = CANPUSH
hunger_enabled = 0
appearance_flags = NO_CLIENT_COLOR
/mob/living/simple_animal/shade/cultify()
return
+2
View File
@@ -50,3 +50,5 @@
//set macro to normal incase it was overriden (like cyborg currently does)
winset(src, null, "mainwindow.macro=macro hotkey_toggle.is-checked=false input.focus=true input.background-color=#D3B5B5")
MOB_STOP_THINKING(src)
update_client_color()
+3
View File
@@ -16,6 +16,9 @@
mind.handle_mob_deletion(src)
for(var/infection in viruses)
qdel(infection)
for(var/cc in client_colors)
qdel(cc)
client_colors = null
viruses.Cut()
//Added this to prevent nonliving mobs from ghostising
@@ -10,6 +10,7 @@
layer = 6
light_power = -100 //eats all light
unacidable = 1 //Don't comment this out.
appearance_flags = NO_CLIENT_COLOR
var/current_size = 1
var/allowed_size = 1
@@ -7,6 +7,7 @@
density = 0
opacity = 0
layer = FLY_LAYER
appearance_flags = NO_CLIENT_COLOR
simulated = 0
mouse_opacity = 0
@@ -132,6 +132,7 @@
icon_state = "m_shield_cult"
light_color = "#B40000"
light_range = 2
appearance_flags = NO_CLIENT_COLOR
/obj/effect/forcefield/cult/cultify()
return