DistanceJoint.cs 6.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219
  1. //********************************** Banshee Engine (www.banshee3d.com) **************************************************//
  2. //**************** Copyright (c) 2016 Marko Pintera ([email protected]). All rights reserved. **********************//
  3. using System;
  4. namespace BansheeEngine
  5. {
  6. /// <summary>
  7. /// A joint that maintains an upper or lower (or both) bound on the distance between two bodies.
  8. /// </summary>
  9. public sealed class DistanceJoint : Joint
  10. {
  11. /// <summary>
  12. /// Flags to control distance joint behaviour.
  13. /// </summary>
  14. [Flags]
  15. private enum Flag
  16. {
  17. MinDistanceLimit = 0x01,
  18. MaxDistanceLimit = 0x02,
  19. Spring = 0x04
  20. }
  21. [SerializeField]
  22. private float minDistance = 0.0f;
  23. [SerializeField]
  24. private float maxDistance = 0.0f;
  25. [SerializeField]
  26. private float tolerance = 0.25f;
  27. [SerializeField]
  28. private Spring spring;
  29. [SerializeField]
  30. private Flag flags = 0;
  31. /// <summary>
  32. /// Returns the current distance between the two joint bodies.
  33. /// </summary>
  34. public float Distance
  35. {
  36. get
  37. {
  38. if(Native != null)
  39. return Native.Distance;
  40. return 0.0f;
  41. }
  42. }
  43. /// <summary>
  44. /// Determines the minimum distance the bodies are allowed to be at, they will get no closer. You must enable
  45. /// <see cref="EnableMinDistanceLimit"/> in order for this to be enforced.
  46. /// </summary>
  47. public float MinDistance
  48. {
  49. get { return minDistance; }
  50. set
  51. {
  52. if (minDistance == value)
  53. return;
  54. minDistance = value;
  55. if (Native != null)
  56. Native.MinDistance = value;
  57. }
  58. }
  59. /// <summary>
  60. /// Determines the maximum distance the bodies are allowed to be at, they will get no further. You must enable
  61. /// <see cref="EnableMaxDistanceLimit"/> in order for this to be enforced.
  62. /// </summary>
  63. public float MaxDistance
  64. {
  65. get { return maxDistance; }
  66. set
  67. {
  68. if (maxDistance == value)
  69. return;
  70. maxDistance = value;
  71. if (Native != null)
  72. Native.MaxDistance = value;
  73. }
  74. }
  75. /// <summary>
  76. /// Determines the error tolerance of the joint at which the joint becomes active. This value slightly extends the
  77. /// lower and upper limit for precision reasons.
  78. /// </summary>
  79. public float Tolerance
  80. {
  81. get { return tolerance; }
  82. set
  83. {
  84. if (tolerance == value)
  85. return;
  86. tolerance = value;
  87. if (Native != null)
  88. Native.Tolerance = value;
  89. }
  90. }
  91. /// <summary>
  92. /// Returns a spring that controls how the joint responds when a limit is reached. You must enable
  93. /// <see cref="EnableSpring"/> in order for the spring to be applied.
  94. /// </summary>
  95. public Spring Spring
  96. {
  97. get { return spring; }
  98. set
  99. {
  100. if (spring == value)
  101. return;
  102. spring = value;
  103. if (Native != null)
  104. Native.Spring = value;
  105. }
  106. }
  107. /// <summary>
  108. /// Enables or disables the limit that causes joint objects to maintain a minimum distance between themselves.
  109. /// </summary>
  110. public bool EnableMinDistanceLimit
  111. {
  112. get { return (flags & Flag.MinDistanceLimit) != 0; }
  113. set
  114. {
  115. if (!SetFlag(Flag.MinDistanceLimit, value))
  116. return;
  117. if (Native != null)
  118. Native.EnableMinDistanceLimit = value;
  119. }
  120. }
  121. /// <summary>
  122. /// Enables or disables the limit that causes joint objects to maintain a maximum distance between themselves.
  123. /// </summary>
  124. public bool EnableMaxDistanceLimit
  125. {
  126. get { return (flags & Flag.MaxDistanceLimit) != 0; }
  127. set
  128. {
  129. if (!SetFlag(Flag.MaxDistanceLimit, value))
  130. return;
  131. if (Native != null)
  132. Native.EnableMinDistanceLimit = value;
  133. }
  134. }
  135. /// <summary>
  136. /// Enables or disables the spring that controls how the joint reacts when the limit is reached.
  137. /// </summary>
  138. public bool EnableSpring
  139. {
  140. get { return (flags & Flag.Spring) != 0; }
  141. set
  142. {
  143. if (!SetFlag(Flag.Spring, value))
  144. return;
  145. if (Native != null)
  146. Native.EnableSpring = value;
  147. }
  148. }
  149. /// <summary>
  150. /// Toggles a specific distance joint flag on or off.
  151. /// </summary>
  152. /// <param name="flag">Flag to toggle.</param>
  153. /// <param name="enabled">Should the flag be turned on or off.</param>
  154. /// <returns>True if the new newly set flag state was different from the previous one.</returns>
  155. private bool SetFlag(Flag flag, bool enabled)
  156. {
  157. Flag newFlags = flags;
  158. if (enabled)
  159. newFlags |= flag;
  160. else
  161. newFlags &= ~flag;
  162. if (newFlags == flags)
  163. return false;
  164. flags = newFlags;
  165. return true;
  166. }
  167. /// <summary>
  168. /// Returns the native joint wrapped by this component.
  169. /// </summary>
  170. private NativeDistanceJoint Native
  171. {
  172. get { return (NativeDistanceJoint)native; }
  173. }
  174. /// <inheritdoc/>
  175. internal override NativeJoint CreateNative()
  176. {
  177. NativeDistanceJoint joint = new NativeDistanceJoint();
  178. // TODO - Apply this all at once to avoid all the individual interop function calls
  179. joint.MinDistance = minDistance;
  180. joint.MaxDistance = maxDistance;
  181. joint.Tolerance = tolerance;
  182. joint.Spring = spring;
  183. joint.EnableMinDistanceLimit = EnableMinDistanceLimit;
  184. joint.EnableMaxDistanceLimit = EnableMaxDistanceLimit;
  185. joint.EnableSpring = EnableSpring;
  186. return joint;
  187. }
  188. }
  189. }