/**************************************************************************** * ResortMUD Version 5.0 was mainly programmed by Ntanel, Garinan, Josh, * * Badastaz, Digifuzz, Senir, Kratas, Scion, Shogar and Tagith. * * ------------------------------------------------------------------------ * * Copyright (C) 1996 - 2001 Haslage Net Electronics: MudWorld of Lorain, * * Ohio. ALL RIGHTS RESERVED See /doc/RMLicense.txt for more details. * ****************************************************************************/ /**************************************************************************** * [S]imulated [M]edieval [A]dventure multi[U]ser [G]ame | \\._.// * * -----------------------------------------------------------| (0...0) * * SMAUG 1.4 (C) 1994, 1995, 1996, 1998 by Derek Snider | ).:.( * * -----------------------------------------------------------| {o o} * * SMAUG code team: Thoric, Altrag, Blodkai, Narn, Haus, | / ' ' \ * * Scryn, Rennard, Swordbearer, Gorog, Grishnakh, Nivek, |~'~.VxvxV.~'~* * Tricops and Fireblade | * * ------------------------------------------------------------------------ * * Merc 2.1 Diku Mud improvments copyright (C) 1992, 1993 by Michael * * Chastain, Michael Quan, and Mitchell Tse. * * Original Diku Mud copyright (C) 1990, 1991 by Sebastian Hammer, * * Michael Seifert, Hans Henrik St{rfeldt, Tom Madsen, and Katja Nyboe. * * ------------------------------------------------------------------------ * * Object manipulation module * ****************************************************************************/ #include <string.h> #include "mud.h" #include "bet.h" /*double sqrt( double x );*/ /* * External functions */ void write_corpses args( ( CHAR_DATA * ch, char *name, OBJ_DATA * objrem ) ); /* * Local functions. */ void get_obj args( ( CHAR_DATA * ch, OBJ_DATA * obj, OBJ_DATA * container ) ); bool remove_obj args( ( CHAR_DATA * ch, int iWear, bool fReplace ) ); void wear_obj args( ( CHAR_DATA * ch, OBJ_DATA * obj, bool fReplace, short wear_bit ) ); OBJ_DATA *recursive_note_find args( ( OBJ_DATA * obj, char *argument ) ); /* * how resistant an object is to damage -Thoric */ short get_obj_resistance( OBJ_DATA * obj ) { short resist; resist = number_fuzzy( MAX_ITEM_IMPACT ); /* * magical items are more resistant */ if( IS_OBJ_STAT( obj, ITEM_MAGIC ) ) resist += number_fuzzy( 12 ); /* * metal objects are definately stronger */ if( IS_OBJ_STAT( obj, ITEM_METAL ) ) resist += number_fuzzy( 5 ); /* * organic objects are most likely weaker */ if( IS_OBJ_STAT( obj, ITEM_ORGANIC ) ) resist -= number_fuzzy( 5 ); /* * blessed objects should have a little bonus */ if( IS_OBJ_STAT( obj, ITEM_BLESS ) ) resist += number_fuzzy( 5 ); /* * lets make store inventory pretty tough */ if( IS_OBJ_STAT( obj, ITEM_INVENTORY ) ) resist += 20; /* * okay... let's add some bonus/penalty for item level... */ resist += ( obj->level / 10 ) - 2; /* * and lasty... take armor or weapon's condition into consideration */ if( obj->item_type == ITEM_ARMOR || obj->item_type == ITEM_WEAPON ) resist += ( obj->value[0] / 2 ) - 2; return URANGE( 10, resist, 99 ); } bool is_class( CHAR_DATA * ch, int class ) { if( IS_NPC( ch ) ) { if( ch->class == class ) return TRUE; } if( ch->level2 == -1 ) { if( ch->class == class ) return TRUE; } else if( ch->level3 == -1 ) { if( ch->class == class || ch->class2 == class ) return TRUE; } else { if( ch->class == class || ch->class2 == class || ch->class3 == class ) return TRUE; } return FALSE; } void get_obj( CHAR_DATA * ch, OBJ_DATA * obj, OBJ_DATA * container ) { CLAN_DATA *clan; int weight; int amt; /* gold per-race multipliers */ if( !CAN_WEAR( obj, ITEM_TAKE ) && ( ch->level < sysdata.level_getobjnotake ) ) { send_to_char( "You can't take that.\r\n", ch ); return; } if( IS_SET( obj->magic_flags, ITEM_PKDISARMED ) ) { if( CAN_PKILL( ch ) && !get_timer( ch, TIMER_PKILLED ) ) { if( ch->level - obj->value[5] > 5 || obj->value[5] - ch->level > 5 ) { send_to_char_color( "\r\n&bA godly force freezes your outstretched hand.\r\n", ch ); return; } else { REMOVE_BIT( obj->magic_flags, ITEM_PKDISARMED ); obj->value[5] = 0; } } else { send_to_char_color( "\r\n&BA godly force freezes your outstretched hand.\r\n", ch ); return; } } if( IS_OBJ_STAT( obj, ITEM_PROTOTYPE ) && !can_take_proto( ch ) ) { send_to_char( "A godly force prevents you from getting close to it.\r\n", ch ); return; } if( ch->carry_number + get_obj_number( obj ) > can_carry_n( ch ) ) { act( AT_PLAIN, "$d: you can't carry that many items.", ch, NULL, obj->name, TO_CHAR ); return; } if( IS_OBJ_STAT( obj, ITEM_COVERING ) ) weight = obj->weight; else weight = get_obj_weight( obj ); if( ch->carry_weight + weight > can_carry_w( ch ) ) { act( AT_PLAIN, "$d: you can't carry that much weight.", ch, NULL, obj->name, TO_CHAR ); return; } if( container ) { if( container->item_type == ITEM_KEYRING && !IS_OBJ_STAT( container, ITEM_COVERING ) ) { act( AT_ACTION, "You remove $p from $P", ch, obj, container, TO_CHAR ); act( AT_ACTION, "$n removes $p from $P", ch, obj, container, TO_ROOM ); } else { act( AT_ACTION, IS_OBJ_STAT( container, ITEM_COVERING ) ? "You get $p from beneath $P." : "You get $p from $P", ch, obj, container, TO_CHAR ); act( AT_ACTION, IS_OBJ_STAT( container, ITEM_COVERING ) ? "$n gets $p from beneath $P." : "$n gets $p from $P", ch, obj, container, TO_ROOM ); } if( IS_OBJ_STAT( container, ITEM_CLANCORPSE ) && !IS_NPC( ch ) && str_cmp( container->name + 7, ch->name ) ) container->value[5]++; obj_from_obj( obj ); } else { act( AT_ACTION, "You get $p.", ch, obj, container, TO_CHAR ); act( AT_ACTION, "$n gets $p.", ch, obj, container, TO_ROOM ); obj_from_room( obj ); } /* * Clan storeroom checks */ if( IS_SET( ch->in_room->room_flags, ROOM_CLANSTOREROOM ) && ( !container || container->carried_by == NULL ) ) { /* if (!char_died) save_char_obj(ch); */ for( clan = first_clan; clan; clan = clan->next ) if( clan->storeroom == ch->in_room->vnum ) save_clan_storeroom( ch, clan ); } if( obj->item_type != ITEM_CONTAINER ) check_for_trap( ch, obj, TRAP_GET ); if( char_died( ch ) ) return; if( obj->item_type == ITEM_GOLD || obj->item_type == ITEM_COPPER || obj->item_type == ITEM_SILVER ) { amt = obj->value[0]; /* * The idea was to make some races more adroit at money handling, * however, this resulted in elves dropping 1M gps and picking * up 1.1M, repeating, and getting rich. The only solution would * be to fuzzify the "drop coins" code, but that seems like it'd * lead to more confusion than it warrants. -h * * When you work on this again, make it so that amt is NEVER multiplied * by more than 1.0. Use less than 1.0 for ogre, orc, troll, etc. * (Ie: a penalty rather than a bonus) */ #ifdef GOLD_MULT switch ( ch->race ) { case ( 1 ): amt *= 1.1; break; /* elf */ case ( 2 ): amt *= 0.97; break; /* dwarf */ case ( 3 ): amt *= 1.02; break; /* halfling */ case ( 4 ): amt *= 1.08; break; /* pixie */ case ( 6 ): amt *= 0.92; break; /* half-ogre */ case ( 7 ): amt *= 0.94; break; /* half-orc */ case ( 8 ): amt *= 0.90; break; /* half-troll */ case ( 9 ): amt *= 1.04; break; /* half-elf */ case ( 10 ): amt *= 1.06; break; /* gith */ } #endif if( obj->item_type == ITEM_GOLD ) { ch->gold += amt; } if( obj->item_type == ITEM_COPPER ) ch->copper += amt; if( obj->item_type == ITEM_SILVER ) ch->silver += amt; extract_obj( obj ); } else { obj = obj_to_char( obj, ch ); } if( char_died( ch ) || obj_extracted( obj ) ) return; oprog_get_trigger( ch, obj ); return; } void do_get( CHAR_DATA * ch, char *argument ) { char arg1[MAX_INPUT_LENGTH]; char arg2[MAX_INPUT_LENGTH]; char buf[1024]; OBJ_DATA *obj; OBJ_DATA *obj_next; OBJ_DATA *container; short number; bool found; argument = one_argument( argument, arg1 ); if( is_number( arg1 ) ) { number = atoi( arg1 ); if( number < 1 ) { send_to_char( "That was easy...\r\n", ch ); return; } if( ( ch->carry_number + number ) > can_carry_n( ch ) ) { send_to_char( "You can't carry that many.\r\n", ch ); return; } argument = one_argument( argument, arg1 ); } else number = 0; argument = one_argument( argument, arg2 ); /* * munch optional words */ if( !str_cmp( arg2, "from" ) && argument[0] != '\0' ) argument = one_argument( argument, arg2 ); /* * Get type. */ if( arg1[0] == '\0' ) { send_to_char( "Get what?\r\n", ch ); return; } if( ms_find_obj( ch ) ) return; if( arg2[0] == '\0' ) { if( number <= 1 && str_cmp( arg1, "all" ) && str_prefix( "all.", arg1 ) ) { /* * 'get obj' */ obj = get_obj_list( ch, arg1, ch->in_room->first_content ); if( !obj ) { act( AT_PLAIN, "I see no $T here.", ch, NULL, arg1, TO_CHAR ); return; } separate_obj( obj ); get_obj( ch, obj, NULL ); if( char_died( ch ) ) return; save_house_by_vnum( ch->in_room->vnum ); /* House Object Saving */ if( IS_SET( sysdata.save_flags, SV_GET ) ) save_char_obj( ch ); } else { short cnt = 0; bool fAll; char *chk; if( IS_SET( ch->in_room->room_flags, ROOM_DONATION ) ) { send_to_char( "The gods frown upon such a display of greed!\r\n", ch ); return; } if( !str_cmp( arg1, "all" ) ) fAll = TRUE; else fAll = FALSE; if( number > 1 ) chk = arg1; else chk = &arg1[4]; /* * 'get all' or 'get all.obj' */ found = FALSE; for( obj = ch->in_room->last_content; obj; obj = obj_next ) { obj_next = obj->prev_content; if( ( fAll || nifty_is_name( chk, obj->name ) ) && can_see_obj( ch, obj ) ) { found = TRUE; if( number && ( cnt + obj->count ) > number ) split_obj( obj, number - cnt ); cnt += obj->count; get_obj( ch, obj, NULL ); if( char_died( ch ) || ch->carry_number >= can_carry_n( ch ) || ch->carry_weight >= can_carry_w( ch ) || ( number && cnt >= number ) ) { if( IS_SET( sysdata.save_flags, SV_GET ) && !char_died( ch ) ) save_char_obj( ch ); return; } } } if( !found ) { if( fAll ) send_to_char( "I see nothing here.\r\n", ch ); else act( AT_PLAIN, "I see no $T here.", ch, NULL, chk, TO_CHAR ); } else if( IS_SET( sysdata.save_flags, SV_GET ) ) save_char_obj( ch ); } } else { /* * 'get ... container' */ if( !str_cmp( arg2, "all" ) || !str_prefix( "all.", arg2 ) ) { send_to_char( "You can't do that.\r\n", ch ); return; } if( ( container = get_obj_here( ch, arg2 ) ) == NULL ) { act( AT_PLAIN, "I see no $T here.", ch, NULL, arg2, TO_CHAR ); return; } switch ( container->item_type ) { default: if( !IS_OBJ_STAT( container, ITEM_COVERING ) ) { send_to_char( "That's not a container.\r\n", ch ); return; } if( ch->carry_weight + container->weight > can_carry_w( ch ) ) { send_to_char( "It's too heavy for you to lift.\r\n", ch ); return; } break; case ITEM_CONTAINER: case ITEM_CORPSE_NPC: case ITEM_KEYRING: case ITEM_QUIVER: break; case ITEM_CORPSE_PC: { char name[MAX_INPUT_LENGTH]; CHAR_DATA *gch; char *pd; if( IS_NPC( ch ) ) { send_to_char( "You can't do that.\r\n", ch ); return; } pd = container->short_descr; pd = one_argument( pd, name ); pd = one_argument( pd, name ); pd = one_argument( pd, name ); pd = one_argument( pd, name ); if( IS_OBJ_STAT( container, ITEM_CLANCORPSE ) && !IS_NPC( ch ) && ( get_timer( ch, TIMER_PKILLED ) > 0 ) && str_cmp( name, ch->name ) ) { send_to_char( "You cannot loot from that corpse...yet.\r\n", ch ); return; } /* * Killer/owner loot only if die to pkill blow --Blod */ if( IS_OBJ_STAT( container, ITEM_CLANCORPSE ) && !IS_NPC( ch ) && container->action_desc[0] != '\0' && str_cmp( name, ch->name ) && str_cmp( container->action_desc, ch->name ) ) { send_to_char( "You did not inflict the death blow upon this corpse.\r\n", ch ); return; } if( IS_OBJ_STAT( container, ITEM_CLANCORPSE ) && !IS_NPC( ch ) /*&& IS_SET( ch->pcdata->flags, PCFLAG_DEADLY ) */ && container->value[4] - ch->level < 10 && container->value[4] - ch->level > -10 ) break; if( str_cmp( name, ch->name ) && !IS_IMMORTAL( ch ) ) { bool fGroup; fGroup = FALSE; for( gch = first_char; gch; gch = gch->next ) { if( !IS_NPC( gch ) && is_same_group( ch, gch ) && !str_cmp( name, gch->name ) ) { fGroup = TRUE; break; } } } } } if( !IS_OBJ_STAT( container, ITEM_COVERING ) && IS_SET( container->value[1], CONT_CLOSED ) ) { act( AT_PLAIN, "The $d is closed.", ch, NULL, container->name, TO_CHAR ); return; } if( number <= 1 && str_cmp( arg1, "all" ) && str_prefix( "all.", arg1 ) ) { /* * 'get obj container' */ obj = get_obj_list( ch, arg1, container->first_content ); if( !obj ) { act( AT_PLAIN, IS_OBJ_STAT( container, ITEM_COVERING ) ? "I see nothing like that beneath the $T." : "I see nothing like that in the $T.", ch, NULL, arg2, TO_CHAR ); return; } separate_obj( obj ); get_obj( ch, obj, container ); if( container->item_type == ITEM_CORPSE_PC ) { char name[MAX_INPUT_LENGTH]; char *pd; pd = container->short_descr; pd = one_argument( pd, name ); pd = one_argument( pd, name ); pd = one_argument( pd, name ); pd = one_argument( pd, name ); if( str_cmp( name, ch->name ) ) { sprintf( buf, "%s is looting %s's corpse! %s(room %d)", ch->name, capitalize( name ), xIS_SET( obj->extra_flags, ITEM_CLANOBJECT ) ? "(ClanObject) " : "", ch->in_room->vnum ); log_string( buf ); sprintf( buf, "%s is looting %s's corpse at %s!", ch->name, capitalize( name ), ch->in_room->name ); do_info( NULL, buf ); } } /* * Oops no wonder corpses were duping oopsie did I do that * * --Shaddai */ if( container->item_type == ITEM_CORPSE_PC ) write_corpses( NULL, container->short_descr + 14, NULL ); check_for_trap( ch, container, TRAP_GET ); if( char_died( ch ) ) return; if( IS_SET( sysdata.save_flags, SV_GET ) ) save_char_obj( ch ); } else { int cnt = 0; bool fAll; char *chk; /* * 'get all container' or 'get all.obj container' */ if( IS_OBJ_STAT( container, ITEM_DONATION ) ) { send_to_char( "The gods frown upon such an act of greed!\r\n", ch ); return; } if( IS_OBJ_STAT( container, ITEM_CLANCORPSE ) && !IS_IMMORTAL( ch ) && !IS_NPC( ch ) && str_cmp( ch->name, container->name + 7 ) ) { send_to_char( "The gods frown upon such wanton greed!\r\n", ch ); return; } if( !str_cmp( arg1, "all" ) ) fAll = TRUE; else fAll = FALSE; if( number > 1 ) chk = arg1; else chk = &arg1[4]; found = FALSE; for( obj = container->first_content; obj; obj = obj_next ) { obj_next = obj->next_content; if( ( fAll || nifty_is_name( chk, obj->name ) ) && can_see_obj( ch, obj ) ) { found = TRUE; if( number && ( cnt + obj->count ) > number ) split_obj( obj, number - cnt ); cnt += obj->count; get_obj( ch, obj, container ); if( char_died( ch ) || ch->carry_number >= can_carry_n( ch ) || ch->carry_weight >= can_carry_w( ch ) || ( number && cnt >= number ) ) { if( container->item_type == ITEM_CORPSE_PC ) write_corpses( NULL, container->short_descr + 14, NULL ); if( found && IS_SET( sysdata.save_flags, SV_GET ) ) save_char_obj( ch ); return; } } } if( !found ) { if( fAll ) { if( container->item_type == ITEM_KEYRING && !IS_OBJ_STAT( container, ITEM_COVERING ) ) act( AT_PLAIN, "The $T holds no keys.", ch, NULL, arg2, TO_CHAR ); else act( AT_PLAIN, IS_OBJ_STAT( container, ITEM_COVERING ) ? "I see nothing beneath the $T." : "I see nothing in the $T.", ch, NULL, arg2, TO_CHAR ); } else { if( container->item_type == ITEM_KEYRING && !IS_OBJ_STAT( container, ITEM_COVERING ) ) act( AT_PLAIN, "The $T does not hold that key.", ch, NULL, arg2, TO_CHAR ); else act( AT_PLAIN, IS_OBJ_STAT( container, ITEM_COVERING ) ? "I see nothing like that beneath the $T." : "I see nothing like that in the $T.", ch, NULL, arg2, TO_CHAR ); } } else check_for_trap( ch, container, TRAP_GET ); if( char_died( ch ) ) return; /* * Oops no wonder corpses were duping oopsie did I do that * * --Shaddai */ if( container->item_type == ITEM_CORPSE_PC ) write_corpses( NULL, container->short_descr + 14, NULL ); if( found && IS_SET( sysdata.save_flags, SV_GET ) ) save_char_obj( ch ); } } return; } void do_put( CHAR_DATA * ch, char *argument ) { char arg1[MAX_INPUT_LENGTH]; char arg2[MAX_INPUT_LENGTH]; OBJ_DATA *container; OBJ_DATA *obj; OBJ_DATA *obj_next; CLAN_DATA *clan; short count; int number; bool save_char = FALSE; argument = one_argument( argument, arg1 ); if( is_number( arg1 ) ) { number = atoi( arg1 ); if( number < 1 ) { send_to_char( "That was easy...\r\n", ch ); return; } argument = one_argument( argument, arg1 ); } else number = 0; argument = one_argument( argument, arg2 ); /* * munch optional words */ if( ( !str_cmp( arg2, "into" ) || !str_cmp( arg2, "inside" ) || !str_cmp( arg2, "in" ) || !str_cmp( arg2, "under" ) || !str_cmp( arg2, "onto" ) || !str_cmp( arg2, "on" ) ) && argument[0] != '\0' ) argument = one_argument( argument, arg2 ); if( arg1[0] == '\0' || arg2[0] == '\0' ) { send_to_char( "Put what in what?\r\n", ch ); return; } if( ms_find_obj( ch ) ) return; if( !str_cmp( arg2, "all" ) || !str_prefix( "all.", arg2 ) ) { send_to_char( "You can't do that.\r\n", ch ); return; } if( ( container = get_obj_here( ch, arg2 ) ) == NULL ) { act( AT_PLAIN, "I see no $T here.", ch, NULL, arg2, TO_CHAR ); return; } if( !container->carried_by && IS_SET( sysdata.save_flags, SV_PUT ) ) save_char = TRUE; if( IS_OBJ_STAT( container, ITEM_COVERING ) ) { if( ch->carry_weight + container->weight > can_carry_w( ch ) ) { send_to_char( "It's too heavy for you to lift.\r\n", ch ); return; } } else { if( container->item_type != ITEM_CONTAINER && container->item_type != ITEM_KEYRING && container->item_type != ITEM_QUIVER ) { send_to_char( "That's not a container.\r\n", ch ); return; } if( IS_SET( container->value[1], CONT_CLOSED ) ) { act( AT_PLAIN, "The $d is closed.", ch, NULL, container->name, TO_CHAR ); return; } } if( number <= 1 && str_cmp( arg1, "all" ) && str_prefix( "all.", arg1 ) ) { /* * 'put obj container' */ if( ( obj = get_obj_carry( ch, arg1 ) ) == NULL ) { send_to_char( "You do not have that item.\r\n", ch ); return; } if( obj == container ) { send_to_char( "You can't fold it into itself.\r\n", ch ); return; } if( !can_drop_obj( ch, obj ) ) { send_to_char( "You can't let go of it.\r\n", ch ); return; } if( container->item_type == ITEM_KEYRING && obj->item_type != ITEM_KEY ) { send_to_char( "That's not a key.\r\n", ch ); return; } if( container->item_type == ITEM_QUIVER && obj->item_type != ITEM_PROJECTILE ) { send_to_char( "That's not a projectile.\r\n", ch ); return; } if( ( IS_OBJ_STAT( container, ITEM_COVERING ) && ( get_obj_weight( obj ) / obj->count ) > ( ( get_obj_weight( container ) / container->count ) - container->weight ) ) ) { send_to_char( "It won't fit under there.\r\n", ch ); return; } /* * note use of get_real_obj_weight */ if( ( get_real_obj_weight( obj ) / obj->count ) + ( get_real_obj_weight( container ) / container->count ) > container->value[0] ) { send_to_char( "It won't fit.\r\n", ch ); return; } separate_obj( obj ); separate_obj( container ); obj_from_char( obj ); obj = obj_to_obj( obj, container ); check_for_trap( ch, container, TRAP_PUT ); if( char_died( ch ) ) return; count = obj->count; obj->count = 1; if( container->item_type == ITEM_KEYRING && !IS_OBJ_STAT( container, ITEM_COVERING ) ) { act( AT_ACTION, "$n slips $p onto $P.", ch, obj, container, TO_ROOM ); act( AT_ACTION, "You slip $p onto $P.", ch, obj, container, TO_CHAR ); } else { act( AT_ACTION, IS_OBJ_STAT( container, ITEM_COVERING ) ? "$n hides $p beneath $P." : "$n puts $p in $P.", ch, obj, container, TO_ROOM ); act( AT_ACTION, IS_OBJ_STAT( container, ITEM_COVERING ) ? "You hide $p beneath $P." : "You put $p in $P.", ch, obj, container, TO_CHAR ); } obj->count = count; /* * Oops no wonder corpses were duping oopsie did I do that * * --Shaddai */ if( container->item_type == ITEM_CORPSE_PC ) write_corpses( NULL, container->short_descr + 14, NULL ); if( save_char ) save_char_obj( ch ); /* * Clan storeroom check */ if( IS_SET( ch->in_room->room_flags, ROOM_CLANSTOREROOM ) && container->carried_by == NULL ) { /* if (!char_died && !save_char ) save_char_obj(ch); */ for( clan = first_clan; clan; clan = clan->next ) if( clan->storeroom == ch->in_room->vnum ) save_clan_storeroom( ch, clan ); } } else { bool found = FALSE; int cnt = 0; bool fAll; char *chk; if( !str_cmp( arg1, "all" ) ) fAll = TRUE; else fAll = FALSE; if( number > 1 ) chk = arg1; else chk = &arg1[4]; separate_obj( container ); /* * 'put all container' or 'put all.obj container' */ for( obj = ch->first_carrying; obj; obj = obj_next ) { obj_next = obj->next_content; if( ( fAll || nifty_is_name( chk, obj->name ) ) && can_see_obj( ch, obj ) && obj->wear_loc == WEAR_NONE && obj != container && can_drop_obj( ch, obj ) && ( container->item_type != ITEM_KEYRING || obj->item_type == ITEM_KEY ) && ( container->item_type != ITEM_QUIVER || obj->item_type == ITEM_PROJECTILE ) && get_obj_weight( obj ) + get_obj_weight( container ) <= container->value[0] ) { if( number && ( cnt + obj->count ) > number ) split_obj( obj, number - cnt ); cnt += obj->count; obj_from_char( obj ); if( container->item_type == ITEM_KEYRING ) { act( AT_ACTION, "$n slips $p onto $P.", ch, obj, container, TO_ROOM ); act( AT_ACTION, "You slip $p onto $P.", ch, obj, container, TO_CHAR ); } else { act( AT_ACTION, "$n puts $p in $P.", ch, obj, container, TO_ROOM ); act( AT_ACTION, "You put $p in $P.", ch, obj, container, TO_CHAR ); } obj = obj_to_obj( obj, container ); found = TRUE; check_for_trap( ch, container, TRAP_PUT ); if( char_died( ch ) ) return; if( number && cnt >= number ) break; } } /* * Don't bother to save anything if nothing was dropped -Thoric */ if( !found ) { if( fAll ) act( AT_PLAIN, "You are not carrying anything.", ch, NULL, NULL, TO_CHAR ); else act( AT_PLAIN, "You are not carrying any $T.", ch, NULL, chk, TO_CHAR ); return; } if( save_char ) save_char_obj( ch ); /* * Oops no wonder corpses were duping oopsie did I do that * * --Shaddai */ if( container->item_type == ITEM_CORPSE_PC ) write_corpses( NULL, container->short_descr + 14, NULL ); /* * Clan storeroom check */ if( IS_SET( ch->in_room->room_flags, ROOM_CLANSTOREROOM ) && container->carried_by == NULL ) { /* if (!char_died && !save_char) save_char_obj(ch); */ for( clan = first_clan; clan; clan = clan->next ) if( clan->storeroom == ch->in_room->vnum ) save_clan_storeroom( ch, clan ); } } return; } void do_drop( CHAR_DATA * ch, char *argument ) { char arg[MAX_INPUT_LENGTH]; OBJ_DATA *obj; OBJ_DATA *obj_next; bool found; CLAN_DATA *clan; int number; int type = 3; argument = one_argument( argument, arg ); if( is_number( arg ) ) { number = atoi( arg ); if( number < 1 ) { send_to_char( "That was easy...\r\n", ch ); return; } argument = one_argument( argument, arg ); } else number = 0; if( arg[0] == '\0' ) { send_to_char( "Drop what?\r\n", ch ); return; } if( ms_find_obj( ch ) ) return; if( xIS_SET( ch->act, PLR_LITTERBUG ) ) { set_char_color( AT_YELLOW, ch ); send_to_char( "A godly force prevents you from dropping anything...\r\n", ch ); return; } if( IS_SET( ch->in_room->room_flags, ROOM_NODROP ) && ch != supermob ) { set_char_color( AT_MAGIC, ch ); send_to_char( "A magical force stops you!\r\n", ch ); set_char_color( AT_TELL, ch ); send_to_char( "Someone tells you, 'No littering here!'\r\n", ch ); return; } if( number > 0 ) { /* * 'drop NNNN coins' */ if( !str_cmp( arg, "gold" ) || !str_cmp( arg, "copper" ) || !str_cmp( arg, "silver" ) ) { /* * type 0 = gold * type 1 = silver * type 2 = copper */ if( !str_cmp( arg, "gold" ) ) type = 0; if( !str_cmp( arg, "silver" ) ) type = 1; if( !str_cmp( arg, "copper" ) ) type = 2; if( type == 0 && ch->gold < number ) { send_to_char( "You haven't got that many coins.\r\n", ch ); return; } if( type == 1 && ch->silver < number ) { send_to_char( "You haven't got that many coins.\r\n", ch ); return; } if( type == 2 && ch->copper < number ) { send_to_char( "You haven't got that many coins.\r\n", ch ); return; } if( type > 2 || type < 0 ) { send_to_char( " <BUG> invalid type, Report to Ddruid\r\n", ch ); return; } if( type == 0 ) ch->gold -= number; if( type == 1 ) ch->silver -= number; if( type == 2 ) ch->copper -= number; for( obj = ch->in_room->first_content; obj; obj = obj_next ) { obj_next = obj->next_content; switch ( obj->pIndexData->vnum ) { case OBJ_VNUM_GOLD_ONE: if( type == 0 ) { number += 1; extract_obj( obj ); } break; case OBJ_VNUM_GOLD_SOME: if( type == 0 ) { number += obj->value[0]; extract_obj( obj ); } break; case OBJ_VNUM_SILVER_ONE: if( type == 1 ) { number += 1; extract_obj( obj ); } break; case OBJ_VNUM_SILVER_SOME: if( type == 1 ) { number += obj->value[0]; extract_obj( obj ); } break; case OBJ_VNUM_COPPER_ONE: if( type == 2 ) { number += 1; extract_obj( obj ); } break; case OBJ_VNUM_COPPER_SOME: if( type == 2 ) { number += obj->value[0]; extract_obj( obj ); } break; } } if( type == 0 ) { act( AT_ACTION, "$n drops some gold.", ch, NULL, NULL, TO_ROOM ); obj_to_room( create_money( number, 0 ), ch->in_room ); send_to_char( "You let the gold slip from your hand.\r\n", ch ); } if( type == 1 ) { act( AT_ACTION, "$n drops some silver.", ch, NULL, NULL, TO_ROOM ); obj_to_room( create_money( number, 1 ), ch->in_room ); send_to_char( "You let the silver slip from your hand.\r\n", ch ); } if( type == 2 ) { act( AT_ACTION, "$n drops some copper.", ch, NULL, NULL, TO_ROOM ); obj_to_room( create_money( number, 2 ), ch->in_room ); send_to_char( "You let the copper slip from your hand.\r\n", ch ); } if( IS_SET( sysdata.save_flags, SV_DROP ) ) save_char_obj( ch ); return; } } if( number <= 1 && str_cmp( arg, "all" ) && str_prefix( "all.", arg ) ) { /* * 'drop obj' */ if( ( obj = get_obj_carry( ch, arg ) ) == NULL ) { send_to_char( "You do not have that item.\r\n", ch ); return; } if( !can_drop_obj( ch, obj ) ) { send_to_char( "You can't let go of it.\r\n", ch ); return; } separate_obj( obj ); act( AT_ACTION, "$n drops $p.", ch, obj, NULL, TO_ROOM ); act( AT_ACTION, "You drop $p.", ch, obj, NULL, TO_CHAR ); obj_from_char( obj ); obj = obj_to_room( obj, ch->in_room ); oprog_drop_trigger( ch, obj ); /* mudprogs */ if( char_died( ch ) || obj_extracted( obj ) ) return; /* * Clan storeroom saving */ if( IS_SET( ch->in_room->room_flags, ROOM_CLANSTOREROOM ) ) { /* if (!char_died) save_char_obj(ch); */ for( clan = first_clan; clan; clan = clan->next ) if( clan->storeroom == ch->in_room->vnum ) save_clan_storeroom( ch, clan ); } } else { int cnt = 0; char *chk; bool fAll; if( !str_cmp( arg, "all" ) ) fAll = TRUE; else fAll = FALSE; if( number > 1 ) chk = arg; else chk = &arg[4]; /* * 'drop all' or 'drop all.obj' */ if( IS_SET( ch->in_room->room_flags, ROOM_NODROPALL ) || IS_SET( ch->in_room->room_flags, ROOM_CLANSTOREROOM ) ) { send_to_char( "You can't seem to do that here...\r\n", ch ); return; } found = FALSE; for( obj = ch->first_carrying; obj; obj = obj_next ) { obj_next = obj->next_content; if( ( fAll || nifty_is_name( chk, obj->name ) ) && can_see_obj( ch, obj ) && obj->wear_loc == WEAR_NONE && can_drop_obj( ch, obj ) ) { found = TRUE; if( HAS_PROG( obj->pIndexData, DROP_PROG ) && obj->count > 1 ) { ++cnt; separate_obj( obj ); obj_from_char( obj ); if( !obj_next ) obj_next = ch->first_carrying; } else { if( number && ( cnt + obj->count ) > number ) split_obj( obj, number - cnt ); cnt += obj->count; obj_from_char( obj ); } act( AT_ACTION, "$n drops $p.", ch, obj, NULL, TO_ROOM ); act( AT_ACTION, "You drop $p.", ch, obj, NULL, TO_CHAR ); obj = obj_to_room( obj, ch->in_room ); oprog_drop_trigger( ch, obj ); /* mudprogs */ if( char_died( ch ) ) return; if( number && cnt >= number ) break; } } if( !found ) { if( fAll ) act( AT_PLAIN, "You are not carrying anything.", ch, NULL, NULL, TO_CHAR ); else act( AT_PLAIN, "You are not carrying any $T.", ch, NULL, chk, TO_CHAR ); } } save_house_by_vnum( ch->in_room->vnum ); /* House Object Saving */ if( IS_SET( sysdata.save_flags, SV_DROP ) ) save_char_obj( ch ); /* duping protector */ return; } void do_give( CHAR_DATA * ch, char *argument ) { char arg1[MAX_INPUT_LENGTH]; char arg2[MAX_INPUT_LENGTH]; char buf[MAX_INPUT_LENGTH]; CHAR_DATA *victim; OBJ_DATA *obj; int type = 3; argument = one_argument( argument, arg1 ); argument = one_argument( argument, arg2 ); if( !str_cmp( arg2, "to" ) && argument[0] != '\0' ) argument = one_argument( argument, arg2 ); if( arg1[0] == '\0' || arg2[0] == '\0' ) { send_to_char( "Give what to whom?\r\n", ch ); return; } if( ms_find_obj( ch ) ) return; if( is_number( arg1 ) ) { /* * 'give NNNN coins victim' */ int amount; amount = atoi( arg1 ); if( amount <= 0 || ( str_cmp( arg2, "gold" ) && str_cmp( arg2, "silver" ) && str_cmp( arg2, "copper" ) ) ) { send_to_char( "Sorry, you can't do that.\r\n", ch ); return; } /* * type 0 = gold * type 1 = silver * type 2 = copper * -Druid */ if( !str_cmp( arg2, "gold" ) ) type = 0; if( !str_cmp( arg2, "silver" ) ) type = 1; if( !str_cmp( arg2, "copper" ) ) type = 2; if( type > 2 || type < 0 ) { send_to_char( "<BUG> invalid coin type, report to Ddruid.\r\n", ch ); return; } argument = one_argument( argument, arg2 ); if( !str_cmp( arg2, "to" ) && argument[0] != '\0' ) argument = one_argument( argument, arg2 ); if( arg2[0] == '\0' ) { send_to_char( "Give what to whom?\r\n", ch ); return; } if( ( victim = get_char_room( ch, arg2 ) ) == NULL ) { send_to_char( "They aren't here.\r\n", ch ); return; } if( type == 0 && ch->gold < amount ) { send_to_char( "Very generous of you, but you haven't got that much gold.\r\n", ch ); return; } if( type == 1 && ch->silver < amount ) { send_to_char( "Very generous of you, but you haven't got that much silver.\r\n", ch ); return; } if( type == 2 && ch->copper < amount ) { send_to_char( "Very generous of you, but you haven't got that much copper.\r\n", ch ); return; } if( type == 0 ) { ch->gold -= amount; victim->gold += amount; strcpy( buf, "$n gives you " ); strcat( buf, arg1 ); strcat( buf, ( amount > 1 ) ? " gold coins." : " gold coin." ); act( AT_ACTION, buf, ch, NULL, victim, TO_VICT ); act( AT_ACTION, "$n gives $N some gold.", ch, NULL, victim, TO_NOTVICT ); act( AT_ACTION, "You give $N some gold.", ch, NULL, victim, TO_CHAR ); mprog_bribe_trigger( victim, ch, amount ); } if( type == 1 ) { ch->silver -= amount; victim->silver += amount; strcpy( buf, "$n gives you " ); strcat( buf, arg1 ); strcat( buf, ( amount > 1 ) ? " silver coins." : " silver coin." ); act( AT_ACTION, buf, ch, NULL, victim, TO_VICT ); act( AT_ACTION, "$n gives $N some silver.", ch, NULL, victim, TO_NOTVICT ); act( AT_ACTION, "You give $N some silver.", ch, NULL, victim, TO_CHAR ); mprog_bribe_trigger_silver( victim, ch, amount ); } if( type == 2 ) { ch->copper -= amount; victim->copper += amount; strcpy( buf, "$n gives you " ); strcat( buf, arg1 ); strcat( buf, ( amount > 1 ) ? " copper coins." : " copper coin." ); act( AT_ACTION, buf, ch, NULL, victim, TO_VICT ); act( AT_ACTION, "$n gives $N some copper.", ch, NULL, victim, TO_NOTVICT ); act( AT_ACTION, "You give $N some copper.", ch, NULL, victim, TO_CHAR ); mprog_bribe_trigger_copper( victim, ch, amount ); if( IS_SET( sysdata.save_flags, SV_GIVE ) && !char_died( ch ) ) save_char_obj( ch ); if( IS_SET( sysdata.save_flags, SV_RECEIVE ) && !char_died( victim ) ) save_char_obj( victim ); return; } } else { if( ( obj = get_obj_carry( ch, arg1 ) ) == NULL ) { send_to_char( "You do not have that item.\r\n", ch ); return; } if( obj->wear_loc != WEAR_NONE ) { send_to_char( "You must remove it first.\r\n", ch ); return; } if( ( victim = get_char_room( ch, arg2 ) ) == NULL ) { send_to_char( "They aren't here.\r\n", ch ); return; } if( !can_drop_obj( ch, obj ) ) { send_to_char( "You can't let go of it.\r\n", ch ); return; } if( victim->carry_number + ( get_obj_number( obj ) / obj->count ) > can_carry_n( victim ) ) { act( AT_PLAIN, "$N has $S hands full.", ch, NULL, victim, TO_CHAR ); return; } if( victim->carry_weight + ( get_obj_weight( obj ) / obj->count ) > can_carry_w( victim ) ) { act( AT_PLAIN, "$N can't carry that much weight.", ch, NULL, victim, TO_CHAR ); return; } if( !can_see_obj( victim, obj ) ) { act( AT_PLAIN, "$N can't see it.", ch, NULL, victim, TO_CHAR ); return; } if( IS_OBJ_STAT( obj, ITEM_PROTOTYPE ) && !can_take_proto( victim ) ) { act( AT_PLAIN, "You cannot give that to $N!", ch, NULL, victim, TO_CHAR ); return; } separate_obj( obj ); obj_from_char( obj ); act( AT_ACTION, "$n gives $p to $N.", ch, obj, victim, TO_NOTVICT ); act( AT_ACTION, "$n gives you $p.", ch, obj, victim, TO_VICT ); act( AT_ACTION, "You give $p to $N.", ch, obj, victim, TO_CHAR ); obj = obj_to_char( obj, victim ); mprog_give_trigger( victim, ch, obj ); if( IS_SET( sysdata.save_flags, SV_GIVE ) && !char_died( ch ) ) save_char_obj( ch ); if( IS_SET( sysdata.save_flags, SV_RECEIVE ) && !char_died( victim ) ) save_char_obj( victim ); return; } } /* * Damage an object. -Thoric * Affect player's AC if necessary. * Make object into scraps if necessary. * Send message about damaged object. */ obj_ret damage_obj( OBJ_DATA * obj ) { CHAR_DATA *ch; obj_ret objcode; ch = obj->carried_by; objcode = rNONE; separate_obj( obj ); if( !IS_NPC( ch ) && ( !IS_PKILL( ch ) || ( IS_PKILL( ch ) && !IS_SET( ch->pcdata->flags, PCFLAG_GAG ) ) ) ) act( AT_OBJECT, "($p gets damaged)", ch, obj, NULL, TO_CHAR ); else if( obj->in_room && ( ch = obj->in_room->first_person ) != NULL ) { act( AT_OBJECT, "($p gets damaged)", ch, obj, NULL, TO_ROOM ); act( AT_OBJECT, "($p gets damaged)", ch, obj, NULL, TO_CHAR ); ch = NULL; } if( obj->item_type != ITEM_LIGHT && !IS_OBJ_STAT( obj, ITEM_NOSCRAP ) && !in_arena( ch ) ) oprog_damage_trigger( ch, obj ); if( obj_extracted( obj ) ) return global_objcode; /* * Don't scrap the item */ if( IS_OBJ_STAT( obj, ITEM_NOSCRAP ) ) return objcode; switch ( obj->item_type ) { default: make_scraps( obj ); objcode = rOBJ_SCRAPPED; break; case ITEM_CONTAINER: case ITEM_KEYRING: case ITEM_QUIVER: if( --obj->value[3] <= 0 ) { if( !in_arena( ch ) ) { make_scraps( obj ); objcode = rOBJ_SCRAPPED; } else obj->value[3] = 1; } break; case ITEM_LIGHT: if( --obj->value[0] <= 0 ) { if( !in_arena( ch ) ) { make_scraps( obj ); objcode = rOBJ_SCRAPPED; } else obj->value[0] = 1; } break; case ITEM_ARMOR: if( ch && obj->value[0] >= 1 ) ch->armor += apply_ac( obj, obj->wear_loc ); if( --obj->value[0] <= 0 ) { if( !IS_PKILL( ch ) && !in_arena( ch ) ) { make_scraps( obj ); objcode = rOBJ_SCRAPPED; } else { obj->value[0] = 1; ch->armor -= apply_ac( obj, obj->wear_loc ); } } else if( ch && obj->value[0] >= 1 ) ch->armor -= apply_ac( obj, obj->wear_loc ); break; case ITEM_WEAPON: if( --obj->value[0] <= 0 ) { if( !IS_PKILL( ch ) && !in_arena( ch ) ) { make_scraps( obj ); objcode = rOBJ_SCRAPPED; } else obj->value[0] = 1; } break; } if( ch != NULL ) save_char_obj( ch ); /* Stop scrap duping - Samson 1-2-00 */ return objcode; } /* * Remove an object. */ bool remove_obj( CHAR_DATA * ch, int iWear, bool fReplace ) { OBJ_DATA *obj, *tmpobj; if( ( obj = get_eq_char( ch, iWear ) ) == NULL ) return TRUE; if( !fReplace && ch->carry_number + get_obj_number( obj ) > can_carry_n( ch ) ) { act( AT_PLAIN, "$d: you can't carry that many items.", ch, NULL, obj->name, TO_CHAR ); return FALSE; } if( !fReplace ) return FALSE; if( IS_OBJ_STAT( obj, ITEM_NOREMOVE ) ) { act( AT_PLAIN, "You can't remove $p.", ch, obj, NULL, TO_CHAR ); return FALSE; } if( obj == get_eq_char( ch, WEAR_WIELD ) && ( tmpobj = get_eq_char( ch, WEAR_DUAL_WIELD ) ) != NULL ) tmpobj->wear_loc = WEAR_WIELD; if( obj == get_eq_char( ch, WEAR_FLOAT ) ) { act( AT_ACTION, "$n grabs $p from the air above $s head.", ch, obj, NULL, TO_ROOM ); act( AT_ACTION, "You grab $p from the air above your head.", ch, obj, NULL, TO_CHAR ); } else { act( AT_ACTION, "$n stops using $p.", ch, obj, NULL, TO_ROOM ); act( AT_ACTION, "You stop using $p.", ch, obj, NULL, TO_CHAR ); } unequip_char( ch, obj ); oprog_remove_trigger( ch, obj ); return TRUE; } /* * See if char could be capable of dual-wielding -Thoric */ bool could_dual( CHAR_DATA * ch ) { if( IS_NPC( ch ) || ch->pcdata->learned[gsn_dual_wield] ) return TRUE; return FALSE; } /* * Check for the ability to dual-wield under all conditions. -Orion * * Original version by Thoric. */ bool can_dual( CHAR_DATA * ch ) { /* * We must assume that when they come in, they are NOT wielding something. We * take care of the actual value later. -Orion */ bool wielding[2], alreadyWielding = FALSE; wielding[0] = FALSE; wielding[1] = FALSE; /* * If they don't have the ability to dual-wield, why should we allow them to * do so? -Orion */ if( !could_dual( ch ) ) return FALSE; /* * Get that true wielding value I mentioned earlier. If they're wielding and * missile wielding, we can simply return FALSE. If not, set the values. -Orion */ if( get_eq_char( ch, WEAR_WIELD ) && get_eq_char( ch, WEAR_MISSILE_WIELD ) ) { send_to_char( "You are already wielding two weapons... grow some more arms!\r\n", ch ); return FALSE; } else { /* * Wield position. -Orion */ wielding[0] = get_eq_char( ch, WEAR_WIELD ) ? TRUE : FALSE; /* * Missile wield position. -Orion */ wielding[1] = get_eq_char( ch, WEAR_MISSILE_WIELD ) ? TRUE : FALSE; } /* * Save some extra typing farther down. -Orion */ if( wielding[0] || wielding[1] ) alreadyWielding = TRUE; /* * If wielding and dual wielding, then they can't wear another weapon. Return * FALSE. We can assume that dual wield will not be full if there is no wield * slot already filled. -Orion */ if( wielding[0] && get_eq_char( ch, WEAR_DUAL_WIELD ) ) { send_to_char( "You are already wielding two weapons... grow some more arms!\r\n", ch ); return FALSE; } /* * If wielding or missile wielding and holding a shield, then we can return * FALSE. -Orion */ if( alreadyWielding && get_eq_char( ch, WEAR_SHIELD ) ) { send_to_char( "You cannot dual wield, you're already holding a shield!\r\n", ch ); return FALSE; } /* * If wielding or missile wielding and holding something, then we can return * FALSE. -Orion */ if( alreadyWielding && get_eq_char( ch, WEAR_HOLD ) ) { send_to_char( "You cannot hold another weapon, you're already holding something in that hand!\r\n", ch ); return FALSE; } return TRUE; } /* * Check to see if there is room to wear another object on this location * (Layered clothing support) */ bool can_layer( CHAR_DATA * ch, OBJ_DATA * obj, short wear_loc ) { OBJ_DATA *otmp; short bitlayers = 0; short objlayers = obj->pIndexData->layers; for( otmp = ch->first_carrying; otmp; otmp = otmp->next_content ) if( otmp->wear_loc == wear_loc ) { if( !otmp->pIndexData->layers ) return FALSE; else bitlayers |= otmp->pIndexData->layers; } if( ( bitlayers && !objlayers ) || bitlayers > objlayers ) return FALSE; if( !bitlayers || ( ( bitlayers & ~objlayers ) == bitlayers ) ) return TRUE; return FALSE; } /* * Wear one object. * Optional replacement of existing objects. * Big repetitive code, ick. * * Restructured a bit to allow for specifying body location -Thoric * & Added support for layering on certain body locations */ void wear_obj( CHAR_DATA * ch, OBJ_DATA * obj, bool fReplace, short wear_bit ) { char buf[MAX_STRING_LENGTH]; OBJ_DATA *tmpobj = NULL; short bit, tmp; separate_obj( obj ); /* * We now will keep people below level 50 from using * * objects above level 50 -- Kratas */ /* * Put back to characters needing to be exact level of object * * -Garinan */ if( ( ch->level2 == -1 || ch->level3 == -1 ) && obj->level > get_trust( ch ) ) { sprintf( buf, "You must be level %d to use this object.\r\n", obj->level ); send_to_char( buf, ch ); act( AT_ACTION, "$n tries to use $p, but is too inexperienced.", ch, obj, NULL, TO_ROOM ); return; } /* * Note, ch->level HAS to be used as opposed to get_trust because ch->level * * holds the remorted level! */ else if( ( ch->level2 != -1 || ch->level3 != -1 ) && obj->level > ch->level && !IS_IMMORTAL( ch ) ) { sprintf( buf, "You need to be level %d or above to use this object.\r\n", obj->level ); send_to_char( buf, ch ); act( AT_ACTION, "$n tries to use $p, but is too inexperienced.", ch, obj, NULL, TO_ROOM ); return; } if( !IS_IMMORTAL( ch ) && ( ( IS_OBJ_STAT( obj, ITEM_ANTI_WARRIOR ) && is_class( ch, CLASS_WARRIOR ) ) || ( IS_OBJ_STAT( obj, ITEM_ANTI_WARRIOR ) && is_class( ch, 8 ) ) || ( IS_OBJ_STAT( obj, ITEM_ANTI_MAGE ) && is_class( ch, CLASS_MAGE ) ) || ( IS_OBJ_STAT( obj, ITEM_ANTI_THIEF ) && is_class( ch, CLASS_THIEF ) ) || ( IS_OBJ_STAT( obj, ITEM_ANTI_VAMPIRE ) && ch->race == RACE_VAMPIRE ) || ( IS_OBJ_STAT( obj, ITEM_ANTI_DRUID ) && is_class( ch, CLASS_DRUID ) ) || ( IS_OBJ_STAT( obj, ITEM_ANTI_WARRIOR ) && is_class( ch, CLASS_RANGER ) ) || ( IS_OBJ_STAT( obj, ITEM_ANTI_MAGE ) && is_class( ch, CLASS_AUGURER ) ) || ( IS_OBJ_STAT( obj, ITEM_ANTI_CLERIC ) && is_class( ch, CLASS_CLERIC ) ) ) ) { act( AT_MAGIC, "You are forbidden to use that item.", ch, NULL, NULL, TO_CHAR ); act( AT_ACTION, "$n tries to use $p, but is forbidden to do so.", ch, obj, NULL, TO_ROOM ); return; } if( wear_bit > -1 ) { bit = wear_bit; if( !CAN_WEAR( obj, 1 << bit ) ) { if( fReplace ) { switch ( 1 << bit ) { case ITEM_HOLD: send_to_char( "You cannot hold that.\r\n", ch ); break; case ITEM_WIELD: case ITEM_MISSILE_WIELD: send_to_char( "You cannot wield that.\r\n", ch ); break; default: sprintf( buf, "You cannot wear that on your %s.\r\n", w_flags[bit] ); send_to_char( buf, ch ); } } return; } } else { for( bit = -1, tmp = 1; tmp < 31; tmp++ ) { if( CAN_WEAR( obj, 1 << tmp ) ) { bit = tmp; break; } } } /* * currently cannot have a light in non-light position */ if( obj->item_type == ITEM_LIGHT ) { if( !remove_obj( ch, WEAR_LIGHT, fReplace ) ) return; if( !oprog_use_trigger( ch, obj, NULL, NULL ) ) { act( AT_ACTION, "$n holds $p as a light.", ch, obj, NULL, TO_ROOM ); act( AT_ACTION, "You hold $p as your light.", ch, obj, NULL, TO_CHAR ); } equip_char( ch, obj, WEAR_LIGHT ); oprog_wear_trigger( ch, obj ); return; } if( bit == -1 ) { if( fReplace ) send_to_char( "You can't wear, wield, or hold that.\r\n", ch ); return; } switch ( 1 << bit ) { default: bug( "wear_obj: uknown/unused item_wear bit %d. %s room %d", bit, ch->name, ch->in_room->vnum ); if( fReplace ) send_to_char( "You can't wear, wield, or hold that.\r\n", ch ); return; case ITEM_WEAR_FINGER: if( get_eq_char( ch, WEAR_FINGER_L ) && get_eq_char( ch, WEAR_FINGER_R ) && !remove_obj( ch, WEAR_FINGER_L, fReplace ) && !remove_obj( ch, WEAR_FINGER_R, fReplace ) ) return; if( !get_eq_char( ch, WEAR_FINGER_L ) ) { if( !oprog_use_trigger( ch, obj, NULL, NULL ) ) { act( AT_ACTION, "$n slips $s left finger into $p.", ch, obj, NULL, TO_ROOM ); act( AT_ACTION, "You slip your left finger into $p.", ch, obj, NULL, TO_CHAR ); } equip_char( ch, obj, WEAR_FINGER_L ); oprog_wear_trigger( ch, obj ); return; } if( !get_eq_char( ch, WEAR_FINGER_R ) ) { if( !oprog_use_trigger( ch, obj, NULL, NULL ) ) { act( AT_ACTION, "$n slips $s right finger into $p.", ch, obj, NULL, TO_ROOM ); act( AT_ACTION, "You slip your right finger into $p.", ch, obj, NULL, TO_CHAR ); } equip_char( ch, obj, WEAR_FINGER_R ); oprog_wear_trigger( ch, obj ); return; } bug( "Wear_obj: no free finger.", 0 ); send_to_char( "You already wear something on both fingers.\r\n", ch ); return; case ITEM_WEAR_NECK: if( get_eq_char( ch, WEAR_NECK_1 ) != NULL && get_eq_char( ch, WEAR_NECK_2 ) != NULL && !remove_obj( ch, WEAR_NECK_1, fReplace ) && !remove_obj( ch, WEAR_NECK_2, fReplace ) ) return; if( !get_eq_char( ch, WEAR_NECK_1 ) ) { if( !oprog_use_trigger( ch, obj, NULL, NULL ) ) { act( AT_ACTION, "$n wears $p around $s neck.", ch, obj, NULL, TO_ROOM ); act( AT_ACTION, "You wear $p around your neck.", ch, obj, NULL, TO_CHAR ); } equip_char( ch, obj, WEAR_NECK_1 ); oprog_wear_trigger( ch, obj ); return; } if( !get_eq_char( ch, WEAR_NECK_2 ) ) { if( !oprog_use_trigger( ch, obj, NULL, NULL ) ) { act( AT_ACTION, "$n wears $p around $s neck.", ch, obj, NULL, TO_ROOM ); act( AT_ACTION, "You wear $p around your neck.", ch, obj, NULL, TO_CHAR ); } equip_char( ch, obj, WEAR_NECK_2 ); oprog_wear_trigger( ch, obj ); return; } bug( "Wear_obj: no free neck.", 0 ); send_to_char( "You already wear two neck items.\r\n", ch ); return; case ITEM_WEAR_BODY: /* * if ( !remove_obj( ch, WEAR_BODY, fReplace ) ) * return; */ if( !can_layer( ch, obj, WEAR_BODY ) ) { send_to_char( "It won't fit overtop of what you're already wearing.\r\n", ch ); return; } if( !oprog_use_trigger( ch, obj, NULL, NULL ) ) { act( AT_ACTION, "$n fits $p on $s body.", ch, obj, NULL, TO_ROOM ); act( AT_ACTION, "You fit $p on your body.", ch, obj, NULL, TO_CHAR ); } equip_char( ch, obj, WEAR_BODY ); oprog_wear_trigger( ch, obj ); return; case ITEM_WEAR_HEAD: if( !remove_obj( ch, WEAR_HEAD, fReplace ) ) return; if( !oprog_use_trigger( ch, obj, NULL, NULL ) ) { act( AT_ACTION, "$n dons $p upon $s head.", ch, obj, NULL, TO_ROOM ); act( AT_ACTION, "You don $p upon your head.", ch, obj, NULL, TO_CHAR ); } equip_char( ch, obj, WEAR_HEAD ); oprog_wear_trigger( ch, obj ); return; case ITEM_WEAR_EYES: if( !remove_obj( ch, WEAR_EYES, fReplace ) ) return; if( !oprog_use_trigger( ch, obj, NULL, NULL ) ) { act( AT_ACTION, "$n places $p on $s eyes.", ch, obj, NULL, TO_ROOM ); act( AT_ACTION, "You place $p on your eyes.", ch, obj, NULL, TO_CHAR ); } equip_char( ch, obj, WEAR_EYES ); oprog_wear_trigger( ch, obj ); return; case ITEM_WEAR_FACE: if( !remove_obj( ch, WEAR_FACE, fReplace ) ) return; if( !oprog_use_trigger( ch, obj, NULL, NULL ) ) { act( AT_ACTION, "$n places $p on $s face.", ch, obj, NULL, TO_ROOM ); act( AT_ACTION, "You place $p on your face.", ch, obj, NULL, TO_CHAR ); } equip_char( ch, obj, WEAR_FACE ); oprog_wear_trigger( ch, obj ); return; case ITEM_WEAR_EARS: if( !remove_obj( ch, WEAR_EARS, fReplace ) ) return; if( !oprog_use_trigger( ch, obj, NULL, NULL ) ) { act( AT_ACTION, "$n wears $p on $s ears.", ch, obj, NULL, TO_ROOM ); act( AT_ACTION, "You wear $p on your ears.", ch, obj, NULL, TO_CHAR ); } equip_char( ch, obj, WEAR_EARS ); oprog_wear_trigger( ch, obj ); return; case ITEM_WEAR_LEGS: if( !can_layer( ch, obj, WEAR_LEGS ) ) { send_to_char( "It won't fit overtop of what you're already wearing.\r\n", ch ); return; } if( !oprog_use_trigger( ch, obj, NULL, NULL ) ) { act( AT_ACTION, "$n slips into $p.", ch, obj, NULL, TO_ROOM ); act( AT_ACTION, "You slip into $p.", ch, obj, NULL, TO_CHAR ); } equip_char( ch, obj, WEAR_LEGS ); oprog_wear_trigger( ch, obj ); return; case ITEM_WEAR_FEET: if( !can_layer( ch, obj, WEAR_FEET ) ) { send_to_char( "It won't fit overtop of what you're already wearing.\r\n", ch ); return; } if( !oprog_use_trigger( ch, obj, NULL, NULL ) ) { act( AT_ACTION, "$n wears $p on $s feet.", ch, obj, NULL, TO_ROOM ); act( AT_ACTION, "You wear $p on your feet.", ch, obj, NULL, TO_CHAR ); } equip_char( ch, obj, WEAR_FEET ); oprog_wear_trigger( ch, obj ); return; case ITEM_WEAR_HANDS: if( !can_layer( ch, obj, WEAR_HANDS ) ) { send_to_char( "It won't fit overtop of what you're already wearing.\r\n", ch ); return; } if( !oprog_use_trigger( ch, obj, NULL, NULL ) ) { act( AT_ACTION, "$n wears $p on $s hands.", ch, obj, NULL, TO_ROOM ); act( AT_ACTION, "You wear $p on your hands.", ch, obj, NULL, TO_CHAR ); } equip_char( ch, obj, WEAR_HANDS ); oprog_wear_trigger( ch, obj ); return; case ITEM_WEAR_ARMS: if( !can_layer( ch, obj, WEAR_ARMS ) ) { send_to_char( "It won't fit overtop of what you're already wearing.\r\n", ch ); return; } if( !oprog_use_trigger( ch, obj, NULL, NULL ) ) { act( AT_ACTION, "$n wears $p on $s arms.", ch, obj, NULL, TO_ROOM ); act( AT_ACTION, "You wear $p on your arms.", ch, obj, NULL, TO_CHAR ); } equip_char( ch, obj, WEAR_ARMS ); oprog_wear_trigger( ch, obj ); return; case ITEM_WEAR_ABOUT: if( !can_layer( ch, obj, WEAR_ABOUT ) ) { send_to_char( "It won't fit overtop of what you're already wearing.\r\n", ch ); return; } if( !oprog_use_trigger( ch, obj, NULL, NULL ) ) { act( AT_ACTION, "$n wears $p about $s body.", ch, obj, NULL, TO_ROOM ); act( AT_ACTION, "You wear $p about your body.", ch, obj, NULL, TO_CHAR ); } equip_char( ch, obj, WEAR_ABOUT ); oprog_wear_trigger( ch, obj ); return; case ITEM_WEAR_BACK: if( !remove_obj( ch, WEAR_BACK, fReplace ) ) return; if( !oprog_use_trigger( ch, obj, NULL, NULL ) ) { act( AT_ACTION, "$n slings $p on $s back.", ch, obj, NULL, TO_ROOM ); act( AT_ACTION, "You sling $p on your back.", ch, obj, NULL, TO_CHAR ); } equip_char( ch, obj, WEAR_BACK ); oprog_wear_trigger( ch, obj ); return; case ITEM_WEAR_WAIST: if( !can_layer( ch, obj, WEAR_WAIST ) ) { send_to_char( "It won't fit overtop of what you're already wearing.\r\n", ch ); return; } if( !oprog_use_trigger( ch, obj, NULL, NULL ) ) { act( AT_ACTION, "$n wears $p about $s waist.", ch, obj, NULL, TO_ROOM ); act( AT_ACTION, "You wear $p about your waist.", ch, obj, NULL, TO_CHAR ); } equip_char( ch, obj, WEAR_WAIST ); oprog_wear_trigger( ch, obj ); return; case ITEM_WEAR_WRIST: if( get_eq_char( ch, WEAR_WRIST_L ) && get_eq_char( ch, WEAR_WRIST_R ) && !remove_obj( ch, WEAR_WRIST_L, fReplace ) && !remove_obj( ch, WEAR_WRIST_R, fReplace ) ) return; if( !get_eq_char( ch, WEAR_WRIST_L ) ) { if( !oprog_use_trigger( ch, obj, NULL, NULL ) ) { act( AT_ACTION, "$n fits $p around $s left wrist.", ch, obj, NULL, TO_ROOM ); act( AT_ACTION, "You fit $p around your left wrist.", ch, obj, NULL, TO_CHAR ); } equip_char( ch, obj, WEAR_WRIST_L ); oprog_wear_trigger( ch, obj ); return; } if( !get_eq_char( ch, WEAR_WRIST_R ) ) { if( !oprog_use_trigger( ch, obj, NULL, NULL ) ) { act( AT_ACTION, "$n fits $p around $s right wrist.", ch, obj, NULL, TO_ROOM ); act( AT_ACTION, "You fit $p around your right wrist.", ch, obj, NULL, TO_CHAR ); } equip_char( ch, obj, WEAR_WRIST_R ); oprog_wear_trigger( ch, obj ); return; } bug( "Wear_obj: no free wrist.", 0 ); send_to_char( "You already wear two wrist items.\r\n", ch ); return; case ITEM_WEAR_ANKLE: if( get_eq_char( ch, WEAR_ANKLE_L ) && get_eq_char( ch, WEAR_ANKLE_R ) && !remove_obj( ch, WEAR_ANKLE_L, fReplace ) && !remove_obj( ch, WEAR_ANKLE_R, fReplace ) ) return; if( !get_eq_char( ch, WEAR_ANKLE_L ) ) { if( !oprog_use_trigger( ch, obj, NULL, NULL ) ) { act( AT_ACTION, "$n fits $p around $s left ankle.", ch, obj, NULL, TO_ROOM ); act( AT_ACTION, "You fit $p around your left ankle.", ch, obj, NULL, TO_CHAR ); } equip_char( ch, obj, WEAR_ANKLE_L ); oprog_wear_trigger( ch, obj ); return; } if( !get_eq_char( ch, WEAR_ANKLE_R ) ) { if( !oprog_use_trigger( ch, obj, NULL, NULL ) ) { act( AT_ACTION, "$n fits $p around $s right ankle.", ch, obj, NULL, TO_ROOM ); act( AT_ACTION, "You fit $p around your right ankle.", ch, obj, NULL, TO_CHAR ); } equip_char( ch, obj, WEAR_ANKLE_R ); oprog_wear_trigger( ch, obj ); return; } bug( "Wear_obj: no free ankle.", 0 ); send_to_char( "You already wear two ankle items.\r\n", ch ); return; case ITEM_WEAR_SHIELD: if( get_eq_char( ch, WEAR_DUAL_WIELD ) || ( get_eq_char( ch, WEAR_WIELD ) && get_eq_char( ch, WEAR_MISSILE_WIELD ) ) || ( get_eq_char( ch, WEAR_WIELD ) && get_eq_char( ch, WEAR_HOLD ) ) ) { if( get_eq_char( ch, WEAR_HOLD ) ) send_to_char( "You can't use a shield while using a weapon and holding something!\r\n", ch ); else send_to_char( "You can't use a shield AND two weapons!\r\n", ch ); return; } if( !remove_obj( ch, WEAR_SHIELD, fReplace ) ) return; if( !oprog_use_trigger( ch, obj, NULL, NULL ) ) { act( AT_ACTION, "$n uses $p as a shield.", ch, obj, NULL, TO_ROOM ); act( AT_ACTION, "You use $p as a shield.", ch, obj, NULL, TO_CHAR ); } equip_char( ch, obj, WEAR_SHIELD ); oprog_wear_trigger( ch, obj ); return; case ITEM_MISSILE_WIELD: case ITEM_WIELD: case ITEM_DUAL_WIELD: if( !could_dual( ch ) ) { if( !remove_obj( ch, WEAR_MISSILE_WIELD, fReplace ) ) return; if( !remove_obj( ch, WEAR_WIELD, fReplace ) ) return; tmpobj = NULL; } else { OBJ_DATA *mw, *dw, *hd, *sd; tmpobj = get_eq_char( ch, WEAR_WIELD ); mw = get_eq_char( ch, WEAR_MISSILE_WIELD ); dw = get_eq_char( ch, WEAR_DUAL_WIELD ); hd = get_eq_char( ch, WEAR_HOLD ); sd = get_eq_char( ch, WEAR_SHIELD ); if( hd && sd ) { send_to_char( "You are already holding something and wearing a shield.\r\n", ch ); return; } if( tmpobj ) { if( !can_dual( ch ) ) return; if( get_obj_weight( obj ) + get_obj_weight( tmpobj ) > str_app[get_curr_str( ch )].wield ) { send_to_char( "It is too heavy for you to wield.\r\n", ch ); return; } if( mw || dw ) { send_to_char( "You're already wielding two weapons.\r\n", ch ); return; } if( hd || sd ) { send_to_char( "You're already wielding a weapon AND holding something.\r\n", ch ); return; } if( !oprog_use_trigger( ch, obj, NULL, NULL ) ) { act( AT_ACTION, "$n dual-wields $p.", ch, obj, NULL, TO_ROOM ); act( AT_ACTION, "You dual-wield $p.", ch, obj, NULL, TO_CHAR ); } if( 1 << bit == ITEM_MISSILE_WIELD ) equip_char( ch, obj, WEAR_MISSILE_WIELD ); else equip_char( ch, obj, WEAR_DUAL_WIELD ); oprog_wear_trigger( ch, obj ); return; } if( mw ) { if( !can_dual( ch ) ) return; if( 1 << bit == ITEM_MISSILE_WIELD ) { send_to_char( "You're already wielding a missile weapon.\r\n", ch ); return; } if( get_obj_weight( obj ) + get_obj_weight( mw ) > str_app[get_curr_str( ch )].wield ) { send_to_char( "It is too heavy for you to wield.\r\n", ch ); return; } if( tmpobj || dw ) { send_to_char( "You're already wielding two weapons.\r\n", ch ); return; } if( hd || sd ) { send_to_char( "You're already wielding a weapon AND holding something.\r\n", ch ); return; } if( !oprog_use_trigger( ch, obj, NULL, NULL ) ) { act( AT_ACTION, "$n wields $p.", ch, obj, NULL, TO_ROOM ); act( AT_ACTION, "You wield $p.", ch, obj, NULL, TO_CHAR ); } equip_char( ch, obj, WEAR_WIELD ); oprog_wear_trigger( ch, obj ); return; } } if( get_obj_weight( obj ) > str_app[get_curr_str( ch )].wield ) { send_to_char( "It is too heavy for you to wield.\r\n", ch ); return; } if( !oprog_use_trigger( ch, obj, NULL, NULL ) ) { act( AT_ACTION, "$n wields $p.", ch, obj, NULL, TO_ROOM ); act( AT_ACTION, "You wield $p.", ch, obj, NULL, TO_CHAR ); } if( 1 << bit == ITEM_MISSILE_WIELD ) equip_char( ch, obj, WEAR_MISSILE_WIELD ); else equip_char( ch, obj, WEAR_WIELD ); oprog_wear_trigger( ch, obj ); return; /* * Floating items added by Scion */ case ITEM_WEAR_FLOAT: if( get_eq_char( ch, WEAR_FLOAT ) ) { send_to_char( "You may only float one item at a time.\r\n", ch ); return; } if( !remove_obj( ch, WEAR_FLOAT, fReplace ) ) return; if( !oprog_use_trigger( ch, obj, NULL, NULL ) ) { act( AT_ACTION, "You release $p, which floats gently above your head.", ch, obj, NULL, TO_CHAR ); act( AT_ACTION, "$n releases $p, which floats gently above $s head.", ch, obj, NULL, TO_ROOM ); } equip_char( ch, obj, WEAR_FLOAT ); oprog_wear_trigger( ch, obj ); return; case ITEM_HOLD: if( get_eq_char( ch, WEAR_DUAL_WIELD ) || ( get_eq_char( ch, WEAR_WIELD ) && ( get_eq_char( ch, WEAR_MISSILE_WIELD ) || get_eq_char( ch, WEAR_SHIELD ) ) ) ) { if( get_eq_char( ch, WEAR_SHIELD ) ) send_to_char( "You cannot hold something while using a weapon and a shield!\r\n", ch ); else send_to_char( "You cannot hold something AND two weapons!\r\n", ch ); return; } if( !remove_obj( ch, WEAR_HOLD, fReplace ) ) return; if( obj->item_type == ITEM_WAND || obj->item_type == ITEM_STAFF || obj->item_type == ITEM_FOOD || obj->item_type == ITEM_COOK || obj->item_type == ITEM_PILL || obj->item_type == ITEM_POTION || obj->item_type == ITEM_SCROLL || obj->item_type == ITEM_DRINK_CON || obj->item_type == ITEM_BLOOD || obj->item_type == ITEM_PIPE || obj->item_type == ITEM_HERB || obj->item_type == ITEM_KEY || !oprog_use_trigger( ch, obj, NULL, NULL ) ) { act( AT_ACTION, "$n holds $p in $s hands.", ch, obj, NULL, TO_ROOM ); act( AT_ACTION, "You hold $p in your hands.", ch, obj, NULL, TO_CHAR ); } equip_char( ch, obj, WEAR_HOLD ); oprog_wear_trigger( ch, obj ); return; } } void do_wear( CHAR_DATA * ch, char *argument ) { char arg1[MAX_INPUT_LENGTH]; char arg2[MAX_INPUT_LENGTH]; OBJ_DATA *obj; short wear_bit; argument = one_argument( argument, arg1 ); argument = one_argument( argument, arg2 ); if( ( !str_cmp( arg2, "on" ) || !str_cmp( arg2, "upon" ) || !str_cmp( arg2, "around" ) ) && argument[0] != '\0' ) argument = one_argument( argument, arg2 ); if( arg1[0] == '\0' ) { send_to_char( "Wear, wield, or hold what?\r\n", ch ); return; } if( ms_find_obj( ch ) ) return; if( !str_cmp( arg1, "all" ) ) { OBJ_DATA *obj_next; for( obj = ch->first_carrying; obj; obj = obj_next ) { obj_next = obj->next_content; if( obj->wear_loc == WEAR_NONE && can_see_obj( ch, obj ) ) { wear_obj( ch, obj, FALSE, -1 ); if( char_died( ch ) ) return; } } return; } else { if( ( obj = get_obj_carry( ch, arg1 ) ) == NULL ) { send_to_char( "You do not have that item.\r\n", ch ); return; } if( arg2[0] != '\0' ) wear_bit = get_wflag( arg2 ); else wear_bit = -1; wear_obj( ch, obj, TRUE, wear_bit ); } return; } void do_remove( CHAR_DATA * ch, char *argument ) { char arg[MAX_INPUT_LENGTH]; OBJ_DATA *obj, *obj_next; one_argument( argument, arg ); if( arg[0] == '\0' ) { send_to_char( "Remove what?\r\n", ch ); return; } if( ms_find_obj( ch ) ) return; if( !str_cmp( arg, "all" ) ) /* SB Remove all */ { for( obj = ch->first_carrying; obj != NULL; obj = obj_next ) { obj_next = obj->next_content; if( obj->wear_loc != WEAR_NONE && can_see_obj( ch, obj ) ) remove_obj( ch, obj->wear_loc, TRUE ); } return; } if( ( obj = get_obj_wear( ch, arg ) ) == NULL ) { send_to_char( "You are not using that item.\r\n", ch ); return; } if( ( obj_next = get_eq_char( ch, obj->wear_loc ) ) != obj ) { act( AT_PLAIN, "You must remove $p first.", ch, obj_next, NULL, TO_CHAR ); return; } remove_obj( ch, obj->wear_loc, TRUE ); return; } void do_bury( CHAR_DATA * ch, char *argument ) { char arg[MAX_INPUT_LENGTH]; OBJ_DATA *obj; bool shovel; short move; one_argument( argument, arg ); if( arg[0] == '\0' ) { send_to_char( "What do you wish to bury?\r\n", ch ); return; } if( ms_find_obj( ch ) ) return; shovel = FALSE; for( obj = ch->first_carrying; obj; obj = obj->next_content ) if( obj->item_type == ITEM_SHOVEL ) { shovel = TRUE; break; } obj = get_obj_list_rev( ch, arg, ch->in_room->last_content ); if( !obj ) { send_to_char( "You can't find it.\r\n", ch ); return; } separate_obj( obj ); /* * if ( !CAN_WEAR(obj, ITEM_TAKE) ) * { * if ( !IS_OBJ_STAT( obj, ITEM_CLANCORPSE ) * || IS_NPC(ch) || !IS_SET( ch->pcdata->flags, PCFLAG_DEADLY ) ) * { * act( AT_PLAIN, "You cannot bury $p.", ch, obj, 0, TO_CHAR ); * return; * } * } */ switch ( ch->in_room->sector_type ) { case SECT_CITY: case SECT_INSIDE: send_to_char( "The floor is too hard to dig through.\r\n", ch ); return; case SECT_WATER_SWIM: case SECT_WATER_NOSWIM: case SECT_UNDERWATER: send_to_char( "You cannot bury something here.\r\n", ch ); return; case SECT_AIR: send_to_char( "What? In the air?!\r\n", ch ); return; } if( obj->weight > ( UMAX( 5, ( can_carry_w( ch ) / 10 ) ) ) && !shovel ) { send_to_char( "You'd need a shovel to bury something that big.\r\n", ch ); return; } move = ( obj->weight * 50 * ( shovel ? 1 : 5 ) ) / UMAX( 1, can_carry_w( ch ) ); move = URANGE( 2, move, 1000 ); if( move > ch->move ) { send_to_char( "You don't have the energy to bury something of that size.\r\n", ch ); return; } ch->move -= move; if( obj->item_type == ITEM_CORPSE_NPC || obj->item_type == ITEM_CORPSE_PC ) adjust_favor( ch, 6, 1 ); act( AT_ACTION, "You solemnly bury $p...", ch, obj, NULL, TO_CHAR ); act( AT_ACTION, "$n solemnly buries $p...", ch, obj, NULL, TO_ROOM ); xSET_BIT( obj->extra_flags, ITEM_BURIED ); WAIT_STATE( ch, URANGE( 10, move / 2, 100 ) ); return; } bool sac_obj( CHAR_DATA * ch, OBJ_DATA * obj ) { if( IS_SET( obj->magic_flags, ITEM_PKDISARMED ) ) { if( CAN_PKILL( ch ) && !get_timer( ch, TIMER_PKILLED ) ) { if( ch->level - obj->value[5] > 5 || obj->value[5] - ch->level > 5 ) { ch_printf( ch, "\r\n&bA godly force freezes your outstretched hand as you reach for %s.\r\n", obj->short_descr ); return FALSE; } } } if( IS_OBJ_STAT( obj, ITEM_CONTAINER ) ) { OBJ_DATA *tmpObj; // if( obj->first_content ) { ch_printf( ch, "The contents of %s spill out!\r\n", obj->short_descr ); for( tmpObj = obj->first_content; tmpObj; tmpObj = tmpObj->next ) { obj_from_obj( tmpObj ); obj_to_room( tmpObj, ch->in_room ); } } } ch->copper += 1; if( obj->item_type == ITEM_CORPSE_NPC || obj->item_type == ITEM_CORPSE_PC ) adjust_favor( ch, 5, 1 ); oprog_sac_trigger( ch, obj ); if( obj_extracted( obj ) ) return FALSE; if( cur_obj == obj->serial ) global_objcode = rOBJ_SACCED; separate_obj( obj ); extract_obj( obj ); save_house_by_vnum( ch->in_room->vnum ); /* Prevent House Object Duplication */ return TRUE; } void do_sacrifice( CHAR_DATA * ch, char *argument ) { char arg[MAX_INPUT_LENGTH]; char buf[MAX_STRING_LENGTH]; char name[50]; OBJ_DATA *obj, *obj_next; int count = 0; one_argument( argument, arg ); if( arg[0] == '\0' || !str_cmp( arg, ch->name ) ) { act( AT_ACTION, "$n offers $mself to $s deity, who graciously declines.", ch, NULL, NULL, TO_ROOM ); send_to_char( "Your deity appreciates your offer and may accept it later.\r\n", ch ); return; } if( ms_find_obj( ch ) ) return; if( !IS_NPC( ch ) && ch->pcdata->deity && ch->pcdata->deity->name[0] != '\0' ) strcpy( name, ch->pcdata->deity->name ); else if( !IS_NPC( ch ) && IS_GUILDED( ch ) && sysdata.guild_overseer[0] != '\0' ) strcpy( name, sysdata.guild_overseer ); else if( !IS_NPC( ch ) && ch->pcdata->clan && ch->pcdata->clan->deity[0] != '\0' ) strcpy( name, ch->pcdata->clan->deity ); else { static char *god_name_table[] = { "Badastaz", "Garinan", "Ender", "Dangel", "Doom", "Josh", "Recca", "Zyrrin", }; strcpy( name, god_name_table[number_range( 0, 3 )] ); } if( !str_cmp( arg, "all" ) ) { int amount; for( obj = ch->in_room->first_content; obj; obj = obj_next ) { obj_next = obj->next_content; if( !IS_SET( obj->wear_flags, ITEM_TAKE ) && obj->item_type != ITEM_CORPSE_NPC ) { act( AT_PLAIN, "$p is not an acceptable sacrifice.", ch, obj, 0, TO_CHAR ); continue; } amount = obj->count; if( sac_obj( ch, obj ) ) count += amount; } if( count > 0 ) { sprintf( buf, "(%d) %s gives you one copper coin for your sacrifice.\r\n", count, name ); send_to_char( buf, ch ); sprintf( buf, "$n sacrifices everything to %s.", name ); act( AT_ACTION, buf, ch, NULL, NULL, TO_ROOM ); } } else { obj = get_obj_list_rev( ch, arg, ch->in_room->last_content ); if( !obj ) { send_to_char( "You can't find it.\r\n", ch ); return; } separate_obj( obj ); /* * Allow saccing of any item that is able to be picked up -- Kratas * if ( obj->item_type != ITEM_CORPSE_NPC ) */ if( !IS_SET( obj->wear_flags, ITEM_TAKE ) && obj->item_type != ITEM_CORPSE_NPC ) { act( AT_PLAIN, "$p is not an acceptable sacrifice.", ch, obj, 0, TO_CHAR ); return; } if( sac_obj( ch, obj ) ) { sprintf( buf, "(%d) %s gives you one copper coin for your sacrifice.\r\n", count, name ); send_to_char( buf, ch ); sprintf( buf, "$n sacrifices $p to %s.", name ); act( AT_ACTION, buf, ch, obj, NULL, TO_ROOM ); } } return; } void do_brandish( CHAR_DATA * ch, char *argument ) { CHAR_DATA *vch; CHAR_DATA *vch_next; OBJ_DATA *staff; ch_ret retcode; int sn; if( ( staff = get_eq_char( ch, WEAR_HOLD ) ) == NULL ) { send_to_char( "You hold nothing in your hand.\r\n", ch ); return; } if( staff->item_type != ITEM_STAFF ) { send_to_char( "You can brandish only with a staff.\r\n", ch ); return; } if( ( sn = staff->value[3] ) < 0 || sn >= top_sn || skill_table[sn]->spell_fun == NULL ) { bug( "Do_brandish: bad sn %d on object vnum %d.", sn, staff->pIndexData->vnum ); return; } WAIT_STATE( ch, 2 * PULSE_VIOLENCE ); if( staff->value[2] > 0 ) { if( !oprog_use_trigger( ch, staff, NULL, NULL ) ) { act( AT_MAGIC, "$n brandishes $p.", ch, staff, NULL, TO_ROOM ); act( AT_MAGIC, "You brandish $p.", ch, staff, NULL, TO_CHAR ); } for( vch = ch->in_room->first_person; vch; vch = vch_next ) { vch_next = vch->next_in_room; if( !IS_NPC( vch ) && xIS_SET( vch->act, PLR_WIZINVIS ) && vch->pcdata->wizinvis >= LEVEL_IMMORTAL ) continue; else switch ( skill_table[sn]->target ) { default: bug( "Do_brandish: bad target for sn %d.", sn ); return; case TAR_IGNORE: if( vch != ch ) continue; break; case TAR_CHAR_OFFENSIVE: if( IS_NPC( ch ) ? IS_NPC( vch ) : !IS_NPC( vch ) ) continue; break; case TAR_CHAR_DEFENSIVE: if( IS_NPC( ch ) ? !IS_NPC( vch ) : IS_NPC( vch ) ) continue; break; case TAR_CHAR_SELF: if( vch != ch ) continue; break; } retcode = obj_cast_spell( staff->value[3], staff->value[0], ch, vch, NULL ); if( retcode == rCHAR_DIED || retcode == rBOTH_DIED ) { bug( "do_brandish: char died", 0 ); return; } } } if( --staff->value[2] <= 0 ) { act( AT_MAGIC, "$p blazes bright and vanishes from $n's hands!", ch, staff, NULL, TO_ROOM ); act( AT_MAGIC, "$p blazes bright and is gone!", ch, staff, NULL, TO_CHAR ); if( staff->serial == cur_obj ) global_objcode = rOBJ_USED; extract_obj( staff ); } return; } void do_zap( CHAR_DATA * ch, char *argument ) { char arg[MAX_INPUT_LENGTH]; CHAR_DATA *victim; OBJ_DATA *wand; OBJ_DATA *obj; ch_ret retcode; one_argument( argument, arg ); if( arg[0] == '\0' && !ch->fighting ) { send_to_char( "Zap whom or what?\r\n", ch ); return; } if( ( wand = get_eq_char( ch, WEAR_HOLD ) ) == NULL ) { send_to_char( "You hold nothing in your hand.\r\n", ch ); return; } if( wand->item_type != ITEM_WAND ) { send_to_char( "You can zap only with a wand.\r\n", ch ); return; } obj = NULL; if( arg[0] == '\0' ) { if( ch->fighting ) { victim = who_fighting( ch ); } else { send_to_char( "Zap whom or what?\r\n", ch ); return; } } else { if( ( victim = get_char_room( ch, arg ) ) == NULL && ( obj = get_obj_here( ch, arg ) ) == NULL ) { send_to_char( "You can't find it.\r\n", ch ); return; } } WAIT_STATE( ch, 1 * PULSE_VIOLENCE ); if( wand->value[2] > 0 ) { if( victim ) { if( !oprog_use_trigger( ch, wand, victim, NULL ) ) { act( AT_MAGIC, "$n aims $p at $N.", ch, wand, victim, TO_ROOM ); act( AT_MAGIC, "You aim $p at $N.", ch, wand, victim, TO_CHAR ); } } else { if( !oprog_use_trigger( ch, wand, NULL, obj ) ) { act( AT_MAGIC, "$n aims $p at $P.", ch, wand, obj, TO_ROOM ); act( AT_MAGIC, "You aim $p at $P.", ch, wand, obj, TO_CHAR ); } } retcode = obj_cast_spell( wand->value[3], wand->value[0], ch, victim, obj ); if( retcode == rCHAR_DIED || retcode == rBOTH_DIED ) { bug( "do_zap: char died", 0 ); return; } } if( --wand->value[2] <= 0 ) { act( AT_MAGIC, "$p explodes into fragments.", ch, wand, NULL, TO_ROOM ); act( AT_MAGIC, "$p explodes into fragments.", ch, wand, NULL, TO_CHAR ); if( wand->serial == cur_obj ) global_objcode = rOBJ_USED; extract_obj( wand ); } return; } /* * Save items in a clan storage room -Scryn & Thoric */ void save_clan_storeroom( CHAR_DATA * ch, CLAN_DATA * clan ) { FILE *fp; char filename[256]; short templvl; OBJ_DATA *contents; if( !clan ) { bug( "save_clan_storeroom: Null clan pointer!", 0 ); return; } if( !ch ) { bug( "save_clan_storeroom: Null ch pointer!", 0 ); return; } sprintf( filename, "%s%s.vault", CLAN_DIR, clan->filename ); if( ( fp = fopen( filename, "w" ) ) == NULL ) { bug( "save_clan_storeroom: fopen", 0 ); perror( filename ); } else { templvl = ch->level; ch->level = LEVEL_HERO; /* make sure EQ doesn't get lost */ contents = ch->in_room->last_content; if( contents ) fwrite_obj( ch, contents, fp, 0, OS_CARRY ); fprintf( fp, "#END\n" ); ch->level = templvl; fclose( fp ); return; } return; } /* put an item on auction, or see the stats on the current item or bet */ void do_auction( CHAR_DATA * ch, char *argument ) { OBJ_DATA *obj; char arg1[MAX_INPUT_LENGTH]; char arg2[MAX_INPUT_LENGTH]; char arg3[MAX_INPUT_LENGTH]; char buf[MAX_STRING_LENGTH]; int i; int gbid = 0; int sbid = 0; int cbid = 0; int tmpvalue = 0; argument = one_argument( argument, arg1 ); argument = one_argument( argument, arg2 ); argument = one_argument( argument, arg3 ); set_char_color( AT_LBLUE, ch ); if( IS_NPC( ch ) ) /* NPC can be extracted at any time and thus can't auction! */ return; if( ch->level < 3 ) { send_to_char( "You must be at least level three to use the auction...\r\n", ch ); return; } if( ( time_info.hour > 19 || time_info.hour < 7 ) && auction->item == NULL && !IS_IMMORTAL( ch ) ) { send_to_char( "\r\nThe auctioneer works between the hours of 7 AM and 7 PM\r\n", ch ); return; } if( arg1[0] == '\0' ) { if( auction->item != NULL ) { AFFECT_DATA *paf; obj = auction->item; tmpvalue = auction->bet; gbid = tmpvalue / 10000; tmpvalue = tmpvalue % 10000; sbid = tmpvalue / 100; tmpvalue = tmpvalue % 100; cbid = tmpvalue; /* * show item data here */ if( auction->bet > 0 ) { if( gbid <= 0 && sbid <= 0 && cbid > 0 ) sprintf( buf, "\r\nCurrent bid on this item is %d copper\r\n", cbid ); else if( gbid > 0 && sbid <= 0 && cbid > 0 ) sprintf( buf, "\r\nCurrent bid on this item is %d gold and %d copper\r\n", gbid, cbid ); else if( gbid > 0 && sbid > 0 && cbid > 0 ) sprintf( buf, "\r\nCurrent bid is %d gold, %d silver, and %d copper\r\n", gbid, sbid, cbid ); else if( gbid <= 0 && sbid > 0 && cbid > 0 ) sprintf( buf, "\r\nCurrent bid on this item is %d silver and %d copper\r\n", sbid, cbid ); else if( gbid > 0 && sbid <= 0 && cbid <= 0 ) sprintf( buf, "\r\nCurrent bid on this item is %d gold\r\n", gbid ); else if( gbid <= 0 && sbid > 0 && cbid <= 0 ) sprintf( buf, "\r\nCurrent bid on this item is %d silver\r\n", sbid ); else if( gbid > 0 && sbid > 0 && cbid <= 0 ) sprintf( buf, "\r\nCurrent bid on this item is %d gold and %d silver\r\n", gbid, sbid ); else sprintf( buf, "Error! report to Ddruid.\r\n" ); } else sprintf( buf, "\r\nNo bids on this item have been received.\r\n" ); set_char_color( AT_BLUE, ch ); send_to_char( buf, ch ); sprintf( buf, "Object '%s' is %s, special properties: %s\r\nIts weight is %d,\r\n", obj->name, aoran( item_type_name( obj ) ), extra_bit_name( &obj->extra_flags ), obj->weight ); set_char_color( AT_LBLUE, ch ); send_to_char( buf, ch ); sprintf( buf, "It value is: %d gold, %d silver, and %d copper\r\nLevel: %d\r\n", obj->gold_cost, obj->silver_cost, obj->copper_cost, obj->level ); set_char_color( AT_LBLUE, ch ); send_to_char( buf, ch ); if( obj->item_type != ITEM_LIGHT && obj->wear_flags - 1 > 0 ) ch_printf( ch, "Item's wear location: %s\r\n", flag_string( obj->wear_flags - 1, w_flags ) ); set_char_color( AT_BLUE, ch ); switch ( obj->item_type ) { case ITEM_CONTAINER: case ITEM_KEYRING: case ITEM_QUIVER: ch_printf( ch, "%s appears to %s.\r\n", capitalize( obj->short_descr ), obj->value[0] < 76 ? "have a small capacity" : obj->value[0] < 150 ? "have a small to medium capacity" : obj->value[0] < 300 ? "have a medium capacity" : obj->value[0] < 500 ? "have a medium to large capacity" : obj->value[0] < 751 ? "have a large capacity" : "have a giant capacity" ); break; case ITEM_PILL: case ITEM_SCROLL: case ITEM_POTION: sprintf( buf, "Level %d spells of:", obj->value[0] ); send_to_char( buf, ch ); if( obj->value[1] >= 0 && obj->value[1] < top_sn ) { send_to_char( " '", ch ); send_to_char( skill_table[obj->value[1]]->name, ch ); send_to_char( "'", ch ); } if( obj->value[2] >= 0 && obj->value[2] < top_sn ) { send_to_char( " '", ch ); send_to_char( skill_table[obj->value[2]]->name, ch ); send_to_char( "'", ch ); } if( obj->value[3] >= 0 && obj->value[3] < top_sn ) { send_to_char( " '", ch ); send_to_char( skill_table[obj->value[3]]->name, ch ); send_to_char( "'", ch ); } send_to_char( ".\r\n", ch ); break; case ITEM_WAND: case ITEM_STAFF: sprintf( buf, "Has %d(%d) charges of level %d", obj->value[1], obj->value[2], obj->value[0] ); send_to_char( buf, ch ); if( obj->value[3] >= 0 && obj->value[3] < top_sn ) { send_to_char( " '", ch ); send_to_char( skill_table[obj->value[3]]->name, ch ); send_to_char( "'", ch ); } send_to_char( ".\r\n", ch ); break; case ITEM_MISSILE_WEAPON: case ITEM_WEAPON: sprintf( buf, "Damage is %d to %d (average %d).%s\r\n", obj->value[1], obj->value[2], ( obj->value[1] + obj->value[2] ) / 2, IS_OBJ_STAT( obj, ITEM_POISONED ) ? "\r\nThis weapon is poisoned." : "" ); send_to_char( buf, ch ); break; case ITEM_ARMOR: sprintf( buf, "Armor class is %d.\r\n", obj->value[0] ); send_to_char( buf, ch ); break; } for( paf = obj->pIndexData->first_affect; paf; paf = paf->next ) showaffect( ch, paf ); for( paf = obj->first_affect; paf; paf = paf->next ) showaffect( ch, paf ); if( ( obj->item_type == ITEM_CONTAINER || obj->item_type == ITEM_KEYRING || obj->item_type == ITEM_QUIVER ) && obj->first_content ) { set_char_color( AT_OBJECT, ch ); send_to_char( "Contents:\r\n", ch ); show_list_to_char( obj->first_content, ch, TRUE, FALSE ); } if( IS_IMMORTAL( ch ) ) { sprintf( buf, "Seller: %s. Bidder: %s. Round: %d.\r\n", auction->seller->name, auction->buyer->name, ( auction->going + 1 ) ); send_to_char( buf, ch ); sprintf( buf, "Time left in round: %d.\r\n", auction->pulse ); send_to_char( buf, ch ); } return; } else { set_char_color( AT_LBLUE, ch ); send_to_char( "\r\nThere is nothing being auctioned right now. What would you like to auction?\r\n", ch ); return; } } if( IS_IMMORTAL( ch ) && !str_cmp( arg1, "stop" ) ) { if( auction->item == NULL ) { send_to_char( "There is no auction to stop.\r\n", ch ); return; } else /* stop the auction */ { gbid = 0; sbid = 0; cbid = 0; tmpvalue = 0; tmpvalue = auction->bet; gbid = tmpvalue / 10000; tmpvalue = tmpvalue % 10000; sbid = tmpvalue / 100; tmpvalue = tmpvalue % 100; cbid = tmpvalue; set_char_color( AT_LBLUE, ch ); sprintf( buf, "Sale of %s has been stopped by an Immortal.", auction->item->short_descr ); talk_auction( buf ); obj_to_char( auction->item, auction->seller ); ch_printf_color( auction->seller, "&C%s is returned to you\r\n", auction->item->short_descr ); if( IS_SET( sysdata.save_flags, SV_AUCTION ) ) save_char_obj( auction->seller ); auction->item = NULL; if( auction->buyer != NULL && auction->buyer != auction->seller ) /* return money to the buyer */ { auction->buyer->gold += gbid; auction->buyer->silver += sbid; auction->buyer->copper += cbid; send_to_char( "Your money has been returned.\r\n", auction->buyer ); } return; } } if( !str_cmp( arg1, "bid" ) ) { if( auction->item != NULL ) { int newbet; int chwealth; tmpvalue = auction->bet; gbid = tmpvalue / 10000; tmpvalue = tmpvalue % 10000; sbid = tmpvalue / 100; tmpvalue = tmpvalue % 100; cbid = tmpvalue; if( ch->level < auction->item->level ) { send_to_char( "This object's level is too high for your use.\r\n", ch ); return; } if( ch == auction->seller ) { send_to_char( "You can't bid on your own item!\r\n", ch ); return; } /* * make - perhaps - a bet now */ if( arg2[0] == '\0' ) { send_to_char( "Bid how much?\r\n", ch ); return; } newbet = parsebet( auction->bet, arg2 ); /* ch_printf( ch, "Bid: %d\r\n",newbet); */ if( newbet < auction->starting ) { send_to_char( "You must place a bid that is higher than the starting bet.\r\n", ch ); return; } /* * to avoid slow auction, use a bigger amount than 100 if the bet * is higher up - changed to 10000 for our high economy */ if( newbet < ( auction->bet + 100 ) ) { send_to_char( "You must at least bid 1 silver coin over the current bid.\r\n", ch ); return; } chwealth = get_value( ch->gold, ch->silver, ch->copper ); if( newbet > chwealth ) { send_to_char( "You don't have that much money!\r\n", ch ); return; } if( newbet > 2000000000 ) { send_to_char( "You can't bid over 2 billion coins.\r\n", ch ); return; } /* * Is it the item they really want to bid on? --Shaddai */ if( arg3[0] != '\0' && !nifty_is_name( arg3, auction->item->name ) ) { send_to_char( "That item is not being auctioned right now.\r\n", ch ); return; } /* * the actual bet is OK! */ /* * return the coins to the last buyer, if one exists */ if( auction->buyer != NULL && auction->buyer != auction->seller ) { send_to_char( "The auctioneer returns your money.\r\n", auction->buyer ); auction->buyer->gold += gbid; auction->buyer->silver += sbid; auction->buyer->copper += cbid; } tmpvalue = newbet; gbid = tmpvalue / 10000; tmpvalue = tmpvalue % 10000; sbid = tmpvalue / 100; tmpvalue = tmpvalue % 100; cbid = tmpvalue; act( AT_ACTION, "The auctioneer appears before $n, demanding some money.", ch, NULL, NULL, TO_ROOM ); act( AT_ACTION, "The auctioneer appears before you demanding your bidded money.", ch, NULL, NULL, TO_CHAR ); if( ch->gold < gbid || ch->silver < sbid || ch->copper < cbid ) { send_to_char( "You give your money to the auctioneer who quickly makes change\r\n", ch ); chwealth -= newbet; conv_currency( ch, chwealth ); } else { send_to_char( "You give your money to the auctioneer.\r\n", ch ); ch->gold -= gbid; ch->silver -= sbid; ch->copper -= cbid; } if( IS_SET( sysdata.save_flags, SV_AUCTION ) ) save_char_obj( ch ); auction->buyer = ch; auction->bet = newbet; auction->going = 0; auction->pulse = PULSE_AUCTION; /* start the auction over again */ if( gbid > 0 && sbid > 0 && cbid > 0 ) sprintf( buf, "A bid of %d gold, %d silver, and %d copper has been received on %s.\r\n", gbid, sbid, cbid, auction->item->short_descr ); else if( gbid > 0 && sbid > 0 && cbid <= 0 ) sprintf( buf, "A bid of %d gold and %d silver has been received on %s.\r\n", gbid, sbid, auction->item->short_descr ); else if( gbid > 0 && sbid <= 0 && cbid <= 0 ) sprintf( buf, "A bid of %d gold has been received on %s.\r\n", gbid, auction->item->short_descr ); else if( gbid <= 0 && sbid > 0 && cbid <= 0 ) sprintf( buf, "A bid of %d silver has been received on %s.\r\n", sbid, auction->item->short_descr ); else if( gbid <= 0 && sbid <= 0 && cbid > 0 ) sprintf( buf, "A bid of %d copper has been received on %s.\r\n", cbid, auction->item->short_descr ); else if( gbid > 0 && sbid <= 0 && cbid > 0 ) sprintf( buf, "A bid of %d gold and %d copper has been received on %s.\r\n", gbid, cbid, auction->item->short_descr ); else if( gbid <= 0 && sbid > 0 && cbid > 0 ) sprintf( buf, "A bid of %d silver and %d copper has been received on %s.\r\n", sbid, cbid, auction->item->short_descr ); else sprintf( buf, "Error! report to Ddruid\r\n" ); talk_auction( buf ); return; } else { send_to_char( "There isn't anything being auctioned right now.\r\n", ch ); return; } } /* finally... */ if( ms_find_obj( ch ) ) return; obj = get_obj_carry( ch, arg1 ); /* does char have the item ? */ if( obj == NULL ) { send_to_char( "You aren't carrying that.\r\n", ch ); return; } if( obj->timer > 0 ) { send_to_char( "You can't auction objects that are decaying.\r\n", ch ); return; } /* * prevent repeat auction items */ for( i = 0; i < AUCTION_MEM && auction->history[i]; i++ ) { if( auction->history[i] == obj->pIndexData ) { send_to_char( "Such an item has been auctioned " "recently, try again later.\r\n", ch ); return; } } if( arg2[0] == '\0' ) { auction->starting = 0; strcpy( arg2, "0" ); } /* * if ( !is_number(arg2) ) * { * send_to_char("You must input a number at which to start the auction.\r\n", ch); * return; * } * * if ( atoi(arg2) < 0 ) * { * send_to_char("You can't auction something for less than 0 gold!\r\n", ch); * return; * } */ if( auction->item == NULL ) switch ( obj->item_type ) { default: act( AT_TELL, "You cannot auction $Ts.", ch, NULL, item_type_name( obj ), TO_CHAR ); return; /* insert any more item types here... items with a timer MAY NOT BE AUCTIONED! */ case ITEM_LIGHT: case ITEM_TREASURE: case ITEM_POTION: case ITEM_CONTAINER: case ITEM_KEYRING: case ITEM_QUIVER: case ITEM_DRINK_CON: case ITEM_FOOD: case ITEM_COOK: case ITEM_PEN: case ITEM_BOAT: case ITEM_PILL: case ITEM_PIPE: case ITEM_HERB_CON: case ITEM_INCENSE: case ITEM_FIRE: case ITEM_RUNEPOUCH: case ITEM_MAP: case ITEM_BOOK: case ITEM_RUNE: case ITEM_MATCH: case ITEM_HERB: case ITEM_WEAPON: case ITEM_MISSILE_WEAPON: case ITEM_ARMOR: case ITEM_STAFF: case ITEM_WAND: case ITEM_SCROLL: separate_obj( obj ); obj_from_char( obj ); if( IS_SET( sysdata.save_flags, SV_AUCTION ) ) save_char_obj( ch ); auction->item = obj; auction->bet = 0; auction->buyer = ch; auction->seller = ch; auction->pulse = PULSE_AUCTION; auction->going = 0; if( arg2[0] != '\0' ) auction->starting = advatoi( arg2 ); else auction->starting = 0; /* * add the new item to the history */ if( AUCTION_MEM > 0 ) { memmove( ( char * )auction->history + sizeof( OBJ_INDEX_DATA * ), auction->history, ( AUCTION_MEM - 1 ) * sizeof( OBJ_INDEX_DATA * ) ); auction->history[0] = obj->pIndexData; } /* * reset the history timer */ auction->hist_timer = 0; if( auction->starting > 0 ) auction->bet = auction->starting; tmpvalue = auction->starting; gbid = tmpvalue / 10000; tmpvalue = tmpvalue % 10000; sbid = tmpvalue / 100; tmpvalue = tmpvalue % 100; cbid = tmpvalue; if( auction->starting == 0 ) sprintf( buf, "A new item is being auctioned: %s at 0 coins.", obj->short_descr ); else if( gbid > 0 && sbid > 0 && cbid > 0 ) sprintf( buf, "A new item is being auctioned: %s at %d gold, %d silver, and %d copper.", obj->short_descr, gbid, sbid, cbid ); else if( gbid > 0 && sbid > 0 && cbid <= 0 ) sprintf( buf, "A new item is being auctioned: %s at %d gold and %d silver.", obj->short_descr, gbid, sbid ); else if( gbid > 0 && sbid <= 0 && cbid <= 0 ) sprintf( buf, "A new item is being auctioned: %s at %d gold.", obj->short_descr, gbid ); else if( gbid <= 0 && sbid > 0 && cbid <= 0 ) sprintf( buf, "A new item is being auctioned: %s at %d silver.", obj->short_descr, sbid ); else if( gbid <= 0 && sbid <= 0 && cbid > 0 ) sprintf( buf, "A new item is being auctioned: %s at %d copper.", obj->short_descr, cbid ); else if( gbid > 0 && sbid <= 0 && cbid > 0 ) sprintf( buf, "A new item is being auctioned: %s at %d gold and %d copper.", obj->short_descr, gbid, cbid ); else if( gbid > 0 && sbid > 0 && cbid > 0 ) sprintf( buf, "A new item is being auctioned: %s at %d silver and %d copper", obj->short_descr, sbid, cbid ); else sprintf( buf, "Error! report to Ddruid.\r\n" ); talk_auction( buf ); return; } /* switch */ else { act( AT_TELL, "Try again later - $p is being auctioned right now!", ch, auction->item, NULL, TO_CHAR ); if( !IS_IMMORTAL( ch ) ) WAIT_STATE( ch, PULSE_VIOLENCE ); return; } } /* Make objects in rooms that are nofloor fall - Scryn 1/23/96 */ void obj_fall( OBJ_DATA * obj, bool through ) { EXIT_DATA *pexit; ROOM_INDEX_DATA *to_room; static int fall_count; char buf[MAX_STRING_LENGTH]; static bool is_falling; /* Stop loops from the call to obj_to_room() -- Altrag */ if( !obj->in_room || is_falling ) return; if( fall_count > 30 ) { bug( "object falling in loop more than 30 times", 0 ); extract_obj( obj ); fall_count = 0; return; } if( IS_SET( obj->in_room->room_flags, ROOM_NOFLOOR ) && CAN_GO( obj, DIR_DOWN ) && !IS_OBJ_STAT( obj, ITEM_MAGIC ) ) { pexit = get_exit( obj->in_room, DIR_DOWN ); to_room = pexit->to_room; if( through ) fall_count++; else fall_count = 0; if( obj->in_room == to_room ) { sprintf( buf, "Object falling into same room, room %d", to_room->vnum ); bug( buf, 0 ); extract_obj( obj ); return; } if( obj->in_room->first_person ) { act( AT_PLAIN, "$p falls far below...", obj->in_room->first_person, obj, NULL, TO_ROOM ); act( AT_PLAIN, "$p falls far below...", obj->in_room->first_person, obj, NULL, TO_CHAR ); } obj_from_room( obj ); is_falling = TRUE; obj = obj_to_room( obj, to_room ); is_falling = FALSE; if( obj->in_room->first_person ) { act( AT_PLAIN, "$p falls from above...", obj->in_room->first_person, obj, NULL, TO_ROOM ); act( AT_PLAIN, "$p falls from above...", obj->in_room->first_person, obj, NULL, TO_CHAR ); } if( !IS_SET( obj->in_room->room_flags, ROOM_NOFLOOR ) && through ) { /* int dam = (int)9.81*sqrt(fall_count*2/9.81)*obj->weight/2; */ int dam = fall_count * obj->weight / 2; /* * Damage players */ if( obj->in_room->first_person && number_percent( ) > 15 ) { CHAR_DATA *rch; CHAR_DATA *vch = NULL; int chcnt = 0; for( rch = obj->in_room->first_person; rch; rch = rch->next_in_room, chcnt++ ) if( number_range( 0, chcnt ) == 0 ) vch = rch; act( AT_WHITE, "$p falls on $n!", vch, obj, NULL, TO_ROOM ); act( AT_WHITE, "$p falls on you!", vch, obj, NULL, TO_CHAR ); damage( vch, vch, dam * vch->level, TYPE_UNDEFINED ); } /* * Damage objects */ switch ( obj->item_type ) { case ITEM_WEAPON: case ITEM_ARMOR: if( ( obj->value[0] - dam ) <= 0 ) { if( obj->in_room->first_person ) { act( AT_PLAIN, "$p is destroyed by the fall!", obj->in_room->first_person, obj, NULL, TO_ROOM ); act( AT_PLAIN, "$p is destroyed by the fall!", obj->in_room->first_person, obj, NULL, TO_CHAR ); } make_scraps( obj ); } else obj->value[0] -= dam; break; default: if( ( dam * 15 ) > get_obj_resistance( obj ) ) { if( obj->in_room->first_person ) { act( AT_PLAIN, "$p is destroyed by the fall!", obj->in_room->first_person, obj, NULL, TO_ROOM ); act( AT_PLAIN, "$p is destroyed by the fall!", obj->in_room->first_person, obj, NULL, TO_CHAR ); } make_scraps( obj ); } break; } } obj_fall( obj, TRUE ); } return; } /* Scryn, by request of Darkur, 12/04/98 */ /* Reworked recursive_note_find to fix crash bug when the note was left * blank. 7/6/98 -- Shaddai */ void do_findnote( CHAR_DATA * ch, char *argument ) { OBJ_DATA *obj; if( IS_NPC( ch ) ) { no_find( ch ); return; } if( argument[0] == '\0' ) { send_to_char( "You must specify at least one keyword.\r\n", ch ); return; } obj = recursive_note_find( ch->first_carrying, argument ); if( obj ) { if( obj->in_obj ) { obj_from_obj( obj ); obj = obj_to_char( obj, ch ); } wear_obj( ch, obj, TRUE, -1 ); } else send_to_char( "Note not found.\r\n", ch ); return; } OBJ_DATA *recursive_note_find( OBJ_DATA * obj, char *argument ) { OBJ_DATA *returned_obj; bool match = TRUE; char *argcopy; char *subject; char arg[MAX_INPUT_LENGTH]; char subj[MAX_STRING_LENGTH]; if( !obj ) return NULL; switch ( obj->item_type ) { case ITEM_PAPER: if( ( subject = get_extra_descr( "_subject_", obj->first_extradesc ) ) == NULL ) break; sprintf( subj, "%s", strlower( subject ) ); subject = strlower( subj ); argcopy = argument; while( match ) { argcopy = one_argument( argcopy, arg ); if( arg[0] == '\0' ) break; if( !strstr( subject, arg ) ) match = FALSE; } if( match ) return obj; break; case ITEM_CONTAINER: case ITEM_CORPSE_NPC: case ITEM_CORPSE_PC: if( obj->first_content ) { returned_obj = recursive_note_find( obj->first_content, argument ); if( returned_obj ) return returned_obj; } break; default: break; } return recursive_note_find( obj->next_content, argument ); } /* * Donate an object, by Tagith. Proposed by Ntanel */ void do_donate( CHAR_DATA * ch, char *argument ) { OBJ_DATA *obj; ROOM_INDEX_DATA *donation; if( ( obj = get_obj_carry( ch, argument ) ) == NULL ) { send_to_char( "You do not have that item.\r\n", ch ); return; } if( ( donation = get_room_index( ROOM_VNUM_DONATE ) ) == NULL ) { bug( "Donation room %d is non-existant!", ROOM_VNUM_DONATE ); return; } if( IS_OBJ_STAT( obj, ITEM_ARTIFACT ) ) { send_to_char( "You cannot bear to part with such a powerful artifact!\r\n", ch ); return; } separate_obj( obj ); obj_from_char( obj ); obj = obj_to_room( obj, donation ); act( AT_MAGIC, "You donate $p.", ch, obj, NULL, TO_CHAR ); /* * objects copying, commented save routine out... * if ( IS_SET( ch->in_room->room_flags, ROOM_CLANSTOREROOM ) ) * { * CLAN_DATA *clan; * * for ( clan = first_clan; clan; clan = clan->next ) * if ( clan->storeroom == ch->in_room->vnum ) * save_clan_storeroom(ch, clan); * } */ if( IS_SET( sysdata.save_flags, SV_DROP ) ) save_char_obj( ch ); return; } /* * Junk command installed by Samson 1-13-98 * Code courtesy of Stu, from the mailing list. Allows player to destroy * an item in their inventory */ void do_junk( CHAR_DATA * ch, char *argument ) { OBJ_DATA *obj, *obj_next; char arg[MAX_INPUT_LENGTH]; char *chk; bool found = FALSE; argument = one_argument( argument, arg ); if( arg[0] == '\0' ) { send_to_char( "Junk what?\r\n", ch ); return; } chk = arg; found = FALSE; for( obj = ch->first_carrying; obj; obj = obj_next ) { obj_next = obj->next_content; if( ( nifty_is_name( chk, obj->name ) ) && can_see_obj( ch, obj ) && obj->wear_loc == WEAR_NONE ) { found = TRUE; break; } } if( found == TRUE ) { if( !can_drop_obj( ch, obj ) && ch->level < LEVEL_IMMORTAL ) { send_to_char( "You cannot junk that, it's cursed!\r\n", ch ); return; } separate_obj( obj ); obj_from_char( obj ); extract_obj( obj ); act( AT_ACTION, "$n junks $p.", ch, obj, NULL, TO_ROOM ); act( AT_ACTION, "You junk $p.", ch, obj, NULL, TO_CHAR ); } return; } /* Connect pieces of an ITEM -- Originally from ACK! * * Modified for Smaug by Zarius 5/19/2000 */ void do_connect( CHAR_DATA * ch, char *argument ) { OBJ_DATA *first_ob; OBJ_DATA *second_ob; OBJ_DATA *new_ob; char arg1[MAX_STRING_LENGTH], arg2[MAX_STRING_LENGTH]; char buf[MAX_STRING_LENGTH]; argument = one_argument( argument, arg1 ); argument = one_argument( argument, arg2 ); if( arg1[0] == '\0' || arg2[0] == '\0' ) { send_to_char( "Syntax: Connect <firstobj> <secondobj>.\r\n", ch ); return; } if( ( first_ob = get_obj_carry( ch, arg1 ) ) == NULL ) { sprintf( buf, "You must be holding both parts!!\r\n" ); send_to_char( buf, ch ); return; } if( ( second_ob = get_obj_carry( ch, arg2 ) ) == NULL ) { sprintf( buf, "You must be holding both parts!!\r\n" ); send_to_char( buf, ch ); return; } if( first_ob->item_type != ITEM_PIECE || second_ob->item_type != ITEM_PIECE ) { send_to_char( "Both items must be pieces of another item!\r\n", ch ); return; } /* * check to see if the pieces connect */ if( ( first_ob->value[0] == second_ob->pIndexData->vnum ) || ( first_ob->value[1] == second_ob->pIndexData->vnum ) ) /* * good connection */ { new_ob = create_object( get_obj_index( first_ob->value[2] ), ch->level ); extract_obj( first_ob ); extract_obj( second_ob ); obj_to_char( new_ob, ch ); act( AT_ACTION, "$n jiggles some pieces together...\r\n ...suddenly they snap in place, creating $p!", ch, new_ob, NULL, TO_ROOM ); act( AT_ACTION, "You jiggle the pieces together...\r\n ...suddenly they snap into place, creating $p!", ch, new_ob, NULL, TO_CHAR ); } else { act( AT_ACTION, "$n jiggles some pieces together, but can't seem to make them connect.", ch, NULL, NULL, TO_ROOM ); act( AT_ACTION, "You try to fit them together every which way, but they just don't want to fit together.", ch, NULL, NULL, TO_CHAR ); return; } return; } int find_rand_room( int vnum ) { OBJ_DATA *obj; ROOM_INDEX_DATA *room = NULL; int count = 0; int i; /* * You'll have to replace sysdata.maxvnum with a hard coded number if you use * Stock Smaug 1.4 - Zarius */ for( i = 300; i <= 66000; i++ ) { if( get_room_index( i ) != NULL ) count++; } for( i = 300; i <= 66000; i++ ) { if( ( room = get_room_index( i ) ) != NULL && number_range( 1, count * 2 ) == 1 ) break; room = NULL; } if( room ) { obj = create_object( get_obj_index( vnum ), 0 ); if( !obj ) return 0; obj_to_room( obj, room ); } else return ( find_rand_room( vnum ) ); return room->vnum; } void do_roload( CHAR_DATA * ch, char *argument ) { char buf[MSL]; int i, wh; char arg1[MAX_STRING_LENGTH]; do_info( ch, "The gods have loaded a special item for you to find." ); argument = one_argument( argument, arg1 ); if( arg1[0] == '\0' ) { send_to_char( "Syntax: roload <vnum>.\r\n", ch ); return; } i = atoi( arg1 ); if( !get_obj_index( i ) ) { send_to_char( "That object doesn't exist!\r\n", ch ); return; } wh = find_rand_room( i ); sprintf( buf, "%s was loaded into the mud at vnum %d\r\n", get_obj_index( i )->short_descr, wh ); send_to_char( buf, ch ); return; }