PageRenderTime 186ms CodeModel.GetById 33ms RepoModel.GetById 1ms app.codeStats 0ms

/src/economy.c

https://github.com/rayhe/stormgate
C | 432 lines | 321 code | 58 blank | 53 comment | 48 complexity | 0038733b255c720f4d6e4f5d19082d22 MD5 | raw file
  1. /*
  2. * The Mythran Mud Economy Snippet Version 2 (used to be banking.c)
  3. *
  4. * Copyrights and rules for using the economy system:
  5. *
  6. * The Mythran Mud Economy system was written by The Maniac, it was
  7. * loosly based on the rather simple 'Ack!'s banking system'
  8. *
  9. * If you use this code you must follow these rules.
  10. * -Keep all the credits in the code.
  11. * -Mail Maniac (v942346@si.hhs.nl) to say you use the code
  12. * -Send a bug report, if you find 'it'
  13. * -Credit me somewhere in your mud.
  14. * -Follow the envy/merc/diku license
  15. * -If you want to: send me some of your code
  16. *
  17. * All my snippets can be found on http://www.hhs.nl/~v942346/snippets.html
  18. * Check it often because it's growing rapidly -- Maniac --
  19. */
  20. /*$Id: economy.c,v 1.3 2005/02/22 23:55:16 ahsile Exp $*/
  21. #if defined( macintosh )
  22. #include <types.h>
  23. #else
  24. #include <sys/types.h>
  25. #endif
  26. #include <ctype.h>
  27. #include <stdio.h>
  28. #include <stdlib.h>
  29. #include <string.h>
  30. #include <time.h>
  31. #include "merc.h"
  32. int share_value = SHARE_VALUE; /* External share_value by Maniac */
  33. /*
  34. * External functions.
  35. */
  36. void show_list_to_char( OBJ_DATA *list, CHAR_DATA *ch, bool fShort,
  37. bool fShowNothing );
  38. int obj_invcount args( ( OBJ_DATA* obj, bool one_item ) );
  39. void do_bank( CHAR_DATA *ch, char *argument )
  40. {
  41. /* The Mythran mud economy system (bank and trading)
  42. *
  43. * based on:
  44. * Simple banking system. by -- Stephen --
  45. *
  46. * The following changes and additions where
  47. * made by the Maniac from Mythran Mud
  48. * (v942346@si.hhs.nl)
  49. *
  50. * History:
  51. * 18/05/96: Added the transfer option, enables chars to transfer
  52. * money from their account to other players' accounts
  53. * 18/05/96: Big bug detected, can deposit/withdraw/transfer
  54. * negative amounts (nice way to steal is
  55. * bank transfer -(lots of dogh) <some rich player>
  56. * Fixed it (thought this was better... -= Maniac =-)
  57. * 21/06/96: Fixed a bug in transfer (transfer to MOBS)
  58. * Moved balance from ch->balance to ch->pcdata->balance
  59. * 21/06/96: Started on the invest option, so players can invest
  60. * money in shares, using buy, sell and check
  61. * Finished version 1.0 releasing it monday 24/06/96
  62. * 24/06/96: Mythran Mud Economy System V1.0 released by Maniac
  63. *
  64. */
  65. CHAR_DATA *mob;
  66. char buf[MAX_STRING_LENGTH];
  67. char arg1[MAX_INPUT_LENGTH];
  68. char arg2[MAX_INPUT_LENGTH];
  69. if ( IS_NPC( ch ) )
  70. {
  71. send_to_char(AT_WHITE, "Banking Services are only available to players!\n\r", ch );
  72. return;
  73. }
  74. /* Check for mob with act->banker */
  75. for ( mob = ch->in_room->people; mob; mob = mob->next_in_room )
  76. {
  77. if ( IS_NPC(mob) && IS_SET(mob->act, ACT_BANKER ) )
  78. break;
  79. }
  80. if ( mob == NULL )
  81. {
  82. send_to_char(AT_WHITE, "You can't do that here.\n\r", ch );
  83. return;
  84. }
  85. if ( argument[0] == '\0' )
  86. {
  87. send_to_char(AT_WHITE, "Bank Options:\n\r\n\r", ch );
  88. send_to_char(AT_WHITE, "Bank balance: Displays your balance.\n\r", ch );
  89. send_to_char(AT_WHITE, "Bank deposit <amount>: Deposit gold into your account.\n\r", ch );
  90. send_to_char(AT_WHITE, "Bank withdraw <amount>: Withdraw gold from your account.\n\r", ch );
  91. send_to_char(AT_WHITE, "Bank retrieve <item>: Retrieve a stored item from the bank.\n\r", ch );
  92. send_to_char(AT_WHITE, "Bank store <item>: Store an item in the bank.\n\r", ch );
  93. #if defined BANK_TRANSFER
  94. send_to_char(AT_WHITE, "Bank transfer <amount> <player>: Transfer <amount> gold to <player> account.\n\r", ch);
  95. #endif
  96. #if defined BANK_INVEST
  97. send_to_char(AT_WHITE, "Bank check: check the current shares price.\n\r", ch );
  98. send_to_char(AT_WHITE, "Bank buy <amount>: Buy <amount> shares.\n\r", ch );
  99. send_to_char(AT_WHITE, "Bank sell <amount>: Sell <amount> shares.\n\r", ch );
  100. #endif
  101. return;
  102. }
  103. argument = one_argument( argument, arg1 );
  104. argument = one_argument( argument, arg2 );
  105. /* Now work out what to do... */
  106. if ( !str_prefix( arg1, "balance" ) )
  107. {
  108. sprintf(buf,"Your current balance is: %d GP.", ch->pcdata->bankaccount );
  109. send_to_char(AT_WHITE, buf, ch);
  110. return;
  111. }
  112. if ( !str_prefix( arg1, "deposit" ) )
  113. {
  114. int amount;
  115. if ( is_number ( arg2 ) )
  116. {
  117. amount = atoi( arg2 );
  118. if (amount > ch->gold )
  119. {
  120. sprintf( buf, "How can you deposit %d GP when you only have %d?", amount, ch->gold );
  121. do_say(mob, buf );
  122. return;
  123. }
  124. if (amount < 0 )
  125. {
  126. do_say (mob, "Only positive amounts allowed...");
  127. return;
  128. }
  129. ch->gold -= amount;
  130. ch->pcdata->bankaccount += amount;
  131. sprintf ( buf, "You deposit %d GP. Your new balance is %d GP.\n\r",
  132. amount, ch->pcdata->bankaccount );
  133. send_to_char(AT_WHITE, buf, ch );
  134. do_save( ch, "" );
  135. return;
  136. }
  137. }
  138. /* We only allow transfers if this is true... so define it... */
  139. #if defined BANK_TRANSFER
  140. if ( !str_prefix( arg1, "transfer" ) )
  141. {
  142. int amount;
  143. CHAR_DATA *victim;
  144. if ( is_number ( arg2 ) )
  145. {
  146. amount = atoi( arg2 );
  147. if ( amount > ch->pcdata->bankaccount )
  148. {
  149. sprintf( buf, "How can you transfer %d GP when your balance is %d?",
  150. amount, ch->pcdata->bankaccount );
  151. send_to_char(AT_WHITE, buf, ch);
  152. return;
  153. }
  154. if (amount < 0 )
  155. {
  156. send_to_char(AT_WHITE, "Only positive amounts allowed...", ch);
  157. return;
  158. }
  159. if ( !( victim = get_char_world( ch, argument ) ) )
  160. {
  161. sprintf (buf, "%s doesn't have a bank account.", argument );
  162. send_to_char(AT_WHITE, buf, ch);
  163. return;
  164. }
  165. if (IS_NPC(victim))
  166. {
  167. send_to_char(AT_WHITE, "You can only transfer money to players.", ch);
  168. return;
  169. }
  170. ch->pcdata->bankaccount -= amount;
  171. victim->pcdata->bankaccount += amount;
  172. sprintf( buf, "You transfer %d GP. Your new balance is %d GP.\n\r",
  173. amount, ch->pcdata->bankaccount );
  174. send_to_char(AT_WHITE, buf, ch );
  175. sprintf (buf, "[BANK] %s has transferred %d gold's to your account.\n\r", ch->name, amount);
  176. send_to_char(AT_WHITE, buf, victim );
  177. do_save( ch, "" );
  178. do_save( victim, "");
  179. return;
  180. }
  181. }
  182. #endif
  183. if ( !str_prefix( arg1, "withdraw" ) )
  184. {
  185. int amount;
  186. if ( is_number ( arg2 ) )
  187. {
  188. amount = atoi( arg2 );
  189. if ( amount > ch->pcdata->bankaccount )
  190. {
  191. sprintf( buf, "How can you withdraw %d GP when your balance is %d?",
  192. amount, ch->pcdata->bankaccount );
  193. do_say (mob, buf );
  194. return;
  195. }
  196. if (amount < 0 )
  197. {
  198. do_say( mob, "Only positive amounts allowed...");
  199. return;
  200. }
  201. ch->pcdata->bankaccount -= amount;
  202. ch->gold += amount;
  203. sprintf( buf, "You withdraw %d GP. Your new balance is %d GP.", amount, ch->pcdata->bankaccount );
  204. send_to_char(AT_WHITE, buf, ch );
  205. do_save( ch, "" );
  206. return;
  207. }
  208. }
  209. if ( !str_prefix( arg1, "store" ) )
  210. {
  211. OBJ_DATA *obj;
  212. int store_cost = 0; /* temp variable for storage costs... don't want stuff to change on us - Ahsile */
  213. if ( !str_prefix( arg2, " " ) )
  214. {
  215. send_to_char( AT_WHITE, "Your storage box contains:\n\r", ch );
  216. show_list_to_char( ch->pcdata->storage, ch, TRUE, TRUE );
  217. return;
  218. }
  219. if ( !( obj = get_obj_carry( ch, arg2 ) ) )
  220. {
  221. send_to_char( AT_WHITE, "You are not carrying that item.\n\r", ch );
  222. return;
  223. }
  224. /* Check container object count - Ahsile */
  225. if ( (ch->pcdata->storcount + obj_invcount( obj, TRUE ) ) >= (ch->level * 2 ) )
  226. {
  227. sprintf(buf,"%s%d%s","You may only have ",(ch->level * 2)," items in your storage box at your level.\n\r");
  228. send_to_char( AT_WHITE, buf , ch );
  229. return;
  230. }
  231. if ( obj->item_type == ITEM_KEY )
  232. {
  233. send_to_char( AT_WHITE,
  234. "You can't store that type of item.\n\r",
  235. ch );
  236. return;
  237. }
  238. /* Storage cost based on share prices - Ahsile */
  239. #if defined BANK_INVEST
  240. store_cost = (share_value + 100) * obj_invcount( obj, TRUE );
  241. #else
  242. store_cost = 200 * obj_invcount( obj, TRUE );
  243. #endif
  244. if ( ch->pcdata->bankaccount < store_cost )
  245. {
  246. sprintf(buf,"%s%d%s","Storing costs ", store_cost ,"gp, which you do not have in your bank account.\n\r");
  247. send_to_char( AT_WHITE, buf, ch );
  248. return;
  249. }
  250. ch->pcdata->bankaccount -= store_cost;
  251. oprog_store_trigger( obj, ch );
  252. obj_from_char( obj );
  253. obj_to_storage( obj, ch );
  254. sprintf(buf,"%s%d%s","The bank deducts ",store_cost,"gp from your account.\n\r");
  255. send_to_char( AT_WHITE, buf, ch );
  256. do_save( ch, "" );
  257. return;
  258. }
  259. if ( !str_prefix( arg1, "retrieve" ) )
  260. {
  261. OBJ_DATA *obj;
  262. if ( !str_prefix( arg2, " " ) )
  263. {
  264. send_to_char( AT_WHITE, "Retrieve what?\n\r", ch );
  265. return;
  266. }
  267. if ( !( obj = get_obj_storage( ch, arg2 ) ) )
  268. {
  269. send_to_char(AT_WHITE, "You do not have that object in storage.\n\r", ch);
  270. send_to_char(AT_WHITE, "Use 'bank store' to see what you have in storage.\n\r",ch);
  271. return;
  272. }
  273. if ( obj_invcount( obj, TRUE ) + ch->carry_number > can_carry_n( ch ) )
  274. {
  275. send_to_char(AT_WHITE, "You will be carrying too many items!",ch);
  276. return;
  277. }
  278. obj_from_storage( obj );
  279. obj_to_char( obj, ch );
  280. oprog_retrieve_trigger( obj, ch );
  281. send_to_char( AT_WHITE, "You retrieve it from storage.\n\r", ch );
  282. do_save( ch, "" );
  283. return;
  284. }
  285. /* If you want to have an invest option... define BANK_INVEST */
  286. #if defined BANK_INVEST
  287. if ( !str_prefix( arg1, "buy" ) )
  288. {
  289. int amount;
  290. if (share_value < 1)
  291. {
  292. send_to_char(AT_WHITE, "There is something wrong with shares, notify the GODS.", ch);
  293. return;
  294. }
  295. if ( is_number ( arg2 ) )
  296. {
  297. amount = atoi( arg2 );
  298. if ( (amount * share_value) > ch->pcdata->bankaccount )
  299. {
  300. sprintf( buf, "%d shares will cost you %d, get more money.", amount, (amount * share_value) );
  301. send_to_char(AT_WHITE, buf, ch);
  302. return;
  303. }
  304. if (amount < 0 )
  305. {
  306. send_to_char(AT_WHITE, "If you want to sell shares you have to say so...", ch);
  307. return;
  308. }
  309. if( ( amount + ch->pcdata->shares ) > 500000 )
  310. {
  311. send_to_char(AT_WHITE, "You can only have 500000 shares.\n\r", ch );
  312. return;
  313. }
  314. ch->pcdata->bankaccount -= (amount * share_value);
  315. ch->pcdata->shares += amount;
  316. sprintf( buf, "You buy %d shares for %d GP, you now have %d shares.\n\r", amount, (amount * share_value), ch->pcdata->shares );
  317. send_to_char(AT_WHITE, buf, ch);
  318. do_save( ch, "" );
  319. return;
  320. }
  321. }
  322. if ( !str_prefix( arg1, "sell" ) )
  323. {
  324. int amount;
  325. if (share_value < 1)
  326. {
  327. send_to_char(AT_WHITE, "There is something wrong with the shares, notify the GODS.", ch);
  328. return;
  329. }
  330. if ( is_number ( arg2 ) )
  331. {
  332. amount = atoi( arg2 );
  333. if ( amount > ch->pcdata->shares )
  334. {
  335. sprintf( buf, "You only have %d shares.", ch->pcdata->shares );
  336. send_to_char(AT_WHITE, buf, ch);
  337. return;
  338. }
  339. if (amount < 0 )
  340. {
  341. send_to_char(AT_WHITE, "If you want to buy shares you have to say so...", ch);
  342. return;
  343. }
  344. if( ( ( amount * share_value ) + ch->pcdata->bankaccount ) > 2000000000 )
  345. {
  346. send_to_char(AT_WHITE, "Your bank account can not handle that much gold.\n\r", ch );
  347. return;
  348. }
  349. ch->pcdata->bankaccount += (amount * share_value);
  350. ch->pcdata->shares -= amount;
  351. sprintf( buf, "You sell %d shares for %d GP, you now have %d shares.\n\r", amount, (amount * share_value), ch->pcdata->shares );
  352. send_to_char(AT_WHITE, buf, ch);
  353. do_save( ch, "" );
  354. return;
  355. }
  356. }
  357. if ( !str_prefix( arg1, "check" ) )
  358. {
  359. sprintf (buf, "The current shareprice is %d.",share_value);
  360. send_to_char(AT_WHITE, buf, ch);
  361. if (ch->pcdata->shares)
  362. {
  363. sprintf (buf, " You have %d shares, (%d a share) worth a total of %d gold.",
  364. ch->pcdata->shares, share_value, (ch->pcdata->shares * share_value) );
  365. send_to_char(AT_WHITE, buf, ch);
  366. }
  367. send_to_char(AT_WHITE, "\n\r", ch );
  368. return;
  369. }
  370. #endif
  371. send_to_char(AT_WHITE, "I don't know what you mean.\n\r", ch);
  372. do_bank( ch, "" ); /* Generate Instructions */
  373. return;
  374. }