/* -*- LPC -*- */ /* * $Locker: $ * $Id: alias.c,v 1.12 2001/06/16 05:01:27 presto Exp $ * $Log: alias.c,v $ * Revision 1.12 2001/06/16 05:01:27 presto * Put in a missing set of braces in query_player_alias * * Revision 1.11 2001/06/16 00:15:35 ceres * Fixed possible runtime in query_player_alias * * Revision 1.10 2001/03/11 01:42:01 ceres * Restricted alias lenghts * * Revision 1.9 1999/04/03 23:19:40 dragonkin * Fixed so that player aliases called "" can be removed by anyone. * * Revision 1.8 1999/03/10 09:44:56 pinkfish * Rip out the guts into the alias commands. * * Revision 1.7 1999/03/09 06:04:38 presto * Forcibly unlocked by pinkfish * * Revision 1.6 1999/02/08 14:15:04 wodan * changed add_actions to other things (/cmds stuff and add_command) * * Revision 1.5 1999/01/27 00:03:46 ceres * Forcibly unlocked by pinkfish * * Revision 1.4 1998/12/30 21:45:13 ceres * Fixed code for checking for colour sequences so it works properly. * * Revision 1.3 1998/12/30 21:42:27 olorin * Forcibly unlocked by ceres * * Revision 1.2 1998/02/21 19:05:47 pinkfish * Fix up the problem with the command queue and aliases. * * Revision 1.1 1998/01/06 04:54:05 ceres * Initial revision * */ /** * The alias control module for players. * @author Pinkfish */ #include <alias.h> #include <player.h> inherit "/global/history"; mapping aliases; nosave mapping doing_alias; protected void exec_alias(string verb, string args); protected string *expand_alias(string verb, string args); protected void set_doing_alias(string verb); protected int is_doing_alias(string verb); protected string *run_alias(string verb, string args); int remove_alias_thing(string); protected int alias(string); protected int edit_alias(string); /** * This method sets the alias to the new value. * @param name the name of the alias * @param value the value to set the alias too * @see query_player_alias() */ int add_player_alias(string name, mixed *value) { if (file_name(previous_object()) != ALIAS_CMD && file_name(previous_object()) != EDIT_ALIAS_CMD) { return 0; } if(name == "unalias" || name == "alias" || name == "ealias") return 0; aliases[name] = value[0..1023]; return 1; } /* add_player_alias() */ /** * This method returns the value of the specified alias. * @param name the name of the alias to query * @return the value of the alias * @see add_player_alias() */ mixed *query_player_alias(string name) { if(!mapp(aliases)) { aliases = ([ ]); return 0; } return copy(aliases[name]); } /* query_player_alias() */ /** * This method will remove the alias from the player. * @param name the name of the alias * @see query_player_alias() * @see add_player_alias() */ int remove_player_alias(string name) { if ((file_name(previous_object()) != UNALIAS_CMD) && name != "" && !this_player(1)->query_lord()) { printf("%O\n", file_name(previous_object())); return 0; } map_delete(aliases, name); return 1; } /* remove_player_alias() */ /** * This method adds all the alias commands onto the player. The commands * are 'alias', 'unalias', 'ealias', 'END_ALIAS' and the "*" pattern * expand the alias. */ void alias_commands() { add_command("END_ALIAS", "<string>", (:remove_alias_thing($4[0]):)); } /* alias_commands() */ /** * This method zaps all the current aliases defined. This can only be * called by a high lord. * @return 0 on failure and 1 on success */ int remove_all_aliases() { if (!this_player(1)->query_lord()) { write("You can't do that :)\n"); return 0; } aliases = ([ ]); return 1; } /* remove_all_aliases() */ /** * This method returns a complete list of all the aliases * defined on the player. This is the internal mapping so it will * be quite unreadable. * @see print_aliases() * @see /include/alias.h * @return the mapping of aliases */ mapping query_aliases() { return copy(aliases); } /* query_aliases() */ /** * This method tells us if the given name is an alias. * @param verb the verb to check * @return 1 if it is an alias, 0 if not */ int is_alias(string verb) { return aliases[verb] != 0; } /* is_alias() */ /** * This method runs the alias and executes all the commands in the * alias. You should probably use run_alias() instead. This calls * set_doing_alias() to setup blocking. * @param verb the name of the alias * @param args the arguments associated with the alias * @see run_alias() * @see set_doing_alias() */ protected void exec_alias(string verb, string args) { string *bing; string comm; bing = run_alias(verb, args); if (bing) { set_doing_alias(verb); foreach (comm in bing) { command(comm); } } } /* exec_alias() */ /** * Attempt to expand the alias. This will look up the alias and * see if it is defined. If it is, it will attempt to expand the * alias. This does not call set_doing_alias(). This will * return 0 if the alias does not exist, or the alias is already * being run. * @return the array if the alias was expanded, 0 if failed * @param verb the name of the alias to expand * @param args the arguments to the alias * @see exec_alias() * @see is_doing_alias() * @see set_doing_alias() * @see expand_alias() */ protected string *run_alias(string verb, string args) { if (!mapp(aliases)) { aliases = ([ ]); } if (!aliases[verb] || is_doing_alias(verb)) { return 0; } return expand_alias(verb, args); } /* run_alias() */ /** * This method checks to see if the player is doing the specified alias * already. * @param verb the verb to check * @see exec_alias() * @see set_doing_alias() */ protected int is_doing_alias(string verb) { if (!doing_alias) { doing_alias = ([ ]); } if (doing_alias[verb]) { return 1; } return 0; } /* is_doing_alias() */ /** * This method sets us as currently doing the given alias. * @param verb the alias to do * @see is_doing_alias() */ protected void set_doing_alias(string verb) { doing_alias[verb] = 1; in_alias_command++; } /* set_doing_alias() */ /** * This method expands the alias from the input string thingy. * @param verb the verb to expand * @param args the arguments to the verb * @see run_alias() */ protected string *expand_alias(string verb, string args) { int i; int num; string *bits; string line; mixed stuff; string *ret; /* Default expansion :) */ if (!aliases[verb]) { return ({ verb + " " + args }); } ret = ({ }); stuff = aliases[verb]; line = ""; if (!args) { args = ""; } bits = explode(verb + " " + args, " "); for (i = 0; i < sizeof(stuff); i++) { if (stringp(stuff[i])) { line += stuff[i]; } else { num = stuff[i] & ALIAS_MASK; switch (stuff[i] - num) { case NEW_LINE : ret += ({ line }); line = ""; break; case ALL_ARGS : line += args; break; case ONE_ARG : if (num < sizeof(bits)) { line += bits[num]; } break; case TO_ARG : line += implode(bits[1..num], " "); break; case FROM_ARG : line += implode(bits[num..100], " "); break; case ALL_ARG : i++; if (args == "") { line += stuff[i]; } else { line += args; } break; case ARG_THING : i++; if (num < sizeof(bits)) { line += bits[num]; } else { line += stuff[i]; } break; case ALL_IFARG : i++; if (args == "") { i += stuff[i]; } break; case IFARG_THING : i++; if (num >= sizeof(bits)) { i += stuff[i]; } break; case ELSE_THING : i++; i += stuff[i]; break; case CURR_LOC : i++; line += file_name(environment())+".c"; break; case END_IF : break; } } } if (line != "") { ret += ({ line }); } ret += ({ "END_ALIAS " + verb }); return ret[0..1023]; } /* expand_alias() */ /** * This is called to signify the end of an alias. This is needed * keep track of recursive aliases and such like. * @param verb the verb name to remove * @return always returns 1 * @see set_doing_alias() * @see is_doing_alias() */ int remove_alias_thing(string verb) { in_alias_command--; map_delete(doing_alias, verb); this_player()->adjust_time_left(-DEFAULT_TIME); return 1; } /* remove_alias_thing() */