public KinematicBody(double mass = 1, ColliderShape shape = null)
        {
            Elements = new List <IPhysicShape>();
            Forces   = new List <Force>();
            NetForce = new Vector3D(0, 0, 0);

            CenterOfMass    = new PhysicPoint(mass);
            CenterPosition  = new Point3D(0, 0, 0);
            AngularPosition = new Vector3D(0, 0, 0);

            PositionDisplacement = new Vector3D(0, 0, 0);
            AngularDisplacement  = new Vector3D(0, 0, 0);
            AngularRadVelocity   = new Vector3D(0, 0, 0);

            DisplacementList = new List <IDisplacement>();

            if (shape == null)
            {
                shape = new PointColliderShape();
            }

            this.Shape = shape;
            OnShapeChange();
            CalculateCenterOfMass();
        }
        internal void DeriveBonePhysicsTransformation(out Matrix derivedTransformation)
        {
            Quaternion rotation;
            Vector3    translation;

            //derive rotation and translation, scale is ignored for now
            Vector3 scale;

            BoneWorldMatrix.Decompose(out scale, out rotation, out translation);

            derivedTransformation = Matrix.RotationQuaternion(rotation) * Matrix.Translation(translation);

            //handle dynamic scaling if allowed (aka not using assets)
            if (CanScaleShape)
            {
                if (scale != ColliderShape.Scaling)
                {
                    ColliderShape.Scaling = scale;
                    ColliderShape.UpdateLocalTransformations();

                    if (DebugEntity != null)
                    {
                        DebugEntity.Transform.Scale = scale;
                    }
                }
            }

            //Handle collider shape offset
            if (ColliderShape.LocalOffset != Vector3.Zero || ColliderShape.LocalRotation != Quaternion.Identity)
            {
                derivedTransformation = Matrix.Multiply(ColliderShape.PositiveCenterMatrix, derivedTransformation);
            }
        }
Beispiel #3
0
        /// <summary>
        /// Checks if a static collider is dynamic shape
        /// </summary>
        /// <param name="collider">The collider to check</param>
        /// <returns><c>true</c> if the collider is dynamic shape, <c>false</c> otherwise</returns>
        public static bool IsDynamicShape(ColliderShape colliderShape)
        {
            if (colliderShape == null)
            {
                return(false);
            }

            if (colliderShape is HeightfieldColliderShape)
            {
                return(true);
            }
            else
            {
                if (colliderShape is CompoundColliderShape compound)
                {
                    for (int i = 0; i < compound.Count; ++i)
                    {
                        if (IsDynamicShape(compound[i]))
                        {
                            return(true);
                        }
                    }
                }
                return(false);
            }
        }
Beispiel #4
0
        private Material GetMaterial(EntityComponent component, ColliderShape shape)
        {
            var componentType = ComponentType.Trigger;

            var rigidbodyComponent = component as RigidbodyComponent;

            if (rigidbodyComponent != null)
            {
                componentType = rigidbodyComponent.IsTrigger ? ComponentType.Trigger :
                                rigidbodyComponent.IsKinematic ? ComponentType.Kinematic : ComponentType.Dynamic;
            }
            else if (component is CharacterComponent)
            {
                componentType = ComponentType.Character;
            }
            else if (component is StaticColliderComponent)
            {
                var staticCollider = (StaticColliderComponent)component;
                componentType = staticCollider.IsTrigger ? ComponentType.Trigger : ComponentType.Static;
            }

            if (shape is StaticPlaneColliderShape)
            {
                return(componentTypeStaticPlaneMaterial[componentType]);
            }
            else if (shape is HeightfieldColliderShape)
            {
                return(componentTypeHeightfieldMaterial[componentType]);
            }
            else
            {
                return(componentTypeDefaultMaterial[componentType]);
            }
        }
        internal void InternalColliderShapeReadd()
        {
            BepuSimulation bs = BepuSimulation.instance;

            // don't worry about switching if we are to be removed (or have been removed)
            if (InternalBody.Handle.Value == -1 || bs.ToBeRemoved.Contains(this))
            {
                return;
            }

            using (bs.simulationLocker.WriteLock())
            {
                // let's check handle again now that we are in the lock, just in case
                if (InternalBody.Handle.Value == -1)
                {
                    return;
                }

                // remove me with the old shape
                bs.internalSimulation.Bodies.Remove(InternalBody.Handle);
                BepuSimulation.RigidMappings.Remove(InternalBody.Handle.Value);

                // add me with the new shape
                bodyDescription.Collidable = ColliderShape.GenerateDescription(bs.internalSimulation, SpeculativeMargin);
                InternalBody.Handle        = bs.internalSimulation.Bodies.Add(bodyDescription);
                BepuSimulation.RigidMappings[InternalBody.Handle.Value] = this;
            }
        }
Beispiel #6
0
        public void ComposeShape()
        {
            ColliderShapeChanged = false;

            if (ColliderShape != null)
            {
                if (!ColliderShape.IsPartOfAsset)
                {
                    ColliderShape.Dispose();
                    ColliderShape = null;
                }
                else
                {
                    ColliderShape = null;
                }
            }

            CanScaleShape = true;

            if (ColliderShapes.Count == 1) //single shape case
            {
                if (ColliderShapes[0] == null)
                {
                    return;
                }
                if (ColliderShapes[0].GetType() == typeof(ColliderShapeAssetDesc))
                {
                    CanScaleShape = false;
                }

                ColliderShape = PhysicsColliderShape.CreateShape(ColliderShapes[0]);

                ColliderShape?.UpdateLocalTransformations();
            }
            else if (ColliderShapes.Count > 1) //need a compound shape in this case
            {
                var compound = new CompoundColliderShape();
                foreach (var desc in ColliderShapes)
                {
                    if (desc == null)
                    {
                        continue;
                    }
                    if (desc.GetType() == typeof(ColliderShapeAssetDesc))
                    {
                        CanScaleShape = false;
                    }

                    var subShape = PhysicsColliderShape.CreateShape(desc);
                    if (subShape != null)
                    {
                        compound.AddChildShape(subShape);
                    }
                }

                ColliderShape = compound;

                ColliderShape.UpdateLocalTransformations();
            }
        }
Beispiel #7
0
        public void ComposeShape()
        {
            ColliderShapeChanged = false;

            if (ColliderShape != null)
            {
                if (!ColliderShape.IsPartOfAsset)
                {
                    ColliderShape.Dispose();
                    ColliderShape = null;
                }
                else
                {
                    ColliderShape = null;
                }
            }

            CanScaleShape = true;

            if (ColliderShapes.Count == 1) // Single shape case
            {
                if (ColliderShapes[0] == null)
                {
                    return;
                }
                if (ColliderShapes[0].GetType() == typeof(BepuColliderShapeAssetDesc))
                {
                    CanScaleShape = false;
                }

                ColliderShape = BepuPhysicsColliderShape.CreateShape(ColliderShapes[0], Simulation.BufferPool);
            }
            else if (ColliderShapes.Count > 1) // Need a compound shape in this case
            {
                //var compound = new BepuCompoundColliderShape();
                //foreach (var desc in ColliderShapes)
                //{
                //    if (desc == null) continue;
                //    if (desc.GetType() == typeof(BepuColliderShapeAssetDesc))
                //    {
                //        CanScaleShape = false;
                //    }

                //    var subShape = BepuPhysicsColliderShape.CreateShape(desc);
                //    if (subShape != null)
                //    {
                //        compound.AddChildShape(subShape);
                //    }
                //}

                //ColliderShape = compound;
            }

            if (ColliderShape != null)
            {
                // Force update internal shape and gizmo scaling
                ColliderShape.Scaling = ColliderShape.Scaling;
            }
        }
Beispiel #8
0
 public ColliderProperties(BattleObject obj)
 {
     TriggerOnly = obj is Projectile;
     Shape       = obj.Settings.ColliderType;
     Mass        = obj.Settings.Mass;
     IsStatic    = obj.Settings.IsStatic;
     Size        = obj.Size;
 }
Beispiel #9
0
        public void ComposeShape()
        {
            ColliderShapeChanged = false;

            if (ColliderShape != null)
            {
                if (!ColliderShape.IsPartOfAsset)
                {
                    ColliderShape.Dispose();
                    ColliderShape = null;
                }
                else
                {
                    ColliderShape = null;
                }
            }

            CanScaleShape = true;
            foreach (var desc in ColliderShapes)
            {
                if (desc is ColliderShapeAssetDesc)
                {
                    CanScaleShape = false;
                }
            }

            var services = Entity?.EntityManager?.Services;

            if (ColliderShapes.Count == 1) //single shape case
            {
                ColliderShape = ColliderShapes[0]?.CreateShape(services);
            }
            else if (ColliderShapes.Count > 1) //need a compound shape in this case
            {
                var compound = new CompoundColliderShape();
                foreach (var desc in ColliderShapes)
                {
                    if (desc == null)
                    {
                        continue;
                    }

                    var subShape = desc.CreateShape(services);
                    if (subShape != null)
                    {
                        compound.AddChildShape(subShape);
                    }
                }

                ColliderShape = compound;
            }

            if (ColliderShape != null)
            {
                // Force update internal shape and gizmo scaling
                ColliderShape.Scaling = ColliderShape.Scaling;
            }
        }
Beispiel #10
0
            public PhysicsElementInfo(PhysicsColliderComponent component)
            {
                shape = component.ColliderShape;
                var rigidbodyComponent = component as RigidbodyComponent;

                isKinematic    = rigidbodyComponent != null && rigidbodyComponent.IsKinematic;
                colliderShapes = component.ColliderShapes != null?CloneDescs(component.ColliderShapes) : null;

                var triggerBase = component as StaticColliderComponent;

                isTrigger = triggerBase != null && triggerBase.GenerateOverlapEvents;
            }
Beispiel #11
0
        public Obstacle(Vector3[] data, ColliderShape shape)
        {
            Data = new Vector3[data.Length];
            Array.Copy(data, Data, data.Length);

            switch (shape)
            {
            case ColliderShape.Box:
                Collider = new Box(Data);
                break;

            case ColliderShape.Sphere:
                Collider = new Sphere(Data);
                break;
            }
        }
Beispiel #12
0
            public PhysicsElementInfo(PhysicsComponent component, SkeletonUpdater skeleton)
            {
                shape = component.ColliderShape;
                var rigidbodyComponent = component as RigidbodyComponent;

                isKinematic    = rigidbodyComponent != null && rigidbodyComponent.IsKinematic;
                colliderShapes = component.ColliderShapes != null?CloneDescs(component.ColliderShapes) : null;

                var componentBase = component as PhysicsSkinnedComponentBase;

                boneName      = componentBase?.NodeName;
                this.skeleton = skeleton;
                boneIndex     = componentBase?.BoneIndex ?? -1;
                var triggerBase = component as PhysicsTriggerComponentBase;

                isTrigger = triggerBase != null && triggerBase.IsTrigger;
            }
Beispiel #13
0
        internal void Detach()
        {
            Data = null;

            //this is mostly required for the game studio gizmos
            if (Simulation.DisableSimulation)
            {
                return;
            }

            // Actually call the detach
            OnDetach();

            if (ColliderShape != null && !ColliderShape.IsPartOfAsset)
            {
                ColliderShape.Dispose();
            }
        }
        private static XElement GetCollisionDataElement(string objectName, ColliderShape shapeType)
        {
            if (_collisionShapeData != null)
            {
                List <XElement> dataElements = (from el
                                                in _collisionShapeData.Elements("collisionshape")
                                                where (
                                                    ((string)el.Attribute("objectname") == objectName) &&
                                                    ((string)el.Attribute("type") == shapeType.ToString().ToLower()))
                                                select el).ToList();

                if (dataElements.Count > 0)
                {
                    return(dataElements[0]);
                }
            }

            return(null);
        }
Beispiel #15
0
        public override void Start()
        {
            //this.GetSimulation().ColliderShapesRendering = true;

            _simulation = this.GetSimulation();

            _collider = new SphereColliderShape(false, 0.2f);

            for (var i = 0; i < RayCount; i++)
            {
                // Offset Vector, from 0 to some place on a circle
                _offsets[i] = Vector3.Transform(
                    Vector3.UnitZ * Radius,
                    Quaternion.RotationY((i / (float)RayCount) * MathUtil.TwoPi)
                    );
            }

            //This code assumes that Y goes to the sky (instead of using the player's up vector)
            offsetMatrix = Matrix.Translation(0, -0.3f, 0);
        }
    private void OnGUI()
    {
        Rect box = new Rect(3, 3, position.width - 6, 20);

        minimumSize   = EditorGUI.Vector3Field(box, "Minimum Size", minimumSize);
        box.y        += 40;
        maximumSize   = EditorGUI.Vector3Field(box, "Maximum Size", maximumSize);
        box.y        += 40;
        colliderShape = (ColliderShape)EditorGUI.EnumPopup(box, "Shape of Collider", colliderShape);
        box.y        += 20;
        if (GUI.Button(box, "Resize Selected Objects") == true)
        {
            foreach (Transform selection in Selection.transforms)
            {
                if (selection != null)
                {
                    ResizeObject(selection);
                }
            }
        }
    }
Beispiel #17
0
    public static ColliderParam ColliderParamFactory(ColliderShape shape)
    {
        ColliderParam ret = null;

        if (shape == ColliderShape.Rect)
        {
            ret = CreateInstance <RectColliderParam>();
        }
        else if (shape == ColliderShape.Sphere)
        {
            ret = CreateInstance <SphereColliderParam>();
        }
        else if (shape == ColliderShape.Capsule)
        {
            ret = CreateInstance <CapsuleColliderParam>();
        }
        else
        {
            Debug.LogError("not implemented");
        }
        return(ret);
    }
Beispiel #18
0
        internal void Detach()
        {
            if (DoNotDispose)
            {
                Data = null;
            }

            //this is mostly required for the game studio gizmos
            if (Simulation.DisableSimulation)
            {
                return;
            }

            // Actually call the detach
            OnDetach();

            if (ColliderShape != null && !ColliderShape.DoNotDispose && !ColliderShape.DoNotDisposeAnyOnNextDetach)
            {
                ColliderShape.Dispose();
                ColliderShape = null;
            }
        }
Beispiel #19
0
        private Material GetMaterial(EntityComponent component, ColliderShape shape)
        {
            var componentType = ComponentType.Trigger;

            var rigidbodyComponent = component as RigidbodyComponent;

            if (rigidbodyComponent != null)
            {
                componentType = rigidbodyComponent.IsKinematic ? ComponentType.Kinematic : ComponentType.Dynamic;
            }
            else if (component is CharacterControllerComponent)
            {
                componentType = ComponentType.Character;
            }
            else if (component is StaticColliderComponent)
            {
                var staticCollider = (StaticColliderComponent)component;
                componentType = staticCollider.GenerateOverlapEvents ? ComponentType.Trigger : ComponentType.Static;
            }

            return(componentTypeDefaultMaterial[componentType]);
        }
Beispiel #20
0
        internal void Detach()
        {
            if (!DoNotDispose)
            {
                Data = null;
            }

            //this is mostly required for the game studio gizmos
            if (Simulation.DisableSimulation)
            {
                return;
            }

            // Actually call the detach
            OnDetach();

            if (ColliderShape != null && !ColliderShape.DoNotDispose && !Xenko.Engine.SceneSystem.physicsDoNotDisposeNextRemoval)
            {
                ColliderShape.Dispose();
                ColliderShape = null;
            }
        }
        private static XElement GetCollisionDataElement(string objectName, ColliderShape shapeType)
        {
            if (_collisionShapeData != null)
            {
                List<XElement> dataElements = (from el
                    in _collisionShapeData.Elements("collisionshape")
                    where (
                        ((string)el.Attribute("objectname") == objectName) &&
                        ((string)el.Attribute("type") == shapeType.ToString().ToLower()))
                    select el).ToList();

                if (dataElements.Count > 0) { return dataElements[0]; }
            }

            return null;
        }
Beispiel #22
0
        private Entity CreateChildEntity(PhysicsComponent component, ColliderShape shape, RenderGroup renderGroup, bool addOffset)
        {
            if (shape == null)
            {
                return(null);
            }

            switch (shape)
            {
            case BoxColliderShape _:
            case ConvexHullColliderShape _:
            case SphereColliderShape _:
            case CylinderColliderShape _:
            case CapsuleColliderShape _:
            case MeshColliderShape _:
            {
                IDebugPrimitive debugPrimitive;
                var             shapeType = shape.GetType();
                if (shapeType == typeof(CapsuleColliderShape) || shapeType == typeof(ConvexHullColliderShape) || shapeType == typeof(MeshColliderShape))
                {
                    if (!debugMeshCache2.TryGetValue(shape, out debugPrimitive))
                    {
                        debugPrimitive = new DebugPrimitive {
                            shape.CreateDebugPrimitive(graphicsDevice)
                        };
                        debugMeshCache2[shape] = debugPrimitive;
                    }
                }
                else
                {
                    if (!debugMeshCache.TryGetValue(shape.GetType(), out debugPrimitive))
                    {
                        debugPrimitive = new DebugPrimitive {
                            shape.CreateDebugPrimitive(graphicsDevice)
                        };
                        debugMeshCache[shape.GetType()] = debugPrimitive;
                    }
                }

                var model = new Model
                {
                    GetMaterial(component, shape),
                };
                foreach (var meshDraw in debugPrimitive.GetMeshDraws())
                {
                    model.Add(new Mesh {
                            Draw = meshDraw
                        });
                }

                var entity = new Entity
                {
                    new ModelComponent
                    {
                        Model       = model,
                        RenderGroup = renderGroup,
                    },
                };

                var offset = addOffset ? Matrix.RotationQuaternion(shape.LocalRotation) * Matrix.Translation(shape.LocalOffset) : Matrix.Identity;

                entity.Transform.LocalMatrix = shape.DebugPrimitiveMatrix * offset * Matrix.Scaling(shape.Scaling);

                entity.Transform.UseTRS = false;

                shape.DebugEntity = entity;

                return(entity);
            }

            default:
                return(null);
            }
        }
Beispiel #23
0
        /// <summary>
        /// Creates a ring-shaped compound collider game object.
        /// </summary>
        public static GameObject CreateRing(PivotAxis pivotAxis, int sides, float outerRadius, float innerRadius,
                                            ColliderShape colliderShape, float height, float rotationOffset, bool hasEndCap)
        {
            // Empty game object that will serve as the root of the compound collider "prefab"
            var compoundCollider = new GameObject("Ring Compound Collider");

            float length = 2 * outerRadius * Mathf.Tan(Mathf.PI / sides);       // Length follows the flow of the ring of the torus
            float width  = outerRadius - innerRadius;

            if (colliderShape.Equals(ColliderShape.Capsule))
            {
                // Capsule length needs to be adjusted to factor in spherical caps
                length = (length / outerRadius * ((outerRadius + innerRadius) / 2)) + (width);
            }

            for (int i = 0; i < sides; i++)
            {
                // Create the new collider object
                GameObject segment = null;

                if (colliderShape.Equals(ColliderShape.Box))
                {
                    segment = GameObject.CreatePrimitive(PrimitiveType.Cube);
                    segment.transform.localScale = new Vector3(length, height, width);           // Set scale
                    segment.transform.Rotate(Vector3.right, rotationOffset);                     // Apply lengthwise rotation

                    // Set the renderer material on the segment object
                    segment.GetComponent <Renderer>().material = colliderMaterial;
                }
                else if (colliderShape.Equals(ColliderShape.Capsule))
                {
                    // Create segment game object and set its position
                    segment = new GameObject("Capsule");

                    // Add CapsuleCollider component
                    var capsuleCollider = segment.AddComponent <CapsuleCollider>();

                    // Turn capsule so it lies length-wise along the X-axis
                    capsuleCollider.direction = 0;

                    capsuleCollider.height = length;
                    capsuleCollider.radius = width / 2;
                }

                float segmentAngleDegrees = i * (360f / sides);

                // Position the segment relative to its parent
                segment.transform.position = new Vector3(0f, 0f, outerRadius - (width / 2));
                segment.transform.RotateAround(Vector3.zero, Vector3.up, segmentAngleDegrees);

                // Rotate to matcb pivot axis
                if (pivotAxis != PivotAxis.Y)                 // We do Y by default so skip this step if Y
                {
                    Vector3 rotationAxis = (pivotAxis == PivotAxis.Z) ? Vector3.right : Vector3.forward;
                    segment.transform.RotateAround(Vector3.zero, rotationAxis, 90f);
                }

                // Set the segment parent to the compound collider GameObject
                segment.transform.SetParent(compoundCollider.transform, true);
            }

            // Add the cap if enabled
            if (hasEndCap)
            {
                var capObject = CreateCylinderPrimitive(sides, outerRadius, width);

                // Position the cap on the bottom of the tube
                capObject.transform.position = new Vector3(0f, -((height / 2) + width / 2), 0f);

                // Set the cap's parent to the compound collider GameObject
                capObject.transform.SetParent(compoundCollider.transform, true);

                // Set the renderer material on the segment object
                capObject.GetComponent <Renderer>().material = colliderMaterial;
            }

            // Register undo event for creation of compound collider
            Undo.RegisterCreatedObjectUndo(compoundCollider, "Create Torus Compound Collider");

            return(compoundCollider);
        }
Beispiel #24
0
        private Entity CreateChildEntity(PhysicsComponent component, ColliderShape shape, bool addOffset)
        {
            if (shape == null)
            {
                return(null);
            }

            switch (shape.Type)
            {
            case ColliderShapeTypes.Compound:
            {
                var entity = new Entity();

                //We got to recurse
                var compound = (CompoundColliderShape)shape;
                for (var i = 0; i < compound.Count; i++)
                {
                    var subShape  = compound[i];
                    var subEntity = CreateChildEntity(component, subShape, true);         //always add offsets to compounds
                    if (subEntity != null)
                    {
                        entity.AddChild(subEntity);
                    }
                }

                entity.Transform.LocalMatrix = Matrix.Identity;
                entity.Transform.UseTRS      = false;

                compound.DebugEntity = entity;

                return(entity);
            }

            case ColliderShapeTypes.Box:
            case ColliderShapeTypes.Capsule:
            case ColliderShapeTypes.ConvexHull:
            case ColliderShapeTypes.Cylinder:
            case ColliderShapeTypes.Sphere:
            case ColliderShapeTypes.Cone:
            {
                var mat = triggerMaterial;

                var rigidbodyComponent = component as RigidbodyComponent;
                if (rigidbodyComponent != null)
                {
                    mat = rigidbodyComponent.IsKinematic ? kinematicMaterial : dynamicMaterial;
                    mat = rigidbodyComponent.IsTrigger ? triggerMaterial : mat;
                }
                else if (component is CharacterComponent)
                {
                    mat = characterMaterial;
                }
                else if (component is StaticColliderComponent)
                {
                    var staticCollider = (StaticColliderComponent)component;
                    mat = staticCollider.IsTrigger ? triggerMaterial : staticMaterial;
                }

                MeshDraw draw;
                var      type = shape.GetType();
                if (type == typeof(CapsuleColliderShape) || type == typeof(ConvexHullColliderShape))
                {
                    if (!debugMeshCache2.TryGetValue(shape, out draw))
                    {
                        draw = shape.CreateDebugPrimitive(graphicsDevice);
                        debugMeshCache2[shape] = draw;
                    }
                }
                else
                {
                    if (!debugMeshCache.TryGetValue(shape.GetType(), out draw))
                    {
                        draw = shape.CreateDebugPrimitive(graphicsDevice);
                        debugMeshCache[shape.GetType()] = draw;
                    }
                }

                var entity = new Entity
                {
                    new ModelComponent
                    {
                        Model = new Model
                        {
                            mat,
                            new Mesh
                            {
                                Draw = draw
                            }
                        }
                    }
                };

                var offset = addOffset ? Matrix.RotationQuaternion(shape.LocalRotation) * Matrix.Translation(shape.LocalOffset) : Matrix.Identity;

                entity.Transform.LocalMatrix = shape.DebugPrimitiveMatrix * offset * Matrix.Scaling(shape.Scaling);

                entity.Transform.UseTRS = false;

                shape.DebugEntity = entity;

                return(entity);
            }

            default:
                return(null);
            }
        }
        private Entity CreateChildEntity(PhysicsComponent component, ColliderShape shape, bool addOffset)
        {
            if (shape == null)
                return null;

            switch (shape.Type)
            {
                case ColliderShapeTypes.Compound:
                    {
                        var entity = new Entity();

                        //We got to recurse
                        var compound = (CompoundColliderShape)shape;
                        for (var i = 0; i < compound.Count; i++)
                        {
                            var subShape = compound[i];
                            var subEntity = CreateChildEntity(component, subShape, true); //always add offsets to compounds
                            if (subEntity != null)
                            {
                                entity.AddChild(subEntity);
                            }
                        }

                        entity.Transform.LocalMatrix = Matrix.Identity;
                        entity.Transform.UseTRS = false;

                        compound.DebugEntity = entity;

                        return entity;
                    }
                case ColliderShapeTypes.Box:
                case ColliderShapeTypes.Capsule:
                case ColliderShapeTypes.ConvexHull:
                case ColliderShapeTypes.Cylinder:
                case ColliderShapeTypes.Sphere:
                case ColliderShapeTypes.Cone:
                    {
                        var mat = triggerMaterial;

                        var rigidbodyComponent = component as RigidbodyComponent;
                        if (rigidbodyComponent != null)
                        {
                            mat = rigidbodyComponent.IsKinematic ? kinematicMaterial : dynamicMaterial;
                            mat = rigidbodyComponent.IsTrigger ? triggerMaterial : mat;
                        }
                        else if (component is CharacterComponent)
                        {
                            mat = characterMaterial;
                        }
                        else if (component is StaticColliderComponent)
                        {
                            var staticCollider = (StaticColliderComponent)component;
                            mat = staticCollider.IsTrigger ? triggerMaterial : staticMaterial;
                        }

                        MeshDraw draw;
                        var type = shape.GetType();
                        if (type == typeof(CapsuleColliderShape) || type == typeof(ConvexHullColliderShape))
                        {
                            if (!debugMeshCache2.TryGetValue(shape, out draw))
                            {
                                draw = shape.CreateDebugPrimitive(graphicsDevice);
                                debugMeshCache2[shape] = draw;
                            }
                        }
                        else
                        {
                            if (!debugMeshCache.TryGetValue(shape.GetType(), out draw))
                            {
                                draw = shape.CreateDebugPrimitive(graphicsDevice);
                                debugMeshCache[shape.GetType()] = draw;
                            }
                        }

                        var entity = new Entity
                        {
                            new ModelComponent
                            {
                                Model = new Model
                                {
                                    mat,
                                    new Mesh
                                    {
                                        Draw = draw
                                    }
                                }
                            }
                        };

                        var offset = addOffset ? Matrix.RotationQuaternion(shape.LocalRotation) * Matrix.Translation(shape.LocalOffset) : Matrix.Identity;

                        entity.Transform.LocalMatrix = shape.DebugPrimitiveMatrix * offset * Matrix.Scaling(shape.Scaling);

                        entity.Transform.UseTRS = false;

                        shape.DebugEntity = entity;

                        return entity;
                    }
                default:
                    return null;
            }
        }
Beispiel #26
0
 public override void Start()
 {
     _initialScale  = Entity.Transform.Scale;
     _colliderShape = Entity.Get <PhysicsComponent>().ColliderShape;
 }
Beispiel #27
0
        private Entity CreateChildEntity(PhysicsComponent component, ColliderShape shape, RenderGroup renderGroup, bool addOffset)
        {
            if (shape == null)
            {
                return(null);
            }

            switch (shape.Type)
            {
            case ColliderShapeTypes.Compound:
            {
                var entity = new Entity();

                //We got to recurse
                var compound = (CompoundColliderShape)shape;
                for (var i = 0; i < compound.Count; i++)
                {
                    var subShape  = compound[i];
                    var subEntity = CreateChildEntity(component, subShape, renderGroup, true);         //always add offsets to compounds
                    if (subEntity != null)
                    {
                        entity.AddChild(subEntity);
                    }
                }

                entity.Transform.LocalMatrix = Matrix.Identity;
                entity.Transform.UseTRS      = false;

                compound.DebugEntity = entity;

                return(entity);
            }

            case ColliderShapeTypes.Box:
            case ColliderShapeTypes.Capsule:
            case ColliderShapeTypes.ConvexHull:
            case ColliderShapeTypes.Cylinder:
            case ColliderShapeTypes.Sphere:
            case ColliderShapeTypes.Cone:
            case ColliderShapeTypes.StaticPlane:
            case ColliderShapeTypes.StaticMesh:
            case ColliderShapeTypes.Heightfield:
            {
                IDebugPrimitive debugPrimitive;
                var             type = shape.GetType();
                if (type == typeof(HeightfieldColliderShape) || type.BaseType == typeof(HeightfieldColliderShape))
                {
                    if (!updatableDebugMeshCache.TryGetValue(shape, out debugPrimitive))
                    {
                        debugPrimitive = shape.CreateUpdatableDebugPrimitive(graphicsDevice);
                        updatableDebugMeshCache[shape] = debugPrimitive;
                    }
                    if (!updatableDebugMeshes.ContainsKey(shape))
                    {
                        updatableDebugMeshes.Add(shape, debugPrimitive);
                    }
                }
                else if (type == typeof(CapsuleColliderShape) || type == typeof(ConvexHullColliderShape) || type == typeof(StaticMeshColliderShape))
                {
                    if (!debugMeshCache2.TryGetValue(shape, out debugPrimitive))
                    {
                        debugPrimitive = new DebugPrimitive {
                            shape.CreateDebugPrimitive(graphicsDevice)
                        };
                        debugMeshCache2[shape] = debugPrimitive;
                    }
                }
                else
                {
                    if (!debugMeshCache.TryGetValue(shape.GetType(), out debugPrimitive))
                    {
                        debugPrimitive = new DebugPrimitive {
                            shape.CreateDebugPrimitive(graphicsDevice)
                        };
                        debugMeshCache[shape.GetType()] = debugPrimitive;
                    }
                }

                var model = new Model
                {
                    GetMaterial(component, shape),
                };
                foreach (var meshDraw in debugPrimitive.GetMeshDraws())
                {
                    model.Add(new Mesh {
                            Draw = meshDraw
                        });
                }

                var entity = new Entity
                {
                    new ModelComponent
                    {
                        Model       = model,
                        RenderGroup = renderGroup,
                    },
                };

                var offset = addOffset ? Matrix.RotationQuaternion(shape.LocalRotation) * Matrix.Translation(shape.LocalOffset) : Matrix.Identity;

                entity.Transform.LocalMatrix = shape.DebugPrimitiveMatrix * offset * Matrix.Scaling(shape.Scaling);

                entity.Transform.UseTRS = false;

                shape.DebugEntity = entity;

                return(entity);
            }

            default:
                return(null);
            }
        }
Beispiel #28
0
        public void ComposeShape()
        {
            ColliderShapeChanged = false;

            if (ColliderShape != null)
            {
                if (!ColliderShape.DoNotDispose && !SceneSystem.physicsDoNotDisposeNextRemoval)
                {
                    ColliderShape.Dispose();
                    ColliderShape = null;
                }
                else
                {
                    ColliderShape = null;
                }
            }

            CanScaleShape = true;

            if (ColliderShapes.Count == 1) //single shape case
            {
                if (ColliderShapes[0] == null)
                {
                    return;
                }
                if (ColliderShapes[0].GetType() == typeof(ColliderShapeAssetDesc))
                {
                    CanScaleShape = false;
                }

                ColliderShape = PhysicsColliderShape.CreateShape(ColliderShapes[0]);
            }
            else if (ColliderShapes.Count > 1) //need a compound shape in this case
            {
                var compound = new CompoundColliderShape();
                foreach (var desc in ColliderShapes)
                {
                    if (desc == null)
                    {
                        continue;
                    }
                    if (desc.GetType() == typeof(ColliderShapeAssetDesc))
                    {
                        CanScaleShape = false;
                    }

                    var subShape = PhysicsColliderShape.CreateShape(desc);
                    if (subShape != null)
                    {
                        compound.AddChildShape(subShape);
                    }
                }

                ColliderShape = compound;
            }

            if (ColliderShape != null)
            {
                // Force update internal shape and gizmo scaling
                ColliderShape.Scaling = ColliderShape.Scaling;
            }
        }
Beispiel #29
0
        void DrawRingGUI()
        {
            // Store distance of inner from outer radius to lock distance if enabled
            var radiusDiff = outerRadius - innerRadius;

            GUILayout.Label("Ring", EditorStyles.boldLabel);
            pivotAxis   = (PivotAxis)EditorGUILayout.EnumPopup("Pivot Axis", pivotAxis);
            segments    = EditorGUILayout.IntSlider("Sides", segments, 3, 64);
            outerRadius = Mathf.Max(EditorGUILayout.FloatField("Outer Radius", outerRadius), 0.011f);             // 0.011-Infinity

            EditorGUILayout.BeginHorizontal();
            if (lockInnerRadiusToOuter)
            {
                GUI.enabled = false;
            }
            innerRadius = Mathf.Clamp(EditorGUILayout.FloatField("Inner Radius", innerRadius), 0.01f, outerRadius - 0.01f);             // 0.01-(outerRadius - 0.01)
            GUI.enabled = true;

            lockInnerRadiusToOuter =
                GUILayout.Toggle(lockInnerRadiusToOuter,
                                 new GUIContent("Lock", "Locks inner radius value to current distance from outer radius."),
                                 "Button",
                                 GUILayout.MaxWidth(50f));

            EditorGUILayout.EndHorizontal();

            // Lock innerRadius to current distance from outerRadius
            if (lockInnerRadiusToOuter)
            {
                innerRadius = Mathf.Max(0.1f, outerRadius - radiusDiff);
            }

            colliderShape =
                (ColliderShape)
                EditorGUILayout.EnumPopup(new GUIContent("Collider Shape", "Sets the shape of the sub-collider objects."),
                                          colliderShape);

            // Options for box collider only
            if (colliderShape == ColliderShape.Box)
            {
                EditorGUILayout.Separator();

                matchHeightToWidth =
                    EditorGUILayout.Toggle(
                        new GUIContent("Match Height to Width", "Lock height to Outer Radius minus Inner Radius."), matchHeightToWidth);
                if (matchHeightToWidth)
                {
                    GUI.enabled = false;
                }
                height      = Mathf.Max(EditorGUILayout.FloatField("Height", height), 0.01f);            // 0.01-Infinity
                GUI.enabled = true;

                hasEndCap =
                    EditorGUILayout.Toggle(
                        new GUIContent("Cap Bottom", "Adds a cylindrical cap to the bottom end of the ring, creating a barrel shape."),
                        hasEndCap);

                EditorGUILayout.Separator();

                rotationOffset =
                    EditorGUILayout.Slider(
                        new GUIContent("Rotation", "Apply rotation to sub-colliders around their length-wise axis."), rotationOffset, 0f, 360f);
            }
        }