ACE3/addons/spectator/functions/fnc_handleInterface.sqf

494 lines
18 KiB
Plaintext
Raw Normal View History

2015-07-15 11:03:54 +00:00
/*
* Author: SilentSpike
* Handles spectator interface events
*
* Arguments:
* 0: Event name <STRING>
* 1: Event arguments <ANY>
*
* Return Value:
* None <NIL>
*
* Example:
* ["onLoad",_this] call ace_spectator_fnc_handleInterface
*
* Public: No
*/
#include "script_component.hpp"
2015-07-18 17:46:46 +00:00
params ["_mode",["_args",[]]];
2015-07-15 11:03:54 +00:00
switch (toLower _mode) do {
case "onload": {
2015-07-18 17:46:46 +00:00
_args params ["_display"];
2015-07-18 14:42:07 +00:00
// Always show interface and hide map upon opening
2015-07-20 21:45:11 +00:00
[_display,nil,nil,!GVAR(showInterface),GVAR(showMap)] call FUNC(toggleInterface);
2015-07-15 11:03:54 +00:00
2015-07-24 18:02:27 +00:00
// Keep unit list and tree up to date
2015-07-19 12:40:08 +00:00
[FUNC(handleUnits), 21, _display] call CBA_fnc_addPerFrameHandler;
// Handle 3D unit icons
GVAR(iconHandler) = addMissionEventHandler ["Draw3D",FUNC(handleIcons)];
// Populate the help window
2015-07-24 16:50:33 +00:00
private "_help";
_help = (_display displayCtrl IDC_HELP) controlsGroupCtrl IDC_HELP_LIST;
2015-07-21 22:20:41 +00:00
{
_i = _help lbAdd (_x select 0);
if ((_x select 1) == "") then {
_help lbSetPicture [_i,"\A3\ui_f\data\map\markers\military\dot_CA.paa"];
_help lbSetPictureColor [_i,[COL_FORE]];
} else {
_help lbSetTooltip [_i,_x select 1];
2015-07-24 16:50:33 +00:00
};
2015-07-21 22:20:41 +00:00
} forEach [
2015-07-24 16:50:33 +00:00
[localize LSTRING(uiControls),""],
2015-07-24 10:23:14 +00:00
[localize LSTRING(uiToggleUnits),"1"],
[localize LSTRING(uiToggleHelp),"2"],
[localize LSTRING(uiToggleTools),"3"],
[localize LSTRING(uiToggleCompass),"4"],
[localize LSTRING(uiToggleIcons),"5"],
[localize LSTRING(uiToggleMap),"M"],
2015-07-24 10:23:14 +00:00
[localize LSTRING(uiToggleInterface),"Backspace"],
[localize LSTRING(freeCamControls),""],
2015-07-21 22:20:41 +00:00
[localize LSTRING(freeCamForward),"W"],
[localize LSTRING(freeCamBackward),"S"],
[localize LSTRING(freeCamLeft),"A"],
[localize LSTRING(freeCamRight),"D"],
[localize LSTRING(freeCamUp),"Q"],
[localize LSTRING(freeCamDown),"Z"],
2015-07-24 10:23:14 +00:00
[localize LSTRING(freeCamPan),"RMB (Hold)"],
[localize LSTRING(freeCamDolly),"LMB (Hold)"],
[localize LSTRING(freeCamBoost),"Shift (Hold)"],
[localize LSTRING(freeCamFocus),"F"],
[localize LSTRING(attributeControls),""],
2015-07-25 10:20:59 +00:00
[localize LSTRING(nextCam),"Up Arrow"],
[localize LSTRING(prevCam),"Down Arrow"],
[localize LSTRING(nextUnit),"Right Arrow"],
[localize LSTRING(prevUnit),"Left Arrow"],
[localize LSTRING(nextVis),"N"],
[localize LSTRING(prevVis),"Ctrl + N"],
[localize LSTRING(adjZoom),"Scrollwheel"],
[localize LSTRING(adjSpeed),"Ctrl + Scrollwheel"],
[localize LSTRING(incZoom),"Num-/Num+"],
[localize LSTRING(incSpeed),"Ctrl + Num-/Num+"],
[localize LSTRING(reZoom),"Alt + Num-"],
[localize LSTRING(reSpeed),"Alt + Num+"]
2015-07-21 22:20:41 +00:00
];
// Handle support for BI's respawn counter
[{
if !(isNull (GETUVAR(RscRespawnCounter,displayNull))) then {
disableSerialization;
private ["_counter","_title","_back","_timer","_frame","_x","_y"];
_counter = GETUVAR(RscRespawnCounter,displayNull);
_title = _counter displayCtrl 1001;
_back = _counter displayCtrl 1002;
_timer = _counter displayCtrl 1003;
_frame = _counter ctrlCreate ["RscFrame",1008];
_x = safeZoneX + safeZoneW - TOOL_W * 4 - MARGIN * 3;
_y = safeZoneY + safeZoneH - TOOL_H;
// Timer
_title ctrlSetPosition [_x,_y,TOOL_W,TOOL_H];
_back ctrlSetPosition [_x,_y,TOOL_W,TOOL_H];
_timer ctrlSetPosition [_x,_y,TOOL_W,TOOL_H];
_frame ctrlSetPosition [_x,_y,TOOL_W,TOOL_H];
_title ctrlSetBackgroundColor [0,0,0,0];
_back ctrlSetBackgroundColor [COL_BACK];
_timer ctrlSetFontHeight TOOL_H;
_frame ctrlSetTextColor [COL_FORE];
_title ctrlCommit 0;
_back ctrlCommit 0;
_timer ctrlCommit 0;
_frame ctrlCommit 0;
};
},[],0.5] call EFUNC(common,waitAndExecute);
2015-07-15 11:03:54 +00:00
};
case "onunload": {
// Kill GUI PFHs
removeMissionEventHandler ["Draw3D",GVAR(iconHandler)];
2015-07-18 16:06:13 +00:00
GVAR(camHandler) = nil;
2015-07-24 18:02:27 +00:00
GVAR(compHandler) = nil;
2015-07-25 11:28:03 +00:00
GVAR(iconHandler) = nil;
2015-07-24 18:02:27 +00:00
GVAR(toolHandler) = nil;
// Reset variables
GVAR(camBoom) = 0;
GVAR(camDolly) = [0,0];
GVAR(ctrlKey) = false;
GVAR(heldKeys) = [];
GVAR(heldKeys) resize 255;
GVAR(mouse) = [false,false];
GVAR(mousePos) = [0.5,0.5];
GVAR(treeSel) = objNull;
2015-07-15 11:03:54 +00:00
};
2015-07-15 11:11:19 +00:00
// Mouse events
case "onmousebuttondown": {
2015-07-18 17:46:46 +00:00
_args params ["_ctrl","_button"];
2015-07-15 11:11:19 +00:00
GVAR(mouse) set [_button,true];
2015-07-15 11:33:32 +00:00
// Detect right click
if ((_button == 1) && (GVAR(camMode) == 1)) then {
2015-07-15 13:33:11 +00:00
// In first person toggle sights mode
2015-07-21 17:05:29 +00:00
GVAR(camGun) = !GVAR(camGun);
2015-07-20 21:45:11 +00:00
[] call FUNC(transitionCamera);
2015-07-15 11:33:32 +00:00
};
2015-07-15 11:11:19 +00:00
};
case "onmousebuttonup": {
2015-07-18 17:46:46 +00:00
_args params ["_ctrl","_button"];
2015-07-15 11:11:19 +00:00
GVAR(mouse) set [_button,false];
2015-07-21 17:44:24 +00:00
if (_button == 0) then { GVAR(camDolly) = [0,0]; };
2015-07-15 11:11:19 +00:00
};
case "onmousezchanged": {
2015-07-18 17:46:46 +00:00
_args params ["_ctrl","_zChange"];
2015-07-15 11:33:32 +00:00
2015-07-19 21:30:44 +00:00
// Scroll to change speed, modifier for zoom
2015-07-15 11:33:32 +00:00
if (GVAR(ctrlKey)) then {
2015-07-24 18:02:27 +00:00
[nil,nil,nil,nil,nil,nil,nil, GVAR(camSpeed) + _zChange * 0.2] call FUNC(setCameraAttributes);
} else {
[nil,nil,nil,nil,nil,nil, GVAR(camZoom) + _zChange * 0.1] call FUNC(setCameraAttributes);
2015-07-15 11:33:32 +00:00
};
2015-07-15 11:11:19 +00:00
};
case "onmousemoving": {
2015-07-18 17:46:46 +00:00
_args params ["_ctrl","_x","_y"];
2015-07-15 11:11:19 +00:00
2015-07-18 15:59:05 +00:00
[_x,_y] call FUNC(handleMouse);
2015-07-15 11:11:19 +00:00
};
2015-07-15 11:03:54 +00:00
// Keyboard events
case "onkeydown": {
2015-07-18 17:46:46 +00:00
_args params ["_display","_dik","_shift","_ctrl","_alt"];
2015-07-15 11:03:54 +00:00
if ((alive player) && {_dik in (actionKeys "curatorInterface")} && {!isNull (getAssignedCuratorLogic player)}) exitWith {
[QGVAR(zeus)] call FUNC(interrupt);
["zeus"] call FUNC(handleInterface);
};
if ((isServer || {serverCommandAvailable "#kick"}) && {_dik in (actionKeys "Chat" + actionKeys "PrevChannel" + actionKeys "NextChannel")}) exitWith {
false
};
2015-07-24 10:12:26 +00:00
// Handle held keys (prevent repeat calling)
if (GVAR(heldKeys) param [_dik,false]) exitwith {};
// Exclude movement/adjustment keys so that speed can be adjusted on fly
if !(_dik in [16,17,30,31,32,44,74,78]) then {
GVAR(heldKeys) set [_dik,true];
2015-07-26 11:23:01 +00:00
};
2015-07-24 10:12:26 +00:00
2015-07-15 11:03:54 +00:00
switch (_dik) do {
case 1: { // Esc
[QGVAR(escape)] call FUNC(interrupt);
["escape"] call FUNC(handleInterface);
2015-07-15 11:03:54 +00:00
};
2015-07-19 21:50:13 +00:00
case 2: { // 1
2015-07-20 21:45:11 +00:00
[_display,nil,nil,nil,nil,nil,true] call FUNC(toggleInterface);
2015-07-19 21:50:13 +00:00
};
case 3: { // 2
[_display,nil,true] call FUNC(toggleInterface);
2015-07-19 21:50:13 +00:00
};
case 4: { // 3
[_display,nil,nil,nil,nil,true] call FUNC(toggleInterface);
2015-07-19 21:50:13 +00:00
};
2015-07-24 16:23:25 +00:00
case 5: { // 4
[_display,true] call FUNC(toggleInterface);
};
case 6: { // 5
2015-07-24 16:23:25 +00:00
GVAR(showIcons) = !GVAR(showIcons);
};
2015-07-15 11:03:54 +00:00
case 14: { // Backspace
2015-07-20 21:45:11 +00:00
[_display,nil,nil,true] call FUNC(toggleInterface);
2015-07-15 11:03:54 +00:00
};
2015-07-15 11:11:19 +00:00
case 16: { // Q
GVAR(camBoom) = 0.5 * GVAR(camSpeed) * ([1, 2] select _shift);
2015-07-15 11:11:19 +00:00
};
case 17: { // W
GVAR(camDolly) set [1, GVAR(camSpeed) * ([1, 2] select _shift)];
2015-07-15 11:11:19 +00:00
};
case 29: { // Ctrl
GVAR(ctrlKey) = true;
};
case 30: { // A
GVAR(camDolly) set [0, -GVAR(camSpeed) * ([1, 2] select _shift)];
2015-07-15 11:11:19 +00:00
};
case 31: { // S
GVAR(camDolly) set [1, -GVAR(camSpeed) * ([1, 2] select _shift)];
2015-07-15 11:11:19 +00:00
};
case 32: { // D
GVAR(camDolly) set [0, GVAR(camSpeed) * ([1, 2] select _shift)];
2015-07-15 11:11:19 +00:00
};
case 33: { // F
private ["_sel","_vector"];
_sel = GVAR(treeSel);
if ((GVAR(camMode) == 0) && {!isNull _sel} && {_sel in GVAR(unitList)}) then {
_vector = (positionCameraToWorld [0,0,0]) vectorDiff (positionCameraToWorld [0,0,25]);
[nil,nil,nil,(getPosATL _sel) vectorAdd _vector] call FUNC(setCameraAttributes);
};
};
2015-07-15 11:11:19 +00:00
case 44: { // Z
GVAR(camBoom) = -0.5 * GVAR(camSpeed) * ([1, 2] select _shift);
2015-07-21 10:59:20 +00:00
};
case 49: { // N
if (GVAR(camMode) == 0) then {
if (_ctrl) then {
[nil,nil,-1] call FUNC(cycleCamera);
} else {
[nil,nil,1] call FUNC(cycleCamera);
};
2015-07-24 10:12:26 +00:00
};
2015-07-15 11:11:19 +00:00
};
2015-07-15 11:03:54 +00:00
case 50: { // M
2015-07-20 21:45:11 +00:00
[_display,nil,nil,nil,true] call FUNC(toggleInterface);
2015-07-15 11:03:54 +00:00
};
2015-07-15 11:33:32 +00:00
case 57: { // Spacebar
2015-07-18 16:13:27 +00:00
// Freecam attachment here, if in external then set cam pos and attach
};
case 74: { // Num -
if (_alt) exitWith { [nil,nil,nil,nil,nil,nil, 1.25] call FUNC(setCameraAttributes); };
if (_ctrl) then {
[nil,nil,nil,nil,nil,nil,nil, GVAR(camSpeed) - 0.05] call FUNC(setCameraAttributes);
} else {
[nil,nil,nil,nil,nil,nil, GVAR(camZoom) - 0.01] call FUNC(setCameraAttributes);
};
};
case 78: { // Num +
if (_alt) exitWith { [nil,nil,nil,nil,nil,nil,nil, 2.5] call FUNC(setCameraAttributes); };
if (_ctrl) then {
[nil,nil,nil,nil,nil,nil,nil, GVAR(camSpeed) + 0.05] call FUNC(setCameraAttributes);
} else {
[nil,nil,nil,nil,nil,nil, GVAR(camZoom) + 0.01] call FUNC(setCameraAttributes);
};
};
2015-07-18 16:13:27 +00:00
case 200: { // Up arrow
2015-07-21 12:31:13 +00:00
[-1] call FUNC(cycleCamera);
2015-07-15 11:33:32 +00:00
};
2015-07-18 15:20:19 +00:00
case 203: { // Left arrow
2015-07-21 15:06:07 +00:00
[nil,1] call FUNC(cycleCamera);
2015-07-18 15:20:19 +00:00
};
case 205: { // Right arrow
2015-07-21 15:06:07 +00:00
[nil,-1] call FUNC(cycleCamera);
2015-07-18 15:20:19 +00:00
};
2015-07-18 18:05:18 +00:00
case 208: { // Down arrow
2015-07-21 12:31:13 +00:00
[1] call FUNC(cycleCamera);
2015-07-18 18:05:18 +00:00
};
2015-07-15 11:03:54 +00:00
};
true
};
case "onkeyup": {
2015-07-18 17:46:46 +00:00
_args params ["_display","_dik","_shift","_ctrl","_alt"];
2015-07-15 11:03:54 +00:00
2015-07-24 10:12:26 +00:00
// No longer being held
GVAR(heldKeys) set [_dik,nil];
2015-07-24 10:12:26 +00:00
2015-07-15 11:03:54 +00:00
switch (_dik) do {
2015-07-15 11:11:19 +00:00
case 16: { // Q
2015-07-21 17:26:49 +00:00
GVAR(camBoom) = 0;
2015-07-15 11:11:19 +00:00
};
case 17: { // W
2015-07-21 17:44:24 +00:00
GVAR(camDolly) set [1, 0];
2015-07-15 11:11:19 +00:00
};
case 29: { // Ctrl
GVAR(ctrlKey) = false;
};
case 30: { // A
2015-07-21 17:44:24 +00:00
GVAR(camDolly) set [0, 0];
2015-07-15 11:11:19 +00:00
};
case 31: { // S
2015-07-21 17:44:24 +00:00
GVAR(camDolly) set [1, 0];
2015-07-15 11:11:19 +00:00
};
case 32: { // D
2015-07-21 17:44:24 +00:00
GVAR(camDolly) set [0, 0];
2015-07-15 11:11:19 +00:00
};
case 44: { // Z
2015-07-21 17:26:49 +00:00
GVAR(camBoom) = 0;
2015-07-15 11:11:19 +00:00
};
2015-07-15 11:03:54 +00:00
};
true
};
2015-07-16 16:01:04 +00:00
// Tree events
case "ontreedblclick": {
2015-07-16 17:31:49 +00:00
// Update camera view when listbox unit is double clicked on
2015-07-18 17:46:46 +00:00
_args params ["_tree","_sel"];
2015-07-16 17:31:49 +00:00
// Ensure a unit was selected
2015-07-20 16:42:11 +00:00
if (count _sel == 3) then {
2015-07-18 17:46:46 +00:00
private ["_netID","_newUnit","_newMode"];
2015-07-16 17:31:49 +00:00
_netID = (_args select 0) tvData _sel;
2015-07-16 18:43:16 +00:00
_newUnit = objectFromNetId _netID;
2015-07-16 17:31:49 +00:00
// When unit is reselected, toggle camera mode
if (_newUnit == GVAR(camUnit) || GVAR(camMode) == 0) then {
2015-07-17 00:52:08 +00:00
_newMode = [2,2,1] select GVAR(camMode);
2015-07-16 16:01:04 +00:00
};
2015-07-21 14:53:20 +00:00
[_newMode,_newUnit] call FUNC(transitionCamera);
2015-07-16 16:01:04 +00:00
};
};
case "ontreeselchanged": {
_args params ["_tree","_sel"];
if (count _sel == 3) then {
GVAR(treeSel) = objectFromNetId (_tree tvData _sel);
} else {
GVAR(treeSel) = objNull;
};
};
2015-07-19 12:40:08 +00:00
case "onunitsupdate": {
2015-07-19 22:03:40 +00:00
_args params ["_tree"];
private ["_cachedUnits","_cachedGrps","_cachedSides","_s","_g","_grp","_u","_unit","_side"];
2015-07-19 12:40:08 +00:00
// Cache existing group and side nodes and cull removed data
_cachedUnits = [];
_cachedGrps = [];
_cachedSides = [];
for "_s" from 0 to ((_tree tvCount []) - 1) do {
for "_g" from 0 to ((_tree tvCount [_s]) - 1) do {
_grp = groupFromNetID (_tree tvData [_s,_g]);
if (_grp in GVAR(groupList)) then {
_cachedGrps pushBack _grp;
_cachedGrps pushBack _g;
for "_u" from 0 to ((_tree tvCount [_s,_g])) do {
_unit = objectFromNetId (_tree tvData [_s,_g,_u]);
if (_unit in GVAR(unitList)) then {
_cachedUnits pushBack _unit;
} else {
_tree tvDelete [_s,_g,_u];
};
};
} else {
_tree tvDelete [_s,_g];
};
};
2015-07-19 12:40:08 +00:00
if ((_tree tvCount [_s]) > 0) then {
_cachedSides pushBack (_tree tvText [_s]);
_cachedSides pushBack _s;
} else {
_tree tvDelete [_s];
};
};
2015-07-19 12:40:08 +00:00
// Update the tree from the unit list
{
_grp = group _x;
2015-07-24 14:53:08 +00:00
_side = [side _grp] call BIS_fnc_sideName;
2015-07-19 12:40:08 +00:00
2015-07-20 16:42:11 +00:00
// Use correct side node
2015-07-21 20:21:46 +00:00
if !(_side in _cachedSides) then {
// Add side node
_s = _tree tvAdd [[], _side];
_tree tvExpand [_s];
2015-07-21 20:21:46 +00:00
_cachedSides pushBack _side;
_cachedSides pushBack _s;
2015-07-21 20:21:46 +00:00
} else {
// If side already processed, use existing node
_s = _cachedSides select ((_cachedSides find _side) + 1);
2015-07-21 20:21:46 +00:00
};
2015-07-20 16:42:11 +00:00
// Use correct group node
if !(_grp in _cachedGrps) then {
// Add group node
_g = _tree tvAdd [[_s], groupID _grp];
_tree tvSetData [[_s,_g], netID _grp];
2015-07-19 12:40:08 +00:00
_cachedGrps pushBack _grp;
_cachedGrps pushBack _g;
2015-07-19 12:40:08 +00:00
} else {
2015-07-20 16:42:11 +00:00
// If group already processed, use existing node
_g = _cachedGrps select ((_cachedGrps find _grp) + 1);
2015-07-19 12:40:08 +00:00
};
_u = _tree tvAdd [[_s,_g], GETVAR(_x,GVAR(uName),"")];
_tree tvSetData [[_s,_g,_u], netID _x];
_tree tvSetPicture [[_s,_g,_u], GETVAR(_x,GVAR(uIcon),"")];
_tree tvSetPictureColor [[_s,_g,_u], GETVAR(_grp,GVAR(gColor),[ARR_4(1,1,1,1)])];
2015-07-19 12:40:08 +00:00
_tree tvSort [[_s,_g],false];
} forEach (GVAR(unitList) - _cachedUnits);
2015-07-21 20:21:46 +00:00
_tree tvSort [[],false];
if ((_tree tvCount []) <= 0) then {
_tree tvAdd [[], localize LSTRING(units_none)];
};
2015-07-19 12:40:08 +00:00
};
2015-07-20 19:30:13 +00:00
// Map events
case "onmapclick": {
_args params ["_map","_button","_x","_y","_shift","_ctrl","_alt"];
2015-07-24 14:36:36 +00:00
private ["_newPos","_oldZ"];
2015-07-20 19:30:13 +00:00
2015-07-25 14:29:53 +00:00
if ((GVAR(camMode) == 0) && (_button == 0)) then {
2015-07-20 19:30:13 +00:00
_newPos = _map ctrlMapScreenToWorld [_x,_y];
2015-07-21 17:05:29 +00:00
_oldZ = (ASLtoATL GVAR(camPos)) select 2;
2015-07-21 17:07:55 +00:00
_newPos set [2, _oldZ];
2015-07-25 11:28:03 +00:00
[nil,nil,nil, _newPos] call FUNC(setCameraAttributes);
2015-07-20 19:30:13 +00:00
};
};
// Interrupt events
2015-07-25 22:59:15 +00:00
case "escape": {
private "_dlg";
2015-07-25 22:59:15 +00:00
createDialog (["RscDisplayInterrupt", "RscDisplayMPInterrupt"] select isMultiplayer);
disableSerialization;
_dlg = finddisplay 49;
_dlg displayAddEventHandler ["KeyDown", {
_key = _this select 1;
!(_key == 1)
}];
// Disable save, respawn, options & manual buttons
(_dlg displayCtrl 103) ctrlEnable false;
if !(alive player) then {
(_dlg displayCtrl 1010) ctrlEnable false;
2015-07-25 22:59:15 +00:00
};
(_dlg displayCtrl 101) ctrlEnable false;
(_dlg displayCtrl 122) ctrlEnable false;
2015-07-25 22:59:15 +00:00
// Initalize abort button (the "spawn" is a necessary evil)
(_dlg displayCtrl 104) ctrlAddEventHandler ["ButtonClick",{_this spawn {
disableSerialization;
_display = ctrlparent (_this select 0);
_abort = [localize "str_msg_confirm_return_lobby",nil,localize "str_disp_xbox_hint_yes",localize "str_disp_xbox_hint_no",_display,nil,true] call BIS_fnc_guiMessage;
if (_abort) then {_display closeDisplay 2; failMission "loser"};
}}];
2015-07-25 22:59:15 +00:00
// PFH to re-open display when menu closes
[{
if !(isNull (findDisplay 49)) exitWith {};
// If still a spectator then re-enter the interface
[QGVAR(escape),false] call FUNC(interrupt);
2015-07-25 22:59:15 +00:00
[_this select 1] call CBA_fnc_removePerFrameHandler;
},0] call CBA_fnc_addPerFrameHandler;
};
case "zeus": {
openCuratorInterface;
[{
// PFH to re-open display when menu closes
[{
if !((isNull curatorCamera) && {isNull (GETMVAR(bis_fnc_moduleRemoteControl_unit,objNull))}) exitWith {};
// If still a spectator then re-enter the interface
[QGVAR(zeus),false] call FUNC(interrupt);
[_this select 1] call CBA_fnc_removePerFrameHandler;
},0] call CBA_fnc_addPerFrameHandler;
},[],5] call EFUNC(common,waitAndExecute);
true
2015-07-25 22:59:15 +00:00
};
2015-07-15 11:03:54 +00:00
};