mirror of
https://github.com/EpochModTeam/DayZ-Epoch.git
synced 2025-12-14 12:12:34 +03:00
1.8.7 player_switchWeapon updates
This commit is contained in:
@@ -825,7 +825,7 @@ class RscDisplayGear {
|
|||||||
h = 0.174;
|
h = 0.174;
|
||||||
color[] = {1,1,1,0.5};
|
color[] = {1,1,1,0.5};
|
||||||
colorActive[] = {1,1,1,0.8};
|
colorActive[] = {1,1,1,0.8};
|
||||||
action = "[""gear""] call player_switchWeapon";
|
action = "0 call dz_fn_switchWeapon";
|
||||||
};
|
};
|
||||||
|
|
||||||
class Button2: RscActiveText {
|
class Button2: RscActiveText {
|
||||||
@@ -840,7 +840,7 @@ class RscDisplayGear {
|
|||||||
h = 0.174;
|
h = 0.174;
|
||||||
color[] = {1,1,1,0.5};
|
color[] = {1,1,1,0.5};
|
||||||
colorActive[] = {1,1,1,0.8};
|
colorActive[] = {1,1,1,0.8};
|
||||||
action = "[""gear""] call player_switchWeapon";
|
action = "0 call dz_fn_switchWeapon";
|
||||||
};
|
};
|
||||||
};
|
};
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -1,214 +1,281 @@
|
|||||||
private ["_event", "_onLadder", "_inVehicle", "_isOk", "_primary", "_current", "_rifle", "_pistol", "_melee"];
|
#include "\z\addons\dayz_code\util\mutex.hpp"
|
||||||
_event = if (count _this > 1) then { _this select 3 } else { _this select 0 };
|
#include "\z\addons\dayz_code\util\player.hpp"
|
||||||
|
|
||||||
_findRifle = {
|
#define BANDAID
|
||||||
private ["_return", "_primary"];
|
|
||||||
_return = "";
|
|
||||||
_primary = primaryWeapon player;
|
|
||||||
|
|
||||||
if (_primary != "") then {
|
#define TIMEOUT 2
|
||||||
if !(_primary in MeleeWeapons) then {
|
|
||||||
_return = _primary;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
if (dayz_onBack != "" && _return == "") then {
|
#define IS_PRIMARY(wpn) (getNumber (configFile >> "CfgWeapons" >> wpn >> "type") == 1)
|
||||||
if !(dayz_onBack in MeleeWeapons) then {
|
#define MELEE(wpn) getNumber (configFile >> "CfgWeapons" >> wpn >> "melee")
|
||||||
_return = dayz_onBack;
|
#define IS_MELEE(wpn) (MELEE(wpn) == 1)
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
_return;
|
//0 if not found, 1 if in primary slot, 2 if on back
|
||||||
};
|
#define FIND_RIFLE() (0 call dz_fn_switchWeapon_find)
|
||||||
|
#define FIND_MELEE() (1 call dz_fn_switchWeapon_find)
|
||||||
|
|
||||||
_findMelee = {
|
dz_switchWeapon_mutex = Mutex_New();
|
||||||
private ["_return", "_primary"];
|
|
||||||
_return = "";
|
|
||||||
|
|
||||||
_primary = primaryWeapon player;
|
//0: switch rifle/melee instantly and update gear
|
||||||
|
//1: switch rifle/melee with animation
|
||||||
if (_primary != "") then {
|
//2: switch to rifle
|
||||||
if (_primary in MeleeWeapons) then {
|
//3: switch to pistol
|
||||||
_return = _primary;
|
//4: switch to melee
|
||||||
};
|
dz_fn_switchWeapon =
|
||||||
};
|
{
|
||||||
|
if (vehicle player != player) exitWith {};
|
||||||
if (dayz_onBack != "" && _return == "") then {
|
if Player_IsOnLadder() exitWith {};
|
||||||
if (dayz_onBack in MeleeWeapons) then {
|
|
||||||
_return = dayz_onBack;
|
private ["_current", "_primary", "_secondary"];
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
_return;
|
|
||||||
};
|
|
||||||
|
|
||||||
_findPistol = {
|
|
||||||
private ["_return"];
|
|
||||||
_return = "";
|
|
||||||
|
|
||||||
{
|
|
||||||
if (getNumber (configFile >> "CfgWeapons" >> _x >> "type") == 2) then {
|
|
||||||
_return = _x;
|
|
||||||
};
|
|
||||||
} foreach (weapons player);
|
|
||||||
|
|
||||||
_return;
|
|
||||||
};
|
|
||||||
|
|
||||||
_selectMuzzle = {
|
|
||||||
private ["_return", "_wpn", "_muzzles"];
|
|
||||||
_wpn = _this select 0;
|
|
||||||
_muzzles = getArray(configFile >> "cfgWeapons" >> _wpn >> "muzzles");
|
|
||||||
|
|
||||||
if (_muzzles select 0 != "this") then {
|
|
||||||
_return = (_muzzles select 0);
|
|
||||||
} else {
|
|
||||||
_return = _wpn;
|
|
||||||
};
|
|
||||||
|
|
||||||
_return;
|
|
||||||
};
|
|
||||||
|
|
||||||
_clearActions = {
|
|
||||||
if (s_player_equip_carry > -1) then {
|
|
||||||
player removeAction s_player_equip_carry;
|
|
||||||
s_player_equip_carry = -1;
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
_switchPrimary = {
|
|
||||||
private ["_primary", "_current"];
|
|
||||||
_primary = primaryWeapon player;
|
|
||||||
_current = currentWeapon player;
|
_current = currentWeapon player;
|
||||||
_timer = 0;
|
|
||||||
|
switch _this do
|
||||||
[] call _clearActions;
|
{
|
||||||
if (_primary != "") then {
|
//Instantly switch primary and carry, also update gear
|
||||||
// check if player is still in the 'open gear' animation state and force him out of it (caused major issues)
|
case 0:
|
||||||
_animState = animationState player;
|
{
|
||||||
|
if (IS_PRIMARY(_current)) then
|
||||||
switch (true) do {
|
{ true call dz_fn_switchWeapon_swap; }
|
||||||
// current weapon is a rifle
|
else
|
||||||
case (_animState == "amovpknlmstpsraswrfldnon_gear" || _animState == "amovpercmstpsraswrfldnon_gear"): {
|
{ false call dz_fn_switchWeapon_swap; };
|
||||||
player playMove "amovpknlmstpslowwrfldnon_amovpknlmstpsraswrfldnon";
|
|
||||||
waitUntil { animationState player == "amovpknlmstpslowwrfldnon_amovpknlmstpsraswrfldnon" };
|
/*call _swapWeapons;
|
||||||
|
if (IS_PRIMARY(_current)) then
|
||||||
|
{ player selectWeapon primaryWeapon player; };*/
|
||||||
|
|
||||||
|
[[(findDisplay 106)],"onLBSelChanged"] execVM "\z\addons\dayz_code\system\handleGear.sqf";
|
||||||
|
};
|
||||||
|
|
||||||
|
//Switch primary and carry
|
||||||
|
case 1:
|
||||||
|
{
|
||||||
|
if (dayz_quickSwitch) then
|
||||||
|
{
|
||||||
|
true call dz_fn_switchWeapon_swap;
|
||||||
|
#ifdef BANDAID
|
||||||
|
call dayz_meleeMagazineCheck;
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{ call dz_fn_switchWeapon_swapSecure; };
|
||||||
|
};
|
||||||
|
|
||||||
|
//Switch to rifle
|
||||||
|
case 2:
|
||||||
|
{
|
||||||
|
//No current weapon
|
||||||
|
if (_current == "") exitWith
|
||||||
|
{
|
||||||
|
switch FIND_RIFLE() do
|
||||||
|
{
|
||||||
|
//In primary
|
||||||
|
case 1:
|
||||||
|
{
|
||||||
|
player selectWeapon primaryWeapon player;
|
||||||
|
};
|
||||||
|
|
||||||
|
//On back
|
||||||
|
case 2:
|
||||||
|
{
|
||||||
|
true call dz_fn_switchWeapon_swap;
|
||||||
|
};
|
||||||
|
};
|
||||||
};
|
};
|
||||||
// current weapon is a pistol
|
|
||||||
case (_animState == "amovpknlmstpsraswpstdnon_gear" || _animState == "amovpercmstpsraswpstdnon_gear"): {
|
//Current weapon is primary
|
||||||
player playMove "amovpknlmstpslowwpstdnon_gear_amovpknlmstpsraswpstdnon";
|
if (IS_PRIMARY(_current)) exitWith
|
||||||
waitUntil { animationState player == "amovpknlmstpslowwpstdnon_gear_amovpknlmstpsraswpstdnon" };
|
{
|
||||||
|
//if current is melee and on back is rifle
|
||||||
|
if (IS_MELEE(_current) && { !IS_MELEE(dayz_onBack) }) then
|
||||||
|
{
|
||||||
|
if (dayz_quickSwitch) then
|
||||||
|
{ true call dz_fn_switchWeapon_swap; }
|
||||||
|
else
|
||||||
|
{ call dz_fn_switchWeapon_swapSecure; };
|
||||||
|
};
|
||||||
};
|
};
|
||||||
// is standing with weapon lowered
|
|
||||||
case (["aidlpercmstpslowwrfldnon", _animState] call fnc_inString): {
|
//Current is pistol
|
||||||
player playMove "amovpercmstpslowwrfldnon_amovpercmstpsraswrfldnon";
|
switch FIND_RIFLE() do
|
||||||
waitUntil { animationState player == "amovpercmstpslowwrfldnon_amovpercmstpsraswrfldnon" };
|
{
|
||||||
|
//In primary
|
||||||
|
case 1:
|
||||||
|
{
|
||||||
|
player selectWeapon primaryWeapon player;
|
||||||
|
};
|
||||||
|
|
||||||
|
//On back
|
||||||
|
case 2:
|
||||||
|
{
|
||||||
|
if (diag_tickTime - dz_switchWeapon_pistolTime < 1) exitWith {};
|
||||||
|
true call dz_fn_switchWeapon_swap;
|
||||||
|
};
|
||||||
};
|
};
|
||||||
};
|
};
|
||||||
|
|
||||||
player removeWeapon _primary;
|
//Switch to pistol
|
||||||
|
case 3:
|
||||||
// make sure animation is playing to prevent instant switch (if current weapon is not pisol)
|
{
|
||||||
if (!dayz_quickSwitch) then {
|
//If current weapon is primary
|
||||||
if (_current != [] call _findPistol) then {
|
if (IS_PRIMARY(_current)) then
|
||||||
_timeout = diag_tickTime + 2;
|
{
|
||||||
_animArray = [
|
_secondary = Player_GetSidearm();
|
||||||
"amovpercmstpsraswrfldnon_amovpercmstpsnonwnondnon", // is standing, has no pistol / is crouched, has no pistol
|
if (!isNil "_secondary") then
|
||||||
"amovpercmstpsraswrfldnon_amovpercmstpsraswpstdnon", // is standing, has pistol
|
{
|
||||||
"amovpknlmstpsraswrfldnon_amovpknlmstpsraswpstdnon", // is crouched, has pistol
|
player selectWeapon _secondary;
|
||||||
"amovppnemstpsraswrfldnon_amovppnemstpsnonwnondnon", // is prone, has no pistol
|
dz_switchWeapon_pistolTime = diag_tickTime;
|
||||||
"amovppnemstpsraswrfldnon_amovppnemstpsraswpstdnon" // is prone, has pistol
|
};
|
||||||
];
|
|
||||||
|
|
||||||
waitUntil { (animationState player) in _animArray || diag_tickTime >= _timeout };
|
|
||||||
waitUntil { !((animationState player) in _animArray) || diag_tickTime >= _timeout };
|
|
||||||
};
|
};
|
||||||
};
|
};
|
||||||
|
|
||||||
|
//Switch to melee
|
||||||
|
case 4:
|
||||||
|
{
|
||||||
|
//No current weapon
|
||||||
|
if (_current == "") exitWith
|
||||||
|
{
|
||||||
|
switch FIND_MELEE() do
|
||||||
|
{
|
||||||
|
//In primary
|
||||||
|
case 1:
|
||||||
|
{
|
||||||
|
player selectWeapon primaryWeapon player;
|
||||||
|
};
|
||||||
|
|
||||||
|
//On back
|
||||||
|
case 2:
|
||||||
|
{
|
||||||
|
true call dz_fn_switchWeapon_swap;
|
||||||
|
#ifdef BANDAID
|
||||||
|
call dayz_meleeMagazineCheck;
|
||||||
|
#endif
|
||||||
|
};
|
||||||
|
};
|
||||||
|
};
|
||||||
|
|
||||||
|
//Current weapon is primary
|
||||||
|
if (IS_PRIMARY(_current)) exitWith
|
||||||
|
{
|
||||||
|
//if current is rifle and on back is melee
|
||||||
|
if (!IS_MELEE(_current) && { IS_MELEE(dayz_onBack) }) then
|
||||||
|
{
|
||||||
|
if (dayz_quickSwitch) then
|
||||||
|
{
|
||||||
|
true call dz_fn_switchWeapon_swap;
|
||||||
|
#ifdef BANDAID
|
||||||
|
call dayz_meleeMagazineCheck;
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{ call dz_fn_switchWeapon_swapSecure; };
|
||||||
|
};
|
||||||
|
};
|
||||||
|
|
||||||
|
//Current is pistol
|
||||||
|
//Find melee weapon
|
||||||
|
switch FIND_MELEE() do
|
||||||
|
{
|
||||||
|
//In primary
|
||||||
|
case 1:
|
||||||
|
{
|
||||||
|
player selectWeapon primaryWeapon player;
|
||||||
|
};
|
||||||
|
|
||||||
|
//On back
|
||||||
|
case 2:
|
||||||
|
{
|
||||||
|
if (diag_tickTime - dz_switchWeapon_pistolTime < 1) exitWith {};
|
||||||
|
true call dz_fn_switchWeapon_swap;
|
||||||
|
};
|
||||||
|
};
|
||||||
|
};
|
||||||
|
};
|
||||||
|
};
|
||||||
|
|
||||||
|
//See FIND_RIFLE() and FIND_MELEE()
|
||||||
|
dz_fn_switchWeapon_find =
|
||||||
|
{
|
||||||
|
_primary = primaryWeapon player;
|
||||||
|
|
||||||
|
if (_primary != "" && { _this == MELEE(_primary) })
|
||||||
|
exitWith { 1 };
|
||||||
|
|
||||||
|
if (dayz_onBack != "" && { _this == MELEE(dayz_onBack) })
|
||||||
|
exitWith { 2 };
|
||||||
|
|
||||||
|
0
|
||||||
|
};
|
||||||
|
|
||||||
|
//Swaps rifle / melee instantly without animation
|
||||||
|
dz_fn_switchWeapon_swap =
|
||||||
|
{
|
||||||
|
if (dayz_onBack == "") then
|
||||||
|
{
|
||||||
|
//Must be in a single statement to ensure atomicity in the scheduled environment.
|
||||||
|
dayz_onBack =
|
||||||
|
[
|
||||||
|
primaryWeapon player,
|
||||||
|
player removeWeapon primaryWeapon player
|
||||||
|
] select 0;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
dayz_onBack =
|
||||||
|
[
|
||||||
|
primaryWeapon player,
|
||||||
|
player removeWeapon primaryWeapon player,
|
||||||
|
player addWeapon dayz_onBack
|
||||||
|
] select 0;
|
||||||
};
|
};
|
||||||
|
|
||||||
if (dayz_onBack != "") then {
|
if (_this) then
|
||||||
player addWeapon dayz_onBack;
|
{ player selectWeapon primaryWeapon player; };
|
||||||
player selectWeapon ([dayz_onBack] call _selectMuzzle);
|
|
||||||
};
|
|
||||||
|
|
||||||
dayz_onBack = _primary;
|
|
||||||
|
|
||||||
call dayz_meleeMagazineCheck;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
_switchPrimaryUI = {
|
//Swaps rifle / melee forcing an animation
|
||||||
private ["_primary", "_current"];
|
dz_fn_switchWeapon_swapSecure =
|
||||||
_primary = primaryWeapon player;
|
{
|
||||||
_current = currentWeapon player;
|
if (!Mutex_TryLock_Fast(dz_switchWeapon_mutex)) exitWith {};
|
||||||
|
|
||||||
[] call _clearActions;
|
//animation states are in the form "AmovPerc...", "AmovPknl...", "AmovPpne..."
|
||||||
|
dz_switchWeapon_anim = format
|
||||||
if (_primary != "") then {
|
[
|
||||||
player removeWeapon _primary;
|
"AmovP%1MstpSrasWrflDnon_AmovP%1MstpSrasWpstDnon",
|
||||||
};
|
//Switch on the 6th letter of the animation class
|
||||||
|
switch ((toArray animationState player) select 5) do
|
||||||
if (dayz_onBack != "") then {
|
{
|
||||||
player addWeapon dayz_onBack;
|
case 101: { "erc" }; //e for erc for erected
|
||||||
|
case 107: { "knl" }; //k for knl for kneeling
|
||||||
if (_primary == _current) then {
|
case 112: { "pne" }; //p for pne for prone
|
||||||
player selectWeapon ([dayz_onBack] call _selectMuzzle);
|
}
|
||||||
};
|
];
|
||||||
};
|
|
||||||
|
//Add AnimDone event handler to wait until current weapon is put away
|
||||||
dayz_onBack = _primary;
|
dz_switchWeapon_handler = player addEventHandler ["AnimDone", dz_fn_switchWeapon_animDone];
|
||||||
|
player playMoveNow dz_switchWeapon_anim;
|
||||||
[[(findDisplay 106)],"onLBSelChanged"] execVM "\z\addons\dayz_code\system\handleGear.sqf"; // update gear dialog
|
dz_switchWeapon_time = diag_tickTime;
|
||||||
};
|
};
|
||||||
|
|
||||||
_onLadder = (getNumber (configFile >> "CfgMovesMaleSdr" >> "States" >> (animationState player) >> "onLadder")) == 1;
|
dz_fn_switchWeapon_animDone =
|
||||||
_inVehicle = (vehicle player != player);
|
{
|
||||||
_isOK = (!_onLadder && !_inVehicle && !r_player_unconscious && !dayz_onBackActive);
|
//Wait at most TIMEOUT seconds
|
||||||
|
if (dz_switchWeapon_time - diag_tickTime > TIMEOUT) exitWith
|
||||||
if (_isOK) then { dayz_onBackActive = true };
|
{
|
||||||
|
player removeEventHandler ["AnimDone", dz_switchWeapon_handler];
|
||||||
switch (_event) do {
|
Mutex_Unlock(dz_switchWeapon_mutex);
|
||||||
case "action": {
|
|
||||||
if (_isOK) then {
|
|
||||||
[] call _switchPrimary;
|
|
||||||
};
|
|
||||||
};
|
};
|
||||||
case "gear": {
|
|
||||||
[] call _switchPrimaryUI;
|
//Check if finished animation is the correct one
|
||||||
};
|
if ((_this select 1) != dz_switchWeapon_anim) exitWith {};
|
||||||
case "rifle": {
|
|
||||||
if (_isOK) then {
|
true call dz_fn_switchWeapon_swap;
|
||||||
_rifle = [] call _findRifle;
|
|
||||||
|
//Remove eventhandler
|
||||||
if (_rifle != "") then {
|
player removeEventHandler ["AnimDone", dz_switchWeapon_handler];
|
||||||
if (_rifle == dayz_onBack) then {
|
Mutex_Unlock(dz_switchWeapon_mutex);
|
||||||
[] call _switchPrimary;
|
|
||||||
} else {
|
#ifdef BANDAID
|
||||||
player selectWeapon ([_rifle] call _selectMuzzle);
|
if (IS_MELEE(primaryWeapon player)) then
|
||||||
};
|
{ call dayz_meleeMagazineCheck; };
|
||||||
};
|
#endif
|
||||||
};
|
};
|
||||||
};
|
|
||||||
case "pistol": {
|
|
||||||
if (_isOK) then {
|
|
||||||
_pistol = [] call _findPistol;
|
|
||||||
|
|
||||||
if (_pistol != "") then {
|
|
||||||
player selectWeapon ([_pistol] call _selectMuzzle);
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
case "melee": {
|
|
||||||
if (_isOK) then {
|
|
||||||
_melee = [] call _findMelee;
|
|
||||||
|
|
||||||
if (_melee != "") then {
|
|
||||||
if (_melee == dayz_onBack) then {
|
|
||||||
[] call _switchPrimary;
|
|
||||||
} else {
|
|
||||||
player selectWeapon ([_melee] call _selectMuzzle);
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
if (_isOK) then { dayz_onBackActive = false };
|
|
||||||
1
SQF/dayz_code/actions/player_switchWeapon_action.sqf
Normal file
1
SQF/dayz_code/actions/player_switchWeapon_action.sqf
Normal file
@@ -0,0 +1 @@
|
|||||||
|
1 call dz_fn_switchWeapon;
|
||||||
@@ -38,6 +38,27 @@ if (_canPickLight && !dayz_hasLight && !_isPZombie) then {
|
|||||||
s_player_removeflare = -1;
|
s_player_removeflare = -1;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
if (s_player_equip_carry < 0) then
|
||||||
|
{
|
||||||
|
if (dayz_onBack != "" && { !_inVehicle && { !_onLadder && { !r_player_unconscious } } }) then
|
||||||
|
{
|
||||||
|
dz_plr_carryActionItem = dayz_onBack;
|
||||||
|
_text = getText (configFile >> "CfgWeapons" >> dz_plr_carryActionItem >> "displayName");
|
||||||
|
s_player_equip_carry = player addAction [
|
||||||
|
format [localize "STR_ACTIONS_WEAPON", _text],
|
||||||
|
"\z\addons\dayz_code\actions\player_switchWeapon_action.sqf",
|
||||||
|
nil, 0.5, false, true];
|
||||||
|
};
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
if (dayz_onBack != dz_plr_carryActionItem || { _inVehicle || { _onLadder || { r_player_unconscious } } } ) then
|
||||||
|
{
|
||||||
|
player removeAction s_player_equip_carry;
|
||||||
|
s_player_equip_carry = -1;
|
||||||
|
};
|
||||||
|
};
|
||||||
|
|
||||||
if (_inVehicle && {_vehicleOwnerID != "0"} && {!(_vehicle isKindOf "Bicycle")}) then {
|
if (_inVehicle && {_vehicleOwnerID != "0"} && {!(_vehicle isKindOf "Bicycle")}) then {
|
||||||
if (s_player_lockUnlockInside_ctrl < 0) then {
|
if (s_player_lockUnlockInside_ctrl < 0) then {
|
||||||
DZE_myVehicle = _vehicle;
|
DZE_myVehicle = _vehicle;
|
||||||
|
|||||||
@@ -44,15 +44,15 @@ if (isNil "keyboard_keys") then {
|
|||||||
_handled = true;
|
_handled = true;
|
||||||
};
|
};
|
||||||
_rifle = {
|
_rifle = {
|
||||||
["rifle"] spawn player_switchWeapon;
|
2 call dz_fn_switchWeapon;
|
||||||
_handled = true;
|
_handled = true;
|
||||||
};
|
};
|
||||||
_pistol = {
|
_pistol = {
|
||||||
["pistol"] spawn player_switchWeapon;
|
3 call dz_fn_switchWeapon;
|
||||||
_handled = true;
|
_handled = true;
|
||||||
};
|
};
|
||||||
_melee = {
|
_melee = {
|
||||||
["melee"] spawn player_switchWeapon;
|
4 call dz_fn_switchWeapon;
|
||||||
_handled = true;
|
_handled = true;
|
||||||
};
|
};
|
||||||
_throwable = { // select next non empty throwable weapon
|
_throwable = { // select next non empty throwable weapon
|
||||||
@@ -74,7 +74,7 @@ if (isNil "keyboard_keys") then {
|
|||||||
};
|
};
|
||||||
} forEach getArray(configFile >> "cfgWeapons" >> _weapon >> _muzz >> "magazines");
|
} forEach getArray(configFile >> "cfgWeapons" >> _weapon >> _muzz >> "magazines");
|
||||||
} forEach _muzzles;
|
} forEach _muzzles;
|
||||||
} forEach [ "Flare", "Throw" ];
|
} forEach [ "Throw"];
|
||||||
|
|
||||||
_magCount = count _ammo_throwable;
|
_magCount = count _ammo_throwable;
|
||||||
if (_magCount > 0) then {
|
if (_magCount > 0) then {
|
||||||
|
|||||||
@@ -5,6 +5,8 @@
|
|||||||
if (!isDedicated) then {
|
if (!isDedicated) then {
|
||||||
|
|
||||||
"filmic" setToneMappingParams [0.07, 0.31, 0.23, 0.37, 0.011, 3.750, 6, 4]; setToneMapping "Filmic";
|
"filmic" setToneMappingParams [0.07, 0.31, 0.23, 0.37, 0.011, 3.750, 6, 4]; setToneMapping "Filmic";
|
||||||
|
|
||||||
|
call compile preprocessFileLineNumbers "\z\addons\dayz_code\util\compile.sqf";
|
||||||
|
|
||||||
BIS_Effects_Burn = compile preprocessFile "\ca\Data\ParticleEffects\SCRIPTS\destruction\burn.sqf";
|
BIS_Effects_Burn = compile preprocessFile "\ca\Data\ParticleEffects\SCRIPTS\destruction\burn.sqf";
|
||||||
player_zombieCheck = compile preprocessFileLineNumbers "\z\addons\dayz_code\compile\player_zombieCheck.sqf"; //Run on a players computer, checks if the player is near a zombie
|
player_zombieCheck = compile preprocessFileLineNumbers "\z\addons\dayz_code\compile\player_zombieCheck.sqf"; //Run on a players computer, checks if the player is near a zombie
|
||||||
@@ -108,7 +110,7 @@ if (!isDedicated) then {
|
|||||||
|
|
||||||
player_wearClothes = compile preprocessFileLineNumbers "\z\addons\dayz_code\actions\player_wearClothes.sqf";
|
player_wearClothes = compile preprocessFileLineNumbers "\z\addons\dayz_code\actions\player_wearClothes.sqf";
|
||||||
object_pickup = compile preprocessFileLineNumbers "\z\addons\dayz_code\actions\object_pickup.sqf";
|
object_pickup = compile preprocessFileLineNumbers "\z\addons\dayz_code\actions\object_pickup.sqf";
|
||||||
player_switchWeapon = compile preprocessFileLineNumbers "\z\addons\dayz_code\actions\player_switchWeapon.sqf";
|
call compile preprocessFileLineNumbers "\z\addons\dayz_code\actions\player_switchWeapon.sqf";
|
||||||
player_flipvehicle = compile preprocessFileLineNumbers "\z\addons\dayz_code\actions\player_flipvehicle.sqf";
|
player_flipvehicle = compile preprocessFileLineNumbers "\z\addons\dayz_code\actions\player_flipvehicle.sqf";
|
||||||
player_sleep = compile preprocessFileLineNumbers "\z\addons\dayz_code\actions\player_sleep.sqf";
|
player_sleep = compile preprocessFileLineNumbers "\z\addons\dayz_code\actions\player_sleep.sqf";
|
||||||
player_antiWall = compile preprocessFileLineNumbers "\z\addons\dayz_code\compile\player_antiWall.sqf";
|
player_antiWall = compile preprocessFileLineNumbers "\z\addons\dayz_code\compile\player_antiWall.sqf";
|
||||||
|
|||||||
@@ -767,7 +767,6 @@ if(!isDedicated) then {
|
|||||||
// dayzDebug = true;
|
// dayzDebug = true;
|
||||||
//};
|
//};
|
||||||
dayz_onBack = "";
|
dayz_onBack = "";
|
||||||
dayz_onBackActive = false;
|
|
||||||
DZE_ActionInProgress = false;
|
DZE_ActionInProgress = false;
|
||||||
|
|
||||||
// DayZ Epoch Client only variables
|
// DayZ Epoch Client only variables
|
||||||
|
|||||||
61
SQF/dayz_code/util/Array.hpp
Normal file
61
SQF/dayz_code/util/Array.hpp
Normal file
@@ -0,0 +1,61 @@
|
|||||||
|
/* Provides functions for working with arrays.
|
||||||
|
|
||||||
|
Author: Foxy
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef _INCLUDE_GUARD_ARRAY
|
||||||
|
#define _INCLUDE_GUARD_ARRAY
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
//Get or set the element at specific index.
|
||||||
|
#define Array_Get(array, index) ((array) select (index))
|
||||||
|
#define Array_Set(array, index, value) ((array) set [index, value])
|
||||||
|
|
||||||
|
//Atomically retrieve and replace the value at specified index.
|
||||||
|
#define Array_GetSet(array, index, value) ([array, index, value] call dz_fn_array_getSet)
|
||||||
|
#define Array_GetSet_Fast(array, index, value) ([(array) select (index), (array) set [index, value]] select 0)
|
||||||
|
|
||||||
|
//Returns true if any of the array elements matches the specified predicate
|
||||||
|
#define Array_Any(arr, predicate) ([arr, predicate] call dz_fn_array_any)
|
||||||
|
|
||||||
|
//Returns true if all of the array elements match the specified predicate
|
||||||
|
#define Array_All(p_arr,p_pred) ([arr, predicate] call dz_fn_array_all)
|
||||||
|
|
||||||
|
//Returns the first element of the array that matches the specified predicate
|
||||||
|
#define Array_First(arr, predicate) ([arr, predicate] call dz_fn_array_first)
|
||||||
|
|
||||||
|
//Selects a random element from the specified array
|
||||||
|
#define Array_SelectRandom(arr) ((arr) call dz_fn_array_selectRandom)
|
||||||
|
#define Array_SelectRandom_Fast(arr) ((arr) select floor random count (arr))
|
||||||
|
|
||||||
|
//Shuffles the given array. Modifies the passed in array and returns it.
|
||||||
|
//To preserve the original pass in a copy: Array_Shuffle(+myArray)
|
||||||
|
//Algorithm: Fisher-Yates Complexity: O(n)
|
||||||
|
#define Array_Shuffle(arr) ((arr) call dz_fn_array_shuffle)
|
||||||
|
|
||||||
|
//Sorts the given array using specified comparer function.
|
||||||
|
//To preserve the original pass in a copy: Array_MergeSort(+myArray, myComparer)
|
||||||
|
//Algorithm: Merge Sort Complexity: O(n log n)
|
||||||
|
#define Array_MergeSort(arr, comparer) ([arr, comparer] call dz_fn_array_mergeSort)
|
||||||
|
|
||||||
|
//Array initialization macros for passing arrays as macro arguments.
|
||||||
|
#define Array_New() []
|
||||||
|
#define Array_New1(p0) [p0]
|
||||||
|
#define Array_New2(p0,p1) [p0,p1]
|
||||||
|
#define Array_New3(p0,p1,p2) [p0,p1,p2]
|
||||||
|
#define Array_New4(p0,p1,p2,p3) [p0,p1,p2,p3]
|
||||||
|
#define Array_New5(p0,p1,p2,p3,p4) [p0,p1,p2,p3,p4]
|
||||||
|
#define Array_New6(p0,p1,p2,p3,p4,p5) [p0,p1,p2,p3,p4,p5]
|
||||||
|
#define Array_New7(p0,p1,p2,p3,p4,p5,p6) [p0,p1,p2,p3,p4,p5,p6]
|
||||||
|
#define Array_New8(p0,p1,p2,p3,p4,p5,p6,p7) [p0,p1,p2,p3,p4,p5,p6,p7]
|
||||||
|
#define Array_New9(p0,p1,p2,p3,p4,p5,p6,p7,p8) [p0,p1,p2,p3,p4,p5,p6,p7,p8]
|
||||||
|
#define Array_New10(p0,p1,p2,p3,p4,p5,p6,p7,p8,p9) [p0,p1,p2,p3,p4,p5,p6,p7,p8,p9]
|
||||||
|
#define Array_New11(p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10) [p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10]
|
||||||
|
#define Array_New12(p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11) [p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11]
|
||||||
|
#define Array_New13(p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11,p12) [p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11,p12]
|
||||||
|
#define Array_New14(p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11,p12,p13) [p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11,p12,p13]
|
||||||
|
#define Array_New15(p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11,p12,p13,p14) [p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11,p12,p13,p14]
|
||||||
|
#define Array_New16(p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11,p12,p13,p14,p15) [p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11,p12,p13,p14,p15]
|
||||||
|
|
||||||
|
#endif
|
||||||
121
SQF/dayz_code/util/Debug.hpp
Normal file
121
SQF/dayz_code/util/Debug.hpp
Normal file
@@ -0,0 +1,121 @@
|
|||||||
|
/* Defines macros for debugging.
|
||||||
|
Care must be taken to only include this header once as it cannot use an include guard.
|
||||||
|
The _DEBUG_ constant can be used outside this header to define custom debug code.
|
||||||
|
|
||||||
|
Author: Foxy
|
||||||
|
|
||||||
|
P.s. Why does this piece of shit not have variadic macros?!
|
||||||
|
*/
|
||||||
|
|
||||||
|
//Comment out to disable debugging
|
||||||
|
//#define _DEBUG_
|
||||||
|
|
||||||
|
//DEBUG ENABLED
|
||||||
|
#ifdef _DEBUG_
|
||||||
|
|
||||||
|
//Logs the specified value
|
||||||
|
#define Debug_Log(val) (diag_log str (val))
|
||||||
|
|
||||||
|
/* Logs generic debug information
|
||||||
|
File name
|
||||||
|
Line number
|
||||||
|
Tick time
|
||||||
|
Frame number
|
||||||
|
*/
|
||||||
|
#define Debug_LogGeneric() (diag_log format ["DEBUG: File:%1 Line:%2 Time:%3 Frame:%4", __FILE__, __LINE__, diag_tickTime, diag_frameno])
|
||||||
|
|
||||||
|
//Assert
|
||||||
|
#define Debug_Assert(condition) (assert (condition))
|
||||||
|
|
||||||
|
/* Validates the array member types.
|
||||||
|
Example:
|
||||||
|
//Scalar, string and array
|
||||||
|
Debug_CheckTypes3("SCALAR","STRING","ARRAY");
|
||||||
|
|
||||||
|
//Boolean and scalar or string
|
||||||
|
Debug_CheckTypes2("BOOL",Array_New2("SCALAR","STRING"));
|
||||||
|
|
||||||
|
//Object or nil and any
|
||||||
|
Debug_CheckTypes2(Array_New2("OBJECT","NIL"),"ANY");
|
||||||
|
|
||||||
|
See https://community.bistudio.com/wiki/Data_Types
|
||||||
|
*/
|
||||||
|
#define Debug_CheckTypes1(arr, p0) ([arr,[p0],__FILE__,__LINE__] call dz_fn_debug_checkTypes)
|
||||||
|
#define Debug_CheckTypes2(arr, p0,p1) ([arr,[p0,p1],__FILE__,__LINE__] call dz_fn_debug_checkTypes)
|
||||||
|
#define Debug_CheckTypes3(arr, p0,p1,p2) ([arr,[p0,p1,p2],__FILE__,__LINE__] call dz_fn_debug_checkTypes)
|
||||||
|
#define Debug_CheckTypes4(arr, p0,p1,p2,p3) ([arr,[p0,p1,p2,p3],__FILE__,__LINE__] call dz_fn_debug_checkTypes)
|
||||||
|
#define Debug_CheckTypes5(arr, p0,p1,p2,p3,p4) ([arr,[p0,p1,p2,p3,p4],__FILE__,__LINE__] call dz_fn_debug_checkTypes)
|
||||||
|
#define Debug_CheckTypes6(arr, p0,p1,p2,p3,p4,p5) ([arr,[p0,p1,p2,p3,p4,p5],__FILE__,__LINE__] call dz_fn_debug_checkTypes)
|
||||||
|
#define Debug_CheckTypes7(arr, p0,p1,p2,p3,p4,p5,p6) ([arr,[p0,p1,p2,p3,p4,p5,p6],__FILE__,__LINE__] call dz_fn_debug_checkTypes)
|
||||||
|
#define Debug_CheckTypes8(arr, p0,p1,p2,p3,p4,p5,p6,p7) ([arr,[p0,p1,p2,p3,p4,p5,p6,p7],__FILE__,__LINE__] call dz_fn_debug_checkTypes)
|
||||||
|
#define Debug_CheckTypes9(arr, p0,p1,p2,p3,p4,p5,p6,p7,p8) ([arr,[p0,p1,p2,p3,p4,p5,p6,p7,p8],__FILE__,__LINE__] call dz_fn_debug_checkTypes)
|
||||||
|
#define Debug_CheckTypes10(arr, p0,p1,p2,p3,p4,p5,p6,p7,p8,p9) ([arr,[p0,p1,p2,p3,p4,p5,p6,p7,p8,p9],__FILE__,__LINE__] call dz_fn_debug_checkTypes)
|
||||||
|
#define Debug_CheckTypes11(arr, p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10) ([arr,[p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10],__FILE__,__LINE__] call dz_fn_debug_checkTypes)
|
||||||
|
#define Debug_CheckTypes12(arr, p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11) ([arr,[p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11],__FILE__,__LINE__] call dz_fn_debug_checkTypes)
|
||||||
|
#define Debug_CheckTypes13(arr, p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11,p12) ([arr,[p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11,p12],__FILE__,__LINE__] call dz_fn_debug_checkTypes)
|
||||||
|
#define Debug_CheckTypes14(arr, p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11,p12,p13) ([arr,[p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11,p12,p13],__FILE__,__LINE__] call dz_fn_debug_checkTypes)
|
||||||
|
#define Debug_CheckTypes15(arr, p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11,p12,p13,p14) ([arr,[p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11,p12,p13,p14],__FILE__,__LINE__] call dz_fn_debug_checkTypes)
|
||||||
|
#define Debug_CheckTypes16(arr, p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11,p12,p13,p14,p15) ([arr,[p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11,p12,p13,p14,p15],__FILE__,__LINE__] call dz_fn_debug_checkTypes)
|
||||||
|
|
||||||
|
//See Debug_CheckTypes. Used for checking script parameters.
|
||||||
|
#define Debug_CheckParams1(p0) Debug_CheckTypes1(_this,p0)
|
||||||
|
#define Debug_CheckParams2(p0,p1) Debug_CheckTypes2(_this,p0,p1)
|
||||||
|
#define Debug_CheckParams3(p0,p1,p2) Debug_CheckTypes3(_this,p0,p1,p2)
|
||||||
|
#define Debug_CheckParams4(p0,p1,p2,p3) Debug_CheckTypes4(_this,p0,p1,p2,p3)
|
||||||
|
#define Debug_CheckParams5(p0,p1,p2,p3,p4) Debug_CheckTypes5(_this,p0,p1,p2,p3,p4)
|
||||||
|
#define Debug_CheckParams6(p0,p1,p2,p3,p4,p5) Debug_CheckTypes6(_this,p0,p1,p2,p3,p4,p5)
|
||||||
|
#define Debug_CheckParams7(p0,p1,p2,p3,p4,p5,p6) Debug_CheckTypes7(_this,p0,p1,p2,p3,p4,p5,p6)
|
||||||
|
#define Debug_CheckParams8(p0,p1,p2,p3,p4,p5,p6,p7) Debug_CheckTypes8(_this,p0,p1,p2,p3,p4,p5,p6,p7)
|
||||||
|
#define Debug_CheckParams9(p0,p1,p2,p3,p4,p5,p6,p7,p8) Debug_CheckTypes9(_this,p0,p1,p2,p3,p4,p5,p6,p7,p8)
|
||||||
|
#define Debug_CheckParams10(p0,p1,p2,p3,p4,p5,p6,p7,p8,p9) Debug_CheckTypes10(_this,p0,p1,p2,p3,p4,p5,p6,p7,p8,p9)
|
||||||
|
#define Debug_CheckParams11(p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10) Debug_CheckTypes11(_this,p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10)
|
||||||
|
#define Debug_CheckParams12(p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11) Debug_CheckTypes12(_this,p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11)
|
||||||
|
#define Debug_CheckParams13(p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11,p12) Debug_CheckTypes13(_this,p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11,p12)
|
||||||
|
#define Debug_CheckParams14(p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11,p12,p13) Debug_CheckTypes14(_this,p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11,p12,p13)
|
||||||
|
#define Debug_CheckParams15(p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11,p12,p13,p14) Debug_CheckTypes15(_this,p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11,p12,p13,p14)
|
||||||
|
#define Debug_CheckParams16(p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11,p12,p13,p14,p15) Debug_CheckTypes16(_this,p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11,p12,p13,p14,p15)
|
||||||
|
|
||||||
|
// DEBUG DISABLED
|
||||||
|
#else
|
||||||
|
|
||||||
|
#define Debug_Log(val)
|
||||||
|
#define Debug_LogGeneric()
|
||||||
|
#define Debug_Assert(condition)
|
||||||
|
|
||||||
|
#define Debug_CheckTypes1(arr,p0)
|
||||||
|
#define Debug_CheckTypes2(arr,p0,p1)
|
||||||
|
#define Debug_CheckTypes3(arr,p0,p1,p2)
|
||||||
|
#define Debug_CheckTypes4(arr,p0,p1,p2,p3)
|
||||||
|
#define Debug_CheckTypes5(arr,p0,p1,p2,p3,p4)
|
||||||
|
#define Debug_CheckTypes6(arr,p0,p1,p2,p3,p4,p5)
|
||||||
|
#define Debug_CheckTypes7(arr,p0,p1,p2,p3,p4,p5,p6)
|
||||||
|
#define Debug_CheckTypes8(arr,p0,p1,p2,p3,p4,p5,p6,p7)
|
||||||
|
#define Debug_CheckTypes9(arr,p0,p1,p2,p3,p4,p5,p6,p7,p8)
|
||||||
|
#define Debug_CheckTypes10(arr,p0,p1,p2,p3,p4,p5,p6,p7,p8,p9)
|
||||||
|
#define Debug_CheckTypes11(arr,p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10)
|
||||||
|
#define Debug_CheckTypes12(arr,p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11)
|
||||||
|
#define Debug_CheckTypes13(arr,p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11,p12)
|
||||||
|
#define Debug_CheckTypes14(arr,p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11,p12,p13)
|
||||||
|
#define Debug_CheckTypes15(arr,p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11,p12,p13,p14)
|
||||||
|
#define Debug_CheckTypes16(arr,p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11,p12,p13,p14,p15)
|
||||||
|
|
||||||
|
#define Debug_CheckParams1(p0)
|
||||||
|
#define Debug_CheckParams2(p0,p1)
|
||||||
|
#define Debug_CheckParams3(p0,p1,p2)
|
||||||
|
#define Debug_CheckParams4(p0,p1,p2,p3)
|
||||||
|
#define Debug_CheckParams5(p0,p1,p2,p3,p4)
|
||||||
|
#define Debug_CheckParams6(p0,p1,p2,p3,p4,p5)
|
||||||
|
#define Debug_CheckParams7(p0,p1,p2,p3,p4,p5,p6)
|
||||||
|
#define Debug_CheckParams8(p0,p1,p2,p3,p4,p5,p6,p7)
|
||||||
|
#define Debug_CheckParams9(p0,p1,p2,p3,p4,p5,p6,p7,p8)
|
||||||
|
#define Debug_CheckParams10(p0,p1,p2,p3,p4,p5,p6,p7,p8,p9)
|
||||||
|
#define Debug_CheckParams11(p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10)
|
||||||
|
#define Debug_CheckParams12(p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11)
|
||||||
|
#define Debug_CheckParams13(p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11,p12)
|
||||||
|
#define Debug_CheckParams14(p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11,p12,p13)
|
||||||
|
#define Debug_CheckParams15(p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11,p12,p13,p14)
|
||||||
|
#define Debug_CheckParams16(p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11,p12,p13,p14,p15)
|
||||||
|
|
||||||
|
#endif
|
||||||
|
|
||||||
|
//Type check define generator http://pastebin.com/kBTVtBzz
|
||||||
29
SQF/dayz_code/util/Dictionary.hpp
Normal file
29
SQF/dayz_code/util/Dictionary.hpp
Normal file
@@ -0,0 +1,29 @@
|
|||||||
|
/* Defines member functions for a dictionary class.
|
||||||
|
Can be used to associate data with a key.
|
||||||
|
See https://en.wikipedia.org/wiki/Associative_array
|
||||||
|
|
||||||
|
Author: Foxy
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef _INCLUDE_GUARD_DICTIONARY
|
||||||
|
#define _INCLUDE_GUARD_DICTIONARY
|
||||||
|
|
||||||
|
//Initializes a new dictionary
|
||||||
|
#define Dictionary_New() [0, [], []]
|
||||||
|
|
||||||
|
//Adds a key value pair to the specified dictionary.
|
||||||
|
#define Dictionary_Add(d, key, value) ([d, key, value] call dz_fn_dictionary_add)
|
||||||
|
|
||||||
|
//Removes a value from the dictionary using specified key.
|
||||||
|
#define Dictionary_Remove(d, key) ([d, key] call dz_fn_ictionary_remove)
|
||||||
|
|
||||||
|
//Retrieves a value from the dictionary using specified key.
|
||||||
|
#define Dictionary_Get(d, key) ([d, key] call dz_fn_dictionary_get)
|
||||||
|
|
||||||
|
//Determines whether the dictionary contains the specified key.
|
||||||
|
#define Dictionary_ContainsKey(d, key) ([d, key] call dz_fn_dictionary_containsKey)
|
||||||
|
|
||||||
|
//Rearranges the internal data structure of the dictionary to free unused memory.
|
||||||
|
#define Dictionary_Compact(d) ((d) call dz_fn_dictionary_compact)
|
||||||
|
|
||||||
|
#endif
|
||||||
22
SQF/dayz_code/util/Math.hpp
Normal file
22
SQF/dayz_code/util/Math.hpp
Normal file
@@ -0,0 +1,22 @@
|
|||||||
|
/* Defines generic math functions.
|
||||||
|
|
||||||
|
Author: Foxy
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef _INCLUDE_GUARD_MATH
|
||||||
|
#define _INCLUDE_GUARD_MATH
|
||||||
|
|
||||||
|
//Calculates the greatest common divisor of two numbers
|
||||||
|
#define Math_GCD(a, b) ([a, b] call dz_fn_math_gcd)
|
||||||
|
|
||||||
|
//Calculates the greatest common divisor of all elements of the given array
|
||||||
|
#define Math_GCDArray(a) ((a) call dz_fn_math_gcdx)
|
||||||
|
|
||||||
|
//Selects a random value in the specified range [min, max)
|
||||||
|
#define Math_RandomRange(min, max) ([min, max] call dz_fn_math_randomRange)
|
||||||
|
#define Math_RandomRange_Fast(min, max) ((min) + random ((max) - (min)))
|
||||||
|
|
||||||
|
//Restricts a value to the specified range [pmin, pmax]
|
||||||
|
#define Math_Clamp(value, pmin, pmax) (pmin max (pmax min value))
|
||||||
|
|
||||||
|
#endif
|
||||||
28
SQF/dayz_code/util/Mutex.hpp
Normal file
28
SQF/dayz_code/util/Mutex.hpp
Normal file
@@ -0,0 +1,28 @@
|
|||||||
|
/* Provides a simple mutex implementation.
|
||||||
|
See https://en.wikipedia.org/wiki/Mutual_exclusion
|
||||||
|
|
||||||
|
Author: Foxy
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef _INCLUDE_GUARD_MUTEX
|
||||||
|
#define _INCLUDE_GUARD_MUTEX
|
||||||
|
|
||||||
|
//Initializes a new unlocked mutex.
|
||||||
|
#define Mutex_New() [true]
|
||||||
|
|
||||||
|
//Attempts to lock the specified mutex. Returns true if the mutex was locked.
|
||||||
|
#define Mutex_TryLock(mtx) ((mtx) call dz_fn_mutex_tryLock)
|
||||||
|
#define Mutex_TryLock_Fast(mtx) ([(mtx) select 0, (mtx) set [0, false]] select 0)
|
||||||
|
|
||||||
|
//Determines if the mutex is locked.
|
||||||
|
//Note: if access to critical section is required use TryLock() instead.
|
||||||
|
#define Mutex_IsLocked(mtx) (!(mtx) select 0)
|
||||||
|
|
||||||
|
//Waits until the mutex becomes available and locks it.
|
||||||
|
#define Mutex_WaitLock(mtx) ((mtx) call dz_fn_mutex_waitLock)
|
||||||
|
#define Mutex_WaitLock_Fast(mtx) waitUntil {Mutex_TryLock_Fast(mtx)}
|
||||||
|
|
||||||
|
//Unlocks the mutex. Use only when you have previously obtained lock yourself.
|
||||||
|
#define Mutex_Unlock(mtx) ((mtx) set [0, true])
|
||||||
|
|
||||||
|
#endif
|
||||||
43
SQF/dayz_code/util/Player.hpp
Normal file
43
SQF/dayz_code/util/Player.hpp
Normal file
@@ -0,0 +1,43 @@
|
|||||||
|
/* Defines functions working with the player object.
|
||||||
|
|
||||||
|
Author: Foxy
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef _INCLUDE_GUARD_PLAYER
|
||||||
|
#define _INCLUDE_GUARD_PLAYER
|
||||||
|
|
||||||
|
#define Player_BASE "DZ_PlayerBase_M"
|
||||||
|
|
||||||
|
//True if player is on a ladder, otherwise false
|
||||||
|
#define Player_IsOnLadder() ((getNumber (configFile >> "CfgMovesMaleSdr" >> "States" >> (animationState player) >> "onLadder")) == 1)
|
||||||
|
|
||||||
|
#define Player_IsInVehicle() (player != vehicle player);
|
||||||
|
|
||||||
|
//Gets the classname of the player's sidearm. nil if the player has no sidearm.
|
||||||
|
#define Player_GetSidearm() ({ if ((getNumber (configFile >> "CfgWeapons" >> _x >> "type")) == 2) exitWith { _x }; nil } foreach weapons player)
|
||||||
|
|
||||||
|
//Returns the number of slots in of the specified type in the player inventory.
|
||||||
|
#define Player_NumSlots(type) (dz_player_invSlots select (dz_player_invTypes find (type)))
|
||||||
|
|
||||||
|
//Returns the number of empty slots of the specified type in the player inventory.
|
||||||
|
#define Player_NumEmptySlots(type) ((type) call dz_fn_player_numEmptySlots)
|
||||||
|
|
||||||
|
//Returns the number of items of the specified type in the player inventory.
|
||||||
|
#define Player_NumItems(type) ((type) call dz_fn_player_numItems)
|
||||||
|
|
||||||
|
/* Adds the specified item to player inventory, vehicle inventory, or on the ground below.
|
||||||
|
Return value indicates if and where the item was placed. */
|
||||||
|
#define Player_AddWeapon(class) ([0, class] call dz_fn_player_addItem)
|
||||||
|
#define Player_AddMagazine(class) ([1, class] call dz_fn_player_addItem)
|
||||||
|
|
||||||
|
#define Player_AddItem_RESULT_FAILURE 0
|
||||||
|
#define Player_AddItem_RESULT_PLAYER 1
|
||||||
|
#define Player_AddItem_RESULT_GROUND 2
|
||||||
|
#define Player_AddItem_RESULT_VEHICLE 3
|
||||||
|
|
||||||
|
/* Adds the specifed item on the ground at the player's feet.
|
||||||
|
The weaponholder containing the item is returned. Returns null if the function fails.*/
|
||||||
|
#define Player_DropWeapon(class) ([0, class] call dz_fn_player_dropItem)
|
||||||
|
#define Player_DropMagazine(class) ([1, class] call dz_fn_player_dropItem)
|
||||||
|
|
||||||
|
#endif
|
||||||
36
SQF/dayz_code/util/Queue.hpp
Normal file
36
SQF/dayz_code/util/Queue.hpp
Normal file
@@ -0,0 +1,36 @@
|
|||||||
|
/* Provides a FIFO data structure implementation.
|
||||||
|
See https://en.wikipedia.org/wiki/FIFO_(computing_and_electronics)
|
||||||
|
|
||||||
|
Author: Foxy
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef _INCLUDE_GUARD_QUEUE
|
||||||
|
#define _INCLUDE_GUARD_QUEUE
|
||||||
|
|
||||||
|
//Initializes a new queue with the specified size
|
||||||
|
#define Queue_New(size) ((size) call dz_fn_queue_new)
|
||||||
|
|
||||||
|
//Attempts to add the specified object to the end of the queue.
|
||||||
|
//Returns false if queue is full, otherwise true.
|
||||||
|
#define Queue_Enqueue(q, element) ([q, element] call dz_fn_queue_enqueue)
|
||||||
|
|
||||||
|
//Attempts to remove the first object from the head of the queue.
|
||||||
|
//Returns nil if queue is empty.
|
||||||
|
#define Queue_Dequeue(q) ((q) call dz_fn_queue_dequeue)
|
||||||
|
|
||||||
|
//Attempts to retrieve the first object from the head of the queue without removing it.
|
||||||
|
//Returns nil if queue is empty.
|
||||||
|
#define Queue_Peek(q) ((q) call dz_fn_queue_peek)
|
||||||
|
|
||||||
|
//Returns the maximum capacity of the queue.
|
||||||
|
#define Queue_Size(q) (count ((q) select 2))
|
||||||
|
|
||||||
|
//Returns the number of items in the queue.
|
||||||
|
#define Queue_Count(q) ((q) select 0)
|
||||||
|
|
||||||
|
//Determines whether the queue is full.
|
||||||
|
#define Queue_IsFull(q) ((q) call dz_fn_queue_isFull)
|
||||||
|
|
||||||
|
//#define Queue_Resize(q, s) ([q, s] call dz_fn_queue_resize)
|
||||||
|
|
||||||
|
#endif
|
||||||
19
SQF/dayz_code/util/Reference.hpp
Normal file
19
SQF/dayz_code/util/Reference.hpp
Normal file
@@ -0,0 +1,19 @@
|
|||||||
|
/* Provides means for passing objects by reference.
|
||||||
|
Reference cannot point to itself or create a loop of references.
|
||||||
|
|
||||||
|
Author: Foxy
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef _INCLUDE_GUARD_REFERENCE
|
||||||
|
#define _INCLUDE_GUARD_REFERENCE
|
||||||
|
|
||||||
|
//Initializes a new reference pointing to the specified object.
|
||||||
|
#define Ref_New(val) [val]
|
||||||
|
|
||||||
|
//Retrieves the object pointed to by the reference.
|
||||||
|
#define Ref_Get(ref) ((ref) select 0)
|
||||||
|
|
||||||
|
//Sets the reference to point to the specified object.
|
||||||
|
#define Ref_Set(ref, val) ((ref) set [0, val])
|
||||||
|
|
||||||
|
#endif
|
||||||
49
SQF/dayz_code/util/Request.hpp
Normal file
49
SQF/dayz_code/util/Request.hpp
Normal file
@@ -0,0 +1,49 @@
|
|||||||
|
/* Provides means for a client to send requests to the server and subsequently receive a reply.
|
||||||
|
Do not use this header on the server.
|
||||||
|
|
||||||
|
Author: Foxy*/
|
||||||
|
|
||||||
|
#include "Dictionary.hpp"
|
||||||
|
|
||||||
|
#ifndef _INCLUDE_GUARD_REQUEST
|
||||||
|
#define _INCLUDE_GUARD_REQUEST
|
||||||
|
|
||||||
|
assert (!isServer);
|
||||||
|
|
||||||
|
#define Request_IsInitialized() (!isNil "dz_owner")
|
||||||
|
|
||||||
|
//Waits for initialization to be completed.
|
||||||
|
#define Request_WaitInit() waitUntil {Request_IsInitialized()}
|
||||||
|
|
||||||
|
/* Send request to server.
|
||||||
|
Parameters:
|
||||||
|
string/scalar request
|
||||||
|
Request type. Various request types can be defined by the server.
|
||||||
|
See Request_Server.hpp.
|
||||||
|
any args
|
||||||
|
Argument(s) sent to the server.
|
||||||
|
boolean reply
|
||||||
|
Whether a reply is wanted from the server.
|
||||||
|
|
||||||
|
Return:
|
||||||
|
Request object which or can be waited and provides the result once completed.
|
||||||
|
See Request_Wait() and Request_GetResult().
|
||||||
|
Returns nil if no reply is expected.
|
||||||
|
|
||||||
|
Example:
|
||||||
|
_myRequest = Request_Send("GetDate", nil, true);
|
||||||
|
Request_Wait(_myRequest);
|
||||||
|
_myDate = Request_GetResult(_myRequest);
|
||||||
|
*/
|
||||||
|
#define Request_Send(request, args, reply) ([request, args, reply] call dz_fn_request_send)
|
||||||
|
|
||||||
|
//Determines whether the specified request is completed.
|
||||||
|
#define Request_IsDone(request) (count (request) > 2)
|
||||||
|
|
||||||
|
//Waits for the request to complete.
|
||||||
|
#define Request_Wait(request) waitUntil {Request_IsDone(request)}
|
||||||
|
|
||||||
|
//Retrieves the result of the request.
|
||||||
|
#define Request_GetResult(request) ((request) select 2)
|
||||||
|
|
||||||
|
#undef
|
||||||
33
SQF/dayz_code/util/Request_Server.hpp
Normal file
33
SQF/dayz_code/util/Request_Server.hpp
Normal file
@@ -0,0 +1,33 @@
|
|||||||
|
/* See Request.hpp
|
||||||
|
Do not use this header on the client.
|
||||||
|
|
||||||
|
Author: Foxy
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include "Array.hpp"
|
||||||
|
#include "Dictionary.hpp"
|
||||||
|
|
||||||
|
#ifndef _INCLUDE_GUARD_REQUEST
|
||||||
|
#define _INCLUDE_GUARD_REQUEST
|
||||||
|
|
||||||
|
assert (isServer);
|
||||||
|
|
||||||
|
/* Registers a request handler.
|
||||||
|
Parameters:
|
||||||
|
string/scalar id
|
||||||
|
String or number used as an identifier for the function.
|
||||||
|
String identifiers are case sensitive.
|
||||||
|
code handler
|
||||||
|
Function that handles the request.
|
||||||
|
If handler return nil an empty array is instead sent to the client.
|
||||||
|
boolean async
|
||||||
|
Indicates whether the request should be handled asynchronously (handler is spawned).
|
||||||
|
|
||||||
|
Example:
|
||||||
|
Request_RegisterHandler("GetDate", {my_global_date_variable}, false);
|
||||||
|
Request_RegisterHandler("GetObjectOwner", {owner _this}, false);
|
||||||
|
Request_RegisterHandler("DoSomething", _my_complicated_asynchronous_handler, true);
|
||||||
|
*/
|
||||||
|
#define Request_RegisterHandler(id, handler, async) Dictionary_Add(dz_request_handlers, id, Array_New2(handler, async))
|
||||||
|
|
||||||
|
#undef
|
||||||
30
SQF/dayz_code/util/Stack.hpp
Normal file
30
SQF/dayz_code/util/Stack.hpp
Normal file
@@ -0,0 +1,30 @@
|
|||||||
|
/* Provides a LIFO data structure implementation.
|
||||||
|
See https://en.wikipedia.org/wiki/Stack_(abstract_data_type)
|
||||||
|
|
||||||
|
Author: Foxy
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef _INCLUDE_GUARD_STACK
|
||||||
|
#define _INCLUDE_GUARD_STACK
|
||||||
|
|
||||||
|
//Initializes a new stack object
|
||||||
|
#define Stack_New() [0,[nil,nil]]
|
||||||
|
|
||||||
|
//Pushes the specified object onto the top of the stack.
|
||||||
|
#define Stack_Push(s, element) ([s, element] call dz_fn_stack_push)
|
||||||
|
|
||||||
|
//Removes the object on top of the stack and returns it.
|
||||||
|
//Returns nil if the stack is empty.
|
||||||
|
#define Stack_Pop(s) ((s) call dz_fn_stack_pop)
|
||||||
|
|
||||||
|
//Retrieves the object on top of the stack without removing it.
|
||||||
|
//Returns nil if the stack is empty.
|
||||||
|
#define Stack_Peek(s) ((s) call dz_fn_stack_peek)
|
||||||
|
|
||||||
|
//Returns the current capacity of the stack.
|
||||||
|
//#define Stack_Size(s) (count ((s) select 1))
|
||||||
|
|
||||||
|
//Returns the number of items currently on the stack.
|
||||||
|
#define Stack_Count(stack) ((stack) select 0)
|
||||||
|
|
||||||
|
#endif
|
||||||
22
SQF/dayz_code/util/String.hpp
Normal file
22
SQF/dayz_code/util/String.hpp
Normal file
@@ -0,0 +1,22 @@
|
|||||||
|
#ifndef _INCLUDE_GUARD_STRING
|
||||||
|
#define _INCLUDE_GUARD_STRING
|
||||||
|
|
||||||
|
//Same as format [STRING, ANY...]
|
||||||
|
#define String_Format1(string,p0) (format [string,p0])
|
||||||
|
#define String_Format2(string,p0,p1) (format [string,p0,p1])
|
||||||
|
#define String_Format3(string,p0,p1,p2) (format [string,p0,p1,p2])
|
||||||
|
#define String_Format4(string,p0,p1,p2,p3) (format [string,p0,p1,p2,p3])
|
||||||
|
#define String_Format5(string,p0,p1,p2,p3,p4) (format [string,p0,p1,p2,p3,p4])
|
||||||
|
#define String_Format6(string,p0,p1,p2,p3,p4,p5) (format [string,p0,p1,p2,p3,p4,p5])
|
||||||
|
#define String_Format7(string,p0,p1,p2,p3,p4,p5,p6) (format [string,p0,p1,p2,p3,p4,p5,p6])
|
||||||
|
#define String_Format8(string,p0,p1,p2,p3,p4,p5,p6,p7) (format [string,p0,p1,p2,p3,p4,p5,p6,p7])
|
||||||
|
#define String_Format9(string,p0,p1,p2,p3,p4,p5,p6,p7,p8) (format [string,p0,p1,p2,p3,p4,p5,p6,p7,p8])
|
||||||
|
#define String_Format10(string,p0,p1,p2,p3,p4,p5,p6,p7,p8,p9) (format [string,p0,p1,p2,p3,p4,p5,p6,p7,p8,p9])
|
||||||
|
#define String_Format11(string,p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10) (format [string,p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10])
|
||||||
|
#define String_Format12(string,p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11) (format [string,p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11])
|
||||||
|
#define String_Format13(string,p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11,p12) (format [string,p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11,p12])
|
||||||
|
#define String_Format14(string,p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11,p12,p13) (format [string,p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11,p12,p13])
|
||||||
|
#define String_Format15(string,p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11,p12,p13,p14) (format [string,p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11,p12,p13,p14])
|
||||||
|
#define String_Format16(string,p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11,p12,p13,p14,p15) (format [string,p0,p1,p2,p3,p4,p5,p6,p7,p8,p9,p10,p11,p12,p13,p14,p15])
|
||||||
|
|
||||||
|
#endif
|
||||||
41
SQF/dayz_code/util/Task.hpp
Normal file
41
SQF/dayz_code/util/Task.hpp
Normal file
@@ -0,0 +1,41 @@
|
|||||||
|
/* Provides means for monitoring the execution and retrieving the result of asynchronous operations.
|
||||||
|
|
||||||
|
Author: Foxy
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef _INCLUDE_GUARD_TASK
|
||||||
|
#define _INCLUDE_GUARD_TASK
|
||||||
|
|
||||||
|
//Creates a new task using the specified function
|
||||||
|
#define Task_New(fnc) [fnc, nil, 0, nil]
|
||||||
|
|
||||||
|
//Starts the task with the specified parameters.
|
||||||
|
//Returns the task if succesfully started, otherwise nil.
|
||||||
|
#define Task_Start(task, params) ([task, params] call dz_fn_task_start)
|
||||||
|
|
||||||
|
//Cancels a currently running task.
|
||||||
|
//Returns true if succesfully canceled, otherwise false.
|
||||||
|
#define Task_Cancel(task) ([task] call dz_fn_task_cancel)
|
||||||
|
|
||||||
|
//Gets the task result. Returns nil if not completed.
|
||||||
|
//Note that nil may also be returned if the task function did not return a value.
|
||||||
|
#define Task_Result(task) ((task) select 3)
|
||||||
|
|
||||||
|
//Waits for the task to complete and returns the result.
|
||||||
|
//Cannot be called in the unscheduled environment.
|
||||||
|
//Waits for completion even if the task has not yet been started.
|
||||||
|
#define Task_Wait(task) ((task) call dz_fn_task_wait)
|
||||||
|
|
||||||
|
//Determines whether the task has been started (may have since completed or been canceled).
|
||||||
|
#define Task_IsStarted(task) (((task) select 2) != 0)
|
||||||
|
|
||||||
|
//Determines whether the task is currently running.
|
||||||
|
#define Task_IsRunning(task) (((task) select 2) == 1)
|
||||||
|
|
||||||
|
//Determines whether the task has completed normally.
|
||||||
|
#define Task_IsCompleted(task) (((task) select 2) == 2)
|
||||||
|
|
||||||
|
//Determines whether the task has canceled prior to completion.
|
||||||
|
#define Task_IsCanceled(task) (((task) select 2) == 3)
|
||||||
|
|
||||||
|
#endif
|
||||||
26
SQF/dayz_code/util/Util.hpp
Normal file
26
SQF/dayz_code/util/Util.hpp
Normal file
@@ -0,0 +1,26 @@
|
|||||||
|
#ifndef _INCLUDE_GUARD_UTIL
|
||||||
|
#define _INCLUDE_GUARD_UTIL
|
||||||
|
|
||||||
|
//Returns true if the current script is running in the unscheduled environment and otherwise false.
|
||||||
|
//If true a script error is also produced however this can be ignored.
|
||||||
|
//#define Util_IsUncheduled() ([diag_frameNo, sleep 0.005, diag_frameNo] call { _this select 0 == _this select 2 })
|
||||||
|
|
||||||
|
/* Send public variables atomically without fear of race conditions. The previous value of the
|
||||||
|
variable is restored automatically after transmission. For example:
|
||||||
|
my_variable = 1;
|
||||||
|
Util_PublicVariable(my_variable, 1337);
|
||||||
|
diag_log str my_variable; //1
|
||||||
|
*/
|
||||||
|
#define Util_PublicVariable(variable, value) ([variable, value] call dz_fn_util_pv)
|
||||||
|
#define Util_PublicVariable_Fast(variable, value) (missionNamespace setVariable [variable, [missionNamespace getVariable (variable), missionNamespace setVariable [variable, value], publicVariable (variable)] select 0])
|
||||||
|
#define Util_PublicVariableServer(variable, value) ([variable, value] call dz_fn_util_pvs)
|
||||||
|
#define Util_PublicVariableServer_Fast(variable, value) (missionNamespace setVariable [variable, [missionNamespace getVariable (variable), missionNamespace setVariable [variable, value], publicVariableServer (variable)] select 0])
|
||||||
|
#define Util_PublicVariableClient(variable, value, client) ([variable, value, client] call dz_fn_util_pvc)
|
||||||
|
#define Util_PublicVariableClient_Fast(variable, value, client) (missionNamespace setVariable [variable, [missionNamespace getVariable (variable), missionNamespace setVariable [variable, value], (client) publicVariableClient (variable)] select 0])
|
||||||
|
|
||||||
|
//Waits until the specified predicate is true, or at most the specified time in seconds.
|
||||||
|
//Returns true if the predicate is true, false if timed out.
|
||||||
|
//Note: the predicate is evaluated once each frame. Expensive operations may cause performance issues.
|
||||||
|
#define Util_WaitUntil(predicate, timeout) ([_this, predicate, timeout, diag_tickTime] call dz_fn_util_waitUntil)
|
||||||
|
|
||||||
|
#endif
|
||||||
87
SQF/dayz_code/util/Vector.hpp
Normal file
87
SQF/dayz_code/util/Vector.hpp
Normal file
@@ -0,0 +1,87 @@
|
|||||||
|
/* Provides functions and constants for working with 3D vectors.
|
||||||
|
|
||||||
|
Author: Foxy
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef _INCLUDE_GUARD_VECTOR
|
||||||
|
#define _INCLUDE_GUARD_VECTOR
|
||||||
|
|
||||||
|
//Vector constants
|
||||||
|
#define Vector_NULL [ 0, 0, 0]
|
||||||
|
#define Vector_UP [ 0, 0, 1]
|
||||||
|
#define Vector_DOWN [ 0, 0,-1]
|
||||||
|
#define Vector_NORTH [ 0, 1, 0]
|
||||||
|
#define Vector_SOUTH [ 0,-1, 0]
|
||||||
|
#define Vector_EAST [ 1, 0, 0]
|
||||||
|
#define Vector_WEST [-1, 0, 0]
|
||||||
|
#define Vector_FRONT Vector_NORTH
|
||||||
|
#define Vector_BACK Vector_SOUTH
|
||||||
|
#define Vector_RIGHT Vector_EAST
|
||||||
|
#define Vector_LEFT Vector_WEST
|
||||||
|
|
||||||
|
#define Vector_New(x,y,z) [z,y,z]
|
||||||
|
|
||||||
|
//Accessors
|
||||||
|
#define Vector_X(v) ((v) select 0)
|
||||||
|
#define Vector_Y(v) ((v) select 1)
|
||||||
|
#define Vector_Z(v) ((v) select 2)
|
||||||
|
|
||||||
|
//Setters
|
||||||
|
#define Vector_SetX(v, x) ((v) set [0, x])
|
||||||
|
#define Vector_SetY(v, x) ((v) set [1, x])
|
||||||
|
#define Vector_SetZ(v, x) ((v) set [2, x])
|
||||||
|
|
||||||
|
//Calculates the dot product of the given vectors
|
||||||
|
#define Vector_DotProduct(a,b) ([a,b] call dz_fn_vector_dotProduct)
|
||||||
|
#define Vector_DotProduct_Fast(a,b) (Vector_X(a) * Vector_X(b) + Vector_Y(a) * Vector_Y(b) + Vector_Z(a) * Vector_Z(b))
|
||||||
|
|
||||||
|
//Calculates the cross product of the given vectors
|
||||||
|
#define Vector_CrossProduct(a,b) ([a,b] call dz_fn_vector_crossProduct)
|
||||||
|
#define Vector_CrossProduct_Fast(a,b) [Vector_Y(a) * Vector_Z(b) - Vector_Z(a) * Vector_Y(b), Vector_Z(a) * Vector_X(b) - Vector_X(a) * Vector_Z(b), Vector_X(a) * Vector_Y(b) - Vector_Y(a) * Vector_X(b)]
|
||||||
|
|
||||||
|
//Magnitude (length) of the vector
|
||||||
|
#define Vector_Magnitude(v) ((v) call dz_fn_vector_magnitude)
|
||||||
|
#define Vector_Magnitude_Fast(v) (sqrt( Vector_X(v)^2 + Vector_Y(v)^2 + Vector_Z(v)^2))
|
||||||
|
|
||||||
|
//Adds two vectors together
|
||||||
|
#define Vector_Add(a,b) ([a,b] call dz_fn_vector_add)
|
||||||
|
#define Vector_Add_Fast(a,b) [Vector_X(a) + Vector_X(b), Vector_Y(a) + Vector_Y(b), Vector_Z(a) + Vector_Z(b)]
|
||||||
|
|
||||||
|
//Subtract second vector from the first
|
||||||
|
#define Vector_Subtract(a,b) ([a,b] call dz_fn_vector_subtract)
|
||||||
|
#define Vector_Subtract_Fast(a,b) [Vector_X(a) - Vector_X(b), Vector_Y(a) - Vector_Y(b), Vector_Z(a) - Vector_Z(b)]
|
||||||
|
|
||||||
|
//Returns the opposite vector of the given vector
|
||||||
|
#define Vector_Negate(v) ((v) call dz_fn_vector_negate)
|
||||||
|
#define Vector_Negate_Fast(v) [-Vector_X(v), -Vector_Y(v), -Vector_Z(v)]
|
||||||
|
|
||||||
|
//Multiplies the vector by a real number
|
||||||
|
#define Vector_Multiply(v,d) ([v,d] call dz_fn_vector_multiply)
|
||||||
|
#define Vector_Multiply_Fast(v,d) [Vector_X(v) * (d), Vector_Y(v) * (d), Vector_Z(v) * (d)]
|
||||||
|
|
||||||
|
//Divides the vector by a real number
|
||||||
|
#define Vector_Divide(v,d) ([v,d] call dz_fn_vector_divide)
|
||||||
|
#define Vector_Divide_Fast(v,d) [Vector_X(v) / (d), Vector_Y(v) / (d), Vector_Z(v) / (d)]
|
||||||
|
|
||||||
|
//Calculates the angle between two given vectors
|
||||||
|
#define Vector_Angle(a,b) ([a,b] call dz_fn_vector_angle)
|
||||||
|
#define Vector_Angle_Fast(a,b) (acos(Vector_DotProduct_Fast(a,b) / Vector_Magnitude_Fast(a) * Vector_Magnitude_Fast(b)))
|
||||||
|
|
||||||
|
//Returns a vector with the same direction as the argument and a magnitude of 1.
|
||||||
|
#define Vector_Normalize(v) ((v) call dz_fn_vector_normalize)
|
||||||
|
#define Vector_Normalize_Fast(v) Vector_Divide(v, Vector_Magnitude_Fast(v))
|
||||||
|
//TODO: performance profiling Divide vs Divide_Fast
|
||||||
|
|
||||||
|
//Returns a horizontal unit vector pointing in the specified direction (degrees).
|
||||||
|
#define Vector_FromDir(deg) ((deg) call dz_fn_vector_fromDir)
|
||||||
|
#define Vector_FromDir_Fast(deg) [sin (deg), cos (deg), 0]
|
||||||
|
|
||||||
|
//Rotates the vector around the global Z (up) axis by the specified angle in degrees
|
||||||
|
#define Vector_Rotate2D(v, deg) ([v, deg] call dz_fn_vector_rotate2d)
|
||||||
|
#define Vector_Rotate2D_Fast(v, deg) [Vector_X(v) * cos -(deg) - Vector_Y(v) * sin -(deg), Vector_X(v) * sin -(deg) + Vector_Y(v) * cos -(deg), Vector_Z(v)]
|
||||||
|
|
||||||
|
//Rotates the vector around the specified axis by the specified angle in degrees, in three dimensions.
|
||||||
|
#define Vector_Rotate3D(v, u, deg) ([v, u, deg] call dz_fn_vector_rotate3d)
|
||||||
|
#define Vector_Rotate3D_Fast(v, u, deg) [((v)select0)*(((u)select0)^2*(1-cos(deg))+cos(deg))+((v)select1)*(((u)select0)*((u)select1)*(1-cos(deg))-((u)select2)*sin(deg))+((v)select2)*(((u)select0)*((u)select2)*(1-cos(deg))+((u)select1)*sin(deg)),((v)select0)*(((u)select1)*((u)select0)*(1-cos(deg))+((u)select2)*sin(deg))+((v)select1)*(((u)select1)^2*(1-cos(deg))+cos(deg))+((v)select2)*(((u)select1)*((u)select2)*(1-cos(deg))-((u)select0)*sin(deg)),((v)select0)*(((u)select2)*((u)select0)*(1-cos(deg))-((u)select1)*sin(deg))+((v)select1)*(((u)select2)*((u)select1)*(1-cos(deg))+((u)select0)*sin(deg))+((v)select2)*(((u)select2)^2*(1-cos(deg))+cos(deg))]
|
||||||
|
|
||||||
|
#endif
|
||||||
137
SQF/dayz_code/util/array.sqf
Normal file
137
SQF/dayz_code/util/array.sqf
Normal file
@@ -0,0 +1,137 @@
|
|||||||
|
#include "Array.hpp"
|
||||||
|
|
||||||
|
//Returns true if the given predicate evaluates to true for any element in the array
|
||||||
|
dz_fn_array_any =
|
||||||
|
{
|
||||||
|
{
|
||||||
|
if (_x call (_this select 1)) exitWith { true };
|
||||||
|
false
|
||||||
|
}
|
||||||
|
foreach (_this select 0);
|
||||||
|
};
|
||||||
|
|
||||||
|
//Returns true if the given predicate evaluates to true for all elements in the array
|
||||||
|
dz_fn_array_all =
|
||||||
|
{
|
||||||
|
{
|
||||||
|
if !(_x call (_this select 1)) exitWith { false };
|
||||||
|
true
|
||||||
|
}
|
||||||
|
foreach (_this select 0);
|
||||||
|
};
|
||||||
|
|
||||||
|
//Returns the first element in the array for which the given predicate evaluates to true. nil if not found
|
||||||
|
dz_fn_array_first =
|
||||||
|
{
|
||||||
|
{
|
||||||
|
if (_x call (_this select 1)) exitWith { _x };
|
||||||
|
nil
|
||||||
|
}
|
||||||
|
foreach (_this select 0);
|
||||||
|
};
|
||||||
|
|
||||||
|
dz_fn_array_getSet =
|
||||||
|
{
|
||||||
|
Array_GetSet_Fast(_this select 0, _this select 1, _this select 2);
|
||||||
|
};
|
||||||
|
|
||||||
|
//Selects a random element from the array
|
||||||
|
dz_fn_array_selectRandom =
|
||||||
|
{
|
||||||
|
_this select floor random count _this
|
||||||
|
};
|
||||||
|
|
||||||
|
//Shuffle using the Fisher-Yates algorithm. Complexity: O(n)
|
||||||
|
dz_fn_array_shuffle =
|
||||||
|
{
|
||||||
|
private ["_i", "_r", "_t"];
|
||||||
|
for "_i" from (count _this) - 1 to 1 step -1 do
|
||||||
|
{
|
||||||
|
//Select random index
|
||||||
|
_r = floor random (_i + 1);
|
||||||
|
|
||||||
|
//Swap
|
||||||
|
if (_i != _r) then
|
||||||
|
{
|
||||||
|
_t = _this select _i;
|
||||||
|
_this set [_i, _this select _r];
|
||||||
|
_this set [_r, _t];
|
||||||
|
};
|
||||||
|
};
|
||||||
|
_this
|
||||||
|
};
|
||||||
|
|
||||||
|
dz_fn_array_mergeSort =
|
||||||
|
{
|
||||||
|
private ["_offset", "_length", "_alen", "_blen", "_ai", "_bi", "_temp"];
|
||||||
|
|
||||||
|
//Root call
|
||||||
|
if (count _this == 2) then
|
||||||
|
{
|
||||||
|
_offset = 0;
|
||||||
|
_length = count (_this select 0);
|
||||||
|
}
|
||||||
|
//Recursive call
|
||||||
|
else
|
||||||
|
{
|
||||||
|
_offset = _this select 2;
|
||||||
|
_length = _this select 3;
|
||||||
|
};
|
||||||
|
|
||||||
|
if (_length <= 1) exitWith {};
|
||||||
|
|
||||||
|
_alen = round (_length / 2);
|
||||||
|
_blen = _length - _alen;
|
||||||
|
|
||||||
|
[_this select 0, _this select 1, _offset, _alen] call dz_fn_array_mergeSort;
|
||||||
|
[_this select 0, _this select 1, _offset + _alen, _blen] call dz_fn_array_mergeSort;
|
||||||
|
|
||||||
|
_ai = 0;
|
||||||
|
_bi = 0;
|
||||||
|
|
||||||
|
_temp = [];
|
||||||
|
_temp resize _length;
|
||||||
|
|
||||||
|
#define A_NEXT (_this select 0) select (_offset + _ai)
|
||||||
|
#define B_NEXT (_this select 0) select (_offset + _alen + _bi)
|
||||||
|
|
||||||
|
for "_i" from 0 to _length - 1 do
|
||||||
|
{
|
||||||
|
switch (true) do
|
||||||
|
{
|
||||||
|
case (_ai == _alen):
|
||||||
|
{
|
||||||
|
_temp set [_i, B_NEXT];
|
||||||
|
_bi = _bi + 1;
|
||||||
|
};
|
||||||
|
|
||||||
|
case (_bi == _blen):
|
||||||
|
{
|
||||||
|
_temp set [_i, A_NEXT];
|
||||||
|
_ai = _ai + 1;
|
||||||
|
};
|
||||||
|
|
||||||
|
case (([A_NEXT, B_NEXT] call (_this select 1)) > 0):
|
||||||
|
{
|
||||||
|
_temp set [_i, A_NEXT];
|
||||||
|
_ai = _ai + 1;
|
||||||
|
};
|
||||||
|
|
||||||
|
default
|
||||||
|
{
|
||||||
|
_temp set [_i, B_NEXT];
|
||||||
|
_bi = _bi + 1;
|
||||||
|
};
|
||||||
|
};
|
||||||
|
};
|
||||||
|
|
||||||
|
#undef A_NEXT
|
||||||
|
#undef B_NEXT
|
||||||
|
|
||||||
|
for "_i" from 0 to _length - 1 do
|
||||||
|
{
|
||||||
|
(_this select 0) set [_offset + _i, _temp select _i];
|
||||||
|
};
|
||||||
|
|
||||||
|
_this select 0
|
||||||
|
};
|
||||||
22
SQF/dayz_code/util/compile.sqf
Normal file
22
SQF/dayz_code/util/compile.sqf
Normal file
@@ -0,0 +1,22 @@
|
|||||||
|
#define STRINGIFY(x) #x
|
||||||
|
#define PATH(sub_path) STRINGIFY(\z\addons\dayz_code\util\sub_path)
|
||||||
|
#define CCPP call compile preprocessFileLineNumbers
|
||||||
|
|
||||||
|
//Debug
|
||||||
|
CCPP PATH(debug.sqf);
|
||||||
|
|
||||||
|
//Very generic utilities
|
||||||
|
CCPP PATH(util.sqf);
|
||||||
|
CCPP PATH(mutex.sqf);
|
||||||
|
CCPP PATH(math.sqf);
|
||||||
|
CCPP PATH(array.sqf);
|
||||||
|
|
||||||
|
//Collections
|
||||||
|
CCPP PATH(stack.sqf);
|
||||||
|
CCPP PATH(queue.sqf);
|
||||||
|
CCPP PATH(dictionary.sqf);
|
||||||
|
|
||||||
|
//Specialized
|
||||||
|
CCPP PATH(vector.sqf);
|
||||||
|
CCPP PATH(task.sqf);
|
||||||
|
CCPP PATH(request.sqf);
|
||||||
42
SQF/dayz_code/util/debug.sqf
Normal file
42
SQF/dayz_code/util/debug.sqf
Normal file
@@ -0,0 +1,42 @@
|
|||||||
|
#include "Debug.hpp"
|
||||||
|
|
||||||
|
#ifdef _DEBUG_
|
||||||
|
|
||||||
|
dz_fn_debug_checkType =
|
||||||
|
{
|
||||||
|
#define IS_ARRAY(x) (typeName x == typeName [])
|
||||||
|
|
||||||
|
if (_exp == "ANY")
|
||||||
|
exitWith { true };
|
||||||
|
|
||||||
|
if (isNil "_x")
|
||||||
|
exitWith { _exp == "NIL" || { IS_ARRAY(_exp) && { "NIL" in _exp } } };
|
||||||
|
|
||||||
|
typeName _x == _exp || { IS_ARRAY(_exp) && { typeName _x in _exp } }
|
||||||
|
|
||||||
|
#undef IS_ARRAY
|
||||||
|
};
|
||||||
|
|
||||||
|
dz_fn_debug_checkTypes =
|
||||||
|
{
|
||||||
|
private "_exp";
|
||||||
|
|
||||||
|
{
|
||||||
|
_exp = (_this select 1) select (_foreachIndex min (count (_this select 1) - 1));
|
||||||
|
|
||||||
|
if (!call dz_fn_debug_checkType) then
|
||||||
|
{
|
||||||
|
assert false;
|
||||||
|
|
||||||
|
diag_log format ['ERROR: Type check failed in file "%1" on line %2. Index:%3 Type:%4 Expected:%5',
|
||||||
|
_this select 2,
|
||||||
|
_this select 3,
|
||||||
|
_foreachIndex,
|
||||||
|
if (isNil "_x") then { "nil" } else { typeName _x },
|
||||||
|
_exp];
|
||||||
|
};
|
||||||
|
}
|
||||||
|
foreach (_this select 0);
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif
|
||||||
67
SQF/dayz_code/util/dictionary.sqf
Normal file
67
SQF/dayz_code/util/dictionary.sqf
Normal file
@@ -0,0 +1,67 @@
|
|||||||
|
#define GET_COUNT(d) ((d) select 0)
|
||||||
|
#define SET_COUNT(d, c) ((d) set [0, c])
|
||||||
|
#define GET_SIZE(d) (count GET_KEYS(d))
|
||||||
|
#define GET_KEYS(d) ((d) select 1)
|
||||||
|
#define GET_VALUES(d) ((d) select 2)
|
||||||
|
#define GET_INDEX(d, k) (GET_KEYS(d) find (k))
|
||||||
|
|
||||||
|
dz_fn_dictionary_containsKey =
|
||||||
|
{
|
||||||
|
GET_INDEX(_this select 0, _this select 1) != -1
|
||||||
|
};
|
||||||
|
|
||||||
|
dz_fn_dictionary_add =
|
||||||
|
{
|
||||||
|
if (GET_INDEX(_this select 0, _this select 1) == -1) exitWith {false};
|
||||||
|
|
||||||
|
private "_index";
|
||||||
|
_index = count GET_KEYS(_this select 0);
|
||||||
|
GET_KEYS(_this select 0) set [_index, _this select 1];
|
||||||
|
GET_VALUES(_this select 0) set [_index, _this select 2];
|
||||||
|
SET_COUNT(_this select 0, GET_COUNT(_this select 0) + 1);
|
||||||
|
|
||||||
|
true
|
||||||
|
};
|
||||||
|
|
||||||
|
dz_fn_dictionary_get =
|
||||||
|
{
|
||||||
|
private "_index";
|
||||||
|
_index = GET_INDEX(_this select 0, _this select 1);
|
||||||
|
if (_index == -1) exitWith {nil};
|
||||||
|
GET_VALUES(_this select 0) select _index
|
||||||
|
};
|
||||||
|
|
||||||
|
dz_fn_dictionary_remove =
|
||||||
|
{
|
||||||
|
private "_index";
|
||||||
|
_index = GET_INDEX(_this select 0, _this select 1);
|
||||||
|
if (_index == -1) exitWith {false};
|
||||||
|
GET_KEYS(_this select 0) set [_index, nil];
|
||||||
|
GET_VALUES(_this select 0) set [_index, nil];
|
||||||
|
SET_COUNT(_this select 0, GET_COUNT(_this select 0) - 1);
|
||||||
|
|
||||||
|
true
|
||||||
|
};
|
||||||
|
|
||||||
|
dz_fn_dictionary_compact =
|
||||||
|
{
|
||||||
|
private ["_keys", "_values", "_i"];
|
||||||
|
_keys = [];
|
||||||
|
_values = [];
|
||||||
|
_keys resize (_this);
|
||||||
|
_values resize (_this);
|
||||||
|
_i = 0;
|
||||||
|
|
||||||
|
{
|
||||||
|
if (!isNil "_x") then
|
||||||
|
{
|
||||||
|
_keys set [_i, _x];
|
||||||
|
_values set [_i, GET_VALUES(_this) select _forEachIndex];
|
||||||
|
_i = _i + 1;
|
||||||
|
};
|
||||||
|
}
|
||||||
|
foreach GET_KEYS(_this);
|
||||||
|
|
||||||
|
_this set [1, _keys];
|
||||||
|
_this set [2, _values];
|
||||||
|
};
|
||||||
40
SQF/dayz_code/util/math.sqf
Normal file
40
SQF/dayz_code/util/math.sqf
Normal file
@@ -0,0 +1,40 @@
|
|||||||
|
dz_fn_math_gcd =
|
||||||
|
{
|
||||||
|
private ["_a","_b","_t"];
|
||||||
|
|
||||||
|
_a = _this select 0;
|
||||||
|
_b = _this select 1;
|
||||||
|
|
||||||
|
while {_b != 0} do
|
||||||
|
{
|
||||||
|
_t = _b;
|
||||||
|
_b = _a % _b;
|
||||||
|
_a = _t;
|
||||||
|
};
|
||||||
|
|
||||||
|
_a
|
||||||
|
};
|
||||||
|
|
||||||
|
dz_fn_math_gcdx =
|
||||||
|
{
|
||||||
|
if ((count _this) == 0) exitWith { 1 };
|
||||||
|
if ((count _this) == 1) exitWith { _this select 0 };
|
||||||
|
|
||||||
|
private "_gcd";
|
||||||
|
|
||||||
|
_gcd = [_this select 0, _this select 1] call dz_fn_math_gcd;
|
||||||
|
|
||||||
|
for "_i" from 2 to (count _this) - 1 do
|
||||||
|
{
|
||||||
|
if (_gcd == 1) exitWith {};
|
||||||
|
|
||||||
|
_gcd = [_gcd, _this select _i] call dz_fn_math_gcd;
|
||||||
|
};
|
||||||
|
|
||||||
|
_gcd
|
||||||
|
};
|
||||||
|
|
||||||
|
dz_fn_math_randomRange =
|
||||||
|
{
|
||||||
|
(_this select 0) + random ((_this select 1) - (_this select 0))
|
||||||
|
};
|
||||||
11
SQF/dayz_code/util/mutex.sqf
Normal file
11
SQF/dayz_code/util/mutex.sqf
Normal file
@@ -0,0 +1,11 @@
|
|||||||
|
#include "Mutex.hpp"
|
||||||
|
|
||||||
|
dz_fn_mutex_tryLock =
|
||||||
|
{
|
||||||
|
Mutex_TryLock_Fast(_this);
|
||||||
|
};
|
||||||
|
|
||||||
|
dz_fn_mutex_waitLock =
|
||||||
|
{
|
||||||
|
Mutex_WaitLock_Fast(_this);
|
||||||
|
};
|
||||||
151
SQF/dayz_code/util/player.sqf
Normal file
151
SQF/dayz_code/util/player.sqf
Normal file
@@ -0,0 +1,151 @@
|
|||||||
|
#define DEBUG_STEP() call { dbg_step = false; waitUntil {dbg_step}; }
|
||||||
|
|
||||||
|
#include "Debug.hpp"
|
||||||
|
#include "Player.hpp"
|
||||||
|
|
||||||
|
#define WeaponSlotPrimary 1
|
||||||
|
#define WeaponSlotHandGun 2
|
||||||
|
#define WeaponSlotSecondary 4
|
||||||
|
#define WeaponSlotHandGunItem 16
|
||||||
|
#define WeaponSlotItem 256
|
||||||
|
#define WeaponSlotBinocular 4096
|
||||||
|
#define WeaponHardMounted 65536
|
||||||
|
#define WeaponSlotInventory 131072
|
||||||
|
|
||||||
|
#define IS_MAGAZINE(type) (type == WeaponSlotHandGunItem || type == WeaponSlotItem)
|
||||||
|
|
||||||
|
dz_player_invTypes = [WeaponSlotPrimary, WeaponSlotHandGun, WeaponSlotSecondary, WeaponSlotHandGunItem, WeaponSlotItem, WeaponSlotBinocular, WeaponHardMounted, WeaponSlotInventory];
|
||||||
|
dz_player_invSlots = [call compile getText (configFile >> "CfgVehicles" >> Player_BASE)] call BIS_FNC_invCodeToArray;
|
||||||
|
//dz_player_invSlots = [1,1,1,8,12,2,0,12];
|
||||||
|
|
||||||
|
dz_fn_player_numItems =
|
||||||
|
{
|
||||||
|
if (_this == 0) exitWith { 0 };
|
||||||
|
|
||||||
|
Debug_Assert(_this in dz_player_invTypes);
|
||||||
|
|
||||||
|
if (IS_MAGAZINE(_this)) then
|
||||||
|
{ { _this == getNumber (configFile >> "CfgMagazines" >> _x >> "type") } count magazines player; }
|
||||||
|
else
|
||||||
|
{ { _this == getNumber (configFile >> "CfgWeapons" >> _x >> "type") } count weapons player; };
|
||||||
|
};
|
||||||
|
|
||||||
|
dz_fn_player_numEmptySlots =
|
||||||
|
{
|
||||||
|
if (_this == 0) exitWith { 1000000 };
|
||||||
|
Debug_Assert(_this in dz_player_invTypes);
|
||||||
|
Player_NumSlots(_this) - Player_NumItems(_this);
|
||||||
|
};
|
||||||
|
|
||||||
|
dz_fn_player_addItem =
|
||||||
|
{
|
||||||
|
Debug_CheckParams2("SCALAR","STRING");
|
||||||
|
|
||||||
|
private ["_type", "_veh", "_num"];
|
||||||
|
|
||||||
|
switch (_this select 0) do
|
||||||
|
{
|
||||||
|
case 0:
|
||||||
|
{
|
||||||
|
_type = getNumber (configFile >> "CfgWeapons" >> _this select 1 >> "type");
|
||||||
|
|
||||||
|
if (_type == 0 || { Player_NumEmptySlots(_type) > 0 } ) exitWith
|
||||||
|
{
|
||||||
|
player addWeapon (_this select 1);
|
||||||
|
Player_AddItem_RESULT_PLAYER
|
||||||
|
};
|
||||||
|
|
||||||
|
_veh = vehicle player;
|
||||||
|
|
||||||
|
if (player != _veh) exitWith
|
||||||
|
{
|
||||||
|
_num = 0;
|
||||||
|
{ _num = _num + _x; } foreach (getWeaponCargo _veh select 1);
|
||||||
|
|
||||||
|
if (_num < getNumber (configFile >> "CfgVehicles" >> typeOf _veh >> "transportMaxWeapons")) exitWith
|
||||||
|
{
|
||||||
|
_veh addWeaponCargoGlobal [_this select 1, 1];
|
||||||
|
Player_AddItem_RESULT_VEHICLE
|
||||||
|
};
|
||||||
|
|
||||||
|
Player_AddItem_RESULT_FAILURE
|
||||||
|
};
|
||||||
|
|
||||||
|
Player_DropWeapon(_this select 1);
|
||||||
|
Player_AddItem_RESULT_GROUND
|
||||||
|
};
|
||||||
|
|
||||||
|
case 1:
|
||||||
|
{
|
||||||
|
_type = getNumber (configFile >> "CfgMagazines" >> _this select 1 >> "type");
|
||||||
|
|
||||||
|
if (_type == 0 || { Player_NumEmptySlots(_type) > 0 } ) exitWith
|
||||||
|
{
|
||||||
|
player addMagazine (_this select 1);
|
||||||
|
Player_AddItem_RESULT_PLAYER
|
||||||
|
};
|
||||||
|
|
||||||
|
_veh = vehicle player;
|
||||||
|
|
||||||
|
if (player != _veh) exitWith
|
||||||
|
{
|
||||||
|
_num = 0;
|
||||||
|
{ _num = _num + _x; } foreach (getMagazineCargo _veh select 1);
|
||||||
|
|
||||||
|
if (_num < getNumber (configFile >> "CfgVehicles" >> typeOf _veh >> "transportMaxMagazines")) exitWith
|
||||||
|
{
|
||||||
|
_veh addMagazineCargoGlobal [_this select 1, 1];
|
||||||
|
Player_AddItem_RESULT_VEHICLE
|
||||||
|
};
|
||||||
|
|
||||||
|
Player_AddItem_RESULT_FAILURE
|
||||||
|
};
|
||||||
|
|
||||||
|
Player_DropMagazine(_this select 1);
|
||||||
|
Player_AddItem_RESULT_GROUND
|
||||||
|
};
|
||||||
|
};
|
||||||
|
};
|
||||||
|
|
||||||
|
dz_fn_player_dropItem =
|
||||||
|
{
|
||||||
|
#define DROP_ITEM_WEAPON_HOLDER_SEARCH_RADIUS 2
|
||||||
|
#define DROP_ITEM_WEAPON_HOLDER_PLAYER_OFFSET [0,0,0]
|
||||||
|
|
||||||
|
Debug_Assert(!Player_IsOnLadder());
|
||||||
|
|
||||||
|
if (Player_IsInVehicle()) exitWith
|
||||||
|
{
|
||||||
|
diag_log "WARNING: dz_fn_player_dropItem called while player was in a vehicle.";
|
||||||
|
objNull
|
||||||
|
};
|
||||||
|
|
||||||
|
private ["_pos","_near","_wh"];
|
||||||
|
|
||||||
|
//Lets get the location of the player in the world
|
||||||
|
_pos = player modeltoWorld DROP_ITEM_WEAPON_HOLDER_PLAYER_OFFSET;
|
||||||
|
_pos set [2, 0];
|
||||||
|
|
||||||
|
//Find WeaponHolders close to the player.
|
||||||
|
_near = _pos nearObjects ["WeaponHolder", DROP_ITEM_WEAPON_HOLDER_SEARCH_RADIUS];
|
||||||
|
|
||||||
|
_wh = nil;
|
||||||
|
|
||||||
|
if (count _near == 0) then
|
||||||
|
{ _wh = createVehicle ["WeaponHolder", _pos, [], 0, "CAN_COLLIDE"]; }
|
||||||
|
else
|
||||||
|
{ _wh = _near select 0; };
|
||||||
|
|
||||||
|
if (_this select 0 == 0) then
|
||||||
|
{ _wh addWeaponCargoGlobal [_this select 1, 1]; }
|
||||||
|
else
|
||||||
|
{ _wh addMagazineCargoGlobal [_this select 1, 1]; };
|
||||||
|
|
||||||
|
//Reveal the item
|
||||||
|
player reveal _wh;
|
||||||
|
|
||||||
|
_wh
|
||||||
|
|
||||||
|
#undef DROP_ITEM_WEAPON_HOLDER_SEARCH_RADIUS
|
||||||
|
#undef DROP_ITEM_WEAPON_HOLDER_PLAYER_OFFSET
|
||||||
|
};
|
||||||
55
SQF/dayz_code/util/queue.sqf
Normal file
55
SQF/dayz_code/util/queue.sqf
Normal file
@@ -0,0 +1,55 @@
|
|||||||
|
/* Implemented as a circular buffer.
|
||||||
|
See https://en.wikipedia.org/wiki/Circular_buffer
|
||||||
|
*/
|
||||||
|
|
||||||
|
#define GET_COUNT(q) ((q) select 0)
|
||||||
|
#define GET_FRONT(q) ((q) select 1)
|
||||||
|
#define GET_ARRAY(q) ((q) select 2)
|
||||||
|
#define GET_SIZE(q) (count GET_ARRAY(q))
|
||||||
|
#define SET_COUNT(q, p) ((q) set [0, p])
|
||||||
|
#define SET_FRONT(q, p) ((q) set [1, p])
|
||||||
|
#define GET_INDEX(q) ((GET_FRONT(q) + GET_COUNT(q) - 1) % GET_SIZE(q))
|
||||||
|
|
||||||
|
dz_fn_queue_new =
|
||||||
|
{
|
||||||
|
private "_q";
|
||||||
|
_q = [0, 0, []];
|
||||||
|
GET_ARRAY(_q) resize _this;
|
||||||
|
_q
|
||||||
|
};
|
||||||
|
|
||||||
|
dz_fn_queue_enqueue =
|
||||||
|
{
|
||||||
|
if (GET_COUNT(_this select 0) == GET_SIZE(_this select 0)) exitWith {false};
|
||||||
|
SET_COUNT(_this select 0, GET_COUNT(_this select 0) + 1);
|
||||||
|
GET_ARRAY(_this select 0) set [GET_INDEX(_this select 0), _this select 1];
|
||||||
|
true
|
||||||
|
};
|
||||||
|
|
||||||
|
dz_fn_queue_dequeue =
|
||||||
|
{
|
||||||
|
if (GET_COUNT(_this) == 0) exitWith {nil};
|
||||||
|
private "_e";
|
||||||
|
_e = GET_ARRAY(_this) select GET_FRONT(_this);
|
||||||
|
GET_ARRAY(_this) set [GET_FRONT(_this), nil];
|
||||||
|
SET_COUNT(_this, GET_COUNT(_this) - 1);
|
||||||
|
SET_FRONT(_this, (GET_FRONT(_this) + 1) % GET_SIZE(_this));
|
||||||
|
_e
|
||||||
|
};
|
||||||
|
|
||||||
|
dz_fn_queue_peek =
|
||||||
|
{
|
||||||
|
if (GET_COUNT(_this) == 0) exitWith {nil};
|
||||||
|
GET_ARRAY(_this) select GET_INDEX(_this);
|
||||||
|
};
|
||||||
|
|
||||||
|
dz_fn_queue_isFull =
|
||||||
|
{
|
||||||
|
GET_COUNT(_this) == GET_SIZE(_this)
|
||||||
|
};
|
||||||
|
|
||||||
|
//TODO: Queue::Resize()
|
||||||
|
dz_fn_queue_resize =
|
||||||
|
{
|
||||||
|
assert (false);
|
||||||
|
};
|
||||||
41
SQF/dayz_code/util/readme.txt
Normal file
41
SQF/dayz_code/util/readme.txt
Normal file
@@ -0,0 +1,41 @@
|
|||||||
|
Author: Foxy https://github.com/AsFoxy
|
||||||
|
|
||||||
|
Here are defined in their own header and code files a variety of utility classes. See the header
|
||||||
|
files for more information about each class and their functions.
|
||||||
|
|
||||||
|
Object oriented classes like Dictionary and Mutex are used to create and utilize objects in a way
|
||||||
|
similar to object oriented C. The object in member functions is always the first parameter. For
|
||||||
|
example:
|
||||||
|
_myDictionary = Dictionary_New();
|
||||||
|
Dictionary_Add(_myDictionary, _myKey, _myValue);
|
||||||
|
|
||||||
|
Some headers define functions suffixed with "Fast" alongside normal counterparts. For example
|
||||||
|
Vector_DotProduct and Vector_DotProduct_Fast in Vector.hpp. The suffixed functions are inlined and
|
||||||
|
as such have very slightly less overhead. The unsuffixed functions should be used when one of the
|
||||||
|
arguments passed is a complex or intensive expression. Each expression passed may be evaluated
|
||||||
|
multiple times when using the suffixed functions. Because of this especially expressions with side
|
||||||
|
effects should not be used. For example:
|
||||||
|
//Good
|
||||||
|
Vector_Multiply_Fast(_myVector, _this select 3);
|
||||||
|
|
||||||
|
//Totally fine but slightly less performant
|
||||||
|
Vector_Multiply(_myVector, _this select 3);
|
||||||
|
|
||||||
|
//BAD!
|
||||||
|
Vector_Multiply_Fast(_myVector, call _my_heavy_function_with_side_effects);
|
||||||
|
|
||||||
|
//Good
|
||||||
|
Vector_Multiply(_myVector, call _my_heavy_function_with_side_effects);
|
||||||
|
|
||||||
|
Function macros parsed by the Arma preprocessor in general must receive arguments that do not
|
||||||
|
contain commas, unless wrapped by another function macro. For example:
|
||||||
|
//Does not work
|
||||||
|
_result = Vector_Add([1,2,3], [4,5,6]);
|
||||||
|
|
||||||
|
//Instead:
|
||||||
|
_myVector1 = [1,2,3];
|
||||||
|
_myVector2 = [4,5,6];
|
||||||
|
_result = Vector_Add(_myVector1, _myVector2);
|
||||||
|
|
||||||
|
//Or:
|
||||||
|
_result = Vector_Add(Vector_New(1,2,3), Vector_New(4,5,6));
|
||||||
174
SQF/dayz_code/util/request.sqf
Normal file
174
SQF/dayz_code/util/request.sqf
Normal file
@@ -0,0 +1,174 @@
|
|||||||
|
#include "Util.hpp"
|
||||||
|
#include "Request.hpp"
|
||||||
|
#include "Array.hpp"
|
||||||
|
#include "Mutex.hpp"
|
||||||
|
#include "Dictionary.hpp"
|
||||||
|
#include "Debug.hpp"
|
||||||
|
|
||||||
|
#define Request_New(id) [dz_owner, id]
|
||||||
|
#define Request_GetOwner(request) ((request) select 0)
|
||||||
|
#define Request_GetID(request) ((request) select 1)
|
||||||
|
#define Request_SetResult(request, result) ((request) set [2, result])
|
||||||
|
#define Request_GetResult(request) ((request) select 2)
|
||||||
|
|
||||||
|
#define Reply_GetID(reply) ((reply) select 0)
|
||||||
|
#define Reply_GetResult(reply) ((reply) select 1)
|
||||||
|
|
||||||
|
#define Request_Server_GetFunc(request) ((request) select 2)
|
||||||
|
#define Request_Server_GetArgs(request) ((request) select 3)
|
||||||
|
#define Request_Server_ExpectsReply(request) (Request_GetID(request) >= 0)
|
||||||
|
|
||||||
|
//TODO: make work for non-dedicated server as well?
|
||||||
|
|
||||||
|
if (!isServer) then //CLIENT
|
||||||
|
{
|
||||||
|
dz_request_mutex = Mutex_New();
|
||||||
|
dz_request_list = [];
|
||||||
|
|
||||||
|
//Send request
|
||||||
|
dz_fn_request_send = // [type, args, reply]
|
||||||
|
{
|
||||||
|
Debug_Assert(Request_IsInitialized());
|
||||||
|
Debug_CheckParams3(Array_New2("SCALAR","STRING"),"ANY","BOOL");
|
||||||
|
|
||||||
|
private ["_id", "_request"];
|
||||||
|
|
||||||
|
//Expecting reply
|
||||||
|
if (_this select 2) exitWith
|
||||||
|
{
|
||||||
|
//Acquire lock
|
||||||
|
Mutex_WaitLock_Fast(dz_request_mutex);
|
||||||
|
|
||||||
|
//Find first valid id and assign the new request to it
|
||||||
|
_id = dz_request_list find 0;
|
||||||
|
if (_id < 0) then { _id = count dz_request_list; };
|
||||||
|
_request = [dz_owner, _id];
|
||||||
|
dz_request_list set [_id, _request];
|
||||||
|
|
||||||
|
Mutex_Unlock(dz_request_mutex);
|
||||||
|
|
||||||
|
Util_PublicVariableServer_Fast("dz_pvs_request", _request + Array_New2(_this select 0, _this select 1));
|
||||||
|
|
||||||
|
/*//send request to server
|
||||||
|
dz_pvs_request = _request + [_this select 0, _this select 1];
|
||||||
|
publicVariableServer "dz_pvs_request";*/
|
||||||
|
|
||||||
|
//return the request object
|
||||||
|
_request
|
||||||
|
};
|
||||||
|
|
||||||
|
//Not expecting reply
|
||||||
|
|
||||||
|
Util_PublicVariableServer_Fast("dz_pvs_request", Array_New4(dz_owner, -1, _this select 0, _this select 1));
|
||||||
|
|
||||||
|
/*//Acquire lock
|
||||||
|
Mutex_WaitLock_Fast(dz_request_mutex);
|
||||||
|
|
||||||
|
//Send request to server
|
||||||
|
dz_pvs_request = Request_New(-1) + [_this select 0, _this select 1];
|
||||||
|
publicVariableServer "dz_pvs_request";
|
||||||
|
|
||||||
|
//Unlock
|
||||||
|
Mutex_Unlock(dz_request_mutex);*/
|
||||||
|
|
||||||
|
//Return nil
|
||||||
|
nil
|
||||||
|
};
|
||||||
|
|
||||||
|
//receive reply
|
||||||
|
"dz_pvc_request" addPublicVariableEventHandler
|
||||||
|
{
|
||||||
|
_id = Reply_GetID(_this select 1);
|
||||||
|
|
||||||
|
//retrieve and remove request from global list
|
||||||
|
_request = dz_request_list select _id;
|
||||||
|
dz_request_list set [_id, 0];
|
||||||
|
|
||||||
|
//set result in request object
|
||||||
|
Request_SetResult(_request, Reply_GetResult(_this select 1));
|
||||||
|
};
|
||||||
|
}
|
||||||
|
else //SERVER
|
||||||
|
{
|
||||||
|
//dz_request_mutex = Mutex_New();
|
||||||
|
dz_request_handlers = Dictionary_New();
|
||||||
|
|
||||||
|
//receive request
|
||||||
|
"dz_pvs_request" addPublicVariableEventHandler
|
||||||
|
{
|
||||||
|
//request handler [handler, async]
|
||||||
|
_handler = Dictionary_Get(dz_request_handlers, Request_Server_GetFunc(_this select 1));
|
||||||
|
|
||||||
|
//No handler found
|
||||||
|
if (isNil "_handler") exitWith
|
||||||
|
{
|
||||||
|
diag_log format ["ERROR: Received an invalid request:%1 ClientID:%2",
|
||||||
|
Request_Server_GetFunc(_this select 1),
|
||||||
|
Request_GetOwner(_this select 1) ];
|
||||||
|
|
||||||
|
//Send reply to prevent client deadlock
|
||||||
|
if (Request_Server_ExpectsReply(_this select 1)) then
|
||||||
|
{
|
||||||
|
Util_PublicVariableClient_Fast("dz_pvc_request", DEFAULT_REPLY, Request_GetOwner(_this select 1));
|
||||||
|
|
||||||
|
//Return default value (empty array)
|
||||||
|
/*_temp = dz_pvc_request;
|
||||||
|
dz_pvc_request = DEFAULT_REPLY;
|
||||||
|
Request_GetOwner(_this select 1) publicVariableClient "dz_pvc_request";
|
||||||
|
dz_pvc_request = _temp;*/
|
||||||
|
};
|
||||||
|
};
|
||||||
|
|
||||||
|
//Async
|
||||||
|
if (_handler select 1) then
|
||||||
|
{
|
||||||
|
//Spawn a new thread to handle request asynchronously
|
||||||
|
[_this select 1, _handler select 0] spawn
|
||||||
|
{
|
||||||
|
__reply = Request_Server_ExpectsReply(_this select 0);
|
||||||
|
_result = Request_Server_GetArgs(_this select 0) call (_this select 1);
|
||||||
|
|
||||||
|
if (!__reply) exitWith {};
|
||||||
|
|
||||||
|
_result = [Request_GetID(_this select 0), _result];
|
||||||
|
|
||||||
|
Util_PublicVariableClient_Fast("dz_pvc_request", _result, Request_GetOwner(_this select 0));
|
||||||
|
|
||||||
|
/*//Acquire lock to prevent race conditions with other asynchronous handlers
|
||||||
|
Mutex_WaitLock_Fast(dz_request_mutex);
|
||||||
|
|
||||||
|
//Send reply
|
||||||
|
dz_pvc_request = _result;
|
||||||
|
Request_GetOwner(_this select 0) publicVariableClient "dz_pvc_request";
|
||||||
|
|
||||||
|
//Unlock
|
||||||
|
Mutex_Unlock(dz_request_mutex);*/
|
||||||
|
};
|
||||||
|
}
|
||||||
|
else //Sync
|
||||||
|
{
|
||||||
|
//Whether client expects a reply.
|
||||||
|
//If the handler knows that the player has disconnected they can set this to false to prevent replying.
|
||||||
|
__reply = Request_Server_ExpectsReply(_this select 1);
|
||||||
|
|
||||||
|
//Execute handler
|
||||||
|
_result = Request_Server_GetArgs(_this select 1) call (_handler select 0);
|
||||||
|
|
||||||
|
if (!__reply) exitWith {};
|
||||||
|
|
||||||
|
_result = [Request_GetID(_this select 1), _result];
|
||||||
|
|
||||||
|
Util_PublicVariableClient_Fast("dz_pvc_request", _result, Request_GetOwner(_this select 1));
|
||||||
|
|
||||||
|
//store previous value in case it's being used by a scheduled thread
|
||||||
|
/*_temp = dz_pvc_request;
|
||||||
|
|
||||||
|
//Send reply
|
||||||
|
dz_pvc_request = _result;
|
||||||
|
Request_GetOwner(_this select 1) publicVariableClient "dz_pvc_request";
|
||||||
|
|
||||||
|
//restore previous value
|
||||||
|
dz_pvc_request = _temp;*/
|
||||||
|
};
|
||||||
|
};
|
||||||
|
};
|
||||||
36
SQF/dayz_code/util/stack.sqf
Normal file
36
SQF/dayz_code/util/stack.sqf
Normal file
@@ -0,0 +1,36 @@
|
|||||||
|
#define GET_COUNT(s) ((s) select 0)
|
||||||
|
#define GET_ARRAY(s) ((s) select 1)
|
||||||
|
#define GET_SIZE(s) (count GET_ARRAY(s))
|
||||||
|
#define SET_COUNT(s, p) ((s) set [0, p])
|
||||||
|
|
||||||
|
dz_fn_stack_push =
|
||||||
|
{
|
||||||
|
if (GET_COUNT(_this select 0) == GET_SIZE(_this select 0)) then
|
||||||
|
{
|
||||||
|
GET_ARRAY(_this select 0) resize (GET_SIZE(_this select 0) * 2);
|
||||||
|
};
|
||||||
|
|
||||||
|
GET_ARRAY(_this select 0) set [GET_COUNT(_this select 0), _this select 1];
|
||||||
|
SET_COUNT(_this select 0, GET_COUNT(_this select 0) + 1);
|
||||||
|
};
|
||||||
|
|
||||||
|
dz_fn_stack_pop =
|
||||||
|
{
|
||||||
|
if (GET_COUNT(_this) == 0) exitWith {nil};
|
||||||
|
|
||||||
|
private "_e";
|
||||||
|
SET_COUNT(_this, GET_COUNT(_this) - 1);
|
||||||
|
_e = GET_ARRAY(_this) select GET_COUNT(_this);
|
||||||
|
GET_ARRAY(_this) set [GET_COUNT(_this), nil];
|
||||||
|
_e
|
||||||
|
};
|
||||||
|
|
||||||
|
dz_fn_stack_peek =
|
||||||
|
{
|
||||||
|
GET_ARRAY(_this) select (GET_COUNT(_this) - 1)
|
||||||
|
};
|
||||||
|
|
||||||
|
dz_fn_stack_size =
|
||||||
|
{
|
||||||
|
count GET_ARRAY(_this)
|
||||||
|
};
|
||||||
96
SQF/dayz_code/util/task.sqf
Normal file
96
SQF/dayz_code/util/task.sqf
Normal file
@@ -0,0 +1,96 @@
|
|||||||
|
/* Task structure
|
||||||
|
|
||||||
|
code task function
|
||||||
|
script script handle
|
||||||
|
int task status
|
||||||
|
any task result
|
||||||
|
*/
|
||||||
|
|
||||||
|
#define STATUS_WAITING 0
|
||||||
|
#define STATUS_STARTED 1
|
||||||
|
#define STATUS_COMPLETED 2
|
||||||
|
#define STATUS_CANCELED 3
|
||||||
|
|
||||||
|
#define GET_CODE(task) ((task) select 0)
|
||||||
|
|
||||||
|
#define GET_SCRIPT(task) ((task) select 1)
|
||||||
|
#define SET_SCRIPT(task, script) ((task) set [1, script])
|
||||||
|
|
||||||
|
#define GET_STATUS(task) ((task) select 2)
|
||||||
|
#define SET_STATUS(task, status) ((task) set [2, status])
|
||||||
|
|
||||||
|
#define GET_RESULT(task) ((task) select 3)
|
||||||
|
#define SET_RESULT(task, result) ((task) set [3, result])
|
||||||
|
|
||||||
|
dz_fn_task_start =
|
||||||
|
{
|
||||||
|
if (GET_STATUS(_this select 0) != STATUS_WAITING) exitWith { nil };
|
||||||
|
|
||||||
|
private "_handle";
|
||||||
|
|
||||||
|
SET_STATUS(_this select 0, STATUS_STARTED);
|
||||||
|
|
||||||
|
_handle = _this spawn
|
||||||
|
{
|
||||||
|
SET_RESULT(_this select 0, (_this select 1) call GET_CODE(_this select 0));
|
||||||
|
|
||||||
|
SET_STATUS(_this select 0, STATUS_COMPLETED);
|
||||||
|
};
|
||||||
|
|
||||||
|
SET_SCRIPT(_this select 0, _handle);
|
||||||
|
|
||||||
|
_this select 0
|
||||||
|
};
|
||||||
|
|
||||||
|
dz_fn_task_cancel =
|
||||||
|
{
|
||||||
|
if (GET_STATUS(_this) != STATUS_STARTED) exitWith { false };
|
||||||
|
|
||||||
|
terminate GET_SCRIPT(_this);
|
||||||
|
SET_STATUS(_this, STATUS_CANCELED);
|
||||||
|
|
||||||
|
true
|
||||||
|
};
|
||||||
|
|
||||||
|
dz_fn_task_wait =
|
||||||
|
{
|
||||||
|
waitUntil {GET_STATUS(_this) > 1};
|
||||||
|
GET_RESULT(_this)
|
||||||
|
};
|
||||||
|
|
||||||
|
/*dz_fn_task_waitAny =
|
||||||
|
{
|
||||||
|
_index = nil;
|
||||||
|
_w = false;
|
||||||
|
|
||||||
|
waitUntil
|
||||||
|
{
|
||||||
|
for "_i" from 0 to count _this - 1 do
|
||||||
|
{
|
||||||
|
if (GET_STATUS(_this select _i) > 1)
|
||||||
|
exitWith {_w = true; _index = _this select _i; };
|
||||||
|
};
|
||||||
|
|
||||||
|
_w
|
||||||
|
};
|
||||||
|
|
||||||
|
_index
|
||||||
|
};
|
||||||
|
|
||||||
|
dz_fn_task_waitAll =
|
||||||
|
{
|
||||||
|
waitUntil
|
||||||
|
{
|
||||||
|
_w = true;
|
||||||
|
|
||||||
|
for "_i" from 0 to count _this - 1 do
|
||||||
|
{
|
||||||
|
if (GET_STATUS(_this select _i) <= 1)
|
||||||
|
exitWith {_w = false};
|
||||||
|
};
|
||||||
|
|
||||||
|
_w
|
||||||
|
};
|
||||||
|
|
||||||
|
nil
|
||||||
|
};*/
|
||||||
11
SQF/dayz_code/util/util.sqf
Normal file
11
SQF/dayz_code/util/util.sqf
Normal file
@@ -0,0 +1,11 @@
|
|||||||
|
#include "Util.hpp"
|
||||||
|
|
||||||
|
dz_fn_util_pv = { Util_PublicVariable_Fast(_this select 0, _this select 1); };
|
||||||
|
dz_fn_util_pvs = { Util_PublicVariableServer_Fast(_this select 0, _this select 1); };
|
||||||
|
dz_fn_util_pvc = { Util_PublicVariableClient_Fast(_this select 0, _this select 1, _this select 2); };
|
||||||
|
|
||||||
|
dz_fn_util_waitUntil =
|
||||||
|
{
|
||||||
|
waitUntil { ((_this select 2) + (_this select 3)) > diag_tickTime || { (_this select 0) call (_this select 1) } };
|
||||||
|
(_this select 0) call (_this select 1);
|
||||||
|
};
|
||||||
53
SQF/dayz_code/util/vector.sqf
Normal file
53
SQF/dayz_code/util/vector.sqf
Normal file
@@ -0,0 +1,53 @@
|
|||||||
|
#include "Vector.hpp"
|
||||||
|
|
||||||
|
#define P0 _this select 0
|
||||||
|
#define P1 _this select 1
|
||||||
|
|
||||||
|
dz_fn_vector_dotProduct = { Vector_DotProduct_Fast(P0, P1); };
|
||||||
|
dz_fn_vector_crossProduct = { Vector_CrossProduct_Fast(P0, P1); };
|
||||||
|
dz_fn_vector_magnitude = { Vector_Magnitude_Fast(_this); };
|
||||||
|
dz_fn_vector_add = { Vector_Add_Fast(P0, P1); };
|
||||||
|
dz_fn_vector_subtract = { Vector_Subtract_Fast(P0, P1); };
|
||||||
|
dz_fn_vector_negate = { Vector_Negate_Fast(_this); };
|
||||||
|
dz_fn_vector_multiply = { Vector_Multiply_Fast(P0, P1); };
|
||||||
|
dz_fn_vector_divide = { Vector_Divide_Fast(P0, P1); };
|
||||||
|
dz_fn_vector_angle = { Vector_Angle_Fast(P0, P1); };
|
||||||
|
dz_fn_vector_normalize = { Vector_Normalize_Fast(_this); };
|
||||||
|
dz_fn_vector_fromDir = { Vector_FromDir_Fast(_this); };
|
||||||
|
dz_fn_vector_rotate2d = { Vector_Rotate2D_Fast(P0, P1); };
|
||||||
|
|
||||||
|
dz_fn_vector_rotate3d =
|
||||||
|
{
|
||||||
|
#define VX (_this select 0 select 0)
|
||||||
|
#define VY (_this select 0 select 1)
|
||||||
|
#define VZ (_this select 0 select 2)
|
||||||
|
#define UX (_this select 1 select 0)
|
||||||
|
#define UY (_this select 1 select 1)
|
||||||
|
#define UZ (_this select 1 select 2)
|
||||||
|
|
||||||
|
private ["_sin", "_cos", "_icos"];
|
||||||
|
_sin = sin (_this select 2);
|
||||||
|
_cos = cos (_this select 2);
|
||||||
|
_icos = 1 - _cos;
|
||||||
|
|
||||||
|
[
|
||||||
|
VX * ( UX ^ 2 * _icos + _cos ) +
|
||||||
|
VY * ( UX * UY * _icos - UZ * _sin ) +
|
||||||
|
VZ * ( UX * UZ * _icos + UY * _sin )
|
||||||
|
,
|
||||||
|
VX * ( UY * UX * _icos + UZ * _sin ) +
|
||||||
|
VY * ( UY ^ 2 * _icos + _cos ) +
|
||||||
|
VZ * ( UY * UZ * _icos - UX * _sin )
|
||||||
|
,
|
||||||
|
VX * ( UZ * UX * _icos - UY * _sin ) +
|
||||||
|
VY * ( UZ * UY * _icos + UX * _sin ) +
|
||||||
|
VZ * ( UZ ^ 2 * _icos + _cos )
|
||||||
|
]
|
||||||
|
|
||||||
|
#undef VX
|
||||||
|
#undef VY
|
||||||
|
#undef VZ
|
||||||
|
#undef UX
|
||||||
|
#undef UY
|
||||||
|
#undef UZ
|
||||||
|
};
|
||||||
@@ -1796,6 +1796,14 @@
|
|||||||
<French>Vous ne pouvez pas effectuer une autre transfusion sanguine si vite, attendez %1 secondes.</French>
|
<French>Vous ne pouvez pas effectuer une autre transfusion sanguine si vite, attendez %1 secondes.</French>
|
||||||
<Czech>Nemůžete provádět další krevní transfuzi tak rychle, počkejte %1 sekund.</Czech>
|
<Czech>Nemůžete provádět další krevní transfuzi tak rychle, počkejte %1 sekund.</Czech>
|
||||||
</Key>
|
</Key>
|
||||||
|
<Key ID="STR_ACTIONS_WEAPON">
|
||||||
|
<English>Weapon %1</English>
|
||||||
|
<Spanish>Arma: %1</Spanish>
|
||||||
|
<Russian>Оружие %1</Russian>
|
||||||
|
<Czech>Zbraň: %1</Czech>
|
||||||
|
<French>Arme: %1</French>
|
||||||
|
<German>Zu %1 wechseln</German>
|
||||||
|
</Key>
|
||||||
<Key ID="str_action_studybody">
|
<Key ID="str_action_studybody">
|
||||||
<Original>Study Body</Original>
|
<Original>Study Body</Original>
|
||||||
<English>Study Body</English>
|
<English>Study Body</English>
|
||||||
|
|||||||
Reference in New Issue
Block a user