/* v5.00 SHIPS 'AHOY! * (c) Angel, Feb 1995. * Original code from Angel, Jan 1995 * Based on similar concept of automatic shuttle craft from numerous TREKmuds */ #include <mudlib.h> /*****************************************************************************/ /* Global Defines */ #define SHIP_NAME capitalize((string)this_object()->query_ship_name()) #define NAME (string)this_player()->query_name() #define PORTS_OF_CALL ({\ ({ "angel's workroom", "/players/angel/workroom", ({ 100, 200, 300, }), }),\ ({ "tempus square", "/room/city/square", ({ 200, 100, 100, }), }),\ ({ "tempus jetty", "/room/city/jetty", ({ 300, 100, 200, }), }),\ }) #define DESTINATION_FILE "/room/city/ships/room" #define SCI_FI #ifdef SCI_FI #define DESTINATION_NAME "empty space" #define SCRIPT_FILE "/room/ships/space.txt" #else #define DESTINATION_NAME "the high seas" #define SCRIPT_FILE "/room/ships/sea.txt" #endif /* SCI_FI */ #ifdef SCI_FI #define MAX_WARP 10 #define WARP_SPEED 10 #define IMPULSE_POWER 4 #endif /* SCI_FI */ #define WAIT_TIME 30 /* seconds until we go again */ #define PLACE 0 /* array element for place name */ #define FILE 1 /* array element for file name */ #define XYZ 2 /* array element for xyz coords */ #define X 0 /* array elements of x xyz co-arr */ #define Y 1 /* array elements of y xyz co-arr */ #define Z 2 /* array elements of z xyz co-arr */ /***************************************************************************/ status automated; /* does the ship go by itself? */ status waiting; /* is the ship waiting to go? */ int counter; /* for automated travel array */ int distance; /* distance to target */ int timer; /* heart beat timer */ int speed; /* how fast we're going */ int x1, y1, z1, x2, y2, z2; /* handy coord ints */ int *my_coordinates; /* where I am now */ int *destination_coordinates; /* where I am going to dock */ int *old_destination_coordinates; /* where I was docked before */ string destination; /* name of the place we're off to */ string destination_file; /* file of the place we're off to */ string ship_name; /* name of the ship! */ /***************************************************************************/ /* Prototypes */ void msg(string str); void ship_travel(int *coords); int calc_distance(int *coordinates1, int *coordinates2); int square_root(int i); status ship_board(string str); status ship_disembark(); status ship_engage(); status ship_input(string str); /***************************************************************************/ inherit ROOM; void reset(status arg) { string txt; int i, j, k; mixed *data; #define SHORT 1 #define LONG 2 #define ITEMS 3 #define WEATHER 4 #define SMELL 5 #define LISTEN 6 if(arg) return; txt = read_bytes(SCRIPT_FILE, 0, file_size(SCRIPT_FILE)); data = explode(txt, "#"); set_short (data[SHORT] ); write("Short: "+this_object()->query_short()+"\n"); set_long (data[LONG] ); write("Long: "+this_object()->query_long()+"\n"); set_items (data[ITEMS] ); write("Items: "+data[ITEMS]+"\n"); write("Weather: "+data[WEATHER]+"\n"); sscanf(data[WEATHER], "%d,%d,%d", i, j, k); set_weather(i, j, k); set_smell (data[SMELL] ); set_listen (data[LISTEN] ); } /***************************************************************************/ /* Actions */ void init() { ::init(); if(environment() && present(this_player(), environment())) add_action("ship_board", "board"); else { add_action("ship_disembark", "disembark"); add_action("ship_disembark", "leave"); if(!automated) { #ifdef SCI_FI add_action("ship_engage", "engage"); #endif /* SCI_FI */ add_action("ship_input", "input"); add_action("ship_input", "enter"); } } } status ship_board(string str) { if(id(str)) { write("You board the "+SHIP_NAME+".\n"); this_player()->move_player("onto the "+SHIP_NAME+"#"+ file_name(this_object())); return 1; } notify_fail("Board what?\n"); return 0; } status ship_disembark() { if(!waiting) return 0; write("You disembark from the "+SHIP_NAME+".\n"); this_player()->move_player("the ship#"+file_name(environment())); return 1; } status ship_input(string str) { int i, j; int x, y, z; string tmp; #ifdef SCI_FI /* Input Warp Speed */ if(sscanf(str, "warp %d", i) == 1) { if(i >= MAX_WARP) { write("The computer chirps: Exceeding maximum warp capability.\n"+ " Enter warp speed again.\n"); return 1; } write("You enter warp "+i+" into the conn.\n"); say(NAME+" engages the warp engines.\n"); speed = i*WARP_SPEED; return 1; } /* Input Impulse Speed */ else if(sscanf(str, "impulse %d/%d", i, j) == 2) { write("You slow the engines down to "+i+"/"+j+" impulse power.\n"); say(NAME+" engages the impulse engines.\n"); speed = (IMPULSE_POWER * i)/j; return 1; } /* Input Travel Coordinates */ else if(sscanf(str, "%dx %dy %dz", x, y, z) == 3) { write("The computer chirps: Coordinates ["+x+", "+y+", "+z+"] entered.\n"); say(NAME+" programmes some coordinates into the conn.\n",this_player()); destination_coordinates = ({ x, y, z, }); ship_travel(destination_coordinates); return 1; } #endif /* SCI_FI */ /* Input Travel Place */ if(sscanf(str, "place %s", str) == 1) { for(i=0; i<sizeof(PORTS_OF_CALL); i++) { if(str == PORTS_OF_CALL[i][PLACE]) { destination_coordinates = PORTS_OF_CALL[i][XYZ]; destination_file = PORTS_OF_CALL[i][FILE]; destination = PORTS_OF_CALL[i][NAME]; #ifdef SCI_FI write("Computer chirps: Destination "+capitalize(str)+" recognised\n"+ "Plotting parabolic course ["+destination_coordinates[X]+"x, "+ destination_coordinates[Y]+"y, "+ destination_coordinates[Z]+"z] to "+ capitalize(destination)+".\n"); #else write("You prepare to travel to "+capitalize(destination)+"\n"); #endif /* SCI_FI */ ship_travel(destination_coordinates); return 1; break; } } } #ifdef SCI_FI else { write("The computer chirps: Incorrect input.\n"); return 1; } #endif /* SCI_FI */ return 0; } status ship_engage() { if(!destination_coordinates) { notify_fail("Computer chirps: Error. No destination entered.\n"); return 0; } write("Computer chirps: Engines engaged.\n"); waiting = 0; set_heart_beat(1); return 1; } /***************************************************************************/ /* Heart Beat Fn's */ void heart_beat() { timer ++; if(automated && waiting) { if(timer > WAIT_TIME) { waiting = 0; timer = 0; ship_travel(destination_coordinates); } } if(timer >= distance) { move_object(this_object(), destination_file); msg("The "+SHIP_NAME+" slows down and docks at "+destination+"\n"); old_destination_coordinates = destination_coordinates; my_coordinates = destination_coordinates; timer = 0; waiting = 1; if(!automated) set_heart_beat(0); else { counter += 1; /* destination_coordinates = [counter][2]; */ } } } /***************************************************************************/ /* Misc Fns */ void ship_travel(int *coords) { int i; for(i=0; i<sizeof(PORTS_OF_CALL); i++) { if(coords == PORTS_OF_CALL[i][XYZ]) { timer = 0; msg("The "+SHIP_NAME+" drops its moorings and heads for "+ PORTS_OF_CALL[i][PLACE]+".\n"); waiting = 0; distance = calc_distance(coords, destination_coordinates); if(!automated) set_heart_beat(1); move_object(this_object(), DESTINATION_FILE); break; } } } int calc_distance(int *coordinates1, int *coordinates2) { x1 = coordinates1[X]; y1 = coordinates1[Y]; z1 = coordinates1[Z]; x2 = coordinates2[X]; y2 = coordinates2[Y]; z2 = coordinates2[Z]; return square_root( ((x2-x1) * (x2-x1)) + ((y2-y1) * (y2-y1)) + ((z2-z1) * (z2-z1))); } int square_root(int i) { return to_int(sqrt(to_float(i))); } void msg(string str) { tell_room(this_object(), str); } /* Query Fn's */ string query_ship_name() { if(!ship_name) ship_name = "Ganges"; return ship_name; }