Hakoza
Member-
Content Count
2 -
Joined
-
Last visited
-
Medals
Community Reputation
0 NeutralAbout Hakoza
-
Rank
Newbie
Profile Information
-
Gender
Male
-
Location
Croatia
-
Interests
Fitness, electronics, mechanics and playing guitar
-
Variable ticket system (Solved!)
Hakoza replied to Hakoza's topic in ARMA 3 - MISSION EDITING & SCRIPTING
I have approached this problem from totally wrong side. Whole script should be done on server side. Everything that has to do with multiple clients is server side business. There is no need for functions or database also. See below initServer.sqf //Variable ticket system by Hakoza (V2) addMissionEventHandler ["EntityRespawned", { params ["_newEntity", "_oldEntity"]; if (isPlayer _newEntity) then { private _sideRespawned = side _newEntity; private _uid = getPlayerUID _newEntity; // Get player's UID // Retrieve the last respawned side, or set it to the deafult east side if not already set private _lastRespawnedSide = missionNamespace getVariable [_uid + "lastRespawnedSide", east]; private _ticket = _oldEntity getVariable ["_ticket", false]; private _sideChanged = false; //Add or subtract tickets based on player side if (_sideRespawned == east && _lastRespawnedSide == west && !_ticket) then { [west, 1] call BIS_fnc_respawnTickets; _sideChanged = true; _ticket = true; } else { if (_sideRespawned == west && _lastRespawnedSide == east && !_ticket) then { [west, -1] call BIS_fnc_respawnTickets; _sideChanged = true; _ticket = true; }; }; if (_sideChanged) then { _newEntity setVariable ["_ticket", _ticket, false]; }; missionNamespace setVariable [_uid + "lastRespawnedSide", _sideRespawned]; // Store the new value based on UID }; }]; // Return lost ticket upon disconnect addMissionEventHandler ["HandleDisconnect", { params ["_body", "_id", "_uid", "_name"]; private "_lastRespawnedSide"; _lastRespawnedSide = missionNamespace getVariable [_uid + "lastRespawnedSide", east]; if (_lastRespawnedSide == west) then { [west, 1] call BIS_fnc_respawnTickets; }; // Set _lastRespawnedSide to nil in the missionNamespace missionNamespace setVariable [_uid + "lastRespawnedSide", nil]; }]; Enjoy 🙂 -
Hakoza started following Variable ticket system (Solved!)
-
Hello people, I have been struggling to make a working custom ticket system for my mission. My goal is to have a maximum of 7 global west tickets as I have 7 available player slots. To make it more fair, I want one ticket to subtract from west side every time a new player respawns on west side, but not when they respawn again. Server should keep track of tickets subtracted and add ticket back if player chooses to change sides to east or if he disconnects the server from the west side. My guess is, i have trouble making database work... Now I don't have any real coding experience and this is my idea of the code which I heavily edited multiple times using logic and ChatGPT: onPlayerRespawn.sqf // Variable ticket system private _uid = getPlayerUID player; // Retrieve player data private _playerData = [_uid] call TAG_fnc_retrievePlayerData; private _tempSideRespawned = side player; private _tempAlreadyRespawnedAsEast; private _tempHasReturnedTicket; private _lastRespawnedSide = profileNamespace getVariable ["lastRespawnedSide", east]; if (!isNull _playerData) then { _tempAlreadyRespawnedAsEast = _playerData select 1; _tempHasReturnedTicket = _playerData select 2; } else { _tempAlreadyRespawnedAsEast = false; _tempHasReturnedTicket = false; }; // Handle ticket decrement and increment based on the respawned side if (_tempSideRespawned == east && _tempSideRespawned != _lastRespawnedSide) then { [east, -1] call BIS_fnc_respawnTickets; _tempHasReturnedTicket = false; } else { if (_tempSideRespawned == west && _lastRespawnedSide == east && !_tempAlreadyRespawnedAsEast && !_tempHasReturnedTicket) then { [west, 1] call BIS_fnc_respawnTickets; _tempAlreadyRespawnedAsEast = true; _tempHasReturnedTicket = true; }; }; // Update the player's last respawned side private _lastRespawnedSide = _tempSideRespawned; profileNamespace setVariable ["lastRespawnedSide", _tempSideRespawned]; // Update the player's data in the database [_uid, [_tempSideRespawned, _tempAlreadyRespawnedAsEast, _tempHasReturnedTicket]] call TAG_fnc_storePlayerData; initServer.sqf execVM "Scripts\functions.sqf"; // Global array to store each player's data in the TAG_database if (isNil "TAG_database") then { TAG_database = []; }; // Event handler for player disconnect addMissionEventHandler ["PlayerDisconnected", { params ["_id", "_uid", "_name", "_jip", "_owner", "_idstr"]; // Get the player's data from TAG_database using UID private _playerData = [_uid] call TAG_fnc_retrievePlayerData; if (count _playerData > 0) then { private _side = _playerData select 0; private _hasReturnedTicket = _playerData select 2; if (_side == west && !_hasReturnedTicket) then { [west, 1] call BIS_fnc_respawnTickets; // Add one ticket to West side on the server diag_log "Ticket returned to West"; // Mark that the ticket has been returned for this player to prevent multiple returns [_uid, _side, true] call TAG_fnc_storePlayerData; }; }; // Remove the player's data from TAG_database upon disconnect TAG_database = TAG_database - [_uid]; }]; functions.sqf TAG_fnc_storePlayerData = { params ["_uid", "_data"]; private _playerIndex = -1; { if ((_x select 0) == _uid) then { _playerIndex = _forEachIndex; true } else { false }; } forEach TAG_database; if (_playerIndex < 0) then { TAG_database pushBack [_uid, _data]; } else { TAG_database set [_playerIndex, [_uid, _data]]; }; }; TAG_fnc_retrievePlayerData = { params ["_uid"]; private _playerIndex = -1; { if ((_x select 0) == _uid) then { _playerIndex = _forEachIndex; true } else { false }; } forEach TAG_database; if (_playerIndex >= 0) then { TAG_database select _playerIndex select 1; } else { []; }; }; TAG_fnc_getPlayerIndex = { params ["_uid"]; private _playerIndex = -1; { if ((_x select 0) == _uid) then { _playerIndex = _forEachIndex; true } else { false }; } forEach _database; _playerIndex; }; description.ext class CfgFunctions { class Anthill { class MissionFunctions { class fnc_startTimer { file = "Scripts\functions.sqf"; }; class fnc_stopTimer { file = "Scripts\functions.sqf"; }; class fnc_resetTimer { file = "Scripts\functions.sqf"; }; class fnc_checkEmptyServer { file = "Scripts\functions.sqf"; }; class fnc_missionTimer { file = "Scripts\functions.sqf"; }; class fnc_scheduleTimer { file = "Scripts\functions.sqf"; }; class TAG_fnc_storePlayerData { file = "Scripts\functions.sqf"; }; class TAG_fnc_retrievePlayerData { file = "Scripts\functions.sqf"; }; class TAG_fnc_getPlayerIndex { file = "Scripts\functions.sqf"; }; }; }; }; I have sorted all errors in RPT files, and I still can't manage to execute full onplayerrespawn.sqf... I don't know where is the problem or how else i can diagnose it beside diag_log which doens't always work. Thanks for insights