Files
Yogstation/code/modules/mob/living/emote.dm
Jordie a28de54405 Ban system and interface update (#41176)
Spiritual successor and extension to #17798, an almost entire rebuild of the SQL ban system backend and interface.
Bantypes are removed per #8584 and #6174. All bans are now 'role bans', server bans are when a ban's role is server. Admin bans are a column, meaning it's possible to ban admins from jobs.
Bans now have only an expiry datetime, duration is calculated from this when queried.
unbanned column is removed as it's superfluous, checking unban status is now done through checking unban_datetime. unban_round_id column added. Each ip and computerid columns rearranged so ip is always first, like in other tables. Bans now permit a null ckey, ip and computerid.

Ban checking is split into two procs now is_banned_from() does a check if a ckey is banned from one or more roles and returns true or false. This effectively replaces jobban_isbanned() used in simple if() statements. If connected a client's ban cache is checked rather than querying the DB. This makes it possible for a client connected to two or more servers to ignore any bans made on one server until their ban cache is rebuilt on the others. Could be avoided with cross-server calls to update ban caches or just the removal of the ban cache but as is I've done neither since I think it's enough of an edge case to not be worth it.
The second proc is is_banned_from_with_details(), this queries the DB for a role ban on a player's ckey, ip or CID and returns the details. This replaces direct queries in IsBanned.dm and the preferences menu.

The legacy ban system is removed.

The interfaces for banning, unbanning and editing bans have been remade to require less clicking and easier simultaneous operations. The banning and jobban panel are combined. They also store player connection details when opened so a client disconnecting no longer stops a ban being placed.

New banning panel:
Key, IP and CID can all be toggled to allow excluding them from a ban.
Checking Use IP and CID from last connection lets you enter only a ckey and have the DB fill these fields in for you, if possible.
Temporary bans have a drop-menu which lets you select between seconds, minutes, hours, days, weeks, months and years so you don't need to calculate how many minutes a long ban would be. The ban is still converted into minutes on the DB however.
Checking any of the head roles will check both of the boxes for you.
The red role box indicates there is already a ban on that role for this ckey. You can apply additional role bans to stack them.

New unbanning panel:
Unbanning panel is now separate from the banning panel but otherwise functionally the same.

Ban editing panel:
Actually just a modified banning panel, all the features from it work the same here.
You can now edit almost all parameters of a ban instead of just the reason.
You can't edit severity as it's not really part of the ban.
The panels have been tested but I've not been able to get my local server to be accessible so ban functionality isn't properly confirmed. Plenty of testing will be required as I'd rather not break bans.

cl
admin: Ban interface rework. The banning and unbanning panels have received a new design which is easier to use and allows multiple role bans to be made at once.
prefix: Ban search and unbanning moved to unbanning panel, which is now a separate panel to the old banning panel.
/cl
2018-12-04 20:48:17 +01:00

513 lines
13 KiB
Plaintext

/* EMOTE DATUMS */
/datum/emote/living
mob_type_allowed_typecache = /mob/living
mob_type_blacklist_typecache = list(/mob/living/simple_animal/slime, /mob/living/brain)
/datum/emote/living/blush
key = "blush"
key_third_person = "blushes"
message = "blushes."
/datum/emote/living/bow
key = "bow"
key_third_person = "bows"
message = "bows."
message_param = "bows to %t."
restraint_check = TRUE
/datum/emote/living/burp
key = "burp"
key_third_person = "burps"
message = "burps."
emote_type = EMOTE_AUDIBLE
/datum/emote/living/choke
key = "choke"
key_third_person = "chokes"
message = "chokes!"
emote_type = EMOTE_AUDIBLE
/datum/emote/living/cross
key = "cross"
key_third_person = "crosses"
message = "crosses their arms."
restraint_check = TRUE
/datum/emote/living/chuckle
key = "chuckle"
key_third_person = "chuckles"
message = "chuckles."
emote_type = EMOTE_AUDIBLE
/datum/emote/living/collapse
key = "collapse"
key_third_person = "collapses"
message = "collapses!"
emote_type = EMOTE_AUDIBLE
/datum/emote/living/collapse/run_emote(mob/user, params)
. = ..()
if(. && isliving(user))
var/mob/living/L = user
L.Unconscious(40)
/datum/emote/living/cough
key = "cough"
key_third_person = "coughs"
message = "coughs!"
emote_type = EMOTE_AUDIBLE
/datum/emote/living/cough/can_run_emote(mob/user, status_check = TRUE)
. = ..()
if(user.reagents && (user.reagents.get_reagent("menthol") || user.reagents.get_reagent("peppermint_patty")))
return FALSE
/datum/emote/living/dance
key = "dance"
key_third_person = "dances"
message = "dances around happily."
restraint_check = TRUE
/datum/emote/living/deathgasp
key = "deathgasp"
key_third_person = "deathgasps"
message = "seizes up and falls limp, their eyes dead and lifeless..."
message_robot = "shudders violently for a moment before falling still, its eyes slowly darkening."
message_AI = "lets out a flurry of sparks, its screen flickering as its systems slowly halt."
message_alien = "lets out a waning guttural screech, green blood bubbling from its maw..."
message_larva = "lets out a sickly hiss of air and falls limply to the floor..."
message_monkey = "lets out a faint chimper as it collapses and stops moving..."
message_simple = "stops moving..."
stat_allowed = UNCONSCIOUS
/datum/emote/living/deathgasp/run_emote(mob/user, params)
var/mob/living/simple_animal/S = user
if(istype(S) && S.deathmessage)
message_simple = S.deathmessage
. = ..()
message_simple = initial(message_simple)
if(. && user.deathsound)
if(isliving(user))
var/mob/living/L = user
if(!L.can_speak_vocal() || L.oxyloss >= 50)
return //stop the sound if oxyloss too high/cant speak
playsound(user, user.deathsound, 80, 1, 1)
/datum/emote/living/drool
key = "drool"
key_third_person = "drools"
message = "drools."
/datum/emote/living/faint
key = "faint"
key_third_person = "faints"
message = "faints."
/datum/emote/living/faint/run_emote(mob/user, params)
. = ..()
if(. && isliving(user))
var/mob/living/L = user
L.SetSleeping(200)
/datum/emote/living/flap
key = "flap"
key_third_person = "flaps"
message = "flaps their wings."
restraint_check = TRUE
var/wing_time = 20
/datum/emote/living/flap/run_emote(mob/user, params)
. = ..()
if(. && ishuman(user))
var/mob/living/carbon/human/H = user
var/open = FALSE
if(H.dna.features["wings"] != "None")
if("wingsopen" in H.dna.species.mutant_bodyparts)
open = TRUE
H.CloseWings()
else
H.OpenWings()
addtimer(CALLBACK(H, open ? /mob/living/carbon/human.proc/OpenWings : /mob/living/carbon/human.proc/CloseWings), wing_time)
/datum/emote/living/flap/aflap
key = "aflap"
key_third_person = "aflaps"
message = "flaps their wings ANGRILY!"
restraint_check = TRUE
wing_time = 10
/datum/emote/living/frown
key = "frown"
key_third_person = "frowns"
message = "frowns."
/datum/emote/living/gag
key = "gag"
key_third_person = "gags"
message = "gags."
emote_type = EMOTE_AUDIBLE
/datum/emote/living/gasp
key = "gasp"
key_third_person = "gasps"
message = "gasps!"
emote_type = EMOTE_AUDIBLE
stat_allowed = UNCONSCIOUS
/datum/emote/living/giggle
key = "giggle"
key_third_person = "giggles"
message = "giggles."
message_mime = "giggles silently!"
emote_type = EMOTE_AUDIBLE
/datum/emote/living/glare
key = "glare"
key_third_person = "glares"
message = "glares."
message_param = "glares at %t."
emote_type = EMOTE_AUDIBLE
/datum/emote/living/grin
key = "grin"
key_third_person = "grins"
message = "grins."
/datum/emote/living/groan
key = "groan"
key_third_person = "groans"
message = "groans!"
message_mime = "appears to groan!"
/datum/emote/living/grimace
key = "grimace"
key_third_person = "grimaces"
message = "grimaces."
/datum/emote/living/jump
key = "jump"
key_third_person = "jumps"
message = "jumps!"
restraint_check = TRUE
/datum/emote/living/kiss
key = "kiss"
key_third_person = "kisses"
message = "blows a kiss."
message_param = "blows a kiss to %t."
emote_type = EMOTE_AUDIBLE
/datum/emote/living/laugh
key = "laugh"
key_third_person = "laughs"
message = "laughs."
message_mime = "laughs silently!"
emote_type = EMOTE_AUDIBLE
/datum/emote/living/laugh/can_run_emote(mob/living/user, status_check = TRUE)
. = ..()
if(. && iscarbon(user))
var/mob/living/carbon/C = user
return !C.silent
/datum/emote/living/laugh/run_emote(mob/user, params)
. = ..()
if(. && ishuman(user))
var/mob/living/carbon/human/H = user
if(H.dna.species.id == "human" && (!H.mind || !H.mind.miming))
if(user.gender == FEMALE)
playsound(H, 'sound/voice/human/womanlaugh.ogg', 50, 1)
else
playsound(H, pick('sound/voice/human/manlaugh1.ogg', 'sound/voice/human/manlaugh2.ogg'), 50, 1)
/datum/emote/living/look
key = "look"
key_third_person = "looks"
message = "looks."
message_param = "looks at %t."
/datum/emote/living/nod
key = "nod"
key_third_person = "nods"
message = "nods."
message_param = "nods at %t."
/datum/emote/living/point
key = "point"
key_third_person = "points"
message = "points."
message_param = "points at %t."
restraint_check = TRUE
/datum/emote/living/point/run_emote(mob/user, params)
message_param = initial(message_param) // reset
if(ishuman(user))
var/mob/living/carbon/human/H = user
if(H.get_num_arms() == 0)
if(H.get_num_legs() != 0)
message_param = "tries to point at %t with a leg, <span class='userdanger'>falling down</span> in the process!"
H.Paralyze(20)
else
message_param = "<span class='userdanger'>bumps [user.p_their()] head on the ground</span> trying to motion towards %t."
H.adjustBrainLoss(5)
..()
/datum/emote/living/pout
key = "pout"
key_third_person = "pouts"
message = "pouts."
emote_type = EMOTE_AUDIBLE
/datum/emote/living/scream
key = "scream"
key_third_person = "screams"
message = "screams."
message_mime = "acts out a scream!"
emote_type = EMOTE_AUDIBLE
/datum/emote/living/scowl
key = "scowl"
key_third_person = "scowls"
message = "scowls."
emote_type = EMOTE_AUDIBLE
/datum/emote/living/shake
key = "shake"
key_third_person = "shakes"
message = "shakes their head."
emote_type = EMOTE_AUDIBLE
/datum/emote/living/shiver
key = "shiver"
key_third_person = "shiver"
message = "shivers."
emote_type = EMOTE_AUDIBLE
/datum/emote/living/sigh
key = "sigh"
key_third_person = "sighs"
message = "sighs."
emote_type = EMOTE_AUDIBLE
/datum/emote/living/sit
key = "sit"
key_third_person = "sits"
message = "sits down."
/datum/emote/living/smile
key = "smile"
key_third_person = "smiles"
message = "smiles."
/datum/emote/living/sneeze
key = "sneeze"
key_third_person = "sneezes"
message = "sneezes."
emote_type = EMOTE_AUDIBLE
/datum/emote/living/smug
key = "smug"
key_third_person = "smugs"
message = "grins smugly."
/datum/emote/living/sniff
key = "sniff"
key_third_person = "sniffs"
message = "sniffs."
emote_type = EMOTE_AUDIBLE
/datum/emote/living/snore
key = "snore"
key_third_person = "snores"
message = "snores."
message_mime = "sleeps soundly."
emote_type = EMOTE_AUDIBLE
stat_allowed = UNCONSCIOUS
/datum/emote/living/stare
key = "stare"
key_third_person = "stares"
message = "stares."
message_param = "stares at %t."
/datum/emote/living/strech
key = "stretch"
key_third_person = "stretches"
message = "stretches their arms."
/datum/emote/living/sulk
key = "sulk"
key_third_person = "sulks"
message = "sulks down sadly."
/datum/emote/living/surrender
key = "surrender"
key_third_person = "surrenders"
message = "puts their hands on their head and falls to the ground, they surrender!"
emote_type = EMOTE_AUDIBLE
/datum/emote/living/surrender/run_emote(mob/user, params)
. = ..()
if(. && isliving(user))
var/mob/living/L = user
L.Paralyze(200)
/datum/emote/living/sway
key = "sway"
key_third_person = "sways"
message = "sways around dizzily."
/datum/emote/living/tremble
key = "tremble"
key_third_person = "trembles"
message = "trembles in fear!"
/datum/emote/living/twitch
key = "twitch"
key_third_person = "twitches"
message = "twitches violently."
/datum/emote/living/twitch_s
key = "twitch_s"
message = "twitches."
/datum/emote/living/wave
key = "wave"
key_third_person = "waves"
message = "waves."
/datum/emote/living/whimper
key = "whimper"
key_third_person = "whimpers"
message = "whimpers."
message_mime = "appears hurt."
/datum/emote/living/wsmile
key = "wsmile"
key_third_person = "wsmiles"
message = "smiles weakly."
/datum/emote/living/yawn
key = "yawn"
key_third_person = "yawns"
message = "yawns."
emote_type = EMOTE_AUDIBLE
/datum/emote/living/custom
key = "me"
key_third_person = "custom"
message = null
/datum/emote/living/custom/proc/check_invalid(mob/user, input)
. = TRUE
if(copytext(input,1,5) == "says")
to_chat(user, "<span class='danger'>Invalid emote.</span>")
else if(copytext(input,1,9) == "exclaims")
to_chat(user, "<span class='danger'>Invalid emote.</span>")
else if(copytext(input,1,6) == "yells")
to_chat(user, "<span class='danger'>Invalid emote.</span>")
else if(copytext(input,1,5) == "asks")
to_chat(user, "<span class='danger'>Invalid emote.</span>")
else
. = FALSE
/datum/emote/living/custom/run_emote(mob/user, params, type_override = null)
if(is_banned_from(user.ckey, "Emote"))
to_chat(user, "You cannot send custom emotes (banned).")
return FALSE
else if(QDELETED(user))
return FALSE
else if(user.client && user.client.prefs.muted & MUTE_IC)
to_chat(user, "You cannot send IC messages (muted).")
return FALSE
else if(!params)
var/custom_emote = copytext(sanitize(input("Choose an emote to display.") as text|null), 1, MAX_MESSAGE_LEN)
if(custom_emote && !check_invalid(user, custom_emote))
var/type = input("Is this a visible or hearable emote?") as null|anything in list("Visible", "Hearable")
switch(type)
if("Visible")
emote_type = EMOTE_VISIBLE
if("Hearable")
emote_type = EMOTE_AUDIBLE
else
alert("Unable to use this emote, must be either hearable or visible.")
return
message = custom_emote
else
message = params
if(type_override)
emote_type = type_override
. = ..()
message = null
emote_type = EMOTE_VISIBLE
/datum/emote/living/custom/replace_pronoun(mob/user, message)
return message
/datum/emote/living/help
key = "help"
/datum/emote/living/help/run_emote(mob/user, params)
var/list/keys = list()
var/list/message = list("Available emotes, you can use them with say \"*emote\": ")
var/datum/emote/E
var/list/emote_list = E.emote_list
for(var/e in emote_list)
if(e in keys)
continue
E = emote_list[e]
if(E.can_run_emote(user, status_check = FALSE))
keys += E.key
keys = sortList(keys)
for(var/emote in keys)
if(LAZYLEN(message) > 1)
message += ", [emote]"
else
message += "[emote]"
message += "."
message = jointext(message, "")
to_chat(user, message)
/datum/emote/sound/beep
key = "beep"
key_third_person = "beeps"
message = "beeps."
message_param = "beeps at %t."
sound = 'sound/machines/twobeep.ogg'
/datum/emote/living/circle
key = "circle"
key_third_person = "circles"
restraint_check = TRUE
/datum/emote/living/circle/run_emote(mob/user, params)
. = ..()
var/obj/item/circlegame/N = new(user)
if(user.put_in_hands(N))
to_chat(user, "<span class='notice'>You make a circle with your hand.</span>")
else
qdel(N)
to_chat(user, "<span class='warning'>You don't have any free hands to make a circle with.</span>")
/datum/emote/living/slap
key = "slap"
key_third_person = "slaps"
restraint_check = TRUE
/datum/emote/living/slap/run_emote(mob/user, params)
. = ..()
if(!.)
return
var/obj/item/slapper/N = new(user)
if(user.put_in_hands(N))
to_chat(user, "<span class='notice'>You ready your slapping hand.</span>")
else
to_chat(user, "<span class='warning'>You're incapable of slapping in your current state.</span>")