cone.go 2.0 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788
  1. // Copyright 2016 The G3N Authors. All rights reserved.
  2. // Use of this source code is governed by a BSD-style
  3. // license that can be found in the LICENSE file.
  4. package equation
  5. import (
  6. "github.com/g3n/engine/math32"
  7. )
  8. // Cone is a cone constraint equation.
  9. // Works to keep the given body world vectors aligned, or tilted within a given angle from each other.
  10. type Cone struct {
  11. Equation
  12. axisA *math32.Vector3 // Local axis in A
  13. axisB *math32.Vector3 // Local axis in B
  14. angle float32 // The "cone angle" to keep
  15. }
  16. // NewCone creates and returns a pointer to a new Cone equation object.
  17. func NewCone(bodyA, bodyB IBody, axisA, axisB *math32.Vector3, angle, maxForce float32) *Cone {
  18. ce := new(Cone)
  19. ce.axisA = axisA // new Vec3(1, 0, 0)
  20. ce.axisB = axisB // new Vec3(0, 1, 0)
  21. ce.angle = angle // 0
  22. ce.Equation.initialize(bodyA, bodyB, -maxForce, maxForce)
  23. return ce
  24. }
  25. // SetAxisA sets the axis of body A.
  26. func (ce *Cone) SetAxisA(axisA *math32.Vector3) {
  27. ce.axisA = axisA
  28. }
  29. // AxisA returns the axis of body A.
  30. func (ce *Cone) AxisA() math32.Vector3 {
  31. return *ce.axisA
  32. }
  33. // SetAxisB sets the axis of body B.
  34. func (ce *Cone) SetAxisB(axisB *math32.Vector3) {
  35. ce.axisB = axisB
  36. }
  37. // AxisB returns the axis of body B.
  38. func (ce *Cone) AxisB() math32.Vector3 {
  39. return *ce.axisB
  40. }
  41. // SetAngle sets the cone angle.
  42. func (ce *Cone) SetAngle(angle float32) {
  43. ce.angle = angle
  44. }
  45. // MaxAngle returns the cone angle.
  46. func (ce *Cone) Angle() float32 {
  47. return ce.angle
  48. }
  49. // ComputeB
  50. func (ce *Cone) ComputeB(h float32) float32 {
  51. // The angle between two vector is:
  52. // cos(theta) = a * b / (length(a) * length(b) = { len(a) = len(b) = 1 } = a * b
  53. // g = a * b
  54. // gdot = (b x a) * wi + (a x b) * wj
  55. // G = [0 bxa 0 axb]
  56. // W = [vi wi vj wj]
  57. ce.jeA.SetRotational(math32.NewVec3().CrossVectors(ce.axisB, ce.axisA))
  58. ce.jeB.SetRotational(math32.NewVec3().CrossVectors(ce.axisA, ce.axisB))
  59. g := math32.Cos(ce.angle) - ce.axisA.Dot(ce.axisB)
  60. GW := ce.ComputeGW()
  61. GiMf := ce.ComputeGiMf()
  62. return -g*ce.a - GW*ce.b - h*GiMf
  63. }