· 6 years ago · Oct 29, 2019, 10:58 PM
1#define FILTERSCRIPT
2#include <a_samp>
3#include <zcmd> // by Yashas - http://forum.sa-mp.com/showthread.php?t=576114
4#include <sqlite> // by Slice - http://forum.sa-mp.com/showthread.php?t=303682
5#include <streamer> // by Incognito - http://forum.sa-mp.com/showthread.php?t=102865
6#include <YSIy_iterate> // by Y_Less - http://forum.sa-mp.com/showthread.php?t=570884
7
8#define MAX_SAFES (25)
9#define MAX_NUMBER (15)
10
11#define SAFE_TIME (120)
12#define SAFE_MONEY_MIN (1500)
13#define SAFE_MONEY_MAX (2500)
14
15enum E_SAFE
16{
17 // from db
18 Float: SafeX,
19 Float: SafeY,
20 Float: SafeZ,
21 Float: SafeRot,
22 // temp
23 SafeOccupiedBy,
24 SafeMoney,
25 SafeNumbers[3],
26 bool: SafeLocks[3],
27 SafeObject,
28 Text3D: SafeLabel,
29 // timer
30 SafeTimeLeft,
31 SafeTimer
32}
33
34new
35 DiffColors[] = {0xA6A6A6FF, 0xBFBFBFFF};
36 // index 0(first color) is the number itself
37
38new
39 SafeData[MAX_SAFES][E_SAFE],
40 Iterator: Safes<MAX_SAFES>;
41
42new
43 DB: SafeDatabase,
44 DBStatement: LoadSafes,
45 DBStatement: AddSafe,
46 DBStatement: UpdateSafe,
47 DBStatement: RemoveSafe;
48
49new
50 CrackingSafeID[MAX_PLAYERS] = {-1, ...},
51 EditingSafeID[MAX_PLAYERS] = {-1, ...},
52 CurSafeNumber[MAX_PLAYERS] = {0, ...};
53
54new
55 Text: tdSafeCrackingBG,
56 Text: tdSafeCrackingTitleBG,
57 Text: tdSafeCrackingTitle,
58 Text: tdSafeCrackingPrev,
59 Text: tdSafeCrackingNext,
60 Text: tdSafeCrackingTry;
61
62new
63 PlayerText: tdSafeNumber[MAX_PLAYERS][3],
64 PlayerText: tdSafeLock[MAX_PLAYERS][3];
65
66RandomEx(min, max) //Y_Less
67 return random(max - min) + min;
68
69ConvertToMinutes(time)
70{
71 // http://forum.sa-mp.com/showpost.php?p=3223897&postcount=11
72 new string[15];//-2000000000:00 could happen, so make the string 15 chars to avoid any errors
73 format(string, sizeof(string), "%02d:%02d", time / 60, time % 60);
74 return string;
75}
76
77formatInt(intVariable, iThousandSeparator = ',', iCurrencyChar = '$')
78{
79 /*
80 By Kar
81 https://gist.github.com/Kar2k/bfb0eafb2caf71a1237b349684e091b9/8849dad7baa863afb1048f40badd103567c005a5#file-formatint-function
82 */
83 static
84 s_szReturn[ 32 ],
85 s_szThousandSeparator[ 2 ] = { ' ', EOS },
86 s_szCurrencyChar[ 2 ] = { ' ', EOS },
87 s_iVariableLen,
88 s_iChar,
89 s_iSepPos,
90 bool:s_isNegative
91 ;
92
93 format( s_szReturn, sizeof( s_szReturn ), "%d", intVariable );
94
95 if(s_szReturn[0] == '-')
96 s_isNegative = true;
97 else
98 s_isNegative = false;
99
100 s_iVariableLen = strlen( s_szReturn );
101
102 if ( s_iVariableLen >= 4 && iThousandSeparator)
103 {
104 s_szThousandSeparator[ 0 ] = iThousandSeparator;
105
106 s_iChar = s_iVariableLen;
107 s_iSepPos = 0;
108
109 while ( --s_iChar > _:s_isNegative )
110 {
111 if ( ++s_iSepPos == 3 )
112 {
113 strins( s_szReturn, s_szThousandSeparator, s_iChar );
114
115 s_iSepPos = 0;
116 }
117 }
118 }
119 if(iCurrencyChar) {
120 s_szCurrencyChar[ 0 ] = iCurrencyChar;
121 strins( s_szReturn, s_szCurrencyChar, _:s_isNegative );
122 }
123 return s_szReturn;
124}
125
126Float: AngleToPoint(Float: X1, Float: Y1, Float: X2, Float: Y2) // By Nero_3D
127 return atan((Y2 - Y1) / (X2 - X1)) + ((X2 < X1) ? 90 : 270);
128
129SafeCracking_GetLockIndex(id)
130{
131 if(!Iter_Contains(Safes, id)) return -2;
132 for(new i; i < 3; i++) if(!SafeData[id][SafeLocks][i]) return i;
133 return -1;
134}
135
136SafeCracking_GetLockNumber(id)
137{
138 if(!Iter_Contains(Safes, id)) return -2;
139 for(new i; i < 3; i++) if(!SafeData[id][SafeLocks][i]) return SafeData[id][SafeNumbers][i];
140 return -1;
141}
142
143SafeCracking_InitPlayer(playerid)
144{
145 // variables
146 CrackingSafeID[playerid] = EditingSafeID[playerid] = -1;
147 CurSafeNumber[playerid] = 0;
148
149 // textdraws
150 tdSafeNumber[playerid][0] = CreatePlayerTextDraw(playerid, 277.000000, 338.000000, "_");
151 PlayerTextDrawBackgroundColor(playerid, tdSafeNumber[playerid][0], 255);
152 PlayerTextDrawFont(playerid, tdSafeNumber[playerid][0], 3);
153 PlayerTextDrawLetterSize(playerid, tdSafeNumber[playerid][0], 0.409999, 2.000000);
154 PlayerTextDrawColor(playerid, tdSafeNumber[playerid][0], -1);
155 PlayerTextDrawSetOutline(playerid, tdSafeNumber[playerid][0], 1);
156 PlayerTextDrawSetProportional(playerid, tdSafeNumber[playerid][0], 1);
157 PlayerTextDrawSetSelectable(playerid, tdSafeNumber[playerid][0], 0);
158
159 tdSafeNumber[playerid][1] = CreatePlayerTextDraw(playerid, 317.000000, 334.000000, "_");
160 PlayerTextDrawAlignment(playerid, tdSafeNumber[playerid][1], 2);
161 PlayerTextDrawBackgroundColor(playerid, tdSafeNumber[playerid][1], 255);
162 PlayerTextDrawFont(playerid, tdSafeNumber[playerid][1], 3);
163 PlayerTextDrawLetterSize(playerid, tdSafeNumber[playerid][1], 0.409999, 2.000000);
164 PlayerTextDrawColor(playerid, tdSafeNumber[playerid][1], -1);
165 PlayerTextDrawSetOutline(playerid, tdSafeNumber[playerid][1], 1);
166 PlayerTextDrawSetProportional(playerid, tdSafeNumber[playerid][1], 1);
167 PlayerTextDrawSetSelectable(playerid, tdSafeNumber[playerid][1], 0);
168
169 tdSafeNumber[playerid][2] = CreatePlayerTextDraw(playerid, 357.000000, 338.000000, "_");
170 PlayerTextDrawAlignment(playerid, tdSafeNumber[playerid][2], 3);
171 PlayerTextDrawBackgroundColor(playerid, tdSafeNumber[playerid][2], 255);
172 PlayerTextDrawFont(playerid, tdSafeNumber[playerid][2], 3);
173 PlayerTextDrawLetterSize(playerid, tdSafeNumber[playerid][2], 0.409999, 2.000000);
174 PlayerTextDrawColor(playerid, tdSafeNumber[playerid][2], -1);
175 PlayerTextDrawSetOutline(playerid, tdSafeNumber[playerid][2], 1);
176 PlayerTextDrawSetProportional(playerid, tdSafeNumber[playerid][2], 1);
177 PlayerTextDrawSetSelectable(playerid, tdSafeNumber[playerid][2], 0);
178
179 tdSafeLock[playerid][0] = CreatePlayerTextDraw(playerid, 267.000000, 362.000000, "_");
180 PlayerTextDrawBackgroundColor(playerid, tdSafeLock[playerid][0], 0);
181 PlayerTextDrawFont(playerid, tdSafeLock[playerid][0], 5);
182 PlayerTextDrawLetterSize(playerid, tdSafeLock[playerid][0], 0.0, 0.0);
183 PlayerTextDrawColor(playerid, tdSafeLock[playerid][0], 0xE74C3CFF);
184 PlayerTextDrawSetOutline(playerid, tdSafeLock[playerid][0], 1);
185 PlayerTextDrawSetProportional(playerid, tdSafeLock[playerid][0], 1);
186 PlayerTextDrawUseBox(playerid, tdSafeLock[playerid][0], 1);
187 PlayerTextDrawBoxColor(playerid, tdSafeLock[playerid][0], 0);
188 PlayerTextDrawTextSize(playerid, tdSafeLock[playerid][0], 20.000000, 20.000000);
189 PlayerTextDrawSetPreviewModel(playerid, tdSafeLock[playerid][0], 19804);
190 PlayerTextDrawSetPreviewRot(playerid, tdSafeLock[playerid][0], 0.000000, 0.000000, 0.000000, 0.65);
191 PlayerTextDrawSetSelectable(playerid, tdSafeLock[playerid][0], 0);
192
193 tdSafeLock[playerid][1] = CreatePlayerTextDraw(playerid, 307.000000, 362.000000, "_");
194 PlayerTextDrawBackgroundColor(playerid, tdSafeLock[playerid][1], 0);
195 PlayerTextDrawFont(playerid, tdSafeLock[playerid][1], 5);
196 PlayerTextDrawLetterSize(playerid, tdSafeLock[playerid][1], 0.0, 0.0);
197 PlayerTextDrawColor(playerid, tdSafeLock[playerid][1], 0xE74C3CFF);
198 PlayerTextDrawSetOutline(playerid, tdSafeLock[playerid][1], 1);
199 PlayerTextDrawSetProportional(playerid, tdSafeLock[playerid][1], 1);
200 PlayerTextDrawUseBox(playerid, tdSafeLock[playerid][1], 1);
201 PlayerTextDrawBoxColor(playerid, tdSafeLock[playerid][1], 0);
202 PlayerTextDrawTextSize(playerid, tdSafeLock[playerid][1], 20.000000, 20.000000);
203 PlayerTextDrawSetPreviewModel(playerid, tdSafeLock[playerid][1], 19804);
204 PlayerTextDrawSetPreviewRot(playerid, tdSafeLock[playerid][1], 0.000000, 0.000000, 0.000000, 0.65);
205 PlayerTextDrawSetSelectable(playerid, tdSafeLock[playerid][1], 0);
206
207 tdSafeLock[playerid][2] = CreatePlayerTextDraw(playerid, 347.000000, 362.000000, "_");
208 PlayerTextDrawBackgroundColor(playerid, tdSafeLock[playerid][2], 0);
209 PlayerTextDrawFont(playerid, tdSafeLock[playerid][2], 5);
210 PlayerTextDrawLetterSize(playerid, tdSafeLock[playerid][2], 0.0, 0.0);
211 PlayerTextDrawColor(playerid, tdSafeLock[playerid][2], 0xE74C3CFF);
212 PlayerTextDrawSetOutline(playerid, tdSafeLock[playerid][2], 1);
213 PlayerTextDrawSetProportional(playerid, tdSafeLock[playerid][2], 1);
214 PlayerTextDrawUseBox(playerid, tdSafeLock[playerid][2], 1);
215 PlayerTextDrawBoxColor(playerid, tdSafeLock[playerid][2], 0);
216 PlayerTextDrawTextSize(playerid, tdSafeLock[playerid][2], 20.000000, 20.000000);
217 PlayerTextDrawSetPreviewModel(playerid, tdSafeLock[playerid][2], 19804);
218 PlayerTextDrawSetPreviewRot(playerid, tdSafeLock[playerid][2], 0.000000, 0.000000, 0.000000, 0.65);
219 PlayerTextDrawSetSelectable(playerid, tdSafeLock[playerid][2], 0);
220
221 // preload anim lib
222 ApplyAnimation(playerid, "COP_AMBIENT", "null", 0.0, 0, 0, 0, 0, 0);
223 return 1;
224}
225
226SafeCracking_SetUIState(playerid, show, nocancel = 0)
227{
228 if(show) {
229 TextDrawShowForPlayer(playerid, tdSafeCrackingBG);
230 TextDrawShowForPlayer(playerid, tdSafeCrackingTitleBG);
231 TextDrawShowForPlayer(playerid, tdSafeCrackingTitle);
232 TextDrawShowForPlayer(playerid, tdSafeCrackingPrev);
233 TextDrawShowForPlayer(playerid, tdSafeCrackingNext);
234 TextDrawShowForPlayer(playerid, tdSafeCrackingTry);
235
236 for(new i; i < 3; i++)
237 {
238 PlayerTextDrawShow(playerid, tdSafeNumber[playerid][i]);
239 PlayerTextDrawShow(playerid, tdSafeLock[playerid][i]);
240 }
241
242 SafeCracking_SetNumber(playerid, 0);
243 SafeCracking_UpdateLocks(playerid);
244 SelectTextDraw(playerid, 0x03A9F4FF);
245 }else{
246 TextDrawHideForPlayer(playerid, tdSafeCrackingBG);
247 TextDrawHideForPlayer(playerid, tdSafeCrackingTitleBG);
248 TextDrawHideForPlayer(playerid, tdSafeCrackingTitle);
249 TextDrawHideForPlayer(playerid, tdSafeCrackingPrev);
250 TextDrawHideForPlayer(playerid, tdSafeCrackingNext);
251 TextDrawHideForPlayer(playerid, tdSafeCrackingTry);
252
253 for(new i; i < 3; i++)
254 {
255 PlayerTextDrawHide(playerid, tdSafeNumber[playerid][i]);
256 PlayerTextDrawHide(playerid, tdSafeLock[playerid][i]);
257 }
258
259 if(!nocancel) CancelSelectTextDraw(playerid);
260 }
261
262 return 1;
263}
264
265SafeCracking_SetNumber(playerid, number)
266{
267 CurSafeNumber[playerid] = number;
268
269 new string[4], value, difference, actual_number = SafeCracking_GetLockNumber(CrackingSafeID[playerid]);
270 for(new i; i < 3; i++)
271 {
272 // probably spaghetti
273 switch(i)
274 {
275 case 0:
276 {
277 // left
278 value = number - 1;
279 if(value < 0) value = MAX_NUMBER;
280 }
281
282 case 1:
283 {
284 // middle
285 value = number;
286 }
287
288 case 2:
289 {
290 // right
291 value = number + 1;
292 if(value > MAX_NUMBER) value = 0;
293 }
294 }
295
296 // current number
297 format(string, sizeof(string), "%02d", value);
298 PlayerTextDrawSetString(playerid, tdSafeNumber[playerid][i], string);
299
300 // difference to safe lock number
301 difference = floatround(floatabs(value - actual_number));
302 if(difference < sizeof(DiffColors)) {
303 PlayerTextDrawColor(playerid, tdSafeNumber[playerid][i], DiffColors[difference]);
304 }else{
305 PlayerTextDrawColor(playerid, tdSafeNumber[playerid][i], -1);
306 }
307
308 // show td again
309 PlayerTextDrawShow(playerid, tdSafeNumber[playerid][i]);
310 }
311
312 return 1;
313}
314
315SafeCracking_UpdateLocks(playerid)
316{
317 if(Iter_Contains(Safes, CrackingSafeID[playerid]))
318 {
319 for(new i; i < 3; i++)
320 {
321 PlayerTextDrawColor(playerid, tdSafeLock[playerid][i], (SafeData[ CrackingSafeID[playerid] ][SafeLocks][i]) ? 0x2ECC71FF : 0xE74C3CFF);
322 PlayerTextDrawShow(playerid, tdSafeLock[playerid][i]);
323 }
324 }
325
326 return 1;
327}
328
329SafeCracking_ResetPlayer(playerid, nocancel = 0)
330{
331 if(Iter_Contains(Safes, CrackingSafeID[playerid])) SafeData[ CrackingSafeID[playerid] ][SafeOccupiedBy] = -1;
332 if(!IsPlayerInAnyVehicle(playerid)) ClearAnimations(playerid);
333 SafeCracking_SetUIState(playerid, 0, nocancel);
334
335 CrackingSafeID[playerid] = -1;
336 CurSafeNumber[playerid] = 0;
337 return 1;
338}
339
340SafeCracking_UnlockSafe(id)
341{
342 if(!Iter_Contains(Safes, id)) return -1;
343 Streamer_SetIntData(STREAMER_TYPE_OBJECT, SafeData[id][SafeObject], E_STREAMER_MODEL_ID, 1829);
344 SetDynamicObjectMaterial(SafeData[id][SafeObject], 1, 19478, "signsurf", "sign", 0xFFFFFFFF);
345
346 SafeData[id][SafeOccupiedBy] = -1;
347 SafeData[id][SafeMoney] = RandomEx(SAFE_MONEY_MIN, SAFE_MONEY_MAX);
348 SafeData[id][SafeTimeLeft] = SAFE_TIME;
349
350 new label[128];
351 format(label, sizeof(label), "Sejf(%d)\n\n{FFFFFF}Naciśnij {F1C40F}~k~~CONVERSATION_YES~ {FFFFFF}aby okraść {2ECC71}%s.\n{E74C3C}Rozkodowywany Sejf (%s)", id, formatInt(SafeData[id][SafeMoney]), ConvertToMinutes(SafeData[id][SafeTimeLeft]));
352 UpdateDynamic3DTextLabelText(SafeData[id][SafeLabel], 0xF1C40FFF, label);
353
354 SafeData[id][SafeTimer] = SetTimerEx("Safe_Lock", 1000, true, "i", id);
355 return 1;
356}
357
358GetClosestSafe(playerid, Float: range = 2.0)
359{
360 new id = -1, Float: dist = range, Float: tempdist;
361 foreach(new i : Safes)
362 {
363 tempdist = GetPlayerDistanceFromPoint(playerid, SafeData[i][SafeX], SafeData[i][SafeY], SafeData[i][SafeZ]);
364
365 if(tempdist > range) continue;
366 if(tempdist <= dist)
367 {
368 dist = tempdist;
369 id = i;
370 }
371 }
372
373 return id;
374}
375
376forward Safe_Lock(id);
377public Safe_Lock(id)
378{
379 new label[128];
380 if(SafeData[id][SafeTimeLeft] > 1) {
381 SafeData[id][SafeTimeLeft]--;
382
383 if(!SafeData[id][SafeMoney]) {
384 format(label, sizeof(label), "Sejf(%d)\n\n{E74C3C}Rozkodowywanie (%s)", id, ConvertToMinutes(SafeData[id][SafeTimeLeft]));
385 }else{
386 format(label, sizeof(label), "Sejf(%d)\n\n{FFFFFF}Naciśnij {F1C40F}~k~~CONVERSATION_YES~ {FFFFFF}aby ukraść {2ECC71}%s.\n{E74C3C}Rozkodowywany Sejf (%s)", id, formatInt(SafeData[id][SafeMoney]), ConvertToMinutes(SafeData[id][SafeTimeLeft]));
387 }
388
389 UpdateDynamic3DTextLabelText(SafeData[id][SafeLabel], 0xF1C40FFF, label);
390 }else if(SafeData[id][SafeTimeLeft] == 1) {
391 for(new i; i < 3; i++)
392 {
393 SafeData[id][SafeNumbers][i] = RandomEx(0, MAX_NUMBER);
394 SafeData[id][SafeLocks][i] = false;
395 }
396
397 KillTimer(SafeData[id][SafeTimer]);
398 SafeData[id][SafeTimer] = -1;
399
400 DestroyDynamicObject(SafeData[id][SafeObject]);
401 SafeData[id][SafeObject] = CreateDynamicObject(2332, SafeData[id][SafeX], SafeData[id][SafeY], SafeData[id][SafeZ], 0.0, 0.0, SafeData[id][SafeRot]);
402
403 format(label, sizeof(label), "Sejf(%d)\n\n{FFFFFF}Naciśnijj {F1C40F}~k~~CONVERSATION_NO~ {FFFFFF}aby ukraść.\n{2ECC71}Rozkodowywany Sejf", id);
404 UpdateDynamic3DTextLabelText(SafeData[id][SafeLabel], 0xF1C40FFF, label);
405 }
406
407 return 1;
408}
409
410public OnFilterScriptInit()
411{
412 // reset variables
413 for(new i; i < MAX_SAFES; i++)
414 {
415 SafeData[i][SafeOccupiedBy] = SafeData[i][SafeObject] = SafeData[i][SafeTimer] = -1;
416 SafeData[i][SafeLabel] = Text3D: -1;
417
418 for(new x; x < 3; x++) SafeData[i][SafeNumbers][x] = SafeData[i][SafeLocks][x] = !!0;
419 }
420
421 // create textdraws
422 tdSafeCrackingBG = TextDrawCreate(235.000000, 320.000000, "_");
423 TextDrawBackgroundColor(tdSafeCrackingBG, 255);
424 TextDrawFont(tdSafeCrackingBG, 1);
425 TextDrawLetterSize(tdSafeCrackingBG, 0.500000, 7.000000);
426 TextDrawColor(tdSafeCrackingBG, -1);
427 TextDrawSetOutline(tdSafeCrackingBG, 0);
428 TextDrawSetProportional(tdSafeCrackingBG, 1);
429 TextDrawSetShadow(tdSafeCrackingBG, 1);
430 TextDrawUseBox(tdSafeCrackingBG, 1);
431 TextDrawBoxColor(tdSafeCrackingBG, 168430200);
432 TextDrawTextSize(tdSafeCrackingBG, 401.000000, 0.000000);
433 TextDrawSetSelectable(tdSafeCrackingBG, 0);
434
435 tdSafeCrackingTitleBG = TextDrawCreate(235.000000, 320.000000, "_");
436 TextDrawBackgroundColor(tdSafeCrackingTitleBG, 255);
437 TextDrawFont(tdSafeCrackingTitleBG, 1);
438 TextDrawLetterSize(tdSafeCrackingTitleBG, 0.270000, 1.400000);
439 TextDrawColor(tdSafeCrackingTitleBG, -1);
440 TextDrawSetOutline(tdSafeCrackingTitleBG, 1);
441 TextDrawSetProportional(tdSafeCrackingTitleBG, 1);
442 TextDrawUseBox(tdSafeCrackingTitleBG, 1);
443 TextDrawBoxColor(tdSafeCrackingTitleBG, 168430335);
444 TextDrawTextSize(tdSafeCrackingTitleBG, 401.000000, 0.000000);
445 TextDrawSetSelectable(tdSafeCrackingTitleBG, 0);
446
447 tdSafeCrackingTitle = TextDrawCreate(237.000000, 321.000000, "Rozkodowywanie Sejfu");
448 TextDrawBackgroundColor(tdSafeCrackingTitle, 255);
449 TextDrawFont(tdSafeCrackingTitle, 2);
450 TextDrawLetterSize(tdSafeCrackingTitle, 0.200000, 1.100000);
451 TextDrawColor(tdSafeCrackingTitle, -1);
452 TextDrawSetOutline(tdSafeCrackingTitle, 1);
453 TextDrawSetProportional(tdSafeCrackingTitle, 1);
454 TextDrawSetSelectable(tdSafeCrackingTitle, 0);
455
456 tdSafeCrackingPrev = TextDrawCreate(240.000000, 340.000000, "LD_BEAT:left");
457 TextDrawBackgroundColor(tdSafeCrackingPrev, 255);
458 TextDrawFont(tdSafeCrackingPrev, 4);
459 TextDrawLetterSize(tdSafeCrackingPrev, 0.200000, 1.100000);
460 TextDrawColor(tdSafeCrackingPrev, -1);
461 TextDrawSetOutline(tdSafeCrackingPrev, 1);
462 TextDrawSetProportional(tdSafeCrackingPrev, 1);
463 TextDrawUseBox(tdSafeCrackingPrev, 1);
464 TextDrawBoxColor(tdSafeCrackingPrev, 255);
465 TextDrawTextSize(tdSafeCrackingPrev, 16.000000, 16.000000);
466 TextDrawSetSelectable(tdSafeCrackingPrev, 1);
467
468 tdSafeCrackingNext = TextDrawCreate(380.000000, 340.000000, "LD_BEAT:right");
469 TextDrawBackgroundColor(tdSafeCrackingNext, 255);
470 TextDrawFont(tdSafeCrackingNext, 4);
471 TextDrawLetterSize(tdSafeCrackingNext, 0.200000, 1.100000);
472 TextDrawColor(tdSafeCrackingNext, -1);
473 TextDrawSetOutline(tdSafeCrackingNext, 1);
474 TextDrawSetProportional(tdSafeCrackingNext, 1);
475 TextDrawUseBox(tdSafeCrackingNext, 1);
476 TextDrawBoxColor(tdSafeCrackingNext, 255);
477 TextDrawTextSize(tdSafeCrackingNext, 16.000000, 16.000000);
478 TextDrawSetSelectable(tdSafeCrackingNext, 1);
479
480 tdSafeCrackingTry = TextDrawCreate(379.000000, 321.000000, " Próba");
481 TextDrawBackgroundColor(tdSafeCrackingTry, 255);
482 TextDrawFont(tdSafeCrackingTry, 2);
483 TextDrawLetterSize(tdSafeCrackingTry, 0.200000, 1.100000);
484 TextDrawColor(tdSafeCrackingTry, -1);
485 TextDrawSetOutline(tdSafeCrackingTry, 1);
486 TextDrawSetProportional(tdSafeCrackingTry, 1);
487 TextDrawUseBox(tdSafeCrackingTry, 1);
488 TextDrawBoxColor(tdSafeCrackingTry, -872414977);
489 TextDrawTextSize(tdSafeCrackingTry, 400.000000, 10.000000);
490 TextDrawSetSelectable(tdSafeCrackingTry, 1);
491
492 // create player textdraws
493 for(new i, max_players = GetPlayerPoolSize(); i <= max_players; i++) if(IsPlayerConnected(i)) SafeCracking_InitPlayer(i);
494
495 // database
496 SafeDatabase = db_open("safe_db.db");
497 db_query(SafeDatabase, "CREATE TABLE IF NOT EXISTS safes (ID INTEGER, PosX FLOAT, PosY FLOAT, PosZ FLOAT, Rotation FLOAT)");
498
499 // prepare queries
500 LoadSafes = db_prepare(SafeDatabase, "SELECT * FROM safes");
501 AddSafe = db_prepare(SafeDatabase, "INSERT INTO safes (ID, PosX, PosY, PosZ, Rotation) VALUES (?, ?, ?, ?, ?)");
502 UpdateSafe = db_prepare(SafeDatabase, "UPDATE safes SET PosX=?, PosY=?, PosZ=?, Rotation=? WHERE ID=?");
503 RemoveSafe = db_prepare(SafeDatabase, "DELETE FROM safes WHERE ID=?");
504
505 // load safes
506 new id, Float: x, Float: y, Float: z, Float: rot;
507 stmt_bind_result_field(LoadSafes, 0, DB::TYPE_INTEGER, id);
508 stmt_bind_result_field(LoadSafes, 1, DB::TYPE_FLOAT, x);
509 stmt_bind_result_field(LoadSafes, 2, DB::TYPE_FLOAT, y);
510 stmt_bind_result_field(LoadSafes, 3, DB::TYPE_FLOAT, z);
511 stmt_bind_result_field(LoadSafes, 4, DB::TYPE_FLOAT, rot);
512
513 if(stmt_execute(LoadSafes))
514 {
515 new label[96], loaded;
516 while(stmt_fetch_row(LoadSafes))
517 {
518 SafeData[id][SafeX] = x;
519 SafeData[id][SafeY] = y;
520 SafeData[id][SafeZ] = z;
521 SafeData[id][SafeRot] = rot;
522 for(new i; i < 3; i++) SafeData[id][SafeNumbers][i] = RandomEx(0, MAX_NUMBER);
523
524 SafeData[id][SafeObject] = CreateDynamicObject(2332, SafeData[id][SafeX], SafeData[id][SafeY], SafeData[id][SafeZ], 0.0, 0.0, SafeData[id][SafeRot]);
525
526 format(label, sizeof(label), "Sejf(%d)\n\n{FFFFFF}Naciśnij {F1C40F}~k~~CONVERSATION_NO~ {FFFFFF}aby ukraść.\n{2ECC71}Rozkodowywany Sejf", id);
527 SafeData[id][SafeLabel] = CreateDynamic3DTextLabel(label, 0xF1C40FFF, SafeData[id][SafeX], SafeData[id][SafeY], SafeData[id][SafeZ] + 0.8, 10.0, .testlos = 1);
528
529 Iter_Add(Safes, id);
530 loaded++;
531 }
532
533 printf("Załadowano %d sejfów.", loaded);
534 }
535
536 return 1;
537}
538
539public OnFilterScriptExit()
540{
541 for(new i, max_players = GetPlayerPoolSize(); i <= max_players; i++)
542 {
543 if(IsPlayerConnected(i))
544 {
545 SafeCracking_SetUIState(i, 0);
546
547 for(new x; x < 3; x++)
548 {
549 PlayerTextDrawDestroy(i, tdSafeNumber[i][x]);
550 PlayerTextDrawDestroy(i, tdSafeLock[i][x]);
551 }
552 }
553 }
554
555 TextDrawDestroy(tdSafeCrackingBG);
556 TextDrawDestroy(tdSafeCrackingTitleBG);
557 TextDrawDestroy(tdSafeCrackingTitle);
558 TextDrawDestroy(tdSafeCrackingPrev);
559 TextDrawDestroy(tdSafeCrackingNext);
560 TextDrawDestroy(tdSafeCrackingTry);
561
562 db_close(SafeDatabase);
563 return 1;
564}
565
566public OnPlayerConnect(playerid)
567{
568 SafeCracking_InitPlayer(playerid);
569 return 1;
570}
571
572public OnPlayerDisconnect(playerid, reason)
573{
574 SafeCracking_ResetPlayer(playerid, 1);
575 return 1;
576}
577
578public OnPlayerStateChange(playerid, newstate, oldstate)
579{
580 SafeCracking_ResetPlayer(playerid);
581 return 1;
582}
583
584public OnPlayerKeyStateChange(playerid, newkeys, oldkeys)
585{
586 if(GetPlayerState(playerid) == PLAYER_STATE_ONFOOT)
587 {
588 if(newkeys & KEY_NO)
589 {
590 // safe cracking
591 new id = GetClosestSafe(playerid);
592 if(id != -1)
593 {
594 if(IsPlayerConnected(SafeData[id][SafeOccupiedBy])) return SendClientMessage(playerid, 0xE74C3CFF, "BLAD: {FFFFFF}Ktoś› inny okrada ten sejf !");
595 if(Streamer_GetIntData(STREAMER_TYPE_OBJECT, SafeData[id][SafeObject], E_STREAMER_MODEL_ID) == 1829) return SendClientMessage(playerid, 0xE74C3CFF, "BLAD: {FFFFFF}Ten sejf jest już okradziony !");
596 SafeData[id][SafeOccupiedBy] = playerid;
597
598 CrackingSafeID[playerid] = id;
599 SafeCracking_SetUIState(playerid, 1);
600
601 new Float: x, Float: y, Float: z;
602 GetPlayerPos(playerid, x, y, z);
603 SetPlayerFacingAngle(playerid, AngleToPoint(x, y, SafeData[id][SafeX], SafeData[id][SafeY]));
604
605 ApplyAnimation(playerid, "COP_AMBIENT", "COPBROWSE_LOOP", 4.0, 1, 0, 0, 0, 0);
606 }
607
608 return 1;
609 }
610
611 if(newkeys & KEY_YES)
612 {
613 // money stealing
614 new id = GetClosestSafe(playerid);
615 if(id != -1)
616 {
617 if(Streamer_GetIntData(STREAMER_TYPE_OBJECT, SafeData[id][SafeObject], E_STREAMER_MODEL_ID) != 1829) return SendClientMessage(playerid, 0xE74C3CFF, "BLAD: {FFFFFF}Ten sejf nie jest obrobiony !");
618 if(!SafeData[id][SafeMoney]) return SendClientMessage(playerid, 0xE74C3CFF, "BLAD: {FFFFFF}Ten sejf jest pusty.");
619 GivePlayerMoney(playerid, SafeData[id][SafeMoney]);
620 SetDynamicObjectMaterial(SafeData[id][SafeObject], 2, 19478, "signsurf", "sign", 0xFFFFFFFF);
621
622 new label[40];
623 format(label, sizeof(label), "Sejf(%d)\n\n{E74C3C}Okradanie (%s)", id, ConvertToMinutes(SafeData[id][SafeTimeLeft]));
624 UpdateDynamic3DTextLabelText(SafeData[id][SafeLabel], 0xF1C40FFF, label);
625 Streamer_Update(playerid);
626
627 new string[64];
628 format(string, sizeof(string), "SEJF: {FFFFFF}Ukradłeś› {2ECC71}%s {FFFFFF}z tego sejfu !", formatInt(SafeData[id][SafeMoney]));
629 SendClientMessage(playerid, 0x3498DBFF, string);
630
631 SafeData[id][SafeMoney] = 0;
632 }
633
634 return 1;
635 }
636 }
637
638 return 1;
639}
640
641public OnPlayerClickTextDraw(playerid, Text:clickedid)
642{
643 if(clickedid == Text: INVALID_TEXT_DRAW) {
644 SafeCracking_ResetPlayer(playerid, 1);
645 return 1;
646 }else{
647 if(clickedid == tdSafeCrackingPrev)
648 {
649 SafeCracking_SetNumber(playerid, (CurSafeNumber[playerid] - 1 < 0) ? MAX_NUMBER : CurSafeNumber[playerid] - 1);
650 PlayerPlaySound(playerid, 17803, 0.0, 0.0, 0.0);
651 return 1;
652 }
653
654 if(clickedid == tdSafeCrackingNext)
655 {
656 SafeCracking_SetNumber(playerid, (CurSafeNumber[playerid] + 1 > MAX_NUMBER) ? 0 : CurSafeNumber[playerid] + 1);
657 PlayerPlaySound(playerid, 17803, 0.0, 0.0, 0.0);
658 return 1;
659 }
660
661 if(clickedid == tdSafeCrackingTry)
662 {
663 new id = CrackingSafeID[playerid];
664 if(id == -1) return SafeCracking_SetUIState(playerid, 0);
665 if(CurSafeNumber[playerid] == SafeCracking_GetLockNumber(id)) {
666 // correct number, open a lock/crack the safe if no locks left
667 new idx = SafeCracking_GetLockIndex(id);
668 if(idx == -1) {
669 SafeCracking_UnlockSafe(id);
670 SafeCracking_ResetPlayer(playerid);
671 Streamer_Update(playerid);
672 }else{
673 SafeData[id][SafeLocks][idx] = true;
674
675 // update textdraws
676 SafeCracking_UpdateLocks(playerid);
677
678 // reset number
679 SafeCracking_SetNumber(playerid, 0);
680
681 // lock check
682 if(SafeCracking_GetLockIndex(id) == -1)
683 {
684 SafeCracking_UnlockSafe(id);
685 SafeCracking_ResetPlayer(playerid);
686 Streamer_Update(playerid);
687 }
688 }
689
690 PlayerPlaySound(playerid, 1083, 0.0, 0.0, 0.0);
691 }else{
692 // incorrect number, reset locks
693 for(new i; i < 3; i++)
694 {
695 SafeData[id][SafeNumbers][i] = RandomEx(0, MAX_NUMBER);
696 SafeData[id][SafeLocks][i] = false;
697 }
698
699 SafeCracking_UpdateLocks(playerid);
700 SafeCracking_SetNumber(playerid, 0);
701
702 SendClientMessage(playerid, 0x3498DBFF, "SEJF: {FFFFFF}Zły kod ! Zmieniono kod na inny !");
703 PlayerPlaySound(playerid, 1085, 0.0, 0.0, 0.0);
704 }
705
706 return 1;
707 }
708 }
709
710 return 0;
711}
712
713public OnPlayerEditDynamicObject(playerid, objectid, response, Float: x, Float: y, Float: z, Float: rx, Float: ry, Float: rz)
714{
715 switch(response)
716 {
717 case EDIT_RESPONSE_CANCEL:
718 {
719 if((Streamer_GetIntData(STREAMER_TYPE_OBJECT, objectid, E_STREAMER_MODEL_ID) == 2332 || Streamer_GetIntData(STREAMER_TYPE_OBJECT, objectid, E_STREAMER_MODEL_ID) == 1829) && Iter_Contains(Safes, EditingSafeID[playerid]))
720 {
721 new id = EditingSafeID[playerid];
722 SetDynamicObjectPos(objectid, SafeData[id][SafeX], SafeData[id][SafeY], SafeData[id][SafeZ]);
723 SetDynamicObjectRot(objectid, 0.0, 0.0, SafeData[id][SafeRot]);
724
725 EditingSafeID[playerid] = -1;
726 }
727 }
728
729 case EDIT_RESPONSE_FINAL:
730 {
731 if((Streamer_GetIntData(STREAMER_TYPE_OBJECT, objectid, E_STREAMER_MODEL_ID) == 2332 || Streamer_GetIntData(STREAMER_TYPE_OBJECT, objectid, E_STREAMER_MODEL_ID) == 1829) && Iter_Contains(Safes, EditingSafeID[playerid]))
732 {
733 new id = EditingSafeID[playerid];
734 SafeData[id][SafeX] = x;
735 SafeData[id][SafeY] = y;
736 SafeData[id][SafeZ] = z;
737 SafeData[id][SafeRot] = rz;
738
739 Streamer_SetFloatData(STREAMER_TYPE_3D_TEXT_LABEL, SafeData[id][SafeLabel], E_STREAMER_X, SafeData[id][SafeX]);
740 Streamer_SetFloatData(STREAMER_TYPE_3D_TEXT_LABEL, SafeData[id][SafeLabel], E_STREAMER_Y, SafeData[id][SafeY]);
741 Streamer_SetFloatData(STREAMER_TYPE_3D_TEXT_LABEL, SafeData[id][SafeLabel], E_STREAMER_Z, SafeData[id][SafeZ] + 0.8);
742
743 SetDynamicObjectPos(objectid, SafeData[id][SafeX], SafeData[id][SafeY], SafeData[id][SafeZ]);
744 SetDynamicObjectRot(objectid, 0.0, 0.0, SafeData[id][SafeRot]);
745
746 // save to database
747 stmt_bind_value(UpdateSafe, 0, DB::TYPE_FLOAT, SafeData[id][SafeX]);
748 stmt_bind_value(UpdateSafe, 1, DB::TYPE_FLOAT, SafeData[id][SafeY]);
749 stmt_bind_value(UpdateSafe, 2, DB::TYPE_FLOAT, SafeData[id][SafeZ]);
750 stmt_bind_value(UpdateSafe, 3, DB::TYPE_FLOAT, SafeData[id][SafeRot]);
751 stmt_bind_value(UpdateSafe, 4, DB::TYPE_INTEGER, id);
752 stmt_execute(UpdateSafe);
753
754 EditingSafeID[playerid] = -1;
755 }
756 }
757 }
758
759 return 1;
760}
761
762CMD:stworzsejf(playerid, params[])
763{
764 if(!IsPlayerAdmin(playerid)) return SendClientMessage(playerid, 0xE74C3CFF, "BLAD: {FFFFFF}Tylko Admin może użyć tą komendę!");
765 new id = Iter_Free(Safes);
766 if(id == -1) return SendClientMessage(playerid, 0xE74C3CFF, "BLAD: {FFFFFF}Liczba sejfów osięgneła limit !.");
767 new Float: x, Float: y, Float: z, Float: a;
768 GetPlayerPos(playerid, x, y, z);
769 GetPlayerFacingAngle(playerid, a);
770
771 x += 1.5 * floatsin(-a, degrees);
772 y += 1.5 * floatcos(-a, degrees);
773 z -= 0.5;
774
775 SafeData[id][SafeX] = x;
776 SafeData[id][SafeY] = y;
777 SafeData[id][SafeZ] = z;
778 SafeData[id][SafeRot] = a;
779 SafeData[id][SafeOccupiedBy] = SafeData[id][SafeTimer] = -1;
780 SafeData[id][SafeMoney] = SafeData[id][SafeTimeLeft] = 0;
781
782 for(new i; i < 3; i++)
783 {
784 SafeData[id][SafeNumbers][i] = RandomEx(0, MAX_NUMBER);
785 SafeData[id][SafeLocks][i] = false;
786 }
787
788 SafeData[id][SafeObject] = CreateDynamicObject(2332, SafeData[id][SafeX], SafeData[id][SafeY], SafeData[id][SafeZ], 0.0, 0.0, SafeData[id][SafeRot]);
789
790 new label[96];
791 format(label, sizeof(label), "Sejf(%d)\n\n{FFFFFF}Naciśnij {F1C40F}~k~~CONVERSATION_NO~ {FFFFFF}aby ukraść.\n{2ECC71}Rozkodowywany Sejf", id);
792 SafeData[id][SafeLabel] = CreateDynamic3DTextLabel(label, 0xF1C40FFF, SafeData[id][SafeX], SafeData[id][SafeY], SafeData[id][SafeZ] + 0.8, 10.0, .testlos = 1);
793
794 Iter_Add(Safes, id);
795
796 EditingSafeID[playerid] = id;
797 EditDynamicObject(playerid, SafeData[id][SafeObject]);
798
799 // insert to database
800 stmt_bind_value(AddSafe, 0, DB::TYPE_INTEGER, id);
801 stmt_bind_value(AddSafe, 1, DB::TYPE_FLOAT, SafeData[id][SafeX]);
802 stmt_bind_value(AddSafe, 2, DB::TYPE_FLOAT, SafeData[id][SafeY]);
803 stmt_bind_value(AddSafe, 3, DB::TYPE_FLOAT, SafeData[id][SafeZ]);
804 stmt_bind_value(AddSafe, 4, DB::TYPE_FLOAT, SafeData[id][SafeRot]);
805 if(stmt_execute(AddSafe)) SendClientMessage(playerid, 0x3498DBFF, "SEJF: {FFFFFF}Sejf utworzony.");
806 return 1;
807}
808
809CMD:sejfkod(playerid, params[])
810{
811 // unethical af
812 if(!IsPlayerAdmin(playerid)) return SendClientMessage(playerid, 0xE74C3CFF, "BLAD: {FFFFFF}Tylko Admin może użyć tą komendę!");
813 if(isnull(params)) return SendClientMessage(playerid, 0xF39C12FF, "UŻYJ: {FFFFFF}/sejfkod [sejf ID]");
814 new id = strval(params);
815 if(!Iter_Contains(Safes, id)) return SendClientMessage(playerid, 0xE74C3CFF, "BLAD: {FFFFFF}Nie poprawne ID sejfu");
816 new string[128];
817 format(string, sizeof(string), "SEJF: {FFFFFF}Kod do sejfu(%d): {F1C40F}%02d %02d %02d", id, SafeData[id][SafeNumbers][0], SafeData[id][SafeNumbers][1], SafeData[id][SafeNumbers][2]);
818 SendClientMessage(playerid, 0x3498DBFF, string);
819 return 1;
820}
821
822CMD:edytujsejf(playerid, params[])
823{
824 if(!IsPlayerAdmin(playerid)) return SendClientMessage(playerid, 0xE74C3CFF, "BLAD: {FFFFFF}Tylko Admin może użyć tą komendę!");
825 if(isnull(params)) return SendClientMessage(playerid, 0xF39C12FF, "UŻYJ: {FFFFFF}/edytujsejf [sejf ID]");
826 new id = strval(params);
827 if(!Iter_Contains(Safes, id)) return SendClientMessage(playerid, 0xE74C3CFF, "BLAD: {FFFFFF}Nie poprawne ID sejfu.");
828 if(!Streamer_IsItemVisible(playerid, STREAMER_TYPE_OBJECT, SafeData[id][SafeObject])) return SendClientMessage(playerid, 0xE74C3CFF, "BLAD: {FFFFFF}Sejf, który chcesz edytować, musi być widoczny.");
829 EditingSafeID[playerid] = id;
830 EditDynamicObject(playerid, SafeData[id][SafeObject]);
831 return 1;
832}
833
834CMD:usunsejf(playerid, params[])
835{
836 if(!IsPlayerAdmin(playerid)) return SendClientMessage(playerid, 0xE74C3CFF, "BLAD: {FFFFFF}Tylko Admin może użyć tą komendę!");
837 if(isnull(params)) return SendClientMessage(playerid, 0xF39C12FF, "UŻYJ: {FFFFFF}/usunsejf [sejf ID]");
838 new id = strval(params);
839 if(!Iter_Contains(Safes, id)) return SendClientMessage(playerid, 0xE74C3CFF, "BLAD: {FFFFFF}Nie poprawne ID sejfu.");
840 // if there is someone cracking the specified safe, cancel their cracking
841 foreach(new i : Player) if(CrackingSafeID[i] == id) SafeCracking_ResetPlayer(i);
842
843 // destroy safe
844 DestroyDynamicObject(SafeData[id][SafeObject]);
845 DestroyDynamic3DTextLabel(SafeData[id][SafeLabel]);
846 if(SafeData[id][SafeTimer] != -1) KillTimer(SafeData[id][SafeTimer]);
847
848 // reset variables
849 SafeData[id][SafeOccupiedBy] = SafeData[id][SafeObject] = SafeData[id][SafeTimer] = -1;
850 SafeData[id][SafeLabel] = Text3D: -1;
851 SafeData[id][SafeMoney] = SafeData[id][SafeTimeLeft] = 0;
852 for(new x; x < 3; x++) SafeData[id][SafeNumbers][x] = SafeData[id][SafeLocks][x] = !!0;
853
854 Iter_Remove(Safes, id);
855
856 // delete from database
857 stmt_bind_value(RemoveSafe, 0, DB::TYPE_INTEGER, id);
858 if(stmt_execute(RemoveSafe)) SendClientMessage(playerid, 0x3498DBFF, "SEJF: {FFFFFF}Sejf usunięty.");
859 return 1;
860}