/src/economy.c
C | 432 lines | 321 code | 58 blank | 53 comment | 48 complexity | 0038733b255c720f4d6e4f5d19082d22 MD5 | raw file
- /*
- * The Mythran Mud Economy Snippet Version 2 (used to be banking.c)
- *
- * Copyrights and rules for using the economy system:
- *
- * The Mythran Mud Economy system was written by The Maniac, it was
- * loosly based on the rather simple 'Ack!'s banking system'
- *
- * If you use this code you must follow these rules.
- * -Keep all the credits in the code.
- * -Mail Maniac (v942346@si.hhs.nl) to say you use the code
- * -Send a bug report, if you find 'it'
- * -Credit me somewhere in your mud.
- * -Follow the envy/merc/diku license
- * -If you want to: send me some of your code
- *
- * All my snippets can be found on http://www.hhs.nl/~v942346/snippets.html
- * Check it often because it's growing rapidly -- Maniac --
- */
- /*$Id: economy.c,v 1.3 2005/02/22 23:55:16 ahsile Exp $*/
- #if defined( macintosh )
- #include <types.h>
- #else
- #include <sys/types.h>
- #endif
- #include <ctype.h>
- #include <stdio.h>
- #include <stdlib.h>
- #include <string.h>
- #include <time.h>
- #include "merc.h"
- int share_value = SHARE_VALUE; /* External share_value by Maniac */
- /*
- * External functions.
- */
- void show_list_to_char( OBJ_DATA *list, CHAR_DATA *ch, bool fShort,
- bool fShowNothing );
- int obj_invcount args( ( OBJ_DATA* obj, bool one_item ) );
- void do_bank( CHAR_DATA *ch, char *argument )
- {
- /* The Mythran mud economy system (bank and trading)
- *
- * based on:
- * Simple banking system. by -- Stephen --
- *
- * The following changes and additions where
- * made by the Maniac from Mythran Mud
- * (v942346@si.hhs.nl)
- *
- * History:
- * 18/05/96: Added the transfer option, enables chars to transfer
- * money from their account to other players' accounts
- * 18/05/96: Big bug detected, can deposit/withdraw/transfer
- * negative amounts (nice way to steal is
- * bank transfer -(lots of dogh) <some rich player>
- * Fixed it (thought this was better... -= Maniac =-)
- * 21/06/96: Fixed a bug in transfer (transfer to MOBS)
- * Moved balance from ch->balance to ch->pcdata->balance
- * 21/06/96: Started on the invest option, so players can invest
- * money in shares, using buy, sell and check
- * Finished version 1.0 releasing it monday 24/06/96
- * 24/06/96: Mythran Mud Economy System V1.0 released by Maniac
- *
- */
-
- CHAR_DATA *mob;
- char buf[MAX_STRING_LENGTH];
- char arg1[MAX_INPUT_LENGTH];
- char arg2[MAX_INPUT_LENGTH];
- if ( IS_NPC( ch ) )
- {
- send_to_char(AT_WHITE, "Banking Services are only available to players!\n\r", ch );
- return;
- }
-
- /* Check for mob with act->banker */
- for ( mob = ch->in_room->people; mob; mob = mob->next_in_room )
- {
- if ( IS_NPC(mob) && IS_SET(mob->act, ACT_BANKER ) )
- break;
- }
-
- if ( mob == NULL )
- {
- send_to_char(AT_WHITE, "You can't do that here.\n\r", ch );
- return;
- }
- if ( argument[0] == '\0' )
- {
- send_to_char(AT_WHITE, "Bank Options:\n\r\n\r", ch );
- send_to_char(AT_WHITE, "Bank balance: Displays your balance.\n\r", ch );
- send_to_char(AT_WHITE, "Bank deposit <amount>: Deposit gold into your account.\n\r", ch );
- send_to_char(AT_WHITE, "Bank withdraw <amount>: Withdraw gold from your account.\n\r", ch );
- send_to_char(AT_WHITE, "Bank retrieve <item>: Retrieve a stored item from the bank.\n\r", ch );
- send_to_char(AT_WHITE, "Bank store <item>: Store an item in the bank.\n\r", ch );
- #if defined BANK_TRANSFER
- send_to_char(AT_WHITE, "Bank transfer <amount> <player>: Transfer <amount> gold to <player> account.\n\r", ch);
- #endif
- #if defined BANK_INVEST
- send_to_char(AT_WHITE, "Bank check: check the current shares price.\n\r", ch );
- send_to_char(AT_WHITE, "Bank buy <amount>: Buy <amount> shares.\n\r", ch );
- send_to_char(AT_WHITE, "Bank sell <amount>: Sell <amount> shares.\n\r", ch );
- #endif
- return;
- }
- argument = one_argument( argument, arg1 );
- argument = one_argument( argument, arg2 );
-
- /* Now work out what to do... */
- if ( !str_prefix( arg1, "balance" ) )
- {
- sprintf(buf,"Your current balance is: %d GP.", ch->pcdata->bankaccount );
- send_to_char(AT_WHITE, buf, ch);
- return;
- }
- if ( !str_prefix( arg1, "deposit" ) )
- {
- int amount;
- if ( is_number ( arg2 ) )
- {
- amount = atoi( arg2 );
- if (amount > ch->gold )
- {
- sprintf( buf, "How can you deposit %d GP when you only have %d?", amount, ch->gold );
- do_say(mob, buf );
- return;
- }
- if (amount < 0 )
- {
- do_say (mob, "Only positive amounts allowed...");
- return;
- }
- ch->gold -= amount;
- ch->pcdata->bankaccount += amount;
- sprintf ( buf, "You deposit %d GP. Your new balance is %d GP.\n\r",
- amount, ch->pcdata->bankaccount );
- send_to_char(AT_WHITE, buf, ch );
- do_save( ch, "" );
- return;
- }
- }
- /* We only allow transfers if this is true... so define it... */
- #if defined BANK_TRANSFER
- if ( !str_prefix( arg1, "transfer" ) )
- {
- int amount;
- CHAR_DATA *victim;
- if ( is_number ( arg2 ) )
- {
- amount = atoi( arg2 );
- if ( amount > ch->pcdata->bankaccount )
- {
- sprintf( buf, "How can you transfer %d GP when your balance is %d?",
- amount, ch->pcdata->bankaccount );
- send_to_char(AT_WHITE, buf, ch);
- return;
- }
- if (amount < 0 )
- {
- send_to_char(AT_WHITE, "Only positive amounts allowed...", ch);
- return;
- }
- if ( !( victim = get_char_world( ch, argument ) ) )
- {
- sprintf (buf, "%s doesn't have a bank account.", argument );
- send_to_char(AT_WHITE, buf, ch);
- return;
- }
- if (IS_NPC(victim))
- {
- send_to_char(AT_WHITE, "You can only transfer money to players.", ch);
- return;
- }
- ch->pcdata->bankaccount -= amount;
- victim->pcdata->bankaccount += amount;
- sprintf( buf, "You transfer %d GP. Your new balance is %d GP.\n\r",
- amount, ch->pcdata->bankaccount );
- send_to_char(AT_WHITE, buf, ch );
- sprintf (buf, "[BANK] %s has transferred %d gold's to your account.\n\r", ch->name, amount);
- send_to_char(AT_WHITE, buf, victim );
- do_save( ch, "" );
- do_save( victim, "");
- return;
- }
- }
- #endif
- if ( !str_prefix( arg1, "withdraw" ) )
- {
- int amount;
- if ( is_number ( arg2 ) )
- {
- amount = atoi( arg2 );
- if ( amount > ch->pcdata->bankaccount )
- {
- sprintf( buf, "How can you withdraw %d GP when your balance is %d?",
- amount, ch->pcdata->bankaccount );
- do_say (mob, buf );
- return;
- }
- if (amount < 0 )
- {
- do_say( mob, "Only positive amounts allowed...");
- return;
- }
- ch->pcdata->bankaccount -= amount;
- ch->gold += amount;
- sprintf( buf, "You withdraw %d GP. Your new balance is %d GP.", amount, ch->pcdata->bankaccount );
- send_to_char(AT_WHITE, buf, ch );
- do_save( ch, "" );
- return;
- }
- }
- if ( !str_prefix( arg1, "store" ) )
- {
- OBJ_DATA *obj;
- int store_cost = 0; /* temp variable for storage costs... don't want stuff to change on us - Ahsile */
-
- if ( !str_prefix( arg2, " " ) )
- {
- send_to_char( AT_WHITE, "Your storage box contains:\n\r", ch );
- show_list_to_char( ch->pcdata->storage, ch, TRUE, TRUE );
- return;
- }
- if ( !( obj = get_obj_carry( ch, arg2 ) ) )
- {
- send_to_char( AT_WHITE, "You are not carrying that item.\n\r", ch );
- return;
- }
- /* Check container object count - Ahsile */
- if ( (ch->pcdata->storcount + obj_invcount( obj, TRUE ) ) >= (ch->level * 2 ) )
- {
- sprintf(buf,"%s%d%s","You may only have ",(ch->level * 2)," items in your storage box at your level.\n\r");
- send_to_char( AT_WHITE, buf , ch );
- return;
- }
- if ( obj->item_type == ITEM_KEY )
- {
- send_to_char( AT_WHITE,
- "You can't store that type of item.\n\r",
- ch );
- return;
- }
- /* Storage cost based on share prices - Ahsile */
- #if defined BANK_INVEST
- store_cost = (share_value + 100) * obj_invcount( obj, TRUE );
- #else
- store_cost = 200 * obj_invcount( obj, TRUE );
- #endif
- if ( ch->pcdata->bankaccount < store_cost )
- {
- sprintf(buf,"%s%d%s","Storing costs ", store_cost ,"gp, which you do not have in your bank account.\n\r");
- send_to_char( AT_WHITE, buf, ch );
- return;
- }
- ch->pcdata->bankaccount -= store_cost;
- oprog_store_trigger( obj, ch );
- obj_from_char( obj );
- obj_to_storage( obj, ch );
- sprintf(buf,"%s%d%s","The bank deducts ",store_cost,"gp from your account.\n\r");
- send_to_char( AT_WHITE, buf, ch );
- do_save( ch, "" );
- return;
- }
- if ( !str_prefix( arg1, "retrieve" ) )
- {
- OBJ_DATA *obj;
- if ( !str_prefix( arg2, " " ) )
- {
- send_to_char( AT_WHITE, "Retrieve what?\n\r", ch );
- return;
- }
- if ( !( obj = get_obj_storage( ch, arg2 ) ) )
- {
- send_to_char(AT_WHITE, "You do not have that object in storage.\n\r", ch);
- send_to_char(AT_WHITE, "Use 'bank store' to see what you have in storage.\n\r",ch);
- return;
- }
- if ( obj_invcount( obj, TRUE ) + ch->carry_number > can_carry_n( ch ) )
- {
- send_to_char(AT_WHITE, "You will be carrying too many items!",ch);
- return;
- }
- obj_from_storage( obj );
- obj_to_char( obj, ch );
- oprog_retrieve_trigger( obj, ch );
- send_to_char( AT_WHITE, "You retrieve it from storage.\n\r", ch );
- do_save( ch, "" );
- return;
- }
- /* If you want to have an invest option... define BANK_INVEST */
- #if defined BANK_INVEST
- if ( !str_prefix( arg1, "buy" ) )
- {
- int amount;
- if (share_value < 1)
- {
- send_to_char(AT_WHITE, "There is something wrong with shares, notify the GODS.", ch);
- return;
- }
- if ( is_number ( arg2 ) )
- {
- amount = atoi( arg2 );
- if ( (amount * share_value) > ch->pcdata->bankaccount )
- {
- sprintf( buf, "%d shares will cost you %d, get more money.", amount, (amount * share_value) );
- send_to_char(AT_WHITE, buf, ch);
- return;
- }
- if (amount < 0 )
- {
- send_to_char(AT_WHITE, "If you want to sell shares you have to say so...", ch);
- return;
- }
- if( ( amount + ch->pcdata->shares ) > 500000 )
- {
- send_to_char(AT_WHITE, "You can only have 500000 shares.\n\r", ch );
- return;
- }
- ch->pcdata->bankaccount -= (amount * share_value);
- ch->pcdata->shares += amount;
- sprintf( buf, "You buy %d shares for %d GP, you now have %d shares.\n\r", amount, (amount * share_value), ch->pcdata->shares );
- send_to_char(AT_WHITE, buf, ch);
- do_save( ch, "" );
- return;
- }
- }
- if ( !str_prefix( arg1, "sell" ) )
- {
- int amount;
- if (share_value < 1)
- {
- send_to_char(AT_WHITE, "There is something wrong with the shares, notify the GODS.", ch);
- return;
- }
- if ( is_number ( arg2 ) )
- {
- amount = atoi( arg2 );
- if ( amount > ch->pcdata->shares )
- {
- sprintf( buf, "You only have %d shares.", ch->pcdata->shares );
- send_to_char(AT_WHITE, buf, ch);
- return;
- }
- if (amount < 0 )
- {
- send_to_char(AT_WHITE, "If you want to buy shares you have to say so...", ch);
- return;
- }
- if( ( ( amount * share_value ) + ch->pcdata->bankaccount ) > 2000000000 )
- {
- send_to_char(AT_WHITE, "Your bank account can not handle that much gold.\n\r", ch );
- return;
- }
- ch->pcdata->bankaccount += (amount * share_value);
- ch->pcdata->shares -= amount;
- sprintf( buf, "You sell %d shares for %d GP, you now have %d shares.\n\r", amount, (amount * share_value), ch->pcdata->shares );
- send_to_char(AT_WHITE, buf, ch);
- do_save( ch, "" );
- return;
- }
- }
- if ( !str_prefix( arg1, "check" ) )
- {
- sprintf (buf, "The current shareprice is %d.",share_value);
- send_to_char(AT_WHITE, buf, ch);
- if (ch->pcdata->shares)
- {
- sprintf (buf, " You have %d shares, (%d a share) worth a total of %d gold.",
- ch->pcdata->shares, share_value, (ch->pcdata->shares * share_value) );
- send_to_char(AT_WHITE, buf, ch);
- }
- send_to_char(AT_WHITE, "\n\r", ch );
- return;
- }
- #endif
- send_to_char(AT_WHITE, "I don't know what you mean.\n\r", ch);
- do_bank( ch, "" ); /* Generate Instructions */
- return;
- }