private static void triggerOnHitObject <T>(T interactionData, IImpactObject otherObject, int physicsMaterialId, bool useMaterialComposition) where T : IInteractionData
 {
     if (otherObject != null)
     {
         if (useMaterialComposition)
         {
             int count = otherObject.GetMaterialCompositionNonAlloc(interactionData.Point, ImpactManagerInstance.MaterialCompositionBuffer);
             for (int i = 0; i < count; i++)
             {
                 ImpactMaterialComposition comp = ImpactManagerInstance.MaterialCompositionBuffer[i];
                 if (comp.CompositionValue > 0)
                 {
                     IInteractionData newInteractionData = interactionData.Clone();
                     newInteractionData.CompositionValue = comp.CompositionValue;
                     ImpactManagerInstance.ProcessInteraction(newInteractionData, comp.Material, otherObject);
                 }
             }
         }
         else
         {
             ImpactManagerInstance.ProcessInteraction(interactionData, otherObject);
         }
     }
     else if (ImpactManagerInstance.UseMaterialMapping)
     {
         IImpactMaterial m;
         if (ImpactManagerInstance.TryGetImpactMaterialFromMapping(physicsMaterialId, out m))
         {
             ImpactManagerInstance.ProcessInteraction(interactionData, m, null);
         }
     }
 }
Beispiel #2
0
        /// <summary>
        /// Process a collision contact to get all material and velocity data.
        /// The material and velocity data will be sent to buildInteractionData, which you can override.
        /// </summary>
        /// <param name="collision">The original collision data.</param>
        /// <param name="contactPoint">The contact point of the collision to use in calculations.</param>
        protected void processCollisionContact(TCollision collision, TContact contactPoint)
        {
            IImpactObject myObject = getImpactObject(contactPoint.ThisObject);

            if (myObject != null)
            {
                IImpactObject otherObject    = contactPoint.OtherObject.GetComponentInParent <IImpactObject>();
                bool          hasOtherObject = otherObject != null;

                //Material composition is enabled
                if (UseMaterialComposition && hasOtherObject)
                {
                    //Get material composition
                    int count = otherObject.GetMaterialCompositionNonAlloc(contactPoint.Point, ImpactManagerInstance.MaterialCompositionBuffer);

                    //Get velocity data
                    VelocityData myVelocityData    = myObject.GetVelocityDataAtPoint(contactPoint.Point);
                    VelocityData otherVelocityData = otherObject.GetVelocityDataAtPoint(contactPoint.Point);

                    //Create interaction for each material
                    for (int i = 0; i < count; i++)
                    {
                        ImpactMaterialComposition comp = ImpactManagerInstance.MaterialCompositionBuffer[i];
                        if (comp.CompositionValue > 0)
                        {
                            buildInteractionData(myObject, collision, contactPoint, myVelocityData, otherVelocityData, comp.Material.MaterialTagsMask, comp.CompositionValue);
                        }
                    }
                }
                //Material composition is not enabled
                else
                {
                    //Get velocity data
                    VelocityData otherVelocityData = hasOtherObject ? otherObject.GetVelocityDataAtPoint(contactPoint.Point) : new VelocityData();
                    VelocityData myVelocityData    = myObject.GetVelocityDataAtPoint(contactPoint.Point);

                    //Get tag mask
                    ImpactTagMask?tagMask = getOtherObjectTagMask(otherObject, contactPoint.Point, contactPoint.OtherPhysicsMaterialID, hasOtherObject);

                    //Create interaction
                    buildInteractionData(myObject, collision, contactPoint, myVelocityData, otherVelocityData, tagMask, 1);
                }
            }
            else
            {
                //Impact object could not be found. MainTarget is not assigned and no Impact Object could be determined from the contact point.
                Debug.LogError("Unable to find Impact Object on GameObject " + gameObject.name);
            }
        }
        private static void triggerOnRaycastingObject <T>(T interactionData, IImpactObject impactObject, IImpactObject otherObject, int physicsMaterialId, bool useMaterialComposition) where T : IInteractionData
        {
            if (otherObject != null)
            {
                if (useMaterialComposition)
                {
                    int count = otherObject.GetMaterialCompositionNonAlloc(interactionData.Point, ImpactManagerInstance.MaterialCompositionBuffer);
                    for (int i = 0; i < count; i++)
                    {
                        ImpactMaterialComposition comp = ImpactManagerInstance.MaterialCompositionBuffer[i];
                        if (comp.CompositionValue > 0)
                        {
                            IInteractionData newInteractionData = interactionData.Clone();
                            newInteractionData.CompositionValue = comp.CompositionValue;
                            newInteractionData.TagMask          = comp.Material.MaterialTagsMask;
                            ImpactManagerInstance.ProcessInteraction(newInteractionData, impactObject);
                        }
                    }
                }
                else
                {
                    IImpactMaterial material = otherObject.GetPrimaryMaterial(interactionData.Point);
                    if (material != null || (ImpactManagerInstance.UseMaterialMapping && ImpactManagerInstance.TryGetImpactMaterialFromMapping(physicsMaterialId, out material)))
                    {
                        interactionData.TagMask = material.MaterialTagsMask;
                    }

                    ImpactManagerInstance.ProcessInteraction(interactionData, impactObject);
                }
            }
            else if (ImpactManagerInstance.UseMaterialMapping)
            {
                IImpactMaterial material;
                if (ImpactManagerInstance.TryGetImpactMaterialFromMapping(physicsMaterialId, out material))
                {
                    interactionData.TagMask = material.MaterialTagsMask;
                }

                ImpactManagerInstance.ProcessInteraction(interactionData, impactObject);
            }
        }
        private void processParticleCollision(ParticleCollisionEvent particleCollisionEvent, GameObject onParticleCollisionObject, bool isParticleSystem)
        {
            IImpactObject myObject;

            //Particle system always uses the main target
            if (isParticleSystem)
            {
                myObject = MainTarget;
            }
            //Non-particle system gets the object from the particle collision event's collider
            else
            {
                myObject = getImpactObject(particleCollisionEvent.colliderComponent.gameObject);
            }

            if (myObject != null)
            {
                IImpactObject otherObject = null;

                //Get other object based on whether or not this object is a particle system
                if (isParticleSystem)
                {
                    otherObject = particleCollisionEvent.colliderComponent.GetComponentInParent <IImpactObject>();
                }
                else
                {
                    otherObject = onParticleCollisionObject.GetComponentInParent <IImpactObject>();
                }

                bool hasOtherObject = otherObject != null;

                if (UseMaterialComposition && hasOtherObject)
                {
                    int count = otherObject.GetMaterialCompositionNonAlloc(particleCollisionEvent.intersection, ImpactManagerInstance.MaterialCompositionBuffer);

                    //Velocity data is dependent on if this is a particle system or a not
                    VelocityData myVelocityData;
                    VelocityData otherVelocityData;
                    if (isParticleSystem)
                    {
                        myVelocityData    = new VelocityData(particleCollisionEvent.velocity, Vector3.zero);
                        otherVelocityData = otherObject.GetVelocityDataAtPoint(particleCollisionEvent.intersection);
                    }
                    else
                    {
                        myVelocityData    = myObject.GetVelocityDataAtPoint(particleCollisionEvent.intersection);
                        otherVelocityData = new VelocityData(particleCollisionEvent.velocity, Vector3.zero);
                    }

                    Vector3 relativeContactPointVelocity = myVelocityData.TotalPointVelocity - otherVelocityData.TotalPointVelocity;

                    for (int i = 0; i < count; i++)
                    {
                        ImpactMaterialComposition comp = ImpactManagerInstance.MaterialCompositionBuffer[i];

                        if (comp.CompositionValue > 0)
                        {
                            InteractionData interactionData = new InteractionData()
                            {
                                TagMask          = comp.Material.MaterialTagsMask,
                                Point            = particleCollisionEvent.intersection,
                                Normal           = particleCollisionEvent.normal,
                                Velocity         = relativeContactPointVelocity,
                                InteractionType  = InteractionData.InteractionTypeCollision,
                                ThisObject       = this.gameObject,
                                OtherObject      = otherObject.GameObject,
                                CompositionValue = 1f
                            };

                            invokeTriggeredEvent(interactionData, myObject);

                            ImpactManagerInstance.ProcessInteraction(interactionData, myObject);
                        }
                    }
                }
                else
                {
                    //Velocity data is dependent on if this is a particle system or a not
                    VelocityData myVelocityData;
                    VelocityData otherVelocityData;
                    if (isParticleSystem)
                    {
                        myVelocityData    = new VelocityData(particleCollisionEvent.velocity, Vector3.zero);
                        otherVelocityData = hasOtherObject ? otherObject.GetVelocityDataAtPoint(particleCollisionEvent.intersection) : new VelocityData();
                    }
                    else
                    {
                        myVelocityData    = myObject.GetVelocityDataAtPoint(particleCollisionEvent.intersection);
                        otherVelocityData = new VelocityData(particleCollisionEvent.velocity, Vector3.zero);
                    }

                    Vector3 relativeContactPointVelocity = myVelocityData.TotalPointVelocity - otherVelocityData.TotalPointVelocity;

                    //Get physics material ID for material mapping, but only if this object is a particle system.
                    //Particles don't have a collider so no need to try and get the physics material if this is not a particle system
                    int           otherPhysicsMaterialID = isParticleSystem ? getPhysicsMaterialID(particleCollisionEvent.colliderComponent) : 0;
                    ImpactTagMask?tagMask = getOtherObjectTagMask(otherObject, particleCollisionEvent.intersection, otherPhysicsMaterialID, hasOtherObject);

                    InteractionData interactionData = new InteractionData()
                    {
                        TagMask          = tagMask,
                        Point            = particleCollisionEvent.intersection,
                        Normal           = particleCollisionEvent.normal,
                        Velocity         = relativeContactPointVelocity,
                        InteractionType  = InteractionData.InteractionTypeCollision,
                        ThisObject       = this.gameObject,
                        OtherObject      = particleCollisionEvent.colliderComponent.gameObject,
                        CompositionValue = 1f
                    };

                    invokeTriggeredEvent(interactionData, myObject);

                    ImpactManagerInstance.ProcessInteraction(interactionData, myObject);
                }
            }
            else
            {
                Debug.LogError("Unable to find Impact Object on GameObject " + gameObject.name);
            }
        }