#include <drinks.h>
#include <language.h>
#include <player.h>
#define TELL_REPLY_PROPERTY "tell reply list"
/* Behaviour when we encounter ear muffs in player */
#define CUT_THOUGH_PROPERTY "cut earmuffed tells"
#define FAIL_DONT_ASK 0
#define ASK 1
#define CUT_DONT_ASK 2
inherit COMMAND_BASE;
inherit SPEECH_BASE;
/* This function handles tells from cres to players who
* have tells ear muffed. */
void delayed_tell( string yesno, object *recicipients, string message,
string language );
#ifdef USE_SMILEYS
string *two_smileys = ({":)", ":(", ":P", ":p", ":b", ";)",
";(", ";P", ";p", ";b", "=)", "=("});
string *three_smileys = ({":-)", ":-(", ":-P", ":-p", ":-b",
";-)", ";-(", ";-P", ";-p", ";-b", ":o)", ":o(", ":oP",
":op", ":ob", ";o)", ";o(", ";oP", ";op", ";ob", "=-)",
"=-(", "=o)", "=o("});
#endif
int cmd( string arg, mixed thing, int silent ) {
string word;
string mangle;
string lang;
string words;
string emotion;
#ifdef USE_SMILEYS
string smiley;
string smiley_words;
#endif
string them_mess;
string temp;
string me_mess;
string *ok_string;
object *obs;
object *net_dead;
object *multiple_earmuffed;
object *cannot_see;
object *ok;
object *fail;
object *earmuffed; /* These people have ear muffed tells */
mixed busy;
/* Don't allow someone with tells ear muffed to use tell. */
if( TP->check_earmuffs("tell") ) {
add_failed_mess( "You have tells ear muffed.\n" );
/* return 0 gave us two messages to player. */
return -1;
}
emotion = "";
if (pointerp(thing)) {
words = arg;
if ( function_exists( "trap_tell", environment( TP ) ) &&
member_array(this_object(), previous_object(-1)) == -1) {
return (int)environment( TP )->trap_tell( words, thing, 0 );
}
} else if ( !objectp( thing ) ) {
if ( !arg || sscanf( arg, "%s %s", word, words ) != 2 ) {
return 0;
}
word = lower_case( word );
word = (string)TP->expand_nickname( word );
if(sizeof(thing = explode(word, ",")) == 1)
thing = find_player( word );
else {
thing = map(thing, (:find_player:));
thing -= ({0});
}
if ( !thing ) {
if ( creatorp(TP) && sscanf( word, "%*s@%*s" ) == 2 ) {
"/net/daemon/out_tell"->do_tell( word+" "+words );
return 1;
}
add_failed_mess( capitalize( word ) +" is not logged in.\n" );
return 0;
}
if ( environment( TP ) ) {
if ( function_exists( "trap_tell", environment( TP ) ) &&
member_array(this_object(), previous_object(-1)) == -1) {
return stringp(thing)?
environment( TP )->trap_tell( words, ({ thing }), 0 ):
environment( TP )->trap_tell( words, thing, 0 );
}
}
} else {
words = arg;
}
if (!pointerp(thing)) {
obs = ({ thing });
} else {
obs = thing;
}
obs -= ({ this_player() });
if ( !sizeof(obs) ) {
add_failed_mess( "Talking to yourself again. I don't know.\n" );
return 0;
}
if (sizeof(obs) > 20) {
add_failed_mess("You can only tell up to 20 people a message.\n");
return 0;
}
fail = this_player()->query_ignoring(obs);
if ( sizeof( fail ) ) {
write( "You are currently ignoring " +
query_multiple_short( fail ) + ", so " +
(sizeof(fail) > 1 ? " they" : fail[0]->query_pronoun()) +
" couldn't reply anyway.\n" );
obs -= fail;
if ( !sizeof( obs ) ) {
return 1;
}
}
fail = this_player()->query_ignored_by(obs);
if ( sizeof( fail ) ) {
if (!creatorp(TP)) {
write( "You are currently being ignored by " +
query_multiple_short( fail ) + ", so " +
" you cannot tell them anything.\n");
obs -= fail;
if ( !sizeof( obs ) ) {
return 1;
}
} else {
write("Warning! " + query_multiple_short(fail) +
" have you on ignore.\n");
}
}
if ( !creatorp(TP) && ( TP->adjust_sp( -TELL_COST ) < 0 ) ) {
return notify_fail( NO_POWER );
}
lang = (string)TP->query_current_language();
if ( !LANGUAGE_HAND->query_language_spoken( lang ) ) {
return notify_fail( capitalize( lang ) +
" is not a spoken language.\n" );
}
if ( !LANGUAGE_HAND->query_language_distance( lang ) ) {
return notify_fail( capitalize( lang ) +
" is not able to be spoken at a distance.\n" );
}
// This is so small tells don't error.
#ifdef USE_SMILEYS
if(sizeof(words) >= 3) {
if(member_array(words[<3..], three_smileys) != -1) {
smiley = words[<3..];
} else if(member_array(words[<2..], two_smileys) != -1) {
smiley = words[<2..];
}
} else if(member_array(words, three_smileys) != -1) {
smiley = words;
} else if(member_array(words, two_smileys) != -1) {
smiley = words;
}
#endif
word = query_word_type(words, "");
if(word != "") {
word = " "+word+"ing";
}
#ifdef USE_SMILEYS
if(smiley) {
// This is so we don't get errors with people telling each
// other smileys on their own.
if(sizeof(words) > 3) {
smiley_words = words[0..<sizeof(smiley) + 1];
} else {
smiley_words = words;
}
word = query_word_type(smiley_words, "");
if(word != "") {
word = " "+word+"ing";
}
}
switch(smiley) {
case ":)" :
case ":-)" :
case ":o)" :
emotion = " happily";
break;
case ":(" :
case ":-(" :
case ":o(" :
emotion = " sadly";
break;
case "=)" :
case "=-)" :
case "=o)" :
emotion = " innocently";
break;
case "=(" :
case "=-(" :
case "=o(" :
emotion = " tearfully";
break;
case ";(" :
case ";-(" :
case ";o(" :
emotion = " angrilly";
break;
case ";)" :
case ";-)" :
case ";o)" :
emotion = " mischieviously";
break;
case ":P" :
case ":-P" :
case ":oP" :
case ":p" :
case ":-p" :
case ":op" :
case ":b" :
case ":-b" :
case ":ob" :
emotion = " insanely";
break;
case "=P" :
case "=-P" :
case "=oP" :
case "=p" :
case "=-p" :
case "=op" :
case "=b" :
case "=-b" :
case "=ob" :
emotion = " cheekily";
break;
case ";P" :
case ";-P" :
case ";oP" :
case ";b" :
case ";-b" :
case ";ob" :
case ";p" :
case ";-p" :
case ";op" :
emotion = " evilly";
break;
default :
emotion = "";
}
#endif
if ( TP->query_volume( D_ALCOHOL ) ) {
words = drunk_speech( words );
}
// General speech modifications (curses, etc)
mangle = TP->mangle_speech( words );
if ( stringp( mangle ) ) {
words = mangle;
}
if ( environment( TP ) ) {
if ( function_exists( "mangle_tell", environment( TP ) ) ) {
words = (string)environment( TP )->mangle_tell( words, thing, 0 );
}
}
if ( word != " asking" ) {
me_mess = "tell";
} else {
me_mess = "ask";
word = "";
}
net_dead = ({ });
multiple_earmuffed = ({ });
earmuffed = ({ });
ok = ({ });
cannot_see = ({ });
foreach (thing in obs) {
if (sizeof(obs) > 1 && thing->check_earmuffs("multiple-tell")) {
multiple_earmuffed += ({ thing });
} else if( thing->check_earmuffs( "tell" ) ) {
if( creatorp(TP) &&
TP->query_property( CUT_THOUGH_PROPERTY ) == CUT_DONT_ASK ) {
/* A cre that doesn't care about ear muffs, so we warn the
* cre and player, but don't add to the ear muffed array. */
write( "You cut through the ear muffs of "+
thing->the_short() +".\n" );
tell_object( thing, TP->the_short()
+" cuts through your ear muffs.\n" );
/* Add to array of people who get the message. */
ok += ({ thing });
} else {
/* Ok, someone cares, so we add to earmuffed array. */
earmuffed += ({ thing });
}
} else if (!this_player()->query_invis() ||
reference_allowed(this_player(), thing)) {
/* All is hoopy. */
ok += ({ thing });
} else {
cannot_see += ({ thing });
ok += ({ thing });
}
}
temp = emotion;
ok_string = map(ok, (: $1->query_name() :)) +
({ this_player()->query_name() });
foreach (thing in ok) {
if(thing->query_earmuffs("emoticon")) {
emotion = "";
}
words = replace(words, "%^", " ");
thing->event_person_tell( TP, capitalize( (string)TP->short(0, 0) ) +
" " + me_mess + "s "+
query_multiple_short(ok - ({ thing }) + ({ "you" })) + emotion +
word + ": ", words, lang );
// Lasts for 15 minutes.
thing->add_property(TELL_REPLY_PROPERTY, ok_string, 15 * 60);
if (!interactive(thing) && userp(thing)) {
net_dead += ({ thing });
}
}
if ( !silent ) {
if ( lang != "common" ) {
word += " in "+ lang;
}
if ( sizeof(net_dead)) {
write("Warning: "+query_multiple_short(
map(net_dead, (: $1->query_cap_name() :)))+
" "+ (sizeof(net_dead)>1?"are":"is")+" net dead.\n" );
}
if (sizeof(multiple_earmuffed)) {
write(capitalize( query_multiple_short(multiple_earmuffed)) +
(sizeof(multiple_earmuffed) > 1?" have ":" has ")+
"multiple tells ear muffed.\n");
}
if( sizeof( earmuffed ) ) {
write(capitalize( query_multiple_short(earmuffed)) +
(sizeof(earmuffed) > 1?" have ":" has ")+
"tells ear muffed.\n");
if( creatorp(TP) &&
TP->query_property( CUT_THOUGH_PROPERTY ) != FAIL_DONT_ASK ) {
write( "Cut through ear muffs? (y/n) " );
input_to( (: delayed_tell :), earmuffed, words, lang );
}
}
emotion = temp;
if(this_player()->query_earmuffs("emoticon")) {
emotion = "";
}
busy = this_player()->query_busy();
if (busy == 1) {
write("Warning! You have your busy flag on.\n");
} else if (pointerp(busy) && sizeof(ok - busy)) {
write("Warning! You are currently set as busy with " +
query_multiple_short(busy) + ".\n");
}
if (sizeof(cannot_see)) {
write("Warning! " + query_multiple_short(cannot_see) +
" cannot see you and will not be able to respond.\n");
}
if( sizeof( ok ) ) {
them_mess =
TP->convert_message(capitalize( query_multiple_short(ok)));
my_mess("You "+ me_mess +" "+ them_mess +
emotion + word+": ", words);
emotion = temp;
if(this_player()->query_earmuffs("emoticon")) {
emotion = "";
}
TP->add_tell_history( "You " + me_mess + " "+ them_mess + word +
emotion+ ": ", words );
} else if( creatorp(TP) && !sizeof( earmuffed ) ) {
/* We don't want this message *and* the one about cutting
* through ear muffs, so if the player is a cre and has
* already gotten the (y/n) stuff, we skip this. */
add_failed_mess( "It seems no one was listening.\n" );
/* return 0 gave two messages. */
return -1;
}
}
TP->adjust_time_left( -5 );
return 1;
} /* cmd() */
int reply_cmd(string mess) {
string *rep;
object *obs;
rep = this_player()->query_property(TELL_REPLY_PROPERTY);
if (!rep) {
add_failed_mess("No one has told you anything in the last 15 minutes.\n");
return 0;
}
obs = map(rep, (: find_living($1) :)) - ({ 0 });
if (!sizeof(obs)) {
add_failed_mess("None of " + query_multiple_short(rep) +
" are currenttly online.\n");
return 0;
}
return cmd(mess, obs, 0);
} /* reply_cmd() */
mixed *query_patterns() {
return ({ "<string'message'>", (: reply_cmd($4[0]) :) });
} /* query_patterns() */
/*
* Tells from cres to ear muffed players.
* All emoticon and "asks you" or "exclaims" stuff removed.
*/
void delayed_tell( string yesno, object *recicipients, string message,
string language ) {
object ob, *netdead;
int disappeared;
/*
* Tried to keep us out
* But nothing stops creators
* Except alter.net
*/
/* Did they really want to break through? */
if( !( yesno == "yes" || yesno == "y" ) ) {
write("Ok, tell aborted.\n");
return;
}
netdead = ({ });
foreach( ob in recicipients ) {
if( !ob ) {
disappeared++;
recicipients -= ({ ob });
} else {
if( !interactive( ob ) )
netdead += ({ ob });
/* Tell them even if they are net dead - it'll end up
* in their tell history..? */
message = replace(message, "%^", " ");
ob->event_person_tell( TP, capitalize( TP->query_name() ) +
" cuts through your ear muffs and tells "
+ query_multiple_short( recicipients - ({ ob }) + ({ "you" }) )
+": ", message, language );
}
}
if( sizeof( netdead ) )
write( "Warning: "+ query_multiple_short( netdead ) +
( sizeof( netdead ) > 1 ? " is": " are" ) +" net dead.\n" );
/* There's no way to get their names now, so we just tell the cre
* how many recicipients disappeared. */
if( disappeared )
write( "It seems "+ disappeared +" person"+
( disappeared > 1 ? "s have" : " has" )
+" disappeared.\n" );
/* Ooops - no one left to talk to! */
if( !sizeof( recicipients ) ) {
write( "No one wanted to stay around long enough "
"to hear what you had to say.\n" );
return;
}
my_mess( "You tell "+
TP->convert_message( query_multiple_short( recicipients ) )
+": ", message );
TP->add_tell_history( "You cut through ear muffs and tell "+
TP->convert_message( capitalize(
query_multiple_short( recicipients ) ) )
+": ", message );
return;
} /* delayed_tell() */