Ejemplo n.º 1
0
 void Start()
 {
     mesh = meshfilter.mesh;
     //meshfilter.mesh = mesh;
     for (int i = 0; i < beams.Length; i++)
     {
         beams[i] = new RaycastBeams();
         for (int j = 0; j < beams[i].hits.Length; j++)
         {
             beams[i].hits[j] = new RaycastHit();
         }
     }
 }
Ejemplo n.º 2
0
    // CastRays is called when a target is colliding with teh targetting area
    // the rays are to check if the target is also within LOS of the originating player
    // if a ray hits it should mark the target as hittable
    // if the trigger is pulled (PullTrigger() on the weapon is called)
    // <AbstractWeapon>.PullTrigger should be passed the rayhit from CastRays() ? or maybe just needs to know true/false if valid target is in range
    // it should cast all the rays every time because multiple targets can be in the range
    // maybe can optimize if there is only 1 target, not sure
    void CastRays()
    {
        float angleBetweenRays = weaponArc / raycasts;
        int   rightBoundAngle  = Mathf.RoundToInt(weaponArc / 2);
        int   leftBoundAngle   = -1 * rightBoundAngle;

        for (int i = 0; i < raycasts; i++)
        {
            Quaternion rotationR = Quaternion.AngleAxis(leftBoundAngle + i * angleBetweenRays, Vector3.up);
            Vector3    dir       = rotationR * transform.forward * weaponRange;
            Ray        newRay    = new Ray(transform.position, dir);
            //create new struct beam of type RaycastBeams
            RaycastBeams beam = GetBeam(i);
            if (beam == null)
            {
                return;
            }
            //add beam to the beams array at index i
            //cast the ray and put the results into the hits array
            var hitsArr = beam.hits;

            var raybeam = Physics.RaycastNonAlloc(newRay, hitsArr, weaponRange, weapon.layerMask);
            if (raybeam > 0)
            {
                beams[i] = beam;
                beam.shouldBeProcessed = true;
            }
            //debug
            Debug.DrawRay(transform.position, dir, Color.green);
            //draw one additional ray at the rightBound
            if (i == raycasts - 1)
            {
                Vector3      rightBound = Quaternion.AngleAxis(rightBoundAngle, Vector3.up) * transform.forward * weaponRange;
                Ray          finalRay   = new Ray(transform.position, rightBound);
                RaycastBeams finalBeam  = new RaycastBeams();

                Physics.RaycastNonAlloc(finalRay, finalBeam.hits, weaponRange, weapon.layerMask);
                beams[i + 1] = finalBeam;
                //debug
                Debug.DrawRay(transform.position, rightBound, Color.green);
            }
        }
    }
Ejemplo n.º 3
0
    // processRays should process all the RaycastHits of every RaycastBeams
    // the goal is to produce either null for no valid target
    // or return the RaycastHit of the closest valid target
    RaycastBeams ProcessRays()
    {
        RaycastBeams        closestValidRaycastBeam           = new RaycastBeams();
        float               closestValidTargetDistance        = 1000f;
        List <RaycastBeams> beamsWithValidTargetsAsTheClosest = new List <RaycastBeams>();

        //RaycastBeams closestPlayerRaycastHit;

        for (int i = 0; i < beams.Length; i++)
        {
            //skip the beam if already processed
            if (beams[i] == null || beams[i].shouldBeProcessed == false)
            {
                continue;
            }
            //Debug.Log("processing beam at " + i);
            //these are for iterating thru the raycasthit array of each beam
            float        closestTargetDistance = 1000f;
            RaycastHit   closestHit            = new RaycastHit();
            RaycastBeams validBeam             = null;

            //cycle thru all the RaycastNonAlloc hits to find the closest
            for (int j = 0; j < beams[i].hits.Length; j++)
            {
                var theHit = beams[i].hits[j];
                if (theHit.distance == 0)
                {
                    continue;
                }
                //Debug.Log("theHit " + theHit.distance) ;
                if (theHit.distance <= closestTargetDistance)
                {
                    closestTargetDistance = theHit.distance;
                    closestHit            = theHit;
                    beams[i].validHit     = theHit;
                    validBeam             = beams[i];
                }
            }

            //Debug.Log("the closest hit is " + closestHit.collider.tag);
            if (closestHit.collider == null)
            {
                continue;
            }


            //if the target is valid
            var isPlayer = closestHit.collider.CompareTag("PlayerHitbox");
            var isNPC    = closestHit.collider.CompareTag("NPCHitbox");

            if (isPlayer || isNPC)
            {
                beamsWithValidTargetsAsTheClosest.Add(validBeam);
                //else dont do anything
            }
            beams[i].shouldBeProcessed = false;
        }
        // Went thru all the beams and have a list of beams with valid targets
        // now go thru this list and find the closest one

        for (int k = 0; k < beamsWithValidTargetsAsTheClosest.Count; k++)
        {
            var theBeam = beamsWithValidTargetsAsTheClosest[k];
            if (theBeam.validHit.distance < closestValidTargetDistance)
            {
                closestValidTargetDistance             = theBeam.validHit.distance;
                closestValidRaycastBeam                = theBeam;
                closestValidRaycastBeam.hasValidTarget = true;
                //Debug.Log("hitting player " + theBeam.validHit.collider.GetComponentInParent<Player>().ID);
            }
        }

        if (beamsWithValidTargetsAsTheClosest.Count > 0)
        {
            WeaponTargettingState = TargettingState.TargetsInLOS;
        }

        return(closestValidRaycastBeam);
    }