Exemple #1
0
        /// <summary>
        /// Computes the new (desired) hand position considering the offset of the collider (to avoid self-collisions)
        /// </summary>
        /// <param name="targetHandPosition"></param>
        /// <param name="currentPosture"></param>
        /// <returns></returns>
        private MVector3 ComputeNewPositionWithOffset(MVector3 targetHandPosition, MAvatarPostureValues currentPosture)
        {
            //Optionally ensure that the object does not intersect the avatar
            MCollider collider = this.SceneAccess.GetColliderById(this.objectTransform.ID);

            //Determine the offset based on the respective collider
            float offset = 0;

            if (collider.SphereColliderProperties != null)
            {
                offset = (float)collider.SphereColliderProperties.Radius;
            }

            if (collider.BoxColliderProperties != null)
            {
                offset = (float)collider.BoxColliderProperties.Size.Magnitude();
            }

            if (collider.CapsuleColliderProperties != null)
            {
                offset = Math.Max((float)collider.CapsuleColliderProperties.Height, (float)collider.CapsuleColliderProperties.Radius);
            }

            //The offset could be also dynamically determined (using the mesh intersection distance or using Physics Compute Pentration in unity)

            this.SkeletonAccess.SetChannelData(currentPosture);

            //Get the shoulder positions
            MVector3 leftShoulderPosition  = this.SkeletonAccess.GetGlobalJointPosition(this.AvatarDescription.AvatarID, MJointType.LeftShoulder);
            MVector3 rightShoulderPosition = this.SkeletonAccess.GetGlobalJointPosition(this.AvatarDescription.AvatarID, MJointType.RightShoulder);

            //Compute the direction vector pointing from the avatar towards the respective hand
            MVector3 dir = new MVector3(0, 0, 0);

            switch (this.handJoint)
            {
            case MJointType.LeftWrist:
                dir = leftShoulderPosition.Subtract(rightShoulderPosition).Normalize();
                break;

            case MJointType.RightWrist:
                dir = rightShoulderPosition.Subtract(leftShoulderPosition).Normalize();
                break;
            }

            //Add an offset on top of the position
            return(targetHandPosition.Add(dir.Multiply(offset)));
        }
        /// <summary>
        /// Sets up the collider of the MSceneObject
        /// </summary>
        private void SetupCollider()
        {
            try
            {
                //Set the collider (if defined)
                if (this.GetComponent <Collider>() != null)
                {
                    //Create a new MCollider instance
                    MCollider mCollider = new MCollider()
                    {
                        ID = this.MSceneObject.ID
                    };

                    //Get the collider instance
                    Collider collider = this.GetComponent <Collider>();


                    //Check if collider is a box collider and create corresponding representation in MMI framework
                    if (collider is BoxCollider)
                    {
                        mCollider.Type = MColliderType.Box;
                        BoxCollider boxCollider = collider as BoxCollider;

                        //Set the specific box collider properties
                        mCollider.BoxColliderProperties = new MBoxColliderProperties
                        {
                            //Calculate the size by consdering the scaling
                            Size = new MVector3(boxCollider.size.x * this.transform.localScale.x, boxCollider.size.y * this.transform.localScale.y, boxCollider.size.z * this.transform.localScale.z)
                        };
                        mCollider.PositionOffset = new MVector3(boxCollider.center.x * this.transform.localScale.x, boxCollider.center.y * this.transform.localScale.y, boxCollider.center.z * this.transform.localScale.z);
                    }

                    //Check if collider is a sphere collider and create corresponding representation in MMI framework
                    if (collider is SphereCollider)
                    {
                        mCollider.Type = MColliderType.Sphere;
                        SphereCollider sphereCollider = collider as SphereCollider;

                        //Set the specific sphere collider properties
                        mCollider.SphereColliderProperties = new MSphereColliderProperties
                        {
                            Radius = sphereCollider.radius * Mathf.Max(this.transform.localScale.x, this.transform.localScale.y, this.transform.localScale.z)
                        };
                        mCollider.PositionOffset = new MVector3(sphereCollider.center.x * this.transform.localScale.x, sphereCollider.center.y * this.transform.localScale.y, sphereCollider.center.z * this.transform.localScale.z);
                    }

                    //Check if collider is a capsule collider and create corresponding representation in MMI framework
                    if (collider is CapsuleCollider)
                    {
                        mCollider.Type = MColliderType.Capsule;
                        CapsuleCollider capsuleCollider = collider as CapsuleCollider;


                        //Set the specific capsule collider properties
                        mCollider.CapsuleColliderProperties = new MCapsuleColliderProperties
                        {
                            Radius = capsuleCollider.radius * Mathf.Max(this.transform.localScale.x, this.transform.localScale.z),
                            Height = capsuleCollider.height * this.transform.localScale.y,
                        };

                        //Set the position offset
                        mCollider.PositionOffset = new MVector3(capsuleCollider.center.x * this.transform.localScale.x, capsuleCollider.center.y * this.transform.localScale.y, capsuleCollider.center.z * this.transform.localScale.z);
                    }

                    //Check if collider is a mesh collider and create corresponding representation in MMI framework
                    if (collider is MeshCollider)
                    {
                        mCollider.Type = MColliderType.Mesh;
                        MeshCollider meshCollider = collider as MeshCollider;
                        mCollider.MeshColliderProperties           = new MMeshColliderProperties();
                        mCollider.MeshColliderProperties.Vertices  = meshCollider.sharedMesh.vertices.Select(s => s.ToMVector3()).ToList();
                        mCollider.MeshColliderProperties.Triangles = meshCollider.sharedMesh.triangles.ToList();

                        //To do provide further option to just consider the bounds as approximation of the mesh collider
                    }

                    //Assign the collider
                    this.MSceneObject.Collider = mCollider;
                }
            }
            catch (System.Exception e)
            {
                Debug.LogError("Problem setting up the collider: " + e.Message + " " + e.StackTrace);
            }
        }
        /// <summary>
        /// Creates a Unity collider based on the MCollider and a transform
        /// </summary>
        /// <param name="collider"></param>
        /// <param name="transform"></param>
        /// <returns></returns>
        public static Collider CreateCollider(MCollider collider, MTransform transform)
        {
            if (collider == null || transform == null)
            {
                return(null);
            }

            GameObject result = null;

            switch (collider.Type)
            {
            case MColliderType.Box:
                MBoxColliderProperties mboxCollider = collider.BoxColliderProperties;

                if (mboxCollider == null)
                {
                    Debug.Log("Box collider is null");
                    return(null);
                }

                GameObject boxGameObject = GameObject.CreatePrimitive(PrimitiveType.Cube);
                boxGameObject.transform.position = transform.Position.ToVector3();
                boxGameObject.transform.rotation = transform.Rotation.ToQuaternion();

                //Assign the properties of the collider
                BoxCollider boxCollider = boxGameObject.GetComponent <BoxCollider>();
                boxCollider.center = collider.PositionOffset.ToVector3();
                boxCollider.size   = mboxCollider.Size.ToVector3();

                result = boxGameObject;
                break;

            case MColliderType.Sphere:
                MSphereColliderProperties mSphereCollider = collider.SphereColliderProperties;

                if (mSphereCollider == null)
                {
                    Debug.Log("Sphere collider is null");
                    return(null);
                }

                GameObject sphereGameObject = GameObject.CreatePrimitive(PrimitiveType.Sphere);
                sphereGameObject.transform.position = transform.Position.ToVector3();
                sphereGameObject.transform.rotation = transform.Rotation.ToQuaternion();

                SphereCollider sphereCollider = sphereGameObject.GetComponent <SphereCollider>();
                sphereCollider.center = collider.PositionOffset.ToVector3();
                sphereCollider.radius = (float)mSphereCollider.Radius;

                result = sphereGameObject;
                break;

            case MColliderType.Capsule:
                MCapsuleColliderProperties mCapsuleCollider = collider.CapsuleColliderProperties;

                if (mCapsuleCollider == null)
                {
                    Debug.Log("Capsule collider is null");
                    return(null);
                }

                GameObject capsule = GameObject.CreatePrimitive(PrimitiveType.Capsule);
                capsule.transform.position = transform.Position.ToVector3();
                capsule.transform.rotation = transform.Rotation.ToQuaternion();

                CapsuleCollider capsuleCollider = capsule.GetComponent <CapsuleCollider>();
                capsuleCollider.center = collider.PositionOffset.ToVector3();
                capsuleCollider.radius = (float)mCapsuleCollider.Radius;
                capsuleCollider.height = (float)mCapsuleCollider.Height;

                result = capsule;

                break;

            case MColliderType.Mesh:

                MMeshColliderProperties mMeshCollider = collider.MeshColliderProperties;

                if (mMeshCollider == null)
                {
                    Debug.Log("Mesh collider is null");
                    return(null);
                }



                //To do
                break;
            }

            return(result.GetComponent <Collider>());
        }