bullet physics using raycast?

As the title says, I need a way to have bullet physics but using raycast. I search but most didn’t give a answer to it. Kind of like this video at around 8:30:

right now for all of the scripts I’m using a forward raycast from the camera, and some guns I don’t want to do that. Here’s the sniper rifle script I want to change:

var GunCamera : Camera;
var shotSound: AudioClip; // Shot sound
var bloodPrefab: GameObject; // Blood for enemy
var sparksPrefab: GameObject; // Sparks for groun
var muzzleFlash : GameObject;
var ShellPrefab : Transform;
var shootEnabled: boolean = true; // allows disabling the shots
var ChangeWep : boolean = true;
var MaxBullets = 9;
var Bullets = 9;
var Clip = 9000;
var shotInterval = 1.0;
var force = 50;
var RayCastDist : float = 50;
var Zoom : int;

function Shoot(){
    var cam : Transform = Camera.main.transform;
    var ray = new Ray(cam.position, cam.forward);
    var hit : RaycastHit;
    var trf = transform; // a little optimization
    var hitRotation = Quaternion.FromToRotation(Vector3.up, hit.normal);
    MuzzleFlashOn();
    audio.PlayOneShot(shotSound); // play the shot sound...
    var ShellClone = GameObject.Instantiate(ShellPrefab, GameObject.Find("ShellSpawner").transform.position, Quaternion.identity);
    ShellClone.rigidbody.AddForce(transform.up + transform.right * 200);
    
        if(Physics.Raycast (ray, hit, RayCastDist)){
        var rot = Quaternion.FromToRotation(Vector3.up, hit.normal);
                 
            if(hit.collider.gameObject.tag == "Box"){
                Debug.Log ("Hit A Box!");
                if (sparksPrefab) Instantiate(sparksPrefab, hit.point, rot); 
                hit.rigidbody.AddForceAtPosition(force * transform.forward , hit.point);
                hit.collider.SendMessageUpwards("ApplyDamage", 5.0);
                //Instantiate(bulletHole, hit.point, rot);
        }
            if(hit.collider.gameObject.tag == "Enemy"){
                Debug.Log ("Hit A Enemy!");
                if (sparksPrefab) Instantiate(sparksPrefab, hit.point, rot);
        } 
            if(hit.collider.gameObject.tag == "Target"){
                Debug.Log ("Target hit!");
                hit.rigidbody.AddForceAtPosition(force * transform.forward , hit.point);
                hit.rigidbody.isKinematic = false;
                hit.rigidbody.useGravity = true;
                if (sparksPrefab) Instantiate(sparksPrefab, hit.point, rot); 
            } else {            
            if (sparksPrefab) Instantiate(sparksPrefab, hit.point, rot);
            Debug.Log ("Hit Other!");
        }
        ChangeWep = false;
        SendMessageUpwards("Recoil");
        shootEnabled = false;
        yield WaitForSeconds(shotInterval);
        shootEnabled = true;
        ChangeWep = true;    
        }
    }

what i would do is to make a Vector3 to simulate gravity multiply it by the distance between the hit and shooter and then add that vector to the hit.point. so depending on how far from the hit is from the shooter, the hit will drop a distance that is scale to its traveled path.

so for example:

        //what i changed
        var Gravity : Vector3 = Vector3(0,-0.5,0); //you might wanna mess around with this number
        if(Physics.Raycast (ray, hit, RayCastDist)){
            var rot = Quaternion.FromToRotation(Vector3.up, hit.normal);
            hit.point = hit.point + hit.distance*Gravity;
        //what i changed

        if(hit.collider.gameObject.tag == "Box"){
            Debug.Log ("Hit A Box!");
            if (sparksPrefab) Instantiate(sparksPrefab, hit.point, rot); 
            hit.rigidbody.AddForceAtPosition(force * transform.forward , hit.point);
            hit.collider.SendMessageUpwards("ApplyDamage", 5.0);
            //Instantiate(bulletHole, hit.point, rot);
    }
        if(hit.collider.gameObject.tag == "Enemy"){
            Debug.Log ("Hit A Enemy!");
            if (sparksPrefab) Instantiate(sparksPrefab, hit.point, rot);
    } 
        if(hit.collider.gameObject.tag == "Target"){
            Debug.Log ("Target hit!");
            hit.rigidbody.AddForceAtPosition(force * transform.forward , hit.point);
            hit.rigidbody.isKinematic = false;
            hit.rigidbody.useGravity = true;
            if (sparksPrefab) Instantiate(sparksPrefab, hit.point, rot); 
        } else {            
        if (sparksPrefab) Instantiate(sparksPrefab, hit.point, rot);
        Debug.Log ("Hit Other!");
    }

The shooting technique used in Elite Squad probably uses multiple rays - the segments that appear in the linked video. You could do something similar by calculating the position each Update or FixedUpdate with speed, gravity and wind taken into account, and check collisions with Linecast between the last and the current positions. An easier possibility is to let Unity do the hard work for you: simply shoot a fast rigidbody (the bullet) and let physics handle the trajectory, but still check collisions with Linecast each FixedUpdate, or you’ll probably miss the smaller targets - something like this (bullet script):

var bulletSpeed: float = 250;
private var startPos: Vector3; // initial position (used for hit.distance calculation)
private var lastPos: Vector3; // bullet position last physics cycle
private var hit: RaycastHit; // hit info will be passed here

function Start(){
  // initialize variables:
  startPos = rigidbody.position; 
  lastPos = startPos;
  // accelerate the bullet:
  rigidbody.velocity = transform.forward * bulletSpeed; 
}

function FixedUpdate(){
  var curPos = rigidbody.position;
  if (Physics.Linecast(lastPos, curPos, hit)){
    HitSomething();
  }
  lastPos = curPos; // update lastPos
}

// regular collisions may be detected as well:
function OnCollisionEnter(col: Collision){
  // copy the important fields from col to hit:
  hit.rigidbody = col.rigidbody;
  hit.transform = col.transform;
  var contact = col.contacts[0];
  hit.point = contact.point;
  hit.normal = contact.normal;
  hit.distance = Vector3.Distance(hit.point, startPos);
  HitSomething();
}

function HitSomething(){
  Destroy(gameObject); // destroy the bullet when hit something
  // your hit code goes here:
  var rot = Quaternion.FromToRotation(Vector3.up, hit.normal);
  if(hit.collider.gameObject.tag == "Box"){
    Debug.Log ("Hit A Box!");
    if (sparksPrefab) Instantiate(sparksPrefab, hit.point, rot); 
    hit.rigidbody.AddForceAtPosition(force * transform.forward , hit.point);
    hit.collider.SendMessageUpwards("ApplyDamage", 5.0);
    ...
}

Your Shoot function would become simpler:

...
var bulletPrefab: GameObject; // drag the bullet prefab here

function Shoot(){
    var trf = transform; // a little optimization
    MuzzleFlashOn();
    audio.PlayOneShot(shotSound); // play the shot sound...
    var ShellClone = GameObject.Instantiate(ShellPrefab, GameObject.Find("ShellSpawner").transform.position, Quaternion.identity);
    ShellClone.rigidbody.AddForce(transform.up + transform.right * 200);
    Instantiate(bulletPrefab, trf.position, trf.rotation);
    ChangeWep = false;
    SendMessageUpwards("Recoil");
    shootEnabled = false;
    yield WaitForSeconds(shotInterval);
    shootEnabled = true;
    ChangeWep = true;    
}

Notice that this is just a basic suggestion: adapting your current code to this will probably cause a couple headaches, because some parts (the hit detection and particles generation) were moved to the bullet script. The Shoot script should be attached to a spawn point object - usually an empty game object childed to the weapon and positioned at the weapon tip, oriented in the weapon forward direction. The original code always shot in the camera’s forward direction, hitting anything at the screen center, but this ballistic-like code will shoot in the direction the weapon is aiming to.

I did that! I shoot a raycast and within time, it’ll increase the range. to simulate the trajectory I made to the transform decrease the rotation in the x-axis depending on bullet’s weight, the air density, and the current speed of the bullet.

works cool, but if anything cross through the bullet’s trajectory, even if the range is 1km still detecting the collision.