Merge branch 'master' into Yote
This commit is contained in:
@@ -231,7 +231,7 @@ GLOBAL_VAR_INIT(observer_default_invisibility, INVISIBILITY_OBSERVER)
|
||||
var/r_val
|
||||
var/b_val
|
||||
var/g_val
|
||||
var/color_format = lentext(input_color)
|
||||
var/color_format = length(input_color)
|
||||
if(color_format == 3)
|
||||
r_val = hex2num(copytext(input_color, 1, 2))*16
|
||||
g_val = hex2num(copytext(input_color, 2, 3))*16
|
||||
@@ -285,10 +285,10 @@ This is the proc mobs get to turn into a ghost. Forked from ghostize due to comp
|
||||
|
||||
// CITADEL EDIT
|
||||
if(istype(loc, /obj/machinery/cryopod))
|
||||
var/response = alert(src, "Are you -sure- you want to ghost?\n(You are alive. If you ghost whilst still alive you won't be able to re-enter this round! You can't change your mind so choose wisely!!)","Are you sure you want to ghost?","Ghost","Stay in body")
|
||||
if(response != "Ghost")//darn copypaste
|
||||
return
|
||||
var/obj/machinery/cryopod/C = loc
|
||||
var/response = alert(src, "Are you -sure- you want to ghost?\n(You are alive. If you ghost whilst still alive you won't be able to re-enter this round! You can't change your mind so choose wisely!!)","Are you sure you want to ghost?","Ghost","Stay in body")
|
||||
if(response != "Ghost" || QDELETED(C) || QDELETED(src) || loc != C)
|
||||
return
|
||||
C.despawn_occupant()
|
||||
return
|
||||
// END EDIT
|
||||
|
||||
@@ -152,8 +152,7 @@
|
||||
newcolor = BLOOD_COLOR_XENO
|
||||
add_atom_colour(newcolor, TEMPORARY_COLOUR_PRIORITY)
|
||||
// but only for a few seconds
|
||||
spawn(30)
|
||||
remove_atom_colour(TEMPORARY_COLOUR_PRIORITY, newcolor)
|
||||
addtimer(CALLBACK(src, /atom/.proc/remove_atom_colour, TEMPORARY_COLOUR_PRIORITY, newcolor), 6 SECONDS)
|
||||
|
||||
/mob/living/proc/phasein(obj/effect/decal/cleanable/B)
|
||||
if(src.notransform)
|
||||
|
||||
@@ -95,8 +95,14 @@ Doesn't work on other aliens/AI.*/
|
||||
var/mob/living/M = input("Select who to whisper to:","Whisper to?",null) as null|mob in options
|
||||
if(!M)
|
||||
return 0
|
||||
if(M.anti_magic_check(FALSE, FALSE, TRUE, 0))
|
||||
to_chat(user, "<span class='noticealien'>As you try to communicate with [M], you're suddenly stopped by a vision of a massive tinfoil wall that streches beyond visible range. It seems you've been foiled.</span>")
|
||||
return FALSE
|
||||
var/msg = sanitize(input("Message:", "Alien Whisper") as text|null)
|
||||
if(msg)
|
||||
if(M.anti_magic_check(FALSE, FALSE, TRUE, 0))
|
||||
to_chat(user, "<span class='notice'>As you try to communicate with [M], you're suddenly stopped by a vision of a massive tinfoil wall that streches beyond visible range. It seems you've been foiled.</span>")
|
||||
return
|
||||
log_directed_talk(user, M, msg, LOG_SAY, tag="alien whisper")
|
||||
to_chat(M, "<span class='noticealien'>You hear a strange, alien voice in your head...</span>[msg]")
|
||||
to_chat(user, "<span class='noticealien'>You said: \"[msg]\" to [M]</span>")
|
||||
|
||||
@@ -585,7 +585,7 @@
|
||||
if(!isnull(E.lighting_alpha))
|
||||
lighting_alpha = E.lighting_alpha
|
||||
|
||||
if(client.eye != src)
|
||||
if(client.eye && client.eye != src)
|
||||
var/atom/A = client.eye
|
||||
if(A.update_remote_sight(src)) //returns 1 if we override all other sight updates.
|
||||
return
|
||||
|
||||
@@ -36,7 +36,7 @@
|
||||
|
||||
/mob/living/carbon/Move(NewLoc, direct)
|
||||
. = ..()
|
||||
if(. && mob_has_gravity()) //floating is easy
|
||||
if(. && (movement_type & FLOATING)) //floating is easy
|
||||
if(HAS_TRAIT(src, TRAIT_NOHUNGER))
|
||||
nutrition = NUTRITION_LEVEL_FED - 1 //just less than feeling vigorous
|
||||
else if(nutrition && stat != DEAD)
|
||||
|
||||
@@ -488,7 +488,7 @@
|
||||
var/counter = 1
|
||||
while(R.fields[text("com_[]", counter)])
|
||||
counter++
|
||||
R.fields[text("com_[]", counter)] = text("Made by [] on [] [], []<BR>[]", allowed_access, STATION_TIME_TIMESTAMP("hh:mm:ss"), time2text(world.realtime, "MMM DD"), GLOB.year_integer+540, t1)
|
||||
R.fields[text("com_[]", counter)] = text("Made by [] on [] [], []<BR>[]", allowed_access, STATION_TIME_TIMESTAMP("hh:mm:ss"), time2text(world.realtime, "MMM DD"), GLOB.year_integer, t1)
|
||||
to_chat(usr, "<span class='notice'>Successfully added comment.</span>")
|
||||
return
|
||||
to_chat(usr, "<span class='warning'>Unable to locate a data core entry for this person.</span>")
|
||||
@@ -946,7 +946,7 @@
|
||||
return FALSE
|
||||
|
||||
/mob/living/carbon/human/proc/clear_shove_slowdown()
|
||||
remove_movespeed_modifier(SHOVE_SLOWDOWN_ID)
|
||||
remove_movespeed_modifier(MOVESPEED_ID_SHOVE)
|
||||
var/active_item = get_active_held_item()
|
||||
if(is_type_in_typecache(active_item, GLOB.shove_disarming_types))
|
||||
visible_message("<span class='warning'>[src.name] regains their grip on \the [active_item]!</span>", "<span class='warning'>You regain your grip on \the [active_item]</span>", null, COMBAT_MESSAGE_RANGE)
|
||||
|
||||
@@ -778,7 +778,7 @@
|
||||
broken_plural = TRUE
|
||||
else
|
||||
var/holder = broken[1] //our one and only element
|
||||
if(holder[lentext(holder)] == "s")
|
||||
if(holder[length(holder)] == "s")
|
||||
broken_plural = TRUE
|
||||
//Put the items in that list into a string of text
|
||||
for(var/B in broken)
|
||||
@@ -790,7 +790,7 @@
|
||||
damaged_plural = TRUE
|
||||
else
|
||||
var/holder = damaged[1]
|
||||
if(holder[lentext(holder)] == "s")
|
||||
if(holder[length(holder)] == "s")
|
||||
damaged_plural = TRUE
|
||||
for(var/D in damaged)
|
||||
damaged_message += D
|
||||
|
||||
@@ -79,7 +79,8 @@
|
||||
|
||||
//This is an UNSAFE proc. Use mob_can_equip() before calling this one! Or rather use equip_to_slot_if_possible() or advanced_equip_to_slot_if_possible()
|
||||
/mob/living/carbon/human/equip_to_slot(obj/item/I, slot)
|
||||
if(!..()) //a check failed or the item has already found its slot
|
||||
. = ..()
|
||||
if(!.) //a check failed or the item has already found its slot
|
||||
return
|
||||
|
||||
var/not_handled = FALSE //Added in case we make this type path deeper one day
|
||||
@@ -136,6 +137,7 @@
|
||||
update_inv_s_store()
|
||||
else
|
||||
to_chat(src, "<span class='danger'>You are trying to equip this item to an unsupported inventory slot. Report this to a coder!</span>")
|
||||
not_handled = TRUE
|
||||
|
||||
//Item is handled and in slot, valid to call callback, for this proc should always be true
|
||||
if(!not_handled)
|
||||
|
||||
@@ -18,7 +18,7 @@
|
||||
#define THERMAL_PROTECTION_HAND_LEFT 0.025
|
||||
#define THERMAL_PROTECTION_HAND_RIGHT 0.025
|
||||
|
||||
/mob/living/carbon/human/Life()
|
||||
/mob/living/carbon/human/Life(seconds, times_fired)
|
||||
set invisibility = 0
|
||||
if (notransform)
|
||||
return
|
||||
@@ -41,7 +41,7 @@
|
||||
|
||||
if(stat != DEAD)
|
||||
//process your dick energy
|
||||
handle_arousal()
|
||||
handle_arousal(times_fired)
|
||||
|
||||
//Update our name based on whether our face is obscured/disfigured
|
||||
name = get_visible_name()
|
||||
|
||||
@@ -21,8 +21,6 @@
|
||||
var/bleed_mod = 1 // % bleeding modifier
|
||||
var/datum/armor/armor // internal armor datum
|
||||
|
||||
var/speed_mod = 0 //tick modifier for each step. Positive is slower, negative is faster.
|
||||
|
||||
var/hunger_mod = 1 //% of hunger rate taken per tick.
|
||||
|
||||
var/do_after_speed = 1 //Speed mod for do_after. Lower is better. If temporarily adjusting, please only modify using *= and /=, so you don't interrupt other calculations.
|
||||
|
||||
@@ -332,6 +332,8 @@ GLOBAL_LIST_EMPTY(roundstart_race_names)
|
||||
if("meat_type" in default_features) //I can't believe it's come to the meat
|
||||
H.type_of_meat = GLOB.meat_types[H.dna.features["meat_type"]]
|
||||
|
||||
C.add_movespeed_modifier(MOVESPEED_ID_SPECIES, TRUE, 100, override=TRUE, multiplicative_slowdown=speedmod, movetypes=(~FLYING))
|
||||
|
||||
SEND_SIGNAL(C, COMSIG_SPECIES_GAIN, src, old_species)
|
||||
|
||||
|
||||
@@ -348,6 +350,8 @@ GLOBAL_LIST_EMPTY(roundstart_race_names)
|
||||
for(var/X in inherent_traits)
|
||||
REMOVE_TRAIT(C, X, SPECIES_TRAIT)
|
||||
|
||||
C.remove_movespeed_modifier(MOVESPEED_ID_SPECIES)
|
||||
|
||||
if("meat_type" in default_features)
|
||||
C.type_of_meat = GLOB.meat_types[C.dna.features["meat_type"]]
|
||||
else
|
||||
@@ -541,7 +545,7 @@ GLOBAL_LIST_EMPTY(roundstart_race_names)
|
||||
if(H.hidden_underwear)
|
||||
H.underwear = "Nude"
|
||||
else
|
||||
H.saved_underwear = H.underwear
|
||||
H.underwear = H.saved_underwear
|
||||
var/datum/sprite_accessory/underwear/bottom/B = GLOB.underwear_list[H.underwear]
|
||||
if(B)
|
||||
var/mutable_appearance/MA = mutable_appearance(B.icon, B.icon_state, -BODY_LAYER)
|
||||
@@ -553,7 +557,7 @@ GLOBAL_LIST_EMPTY(roundstart_race_names)
|
||||
if(H.hidden_undershirt)
|
||||
H.undershirt = "Nude"
|
||||
else
|
||||
H.saved_undershirt = H.undershirt
|
||||
H.undershirt = H.saved_undershirt
|
||||
var/datum/sprite_accessory/underwear/top/T = GLOB.undershirt_list[H.undershirt]
|
||||
if(T)
|
||||
var/mutable_appearance/MA
|
||||
@@ -569,7 +573,7 @@ GLOBAL_LIST_EMPTY(roundstart_race_names)
|
||||
if(H.hidden_socks)
|
||||
H.socks = "Nude"
|
||||
else
|
||||
H.saved_socks = H.socks
|
||||
H.socks = H.saved_socks
|
||||
var/datum/sprite_accessory/underwear/socks/S = GLOB.socks_list[H.socks]
|
||||
if(S)
|
||||
var/digilegs = (DIGITIGRADE in species_traits) ? "_d" : ""
|
||||
@@ -1389,39 +1393,16 @@ GLOBAL_LIST_EMPTY(roundstart_race_names)
|
||||
/datum/species/proc/movement_delay(mob/living/carbon/human/H)
|
||||
. = 0 //We start at 0.
|
||||
var/flight = 0 //Check for flight and flying items
|
||||
var/ignoreslow = 0
|
||||
var/gravity = 0
|
||||
if(H.movement_type & FLYING)
|
||||
flight = 1
|
||||
|
||||
gravity = H.has_gravity()
|
||||
|
||||
if(gravity && !flight) //Check for chemicals and innate speedups and slowdowns if we're on the ground
|
||||
if(HAS_TRAIT(H, TRAIT_GOTTAGOFAST))
|
||||
. -= 1
|
||||
if(HAS_TRAIT(H, TRAIT_GOTTAGOREALLYFAST))
|
||||
. -= 2
|
||||
. += speedmod
|
||||
. += H.physiology.speed_mod
|
||||
|
||||
if (H.m_intent == MOVE_INTENT_WALK && HAS_TRAIT(H, TRAIT_SPEEDY_STEP))
|
||||
. -= 1.5
|
||||
|
||||
if(HAS_TRAIT(H, TRAIT_IGNORESLOWDOWN))
|
||||
ignoreslow = 1
|
||||
|
||||
if(!gravity)
|
||||
var/obj/item/tank/jetpack/J = H.back
|
||||
var/obj/item/clothing/suit/space/hardsuit/C = H.wear_suit
|
||||
var/obj/item/organ/cyberimp/chest/thrusters/T = H.getorganslot(ORGAN_SLOT_THRUSTERS)
|
||||
if(!istype(J) && istype(C))
|
||||
J = C.jetpack
|
||||
if(istype(J) && J.full_speed && J.allow_thrust(0.01, H)) //Prevents stacking
|
||||
. -= 0.4
|
||||
else if(istype(T) && T.allow_thrust(0.01, H))
|
||||
. -= 0.4
|
||||
|
||||
if(!ignoreslow && gravity)
|
||||
if(!HAS_TRAIT(H, TRAIT_IGNORESLOWDOWN) && gravity)
|
||||
if(H.wear_suit)
|
||||
. += H.wear_suit.slowdown
|
||||
if(H.shoes)
|
||||
@@ -1448,16 +1429,6 @@ GLOBAL_LIST_EMPTY(roundstart_race_names)
|
||||
var/grav_force = min(gravity - STANDARD_GRAVITY,3)
|
||||
. += 1 + grav_force
|
||||
|
||||
var/datum/component/mood/mood = H.GetComponent(/datum/component/mood)
|
||||
if(mood && !flight) //How can depression slow you down if you can just fly away from your problems?
|
||||
switch(mood.sanity)
|
||||
if(SANITY_INSANE to SANITY_CRAZY)
|
||||
. += 1.5
|
||||
if(SANITY_CRAZY to SANITY_UNSTABLE)
|
||||
. += 1
|
||||
if(SANITY_UNSTABLE to SANITY_DISTURBED)
|
||||
. += 0.5
|
||||
|
||||
if(HAS_TRAIT(H, TRAIT_FAT))
|
||||
. += (1.5 - flight)
|
||||
if(H.bodytemperature < BODYTEMP_COLD_DAMAGE_LIMIT && !HAS_TRAIT(H, TRAIT_RESISTCOLD))
|
||||
@@ -1784,7 +1755,7 @@ GLOBAL_LIST_EMPTY(roundstart_race_names)
|
||||
|
||||
switch(hit_area)
|
||||
if(BODY_ZONE_HEAD)
|
||||
if(!I.is_sharp() && armor_block < 50)
|
||||
if(!I.get_sharpness() && armor_block < 50)
|
||||
if(prob(I.force))
|
||||
H.adjustOrganLoss(ORGAN_SLOT_BRAIN, 20)
|
||||
if(H.stat == CONSCIOUS)
|
||||
@@ -1817,7 +1788,7 @@ GLOBAL_LIST_EMPTY(roundstart_race_names)
|
||||
H.update_inv_glasses()
|
||||
|
||||
if(BODY_ZONE_CHEST)
|
||||
if(H.stat == CONSCIOUS && !I.is_sharp() && armor_block < 50)
|
||||
if(H.stat == CONSCIOUS && !I.get_sharpness() && armor_block < 50)
|
||||
if(prob(I.force))
|
||||
H.visible_message("<span class='danger'>[H] has been knocked down!</span>", \
|
||||
"<span class='userdanger'>[H] has been knocked down!</span>")
|
||||
@@ -1940,8 +1911,8 @@ GLOBAL_LIST_EMPTY(roundstart_race_names)
|
||||
var/knocked_item = FALSE
|
||||
if(!is_type_in_typecache(target_held_item, GLOB.shove_disarming_types))
|
||||
target_held_item = null
|
||||
if(!target.has_movespeed_modifier(SHOVE_SLOWDOWN_ID))
|
||||
target.add_movespeed_modifier(SHOVE_SLOWDOWN_ID, multiplicative_slowdown = SHOVE_SLOWDOWN_STRENGTH)
|
||||
if(!target.has_movespeed_modifier(MOVESPEED_ID_SHOVE))
|
||||
target.add_movespeed_modifier(MOVESPEED_ID_SHOVE, multiplicative_slowdown = SHOVE_SLOWDOWN_STRENGTH)
|
||||
if(target_held_item)
|
||||
target.visible_message("<span class='danger'>[target.name]'s grip on \the [target_held_item] loosens!</span>",
|
||||
"<span class='danger'>Your grip on \the [target_held_item] loosens!</span>", null, COMBAT_MESSAGE_RANGE)
|
||||
|
||||
@@ -29,7 +29,7 @@
|
||||
if(fly)
|
||||
fly.Remove(H)
|
||||
if(H.movement_type & FLYING)
|
||||
H.movement_type &= ~FLYING
|
||||
H.setMovetype(H.movement_type & ~FLYING)
|
||||
ToggleFlight(H,0)
|
||||
if(H.dna && H.dna.species && (H.dna.features["wings"] == "Angel"))
|
||||
if("wings" in H.dna.species.mutant_bodyparts)
|
||||
@@ -132,14 +132,14 @@
|
||||
if(flight && CanFly(H))
|
||||
stunmod = 2
|
||||
speedmod = -0.35
|
||||
H.movement_type |= FLYING
|
||||
H.setMovetype(H.movement_type | FLYING)
|
||||
override_float = TRUE
|
||||
H.pass_flags |= PASSTABLE
|
||||
H.OpenWings()
|
||||
else
|
||||
stunmod = 1
|
||||
speedmod = 0
|
||||
H.movement_type &= ~FLYING
|
||||
H.setMovetype(H.movement_type & ~FLYING)
|
||||
override_float = FALSE
|
||||
H.pass_flags &= ~PASSTABLE
|
||||
H.CloseWings()
|
||||
@@ -796,7 +796,7 @@
|
||||
if(resistance_flags & ON_FIRE)
|
||||
return
|
||||
|
||||
if(P.is_hot())
|
||||
if(P.get_temperature())
|
||||
visible_message("<span class='danger'>[src] bursts into flames!</span>")
|
||||
fire_act()
|
||||
|
||||
|
||||
@@ -472,37 +472,25 @@
|
||||
H.hair_style = new_style
|
||||
H.update_hair()
|
||||
else if (select_alteration == "Genitals")
|
||||
var/list/organs = list()
|
||||
var/operation = input("Select organ operation.", "Organ Manipulation", "cancel") in list("add sexual organ", "remove sexual organ", "cancel")
|
||||
switch(operation)
|
||||
if("add sexual organ")
|
||||
var/new_organ = input("Select sexual organ:", "Organ Manipulation") in list("Penis", "Testicles", "Breasts", "Vagina", "Womb", "Cancel")
|
||||
if(new_organ == "Penis")
|
||||
H.give_penis()
|
||||
else if(new_organ == "Testicles")
|
||||
H.give_balls()
|
||||
else if(new_organ == "Breasts")
|
||||
H.give_breasts()
|
||||
else if(new_organ == "Vagina")
|
||||
H.give_vagina()
|
||||
else if(new_organ == "Womb")
|
||||
H.give_womb()
|
||||
else
|
||||
var/new_organ = input("Select sexual organ:", "Organ Manipulation") as null|anything in GLOB.genitals_list
|
||||
if(!new_organ)
|
||||
return
|
||||
H.give_genital(GLOB.genitals_list[new_organ])
|
||||
|
||||
if("remove sexual organ")
|
||||
var/list/organs = list()
|
||||
for(var/obj/item/organ/genital/X in H.internal_organs)
|
||||
var/obj/item/organ/I = X
|
||||
organs["[I.name] ([I.type])"] = I
|
||||
var/obj/item/organ = input("Select sexual organ:", "Organ Manipulation", null) in organs
|
||||
organ = organs[organ]
|
||||
if(!organ)
|
||||
var/obj/item/O = input("Select sexual organ:", "Organ Manipulation", null) as null|anything in organs
|
||||
var/obj/item/organ/genital/G = organs[O]
|
||||
if(!G)
|
||||
return
|
||||
var/obj/item/organ/genital/O
|
||||
if(isorgan(organ))
|
||||
O = organ
|
||||
O.Remove(H)
|
||||
organ.forceMove(get_turf(H))
|
||||
qdel(organ)
|
||||
G.forceMove(get_turf(H))
|
||||
qdel(G)
|
||||
H.update_genitals()
|
||||
|
||||
else if (select_alteration == "Ears")
|
||||
@@ -592,8 +580,8 @@
|
||||
if(new_shape)
|
||||
H.dna.features["cock_shape"] = new_shape
|
||||
H.update_genitals()
|
||||
H.give_balls()
|
||||
H.give_penis()
|
||||
H.give_genital(/obj/item/organ/genital/testicles)
|
||||
H.give_genital(/obj/item/organ/genital/penis)
|
||||
H.apply_overlay()
|
||||
|
||||
|
||||
@@ -605,8 +593,8 @@
|
||||
if(new_shape)
|
||||
H.dna.features["vag_shape"] = new_shape
|
||||
H.update_genitals()
|
||||
H.give_womb()
|
||||
H.give_vagina()
|
||||
H.give_genital(/obj/item/organ/genital/womb)
|
||||
H.give_genital(/obj/item/organ/genital/vagina)
|
||||
H.apply_overlay()
|
||||
|
||||
else if (select_alteration == "Penis Length")
|
||||
@@ -618,8 +606,8 @@
|
||||
H.dna.features["cock_length"] = max(min( round(text2num(new_length)), COCK_SIZE_MAX),COCK_SIZE_MIN)
|
||||
H.update_genitals()
|
||||
H.apply_overlay()
|
||||
H.give_balls()
|
||||
H.give_penis()
|
||||
H.give_genital(/obj/item/organ/genital/testicles)
|
||||
H.give_genital(/obj/item/organ/genital/penis)
|
||||
|
||||
else if (select_alteration == "Breast Size")
|
||||
for(var/obj/item/organ/genital/breasts/X in H.internal_organs)
|
||||
@@ -630,7 +618,7 @@
|
||||
H.dna.features["breasts_size"] = new_size
|
||||
H.update_genitals()
|
||||
H.apply_overlay()
|
||||
H.give_breasts()
|
||||
H.give_genital(/obj/item/organ/genital/breasts)
|
||||
|
||||
else if (select_alteration == "Breast Shape")
|
||||
for(var/obj/item/organ/genital/breasts/X in H.internal_organs)
|
||||
@@ -641,7 +629,7 @@
|
||||
H.dna.features["breasts_shape"] = new_shape
|
||||
H.update_genitals()
|
||||
H.apply_overlay()
|
||||
H.give_breasts()
|
||||
H.give_genital(/obj/item/organ/genital/breasts)
|
||||
|
||||
else
|
||||
return
|
||||
@@ -856,6 +844,8 @@
|
||||
return FALSE
|
||||
if(HAS_TRAIT(M, TRAIT_MINDSHIELD)) //mindshield implant, no dice
|
||||
return FALSE
|
||||
if(M.anti_magic_check(FALSE, FALSE, TRUE, 0))
|
||||
return FALSE
|
||||
if(M in linked_mobs)
|
||||
return FALSE
|
||||
linked_mobs.Add(M)
|
||||
@@ -941,9 +931,14 @@
|
||||
var/mob/living/M = input("Select who to send your message to:","Send thought to?",null) as null|mob in options
|
||||
if(!M)
|
||||
return
|
||||
|
||||
if(M.anti_magic_check(FALSE, FALSE, TRUE, 0))
|
||||
to_chat(H, "<span class='notice'>As you try to communicate with [M], you're suddenly stopped by a vision of a massive tinfoil wall that streches beyond visible range. It seems you've been foiled.</span>")
|
||||
return
|
||||
var/msg = sanitize(input("Message:", "Telepathy") as text|null)
|
||||
if(msg)
|
||||
if(M.anti_magic_check(FALSE, FALSE, TRUE, 0))
|
||||
to_chat(H, "<span class='notice'>As you try to communicate with [M], you're suddenly stopped by a vision of a massive tinfoil wall that streches beyond visible range. It seems you've been foiled.</span>")
|
||||
return
|
||||
log_directed_talk(H, M, msg, LOG_SAY, "slime telepathy")
|
||||
to_chat(M, "<span class='notice'>You hear an alien voice in your head... </span><font color=#008CA2>[msg]</font>")
|
||||
to_chat(H, "<span class='notice'>You telepathically said: \"[msg]\" to [M]</span>")
|
||||
|
||||
@@ -45,14 +45,14 @@
|
||||
C.adjustOxyLoss(-4)
|
||||
C.adjustCloneLoss(-4)
|
||||
return
|
||||
C.blood_volume -= 0.75
|
||||
C.blood_volume -= 0.75 //Will take roughly 19.5 minutes to die from standard blood volume, roughly 83 minutes to die from max blood volume.
|
||||
if(C.blood_volume <= (BLOOD_VOLUME_SURVIVE*C.blood_ratio))
|
||||
to_chat(C, "<span class='danger'>You ran out of blood!</span>")
|
||||
C.dust()
|
||||
var/area/A = get_area(C)
|
||||
if(istype(A, /area/chapel))
|
||||
to_chat(C, "<span class='danger'>You don't belong here!</span>")
|
||||
C.adjustFireLoss(20)
|
||||
C.adjustFireLoss(5)
|
||||
C.adjust_fire_stacks(6)
|
||||
C.IgniteMob()
|
||||
|
||||
@@ -88,7 +88,7 @@
|
||||
to_chat(H, "<span class='notice'>[victim] doesn't have blood!</span>")
|
||||
return
|
||||
V.drain_cooldown = world.time + 30
|
||||
if(victim.anti_magic_check(FALSE, TRUE))
|
||||
if(victim.anti_magic_check(FALSE, TRUE, FALSE, 0))
|
||||
to_chat(victim, "<span class='warning'>[H] tries to bite you, but stops before touching you!</span>")
|
||||
to_chat(H, "<span class='warning'>[victim] is blessed! You stop just in time to avoid catching fire.</span>")
|
||||
return
|
||||
@@ -141,7 +141,7 @@
|
||||
H = new(shape,src,caster)
|
||||
if(istype(H, /mob/living/simple_animal))
|
||||
var/mob/living/simple_animal/SA = H
|
||||
if(ventcrawl_nude_only && length(caster.get_equipped_items(include_pockets = TRUE)))
|
||||
if((caster.blood_volume >= (BLOOD_VOLUME_BAD*caster.blood_ratio)) || (ventcrawl_nude_only && length(caster.get_equipped_items(include_pockets = TRUE))))
|
||||
SA.ventcrawler = FALSE
|
||||
if(transfer_name)
|
||||
H.name = caster.name
|
||||
|
||||
@@ -66,7 +66,7 @@
|
||||
playsound(C, pick(spooks), 50, TRUE, 10)
|
||||
|
||||
//Congrats you somehow died so hard you stopped being a zombie
|
||||
/datum/species/zombie/infectious/spec_death(mob/living/carbon/C)
|
||||
/datum/species/zombie/infectious/spec_death(gibbed, mob/living/carbon/C)
|
||||
. = ..()
|
||||
var/obj/item/organ/zombie_infection/infection
|
||||
infection = C.getorganslot(ORGAN_SLOT_ZOMBIE)
|
||||
|
||||
@@ -98,7 +98,7 @@
|
||||
var/datum/gas_mixture/breath
|
||||
|
||||
if(!getorganslot(ORGAN_SLOT_BREATHING_TUBE))
|
||||
if(health <= HEALTH_THRESHOLD_FULLCRIT || (pulledby && pulledby.grab_state >= GRAB_KILL) || lungs.organ_flags & ORGAN_FAILING)
|
||||
if(health <= HEALTH_THRESHOLD_FULLCRIT || (pulledby && pulledby.grab_state >= GRAB_KILL) || !lungs || lungs.organ_flags & ORGAN_FAILING)
|
||||
losebreath++ //You can't breath at all when in critical or when being choked, so you're going to miss a breath
|
||||
|
||||
else if(health <= crit_threshold)
|
||||
|
||||
@@ -23,7 +23,7 @@
|
||||
|
||||
if(changed)
|
||||
animate(src, transform = ntransform, time = 2, pixel_y = final_pixel_y, dir = final_dir, easing = EASE_IN|EASE_OUT)
|
||||
floating = 0 // If we were without gravity, the bouncing animation got stopped, so we make sure we restart it in next life().
|
||||
setMovetype(movement_type & ~FLOATING) // If we were without gravity, the bouncing animation got stopped, so we make sure we restart it in next life().
|
||||
|
||||
|
||||
/mob/living/carbon
|
||||
|
||||
@@ -4,7 +4,7 @@
|
||||
if(digitalinvis)
|
||||
handle_diginvis() //AI becomes unable to see mob
|
||||
|
||||
if((movement_type & FLYING) && !floating) //TODO: Better floating
|
||||
if((movement_type & FLYING) && !(movement_type & FLOATING)) //TODO: Better floating
|
||||
float(on = TRUE)
|
||||
|
||||
if (client)
|
||||
|
||||
@@ -716,14 +716,14 @@
|
||||
var/fixed = 0
|
||||
if(anchored || (buckled && buckled.anchored))
|
||||
fixed = 1
|
||||
if(on && !floating && !fixed)
|
||||
if(on && !(movement_type & FLOATING) && !fixed)
|
||||
animate(src, pixel_y = pixel_y + 2, time = 10, loop = -1)
|
||||
sleep(10)
|
||||
animate(src, pixel_y = pixel_y - 2, time = 10, loop = -1)
|
||||
floating = TRUE
|
||||
else if(((!on || fixed) && floating))
|
||||
setMovetype(movement_type | FLOATING)
|
||||
else if(((!on || fixed) && (movement_type & FLOATING)))
|
||||
animate(src, pixel_y = get_standard_pixel_y_offset(lying), time = 10)
|
||||
floating = FALSE
|
||||
setMovetype(movement_type & ~FLOATING)
|
||||
|
||||
// The src mob is trying to strip an item from someone
|
||||
// Override if a certain type of mob should be behave differently when stripping items (can't, for example)
|
||||
@@ -795,7 +795,7 @@
|
||||
var/final_pixel_y = get_standard_pixel_y_offset(lying)
|
||||
animate(src, pixel_x = pixel_x + pixel_x_diff, pixel_y = pixel_y + pixel_y_diff , time = 2, loop = 6)
|
||||
animate(pixel_x = final_pixel_x , pixel_y = final_pixel_y , time = 2)
|
||||
floating = 0 // If we were without gravity, the bouncing animation got stopped, so we make sure to restart it in next life().
|
||||
setMovetype(movement_type & ~FLOATING) // If we were without gravity, the bouncing animation got stopped, so we make sure to restart it in next life().
|
||||
|
||||
/mob/living/proc/get_temperature(datum/gas_mixture/environment)
|
||||
var/loc_temp = environment ? environment.temperature : T0C
|
||||
@@ -935,7 +935,7 @@
|
||||
|
||||
apply_effect((amount*RAD_MOB_COEFFICIENT)/max(1, (radiation**2)*RAD_OVERDOSE_REDUCTION), EFFECT_IRRADIATE, blocked)
|
||||
|
||||
/mob/living/anti_magic_check(magic = TRUE, holy = FALSE)
|
||||
/mob/living/anti_magic_check(magic = TRUE, holy = FALSE, chargecost = 1, self = FALSE)
|
||||
. = ..()
|
||||
if(.)
|
||||
return
|
||||
|
||||
@@ -422,4 +422,4 @@
|
||||
if(!used_item)
|
||||
used_item = get_active_held_item()
|
||||
..()
|
||||
floating = 0 // If we were without gravity, the bouncing animation got stopped, so we make sure we restart the bouncing after the next movement.
|
||||
setMovetype(movement_type & ~FLOATING) // If we were without gravity, the bouncing animation got stopped, so we make sure we restart the bouncing after the next movement.
|
||||
|
||||
@@ -36,6 +36,8 @@
|
||||
|
||||
if(istype(loc, /obj/item/aicard/aitater))
|
||||
loc.icon_state = "aitater-404"
|
||||
else if(istype(loc, /obj/item/aicard/aispook))
|
||||
loc.icon_state = "aispook-404"
|
||||
else if(istype(loc, /obj/item/aicard))
|
||||
loc.icon_state = "aicard-404"
|
||||
|
||||
|
||||
@@ -140,7 +140,7 @@
|
||||
radio.attack_self(src)
|
||||
|
||||
if("image")
|
||||
var/newImage = input("Select your new display image.", "Display Image", "Happy") in list("Happy", "Cat", "Extremely Happy", "Face", "Laugh", "Off", "Sad", "Angry", "What" , "Exclamation" ,"Question") // CITADEL EDIT
|
||||
var/newImage = input("Select your new display image.", "Display Image", "Happy") in list("Happy", "Cat", "Extremely Happy", "Face", "Laugh", "Off", "Sad", "Angry", "What" , "Exclamation" ,"Question", "Sunglasses")
|
||||
var/pID = 1
|
||||
|
||||
switch(newImage)
|
||||
@@ -164,10 +164,12 @@
|
||||
pID = 9
|
||||
if("Null")
|
||||
pID = 10
|
||||
if("Exclamation") // CITADEL EDIT
|
||||
if("Exclamation")
|
||||
pID = 11
|
||||
if("Question") // CITADEL EDIT
|
||||
if("Question")
|
||||
pID = 12
|
||||
if("Sunglasses")
|
||||
pID = 13
|
||||
card.setEmotion(pID)
|
||||
|
||||
if("signaller")
|
||||
|
||||
@@ -8,6 +8,8 @@
|
||||
righthand_file = 'icons/mob/inhands/misc/devices_righthand.dmi'
|
||||
flags_1 = CONDUCT_1
|
||||
|
||||
var/borghealth = 100
|
||||
|
||||
var/list/basic_modules = list() //a list of paths, converted to a list of instances on New()
|
||||
var/list/emag_modules = list() //ditto
|
||||
var/list/ratvar_modules = list() //ditto ditto
|
||||
@@ -223,6 +225,8 @@
|
||||
INVOKE_ASYNC(RM, .proc/do_transform_animation)
|
||||
if(RM.dogborg)
|
||||
RM.dogborg_equip()
|
||||
R.maxHealth = borghealth
|
||||
R.health = min(borghealth, R.health)
|
||||
qdel(src)
|
||||
return RM
|
||||
|
||||
@@ -617,6 +621,14 @@
|
||||
sleeper_overlay = "valesecsleeper"
|
||||
return ..()
|
||||
|
||||
/obj/item/robot_module/security/Initialize()
|
||||
. = ..()
|
||||
if(!CONFIG_GET(flag/weaken_secborg))
|
||||
for(var/obj/item/gun/energy/disabler/cyborg/pewpew in basic_modules)
|
||||
basic_modules -= pewpew
|
||||
basic_modules += new /obj/item/gun/energy/e_gun/advtaser/cyborg(src)
|
||||
qdel(pewpew)
|
||||
|
||||
/obj/item/robot_module/peacekeeper
|
||||
name = "Peacekeeper"
|
||||
basic_modules = list(
|
||||
@@ -628,6 +640,7 @@
|
||||
/obj/item/reagent_containers/borghypo/peace,
|
||||
/obj/item/holosign_creator/cyborg,
|
||||
/obj/item/borg/cyborghug/peacekeeper,
|
||||
/obj/item/megaphone,
|
||||
/obj/item/borg/projectile_dampen)
|
||||
emag_modules = list(/obj/item/reagent_containers/borghypo/peace/hacked)
|
||||
ratvar_modules = list(
|
||||
|
||||
@@ -101,7 +101,7 @@
|
||||
|
||||
if(ASSEMBLY_FOURTH_STEP)
|
||||
if(istype(W, /obj/item/weldingtool))
|
||||
if(W.use_tool(src, user, 0, volume=40))
|
||||
if(W.use_tool(src, user, 0, volume=40) && build_step == 4)
|
||||
name = "shielded frame assembly"
|
||||
to_chat(user, "<span class='notice'>You weld the vest to [src].</span>")
|
||||
build_step++
|
||||
@@ -183,7 +183,7 @@
|
||||
if(8)
|
||||
if(istype(W, /obj/item/screwdriver))
|
||||
to_chat(user, "<span class='notice'>You start attaching the gun to the frame...</span>")
|
||||
if(W.use_tool(src, user, 40, volume=100))
|
||||
if(W.use_tool(src, user, 40, volume=100) && build_step == 8)
|
||||
name = "armed [name]"
|
||||
to_chat(user, "<span class='notice'>Taser gun attached.</span>")
|
||||
build_step++
|
||||
|
||||
@@ -383,7 +383,7 @@
|
||||
if((!C.reagents.has_reagent(treatment_fire_avoid)) && (C.getFireLoss() >= heal_threshold) && (!C.reagents.has_reagent(treatment_fire)))
|
||||
return TRUE
|
||||
var/treatment_toxavoid = get_avoidchem_toxin(C)
|
||||
if(((treatment_toxavoid && !C.reagents.has_reagent(treatment_toxavoid))) && (C.getToxLoss() >= heal_threshold) && (!C.reagents.has_reagent(get_healchem_toxin(C))))
|
||||
if(((isnull(treatment_toxavoid) || !C.reagents.has_reagent(treatment_toxavoid))) && (C.getToxLoss() >= heal_threshold) && (!C.reagents.has_reagent(get_healchem_toxin(C))))
|
||||
return TRUE
|
||||
|
||||
if(treat_virus && !C.reagents.has_reagent(treatment_virus_avoid) && !C.reagents.has_reagent(treatment_virus))
|
||||
@@ -472,7 +472,7 @@
|
||||
if(!reagent_id && (C.getToxLoss() >= heal_threshold))
|
||||
var/toxin_heal_avoid = get_avoidchem_toxin(C)
|
||||
var/toxin_healchem = get_healchem_toxin(C)
|
||||
if(!C.reagents.has_reagent(toxin_healchem) && (toxin_heal_avoid && !C.reagents.has_reagent(toxin_heal_avoid)))
|
||||
if(!C.reagents.has_reagent(toxin_healchem) && (isnull(toxin_heal_avoid) || !C.reagents.has_reagent(toxin_heal_avoid)))
|
||||
reagent_id = toxin_healchem
|
||||
|
||||
//If the patient is injured but doesn't have our special reagent in them then we should give it to them first
|
||||
|
||||
@@ -323,6 +323,132 @@
|
||||
else
|
||||
STOP_PROCESSING(SSobj, src)
|
||||
|
||||
// Space kiwis, ergo quite a copypasta of chickens.
|
||||
|
||||
/mob/living/simple_animal/kiwi
|
||||
name = "space kiwi"
|
||||
desc = "Exposure to low gravity made them grow larger."
|
||||
gender = FEMALE
|
||||
icon_state = "kiwi"
|
||||
icon_living = "kiwi"
|
||||
icon_dead = "kiwi_dead"
|
||||
speak = list("Chirp!","Cheep cheep chirp!!","Cheep.")
|
||||
speak_emote = list("chirps","trills")
|
||||
emote_hear = list("chirps.")
|
||||
emote_see = list("pecks at the ground.","jumps in place.")
|
||||
density = FALSE
|
||||
speak_chance = 2
|
||||
turns_per_move = 3
|
||||
butcher_results = list(/obj/item/reagent_containers/food/snacks/meat/slab = 3)
|
||||
var/egg_type = /obj/item/reagent_containers/food/snacks/egg/kiwiEgg
|
||||
var/food_type = /obj/item/reagent_containers/food/snacks/grown/wheat
|
||||
response_help = "pets"
|
||||
response_disarm = "gently pushes aside"
|
||||
response_harm = "kicks"
|
||||
attacktext = "kicks"
|
||||
health = 25
|
||||
maxHealth = 25
|
||||
ventcrawler = VENTCRAWLER_ALWAYS
|
||||
var/eggsleft = 0
|
||||
var/eggsFertile = TRUE
|
||||
pass_flags = PASSTABLE | PASSMOB
|
||||
mob_size = MOB_SIZE_SMALL
|
||||
var/list/feedMessages = list("It chirps happily.","It chirps happily.")
|
||||
var/list/layMessage = list("lays an egg.","squats down and croons.","begins making a huge racket.","begins chirping raucously.")
|
||||
gold_core_spawnable = FRIENDLY_SPAWN
|
||||
var/static/kiwi_count = 0
|
||||
|
||||
/mob/living/simple_animal/kiwi/Destroy()
|
||||
--kiwi_count
|
||||
return ..()
|
||||
|
||||
/mob/living/simple_animal/kiwi/Initialize()
|
||||
. = ..()
|
||||
++kiwi_count
|
||||
|
||||
/mob/living/simple_animal/kiwi/Life()
|
||||
. =..()
|
||||
if(!.)
|
||||
return
|
||||
if((!stat && prob(3) && eggsleft > 0) && egg_type)
|
||||
visible_message("[src] [pick(layMessage)]")
|
||||
eggsleft--
|
||||
var/obj/item/E = new egg_type(get_turf(src))
|
||||
E.pixel_x = rand(-6,6)
|
||||
E.pixel_y = rand(-6,6)
|
||||
if(eggsFertile)
|
||||
if(kiwi_count < MAX_CHICKENS && prob(25))
|
||||
START_PROCESSING(SSobj, E)
|
||||
|
||||
/obj/item/reagent_containers/food/snacks/egg/kiwiEgg/process()
|
||||
if(isturf(loc))
|
||||
amount_grown += rand(1,2)
|
||||
if(amount_grown >= 100)
|
||||
visible_message("[src] hatches with a quiet cracking sound.")
|
||||
new /mob/living/simple_animal/babyKiwi(get_turf(src))
|
||||
STOP_PROCESSING(SSobj, src)
|
||||
qdel(src)
|
||||
else
|
||||
STOP_PROCESSING(SSobj, src)
|
||||
|
||||
/mob/living/simple_animal/kiwi/attackby(obj/item/O, mob/user, params)
|
||||
if(istype(O, food_type)) //feedin' dem kiwis
|
||||
if(!stat && eggsleft < 8)
|
||||
var/feedmsg = "[user] feeds [O] to [name]! [pick(feedMessages)]"
|
||||
user.visible_message(feedmsg)
|
||||
qdel(O)
|
||||
eggsleft += rand(1, 4)
|
||||
else
|
||||
to_chat(user, "<span class='warning'>[name] doesn't seem hungry!</span>")
|
||||
else
|
||||
..()
|
||||
|
||||
/mob/living/simple_animal/babyKiwi
|
||||
name = "baby space kiwi"
|
||||
desc = "So huggable."
|
||||
icon_state = "babykiwi"
|
||||
icon_living = "babykiwi"
|
||||
icon_dead = "babykiwi_dead"
|
||||
gender = FEMALE
|
||||
speak = list("Cherp.","Cherp?","Chirrup.","Cheep!")
|
||||
speak_emote = list("chirps")
|
||||
emote_hear = list("chirps.")
|
||||
emote_see = list("pecks at the ground.","Happily bounces in place.")
|
||||
density = FALSE
|
||||
speak_chance = 2
|
||||
turns_per_move = 2
|
||||
butcher_results = list(/obj/item/reagent_containers/food/snacks/meat/slab = 2)
|
||||
response_help = "pets"
|
||||
response_disarm = "gently pushes aside"
|
||||
response_harm = "kicks"
|
||||
attacktext = "kicks"
|
||||
health = 10
|
||||
maxHealth = 10
|
||||
ventcrawler = VENTCRAWLER_ALWAYS
|
||||
var/amount_grown = 0
|
||||
pass_flags = PASSTABLE | PASSGRILLE | PASSMOB
|
||||
mob_size = MOB_SIZE_TINY
|
||||
gold_core_spawnable = FRIENDLY_SPAWN
|
||||
|
||||
/mob/living/simple_animal/babyKiwi/Initialize()
|
||||
. = ..()
|
||||
pixel_x = rand(-6, 6)
|
||||
pixel_y = rand(0, 10)
|
||||
|
||||
/mob/living/simple_animal/babyKiwi/Life()
|
||||
. =..()
|
||||
if(!.)
|
||||
return
|
||||
if(!stat && !ckey)
|
||||
amount_grown += rand(1,2)
|
||||
if(amount_grown >= 100)
|
||||
new /mob/living/simple_animal/kiwi(src.loc)
|
||||
qdel(src)
|
||||
|
||||
/obj/item/reagent_containers/food/snacks/egg/kiwiEgg
|
||||
name = "kiwi egg"
|
||||
desc = "A slightly bigger egg!"
|
||||
icon_state = "kiwiegg"
|
||||
|
||||
/obj/item/udder
|
||||
name = "udder"
|
||||
|
||||
@@ -0,0 +1,100 @@
|
||||
/mob/living/simple_animal/banana_spider
|
||||
name = "banana spider"
|
||||
desc = "What the fuck is this abomination?"
|
||||
icon_state = "bananaspider"
|
||||
icon_dead = "bananaspider_peel"
|
||||
health = 1
|
||||
maxHealth = 1
|
||||
turns_per_move = 5 //this isn't player speed =|
|
||||
speed = 2 //this is player speed
|
||||
loot = list(/obj/item/reagent_containers/food/snacks/deadbanana_spider)
|
||||
atmos_requirements = list("min_oxy" = 0, "max_oxy" = 0, "min_tox" = 0, "max_tox" = 0, "min_co2" = 0, "max_co2" = 0, "min_n2" = 0, "max_n2" = 0)
|
||||
minbodytemp = 270
|
||||
maxbodytemp = INFINITY
|
||||
pass_flags = PASSTABLE | PASSGRILLE | PASSMOB
|
||||
mob_size = MOB_SIZE_TINY
|
||||
response_help = "pokes"
|
||||
response_disarm = "shoos"
|
||||
response_harm = "splats"
|
||||
speak_emote = list("chitters")
|
||||
mouse_opacity = 2
|
||||
density = TRUE
|
||||
ventcrawler = VENTCRAWLER_ALWAYS
|
||||
gold_core_spawnable = FRIENDLY_SPAWN
|
||||
verb_say = "chitters"
|
||||
verb_ask = "chitters inquisitively"
|
||||
verb_exclaim = "chitters loudly"
|
||||
verb_yell = "chitters loudly"
|
||||
var/squish_chance = 50
|
||||
var/projectile_density = TRUE //griffons get shot
|
||||
del_on_death = TRUE
|
||||
|
||||
/mob/living/simple_animal/banana_spider/Initialize()
|
||||
. = ..()
|
||||
var/area/A = get_area(src)
|
||||
if(A)
|
||||
notify_ghosts("A banana spider has been created in \the [A.name].", source = src, action=NOTIFY_ATTACK, flashwindow = FALSE)
|
||||
|
||||
/mob/living/simple_animal/banana_spider/attack_ghost(mob/user)
|
||||
if(key) //please stop using src. without a good reason.
|
||||
return
|
||||
if(CONFIG_GET(flag/use_age_restriction_for_jobs))
|
||||
if(!isnum(user.client.player_age))
|
||||
return
|
||||
if(!SSticker.mode)
|
||||
to_chat(user, "Can't become a banana spider before the game has started.")
|
||||
return
|
||||
var/be_spider = alert("Become a banana spider? (Warning, You can no longer be cloned!)",,"Yes","No")
|
||||
if(be_spider == "No" || QDELETED(src) || !isobserver(user))
|
||||
return
|
||||
sentience_act()
|
||||
user.transfer_ckey(src, FALSE)
|
||||
density = TRUE
|
||||
|
||||
/mob/living/simple_animal/banana_spider/ComponentInitialize()
|
||||
. = ..()
|
||||
AddComponent(/datum/component/slippery, 40)
|
||||
|
||||
/mob/living/simple_animal/banana_spider/Crossed(atom/movable/AM) //no /var in proc headers
|
||||
. = ..()
|
||||
if(istype(AM, /obj/item/projectile) && projectile_density) //forced projectile density
|
||||
var/obj/item/projectile/P = AM
|
||||
P.Bump(src)
|
||||
if(ismob(AM))
|
||||
if(isliving(AM))
|
||||
var/mob/living/A = AM
|
||||
if(A.mob_size > MOB_SIZE_SMALL && !(A.movement_type & FLYING))
|
||||
if(prob(squish_chance))
|
||||
A.visible_message("<span class='notice'>[A] squashed [src].</span>", "<span class='notice'>You squashed [src] under your weight as you fell.</span>")
|
||||
adjustBruteLoss(1)
|
||||
else
|
||||
visible_message("<span class='notice'>[src] avoids getting crushed.</span>")
|
||||
else
|
||||
if(isstructure(AM))
|
||||
if(prob(squish_chance))
|
||||
AM.visible_message("<span class='notice'>[src] was crushed under [AM]'s weight as they fell.</span>")
|
||||
adjustBruteLoss(1)
|
||||
else
|
||||
visible_message("<span class='notice'>[src] avoids getting crushed.</span>")
|
||||
|
||||
/mob/living/simple_animal/banana_spider/ex_act()
|
||||
return
|
||||
|
||||
/mob/living/simple_animal/banana_spider/start_pulling()
|
||||
return FALSE //No.
|
||||
|
||||
/obj/item/reagent_containers/food/snacks/deadbanana_spider
|
||||
name = "dead banana spider"
|
||||
desc = "Thank god it's gone...but it does look slippery."
|
||||
icon_state = "bananaspider"
|
||||
bitesize = 3
|
||||
eatverb = "devours"
|
||||
list_reagents = list("nutriment" = 3, "vitamin" = 2)
|
||||
foodtype = GROSS | MEAT | RAW
|
||||
grind_results = list("blood" = 20, "liquidgibs" = 5)
|
||||
juice_results = list("banana" = 0)
|
||||
|
||||
|
||||
/obj/item/reagent_containers/food/snacks/deadbanana_spider/Initialize()
|
||||
. = ..()
|
||||
AddComponent(/datum/component/slippery, 20)
|
||||
@@ -175,14 +175,17 @@
|
||||
status_flags = NONE
|
||||
mob_size = MOB_SIZE_LARGE
|
||||
gold_core_spawnable = NO_SPAWN
|
||||
var/slowed_by_webs = FALSE
|
||||
|
||||
/mob/living/simple_animal/hostile/poison/giant_spider/tarantula/movement_delay()
|
||||
var/turf/T = get_turf(src)
|
||||
if(locate(/obj/structure/spider/stickyweb) in T)
|
||||
speed = 2
|
||||
else
|
||||
speed = 7
|
||||
/mob/living/simple_animal/hostile/poison/giant_spider/tarantula/Moved(atom/oldloc, dir)
|
||||
. = ..()
|
||||
if(slowed_by_webs)
|
||||
if(!(locate(/obj/structure/spider/stickyweb) in loc))
|
||||
remove_movespeed_modifier(MOVESPEED_ID_TARANTULA_WEB)
|
||||
slowed_by_webs = FALSE
|
||||
else if(locate(/obj/structure/spider/stickyweb) in loc)
|
||||
add_movespeed_modifier(MOVESPEED_ID_TARANTULA_WEB, priority=100, multiplicative_slowdown=3)
|
||||
slowed_by_webs = TRUE
|
||||
|
||||
//midwives are the queen of the spiders, can send messages to all them and web faster. That rare round where you get a queen spider and turn your 'for honor' players into 'r6siege' players will be a fun one.
|
||||
/mob/living/simple_animal/hostile/poison/giant_spider/nurse/midwife
|
||||
|
||||
@@ -2,7 +2,7 @@
|
||||
#define GORILLA_TOTAL_LAYERS 1
|
||||
|
||||
/mob/living/simple_animal/hostile/gorilla
|
||||
name = "Gorilla"
|
||||
name = "gorilla"
|
||||
desc = "A ground-dwelling, predominantly herbivorous ape that inhabits the forests of central Africa."
|
||||
icon = 'icons/mob/gorilla.dmi'
|
||||
icon_state = "crawling"
|
||||
@@ -108,3 +108,10 @@
|
||||
playsound(src, 'sound/creatures/gorilla.ogg', 200)
|
||||
oogas = 0
|
||||
|
||||
/mob/living/simple_animal/hostile/gorilla/familiar
|
||||
name = "familiar gorilla"
|
||||
desc = "There is no need to be upset."
|
||||
unique_name = FALSE
|
||||
AIStatus = AI_OFF
|
||||
atmos_requirements = list("min_oxy" = 0, "max_oxy" = 0, "min_tox" = 0, "max_tox" = 0, "min_co2" = 0, "max_co2" = 0, "min_n2" = 0, "max_n2" = 0)
|
||||
minbodytemp = 0
|
||||
@@ -344,6 +344,7 @@
|
||||
|
||||
|
||||
/mob/living/simple_animal/hostile/proc/AttackingTarget()
|
||||
SEND_SIGNAL(src, COMSIG_HOSTILE_ATTACKINGTARGET, target)
|
||||
in_melee = TRUE
|
||||
if(vore_active)
|
||||
if(isliving(target))
|
||||
@@ -426,12 +427,13 @@
|
||||
if(casingtype)
|
||||
var/obj/item/ammo_casing/casing = new casingtype(startloc)
|
||||
playsound(src, projectilesound, 100, 1)
|
||||
casing.fire_casing(targeted_atom, src, null, null, null, ran_zone())
|
||||
casing.fire_casing(targeted_atom, src, null, null, null, ran_zone(), src)
|
||||
else if(projectiletype)
|
||||
var/obj/item/projectile/P = new projectiletype(startloc)
|
||||
playsound(src, projectilesound, 100, 1)
|
||||
P.starting = startloc
|
||||
P.firer = src
|
||||
P.fired_from = src
|
||||
P.yo = targeted_atom.y - startloc.y
|
||||
P.xo = targeted_atom.x - startloc.x
|
||||
if(AIStatus != AI_ON)//Don't want mindless mobs to have their movement screwed up firing in space
|
||||
|
||||
@@ -388,7 +388,7 @@ Difficulty: Very Hard
|
||||
ActivationReaction(user, ACTIVATE_TOUCH)
|
||||
|
||||
/obj/machinery/anomalous_crystal/attackby(obj/item/I, mob/user, params)
|
||||
if(I.is_hot())
|
||||
if(I.get_temperature())
|
||||
ActivationReaction(user, ACTIVATE_HEAT)
|
||||
else
|
||||
ActivationReaction(user, ACTIVATE_WEAPON)
|
||||
@@ -649,7 +649,7 @@ Difficulty: Very Hard
|
||||
L.heal_overall_damage(heal_power, heal_power)
|
||||
new /obj/effect/temp_visual/heal(get_turf(target), "#80F5FF")
|
||||
|
||||
/mob/living/simple_animal/hostile/lightgeist/ghostize(can_reenter_corpse = TRUE, send_the_signal = TRUE)
|
||||
/mob/living/simple_animal/hostile/lightgeist/ghostize(can_reenter_corpse = TRUE, special = FALSE)
|
||||
. = ..()
|
||||
if(.)
|
||||
death()
|
||||
|
||||
@@ -34,7 +34,7 @@
|
||||
|
||||
/mob/living/simple_animal/hostile/netherworld/migo/Initialize()
|
||||
. = ..()
|
||||
migo_sounds = list('sound/items/bubblewrap.ogg', 'sound/items/change_jaws.ogg', 'sound/items/crowbar.ogg', 'sound/items/drink.ogg', 'sound/items/deconstruct.ogg', 'sound/items/carhorn.ogg', 'sound/items/change_drill.ogg', 'sound/items/dodgeball.ogg', 'sound/items/eatfood.ogg', 'sound/items/megaphone.ogg', 'sound/items/screwdriver.ogg', 'sound/items/weeoo1.ogg', 'sound/items/wirecutter.ogg', 'sound/items/welder.ogg', 'sound/items/zip.ogg', 'sound/items/rped.ogg', 'sound/items/ratchet.ogg', 'sound/items/polaroid1.ogg', 'sound/items/pshoom.ogg', 'sound/items/airhorn.ogg', 'sound/items/geiger/high1.ogg', 'sound/items/geiger/high2.ogg', 'sound/voice/beepsky/creep.ogg', 'sound/voice/beepsky/iamthelaw.ogg', 'sound/voice/ed209_20sec.ogg', 'sound/voice/hiss3.ogg', 'sound/voice/hiss6.ogg', 'sound/voice/medbot/patchedup.ogg', 'sound/voice/medbot/feelbetter.ogg', 'sound/voice/human/manlaugh1.ogg', 'sound/voice/human/womanlaugh.ogg', 'sound/weapons/sear.ogg', 'sound/ambience/antag/clockcultalr.ogg', 'sound/ambience/antag/ling_aler.ogg', 'sound/ambience/antag/tatoralert.ogg', 'sound/ambience/antag/monkey.ogg', 'sound/mecha/nominal.ogg', 'sound/mecha/weapdestr.ogg', 'sound/mecha/critdestr.ogg', 'sound/mecha/imag_enh.ogg', 'sound/effects/adminhelp.ogg', 'sound/effects/alert.ogg', 'sound/effects/attackblob.ogg', 'sound/effects/bamf.ogg', 'sound/effects/blobattack.ogg', 'sound/effects/break_stone.ogg', 'sound/effects/bubbles.ogg', 'sound/effects/bubbles2.ogg', 'sound/effects/clang.ogg', 'sound/effects/clockcult_gateway_disrupted.ogg', 'sound/effects/clownstep2.ogg', 'sound/effects/curse1.ogg', 'sound/effects/dimensional_rend.ogg', 'sound/effects/doorcreaky.ogg', 'sound/effects/empulse.ogg', 'sound/effects/explosion_distant.ogg', 'sound/effects/explosionfar.ogg', 'sound/effects/explosion1.ogg', 'sound/effects/grillehit.ogg', 'sound/effects/genetics.ogg', 'sound/effects/heart_beat.ogg', 'sound/effects/hyperspace_begin.ogg', 'sound/effects/hyperspace_end.ogg', 'sound/effects/his_grace_awaken.ogg', 'sound/effects/pai_boot.ogg', 'sound/effects/phasein.ogg', 'sound/effects/picaxe1.ogg', 'sound/effects/ratvar_reveal.ogg', 'sound/effects/sparks1.ogg', 'sound/effects/smoke.ogg', 'sound/effects/splat.ogg', 'sound/effects/snap.ogg', 'sound/effects/tendril_destroyed.ogg', 'sound/effects/supermatter.ogg', 'sound/misc/desceration-01.ogg', 'sound/misc/desceration-02.ogg', 'sound/misc/desceration-03.ogg', 'sound/misc/bloblarm.ogg', 'sound/misc/airraid.ogg', 'sound/misc/bang.ogg','sound/misc/highlander.ogg', 'sound/misc/interference.ogg', 'sound/misc/notice1.ogg', 'sound/misc/notice2.ogg', 'sound/misc/sadtrombone.ogg', 'sound/misc/slip.ogg', 'sound/misc/splort.ogg', 'sound/weapons/armbomb.ogg', 'sound/weapons/beam_sniper.ogg', 'sound/weapons/chainsawhit.ogg', 'sound/weapons/emitter.ogg', 'sound/weapons/emitter2.ogg', 'sound/weapons/blade1.ogg', 'sound/weapons/bladeslice.ogg', 'sound/weapons/blastcannon.ogg', 'sound/weapons/blaster.ogg', 'sound/weapons/bulletflyby3.ogg', 'sound/weapons/circsawhit.ogg', 'sound/weapons/cqchit2.ogg', 'sound/weapons/drill.ogg', 'sound/weapons/genhit1.ogg', 'sound/weapons/gunshot_silenced.ogg', 'sound/weapons/gunshot2.ogg', 'sound/weapons/handcuffs.ogg', 'sound/weapons/homerun.ogg', 'sound/weapons/kenetic_accel.ogg', 'sound/machines/clockcult/steam_whoosh.ogg', 'sound/machines/fryer/deep_fryer_emerge.ogg', 'sound/machines/airlock.ogg', 'sound/machines/airlock_alien_prying.ogg', 'sound/machines/airlockclose.ogg', 'sound/machines/airlockforced.ogg', 'sound/machines/airlockopen.ogg', 'sound/machines/alarm.ogg', 'sound/machines/blender.ogg', 'sound/machines/boltsdown.ogg', 'sound/machines/boltsup.ogg', 'sound/machines/buzz-sigh.ogg', 'sound/machines/buzz-two.ogg', 'sound/machines/chime.ogg', 'sound/machines/cryo_warning.ogg', 'sound/machines/defib_charge.ogg', 'sound/machines/defib_failed.ogg', 'sound/machines/defib_ready.ogg', 'sound/machines/defib_zap.ogg', 'sound/machines/deniedbeep.ogg', 'sound/machines/ding.ogg', 'sound/machines/disposalflush.ogg', 'sound/machines/door_close.ogg', 'sound/machines/door_open.ogg', 'sound/machines/engine_alert1.ogg', 'sound/machines/engine_alert2.ogg', 'sound/machines/hiss.ogg', 'sound/machines/honkbot_evil_laugh.ogg', 'sound/machines/juicer.ogg', 'sound/machines/ping.ogg', 'sound/machines/signal.ogg', 'sound/machines/synth_no.ogg', 'sound/machines/synth_yes.ogg', 'sound/machines/terminal_alert.ogg', 'sound/machines/triple_beep.ogg', 'sound/machines/twobeep.ogg', 'sound/machines/ventcrawl.ogg', 'sound/machines/warning-buzzer.ogg', 'sound/ai/outbreak5.ogg', 'sound/ai/outbreak7.ogg', 'sound/ai/poweroff.ogg', 'sound/ai/radiation.ogg', 'sound/ai/shuttlecalled.ogg', 'sound/ai/shuttledock.ogg', 'sound/ai/shuttlerecalled.ogg', 'sound/ai/aimalf.ogg') //hahahaha fuck you code divers
|
||||
migo_sounds = list('sound/items/bubblewrap.ogg', 'sound/items/change_jaws.ogg', 'sound/items/crowbar.ogg', 'sound/items/drink.ogg', 'sound/items/deconstruct.ogg', 'sound/items/carhorn.ogg', 'sound/items/change_drill.ogg', 'sound/items/dodgeball.ogg', 'sound/items/eatfood.ogg', 'sound/items/megaphone.ogg', 'sound/items/screwdriver.ogg', 'sound/items/weeoo1.ogg', 'sound/items/wirecutter.ogg', 'sound/items/welder.ogg', 'sound/items/zip.ogg', 'sound/items/rped.ogg', 'sound/items/ratchet.ogg', 'sound/items/polaroid1.ogg', 'sound/items/pshoom.ogg', 'sound/items/airhorn.ogg', 'sound/items/geiger/high1.ogg', 'sound/items/geiger/high2.ogg', 'sound/voice/beepsky/creep.ogg', 'sound/voice/beepsky/iamthelaw.ogg', 'sound/voice/ed209_20sec.ogg', 'sound/voice/hiss3.ogg', 'sound/voice/hiss6.ogg', 'sound/voice/medbot/patchedup.ogg', 'sound/voice/medbot/feelbetter.ogg', 'sound/voice/human/manlaugh1.ogg', 'sound/voice/human/womanlaugh.ogg', 'sound/weapons/sear.ogg', 'sound/ambience/antag/clockcultalr.ogg', 'sound/ambience/antag/ling_aler.ogg', 'sound/ambience/antag/tatoralert.ogg', 'sound/ambience/antag/monkey.ogg', 'sound/mecha/nominal.ogg', 'sound/mecha/weapdestr.ogg', 'sound/mecha/critdestr.ogg', 'sound/mecha/imag_enh.ogg', 'sound/effects/adminhelp.ogg', 'sound/effects/alert.ogg', 'sound/effects/attackblob.ogg', 'sound/effects/bamf.ogg', 'sound/effects/blobattack.ogg', 'sound/effects/break_stone.ogg', 'sound/effects/bubbles.ogg', 'sound/effects/bubbles2.ogg', 'sound/effects/clang.ogg', 'sound/effects/clockcult_gateway_disrupted.ogg', 'sound/effects/clownstep2.ogg', 'sound/effects/curse1.ogg', 'sound/effects/dimensional_rend.ogg', 'sound/effects/doorcreaky.ogg', 'sound/effects/empulse.ogg', 'sound/effects/explosion_distant.ogg', 'sound/effects/explosionfar.ogg', 'sound/effects/explosion1.ogg', 'sound/effects/grillehit.ogg', 'sound/effects/genetics.ogg', 'sound/effects/heart_beat.ogg', 'sound/effects/hyperspace_begin.ogg', 'sound/effects/hyperspace_end.ogg', 'sound/effects/his_grace_awaken.ogg', 'sound/effects/pai_boot.ogg', 'sound/effects/phasein.ogg', 'sound/effects/picaxe1.ogg', 'sound/effects/ratvar_reveal.ogg', 'sound/effects/sparks1.ogg', 'sound/effects/smoke.ogg', 'sound/effects/splat.ogg', 'sound/effects/snap.ogg', 'sound/effects/tendril_destroyed.ogg', 'sound/effects/supermatter.ogg', 'sound/misc/desceration-01.ogg', 'sound/misc/desceration-02.ogg', 'sound/misc/desceration-03.ogg', 'sound/misc/bloblarm.ogg', 'sound/misc/airraid.ogg', 'sound/misc/bang.ogg','sound/misc/highlander.ogg', 'sound/misc/interference.ogg', 'sound/misc/notice1.ogg', 'sound/misc/notice2.ogg', 'sound/misc/sadtrombone.ogg', 'sound/misc/slip.ogg', 'sound/misc/splort.ogg', 'sound/weapons/armbomb.ogg', 'sound/weapons/beam_sniper.ogg', 'sound/weapons/chainsawhit.ogg', 'sound/weapons/emitter.ogg', 'sound/weapons/emitter2.ogg', 'sound/weapons/blade1.ogg', 'sound/weapons/bladeslice.ogg', 'sound/weapons/blastcannon.ogg', 'sound/weapons/blaster.ogg', 'sound/weapons/bulletflyby3.ogg', 'sound/weapons/circsawhit.ogg', 'sound/weapons/cqchit2.ogg', 'sound/weapons/drill.ogg', 'sound/weapons/genhit1.ogg', 'sound/weapons/gunshot_silenced.ogg', 'sound/weapons/gunshot2.ogg', 'sound/weapons/handcuffs.ogg', 'sound/weapons/homerun.ogg', 'sound/weapons/kenetic_accel.ogg', 'sound/machines/clockcult/steam_whoosh.ogg', 'sound/machines/fryer/deep_fryer_emerge.ogg', 'sound/machines/airlock.ogg', 'sound/machines/airlock_alien_prying.ogg', 'sound/machines/airlockclose.ogg', 'sound/machines/airlockforced.ogg', 'sound/machines/airlockopen.ogg', 'sound/machines/alarm.ogg', 'sound/machines/blender.ogg', 'sound/machines/boltsdown.ogg', 'sound/machines/boltsup.ogg', 'sound/machines/buzz-sigh.ogg', 'sound/machines/buzz-two.ogg', 'sound/machines/chime.ogg', 'sound/machines/cryo_warning.ogg', 'sound/machines/defib_charge.ogg', 'sound/machines/defib_failed.ogg', 'sound/machines/defib_ready.ogg', 'sound/machines/defib_zap.ogg', 'sound/machines/deniedbeep.ogg', 'sound/machines/ding.ogg', 'sound/machines/disposalflush.ogg', 'sound/machines/door_close.ogg', 'sound/machines/door_open.ogg', 'sound/machines/engine_alert1.ogg', 'sound/machines/engine_alert2.ogg', 'sound/machines/hiss.ogg', 'sound/machines/honkbot_evil_laugh.ogg', 'sound/machines/juicer.ogg', 'sound/machines/ping.ogg', 'sound/machines/signal.ogg', 'sound/machines/synth_no.ogg', 'sound/machines/synth_yes.ogg', 'sound/machines/terminal_alert.ogg', 'sound/machines/triple_beep.ogg', 'sound/machines/twobeep.ogg', 'sound/machines/ventcrawl.ogg', 'sound/machines/warning-buzzer.ogg', get_announcer_sound("outbreak5"), get_announcer_sound("outbreak7"), get_announcer_sound("poweroff"), get_announcer_sound("radiation"), get_announcer_sound("shuttlerecalled"), get_announcer_sound("shuttledock"), get_announcer_sound("shuttlecalled"), get_announcer_sound("aimalf")) //hahahaha fuck you code divers
|
||||
|
||||
/mob/living/simple_animal/hostile/netherworld/migo/say(message, bubble_type, var/list/spans = list(), sanitize = TRUE, datum/language/language = null, ignore_spam = FALSE, forced = null)
|
||||
..()
|
||||
|
||||
@@ -363,7 +363,7 @@
|
||||
density = initial(density)
|
||||
lying = 0
|
||||
. = 1
|
||||
movement_type = initial(movement_type)
|
||||
setMovetype(initial(movement_type))
|
||||
|
||||
/mob/living/simple_animal/proc/make_babies() // <3 <3 <3
|
||||
if(gender != FEMALE || stat || next_scan_time > world.time || !childtype || !animal_species || !SSticker.IsRoundInProgress())
|
||||
|
||||
@@ -100,7 +100,7 @@ GLOBAL_LIST_INIT(ventcrawl_machinery, typecacheof(list(
|
||||
A.pipe_vision_img.plane = ABOVE_HUD_PLANE
|
||||
client.images += A.pipe_vision_img
|
||||
pipes_shown += A.pipe_vision_img
|
||||
movement_type |= VENTCRAWLING
|
||||
setMovetype(movement_type | VENTCRAWLING)
|
||||
|
||||
|
||||
/mob/living/proc/remove_ventcrawl()
|
||||
@@ -108,7 +108,7 @@ GLOBAL_LIST_INIT(ventcrawl_machinery, typecacheof(list(
|
||||
for(var/image/current_image in pipes_shown)
|
||||
client.images -= current_image
|
||||
pipes_shown.len = 0
|
||||
movement_type &= ~VENTCRAWLING
|
||||
setMovetype(movement_type & ~VENTCRAWLING)
|
||||
|
||||
|
||||
|
||||
|
||||
+10
-4
@@ -737,15 +737,17 @@ GLOBAL_VAR_INIT(exploit_warn_spam_prevention, 0)
|
||||
mob_spell_list -= S
|
||||
qdel(S)
|
||||
|
||||
/mob/proc/anti_magic_check(magic = TRUE, holy = FALSE)
|
||||
if(!magic && !holy)
|
||||
/mob/proc/anti_magic_check(magic = TRUE, holy = FALSE, tinfoil = FALSE, chargecost = 1, self = FALSE)
|
||||
if(!magic && !holy && !tinfoil)
|
||||
return
|
||||
var/list/protection_sources = list()
|
||||
if(SEND_SIGNAL(src, COMSIG_MOB_RECEIVE_MAGIC, magic, holy, protection_sources) & COMPONENT_BLOCK_MAGIC)
|
||||
if(SEND_SIGNAL(src, COMSIG_MOB_RECEIVE_MAGIC, src, magic, holy, tinfoil, chargecost, self, protection_sources) & COMPONENT_BLOCK_MAGIC)
|
||||
if(protection_sources.len)
|
||||
return pick(protection_sources)
|
||||
else
|
||||
return src
|
||||
if((magic && HAS_TRAIT(src, TRAIT_ANTIMAGIC)) || (holy && HAS_TRAIT(src, TRAIT_HOLY)))
|
||||
return src
|
||||
|
||||
//You can buckle on mobs if you're next to them since most are dense
|
||||
/mob/buckle_mob(mob/living/M, force = FALSE, check_loc = TRUE)
|
||||
@@ -862,7 +864,7 @@ GLOBAL_VAR_INIT(exploit_warn_spam_prevention, 0)
|
||||
replace_identification_name(oldname,newname)
|
||||
|
||||
for(var/datum/mind/T in SSticker.minds)
|
||||
for(var/datum/objective/obj in T.objectives)
|
||||
for(var/datum/objective/obj in T.get_all_objectives())
|
||||
// Only update if this player is a target
|
||||
if(obj.target && obj.target.current && obj.target.current.real_name == name)
|
||||
obj.update_explanation_text()
|
||||
@@ -959,3 +961,7 @@ GLOBAL_VAR_INIT(exploit_warn_spam_prevention, 0)
|
||||
|
||||
var/datum/language_holder/H = get_language_holder()
|
||||
H.open_language_menu(usr)
|
||||
|
||||
/mob/setMovetype(newval)
|
||||
. = ..()
|
||||
update_movespeed(FALSE)
|
||||
@@ -67,8 +67,8 @@
|
||||
/proc/slur(n,var/strength=50)
|
||||
strength = min(strength,50)
|
||||
var/phrase = html_decode(n)
|
||||
var/leng = lentext(phrase)
|
||||
var/counter=lentext(phrase)
|
||||
var/leng = length(phrase)
|
||||
var/counter=length(phrase)
|
||||
var/newphrase=""
|
||||
var/newletter=""
|
||||
while(counter>=1)
|
||||
@@ -102,8 +102,8 @@
|
||||
|
||||
/proc/cultslur(n) // Inflicted on victims of a stun talisman
|
||||
var/phrase = html_decode(n)
|
||||
var/leng = lentext(phrase)
|
||||
var/counter=lentext(phrase)
|
||||
var/leng = length(phrase)
|
||||
var/counter=length(phrase)
|
||||
var/newphrase=""
|
||||
var/newletter=""
|
||||
while(counter>=1)
|
||||
|
||||
@@ -1,23 +1,29 @@
|
||||
|
||||
/*Current movespeed modification list format: list(id = list(
|
||||
priority,
|
||||
flags,
|
||||
legacy slowdown/speedup amount,
|
||||
movetype_flags,
|
||||
blacklisted_movetypes,
|
||||
conflict
|
||||
))
|
||||
*/
|
||||
|
||||
//ANY ADD/REMOVE DONE IN UPDATE_MOVESPEED MUST HAVE THE UPDATE ARGUMENT SET AS FALSE!
|
||||
/mob/proc/add_movespeed_modifier(id, update = TRUE, priority = 0, flags = NONE, override = FALSE, multiplicative_slowdown = 0)
|
||||
var/list/temp = list(priority, flags, multiplicative_slowdown) //build the modification list
|
||||
/mob/proc/add_movespeed_modifier(id, update=TRUE, priority=0, flags=NONE, override=FALSE, multiplicative_slowdown=0, movetypes=ALL, blacklisted_movetypes=NONE, conflict=FALSE)
|
||||
var/list/temp = list(priority, flags, multiplicative_slowdown, movetypes, blacklisted_movetypes, conflict) //build the modification list
|
||||
var/resort = TRUE
|
||||
if(LAZYACCESS(movespeed_modification, id))
|
||||
if(movespeed_modifier_identical_check(movespeed_modification[id], temp))
|
||||
var/list/existing_data = movespeed_modification[id]
|
||||
if(movespeed_modifier_identical_check(existing_data, temp))
|
||||
return FALSE
|
||||
if(!override)
|
||||
return FALSE
|
||||
else
|
||||
remove_movespeed_modifier(id, update)
|
||||
LAZYSET(movespeed_modification, id, list(priority, flags, multiplicative_slowdown))
|
||||
if(priority == existing_data[MOVESPEED_DATA_INDEX_PRIORITY])
|
||||
resort = FALSE // We don't need to re-sort if we're replacing something already there and it's the same priority
|
||||
LAZYSET(movespeed_modification, id, temp)
|
||||
if(update)
|
||||
update_movespeed(TRUE)
|
||||
update_movespeed(resort)
|
||||
return TRUE
|
||||
|
||||
/mob/proc/remove_movespeed_modifier(id, update = TRUE)
|
||||
@@ -55,9 +61,23 @@
|
||||
if(resort)
|
||||
sort_movespeed_modlist()
|
||||
. = 0
|
||||
var/list/conflict_tracker = list()
|
||||
for(var/id in get_movespeed_modifiers())
|
||||
var/list/data = movespeed_modification[id]
|
||||
. += data[MOVESPEED_DATA_INDEX_MULTIPLICATIVE_SLOWDOWN]
|
||||
if(!(data[MOVESPEED_DATA_INDEX_MOVETYPE] & movement_type)) // We don't affect any of these move types, skip
|
||||
continue
|
||||
if(data[MOVESPEED_DATA_INDEX_BL_MOVETYPE] & movement_type) // There's a movetype here that disables this modifier, skip
|
||||
continue
|
||||
var/conflict = data[MOVESPEED_DATA_INDEX_CONFLICT]
|
||||
var/amt = data[MOVESPEED_DATA_INDEX_MULTIPLICATIVE_SLOWDOWN]
|
||||
if(conflict)
|
||||
// Conflicting modifiers prioritize the larger slowdown or the larger speedup
|
||||
// We purposefuly don't handle mixing speedups and slowdowns on the same id
|
||||
if(abs(conflict_tracker[conflict]) < abs(amt))
|
||||
conflict_tracker[conflict] = amt
|
||||
else
|
||||
continue
|
||||
. += amt
|
||||
cached_multiplicative_slowdown = .
|
||||
|
||||
/mob/proc/get_movespeed_modifiers()
|
||||
|
||||
@@ -47,7 +47,7 @@
|
||||
D.updateappearance(mutcolor_update=1, mutations_overlay_update=1)
|
||||
else if(ishuman(M))
|
||||
var/mob/living/carbon/human/H = M
|
||||
client.prefs.copy_to(H)
|
||||
client?.prefs.copy_to(H)
|
||||
H.dna.update_dna_identity()
|
||||
|
||||
if(mind && isliving(M))
|
||||
|
||||
@@ -25,7 +25,7 @@
|
||||
if(flavor_text && flavor_text != "")
|
||||
// We are decoding and then encoding to not only get correct amount of characters, but also to prevent partial escaping characters being shown.
|
||||
var/msg = html_decode(replacetext(flavor_text, "\n", " "))
|
||||
if(lentext(msg) <= 40)
|
||||
if(length(msg) <= 40)
|
||||
return "<span class='notice'>[html_encode(msg)]</span>"
|
||||
else
|
||||
return "<span class='notice'>[html_encode(copytext(msg, 1, 37))]... <a href='?src=[REF(src)];flavor_more=1'>More...</span></a>"
|
||||
|
||||
Reference in New Issue
Block a user