Whisper overhaul

This commit overhauls whisper to work at a /mob/living level
This means that all mobs will now be able to whisper properly, not just
humans. Exception; Drones will just say() what they attempt to whisper.
Also fixes autohiss not working for whispering.
This commit is contained in:
Tigercat2000
2015-09-20 19:23:30 -07:00
parent 7a288c52f8
commit 7db714f2ef
6 changed files with 156 additions and 145 deletions
+1 -1
View File
@@ -73,7 +73,7 @@
/datum/species/proc/handle_autohiss(message, datum/language/lang, mode)
if(!autohiss_basic_map)
return message
if(autohiss_exempt && (lang.name in autohiss_exempt))
if(autohiss_exempt && (lang && (lang.name in autohiss_exempt)))
return message
var/map = autohiss_basic_map.Copy()
+13 -138
View File
@@ -2,150 +2,25 @@
/mob/living/carbon/human/whisper(message as text)
var/alt_name = ""
message = trim_strip_html_properly(message)
log_whisper("[src.name]/[src.key] : [message]")
if (src.client)
if (src.client.prefs.muted & MUTE_IC)
src << "\red You cannot whisper (muted)."
return
if (src.client.handle_spam_prevention(message,MUTE_IC))
return
if (src.stat == 2)
return src.say_dead(message)
if (src.stat)
return
if(name != GetVoice())
alt_name = "(as [get_id_name("Unknown")])"
message = trim_strip_html_properly(message) //bit of duplicate code, acceptable because the workaround would be annoying
//parse the language code and consume it
var/datum/language/speaking = parse_language(message)
if (speaking)
message = copytext(message,2+length(speaking.key))
whisper_say(message, speaking, alt_name)
//This is used by both the whisper verb and human/say() to handle whispering
/mob/living/carbon/human/proc/whisper_say(var/message, var/datum/language/speaking = null, var/alt_name="", var/verb="whispers")
if (istype(src.wear_mask, /obj/item/clothing/mask/muzzle))
src << "<span class='danger'>You're muzzled and cannot speak!</span>"
return
var/message_range = 1
var/eavesdropping_range = 2
var/watching_range = 5
var/italics = 1
var/not_heard //the message displayed to people who could not hear the whispering
if (speaking)
if (speaking.whisper_verb)
verb = speaking.whisper_verb
not_heard = "[verb] something"
else
var/adverb = pick("quietly", "softly")
verb = "[speaking.speech_verb] [adverb]"
not_heard = "[speaking.speech_verb] something [adverb]"
if(speaking)
message = copytext(message, 2 + length(speaking.key))
else
not_heard = "[verb] something" //TODO get rid of the null language and just prevent speech if language is null
speaking = get_default_language()
message = capitalize(trim(message))
// This is broadcast to all mobs with the language,
// irrespective of distance or anything else.
if(speaking && (speaking.flags & HIVEMIND))
speaking.broadcast(src,trim(message))
return 1
if(speech_problem_flag)
var/list/handle_r = handle_speech_problems(message)
message = handle_r[1]
verb = handle_r[2]
if(verb == "yells loudly")
verb = "slurs emphatically"
else
var/adverb = pick("quietly", "softly")
verb = "[verb] [adverb]"
message = trim_left(message)
message = handle_autohiss(message, speaking)
speech_problem_flag = handle_r[3]
if(!message || message=="")
return
//looks like this only appears in whisper. Should it be elsewhere as well? Maybe handle_speech_problems?
/*var/voice_sub
for(var/obj/item/gear in list(wear_mask,wear_suit,head))
if(!gear)
continue
var/obj/item/voice_changer/changer = locate() in gear
if(changer && changer.active && changer.voice)
voice_sub = changer.voice
if(voice_sub == "Unknown")
if(copytext(message, 1, 2) != "*")
var/list/temp_message = text2list(message, " ")
var/list/pick_list = list()
for(var/i = 1, i <= temp_message.len, i++)
pick_list += i
for(var/i=1, i <= abs(temp_message.len/3), i++)
var/H = pick(pick_list)
if(findtext(temp_message[H], "*") || findtext(temp_message[H], ";") || findtext(temp_message[H], ":")) continue
temp_message[H] = ninjaspeak(temp_message[H])
pick_list -= H
message = list2text(temp_message, " ")
message = replacetext(message, "o", "")
message = replacetext(message, "p", "")
message = replacetext(message, "l", "")
message = replacetext(message, "s", "")
message = replacetext(message, "u", "")
message = replacetext(message, "b", "")*/
var/list/listening = hearers(message_range, src)
listening |= src
//ghosts
for (var/mob/M in dead_mob_list) //does this include players who joined as observers as well?
if (!(M.client))
continue
if(M.stat == DEAD && M.client && (M.client.prefs.toggles & CHAT_GHOSTEARS))
listening |= M
//Pass whispers on to anything inside the immediate listeners.
for(var/mob/L in listening)
for(var/mob/C in L.contents)
if(istype(C,/mob/living))
listening += C
//pass on the message to objects that can hear us.
for (var/obj/O in view(message_range, src))
spawn (0)
if (O)
O.hear_talk(src, message, verb, speaking)
var/list/eavesdropping = hearers(eavesdropping_range, src)
eavesdropping -= src
eavesdropping -= listening
var/list/watching = hearers(watching_range, src)
watching -= src
watching -= listening
watching -= eavesdropping
//now mobs
var/speech_bubble_test = say_test(message)
var/image/speech_bubble = image('icons/mob/talk.dmi',src,"h[speech_bubble_test]")
spawn(30) qdel(speech_bubble)
for(var/mob/M in listening)
M << speech_bubble
M.hear_say(message, verb, speaking, alt_name, italics, src)
if (eavesdropping.len)
var/new_message = stars(message) //hopefully passing the message twice through stars() won't hurt... I guess if you already don't understand the language, when they speak it too quietly to hear normally you would be able to catch even less.
for(var/mob/M in eavesdropping)
M << speech_bubble
M.hear_say(new_message, verb, speaking, alt_name, italics, src)
if (watching.len)
var/rendered = "<span class='game say'><span class='name'>[src.name]</span> [not_heard].</span>"
for (var/mob/M in watching)
M.show_message(rendered, 2)
whisper_say(message, speaking, alt_name)
+128 -1
View File
@@ -94,6 +94,10 @@ proc/get_radio_key_from_channel(var/channel)
return returns
/mob/living/proc/handle_message_mode(message_mode, message, verb, speaking, used_radios, alt_name)
switch(message_mode)
if("whisper") //all mobs can whisper by default
whisper_say(message, speaking, alt_name)
return 1
return 0
/mob/living/proc/handle_speech_sound()
@@ -291,4 +295,127 @@ proc/get_radio_key_from_channel(var/channel)
else //everything else failed, emote is probably invalid
if(act == "help") return //except help, because help is handled individually
src << "\blue Unusable emote '[act]'. Say *help for a list."
src << "\blue Unusable emote '[act]'. Say *help for a list."
/mob/living/whisper(message as text)
message = trim_strip_html_properly(message)
//parse the language code and consume it
var/datum/language/speaking = parse_language(message)
if(speaking)
message = copytext(message, 2 + length(speaking.key))
else
speaking = get_default_language()
// This is broadcast to all mobs with the language,
// irrespective of distance or anything else.
if(speaking && (speaking.flags & HIVEMIND))
speaking.broadcast(src,trim(message))
return 1
message = trim_left(message)
message = handle_autohiss(message, speaking)
whisper_say(message, speaking)
/mob/living/proc/whisper_say(var/message, var/datum/language/speaking = null, var/alt_name="", var/verb="whispers")
if(client)
if(client.prefs.muted & MUTE_IC)
src << "<span class='danger'>You cannot speak in IC (Muted).</span>"
return
if(stat)
if(stat == 2)
return say_dead(message)
return
if(is_muzzled())
src << "<span class='danger'>You're muzzled and cannot speak!</span>"
return
var/message_range = 1
var/eavesdropping_range = 2
var/watching_range = 5
var/italics = 1
var/not_heard //the message displayed to people who could not hear the whispering
if(speaking)
if(speaking.whisper_verb)
verb = speaking.whisper_verb
not_heard = "[verb] something"
else
var/adverb = pick("quietly", "softly")
verb = "[speaking.speech_verb] [adverb]"
not_heard = "[speaking.speech_verb] something [adverb]"
else
not_heard = "[verb] something" //TODO get rid of the null language and just prevent speech if language is null
message = trim(message)
var/speech_problem_flag = 0
var/list/handle_s = handle_speech_problems(message, verb)
message = handle_s[1]
verb = handle_s[2]
speech_problem_flag = handle_s[3]
if(verb == "yells loudly")
verb = "slurs emphatically"
else if(speech_problem_flag)
var/adverb = pick("quietly", "softly")
verb = "[verb] [adverb]"
if(!message || message=="")
return
var/list/listening = hearers(message_range, src)
listening |= src
//ghosts
for(var/mob/M in dead_mob_list) //does this include players who joined as observers as well?
if(!M.client)
continue
if(M.stat == DEAD && M.client && (M.client.prefs.toggles & CHAT_GHOSTEARS))
listening |= M
//Pass whispers on to anything inside the immediate listeners.
for(var/mob/L in listening)
for(var/mob/C in L.contents)
if(istype(C,/mob/living))
listening += C
//pass on the message to objects that can hear us.
for(var/obj/O in view(message_range, src))
spawn(0)
if(O)
O.hear_talk(src, message, verb, speaking)
var/list/eavesdropping = hearers(eavesdropping_range, src)
eavesdropping -= src
eavesdropping -= listening
var/list/watching = hearers(watching_range, src)
watching -= src
watching -= listening
watching -= eavesdropping
//now mobs
var/speech_bubble_test = say_test(message)
var/image/speech_bubble = image('icons/mob/talk.dmi',src,"h[speech_bubble_test]")
spawn(30) qdel(speech_bubble)
for(var/mob/M in listening)
M << speech_bubble
M.hear_say(message, verb, speaking, alt_name, italics, src)
if(eavesdropping.len)
var/new_message = stars(message) //hopefully passing the message twice through stars() won't hurt... I guess if you already don't understand the language, when they speak it too quietly to hear normally you would be able to catch even less.
for(var/mob/M in eavesdropping)
M << speech_bubble
M.hear_say(new_message, verb, speaking, alt_name, italics, src)
if(watching.len)
var/rendered = "<span class='game say'><span class='name'>[src.name]</span> [not_heard].</span>"
for (var/mob/M in watching)
M.show_message(rendered, 2)
log_whisper("[src.name]/[src.key] : [message]")
return 1
@@ -37,4 +37,8 @@
else if(M.stat == 2 && M.client.prefs.toggles & CHAT_GHOSTEARS)
if(M.client) M << "<b>[src]</b> transmits, \"[message]\""
return 1
return ..(message, 0)
return ..(message, 0)
/mob/living/silicon/robot/drone/whisper_say(var/message, var/datum/language/speaking = null, var/alt_name="", var/verb="whispers")
say(message) //drones do not get to whisper, only speak normally
return 1
+8 -3
View File
@@ -1,8 +1,11 @@
/mob/living/silicon/handle_message_mode(message_mode, message, verb, speaking, used_radios, alt_name)
log_say("[key_name(src)] : [message]")
if(..())
return 1
/mob/living/silicon/robot/handle_message_mode(message_mode, message, verb, speaking, used_radios, alt_name)
..()
if(..())
return 1
if(message_mode)
if(!is_component_functioning("radio"))
src << "<span class='warning'>Your radio isn't functional at this time.</span>"
@@ -12,7 +15,8 @@
return radio.talk_into(src,message,message_mode,verb,speaking)
/mob/living/silicon/ai/handle_message_mode(message_mode, message, verb, speaking, used_radios, alt_name)
..()
if(..())
return 1
if(message_mode == "department")
return holopad_talk(message, verb, speaking)
else if(message_mode)
@@ -24,7 +28,8 @@
return aiRadio.talk_into(src,message,message_mode,verb,speaking)
/mob/living/silicon/pai/handle_message_mode(message_mode, message, verb, speaking, used_radios, alt_name)
..()
if(..())
return 1
if(message_mode)
if(message_mode == "general")
message_mode = null
+1 -1
View File
@@ -2,7 +2,7 @@
/mob/proc/say()
return
/mob/verb/whisper()
/mob/verb/whisper(message as text)
set name = "Whisper"
set category = "IC"
return