Merge branch 'master' into explosiveInteraction

This commit is contained in:
Garth L-H de Wet 2015-03-01 14:31:06 +02:00
commit 3ff1bff2bf
38 changed files with 697 additions and 418 deletions

View File

@ -1,7 +1,7 @@
root = true root = true
[*] [*]
end_of_line = lf end_of_line = crlf
insert_final_newline = true insert_final_newline = true
charset = utf-8 charset = utf-8
indent_style = space indent_style = space

View File

@ -4,14 +4,8 @@
_fnc = { _fnc = {
_this call FUNC(render); _this call FUNC(render);
}; };
// [_fnc, 0, []] call cba_fnc_addPerFrameHandler;
addMissionEventHandler ["Draw3D", _fnc]; addMissionEventHandler ["Draw3D", _fnc];
_fnc = {
_this call FUNC(probe);
};
[_fnc, 0.5, []] call cba_fnc_addPerFrameHandler;
["ACE3", ["ACE3",
"Interact Key", "Interact Key",
{_this call FUNC(keyDown)}, {_this call FUNC(keyDown)},

View File

@ -9,15 +9,13 @@ PREP(keyDown);
PREP(keyDownSelfAction); PREP(keyDownSelfAction);
PREP(keyUp); PREP(keyUp);
PREP(keyUpSelfAction); PREP(keyUpSelfAction);
PREP(probe);
PREP(removeAction); PREP(removeAction);
PREP(render); PREP(render);
PREP(renderIcon); PREP(renderIcon);
PREP(renderMenu); PREP(renderMenu);
PREP(rotateVectLine); PREP(rotateVectLine);
PREP(rotateVectLineGetMap); PREP(rotateVectLineGetMap);
PREP(updateVecLineMap);
GVAR(toRender) = [];
GVAR(keyDown) = false; GVAR(keyDown) = false;
GVAR(keyDownSelfAction) = false; GVAR(keyDownSelfAction) = false;
@ -30,11 +28,7 @@ GVAR(selectedAction) = {};
GVAR(actionSelected) = false; GVAR(actionSelected) = false;
GVAR(selectedTarget) = objNull; GVAR(selectedTarget) = objNull;
GVAR(filter) = [];
GVAR(menuDepthPath) = []; GVAR(menuDepthPath) = [];
GVAR(renderDepth) = 0;
GVAR(lastRenderDepth) = 0;
GVAR(vecLineMap) = []; GVAR(vecLineMap) = [];
GVAR(lastPos) = [0,0,0]; GVAR(lastPos) = [0,0,0];
@ -44,13 +38,10 @@ GVAR(lastPath) = [];
GVAR(expanded) = false; GVAR(expanded) = false;
GVAR(maxRenderDepth) = 0;
GVAR(startHoverTime) = diag_tickTime; GVAR(startHoverTime) = diag_tickTime;
GVAR(iconCtrls) = []; GVAR(iconCtrls) = [];
GVAR(iconCount) = 0; GVAR(iconCount) = 0;
GVAR(objectActionsHash) = HASH_CREATE;
GVAR(uidCounter) = 0; GVAR(uidCounter) = 0;
ADDON = true; ADDON = true;

View File

@ -1,39 +1,40 @@
/* /*
* Author: commy2 and NouberNou * Author: commy2, NouberNou and CAA-Picard
* Add an ACE action to an object or inside a parent action. Note: This function is NOT global. * Add an ACE action to an object, under a certain config path
* Note: This function is NOT global.
* *
* Argument: * Argument:
* 0: Object the action should be assigned to or parent action <OBJECT> or <ARRAY> * 0: Object the action should be assigned to <OBJECT>
* 1: Name of the action shown in the menu <STRING> * 1: Type of action, 0 for actions, 1 for self-actions <NUMBER>
* 2: Icon <STRING> * 2: Full path of the new action <ARRAY>
* 3: Position (Position or Selection Name) <POSITION> or <STRING> * 3: Name of the action shown in the menu <STRING>
* 4: Statement <CODE> * 4: Icon <STRING>
* 5: Condition <CODE> * 5: Position (Position or Selection Name) <POSITION> or <STRING>
* 6: Distance <NUMBER> * 6: Statement <CODE>
* 7: Condition <CODE>
* 8: Distance <NUMBER>
* *
* Return value: * Return value:
* The entry array, which can be used to remove the entry, or add children entries <ARRAY>. * The entry full path, which can be used to remove the entry, or add children entries <ARRAY>.
*
* Example:
* [cursorTarget,0,["ACE_TapShoulderRight","VulcanPinch"],"Vulcan Pinch","",[0,0,0],{_target setDamage 1;},{true},100] call ace_interact_menu_fnc_addAction;
* *
* Public: No * Public: No
*/ */
#include "script_component.hpp" #include "script_component.hpp"
EXPLODE_7_PVT(_this,_object,_displayName,_icon,_position,_statement,_condition,_distance); EXPLODE_9_PVT(_this,_object,_typeNum,_fullPath,_displayName,_icon,_position,_statement,_condition,_distance);
private ["_varName","_actions"];
private ["_actions","_entry"]; _varName = [QGVAR(actions),QGVAR(selfActions)] select _typeNum;
_actions = []; _actions = _object getVariable [_varName, []];
if(IS_OBJECT(_object)) then {
_actions = _object getVariable [QUOTE(GVAR(actionData)), []];
if((count _actions) == 0) then { if((count _actions) == 0) then {
_object setVariable [QUOTE(GVAR(actionData)), _actions] _object setVariable [_varName, _actions];
};
} else {
if(IS_ARRAY(_object)) then {
_actions = _object select 6;
};
}; };
private "_entry";
_entry = [ _entry = [
_displayName, _displayName,
_icon, _icon,
@ -42,8 +43,11 @@ _entry = [
_condition, _condition,
_distance, _distance,
[], [],
GVAR(uidCounter) GVAR(uidCounter),
+ _fullPath
]; ];
GVAR(uidCounter) = GVAR(uidCounter) + 1; GVAR(uidCounter) = GVAR(uidCounter) + 1;
_actions pushBack _entry; _actions pushBack _entry;
_entry;
_fullPath

View File

@ -1,6 +1,6 @@
/* /*
* Author: NouberNou * Author: NouberNou and CAA-Picard
* Compile the action menu from config for a given object. * Compile the action menu from config for an object's class
* *
* Argument: * Argument:
* 0: Object <OBJECT> * 0: Object <OBJECT>
@ -14,30 +14,20 @@
EXPLODE_1_PVT(_this,_object); EXPLODE_1_PVT(_this,_object);
/* private ["_objectType","_actionsVarName"];
[
[
"Launch",
"\a3\ui_f\data\IGUI\Cfg\Actions\eject_ca.paa",
[0,0,0],
{ (_this select 0) setVelocity [0,0,10]; },
{ true },
1,
[]
]
]
*/
private ["_objectType","_recurseFnc","_actions"];
_objectType = typeOf _object; _objectType = typeOf _object;
_actionsCfg = configFile >> "CfgVehicles" >> _objectType >> "ACE_Actions"; _actionsVarName = format [QGVAR(Act_%1), _objectType];
// Exit if the action menu is already compiled for this class
if !(isNil {missionNamespace getVariable [_actionsVarName, nil]}) exitWith {};
private "_recurseFnc";
_recurseFnc = { _recurseFnc = {
private ["_actions", "_displayName", "_distance", "_icon", "_statement", "_selection", "_condition", "_showDisabled", private ["_actions", "_displayName", "_distance", "_icon", "_statement", "_selection", "_condition", "_showDisabled",
"_enableInside", "_children", "_entry", "_actionsCfg"]; "_enableInside", "_children", "_entry", "_entryCfg", "_fullPath"];
EXPLODE_2_PVT(_this,_actionsCfg,_parentPath);
_actions = []; _actions = [];
_actionsCfg = _this select 0;
for "_i" from 0 to (count _actionsCfg) - 1 do { for "_i" from 0 to (count _actionsCfg) - 1 do {
_entryCfg = _actionsCfg select _i; _entryCfg = _actionsCfg select _i;
if(isClass _entryCfg) then { if(isClass _entryCfg) then {
@ -58,8 +48,12 @@ _recurseFnc = {
_showDisabled = getNumber (_entryCfg >> "showDisabled"); _showDisabled = getNumber (_entryCfg >> "showDisabled");
_enableInside = getNumber (_entryCfg >> "enableInside"); _enableInside = getNumber (_entryCfg >> "enableInside");
_fullPath = (+ _parentPath);
_fullPath pushBack (configName _entryCfg);
_condition = compile _condition; _condition = compile _condition;
_children = [_entryCfg] call _recurseFnc; _children = [_entryCfg, _fullPath] call _recurseFnc;
_entry = [ _entry = [
_displayName, _displayName,
_icon, _icon,
@ -68,8 +62,10 @@ _recurseFnc = {
_condition, _condition,
_distance, _distance,
_children, _children,
GVAR(uidCounter) GVAR(uidCounter),
_fullPath
]; ];
GVAR(uidCounter) = GVAR(uidCounter) + 1; GVAR(uidCounter) = GVAR(uidCounter) + 1;
_actions pushBack _entry; _actions pushBack _entry;
}; };
@ -77,6 +73,23 @@ _recurseFnc = {
_actions _actions
}; };
_actions = [_actionsCfg] call _recurseFnc; private "_actionsCfg";
_actionsCfg = configFile >> "CfgVehicles" >> _objectType >> "ACE_Actions";
_object setVariable [QUOTE(GVAR(actionData)), _actions]; missionNamespace setVariable [_actionsVarName, [_actionsCfg, []] call _recurseFnc];
/*
[
[
"My Action",
"\a3\ui_f\data\IGUI\Cfg\Actions\eject_ca.paa",
[0,0,0],
{ (_this select 0) setVelocity [0,0,10]; },
{ true },
1,
[],
uid,
["MainActions","TeamManagement","MyAction"]
]
]
*/

View File

@ -1,6 +1,6 @@
/* /*
* Author: NouberNou and CAA-Picard * Author: NouberNou and CAA-Picard
* Compile the self action menu from config for a given object. * Compile the self action menu from config for an object's class
* *
* Argument: * Argument:
* 0: Object <OBJECT> * 0: Object <OBJECT>
@ -14,34 +14,25 @@
EXPLODE_1_PVT(_this,_object); EXPLODE_1_PVT(_this,_object);
/* private ["_objectType","_actionsVarName"];
[
[
"Launch",
"\a3\ui_f\data\IGUI\Cfg\Actions\eject_ca.paa",
[0,0,0],
{ (_this select 0) setVelocity [0,0,10]; },
{ true },
1,
[]
]
]
*/
private ["_objectType","_recurseFnc","_actions"];
_objectType = typeOf _object; _objectType = typeOf _object;
_actionsCfg = configFile >> "CfgVehicles" >> _objectType >> "ACE_SelfActions"; _actionsVarName = format [QGVAR(SelfAct_%1), _objectType];
// Exit if the action menu is already compiled for this class
if !(isNil {missionNamespace getVariable [_actionsVarName, nil]}) exitWith {};
private "_recurseFnc";
_recurseFnc = { _recurseFnc = {
private ["_actions", "_displayName", "_distance", "_icon", "_statement", "_condition", "_showDisabled", private ["_actions", "_displayName", "_distance", "_icon", "_statement", "_selection", "_condition", "_showDisabled",
"_enableInside", "_children", "_entry", "_actionsCfg"]; "_enableInside", "_children", "_entry", "_entryCfg", "_fullPath"];
EXPLODE_2_PVT(_this,_actionsCfg,_parentPath);
_actions = []; _actions = [];
_actionsCfg = _this select 0;
for "_i" from 0 to (count _actionsCfg) - 1 do { for "_i" from 0 to (count _actionsCfg) - 1 do {
_entryCfg = _actionsCfg select _i; _entryCfg = _actionsCfg select _i;
if(isClass _entryCfg) then { if(isClass _entryCfg) then {
_displayName = getText (_entryCfg >> "displayName"); _displayName = getText (_entryCfg >> "displayName");
_icon = getText (_entryCfg >> "icon"); _icon = getText (_entryCfg >> "icon");
_statement = compile (getText (_entryCfg >> "statement")); _statement = compile (getText (_entryCfg >> "statement"));
@ -54,8 +45,12 @@ _recurseFnc = {
_showDisabled = getNumber (_entryCfg >> "showDisabled"); _showDisabled = getNumber (_entryCfg >> "showDisabled");
_enableInside = getNumber (_entryCfg >> "enableInside"); _enableInside = getNumber (_entryCfg >> "enableInside");
_fullPath = (+ _parentPath);
_fullPath pushBack (configName _entryCfg);
_condition = compile _condition; _condition = compile _condition;
_children = [_entryCfg] call _recurseFnc; _children = [_entryCfg, _fullPath] call _recurseFnc;
_entry = [ _entry = [
_displayName, _displayName,
_icon, _icon,
@ -64,8 +59,10 @@ _recurseFnc = {
_condition, _condition,
10, //distace 10, //distace
_children, _children,
GVAR(uidCounter) GVAR(uidCounter),
_fullPath
]; ];
GVAR(uidCounter) = GVAR(uidCounter) + 1; GVAR(uidCounter) = GVAR(uidCounter) + 1;
_actions pushBack _entry; _actions pushBack _entry;
}; };
@ -73,7 +70,8 @@ _recurseFnc = {
_actions _actions
}; };
_actions = [_actionsCfg] call _recurseFnc; private "_actionsCfg";
_actionsCfg = configFile >> "CfgVehicles" >> _objectType >> "ACE_SelfActions";
// Create a master action to base on self action // Create a master action to base on self action
_actions = [[ _actions = [[
@ -83,10 +81,11 @@ _actions = [[
{ true }, { true },
{ true }, { true },
10, 10,
_actions, [_actionsCfg, ["SelfActions"]] call _recurseFnc,
GVAR(uidCounter) GVAR(uidCounter),
["SelfActions"]
] ]
]; ];
GVAR(uidCounter) = GVAR(uidCounter) + 1; GVAR(uidCounter) = GVAR(uidCounter) + 1;
_object setVariable [QUOTE(GVAR(selfActionData)), _actions]; missionNamespace setVariable [_actionsVarName, _actions];

View File

@ -17,7 +17,7 @@ if(GVAR(actionSelected)) then {
this = GVAR(selectedTarget); this = GVAR(selectedTarget);
_player = ACE_Player; _player = ACE_Player;
_target = GVAR(selectedTarget); _target = GVAR(selectedTarget);
[GVAR(selectedTarget), player] call GVAR(selectedAction); [GVAR(selectedTarget), ACE_player] call GVAR(selectedAction);
}; };
GVAR(expanded) = false; GVAR(expanded) = false;
GVAR(lastPath) = []; GVAR(lastPath) = [];

View File

@ -17,7 +17,7 @@ if(GVAR(actionSelected)) then {
this = GVAR(selectedTarget); this = GVAR(selectedTarget);
_player = ACE_Player; _player = ACE_Player;
_target = GVAR(selectedTarget); _target = GVAR(selectedTarget);
[GVAR(selectedTarget), player] call GVAR(selectedAction); [GVAR(selectedTarget), ACE_player] call GVAR(selectedAction);
}; };
GVAR(expanded) = false; GVAR(expanded) = false;
GVAR(lastPath) = []; GVAR(lastPath) = [];

View File

@ -1,55 +0,0 @@
/*
* Author: NouberNou
* Scan de vicinity of the player and collect every interaction available around it on
* the GVAR(toRender) array.
*
* Argument:
* None
*
* Return value:
* None
*
* Public: No
*/
#include "script_component.hpp"
private ["_nearestObjects", "_actionObject", "_x", "_actionData", "_renderData", "_actionItem", "_active", "_renderItem", "_object", "_forEachIndex"];
if(!GVAR(keyDown)) then {
_nearestObjects = nearestObjects [(getPos ACE_player), ["All"], 100];
GVAR(toRender) = [];
{
_actionObject = _x;
_actionData = _actionObject getVariable [QUOTE(GVAR(actionData)), []];
if((count _actionData) > 0) then {
_renderData = [];
{
_actionItem = _x;
this = _actionObject;
_target = _actionObject;
_player = ACE_player;
_active = [_target, ACE_player] call (_actionItem select 4);
systemChat format ["%1 %2 is active %3", _actionObject, _actionItem select 0, _active];
// player sideChat format["_active: %1 %2", _actionItem select 0, _active];
if(_active) then {
_renderItem = +_actionItem;
_renderItem set[4, true];
_renderData set[(count _renderData), _renderItem];
};
} forEach _actionData;
if((count _renderData) > 0) then {
GVAR(toRender) set[(count GVAR(toRender)), [_actionObject, _renderData]];
};
};
} forEach _nearestObjects;
// player sideChat format["p: %1", count GVAR(toRender)];
} else {
GVAR(filter) = [];
{
_object = _x select 0;
if(_object distance ACE_player > 100) then {
GVAR(filter) set[(count GVAR(filter)), _forEachIndex];
};
} forEach GVAR(toRender);
};

View File

@ -1,50 +1,30 @@
/* /*
* Author: commy2 and NouberNou * Author: commy2, NouberNou and CAA-Picard
* Remove an action from an object * Remove an action from an object
* *
* Argument: * Argument:
* 0: Object the action should be assigned to <OBJECT> * 0: Object the action is assigned to <OBJECT>
* 1: Entry to remove <ARRAY> or <NUMBER> * 1: Type of action, 0 for actions, 1 for self-actions <NUMBER>
* 2: Full path of the action to remove <ARRAY>
* *
* Return value: * Return value:
* None * None
* *
* Example:
* [cursorTarget,0,["ACE_TapShoulderRight","VulcanPinch"]] call ace_interact_menu_fnc_removeAction;
*
* Public: No * Public: No
*/ */
#include "script_component.hpp" #include "script_component.hpp"
EXPLODE_2_PVT(_this,_object,_entry); EXPLODE_3_PVT(_this,_object,_typeNum,_fullPath);
private ["_found", "_actions", "_searchFnc"]; private ["_varName","_actions"];
_varName = [QGVAR(actions),QGVAR(selfActions)] select _typeNum;
_actions = _object getVariable [_varName, []];
if(!IS_OBJECT(_object)) exitWith {false};
_actions = _object getVariable [QUOTE(GVAR(actionData)), []];
if(IS_ARRAY(_entry)) then {
_entry = _entry select 7;
};
_found = false;
_searchFnc = {
private ["_actions", "_entry", "_childActions"];
_actions = _this select 0;
_entry = _this select 1;
{ {
if((_x select 7) == _entry) then { if ((_x select 8) isEqualTo _fullPath) exitWith {
_actions set[_forEachIndex, "aceactiondelete"]; _actions deleteAt _forEachIndex;
_actions = _actions - ["aceactiondelete"];
_found = true;
} else {
if(!_found && {count (_x select 6) > 0}) then {
_childActions = [(_x select 6), _entry] call _searchFnc;
_x set[6, _childActions];
};
}; };
} forEach _actions; } forEach _actions;
_actions;
};
_actions = [_actions, _entry] call _searchFnc;
_object setVariable [QUOTE(GVAR(actionData)), _actions];
_found;

View File

@ -16,41 +16,91 @@ private ["_cursorPos1", "_cursorPos2", "_cursorVec", "_p1", "_p2", "_p", "_v", "
_foundTarget = false; _foundTarget = false;
_cursorPos1 = positionCameraToWorld [0, 0, 0]; _cursorPos1 = positionCameraToWorld [0, 0, 0];
_cursorPos2 = positionCameraToWorld [0, 0, 2]; _cursorPos2 = positionCameraToWorld [0, 0, 2];
GVAR(currentOptions) = []; GVAR(currentOptions) = [];
if((count GVAR(toRender)) > 0 && (GVAR(keyDown) || GVAR(keyDownSelfAction))) then {
if((count GVAR(vecLineMap)) == 0 || ((count GVAR(menuDepthPath)) > 0 && (getPosASL player) distance GVAR(lastPos) > 0.01)) then {
GVAR(lastPos) = getPosASL player;
_cursorVec = [_cursorPos2, _cursorPos1] call BIS_fnc_vectorFromXtoY;
_p1 = [0,0,0];
_p2 = +_cursorVec;
_p = (_cursorVec call CBA_fnc_vect2polar);
_v = [(_p select 0), (_p select 1), (_p select 2)+90] call CBA_fnc_polar2vect;
_cp = [_cursorVec, _v] call BIS_fnc_crossProduct;
GVAR(vecLineMap) = [_cp, _p1, _p2] call FUNC(rotateVectLineGetMap); private ["_actionsVarName","_classActions","_objectActions","_target","_player","_actionItem","_active"];
};
if (GVAR(keyDown)) then { if (GVAR(keyDown)) then {
[] call FUNC(updateVecLineMap);
// Render all nearby interaction menus // Render all nearby interaction menus
_nearestObjects = nearestObjects [(getPos ACE_player), ["All"], 15];
{ {
if(!(_forEachIndex in GVAR(filter))) then { _target = _x;
GVAR(renderDepth) = 0; _player = ACE_player;
_renderTargets = _x;
// Iterate through object actions, find base level actions and render them if appropiate
_actionsVarName = format [QGVAR(Act_%1), typeOf _target];
GVAR(objectActions) = _target getVariable [QGVAR(actions), []];
{ {
[_renderTargets select 0, _x, 0, [180, 360]] call FUNC(renderMenu); _actionItem = _x;
} forEach (_renderTargets select 1); // Only render them directly if they are base level actions
if (count (_actionItem select 8) == 1) then {
_active = [_target, ACE_player] call (_actionItem select 4);
if (_active) then {
[_target, _actionItem, 0, [180, 360]] call FUNC(renderMenu);
}; };
} forEach GVAR(toRender); };
} forEach GVAR(objectActions);
// Iterate through base level class actions and render them if appropiate
_classActions = missionNamespace getVariable [_actionsVarName, []];
{
_actionItem = _x;
_active = [_target, ACE_player] call (_actionItem select 4);
if (_active) then {
[_target, _actionItem, 0, [180, 360]] call FUNC(renderMenu);
};
} forEach _classActions;
} forEach _nearestObjects;
} else { } else {
if (GVAR(keyDownSelfAction)) then {
[] call FUNC(updateVecLineMap);
// Render only the self action menu // Render only the self action menu
_actions = (ACE_player getVariable QGVAR(selfActionData)) select 0; _target = vehicle ACE_player;
_player = ACE_player;
// Iterate through object actions, find base level actions and render them if appropiate
_actionsVarName = format [QGVAR(SelfAct_%1), typeOf _target];
GVAR(objectActions) = _target getVariable [QGVAR(selfActions), []];
{
_actionItem = _x;
// Only render them directly if they are base level actions
if (count (_actionItem select 8) == 1) then {
_active = [_target, ACE_player] call (_actionItem select 4);
if (_active) then {
[_target, _actionItem, 0, [180, 360]] call FUNC(renderMenu);
};
};
} forEach GVAR(objectActions);
// Iterate through base level class actions and render them if appropiate
_actionsVarName = format [QGVAR(SelfAct_%1), typeOf _target];
_classActions = missionNamespace getVariable [_actionsVarName, []];
{
_actionItem = _x;
_active = [_target, ACE_player] call (_actionItem select 4);
if (_active) then {
_pos = (ACE_player modelToWorld (ACE_player selectionPosition "spine3")) vectorAdd GVAR(selfMenuOffset) vectorAdd [0,0,0.25]; _pos = (ACE_player modelToWorld (ACE_player selectionPosition "spine3")) vectorAdd GVAR(selfMenuOffset) vectorAdd [0,0,0.25];
[ACE_player, _actions, 0, [180, 360], _pos] call FUNC(renderMenu); [ACE_player, _actionItem, 0, [180, 360], _pos] call FUNC(renderMenu);
};
} forEach _classActions;
};
}; };
// player sideChat format["c: %1", count GVAR(toRender)];
};
if(GVAR(keyDown) || GVAR(keyDownSelfAction)) then { if(GVAR(keyDown) || GVAR(keyDownSelfAction)) then {
drawIcon3D ["\a3\ui_f\data\IGUI\Cfg\Cursors\selected_ca.paa", [1,0,0,1], _cursorPos2, 1, 1, 0, "", 0.5, 0.025, "TahomaB"];
_cursorScreenPos = worldToScreen _cursorPos2; _cursorScreenPos = worldToScreen _cursorPos2;
_closestDistance = 1000000; _closestDistance = 1000000;
@ -67,7 +117,8 @@ if(GVAR(keyDown) || GVAR(keyDownSelfAction)) then {
}; };
} forEach GVAR(currentOptions); } forEach GVAR(currentOptions);
if(_closestSelection != -1) then {
if(_closestSelection == -1) exitWith {};
_closest = GVAR(currentOptions) select _closestSelection; _closest = GVAR(currentOptions) select _closestSelection;
@ -107,8 +158,7 @@ if(GVAR(keyDown) || GVAR(keyDownSelfAction)) then {
}; };
}; };
}; };
drawIcon3D ["\a3\ui_f\data\IGUI\Cfg\Cursors\selected_ca.paa", [1,0,0,1], _cursorPos2, 1, 1, 0, "", 0.5, 0.025, "TahomaB"];
};
if(!_foundTarget && GVAR(actionSelected)) then { if(!_foundTarget && GVAR(actionSelected)) then {
GVAR(actionSelected) = false; GVAR(actionSelected) = false;
GVAR(expanded) = false; GVAR(expanded) = false;

View File

@ -24,6 +24,8 @@ _color = _this select 1;
_pos = _this select 2; _pos = _this select 2;
_icon = _this select 6; _icon = _this select 6;
//systemChat format ["Icon %1 - %2,%3,%4", _text, _pos select 0, _pos select 1, _pos select 2];
_sPos = worldToScreen _pos; _sPos = worldToScreen _pos;
// _sPos = _pos; // _sPos = _pos;
if(count _sPos > 0) then { if(count _sPos > 0) then {

View File

@ -1,6 +1,6 @@
/* /*
* Author: NouberNou and CAA-Picard * Author: NouberNou and CAA-Picard
* Render a interaction menu * Render a interaction menu and it's children recursively
* *
* Argument: * Argument:
* 0: Object <OBJECT> * 0: Object <OBJECT>
@ -8,7 +8,6 @@
* 2: ? * 2: ?
* 3: Angle range available for rendering <ARRAY> * 3: Angle range available for rendering <ARRAY>
* 4: 3D position <ARRAY> (Optional) * 4: 3D position <ARRAY> (Optional)
* 5: Path of UIDs <ARRAY> (Optional)
* *
* Return value: * Return value:
* None * None
@ -17,16 +16,15 @@
*/ */
#include "script_component.hpp" #include "script_component.hpp"
private ["_object", "_actionData", "_distance", "_uid", "_pos", "_cursorScreenPos", "_path", "_menuDepth", "_opacity", "_currentRenderDepth", "_radialOffset", "_active", "_x", "_offset", "_newPos", "_forEachIndex"]; private ["_distance", "_uid", "_pos", "_cursorScreenPos", "_path", "_menuDepth", "_opacity", "_currentRenderDepth", "_radialOffset", "_active", "_x", "_offset", "_newPos", "_forEachIndex"];
_object = _this select 0; EXPLODE_4_PVT(_this,_object,_actionData,_dummy,_angles);
_actionData = _this select 1;
_uid = _actionData select 7;//_this select 2;
_angles = _this select 3;
_distance = _actionData select 5;
EXPLODE_2_PVT(_angles,_centerAngle,_maxAngleSpan); EXPLODE_2_PVT(_angles,_centerAngle,_maxAngleSpan);
_uid = _actionData select 7;
_distance = _actionData select 5;
// Obtain a 3D position for the action
if((count _this) > 4) then { if((count _this) > 4) then {
_pos = _this select 4; _pos = _this select 4;
} else { } else {
@ -36,70 +34,108 @@ if((count _this) > 4) then {
_pos = _object modelToWorld (_object selectionPosition (_actionData select 2)); _pos = _object modelToWorld (_object selectionPosition (_actionData select 2));
}; };
}; };
_cursorScreenPos = (positionCameraToWorld [0, 0, 0]);
if(_cursorScreenPos distance _pos <= _distance) then {
_path = [];
if((count _this) > 5) then {
_path = +(_this select 5);
};
_menuDepth = (count GVAR(menuDepthPath));
_cursorScreenPos = (positionCameraToWorld [0, 0, 0]);
// Exit if the action is too far away
if(_cursorScreenPos distance _pos >= _distance) exitWith {};
// Exit if the action is behind you
if(_cursorScreenPos select 2 < 0) exitWith {};
_menuDepth = (count GVAR(menuDepthPath)) - 1;
// Store path to action
_path = [_object];
_path = _path + (_actionData select 8);
// Check if the menu is on the selected path
private "_menuInSelectedPath";
_menuInSelectedPath = true;
{
if (_forEachIndex >= (count GVAR(menuDepthPath))) exitWith {
_menuInSelectedPath = false;
};
if (_x != (GVAR(menuDepthPath) select _forEachIndex)) exitWith {
_menuInSelectedPath = false;
};
} forEach _path;
// Render icon
// ARGB Color (First Hex Pair is transparancy) // ARGB Color (First Hex Pair is transparancy)
_color = "#FFFFFFFF"; _color = "#FFFFFFFF";
if(_menuDepth > 0 && _uid != (GVAR(menuDepthPath) select (GVAR(renderDepth)))) then { if(_menuDepth > 0 && !_menuInSelectedPath) then {
_color = format ["#%1FFFFFF", [255 * (((GVAR(renderDepth)/_menuDepth)) max 0.25)] call EFUNC(common,toHex)]; _color = format ["#%1FFFFFF", [255 * ((((count _path) - 2)/_menuDepth) max 0.25)] call EFUNC(common,toHex)];
}; };
_path set[(count _path), _uid];
[_actionData select 0, _color, _pos, 1, 1, 0, _actionData select 1, 0.5, 0.025, "TahomaB"] call FUNC(renderIcon); [_actionData select 0, _color, _pos, 1, 1, 0, _actionData select 1, 0.5, 0.025, "TahomaB"] call FUNC(renderIcon);
GVAR(currentOptions) set[(count GVAR(currentOptions)), [_this, _pos, _path]];
_currentRenderDepth = -1; // Add the action to current options
_currentRenderDepth = GVAR(renderDepth); GVAR(currentOptions) pushBack [_this, _pos, _path];
GVAR(renderDepth) = GVAR(renderDepth) + 1;
if(_uid == (GVAR(menuDepthPath) select (GVAR(renderDepth)-1))) then { // Exit without rendering children if it isn't
// Count how many actions are active if !(_menuInSelectedPath) exitWith {};
private "_numActions";
_numActions = 0; // Collect all active children actions
private "_activeChildren";
_activeChildren = [];
// Collect children class actions
{ {
this = _object;
_target = _object; _target = _object;
_player = ACE_player; _player = ACE_player;
_active = [_object, ACE_player] call (_x select 4); _active = [_object, ACE_player] call (_x select 4);
if(_active) then { if(_active) then {
_numActions = _numActions + 1; _activeChildren pushBack _x;
}; };
} forEach (_actionData select 6); } forEach (_actionData select 6);
systemChat format ["Menu %1, _numActions: %2", _actionData select 0, _numActions];
private "_angleSpan"; // Collect children object actions
_angleSpan = _maxAngleSpan min (55 * (_numActions - 1)); {
_actionItem = _x;
// Check if the action is children of the selected menu
if ((count (_actionItem select 8)) == (count _path)) then {
// Compare parent path to see if it's a suitable child
private "_isChild";
_isChild = true;
for "_i" from 0 to (count (_actionItem select 8)) - 2 do {
if !(((_actionItem select 8) select _i) isEqualTo (_path select (_i + 1))) exitWith {
_isChild = false;
};
};
if (_isChild) exitWith {
_target = _object;
_player = ACE_player;
_active = [_target, ACE_player] call (_actionItem select 4);
if (_active) then {
_activeChildren pushBack _actionItem;
};
};
};
} forEach GVAR(objectActions);
private ["_angleSpan","_angle"];
_angleSpan = _maxAngleSpan min (55 * ((count _activeChildren) - 1));
if (_angleSpan >= 305) then {
_angleSpan = 360;
};
private "_angle";
_angle = _centerAngle - _angleSpan / 2; _angle = _centerAngle - _angleSpan / 2;
{ {
this = _object;
_target = _object; _target = _object;
_player = ACE_player; _player = ACE_player;
_active = [_object, ACE_player] call (_x select 4);
// diag_log text format["_active: %1: %2", (_x select 0), _active];
if(_active) then {
//systemChat format ["_angle: %1", _angle];
_offset = [GVAR(vecLineMap), _angle] call FUNC(rotateVectLine);
_mod = 0.15 max (0.15 * (_cursorScreenPos distance _pos)); //0.5;//0.1*_distance;
_newPos = [
(_pos select 0) + ((_offset select 0)*_mod),
(_pos select 1) + ((_offset select 1)*_mod),
(_pos select 2) + ((_offset select 2)*_mod)
];
// drawLine3D [_pos, _newPos, [1,0,0,0.5]];
[_object, _x, _forEachIndex, [_angle, 150], _newPos, _path] call FUNC(renderMenu);
if (_angle == 360) then { _offset = [GVAR(vecLineMap), _angle] call FUNC(rotateVectLine);
_angle = _angle + _angleSpan / _numActions; _mod = 0.15 max (0.15 * (_cursorScreenPos distance _pos));
_newPos = _pos vectorAdd (_offset vectorMultiply _mod);
// drawLine3D [_pos, _newPos, [1,0,0,0.5]];
[_object, _x, _forEachIndex, [_angle, 140], _newPos] call FUNC(renderMenu);
if (_angleSpan == 360) then {
_angle = _angle + _angleSpan / (count _activeChildren);
} else { } else {
_angle = _angle + _angleSpan / ((_numActions-1) max 1); _angle = _angle + _angleSpan / (((count _activeChildren)-1) max 1);
};
};
} forEach (_actionData select 6);
};
GVAR(renderDepth) = GVAR(renderDepth) - 1;
}; };
} forEach _activeChildren;

View File

@ -0,0 +1,13 @@
#include "script_component.hpp";
if((count GVAR(vecLineMap)) == 0 || ((count GVAR(menuDepthPath)) > 0 && (getPosASL player) distance GVAR(lastPos) > 0.01)) then {
GVAR(lastPos) = getPosASL player;
_cursorVec = [_cursorPos2, _cursorPos1] call BIS_fnc_vectorFromXtoY;
_p1 = [0,0,0];
_p2 = +_cursorVec;
_p = (_cursorVec call CBA_fnc_vect2polar);
_v = [(_p select 0), (_p select 1), (_p select 2)+90] call CBA_fnc_polar2vect;
_cp = [_cursorVec, _v] call BIS_fnc_crossProduct;
GVAR(vecLineMap) = [_cp, _p1, _p2] call FUNC(rotateVectLineGetMap);
};

View File

@ -1,4 +1,18 @@
// by commy2 /*
* Author: commy2
* Tests the the player can climb.
*
* Arguments:
* 0: The Unit (usually the player) <OBJECT>
*
* Return Value:
* The return value <BOOL>
*
* Example:
* _bool = [player] call ace_movement_fnc_canClimb
*
* Public: No
*/
#include "script_component.hpp" #include "script_component.hpp"
private ["_unit", "_pos", "_dir"]; private ["_unit", "_pos", "_dir"];

View File

@ -1,4 +1,18 @@
// by commy2 /*
* Author: commy2
* Make the player climb over short walls.
*
* Arguments:
* 0: The Unit (usually the player) <OBJECT>
*
* Return Value:
* Nothing
*
* Example:
* [player] call ace_movement_fnc_climb
*
* Public: No
*/
#include "script_component.hpp" #include "script_component.hpp"
private "_unit"; private "_unit";

View File

@ -1,4 +1,18 @@
// by commy2 /*
* Author: commy2
* Returns the weight (from the loadAbs command) in lbs/kg (based on user option)
*
* Arguments:
* 0: The Unit (usually the player) <OBJECT>
*
* Return Value:
* The return value <NUMBER>
*
* Example:
* _bool = [player] call ace_movement_fnc_getWeight
*
* Public: No
*/
#include "script_component.hpp" #include "script_component.hpp"
private ["_unit", "_weight"]; private ["_unit", "_weight"];

View File

@ -1,4 +1,19 @@
// by commy2 /*
* Author: commy2
* Handles the climb animation finishing. Called from "AnimDone" event handler.
*
* Arguments:
* 0: The Unit (usually the player) <OBJECT>
* 1: The finisehd animation <STRING>
*
* Return Value:
* Nothing
*
* Example:
* [player, "ACE_climb"] call ace_movement_fnc_handleClimb
*
* Public: No
*/
#include "script_component.hpp" #include "script_component.hpp"
private ["_unit", "_anim", "_pos"]; private ["_unit", "_anim", "_pos"];

View File

@ -55,6 +55,15 @@ class CfgVehicles {
}; };
}; };
}; };
class showCursorTagForVehicles {
displayName = "Show for Vehicles";
description = "Show cursor NameTag for vehicle commander (only if client has name tags enabled)Default: No";
typeName = "BOOL";
class values {
class Yes {name = "Yes"; value = 1;};
class No {default = 1; name = "No"; value = 0;};
};
};
}; };
}; };
}; };

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

View File

@ -1,6 +1,8 @@
// by commy2 and CAA-Picard // by commy2 and CAA-Picard
#include "script_component.hpp" #include "script_component.hpp"
[] call FUNC(initIsSpeaking);
if (!hasInterface) exitWith {}; if (!hasInterface) exitWith {};
@ -25,57 +27,4 @@ if (!hasInterface) exitWith {};
// Draw handle // Draw handle
addMissionEventHandler ["Draw3D", { addMissionEventHandler ["Draw3D", {_this call FUNC(onDraw3d);}];
if (GVAR(showPlayerNames) == 0) exitWith {};
_player = ACE_player;
if (GVAR(showPlayerNames) in [2,4]) then { //only on cursor
_target = cursorTarget;
_target = if (_target in allUnitsUAV) then {objNull} else {effectiveCommander _target};
if (!isNull _target && {side group _target == playerSide} && {_target != _player} && {isPlayer _target || {GVAR(ShowNamesForAI)}} && {!(_target getVariable ["ACE_hideName", false])}) then {
_distance = _player distance _target;
_alpha = ((1 - 0.2 * (_distance - GVAR(PlayerNamesViewDistance))) min 1) * GVAR(PlayerNamesMaxAlpha);
if ((GVAR(showPlayerNames) in [3,4])) then { //only on keypress
_alpha = _alpha min (1 - (time - GVAR(ShowNamesTime) - 1));
};
[_player, _target, _alpha, _distance * 0.026] call FUNC(drawNameTagIcon);
};
} else {
_pos = positionCameraToWorld [0, 0, 0];
_targets = _pos nearObjects ["Man", GVAR(PlayerNamesViewDistance) + 5];
if (!surfaceIsWater _pos) then {
_pos = ATLtoASL _pos;
};
_pos2 = positionCameraToWorld [0, 0, 1];
if (!surfaceIsWater _pos2) then {
_pos2 = ATLtoASL _pos2;
};
_vecy = _pos2 vectorDiff _pos;
{
_target = if (_x in allUnitsUAV) then {objNull} else {effectiveCommander _x};
if (!isNull _target && {side group _target == playerSide} && {_target != _player} && {isPlayer _target || {GVAR(ShowNamesForAI)}} && {!(_target getVariable ["ACE_hideName", false])}) then {
_relPos = (visiblePositionASL _target) vectorDiff _pos;
_distance = vectorMagnitude _relPos;
_projDist = _relPos vectorDistance (_vecy vectorMultiply (_relPos vectorDotProduct _vecy));
_alpha = ((1 - 0.2 * (_distance - GVAR(PlayerNamesViewDistance))) min (1 - 0.15 * (_projDist * 5 - _distance - 3)) min 1) * GVAR(PlayerNamesMaxAlpha);
if ((GVAR(showPlayerNames) in [3,4])) then { //only on keypress
_alpha = _alpha min (1 - (time - GVAR(ShowNamesTime) - 1));
};
// Check if there is line of sight
if (_alpha > 0) then {
if (lineIntersects [_pos, (visiblePositionASL _target) vectorAdd [0,0,1], vehicle _player, _target]) then {
_alpha = 0;
};
};
[_player, _target, _alpha, _distance * 0.026] call FUNC(drawNameTagIcon);
};
} forEach _targets;
};
}];

View File

@ -6,7 +6,9 @@ PREP(canShow);
PREP(doShow); PREP(doShow);
PREP(drawNameTagIcon); PREP(drawNameTagIcon);
PREP(getVehicleData); PREP(getVehicleData);
PREP(initIsSpeaking);
PREP(moduleNameTags); PREP(moduleNameTags);
PREP(onDraw3d);
PREP(onMouseZChanged); PREP(onMouseZChanged);
PREP(setText); PREP(setText);

View File

@ -16,6 +16,12 @@ class CfgPatches {
#include "CfgVehicles.hpp" #include "CfgVehicles.hpp"
class ACE_Settings { class ACE_Settings {
class GVAR(defaultNametagColor) {
value[] = {0.77, 0.51, 0.08, 1};
typeName = "COLOR";
isClientSetable = 1;
displayName = "$STR_ACE_NameTags_DefaultNametagColor";
};
class GVAR(showPlayerNames) { class GVAR(showPlayerNames) {
value = 1; value = 1;
typeName = "SCALAR"; typeName = "SCALAR";
@ -41,7 +47,18 @@ class ACE_Settings {
isClientSetable = 1; isClientSetable = 1;
displayName = "$STR_ACE_NameTags_ShowNamesForAI"; displayName = "$STR_ACE_NameTags_ShowNamesForAI";
}; };
class GVAR(showCursorTagForVehicles) {
value = 0;
typeName = "BOOL";
isClientSetable = 0;
};
class GVAR(showSoundWaves) {
value = 1;
typeName = "SCALAR";
isClientSetable = 1;
displayName = "$STR_ACE_NameTags_ShowSoundWaves";
values[] = {"Disabled", "Use Nametag settings", "Always Show All"};
};
class GVAR(PlayerNamesViewDistance) { class GVAR(PlayerNamesViewDistance) {
value = 5; value = 5;
typeName = "SCALAR"; typeName = "SCALAR";

View File

@ -4,9 +4,11 @@
* Draw the nametag and rank icon. * Draw the nametag and rank icon.
* *
* Argument: * Argument:
* 0: Unit (Array) * 0: Unit (Player) <OBJECT>
* 1: alpha (Number) * 1: Target <OBJECT>
* 2: Height offset (Number) * 2: alpha (Number)
* 4: Height offset (Number)
* 5: Draw Type <NUMBER>
* *
* Return value: * Return value:
* None. * None.
@ -25,32 +27,49 @@
"\A3\Ui_f\data\GUI\Cfg\Ranks\colonel_gs.paa" \ "\A3\Ui_f\data\GUI\Cfg\Ranks\colonel_gs.paa" \
] ]
private ["_player", "_target", "_alpha", "_heightOffset", "_height", "_position", "_color", "_name", "_rank", "_size"]; private ["_height", "_position", "_color", "_name", "_rank", "_size"];
_player = _this select 0; PARAMS_5(_player,_target,_alpha,_heightOffset,_iconType);
_target = _this select 1;
_alpha = _this select 2;
_heightOffset = _this select 3;
_height = [2, 1.5, 1, 1.5, 1] select (["STAND", "CROUCH", "PRONE", "UNDEFINED", ""] find stance _target); if (_alpha < 0) exitWith {}; //Don't waste time if not visable
if (_iconType == ICON_NONE) exitWith {}; //Don't waste time if not visable
_position = visiblePositionASL _target;
// Convert position to ASLW (expected by drawIcon3D) and add height offsets
_position set [2, ((_target modelToWorld [0,0,0]) select 2) + _height + _heightOffset];
_color = if !(group _target == group _player) then { //Set Text:
[0.77, 0.51, 0.08, _alpha] _name = if (_iconType in [ICON_NAME, ICON_NAME_RANK, ICON_NAME_SPEAK]) then {
[_target, true] call EFUNC(common,getName)
} else { } else {
[[1, 1, 1, _alpha], [1, 0, 0, _alpha], [0, 1, 0, _alpha], [0, 0, 1, _alpha], [1, 1, 0, _alpha]] select (["MAIN", "RED", "GREEN", "BLUE", "YELLOW"] find (if (_target == _player) then {0} else {assignedTeam _target})) max 0 ""
}; };
_name = [_target, true] call EFUNC(common,getName); //Set Icon:
_icon = "";
_size = 0;
if ((_iconType == ICON_NAME_SPEAK) || (_iconType == ICON_SPEAK)) then {
_icon = QUOTE(PATHTOF(UI\soundwave)) + str (floor (random 10)) + ".paa";
_size = 0.75;
_alpha = _alpha + 0.6;//Boost alpha when speaking
} else {
if (_iconType == ICON_NAME_RANK) then {
_icon = TEXTURES_RANKS select ((["PRIVATE", "CORPORAL", "SERGEANT", "LIEUTENANT", "CAPTAIN", "MAJOR", "COLONEL"] find (rank _target)) + 1);
_size = 0.75;
};
};
_rank = TEXTURES_RANKS select ((["PRIVATE", "CORPORAL", "SERGEANT", "LIEUTENANT", "CAPTAIN", "MAJOR", "COLONEL"] find rank _target) + 1); //Set Color:
_size = [0, 1] select GVAR(showPlayerRanks); if !(group _target == group _player) then {
_color = +GVAR(defaultNametagColor); //Make a copy, then multiply both alpha values (allows client to decrease alpha in settings)
_color set [3, (_color select 3) * _alpha];
} else {
_color = [[1, 1, 1, _alpha], [1, 0, 0, _alpha], [0, 1, 0, _alpha], [0, 0, 1, _alpha], [1, 1, 0, _alpha]] select (["MAIN", "RED", "GREEN", "BLUE", "YELLOW"] find (if (_target == _player) then {0} else {assignedTeam _target})) max 0
};
_height = [2, 1.5, 1, 1.5, 1] select (["STAND", "CROUCH", "PRONE", "UNDEFINED", ""] find (stance _target));
// Convert position to ASLW (expected by drawIcon3D) and add height offsets
_position = _target modelToWorldVisual [0, 0, (_height + _heightOffset)];
drawIcon3D [ drawIcon3D [
_rank, _icon,
_color, _color,
_position, _position,
_size, _size,

View File

@ -0,0 +1,76 @@
/*
* Author: Glowbal, PabstMirror
* Starts up a PFEH to monitor the when players are talking.
* Compatiblity with TFR/ACRE and Arma's VON
*
* Arguments:
* NONE
*
* Return Value:
* NONE
*
* Example:
* [] call ACE_nametags_fnc_initIsSpeaking
*
* Public: No
*/
#include "script_component.hpp"
if (isServer) then {
//If someone disconnects while speaking, reset their variable
addMissionEventHandler ["HandleDisconnect", {
PARAMS_1(_disconnectedPlayer);
if (_disconnectedPlayer getVariable [QGVAR(isSpeaking), false]) then {
_disconnectedPlayer setVariable [QGVAR(isSpeaking), false, true];
};
}];
};
if (!hasInterface) exitWith {};
["playerChanged", {
//When player changes, make sure to reset old unit's variable
PARAMS_2(_newUnit,_oldUnit);
if (_oldUnit getVariable [QGVAR(isSpeaking), false]) then {
_oldUnit setVariable [QGVAR(isSpeaking), false, true];
};
}] call EFUNC(common,addEventHandler);
//For performance, chose different code paths at mission start based on installed mods (once, instead of checking each time)
_pfEHCode = switch (true) do {
case (isClass (configFile >> "cfgPatches" >> "acre_api")): {
{
_oldSetting = ACE_player getVariable [QGVAR(isSpeaking), false];
_newSetting = ([ACE_player] call ACRE_api_fnc_isBroadcasting) || {!(isNull findDisplay 55)};
if (!(_oldSetting isEqualTo _newSetting)) then {
ACE_player setVariable [QGVAR(isSpeaking), _newSetting, true];
};
};
};
case (isClass (configFile >> "cfgPatches" >> "task_force_radio")): {
//Note: TFAR has a TFAR_fnc_isSpeaking function, but it has a fairly costly `callExtension`
//I think it's much faster to use the internal "tf_isSpeaking" variable
//If we don't care about the built-in VON, we could switch this to a pure event driven system
{
_oldSetting = ACE_player getVariable [QGVAR(isSpeaking), false];
_newSetting = (ACE_player getVariable ["tf_isSpeaking", false]) || {!(isNull findDisplay 55)};
if (!(_oldSetting isEqualTo _newSetting)) then {
ACE_player setVariable [QGVAR(isSpeaking), _newSetting, true];
};
};
};
default {
//Note: class RscDisplayVoiceChat {idd = 55}; //only present when talking
{
_oldSetting = ACE_player getVariable [QGVAR(isSpeaking), false];
_newSetting = (!(isNull findDisplay 55));
if (!(_oldSetting isEqualTo _newSetting)) then {
ACE_player setVariable [QGVAR(isSpeaking), _newSetting, true];
};
};
};
};
//Is 0.05sec precision enough??
[_pfEHCode, 0.05, []] call CBA_fnc_addPerFrameHandler;

View File

@ -25,5 +25,6 @@ GVAR(Module) = true;
[_logic, QGVAR(PlayerNamesViewDistance), "PlayerNamesViewDistance" ] call EFUNC(common,readSettingFromModule); [_logic, QGVAR(PlayerNamesViewDistance), "PlayerNamesViewDistance" ] call EFUNC(common,readSettingFromModule);
[_logic, QGVAR(ShowNamesForAI), "ShowNamesForAI" ] call EFUNC(common,readSettingFromModule); [_logic, QGVAR(ShowNamesForAI), "ShowNamesForAI" ] call EFUNC(common,readSettingFromModule);
[_logic, QGVAR(showVehicleCrewInfo), "showVehicleCrewInfo" ] call EFUNC(common,readSettingFromModule); [_logic, QGVAR(showVehicleCrewInfo), "showVehicleCrewInfo" ] call EFUNC(common,readSettingFromModule);
[_logic, QGVAR(showCursorTagForVehicles), "showCursorTagForVehicles" ] call EFUNC(common,readSettingFromModule);
diag_log text "[ACE]: NameTags Module Initialized."; diag_log text "[ACE]: NameTags Module Initialized.";

View File

@ -0,0 +1,108 @@
#include "script_component.hpp"
_player = ACE_player;
//don't show nametags in spectator
if (!alive _player) exitWith {};
_onKeyPressAlphaMax = if ((GVAR(showPlayerNames) in [3,4])) then {
2 + (GVAR(ShowNamesTime) - time); //after release 1 second of full opacity, 1 second of fading to 0
} else {
1
};
_defaultIcon = if (GVAR(showPlayerRanks)) then {
ICON_NAME_RANK;
} else {
ICON_NAME;
};
//When cursorTarget is on a vehicle show the nametag for the commander.
//If set to "Only On Keypress" settings, fade just like main tags
if (GVAR(showCursorTagForVehicles) && {_onKeyPressAlphaMax > 0}) then {
_target = cursorTarget;
if ((!(_target isKindOf "CAManBase")) && {!(_target in allUnitsUAV)}) then {
_target = effectiveCommander _target;
if ((!isNull _target) &&
{(side (group _target)) == (side (group _player))} &&
{_target != _player} &&
{GVAR(ShowNamesForAI) || {[_target] call EFUNC(common,isPlayer)}} &&
{!(_target getVariable ["ACE_hideName", false])}) then {
_distance = _player distance _target;
_alpha = ((1 - 0.2 * (_distance - GVAR(PlayerNamesViewDistance))) min 1) * GVAR(PlayerNamesMaxAlpha);
_alpha = _alpha min _onKeyPressAlphaMax;
[_player, _target, _alpha, _distance * 0.026, _defaultIcon] call FUNC(drawNameTagIcon);
};
};
};
//"Only Cursor" mode, only show nametags for humans on cursorTarget
if ((GVAR(showPlayerNames) in [2,4]) && {_onKeyPressAlphaMax > 0}) then {
_target = cursorTarget;
if ((!isNull _target) &&
{_target isKindOf "CAManBase"} &&
{(side (group _target)) == (side (group _player))} &&
{_target != _player} &&
{GVAR(ShowNamesForAI) || {[_target] call EFUNC(common,isPlayer)}} &&
{!(_target getVariable ["ACE_hideName", false])}) then {
_distance = _player distance _target;
_alpha = ((1 - 0.2 * (_distance - GVAR(PlayerNamesViewDistance))) min 1) * GVAR(PlayerNamesMaxAlpha);
_alpha = _alpha min _onKeyPressAlphaMax;
_icon = ICON_NONE;
if (GVAR(showSoundWaves) == 2) then { //icon will be drawn below, so only show name here
_icon = if ((_target getVariable [QGVAR(isSpeaking), false]) && {(vehicle _target) == _target}) then {ICON_NAME} else {_defaultIcon};
} else {
_icon = if ((_target getVariable [QGVAR(isSpeaking), false]) && {(vehicle _target) == _target} && {GVAR(showSoundWaves) > 0}) then {ICON_NAME_SPEAK} else {_defaultIcon};
};
[_player, _target, _alpha, _distance * 0.026, _icon] call FUNC(drawNameTagIcon);
};
};
if (((GVAR(showPlayerNames) in [1,3]) && {_onKeyPressAlphaMax > 0}) || {GVAR(showSoundWaves) == 2}) then {
_pos = positionCameraToWorld [0, 0, 0];
_targets = _pos nearObjects ["CAManBase", GVAR(PlayerNamesViewDistance) + 5];
if (!surfaceIsWater _pos) then {
_pos = ATLtoASL _pos;
};
_pos2 = positionCameraToWorld [0, 0, 1];
if (!surfaceIsWater _pos2) then {
_pos2 = ATLtoASL _pos2;
};
_vecy = _pos2 vectorDiff _pos;
{
_target = _x;
_icon = ICON_NONE;
if ((GVAR(showPlayerNames) in [1,3]) && {_onKeyPressAlphaMax > 0}) then {
if ((_target getVariable [QGVAR(isSpeaking), false]) && {(vehicle _target) == _target} && {GVAR(showSoundWaves) > 0}) then {_icon = ICON_NAME_SPEAK;} else {_icon = _defaultIcon};
} else {
//showSoundWaves must be 2, only draw speak icon
if ((_target getVariable [QGVAR(isSpeaking), false]) && {(vehicle _target) == _target}) then {_icon = ICON_SPEAK;};
};
if ((_icon != ICON_NONE) &&
{(side (group _target)) == (side (group _player))} &&
{_target != _player} &&
{GVAR(ShowNamesForAI) || {[_target] call EFUNC(common,isPlayer)}} &&
{!(_target getVariable ["ACE_hideName", false])}) then {
if (lineIntersects [_pos, (visiblePositionASL _target) vectorAdd [0,0,1], vehicle _player, _target]) exitWith {}; // Check if there is line of sight
_relPos = (visiblePositionASL _target) vectorDiff _pos;
_distance = vectorMagnitude _relPos;
_projDist = _relPos vectorDistance (_vecy vectorMultiply (_relPos vectorDotProduct _vecy));
_alpha = ((1 - 0.2 * (_distance - GVAR(PlayerNamesViewDistance))) min (1 - 0.15 * (_projDist * 5 - _distance - 3)) min 1) * GVAR(PlayerNamesMaxAlpha);
if ((GVAR(showSoundWaves) == 2) && {(_target getVariable [QGVAR(isSpeaking), false]) && {(vehicle _target) == _target}}) then {
_alpha = 1;
} else {
_alpha = _alpha min _onKeyPressAlphaMax;
};
[_player, _target, _alpha, _distance * 0.026, _icon] call FUNC(drawNameTagIcon);
};
} forEach _targets;
};

View File

@ -10,3 +10,9 @@
#endif #endif
#include "\z\ace\addons\main\script_macros.hpp" #include "\z\ace\addons\main\script_macros.hpp"
#define ICON_NONE 0
#define ICON_NAME 1
#define ICON_NAME_RANK 2
#define ICON_NAME_SPEAK 3
#define ICON_SPEAK 4

View File

@ -1,5 +1,5 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<!-- Edited with tabler - 2014-12-17 --> <!-- Edited with tabler - 2015-02-13 -->
<Project name="ACE"> <Project name="ACE">
<Package name="NameTags"> <Package name="NameTags">
<Key ID="STR_ACE_NameTags_ShowNames"> <Key ID="STR_ACE_NameTags_ShowNames">
@ -69,5 +69,13 @@
<Key ID="STR_ACE_NameTags_ShowNamesForAI"> <Key ID="STR_ACE_NameTags_ShowNamesForAI">
<English>Show name tags for AI units</English> <English>Show name tags for AI units</English>
</Key> </Key>
<Key ID="STR_ACE_NameTags_ShowSoundWaves">
<English>Show SoundWaves (requires player names)</English>
<German>Zeigen Schallwelle (benötigt spielernamen)</German>
<Spanish>Mostrar onda sonora (requiere Mostrar nombres de jugadores)</Spanish>
</Key>
<Key ID="STR_ACE_NameTags_DefaultNametagColor">
<English>Default Nametag Color (Non Group Members)</English>
</Key>
</Package> </Package>
</Project> </Project>