/* $Header: look.c,v 2.0 90/05/05 12:45:36 lachesis Exp $ * $Log: look.c,v $ * Revision 2.0 90/05/05 12:45:36 lachesis * Incorporated ABODE and HAVEN flags (remembering to convert FireFoot's * usage of those flags to ours). * Added Examine of objects that don't belong to you, added GOD_PRIV. * * Revision 1.3 90/04/21 17:20:46 lachesis * Added property lists. * * Revision 1.2 90/04/20 14:06:44 lachesis * Added @odrop && @drop. * * Revision 1.1 90/04/14 14:56:46 lachesis * Initial revision * */ #include "copyright.h" /* commands which look at things */ #include "os.h" #include "db.h" #include "config.h" #include "interface.h" #include "match.h" #include "externs.h" char buf[BUFFER_LEN]; /* prints owner of something */ static void print_owner (dbref player, dbref thing) { char buf[BUFFER_LEN]; switch (Typeof (thing)) { case TYPE_ROOM: sprintf (buf, "Owner: %s", db[db[thing].sp.room.owner].name); break; case TYPE_THING: sprintf (buf, "Owner: %s", db[db[thing].sp.thing.owner].name); break; case TYPE_PLAYER: sprintf (buf, "%s is a player", db[thing].name); break; case TYPE_EXIT: sprintf (buf, "Owner: %s", db[db[thing].sp.exit.owner].name); break; #ifdef RECYCLE case TYPE_GARBAGE: sprintf (buf, "%s is garbage", db[thing].name); break; #endif } notify (player, buf); } static void look_contents (dbref player, dbref loc, const char *contents_name) { dbref thing; dbref can_see_loc; /* check to see if he can see the location */ can_see_loc = (!Dark (loc) || controls (player, loc)); /* check to see if there is anything there */ DOLIST (thing, db[loc].contents) { if (can_see (player, thing, can_see_loc)) { /* something exists! show him everything */ notify (player, contents_name); DOLIST (thing, db[loc].contents) { if (can_see (player, thing, can_see_loc)) { notify (player, unparse_object (player, thing)); } } break; /* we're done */ } } } static void look_simple (dbref player, dbref thing) { if (db[thing].description) { notify (player, db[thing].description); } else { notify (player, "You see nothing special."); } } void look_room (dbref player, dbref loc) { /* tell him the name, and the number if he can link to it */ notify (player, unparse_object (player, loc)); /* tell him the description */ if (db[loc].description) { notify (player, db[loc].description); } /* tell him the appropriate messages if he has the key */ can_doit (player, loc, 0); /* tell him the contents */ look_contents (player, loc, "Contents:"); } void do_look_around (dbref player) { dbref loc; if ((loc = getloc (player)) == NOTHING) return; look_room (player, loc); } void do_look_at (dbref player, const char *name) { dbref thing; if (*name == '\0') { if ((thing = getloc (player)) != NOTHING) { look_room (player, thing); } } else { /* look at a thing here */ init_match (player, name, NOTYPE); match_all_exits (); match_neighbor (); match_possession (); if (Wizard (player)) { match_absolute (); match_player (); } match_here (); match_me (); if ((thing = noisy_match_result ()) != NOTHING) { switch (Typeof (thing)) { case TYPE_ROOM: look_room (player, thing); break; case TYPE_PLAYER: look_simple (player, thing); look_contents (player, thing, "Carrying:"); break; default: look_simple (player, thing); break; } } } } #ifdef VERBOSE_EXAMINE static const char *flag_description (dbref thing) { static char buf[BUFFER_LEN]; strcpy (buf, "Type: "); switch (Typeof (thing)) { case TYPE_ROOM: strcat (buf, "ROOM"); break; case TYPE_EXIT: strcat (buf, "EXIT/ACTION"); break; case TYPE_THING: strcat (buf, "THING"); break; case TYPE_PLAYER: strcat (buf, "PLAYER"); break; #ifdef RECYCLE case TYPE_GARBAGE: strcat (buf, "GARBAGE"); break; #endif default: strcat (buf, "***UNKNOWN TYPE***"); break; } if (db[thing].flags & ~TYPE_MASK) { /* print flags */ strcat (buf, " Flags:"); if (db[thing].flags & WIZARD) strcat (buf, " WIZARD"); if (db[thing].flags & STICKY) strcat (buf, " STICKY"); if (db[thing].flags & DARK) strcat (buf, " DARK"); if (db[thing].flags & LINK_OK) strcat (buf, " LINK_OK"); if (db[thing].flags & TEMPLE) strcat (buf, " TEMPLE"); #ifdef RESTRICTED_BUILDING if (db[thing].flags & BUILDER) strcat (buf, " BUILDER"); #endif /* RESTRICTED_BUILDING */ #ifdef PLAYER_CHOWN if (db[thing].flags & CHOWN_OK) strcat (buf, " CHOWN_OK"); #endif /* PLAYER_CHOWN */ if (db[thing].flags & JUMP_OK) strcat (buf, " JUMP_OK"); #ifdef HAVEN if (db[thing].flags & HAVEN) strcat (buf, " HAVEN"); #endif /* HAVEN */ #ifdef ABODE if (db[thing].flags & ABODE) strcat (buf, " ABODE"); #endif /* ABODE */ } return buf; } #endif /* VERBOSE_EXAMINE */ void do_examine (dbref player, const char *name) { dbref thing; char buf[BUFFER_LEN]; dbref content; dbref exit; int i; if (*name == '\0') { if ((thing = getloc (player)) == NOTHING) return; } else { /* look it up */ init_match (player, name, NOTYPE); match_all_exits (); match_neighbor (); match_possession (); match_absolute (); /* only Wizards can examine other players */ if (Wizard (player)) match_player (); match_here (); match_me (); /* get result */ if ((thing = noisy_match_result ()) == NOTHING) return; } if (!can_link (player, thing)) { print_owner (player, thing); do_look_at (player, name); return; } switch (Typeof (thing)) { case TYPE_ROOM: sprintf (buf, "%s Owner: %s", unparse_object (player, thing), db[db[thing].sp.room.owner].name); break; case TYPE_THING: sprintf (buf, "%s Owner: %s Value: %d", unparse_object (player, thing), db[db[thing].sp.thing.owner].name, db[thing].sp.thing.value); break; case TYPE_PLAYER: sprintf (buf, "%s Cookies: %d ", unparse_object (player, thing), db[thing].sp.player.pennies); break; case TYPE_EXIT: sprintf (buf, "%s Owner: %s", unparse_object (player, thing), db[db[thing].sp.exit.owner].name); break; #ifdef RECYCLE case TYPE_GARBAGE: strcpy (buf, unparse_object (player, thing)); break; #endif } notify (player, buf); #ifdef VERBOSE_EXAMINE notify (player, flag_description (thing)); #endif /* VERBOSE_EXAMINE */ if (db[thing].description) notify (player, db[thing].description); sprintf (buf, "Key: %s", unparse_boolexp (player, db[thing].key)); notify (player, buf); if (db[thing].fail_message) { sprintf (buf, "Fail: %s", db[thing].fail_message); notify (player, buf); } if (db[thing].succ_message) { sprintf (buf, "Success: %s", db[thing].succ_message); notify (player, buf); } if (db[thing].drop_message) { sprintf (buf, "Drop: %s", db[thing].drop_message); notify (player, buf); } if (db[thing].ofail) { sprintf (buf, "Ofail: %s", db[thing].ofail); notify (player, buf); } if (db[thing].osuccess) { sprintf (buf, "Osuccess: %s", db[thing].osuccess); notify (player, buf); } if (db[thing].odrop) { sprintf (buf, "Odrop: %s", db[thing].odrop); notify (player, buf); } /* show him the properties */ if (db[thing].properties) { struct plist *p; char buf[BUFFER_LEN]; notify (player, "Properties:"); for (p = db[thing].properties; p; p = p->next) { strncpy (buf, p->type, BUFFER_LEN - 1); strncat (buf, ": ", BUFFER_LEN - 1); strncat (buf, p->class, BUFFER_LEN - 1); notify (player, buf); } } /* show him the contents */ if (db[thing].contents != NOTHING) { if (Typeof (thing) == TYPE_PLAYER) notify (player, "Carrying:"); else notify (player, "Contents:"); DOLIST (content, db[thing].contents) { notify (player, unparse_object (player, content)); } } switch (Typeof (thing)) { case TYPE_ROOM: /* tell him about exits */ if (db[thing].sp.room.exits != NOTHING) { notify (player, "Exits:"); DOLIST (exit, db[thing].sp.room.exits) { notify (player, unparse_object (player, exit)); } } else { notify (player, "No exits."); } /* print dropto if present */ if (db[thing].sp.room.dropto != NOTHING) { sprintf (buf, "Dropped objects go to: %s", unparse_object (player, db[thing].sp.room.dropto)); notify (player, buf); } break; case TYPE_THING: /* print home */ sprintf (buf, "Home: %s", unparse_object (player, db[thing].sp.thing.home)); /* home */ notify (player, buf); /* print location if player can link to it */ if (db[thing].location != NOTHING && (controls (player, db[thing].location) || can_link_to (player, db[thing].location))) { sprintf (buf, "Location: %s", unparse_object (player, db[thing].location)); notify (player, buf); } /* print thing's actions, if any */ if (db[thing].sp.thing.actions != NOTHING) { notify (player, "Actions/exits:"); DOLIST (exit, db[thing].sp.thing.actions) { notify (player, unparse_object (player, exit)); } } else { notify (player, "No actions attached."); } break; case TYPE_PLAYER: /* print home */ sprintf (buf, "Home: %s", unparse_object (player, db[thing].sp.player.home)); /* home */ notify (player, buf); /* print location if player can link to it */ if (db[thing].location != NOTHING && (controls (player, db[thing].location) || can_link_to (player, db[thing].location))) { sprintf (buf, "Location: %s", unparse_object (player, db[thing].location)); notify (player, buf); } /* print player's actions, if any */ if (db[thing].sp.player.actions != NOTHING) { notify (player, "Actions/exits:"); DOLIST (exit, db[thing].sp.player.actions) { notify (player, unparse_object (player, exit)); } } else { notify (player, "No actions attached."); } break; case TYPE_EXIT: if (db[thing].location != NOTHING) { sprintf (buf, "Source: %s", unparse_object (player, db[thing].location)); notify (player, buf); } /* print destinations */ if (db[thing].sp.exit.ndest == 0) break; for (i = 0; i < db[thing].sp.exit.ndest; i++) { switch ((db[thing].sp.exit.dest)[i]) { case NOTHING: break; case HOME: notify (player, "Destination: *HOME*"); break; default: sprintf (buf, "Destination: %s", unparse_object (player, (db[thing].sp.exit.dest)[i])); notify (player, buf); break; } } break; default: /* do nothing */ break; } } void do_score (dbref player) { char buf[BUFFER_LEN]; sprintf (buf, "You have %d %s.", db[player].sp.player.pennies, db[player].sp.player.pennies == 1 ? "cookie" : "cookies"); notify (player, buf); } void do_inventory (dbref player) { dbref thing; if ((thing = db[player].contents) == NOTHING) { notify (player, "You aren't carrying anything."); } else { notify (player, "You are carrying:"); DOLIST (thing, thing) { notify (player, unparse_object (player, thing)); } } do_score (player); } void do_find (dbref player, const char *name) { dbref i; if (!payfor (player, LOOKUP_COST)) { notify (player, "You don't have enough cookies."); } else { for (i = 0; i < db_top; i++) { if (Typeof (i) != TYPE_EXIT && controls (player, i) && (!*name || string_match (db[i].name, name))) { notify (player, unparse_object (player, i)); } } notify (player, "***End of List***"); } }