summaryrefslogtreecommitdiff
path: root/GameCode/Gun.cs
diff options
context:
space:
mode:
authorchai <215380520@qq.com>2023-10-27 11:05:14 +0800
committerchai <215380520@qq.com>2023-10-27 11:05:14 +0800
commit766cdff5ffa72b65d7f106658d1603f47739b2ba (patch)
tree34d7799a94dfa9be182825577583c0fa6dc935f7 /GameCode/Gun.cs
+ init
Diffstat (limited to 'GameCode/Gun.cs')
-rw-r--r--GameCode/Gun.cs698
1 files changed, 698 insertions, 0 deletions
diff --git a/GameCode/Gun.cs b/GameCode/Gun.cs
new file mode 100644
index 0000000..36e8df2
--- /dev/null
+++ b/GameCode/Gun.cs
@@ -0,0 +1,698 @@
+using System;
+using System.Collections;
+using System.Collections.Generic;
+using Photon.Pun;
+using Sirenix.OdinInspector;
+using SoundImplementation;
+using UnityEngine;
+
+public class Gun : Weapon
+{
+ [Header("Sound Player Settings")]
+ public SoundGun soundGun = new SoundGun();
+
+ [Header("Sound Card Settings")]
+ public SoundShotModifier soundShotModifier;
+
+ public SoundImpactModifier soundImpactModifier;
+
+ public bool soundDisableRayHitBulletSound;
+
+ [Header("Settings")]
+ public float recoil;
+
+ public float bodyRecoil;
+
+ public float shake;
+
+ public bool forceSpecificShake;
+
+ public ProjectilesToSpawn[] projectiles;
+
+ private Rigidbody2D rig;
+
+ public Transform shootPosition;
+
+ [HideInInspector]
+ public Player player;
+
+ [HideInInspector]
+ public bool isReloading;
+
+ [Header("Multiply")]
+ [FoldoutGroup("Stats", 0)]
+ public float damage = 1f;
+
+ [FoldoutGroup("Stats", 0)]
+ public float reloadTime = 1f;
+
+ [FoldoutGroup("Stats", 0)]
+ public float reloadTimeAdd;
+
+ [FoldoutGroup("Stats", 0)]
+ public float recoilMuiltiplier = 1f;
+
+ [FoldoutGroup("Stats", 0)]
+ public float knockback = 1f;
+
+ [FoldoutGroup("Stats", 0)]
+ public float attackSpeed = 1f;
+
+ [FoldoutGroup("Stats", 0)]
+ public float projectileSpeed = 1f;
+
+ [FoldoutGroup("Stats", 0)]
+ public float projectielSimulatonSpeed = 1f;
+
+ [FoldoutGroup("Stats", 0)]
+ public float gravity = 1f;
+
+ [FoldoutGroup("Stats", 0)]
+ public float damageAfterDistanceMultiplier = 1f;
+
+ [FoldoutGroup("Stats", 0)]
+ public float bulletDamageMultiplier = 1f;
+
+ [FoldoutGroup("Stats", 0)]
+ public float multiplySpread = 1f;
+
+ [FoldoutGroup("Stats", 0)]
+ public float shakeM = 1f;
+
+ [Header("Add")]
+ [FoldoutGroup("Stats", 0)]
+ public int ammo;
+
+ [FoldoutGroup("Stats", 0)]
+ public float ammoReg;
+
+ [FoldoutGroup("Stats", 0)]
+ public float size;
+
+ [FoldoutGroup("Stats", 0)]
+ public float overheatMultiplier;
+
+ [FoldoutGroup("Stats", 0)]
+ public float timeToReachFullMovementMultiplier;
+
+ [FoldoutGroup("Stats", 0)]
+ public int numberOfProjectiles;
+
+ [FoldoutGroup("Stats", 0)]
+ public int bursts;
+
+ [FoldoutGroup("Stats", 0)]
+ public int reflects;
+
+ [FoldoutGroup("Stats", 0)]
+ public int smartBounce;
+
+ [FoldoutGroup("Stats", 0)]
+ public int bulletPortal;
+
+ [FoldoutGroup("Stats", 0)]
+ public int randomBounces;
+
+ [FoldoutGroup("Stats", 0)]
+ public float timeBetweenBullets;
+
+ [FoldoutGroup("Stats", 0)]
+ public float projectileSize;
+
+ [FoldoutGroup("Stats", 0)]
+ public float speedMOnBounce = 1f;
+
+ [FoldoutGroup("Stats", 0)]
+ public float dmgMOnBounce = 1f;
+
+ [FoldoutGroup("Stats", 0)]
+ public float drag;
+
+ [FoldoutGroup("Stats", 0)]
+ public float dragMinSpeed = 1f;
+
+ [FoldoutGroup("Stats", 0)]
+ public float spread;
+
+ [FoldoutGroup("Stats", 0)]
+ public float evenSpread;
+
+ [FoldoutGroup("Stats", 0)]
+ public float percentageDamage;
+
+ [FoldoutGroup("Stats", 0)]
+ public float cos;
+
+ [FoldoutGroup("Stats", 0)]
+ public float slow;
+
+ [FoldoutGroup("Stats", 0)]
+ [Header("Charge Multiply")]
+ public float chargeDamageMultiplier = 1f;
+
+ [FoldoutGroup("Stats", 0)]
+ [Header("(1 + Charge * x) Multiply")]
+ public float chargeSpreadTo;
+
+ [FoldoutGroup("Stats", 0)]
+ public float chargeEvenSpreadTo;
+
+ [FoldoutGroup("Stats", 0)]
+ public float chargeSpeedTo;
+
+ [FoldoutGroup("Stats", 0)]
+ public float chargeRecoilTo;
+
+ [FoldoutGroup("Stats", 0)]
+ [Header("(1 + Charge * x) Add")]
+ public float chargeNumberOfProjectilesTo;
+
+ [FoldoutGroup("Stats", 0)]
+ [Header("Special")]
+ public float destroyBulletAfter;
+
+ [FoldoutGroup("Stats", 0)]
+ public float forceSpecificAttackSpeed;
+
+ [FoldoutGroup("Stats", 0)]
+ public bool lockGunToDefault;
+
+ [FoldoutGroup("Stats", 0)]
+ public bool unblockable;
+
+ [FoldoutGroup("Stats", 0)]
+ public bool ignoreWalls;
+
+ [HideInInspector]
+ public float currentCharge;
+
+ public bool useCharge;
+
+ public bool dontAllowAutoFire;
+
+ public ObjectsToSpawn[] objectsToSpawn;
+
+ public Color projectileColor = Color.black;
+
+ public bool waveMovement;
+
+ public bool teleport;
+
+ public bool spawnSkelletonSquare;
+
+ public float explodeNearEnemyRange;
+
+ public float explodeNearEnemyDamage;
+
+ public float hitMovementMultiplier = 1f;
+
+ private Action attackAction;
+
+ [HideInInspector]
+ public bool isProjectileGun;
+
+ [HideInInspector]
+ public float defaultCooldown = 1f;
+
+ [HideInInspector]
+ public int attackID = -1;
+
+ public float attackSpeedMultiplier = 1f;
+
+ private int gunID = -1;
+
+ private GunAmmo gunAmmo;
+
+ private Vector3 spawnPos;
+
+ public Action<GameObject> ShootPojectileAction;
+
+ private float spreadOfLastBullet;
+
+ private SpawnedAttack spawnedAttack;
+
+ [HideInInspector]
+ internal Vector3 forceShootDir;
+
+ private float usedCooldown
+ {
+ get
+ {
+ if (!lockGunToDefault)
+ {
+ return attackSpeed;
+ }
+ return defaultCooldown;
+ }
+ }
+
+ internal float GetRangeCompensation(float distance)
+ {
+ return Mathf.Pow(distance, 2f) * 0.015f / projectileSpeed;
+ }
+
+ internal void ResetStats()
+ {
+ isReloading = false;
+ damage = 1f;
+ reloadTime = 1f;
+ reloadTimeAdd = 0f;
+ recoilMuiltiplier = 1f;
+ gunAmmo.reloadTimeMultiplier = 1f;
+ gunAmmo.reloadTimeAdd = 0f;
+ knockback = 1f;
+ attackSpeed = 0.3f;
+ projectileSpeed = 1f;
+ projectielSimulatonSpeed = 1f;
+ gravity = 1f;
+ damageAfterDistanceMultiplier = 1f;
+ bulletDamageMultiplier = 1f;
+ multiplySpread = 1f;
+ shakeM = 1f;
+ ammo = 0;
+ ammoReg = 0f;
+ size = 0f;
+ overheatMultiplier = 0f;
+ timeToReachFullMovementMultiplier = 0f;
+ numberOfProjectiles = 1;
+ bursts = 0;
+ reflects = 0;
+ smartBounce = 0;
+ bulletPortal = 0;
+ randomBounces = 0;
+ timeBetweenBullets = 0f;
+ projectileSize = 0f;
+ speedMOnBounce = 1f;
+ dmgMOnBounce = 1f;
+ drag = 0f;
+ dragMinSpeed = 1f;
+ spread = 0f;
+ evenSpread = 0f;
+ percentageDamage = 0f;
+ cos = 0f;
+ slow = 0f;
+ chargeNumberOfProjectilesTo = 0f;
+ destroyBulletAfter = 0f;
+ forceSpecificAttackSpeed = 0f;
+ lockGunToDefault = false;
+ unblockable = false;
+ ignoreWalls = false;
+ currentCharge = 0f;
+ useCharge = false;
+ waveMovement = false;
+ teleport = false;
+ spawnSkelletonSquare = false;
+ explodeNearEnemyRange = 0f;
+ explodeNearEnemyDamage = 0f;
+ hitMovementMultiplier = 1f;
+ isProjectileGun = false;
+ defaultCooldown = 1f;
+ attackSpeedMultiplier = 1f;
+ objectsToSpawn = new ObjectsToSpawn[0];
+ GetComponentInChildren<GunAmmo>().maxAmmo = 3;
+ GetComponentInChildren<GunAmmo>().ReDrawTotalBullets();
+ projectileColor = Color.black;
+ }
+
+ private void Start()
+ {
+ gunAmmo = GetComponentInChildren<GunAmmo>();
+ Gun[] componentsInChildren = base.transform.root.GetComponentsInChildren<Gun>();
+ for (int i = 0; i < componentsInChildren.Length; i++)
+ {
+ if (componentsInChildren[i] == this)
+ {
+ gunID = i;
+ }
+ }
+ if (!player)
+ {
+ player = GetComponentInParent<Player>();
+ }
+ if (!player)
+ {
+ ProjectileHit componentInParent = GetComponentInParent<ProjectileHit>();
+ if ((bool)componentInParent)
+ {
+ player = componentInParent.ownPlayer;
+ }
+ }
+ if (!player)
+ {
+ SpawnedAttack component = base.transform.root.GetComponent<SpawnedAttack>();
+ if ((bool)component)
+ {
+ player = component.spawner;
+ }
+ }
+ holdable = GetComponent<Holdable>();
+ defaultCooldown = usedCooldown;
+ ShootPos componentInChildren = GetComponentInChildren<ShootPos>();
+ if ((bool)componentInChildren)
+ {
+ shootPosition = componentInChildren.transform;
+ }
+ else
+ {
+ shootPosition = base.transform;
+ }
+ rig = GetComponent<Rigidbody2D>();
+ soundGun.SetGun(this);
+ soundGun.SetGunTransform(base.transform);
+ soundGun.RefreshSoundModifiers();
+ }
+
+ private void Update()
+ {
+ if ((bool)holdable && (bool)holdable.holder && (bool)holdable.holder.player)
+ {
+ player = holdable.holder.player;
+ }
+ sinceAttack += TimeHandler.deltaTime * attackSpeedMultiplier;
+ if (!GameManager.instance.battleOngoing || (player != null && (!player.data.isPlaying || player.data.dead)))
+ {
+ soundGun.StopAutoPlayTail();
+ }
+ }
+
+ private void OnDestroy()
+ {
+ soundGun.StopAutoPlayTail();
+ }
+
+ public bool IsReady(float readuIn = 0f)
+ {
+ return sinceAttack + readuIn * attackSpeedMultiplier > usedCooldown;
+ }
+
+ public float ReadyAmount()
+ {
+ return sinceAttack / usedCooldown;
+ }
+
+ public override bool Attack(float charge, bool forceAttack = false, float damageM = 1f, float recoilM = 1f, bool useAmmo = true)
+ {
+ if (sinceAttack < usedCooldown && !forceAttack)
+ {
+ return false;
+ }
+ if (isReloading && !forceAttack)
+ {
+ return false;
+ }
+ sinceAttack = 0f;
+ int attacks = Mathf.Clamp(Mathf.RoundToInt(0.5f * charge / attackSpeed), 1, 10);
+ if (lockGunToDefault)
+ {
+ attacks = 1;
+ }
+ StartCoroutine(DoAttacks(charge, forceAttack, damageM, attacks, recoilM, useAmmo));
+ return true;
+ }
+
+ private IEnumerator DoAttacks(float charge, bool forceAttack = false, float damageM = 1f, int attacks = 1, float recoilM = 1f, bool useAmmo = true)
+ {
+ for (int i = 0; i < attacks; i++)
+ {
+ DoAttack(charge, forceAttack, damageM, recoilM, useAmmo);
+ yield return new WaitForSeconds(0.3f / (float)attacks);
+ }
+ }
+
+ private void DoAttack(float charge, bool forceAttack = false, float damageM = 1f, float recoilM = 1f, bool useAmmo = true)
+ {
+ float num = 1f * (1f + charge * chargeRecoilTo) * recoilM;
+ if ((bool)rig)
+ {
+ rig.AddForce(rig.mass * recoil * Mathf.Clamp(usedCooldown, 0f, 1f) * -base.transform.up, ForceMode2D.Impulse);
+ }
+ _ = (bool)holdable;
+ if (attackAction != null)
+ {
+ attackAction();
+ }
+ StartCoroutine(FireBurst(charge, forceAttack, damageM, recoilM, useAmmo));
+ }
+
+ private bool CheckIsMine()
+ {
+ bool result = false;
+ if ((bool)holdable && (bool)holdable.holder)
+ {
+ result = holdable.holder.player.data.view.IsMine;
+ }
+ else
+ {
+ Player componentInParent = GetComponentInParent<Player>();
+ if ((bool)componentInParent)
+ {
+ result = componentInParent.data.view.IsMine;
+ }
+ }
+ return result;
+ }
+
+ private IEnumerator FireBurst(float charge, bool forceAttack = false, float damageM = 1f, float recoilM = 1f, bool useAmmo = true)
+ {
+ int currentNumberOfProjectiles = (lockGunToDefault ? 1 : (numberOfProjectiles + Mathf.RoundToInt(chargeNumberOfProjectilesTo * charge)));
+ if (!lockGunToDefault)
+ {
+ _ = currentNumberOfProjectiles;
+ }
+ if (timeBetweenBullets == 0f)
+ {
+ GamefeelManager.GameFeel(base.transform.up * shake);
+ soundGun.PlayShot(currentNumberOfProjectiles);
+ }
+ for (int ii = 0; ii < Mathf.Clamp(bursts, 1, 100); ii++)
+ {
+ for (int i = 0; i < projectiles.Length; i++)
+ {
+ for (int j = 0; j < currentNumberOfProjectiles; j++)
+ {
+ if (CheckIsMine())
+ {
+ spawnPos = base.transform.position;
+ if ((bool)player)
+ {
+ player.GetComponent<PlayerAudioModifyers>().SetStacks();
+ if ((bool)holdable)
+ {
+ spawnPos = player.transform.position;
+ }
+ }
+ GameObject gameObject = PhotonNetwork.Instantiate(projectiles[i].objectToSpawn.gameObject.name, spawnPos, getShootRotation(j, currentNumberOfProjectiles, charge), 0);
+ if ((bool)holdable)
+ {
+ if (useAmmo)
+ {
+ if (PhotonNetwork.OfflineMode)
+ {
+ gameObject.GetComponent<ProjectileInit>().OFFLINE_Init(holdable.holder.player.playerID, currentNumberOfProjectiles, damageM, UnityEngine.Random.Range(0f, 1f));
+ }
+ else
+ {
+ gameObject.GetComponent<PhotonView>().RPC("RPCA_Init", RpcTarget.All, holdable.holder.view.OwnerActorNr, currentNumberOfProjectiles, damageM, UnityEngine.Random.Range(0f, 1f));
+ }
+ }
+ else if (PhotonNetwork.OfflineMode)
+ {
+ gameObject.GetComponent<ProjectileInit>().OFFLINE_Init_noAmmoUse(holdable.holder.player.playerID, currentNumberOfProjectiles, damageM, UnityEngine.Random.Range(0f, 1f));
+ }
+ else
+ {
+ gameObject.GetComponent<PhotonView>().RPC("RPCA_Init_noAmmoUse", RpcTarget.All, holdable.holder.view.OwnerActorNr, currentNumberOfProjectiles, damageM, UnityEngine.Random.Range(0f, 1f));
+ }
+ }
+ else if (PhotonNetwork.OfflineMode)
+ {
+ gameObject.GetComponent<ProjectileInit>().OFFLINE_Init_SeparateGun(GetComponentInParent<Player>().playerID, gunID, currentNumberOfProjectiles, damageM, UnityEngine.Random.Range(0f, 1f));
+ }
+ else
+ {
+ gameObject.GetComponent<PhotonView>().RPC("RPCA_Init_SeparateGun", RpcTarget.All, GetComponentInParent<CharacterData>().view.OwnerActorNr, gunID, currentNumberOfProjectiles, damageM, UnityEngine.Random.Range(0f, 1f));
+ }
+ }
+ if (timeBetweenBullets != 0f)
+ {
+ GamefeelManager.GameFeel(base.transform.up * shake);
+ soundGun.PlayShot(currentNumberOfProjectiles);
+ }
+ }
+ }
+ if (bursts > 1 && ii + 1 == Mathf.Clamp(bursts, 1, 100))
+ {
+ soundGun.StopAutoPlayTail();
+ }
+ if (timeBetweenBullets > 0f)
+ {
+ yield return new WaitForSeconds(timeBetweenBullets);
+ }
+ }
+ }
+
+ public void BulletInit(GameObject bullet, int usedNumberOfProjectiles, float damageM, float randomSeed, bool useAmmo = true)
+ {
+ spawnedAttack = bullet.GetComponent<SpawnedAttack>();
+ if (!spawnedAttack)
+ {
+ spawnedAttack = bullet.AddComponent<SpawnedAttack>();
+ }
+ if (!bullet.GetComponentInChildren<DontChangeMe>())
+ {
+ ApplyProjectileStats(bullet, usedNumberOfProjectiles, damageM, randomSeed);
+ }
+ if (soundDisableRayHitBulletSound)
+ {
+ RayHitBulletSound component = bullet.GetComponent<RayHitBulletSound>();
+ if (component != null)
+ {
+ component.disableImpact = true;
+ }
+ }
+ ApplyPlayerStuff(bullet);
+ if (ShootPojectileAction != null)
+ {
+ ShootPojectileAction(bullet);
+ }
+ if (useAmmo && (bool)gunAmmo)
+ {
+ gunAmmo.Shoot(bullet);
+ }
+ }
+
+ private Quaternion getShootRotation(int bulletID, int numOfProj, float charge)
+ {
+ Vector3 forward = shootPosition.forward;
+ if (forceShootDir != Vector3.zero)
+ {
+ forward = forceShootDir;
+ }
+ float num = multiplySpread * Mathf.Clamp(1f + charge * chargeSpreadTo, 0f, float.PositiveInfinity);
+ float num2 = UnityEngine.Random.Range(0f - spread, spread);
+ num2 /= (1f + projectileSpeed * 0.5f) * 0.5f;
+ forward += Vector3.Cross(forward, Vector3.forward) * num2 * num;
+ return Quaternion.LookRotation(lockGunToDefault ? shootPosition.forward : forward);
+ }
+
+ private void ApplyPlayerStuff(GameObject obj)
+ {
+ ProjectileHit component = obj.GetComponent<ProjectileHit>();
+ component.ownWeapon = base.gameObject;
+ if ((bool)player)
+ {
+ component.ownPlayer = player;
+ }
+ spawnedAttack.spawner = player;
+ spawnedAttack.attackID = attackID;
+ }
+
+ private void ApplyProjectileStats(GameObject obj, int numOfProj = 1, float damageM = 1f, float randomSeed = 0f)
+ {
+ ProjectileHit component = obj.GetComponent<ProjectileHit>();
+ component.dealDamageMultiplierr *= bulletDamageMultiplier;
+ component.damage *= damage * damageM;
+ component.percentageDamage = percentageDamage;
+ component.stun = component.damage / 150f;
+ component.force *= knockback;
+ component.movementSlow = slow;
+ component.hasControl = CheckIsMine();
+ component.projectileColor = projectileColor;
+ component.unblockable = unblockable;
+ RayCastTrail component2 = obj.GetComponent<RayCastTrail>();
+ if (ignoreWalls)
+ {
+ component2.mask = component2.ignoreWallsMask;
+ }
+ if ((bool)component2)
+ {
+ component2.extraSize += size;
+ }
+ if ((bool)player)
+ {
+ PlayerSkin teamColor = (component.team = PlayerSkinBank.GetPlayerSkinColors(player.playerID));
+ obj.GetComponent<RayCastTrail>().teamID = player.playerID;
+ SetTeamColor.TeamColorThis(obj, teamColor);
+ }
+ List<ObjectsToSpawn> list = new List<ObjectsToSpawn>();
+ for (int i = 0; i < objectsToSpawn.Length; i++)
+ {
+ list.Add(objectsToSpawn[i]);
+ if (!objectsToSpawn[i].AddToProjectile || ((bool)objectsToSpawn[i].AddToProjectile.gameObject.GetComponent<StopRecursion>() && isProjectileGun))
+ {
+ continue;
+ }
+ GameObject gameObject = UnityEngine.Object.Instantiate(objectsToSpawn[i].AddToProjectile, component.transform.position, component.transform.rotation, component.transform);
+ gameObject.transform.localScale *= 1f * (1f - objectsToSpawn[i].scaleFromDamage) + component.damage / 55f * objectsToSpawn[i].scaleFromDamage;
+ if (objectsToSpawn[i].scaleStacks)
+ {
+ gameObject.transform.localScale *= 1f + (float)objectsToSpawn[i].stacks * objectsToSpawn[i].scaleStackM;
+ }
+ if (!objectsToSpawn[i].removeScriptsFromProjectileObject)
+ {
+ continue;
+ }
+ MonoBehaviour[] componentsInChildren = gameObject.GetComponentsInChildren<MonoBehaviour>();
+ for (int j = 0; j < componentsInChildren.Length; j++)
+ {
+ if (componentsInChildren[j].GetType().ToString() != "SoundImplementation.SoundUnityEventPlayer")
+ {
+ UnityEngine.Object.Destroy(componentsInChildren[j]);
+ }
+ Debug.Log(componentsInChildren[j].GetType().ToString());
+ }
+ }
+ component.objectsToSpawn = list.ToArray();
+ if (reflects > 0)
+ {
+ RayHitReflect rayHitReflect = obj.gameObject.AddComponent<RayHitReflect>();
+ rayHitReflect.reflects = reflects;
+ rayHitReflect.speedM = speedMOnBounce;
+ rayHitReflect.dmgM = dmgMOnBounce;
+ }
+ if (!forceSpecificShake)
+ {
+ float num = component.damage / 100f * ((1f + usedCooldown) / 2f) / ((1f + (float)numOfProj) / 2f) * 2f;
+ float num2 = Mathf.Clamp((0.2f + component.damage * (((float)numberOfProjectiles + 2f) / 2f) / 100f * ((1f + usedCooldown) / 2f)) * 1f, 0f, 3f);
+ component.shake = num * shakeM;
+ shake = num2;
+ }
+ MoveTransform component3 = obj.GetComponent<MoveTransform>();
+ component3.localForce *= projectileSpeed;
+ component3.simulationSpeed *= projectielSimulatonSpeed;
+ component3.gravity *= gravity;
+ component3.worldForce *= gravity;
+ component3.drag = drag;
+ component3.drag = Mathf.Clamp(component3.drag, 0f, 45f);
+ component3.velocitySpread = Mathf.Clamp(spread * 50f, 0f, 50f);
+ component3.dragMinSpeed = dragMinSpeed;
+ component3.localForce *= Mathf.Lerp(1f - component3.velocitySpread * 0.01f, 1f + component3.velocitySpread * 0.01f, randomSeed);
+ component3.selectedSpread = 0f;
+ if (damageAfterDistanceMultiplier != 1f)
+ {
+ obj.AddComponent<ChangeDamageMultiplierAfterDistanceTravelled>().muiltiplier = damageAfterDistanceMultiplier;
+ }
+ if (cos > 0f)
+ {
+ obj.gameObject.AddComponent<Cos>().multiplier = cos;
+ }
+ if (destroyBulletAfter != 0f)
+ {
+ obj.GetComponent<RemoveAfterSeconds>().seconds = destroyBulletAfter;
+ }
+ if ((bool)spawnedAttack && projectileColor != Color.black)
+ {
+ spawnedAttack.SetColor(projectileColor);
+ }
+ }
+
+ public void AddAttackAction(Action action)
+ {
+ attackAction = (Action)Delegate.Combine(attackAction, action);
+ }
+
+ internal void RemoveAttackAction(Action action)
+ {
+ attackAction = (Action)Delegate.Remove(attackAction, action);
+ }
+}