PPC_Common.inc 21 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564
  1. // This file holds all common functions that don't fit in any other file
  2. // This functions gives the player the given amount of money and scorepoints
  3. RewardPlayer(playerid, Money, Points)
  4. {
  5. // Add the given amount of money to the player's account
  6. APlayerData[playerid][PlayerMoney] = APlayerData[playerid][PlayerMoney] + Money;
  7. // Add the given amount of scorepoints to the player's account
  8. APlayerData[playerid][PlayerScore] = APlayerData[playerid][PlayerScore] + Points;
  9. }
  10. // This function creates the vehicle and saves the vehicle-lodel in the AVehicleData-array (can only be used during GameModeInit)
  11. // It also sets the fuel to maximum
  12. Vehicle_AddStatic(vModel, Float:vX, Float:vY, Float:vZ, Float:vRotation, vC1, vC2, vSpawnDelay)
  13. {
  14. // Create a new static vehicle during GameModeInit
  15. new vid = AddStaticVehicleEx(vModel, vX, vY, vZ, vRotation, vC1, vC2, vSpawnDelay);
  16. // Save the vehicle-model
  17. AVehicleData[vid][Model] = vModel;
  18. // Set the fuel to maximum so the vehicle can be used
  19. AVehicleData[vid][Fuel] = MaxFuel;
  20. // Save the colors
  21. AVehicleData[vid][Color1] = vC1;
  22. AVehicleData[vid][Color2] = vC2;
  23. // Set this vehicle as a static vehicle
  24. AVehicleData[vid][StaticVehicle] = true;
  25. return vid;
  26. }
  27. // This function is the same as Vehicle_AddStatic, but uses CreateVehicle instead of AddStaticVehicleEx, so can be used everywhere
  28. Vehicle_Create(vModel, Float:vX, Float:vY, Float:vZ, Float:vRotation, vC1, vC2, vSpawnDelay)
  29. {
  30. // Create a new static vehicle during GameModeInit
  31. new vid = CreateVehicle(vModel, vX, vY, vZ, vRotation, vC1, vC2, vSpawnDelay);
  32. // Save the vehicle-model
  33. AVehicleData[vid][Model] = vModel;
  34. // Set the fuel to maximum so the vehicle can be used
  35. AVehicleData[vid][Fuel] = MaxFuel;
  36. // Save the colors
  37. AVehicleData[vid][Color1] = vC1;
  38. AVehicleData[vid][Color2] = vC2;
  39. return vid;
  40. }
  41. // This function deletes the vehicle and clears all the data (is only used for player-owned vehicles)
  42. Vehicle_Delete(vid)
  43. {
  44. // Setup local variables
  45. new HouseID, CarSlot;
  46. // Get the HouseID and CarSlot where the vehicle is linked to
  47. HouseID = AVehicleData[vid][BelongsToHouse];
  48. // Check if this was a valid HouseID
  49. if (HouseID != 0)
  50. {
  51. // Loop through all carslots of this house to find the vehicle-id
  52. for (new i; i < 10; i++)
  53. {
  54. // Check if this carslot holds the same vehicle-id
  55. if (AHouseData[HouseID][VehicleIDs][i] == vid)
  56. {
  57. CarSlot = i; // The carslot has been found where the vehicle is stored, remember it
  58. break; // Stop the for-loop
  59. }
  60. }
  61. // Remove the vehicle from the house
  62. AHouseData[HouseID][VehicleIDs][CarSlot] = 0;
  63. }
  64. // Delete the vehicle
  65. DestroyVehicle(vid);
  66. // Clear the data
  67. AVehicleData[vid][Owned] = false;
  68. AVehicleData[vid][Owner] = 0;
  69. AVehicleData[vid][Model] = 0;
  70. AVehicleData[vid][PaintJob] = 0;
  71. for (new i; i < 14; i++)
  72. AVehicleData[vid][Components][i] = 0;
  73. AVehicleData[vid][Color1] = 0;
  74. AVehicleData[vid][Color2] = 0;
  75. AVehicleData[vid][SpawnX] = 0.0;
  76. AVehicleData[vid][SpawnY] = 0.0;
  77. AVehicleData[vid][SpawnZ] = 0.0;
  78. AVehicleData[vid][SpawnRot] = 0.0;
  79. AVehicleData[vid][BelongsToHouse] = 0;
  80. }
  81. // This function returns "1" if both locations are not closeby and returns "0" if both locations are close to eachother
  82. Locations_CheckDistance(LocationA, LocationB, Float:Range)
  83. {
  84. // Setup local variables
  85. new Float:Xa, Float:Ya, Float:Xb, Float:Yb, Float:X, Float:Y;
  86. // Get the coordinates of LocationA
  87. Xa = ALocations[LocationA][LocX];
  88. Ya = ALocations[LocationA][LocY];
  89. // Get the coordinates of LocationB
  90. Xb = ALocations[LocationB][LocX];
  91. Yb = ALocations[LocationB][LocY];
  92. // Calculate the distances between both locations
  93. Y = Yb - Ya;
  94. X = Xb - Xa;
  95. // Check if both locations are further apart then the range indicates
  96. if (((X * X) + (Y * Y)) > (Range * Range))
  97. return 1; // Location B is further away from Location A than Range indicates
  98. else
  99. return 0; // both locations are closer to eachother than Range indicates
  100. }
  101. // This function ports all non-admin players out of the given area to the location specified
  102. Player_PortOutAdminZone(playerid, Float:x1, Float:y1, Float:z1, Float:x2, Float:y2, Float:z2, Float:x3, Float:y3, Float:z3)
  103. {
  104. // Setup local variables
  105. new Float:x, Float:y, Float:z;
  106. // Get the player's coordinates
  107. GetPlayerPos(playerid, x, y, z);
  108. // Check if the player is not an admin
  109. if (APlayerData[playerid][PlayerLevel] == 0)
  110. if ((x1 < x) && (x < x2))
  111. if ((y1 < y) && (y < y2))
  112. if ((z1 < z) && (z < z2))
  113. {
  114. SendClientMessage(playerid, 0xFFFFFFFF, "{FF0000}You're not allowed inside an admin-area");
  115. SetPlayerPos(playerid, x3, y3, z3); // Port the player out of the area
  116. }
  117. }
  118. // This function sends the given text to all admins
  119. SendAdminText(playerid, command[], text[])
  120. {
  121. // Setup local variables
  122. new Name[24], Msg[128];
  123. // Loop through all players
  124. for (new i; i < MAX_PLAYERS; i++)
  125. {
  126. // Check if the player is an admin
  127. if (APlayerData[i][PlayerLevel] > 0)
  128. {
  129. // Get the player's name
  130. GetPlayerName(playerid, Name, sizeof(Name));
  131. // Send the given text to the admin
  132. format(Msg, 128, "{00FFCC}%s used: %s %s", Name, command, text);
  133. SendClientMessage(i, 0xFFFFFFFF, Msg);
  134. }
  135. }
  136. // Also log all used commands in the server.log file
  137. format(Msg, 128, "%s used: %s %s", Name, command, text);
  138. print(Msg);
  139. }
  140. // This timer informs the player how long he will be frozen
  141. forward Player_FreezeTimer(playerid);
  142. public Player_FreezeTimer(playerid)
  143. {
  144. // Setup local variables
  145. new Msg[128];
  146. // Decrease the remaining time this player will be frozen
  147. APlayerData[playerid][PlayerFrozen]--;
  148. // Check if the player is allowed to move again
  149. if (APlayerData[playerid][PlayerFrozen] > 0)
  150. {
  151. // Construct the message to inform the player how long he stays frozen
  152. if (APlayerData[playerid][PlayerFrozen] >= 60)
  153. format(Msg, 128, "Frozen for %i minutes", APlayerData[playerid][PlayerFrozen] / 60);
  154. else
  155. format(Msg, 128, "Frozen for %i seconds", APlayerData[playerid][PlayerFrozen]);
  156. // Display the message to inform the player how long he stays frozen
  157. GameTextForPlayer(playerid, Msg, 1000, 4);
  158. }
  159. else // The timer has run out, so allow his to move again
  160. TogglePlayerControllable(playerid, 1);
  161. }
  162. // This function creates a list of commands, starting from the FirstCommand and automatically shows the dialog
  163. CommandList_Create(playerid)
  164. {
  165. // Setup local variables
  166. new Counter, CommandList[1000], DialogTitle[128];
  167. // Only add 4 commands to the list, starting from the FirstItem
  168. for (new i = APlayerData[playerid][DialogFirstItem]; i < sizeof(ACommands); i++)
  169. {
  170. // Increase a counter (which holds the number of commands that have been added to the list
  171. Counter++;
  172. // Check if the maximum hasn't been reached yet
  173. if (Counter <= 5)
  174. {
  175. // Check if this command is valid for this player
  176. if (APlayerData[playerid][PlayerLevel] >= ACommands[i][CommandLevel])
  177. {
  178. // Check if the command is used for admins or not
  179. if (ACommands[i][CommandLevel] == 0)
  180. {
  181. // Add the commandname and description to the list
  182. format(CommandList, 500, "%s%s{00FF00}%s", CommandList, "\n", ACommands[i][CommandStructure]); // Add the name of the next command to the list on the next line
  183. format(CommandList, 500, "%s%s\t\t{FFFF00}%s", CommandList, "\n", ACommands[i][CommandDescription]); // Add the description of the next command to the list on the next line
  184. }
  185. else
  186. {
  187. // Add the commandname and description to the list
  188. format(CommandList, 500, "%s%sLvl %i: {00FF00}%s", CommandList, "\n", ACommands[i][CommandLevel], ACommands[i][CommandStructure]); // Add the name of the next command to the list on the next line
  189. format(CommandList, 500, "%s%s\t\t{FFFF00}%s", CommandList, "\n", ACommands[i][CommandDescription]); // Add the description of the next command to the list on the next line
  190. }
  191. }
  192. else
  193. break;
  194. }
  195. else // 5 commands have been added to the list (now Counter = 6)
  196. {
  197. // Add an empty line and "Next..." to the list to let the player know there are more commands
  198. format(CommandList, 500, "%s%s%s", CommandList, "\n \n", TXT_DialogEntryNext);
  199. // Also stop the For-loop
  200. break;
  201. }
  202. }
  203. // Construct the title for the dialog (to include a page number)
  204. format(DialogTitle, 128, TXT_DialogCommandTitle, (APlayerData[playerid][DialogFirstItem] / 5) + 1);
  205. // Show the commands in a dialog
  206. ShowPlayerDialog(playerid, DialogPlayerCommands, DIALOG_STYLE_LIST, DialogTitle, CommandList, TXT_DialogButtonSelect, TXT_DialogButtonCancel);
  207. return 1;
  208. }
  209. // This function returns "1" if the given vehicle-id is a plane or helicopter
  210. IsVehicleAirVehicle(vid)
  211. {
  212. switch (GetVehicleModel(vid))
  213. {
  214. case 592, 577, 511, 512, 593, 520, 553, 476, 519, 460, 513, 548, 425, 417, 487, 488, 497, 563, 447, 469: return 1;
  215. default: return 0;
  216. }
  217. return 0;
  218. }
  219. // This function creates a speedcamera (store data and create the objects)
  220. SetupSpeedCamera(CamID, Float:x, Float:y, Float:z, Float:rot, MaxSpeed)
  221. {
  222. // Store all the given values
  223. ACameras[CamID][CamX] = x;
  224. ACameras[CamID][CamY] = y;
  225. ACameras[CamID][CamZ] = z;
  226. ACameras[CamID][CamAngle] = rot;
  227. ACameras[CamID][CamSpeed] = MaxSpeed;
  228. // Create both camera objects and store their reference
  229. ACameras[CamID][CamObj1] = CreateObject(18880, x, y, z, 0.0, 0.0, rot);
  230. ACameras[CamID][CamObj2] = CreateObject(18880, x, y, z, 0.0, 0.0, rot + 180.0);
  231. }
  232. // This function sends the report to all admins
  233. SendReportToAdmins(OffenderID, Reason[], bool:AutoReport = false)
  234. {
  235. // Setup local variables
  236. new Name[24], Msg[128], TxtMsg[128], TotalReason[128];
  237. // Get the name of the offender
  238. GetPlayerName(OffenderID, Name, sizeof(Name));
  239. // Construct the report message for all admins
  240. if (AutoReport == false)
  241. {
  242. // Construct the report messages for a normal report
  243. format(Msg, 128, "{00FFFF}*** Report: %s (%i): %s", Name, OffenderID, Reason);
  244. format(TxtMsg, 128, "Report:~n~~g~%s (%i)~n~~r~%s", Name, OffenderID, Reason);
  245. format(TotalReason, 128, Reason);
  246. }
  247. else
  248. {
  249. // Construct the report messages for an automated report (sent by the AntiHack function)
  250. format(Msg, 128, "{00FFFF}*** Auto-Report: %s (%i): %s", Name, OffenderID, Reason);
  251. format(TxtMsg, 128, "Auto-Report:~n~~g~%s (%i)~n~~r~%s", Name, OffenderID, Reason);
  252. format(TotalReason, 128, "%s (by AntiHack)", Reason);
  253. // For automated reports, preset the time to 60 seconds to stop the Anti-Hack system reporting the player every half a second
  254. APlayerData[OffenderID][AutoReportTime] = 120; // The time must be doubled, as the speedometer runs twice every second
  255. }
  256. // Loop through all the players to find all online admins
  257. for (new playerid; playerid < MAX_PLAYERS; playerid++)
  258. {
  259. // Check if this player is an admin
  260. if (APlayerData[playerid][PlayerLevel] > 0)
  261. {
  262. // Send a message to the admin to inform him about the report
  263. SendClientMessage(playerid, 0xFFFFFFFF, Msg);
  264. // Also send the admin a GameText-message so he can see it more clearly
  265. GameTextForPlayer(playerid, TxtMsg, 10000, 4);
  266. }
  267. }
  268. // Add the report to the AReports-array so admins can review it in a dialog (maximum 50 reports can be stored)
  269. AddReport(OffenderID, TotalReason);
  270. }
  271. // This function adds the report to the AReports array automatically
  272. AddReport(OffenderID, Reason[])
  273. {
  274. // Setup local variables
  275. new ReportID = -1, Name[24];
  276. // Check if there is a free spot in the AReports array
  277. for (new i; i < 50; i++)
  278. {
  279. // Check if this report-spot is empty
  280. if (AReports[i][ReportUsed] == false)
  281. {
  282. ReportID = i;
  283. break; // If this spot hasn't been used yet, stop the for-loop
  284. }
  285. }
  286. // If no spot is free (ReportID is still -1)
  287. if (ReportID == -1)
  288. {
  289. // Drop the report on ID 0, and move them all downwards
  290. for (new i = 1; i < 50; i++)
  291. {
  292. AReports[i - 1][ReportUsed] = AReports[i][ReportUsed];
  293. format(AReports[i - 1][ReportName], 24, "%s", AReports[i][ReportName]);
  294. format(AReports[i - 1][ReportReason], 128, "%s", AReports[i][ReportReason]);
  295. }
  296. // ReportID 49 is available now, so use this to add the new report
  297. ReportID = 49;
  298. }
  299. // Get the name of the offender
  300. GetPlayerName(OffenderID, Name, sizeof(Name));
  301. // Store the data into the array
  302. AReports[ReportID][ReportUsed] = true;
  303. format(AReports[ReportID][ReportName], 24, "%s", Name);
  304. format(AReports[ReportID][ReportReason], 128, "%s", Reason);
  305. }
  306. // This function converts an ip-address into 4 separate integer parts and returns a string that only holds the first three parts
  307. GetFirstThreeDigitsFromIP(PlayerIP[])
  308. {
  309. // Setup local variables
  310. new Part1, Part2, Part3, DotLoc, RetIP[16];
  311. // Get the first part of the IP-address
  312. Part1 = strval(PlayerIP[0]);
  313. // Find the first dot
  314. DotLoc = strfind(PlayerIP, ".", false, 0);
  315. // Get the second part of the IP-address (the part that follows the first dot)
  316. Part2 = strval(PlayerIP[DotLoc+1]);
  317. // Find the second dot
  318. DotLoc = strfind(PlayerIP, ".", false, DotLoc+1);
  319. // Get the third part of the IP-address (the part that follows the second dot)
  320. Part3 = strval(PlayerIP[DotLoc+1]);
  321. // Combine them all into an IP that only holds the first three digits, followed by a dot
  322. format(RetIP, 16, "%i.%i.%i.", Part1, Part2, Part3);
  323. // Return it to the calling function
  324. return RetIP;
  325. }
  326. // This timer is executed every 2 minutes and sends all timedmessages one at a time
  327. forward Timer_TimedMessages();
  328. public Timer_TimedMessages()
  329. {
  330. // Send the message
  331. SendClientMessageToAll(0xFFFFFFFF, ATimedMessages[LastTimedMessage]);
  332. // Select the next message
  333. LastTimedMessage++;
  334. // Check if the next chosen message exists (the messagenumber is the same as the size of the array of messages)
  335. if (LastTimedMessage == sizeof(ATimedMessages))
  336. LastTimedMessage = 0; // Select the first message again
  337. return 1;
  338. }
  339. // This timer is executed every 5 minutes and sends the data about a random bonus mission to every trucker
  340. forward ShowRandomBonusMission();
  341. public ShowRandomBonusMission()
  342. {
  343. // Setup local variables
  344. new bool:MissionSet = false, Msg1[128], Msg2[128], Msg3[128], lName[50], sName[50], eName[50], tName[100];
  345. // Check if there is no mission defined yet (only happens when server is restarted), or when the mission has been completed by a player
  346. if ((RandomBonusMission[RandomLoad] == 0) || (RandomBonusMission[MissionFinished] == true))
  347. {
  348. // Keep checking until a valid mission has been set
  349. while (MissionSet == false)
  350. {
  351. // Choose a random LoadID
  352. RandomBonusMission[RandomLoad] = random(sizeof(ALoads));
  353. switch (RandomBonusMission[RandomLoad])
  354. {
  355. case 0: MissionSet = false; // If the dummy load has been chosen, allow the while loop to run again to search for another valid load
  356. default: // If another load has been chosen, check if it is a trucker load
  357. {
  358. switch(ALoads[RandomBonusMission[RandomLoad]][PCV_Required]) // Check the class & vehicle variable
  359. {
  360. case PCV_TruckerOreTrailer, PCV_TruckerFluidsTrailer, PCV_TruckerCargoTrailer, PCV_TruckerCementTruck, PCV_TruckerNoTrailer:
  361. {
  362. // Now only the loads for truckers are checked
  363. MissionSet = true; // The load has been determined now as it's a valid load for truckers only
  364. }
  365. default: MissionSet = false; // If another class & vehicle has been chosen (mafia or pilot load), search again
  366. }
  367. }
  368. }
  369. }
  370. // Find a random startlocation and endlocation from the chosen load
  371. RandomBonusMission[RandomStartLoc] = Product_GetRandomStartLoc(RandomBonusMission[RandomLoad]);
  372. RandomBonusMission[RandomEndLoc] = Product_GetRandomEndLoc(RandomBonusMission[RandomLoad]);
  373. // Set the new random mission as not-completed yet
  374. RandomBonusMission[MissionFinished] = false;
  375. }
  376. // Get the names of the load, start-location and end-location
  377. format(lName, 50, ALoads[RandomBonusMission[RandomLoad]][LoadName]);
  378. format(sName, 50, ALocations[RandomBonusMission[RandomStartLoc]][LocationName]);
  379. format(eName, 50, ALocations[RandomBonusMission[RandomEndLoc]][LocationName]);
  380. // Setup the name of the vehicle you'll need for this mission
  381. switch(ALoads[RandomBonusMission[RandomLoad]][PCV_Required])
  382. {
  383. case PCV_TruckerOreTrailer: format(tName, 128, "truck with ore trailer");
  384. case PCV_TruckerFluidsTrailer: format(tName, 128, "truck with fluids trailer");
  385. case PCV_TruckerCargoTrailer: format(tName, 128, "truck with cargo trailer");
  386. case PCV_TruckerCementTruck: format(tName, 128, "cement truck");
  387. case PCV_TruckerNoTrailer: format(tName, 128, "Flatbed or DFT-30");
  388. }
  389. // Construct the messages that describe the mission
  390. format(Msg1, 128, "{00BBFF}Bonus mission: transport {FFBB00}%s", lName);
  391. format(Msg2, 128, "{00BBFF}from {FFBB00}%s{00BBFF} to {FFBB00}%s", sName, eName);
  392. format(Msg3, 128, "{00BBFF}You'll need a {FFBB00}%s{00BBFF} to complete this mission", tName);
  393. // Now send the data about the random mission to all truckers
  394. for (new playerid; playerid < MAX_PLAYERS; playerid++)
  395. {
  396. // Check if this player is online
  397. if (APlayerData[playerid][LoggedIn] == true)
  398. {
  399. // Check if this player is a trucker
  400. if (APlayerData[playerid][PlayerClass] == ClassTruckDriver)
  401. {
  402. SendClientMessage(playerid, 0xFFFFFFFF, Msg1);
  403. SendClientMessage(playerid, 0xFFFFFFFF, Msg2);
  404. SendClientMessage(playerid, 0xFFFFFFFF, Msg3);
  405. }
  406. }
  407. }
  408. return 1;
  409. }
  410. // This function displays the main bank menu dialog
  411. ShowBankMenu(playerid)
  412. {
  413. // Setup local variables
  414. new BankOptions[256], BankTitle[128];
  415. // Construct the title of the bank dialog
  416. format(BankTitle, sizeof(BankTitle), "{FFFFFF}Your bank funds: {00FF00}$%i", APlayerData[playerid][BankMoney]);
  417. // Construct the options of the bank dialog
  418. format(BankOptions, sizeof(BankOptions), "{00FF00}Deposit money\n");
  419. format(BankOptions, sizeof(BankOptions), "%s{00FF00}Withdraw money\n", BankOptions);
  420. format(BankOptions, sizeof(BankOptions), "%s{00FF00}Transfer money\n", BankOptions);
  421. format(BankOptions, sizeof(BankOptions), "%s{00FF00}Cancel bank account\n", BankOptions);
  422. // Show the bank dialog
  423. ShowPlayerDialog(playerid, DialogBankOptions, DIALOG_STYLE_LIST, BankTitle, BankOptions, TXT_DialogButtonSelect, TXT_DialogButtonCancel);
  424. }
  425. // This timer increases the variable "CurrentIntrestTime" every hour
  426. forward Bank_IntrestTimer();
  427. public Bank_IntrestTimer()
  428. {
  429. // Setup local variables
  430. new IntrestAmount, Msg[128];
  431. // Increase the variable by one
  432. CurrentIntrestTime++;
  433. // And save it to the file
  434. IntrestTime_Save();
  435. // Process intrest for all online player with a bank account if intrest is enabled
  436. if (IntrestEnabled == true)
  437. {
  438. // Loop through all players
  439. for (new playerid; playerid < MAX_PLAYERS; playerid++)
  440. {
  441. // Check if this player is logged in
  442. if (APlayerData[playerid][LoggedIn] == true)
  443. {
  444. // Check if this player has a bank account (just check if there is money in the bank, it's useless to process the intrest for
  445. // a bank account which doesn't have any money in it, and having BankMoney also means the player has a bank account)
  446. if (APlayerData[playerid][BankMoney] > 0)
  447. {
  448. // Calculate the intrest
  449. IntrestAmount = floatround(floatmul(APlayerData[playerid][BankMoney], BankIntrest), floatround_floor);
  450. // Add intrest to this player's bank account
  451. APlayerData[playerid][BankMoney] = APlayerData[playerid][BankMoney] + IntrestAmount;
  452. // Save the CurrentIntrestTime for this bank account
  453. APlayerData[playerid][LastIntrestTime] = CurrentIntrestTime;
  454. // Save the player's bank account
  455. BankFile_Save(playerid);
  456. // Inform the player that he received intrest on his bank account and how much
  457. format(Msg, 128, "{00BBFF}You've received {FFBB00}$%i{00BBFF} intrest on your bank account", IntrestAmount);
  458. SendClientMessage(playerid, 0xFFFFFFFF, Msg);
  459. }
  460. }
  461. }
  462. }
  463. }
  464. // This function creates a list of help-items, for which the player can get information about it
  465. HelpList_Create(playerid)
  466. {
  467. // Setup local variables
  468. new HelpList[1000], DialogTitle[128];
  469. // Construct the title for the dialog (to include a page number)
  470. format(DialogTitle, 128, "Here you can get help about any of these items:");
  471. // Add all help-topics to the list
  472. for (new i; i < sizeof(AHelpTopics); i++)
  473. {
  474. format(HelpList, 1000, "%s%s\n", HelpList, AHelpTopics[i]);
  475. }
  476. // Show the commands in a dialog
  477. ShowPlayerDialog(playerid, DialogHelpItemChosen, DIALOG_STYLE_LIST, DialogTitle, HelpList, TXT_DialogButtonSelect, TXT_DialogButtonCancel);
  478. return 1;
  479. }