diff -BbuprN tbamud-3.55/src/Makefile tbamud-3.55+automap/src/Makefile
--- tbamud-3.55/src/Makefile	2008-02-05 21:27:51.944422000 +0000
+++ tbamud-3.55+automap/src/Makefile	2008-02-05 20:03:52.928797000 +0000
@@ -26,8 +26,8 @@ LIBS =  -lcrypt 
 
 OBJFILES = act.comm.o act.informative.o act.item.o act.movement.o \
 	act.offensive.o act.other.o act.social.o act.wizard.o aedit.o \
-	ban.o boards.o bsd-snprintf.o castle.o cedit.o class.o comm.o config.o \
-	constants.o db.o dg_comm.o dg_db_scripts.o dg_event.o \
+	asciimap.o ban.o boards.o bsd-snprintf.o castle.o cedit.o class.o \
+	comm.o config.o constants.o db.o dg_comm.o dg_db_scripts.o dg_event.o \
 	dg_handler.o dg_misc.o dg_mobcmd.o dg_objcmd.o dg_olc.o dg_scripts.o \
 	dg_triggers.o dg_variables.o dg_wldcmd.o fight.o genmob.o \
 	genobj.o genolc.o genshp.o genwld.o genzon.o graph.o handler.o hedit.o \
@@ -39,8 +39,8 @@ OBJFILES = act.comm.o act.informative.o 
 
 CXREF_FILES = act.comm.c act.informative.c act.item.c act.movement.c \
 	act.offensive.c act.other.c act.social.c act.wizard.c aedit.c \
-	ban.c boards.c bsd-snprintf.c castle.c cedit.c class.c comm.c config.c \
-	constants.c db.c dg_comm.c dg_db_scripts.c dg_event.c \
+	asciimap.c ban.c boards.c bsd-snprintf.c castle.c cedit.c class.c \
+	comm.c config.c constants.c db.c dg_comm.c dg_db_scripts.c dg_event.c \
 	dg_handler.c dg_misc.c dg_mobcmd.c dg_objcmd.c dg_olc.c dg_scripts.c \
 	dg_triggers.c dg_variables.c dg_wldcmd.c fight.c genmob.c \
 	genobj.c genolc.c genshp.c genwld.c genzon.c graph.c handler.c hedit.c \
diff -BbuprN tbamud-3.55/src/Makefile.in tbamud-3.55+automap/src/Makefile.in
--- tbamud-3.55/src/Makefile.in	2008-01-16 23:21:14.000000000 +0000
+++ tbamud-3.55+automap/src/Makefile.in	2008-02-05 20:00:07.631922000 +0000
@@ -25,8 +25,8 @@ LIBS = @LIBS@ @CRYPTLIB@ @NETLIB@
 
 OBJFILES = act.comm.o act.informative.o act.item.o act.movement.o \
 	act.offensive.o act.other.o act.social.o act.wizard.o aedit.o \
-	ban.o boards.o bsd-snprintf.o castle.o cedit.o class.o comm.o config.o \
-	constants.o db.o dg_comm.o dg_db_scripts.o dg_event.o \
+	asciimap.o ban.o boards.o bsd-snprintf.o castle.o cedit.o class.o \
+	comm.o config.o constants.o db.o dg_comm.o dg_db_scripts.o dg_event.o \
 	dg_handler.o dg_misc.o dg_mobcmd.o dg_objcmd.o dg_olc.o dg_scripts.o \
 	dg_triggers.o dg_variables.o dg_wldcmd.o fight.o genmob.o \
 	genobj.o genolc.o genshp.o genwld.o genzon.o graph.o handler.o hedit.o \
@@ -38,8 +38,8 @@ OBJFILES = act.comm.o act.informative.o 
 
 CXREF_FILES = act.comm.c act.informative.c act.item.c act.movement.c \
 	act.offensive.c act.other.c act.social.c act.wizard.c aedit.c \
-	ban.c boards.c bsd-snprintf.c castle.c cedit.c class.c comm.c config.c \
-	constants.c db.c dg_comm.c dg_db_scripts.c dg_event.c \
+	asciimap.c ban.c boards.c bsd-snprintf.c castle.c cedit.c class.c \
+	comm.c config.c constants.c db.c dg_comm.c dg_db_scripts.c dg_event.c \
 	dg_handler.c dg_misc.c dg_mobcmd.c dg_objcmd.c dg_olc.c dg_scripts.c \
 	dg_triggers.c dg_variables.c dg_wldcmd.c fight.c genmob.c \
 	genobj.c genolc.c genshp.c genwld.c genzon.c graph.c handler.c hedit.c \
diff -BbuprN tbamud-3.55/src/act.informative.c tbamud-3.55+automap/src/act.informative.c
--- tbamud-3.55/src/act.informative.c	2008-01-16 23:28:12.000000000 +0000
+++ tbamud-3.55+automap/src/act.informative.c	2008-02-05 19:58:08.803797000 +0000
@@ -47,6 +47,8 @@ char *title_female(int chclass, int leve
 struct time_info_data *real_time_passed(time_t t2, time_t t1);
 int compute_armor_class(struct char_data *ch);
 int has_mail(long id);
+bool can_see_map(struct char_data *ch);
+void str_and_map(char *str, struct char_data *ch );
 
 /* local functions */
 int sort_commands_helper(const void *a, const void *b);
@@ -529,7 +531,16 @@ void look_at_room(struct char_data *ch, 
 
   if ((!IS_NPC(ch) && !PRF_FLAGGED(ch, PRF_BRIEF)) || ignore_brief ||
       ROOM_FLAGGED(IN_ROOM(ch), ROOM_DEATH))
+  {
+      if(!IS_NPC(ch) && PRF_FLAGGED(ch, PRF_AUTOMAP) && can_see_map(ch))
+      {
+        str_and_map(world[IN_ROOM(ch)].description, ch);
+      }
+      else
+      {
     send_to_char(ch, "%s", world[IN_ROOM(ch)].description);
+      }
+  }
 
   /* autoexits */
   if (!IS_NPC(ch) && PRF_FLAGGED(ch, PRF_AUTOEXIT))
@@ -1860,6 +1871,10 @@ ACMD(do_toggle)
     {"autoassist", PRF_AUTOASSIST, 0,
     "Autoassist disabled.\r\n",
     "Autoassist enabled.\r\n"},
+    {"screenwidth", 0, 0, "\n", "\n"},
+    {"automap", PRF_AUTOMAP, 0,
+    "You will no longer see the mini-map.\r\n",
+    "You will now see a mini-map at the side of room descriptions.\r\n"},
     {"\n", 0, -1, "\n", "\n"} /* must be last */
   };
 
@@ -1931,9 +1946,12 @@ ACMD(do_toggle)
 
     "        AutoSac: %-3s    "
     "     AutoAssist: %-3s    "
-    "            AFK: %-3s\r\n"
+    "        AutoMap: %-3s    "
 
     "     Pagelength: %-3d    "
+    "    Screenwidth: %-3d    "
+    "            AFK: %-3s\r\n"
+
     "          Color: %s     \r\n ",
 
     ONOFF(PRF_FLAGGED(ch, PRF_DISPHP)),
@@ -1962,9 +1980,12 @@ ACMD(do_toggle)
 
     ONOFF(PRF_FLAGGED(ch, PRF_AUTOSAC)),
     ONOFF(PRF_FLAGGED(ch, PRF_AUTOASSIST)),
-    ONOFF(PRF_FLAGGED(ch, PRF_AFK)),
+    ONOFF(PRF_FLAGGED(ch, PRF_AUTOMAP)),
 
     GET_PAGE_LENGTH(ch),
+    GET_SCREEN_WIDTH(ch),
+    ONOFF(PRF_FLAGGED(ch, PRF_AFK)),
+
     types[COLOR_LEV(ch)]);
     return;
   }
@@ -2080,6 +2101,33 @@ ACMD(do_toggle)
     } else
       send_to_char(ch, "Please specify a number of lines (5 - 255).");
       break;
+  case SCMD_SCREENWIDTH:
+    if (!*arg2)
+      send_to_char(ch, "You current screen width is set to %d characters.", GET_SCREEN_WIDTH(ch));
+    else if (is_number(arg2)) {
+      GET_SCREEN_WIDTH(ch) = MIN(MAX(atoi(arg2), 40), 200);
+      send_to_char(ch, "Okay, your screen width is now set to %d characters.", GET_SCREEN_WIDTH(ch));
+    } else
+      send_to_char(ch, "Please specify a number of characters (40 - 200).");
+      break;
+  case SCMD_AUTOMAP:
+    if (can_see_map(ch)) {
+      if (!*arg2) {
+        TOGGLE_BIT_AR(PRF_FLAGS(ch), tog_messages[toggle].toggle);
+        result = (PRF_FLAGGED(ch, tog_messages[toggle].toggle));
+      } else if (!strcmp(arg2, "on")) {
+        SET_BIT_AR(PRF_FLAGS(ch), tog_messages[toggle].toggle);
+        result = 1;
+      } else if (!strcmp(arg2, "off")) {
+        REMOVE_BIT_AR(PRF_FLAGS(ch), tog_messages[toggle].toggle);
+      } else {
+        send_to_char(ch, "Value for %s must either be 'on' or 'off'.\r\n", tog_messages[toggle].command);
+        return;
+      }
+    } else {
+      send_to_char(ch, "Sorry, automap is currently disabled.\r\n");
+      return;
+    }
   default:
     if (!*arg2) {
       TOGGLE_BIT_AR(PRF_FLAGS(ch), tog_messages[toggle].toggle);
diff -BbuprN tbamud-3.55/src/act.wizard.c tbamud-3.55+automap/src/act.wizard.c
--- tbamud-3.55/src/act.wizard.c	2008-01-16 23:28:42.000000000 +0000
+++ tbamud-3.55+automap/src/act.wizard.c	2008-02-05 19:05:52.913172000 +0000
@@ -862,7 +862,9 @@ void do_stat_character(struct char_data 
 	  GET_GOLD(k), GET_BANK_GOLD(k), GET_GOLD(k) + GET_BANK_GOLD(k));
 
   if (!IS_NPC(k))
-    send_to_char(ch, "Questpoints: [%d]\r\n", GET_QUESTPOINTS(k));
+    send_to_char(ch, "Questpoints: [%d]    Screen %s[%s%d%sx%s%d%s]%s\r\n", GET_QUESTPOINTS(k),
+                      CCCYN(ch, C_NRM), CCYEL(ch, C_NRM), GET_SCREEN_WIDTH(k), CCNRM(ch, C_NRM),
+                      CCYEL(ch, C_NRM), GET_PAGE_LENGTH(k), CCCYN(ch, C_NRM), CCNRM(ch, C_NRM));
   
   send_to_char(ch, "AC: [%d%+d/10], Hitroll: [%2d], Damroll: [%2d], Saving throws: [%d/%d/%d/%d/%d]\r\n",
 	  GET_AC(k), dex_app[GET_DEX(k)].defensive, k->points.hitroll,
@@ -2744,18 +2746,19 @@ ACMD(do_show)
    { "practices", 	LVL_GOD, 	PC, 	NUMBER },   /* 40 */
    { "quest",		LVL_GOD, 	PC, 	BINARY },
    { "room",		LVL_BUILDER, 	BOTH, 	NUMBER },
+   { "screenwidth",	LVL_GOD, 	PC, 	NUMBER },
    { "sex", 		LVL_GOD, 	BOTH, 	MISC },
-   { "showvnums", 	LVL_BUILDER, 	PC,	BINARY },
-   { "siteok",		LVL_GOD, 	PC, 	BINARY },  /* 45 */
+   { "showvnums", 	LVL_BUILDER, 	PC,	BINARY },  /* 45 */
+   { "siteok",		LVL_GOD, 	PC, 	BINARY },
    { "str",		LVL_BUILDER, 	BOTH, 	NUMBER },
    { "stradd",		LVL_BUILDER, 	BOTH, 	NUMBER },
    { "thief",		LVL_GOD, 	PC, 	BINARY },
-   { "thirst",		LVL_BUILDER, 	BOTH, 	MISC },
-   { "title",		LVL_GOD, 	PC, 	MISC   },  /* 50 */
+   { "thirst",		LVL_BUILDER, 	BOTH, 	MISC },  /* 50 */
+   { "title",		LVL_GOD, 	PC, 	MISC   },
    { "variable",        LVL_GRGOD,	PC,	MISC },
    { "weight",		LVL_BUILDER,	BOTH,	NUMBER },
    { "wis", 		LVL_BUILDER, 	BOTH, 	NUMBER },
-   { "questpoints",     LVL_GOD,        PC,     NUMBER },
+   { "questpoints",     LVL_GOD,        PC,     NUMBER },  /* 55 */
    { "\n", 0, BOTH, MISC }
   };
 
@@ -3074,20 +3077,23 @@ int perform_set(struct char_data *ch, st
         char_from_room(vict);
       char_to_room(vict, rnum);
       break;
-    case 43: /* sex */
+    case 43: /* screenwidth */
+      GET_SCREEN_WIDTH(vict) = RANGE(40, 200);
+      break;
+    case 44: /* sex */
       if ((i = search_block(val_arg, genders, FALSE)) < 0) {
         send_to_char(ch, "Must be 'male', 'female', or 'neutral'.\r\n");
         return (0);
       }
       GET_SEX(vict) = i;
       break;
-    case 44: /* showvnums */
+    case 45: /* showvnums */
       SET_OR_REMOVE(PRF_FLAGS(vict), PRF_SHOWVNUMS);
       break;
-    case 45: /* siteok */
+    case 46: /* siteok */
       SET_OR_REMOVE(PLR_FLAGS(vict), PLR_SITEOK);
       break;
-    case 46: /* str */
+    case 47: /* str */
       if (IS_NPC(vict) || GET_LEVEL(vict) >= LVL_GRGOD)
         RANGE(3, 25);
       else
@@ -3096,16 +3102,16 @@ int perform_set(struct char_data *ch, st
       vict->real_abils.str_add = 0;
       affect_total(vict);
       break;
-    case 47: /* stradd */
+    case 48: /* stradd */
       vict->real_abils.str_add = RANGE(0, 100);
       if (value > 0)
         vict->real_abils.str = 18;
       affect_total(vict);
       break;
-    case 48: /* thief */
+    case 49: /* thief */
       SET_OR_REMOVE(PLR_FLAGS(vict), PLR_THIEF);
       break;
-    case 49: /* thirst */
+    case 50: /* thirst */
       if (!str_cmp(val_arg, "off")) {
         GET_COND(vict, THIRST) = -1;
         send_to_char(ch, "%s's thirst is now off.\r\n", GET_NAME(vict));
@@ -3119,18 +3125,18 @@ int perform_set(struct char_data *ch, st
         return (0);
       }
       break;
-  case 50: /* title */
+  case 51: /* title */
       set_title(vict, val_arg);
       send_to_char(ch, "%s's title is now: %s\r\n", GET_NAME(vict), GET_TITLE(vict));
       break;
-    case 51: /* variable */
+    case 52: /* variable */
       return perform_set_dg_var(ch, vict, val_arg);
       break;
-    case 52: /* weight */
+    case 53: /* weight */
       GET_WEIGHT(vict) = value;
       affect_total(vict);
       break;
-    case 53: /* wis */
+    case 54: /* wis */
       if (IS_NPC(vict) || GET_LEVEL(vict) >= LVL_GRGOD)
         RANGE(3, 25);
       else
@@ -3138,7 +3144,7 @@ int perform_set(struct char_data *ch, st
       vict->real_abils.wis = value;
       affect_total(vict);
       break;
-    case 54: /* questpoints */
+    case 55: /* questpoints */
       GET_QUESTPOINTS(vict) = RANGE(0, 100000000);
       break;
     default:
diff -BbuprN tbamud-3.55/src/asciimap.c tbamud-3.55+automap/src/asciimap.c
--- tbamud-3.55/src/asciimap.c	1970-01-01 00:00:00.000000000 +0000
+++ tbamud-3.55+automap/src/asciimap.c	2008-02-05 20:24:41.069422000 +0000
@@ -0,0 +1,528 @@
+/**************************************************************************
+*  File: asciimap.c                                        Part of tbaMUD *
+*  Usage: Generates an ASCII map of the player's surroundings.            *
+*                                                                         *
+*  All rights reserved.  See license for complete information.            *
+*                                                                         *
+*  Copyright (C) 1993, 94 by the Trustees of the Johns Hopkins University *
+*  CircleMUD is based on DikuMUD, Copyright (C) 1990, 1991.               *
+**************************************************************************/
+
+#include "conf.h"
+#include "sysdep.h"
+
+#include "structs.h"
+#include "utils.h"
+#include "comm.h"
+#include "interpreter.h"
+#include "handler.h"
+#include "db.h"
+#include "spells.h"
+#include "house.h"
+#include "constants.h"
+#include "dg_scripts.h"
+
+/* Do not blindly change these values, as many values cause the map to stop working - backup first */
+#define CANVAS_HEIGHT 19
+#define CANVAS_WIDTH  51
+#define LEGEND_WIDTH  15
+
+#define DEFAULT_MAP_SIZE CONFIG_MAP_SIZE
+
+#define MAX_MAP_SIZE (CANVAS_WIDTH - 1)/4
+#define MAX_MAP      CANVAS_WIDTH
+
+#define MAX_MAP_DIR 6
+#define MAX_MAP_FOLLOW 4
+
+#define SECT_EMPTY	30 /* anything greater than num sect types */
+#define SECT_STRANGE	(SECT_EMPTY + 1)
+#define SECT_HERE	(SECT_STRANGE + 1)
+
+#define DOOR_NS   -1
+#define DOOR_EW   -2
+#define DOOR_UP   -3
+#define DOOR_DOWN -4
+#define VDOOR_NS  -5
+#define VDOOR_EW  -6
+#define DOOR_NONE -7
+#define NUM_DOOR_TYPES 7
+
+#define MAP_CIRCLE    0
+#define MAP_RECTANGLE 1
+
+#define MAP_NORMAL  0
+#define MAP_COMPACT 1
+
+// char *strfrmt(char *str, int w, int h, int justify, int hpad, int vpad);
+// char *strpaste(char *str1, char *str2, char *joiner);
+
+extern struct room_data *world;
+int add_to_save_list(zone_vnum zone, int type);
+int can_edit_zone(struct char_data *ch, int number);
+
+struct map_info_type
+{
+  int  sector_type;
+  char disp[20];
+};
+
+struct map_info_type door_info[] =
+{
+  { DOOR_NONE, "   " },
+  { VDOOR_EW,  " @m+@n " },
+  { VDOOR_NS,  " @m+@n "},
+  { DOOR_DOWN, "@r-@n  " },
+  { DOOR_UP,   "@r+@n  " },
+  { DOOR_EW,   " - " },
+  { DOOR_NS,   " | " }
+};
+
+struct map_info_type compact_door_info[] =
+{
+  { DOOR_NONE, " " },
+  { VDOOR_EW,  " @m+@n " },
+  { VDOOR_NS,  " @m+@n "},
+  { DOOR_DOWN, "@r-@n" },
+  { DOOR_UP,   "@r+@n" },
+  { DOOR_EW,   "-" },
+  { DOOR_NS,   " | " }
+};
+
+/* Add new sector types below for both map_info and world_map_info     */
+/* The last 3 MUST remain the same, although the symbol can be changed */
+/* New sectors also need to be added to the perform_map function below */
+struct map_info_type map_info[] =
+{
+  { SECT_INSIDE,       "@c[@n.@c]@n" }, /* 0 */
+  { SECT_CITY,         "@c[@wC@c]@n" },
+  { SECT_FIELD,        "@c[@g,@c]@n" },
+  { SECT_FOREST,       "@c[@gY@c]@n" },
+  { SECT_HILLS,        "@c[@Mm@c]@n" },
+  { SECT_MOUNTAIN,     "@c[@rM@c]@n" }, /* 5 */
+  { SECT_WATER_SWIM,   "@c[@c~@c]@n" },
+  { SECT_WATER_NOSWIM, "@c[@b=@c]@n" },
+  { SECT_FLYING,       "@c[@C^@c]@n" },
+  { SECT_UNDERWATER,   "@c[@bU@c]@n" },
+  { -1,                ""        }, /* 10 */
+  { -1,                ""        },
+  { -1,                ""        },
+  { -1,                ""        },
+  { -1,                ""        },
+  { -1,                ""        }, /* 15 */
+  { -1,                ""        },
+  { -1,                ""        },
+  { -1,                ""        },
+  { -1,                ""        },
+  { -1,                ""        }, /* 20 */
+  { -1,                ""        },
+  { -1,                ""        },
+  { -1,                ""        },
+  { -1,                ""        },
+  { -1,                ""        }, /* 25 */
+  { -1,                ""        },
+  { -1,                ""        },
+  { -1,                ""        },
+  { -1,                ""        },
+  { SECT_EMPTY,        "   "     }, /* 30 */
+  { SECT_STRANGE,      "@c[@R?@c]@n" },
+  { SECT_HERE,         "@c[@B!@c]@n"     },
+};
+
+struct map_info_type world_map_info[] =
+{
+  { SECT_INSIDE,       "@n."  }, /* 0 */
+  { SECT_CITY,         "@wC"  },
+  { SECT_FIELD,        "@g,"  },
+  { SECT_FOREST,       "@gY"  },
+  { SECT_HILLS,        "@Mm"  },
+  { SECT_MOUNTAIN,     "@rM"  }, /* 5 */
+  { SECT_WATER_SWIM,   "@c~"  },
+  { SECT_WATER_NOSWIM, "@b="  },
+  { SECT_FLYING,       "@C^"  },
+  { SECT_UNDERWATER,   "@bU"  },
+  { -1,                ""     }, /* 10 */
+  { -1,                ""     },
+  { -1,                ""     },
+  { -1,                ""     },
+  { -1,                ""     },
+  { -1,                ""     }, /* 15 */
+  { -1,                ""     },
+  { -1,                ""     },
+  { -1,                ""     },
+  { -1,                ""     },
+  { -1,                ""     }, /* 20 */
+  { -1,                ""     },
+  { -1,                ""     },
+  { -1,                ""     },
+  { -1,                ""     },
+  { -1,                ""     }, /* 25 */
+  { -1,                ""     },
+  { -1,                ""     },
+  { -1,                ""     },
+  { -1,                ""     },
+  { SECT_EMPTY,        " "    }, /* 30 */
+  { SECT_STRANGE,      "@R?"  },
+  { SECT_HERE,         "@B!"  },
+};
+
+
+int map[MAX_MAP][MAX_MAP];
+int offsets[4][2] ={ {-2, 0},{ 0, 2},{ 2, 0},{ 0, -2} };
+int offsets_worldmap[4][2] ={ {-1, 0},{ 0, 1},{ 1, 0},{ 0, -1} };
+int door_offsets[6][2] ={ {-1, 0},{ 0, 1},{ 1, 0},{ 0, -1},{ -1, 1},{ 1, 1} };
+int door_marks[6] = { DOOR_NS, DOOR_EW, DOOR_NS, DOOR_EW, DOOR_UP, DOOR_DOWN };
+int vdoor_marks[4] = { VDOOR_NS, VDOOR_EW, VDOOR_NS, VDOOR_EW };
+
+bool can_see_map(struct char_data *ch) {
+  /* Is the map funcionality disabled? */
+  if (CONFIG_MAP == MAP_OFF)
+    return FALSE;
+  else if ((CONFIG_MAP == MAP_IMM_ONLY) && (GET_LEVEL(ch) < LVL_IMMORT))
+    return FALSE;
+
+  return TRUE;
+}
+
+/* MapArea function - create the actual map */
+void MapArea(room_rnum room, struct char_data *ch, int x, int y, int min, int max, sh_int xpos, sh_int ypos, bool worldmap)
+{
+  room_rnum prospect_room;
+  struct room_direction_data *pexit;
+  int door, ew_size=0, ns_size=0, x_exit_pos=0, y_exit_pos=0;
+  sh_int prospect_xpos, prospect_ypos;
+
+  if (map[x][y] < 0)
+    return; /* this is a door */
+
+  /* marks the room as visited */
+  if(room == IN_ROOM(ch))
+    map[x][y] = SECT_HERE;
+  else
+    map[x][y] = SECT(room);
+
+  if ( (x < min) || ( y < min) || ( x > max ) || ( y > max) ) return;
+
+  /* Check for exits */
+  for ( door = 0; door < MAX_MAP_DIR; door++ ) {
+
+    if( door < MAX_MAP_FOLLOW &&
+        xpos+door_offsets[door][0] >= 0 &&
+        xpos+door_offsets[door][0] <= ns_size &&
+        ypos+door_offsets[door][1] >= 0 &&
+        ypos+door_offsets[door][1] <= ew_size)
+    { /* Virtual exit */
+
+      map[x+door_offsets[door][0]][y+door_offsets[door][1]] = vdoor_marks[door] ;
+      if (map[x+offsets[door][0]][y+offsets[door][1]] == SECT_EMPTY )
+        MapArea(room,ch,x + offsets[door][0], y + offsets[door][1], min, max, xpos+door_offsets[door][0], ypos+door_offsets[door][1], worldmap);
+      continue;
+    }
+
+    if ( (pexit = world[room].dir_option[door]) > 0  &&
+         (pexit->to_room > 0 ) && (pexit->to_room != NOWHERE) &&
+         (!IS_SET(pexit->exit_info, EX_CLOSED))) { /* A real exit */
+
+      /* But is the door here... */
+      switch (door) {
+      case NORTH:
+        if(xpos > 0 || ypos!=y_exit_pos) continue;
+	break;
+      case SOUTH:
+        if(xpos < ns_size || ypos!=y_exit_pos) continue;
+	break;
+      case EAST:
+        if(ypos < ew_size || xpos!=x_exit_pos) continue;
+	break;
+      case WEST:
+        if(ypos > 0 || xpos!=x_exit_pos) continue;
+	break;
+      }
+
+
+ /*     if ( (x < min) || ( y < min) || ( x > max ) || ( y > max) ) return;*/
+      prospect_room = pexit->to_room;
+
+        /* one way into area OR maze */
+        if ( world[prospect_room].dir_option[rev_dir[door]] &&
+             world[prospect_room].dir_option[rev_dir[door]]->to_room != room) {
+          map[x][y] = SECT_STRANGE;
+        return;
+        }
+
+      if(!worldmap)
+        map[x+door_offsets[door][0]][y+door_offsets[door][1]] = door_marks[door] ;
+
+      prospect_xpos = prospect_ypos = 0;
+      switch (door) {
+      case NORTH:
+        prospect_xpos = ns_size;
+      case SOUTH:
+        prospect_ypos = world[prospect_room].dir_option[rev_dir[door]] ? y_exit_pos : ew_size/2;
+      break;
+      case WEST:
+        prospect_ypos = ew_size;
+      case EAST:
+        prospect_xpos = world[prospect_room].dir_option[rev_dir[door]] ? x_exit_pos : ns_size/2;
+      }
+
+      if(worldmap) {
+	if ( door < MAX_MAP_FOLLOW && map[x+offsets_worldmap[door][0]][y+offsets_worldmap[door][1]] == SECT_EMPTY )
+	  MapArea(pexit->to_room,ch,x + offsets_worldmap[door][0], y + offsets_worldmap[door][1], min, max, prospect_xpos, prospect_ypos, worldmap);
+      } else {
+	if ( door < MAX_MAP_FOLLOW && map[x+offsets[door][0]][y+offsets[door][1]] == SECT_EMPTY )
+	  MapArea(pexit->to_room,ch,x + offsets[door][0], y + offsets[door][1], min, max, prospect_xpos, prospect_ypos, worldmap);
+      }
+    } /* end if exit there */
+  }
+  return;
+}
+
+/* Returns a string representation of the map */
+char *StringMap(int centre, int size)
+{
+  static char strmap[MAX_MAP*MAX_MAP*11 + MAX_MAP*2 + 1];
+  char *mp = strmap;
+  char *tmp;
+  int x, y;
+
+  /* every row */
+  for (x = centre - CANVAS_HEIGHT/2; x <= centre + CANVAS_HEIGHT/2; x++) {
+    /* every column */
+    for (y = centre - CANVAS_WIDTH/6; y <= centre + CANVAS_WIDTH/6; y++) {
+      if (abs(centre - x)<=size && abs(centre-y)<=size)
+        tmp = (map[x][y]<0) ? \
+	      door_info[NUM_DOOR_TYPES + map[x][y]].disp : \
+	      map_info[map[x][y]].disp ;
+      else
+	tmp = map_info[SECT_EMPTY].disp;
+      strcpy(mp, tmp);
+      mp += strlen(tmp);
+    }
+    strcpy(mp, "\r\n");
+    mp+=2;
+  }
+  *mp='\0';
+  return strmap;
+}
+
+char *WorldMap(int centre, int size, int mapshape, int maptype )
+{
+  static char strmap[MAX_MAP*MAX_MAP*4 + MAX_MAP*2 + 1];
+  char *mp = strmap;
+  int x, y;
+  int xmin, xmax, ymin, ymax;
+
+  switch(maptype) {
+    case MAP_COMPACT:
+      xmin = centre - size;
+      xmax = centre + size;
+      ymin = centre - 2*size;
+      ymax = centre + 2*size;
+      break;
+    default:
+      xmin = centre - CANVAS_HEIGHT/2;
+      xmax = centre + CANVAS_HEIGHT/2;
+      ymin = centre - CANVAS_WIDTH/2;
+      ymax = centre + CANVAS_WIDTH/2;
+  }
+
+
+  /* every row */
+  /* for (x = centre - size; x <= centre + size; x++) { */
+  for (x = xmin; x <= xmax; x++) {
+    /* every column */
+    /* for (y = centre - (2*size) ; y <= centre + (2*size) ; y++) {  */
+    for (y = ymin ; y <= ymax ; y++) {
+
+      if((mapshape == MAP_RECTANGLE && abs(centre - y) <= size*2  && abs(centre - x) <= size ) ||
+	  ((mapshape == MAP_CIRCLE) && (centre-x)*(centre-x) + (centre-y)*(centre-y)/4 <= (size * size + 1))) {
+        strcpy(mp, world_map_info[map[x][y]].disp);
+        mp += strlen(world_map_info[map[x][y]].disp);
+      } else {
+	strcpy(mp++, " ");
+      }
+    }
+    strcpy(mp, "@n\r\n");
+    mp+=4;
+  }
+  *mp='\0';
+  return strmap;
+}
+
+char *CompactStringMap(int centre, int size)
+{
+  static char strmap[MAX_MAP*MAX_MAP*12 + MAX_MAP*2 + 1];
+  char *mp = strmap;
+  int x, y;
+
+  /* every row */
+  for (x = centre - size; x <= centre + size; x++) {
+    /* every column */
+    for (y = centre - size; y <= centre + size; y++) {
+      strcpy(mp, (map[x][y]<0) ? \
+	      compact_door_info[NUM_DOOR_TYPES + map[x][y]].disp : \
+	      map_info[map[x][y]].disp);
+      mp += strlen((map[x][y]<0) ? \
+	      compact_door_info[NUM_DOOR_TYPES + map[x][y]].disp : \
+	      map_info[map[x][y]].disp);
+    }
+    strcpy(mp, "\r\n");
+    mp+=2;
+  }
+  *mp='\0';
+  return strmap;
+}
+
+/* Display a nicely formatted map with a legend */
+void perform_map( struct char_data *ch, char *argument, bool worldmap )
+{
+  int size = DEFAULT_MAP_SIZE;
+  int centre, x, y, min, max;
+  char arg1[MAX_INPUT_LENGTH], arg2[MAX_INPUT_LENGTH], buf[MAX_STRING_LENGTH], buf1[MAX_STRING_LENGTH], buf2[MAX_STRING_LENGTH];
+  int count = 0;
+  int ew_size=0, ns_size=0;
+  int mapshape = MAP_CIRCLE;
+
+  two_arguments( argument, arg1 , arg2 );
+  if(*arg1)
+  {
+    size = atoi(arg1);
+  }
+  if (*arg2)
+  {
+    if (is_abbrev(arg2, "normal")) worldmap=FALSE;
+    else if (is_abbrev(arg2, "world")) worldmap=TRUE;
+    else {
+      send_to_char(ch, "Usage: @ymap <distance> [ normal | world ]@n");
+      return;
+    }
+  }
+
+  if(size<0) {
+    size = -size;
+    mapshape = MAP_RECTANGLE;
+  }
+  size = URANGE(1,size,MAX_MAP_SIZE);
+
+  centre = MAX_MAP/2;
+
+  if(worldmap) {
+    min = centre - 2*size;
+    max = centre + 2*size;
+  } else {
+    min = centre - size;
+    max = centre + size;
+  }
+
+  /* Blank the map */
+  for (x = 0; x < MAX_MAP; ++x)
+      for (y = 0; y < MAX_MAP; ++y)
+           map[x][y]= (!(y%2) && !worldmap) ? DOOR_NONE : SECT_EMPTY;
+
+  /* starts the mapping with the centre room */
+  MapArea(IN_ROOM(ch), ch, centre, centre, min, max, ns_size/2, ew_size/2, worldmap);
+
+  /* marks the center, where ch is */
+  map[centre][centre] = SECT_HERE;
+
+  /* Feel free to put your own MUD name or header in here */
+  send_to_char(ch, " @Y-@ytbaMUD Map System@Y-@n\r\n"
+                   "@D  .-.__--.,--.__.-.@n\r\n" );
+
+  count += sprintf(buf + count, "@n@n@n%s Up\\\\", door_info[NUM_DOOR_TYPES + DOOR_UP].disp);
+  count += sprintf(buf + count, "@n@n@n%s Down\\\\", door_info[NUM_DOOR_TYPES + DOOR_DOWN].disp);
+  count += sprintf(buf + count, "@n%s You\\\\", map_info[SECT_HERE].disp);
+  count += sprintf(buf + count, "@n%s Inside\\\\", map_info[SECT_INSIDE].disp);
+  count += sprintf(buf + count, "@n%s City\\\\", map_info[SECT_CITY].disp);
+  count += sprintf(buf + count, "@n%s Field\\\\", map_info[SECT_FIELD].disp);
+  count += sprintf(buf + count, "@n%s Forest\\\\", map_info[SECT_FOREST].disp);
+  count += sprintf(buf + count, "@n%s Hills\\\\", map_info[SECT_HILLS].disp);
+  count += sprintf(buf + count, "@n%s Mountain\\\\", map_info[SECT_MOUNTAIN].disp);
+  count += sprintf(buf + count, "@n%s Swim\\\\", map_info[SECT_WATER_SWIM].disp);
+  count += sprintf(buf + count, "@n%s Boat\\\\", map_info[SECT_WATER_NOSWIM].disp);
+  count += sprintf(buf + count, "@n%s Flying\\\\", map_info[SECT_FLYING].disp);
+  count += sprintf(buf + count, "@n%s Underwater\\\\", map_info[SECT_UNDERWATER].disp);
+
+  strcpy(buf, strfrmt(buf, LEGEND_WIDTH, CANVAS_HEIGHT + 2, FALSE, TRUE, TRUE));
+
+  /* Start with an empty column */
+  strcpy(buf1, strfrmt("",0, CANVAS_HEIGHT + 2, FALSE, FALSE, TRUE));
+
+  /* Paste the legend */
+  strcpy(buf2, strpaste(buf1, buf, "@D | @n"));
+
+  /* Set up the map */
+  memset(buf, ' ', CANVAS_WIDTH);
+  count = (CANVAS_WIDTH);
+  if(worldmap)
+    count += sprintf(buf + count , "\r\n%s", WorldMap(centre, size, mapshape, MAP_NORMAL));
+  else
+    count += sprintf(buf + count , "\r\n%s", StringMap(centre, size));
+  memset(buf + count, ' ', CANVAS_WIDTH);
+  strcpy(buf + count + CANVAS_WIDTH, "\r\n");
+  /* Paste it on */
+  strcpy(buf2, strpaste(buf2, buf, "@D | @n"));
+  /* Paste on the right border */
+  strcpy(buf2, strpaste(buf2, buf1, "  "));
+  /* Print it all out */
+  send_to_char(ch, buf2);
+
+  send_to_char(ch, "@D `.-.__--.,-.__.-.-'@n\r\n");
+  return;
+}
+
+/* Display a string with the map beside it */
+void str_and_map(char *str, struct char_data *ch ) {
+  int size, centre, x, y, min, max, char_size;
+  int ew_size=0, ns_size=0;
+  bool worldmap;
+
+  /* Check MUDs map config options - if disabled, just show room decsription */
+  if (!can_see_map(ch)) {
+    send_to_char(ch, strfrmt(str, GET_SCREEN_WIDTH(ch), 1, FALSE, FALSE, FALSE));
+    return;
+  }
+
+  worldmap = ROOM_FLAGGED(IN_ROOM(ch), ROOM_WORLDMAP) ? TRUE : FALSE ;
+
+  if(!PRF_FLAGGED(ch, PRF_AUTOMAP)) {
+    send_to_char(ch, strfrmt(str, GET_SCREEN_WIDTH(ch), 1, FALSE, FALSE, FALSE));
+    return;
+  }
+
+  size = CONFIG_MINIMAP_SIZE;
+  centre = MAX_MAP/2;
+  min = centre - 2*size;
+  max = centre + 2*size;
+
+  for (x = 0; x < MAX_MAP; ++x)
+    for (y = 0; y < MAX_MAP; ++y)
+      map[x][y]= (!(y%2) && !worldmap) ? DOOR_NONE : SECT_EMPTY;
+
+  /* starts the mapping with the center room */
+  MapArea(IN_ROOM(ch), ch, centre, centre, min, max, ns_size/2, ew_size/2, worldmap );
+  map[centre][centre] = SECT_HERE;
+
+  /* char_size = rooms + doors + padding */
+  if(worldmap)
+    char_size = size * 4 + 5;
+  else
+    char_size = 3*(size+1) + (size) + 4;
+
+  if(worldmap)
+    send_to_char(ch, strpaste(strfrmt(str, GET_SCREEN_WIDTH(ch) - char_size, size*2 + 1, FALSE, TRUE, TRUE), WorldMap(centre, size, MAP_CIRCLE, MAP_COMPACT), "   "));
+  else
+    send_to_char(ch, strpaste(strfrmt(str, GET_SCREEN_WIDTH(ch) - char_size, size*2 + 1, FALSE, TRUE, TRUE), CompactStringMap(centre, size), "   "));
+
+}
+
+ACMD(do_map) {
+  if (!can_see_map(ch)) {
+    send_to_char(ch, "Sorry, the map is disabled!\r\n");
+    return;
+  }
+  perform_map(ch, argument, ROOM_FLAGGED(IN_ROOM(ch), ROOM_WORLDMAP) ? 1 : 0 );
+}
+
+
diff -BbuprN tbamud-3.55/src/cedit.c tbamud-3.55+automap/src/cedit.c
--- tbamud-3.55/src/cedit.c	2008-01-16 23:21:14.000000000 +0000
+++ tbamud-3.55+automap/src/cedit.c	2008-02-05 20:19:50.569422000 +0000
@@ -103,6 +103,9 @@ void cedit_setup(struct descriptor_data 
   OLC_CONFIG(d)->play.track_through_doors = CONFIG_TRACK_T_DOORS;
   OLC_CONFIG(d)->play.no_mort_to_immort   = CONFIG_NO_MORT_TO_IMMORT;
   OLC_CONFIG(d)->play.disp_closed_doors   = CONFIG_DISP_CLOSED_DOORS;
+  OLC_CONFIG(d)->play.map_option          = CONFIG_MAP;
+  OLC_CONFIG(d)->play.map_size            = CONFIG_MAP_SIZE;
+  OLC_CONFIG(d)->play.minimap_size        = CONFIG_MINIMAP_SIZE;
 
   /* Crash Saves */
   OLC_CONFIG(d)->csd.free_rent            = CONFIG_FREE_RENT;
@@ -196,6 +199,9 @@ void cedit_save_internally(struct descri
   CONFIG_TRACK_T_DOORS = OLC_CONFIG(d)->play.track_through_doors;
   CONFIG_NO_MORT_TO_IMMORT   = OLC_CONFIG(d)->play.no_mort_to_immort;
   CONFIG_DISP_CLOSED_DOORS   = OLC_CONFIG(d)->play.disp_closed_doors;
+  CONFIG_MAP                 = OLC_CONFIG(d)->play.map_option;
+  CONFIG_MAP_SIZE            = OLC_CONFIG(d)->play.map_size;
+  CONFIG_MINIMAP_SIZE        = OLC_CONFIG(d)->play.minimap_size;
 
   /* Crash Saves */
   CONFIG_FREE_RENT            = OLC_CONFIG(d)->csd.free_rent;
@@ -354,6 +360,12 @@ int save_config( IDXTYPE nowhere )
               "no_mort_to_immort = %d\n\n", CONFIG_NO_MORT_TO_IMMORT);
   fprintf(fl, "* Should closed doors be shown on autoexit / exit?\n"
               "disp_closed_doors = %d\n\n", CONFIG_DISP_CLOSED_DOORS);
+  fprintf(fl, "* Who can use the map functions? 0=off, 1=on, 2=imm_only\n"
+              "map_option = %d\n\n", CONFIG_MAP);
+  fprintf(fl, "* Default size of map shown by 'map' command\n"
+              "default_map_size = %d\n\n", CONFIG_MAP_SIZE);
+  fprintf(fl, "* Default minimap size shown to the right of room descriptions\n"
+              "default_minimap_size = %d\n\n", CONFIG_MINIMAP_SIZE);
 
   strcpy(buf, CONFIG_OK);
   strip_cr(buf);
@@ -553,9 +565,12 @@ void cedit_disp_menu(struct descriptor_d
 
 void cedit_disp_game_play_options(struct descriptor_data *d)
 {
+  int m_opt;
   get_char_colors(d->character);
   clear_screen(d);
 
+  m_opt = OLC_CONFIG(d)->play.map_option;
+
   write_to_output(d, "\r\n\r\n"
         "%sA%s) Player Killing Allowed  : %s%s\r\n"
         "%sB%s) Player Thieving Allowed : %s%s\r\n"
@@ -577,6 +592,9 @@ void cedit_disp_game_play_options(struct
 	"%s1%s) OK Message Text         : %s%s"
         "%s2%s) NOPERSON Message Text   : %s%s"
         "%s3%s) NOEFFECT Message Text   : %s%s"
+        "%s4%s) Map/Automap Option      : %s%s\r\n"
+        "%s5%s) Default map size        : %s%d\r\n"
+        "%s6%s) Default minimap size    : %s%d\r\n"
         "%sQ%s) Exit To The Main Menu\r\n"
         "Enter your choice : ",
         grn, nrm, cyn, CHECK_VAR(OLC_CONFIG(d)->play.pk_allowed),
@@ -601,6 +619,9 @@ void cedit_disp_game_play_options(struct
         grn, nrm, cyn, OLC_CONFIG(d)->play.OK,
         grn, nrm, cyn, OLC_CONFIG(d)->play.NOPERSON,
         grn, nrm, cyn, OLC_CONFIG(d)->play.NOEFFECT,
+        grn, nrm, cyn, m_opt == 0 ? "Off" : (m_opt == 1 ? "On" : (m_opt == 2 ? "Imm-Only" : "Invalid!")),
+        grn, nrm, cyn, OLC_CONFIG(d)->play.map_size,
+        grn, nrm, cyn, OLC_CONFIG(d)->play.minimap_size,
 
         grn, nrm
         );
@@ -910,6 +931,24 @@ void cedit_parse(struct descriptor_data 
           OLC_MODE(d) = CEDIT_NOEFFECT;
           return;
 
+        case '4':
+          write_to_output(d, "1) Disable maps\r\n");
+          write_to_output(d, "2) Enable Maps\r\n");
+          write_to_output(d, "3) Maps for Immortals only\r\n");
+          write_to_output(d, "Enter choice: ");
+          OLC_MODE(d) = CEDIT_MAP_OPTION;
+          return;
+
+        case '5':
+          write_to_output(d, "Enter default map size (1-12) : ");
+          OLC_MODE(d) = CEDIT_MAP_SIZE;
+          return;
+
+        case '6':
+          write_to_output(d, "Enter default mini-map size (1-12) : ");
+          OLC_MODE(d) = CEDIT_MINIMAP_SIZE;
+          return;
+
         case 'q':
         case 'Q':
           cedit_disp_menu(d);
@@ -1522,6 +1561,40 @@ void cedit_parse(struct descriptor_data 
       }
       break;
 
+    case CEDIT_MAP_OPTION:
+      if (!*arg) {
+        write_to_output(d,
+          "That is an invalid choice!\r\n"
+          "Select 1, 2 or 3 (0 to cancel) :");
+      } else {
+        if ((atoi(arg) >= 1) && (atoi(arg) <= 3))
+          OLC_CONFIG(d)->play.map_option = (atoi(arg) - 1);
+        cedit_disp_game_play_options(d);
+      }
+      break;
+
+    case CEDIT_MAP_SIZE:
+      if (!*arg) {
+		/* User just pressed return - restore to default */
+        OLC_CONFIG(d)->play.map_size = 6;
+        cedit_disp_game_play_options(d);
+      } else {
+        OLC_CONFIG(d)->play.map_size = MIN(MAX((atoi(arg)), 1), 12);
+        cedit_disp_game_play_options(d);
+      }
+      break;
+
+    case CEDIT_MINIMAP_SIZE:
+      if (!*arg) {
+		/* User just pressed return - restore to default */
+        OLC_CONFIG(d)->play.minimap_size = 2;
+        cedit_disp_game_play_options(d);
+      } else {
+        OLC_CONFIG(d)->play.minimap_size = MIN(MAX((atoi(arg)), 1), 12);
+        cedit_disp_game_play_options(d);
+      }
+      break;
+
     default:  /* We should never get here, but just in case... */
       cleanup_olc(d, CLEANUP_CONFIG);
       mudlog(BRF, LVL_BUILDER, TRUE, "SYSERR: OLC: cedit_parse(): Reached default case!");
diff -BbuprN tbamud-3.55/src/config.c tbamud-3.55+automap/src/config.c
--- tbamud-3.55/src/config.c	2008-01-16 23:21:14.000000000 +0000
+++ tbamud-3.55+automap/src/config.c	2008-02-05 15:00:09.663172000 +0000
@@ -302,3 +302,9 @@ int min_wizlist_lev = LVL_GOD;
 /* To mimic stock behavior set to NO. To allow mortals to see doors in exits
  * set to YES. */
 int display_closed_doors = YES;
+
+/* Automap and map options */
+/* Default is to have automap and map command enabled for all players and immortals */
+int map_option = MAP_ON;
+int default_map_size = 6;
+int default_minimap_size = 2;
diff -BbuprN tbamud-3.55/src/constants.c tbamud-3.55+automap/src/constants.c
--- tbamud-3.55/src/constants.c	2008-01-16 23:21:16.000000000 +0000
+++ tbamud-3.55+automap/src/constants.c	2008-02-05 22:12:26.819422000 +0000
@@ -50,6 +50,7 @@ const char *room_bits[] = {
   "ATRIUM",
   "OLC",
   "*",				/* BFS MARK */
+  "WORLDMAP",
   "\n"
 };
 
@@ -184,6 +185,7 @@ const char *preference_bits[] = {
   "AUTOSPLIT",
   "AUTOSAC",
   "AUTOASSIST",
+  "AUTOMAP",
   "\n"
 };
 
diff -BbuprN tbamud-3.55/src/db.c tbamud-3.55+automap/src/db.c
--- tbamud-3.55/src/db.c	2008-01-16 23:21:14.000000000 +0000
+++ tbamud-3.55+automap/src/db.c	2008-02-05 18:50:11.538172000 +0000
@@ -3044,6 +3044,7 @@ void init_char(struct char_data *ch)
     GET_COND(ch, i) = (GET_LEVEL(ch) == LVL_IMPL ? -1 : 24);
 
   GET_LOADROOM(ch) = NOWHERE;
+  GET_SCREEN_WIDTH(ch) = PAGE_WIDTH;
 }
 
 /* returns the real number of the room with given virtual number */
@@ -3340,6 +3341,9 @@ extern int min_wizlist_lev;
 extern const char *OK;
 extern const char *NOPERSON;
 extern const char *NOEFFECT;
+extern int map_option;
+extern int default_map_size;
+extern int default_minimap_size;
 
 void load_default_config( void )
 {
@@ -3366,6 +3370,9 @@ void load_default_config( void )
   CONFIG_TRACK_T_DOORS          = track_through_doors;
   CONFIG_NO_MORT_TO_IMMORT	= no_mort_to_immort;
   CONFIG_DISP_CLOSED_DOORS      = display_closed_doors;
+  CONFIG_MAP                    = map_option;
+  CONFIG_MAP_SIZE               = default_map_size;
+  CONFIG_MINIMAP_SIZE           = default_minimap_size;
 
   /* Rent / crashsave options. */
   CONFIG_FREE_RENT              = free_rent;
@@ -3488,6 +3495,10 @@ void load_config( void )
             CONFIG_DFLT_IP = NULL;
         } else if (!str_cmp(tag, "dflt_port"))
           CONFIG_DFLT_PORT = num;
+        else if (!str_cmp(tag, "default_map_size"))
+          CONFIG_MAP_SIZE = num;
+        else if (!str_cmp(tag, "default_minimap_size"))
+          CONFIG_MINIMAP_SIZE = num;
         break;
 
       case 'f':
@@ -3558,6 +3569,8 @@ void load_config( void )
           CONFIG_MIN_WIZLIST_LEV = num;
         else if (!str_cmp(tag, "mortal_start_room"))
           CONFIG_MORTAL_START = num;
+        else if (!str_cmp(tag, "map_option"))
+          CONFIG_MAP = num;
         break;
 
       case 'n':
diff -BbuprN tbamud-3.55/src/interpreter.c tbamud-3.55+automap/src/interpreter.c
--- tbamud-3.55/src/interpreter.c	2008-01-16 23:27:40.000000000 +0000
+++ tbamud-3.55+automap/src/interpreter.c	2008-02-05 19:56:41.522547000 +0000
@@ -131,6 +131,7 @@ ACMD(do_levels);
 ACMD(do_links);
 ACMD(do_load);
 ACMD(do_look);
+ACMD(do_map);
 ACMD(do_masound);
 ACMD(do_mat);
 ACMD(do_mdamage);
@@ -360,6 +361,7 @@ cpp_extern const struct command_info cmd
 
   { "motd"     , "motd"    , POS_DEAD    , do_gen_ps   , 0, SCMD_MOTD },
   { "mail"     , "mail"    , POS_STANDING, do_not_here , 1, 0 },
+  { "map"      , "map"     , POS_STANDING, do_map      , 1, 0 },
   { "medit"    , "med"     , POS_DEAD    , do_oasis_medit, LVL_BUILDER, 0 },
   { "mlist"    , "mlist"   , POS_DEAD    , do_oasis_list , LVL_BUILDER, SCMD_OASIS_MLIST },
   { "mcopy"    , "mcopy"   , POS_DEAD    , do_oasis_copy, LVL_GOD, CON_MEDIT },
diff -BbuprN tbamud-3.55/src/interpreter.h tbamud-3.55+automap/src/interpreter.h
--- tbamud-3.55/src/interpreter.h	2008-01-16 23:21:16.000000000 +0000
+++ tbamud-3.55+automap/src/interpreter.h	2008-02-05 19:45:47.225672000 +0000
@@ -121,6 +121,13 @@ struct alias_data {
 #define SCMD_SYSLOG     21
 #define SCMD_WIMPY      22
 #define SCMD_PAGELENGTH 23
+#define SCMD_AUTOLOOT   24
+#define SCMD_AUTOGOLD   25
+#define SCMD_AUTOSPLIT  26
+#define SCMD_AUTOSAC    27
+#define SCMD_AUTOASSIST 28
+#define SCMD_SCREENWIDTH 29
+#define SCMD_AUTOMAP    30
 
 /* do_wizutil */
 #define SCMD_REROLL	0
diff -BbuprN tbamud-3.55/src/oasis.h tbamud-3.55+automap/src/oasis.h
--- tbamud-3.55/src/oasis.h	2008-01-16 23:21:16.000000000 +0000
+++ tbamud-3.55+automap/src/oasis.h	2008-02-05 20:05:30.881922000 +0000
@@ -17,7 +17,7 @@
 
 /* Macros, defines, structs and globals for the OLC suite.  You will need
    to adjust these numbers if you ever add more. */
-#define NUM_ROOM_FLAGS 		16
+#define NUM_ROOM_FLAGS 		17
 #define NUM_ROOM_SECTORS	10
 
 #define NUM_MOB_FLAGS		18
@@ -355,6 +355,9 @@ extern const char *nrm, *grn, *cyn, *yel
 #define CEDIT_NAMESERVER_IS_SLOW	51
 #define CEDIT_USE_AUTOWIZ		52
 #define CEDIT_MIN_WIZLIST_LEV		53
+#define CEDIT_MAP_OPTION		54
+#define CEDIT_MAP_SIZE			55
+#define CEDIT_MINIMAP_SIZE		56
 
 /* Hedit Submodes of connectedness. */
 #define HEDIT_CONFIRM_SAVESTRING        0
diff -BbuprN tbamud-3.55/src/pfdefaults.h tbamud-3.55+automap/src/pfdefaults.h
--- tbamud-3.55/src/pfdefaults.h	2008-01-16 23:21:16.000000000 +0000
+++ tbamud-3.55+automap/src/pfdefaults.h	2008-02-05 18:01:18.991297000 +0000
@@ -50,6 +50,7 @@
 #define PFDEF_DRUNK		0
 #define PFDEF_OLC               NOWHERE 
 #define PFDEF_PAGELENGTH        22
+#define PFDEF_SCREENWIDTH       80
 #define PFDEF_QUESTPOINTS       0
 
 #endif
diff -BbuprN tbamud-3.55/src/players.c tbamud-3.55+automap/src/players.c
--- tbamud-3.55/src/players.c	2008-01-16 23:21:14.000000000 +0000
+++ tbamud-3.55+automap/src/players.c	2008-02-05 18:30:24.413172000 +0000
@@ -260,6 +260,7 @@ int load_char(const char *name, struct c
     GET_MAX_MOVE(ch) = PFDEF_MAXMOVE;
     GET_OLC_ZONE(ch) = PFDEF_OLC;
     GET_PAGE_LENGTH(ch) = PFDEF_PAGELENGTH;
+    GET_SCREEN_WIDTH(ch) = PFDEF_SCREENWIDTH;
     GET_ALIASES(ch) = NULL;
     SITTING(ch) = NULL;
     NEXT_SITTING(ch) = NULL;
@@ -395,6 +396,7 @@ int load_char(const char *name, struct c
 
       case 'S':
 	     if (!strcmp(tag, "Sex "))	GET_SEX(ch)		= atoi(line);
+	else if (!strcmp(tag, "ScrW"))	GET_SCREEN_WIDTH(ch) = atoi(line);
 	else if (!strcmp(tag, "Skil"))	load_skills(fl, ch);
 	else if (!strcmp(tag, "Str "))	load_HMVS(ch, line, LOAD_STRENGTH);
 	break;
@@ -598,6 +600,7 @@ void save_char(struct char_data * ch)
   if (GET_DAMROLL(ch)	   != PFDEF_DAMROLL)	fprintf(fl, "Drol: %d\n", GET_DAMROLL(ch));
   if (GET_OLC_ZONE(ch)     != PFDEF_OLC)        fprintf(fl, "Olc : %d\n", GET_OLC_ZONE(ch));
   if (GET_PAGE_LENGTH(ch)  != PFDEF_PAGELENGTH) fprintf(fl, "Page: %d\n", GET_PAGE_LENGTH(ch));
+  if (GET_SCREEN_WIDTH(ch) != PFDEF_SCREENWIDTH) fprintf(fl, "ScrW: %d\n", GET_SCREEN_WIDTH(ch));
   if (GET_QUESTPOINTS(ch)  != PFDEF_QUESTPOINTS) fprintf(fl, "Qstp: %d\n", GET_QUESTPOINTS(ch));
 
   /* Save skills */
diff -BbuprN tbamud-3.55/src/structs.h tbamud-3.55+automap/src/structs.h
--- tbamud-3.55/src/structs.h	2008-01-16 23:21:16.000000000 +0000
+++ tbamud-3.55+automap/src/structs.h	2008-02-05 20:05:12.647547000 +0000
@@ -69,6 +69,7 @@
 #define ROOM_ATRIUM        13   /* (R) The door to a house */
 #define ROOM_OLC           14   /* (R) Modifyable/!compress */
 #define ROOM_BFS_MARK      15   /* (R) breath-first srch mrk */
+#define ROOM_WORLDMAP      16   /* World-map style maps here */
 
 /* Exit info: used in room_data.dir_option.exit_info */
 #define EX_ISDOOR		(1 << 0)   /* Exit is a door		*/
@@ -208,7 +209,8 @@
 #define PRF_AUTOSPLIT    28   /* Split gold with group */
 #define PRF_AUTOSAC      29   /* Sacrifice a corpse */
 #define PRF_AUTOASSIST   30   /* Auto-assist toggle */
-#define NUM_PRF_FLAGS    31
+#define PRF_AUTOMAP      31   /* Show map at the side of room descs */
+#define NUM_PRF_FLAGS    32
 
 /* Affect bits: used in char_data.char_specials.saved.affected_by */
 /* WARNING: In the world files, NEVER set the bits marked "R" ("Reserved") */
@@ -456,6 +458,11 @@
 #define NUM_OF_DIRS	6	/* number of directions in a room (nsewud) */
 #define MAGIC_NUMBER	(0x06)	/* Arbitrary number that won't be in a string */
 
+/* Map options (settable in cedit) */
+#define MAP_OFF      0
+#define MAP_ON       1
+#define MAP_IMM_ONLY 2
+
 /* OPT_USEC determines how many commands will be processed by the MUD per
  * second and how frequently it does socket I/O.  A low setting will cause
  * actions to be executed more frequently but will increase overhead due to
@@ -772,6 +779,7 @@ struct player_special_data_saved {
    sbyte conditions[3];         /* Drunk, hunger, thirst */
    struct txt_block *comm_hist[NUM_HIST]; /* Player's comms history */
    ubyte page_length;           /* How long a players page is */
+   ubyte screen_width;          /* How wide a players page is */
    int spells_to_learn;         /* How many spells you can learn */
    int olc_zone;                /* A players olc access */
    int questpoints;             /* A players questpoints earned */
@@ -1047,6 +1055,9 @@ struct game_data {
   int track_through_doors;/* Track through doors while closed?    */
   int no_mort_to_immort;  /* Prevent mortals leveling to imms?    */
   int disp_closed_doors;  /* Display closed doors in autoexit?    */
+  int map_option;         /* MAP_ON, MAP_OFF or MAP_IMM_ONLY      */
+  int map_size;           /* Default size for map command         */
+  int minimap_size;       /* Default size for mini-map (automap)  */
 
   char *OK;               /* When player receives 'Okay.' text.	  */
   char *NOPERSON;         /* 'No one by that name here.'	  */
diff -BbuprN tbamud-3.55/src/utils.c tbamud-3.55+automap/src/utils.c
--- tbamud-3.55/src/utils.c	2008-01-16 23:21:14.000000000 +0000
+++ tbamud-3.55+automap/src/utils.c	2008-02-05 20:07:40.569422000 +0000
@@ -735,3 +735,170 @@ void char_from_furniture(struct char_dat
 
  return;
 }
+
+/*
+   strfrmt (String Format) function
+   Used by automap/map system
+   Re-formats a string to fit within a particular size box.
+   Recognises @ color codes, and if a line ends in one color, the
+   next line will start with the same color.
+   Ends every line with @n to prevent color bleeds.
+*/
+char *strfrmt(char *str, int w, int h, int justify, int hpad, int vpad)
+{
+  static char ret[MAX_STRING_LENGTH];
+  char line[MAX_INPUT_LENGTH];
+  char *sp = str;
+  char *lp = line;
+  char *rp = ret;
+  char *wp;
+  int wlen = 0, llen = 0, lcount = 0;
+  char last_color='n';
+  bool new_line_started = FALSE;
+
+  memset(line, '\0', MAX_INPUT_LENGTH);
+  /* Nomalize spaces and newlines */
+  /* Split into lines, including convert \\ into \r\n */
+  while(*sp) {
+    /* eat leading space */
+    while(*sp && isspace(*sp)) sp++;
+    /* word begins */
+    wp = sp;
+    wlen = 0;
+    while(*sp) { /* Find the end of the word */
+      if(isspace(*sp)) break;
+      if(*sp=='\\' && sp[1] && sp[1]=='\\') {
+        if(sp!=wp)
+          break; /* Finish dealing with the current word */
+        sp += 2; /* Eat the marker and any trailing space */
+        while(*sp && isspace(*sp)) sp++;
+        wp = sp;
+        /* Start a new line */
+        if(hpad)
+          for(; llen < w; llen++)
+            *lp++ = ' ';
+        *lp++ = '\r';
+        *lp++ = '\n';
+        *lp++ = '\0';
+        rp += sprintf(rp, "%s", line);
+        llen = 0;
+        lcount++;
+        lp = line;
+      } else if (*sp=='`'||*sp=='$'||*sp=='#'||*sp=='@') {
+        if (sp[1] && (sp[1]==*sp))
+          wlen++; /* One printable char here */
+        if (*sp=='@' && (sp[1]!=*sp)) /* Color code, not @@ */
+          last_color = sp[1];
+        sp += 2; /* Eat the whole code regardless */
+      } else {
+        wlen++;
+        sp++;
+      }
+    }
+    if(llen + wlen + (lp==line ? 0 : 1) > w) {
+      /* Start a new line */
+      if(hpad)
+        for(; llen < w; llen++)
+          *lp++ = ' ';
+      *lp++ = '@';  /* 'normal' color */
+      *lp++ = 'n';
+      *lp++ = '\r'; /* New line */
+      *lp++ = '\n';
+      *lp++ = '\0';
+      sprintf(rp, "%s", line);
+      rp += strlen(line);
+      llen = 0;
+      lcount++;
+      lp = line;
+      if (last_color != 'n') {
+        *lp++ = '@';  /* restore previous color */
+        *lp++ = last_color;
+        new_line_started = TRUE;
+      }
+    }
+    /* add word to line */
+    if (lp!=line && new_line_started!=TRUE) {
+      *lp++ = ' ';
+      llen++;
+    }
+    new_line_started = FALSE;
+    llen += wlen ;
+    for( ; wp!=sp ; *lp++ = *wp++);
+  }
+  /* Copy over the last line */
+  if(lp!=line) {
+    if(hpad)
+      for(; llen < w; llen++)
+        *lp++ = ' ';
+    *lp++ = '\r';
+    *lp++ = '\n';
+    *lp++ = '\0';
+    sprintf(rp, "%s", line);
+    rp += strlen(line);
+    lcount++;
+  }
+  if(vpad) {
+    while(lcount < h) {
+      if(hpad) {
+        memset(rp, ' ', w);
+        rp += w;
+      }
+      *rp++ = '\r';
+      *rp++ = '\n';
+      lcount++;
+    }
+    *rp = '\0';
+  }
+  return ret;
+}
+
+/*
+   strpaste (String Paste) function
+   Takes two long strings (multiple lines) and joins them side-by-side.
+   Used by the automap/map system
+*/
+char *strpaste(char *str1, char *str2, char *joiner)
+{
+  static char ret[MAX_STRING_LENGTH+1];
+  char *sp1 = str1;
+  char *sp2 = str2;
+  char *rp = ret;
+  int jlen = strlen(joiner);
+
+  while((rp - ret) < MAX_STRING_LENGTH && (*sp1 || *sp2)) {
+     /* Copy line from str1 */
+    while((rp - ret) < MAX_STRING_LENGTH && *sp1 && !ISNEWL(*sp1))
+      *rp++ = *sp1++;
+    /* Eat the newline */
+    if(*sp1) {
+      if(sp1[1] && sp1[1]!=sp1[0] && ISNEWL(sp1[1]))
+        sp1++;
+      sp1++;
+    }
+
+    /* Add the joiner */
+    if((rp - ret) + jlen >= MAX_STRING_LENGTH)
+      break;
+    strcpy(rp, joiner);
+    rp += jlen;
+
+     /* Copy line from str2 */
+    while((rp - ret) < MAX_STRING_LENGTH && *sp2 && !ISNEWL(*sp2))
+      *rp++ = *sp2++;
+    /* Eat the newline */
+    if(*sp2) {
+      if(sp2[1] && sp2[1]!=sp2[0] && ISNEWL(sp2[1]))
+        sp2++;
+      sp2++;
+    }
+
+    /* Add the newline */
+    if((rp - ret) + 2 >= MAX_STRING_LENGTH)
+      break;
+    *rp++ = '\r';
+    *rp++ = '\n';
+  }
+  /* Close off the string */
+  *rp = '\0';
+  return ret;
+}
diff -BbuprN tbamud-3.55/src/utils.h tbamud-3.55+automap/src/utils.h
--- tbamud-3.55/src/utils.h	2008-01-16 23:21:14.000000000 +0000
+++ tbamud-3.55+automap/src/utils.h	2008-02-05 20:12:11.928797000 +0000
@@ -36,6 +36,8 @@ void	core_dump_real(const char *who, int
 int     count_color_chars(char *string);
 int	room_is_dark(room_rnum room);
 int     levenshtein_distance(char *s1, char *s2);
+char *strfrmt(char *str, int w, int h, int justify, int hpad, int vpad);
+char *strpaste(char *str1, char *str2, char *joiner);
 
 #define core_dump()		core_dump_real(__FILE__, __LINE__)
 
@@ -131,6 +133,10 @@ void char_from_furniture(struct char_dat
 #define SECS_PER_REAL_DAY	(24*SECS_PER_REAL_HOUR)
 #define SECS_PER_REAL_YEAR	(365*SECS_PER_REAL_DAY)
 
+/* integer utils */
+
+#define URANGE(a, b, c)          ((b) < (a) ? (a) : ((b) > (c) ? (c) : (b)))
+
 /* string utils */
 #define YESNO(a) ((a) ? "YES" : "NO")
 #define ONOFF(a) ((a) ? "ON" : "OFF")
@@ -316,6 +322,7 @@ void char_from_furniture(struct char_dat
 #define GET_HOST(ch)		CHECK_PLAYER_SPECIAL((ch), ((ch)->player_specials->host))
 #define GET_HISTORY(ch, i)      CHECK_PLAYER_SPECIAL((ch), ((ch)->player_specials->saved.comm_hist[i]))
 #define GET_PAGE_LENGTH(ch)     CHECK_PLAYER_SPECIAL((ch), ((ch)->player_specials->saved.page_length))
+#define GET_SCREEN_WIDTH(ch)    CHECK_PLAYER_SPECIAL((ch), ((ch)->player_specials->saved.screen_width))
 #define GET_QUESTPOINTS(ch)     CHECK_PLAYER_SPECIAL((ch), ((ch)->player_specials->saved.questpoints))
 
 #define GET_SKILL(ch, i)	CHECK_PLAYER_SPECIAL((ch), ((ch)->player_specials->saved.skills[i]))
@@ -549,6 +556,11 @@ void char_from_furniture(struct char_dat
 #define CONFIG_NOEFFECT         config_info.play.NOEFFECT
 #define CONFIG_DISP_CLOSED_DOORS config_info.play.disp_closed_doors
 
+/* Map/Automap options */
+#define CONFIG_MAP             config_info.play.map_option
+#define CONFIG_MAP_SIZE        config_info.play.map_size
+#define CONFIG_MINIMAP_SIZE    config_info.play.minimap_size
+
 /* Crash Saves */
 #define CONFIG_FREE_RENT        config_info.csd.free_rent
 #define CONFIG_MAX_OBJ_SAVE     config_info.csd.max_obj_save
