ProjectileGun | FEP
Wed May 04 2022 17:48:45 GMT+0000 (Coordinated Universal Time)
Saved by @BiscuitTinx #c#
using UnityEngine; using TMPro; public class ProjectileGun : MonoBehaviour { // audio public AudioSource Audio; public AudioClip GunShotSFX; public AudioClip ReloadSFX; // bullet public GameObject bullet; // bullet force public float shootForce, upwardForce; // Gun stats public float timeBetweenShooting, spread, reloadTime, timeBetweenShots; public int magazineSize, bulletsPerTap; public bool allowButtonHold; int bulletsLeft, bulletsShot; // recoil public Rigidbody playerRb; public float recoilForce; // bools bool shooting, readyToShoot, reloading; // Reference public Camera fpsCam; public Transform attackPoint; // graphics public TextMeshProUGUI ammunitionDisplay; // bug fixing public bool allowInvoke = true; private void Awake() { // make sure magazine is full bulletsLeft = magazineSize; readyToShoot = true; } private void Update() { MyInputs(); // set ammo display, if it exists if (ammunitionDisplay != null) { ammunitionDisplay.text = "Ammo: " + (bulletsLeft / bulletsPerTap + " / " + magazineSize / bulletsPerTap); } } private void MyInputs() { // check if allowed to hold down button and take corresponding input if (allowButtonHold) shooting = Input.GetKey(KeyCode.Mouse0); else shooting = Input.GetKeyDown(KeyCode.Mouse0); // reloading if (Input.GetKeyDown(KeyCode.R) && bulletsLeft < magazineSize && !reloading) { Reload(); } // reload automatically when trying to shoot without ammo if (readyToShoot && shooting && !reloading && bulletsLeft <= 0) { Reload(); } // shooting if (readyToShoot && shooting && !reloading && bulletsLeft > 0) { // set bullets shot to 0 bulletsShot = 0; Shoot(); Audio.PlayOneShot(GunShotSFX); } } public void Shoot() { readyToShoot = false; // find the exact hit position using a raycast Ray ray = fpsCam.ViewportPointToRay(new Vector3(0.5f, 0.5f, 0)); RaycastHit hit; // check if ray hits something Vector3 targetPoint; if (Physics.Raycast(ray, out hit)) { targetPoint = hit.point; } else { targetPoint = ray.GetPoint(75); // just a point far away from the player } // calculate direction from attackPoint to targetPoint Vector3 directionWithoutSpread = targetPoint - attackPoint.position; // calculate spread float x = Random.Range(-spread, spread); float y = Random.Range(-spread, spread); // calculate new direction with spread Vector3 directionWithSpread = directionWithoutSpread + new Vector3(x, y, 0); // just add spread to last direction // instantiate bullet/projectile GameObject currentBullet = Instantiate(bullet, attackPoint.position, Quaternion.identity); // rotate bullet to shoot direction currentBullet.transform.forward = directionWithSpread.normalized; // add force to bullet currentBullet.GetComponent<Rigidbody>().AddForce(directionWithSpread.normalized * shootForce, ForceMode.Impulse); currentBullet.GetComponent<Rigidbody>().AddForce(fpsCam.transform.up * upwardForce, ForceMode.Impulse); bulletsLeft--; bulletsShot++; // invoke resetShot function (if not already invoked) if (allowInvoke) { Invoke("ResetShot", timeBetweenShooting); allowInvoke = false; // add recoil to player playerRb.AddForce(-directionWithSpread.normalized * recoilForce, ForceMode.Impulse); } // if more than one bulletPerTap make sure to repeat shoot function if (bulletsShot < bulletsPerTap && bulletsLeft > 0) { Invoke("Shoot", timeBetweenShots); } } private void ResetShot() { readyToShoot = true; allowInvoke = true; } private void Reload() { reloading = true; Invoke("ReloadFinished", reloadTime); Audio.PlayOneShot(ReloadSFX); } private void ReloadFinished() { bulletsLeft = magazineSize; reloading = false; } }
Comments