예제 #1
0
 public static bool RayCast(Vector3 _origin, Vector3 _direction, float _distance, TxBody _skip, out TxBody _body, out Vector3 _point, out Vector3 _normal, out int _face)
 {
     if (sm_world != null)
     {
         return(sm_world.RayCast(_origin, _direction, _distance, _skip, out _body, out _point, out _normal, out _face));
     }
     _body = null; _point = Vector3.zero; _normal = Vector3.zero; _face = -1;
     return(false);
 }
예제 #2
0
    void GroupCollisionUI(TxBody _rootBody)
    {
        string[]          groupLayers  = _rootBody.groupLayers;
        List <GUIContent> layerNames   = new List <GUIContent>();
        List <int>        layerIndices = new List <int>();
        GUIStyle          lableStyle   = EditorStyles.label;
        float             maxLength    = 0;

        for (int i = 0; i < groupLayers.Length; ++i)
        {
            string layerName = groupLayers[i];
            if (layerName != string.Empty)
            {
                layerNames.Add(new GUIContent(layerName));
                layerIndices.Add(i);
                maxLength = Mathf.Max(maxLength, lableStyle.CalcSize(new GUIContent(layerName)).x);
            }
        }
        int num = layerNames.Count;

        sm_showCollision = EditorGUILayout.Foldout(sm_showCollision, "Collision");
        if (sm_showCollision)
        {
            Rect rect = GUILayoutUtility.GetRect(EditorGUIUtility.labelWidth, maxLength);
            for (int j = 0; j < num; j++)
            {
                Vector3 pos = new Vector3(EditorGUIUtility.labelWidth + (num - j + 1) * 15f - 1f, rect.y - 9f, 0f);
                GUI.matrix = Matrix4x4.identity;
                GUIUtility.RotateAroundPivot(90.0f, pos);
                if (SystemInfo.graphicsDeviceVersion.StartsWith("Direct3D 9.0"))
                {
                    GUI.matrix *= Matrix4x4.TRS(new Vector3(-0.5f, -0.5f, 0f), Quaternion.identity, Vector3.one);
                }
                GUI.Label(new Rect(pos.x, pos.y, maxLength, 15f), layerNames[j], "RightLabel");
            }
            GUI.matrix = Matrix4x4.identity;
            for (int k = 0; k < num; k++)
            {
                GUILayoutUtility.GetRect((float)(30 + 15 * num + 100), 15f);
                GUI.Label(new Rect(15f, rect.y + maxLength + k * 15f - 10f, EditorGUIUtility.labelWidth, 15f), layerNames[k], "RightLabel");
                for (int l = k; l < num; l++)
                {
                    GUIContent         content = new GUIContent(string.Empty, layerNames[k].text + "/" + layerNames[l].text);
                    int                ki = layerIndices[k], li = layerIndices[l];
                    int                index     = ki * 8 - ki * (ki + 1) / 2 + li;
                    SerializedProperty collision = groupCollision.GetArrayElementAtIndex(index);
                    bool               flag      = collision.boolValue;
                    bool               flag2     = GUI.Toggle(new Rect(EditorGUIUtility.labelWidth + (num - l) * 15f, rect.y + maxLength + k * 15f - 10f, 15f, 15f), flag, content);
                    if (flag2 != flag)
                    {
                        collision.boolValue = flag2;
                    }
                }
            }
        }
    }
예제 #3
0
    protected override void RegisterDependencies()
    {
        TxBody parentBody = FindParentBody();

        if (parentBody)
        {
            AddDependency(parentBody);
        }
        base.RegisterDependencies();
    }
예제 #4
0
 public bool RayCast(Vector3 _origin, Vector3 _direction, float _distance, TxBody _skip, out TxBody _body, out Vector3 _point, out Vector3 _normal, out int _face)
 {
     _body = null; int hitObjectID = -1; _point = Vector3.zero; _normal = Vector3.zero; _face = -1;
     if (TxNative.WorldRayCast(m_worldID, _origin, _direction, _distance, _skip ?_skip.objectID : -1, ref hitObjectID, ref _point, ref _normal, ref _face))
     {
         _body = TxBody.Find(hitObjectID);
         return(true);
     }
     return(false);
 }
예제 #5
0
 int InSameGroup(ref TxBody _rootBody)
 {
     foreach (var b in m_targets)
     {
         int inGroup = InGroup(b, ref _rootBody);
         if (inGroup != 1)
         {
             return(inGroup);
         }
     }
     return(1);
 }
예제 #6
0
    protected void CreateBody()
    {
        m_worldID = TxWorld.instance.worldID;
        if (!TxNative.WorldObjectExists(m_worldID, m_objectID))
        {
            m_objectID = TxNative.WorldCreateObject(m_worldID, transform.localToWorldMatrix);

            sm_bodies.Add(m_objectID, this);

            TxNative.WorldObjectSetEnabled(m_worldID, m_objectID, m_spawnEnabled);

            if (m_groupRoot)
            {
                m_groupID = TxNative.WorldCreateGroup(m_worldID);
                TxNative.WorldObjectSetGroup(m_worldID, m_objectID, m_groupID);
                for (int i = 0; i < 8; ++i)
                {
                    for (int j = i; j < 8; ++j)
                    {
                        int  index = i * 8 - i * (i + 1) / 2 + j;
                        bool yes   = m_groupCollision[index];
                        TxNative.WorldGroupSetColliding(m_worldID, m_groupID, i, j, yes);
                    }
                }
            }
            else
            {
                m_groupID = -1;
                Transform parent = transform;
                while (parent != null)
                {
                    TxBody parentBody = parent.GetComponent <TxBody>();
                    if (parentBody != null && parentBody.groupRoot)
                    {
                        if (!parentBody.isValid)
                        {
                            parentBody.Create();
                        }
                        m_groupID = parentBody.groupID;
                        break;
                    }
                    parent = parent.parent;
                }
                TxNative.WorldObjectSetGroup(m_worldID, m_objectID, m_groupID);
            }

            TxNative.WorldObjectSetWorldLayer(m_worldID, m_objectID, gameObject.layer);
            TxNative.WorldObjectSetGroupLayer(m_worldID, m_objectID, m_groupLayer);
        }
    }
예제 #7
0
    public TxBody FindParentBody()
    {
        Transform parent = transform.parent;

        while (parent != null)
        {
            TxBody body = parent.GetComponent <TxBody>();
            if (body != null)
            {
                return(body);
            }
            parent = parent.parent;
        }
        return(null);
    }
예제 #8
0
    void GroupLayerUI(TxBody _rootBody)
    {
        string[]          groupLayers  = _rootBody.groupLayers;
        List <GUIContent> layerNames   = new List <GUIContent>();
        List <int>        layerIndices = new List <int>();

        for (int i = 0; i < groupLayers.Length; ++i)
        {
            string layerName = groupLayers[i];
            if (layerName != string.Empty)
            {
                layerNames.Add(new GUIContent(layerName));
                layerIndices.Add(i);
            }
        }
        EditorGUILayout.IntPopup(groupLayer, layerNames.ToArray(), layerIndices.ToArray(), new GUIContent("Layer"));
    }
예제 #9
0
 protected override void OnAfterStep()
 {
     if (onCollision != null)
     {
         int contactID = TxNative.WorldObjectFirstContact(m_worldID, m_objectID);
         while (TxNative.WorldContactExists(m_worldID, contactID))
         {
             Contact c = new Contact();
             int     objectA = -1, objectB = -1;
             if (TxNative.WorldContactGetInfo(m_worldID, contactID, ref objectA, ref objectB, ref c.averagePosition, ref c.averageNormal, ref c.minimumDistance, ref c.totalImpulse, ref c.relativeVelocity))
             {
                 c.bodyA = TxBody.Find(objectA);
                 c.bodyB = TxBody.Find(objectB);
                 onCollision(c);
             }
             contactID = TxNative.WorldObjectNextContact(m_worldID, m_objectID, contactID);
         }
     }
     base.OnAfterStep();
 }
예제 #10
0
    protected void BodyGroupUI()
    {
        bool isPlaying = Application.isPlaying;

        sm_showGroup = EditorGUILayout.Foldout(sm_showGroup, "Group");
        if (sm_showGroup)
        {
            EditorGUI.indentLevel++;

            GUI.enabled = !isPlaying;
            EditorGUILayout.PropertyField(groupRoot, new GUIContent("Root"));

            TxBody rootBody = null;
            int    inGroup  = InSameGroup(ref rootBody);
            switch (inGroup)
            {
            case 0:
                GUI.enabled = false;
                EditorGUILayout.LabelField("Different groups");
                break;

            case -1:
                GUI.enabled = false;
                EditorGUILayout.LabelField("Not in a group");
                break;

            case 1:
                GUI.enabled = !isPlaying;
                if (m_targets.Length == 1 && m_targets[0] == rootBody)
                {
                    EditorGUI.indentLevel++;
                    GroupLayersUI();
                    GroupCollisionUI(rootBody);
                    EditorGUI.indentLevel--;
                }
                GroupLayerUI(rootBody);
                break;
            }
            EditorGUI.indentLevel--;
        }
    }
예제 #11
0
    int InGroup(TxBody _target, ref TxBody _rootBody)
    {
        Transform parent = _target.transform;

        while (parent != null)
        {
            TxBody parentBody = parent.GetComponent <TxBody>();
            if (parentBody != null && parentBody.groupRoot)
            {
                if (_rootBody == null)
                {
                    _rootBody = parentBody;
                }
                else if (_rootBody != parentBody)
                {
                    return(0);
                }
                return(1);
            }
            parent = parent.parent;
        }
        return(-1);
    }
예제 #12
0
    public virtual void Destroy()
    {
        if (onBeforeDestroy != null)
        {
            onBeforeDestroy(this);
        }

        TxBody parentBody = (this is TxBody) ? (this as TxBody).FindParentBody() : (this is TxConstraint) ? (this as TxConstraint).attachedBody : null;

        if (parentBody != null)
        {
            parentBody.onBeforeStep  -= OnBeforeStep;
            parentBody.onAfterStep   -= OnAfterStep;
            parentBody.onAfterUpdate -= OnAfterUpdate;
        }
        else
        {
            TxPhysics.onBeforeStep  -= OnBeforeStep;
            TxPhysics.onAfterStep   -= OnAfterStep;
            TxPhysics.onAfterUpdate -= OnAfterUpdate;
        }

        m_valid = false;
    }
예제 #13
0
    public virtual void Create()
    {
        TxBody parentBody = (this is TxBody) ? (this as TxBody).FindParentBody() : (this is TxConstraint) ? (this as TxConstraint).attachedBody : null;

        if (parentBody != null)
        {
            parentBody.onBeforeStep  += OnBeforeStep;
            parentBody.onAfterStep   += OnAfterStep;
            parentBody.onAfterUpdate += OnAfterUpdate;
        }
        else
        {
            TxPhysics.onBeforeStep  += OnBeforeStep;
            TxPhysics.onAfterStep   += OnAfterStep;
            TxPhysics.onAfterUpdate += OnAfterUpdate;
        }

        m_valid = true;

        if (onAfterCreate != null)
        {
            onAfterCreate(this);
        }
    }
예제 #14
0
    protected override TxComponent GetComponentMaster()
    {
        TxBody parent = FindParentBody();

        return(parent != null ? (TxComponent)parent : (TxComponent)TxWorld.instance);
    }
예제 #15
0
    void OnSceneGUI()
    {
        Color yellow = new Color(1.0f, 0.5f, 0.0f);
        Color green  = new Color(0.0f, 0.5f, 0.0f);
        Color blue   = new Color(0.0f, 0.5f, 1.0f);
        Color red    = new Color(0.5f, 0.0f, 0.0f);
        float size   = 0.1f;

        foreach (TxConstraint constraint in m_targets)
        {
            if (!constraint.enabled || constraint.isBroken)
            {
                continue;
            }
            TxSoftBody bodyA  = constraint.attachedBody;
            TxTruss    trussA = bodyA.truss;
            if (trussA == null)
            {
                continue;
            }
            if (constraint.enableMotor)
            {
                int[] motorAxis = trussA.FindNodeSet(constraint.motorAxis);
                if (motorAxis != null && motorAxis.Length == 2)
                {
                    Vector3 axis0 = bodyA.nodePosition[motorAxis[0]];
                    Vector3 axis1 = bodyA.nodePosition[motorAxis[1]];
                    Handles.color = red;
                    Handles.DrawLine(axis0, axis1);
                }
            }
            if (constraint.baseBody is TxSoftBody)
            {
                Handles.color = yellow;
                TxSoftBody bodyB  = constraint.baseBody as TxSoftBody;
                TxTruss    trussB = bodyB.truss;
                if (trussB == null)
                {
                    continue;
                }
                TxConstraint.Snap[] snaps = constraint.snaps;
                foreach (var s in snaps)
                {
                    if (!s.show)
                    {
                        continue;
                    }
                    int[] indicesA = trussA.FindNodeSet(s.node);
                    if (indicesA != null && indicesA.Length == 1)
                    {
                        Vector3 positionA = bodyA.nodePosition[indicesA[0]];
                        int[]   indicesB  = trussB.FindNodeSet(s.featureB);
                        if (indicesB != null)
                        {
                            switch (s.type)
                            {
                            case TxConstraint.SnapType.Node:
                                if (indicesB.Length == 1)
                                {
                                    Matrix4x4 matrixB   = bodyB.transform.localToWorldMatrix;
                                    Vector3   positionB = bodyB.nodePosition[indicesB[0]];
                                    if (Vector3.Distance(positionA, positionB) > 0.001f)
                                    {
                                        Handles.color = yellow;
                                        size          = HandleUtility.GetHandleSize(positionA) * 0.08f;
                                        Handles.SphereCap(-1, positionA, Quaternion.identity, size);
                                        Handles.color = blue;
                                        size          = HandleUtility.GetHandleSize(positionB) * 0.08f;
                                        Handles.SphereCap(-1, positionB, Quaternion.identity, size);
                                        Handles.color = green;
                                        Handles.DrawLine(positionA, positionB);
                                    }
                                    else
                                    {
                                        Handles.color = green;
                                        size          = HandleUtility.GetHandleSize(positionA) * 0.08f;
                                        Handles.SphereCap(-1, positionA, Quaternion.identity, size);
                                    }
                                    if (s.maxLimit > 0.001f)
                                    {
                                        if (s.minLimit < s.maxLimit - 0.001f)
                                        {
                                            Handles.color = blue;
                                            Handles.DrawWireDisc(positionB, matrixB.GetColumn(0), s.minLimit);
                                            Handles.DrawWireDisc(positionB, matrixB.GetColumn(1), s.minLimit);
                                            Handles.DrawWireDisc(positionB, matrixB.GetColumn(2), s.minLimit);
                                            Handles.color = yellow;
                                            Handles.DrawWireDisc(positionB, matrixB.GetColumn(0), s.maxLimit);
                                            Handles.DrawWireDisc(positionB, matrixB.GetColumn(1), s.maxLimit);
                                            Handles.DrawWireDisc(positionB, matrixB.GetColumn(2), s.maxLimit);
                                        }
                                        else
                                        {
                                            Handles.color = green;
                                            Handles.DrawWireDisc(positionB, matrixB.GetColumn(0), s.maxLimit);
                                            Handles.DrawWireDisc(positionB, matrixB.GetColumn(1), s.maxLimit);
                                            Handles.DrawWireDisc(positionB, matrixB.GetColumn(2), s.maxLimit);
                                        }
                                    }
                                }
                                break;

                            case TxConstraint.SnapType.Edge:
                                if (indicesB.Length == 2)
                                {
                                    Vector3 positionB0 = bodyB.nodePosition[indicesB[0]];
                                    Vector3 positionB1 = bodyB.nodePosition[indicesB[1]];
                                    Handles.color = blue;
                                    size          = HandleUtility.GetHandleSize(positionB0) * 0.08f;
                                    Handles.SphereCap(-1, positionB0, Quaternion.identity, size);
                                    size = HandleUtility.GetHandleSize(positionB1) * 0.08f;
                                    Handles.SphereCap(-1, positionB1, Quaternion.identity, size);
                                    Handles.DrawLine(positionB0, positionB1);
                                    Vector3 positionB = positionB0 + (positionB1 - positionB0) * Vector3.Dot(positionB1 - positionB0, positionA - positionB0) / (positionB1 - positionB0).sqrMagnitude;
                                    if (Vector3.Distance(positionA, positionB) > 0.001f)
                                    {
                                        Handles.color = yellow;
                                        size          = HandleUtility.GetHandleSize(positionA) * 0.08f;
                                        Handles.SphereCap(-1, positionA, Quaternion.identity, size);
                                        Handles.color = blue;
                                        size          = HandleUtility.GetHandleSize(positionB) * 0.08f;
                                        Handles.SphereCap(-1, positionB, Quaternion.identity, size);
                                        Handles.color = green;
                                        Handles.DrawLine(positionA, positionB);
                                    }
                                    else
                                    {
                                        Handles.color = green;
                                        size          = HandleUtility.GetHandleSize(positionA) * 0.08f;
                                        Handles.SphereCap(-1, positionA, Quaternion.identity, size);
                                    }
                                    if (s.maxLimit > 0.001f)
                                    {
                                        Vector3 normal = (positionB1 - positionB0).normalized;
                                        if (s.minLimit < s.maxLimit - 0.001f)
                                        {
                                            Handles.color = blue;
                                            Handles.DrawWireDisc(positionB0, normal, s.minLimit);
                                            Handles.DrawWireDisc((positionB0 + positionB1) * 0.5f, normal, s.minLimit);
                                            Handles.DrawWireDisc(positionB1, normal, s.minLimit);
                                            Handles.color = yellow;
                                            Handles.DrawWireDisc(positionB0, normal, s.maxLimit);
                                            Handles.DrawWireDisc((positionB0 + positionB1) * 0.5f, normal, s.maxLimit);
                                            Handles.DrawWireDisc(positionB1, normal, s.maxLimit);
                                        }
                                        else
                                        {
                                            Handles.color = green;
                                            Handles.DrawWireDisc(positionB0, normal, s.maxLimit);
                                            Handles.DrawWireDisc((positionB0 + positionB1) * 0.5f, normal, s.maxLimit);
                                            Handles.DrawWireDisc(positionB1, normal, s.maxLimit);
                                        }
                                    }
                                }
                                break;
                            }
                        }
                    }
                }
            }
            else
            {
                TxBody              bodyB   = constraint.baseBody;
                Matrix4x4           matrixA = Application.isPlaying ? constraint.startMatrix : bodyB ? bodyB.transform.worldToLocalMatrix * bodyA.transform.localToWorldMatrix : bodyA.transform.localToWorldMatrix;
                Matrix4x4           matrixB = bodyB ? bodyB.transform.localToWorldMatrix : Matrix4x4.identity;
                TxConstraint.Snap[] snaps   = constraint.snaps;
                foreach (var s in snaps)
                {
                    if (!s.show)
                    {
                        continue;
                    }
                    int[] indices = trussA.FindNodeSet(s.node);
                    if (indices != null)
                    {
                        foreach (var i in indices)
                        {
                            if (s.maxLimit > 0.001f)
                            {
                                Vector3 positionA = bodyA.nodePosition[i];
                                Vector3 positionB = matrixB.MultiplyPoint(matrixA.MultiplyPoint(trussA.nodePosition[i]));
                                if (Vector3.Distance(positionA, positionB) > 0.001f)
                                {
                                    Handles.color = yellow;
                                    size          = HandleUtility.GetHandleSize(positionA) * 0.08f;
                                    Handles.SphereCap(-1, positionA, Quaternion.identity, size);
                                    Handles.color = blue;
                                    size          = HandleUtility.GetHandleSize(positionB) * 0.08f;
                                    Handles.SphereCap(-1, positionB, Quaternion.identity, size);
                                }
                                else
                                {
                                    Handles.color = green;
                                    size          = HandleUtility.GetHandleSize(positionA) * 0.08f;
                                    Handles.SphereCap(-1, positionA, Quaternion.identity, size);
                                }
                                Handles.color = green;
                                Handles.DrawWireDisc(positionB, matrixB.GetColumn(0), s.maxLimit);
                                Handles.DrawWireDisc(positionB, matrixB.GetColumn(1), s.maxLimit);
                                Handles.DrawWireDisc(positionB, matrixB.GetColumn(2), s.maxLimit);
                            }
                            else
                            {
                                Vector3 position = matrixB.MultiplyPoint(matrixA.MultiplyPoint(trussA.nodePosition[i]));
                                Handles.color = green;
                                size          = HandleUtility.GetHandleSize(position) * 0.08f;
                                Handles.SphereCap(-1, position, Quaternion.identity, size);
                            }
                        }
                    }
                }
            }
        }
        Handles.color = Color.white;
    }