aboutsummaryrefslogtreecommitdiffstatshomepage
path: root/OpenSim/Region/Physics/OdePlugin/ODEPrim.cs
diff options
context:
space:
mode:
Diffstat (limited to '')
-rw-r--r--OpenSim/Region/Physics/OdePlugin/ODEPrim.cs321
1 files changed, 201 insertions, 120 deletions
diff --git a/OpenSim/Region/Physics/OdePlugin/ODEPrim.cs b/OpenSim/Region/Physics/OdePlugin/ODEPrim.cs
index 34c5cfd..eb90cf4 100644
--- a/OpenSim/Region/Physics/OdePlugin/ODEPrim.cs
+++ b/OpenSim/Region/Physics/OdePlugin/ODEPrim.cs
@@ -90,6 +90,11 @@ namespace OpenSim.Region.Physics.OdePlugin
90 public IntPtr prev_geom; 90 public IntPtr prev_geom;
91 public IntPtr _triMeshData; 91 public IntPtr _triMeshData;
92 92
93 private IntPtr _linkJointGroup = (IntPtr)0;
94 private PhysicsActor _parent = null;
95 private PhysicsActor m_taintparent = null;
96
97
93 private bool iscolliding = false; 98 private bool iscolliding = false;
94 private bool m_isphysical = false; 99 private bool m_isphysical = false;
95 private bool m_isSelected = false; 100 private bool m_isSelected = false;
@@ -113,6 +118,8 @@ namespace OpenSim.Region.Physics.OdePlugin
113 private PhysicsVector _target_velocity; 118 private PhysicsVector _target_velocity;
114 public d.Mass pMass; 119 public d.Mass pMass;
115 120
121 private IntPtr m_linkJoint = (IntPtr)0;
122
116 private int debugcounter = 0; 123 private int debugcounter = 0;
117 124
118 public OdePrim(String primName, OdeScene parent_scene, PhysicsVector pos, PhysicsVector size, 125 public OdePrim(String primName, OdeScene parent_scene, PhysicsVector pos, PhysicsVector size,
@@ -719,6 +726,45 @@ namespace OpenSim.Region.Physics.OdePlugin
719 726
720 if (m_taintVelocity != PhysicsVector.Zero) 727 if (m_taintVelocity != PhysicsVector.Zero)
721 changevelocity(timestep); 728 changevelocity(timestep);
729
730 if (m_taintparent != _parent)
731 changelink(timestep);
732 }
733
734 private void changelink(float timestep)
735 {
736 while (ode.lockquery())
737 {
738 }
739 ode.dlock(_parent_scene.world);
740
741 if (_parent == null && m_taintparent != null)
742 {
743 if (m_taintparent.PhysicsActorType == (int)ActorTypes.Prim)
744 {
745 OdePrim obj = (OdePrim)m_taintparent;
746 if (obj.Body != (IntPtr)0 && Body != (IntPtr)0)
747 {
748 _linkJointGroup = d.JointGroupCreate(0);
749 m_linkJoint = d.JointCreateFixed(_parent_scene.world, _linkJointGroup);
750 d.JointAttach(m_linkJoint, obj.Body, Body);
751 d.JointSetFixed(m_linkJoint);
752 }
753 }
754
755 }
756 else if (_parent != null && m_taintparent == null)
757 {
758 if (Body != (IntPtr)0 && _linkJointGroup != (IntPtr)0)
759 d.JointGroupDestroy(_linkJointGroup);
760
761 _linkJointGroup = (IntPtr)0;
762 m_linkJoint = (IntPtr)0;
763
764 }
765 ode.dunlock(_parent_scene.world);
766
767 _parent = m_taintparent;
722 } 768 }
723 769
724 private void changeSelectedStatus(float timestep) 770 private void changeSelectedStatus(float timestep)
@@ -970,8 +1016,25 @@ namespace OpenSim.Region.Physics.OdePlugin
970 enableBody(); 1016 enableBody();
971 //Prim auto disable after 20 frames, 1017 //Prim auto disable after 20 frames,
972 //if you move it, re-enable the prim manually. 1018 //if you move it, re-enable the prim manually.
973 1019 if (_parent != null)
1020 {
1021 if (m_linkJoint != (IntPtr)0)
1022 {
1023 d.JointDestroy(m_linkJoint);
1024 m_linkJoint = (IntPtr)0;
1025 }
1026 }
974 d.BodySetPosition(Body, _position.X, _position.Y, _position.Z); 1027 d.BodySetPosition(Body, _position.X, _position.Y, _position.Z);
1028 if (_parent != null)
1029 {
1030 OdePrim odParent = (OdePrim)_parent;
1031 if (Body != (IntPtr)0 && odParent.Body != (IntPtr)0)
1032 {
1033 m_linkJoint = d.JointCreateFixed(_parent_scene.world, _linkJointGroup);
1034 d.JointAttach(m_linkJoint, Body, odParent.Body);
1035 d.JointSetFixed(m_linkJoint);
1036 }
1037 }
975 d.BodyEnable(Body); 1038 d.BodyEnable(Body);
976 1039
977 } 1040 }
@@ -1652,154 +1715,172 @@ namespace OpenSim.Region.Physics.OdePlugin
1652 m_log.Warn("[PHYSICS]: Too many crossing failures for: " + m_primName); 1715 m_log.Warn("[PHYSICS]: Too many crossing failures for: " + m_primName);
1653 } 1716 }
1654 } 1717 }
1718
1719 public override void link(PhysicsActor obj)
1720 {
1721 m_taintparent = obj;
1722 }
1723
1724 public override void delink()
1725 {
1726 m_taintparent = null;
1727 }
1728
1655 public void UpdatePositionAndVelocity() 1729 public void UpdatePositionAndVelocity()
1656 { 1730 {
1657 // no lock; called from Simulate() -- if you call this from elsewhere, gotta lock or do Monitor.Enter/Exit! 1731 // no lock; called from Simulate() -- if you call this from elsewhere, gotta lock or do Monitor.Enter/Exit!
1658 PhysicsVector pv = new PhysicsVector(0, 0, 0); 1732 if (_parent != null)
1659 bool lastZeroFlag = _zeroFlag;
1660 if (Body != (IntPtr) 0)
1661 { 1733 {
1662 d.Vector3 vec = d.BodyGetPosition(Body);
1663 d.Quaternion ori = d.BodyGetQuaternion(Body);
1664 d.Vector3 vel = d.BodyGetLinearVel(Body);
1665 d.Vector3 rotvel = d.BodyGetAngularVel(Body);
1666 1734
1667 PhysicsVector l_position = new PhysicsVector(); 1735 }
1736 else
1737 {
1738 PhysicsVector pv = new PhysicsVector(0, 0, 0);
1739 bool lastZeroFlag = _zeroFlag;
1740 if (Body != (IntPtr)0)
1741 {
1742 d.Vector3 vec = d.BodyGetPosition(Body);
1743 d.Quaternion ori = d.BodyGetQuaternion(Body);
1744 d.Vector3 vel = d.BodyGetLinearVel(Body);
1745 d.Vector3 rotvel = d.BodyGetAngularVel(Body);
1668 1746
1669 1747 PhysicsVector l_position = new PhysicsVector();
1670 // kluge to keep things in bounds. ODE lets dead avatars drift away (they should be removed!)
1671 //if (vec.X < 0.0f) { vec.X = 0.0f; if (Body != (IntPtr)0) d.BodySetAngularVel(Body, 0, 0, 0); }
1672 //if (vec.Y < 0.0f) { vec.Y = 0.0f; if (Body != (IntPtr)0) d.BodySetAngularVel(Body, 0, 0, 0); }
1673 //if (vec.X > 255.95f) { vec.X = 255.95f; if (Body != (IntPtr)0) d.BodySetAngularVel(Body, 0, 0, 0); }
1674 //if (vec.Y > 255.95f) { vec.Y = 255.95f; if (Body != (IntPtr)0) d.BodySetAngularVel(Body, 0, 0, 0); }
1675 1748
1676 m_lastposition = _position;
1677 1749
1678 l_position.X = vec.X; 1750 // kluge to keep things in bounds. ODE lets dead avatars drift away (they should be removed!)
1679 l_position.Y = vec.Y; 1751 //if (vec.X < 0.0f) { vec.X = 0.0f; if (Body != (IntPtr)0) d.BodySetAngularVel(Body, 0, 0, 0); }
1680 l_position.Z = vec.Z; 1752 //if (vec.Y < 0.0f) { vec.Y = 0.0f; if (Body != (IntPtr)0) d.BodySetAngularVel(Body, 0, 0, 0); }
1753 //if (vec.X > 255.95f) { vec.X = 255.95f; if (Body != (IntPtr)0) d.BodySetAngularVel(Body, 0, 0, 0); }
1754 //if (vec.Y > 255.95f) { vec.Y = 255.95f; if (Body != (IntPtr)0) d.BodySetAngularVel(Body, 0, 0, 0); }
1681 1755
1682 if (l_position.X > 255.95f || l_position.X < 0f || l_position.Y > 255.95f || l_position.Y < 0f) 1756 m_lastposition = _position;
1683 { 1757
1684 base.RaiseOutOfBounds(_position); 1758 l_position.X = vec.X;
1685 } 1759 l_position.Y = vec.Y;
1760 l_position.Z = vec.Z;
1761
1762 if (l_position.X > 255.95f || l_position.X < 0f || l_position.Y > 255.95f || l_position.Y < 0f)
1763 {
1764 base.RaiseOutOfBounds(_position);
1765 }
1686 //if (m_crossingfailures < 5) 1766 //if (m_crossingfailures < 5)
1687 //{ 1767 //{
1688 //base.RequestPhysicsterseUpdate(); 1768 //base.RequestPhysicsterseUpdate();
1769 //}
1689 //} 1770 //}
1690 //}
1691
1692 if (l_position.Z < 0)
1693 {
1694 // This is so prim that get lost underground don't fall forever and suck up
1695 //
1696 // Sim resources and memory.
1697 // Disables the prim's movement physics....
1698 // It's a hack and will generate a console message if it fails.
1699
1700
1701 //IsPhysical = false;
1702 base.RaiseOutOfBounds(_position);
1703 _velocity.X = 0;
1704 _velocity.Y = 0;
1705 _velocity.Z = 0;
1706 m_rotationalVelocity.X = 0;
1707 m_rotationalVelocity.Y = 0;
1708 m_rotationalVelocity.Z = 0;
1709 base.RequestPhysicsterseUpdate();
1710 m_throttleUpdates = false;
1711 throttleCounter = 0;
1712 _zeroFlag = true;
1713 //outofBounds = true;
1714 }
1715
1716 if ((Math.Abs(m_lastposition.X - l_position.X) < 0.02)
1717 && (Math.Abs(m_lastposition.Y - l_position.Y) < 0.02)
1718 && (Math.Abs(m_lastposition.Z - l_position.Z) < 0.02))
1719 {
1720 _zeroFlag = true;
1721 m_throttleUpdates = false;
1722 }
1723 else
1724 {
1725 //System.Console.WriteLine(Math.Abs(m_lastposition.X - l_position.X).ToString());
1726 _zeroFlag = false;
1727 }
1728
1729 1771
1730 if (_zeroFlag) 1772 if (l_position.Z < 0)
1731 {
1732 // Supposedly this is supposed to tell SceneObjectGroup that
1733 // no more updates need to be sent..
1734 // but it seems broken.
1735 _velocity.X = 0.0f;
1736 _velocity.Y = 0.0f;
1737 _velocity.Z = 0.0f;
1738 //_orientation.w = 0f;
1739 //_orientation.x = 0f;
1740 //_orientation.y = 0f;
1741 //_orientation.z = 0f;
1742 m_rotationalVelocity.X = 0;
1743 m_rotationalVelocity.Y = 0;
1744 m_rotationalVelocity.Z = 0;
1745 if (!m_lastUpdateSent)
1746 { 1773 {
1774 // This is so prim that get lost underground don't fall forever and suck up
1775 //
1776 // Sim resources and memory.
1777 // Disables the prim's movement physics....
1778 // It's a hack and will generate a console message if it fails.
1779
1780
1781 //IsPhysical = false;
1782 base.RaiseOutOfBounds(_position);
1783 _velocity.X = 0;
1784 _velocity.Y = 0;
1785 _velocity.Z = 0;
1786 m_rotationalVelocity.X = 0;
1787 m_rotationalVelocity.Y = 0;
1788 m_rotationalVelocity.Z = 0;
1789 base.RequestPhysicsterseUpdate();
1747 m_throttleUpdates = false; 1790 m_throttleUpdates = false;
1748 throttleCounter = 0; 1791 throttleCounter = 0;
1749 m_rotationalVelocity = pv; 1792 _zeroFlag = true;
1750 base.RequestPhysicsterseUpdate(); 1793 //outofBounds = true;
1751 m_lastUpdateSent = true;
1752 } 1794 }
1753 }
1754 else
1755 {
1756 if (lastZeroFlag != _zeroFlag)
1757 base.RequestPhysicsterseUpdate();
1758
1759 m_lastVelocity = _velocity;
1760 1795
1761 _position = l_position; 1796 if ((Math.Abs(m_lastposition.X - l_position.X) < 0.02)
1762 1797 && (Math.Abs(m_lastposition.Y - l_position.Y) < 0.02)
1763 _velocity.X = vel.X; 1798 && (Math.Abs(m_lastposition.Z - l_position.Z) < 0.02))
1764 _velocity.Y = vel.Y;
1765 _velocity.Z = vel.Z;
1766 if (_velocity.IsIdentical(pv, 0.5f))
1767 { 1799 {
1768 m_rotationalVelocity = pv; 1800 _zeroFlag = true;
1801 m_throttleUpdates = false;
1769 } 1802 }
1770 else 1803 else
1771 { 1804 {
1772 m_rotationalVelocity.setValues(rotvel.X, rotvel.Y, rotvel.Z); 1805 //System.Console.WriteLine(Math.Abs(m_lastposition.X - l_position.X).ToString());
1806 _zeroFlag = false;
1773 } 1807 }
1774 1808
1775 //System.Console.WriteLine("ODE: " + m_rotationalVelocity.ToString()); 1809
1776 _orientation.w = ori.W; 1810 if (_zeroFlag)
1777 _orientation.x = ori.X;
1778 _orientation.y = ori.Y;
1779 _orientation.z = ori.Z;
1780 m_lastUpdateSent = false;
1781 if (!m_throttleUpdates || throttleCounter > 15)
1782 { 1811 {
1783 1812 // Supposedly this is supposed to tell SceneObjectGroup that
1784 base.RequestPhysicsterseUpdate(); 1813 // no more updates need to be sent..
1814 // but it seems broken.
1815 _velocity.X = 0.0f;
1816 _velocity.Y = 0.0f;
1817 _velocity.Z = 0.0f;
1818 //_orientation.w = 0f;
1819 //_orientation.x = 0f;
1820 //_orientation.y = 0f;
1821 //_orientation.z = 0f;
1822 m_rotationalVelocity.X = 0;
1823 m_rotationalVelocity.Y = 0;
1824 m_rotationalVelocity.Z = 0;
1825 if (!m_lastUpdateSent)
1826 {
1827 m_throttleUpdates = false;
1828 throttleCounter = 0;
1829 m_rotationalVelocity = pv;
1830 base.RequestPhysicsterseUpdate();
1831 m_lastUpdateSent = true;
1832 }
1785 } 1833 }
1786 else 1834 else
1787 { 1835 {
1788 throttleCounter++; 1836 if (lastZeroFlag != _zeroFlag)
1837 base.RequestPhysicsterseUpdate();
1838
1839 m_lastVelocity = _velocity;
1840
1841 _position = l_position;
1842
1843 _velocity.X = vel.X;
1844 _velocity.Y = vel.Y;
1845 _velocity.Z = vel.Z;
1846 if (_velocity.IsIdentical(pv, 0.5f))
1847 {
1848 m_rotationalVelocity = pv;
1849 }
1850 else
1851 {
1852 m_rotationalVelocity.setValues(rotvel.X, rotvel.Y, rotvel.Z);
1853 }
1854
1855 //System.Console.WriteLine("ODE: " + m_rotationalVelocity.ToString());
1856 _orientation.w = ori.W;
1857 _orientation.x = ori.X;
1858 _orientation.y = ori.Y;
1859 _orientation.z = ori.Z;
1860 m_lastUpdateSent = false;
1861 if (!m_throttleUpdates || throttleCounter > 15)
1862 {
1863
1864 base.RequestPhysicsterseUpdate();
1865 }
1866 else
1867 {
1868 throttleCounter++;
1869 }
1789 } 1870 }
1871 m_lastposition = l_position;
1872 }
1873 else
1874 {
1875 // Not a body.. so Make sure the client isn't interpolating
1876 _velocity.X = 0;
1877 _velocity.Y = 0;
1878 _velocity.Z = 0;
1879 m_rotationalVelocity.X = 0;
1880 m_rotationalVelocity.Y = 0;
1881 m_rotationalVelocity.Z = 0;
1882 _zeroFlag = true;
1790 } 1883 }
1791 m_lastposition = l_position;
1792 }
1793 else
1794 {
1795 // Not a body.. so Make sure the client isn't interpolating
1796 _velocity.X = 0;
1797 _velocity.Y = 0;
1798 _velocity.Z = 0;
1799 m_rotationalVelocity.X = 0;
1800 m_rotationalVelocity.Y = 0;
1801 m_rotationalVelocity.Z = 0;
1802 _zeroFlag = true;
1803 } 1884 }
1804 } 1885 }
1805 1886