version 1.76 | | version 1.77 |
---|
| | |
/* | | /* |
* static char *rcsid_c_wiz_c = | | * static char *rcsid_c_wiz_c = |
* "$Id: c_wiz.c,v 1.76 2005/11/27 14:16:46 ryo_saeba Exp $"; | | * "$Id: c_wiz.c,v 1.77 2005/12/18 11:45:00 akirschbaum Exp $"; |
*/ | | */ |
| | |
/* | | /* |
| | |
The authors can be reached via e-mail at crossfire-devel@real-time.com | | The authors can be reached via e-mail at crossfire-devel@real-time.com |
*/ | | */ |
| | |
/* | | |
* End of non-DM commands. DM-only commands below. | | |
* (This includes commands directly from socket) | | |
*/ | | |
| | |
/* Some commands not accepted from socket */ | | |
| | |
#include <global.h> | | #include <global.h> |
#ifndef __CEXTRACT__ | | #ifndef __CEXTRACT__ |
#include <sproto.h> | | #include <sproto.h> |
| | |
#define STACK_FROM_NUMBER 3 /* Item is a number (may be top) */ | | #define STACK_FROM_NUMBER 3 /* Item is a number (may be top) */ |
| | |
| | |
/* Enough of the DM functions seem to need this that I broke | | /** |
| | * Enough of the DM functions seem to need this that I broke |
* it out to a seperate function. name is the person | | * it out to a seperate function. name is the person |
* being saught, rq is who is looking for them. This | | * being saught, rq is who is looking for them. This |
* prints diagnostics messages, and returns the | | * prints diagnostics messages, and returns the |
* other player, or NULL otherwise. | | * other player, or NULL otherwise. |
*/ | | */ |
static player *get_other_player_from_name(object *op, char *name) | | static player *get_other_player_from_name(object *op, char *name) { |
{ | | |
player *pl; | | player *pl; |
| | |
if (!name) return NULL; | | if (!name) |
| | return NULL; |
| | |
for(pl=first_player;pl!=NULL;pl=pl->next) | | for(pl=first_player;pl!=NULL;pl=pl->next) |
if(!strncmp(pl->ob->name, name, MAX_NAME)) | | if(!strncmp(pl->ob->name, name, MAX_NAME)) |
| | |
return pl; | | return pl; |
} | | } |
| | |
| | /** |
| | * This command will stress server. |
| | */ |
int command_loadtest(object *op, char *params){ | | int command_loadtest(object *op, char *params){ |
uint32 x,y; | | uint32 x,y; |
char buf[1024]; | | char buf[1024]; |
/*This command will stress server*/ | | |
new_draw_info(NDI_UNIQUE, 0,op, "loadtest will stress server through teleporting"); | | new_draw_info(NDI_UNIQUE, 0,op, "loadtest will stress server through teleporting"); |
new_draw_info(NDI_UNIQUE, 0,op, "at different map places."); | | new_draw_info(NDI_UNIQUE, 0,op, "at different map places."); |
new_draw_info(NDI_UNIQUE, 0,op, "use at your own risks."); | | new_draw_info(NDI_UNIQUE, 0,op, "use at your own risks."); |
| | |
return 0; | | return 0; |
if (strncmp (params,"TRUE",4)) | | if (strncmp (params,"TRUE",4)) |
return 0; | | return 0; |
| | |
new_draw_info_format(NDI_UNIQUE, 0, op,"gogogo"); | | new_draw_info_format(NDI_UNIQUE, 0, op,"gogogo"); |
for (x=0; x<settings.worldmaptilesx; x++) | | for (x = 0; x < settings.worldmaptilesx; x++) { |
for (y=0; y<settings.worldmaptilesy; y++){ | | for (y=0; y<settings.worldmaptilesy; y++){ |
sprintf (buf,"/world/world_%d_%d",x+settings.worldmapstartx,y+settings.worldmapstarty); | | sprintf (buf,"/world/world_%d_%d",x+settings.worldmapstartx,y+settings.worldmapstarty); |
/*new_draw_info_format(NDI_UNIQUE, 0, op,"going to %s",buf);*/ | | |
command_goto (op, buf); | | command_goto (op, buf); |
} | | } |
| | } |
| | |
return 0; | | return 0; |
} | | } |
| | |
| | |
* If 'silent_dm' is non zero, other players are informed of DM entering/leaving, | | * If 'silent_dm' is non zero, other players are informed of DM entering/leaving, |
* else they just think someone left/entered. | | * else they just think someone left/entered. |
*/ | | */ |
void do_wizard_hide( object* op, int silent_dm ) | | void do_wizard_hide(object *op, int silent_dm) { |
{ | | if (op->contr->hidden) { |
if (op->contr->hidden) | | |
{ | | |
op->contr->hidden=0; | | op->contr->hidden=0; |
op->invisible=1; | | op->invisible=1; |
new_draw_info(NDI_UNIQUE, 0,op, "You are no longer hidden from other players"); | | new_draw_info(NDI_UNIQUE, 0,op, "You are no longer hidden from other players"); |
op->map->players++; | | op->map->players++; |
new_draw_info_format(NDI_UNIQUE | NDI_ALL | NDI_DK_ORANGE, 5, NULL, | | new_draw_info_format(NDI_UNIQUE | NDI_ALL | NDI_DK_ORANGE, 5, NULL, |
"%s has entered the game.",op->name); | | "%s has entered the game.",op->name); |
if ( !silent_dm ) | | if (!silent_dm) { |
{ | | |
new_draw_info(NDI_UNIQUE | NDI_ALL | NDI_LT_GREEN, 1, NULL, | | new_draw_info(NDI_UNIQUE | NDI_ALL | NDI_LT_GREEN, 1, NULL, |
"The Dungeon Master has arrived!"); | | "The Dungeon Master has arrived!"); |
} | | } |
} | | } else { |
else | | |
{ | | |
op->contr->hidden=1; | | op->contr->hidden=1; |
new_draw_info(NDI_UNIQUE, 0,op, "Other players will no longer see you."); | | new_draw_info(NDI_UNIQUE, 0,op, "Other players will no longer see you."); |
op->map->players--; | | op->map->players--; |
if ( !silent_dm ) | | if (!silent_dm) { |
{ | | |
new_draw_info(NDI_UNIQUE | NDI_ALL | NDI_LT_GREEN, 1, NULL, | | new_draw_info(NDI_UNIQUE | NDI_ALL | NDI_LT_GREEN, 1, NULL, |
"The Dungeon Master is gone.."); | | "The Dungeon Master is gone.."); |
} | | } |
| | |
return 1; | | return 1; |
} | | } |
| | |
| | /** |
/* This finds and returns the object which matches the name or | | * This finds and returns the object which matches the name or |
* object nubmer (specified via num #whatever). | | * object nubmer (specified via num #whatever). |
*/ | | */ |
| | static object *find_object_both(char *params) { |
static object *find_object_both(char *params) | | if (!params) |
{ | | return NULL; |
if (!params) return NULL; | | if (params[0] == '#') |
if(params[0]=='#') return find_object(atol(params+1)); | | return find_object(atol(params+1)); |
else return find_object_name(params); | | else |
| | return find_object_name(params); |
} | | } |
| | |
/* Sets the god for some objects. params should contain two values - | | /** |
| | * Sets the god for some objects. params should contain two values - |
* first the object to change, followed by the god to change it to. | | * first the object to change, followed by the god to change it to. |
*/ | | */ |
int command_setgod(object *op, char *params) | | int command_setgod(object *op, char *params) { |
{ | | |
object *ob, *god; | | object *ob, *god; |
char *str; | | char *str; |
| | |
| | |
new_draw_info(NDI_UNIQUE,0,op,"Usage: setgod object god"); | | new_draw_info(NDI_UNIQUE,0,op,"Usage: setgod object god"); |
return 0; | | return 0; |
} | | } |
| | |
/* kill the space, and set string to the next param */ | | /* kill the space, and set string to the next param */ |
*str++='\0'; | | *str++='\0'; |
if(!(ob=find_object_both(params))) { | | if(!(ob=find_object_both(params))) { |
new_draw_info_format(NDI_UNIQUE,0,op,"Set whose god - can not find object %s?",params); | | new_draw_info_format(NDI_UNIQUE,0,op,"Set whose god - can not find object %s?",params); |
return 1; | | return 1; |
} | | } |
/* Perhaps this is overly restrictive? Should we perhaps be able | | |
| | /* |
| | * Perhaps this is overly restrictive? Should we perhaps be able |
* to rebless altars and the like? | | * to rebless altars and the like? |
*/ | | */ |
if (ob->type!=PLAYER) { | | if (ob->type!=PLAYER) { |
new_draw_info_format(NDI_UNIQUE,0,op,"%s is not a player - can not change its god",ob->name); | | new_draw_info_format(NDI_UNIQUE,0,op,"%s is not a player - can not change its god",ob->name); |
return 1; | | return 1; |
} | | } |
| | |
god = find_god(str); | | god = find_god(str); |
if(god==NULL) { | | if(god==NULL) { |
new_draw_info_format(NDI_UNIQUE,0,op,"No such god %s.",str); | | new_draw_info_format(NDI_UNIQUE,0,op,"No such god %s.",str); |
return 1; | | return 1; |
} | | } |
| | |
become_follower(ob,god); | | become_follower(ob,god); |
return 1; | | return 1; |
} | | } |
| | |
/*Add player's IP to ban_file and kick them off the server | | /** |
| | * Add player's IP to ban_file and kick them off the server |
* I know most people have dynamic IPs but this is more of a short term | | * I know most people have dynamic IPs but this is more of a short term |
* solution if they have to get a new IP to play maybe they'll calm down. | | * solution if they have to get a new IP to play maybe they'll calm down. |
* This uses the banish_file in the local directory *not* the ban_file | | * This uses the banish_file in the local directory *not* the ban_file |
| | |
} | | } |
| | |
pl = get_other_player_from_name(op, params); | | pl = get_other_player_from_name(op, params); |
if (!pl) return 1; | | if (!pl) |
| | return 1; |
| | |
sprintf (buf, "%s/%s", settings.localdir, BANISHFILE); | | sprintf (buf, "%s/%s", settings.localdir, BANISHFILE); |
| | |
if ((banishfile = fopen(buf, "a")) == NULL) { | | if ((banishfile = fopen(buf, "a")) == NULL) { |
LOG (llevDebug, "Could not find file banish_file.\n"); | | LOG (llevDebug, "Could not find file banish_file.\n"); |
new_draw_info(NDI_UNIQUE,0,op,"Could not find banish_file."); | | new_draw_info(NDI_UNIQUE,0,op,"Could not find banish_file."); |
return(0); | | return 0; |
} | | } |
| | |
now = time(NULL); | | now = time(NULL); |
/* Record this as a comment - then we don't have to worry about changing | | /* |
| | * Record this as a comment - then we don't have to worry about changing |
* the parsing code. | | * the parsing code. |
*/ | | */ |
fprintf(banishfile, "# %s (%s) banned by %s at %s\n", pl->ob->name, | | fprintf(banishfile, "# %s (%s) banned by %s at %s\n", pl->ob->name, |
| | |
return 1; | | return 1; |
} | | } |
| | |
int command_kick (object *op, char *params) | | int command_kick(object *op, char *params) { |
{ | | |
struct pl *pl; | | struct pl *pl; |
| | |
for(pl=first_player;pl!=NULL;pl=pl->next) | | for (pl = first_player; pl != NULL; pl = pl->next) { |
{ | | |
if((params==NULL || !strcmp(pl->ob->name,params)) && pl->ob!=op) { | | if((params==NULL || !strcmp(pl->ob->name,params)) && pl->ob!=op) { |
object *op; | | object *op; |
int removed=0; | | int removed=0; |
| | |
"%s is kicked out of the game.",op->name); | | "%s is kicked out of the game.",op->name); |
strcpy(op->contr->killer,"left"); | | strcpy(op->contr->killer,"left"); |
check_score(op); /* Always check score */ | | check_score(op); /* Always check score */ |
/* not sure how the player would be freed, but did see | | |
| | /* |
| | * not sure how the player would be freed, but did see |
* a crash here - if that is the case, don't save the | | * a crash here - if that is the case, don't save the |
* the player. | | * the player. |
*/ | | */ |
if (!removed && !QUERY_FLAG(op, FLAG_FREED)) { | | if (!removed && !QUERY_FLAG(op, FLAG_FREED)) { |
(void)save_player(op,0); | | (void)save_player(op,0); |
if (op->map) op->map->players--; | | if (op->map) |
| | op->map->players--; |
} | | } |
#if MAP_MAXTIMEOUT | | #if MAP_MAXTIMEOUT |
if (op->map) op->map->timeout = MAP_TIMEOUT(op->map); | | if (op->map) |
| | op->map->timeout = MAP_TIMEOUT(op->map); |
#endif | | #endif |
pl->socket.status = Ns_Dead; | | pl->socket.status = Ns_Dead; |
} | | } |
} | | } |
| | |
return 1; | | return 1; |
} | | } |
| | |
int command_save_overlay(object *op, char *params) | | int command_save_overlay(object *op, char *params) { |
{ | | |
if (!op) | | if (!op) |
return(0); | | return 0; |
| | |
if (op!=NULL && !QUERY_FLAG(op, FLAG_WIZ)) | | if (op != NULL && !QUERY_FLAG(op, FLAG_WIZ)) { |
{ | | |
new_draw_info(NDI_UNIQUE, 0, op, | | new_draw_info(NDI_UNIQUE, 0, op, |
"Sorry, you can't force an overlay save."); | | "Sorry, you can't force an overlay save."); |
return(1); | | return 1; |
} | | } |
| | |
new_save_map(op->map, 2); | | new_save_map(op->map, 2); |
new_save_map(op->map, 0); | | new_save_map(op->map, 0); |
new_draw_info(NDI_UNIQUE, 0, op, "Current map has been saved as an" | | new_draw_info(NDI_UNIQUE, 0, op, "Current map has been saved as an" |
| | |
| | |
ready_map_name(op->map->path, 0); | | ready_map_name(op->map->path, 0); |
| | |
return(1); | | return 1; |
} | | } |
/*a simple toggle for the no_shout field. | | |
AKA the MUZZLE command | | /* |
| | * A simple toggle for the no_shout field. |
| | * AKA the MUZZLE command |
*/ | | */ |
int command_toggle_shout(object *op, char *params) | | int command_toggle_shout(object *op, char *params) { |
{ | | |
player *pl; | | player *pl; |
| | |
if (!params) { | | if (!params) { |
| | |
} | | } |
| | |
pl = get_other_player_from_name(op, params); | | pl = get_other_player_from_name(op, params); |
if (!pl) return 1; | | if (!pl) |
| | return 1; |
| | |
if (pl->ob->contr->no_shout == 0){ | | if (pl->ob->contr->no_shout == 0){ |
pl->ob->contr->no_shout = 1; | | pl->ob->contr->no_shout = 1; |
new_draw_info(NDI_UNIQUE | NDI_RED, 0, pl->ob, | | |
"You have been muzzled by the DM!"); | | new_draw_info(NDI_UNIQUE|NDI_RED, 0, pl->ob, "You have been muzzled by the DM!"); |
new_draw_info_format(NDI_UNIQUE , 0, op, | | new_draw_info_format(NDI_UNIQUE, 0, op, "You muzzle %s.", pl->ob->name); |
"You muzzle %s.", pl->ob->name); | | |
| | |
/* Avion : Here we handle the MUZZLE global event */ | | /* Avion : Here we handle the MUZZLE global event */ |
execute_global_event(EVENT_MUZZLE,pl->ob,params); | | execute_global_event(EVENT_MUZZLE,pl->ob,params); |
| | |
} | | } |
} | | } |
| | |
int command_shutdown(object *op, char *params) | | int command_shutdown(object *op, char *params) { |
{ | | if (op!=NULL && !QUERY_FLAG(op, FLAG_WIZ)) { |
| | |
if(op!=NULL && !QUERY_FLAG(op,FLAG_WIZ)) | | |
{ | | |
new_draw_info(NDI_UNIQUE,0,op,"Sorry, you can't shutdown the server."); | | new_draw_info(NDI_UNIQUE,0,op,"Sorry, you can't shutdown the server."); |
return 1; | | return 1; |
} | | } |
/* We need to give op - command_kick expects it. however, this means | | |
| | /* |
| | * We need to give op - command_kick expects it. however, this means |
* the op won't get kicked off, so we do it ourselves | | * the op won't get kicked off, so we do it ourselves |
*/ | | */ |
command_kick(op,NULL); | | command_kick(op,NULL); |
| | |
new_draw_info(NDI_UNIQUE, 0,op,"Go to what level?"); | | new_draw_info(NDI_UNIQUE, 0,op,"Go to what level?"); |
return 1; | | return 1; |
} | | } |
| | |
name = params; | | name = params; |
dummy=get_object(); | | dummy=get_object(); |
dummy->map = op->map; | | dummy->map = op->map; |
| | |
new_draw_info_format(NDI_UNIQUE, 0, op, | | new_draw_info_format(NDI_UNIQUE, 0, op, |
"Difficulty: %d.",op->map->difficulty); | | "Difficulty: %d.",op->map->difficulty); |
} | | } |
| | |
return 1; | | return 1; |
} | | } |
| | |
| | |
sscanf(params, "%d", &nr); | | sscanf(params, "%d", &nr); |
for(i = 0; i < nr; i++) { | | for(i = 0; i < nr; i++) { |
retry = 50; | | retry = 50; |
while((tmp=generate_treasure(0,op->map->difficulty))==NULL && --retry); | | while ((tmp=generate_treasure(0, op->map->difficulty)) == NULL && --retry) |
| | ; |
if (tmp != NULL) { | | if (tmp != NULL) { |
tmp = insert_ob_in_ob(tmp, op); | | tmp = insert_ob_in_ob(tmp, op); |
if (op->type == PLAYER) | | if (op->type == PLAYER) |
esrv_send_item (op, tmp); | | esrv_send_item (op, tmp); |
} | | } |
} | | } |
| | |
return 1; | | return 1; |
} | | } |
| | |
int command_freeze(object *op, char *params) | | int command_freeze(object *op, char *params) { |
{ | | |
int ticks; | | int ticks; |
player *pl; | | player *pl; |
| | |
| | |
| | |
ticks = atoi(params); | | ticks = atoi(params); |
if (ticks) { | | if (ticks) { |
while ((isdigit(*params) || isspace(*params)) && *params != 0) params++; | | while ((isdigit(*params) || isspace(*params)) && *params != 0) |
| | params++; |
if (*params == 0) { | | if (*params == 0) { |
new_draw_info(NDI_UNIQUE, 0,op,"Usage: freeze [ticks] <player>."); | | new_draw_info(NDI_UNIQUE, 0,op,"Usage: freeze [ticks] <player>."); |
return 1; | | return 1; |
} | | } |
} else ticks=100; | | } else |
| | ticks = 100; |
| | |
pl = get_other_player_from_name(op, params); | | pl = get_other_player_from_name(op, params); |
if (!pl) return 1; | | if (!pl) |
| | return 1; |
| | |
new_draw_info(NDI_UNIQUE | NDI_RED, 0, pl->ob, "You have been frozen by the DM!"); | | new_draw_info(NDI_UNIQUE | NDI_RED, 0, pl->ob, "You have been frozen by the DM!"); |
new_draw_info_format(NDI_UNIQUE , 0, op, | | new_draw_info_format(NDI_UNIQUE , 0, op, |
"You freeze %s for %d ticks", pl->ob->name, ticks); | | "You freeze %s for %d ticks", pl->ob->name, ticks); |
| | |
return 0; | | return 0; |
} | | } |
| | |
| | int command_summon(object *op, char *params) { |
int command_summon (object *op, char *params) | | |
{ | | |
int i; | | int i; |
object *dummy; | | object *dummy; |
player *pl; | | player *pl; |
| | |
} | | } |
| | |
pl = get_other_player_from_name(op, params); | | pl = get_other_player_from_name(op, params); |
if (!pl) return 1; | | if (!pl) |
| | return 1; |
| | |
i=find_free_spot(op,op->map,op->x,op->y,1,9); | | i=find_free_spot(op,op->map,op->x,op->y,1,9); |
if (i==-1) { | | if (i==-1) { |
new_draw_info(NDI_UNIQUE, 0, op, "Can not find a free spot to place summoned player."); | | new_draw_info(NDI_UNIQUE, 0, op, "Can not find a free spot to place summoned player."); |
return 1; | | return 1; |
} | | } |
| | |
dummy=get_object(); | | dummy=get_object(); |
EXIT_PATH(dummy)=add_string(op->map->path); | | EXIT_PATH(dummy)=add_string(op->map->path); |
EXIT_X(dummy)=op->x+freearr_x[i]; | | EXIT_X(dummy)=op->x+freearr_x[i]; |
| | |
return 1; | | return 1; |
} | | } |
| | |
/* Teleport next to target player */ | | /** |
| | * Teleport next to target player. |
| | */ |
/* mids 01/16/2002 */ | | /* mids 01/16/2002 */ |
| | |
int command_teleport (object *op, char *params) { | | int command_teleport (object *op, char *params) { |
int i; | | int i; |
object *dummy; | | object *dummy; |
| | |
} | | } |
| | |
pl = get_other_player_from_name(op, params); | | pl = get_other_player_from_name(op, params); |
if (!pl) return 1; | | if (!pl) |
| | return 1; |
| | |
i = find_free_spot(pl->ob, pl->ob->map, pl->ob->x, pl->ob->y, 1, 9); | | i = find_free_spot(pl->ob, pl->ob->map, pl->ob->x, pl->ob->y, 1, 9); |
if (i==-1) { | | if (i==-1) { |
new_draw_info(NDI_UNIQUE, 0, op, "Can not find a free spot to teleport to."); | | new_draw_info(NDI_UNIQUE, 0, op, "Can not find a free spot to teleport to."); |
return 1; | | return 1; |
} | | } |
| | |
dummy = get_object(); | | dummy = get_object(); |
EXIT_PATH(dummy) = add_string(pl->ob->map->path); | | EXIT_PATH(dummy) = add_string(pl->ob->map->path); |
EXIT_X(dummy) = pl->ob->x + freearr_x[i]; | | EXIT_X(dummy) = pl->ob->x + freearr_x[i]; |
| | |
return 1; | | return 1; |
} | | } |
| | |
/* This function is a real mess, because we're stucking getting | | /** |
| | * This function is a real mess, because we're stucking getting |
* the entire item description in one block of text, so we just | | * the entire item description in one block of text, so we just |
* can't simply parse it - we need to look for double quotes | | * can't simply parse it - we need to look for double quotes |
* for example. This could actually get much simpler with just a | | * for example. This could actually get much simpler with just a |
| | |
* dragon name "big nasty creature" hp 5 sp 30 | | * dragon name "big nasty creature" hp 5 sp 30 |
* for example. | | * for example. |
*/ | | */ |
int command_create (object *op, char *params) | | int command_create(object *op, char *params) { |
{ | | |
object *tmp=NULL; | | object *tmp=NULL; |
int nrof,i, magic, set_magic = 0, set_nrof = 0, gotquote, gotspace; | | int nrof,i, magic, set_magic = 0, set_nrof = 0, gotquote, gotspace; |
char buf[MAX_BUF], *cp, *bp = buf, *bp2, *bp3, *bp4, *endline; | | char buf[MAX_BUF], *cp, *bp = buf, *bp2, *bp3, *bp4, *endline; |
| | |
*cp = '\0'; | | *cp = '\0'; |
cp += 4; | | cp += 4; |
} | | } |
for (bp2=bp; *bp2; bp2++) | | for (bp2 = bp; *bp2; bp2++) { |
if (*bp2 == ' ') { | | if (*bp2 == ' ') { |
*bp2 = '\0'; | | *bp2 = '\0'; |
bp2++; | | bp2++; |
break; | | break; |
} | | } |
| | } |
| | |
if((at=find_archetype(bp))==NULL) { | | if((at=find_archetype(bp))==NULL) { |
new_draw_info(NDI_UNIQUE, 0, op, "No such archetype."); | | new_draw_info(NDI_UNIQUE, 0, op, "No such archetype."); |
| | |
if (cp) { | | if (cp) { |
char spell_name[MAX_BUF], *fsp=NULL; | | char spell_name[MAX_BUF], *fsp=NULL; |
| | |
/* Try to find a spell object for this. Note that | | /* |
| | * Try to find a spell object for this. Note that |
* we also set up spell_name which is only | | * we also set up spell_name which is only |
* the first word. | | * the first word. |
*/ | | */ |
| | |
if (find_artifactlist(at->clone.type)==NULL) { | | if (find_artifactlist(at->clone.type)==NULL) { |
new_draw_info_format(NDI_UNIQUE, 0, op, | | new_draw_info_format(NDI_UNIQUE, 0, op, |
"No artifact list for type %d\n", at->clone.type); | | "No artifact list for type %d\n", at->clone.type); |
} | | } else { |
else { | | |
art = find_artifactlist(at->clone.type)->items; | | art = find_artifactlist(at->clone.type)->items; |
| | |
do { | | do { |
if (!strcmp(art->item->name, cp)) break; | | if (!strcmp(art->item->name, cp)) |
| | break; |
art = art->next; | | art = art->next; |
} while (art!=NULL); | | } while (art!=NULL); |
if (!art) { | | if (!art) { |
| | |
set_nrof ? nrof : 0, set_magic ? magic : 0 , bp, cp); | | set_nrof ? nrof : 0, set_magic ? magic : 0 , bp, cp); |
} | | } |
} /* if cp */ | | } /* if cp */ |
| | |
if ((at->clone.type == ROD || at->clone.type == WAND || at->clone.type == SCROLL || | | if ((at->clone.type == ROD || at->clone.type == WAND || at->clone.type == SCROLL || |
at->clone.type == HORN || at->clone.type == SPELLBOOK) && !at_spell) { | | at->clone.type == HORN || at->clone.type == SPELLBOOK) && !at_spell) { |
new_draw_info_format(NDI_UNIQUE, 0, op, | | new_draw_info_format(NDI_UNIQUE, 0, op, |
| | |
return 1; | | return 1; |
} | | } |
| | |
/* Rather than have two different blocks with a lot of similar code, | | /* |
| | * Rather than have two different blocks with a lot of similar code, |
* just create one object, do all the processing, and then determine | | * just create one object, do all the processing, and then determine |
* if that one object should be inserted or if we need to make copies. | | * if that one object should be inserted or if we need to make copies. |
*/ | | */ |
| | |
CLEAR_FLAG(tmp, FLAG_KNOWN_MAGICAL); | | CLEAR_FLAG(tmp, FLAG_KNOWN_MAGICAL); |
} | | } |
| | |
/* This entire block here tries to find variable pairings, | | /* |
| | * This entire block here tries to find variable pairings, |
* eg, 'hp 4' or the like. The mess here is that values | | * eg, 'hp 4' or the like. The mess here is that values |
* can be quoted (eg "my cool sword"); So the basic logic | | * can be quoted (eg "my cool sword"); So the basic logic |
* is we want to find two spaces, but if we got a quote, | | * is we want to find two spaces, but if we got a quote, |
| | |
if (*bp3 == '"') { | | if (*bp3 == '"') { |
*bp3 = '\0'; | | *bp3 = '\0'; |
gotquote++; | | gotquote++; |
| | } else |
| | bp3++; |
} | | } |
else bp3++; | | } else if (*bp3==' ') { |
} | | |
} | | |
else if (*bp3==' ') { | | |
gotspace++; | | gotspace++; |
} | | } |
} | | } |
/* If we got two spaces, send the second one to null. | | |
| | /* |
| | * If we got two spaces, send the second one to null. |
* if we've reached the end of the line, increase gotspace - | | * if we've reached the end of the line, increase gotspace - |
* this is perfectly valid for the list entry listed. | | * this is perfectly valid for the list entry listed. |
*/ | | */ |
if (gotspace == 2 || gotquote == 2) { | | if (gotspace == 2 || gotquote == 2) { |
bp3--; /* Undo the extra increment */ | | bp3--; /* Undo the extra increment */ |
*bp3='\0'; | | *bp3='\0'; |
} else if (*bp3=='\0') gotspace++; | | } else if (*bp3=='\0') |
| | gotspace++; |
| | |
if ((gotquote && gotquote != 2) || (gotspace !=2 && gotquote!=2)) { | | if ((gotquote && gotquote != 2) || (gotspace !=2 && gotquote!=2)) { |
/* Unfortunately, we've clobbered lots of values, so printing | | /* |
| | * Unfortunately, we've clobbered lots of values, so printing |
* out what we have probably isn't useful. Break out, because | | * out what we have probably isn't useful. Break out, because |
* trying to recover is probably won't get anything useful | | * trying to recover is probably won't get anything useful |
* anyways, and we'd be confused about end of line pointers | | * anyways, and we'd be confused about end of line pointers |
| | |
bp2 = bp3 + 1; | | bp2 = bp3 + 1; |
} | | } |
| | |
| | |
if(at->clone.nrof) { | | if(at->clone.nrof) { |
if (at_spell) | | if (at_spell) |
insert_ob_in_ob(arch_to_object(at_spell), tmp); | | insert_ob_in_ob(arch_to_object(at_spell), tmp); |
| | |
if (at_spell) | | if (at_spell) |
insert_ob_in_ob(arch_to_object(at_spell), dup); | | insert_ob_in_ob(arch_to_object(at_spell), dup); |
| | |
/* The head is what contains all the important bits, | | /* |
| | * The head is what contains all the important bits, |
* so just copying it over should be fine. | | * so just copying it over should be fine. |
*/ | | */ |
if(head==NULL) { | | if(head==NULL) { |
| | |
} | | } |
prev=dup; | | prev=dup; |
} | | } |
| | |
if (QUERY_FLAG(head, FLAG_ALIVE)) { | | if (QUERY_FLAG(head, FLAG_ALIVE)) { |
object* check = head; | | object* check = head; |
int size_x = 0; | | int size_x = 0; |
int size_y = 0; | | int size_y = 0; |
while (check) | | |
{ | | while (check) { |
size_x = MAX(size_x, check->arch->clone.x); | | size_x = MAX(size_x, check->arch->clone.x); |
size_y = MAX(size_y, check->arch->clone.y); | | size_y = MAX(size_y, check->arch->clone.y); |
check = check->more; | | check = check->more; |
} | | } |
if (out_of_map(op->map,head->x + size_x, head->y + size_y)) | | |
{ | | if (out_of_map(op->map, head->x+size_x, head->y+size_y)) { |
if ((head->x < size_x) || (head->y < size_y)) | | if (head->x < size_x || head->y < size_y) { |
{ | | |
dm_stack_pop(op->contr); | | dm_stack_pop(op->contr); |
free_object(head); | | free_object(head); |
new_draw_info(NDI_UNIQUE, 0, op,"Object too big to insert in map, or wrong position."); | | new_draw_info(NDI_UNIQUE, 0, op,"Object too big to insert in map, or wrong position."); |
free_object(tmp); | | free_object(tmp); |
return 1; | | return 1; |
} | | } |
| | |
check = head; | | check = head; |
while ( check ) | | while (check) { |
{ | | |
check->x -= size_x; | | check->x -= size_x; |
check->y -= size_y; | | check->y -= size_y; |
check = check->more; | | check = check->more; |
} | | } |
} | | } |
| | |
insert_ob_in_map(head, op->map, op, 0); | | insert_ob_in_map(head, op->map, op, 0); |
} | | } else |
else | | |
head = insert_ob_in_ob(head, op); | | head = insert_ob_in_ob(head, op); |
| | |
/* Let's put this created item on stack so dm can access it easily. */ | | /* Let's put this created item on stack so dm can access it easily. */ |
| | |
op->map->difficulty, 0); | | op->map->difficulty, 0); |
esrv_send_item(op, head); | | esrv_send_item(op, head); |
} | | } |
| | |
/* free the one we used to copy */ | | /* free the one we used to copy */ |
free_object(tmp); | | free_object(tmp); |
} | | } |
| | |
return 1; | | return 1; |
} | | } |
| | |
/* if(<not socket>) */ | | |
| | |
/* | | /* |
* Now follows dm-commands which are also acceptable from sockets | | * Now follows dm-commands which are also acceptable from sockets |
*/ | | */ |
| | |
int command_inventory (object *op, char *params) | | int command_inventory(object *op, char *params) { |
{ | | |
object *tmp; | | object *tmp; |
int i; | | int i; |
| | |
| | |
new_draw_info(NDI_UNIQUE, 0,op,"Inventory of what object (nr)?"); | | new_draw_info(NDI_UNIQUE, 0,op,"Inventory of what object (nr)?"); |
return 1; | | return 1; |
} | | } |
| | |
inventory(op,tmp); | | inventory(op,tmp); |
return 1; | | return 1; |
} | | } |
| | |
* already see skills w/ inventory command - b.t. | | * already see skills w/ inventory command - b.t. |
*/ | | */ |
| | |
int command_skills (object *op, char *params) | | int command_skills (object *op, char *params) { |
{ | | |
show_skills(op, params); | | show_skills(op, params); |
return 0; | | return 0; |
} | | } |
| | |
int command_dump (object *op, char *params) | | int command_dump (object *op, char *params) { |
{ | | |
object *tmp; | | object *tmp; |
| | |
tmp = get_dm_object( op->contr, ¶ms, NULL ); | | tmp = get_dm_object( op->contr, ¶ms, NULL ); |
if ( !tmp ) | | if ( !tmp ) |
return 1; | | return 1; |
| | |
return 1; | | return 1; |
} | | } |
| | |
/* When DM is possessing a monster, flip aggression on and off, to allow | | /** |
better motion */ | | * When DM is possessing a monster, flip aggression on and off, to allow |
| | * better motion. |
int command_mon_aggr (object *op, char *params) | | */ |
{ | | int command_mon_aggr(object *op, char *params) { |
if (op->enemy || !QUERY_FLAG(op, FLAG_UNAGGRESSIVE)) { | | if (op->enemy || !QUERY_FLAG(op, FLAG_UNAGGRESSIVE)) { |
op->enemy = NULL; | | op->enemy = NULL; |
SET_FLAG(op, FLAG_UNAGGRESSIVE); | | SET_FLAG(op, FLAG_UNAGGRESSIVE); |
| | |
CLEAR_FLAG(op, FLAG_UNAGGRESSIVE); | | CLEAR_FLAG(op, FLAG_UNAGGRESSIVE); |
new_draw_info(NDI_UNIQUE, 0, op, "Aggression turned ON"); | | new_draw_info(NDI_UNIQUE, 0, op, "Aggression turned ON"); |
} | | } |
| | |
return 1; | | return 1; |
} | | } |
| | |
/* DM can possess a monster. Basically, this tricks the client into thinking | | /** DM can possess a monster. Basically, this tricks the client into thinking |
* a given monster, is actually the player it controls. This allows a DM | | * a given monster, is actually the player it controls. This allows a DM |
* to inhabit a monster's body, and run around the game with it. | | * to inhabit a monster's body, and run around the game with it. |
* This function is severely broken - it has tons of hardcoded values, | | * This function is severely broken - it has tons of hardcoded values, |
*/ | | */ |
| | int command_possess(object *op, char *params) { |
int command_possess (object *op, char *params) | | |
{ | | |
object *victim, *curinv, *nextinv; | | object *victim, *curinv, *nextinv; |
player *pl; | | player *pl; |
int i; | | int i; |
| | |
new_draw_info(NDI_UNIQUE, 0, op, "Patch what object (nr)?"); | | new_draw_info(NDI_UNIQUE, 0, op, "Patch what object (nr)?"); |
return 1; | | return 1; |
} | | } |
| | |
if (victim==op) { | | if (victim==op) { |
new_draw_info(NDI_UNIQUE, 0, op, "As insane as you are, I cannot " | | new_draw_info(NDI_UNIQUE, 0, op, "As insane as you are, I cannot " |
"allow you to possess yourself."); | | "allow you to possess yourself."); |
| | |
esrv_del_item(op->contr, curinv->count); | | esrv_del_item(op->contr, curinv->count); |
curinv = nextinv; | | curinv = nextinv; |
} | | } |
| | |
/* make the switch */ | | /* make the switch */ |
pl = op->contr; | | pl = op->contr; |
victim->contr = pl; | | victim->contr = pl; |
| | |
victim->type = PLAYER; | | victim->type = PLAYER; |
SET_FLAG(victim, FLAG_WIZ); | | SET_FLAG(victim, FLAG_WIZ); |
| | |
/* remove all the skill/exp granting code - that was broken. | | |
*/ | | |
| | |
/* send the inventory to the client */ | | /* send the inventory to the client */ |
curinv = victim->inv; | | curinv = victim->inv; |
while (curinv != NULL) { | | while (curinv != NULL) { |
| | |
return 1; | | return 1; |
} | | } |
| | |
| | int command_patch(object *op, char *params) { |
int command_patch (object *op, char *params) | | |
{ | | |
char *arg,*arg2; | | char *arg,*arg2; |
object *tmp; | | object *tmp; |
| | |
| | |
new_draw_info(NDI_UNIQUE, 0,op,"Patch what values?"); | | new_draw_info(NDI_UNIQUE, 0,op,"Patch what values?"); |
return 1; | | return 1; |
} | | } |
| | |
if((arg2=strchr(arg,' '))) | | if((arg2=strchr(arg,' '))) |
arg2++; | | arg2++; |
if (settings.real_wiz == FALSE) | | if (settings.real_wiz == FALSE) |
| | |
new_draw_info_format(NDI_UNIQUE, 0, op, | | new_draw_info_format(NDI_UNIQUE, 0, op, |
"(%s#%d)->%s=%s",tmp->name,tmp->count,arg,arg2); | | "(%s#%d)->%s=%s",tmp->name,tmp->count,arg,arg2); |
} | | } |
| | |
return 1; | | return 1; |
} | | } |
| | |
int command_remove (object *op, char *params) | | int command_remove (object *op, char *params) { |
{ | | |
object *tmp; | | object *tmp; |
int from; | | int from; |
| | |
| | |
new_draw_info(NDI_UNIQUE, 0,op,"Remove what object (nr)?"); | | new_draw_info(NDI_UNIQUE, 0,op,"Remove what object (nr)?"); |
return 1; | | return 1; |
} | | } |
| | |
if (tmp->type == PLAYER) { | | if (tmp->type == PLAYER) { |
new_draw_info(NDI_UNIQUE, 0,op,"Unable to remove a player!"); | | new_draw_info(NDI_UNIQUE, 0,op,"Unable to remove a player!"); |
return 1; | | return 1; |
} | | } |
| | |
if (QUERY_FLAG(tmp, FLAG_REMOVED)) { | | if (QUERY_FLAG(tmp, FLAG_REMOVED)) { |
new_draw_info_format(NDI_UNIQUE, 0,op,"%s is already removed!", | | new_draw_info_format(NDI_UNIQUE, 0,op,"%s is already removed!", |
query_name(tmp)); | | query_name(tmp)); |
return 1; | | return 1; |
} | | } |
| | |
if ( from != STACK_FROM_STACK ) | | if ( from != STACK_FROM_STACK ) |
/* Item is either stack top, or is a number thus is now stack top, let's remove it */ | | /* Item is either stack top, or is a number thus is now stack top, let's remove it */ |
dm_stack_pop( op->contr ); | | dm_stack_pop( op->contr ); |
| | |
/* Always work on the head - otherwise object will get in odd state */ | | /* Always work on the head - otherwise object will get in odd state */ |
if (tmp->head) tmp=tmp->head; | | if (tmp->head) |
| | tmp = tmp->head; |
remove_ob(tmp); | | remove_ob(tmp); |
return 1; | | return 1; |
} | | } |
| | |
int command_free (object *op, char *params) | | int command_free(object *op, char *params) { |
{ | | |
object *tmp; | | object *tmp; |
int from; | | int from; |
| | |
| | |
new_draw_info(NDI_UNIQUE, 0,op,"Free what object (nr)?"); | | new_draw_info(NDI_UNIQUE, 0,op,"Free what object (nr)?"); |
return 1; | | return 1; |
} | | } |
| | |
if ( from != STACK_FROM_STACK ) | | if ( from != STACK_FROM_STACK ) |
/* Item is either stack top, or is a number thus is now stack top, let's remove it */ | | /* Item is either stack top, or is a number thus is now stack top, let's remove it */ |
dm_stack_pop( op->contr ); | | dm_stack_pop( op->contr ); |
| | |
if ( !QUERY_FLAG( tmp, FLAG_REMOVED ) ) | | if (!QUERY_FLAG(tmp, FLAG_REMOVED)) { |
{ | | |
new_draw_info( NDI_UNIQUE, 0, op, "Warning, item wasn't removed." ); | | new_draw_info( NDI_UNIQUE, 0, op, "Warning, item wasn't removed." ); |
remove_ob( tmp ); | | remove_ob( tmp ); |
} | | } |
| | |
if (tmp->head) tmp=tmp->head; | | if (tmp->head) |
| | tmp = tmp->head; |
free_object(tmp); | | free_object(tmp); |
return 1; | | return 1; |
} | | } |
| | |
/* This adds exp to a player. We now allow adding to a specific skill. | | /** |
| | * This adds exp to a player. We now allow adding to a specific skill. |
*/ | | */ |
int command_addexp (object *op, char *params) | | int command_addexp(object *op, char *params) { |
{ | | |
char buf[MAX_BUF], skill[MAX_BUF]; | | char buf[MAX_BUF], skill[MAX_BUF]; |
int i, q; | | int i, q; |
object *skillob=NULL; | | object *skillob=NULL; |
| | |
new_draw_info_format(NDI_UNIQUE, 0,op,"Unable to find skill %s in %s", skill, buf); | | new_draw_info_format(NDI_UNIQUE, 0,op,"Unable to find skill %s in %s", skill, buf); |
return 1; | | return 1; |
} | | } |
| | |
i = check_exp_adjust(skillob,i); | | i = check_exp_adjust(skillob,i); |
skillob->stats.exp += i; | | skillob->stats.exp += i; |
calc_perm_exp(skillob); | | calc_perm_exp(skillob); |
player_lvl_adj(pl->ob, skillob); | | player_lvl_adj(pl->ob, skillob); |
} | | } |
| | |
| | |
pl->ob->stats.exp += i; | | pl->ob->stats.exp += i; |
calc_perm_exp(pl->ob); | | calc_perm_exp(pl->ob); |
player_lvl_adj(pl->ob, NULL); | | player_lvl_adj(pl->ob, NULL); |
| | |
return 1; | | return 1; |
} | | } |
| | |
int command_speed (object *op, char *params) | | int command_speed(object *op, char *params) { |
{ | | |
int i; | | int i; |
| | |
if(params==NULL || !sscanf(params, "%d", &i)) { | | if(params==NULL || !sscanf(params, "%d", &i)) { |
sprintf(errmsg,"Current speed is %ld",max_time); | | sprintf(errmsg,"Current speed is %ld",max_time); |
new_draw_info(NDI_UNIQUE, 0,op,errmsg); | | new_draw_info(NDI_UNIQUE, 0,op,errmsg); |
return 1; | | return 1; |
} | | } |
| | |
set_max_time(i); | | set_max_time(i); |
reset_sleep(); | | reset_sleep(); |
new_draw_info(NDI_UNIQUE, 0,op,"The speed is changed."); | | new_draw_info(NDI_UNIQUE, 0,op,"The speed is changed."); |
return 1; | | return 1; |
} | | } |
| | |
| | |
/**************************************************************************/ | | /**************************************************************************/ |
/* Mods made by Tyler Van Gorder, May 10-13, 1992. */ | | /* Mods made by Tyler Van Gorder, May 10-13, 1992. */ |
/* CSUChico : tvangod@cscihp.ecst.csuchico.edu */ | | /* CSUChico : tvangod@cscihp.ecst.csuchico.edu */ |
/**************************************************************************/ | | /**************************************************************************/ |
| | |
int command_stats (object *op, char *params) | | int command_stats(object *op, char *params) { |
{ | | |
char thing[20]; | | char thing[20]; |
player *pl; | | player *pl; |
char buf[MAX_BUF]; | | char buf[MAX_BUF]; |
| | |
new_draw_info(NDI_UNIQUE, 0,op,"Who?"); | | new_draw_info(NDI_UNIQUE, 0,op,"Who?"); |
return 1; | | return 1; |
} | | } |
| | |
for(pl=first_player;pl!=NULL;pl=pl->next) | | for(pl=first_player;pl!=NULL;pl=pl->next) |
if(!strcmp(pl->ob->name,thing)) { | | if(!strcmp(pl->ob->name,thing)) { |
sprintf(buf,"Str : %-2d H.P. : %-4d MAX : %d", | | sprintf(buf,"Str : %-2d H.P. : %-4d MAX : %d", |
| | |
return 1; | | return 1; |
} | | } |
| | |
int command_abil (object *op, char *params) | | int command_abil(object *op, char *params) { |
{ | | |
char thing[20], thing2[20]; | | char thing[20], thing2[20]; |
int iii; | | int iii; |
player *pl; | | player *pl; |
| | |
new_draw_info(NDI_UNIQUE, 0,op,"Who?"); | | new_draw_info(NDI_UNIQUE, 0,op,"Who?"); |
return 1; | | return 1; |
} | | } |
| | |
if (thing2==NULL){ | | if (thing2==NULL){ |
new_draw_info(NDI_UNIQUE, 0,op,"You can't change that."); | | new_draw_info(NDI_UNIQUE, 0,op,"You can't change that."); |
return 1; | | return 1; |
} | | } |
| | |
if (iii<MIN_STAT||iii>MAX_STAT) { | | if (iii<MIN_STAT||iii>MAX_STAT) { |
new_draw_info(NDI_UNIQUE, 0,op,"Illegal range of stat.\n"); | | new_draw_info(NDI_UNIQUE, 0,op,"Illegal range of stat.\n"); |
return 1; | | return 1; |
} | | } |
for(pl=first_player;pl!=NULL;pl=pl->next) | | |
| | for (pl = first_player; pl != NULL; pl = pl->next) { |
if(!strcmp(pl->ob->name,thing)){ | | if(!strcmp(pl->ob->name,thing)){ |
if (settings.real_wiz == FALSE) | | if (settings.real_wiz == FALSE) |
SET_FLAG(pl->ob, FLAG_WAS_WIZ); | | SET_FLAG(pl->ob, FLAG_WAS_WIZ); |
| | |
fix_player(pl->ob); | | fix_player(pl->ob); |
return 1; | | return 1; |
} | | } |
| | } |
| | |
new_draw_info(NDI_UNIQUE, 0,op,"No such player."); | | new_draw_info(NDI_UNIQUE, 0,op,"No such player."); |
return 1; | | return 1; |
} | | } |
| | |
int command_reset (object *op, char *params) | | int command_reset (object *op, char *params) { |
{ | | |
mapstruct *m; | | mapstruct *m; |
object *dummy = NULL, *tmp = NULL; | | object *dummy = NULL, *tmp = NULL; |
| | |
| | |
new_draw_info(NDI_UNIQUE, 0,op,"Reset what map [name]?"); | | new_draw_info(NDI_UNIQUE, 0,op,"Reset what map [name]?"); |
return 1; | | return 1; |
} | | } |
| | |
if (strcmp(params, ".") == 0) | | if (strcmp(params, ".") == 0) |
params = op->map->path; | | params = op->map->path; |
m = has_been_loaded(params); | | m = has_been_loaded(params); |
| | |
LOG(llevError,"Tried to swap out map which was not in memory.\n"); | | LOG(llevError,"Tried to swap out map which was not in memory.\n"); |
return 0; | | return 0; |
} | | } |
/* Only attempt to remove the player that is doing the reset, and not other | | |
| | /* |
| | * Only attempt to remove the player that is doing the reset, and not other |
* players or wiz's. | | * players or wiz's. |
*/ | | */ |
if (op->map == m ) { | | if (op->map == m ) { |
| | |
swap_map(m); | | swap_map(m); |
} | | } |
| | |
| | |
if (m->in_memory == MAP_SWAPPED) { | | if (m->in_memory == MAP_SWAPPED) { |
LOG(llevDebug,"Resetting map %s.\n",m->path); | | LOG(llevDebug,"Resetting map %s.\n",m->path); |
| | |
| | |
} else { | | } else { |
player *pl; | | player *pl; |
int playercount=0; | | int playercount=0; |
| | |
/* Need to re-insert player if swap failed for some reason */ | | /* Need to re-insert player if swap failed for some reason */ |
if (tmp) { | | if (tmp) { |
insert_ob_in_map(op, m, NULL,0); | | insert_ob_in_map(op, m, NULL,0); |
free_object(dummy); | | free_object(dummy); |
} | | } |
| | |
new_draw_info(NDI_UNIQUE, 0,op, | | new_draw_info(NDI_UNIQUE, 0,op, |
"Reset failed, couldn't swap map, the following players are on it:"); | | "Reset failed, couldn't swap map, the following players are on it:"); |
for (pl=first_player; pl!=NULL; pl=pl->next) { | | for (pl=first_player; pl!=NULL; pl=pl->next) { |
| | |
playercount++; | | playercount++; |
} | | } |
} | | } |
if (!playercount) new_draw_info(NDI_UNIQUE, 0, op, | | if (!playercount) |
| | new_draw_info(NDI_UNIQUE, 0, op, |
"hmm, I don't see any other players on this map, something else is the problem."); | | "hmm, I don't see any other players on this map, something else is the problem."); |
return 1; | | return 1; |
} | | } |
} | | } |
| | |
int command_nowiz (object *op, char *params) /* 'noadm' is alias */ | | int command_nowiz(object *op, char *params) { /* 'noadm' is alias */ |
{ | | |
CLEAR_FLAG(op, FLAG_WIZ); | | CLEAR_FLAG(op, FLAG_WIZ); |
CLEAR_FLAG(op, FLAG_WIZPASS); | | CLEAR_FLAG(op, FLAG_WIZPASS); |
CLEAR_FLAG(op, FLAG_WIZCAST); | | CLEAR_FLAG(op, FLAG_WIZCAST); |
| | |
if (settings.real_wiz == TRUE) | | if (settings.real_wiz == TRUE) |
CLEAR_FLAG(op, FLAG_WAS_WIZ); | | CLEAR_FLAG(op, FLAG_WAS_WIZ); |
if ( op->contr->hidden ) | | if (op->contr->hidden) { |
{ | | |
new_draw_info(NDI_UNIQUE, 0,op, "You are no longer hidden from other players"); | | new_draw_info(NDI_UNIQUE, 0,op, "You are no longer hidden from other players"); |
op->map->players++; | | op->map->players++; |
new_draw_info_format(NDI_UNIQUE | NDI_ALL | NDI_DK_ORANGE, 5, NULL, | | new_draw_info_format(NDI_UNIQUE | NDI_ALL | NDI_DK_ORANGE, 5, NULL, |
"%s has entered the game.",op->name); | | "%s has entered the game.",op->name); |
op->contr->hidden=0; | | op->contr->hidden=0; |
op->invisible=1; | | op->invisible=1; |
} | | } else |
else | | |
new_draw_info(NDI_UNIQUE | NDI_ALL | NDI_LT_GREEN, 1, NULL, "The Dungeon Master is gone.."); | | new_draw_info(NDI_UNIQUE | NDI_ALL | NDI_LT_GREEN, 1, NULL, "The Dungeon Master is gone.."); |
return 1; | | return 1; |
} | | } |
| | |
/* | | /** |
* object *op is trying to become dm. | | * object *op is trying to become dm. |
* pl_name is name supplied by player. Restrictive DM will make it harder | | * pl_name is name supplied by player. Restrictive DM will make it harder |
* for socket users to become DM - in that case, it will check for the players | | * for socket users to become DM - in that case, it will check for the players |
| | |
sprintf (buf, "%s/%s", settings.confdir, DMFILE); | | sprintf (buf, "%s/%s", settings.confdir, DMFILE); |
if ((dmfile = fopen(buf, "r")) == NULL) { | | if ((dmfile = fopen(buf, "r")) == NULL) { |
LOG (llevDebug, "Could not find DM file.\n"); | | LOG (llevDebug, "Could not find DM file.\n"); |
return(0); | | return 0; |
} | | } |
| | |
while(fgets(line_buf, 160, dmfile) != NULL) { | | while(fgets(line_buf, 160, dmfile) != NULL) { |
if (line_buf[0]=='#') continue; | | if (line_buf[0] == '#') |
| | continue; |
if (sscanf(line_buf,"%[^:]:%[^:]:%s\n",name, passwd, host)!=3) { | | if (sscanf(line_buf,"%[^:]:%[^:]:%s\n",name, passwd, host)!=3) { |
LOG(llevError,"Warning - malformed dm file entry: %s\n", line_buf); | | LOG(llevError,"Warning - malformed dm file entry: %s\n", line_buf); |
} | | } else if ((!strcmp(name, "*") || (pl_name && !strcmp(pl_name, name))) |
else if ((!strcmp(name,"*") || (pl_name && !strcmp(pl_name, name))) | | |
&& (!strcmp(passwd,"*") || !strcmp(passwd,pl_passwd)) && | | && (!strcmp(passwd,"*") || !strcmp(passwd,pl_passwd)) && |
(!strcmp(host,"*") || !strcmp(host, pl_host))) { | | (!strcmp(host,"*") || !strcmp(host, pl_host))) { |
fclose(dmfile); | | fclose(dmfile); |
| | |
} | | } |
| | |
int do_wizard_dm( object* op, char* params, int silent ) { | | int do_wizard_dm( object* op, char* params, int silent ) { |
| | |
if ( !op->contr ) | | if ( !op->contr ) |
return 0; | | return 0; |
| | |
| | |
SET_FLAG(op, FLAG_WIZPASS); | | SET_FLAG(op, FLAG_WIZPASS); |
SET_FLAG(op, FLAG_WIZCAST); | | SET_FLAG(op, FLAG_WIZCAST); |
new_draw_info(NDI_UNIQUE, 0,op, "Ok, you are the Dungeon Master!"); | | new_draw_info(NDI_UNIQUE, 0,op, "Ok, you are the Dungeon Master!"); |
/* Remove setting flying here - that won't work, because next | | /* |
| | * Remove setting flying here - that won't work, because next |
* fix_player() is called that will get cleared - proper solution | | * fix_player() is called that will get cleared - proper solution |
* is probably something like a wiz_force which gives that and any | | * is probably something like a wiz_force which gives that and any |
* other desired abilities. | | * other desired abilities. |
| | |
} | | } |
} | | } |
| | |
/* Actual command to perhaps become dm. Changed aroun a bit in version 0.92.2 | | /* |
| | * Actual command to perhaps become dm. Changed aroun a bit in version 0.92.2 |
* - allow people on sockets to become dm, and allow better dm file | | * - allow people on sockets to become dm, and allow better dm file |
*/ | | */ |
| | int command_dm(object *op, char *params) { |
int command_dm (object *op, char *params) | | if (!op->contr) |
{ | | return 0; |
if (!op->contr) return 0; | | |
| | |
do_wizard_dm( op, params, 0 ); | | do_wizard_dm( op, params, 0 ); |
| | |
return 1; | | return 1; |
} | | } |
| | |
int command_invisible (object *op, char *params) | | int command_invisible(object *op, char *params) { |
{ | | |
if (op) { | | if (op) { |
op->invisible+=100; | | op->invisible+=100; |
update_object(op,UP_OBJ_FACE); | | update_object(op,UP_OBJ_FACE); |
new_draw_info(NDI_UNIQUE, 0,op,"You turn invisible."); | | new_draw_info(NDI_UNIQUE, 0,op,"You turn invisible."); |
} | | } |
| | |
return 0; | | return 0; |
} | | } |
| | |
| | |
* Returns NULL if 0 or more than one spell matches. | | * Returns NULL if 0 or more than one spell matches. |
* Used for wizard's learn spell/prayer. | | * Used for wizard's learn spell/prayer. |
*/ | | */ |
object* get_spell_by_name( const char* spell_name ) | | object *get_spell_by_name(const char *spell_name) { |
{ | | |
archetype* ar; | | archetype* ar; |
archetype* found; | | archetype* found; |
size_t length; | | size_t length; |
| | |
found = NULL; | | found = NULL; |
length = strlen( spell_name ); | | length = strlen( spell_name ); |
| | |
for (ar = first_archetype ; ar != NULL; ar = ar->next ) | | for (ar = first_archetype; ar != NULL; ar = ar->next) { |
{ | | |
if ( ar->clone.type != SPELL ) | | if ( ar->clone.type != SPELL ) |
continue; | | continue; |
| | |
if ( strlen( ar->clone.name ) < length ) | | if ( strlen( ar->clone.name ) < length ) |
continue; | | continue; |
| | |
if ( !strncmp( ar->clone.name, spell_name, length ) ) | | if (!strncmp(ar->clone.name, spell_name, length)) { |
{ | | |
if ( found ) | | if ( found ) |
/* Already had one, >1 match, return NULL. */ | | /* Already had one, >1 match, return NULL. */ |
return NULL; | | return NULL; |
| | |
} | | } |
| | |
static int command_learn_spell_or_prayer (object *op, char *params, | | static int command_learn_spell_or_prayer (object *op, char *params, |
int special_prayer) | | int special_prayer) { |
{ | | |
object *tmp; | | object *tmp; |
| | |
if (op->contr == NULL || params == NULL) | | if (op->contr == NULL || params == NULL) |
| | |
"Could not find a spell by name of %s\n", params); | | "Could not find a spell by name of %s\n", params); |
return 0; | | return 0; |
} | | } |
| | |
do_learn_spell (op, tmp, special_prayer); | | do_learn_spell (op, tmp, special_prayer); |
free_object(tmp); | | free_object(tmp); |
return 1; | | return 1; |
} | | } |
| | |
int command_learn_spell (object *op, char *params) | | int command_learn_spell(object *op, char *params) { |
{ | | |
return command_learn_spell_or_prayer (op, params, 0); | | return command_learn_spell_or_prayer (op, params, 0); |
} | | } |
| | |
| | |
do_forget_spell (op, params); | | do_forget_spell (op, params); |
return 1; | | return 1; |
} | | } |
/* Lauwenmark */ | | |
/* Lists all plugins currently loaded with their IDs and full names. */ | | /** |
| | * Lists all plugins currently loaded with their IDs and full names. |
| | */ |
int command_listplugins(object *op, char *params) | | int command_listplugins(object *op, char *params) |
{ | | { |
plugins_display_list(op); | | plugins_display_list(op); |
return 1; | | return 1; |
} | | } |
/* Lauwenmark */ | | |
/* Loads the given plugin. The DM specifies the name of the library to load */ | | /** |
/* (no pathname is needed). Do not ever attempt to load the same plugin more */ | | * Loads the given plugin. The DM specifies the name of the library to load (no |
/* than once at a time, or bad things could happen. */ | | * pathname is needed). Do not ever attempt to load the same plugin more than |
int command_loadplugin(object *op, char *params) | | * once at a time, or bad things could happen. |
{ | | */ |
| | int command_loadplugin(object *op, char *params) { |
char buf[MAX_BUF]; | | char buf[MAX_BUF]; |
| | |
if (params == NULL) { | | if (params == NULL) { |
| | |
new_draw_info(NDI_UNIQUE, 0, op, "Could not load plugin."); | | new_draw_info(NDI_UNIQUE, 0, op, "Could not load plugin."); |
return 1; | | return 1; |
} | | } |
/* Lauwenmark */ | | |
/* Unloads the given plugin. The DM specified the ID of the library to */ | | /** |
/* unload. Note that some things may behave strangely if the correct plugins */ | | * Unloads the given plugin. The DM specified the ID of the library to unload. |
/* are not loaded. */ | | * Note that some things may behave strangely if the correct plugins are not |
| | * loaded. |
| | */ |
int command_unloadplugin(object *op, char *params) | | int command_unloadplugin(object *op, char *params) |
{ | | { |
if (params == NULL) { | | if (params == NULL) { |
| | |
* Let's see if that's authorized. | | * Let's see if that's authorized. |
* Make sure to not tell anything to anyone. | | * Make sure to not tell anything to anyone. |
*/ | | */ |
int command_dmhide( object* op, char* params ) | | int command_dmhide(object *op, char *params) { |
{ | | |
if ( !do_wizard_dm( op, params, 1 ) ) | | if ( !do_wizard_dm( op, params, 1 ) ) |
return 0; | | return 0; |
| | |
| | |
return 1; | | return 1; |
} | | } |
| | |
void dm_stack_pop( player* pl ) | | void dm_stack_pop(player *pl) { |
{ | | if (!pl->stack_items || !pl->stack_position) { |
if ( !pl->stack_items || !pl->stack_position ) | | |
{ | | |
new_draw_info( NDI_UNIQUE, 0, pl->ob, "Empty stack!" ); | | new_draw_info( NDI_UNIQUE, 0, pl->ob, "Empty stack!" ); |
return; | | return; |
} | | } |
| | |
new_draw_info_format( NDI_UNIQUE, 0, pl->ob, "Popped item from stack, %d left.", pl->stack_position ); | | new_draw_info_format( NDI_UNIQUE, 0, pl->ob, "Popped item from stack, %d left.", pl->stack_position ); |
} | | } |
| | |
| | |
/** | | /** |
* Get current stack top item for player. | | * Get current stack top item for player. |
* Returns NULL if no stacked item. | | * Returns NULL if no stacked item. |
| | |
* | | * |
* Ryo, august 2004 | | * Ryo, august 2004 |
*/ | | */ |
object* dm_stack_peek( player* pl ) | | object *dm_stack_peek(player *pl) { |
{ | | |
object* ob; | | object* ob; |
| | |
if ( !pl->stack_position ) | | if (!pl->stack_position) { |
{ | | |
new_draw_info( NDI_UNIQUE, 0, pl->ob, "Empty stack!" ); | | new_draw_info( NDI_UNIQUE, 0, pl->ob, "Empty stack!" ); |
return NULL; | | return NULL; |
} | | } |
| | |
ob = find_object( pl->stack_items[ pl->stack_position - 1 ] ); | | ob = find_object( pl->stack_items[ pl->stack_position - 1 ] ); |
if ( !ob ) | | if (!ob) { |
{ | | |
new_draw_info( NDI_UNIQUE, 0, pl->ob, "Stacked item was removed!" ); | | new_draw_info( NDI_UNIQUE, 0, pl->ob, "Stacked item was removed!" ); |
dm_stack_pop( pl ); | | dm_stack_pop( pl ); |
return NULL; | | return NULL; |
| | |
* Inform player of position. | | * Inform player of position. |
* Initializes variables if needed. | | * Initializes variables if needed. |
*/ | | */ |
void dm_stack_push( player* pl, tag_t item ) | | void dm_stack_push(player *pl, tag_t item) { |
{ | | if (!pl->stack_items) { |
if ( !pl->stack_items ) | | |
{ | | |
pl->stack_items = ( tag_t* )malloc( sizeof( tag_t ) * STACK_SIZE ); | | pl->stack_items = ( tag_t* )malloc( sizeof( tag_t ) * STACK_SIZE ); |
memset( pl->stack_items, 0, sizeof( tag_t ) * STACK_SIZE ); | | memset( pl->stack_items, 0, sizeof( tag_t ) * STACK_SIZE ); |
} | | } |
| | |
if ( pl->stack_position == STACK_SIZE ) | | if (pl->stack_position == STACK_SIZE) { |
{ | | |
new_draw_info( NDI_UNIQUE, 0, pl->ob, "Item stack full!" ); | | new_draw_info( NDI_UNIQUE, 0, pl->ob, "Item stack full!" ); |
return; | | return; |
} | | } |
| | |
* | | * |
* Ryo, august 2004 | | * Ryo, august 2004 |
*/ | | */ |
object* get_dm_object( player* pl, char** params, int* from ) | | object *get_dm_object(player *pl, char **params, int *from) { |
{ | | |
int item_tag, item_position; | | int item_tag, item_position; |
object* ob; | | object* ob; |
| | |
if ( !pl ) | | if ( !pl ) |
return NULL; | | return NULL; |
| | |
if ( ( !params ) || !( *params ) || ( '\0' == **params ) ) | | if (!params || !*params || **params == '\0') { |
{ | | |
if ( from ) | | if ( from ) |
*from = STACK_FROM_TOP; | | *from = STACK_FROM_TOP; |
/* No parameter => get stack item */ | | /* No parameter => get stack item */ |
| | |
( *params )++; | | ( *params )++; |
| | |
/* Next case: number => item tag */ | | /* Next case: number => item tag */ |
if ( sscanf( *params, "%d", &item_tag ) ) | | if (sscanf(*params, "%d", &item_tag)) { |
{ | | |
/* Move parameter to next item */ | | /* Move parameter to next item */ |
while ( isdigit( **params ) ) | | while ( isdigit( **params ) ) |
( *params )++; | | ( *params )++; |
| | |
/* And skip blanks, too */ | | /* And skip blanks, too */ |
while ( ' ' == ( **params ) ) | | while (**params == ' ') |
( *params )++; | | ( *params )++; |
| | |
/* Get item */ | | /* Get item */ |
ob = find_object( item_tag ); | | ob = find_object( item_tag ); |
if ( !ob ) | | if (!ob) { |
{ | | |
if ( from ) | | if ( from ) |
*from = STACK_FROM_NONE; | | *from = STACK_FROM_NONE; |
new_draw_info_format( NDI_UNIQUE, 0, pl->ob, "No such item %d!", item_tag ); | | new_draw_info_format( NDI_UNIQUE, 0, pl->ob, "No such item %d!", item_tag ); |
| | |
} | | } |
| | |
/* Next case: $number => stack item */ | | /* Next case: $number => stack item */ |
if ( sscanf( *params, "$%d", &item_position ) ) | | if (sscanf(*params, "$%d", &item_position)) { |
{ | | |
/* Move parameter to next item */ | | /* Move parameter to next item */ |
( *params )++; | | ( *params )++; |
| | |
while ( isdigit( **params ) ) | | while ( isdigit( **params ) ) |
( *params )++; | | ( *params )++; |
while ( ' ' == ( **params ) ) | | while (**params == ' ') |
( *params )++; | | ( *params )++; |
| | |
if ( item_position >= pl->stack_position ) | | if (item_position >= pl->stack_position) { |
{ | | |
if ( from ) | | if ( from ) |
*from = STACK_FROM_NONE; | | *from = STACK_FROM_NONE; |
new_draw_info_format( NDI_UNIQUE, 0, pl->ob, "No such stack item %d!", item_position ); | | new_draw_info_format( NDI_UNIQUE, 0, pl->ob, "No such stack item %d!", item_position ); |
| | |
} | | } |
| | |
ob = find_object( pl->stack_items[ item_position ] ); | | ob = find_object( pl->stack_items[ item_position ] ); |
if ( !ob ) | | if (!ob) { |
{ | | |
if ( from ) | | if ( from ) |
*from = STACK_FROM_NONE; | | *from = STACK_FROM_NONE; |
new_draw_info_format( NDI_UNIQUE, 0, pl->ob, "Stack item %d was removed.", item_position ); | | new_draw_info_format( NDI_UNIQUE, 0, pl->ob, "Stack item %d was removed.", item_position ); |
| | |
} | | } |
| | |
if ( from ) | | if ( from ) |
*from = ( item_position < ( pl->stack_position - 1 ) ) ? STACK_FROM_STACK : STACK_FROM_TOP; | | *from = item_position < pl->stack_position-1 ? STACK_FROM_STACK : STACK_FROM_TOP; |
return ob; | | return ob; |
} | | } |
| | |
/* Next case: 'me' => return pl->ob */ | | /* Next case: 'me' => return pl->ob */ |
if ( !strncmp( *params, "me", 2 ) ) | | if (!strncmp(*params, "me", 2)) { |
{ | | |
if ( from ) | | if ( from ) |
*from = STACK_FROM_NUMBER; | | *from = STACK_FROM_NUMBER; |
dm_stack_push( pl, pl->ob->count ); | | dm_stack_push( pl, pl->ob->count ); |
| | |
/* Skip to next token */ | | /* Skip to next token */ |
( *params ) += 2; | | ( *params ) += 2; |
while ( ' ' == ( **params ) ) | | while (**params == ' ') |
( *params )++; | | ( *params )++; |
| | |
return pl->ob; | | return pl->ob; |
| | |
/** | | /** |
* Pop the stack top. | | * Pop the stack top. |
*/ | | */ |
int command_stack_pop( object* op, char* params ) | | int command_stack_pop(object *op, char *params) { |
{ | | |
dm_stack_pop( op->contr ); | | dm_stack_pop( op->contr ); |
return 0; | | return 0; |
} | | } |
| | |
/** | | /** |
* Push specified item on stack. | | * Push specified item on stack. |
*/ | | */ |
int command_stack_push( object* op, char* params ) | | int command_stack_push(object *op, char *params) { |
{ | | |
object* ob; | | object* ob; |
int from; | | int from; |
ob = get_dm_object( op->contr, ¶ms, &from ); | | ob = get_dm_object( op->contr, ¶ms, &from ); |
| | |
if ( ob && ( from != STACK_FROM_NUMBER ) ) | | if (ob && from != STACK_FROM_NUMBER) |
/* Object was from stack, need to push it again */ | | /* Object was from stack, need to push it again */ |
dm_stack_push( op->contr, ob->count ); | | dm_stack_push( op->contr, ob->count ); |
| | |
| | |
/** | | /** |
* Displays stack contents. | | * Displays stack contents. |
*/ | | */ |
int command_stack_list( object* op, char* params ) | | int command_stack_list(object *op, char *params) { |
{ | | |
int item; | | int item; |
object* display; | | object* display; |
player* pl = op->contr; | | player* pl = op->contr; |
| | |
new_draw_info( NDI_UNIQUE,0, op, "Item stack contents: " ); | | new_draw_info( NDI_UNIQUE,0, op, "Item stack contents: " ); |
| | |
for ( item = 0; item < pl->stack_position; item++ ) | | for (item = 0; item < pl->stack_position; item++) { |
{ | | |
display = find_object( pl->stack_items[ item ] ); | | display = find_object( pl->stack_items[ item ] ); |
if ( display ) | | if ( display ) |
new_draw_info_format( NDI_UNIQUE, 0, op, " %d : %s [%d]", item, display->name, display->count ); | | new_draw_info_format( NDI_UNIQUE, 0, op, " %d : %s [%d]", item, display->name, display->count ); |
| | |
/** | | /** |
* Empty DM item stack. | | * Empty DM item stack. |
*/ | | */ |
int command_stack_clear( object* op, char* params ) | | int command_stack_clear(object *op, char *params) { |
{ | | |
op->contr->stack_position = 0; | | op->contr->stack_position = 0; |
new_draw_info( NDI_UNIQUE, 0, op, "Item stack cleared." ); | | new_draw_info( NDI_UNIQUE, 0, op, "Item stack cleared." ); |
return 0; | | return 0; |
| | |
* | | * |
* Ryo, august 2004 | | * Ryo, august 2004 |
*/ | | */ |
int command_diff( object* op, char* params ) | | int command_diff(object *op, char *params) { |
{ | | |
object* left, *right, *top; | | object* left, *right, *top; |
const char* diff; | | const char* diff; |
int left_from, right_from; | | int left_from, right_from; |
| | |
top = NULL; | | top = NULL; |
| | |
left = get_dm_object( op->contr, ¶ms, &left_from ); | | left = get_dm_object( op->contr, ¶ms, &left_from ); |
if ( !left ) | | if (!left) { |
{ | | |
new_draw_info( NDI_UNIQUE, 0, op, "Compare to what item?" ); | | new_draw_info( NDI_UNIQUE, 0, op, "Compare to what item?" ); |
return 0; | | return 0; |
} | | } |
| | |
| | |
right = get_dm_object( op->contr, ¶ms, &right_from ); | | right = get_dm_object( op->contr, ¶ms, &right_from ); |
| | |
if ( !right ) | | if (!right) { |
{ | | |
new_draw_info( NDI_UNIQUE, 0, op, "Compare what item?" ); | | new_draw_info( NDI_UNIQUE, 0, op, "Compare what item?" ); |
return 0; | | return 0; |
} | | } |
| | |
new_draw_info( NDI_UNIQUE, 0, op, "Item difference:" ); | | new_draw_info( NDI_UNIQUE, 0, op, "Item difference:" ); |
| | |
if ( ( left_from == STACK_FROM_TOP ) && ( right_from == STACK_FROM_TOP ) ) | | if (left_from == STACK_FROM_TOP && right_from == STACK_FROM_TOP) { |
{ | | /* |
/* Special case: both items were taken from stack top. | | * Special case: both items were taken from stack top. |
Override the behaviour, taking left as item just below top, if exists. | | * Override the behaviour, taking left as item just below top, if exists. |
See function description for why. | | * See function description for why. |
Besides, if we don't do anything, compare an item to itself, not really useful. | | * Besides, if we don't do anything, compare an item to itself, not really useful. |
*/ | | */ |
if ( op->contr->stack_position > 1 ) | | if (op->contr->stack_position > 1) { |
{ | | |
left = find_object( op->contr->stack_items[ op->contr->stack_position - 2 ] ); | | left = find_object( op->contr->stack_items[ op->contr->stack_position - 2 ] ); |
if ( left ) | | if ( left ) |
new_draw_info( NDI_UNIQUE, 0, op, "(Note: first item taken from undertop)" ); | | new_draw_info( NDI_UNIQUE, 0, op, "(Note: first item taken from undertop)" ); |
| | |
| | |
diff = get_ob_diff( left, right ); | | diff = get_ob_diff( left, right ); |
| | |
if ( !diff ) | | if (!diff) { |
{ | | |
new_draw_info( NDI_UNIQUE, 0, op, "Objects are the same." ); | | new_draw_info( NDI_UNIQUE, 0, op, "Objects are the same." ); |
return 0; | | return 0; |
} | | } |
| | |
new_draw_info( NDI_UNIQUE, 0, op, diff ); | | new_draw_info( NDI_UNIQUE, 0, op, diff ); |
return 0; | | return 0; |
} | | } |