vector3.go 16 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668
  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 math32
  5. // Vector3 is a 3D vector/point with X, Y and Z components.
  6. type Vector3 struct {
  7. X float32
  8. Y float32
  9. Z float32
  10. }
  11. // NewVector3 creates and returns a pointer to a new Vector3 with
  12. // the specified x, y and y components
  13. func NewVector3(x, y, z float32) *Vector3 {
  14. return &Vector3{X: x, Y: y, Z: z}
  15. }
  16. // NewVec3 creates and returns a pointer to a new zero-ed Vector3.
  17. func NewVec3() *Vector3 {
  18. return &Vector3{X: 0, Y: 0, Z: 0}
  19. }
  20. // Set sets this vector X, Y and Z components.
  21. // Returns the pointer to this updated vector.
  22. func (v *Vector3) Set(x, y, z float32) *Vector3 {
  23. v.X = x
  24. v.Y = y
  25. v.Z = z
  26. return v
  27. }
  28. // SetX sets this vector X component.
  29. // Returns the pointer to this updated Vector.
  30. func (v *Vector3) SetX(x float32) *Vector3 {
  31. v.X = x
  32. return v
  33. }
  34. // SetY sets this vector Y component.
  35. // Returns the pointer to this updated vector.
  36. func (v *Vector3) SetY(y float32) *Vector3 {
  37. v.Y = y
  38. return v
  39. }
  40. // SetZ sets this vector Z component.
  41. // Returns the pointer to this updated vector.
  42. func (v *Vector3) SetZ(z float32) *Vector3 {
  43. v.Z = z
  44. return v
  45. }
  46. // SetComponent sets this vector component value by its index: 0 for X, 1 for Y, 2 for Z.
  47. // Returns the pointer to this updated vector
  48. func (v *Vector3) SetComponent(index int, value float32) {
  49. switch index {
  50. case 0:
  51. v.X = value
  52. case 1:
  53. v.Y = value
  54. case 2:
  55. v.Z = value
  56. default:
  57. panic("index is out of range: ")
  58. }
  59. }
  60. // Component returns this vector component by its index: 0 for X, 1 for Y, 2 for Z.
  61. func (v *Vector3) Component(index int) float32 {
  62. switch index {
  63. case 0:
  64. return v.X
  65. case 1:
  66. return v.Y
  67. case 2:
  68. return v.Z
  69. default:
  70. panic("index is out of range")
  71. }
  72. }
  73. // SetByName sets this vector component value by its case insensitive name: "x", "y", or "z".
  74. func (v *Vector3) SetByName(name string, value float32) {
  75. switch name {
  76. case "x", "X":
  77. v.X = value
  78. case "y", "Y":
  79. v.Y = value
  80. case "z", "Z":
  81. v.Z = value
  82. default:
  83. panic("Invalid Vector3 component name: " + name)
  84. }
  85. }
  86. // Zero sets this vector X, Y and Z components to be zero.
  87. // Returns the pointer to this updated vector.
  88. func (v *Vector3) Zero() *Vector3 {
  89. v.X = 0
  90. v.Y = 0
  91. v.Z = 0
  92. return v
  93. }
  94. // Copy copies other vector to this one.
  95. // It is equivalent to: *v = *other.
  96. // Returns the pointer to this updated vector.
  97. func (v *Vector3) Copy(other *Vector3) *Vector3 {
  98. *v = *other
  99. return v
  100. }
  101. // Add adds other vector to this one.
  102. // Returns the pointer to this updated vector.
  103. func (v *Vector3) Add(other *Vector3) *Vector3 {
  104. v.X += other.X
  105. v.Y += other.Y
  106. v.Z += other.Z
  107. return v
  108. }
  109. // AddScalar adds scalar s to each component of this vector.
  110. // Returns the pointer to this updated vector.
  111. func (v *Vector3) AddScalar(s float32) *Vector3 {
  112. v.X += s
  113. v.Y += s
  114. v.Z += s
  115. return v
  116. }
  117. // AddVectors adds vectors a and b to this one.
  118. // Returns the pointer to this updated vector.
  119. func (v *Vector3) AddVectors(a, b *Vector3) *Vector3 {
  120. v.X = a.X + b.X
  121. v.Y = a.Y + b.Y
  122. v.Z = a.Z + b.Z
  123. return v
  124. }
  125. // Sub subtracts other vector from this one.
  126. // Returns the pointer to this updated vector.
  127. func (v *Vector3) Sub(other *Vector3) *Vector3 {
  128. v.X -= other.X
  129. v.Y -= other.Y
  130. v.Z -= other.Z
  131. return v
  132. }
  133. // SubScalar subtracts scalar s from each component of this vector.
  134. // Returns the pointer to this updated vector.
  135. func (v *Vector3) SubScalar(s float32) *Vector3 {
  136. v.X -= s
  137. v.Y -= s
  138. v.Z -= s
  139. return v
  140. }
  141. // SubVectors sets this vector to a - b.
  142. // Returns the pointer to this updated vector.
  143. func (v *Vector3) SubVectors(a, b *Vector3) *Vector3 {
  144. v.X = a.X - b.X
  145. v.Y = a.Y - b.Y
  146. v.Z = a.Z - b.Z
  147. return v
  148. }
  149. // Multiply multiplies each component of this vector by the corresponding one from other vector.
  150. // Returns the pointer to this updated vector.
  151. func (v *Vector3) Multiply(other *Vector3) *Vector3 {
  152. v.X *= other.X
  153. v.Y *= other.Y
  154. v.Z *= other.Z
  155. return v
  156. }
  157. // MultiplyScalar multiplies each component of this vector by the scalar s.
  158. // Returns the pointer to this updated vector.
  159. func (v *Vector3) MultiplyScalar(s float32) *Vector3 {
  160. v.X *= s
  161. v.Y *= s
  162. v.Z *= s
  163. return v
  164. }
  165. // Divide divides each component of this vector by the corresponding one from other vector.
  166. // Returns the pointer to this updated vector
  167. func (v *Vector3) Divide(other *Vector3) *Vector3 {
  168. v.X /= other.X
  169. v.Y /= other.Y
  170. v.Z /= other.Z
  171. return v
  172. }
  173. // DivideScalar divides each component of this vector by the scalar s.
  174. // If scalar is zero, sets this vector to zero.
  175. // Returns the pointer to this updated vector.
  176. func (v *Vector3) DivideScalar(scalar float32) *Vector3 {
  177. if scalar != 0 {
  178. invScalar := 1 / scalar
  179. v.X *= invScalar
  180. v.Y *= invScalar
  181. v.Z *= invScalar
  182. } else {
  183. v.X = 0
  184. v.Y = 0
  185. v.Z = 0
  186. }
  187. return v
  188. }
  189. // Min sets this vector components to the minimum values of itself and other vector.
  190. // Returns the pointer to this updated vector.
  191. func (v *Vector3) Min(other *Vector3) *Vector3 {
  192. if v.X > other.X {
  193. v.X = other.X
  194. }
  195. if v.Y > other.Y {
  196. v.Y = other.Y
  197. }
  198. if v.Z > other.Z {
  199. v.Z = other.Z
  200. }
  201. return v
  202. }
  203. // Max sets this vector components to the maximum value of itself and other vector.
  204. // Returns the pointer to this updated vector.
  205. func (v *Vector3) Max(other *Vector3) *Vector3 {
  206. if v.X < other.X {
  207. v.X = other.X
  208. }
  209. if v.Y < other.Y {
  210. v.Y = other.Y
  211. }
  212. if v.Z < other.Z {
  213. v.Z = other.Z
  214. }
  215. return v
  216. }
  217. // Clamp sets this vector components to be no less than the corresponding components of min
  218. // and not greater than the corresponding component of max.
  219. // Assumes min < max, if this assumption isn't true it will not operate correctly.
  220. // Returns the pointer to this updated vector.
  221. func (v *Vector3) Clamp(min, max *Vector3) *Vector3 {
  222. if v.X < min.X {
  223. v.X = min.X
  224. } else if v.X > max.X {
  225. v.X = max.X
  226. }
  227. if v.Y < min.Y {
  228. v.Y = min.Y
  229. } else if v.Y > max.Y {
  230. v.Y = max.Y
  231. }
  232. if v.Z < min.Z {
  233. v.Z = min.Z
  234. } else if v.Z > max.Z {
  235. v.Z = max.Z
  236. }
  237. return v
  238. }
  239. // ClampScalar sets this vector components to be no less than minVal and not greater than maxVal.
  240. // Returns the pointer to this updated vector.
  241. func (v *Vector3) ClampScalar(minVal, maxVal float32) *Vector3 {
  242. min := NewVector3(minVal, minVal, minVal)
  243. max := NewVector3(maxVal, maxVal, maxVal)
  244. return v.Clamp(min, max)
  245. }
  246. // Floor applies math32.Floor() to each of this vector's components.
  247. // Returns the pointer to this updated vector.
  248. func (v *Vector3) Floor() *Vector3 {
  249. v.X = Floor(v.X)
  250. v.Y = Floor(v.Y)
  251. v.Z = Floor(v.Z)
  252. return v
  253. }
  254. // Ceil applies math32.Ceil() to each of this vector's components.
  255. // Returns the pointer to this updated vector.
  256. func (v *Vector3) Ceil() *Vector3 {
  257. v.X = Ceil(v.X)
  258. v.Y = Ceil(v.Y)
  259. v.Z = Ceil(v.Z)
  260. return v
  261. }
  262. // Round rounds each of this vector's components.
  263. // Returns the pointer to this updated vector.
  264. func (v *Vector3) Round() *Vector3 {
  265. v.X = Floor(v.X + 0.5)
  266. v.Y = Floor(v.Y + 0.5)
  267. v.Z = Floor(v.Z + 0.5)
  268. return v
  269. }
  270. // Negate negates each of this vector's components.
  271. // Returns the pointer to this updated vector.
  272. func (v *Vector3) Negate() *Vector3 {
  273. v.X = -v.X
  274. v.Y = -v.Y
  275. v.Z = -v.Z
  276. return v
  277. }
  278. // Dot returns the dot product of this vector with other.
  279. // None of the vectors are changed.
  280. func (v *Vector3) Dot(other *Vector3) float32 {
  281. return v.X*other.X + v.Y*other.Y + v.Z*other.Z
  282. }
  283. // LengthSq returns the length squared of this vector.
  284. // LengthSq can be used to compare vectors' lengths without the need to perform a square root.
  285. func (v *Vector3) LengthSq() float32 {
  286. return v.X*v.X + v.Y*v.Y + v.Z*v.Z
  287. }
  288. // Length returns the length of this vector.
  289. func (v *Vector3) Length() float32 {
  290. return Sqrt(v.X*v.X + v.Y*v.Y + v.Z*v.Z)
  291. }
  292. // Normalize normalizes this vector so its length will be 1.
  293. // Returns the pointer to this updated vector.
  294. func (v *Vector3) Normalize() *Vector3 {
  295. return v.DivideScalar(v.Length())
  296. }
  297. // DistanceTo returns the distance of this point to other.
  298. func (v *Vector3) DistanceTo(other *Vector3) float32 {
  299. return Sqrt(v.DistanceToSquared(other))
  300. }
  301. // DistanceToSquared returns the distance squared of this point to other.
  302. func (v *Vector3) DistanceToSquared(other *Vector3) float32 {
  303. dx := v.X - other.X
  304. dy := v.Y - other.Y
  305. dz := v.Z - other.Z
  306. return dx*dx + dy*dy + dz*dz
  307. }
  308. // SetLength sets this vector to have the specified length.
  309. // If the current length is zero, does nothing.
  310. // Returns the pointer to this updated vector.
  311. func (v *Vector3) SetLength(l float32) *Vector3 {
  312. oldLength := v.Length()
  313. if oldLength != 0 && l != oldLength {
  314. v.MultiplyScalar(l / oldLength)
  315. }
  316. return v
  317. }
  318. // Lerp sets each of this vector's components to the linear interpolated value of
  319. // alpha between ifself and the corresponding other component.
  320. // Returns the pointer to this updated vector.
  321. func (v *Vector3) Lerp(other *Vector3, alpha float32) *Vector3 {
  322. v.X += (other.X - v.X) * alpha
  323. v.Y += (other.Y - v.Y) * alpha
  324. v.Z += (other.Z - v.Z) * alpha
  325. return v
  326. }
  327. // Equals returns if this vector is equal to other.
  328. func (v *Vector3) Equals(other *Vector3) bool {
  329. return (other.X == v.X) && (other.Y == v.Y) && (other.Z == v.Z)
  330. }
  331. // FromArray sets this vector's components from the specified array and offset
  332. // Returns the pointer to this updated vector.
  333. func (v *Vector3) FromArray(array []float32, offset int) *Vector3 {
  334. v.X = array[offset]
  335. v.Y = array[offset+1]
  336. v.Z = array[offset+2]
  337. return v
  338. }
  339. // ToArray copies this vector's components to array starting at offset.
  340. // Returns the array.
  341. func (v *Vector3) ToArray(array []float32, offset int) []float32 {
  342. array[offset] = v.X
  343. array[offset+1] = v.Y
  344. array[offset+2] = v.Z
  345. return array
  346. }
  347. // MultiplyVectors multiply vectors a and b storing the result in this vector.
  348. // Returns the pointer to this updated vector.
  349. func (v *Vector3) MultiplyVectors(a, b *Vector3) *Vector3 {
  350. v.X = a.X * b.X
  351. v.Y = a.Y * b.Y
  352. v.Z = a.Z * b.Z
  353. return v
  354. }
  355. // ApplyAxisAngle rotates the vector around axis by angle.
  356. // Returns the pointer to this updated vector.
  357. func (v *Vector3) ApplyAxisAngle(axis *Vector3, angle float32) *Vector3 {
  358. var quaternion Quaternion
  359. v.ApplyQuaternion(quaternion.SetFromAxisAngle(axis, angle))
  360. return v
  361. }
  362. // ApplyMatrix3 multiplies the specified 3x3 matrix by this vector.
  363. // Returns the pointer to this updated vector.
  364. func (v *Vector3) ApplyMatrix3(m *Matrix3) *Vector3 {
  365. x := v.X
  366. y := v.Y
  367. z := v.Z
  368. v.X = m[0]*x + m[3]*y + m[6]*z
  369. v.Y = m[1]*x + m[4]*y + m[7]*z
  370. v.Z = m[2]*x + m[5]*y + m[8]*z
  371. return v
  372. }
  373. // ApplyMatrix4 multiplies the specified 4x4 matrix by this vector.
  374. // Returns the pointer to this updated vector.
  375. func (v *Vector3) ApplyMatrix4(m *Matrix4) *Vector3 {
  376. x := v.X
  377. y := v.Y
  378. z := v.Z
  379. v.X = m[0]*x + m[4]*y + m[8]*z + m[12]
  380. v.Y = m[1]*x + m[5]*y + m[9]*z + m[13]
  381. v.Z = m[2]*x + m[6]*y + m[10]*z + m[14]
  382. return v
  383. }
  384. // ApplyProjection applies the projection matrix m to this vector
  385. // Returns the pointer to this updated vector.
  386. func (v *Vector3) ApplyProjection(m *Matrix4) *Vector3 {
  387. x := v.X
  388. y := v.Y
  389. z := v.Z
  390. d := 1 / (m[3]*x + m[7]*y + m[11]*z + m[15]) // perspective divide
  391. v.X = (m[0]*x + m[4]*y + m[8]*z + m[12]) * d
  392. v.Y = (m[1]*x + m[5]*y + m[9]*z + m[13]) * d
  393. v.Z = (m[2]*x + m[6]*y + m[10]*z + m[14]) * d
  394. return v
  395. }
  396. // ApplyQuaternion transforms this vector by multiplying it by
  397. // the specified quaternion and then by the quaternion inverse.
  398. // It basically applies the rotation encoded in the quaternion to this vector.
  399. // Returns the pointer to this updated vector.
  400. func (v *Vector3) ApplyQuaternion(q *Quaternion) *Vector3 {
  401. x := v.X
  402. y := v.Y
  403. z := v.Z
  404. qx := q.X
  405. qy := q.Y
  406. qz := q.Z
  407. qw := q.W
  408. // calculate quat * vector
  409. ix := qw*x + qy*z - qz*y
  410. iy := qw*y + qz*x - qx*z
  411. iz := qw*z + qx*y - qy*x
  412. iw := -qx*x - qy*y - qz*z
  413. // calculate result * inverse quat
  414. v.X = ix*qw + iw*-qx + iy*-qz - iz*-qy
  415. v.Y = iy*qw + iw*-qy + iz*-qx - ix*-qz
  416. v.Z = iz*qw + iw*-qz + ix*-qy - iy*-qx
  417. return v
  418. }
  419. // Cross calculates the cross product of this vector with other and returns the result vector.
  420. func (v *Vector3) Cross(other *Vector3) *Vector3 {
  421. cx := v.Y*other.Z - v.Z*other.Y
  422. cy := v.Z*other.X - v.X*other.Z
  423. cz := v.X*other.Y - v.Y*other.X
  424. v.X = cx
  425. v.Y = cy
  426. v.Z = cz
  427. return v
  428. }
  429. // CrossVectors calculates the cross product of a and b storing the result in this vector.
  430. // Returns the pointer to this updated vector.
  431. func (v *Vector3) CrossVectors(a, b *Vector3) *Vector3 {
  432. cx := a.Y*b.Z - a.Z*b.Y
  433. cy := a.Z*b.X - a.X*b.Z
  434. cz := a.X*b.Y - a.Y*b.X
  435. v.X = cx
  436. v.Y = cy
  437. v.Z = cz
  438. return v
  439. }
  440. // ProjectOnVector sets this vector to its projection on other vector.
  441. // Returns the pointer to this updated vector.
  442. func (v *Vector3) ProjectOnVector(other *Vector3) *Vector3 {
  443. var on Vector3
  444. on.Copy(other).Normalize()
  445. dot := v.Dot(&on)
  446. return v.Copy(&on).MultiplyScalar(dot)
  447. }
  448. // ProjectOnPlane sets this vector to its projection on the plane
  449. // specified by its normal vector.
  450. // Returns the pointer to this updated vector.
  451. func (v *Vector3) ProjectOnPlane(planeNormal *Vector3) *Vector3 {
  452. var tmp Vector3
  453. tmp.Copy(v).ProjectOnVector(planeNormal)
  454. return v.Sub(&tmp)
  455. }
  456. // Reflect sets this vector to its reflection relative to the normal vector.
  457. // The normal vector is assumed to be normalized.
  458. // Returns the pointer to this updated vector.
  459. func (v *Vector3) Reflect(normal *Vector3) *Vector3 {
  460. var tmp Vector3
  461. return v.Sub(tmp.Copy(normal).MultiplyScalar(2 * v.Dot(normal)))
  462. }
  463. // AngleTo returns the angle between this vector and other
  464. func (v *Vector3) AngleTo(other *Vector3) float32 {
  465. theta := v.Dot(other) / (v.Length() * other.Length())
  466. // clamp, to handle numerical problems
  467. return Acos(Clamp(theta, -1, 1))
  468. }
  469. // SetFromMatrixPosition set this vector from the translation coordinates
  470. // in the specified transformation matrix.
  471. func (v *Vector3) SetFromMatrixPosition(m *Matrix4) *Vector3 {
  472. v.X = m[12]
  473. v.Y = m[13]
  474. v.Z = m[14]
  475. return v
  476. }
  477. // SetFromMatrixColumn set this vector with the column at index of the m matrix.
  478. // Returns the pointer to this updated vector.
  479. func (v *Vector3) SetFromMatrixColumn(index int, m *Matrix4) *Vector3 {
  480. offset := index * 4
  481. v.X = m[offset]
  482. v.Y = m[offset+1]
  483. v.Z = m[offset+2]
  484. return v
  485. }
  486. // Clone returns a copy of this vector
  487. func (v *Vector3) Clone() *Vector3 {
  488. return NewVector3(v.X, v.Y, v.Z)
  489. }
  490. // SetFromRotationMatrix sets this vector components to the Euler angles
  491. // from the specified pure rotation matrix.
  492. // Returns the pointer to this updated vector.
  493. func (v *Vector3) SetFromRotationMatrix(m *Matrix4) *Vector3 {
  494. m11 := m[0]
  495. m12 := m[4]
  496. m13 := m[8]
  497. m22 := m[5]
  498. m23 := m[9]
  499. m32 := m[6]
  500. m33 := m[10]
  501. v.Y = Asin(Clamp(m13, -1, 1))
  502. if Abs(m13) < 0.99999 {
  503. v.X = Atan2(-m23, m33)
  504. v.Z = Atan2(-m12, m11)
  505. } else {
  506. v.X = Atan2(m32, m22)
  507. v.Z = 0
  508. }
  509. return v
  510. }
  511. // SetFromQuaternion sets this vector components to the Euler angles
  512. // from the specified quaternion
  513. // Returns the pointer to this updated vector.
  514. func (v *Vector3) SetFromQuaternion(q *Quaternion) *Vector3 {
  515. matrix := NewMatrix4()
  516. matrix.MakeRotationFromQuaternion(q)
  517. v.SetFromRotationMatrix(matrix)
  518. return v
  519. }
  520. // RandomTangents computes and returns two arbitrary tangents to the vector.
  521. func (v *Vector3) RandomTangents() (*Vector3, *Vector3) {
  522. t1 := NewVector3(0,0,0)
  523. t2 := NewVector3(0,0,0)
  524. length := v.Length()
  525. if length > 0 {
  526. n := NewVector3(v.X/length, v.Y/length, v.Z/length)
  527. randVec := NewVector3(0,0,0)
  528. if Abs(n.X) < 0.9 {
  529. randVec.SetX(1)
  530. t1.CrossVectors(n, randVec)
  531. } else if Abs(n.Y) < 0.9 {
  532. randVec.SetY(1)
  533. t1.CrossVectors(n, randVec)
  534. } else {
  535. randVec.SetZ(1)
  536. t1.CrossVectors(n, randVec)
  537. }
  538. t2.CrossVectors(n, t1)
  539. } else {
  540. t1.SetX(1)
  541. t2.SetY(1)
  542. }
  543. return t1, t2
  544. }