June 18, 2021, 07:08:53 AM

### Author Topic: [bb] Vector 3D Math Library [v1.7] by Chroma [ 1+ years ago ]  (Read 1442 times)

#### BlitzBot

• Jr. Member
• Posts: 1
##### [bb] Vector 3D Math Library [v1.7] by Chroma [ 1+ years ago ]
« on: June 29, 2017, 12:28:42 AM »
Title : Vector 3D Math Library [v1.7]
Author : Chroma
Posted : 1+ years ago

Description : Here's my conversion of the Vector3D functions from C++. I originally posted this in the archives over 2 years ago.  I've recently perused the code and made some improvements.  Hopefully you'll find this immensely useful because I know I have.  Have fun!

-Last Updated on November 30, 2004

v1.0 initial release Sept 15, 2002
v1.1 fixed errors in crossproduct Sept 17, 2002
v1.2 cleaned up some functions July 15, 2004
v1.3 most functions return vectors now! July 22,2004
v1.4 added function AddVectorTimeStep for easier physics use - July 23, 2004
v1.5 vTmp was not a good idea for internal calcs - caused vector bleeding - fixed! - July 23, 2004
v1.6 changed ReverseVector to use 2 vectors for ease of use
v1.7 renamed and rearranged the code slightly

Code :
Code: BlitzBasic
1. ;// Vector Math Library v1.7
2. ;// by Chroma
3.
4. ;// Last Update: November 30, 2004
5. ;// Comments: Renamed and rearranged the code slightly
6.
7.
8. ;----------------------------------------------------------------------;
9. ;// Testing...
10. ;// Remove ";--" in front of lines to see the Vectory Library test demo
11. ;--Graphics 400,300,16,2
12. ;--SetBuffer BackBuffer()
13. ;--AppTitle "Vector 3D Math Library v1.7 - Vector Addition Test"
14.
15. ;// Create two test vectors
16. ;--this.Vector = Vector()
17. ;--that.Vector = Vector(1,2,3)
18.
19. ;// Loop
20. ;--While Not KeyHit(1)
21. ;--Cls
22.
24. ;--Vector_Show(this,10,10,"Test")
25.
26. ;--Flip
27. ;--Wend
28. ;--End
29. ;//...End Test
30. ;----------------------------------------------------------------------;
31.
32.
33. ;// Tolerance
34. Const tol# = 0.001
35.
36.
37. ;// Vector Type
38. Type Vector
39.         Field x#
40.         Field y#
41.         Field z#
42. End Type
43.
44.
45. ;// Create a Vector
46. ;// Example: this.Vector = Vector()
47. ;// Example: this.Vector = Vector(1,2,3)
48. Function Vector.Vector(x#=0,y#=0,z#=0)
49.         v.Vector = New Vector
50.         vx=x
51.         vy=y
52.         vz=z
53.         Return v
54. End Function
55.
56.
57. ;// Set a Vector with New Components
58. Function Vector_Set(v.Vector,x#,y#,z#)
59.         vx = x
60.         vy = y
61.         vz = z
62. End Function
63.
64.
65. ;// Vector Component Set
66. ;// Example 1: Vector_SetX(this.Vector,1.0)
67. ;// Example 2: thisx = 1.0
68. Function Vector_SetX(v.Vector,x#)
69.         vx = x
70. End Function
71.
72. Function Vector_SetY(v.Vector,y#)
73.         vy = y
74. End Function
75.
76. Function Vector_SetZ(v.Vector,z#)
77.         vz = z
78. End Function
79.
80.
81. ;// Vector Component Retrieval
82. ;// Example 1: myvar# = Vector_GetX(this.Vector)
83. ;// Example 2: myvar# = thisx
84. Function Vector_GetX#(v.Vector)
85.         Return vx
86. End Function
87.
88. Function Vector_GetY#(v.Vector)
89.         Return vy
90. End Function
91.
92. Function Vector_GetZ#(v.Vector)
93.         Return vz
94. End Function
95.
96.
98. ;// Form of: Vector1 = Vector2 + Vector3
100.         v1x = v2x + v3x
101.         v1y = v2y + v3y
102.         v1z = v2z + v3z
103. End Function
104.
105.
107. ;// Form of: Vector1 = Vector2 + Scalar#
109.         v1x = v2x + s
110.         v1y = v2y + s
111.         v1z = v2z + s
112. End Function
113.
114.
115. ;// Vector Addition * Time Step
116. ;// Form of: Vector1 = Vector1 + Vector2 * Time_Step#
118.         v1x = v1x + v2x * time_step
119.         v1y = v1y + v2y * time_step
120.         v1z = v1z + v2z * time_step
121. End Function
122.
123.
124. ;// Vector Subtraction
125. ;// Form of: Vector1 = Vector2 - Vector3
126. Function Vector_Subtract(v1.Vector,v2.Vector,v3.Vector)
127.         v1x = v2x - v3x
128.         v1y = v2y - v3y
129.         v1z = v2z - v3z
130. End Function
131.
132.
133. ;// Vector Scalar Subtraction
134. ;// Form of: Vector1 = Vector2 - Scalar#
135. Function Vector_SubtractScalar.Vector(v1.Vector,v2.Vector,s#)
136.         v1x = v2x - s
137.         v1y = v2y - s
138.         v1z = v2z - s
139. End Function
140.
141.
142. ;// Vector Scalar Multiplication
143. ;// Form of: Vector1 = Vector2 * Scalar#
144. Function Vector_MultiplyScalar(v1.Vector,v2.Vector,s#)
145.         v1x = v2x * s
146.         v1y = v2y * s
147.         v1z = v2z * s
148. End Function
149.
150.
151. ;// Vector Scalar Division
152. ;// Form of: Vector1 = Vector1 / Scalar#
153. Function Vector_DivideScalar(v1.Vector,v2.Vector,s#)
154.         v1x = v2x / s
155.         v1y = v2y / s
156.         v1z = v2z / s
157. End Function
158.
159.
160. ;// Cross Product
161. ;// Form of: Vector1 = U.Vector |CrossProduct| V.Vector
162. Function Vector_CrossProduct(v1.Vector,u.Vector,v.Vector)
163.         v1x =  uy * vz  -  uz * vy
164.         v1y = -ux * vz  +  uz * vx
165.         v1z =  ux * vy  -  uy * vx
166. End Function
167.
168.
169. ;// Dot Product
170. Function Vector_DotProduct#(u.Vector,v.Vector)
171.         Return ux * vx + uy * vy + uz * vz
172. End Function
173.
174.
175. ;// Magnitude
176. ;// Example: this_magnitude# = Vector_Magnitude(this.Vector)
177. Function Vector_Magnitude#(v.Vector)
178.         Return Sqr(vx * vx + vy * vy + vz * vz)
179. End Function
180.
181.
182. ;// Normalize
183. ;// Example: Vector_Normalize(this.Vector)
184. Function Vector_Normalize(v.Vector)
185.         mag#=Sqr(vx * vx + vy * vy + vz * vz)
186.         vx = vx / mag
187.         vy = vy / mag
188.         vz = vz / mag
189.         If (Abs(vx) < tol) vx = 0.0
190.         If (Abs(vy) < tol) vy = 0.0
191.         If (Abs(vz) < tol) vz = 0.0
192. End Function
193.
194.
195. ;// Reverse a Vector
196. ;// Form of: Vector1 = -Vector2
197. ;// Example: Vector_Reverse(this.Vector,that.Vector)
198. Function Vector_Reverse(v1.Vector,v2.Vector)
199.         v1x = -v2x
200.         v1y = -v2y
201.         v1z = -v2z
202. End Function
203.
204.
205. ;// Reset a Vector to Zero
206. ;// Example: Vector_Reset(this.Vector)
207. Function Vector_Reset(v.Vector)
208.         vx = 0.0
209.         vy = 0.0
210.         vz = 0.0
211. End Function
212.
213.
214. ;// Vector 1 is set to Vector 2
215. ;// Example 1: Vector_Clone(this.Vector,that.Vector)
216. ;// Example 2: this.Vector = that.Vector
217. Function Vector_Clone(v1.Vector,v2.Vector)
218.         v1x = v2x
219.         v1y = v2y
220.         v1z = v2z
221. End Function
222.
223.
224. ;// Free a Vector
225. ;// Example: Vector_Free(this.Vector)
226. Function Vector_Free(v.Vector)
227.         Delete v
228. End Function
229.
230.
231. ;// PositionEntity Replacement for Vector Object
232. ;// Example: Vector_PositionEntity MyEntity,v.vector
233. Function Vector_PositionEntity(ent,v.vector)
234.         PositionEntity ent,vx,vy,vz
235. End Function
236.
237.
238. ;// Show Vector Values
239. ;// Place This Function After Renderworld
240. ;// Example: Vector_Show(this.Vector,15,15,"Test")
241. Function Vector_Show(v.Vector,xpos,ypos,label\$)
242.         Text xpos,ypos, label\$ + "_X=" + vx
243.         Text xpos,ypos + 15,label\$ + "_Y=" + vy
244.         Text xpos,ypos + 30,label\$ + "_Z=" + vz
245. End Function
246.
247.
248. ;// Degrees To Radians Conversion
250.         Return deg * Pi / 180.0
251. End Function
252.
253.
254. ;// Radians To Degrees Conversion
256.         Return rad * 180.0 / Pi
257. End Function

LarsG(Posted 1+ years ago)

Hey Chroma..I enhanced your code a little bit.. I hope you don't mind?!
Code: [Select]
`Strict'// Vector Math Library v0.9'// by Chroma'// rewritten, extended and OOP'ified for use in BlitzMax by LarsG'// Last Update: June 23, 2005'// Comments: Enhanced and OOP'ified by LarsG'----------------------------------------------------------------------;'// Testing...Global vec1:TVectorFGlobal vec2:TVectorF'// Create two test vectorsvec1 = TVectorF.Create(1,2,3)vec2 = TVectorF.Create()Print "Vec1: "Print vec1.show(", ")Print "vec2 cloning vec1..."vec2.clone(vec1)Print "Vec2: "Print vec2.show(", ")Print "Adding vec2 to vec1..."vec1.add(vec2)Print "Vec1: "Print vec1.Show(", ")End'//...End Test'----------------------------------------------------------------------;'// Vector Type Float (32 Bit)Type TVectorF Field x:Float Field y:Float Field z:Float Const TOL:Float = 0.001 '**** THE METHODS ***** Function Create:TVectorF(x:Float=0, y:Float=0, z:Float=0) Local v:TVectorF = New TVectorF v.x = x v.y = y v.z = z Return v EndFunction Method Set(x:Float, y:Float, z:Float) self.x = x self.y = y self.z = z EndMethod Method SetX(x:Float) self.x = x EndMethod Method SetY(y:Float) self.y = y EndMethod Method SetZ(z:Float) self.z = z EndMethod Method GetX:Float() Return self.x EndMethod Method GetY:Float() Return self.y EndMethod Method GetZ:Float() Return self.z EndMethod Method Add(plus:TVectorF) self.x :+ plus.x self.y :+ plus.y self.z :+ plus.z EndMethod Method AddScalar(scale:Float) self.x :+ scale self.y :+ scale self.z :+ scale EndMethod Method AddTimeStep(plus:TVectorF, tstep:Float) self.x :+ (plus.x * tstep) self.y :+ (plus.y * tstep) self.z :+ (plus.z * tstep) EndMethod Method Subtract(sub:TVectorF) self.x :- sub.x self.y :- sub.y self.z :- sub.z EndMethod Method SubtractScalar(scale:Float) self.x :- scale self.y :- scale self.z :- scale EndMethod Method SubtractTimeStep(sub:TVectorF, tstep:Float) self.x :- (sub.x * tstep) self.y :- (sub.y * tstep) self.z :- (sub.z * tstep) EndMethod Method DivideScalar(scale:Float) self.x :/ scale self.y :/ scale self.z :/ scale EndMethod Method CrossProduct(vec1:TVectorF, vec2:TVectorF) self.x =  vec1.y * vec2.z  -  vec1.z * vec2.y self.y = -vec1.x * vec2.z  +  vec1.z * vec2.x self.z =  vec1.x * vec2.y  -  vec1.y * vec2.x EndMethod Method DotProduct:Float(vec:TVectorF) Return vec.x * self.x + vec.y * self.y + vec.z * self.z EndMethod Method Magnitude:Float() Return Sqr(self.x * self.x + self.y * Self.y + self.z * self.z) EndMethod Method Normalize() Local magnitude:Float = self.Magnitude() self.x :/ magnitude self.y :/ magnitude self.z :/ magnitude If (Abs(self.x) < self.TOL) Then self.x = 0.0 If (Abs(self.y) < self.TOL) Then self.y = 0.0 If (Abs(self.z) < self.TOL) Then self.z = 0.0 EndMethod Method Reverse(vec:TVectorF) self.x = -vec.x self.y = -vec.y self.z = -vec.z EndMethod Method Reset() self.x = 0 self.y = 0 self.z = 0 EndMethod Method Clone(vec:TVectorF) ' not sure if it's neccesary to do it this way.. ' oh well.. it's there anyway ' maybe self = vec will do.. self.x = vec.x self.y = vec.y self.z = vec.z EndMethod Method Show:String(sep:String) Return String(self.x) + sep + .. String(self.y) + sep + .. String(self.z) EndMethodEndType'// Vector Type Double (64 Bit)Type TVectorD Field x:Double Field y:Double Field z:Double Const TOL:Double = 0.001 '**** THE METHODS ***** Function Create:TVectorD(x:Double=0, y:Double=0, z:Double=0) Local v:TVectorD = New TVectorD v.x = x v.y = y v.z = z Return v EndFunction Method Set(x:Double, y:Double, z:Double) self.x = x self.y = y self.z = z EndMethod Method SetX(x:Double) self.x = x EndMethod Method SetY(y:Double) self.y = y EndMethod Method SetZ(z:Double) self.z = z EndMethod Method GetX:Double() Return self.x EndMethod Method GetY:Double() Return self.y EndMethod Method GetZ:Double() Return self.z EndMethod Method Add(plus:TVectorD) self.x :+ plus.x self.y :+ plus.y self.z :+ plus.z EndMethod Method AddScalar(scale:Double) self.x :+ scale self.y :+ scale self.z :+ scale EndMethod Method AddTimeStep(plus:TVectorD, tstep:Double) self.x :+ (plus.x * tstep) self.y :+ (plus.y * tstep) self.z :+ (plus.z * tstep) EndMethod Method Subtract(sub:TVectorD) self.x :- sub.x self.y :- sub.y self.z :- sub.z EndMethod Method SubtractScalar(scale:Double) self.x :- scale self.y :- scale self.z :- scale EndMethod Method SubtractTimeStep(sub:TVectorD, tstep:Double) self.x :- (sub.x * tstep) self.y :- (sub.y * tstep) self.z :- (sub.z * tstep) EndMethod Method DivideScalar(scale:Double) self.x :/ scale self.y :/ scale self.z :/ scale EndMethod Method CrossProduct(vec1:TVectorD, vec2:TVectorD) self.x =  vec1.y * vec2.z  -  vec1.z * vec2.y self.y = -vec1.x * vec2.z  +  vec1.z * vec2.x self.z =  vec1.x * vec2.y  -  vec1.y * vec2.x EndMethod Method DotProduct:Double(vec:TVectorD) Return vec.x * self.x + vec.y * self.y + vec.z * self.z EndMethod Method Magnitude:Double() Return Sqr(self.x * self.x + self.y * Self.y + self.z * self.z) EndMethod Method Normalize() Local magnitude:Double = self.Magnitude() self.x :/ magnitude self.y :/ magnitude self.z :/ magnitude If (Abs(self.x) < self.TOL) Then self.x = 0.0 If (Abs(self.y) < self.TOL) Then self.y = 0.0 If (Abs(self.z) < self.TOL) Then self.z = 0.0 EndMethod Method Reverse(vec:TVectorD) self.x = -vec.x self.y = -vec.y self.z = -vec.z EndMethod Method Reset() self.x = 0 self.y = 0 self.z = 0 EndMethod Method Clone(vec:TVectorD) self.x = vec.x self.y = vec.y self.z = vec.z EndMethod Method Show:String(sep:String) Return String(self.x) + sep + .. String(self.y) + sep + .. String(self.z) EndMethodEndType`

Braincell(Posted 1+ years ago)

Thanks. I will probably use some of this in my free stencil shadows library, incl your credits.

Chroma(Posted 1+ years ago)

I'm guessing that's it converted to BMax.  Looks pretty nice.  I personally would have substituted the word "self" for "this". :)Just looking at your conversion makes me want to buy BMax right now...but I'm gonna wait until the OpenGL module is totally complete.  I hate hacking graphics.

LarsG(Posted 1+ years ago)

Yeah.. I basically converted it.. and added the option of using Doubles as well..Hope I got it right.. (seeing as I'm not very good at this kind of math.. just followed your calculations.. )side note; cool that the code makes you want to buy BMax right away.. hehe.. and you should.. that way you can play with it, and make yourself familiar with it, until the 3D module is released..

Chroma(Posted 1+ years ago)

Just bought bmax today and I'm finishing up my vector lib conversion...and it's looks pretty darn similar to yours.  Nice job there LarsG.

Chroma(Posted 1+ years ago)

I took out the Reset command.  Seems very unnecessary since you can just do a:vPos.Set(0,0,0)Also set the Set command to default x,y,z to 0.  So you could also just do a:vPos.Set()Edit:  Also took out the SetX,Y,Z and GetX,Y,Z since you can access them directly with something like:vPos.x = 20Local this:Float = vPos.xStill tweaking here. [/i]