/** * This file contains all the start position related code. It sets up * and controls the start location of the player. This was split off from * the main player code by Pinkfish in April 1998. * @see /global/player.c * @author Pinkfish */ inherit "/std/basic/virtual_quit_control"; #include <playerinfo.h> #include <config.h> #define MULTIPLAYER "/handlers/multiplayer" private int *saved_co_ords; private string last_pos; private string *starts; protected void inform_entered_game(); string query_name(); string query_cap_name(); varargs int move(string pos, string messin, string messout); void create() { starts = ({ }); } /* create() */ /** * This method returns the co-ordinates of the room in which the player * last saved. * @see check_last_pos() * @see move_to_start() * @see query_start_pos() * @return the last saved co-ordinates */ int *query_saved_co_ords() { return saved_co_ords; } /** * This method sets the current start location. * @param last_pos the start location */ protected void set_last_pos(string pos) { if( pos[0..4] != "/room") last_pos = pos; } /* set_last_pos() */ /** * This method returns the starting location of the player. This the * location they will start at if the saved position does not work * for some reason. * @return the start position to use * @see query_starts() * @see add_start() * @see remove_start() * @see reset_starts() * @see set_start_location() */ string query_start_pos() { string tmp; object ob; starts -= ({ 0 }); if( creatorp(TO) ) { tmp = "/w/"+query_name()+"/workroom"; if( !catch( ob = load_object(tmp) ) && ob ) return tmp; } tmp = ( !sizeof( starts ) ? CONFIG_START_LOCATION : starts[ 0 ] ); if( catch( ob = load_object(tmp) ) || !ob ) tmp = CONFIG_START_LOCATION; return tmp; } /* query_start_pos() */ /** * This method returns the current array of possible start positions on * the player. * @return the array of possible start locations * @see query_start_pos() * @see add_start() * @see remove_start() * @see reset_starts() * @see set_start_location() */ string *query_starts() { return starts; } /** * This method resets the start locations back to an empty array. * @see query_start_pos() * @see add_start() * @see remove_start() * @see query_starts() * @see set_start_location() */ void reset_starts() { starts = ({ }); } /** * This method will add a new start location to the player. The * description will be used in the starts command. * @param start_file the file name of the start location * @param start_desc the description of the start location * @see query_start_pos() * @see reset_starts() * @see remove_start() * @see query_starts() * @see set_start_location() * @example * // NB: This should be done with a define :) * player->add_start("/d/am/am/mendeddrum", "the mended drum"); */ void add_start( string start_file, string start_desc ) { if( !stringp(start_file) || !sizeof(start_file) ) return; if( !starts ) starts = ({ }); if( member_array( start_file, starts ) != -1 ) return; starts += ({ start_file, start_desc }); } /* add_start() */ /** * This method will remove a start location from the player. * @param start_file the file name of the location to remove * @see query_start_pos() * @see reset_starts() * @see add_start() * @see query_starts() * @see set_start_location() * @example * // NB: This should be done with a define :) * player->remove_start("/d/am/am/mendeddrum"); */ void remove_start( string start_file ) { int i; if( !starts ) return; if( ( i = member_array( start_file, starts ) ) == -1 ) return; starts = delete( starts, i, 2 ); } /* remove_start() */ /** * This method sets the start location of the player. * @param start_file the start location to set * @see query_start_pos() * @see reset_starts() * @see remove_start() * @see query_starts() * @see add_start() * @example * // NB: This should be done with a define :) * player->set_start_location("/d/am/am/mendeddrum"); */ void set_start_location( string start_file ) { int i; if( !starts ) return; if( ( i = member_array( start_file, starts ) ) <= 0 ) return; starts = starts[i..i+1] + starts[0..i-1] + starts[i+2..]; } /* set_start_location() */ /** * This method moves the player to the last saved position. This should * only be called in the startup sequence. If the last location could * not be loaded, the the start position will be used. * @see query_last_pos() * @see quert_start_pos() */ protected void move_to_start_pos() { object ob; string tmp; if( !last_pos || catch( ob = load_object(last_pos) ) || !ob ) { tmp = query_start_pos(); if( last_pos != tmp && !catch( ob = load_object(tmp) ) && ob ) last_pos = tmp; else last_pos = CONFIG_START_LOCATION; saved_co_ords = 0; } move(last_pos); // Set the old coord if one does not already exist. // Otherwise don't destroy the already existing scheme. if( saved_co_ords && !last_pos->query_co_ord() && !last_pos->query_property("no map") && !creatorp(TO) ) { last_pos->set_co_ord( saved_co_ords ); } inform_entered_game(); } /* move_to_start_pos() */ private function query_extra_login_stuff( string start ) { string ip_str; object *obs; object mph; string alert; int num; string *dups; switch( TO->query_invis() ) { case 0 : break; case 1: start += " (Invisible)"; break; case 2: start += " (Lord Invisible)"; break; default : start += " (Admin Invisible)"; } mph = load_object(MULTIPLAYER); obs = filter( users() - ({ TO }), (: query_ip_number($1) == query_ip_number(TO) && !$1->query_login_ob() :) ); if( sizeof(obs) && sizeof( ( dups = mph->check_allowed( TO, obs ) ) ) ) { ip_str = " ("+query_ip_name(TO)+")"; ip_str += " Duplicate: "+query_multiple_short(dups); } if( !catch( num = PLAYERINFO_HANDLER->query_alerts_for( query_name() ) ) ) { if( num > 0 ) { alert = " %^BOLD%^%^RED%^"+num+" alert"; if( num > 1 ) alert += "s"; alert += "%^RESET%^"; } } if( ip_str ) { if( !alert ) alert = ""; return (: $(start) + ( creatorp($1) ? $(ip_str) + $(alert) : "") :); } else { if( alert ) { return (: $(start) + ( creatorp($1) ? $(alert) : "") :); } else { return (: $(start) :); } } } /* query_extra_login_stuff() */ /** * This method handles informing people that the * player has entered the game. * @see move_to_start_pos() */ protected void inform_entered_game() { string logon_str; logon_str = query_cap_name()+" enters "+mud_name(); if( adminp( query_name() ) ) { logon_str += " %^BLUE%^(Admin)"; } else if( lordp( query_name() ) ) { logon_str += " %^GREEN%^(Lord)"; } else if( liaisonp( query_name() ) ) { logon_str += " %^YELLOW%^(Liaison)"; } else if( seniorp( query_name() ) ) { logon_str += " %^RED%^(Senior Creator)"; } else if( DOMAIN_H->query_member("sage", query_name() ) ) { logon_str += " %^CYAN%^(Sage)"; } else if( DOMAIN_H->query_member("learning", query_name() ) ) { logon_str += " %^CYAN%^(Apprentice)"; } else if( creatorp( query_name() ) ) { logon_str += " %^CYAN%^(Creator)"; } else if( TO->query_property("guest") ) { logon_str += " %^MAGENTA%^(Guest)"; } else if( TO->query_property("new player!") ) { logon_str += " %^WHITE%^(New Player)"; } else if( playtesterp( query_name() ) ) { if( PLAYTESTERS_H->query_senior_playtester( query_name() ) ) { logon_str += " %^BOLD%^%^CYAN%^(Senior Playtester)"; } else { logon_str += " %^CYAN%^(Playtester)"; } } user_event( TO, "inform", query_extra_login_stuff(logon_str), "logon", TO ); event( ENV( TO ), "see", query_cap_name()+" enters the game.\n", TO, ({ TO }) ); last_pos->enter(TO); } /* inform_enter_game() */ /** * This method is called to inform people that someone * has just reconnected. */ void inform_reconnect_game() { user_event("inform", query_extra_login_stuff( query_cap_name()+" reconnects"), "link-death", TO ); } /* inform_reconnect_game() */ /** * This method figured out what the last saved position was and sets it * on the player. This basicly sets the last saved postion. * @see query_last_pos() */ void check_last_pos() { last_pos = find_start_pos( TO, environment() ); saved_co_ords = find_start_coord( TO, environment() ); } /* check_last_pos() */