/// <summary> /// Function called when this object is hit by a player's tool. /// </summary> /// <param name="toolTransform">Position of the player that hit this object.</param> /// <param name="toolType">Type of tool equipped.</param> /// <param name="toolMode">Mode (primary or secondary) of tool equipped.</param> public override void HitByTool(PlayerServer player, Transform toolTransform, ToolType toolType, ToolMode toolMode) { // Call the base's HitByTool function (burns the object) base.HitByTool(player, toolTransform, toolType, toolMode); // Get information about the tool that was used on this object. ToolInfo toolInfo = Tool.GetToolInfo(toolType); // If this is a leafblower. if (toolType == ToolType.BLOWER) { // If this is the leafblower's primary tool. if (toolMode == ToolMode.PRIMARY) { // Get the force of this tool. float toolForce = toolInfo.Force; // Get the vector from the player to the object. Vector3 playerToObj = Transform.Position - toolTransform.Position; playerToObj.Y = 0.0f; float distance = playerToObj.Length(); // Divide the vector by the range of the tool to normalize it. playerToObj /= toolInfo.Range; // Multiply tool force by distance so that it's stronger on objects that are closer. // Also make sure denominator can't be zero. toolForce /= Math.Max(0.001f, distance * Constants.BLOWER_DISTANCE_SCALER); // Apply a force in the direction of the player -> object. Vector3 force = playerToObj * toolForce; ApplyForce(force); // Console.WriteLine("Blowing object {0} {1} with force {2}", this.GetType().ToString(), Id, force); } else if (toolMode == ToolMode.SECONDARY) { // Get the force of this tool. float toolForce = toolInfo.Force * 0.25f; float toolRange = toolInfo.Range * 0.5f; // Get the vector from the player to the object. Vector3 objToPlayer = toolTransform.Position - Transform.Position; objToPlayer.Y = 0.0f; float distance = objToPlayer.Length(); // Divide the vector by the range of the tool to normalize it. objToPlayer /= toolRange; // Multiply tool force by distance so that it's stronger on objects that are closer. // Also make sure denominator can't be zero. toolForce /= Math.Max(0.001f, distance * Constants.BLOWER_DISTANCE_SCALER); // Apply a force in the direction of the player -> object. Vector3 force = objToPlayer * toolForce; ApplyForce(force); } } }
/// <summary> /// Function called when this object is hit by the player's active tool (in range) /// </summary> /// <param name="toolTransform">Position of the player. </param> /// <param name="toolType">Type of the tool hit by.</param> /// <param name="toolMode">Mode (primary or secondary) the tool was in.</param> public virtual void HitByTool(PlayerServer player, Transform toolTransform, ToolType toolType, ToolMode toolMode) { // Get information about the tool that was used on this object. ToolInfo toolInfo = Tool.GetToolInfo(toolType); LastPlayerInteracted = player; if (toolType == ToolType.THROWER) { // If it's the primary flamethrower function if (toolMode == ToolMode.PRIMARY) { CatchFire(); PlayerThatSetThisOnFire = player; if (burnFrames == 0) { if (this is LeafServer) { player.playerStats.numLeavesSetOnFire++; } else if (this is PlayerServer me) { if (me.Team == player.Team) { player.playerStats.numTeammateSetOnFire++; } else { player.playerStats.numEnemiesSetOnFire++; } } } } } if (toolType == ToolType.BLOWER) { // If this is the primary function of the blower. if (toolMode == ToolMode.PRIMARY && Burning) { blowFrames++; } else { blowFrames = 0; } } else { blowFrames = 0; } }
/// <summary> /// Update step for this game object. Runs every tick. /// </summary> /// <param name="deltaTime">Time since last frame.</param> public override void Update(float deltaTime) { CheckIfChangedSection(); // If this object is burning. if (Burning || FlamethrowerActivelyBurning) { //The object took damage, it's been modified. Modified = true; // If it is being actively burned this frame. if (FlamethrowerActivelyBurning) { // Increase the frames this object is burning. burnFrames++; // No longer burning next frame FlamethrowerActivelyBurning = false; } // If not actively being burned this frame, drop burn frames by 1, capping at one. else { // Subtract by 1 or set to 1 if at 1 already. burnFrames = Math.Max(1, burnFrames - 1); } // If we've been blowing on the object for the desired period of time, extinguish it. if (blowFrames * deltaTime > SECONDS_TO_EXTINGUISH) { // Stop the object from burning. Extinguish(); // If there was a player that interacted with this object. if (LastPlayerInteracted != null) { // If this is a leaf. if (this is LeafServer) { // Increment the number of leaves that were extinguished. LastPlayerInteracted.playerStats.numLeavesExtinguished++; } // If this is a Player. else if (this is PlayerServer me && me.Team == LastPlayerInteracted.Team) { // Increment number of teammates that were extinguished. LastPlayerInteracted.playerStats.timesTeammateExtinguished++; } } } // Get fire damage from the flamethrower. float fireDamage = Tool.GetToolInfo(ToolType.THROWER).Damage; float totalDamageToDeal = fireDamage * deltaTime * Math.Min(burnFrames * BURNING_RAMP_RATE, 10); // Decrease health by burn damage. Health -= totalDamageToDeal; // If there is a player that set this object on fire. if (PlayerThatSetThisOnFire != null) { // If this is a leaf. if (this is LeafServer) { // Increase player's damage to leaves. PlayerThatSetThisOnFire.playerStats.fireDamageDealtToLeaves += totalDamageToDeal; } // If this is a player. else if (this is PlayerServer me) { // Increase damage to enemy players. if (me.Team != PlayerThatSetThisOnFire.Team) { PlayerThatSetThisOnFire.playerStats.fireDamageDealtToEnemies += totalDamageToDeal; } // Increase damage to team players. else { PlayerThatSetThisOnFire.playerStats.fireDamageDealtToTeammates += totalDamageToDeal; } // Increment damage taken. me.playerStats.damageTaken += totalDamageToDeal; } } // If health goes negative, destroy the object. if (Health <= 0) { // Destroy. Die(); } if (ExtinguishTimer.ElapsedMilliseconds / 1000.0f >= Constants.MAX_SECONDS_BURNING) { Extinguish(); } } }