/* * Check light range for LightSensors that should be lit */ public override void LightSensorCheck() { litObjects = new List <GameObject>(); if (!light.enabled) { return; } Vector3 position = transform.position; Vector3 forward = transform.forward; float lightAngle = light.spotAngle * 0.5f; float lightRange = light.range; float radius = Mathf.Tan(lightAngle * Mathf.Deg2Rad) * lightRange; float coneHyp = Mathf.Sqrt(lightRange * lightRange + radius * radius); Collider[] cols = Physics.OverlapCapsule(position + (forward * radius), position + (forward * lightRange), radius, layerMask, QueryTriggerInteraction.Ignore); foreach (Collider col in cols) { // Check object has a LightSensor LightSensor sensor = col.GetComponent <LightSensor>(); if (sensor == null) { continue; } RaycastHit hitInfo; // perform initial position check Vector3 sensorPos = sensor.transform.position; float hitAngle = Vector3.Angle(forward, sensorPos - position); float rayLength = Utilities.MapValues(hitAngle, 0f, lightAngle, lightRange, coneHyp); if (hitAngle <= lightAngle && Physics.Raycast(position, sensorPos - position, out hitInfo, rayLength, layerMask)) { if (hitInfo.transform == sensor.transform) { litObjects.Add(sensor.gameObject); sensor.LightObject(GetIntensity(hitInfo.point)); continue; } } // if no custom points defined, can just skip expanded check logic if (!sensor.UseCustomPoints()) { continue; } // TODO: This section will finish when the first lit point is found. // Thus the intensity returned will be the first one found, rather then the highest of all points hit. // Unsure what ways around this there might be without constantly needing to check every point. // TODO: Somehow order points by distance from light???? List <Vector3> points = sensor.GetLightCheckPoints(sensorPos - position); foreach (Vector3 point in points) { // check if the point is within the spot angle Vector3 dir = point - position; hitAngle = Vector3.Angle(forward, dir); if (hitAngle > lightAngle) { continue; } Ray ray = new Ray(position, dir); rayLength = Utilities.MapValues(hitAngle, 0f, lightAngle, lightRange, coneHyp); if (Physics.Raycast(ray, out hitInfo, rayLength, layerMask, QueryTriggerInteraction.Ignore)) { // only trigger 'lit' status if raycast hits the sensor object if (hitInfo.transform == sensor.transform) { litObjects.Add(sensor.gameObject); sensor.LightObject(GetIntensity(hitInfo.point)); break; } } } } }
/* * Check light range for LightSensors that should be lit */ public override void LightSensorCheck() { litObjects = new List <GameObject>(); if (!light.enabled) { return; } Vector3 position = transform.position; float range = light.range; Collider[] cols = Physics.OverlapSphere(position, range, layerMask, QueryTriggerInteraction.Ignore); foreach (Collider col in cols) { // check object has a LightSensor LightSensor sensor = col.gameObject.GetComponent <LightSensor>(); if (sensor == null) { continue; } Vector3 colPos = col.transform.position; RaycastHit hitInfo; if (Physics.Raycast(position, colPos - position, out hitInfo, range, layerMask)) { // perform initial position check if (hitInfo.transform == col.transform) { litObjects.Add(sensor.gameObject); sensor.LightObject(GetIntensity(hitInfo.point)); continue; } } // if no custom points defined, can just skip next bit of logic if (!sensor.UseCustomPoints()) { continue; } // TODO: This section will finish when the first lit point is found. // Thus the intensity returned will be the first one found, rather then the highest of all points hit. // Unsure what ways around this there might be without constantly needing to check every point. // TODO: Somehow order points by distance from light???? List <Vector3> points = sensor.GetLightCheckPoints(colPos - position); foreach (Vector3 point in points) { Ray ray = new Ray(position, point - position); if (Physics.Raycast(ray, out hitInfo, range, layerMask, QueryTriggerInteraction.Ignore)) { // only trigger 'lit' status if raycast hits the sensor object if (hitInfo.transform == col.transform) { litObjects.Add(sensor.gameObject); sensor.LightObject(GetIntensity(hitInfo.point)); break; } } } } }