· 9 years ago · Jan 19, 2017, 11:34 PM
1/********************* PARKING METER BY JAKE ELITE (2017) *********************/
2/******** COMMANDS: /createparkmeter, /eraseparkmeter, /insertparkmeter *******/
3/********************* PARKING METER BY JAKE ELITE (2017) *********************/
4
5#include <a_samp>
6#include <zcmd>
7#include <sscanf2>
8#include <streamer>
9
10native IsValidVehicle(vehicleid);
11
12new DB: pmeter;
13
14new VehicleNames[212][] = {
15 {"Landstalker"},{"Bravura"},{"Buffalo"},{"Linerunner"},{"Perrenial"},{"Sentinel"},{"Dumper"},
16 {"Firetruck"},{"Trashmaster"},{"Stretch"},{"Manana"},{"Infernus"},{"Voodoo"},{"Pony"},{"Mule"},
17 {"Cheetah"},{"Ambulance"},{"Leviathan"},{"Moonbeam"},{"Esperanto"},{"Taxi"},{"Washington"},
18 {"Bobcat"},{"Mr Whoopee"},{"BF Injection"},{"Hunter"},{"Premier"},{"Enforcer"},{"Securicar"},
19 {"Banshee"},{"Predator"},{"Bus"},{"Rhino"},{"Barracks"},{"Hotknife"},{"Trailer 1"},{"Previon"},
20 {"Coach"},{"Cabbie"},{"Stallion"},{"Rumpo"},{"RC Bandit"},{"Romero"},{"Packer"},{"Monster"},
21 {"Admiral"},{"Squalo"},{"Seasparrow"},{"Pizzaboy"},{"Tram"},{"Trailer 2"},{"Turismo"},
22 {"Speeder"},{"Reefer"},{"Tropic"},{"Flatbed"},{"Yankee"},{"Caddy"},{"Solair"},{"Berkley's RC Van"},
23 {"Skimmer"},{"PCJ-600"},{"Faggio"},{"Freeway"},{"RC Baron"},{"RC Raider"},{"Glendale"},{"Oceanic"},
24 {"Sanchez"},{"Sparrow"},{"Patriot"},{"Quad"},{"Coastguard"},{"Dinghy"},{"Hermes"},{"Sabre"},
25 {"Rustler"},{"ZR-350"},{"Walton"},{"Regina"},{"Comet"},{"BMX"},{"Burrito"},{"Camper"},{"Marquis"},
26 {"Baggage"},{"Dozer"},{"Maverick"},{"News Chopper"},{"Rancher"},{"FBI Rancher"},{"Virgo"},{"Greenwood"},
27 {"Jetmax"},{"Hotring"},{"Sandking"},{"Blista Compact"},{"Police Maverick"},{"Boxville"},{"Benson"},
28 {"Mesa"},{"RC Goblin"},{"Hotring Racer A"},{"Hotring Racer B"},{"Bloodring Banger"},{"Rancher"},
29 {"Super GT"},{"Elegant"},{"Journey"},{"Bike"},{"Mountain Bike"},{"Beagle"},{"Cropdust"},{"Stunt"},
30 {"Tanker"}, {"Roadtrain"},{"Nebula"},{"Majestic"},{"Buccaneer"},{"Shamal"},{"Hydra"},{"FCR-900"},
31 {"NRG-500"},{"HPV1000"},{"Cement Truck"},{"Tow Truck"},{"Fortune"},{"Cadrona"},{"FBI Truck"},
32 {"Willard"},{"Forklift"},{"Tractor"},{"Combine"},{"Feltzer"},{"Remington"},{"Slamvan"},
33 {"Blade"},{"Freight"},{"Streak"},{"Vortex"},{"Vincent"},{"Bullet"},{"Clover"},{"Sadler"},
34 {"Firetruck LA"},{"Hustler"},{"Intruder"},{"Primo"},{"Cargobob"},{"Tampa"},{"Sunrise"},{"Merit"},
35 {"Utility"},{"Nevada"},{"Yosemite"},{"Windsor"},{"Monster A"},{"Monster B"},{"Uranus"},{"Jester"},
36 {"Sultan"},{"Stratum"},{"Elegy"},{"Raindance"},{"RC Tiger"},{"Flash"},{"Tahoma"},{"Savanna"},
37 {"Bandito"},{"Freight Flat"},{"Streak Carriage"},{"Kart"},{"Mower"},{"Duneride"},{"Sweeper"},
38 {"Broadway"},{"Tornado"},{"AT-400"},{"DFT-30"},{"Huntley"},{"Stafford"},{"BF-400"},{"Newsvan"},
39 {"Tug"},{"Trailer 3"},{"Emperor"},{"Wayfarer"},{"Euros"},{"Hotdog"},{"Club"},{"Freight Carriage"},
40 {"Trailer 3"},{"Andromada"},{"Dodo"},{"RC Cam"},{"Launch"},{"Police Car (LSPD)"},{"Police Car (SFPD)"},
41 {"Police Car (LVPD)"},{"Police Ranger"},{"Picador"},{"S.W.A.T. Van"},{"Alpha"},{"Phoenix"},{"Glendale"},
42 {"Sadler"},{"Luggage Trailer A"},{"Luggage Trailer B"},{"Stair Trailer"},{"Boxville"},{"Farm Plow"},
43 {"Utility Trailer"}
44};
45
46#define MAX_METERS 100 // Maximum Parking Meters that can be made in the server.
47#define CASH_PER_MINUTES 10 // $10 per minutes
48
49enum ParkingMeters
50{
51 parkObject,
52 parkVehicle,
53 parkSeconds,
54 Text3D:parkLabel,
55 parkID,
56 Float:parkX,
57 Float:parkY,
58 Float:parkZ,
59 Float:parkA,
60 bool:parkAvailable
61};
62new pMeter[MAX_METERS][ParkingMeters];
63
64////////////////////////////////////////////////////////////////////////////////
65
66public OnFilterScriptInit()
67{
68 SetTimer("MeterCheck", 1000, true);
69
70 pmeter = db_open("parkingmeters.db");
71 db_query(pmeter, "CREATE TABLE IF NOT EXISTS `pmeters` (`id` INTEGER PRIMARY KEY AUTOINCREMENT, `x` FLOAT, `y` FLOAT, `z` FLOAT, `angle` FLOAT)");
72
73 for(new i; i < MAX_METERS; i++)
74 {
75 pMeter[i][parkID] = -1;
76 pMeter[i][parkX] = 0.0;
77 pMeter[i][parkY] = 0.0;
78 pMeter[i][parkZ] = 0.0;
79 pMeter[i][parkA] = 0.0;
80 pMeter[i][parkVehicle] = 0;
81 pMeter[i][parkAvailable] = false;
82 }
83 LoadParkMeters();
84 return 1;
85}
86
87public OnFilterScriptExit()
88{
89 db_close(pmeter);
90 return 1;
91}
92
93forward MeterCheck();
94public MeterCheck()
95{
96 new string[128], vid;
97
98 for(new i; i < MAX_METERS; i++)
99 {
100 if(pMeter[i][parkID] > -1)
101 {
102 vid = GetClosestVehicleInObject(pMeter[i][parkObject]);
103
104 switch(pMeter[i][parkAvailable])
105 {
106 case true:
107 {
108 format(string, sizeof(string), "# (%d)\nAVAILABLE FOR PARKING\nTime: None", i);
109 UpdateDynamic3DTextLabelText(pMeter[i][parkLabel], 0x33AA33FF, string);
110 }
111 case false:
112 {
113 if(pMeter[i][parkVehicle] != vid)
114 {
115 pMeter[i][parkSeconds] = 0;
116 pMeter[i][parkAvailable] = true;
117 pMeter[i][parkVehicle] = 0;
118 }
119 else
120 {
121 pMeter[i][parkSeconds] --;
122 if(pMeter[i][parkSeconds] < 1)
123 {
124 pMeter[i][parkSeconds] = 0;
125 pMeter[i][parkAvailable] = true;
126 pMeter[i][parkVehicle] = 0;
127 }
128 }
129
130 format(string, sizeof(string), "# %d\nNOT AVAILABLE FOR PARKING\nTime: %d", i, pMeter[i][parkSeconds]);
131 UpdateDynamic3DTextLabelText(pMeter[i][parkLabel], 0xFF6347FF, string);
132 if(vid != pMeter[i][parkVehicle])
133 {
134 pMeter[i][parkSeconds] = 0;
135 pMeter[i][parkAvailable] = true;
136 pMeter[i][parkVehicle] = 0;
137 }
138 }
139 }
140 }
141 }
142 return 1;
143}
144
145public OnPlayerConnect(playerid)
146{
147 return 1;
148}
149
150public OnPlayerDisconnect(playerid, reason)
151{
152 return 1;
153}
154
155////////////////////////////////////////////////////////////////////////////////
156
157CMD:createparkmeter(playerid, params[])
158{
159 if(IsPlayerAdmin(playerid))
160 {
161 new id = -1, string[128];
162
163 if(IsPlayerNearParkMeter(playerid) != -1)
164 return SendClientMessage(playerid, -1, "* There are another parking meter next to you, Move a little bit.");
165
166 new Float:x, Float:y, Float:z, Float:a;
167 GetPlayerPos(playerid, x, y, z);
168 GetPlayerFacingAngle(playerid, a);
169 id = InsertParkMeters(x, y, z, a);
170
171 if(id == -1)
172 return SendClientMessage(playerid, -1, "* The server cannot create a new parking meter, it has reached the limit of "#MAX_METERS" parking meters.");
173
174 format(string, sizeof(string), "* You have inserted a new parking meter # %d", id);
175 SendClientMessage(playerid, 0xFFFF00FF, string);
176 }
177 else
178 {
179 SendClientMessage(playerid, -1, "* You need to be an admin to use this command.");
180 }
181 return 1;
182}
183
184CMD:eraseparkmeter(playerid, params[])
185{
186 if(IsPlayerAdmin(playerid))
187 {
188 new id, string[128];
189
190 if(sscanf(params, "d", id))
191 return SendClientMessage(playerid, -1, "[?] /eraseparkmeter [ID]");
192
193 if(id < 0 || pMeter[id][parkID] < 0 || id >= MAX_METERS)
194 return SendClientMessage(playerid, -1, "* Invalid ID.");
195
196 format(string, sizeof(string), "* You have erased the parking meter # %d", id);
197 SendClientMessage(playerid, 0xFFFF00FF, string);
198
199 EraseParkMeter(id);
200 }
201 else
202 {
203 SendClientMessage(playerid, -1, "* You need to be an admin to use this command.");
204 }
205 return 1;
206}
207
208CMD:insertparkmeter(playerid, params[])
209{
210 new id = -1, vid = -1, Float:x, Float:y, Float:z, cash, string[128];
211
212 if(IsPlayerInAnyVehicle(playerid))
213 return SendClientMessage(playerid, -1, "* You must be on foot when using this command.");
214
215 if((id = IsPlayerNearParkMeter(playerid)) != -1)
216 {
217 if(sscanf(params, "d", cash))
218 return SendClientMessage(playerid, -1, "[?] /insertparkmeter [minutes] = $"#CASH_PER_MINUTES" per minutes");
219
220 if(cash < 1 || cash > 30)
221 return SendClientMessage(playerid, -1, "[!] You can only set 1 minute up to 30 minutes on the park meter.");
222
223 if(GetPlayerMoney(playerid) < cash * CASH_PER_MINUTES)
224 {
225 format(string, sizeof(string), "* You don't have $%d to set the park meter to %d minute(s).", cash * CASH_PER_MINUTES, cash);
226 return SendClientMessage(playerid, -1, string);
227 }
228
229 for(new i = 1; i < MAX_VEHICLES; i++)
230 {
231 if(IsValidVehicle(i))
232 {
233 GetVehiclePos(i, x, y, z);
234 if(IsPlayerInRangeOfPoint(playerid, 6.0, x, y, z))
235 {
236 vid = i;
237 break;
238 }
239 }
240 }
241
242 if(vid != -1)
243 {
244 format(string, sizeof(string), "* You have paid $%d and set the parking meter's minute to (%d), Your %s is now legally parked.", cash * CASH_PER_MINUTES, cash, VehicleNames[GetVehicleModel(vid)-400]);
245 SendClientMessage(playerid, 0x33AA33FF, string);
246
247 GivePlayerMoney(playerid, - cash * CASH_PER_MINUTES);
248
249 pMeter[id][parkSeconds] = cash * 60;
250 pMeter[id][parkVehicle] = vid;
251 pMeter[id][parkAvailable] = false;
252 }
253 else
254 {
255 SendClientMessage(playerid, -1, "* No vehicles are near by the park meter!");
256 }
257 }
258 else
259 {
260 SendClientMessage(playerid, -1, "* You are not near in any parking meter.");
261 }
262 return 1;
263}
264
265////////////////////////////////////////////////////////////////////////////////
266
267stock InsertParkMeters(Float:x, Float:y, Float:z, Float:angle)
268{
269 new nextid = -1, query[128];
270
271 for(new i; i < MAX_METERS; i++)
272 {
273 if(pMeter[i][parkID] == -1)
274 {
275 nextid = i;
276 break;
277 }
278 }
279
280 if(nextid < 0)
281 {
282 print("* Can't insert a new parking meter, no IDs are vacant for use - pmeter.amx");
283 }
284 else
285 {
286 printf("* A new parking meter has been inserted to ID %d - pmeter.amx", nextid);
287
288 pMeter[nextid][parkID] = nextid;
289 pMeter[nextid][parkX] = x;
290 pMeter[nextid][parkY] = y;
291 pMeter[nextid][parkZ] = z;
292 pMeter[nextid][parkA] = angle;
293 pMeter[nextid][parkAvailable] = true;
294 pMeter[nextid][parkVehicle] = 0;
295 pMeter[nextid][parkSeconds] = 0;
296
297 format(query, sizeof(query), "INSERT INTO `pmeters` (`x`, `y`, `z`, `angle`) VALUES(%.4f, %.4f, %.4f, %.4f)", pMeter[nextid][parkX], pMeter[nextid][parkY], pMeter[nextid][parkZ], pMeter[nextid][parkA]);
298 db_query(pmeter, query);
299
300 if(IsValidDynamicObject(pMeter[nextid][parkObject]))
301 DestroyDynamicObject(pMeter[nextid][parkObject]);
302
303 if(IsValidDynamic3DTextLabel(pMeter[nextid][parkLabel]))
304 DestroyDynamic3DTextLabel(pMeter[nextid][parkLabel]);
305
306 pMeter[nextid][parkObject] = CreateDynamicObject(1269, pMeter[nextid][parkX], pMeter[nextid][parkY], pMeter[nextid][parkZ] - 0.50, 0.0, 0.0, pMeter[nextid][parkA]);
307 pMeter[nextid][parkLabel] = CreateDynamic3DTextLabel("PARK METER CREATED", 0xFF6347AA, pMeter[nextid][parkX], pMeter[nextid][parkY], pMeter[nextid][parkZ], 15.0);
308 }
309 return nextid;
310}
311
312stock EraseParkMeter(id)
313{
314 new query[92];
315
316 if(pMeter[id][parkID] > - 1)
317 {
318 if(IsValidDynamicObject(pMeter[id][parkObject]))
319 DestroyDynamicObject(pMeter[id][parkObject]);
320
321 if(IsValidDynamic3DTextLabel(pMeter[id][parkLabel]))
322 DestroyDynamic3DTextLabel(pMeter[id][parkLabel]);
323
324 format(query, sizeof(query), "DELETE FROM `pmeters` WHERE `id` = %d", pMeter[id][parkID]);
325 db_query(pmeter, query);
326
327 pMeter[id][parkID] = -1;
328 pMeter[id][parkX] = 0.0;
329 pMeter[id][parkY] = 0.0;
330 pMeter[id][parkZ] = 0.0;
331 pMeter[id][parkA] = 0.0;
332 pMeter[id][parkAvailable] = true;
333 pMeter[id][parkVehicle] = 0;
334 pMeter[id][parkSeconds] = 0;
335 }
336 return 1;
337}
338
339stock LoadParkMeters()
340{
341 new
342 DBResult:dbresult,
343 idx
344 ;
345
346 dbresult = db_query(pmeter, "SELECT * FROM `pmeters` ORDER BY `id`");
347
348 for (new i, j = db_num_rows(dbresult); i != j; i++)
349 {
350 pMeter[i][parkID] = db_get_field_assoc_int(dbresult, "id");
351 pMeter[i][parkX] = db_get_field_assoc_int(dbresult, "x");
352 pMeter[i][parkY] = db_get_field_assoc_int(dbresult, "y");
353 pMeter[i][parkZ] = db_get_field_assoc_int(dbresult, "z");
354 pMeter[i][parkA] = db_get_field_assoc_int(dbresult, "angle");
355 pMeter[i][parkAvailable] = true;
356 pMeter[i][parkVehicle] = 0;
357 pMeter[i][parkSeconds] = 0;
358
359 if(IsValidDynamicObject(pMeter[i][parkObject]))
360 DestroyDynamicObject(pMeter[i][parkObject]);
361
362 if(IsValidDynamic3DTextLabel(pMeter[i][parkLabel]))
363 DestroyDynamic3DTextLabel(pMeter[i][parkLabel]);
364
365 pMeter[i][parkObject] = CreateDynamicObject(1269, pMeter[i][parkX], pMeter[i][parkY], pMeter[i][parkZ] - 0.50, 0.0, 0.0, pMeter[i][parkA]);
366 pMeter[i][parkLabel] = CreateDynamic3DTextLabel("_", 0xFF6347AA, pMeter[i][parkX], pMeter[i][parkY], pMeter[i][parkZ], 15.0);
367
368 idx++;
369
370 db_next_row(dbresult);
371 }
372 db_free_result(dbresult);
373
374 printf("* There are %d parking meters loaded from pmeter.amx", idx);
375 return 1;
376}
377
378stock IsPlayerNearParkMeter(playerid)
379{
380 new id = -1;
381
382 for(new i; i < MAX_METERS; i++)
383 {
384 if(pMeter[i][parkID] > -1 && IsPlayerInRangeOfPoint(playerid, 3.0, pMeter[i][parkX], pMeter[i][parkY], pMeter[i][parkZ]))
385 {
386 return i;
387 }
388 }
389 return id;
390}
391
392stock GetClosestVehicleInObject(objectid)
393{
394 new vid, Float:x, Float:y, Float:z, Float:distance;
395 GetDynamicObjectPos(objectid, x, y, z);
396 for(new i; i < MAX_VEHICLES; i++)
397 {
398 if(IsValidVehicle(i))
399 {
400 distance = GetVehicleDistanceFromPoint(i, x, y, z);
401 if(distance <= 6)
402 {
403 vid = i;
404 break;
405 }
406 }
407 }
408 return vid;
409}