public void OnAsyncRequestCompleted(FCgTraceRequest request) { // Setup Response FCgTraceResponse response = AllocateResponse(); response.CopyHitResults(ref request.Results); float currentTime = FCgManager_Time.Get().GetTimeSinceStart(TimeType); response.ResolveHitBuffers(currentTime, request.Start, request.End); response.ElapsedTime = currentTime - request.StartTime; #if UNITY_EDITOR if (DrawResponses.Draw()) { if (response.bResult) { // Sphere around Start FCgManager_GizmoDraw.Get().DrawSphere(response.OutHits[FIRST].TraceStart, 16.0f, Color.green, 0.1f); // Line from Start to End FCgManager_GizmoDraw.Get().DrawLine(response.OutHits[FIRST].TraceStart, response.OutHits[FIRST].Location, Color.red, 0.1f); } } #endif // #if UNITY_EDITOR LogTransaction(ECgManagerTraceCached.OnAsyncRequestCompleted, ECgTraceTransaction.Complete, request, response); // Broadcast Response request.OnResponse_Event.Broadcast(request.Id, response); response.Reset(); request.bProcessing = false; request.bCompleted = true; }
public FCgTraceResponse AllocateResponse() { for (byte i = 0; i < RESPONSE_SIZE; ++i) { ResponseIndex = (byte)((ResponseIndex + 1) % RESPONSE_SIZE); FCgTraceResponse response = Responses[ResponseIndex]; if (!response.bAllocated) { response.bAllocated = true; return(response); } } FCgDebug.LogError("FCsManager_Trace::AllocateResponse: Pool is exhausted"); return(null); }
public virtual void LogTransaction(string functionName, ECgTraceTransaction transaction, FCgTraceRequest request, FCgTraceResponse response) { }
public FCgTraceResponse Trace(FCgTraceRequest request) { request.StartTime = FCgManager_Time.Get().GetTimeSinceStart(TimeType); bool addPending = !request.bForce && TraceCountThisFrame >= RequestsProcessedPerTick; // TODO: Print warning for a normal trace moved to Async if (addPending && !request.bAsync) { request.Reset(); FCgDebug.LogWarning("FCsManager_Trace.Trace: Reached maximum RequestsProcessedPerTick: " + RequestsProcessedPerTick + " and Request is NOT Async. Abandoning Request."); return(null); } // Async if (request.bAsync || addPending) { // if NOT Pending, Start Async if (!addPending) { // if Successful in processing Request, EXIT if (ProcessRequest(request)) { AddPendingRequest(request); IncrementTraceCount(request); return(null); } } // ADD Pending Request AddPendingRequest(request); return(null); } // Normal else { #if UNITY_EDITOR if (DrawRequests.Draw()) { // Sphere around Start FCgManager_GizmoDraw.Get().DrawSphere(request.Start, 0.16f, Color.green, 0.1f); // Line from Start to End FCgManager_GizmoDraw.Get().DrawLine(request.Start, request.End, Color.red, 0.1f); } #endif // #if UNITY_EDITOR FCgTraceResponse response = AllocateResponse(); response.ElapsedTime = 0.0f; // Line if (request.Type == ECgTraceType.Line) { // Test if (request.Method == ECgTraceMethod.Test) { // Linecast response.bResult = Physics.Linecast(request.Start, request.End, request.LayerMask); } // Single else if (request.Method == ECgTraceMethod.Single) { FCgDebug.LogWarning("FCsManager_Trace.Trace: Line Trace Single is NOT supported. Use TraceMethod: Test or Multi. Abandoning Request."); } // Multi else if (request.Method == ECgTraceMethod.Multi) { // RaycastNonAlloc Vector3 v = request.End - request.Start; float distance = v.magnitude; Vector3 dir = distance > 0.0f ? v / distance : Vector3.zero; float EXTEND = 0.1f; response.OutHitCount = Physics.RaycastNonAlloc(request.Start, dir, response.OutHitBuffer, distance + EXTEND, request.LayerMask); response.ResolveHitBuffers(request.StartTime, request.Start, request.End); } } // Sweep else if (request.Type == ECgTraceType.Sweep) { // Test if (request.Method == ECgTraceMethod.Test) { // Box if (request.Shape == ECgCollisionShape.Box) { // CheckBox response.bResult = Physics.CheckBox(request.BoxParams.Center, request.BoxParams.HalfExtents, request.BoxParams.Orientation, request.LayerMask); } // Sphere else if (request.Shape == ECgCollisionShape.Sphere) { // CheckSphere response.bResult = Physics.CheckSphere(request.SphereParams.Position, request.SphereParams.Radius, request.LayerMask); } // Capsule else if (request.Shape == ECgCollisionShape.Capsule) { // CheckCapsule response.bResult = Physics.CheckCapsule(request.CapsuleParams.Start, request.CapsuleParams.End, request.CapsuleParams.Radius, request.LayerMask); } } // Single else if (request.Method == ECgTraceMethod.Single) { FCgDebug.LogWarning("FCsManager_Trace.Trace: Sweep Trace Single is NOT supported. Use TraceMethod: Test or Multi. Abandoning Request."); } // Multi else if (request.Method == ECgTraceMethod.Multi) { // Box if (request.Shape == ECgCollisionShape.Box) { // BoxCastNonAlloc Vector3 v = request.End - request.Start; float distance = v.magnitude; Vector3 dir = distance > 0.0f ? v / distance : Vector3.zero; float EXTEND = 0.1f; response.OutHitCount = Physics.BoxCastNonAlloc(request.BoxParams.Center, request.BoxParams.HalfExtents, dir, response.OutHitBuffer, request.BoxParams.Orientation, distance + EXTEND, request.LayerMask); response.ResolveHitBuffers(request.StartTime, request.Start, request.End); } // Sphere else if (request.Shape == ECgCollisionShape.Sphere) { // SphereCastNonAlloc Vector3 v = request.End - request.Start; float distance = v.magnitude; Vector3 dir = distance > 0.0f ? v / distance : Vector3.zero; float EXTEND = 0.1f; response.OutHitCount = Physics.SphereCastNonAlloc(request.Start, request.SphereParams.Radius, dir, response.OutHitBuffer, distance + EXTEND, request.LayerMask); response.ResolveHitBuffers(request.StartTime, request.Start, request.End); } // Capsule else if (request.Shape == ECgCollisionShape.Capsule) { // CapsuleCastNonAlloc Vector3 v = request.End - request.Start; float distance = v.magnitude; Vector3 dir = distance > 0.0f ? v / distance : Vector3.zero; float EXTEND = 0.1f; response.OutHitCount = Physics.CapsuleCastNonAlloc(request.CapsuleParams.Start, request.CapsuleParams.End, request.CapsuleParams.Radius, dir, response.OutHitBuffer, distance + EXTEND, request.LayerMask); response.ResolveHitBuffers(request.StartTime, request.Start, request.End); } } } // Overlap else if (request.Type == ECgTraceType.Overlap) { // Test if (request.Method == ECgTraceMethod.Test) { FCgDebug.LogWarning("FCsManager_Trace.Trace: Overlap Trace Test is NOT supported. Use TraceMethod: Multi. Abandoning Request."); } // Single else if (request.Method == ECgTraceMethod.Single) { FCgDebug.LogWarning("FCsManager_Trace.Trace: Overlap Trace Single is NOT supported. Use TraceMethod: Multi. Abandoning Request."); } // Multi else if (request.Method == ECgTraceMethod.Multi) { // Box if (request.Shape == ECgCollisionShape.Box) { // OverlapBoxNonAlloc response.OutOverlapCount = Physics.OverlapBoxNonAlloc(request.BoxParams.Center, request.BoxParams.HalfExtents, response.OutOverlapBuffer, request.BoxParams.Orientation, request.LayerMask); response.ResolveOverlapBuffers(request.StartTime); } // Sphere else if (request.Shape == ECgCollisionShape.Sphere) { // OverlapSphereNonAlloc response.OutOverlapCount = Physics.OverlapSphereNonAlloc(request.SphereParams.Position, request.SphereParams.Radius, response.OutOverlapBuffer, request.LayerMask); response.ResolveOverlapBuffers(request.StartTime); } // Capsule else if (request.Shape == ECgCollisionShape.Capsule) { // CapsuleCastNonAlloc response.OutOverlapCount = Physics.OverlapCapsuleNonAlloc(request.CapsuleParams.Start, request.CapsuleParams.End, request.CapsuleParams.Radius, response.OutOverlapBuffer, request.LayerMask); response.ResolveOverlapBuffers(request.StartTime); } } } IncrementTraceCount(request); request.Reset(); #if UNITY_EDITOR if (DrawResponses.Draw()) { if (response.bResult) { // Sphere around Start FCgManager_GizmoDraw.Get().DrawSphere(response.OutHits[FIRST].TraceStart, 0.16f, Color.green, 0.1f); // Line from Start to End FCgManager_GizmoDraw.Get().DrawLine(response.OutHits[FIRST].TraceStart, response.OutHits[FIRST].Location, Color.red, 0.1f); } } #endif // #if UNITY_EDITOR return(response); } }
public FCgManager_Trace() { TimeType = ECgTime.Update; RequestsProcessedPerTick = MAX_REQUESTS_PROCESSED_PER_TICK; TraceCountLifetimeByObjectId = new Dictionary <ulong, ulong>(); TraceCountLifetimeByType = new ulong[TRACE_TYPE_MAX]; for (byte i = 0; i < TRACE_TYPE_MAX; ++i) { TraceCountLifetimeByType[i] = 0; } TraceCountLifetimeByMethod = new ulong[TRACE_METHOD_MAX]; for (byte i = 0; i < TRACE_METHOD_MAX; ++i) { TraceCountLifetimeByMethod[i] = 0; } TraceCountLifetimeByObjectId = new Dictionary <ulong, ulong>(); TraceCountThisFrameByObjectId = new Dictionary <ulong, ushort>(); TraceCountThisFrameByType = new ushort[TRACE_TYPE_MAX]; for (byte i = 0; i < TRACE_TYPE_MAX; ++i) { TraceCountThisFrameByType[i] = 0; } TraceCountThisFrameByMethod = new ushort[TRACE_METHOD_MAX]; for (byte i = 0; i < TRACE_METHOD_MAX; ++i) { TraceCountThisFrameByMethod[i] = 0; } Requests = new FCgTraceRequest[REQUEST_SIZE]; for (byte i = 0; i < REQUEST_SIZE; ++i) { Requests[i] = new FCgTraceRequest(i); } RequestIndex = 0; PendingRequests = new LinkedList <FCgTraceRequest>(); PendingRequestMap = new Dictionary <byte, FCgTraceRequest>(); PendingRequestsByTraceId = new Dictionary <ulong, FCgTraceRequest>(); PendingRequestsByObjectId = new Dictionary <ulong, Dictionary <byte, FCgTraceRequest> >(); PendingRequestsByType = new Dictionary <ECgTraceType, Dictionary <byte, FCgTraceRequest> >(new ECgTraceTypeEqualityComparer()); for (byte i = 0; i < TRACE_TYPE_MAX; ++i) { Dictionary <byte, FCgTraceRequest> addMap = new Dictionary <byte, FCgTraceRequest>(); PendingRequestsByType.Add((ECgTraceType)i, addMap); } PendingRequestsByMethod = new Dictionary <ECgTraceMethod, Dictionary <byte, FCgTraceRequest> >(new ECgTraceMethodEqualityComparer()); for (byte i = 0; i < TRACE_METHOD_MAX; ++i) { Dictionary <byte, FCgTraceRequest> addMap = new Dictionary <byte, FCgTraceRequest>(); PendingRequestsByMethod.Add((ECgTraceMethod)i, addMap); } Responses = new FCgTraceResponse[RESPONSE_SIZE]; for (int i = 0; i < RESPONSE_SIZE; ++i) { Responses[i] = new FCgTraceResponse(); } ResponseIndex = 0; }
public virtual void PerformViewTrace_Respone(byte requestId, FCgTraceResponse response) { }