public bool Interact(PositionalHandApply interaction) { if (DefaultWillInteract.Default(interaction, NetworkSide.Client) == false) { return(false); } //**Client** if (Validations.HasComponent <Dissectible>(interaction.TargetObject) == false) { return(false); } var RegisterPlayer = interaction.TargetObject.GetComponent <RegisterPlayer>(); if (RegisterPlayer == null) { return(false); //Player script changes needed } if (RegisterPlayer.IsLayingDown == false) { return(false); } if (ProcedureInProgress == false) { if (KeyboardInputManager.Instance.CheckKeyAction(KeyAction.InteractionModifier, KeyboardInputManager.KeyEventType.Hold) == false) { return(false); } if (Validations.HasAnyTrait(interaction.HandObject, InitiateSurgeryItemTraits) == false) { return(false); } } else { if (Validations.HasAnyTrait(interaction.HandObject, InitiateSurgeryItemTraits) == false) { return(false); } } if (ProcedureInProgress == false) //Defer to server { if (BodyPartIsOn != null) //Body part not picked? { if (BodyPartIsopen) { // var Options = currentlyOn.ContainBodyParts; // UIManager.Instance.SurgeryDialogue.ShowDialogue(this, Options); RequestBodyParts.Send(this.gameObject); return(true); //Show dialogue for Pick organ and Procedure set it } else { // var Options = currentlyOn; // UIManager.Instance.SurgeryDialogue.ShowDialogue(this, Options); RequestBodyParts.Send(this.gameObject); return(true); //Show dialogue for possible surgeries } } else { // var Options = LivingHealthMasterBase.GetBodyPartsInZone(interaction.TargetBodyPart); // UIManager.Instance.SurgeryDialogue.ShowDialogue(this, Options, true); RequestBodyParts.Send(this.gameObject, interaction.TargetBodyPart); return(true); //showDialogue box, For which body part // Set currently on and choose what surgery } } else { return(false); //? //Pass over to Body part being operated on } }
public bool WillInteract(ContextMenuApply interaction, NetworkSide side) { return(DefaultWillInteract.Default(interaction, side) && noteText.IsNullOrEmpty() == false); }
public bool WillInteract(InventoryApply interaction, NetworkSide side) { return(DefaultWillInteract.Default(interaction, side) && CommonWillInteract(interaction)); }
public bool WillInteract(ContextMenuApply interaction, NetworkSide side) { return(DefaultWillInteract.Default(interaction, side)); }
public bool WillInteract(HandApply interaction, NetworkSide side) { return(DefaultWillInteract.Default(interaction, side) && (interaction.HandObject == null || (interaction.Intent == Intent.Help || interaction.Intent == Intent.Grab))); }
/// <summary> /// Client: /// Allow items to be stored by clicking on bags with item in hand /// and clicking items with bag in hand if CanClickPickup is enabled /// </summary> public bool WillInteract(PositionalHandApply interaction, NetworkSide side) { if (!allowedToInteract) { return(false); } // Use default interaction checks if (!DefaultWillInteract.Default(interaction, side)) { return(false); } // See which item needs to be stored if (Validations.IsTarget(gameObject, interaction)) { // We're the target // If player's hands are empty let Pickupable handle the interaction if (interaction.HandObject == null) { return(false); } // There's something in the player's hands // Check if item from the hand slot fits in this storage sitting in the world if (!Validations.CanPutItemToStorage(interaction.PerformerPlayerScript, itemStorage, interaction.HandObject, side, examineRecipient: interaction.Performer)) { Chat.AddExamineMsgToClient($"The {interaction.HandObject.ExpensiveName()} doesn't fit!"); return(false); } return(true); } else if (canClickPickup) { // If we can click pickup then try to store the target object switch (pickupMode) { case PickupMode.Single: // See if there's an item to pickup if (interaction.TargetObject == null || interaction.TargetObject.Item() == null) { Chat.AddExamineMsgToClient("There's nothing to pickup!"); return(false); } if (!Validations.CanPutItemToStorage(interaction.PerformerPlayerScript, itemStorage, interaction.TargetObject, side, examineRecipient: interaction.Performer)) { // In Single pickup mode if the target item doesn't // fit then don't interact Chat.AddExamineMsgToClient($"The {interaction.TargetObject.ExpensiveName()} doesn't fit!"); return(false); } break; case PickupMode.Same: if (interaction.TargetObject == null) { // If there's nothing to compare then don't interact Chat.AddExamineMsgToClient("There's nothing to pickup!"); return(false); } break; } // In Same and All pickup modes other items on the // tile could still be picked up, so we interact return(true); } else { // We're not the target and we can't click pickup so don't do anything return(false); } }
/// <summary> /// Checks to make sure the player is conscious and stuff /// </summary> public bool WillInteract(HandActivate interaction, NetworkSide side) { return DefaultWillInteract.Default(interaction, side); }
private static bool CheckInteractInternal <T>(this IBaseInteractable <T> interactable, T interaction, NetworkSide side, out bool wasClientInteractable) where T : Interaction { wasClientInteractable = false; //interactions targeting an object at hiddenpos are NEVER allowed (except for inventory actions, //since they can target an object in inventory which means its at hiddenpos) if (!(interaction is InventoryApply) && interaction is TargetedInteraction targetedInteraction && !(interaction is ContextMenuApply)) { if (targetedInteraction.TargetObject != null && targetedInteraction.TargetObject.IsAtHiddenPos()) { Logger.LogTraceFormat("Aborting {0} interaction on object {1} because the object is hidden.", Category.Interaction, typeof(T).Name, targetedInteraction.TargetObject.name); return(false); } } if (Cooldowns.IsOn(interaction, CooldownID.Asset(CommonCooldowns.Instance.Interaction, side))) { return(false); } var result = false; //check if client side interaction should be triggered if (side == NetworkSide.Client && interactable is IClientInteractable <T> clientInteractable) { result = clientInteractable.Interact(interaction); if (result) { Logger.LogTraceFormat("ClientInteractable triggered from {0} on {1} for object {2}", Category.Interaction, typeof(T).Name, clientInteractable.GetType().Name, (clientInteractable as Component).gameObject.name); Cooldowns.TryStartClient(interaction, CommonCooldowns.Instance.Interaction); wasClientInteractable = true; return(true); } } //check other kinds of interactions if (interactable is ICheckable <T> checkable) { result = checkable.WillInteract(interaction, side); if (result) { Logger.LogTraceFormat("WillInteract triggered from {0} on {1} for object {2}", Category.Interaction, typeof(T).Name, checkable.GetType().Name, (checkable as Component).gameObject.name); wasClientInteractable = false; return(true); } } else if (interactable is IInteractable <T> ) { //use default logic result = DefaultWillInteract.Default(interaction, side); if (result) { Logger.LogTraceFormat("WillInteract triggered from {0} on {1} for object {2}", Category.Interaction, typeof(T).Name, interactable.GetType().Name, (interactable as Component).gameObject.name); wasClientInteractable = false; return(true); } } Logger.LogTraceFormat("No interaction triggered from {0} on {1} for object {2}", Category.Interaction, typeof(T).Name, interactable.GetType().Name, (interactable as Component).gameObject.name); wasClientInteractable = false; return(false); }
public bool WillInteract(InventoryApply interaction, NetworkSide side) { return(DefaultWillInteract.Default(interaction, side) && interaction.UsedObject == null && interaction.Intent == Intent.Harm); }
public virtual bool WillInteract(TileApply interaction, NetworkSide side) { return(DefaultWillInteract.Default(interaction, side)); }
public bool WillInteract(AimApply interaction, NetworkSide side) { if (!DefaultWillInteract.Default(interaction, side)) { return(false); } if (CurrentMagazine == null) { PlayEmptySFX(); if (interaction.Performer != PlayerManager.LocalPlayer) { Logger.LogTrace("Server rejected shot - No magazine being loaded", Category.Firearms); } return(false); } //note: fire count down is only checked local player side, as server processes all the shots in a queue //anyway so client cannot exceed that firing rate no matter what. If we validate firing rate server //side at the moment of interaction, it will reject client's shots because of lag between server / client //firing countdown if (Projectile != null && CurrentMagazine.ClientAmmoRemains <= 0 && (interaction.Performer != PlayerManager.LocalPlayer || FireCountDown <= 0)) { if (SmartGun && allowMagazineRemoval) // smartGun is forced off when using an internal magazine { RequestUnload(CurrentMagazine); OutOfAmmoSFX(); } else { PlayEmptySFX(); } if (interaction.Performer != PlayerManager.LocalPlayer) { Logger.LogTrace("Server rejected shot - out of ammo", Category.Firearms); } return(false); } if (Projectile != null && CurrentMagazine.ClientAmmoRemains > 0 && (interaction.Performer != PlayerManager.LocalPlayer || FireCountDown <= 0)) { if (WeaponType == WeaponType.Burst) { //being held and is a burst weapon, check how many shots have been fired our the current burst if (currentBurstCount < burstCount) { //we have shot less then the max allowed shots in our current burst, increase and fire again currentBurstCount++; return(true); } else if (currentBurstCount >= burstCount) { //we have shot the max allowed shots in our current burst, start cooldown and then fire the first shot WaitFor.Seconds((float)burstCooldown); currentBurstCount = 1; return(true); } } else if (interaction.MouseButtonState == MouseButtonState.PRESS) { if (currentBurstCount != 0) { currentBurstCount = 0; } return(true); } else { //being held, only can shoot if this is an automatic return(WeaponType == WeaponType.FullyAutomatic); } } if (interaction.Performer != PlayerManager.LocalPlayer) { Logger.LogTraceFormat("Server rejected shot - unknown reason. MouseButtonState {0} ammo remains {1} weapon type {2}", Category.Firearms, interaction.MouseButtonState, CurrentMagazine.ClientAmmoRemains, WeaponType); } return(false); }
public bool WillInteract(HandApply interaction, NetworkSide side) { if (!DefaultWillInteract.Default(interaction, side)) { return(false); } if (!Validations.IsTarget(gameObject, interaction)) { return(false); } //Anchor or disassemble if (CurrentState == initialState) { return(Validations.HasUsedItemTrait(interaction, CommonTraits.Instance.Wrench) || Validations.HasUsedActiveWelder(interaction)); } //Adding Circuit board or unanchor if (CurrentState == anchoredState) { return(Validations.HasUsedItemTrait(interaction, aiCoreCircuitBoardTrait) || Validations.HasUsedItemTrait(interaction, CommonTraits.Instance.Wrench)); } //Screwdriver or remove Circuit board if (CurrentState == circuitAddedState) { return(Validations.HasUsedItemTrait(interaction, CommonTraits.Instance.Screwdriver) || interaction.HandObject == null); } //Add wire or unscrew if (CurrentState == screwState) { return(Validations.HasUsedItemTrait(interaction, CommonTraits.Instance.Cable) || Validations.HasUsedItemTrait(interaction, CommonTraits.Instance.Screwdriver)); } //Add brain, or skip brain and add reinforced glass or remove wire if (CurrentState == wireAddedState) { //TODO enable brain stuff return //Validations.HasUsedItemTrait(interaction, CommonTraits.Instance.MMI / or Positron) || (Validations.HasUsedItemTrait(interaction, CommonTraits.Instance.ReinforcedGlassSheet) || Validations.HasUsedItemTrait(interaction, CommonTraits.Instance.Wirecutter)); } //Add reinforced glass or remove brain if (CurrentState == brainAddedState) { return(Validations.HasUsedItemTrait(interaction, CommonTraits.Instance.ReinforcedGlassSheet) || Validations.HasUsedItemTrait(interaction, CommonTraits.Instance.Crowbar)); } //Screw to finish or remove glass if (CurrentState == glassState) { return(Validations.HasUsedItemTrait(interaction, CommonTraits.Instance.Screwdriver) || Validations.HasUsedItemTrait(interaction, CommonTraits.Instance.Crowbar)); } return(false); }
public bool WillInteract(HandApply interaction, NetworkSide side) { if (!DefaultWillInteract.Default(interaction, side)) { return(false); } if (!Validations.IsTarget(gameObject, interaction)) { return(false); } //Anchor or disassemble if (CurrentState == initialState) { return(Validations.HasUsedItemTrait(interaction, CommonTraits.Instance.Wrench) || Validations.HasUsedItemTrait(interaction, CommonTraits.Instance.Crowbar)); } //Adding metal or unanchor if (CurrentState == anchoredState) { return(Validations.HasUsedItemTrait(interaction, CommonTraits.Instance.MetalSheet) || Validations.HasUsedItemTrait(interaction, CommonTraits.Instance.Wrench)); } //Wrench or remove metal if (CurrentState == metalAddedState) { return(Validations.HasUsedItemTrait(interaction, CommonTraits.Instance.Wrench) || Validations.HasUsedActiveWelder(interaction)); } //Add gun or unwrench if (CurrentState == wrenchState) { return(Validations.HasUsedItemTrait(interaction, gunTrait) || Validations.HasUsedItemTrait(interaction, CommonTraits.Instance.Wrench)); } //Add prox or remove gun if (CurrentState == gunAddedState) { return(Validations.HasUsedItemTrait(interaction, CommonTraits.Instance.ProximitySensor) || interaction.HandObject == null); } //Screw or remove prox if (CurrentState == proxAddedState) { return(Validations.HasUsedItemTrait(interaction, CommonTraits.Instance.Screwdriver) || interaction.HandObject == null); } //Add metal or unscrew if (CurrentState == screwState) { return(Validations.HasUsedItemTrait(interaction, CommonTraits.Instance.MetalSheet) || Validations.HasUsedItemTrait(interaction, CommonTraits.Instance.Screwdriver)); } //Finish construction or remove metal if (CurrentState == secondMetalAddedState) { return(Validations.HasUsedActiveWelder(interaction) || Validations.HasUsedItemTrait(interaction, CommonTraits.Instance.Crowbar)); } return(false); }
public bool WillInteract(HandApply interaction, NetworkSide side) { return(DefaultWillInteract.Default(interaction, side) && Validations.HasComponent <IDCard>(interaction.HandObject)); }
public virtual bool WillInteract(AimApply interaction, NetworkSide side) { if (!DefaultWillInteract.Default(interaction, side)) { return(false); } if (CurrentMagazine == null) { PlayEmptySFX(); if (side == NetworkSide.Server) { Logger.LogTrace("Server rejected shot - No magazine being loaded", Category.Firearms); } return(false); } //note: fire count down is only checked local player side, as server processes all the shots in a queue //anyway so client cannot exceed that firing rate no matter what. If we validate firing rate server //side at the moment of interaction, it will reject client's shots because of lag between server / client //firing countdown if (side == NetworkSide.Server || FireCountDown <= 0) { if (CurrentMagazine.ClientAmmoRemains <= 0) { if (SmartGun && allowMagazineRemoval) // smartGun is forced off when using an internal magazine { RequestUnload(CurrentMagazine); OutOfAmmoSFX(); } else { PlayEmptySFX(); } if (side == NetworkSide.Server) { Logger.LogTrace("Server rejected shot - out of ammo", Category.Firearms); } return(false); } if (CurrentMagazine.containedBullets[0] != null) { if (interaction.MouseButtonState == MouseButtonState.PRESS) { return(true); } else { //being held, only can shoot if this is an automatic return(WeaponType == WeaponType.FullyAutomatic); } } } if (side == NetworkSide.Server) { Logger.LogTraceFormat("Server rejected shot - unknown reason. MouseButtonState {0} ammo remains {1} weapon type {2}", Category.Firearms, interaction.MouseButtonState, CurrentMagazine.ClientAmmoRemains, WeaponType); } return(false); }
// will a player start to craft something? public bool WillInteract(HandApply interaction, NetworkSide side) { if (HasSimpleRelatedRecipe == false || interaction.HandObject == null || DefaultWillInteract.Default(interaction, side) == false ) { return(false); } // we should check related recipes in WillInteract() because otherwise // other interactions will be blocked because of an interaction cooldown List <CraftingIngredient> possibleIngredients = new List <CraftingIngredient>(); possibleIngredients.Add(this); if (interaction.HandObject.TryGetComponent(out CraftingIngredient otherPossibleIngredient)) { possibleIngredients.Add(otherPossibleIngredient); } List <ItemAttributesV2> possibleTools = new List <ItemAttributesV2>(); if (TryGetComponent(out ItemAttributesV2 selfPossibleTool)) { possibleTools.Add(selfPossibleTool); } if (interaction.HandObject.TryGetComponent(out ItemAttributesV2 otherPossibleTool)) { possibleTools.Add(otherPossibleTool); } foreach (RelatedRecipe relatedRecipe in relatedRecipes) { if (relatedRecipe.Recipe.IsSimple == false) { continue; } if (side == NetworkSide.Client) { if (interaction.PerformerPlayerScript.PlayerCrafting.CanClientCraft( relatedRecipe.Recipe, possibleIngredients, possibleTools ) == CraftingStatus.AllGood ) { return(true); } } else if (side == NetworkSide.Server) { if (interaction.PerformerPlayerScript.PlayerCrafting.CanCraft( relatedRecipe.Recipe, possibleIngredients, possibleTools, new List <ReagentContainer>() ) == CraftingStatus.AllGood ) { return(true); } } } return(false); }
public virtual bool WillInteract(HandActivate interaction, NetworkSide side) { return(DefaultWillInteract.Default(interaction, side)); }
/// <summary> /// Decides if interaction logic should proceed. On client side, the interaction /// request will only be sent to the server if this returns true. On server side, /// the interaction will only be performed if this returns true. /// /// Each interaction has a default implementation of this which should apply for most cases. /// By overriding this and adding more specific logic, you can reduce the amount of messages /// sent by the client to the server, decreasing overall network load. /// </summary> /// <param name="interaction">interaction to validate</param> /// <param name="side">which side of the network this is being invoked on</param> /// <returns>True/False based on whether the interaction logic should proceed as described above.</returns> protected virtual bool WillInteract(T interaction, NetworkSide side) { return(DefaultWillInteract.Default(interaction, side)); }
/// <summary> /// Decides if interaction logic should proceed. On client side, the interaction /// request will only be sent to the server if this returns true. On server side, /// the interaction will only be performed if this returns true. /// /// Each interaction has a default implementation of this which should apply for most cases. /// By overriding this and adding more specific logic, you can reduce the amount of messages /// sent by the client to the server, decreasing overall network load. /// </summary> /// <param name="interaction">interaction to validate</param> /// <param name="side">which side of the network this is being invoked on</param> /// <returns>True/False based on whether the interaction logic should proceed as described above.</returns> protected virtual bool WillInteract(PositionalHandApply interaction, NetworkSide side) { return(DefaultWillInteract.Default(interaction, side)); }
public bool WillInteract(PositionalHandApply interaction, NetworkSide side) { return(DefaultWillInteract.Default(interaction, side)); }