Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
24 changes: 24 additions & 0 deletions code/__DEFINES/dcs/signals/signals_atom/signals_atom_movable.dm
Original file line number Diff line number Diff line change
Expand Up @@ -108,6 +108,30 @@
#define MOVABLE_SAY_QUOTE_MESSAGE_SPANS 2
#define MOVABLE_SAY_QUOTE_MESSAGE_MODS 3

/// Sent from /atom/movable/proc/say_mod() to pick a say verb
#define COMSIG_MOVABLE_SAY_MOD "movable_say_mod"
// Saymod handler categories
/// Say mod for strings that end in a question mark
#define SAY_MOD_ASK "ask"
/// Default saymod for no special handling
#define SAY_MOD_DEFAULT "say"
/// Say mod for strings that end in an exclamation mark
#define SAY_MOD_EXCLAIM "exclaim"
/// Say mod for strings that are sung
#define SAY_MOD_SING "sing"
/// Say mod for strings that are whispered
#define SAY_MOD_WHISPER "whisper"
/// Say mod for strings that are whispered, but also has two exclamations marks
#define SAY_MOD_WHISPER_YELL "whisper_yell"
/// Say mod for strings that have two exclamation marks
#define SAY_MOD_YELL "yell"

// Priorities for say mods
#define SAY_MOD_PRIORITY_DEFAULT -10
#define SAY_MOD_PRIORITY_LOW 0
#define SAY_MOD_PRIORITY_MEDIUM 10
#define SAY_MOD_PRIORITY_HIGH 20

/// From /datum/element/immerse/proc/add_submerge_overlay(): (visual_overlay)
#define COMSIG_MOVABLE_EDIT_UNIQUE_IMMERSE_OVERLAY "movable_edit_unique_submerge_overlay"
/// From base of area/Exited(): (area/left, direction)
Expand Down
7 changes: 7 additions & 0 deletions code/__DEFINES/say.dm
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,10 @@
#define MODE_WHISPER "whisper"
#define MODE_WHISPER_CRIT "whispercrit"

#define SHOUT_MODE "the type of shout"
#define MODE_YELL "yell" // !!
#define MODE_SHOUT "shout" // !

#define MODE_DEPARTMENT "department"
#define MODE_KEY_DEPARTMENT "h"
#define MODE_TOKEN_DEPARTMENT ":h"
Expand Down Expand Up @@ -132,3 +136,6 @@
///Defines for priorities for the bubble_icon_override comp
#define BUBBLE_ICON_PRIORITY_ACCESSORY 2
#define BUBBLE_ICON_PRIORITY_ORGAN 1

/// Applies a span to a message if the span is not null, otherwise just uses the text
#define CONDITIONAL_SPAN(span, text) (span ? "<span class='[span]'>[text]</span>" : text)
3 changes: 2 additions & 1 deletion code/__DEFINES/span.dm
Original file line number Diff line number Diff line change
Expand Up @@ -47,9 +47,10 @@
#define span_deadsay(str) ("<span class='deadsay'>" + str + "</span>")
#define span_deconversion_message(str) ("<span class='deconversion_message'>" + str + "</span>")
#define span_drone(str) ("<span class='drone'>" + str + "</span>")
#define span_emote(str) ("<span class='emote'>" + str + "</span>")
#define span_engradio(str) ("<span class='engradio'>" + str + "</span>")
#define span_extremelybig(str) ("<span class='extremelybig'>" + str + "</span>")
#define span_enteradio(str) ("<span class='enteradio'>" + str + "</span>")
#define span_extremelybig(str) ("<span class='extremelybig'>" + str + "</span>")
#define span_game_say(str) ("<span class='game say'>" + str + "</span>")
#define span_ghostalert(str) ("<span class='ghostalert'>" + str + "</span>")
#define span_green(str) ("<span class='green'>" + str + "</span>")
Expand Down
4 changes: 0 additions & 4 deletions code/datums/chatmessage.dm
Original file line number Diff line number Diff line change
Expand Up @@ -135,10 +135,6 @@
if (!ismob(target))
extra_classes |= "small"

// Why are you yelling?
if(copytext_char(text, -2) == "!!")
extra_classes |= SPAN_YELL

var/list/prefixes
var/chat_color_name_to_use

Expand Down
38 changes: 15 additions & 23 deletions code/datums/components/sign_language.dm
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,16 @@
var/regex/omissions = new ("\[!?\]", "g")
/// The action for toggling sign language.
var/datum/action/innate/sign_language/linked_action
/// Saymods for sign language users, overrides default saymods
var/static/list/say_mods = list(
SAY_MOD_ASK = "signs",
SAY_MOD_DEFAULT = "signs",
SAY_MOD_EXCLAIM = "signs",
SAY_MOD_SING = "rythmically signs",
SAY_MOD_WHISPER = "subtly signs",
SAY_MOD_WHISPER_YELL = "signs",
SAY_MOD_YELL = "emphatically signs",
)

/// Replace specific characters in the input string with periods.
/datum/component/sign_language/proc/sanitize_message(input)
Expand Down Expand Up @@ -67,18 +77,10 @@
SIGNAL_HANDLER

var/mob/living/carbon/carbon_parent = parent
var/obj/item/organ/tongue/tongue = carbon_parent.get_organ_slot(ORGAN_SLOT_TONGUE)
if(tongue)
tongue.temp_say_mod = "signs"
//this speech relies on hands, which we have our own way of garbling speech when they're occupied, so we can have this always on
ADD_TRAIT(carbon_parent, TRAIT_SPEAKS_CLEARLY, SPEAKING_FROM_HANDS)
carbon_parent.verb_ask = "signs"
carbon_parent.verb_exclaim = "signs"
carbon_parent.verb_whisper = "subtly signs"
carbon_parent.verb_sing = "rythmically signs"
carbon_parent.verb_yell = "emphatically signs"
carbon_parent.bubble_icon = "signlang"
RegisterSignal(carbon_parent, COMSIG_CARBON_GAIN_ORGAN, PROC_REF(on_added_organ))
RegisterSignal(carbon_parent, COMSIG_MOVABLE_SAY_MOD, PROC_REF(handle_saymod))
RegisterSignal(carbon_parent, COMSIG_MOB_TRY_SPEECH, PROC_REF(on_try_speech))
RegisterSignal(carbon_parent, COMSIG_LIVING_TREAT_MESSAGE, PROC_REF(on_treat_living_message))
RegisterSignal(carbon_parent, COMSIG_MOVABLE_USING_RADIO, PROC_REF(on_using_radio))
Expand All @@ -94,18 +96,10 @@
SIGNAL_HANDLER

var/mob/living/carbon/carbon_parent = parent
var/obj/item/organ/tongue/tongue = carbon_parent.get_organ_slot(ORGAN_SLOT_TONGUE)
if(tongue)
tongue.temp_say_mod = ""
REMOVE_TRAIT(carbon_parent, TRAIT_SPEAKS_CLEARLY, SPEAKING_FROM_HANDS)
carbon_parent.verb_ask = initial(carbon_parent.verb_ask)
carbon_parent.verb_exclaim = initial(carbon_parent.verb_exclaim)
carbon_parent.verb_whisper = initial(carbon_parent.verb_whisper)
carbon_parent.verb_sing = initial(carbon_parent.verb_sing)
carbon_parent.verb_yell = initial(carbon_parent.verb_yell)
carbon_parent.bubble_icon = initial(carbon_parent.bubble_icon)
UnregisterSignal(carbon_parent, list(
COMSIG_CARBON_GAIN_ORGAN,
COMSIG_MOVABLE_SAY_MOD,
COMSIG_MOB_TRY_SPEECH,
COMSIG_LIVING_TREAT_MESSAGE,
COMSIG_MOVABLE_USING_RADIO,
Expand All @@ -117,13 +111,11 @@

///Signal proc for [COMSIG_CARBON_GAIN_ORGAN]
///Applies the new say mod to any tongues that have appeared!
/datum/component/sign_language/proc/on_added_organ(mob/living/source, obj/item/organ/new_organ)
/datum/component/sign_language/proc/handle_saymod(mob/living/source, datum/saymod_selector/selector)
SIGNAL_HANDLER

if(!istype(new_organ, /obj/item/organ/tongue))
return
var/obj/item/organ/tongue/new_tongue = new_organ
new_tongue.temp_say_mod = "signs"
for(var/saymod_type, saymod_verb in say_mods)
selector.add_saymod(saymod_type, saymod_verb, SAY_MOD_PRIORITY_DEFAULT + 1)

/// Signal proc for [COMSIG_MOB_TRY_SPEECH]
/// Sign languagers can always speak regardless of they're mute (as long as they're not mimes)
Expand Down
35 changes: 25 additions & 10 deletions code/datums/emotes.dm
Original file line number Diff line number Diff line change
Expand Up @@ -62,6 +62,8 @@
var/can_message_change = FALSE
/// How long is the cooldown on the audio of the emote, if it has one?
var/audio_cooldown = 2 SECONDS
/// Range of the emotes messages
var/emote_range = DEFAULT_MESSAGE_RANGE

/datum/emote/New()
switch(mob_type_allowed_typecache)
Expand Down Expand Up @@ -136,37 +138,47 @@

// Emote doesn't get printed to chat, runechat only
if(emote_type & EMOTE_RUNECHAT)
for(var/mob/viewer as anything in viewers(user))
for(var/mob/viewer as anything in viewers(emote_range, user))
if(isnull(viewer.client))
continue
if(!is_important && viewer != user && (!is_visual || !is_audible))
if(is_audible && !viewer.can_hear())
continue
if(is_visual && viewer.is_blind())
continue

var/personal_msg = msg
var/distance_span = viewer.get_distance_based_span(get_dist(user, viewer) - (is_visual ? 4 : 2)) // -2 to -4 effective distance

if(user.runechat_prefs_check(viewer, EMOTE_MESSAGE))
viewer.create_chat_message(
speaker = user,
raw_message = msg,
runechat_flags = EMOTE_MESSAGE,
)
else if(is_important)
to_chat(viewer, "<span class='emote'><b>[user]</b> [msg]</span>")
to_chat(viewer, CONDITIONAL_SPAN(distance_span, span_emote("<b>[user]</b> [personal_msg]")))
else if(is_audible && is_visual)
viewer.show_message(
"<span class='emote'><b>[user]</b> [msg]</span>", MSG_AUDIBLE,
"<span class='emote'>You see how <b>[user]</b> [msg]</span>", MSG_VISUAL,
CONDITIONAL_SPAN(distance_span, span_emote("<b>[user]</b> [personal_msg]")), MSG_AUDIBLE,
CONDITIONAL_SPAN(distance_span, span_emote("You see how <b>[user]</b> [personal_msg]")), MSG_VISUAL,
)
else if(is_audible)
viewer.show_message("<span class='emote'><b>[user]</b> [msg]</span>", MSG_AUDIBLE)
viewer.show_message(CONDITIONAL_SPAN(distance_span, span_emote("<b>[user]</b> [personal_msg]")), MSG_AUDIBLE)
else if(is_visual)
viewer.show_message("<span class='emote'><b>[user]</b> [msg]</span>", MSG_VISUAL)
viewer.show_message(CONDITIONAL_SPAN(distance_span, span_emote("<b>[user]</b> [personal_msg]")), MSG_VISUAL)
return TRUE // Early exit so no dchat message

// The emote has some important information, and should always be shown to the user
else if(is_important)
for(var/mob/viewer as anything in viewers(user))
to_chat(viewer, "<span class='emote'><b>[user]</b> [msg]</span>")
for(var/mob/viewer as anything in viewers(emote_range, user))
if(isnull(viewer.client))
continue

var/personal_msg = msg
var/distance_span = viewer.get_distance_based_span(get_dist(user, viewer) - 4) // -4 effective distance

to_chat(viewer, CONDITIONAL_SPAN(distance_span, span_emote("<b>[user]</b> [personal_msg]")))
if(user.runechat_prefs_check(viewer, EMOTE_MESSAGE))
viewer.create_chat_message(
speaker = user,
Expand All @@ -178,23 +190,26 @@
else if(is_visual && is_audible)
user.audible_message(
message = msg,
deaf_message = "<span class='emote'>You see how <b>[user]</b> [msg]</span>",
deaf_message = span_emote("You see how <b>[user]</b> [msg]"),
self_message = msg,
audible_message_flags = EMOTE_MESSAGE|ALWAYS_SHOW_SELF_MESSAGE,
hearing_distance = emote_range,
)
// Emote is entirely audible, no visible component
else if(is_audible)
user.audible_message(
message = msg,
self_message = msg,
audible_message_flags = EMOTE_MESSAGE,
hearing_distance = emote_range,
)
// Emote is entirely visible, no audible component
else if(is_visual)
user.visible_message(
message = msg,
self_message = msg,
visible_message_flags = EMOTE_MESSAGE|ALWAYS_SHOW_SELF_MESSAGE,
vision_distance = emote_range
)
else
CRASH("Emote [type] has no valid emote type set!")
Expand All @@ -206,7 +221,7 @@
continue
if(!(get_chat_toggles(ghost.client) & CHAT_GHOSTSIGHT))
continue
to_chat(ghost, "<span class='emote'>[FOLLOW_LINK(ghost, user)] [dchatmsg]</span>")
to_chat(ghost, span_emote("[FOLLOW_LINK(ghost, user)] [dchatmsg]"))

return TRUE

Expand Down
15 changes: 15 additions & 0 deletions code/datums/status_effects/debuffs/speech_debuffs.dm
Original file line number Diff line number Diff line change
Expand Up @@ -16,10 +16,12 @@

/datum/status_effect/speech/on_apply()
RegisterSignal(owner, COMSIG_LIVING_TREAT_MESSAGE, PROC_REF(handle_message))
RegisterSignal(owner, COMSIG_MOVABLE_SAY_MOD, PROC_REF(handle_saymod))
return TRUE

/datum/status_effect/speech/on_remove()
UnregisterSignal(owner, COMSIG_LIVING_TREAT_MESSAGE)
UnregisterSignal(owner, COMSIG_MOVABLE_SAY_MOD)

/**
* Signal proc for [COMSIG_LIVING_TREAT_MESSAGE]
Expand Down Expand Up @@ -74,6 +76,10 @@
stack_trace("[type] didn't implement apply_speech.")
return original_char

/datum/status_effect/speech/proc/handle_saymod(datum/source, datum/saymod_selector/selector)
SIGNAL_HANDLER
return

/datum/status_effect/speech/stutter
id = "stutter"
make_tts_message_original = TRUE
Expand Down Expand Up @@ -117,6 +123,9 @@

return some_char

/datum/status_effect/speech/stutter/handle_saymod(datum/source, datum/saymod_selector/selector)
selector.add_saymod(SAY_MOD_DEFAULT, HAS_TRAIT(owner, TRAIT_SIGN_LANG) ? "shakily signs" : "stammers", SAY_MOD_PRIORITY_MEDIUM)

/datum/status_effect/speech/stutter/anxiety
id = "anxiety_stutter"
stutter_prob = 5
Expand All @@ -133,6 +142,9 @@
stutter_prob = clamp(host_quirk?.calculate_mood_mod() * 0.5, 5, 50)
return ..()

/datum/status_effect/speech/stutter/anxiety/handle_saymod(datum/source, datum/saymod_selector/selector)
return

/datum/status_effect/speech/stutter/derpspeech
id = "derp_stutter"
/// The probability of making our message entirely uppercase + adding exclamations
Expand Down Expand Up @@ -172,6 +184,9 @@
// Otherwise just return and don't call parent, we already modified our speech
return

/datum/status_effect/speech/stutter/derpspeech/handle_saymod(datum/source, datum/saymod_selector/selector)
selector.add_saymod(SAY_MOD_DEFAULT, HAS_TRAIT(owner, TRAIT_SIGN_LANG) ? "incoherently signs" : "gibbers", SAY_MOD_PRIORITY_MEDIUM + 1)

/datum/status_effect/speech/slurring
/// The chance that any given character in a message will be replaced with a common character
var/common_prob = 25
Expand Down
6 changes: 0 additions & 6 deletions code/game/machinery/requests_console.dm
Original file line number Diff line number Diff line change
Expand Up @@ -314,12 +314,6 @@ GLOBAL_LIST_EMPTY(req_console_ckey_departments)

return data

/obj/machinery/requests_console/say_mod(input, list/message_mods = list())
if(spantext_char(input, "!", -3))
return "blares"
else
. = ..()

/// Turns the emergency console back to its normal sprite once the emergency has timed out
/obj/machinery/requests_console/proc/clear_emergency()
emergency = null
Expand Down
1 change: 1 addition & 0 deletions code/game/objects/items/devices/megaphone.dm
Original file line number Diff line number Diff line change
Expand Up @@ -39,6 +39,7 @@
else
playsound(loc, 'sound/items/megaphone.ogg', 100, FALSE, TRUE)
spamcheck = world.time + 50
speech_args[SPEECH_MODS][MODE_SHOUT] = MODE_YELL
speech_args[SPEECH_SPANS] |= voicespan

/obj/item/megaphone/emag_act(mob/user, obj/item/card/emag/emag_card)
Expand Down
Loading
Loading