private void OnTriggerStay2D(Collider2D collision) { if (!collision.attachedRigidbody) { return; } PerceiveUnit unit = collision.GetComponent <PerceiveUnit>(); if (!unit) { return; } _noiseAccumulator += collision.attachedRigidbody.velocity.magnitude * walkVelocityScale; if (_noiseAccumulator > noiseThreshold && SenseNoise.CanSpreadNoise()) { _noiseAccumulator = 0; NoiseData noiseData = new NoiseData(); noiseData.position = collision.transform.position; noiseData.velocity = collision.attachedRigidbody.velocity; noiseData.fraction = unit.fraction; SenseNoise.SpreadNoise(noiseData); } }
bool DoObstaclesBlockVision(Vector3 target) { // we will change searchDistance based on visibility of obstacles; float localSearchDistance = this.searchDistance; Vector3 toTarget = target - cachedTransform.position; float toTargetSq = toTarget.ToPlane().sqrMagnitude; int n = Physics.RaycastNonAlloc(cachedTransform.position, toTarget, StaticCacheLists.raycastHitCache, toTarget.magnitude, obstacleMask); bool bObstaclesBlocksVision = false; for (int i = 0; i < n; ++i) { var it = StaticCacheLists.raycastHitCache[i]; PerceiveUnit unit = it.collider.GetComponent <PerceiveUnit>(); if (!unit) { // we assume objects that do not have perceive unit will behave as non transparent // so we can't see our target bObstaclesBlocksVision = true; break; } if (unit == myUnit) { // well, i'm not that fat ... i guess continue; } localSearchDistance *= unit.transparencyLevel; if (localSearchDistance * localSearchDistance < toTargetSq * myUnit.distanceModificator) // transparency is reduced too much to see the target { bObstaclesBlocksVision = true; break; } } Debug.DrawRay(cachedTransform.position, toTarget, bObstaclesBlocksVision ? Color.yellow : Color.green, 0.25f); return(bObstaclesBlocksVision); }
private void OnCollisionEnter2D(Collision2D collision) { // omit too weak touches if (collision.relativeVelocity.sqrMagnitude < minimalRelativeVelocity * minimalRelativeVelocity) { return; } // only targets with perceive unit will report // mostly to allow to tune what is perceived PerceiveUnit otherUnit = collision.gameObject.GetComponent <PerceiveUnit>(); if (!otherUnit) { return; } // only report every given seconds if (!tTouch.IsReadyRestart()) { return; } var otherRigidbody = collision.rigidbody; var otherTransform = collision.transform; MemoryEvent ev = new MemoryEvent(); ev.exactPosition = otherTransform.position; ev.forward = otherTransform.up; ev.velocity = otherRigidbody ? otherRigidbody.velocity : Vector2.zero; ev.lifetimeTimer.Restart(); touchStorage.PerceiveEvent(ev); #if UNITY_EDITOR Debug.DrawRay(ev.exactPosition, Vector3.up, Color.blue); #endif }
protected void Awake() { myUnit = GetComponentInParent <PerceiveUnit>(); behaviourController = GetComponentInChildren <BehaviourController>(); }
void PerformSearch() { Fraction myFraction = myUnit.fraction; if (!myFraction) { #if UNITY_EDITOR Debug.LogWarning("No fraction in perceive unit but trying to use sight"); #endif // there's no way to determine where to put events return; } // perform cast int n = Physics.OverlapSphereNonAlloc(cachedTransform.position, searchDistance, StaticCacheLists.colliderCache, memorableMask); // preselect targets // they have to be in proper angle and contain PerceiveUnit for (int i = 0; i < n; ++i) { var it = StaticCacheLists.colliderCache[i]; Transform itTransform = it.transform; //// check if the target is in proper angle Vector3 toIt = itTransform.position - cachedTransform.position; toIt = toIt.To2D(); float cosAngle = Vector2.Dot(toIt.normalized, cachedTransform.forward.To2D()); float angle = Mathf.Acos(cosAngle) * 180 / Mathf.PI; //Debug.Log(angle); bool bProperAngle = angle < coneAngle * 0.5f; if (!bProperAngle) { continue; } // ok, now check if it has PerceiveUnit component // we need it's fraction to determine our attitude PerceiveUnit perceiveUnit = it.GetComponent <PerceiveUnit>(); if (perceiveUnit == myUnit) { // oh, come on do not look at yourself... don't be soo narcissistic continue; } if (!perceiveUnit) { // no perceive unit, this target is invisible to us continue; } Fraction itFraction = perceiveUnit.fraction; if (!itFraction) { // the same as above, return; } //// determine attitude Fraction.EAttitude attitude = myFraction.GetAttitude(itFraction); //// Check if obstacles blocks vision if (DoObstaclesBlockVision(itTransform.position)) { continue; } //// create event var rb = it.attachedRigidbody; MemoryEvent ev = new MemoryEvent { exactPosition = itTransform.position, forward = itTransform.up, // if collider has rigidbody then take its velocity // otherwise there is no simple way to determine event velocity velocity = rb ? rb.velocity * velocityPredictionScale : Vector3.zero, // set up agent responsible for this event perceiveUnit = perceiveUnit }; // ensure event will tick from now on ev.lifetimeTimer.Restart(); Debug.DrawRay(itTransform.position, Vector3.up, Color.blue, _searchTime * nEvents); Debug.DrawRay(itTransform.position, ev.velocity * _searchTime, Color.gray, _searchTime); InsertEvent(ev, attitude); } }