diff --git a/code/__DEFINES/mobs.dm b/code/__DEFINES/mobs.dm index 8667cba2c2d..0b352ee2c12 100644 --- a/code/__DEFINES/mobs.dm +++ b/code/__DEFINES/mobs.dm @@ -374,17 +374,17 @@ //Badmin magic mirror #define MIRROR_BADMIN (1<<0) //Standard magic mirror (wizard) -#define MIRROR_MAGIC (1<<1) +#define MIRROR_MAGIC (1<<1) //Pride ruin mirror -#define MIRROR_PRIDE (1<<2) +#define MIRROR_PRIDE (1<<2) //Race swap wizard event -#define RACE_SWAP (1<<3) +#define RACE_SWAP (1<<3) //ERT spawn template (avoid races that don't function without correct gear) -#define ERT_SPAWN (1<<4) +#define ERT_SPAWN (1<<4) //xenobio black crossbreed #define SLIME_EXTRACT (1<<5) //Wabbacjack staff projectiles -#define WABBAJACK (1<<6) +#define WABBAJACK (1<<6) // Reasons a defibrilation might fail #define DEFIB_POSSIBLE (1<<0) diff --git a/code/game/objects/structures/mirror.dm b/code/game/objects/structures/mirror.dm index 648f7a5b9a9..22a1ca6eea6 100644 --- a/code/game/objects/structures/mirror.dm +++ b/code/game/objects/structures/mirror.dm @@ -19,36 +19,34 @@ MAPPING_DIRECTIONAL_HELPERS(/obj/structure/mirror, 28) /obj/structure/mirror/attack_hand(mob/user, list/modifiers) . = ..() if(.) - return + return TRUE if(broken || !Adjacent(user)) - return + return TRUE - if(ishuman(user)) - var/mob/living/carbon/human/H = user + if(!ishuman(user)) + return TRUE + var/mob/living/carbon/human/hairdresser = user - //see code/modules/mob/dead/new_player/preferences.dm at approx line 545 for comments! - //this is largely copypasted from there. - - //handle facial hair (if necessary) - if(H.gender != FEMALE) - var/new_style = input(user, "Select a facial hairstyle", "Grooming") as null|anything in GLOB.facial_hairstyles_list - if(!user.canUseTopic(src, BE_CLOSE, FALSE, NO_TK)) - return //no tele-grooming - if(new_style) - H.facial_hairstyle = new_style - else - H.facial_hairstyle = "Shaved" - - //handle normal hair - var/new_style = input(user, "Select a hairstyle", "Grooming") as null|anything in GLOB.hairstyles_list + //handle facial hair (if necessary) + if(hairdresser.gender != FEMALE) + var/new_style = input(user, "Select a facial hairstyle", "Grooming") as null|anything in GLOB.facial_hairstyles_list if(!user.canUseTopic(src, BE_CLOSE, FALSE, NO_TK)) - return //no tele-grooming - if(HAS_TRAIT(H, TRAIT_BALD)) - to_chat(H, span_notice("If only growing back hair were that easy for you...")) + return TRUE //no tele-grooming if(new_style) - H.hairstyle = new_style + hairdresser.facial_hairstyle = new_style + else + hairdresser.facial_hairstyle = "Shaved" - H.update_hair() + //handle normal hair + var/new_style = input(user, "Select a hairstyle", "Grooming") as null|anything in GLOB.hairstyles_list + if(!user.canUseTopic(src, BE_CLOSE, FALSE, NO_TK)) + return TRUE //no tele-grooming + if(HAS_TRAIT(hairdresser, TRAIT_BALD)) + to_chat(hairdresser, span_notice("If only growing back hair were that easy for you...")) + if(new_style) + hairdresser.hairstyle = new_style + + hairdresser.update_hair() /obj/structure/mirror/examine_status(mob/user) if(broken) @@ -62,7 +60,7 @@ MAPPING_DIRECTIONAL_HELPERS(/obj/structure/mirror, 28) . = ..() if(broken) // breaking a mirror truly gets you bad luck! to_chat(user, span_warning("A chill runs down your spine as [src] shatters...")) - user.AddComponent(/datum/component/omen, silent=TRUE) // we have our own message + user.AddComponent(/datum/component/omen, silent = TRUE) // we have our own message /obj/structure/mirror/bullet_act(obj/projectile/P) if(broken || !isliving(P.firer) || !P.damage) @@ -123,149 +121,169 @@ MAPPING_DIRECTIONAL_HELPERS(/obj/structure/mirror, 28) name = "magic mirror" desc = "Turn and face the strange... face." icon_state = "magic_mirror" - var/list/choosable_races = list() + + ///Flags this race must have to be selectable with this type of mirror. + var/race_flags = MIRROR_MAGIC + ///List of all Races that can be chosen, decided by its Initialize. + var/list/selectable_races = list() /obj/structure/mirror/magic/Initialize(mapload) . = ..() - if(!choosable_races.len) - for(var/datum/species/species_type as anything in subtypesof(/datum/species)) - if(initial(species_type.changesource_flags) & MIRROR_MAGIC) - choosable_races += initial(species_type.name) - choosable_races = sort_list(choosable_races) -/obj/structure/mirror/magic/lesser/Initialize(mapload) - choosable_races = get_selectable_species().Copy() - return ..() - -/obj/structure/mirror/magic/badmin/Initialize(mapload) + if(selectable_races.len) + return for(var/datum/species/species_type as anything in subtypesof(/datum/species)) - if(initial(species_type.changesource_flags) & MIRROR_BADMIN) - choosable_races += initial(species_type.name) - return ..() + if(initial(species_type.changesource_flags) & race_flags) + selectable_races[initial(species_type.name)] = species_type + selectable_races = sort_list(selectable_races) /obj/structure/mirror/magic/attack_hand(mob/user, list/modifiers) . = ..() if(.) - return + return TRUE if(!ishuman(user)) - return + return TRUE - var/mob/living/carbon/human/H = user + var/mob/living/carbon/human/amazed_human = user var/choice = input(user, "Something to change?", "Magical Grooming") as null|anything in list("name", "race", "gender", "hair", "eyes") if(!user.canUseTopic(src, BE_CLOSE, FALSE, NO_TK)) - return + return TRUE switch(choice) if("name") - var/newname = sanitize_name(stripped_input(H, "Who are we again?", "Name change", H.name, MAX_NAME_LEN), allow_numbers = TRUE) //It's magic so whatever. + var/newname = sanitize_name(stripped_input(amazed_human, "Who are we again?", "Name change", amazed_human.name, MAX_NAME_LEN), allow_numbers = TRUE) //It's magic so whatever. if(!newname) - return + return TRUE if(!user.canUseTopic(src, BE_CLOSE, FALSE, NO_TK)) - return - H.real_name = newname - H.name = newname - if(H.dna) - H.dna.real_name = newname - if(H.mind) - H.mind.name = newname + return TRUE + amazed_human.real_name = newname + amazed_human.name = newname + if(amazed_human.dna) + amazed_human.dna.real_name = newname + if(amazed_human.mind) + amazed_human.mind.name = newname if("race") - var/newrace - var/racechoice = input(H, "What are we again?", "Race change") as null|anything in choosable_races - newrace = GLOB.species_list[racechoice] - - if(!newrace) - return + var/racechoice = input(amazed_human, "What are we again?", "Race change") as null|anything in selectable_races + if(!racechoice || !selectable_races[racechoice]) + return TRUE if(!user.canUseTopic(src, BE_CLOSE, FALSE, NO_TK)) - return - H.set_species(newrace, icon_update=0) + return TRUE - if(H.dna.species.use_skintones) + var/datum/species/newrace = selectable_races[racechoice] + amazed_human.set_species(newrace, icon_update = FALSE) + + if(amazed_human.dna.species.use_skintones) var/new_s_tone = input(user, "Choose your skin tone:", "Race change") as null|anything in GLOB.skin_tones - if(!user.canUseTopic(src, BE_CLOSE, FALSE, NO_TK)) - return - if(new_s_tone) - H.skin_tone = new_s_tone - H.dna.update_ui_block(DNA_SKIN_TONE_BLOCK) + amazed_human.skin_tone = new_s_tone + amazed_human.dna.update_ui_block(DNA_SKIN_TONE_BLOCK) - if(MUTCOLORS in H.dna.species.species_traits) - var/new_mutantcolor = input(user, "Choose your skin color:", "Race change",H.dna.features["mcolor"]) as color|null + if(MUTCOLORS in amazed_human.dna.species.species_traits) + var/new_mutantcolor = input(user, "Choose your skin color:", "Race change", amazed_human.dna.features["mcolor"]) as color|null if(!user.canUseTopic(src, BE_CLOSE, FALSE, NO_TK)) - return + return TRUE if(new_mutantcolor) var/temp_hsv = RGBtoHSV(new_mutantcolor) if(ReadHSV(temp_hsv)[3] >= ReadHSV("#7F7F7F")[3]) // mutantcolors must be bright - H.dna.features["mcolor"] = sanitize_hexcolor(new_mutantcolor) - H.dna.update_uf_block(DNA_MUTANT_COLOR_BLOCK) + amazed_human.dna.features["mcolor"] = sanitize_hexcolor(new_mutantcolor) + amazed_human.dna.update_uf_block(DNA_MUTANT_COLOR_BLOCK) else - to_chat(H, span_notice("Invalid color. Your color is not bright enough.")) + to_chat(amazed_human, span_notice("Invalid color. Your color is not bright enough.")) + return TRUE - H.update_body() - H.update_hair() - H.update_body_parts() - H.update_mutations_overlay() // no hulk lizard + amazed_human.update_body() + amazed_human.update_hair() + amazed_human.update_body_parts() + amazed_human.update_mutations_overlay() // no hulk lizard if("gender") - if(!(H.gender in list("male", "female"))) //blame the patriarchy - return - if(H.gender == "male") - if(tgui_alert(H, "Become a Witch?", "Confirmation", list("Yes", "No")) == "Yes") + if(!(amazed_human.gender in list("male", "female"))) //blame the patriarchy + return TRUE + if(amazed_human.gender == "male") + if(tgui_alert(amazed_human, "Become a Witch?", "Confirmation", list("Yes", "No")) == "Yes") if(!user.canUseTopic(src, BE_CLOSE, FALSE, NO_TK)) - return - H.gender = FEMALE - H.body_type = FEMALE - to_chat(H, span_notice("Man, you feel like a woman!")) + return TRUE + amazed_human.gender = FEMALE + amazed_human.body_type = FEMALE + to_chat(amazed_human, span_notice("Man, you feel like a woman!")) else - return + return TRUE else - if(tgui_alert(H, "Become a Warlock?", "Confirmation", list("Yes", "No")) == "Yes") + if(tgui_alert(amazed_human, "Become a Warlock?", "Confirmation", list("Yes", "No")) == "Yes") if(!user.canUseTopic(src, BE_CLOSE, FALSE, NO_TK)) - return - H.gender = MALE - H.body_type = MALE - to_chat(H, span_notice("Whoa man, you feel like a man!")) + return TRUE + amazed_human.gender = MALE + amazed_human.body_type = MALE + to_chat(amazed_human, span_notice("Whoa man, you feel like a man!")) else - return - H.dna.update_ui_block(DNA_GENDER_BLOCK) - H.update_body() - H.update_mutations_overlay() //(hulk male/female) + return TRUE + amazed_human.dna.update_ui_block(DNA_GENDER_BLOCK) + amazed_human.update_body() + amazed_human.update_mutations_overlay() //(hulk male/female) if("hair") - var/hairchoice = tgui_alert(H, "Hairstyle or hair color?", "Change Hair", list("Style", "Color")) + var/hairchoice = tgui_alert(amazed_human, "Hairstyle or hair color?", "Change Hair", list("Style", "Color")) if(!user.canUseTopic(src, BE_CLOSE, FALSE, NO_TK)) - return + return TRUE if(hairchoice == "Style") //So you just want to use a mirror then? - ..() + return ..() else - var/new_hair_color = input(H, "Choose your hair color", "Hair Color",H.hair_color) as color|null + var/new_hair_color = input(amazed_human, "Choose your hair color", "Hair Color",amazed_human.hair_color) as color|null if(!user.canUseTopic(src, BE_CLOSE, FALSE, NO_TK)) - return + return TRUE if(new_hair_color) - H.hair_color = sanitize_hexcolor(new_hair_color) - H.dna.update_ui_block(DNA_HAIR_COLOR_BLOCK) - if(H.gender == "male") - var/new_face_color = input(H, "Choose your facial hair color", "Hair Color",H.facial_hair_color) as color|null + amazed_human.hair_color = sanitize_hexcolor(new_hair_color) + amazed_human.dna.update_ui_block(DNA_HAIR_COLOR_BLOCK) + if(amazed_human.gender == "male") + var/new_face_color = input(amazed_human, "Choose your facial hair color", "Hair Color", amazed_human.facial_hair_color) as color|null if(new_face_color) - H.facial_hair_color = sanitize_hexcolor(new_face_color) - H.dna.update_ui_block(DNA_FACIAL_HAIR_COLOR_BLOCK) - H.update_hair() + amazed_human.facial_hair_color = sanitize_hexcolor(new_face_color) + amazed_human.dna.update_ui_block(DNA_FACIAL_HAIR_COLOR_BLOCK) + amazed_human.update_hair() if(BODY_ZONE_PRECISE_EYES) - var/new_eye_color = input(H, "Choose your eye color", "Eye Color",H.eye_color) as color|null + var/new_eye_color = input(amazed_human, "Choose your eye color", "Eye Color", amazed_human.eye_color) as color|null if(!user.canUseTopic(src, BE_CLOSE, FALSE, NO_TK)) - return + return TRUE if(new_eye_color) - H.eye_color = sanitize_hexcolor(new_eye_color) - H.dna.update_ui_block(DNA_EYE_COLOR_BLOCK) - H.update_body() - if(choice) - curse(user) + amazed_human.eye_color = sanitize_hexcolor(new_eye_color) + amazed_human.dna.update_ui_block(DNA_EYE_COLOR_BLOCK) + amazed_human.update_body() -/obj/structure/mirror/magic/proc/curse(mob/living/user) - return +/obj/structure/mirror/magic/lesser/Initialize(mapload) + // Roundstart species don't have a flag, so it has to be set on Initialize. + selectable_races = get_selectable_species().Copy() + return ..() + +/obj/structure/mirror/magic/badmin + race_flags = MIRROR_BADMIN + +/obj/structure/mirror/magic/pride + name = "pride's mirror" + desc = "Pride cometh before the..." + race_flags = MIRROR_PRIDE + +/obj/structure/mirror/magic/pride/attack_hand(mob/user, list/modifiers) + . = ..() + if(.) + return TRUE + + user.visible_message(span_danger("The ground splits beneath [user] as [user.p_their()] hand leaves the mirror!"), \ + span_notice("Perfect. Much better! Now nobody will be able to resist yo-")) + + var/turf/user_turf = get_turf(user) + var/list/levels = SSmapping.levels_by_trait(ZTRAIT_SPACE_RUINS) + var/turf/dest + if(levels.len) + dest = locate(user_turf.x, user_turf.y, pick(levels)) + + user_turf.ChangeTurf(/turf/open/chasm, flags = CHANGETURF_INHERIT_AIR) + var/turf/open/chasm/new_chasm = user_turf + new_chasm.set_target(dest) + new_chasm.drop(user) diff --git a/code/modules/ruins/objects_and_mobs/sin_ruins.dm b/code/modules/ruins/objects_and_mobs/sin_ruins.dm index 3bbe34e0cd0..7c87d74c1b4 100644 --- a/code/modules/ruins/objects_and_mobs/sin_ruins.dm +++ b/code/modules/ruins/objects_and_mobs/sin_ruins.dm @@ -106,32 +106,6 @@ if(istype(mover, /mob/living/simple_animal/hostile/morph)) return TRUE -/obj/structure/mirror/magic/pride //Pride's mirror: Used in the Pride ruin. - name = "pride's mirror" - desc = "Pride cometh before the..." - icon_state = "magic_mirror" - -/obj/structure/mirror/magic/pride/New() - for(var/datum/species/species_type as anything in subtypesof(/datum/species)) - if(initial(species_type.changesource_flags) & MIRROR_PRIDE) - choosable_races += initial(species_type.name) - ..() - -/obj/structure/mirror/magic/pride/curse(mob/user) - user.visible_message(span_danger("The ground splits beneath [user] as [user.p_their()] hand leaves the mirror!"), \ - span_notice("Perfect. Much better! Now nobody will be able to resist yo-")) - - var/turf/T = get_turf(user) - var/list/levels = SSmapping.levels_by_trait(ZTRAIT_SPACE_RUINS) - var/turf/dest - if (levels.len) - dest = locate(T.x, T.y, pick(levels)) - - T.ChangeTurf(/turf/open/chasm, flags = CHANGETURF_INHERIT_AIR) - var/turf/open/chasm/C = T - C.set_target(dest) - C.drop(user) - //can't be bothered to do sloth right now, will make later /obj/item/knife/envy //Envy's knife: Found in the Envy ruin. Attackers take on the appearance of whoever they strike.