enum ActionInputType { AIT_CONTINUOUS, //React to hold input and release after it AIT_SINGLE, //React to click input - single use actions AIT_DOUBLECLICK, //React to double click input - single use actions AIT_HOLDSINGLE, //React to hold input - single use actions AIT_CLICKCONTINUOUS, //React to click input for start and click for end AIT_NOINPUTCONTROL, AIT_INVENTORYINPUT, //Inventory specific actions } class ForcedActionData { ActionBase m_Action; ref ActionTarget m_Target; ItemBase m_Item; } class ActionInput : ActionInput_Basic { UAIDWrapper m_input; //Input ID automaticly generated from name. int m_InputType; //Use from action manager for handling input int m_Priority; bool m_DetectFromItem; //Can be used action from item in hands? bool m_DetectFromTarget; //Can be used action from target in vicinity? bool m_DetectFromPlayer; //Can be used action from player? bool m_Enabled; bool m_JustActivate; bool m_HasTarget; PlayerBase m_Player; ref ActionTarget m_ForcedTarget; ref ForcedActionData m_ForcedActionData; ref ActionTarget m_Target; ItemBase m_MainItem; int m_ConditionMask; bool m_Active; void ActionInput() { m_Active = false; m_Enabled = true; m_ForcedTarget = null; m_ForcedActionData = null; m_HasTarget = false; m_JustActivate = false; m_DetectFromTarget = false; m_DetectFromItem = true; m_DetectFromPlayer = true; m_Priority = 100; } void Init(PlayerBase player, ActionManagerClient am) { m_Player = player; if ( LogManager.IsActionLogEnable()) { Debug.ActionLog("n/a",this.ToString(), "n/a","Init()", player.ToString()); } } void SetEnablity(bool value) { m_Enabled = value; } protected void SetInput(string input_name) { m_input = GetUApi().GetInputByName(input_name).GetPersistentWrapper(); if ( LogManager.IsActionLogEnable()) { if (m_input && m_input.InputP()) Debug.ActionLog("(+) input set to " + input_name ,this.ToString(), "n/a","SetInput()", "n/a"); else Debug.ActionLog("(-) input is not set to " + input_name ,this.ToString(), "n/a","SetInput()","n/a"); } } int GetInputType() { return m_InputType; } UAInput GetUAInput() { return m_input.InputP(); } bool JustActivate() { return m_JustActivate; } bool IsActive() { return m_Active; } bool WasEnded() { return !m_Active; } void Update() { if( !m_Enabled ) { m_Active = false; m_JustActivate = false; return; } switch ( m_InputType ) { case ActionInputType.AIT_CONTINUOUS: m_JustActivate = false; if(m_Active) { m_Active = m_input.InputP().LocalHold(); } else { m_Active = m_input.InputP().LocalHoldBegin(); m_JustActivate = m_Active; } break; case ActionInputType.AIT_SINGLE: m_Active = m_input.InputP().LocalClick(); m_JustActivate = m_Active; break; case ActionInputType.AIT_DOUBLECLICK: m_Active = m_input.InputP().LocalDoubleClick(); m_JustActivate = m_Active; break; break; case ActionInputType.AIT_HOLDSINGLE: m_Active = m_input.InputP().LocalHoldBegin(); m_JustActivate = m_Active; break; break; case ActionInputType.AIT_CLICKCONTINUOUS: m_JustActivate = false; if(m_Active) { if ( m_input.InputP().LocalClick() ) { m_Active = false; } } else { m_Active = m_input.InputP().LocalClick(); m_JustActivate = m_Active; } break; break; default: break; } } void Reset() { m_Active = false; ActionsSelectReset(); } void UpdatePossibleActions(PlayerBase player, ActionTarget target, ItemBase item, int action_condition_mask) { } ActionBase GetAction() { return NULL; } ActionTarget GetUsedActionTarget() { return m_Target; } ItemBase GetUsedMainItem() { return m_MainItem; } array GetPossibleActions() { return NULL; } ActionBase GetPossibleAction() { return NULL; } int GetPossibleActionIndex() { return -1; } bool HasTarget() { return false; } void OnActionStart() { ActionsSelectReset(); } void OnActionEnd() { Reset(); } void ActionsSelectReset() {} void ForceAction(ActionBase action, ActionTarget target, ItemBase item ) { m_ForcedActionData = new ForcedActionData; m_ForcedActionData.m_Action = action; m_ForcedActionData.m_Target = target; m_ForcedActionData.m_Item = item; } void ForceActionTarget( ActionTarget target ) { m_ForcedTarget = target; } void ClearForcedAction() { m_ForcedActionData = null; } void ClearForcedTarget() { m_ForcedTarget = NULL; } bool ForceActionCheck(PlayerBase player) { if (m_ForcedActionData) { if (m_ForcedActionData.m_Action.Can(player, m_ForcedActionData.m_Target, m_ForcedActionData.m_Item)) { m_MainItem = m_ForcedActionData.m_Item; m_Target = m_ForcedActionData.m_Target; return true; } } return false; } void SelectNextAction() { } void SelectPrevAction() {} int GetPossibleActionsCount() { return -1; } bool HasInput() { return m_input != NULL; } int GetPriority() { return m_Priority; } } class StandardActionInput : ActionInput { ref array m_SelectActions; int m_selectedActionIndex; void StandardActionInput(PlayerBase player) { m_selectedActionIndex = 0; m_SelectActions = new array; } override void ForceAction(ActionBase action, ActionTarget target, ItemBase item ) { super.ForceAction(action, target, item); m_selectedActionIndex = 0; } void _GetSelectedActions( Object action_source_object, out array select_actions_all, out bool has_any_action_target) { if ( !action_source_object ) return; array possible_actions; array variant_actions; action_source_object.GetActions(this.Type(), possible_actions); ActionBase action; if(possible_actions) { for (int i = 0; i < possible_actions.Count(); i++) { action = ActionBase.Cast(possible_actions.Get(i)); if ( action.HasVariants() ) { action.UpdateVariants( m_MainItem, m_Target.GetObject(), m_Target.GetComponentIndex() ); action.GetVariants( variant_actions); for (int j = 0; j < variant_actions.Count(); j++) { action = variant_actions[j]; if ( action.Can(m_Player, m_Target, m_MainItem, m_ConditionMask) ) { select_actions_all.Insert(action); if (action.HasTarget()) has_any_action_target = true; } } } else { if ( action.Can(m_Player, m_Target, m_MainItem, m_ConditionMask) ) { select_actions_all.Insert(action); if (action.HasTarget()) has_any_action_target = true; } } } } } override void UpdatePossibleActions(PlayerBase player, ActionTarget target, ItemBase item, int action_condition_mask) { if ( ForceActionCheck(player)) { m_SelectActions.Clear(); m_SelectActions.Insert(m_ForcedActionData.m_Action); return; } if(m_ForcedTarget) { target = m_ForcedTarget; } array select_actions_all = new array; int i, last_index; bool change = false; m_HasTarget = false; m_MainItem = item; m_Target = target; m_ConditionMask = action_condition_mask; if( m_DetectFromItem ) { _GetSelectedActions( item, select_actions_all, m_HasTarget); } if( m_DetectFromTarget ) { _GetSelectedActions( target.GetObject(), select_actions_all, m_HasTarget); _GetSelectedActions( target.GetParent(), select_actions_all, m_HasTarget); } if( m_DetectFromPlayer ) { _GetSelectedActions( player, select_actions_all, m_HasTarget); } if (select_actions_all.Count()) { last_index = 0; for ( i = 0; i < select_actions_all.Count(); i++ ) { ActionBase action = select_actions_all[i]; if ( m_HasTarget ) { if ( action.HasTarget() ) { if ( m_SelectActions.Count() > last_index ) { if ( m_SelectActions[last_index] != action ) { change = true; m_SelectActions[last_index] = action; } } else { change = true; m_SelectActions.Insert(action); } action.OnActionInfoUpdate(player, target, item); last_index++; } } else { if ( m_SelectActions.Count() > last_index ) { if ( m_SelectActions[last_index] != action ) { change = true; m_SelectActions[last_index++] = action; } } else { change = true; m_SelectActions.Insert(action); } action.OnActionInfoUpdate(player, target, item); last_index++; } } } else { change = true; m_selectedActionIndex = 0; m_SelectActions.Clear(); } if (m_SelectActions.Count() > last_index) { change = true; for (i = last_index; i < m_SelectActions.Count(); i++) { m_SelectActions.Remove(last_index); } } if ( change ) { m_selectedActionIndex = 0; m_Player.GetActionManager().SelectFirstActionCategory(); } } override array GetPossibleActions() { return m_SelectActions; } override int GetPossibleActionsCount() { return m_SelectActions.Count(); } override bool HasTarget() { return m_HasTarget; } override int GetPossibleActionIndex() { return m_selectedActionIndex; } override ActionBase GetAction() { if (m_SelectActions.Count() > 0) return m_SelectActions[m_selectedActionIndex]; return null; } override void ActionsSelectReset() { m_SelectActions.Clear(); m_selectedActionIndex = 0; } override void SelectNextAction() { if(m_SelectActions.Count()) { m_selectedActionIndex++; if(m_SelectActions.Count() <= m_selectedActionIndex ) { m_selectedActionIndex = 0; } } } override void SelectPrevAction() { if(m_SelectActions.Count()) { m_selectedActionIndex--; if(0 > m_selectedActionIndex ) { m_selectedActionIndex = m_SelectActions.Count() - 1; } } } } class ContinuousInteractActionInput : StandardActionInput { void ContinuousInteractActionInput(PlayerBase player) { SetInput("UAAction"); m_Priority = 60; m_InputType = ActionInputType.AIT_CONTINUOUS; m_DetectFromTarget = true; m_DetectFromItem = false; m_DetectFromPlayer = true; } }; class InteractActionInput : ContinuousInteractActionInput { void InteractActionInput(PlayerBase player) { m_InputType = ActionInputType.AIT_SINGLE; m_Priority = 80; } override void OnActionStart() { super.OnActionStart(); m_Active = false; } override bool WasEnded() { return false; } }; class NoIndicationActionInputBase : ActionInput { void NoIndicationActionInputBase(PlayerBase player) { m_DetectFromTarget = false; } override void UpdatePossibleActions(PlayerBase player, ActionTarget target, ItemBase item, int action_condition_mask) { m_MainItem = item; m_Target = target; m_ConditionMask = action_condition_mask; } override ActionBase GetAction() { if ( ForceActionCheck(m_Player) ) return m_ForcedActionData.m_Action; if(m_MainItem) { array possible_actions; ActionBase action; m_MainItem.GetActions(this.Type(), possible_actions); if(possible_actions) { for (int i = 0; i < possible_actions.Count(); i++) { action = ActionBase.Cast(possible_actions.Get(i)); if ( action.Can(m_Player, m_Target, m_MainItem, m_ConditionMask) ) { return action; } } } } return NULL; } override ActionBase GetPossibleAction() { return GetAction(); } } class ContinuousDefaultActionInput : StandardActionInput { protected ActionBase m_SelectAction; //Do nothing only for back compatibilit, relevant only for inherited class void ContinuousDefaultActionInput(PlayerBase player) { SetInput("UADefaultAction"); m_InputType = ActionInputType.AIT_CONTINUOUS; m_Priority = 20; m_DetectFromTarget = false; m_DetectFromItem = true; m_DetectFromPlayer = true; m_SelectAction = null; } override ActionBase GetPossibleAction() { return m_SelectAction; } override void ActionsSelectReset() { super.ActionsSelectReset(); m_SelectAction = NULL; } }; class DefaultActionInput : ContinuousDefaultActionInput { void DefaultActionInput(PlayerBase player) { m_InputType = ActionInputType.AIT_SINGLE; m_Priority = 40; } override void OnActionStart() { super.OnActionStart(); m_Active = false; } override bool WasEnded() { return false; } }; class DropActionInput : NoIndicationActionInputBase { void DropActionInput(PlayerBase player) { SetInput("UADropitem"); m_InputType = ActionInputType.AIT_HOLDSINGLE; } }; class CarHornShortActionInput : ContinuousDefaultActionInput { ref ActionTarget targetNew; void CarHornShortActionInput(PlayerBase player) { SetInput("UACarHorn"); m_InputType = ActionInputType.AIT_SINGLE; m_Priority = 100; m_DetectFromItem = false; m_DetectFromTarget = false; m_DetectFromPlayer = false; } override void UpdatePossibleActions(PlayerBase player, ActionTarget target, ItemBase item, int action_condition_mask) { if (ForceActionCheck(player)) { m_SelectAction = m_ForcedActionData.m_Action; return; } m_SelectAction = null; array possibleActions; ActionBase action; int i; m_MainItem = null; if (player && player.IsInVehicle()) { HumanCommandVehicle vehCommand = player.GetCommand_Vehicle(); if (vehCommand) { Transport trans = vehCommand.GetTransport(); if (trans) { targetNew = new ActionTarget(trans, null, -1, vector.Zero, -1); ForceActionTarget(targetNew); } } if (!targetNew) { ClearForcedTarget(); } } target = m_ForcedTarget; m_Target = m_ForcedTarget; if (target && target.GetObject()) { target.GetObject().GetActions(this.Type(), possibleActions); if (possibleActions) { for (i = 0; i < possibleActions.Count(); i++) { action = ActionBase.Cast(possibleActions.Get(i)); if (action.Can(player, target, m_MainItem, action_condition_mask)) { m_SelectAction = action; return; } } } } } override ActionBase GetAction() { return m_SelectAction; } } class CarHornLongActionInput : CarHornShortActionInput { void CarHornLongActionInput(PlayerBase player) { SetInput("UACarHorn"); m_InputType = ActionInputType.AIT_CONTINUOUS; m_Priority = 101; m_DetectFromItem = false; m_DetectFromTarget = false; m_DetectFromPlayer = false; } } class ToggleLightsActionInput : DefaultActionInput { ref ActionTarget target_new; void ToggleLightsActionInput(PlayerBase player) { SetInput("UAToggleHeadlight"); m_InputType = ActionInputType.AIT_SINGLE; m_Priority = 100; } override void UpdatePossibleActions(PlayerBase player, ActionTarget target, ItemBase item, int action_condition_mask) { if( ForceActionCheck(player) ) { m_SelectAction = m_ForcedActionData.m_Action; return; } //ForceActionTarget(player.m_PlayerLightManager. m_SelectAction = NULL; array possible_actions; ActionBase action; int i; m_MainItem = NULL; if ( player && !player.IsInVehicle() ) { Clothing headgear = Clothing.Cast(player.FindAttachmentBySlotName("Headgear")); Clothing eyewear = Clothing.Cast(player.FindAttachmentBySlotName("Eyewear")); //TODO - extend this to allow for a switchable control over all possible light sources (depth 0 or 1 only?) if ( headgear && headgear.GetLightSourceItem() ) { target_new = new ActionTarget(headgear, null, -1, vector.Zero, -1); ForceActionTarget(target_new); } else if ( eyewear && eyewear.GetLightSourceItem() ) { target_new = new ActionTarget(eyewear, null, -1, vector.Zero, -1); ForceActionTarget(target_new); } else ClearForcedTarget(); } else if ( player && player.IsInVehicle() ) { HumanCommandVehicle vehCommand = player.GetCommand_Vehicle(); if( vehCommand ) { Transport trans = vehCommand.GetTransport(); if( trans ) { target_new = new ActionTarget(trans, null, -1, vector.Zero, -1); ForceActionTarget(target_new); } } if ( !target_new ) ClearForcedTarget(); } target = m_ForcedTarget; m_Target = m_ForcedTarget; if(target && target.GetObject()) { target.GetObject().GetActions(this.Type(), possible_actions); if(possible_actions) { for (i = 0; i < possible_actions.Count(); i++) { action = ActionBase.Cast(possible_actions.Get(i)); if ( action.Can(player, target, m_MainItem, action_condition_mask) ) { m_SelectAction = action; return; } } } } } override ActionBase GetAction() { return m_SelectAction; } }; class ToggleNVGActionInput : DefaultActionInput { ref ActionTarget target_new; void ToggleNVGActionInput(PlayerBase player) { SetInput("UAToggleNVG"); m_InputType = ActionInputType.AIT_HOLDSINGLE; m_Priority = 100; } override void UpdatePossibleActions(PlayerBase player, ActionTarget target, ItemBase item, int action_condition_mask) { if( ForceActionCheck(player) ) { m_SelectAction = m_ForcedActionData.m_Action; return; } //ForceActionTarget(player.m_PlayerLightManager. m_SelectAction = NULL; array possible_actions; ActionBase action; int i; m_MainItem = NULL; if ( player ) { Mich2001Helmet helmet = Mich2001Helmet.Cast(player.FindAttachmentBySlotName("Headgear")); NVGHeadstrap headstrap = NVGHeadstrap.Cast(player.FindAttachmentBySlotName("Eyewear")); if ( helmet ) { //m_MainItem = Headtorch_ColorBase.Cast(player.FindAttachmentBySlotName("Headgear")); target_new = new ActionTarget(helmet, null, -1, vector.Zero, -1); ForceActionTarget(target_new); } else if ( headstrap ) { target_new = new ActionTarget(headstrap, null, -1, vector.Zero, -1); ForceActionTarget(target_new); } else ClearForcedTarget(); } target = m_ForcedTarget; m_Target = m_ForcedTarget; if(target && target.GetObject()) { target.GetObject().GetActions(this.Type(), possible_actions); if(possible_actions) { for (i = 0; i < possible_actions.Count(); i++) { action = ActionBase.Cast(possible_actions.Get(i)); if ( action.Can(player, target, m_MainItem, action_condition_mask) ) { m_SelectAction = action; return; } } } } } override ActionBase GetAction() { return m_SelectAction; } }; class ContinuousWeaponManipulationActionInput : NoIndicationActionInputBase { void ContinuousWeaponManipulationActionInput(PlayerBase player) { SetInput("UAReloadMagazine"); m_InputType = ActionInputType.AIT_CONTINUOUS; } }; class WeaponManipulationActionInput : NoIndicationActionInputBase { void WeaponManipulationActionInput(PlayerBase player) { SetInput("UAReloadMagazine"); m_InputType = ActionInputType.AIT_SINGLE; } }; class ExternalControlledActionInput : NoIndicationActionInputBase { void ExternalControlledActionInput(PlayerBase player) { //SetInput("UAReloadMagazine"); m_InputType = ActionInputType.AIT_NOINPUTCONTROL; } }; class InventoryOnlyActionInput : NoIndicationActionInputBase { void InventoryOnlyActionInput(PlayerBase player) { //SetInput("UAReloadMagazine"); m_InputType = ActionInputType.AIT_INVENTORYINPUT; } }; class QuickaBarActionInput : ExternalControlledActionInput { };