Graphviz 13.1.2~dev.20250807.2324
Loading...
Searching...
No Matches
arcball.h
Go to the documentation of this file.
1
18/*************************************************************/
19
20/*************************************************************************************/
42/*************************************************************************************/
43
44#pragma once
45
46// 8<--Snip here if you have your own math types/funcs-->8
47
48# include <assert.h>
49
50//Math types derived from the KempoApi tMath library
51typedef union {
52 struct {
53 float X, Y;
54 } s;
55
56 float T[2];
57} Tuple2fT; //A generic 2-element tuple that is represented by single-precision floating point x,y coordinates.
58
59typedef union {
60 struct {
61 float X, Y, Z;
62 } s;
63
64 float T[3];
65} Tuple3fT; //A generic 3-element tuple that is represented by single precision-floating point x,y,z coordinates.
66
67typedef union {
68 struct {
69 float X, Y, Z, W;
70 } s;
71
72 float T[4];
73} Tuple4fT; //A 4-element tuple represented by single-precision floating point x,y,z,w coordinates.
74
75typedef union {
76 float M[9];
77 struct {
78 //column major
79 union {
80 float M00;
81 float XX;
82 float SX;
83 }; //XAxis.X and Scale X
84 union {
85 float M10;
86 float XY;
87 }; //XAxis.Y
88 union {
89 float M20;
90 float XZ;
91 }; //XAxis.Z
92 union {
93 float M01;
94 float YX;
95 }; //YAxis.X
96 union {
97 float M11;
98 float YY;
99 float SY;
100 }; //YAxis.Y and Scale Y
101 union {
102 float M21;
103 float YZ;
104 }; //YAxis.Z
105 union {
106 float M02;
107 float ZX;
108 }; //ZAxis.X
109 union {
110 float M12;
111 float ZY;
112 }; //ZAxis.Y
113 union {
114 float M22;
115 float ZZ;
116 float SZ;
117 }; //ZAxis.Z and Scale Z
118 } s;
119} Matrix3fT; //A single precision floating point 3 by 3 matrix.
120
121typedef union {
122 float M[16];
123 struct {
124 //column major
125 union {
126 float M00;
127 float XX;
128 float SX;
129 }; //XAxis.X and Scale X
130 union {
131 float M10;
132 float XY;
133 }; //XAxis.Y
134 union {
135 float M20;
136 float XZ;
137 }; //XAxis.Z
138 union {
139 float M30;
140 float XW;
141 }; //XAxis.W
142 union {
143 float M01;
144 float YX;
145 }; //YAxis.X
146 union {
147 float M11;
148 float YY;
149 float SY;
150 }; //YAxis.Y and Scale Y
151 union {
152 float M21;
153 float YZ;
154 }; //YAxis.Z
155 union {
156 float M31;
157 float YW;
158 }; //YAxis.W
159 union {
160 float M02;
161 float ZX;
162 }; //ZAxis.X
163 union {
164 float M12;
165 float ZY;
166 }; //ZAxis.Y
167 union {
168 float M22;
169 float ZZ;
170 float SZ;
171 }; //ZAxis.Z and Scale Z
172 union {
173 float M32;
174 float ZW;
175 }; //ZAxis.W
176 union {
177 float M03;
178 float TX;
179 }; //Trans.X
180 union {
181 float M13;
182 float TY;
183 }; //Trans.Y
184 union {
185 float M23;
186 float TZ;
187 }; //Trans.Z
188 union {
189 float M33;
190 float TW;
191 float SW;
192 }; //Trans.W and Scale W
193 } s;
194} Matrix4fT; //A single precision floating point 4 by 4 matrix.
195
196
197//"Inherited" types
198#define Point2fT Tuple2fT //A 2 element point that is represented by single precision floating point x,y coordinates.
199
200#define Quat4fT Tuple4fT //A 4 element unit quaternion represented by single precision floating point x,y,z,w coordinates.
201
202#define Vector3fT Tuple3fT //A 3-element vector that is represented by single-precision floating point x,y,z coordinates.
203
204//Custom math, or speed overrides
205#define FuncSqrt sqrtf
206
207//utility macros
208//assuming IEEE-754(float), which i believe has max precision of 7 bits
209# define Epsilon 1.0e-5
210
211//Math functions
212
213#ifdef ARCBALL_C
220static void Vector3fCross(Vector3fT * NewObj, const Vector3fT * v1,
221 const Vector3fT * v2)
222{
223 Vector3fT Result; //safe not to initialize
224
225 assert(NewObj && v1 && v2);
226
227 // store on stack once for aliasing-safty
228 // i.e. safe when a.cross(a, b)
229
230 Result.s.X = (v1->s.Y * v2->s.Z) - (v1->s.Z * v2->s.Y);
231 Result.s.Y = (v1->s.Z * v2->s.X) - (v1->s.X * v2->s.Z);
232 Result.s.Z = (v1->s.X * v2->s.Y) - (v1->s.Y * v2->s.X);
233
234 //copy result back
235 *NewObj = Result;
236}
237
243static float Vector3fDot(const Vector3fT * NewObj, const Vector3fT * v1)
244{
245 assert(NewObj && v1);
246
247 return (NewObj->s.X * v1->s.X) +
248 (NewObj->s.Y * v1->s.Y) + (NewObj->s.Z * v1->s.Z);
249}
250
256static float Vector3fLengthSquared(const Vector3fT * NewObj)
257{
258 assert(NewObj);
259
260 return (NewObj->s.X * NewObj->s.X) +
261 (NewObj->s.Y * NewObj->s.Y) + (NewObj->s.Z * NewObj->s.Z);
262}
263
269static float Vector3fLength(const Vector3fT * NewObj)
270{
271 assert(NewObj);
272
273 return FuncSqrt(Vector3fLengthSquared(NewObj));
274}
275
281 //$hack this can be optimized some(if s == 0)
282
283static void Matrix3fSetRotationFromQuat4f(Matrix3fT * NewObj,
284 const Quat4fT * q1)
285{
286 float n, s;
287 float xs, ys, zs;
288 float wx, wy, wz;
289 float xx, xy, xz;
290 float yy, yz, zz;
291
292 assert(NewObj && q1);
293
294 n = (q1->s.X * q1->s.X) + (q1->s.Y * q1->s.Y) + (q1->s.Z * q1->s.Z) +
295 (q1->s.W * q1->s.W);
296 s = (n > 0.0f) ? (2.0f / n) : 0.0f;
297
298 xs = q1->s.X * s;
299 ys = q1->s.Y * s;
300 zs = q1->s.Z * s;
301 wx = q1->s.W * xs;
302 wy = q1->s.W * ys;
303 wz = q1->s.W * zs;
304 xx = q1->s.X * xs;
305 xy = q1->s.X * ys;
306 xz = q1->s.X * zs;
307 yy = q1->s.Y * ys;
308 yz = q1->s.Y * zs;
309 zz = q1->s.Z * zs;
310
311 NewObj->s.XX = 1.0f - (yy + zz);
312 NewObj->s.YX = xy - wz;
313 NewObj->s.ZX = xz + wy;
314 NewObj->s.XY = xy + wz;
315 NewObj->s.YY = 1.0f - (xx + zz);
316 NewObj->s.ZY = yz - wx;
317 NewObj->s.XZ = xz - wy;
318 NewObj->s.YZ = yz + wx;
319 NewObj->s.ZZ = 1.0f - (xx + yy);
320}
321
328static void Matrix3fMulMatrix3f(Matrix3fT * NewObj, const Matrix3fT * m1)
329{
330 Matrix3fT Result; //safe not to initialize
331
332 assert(NewObj && m1);
333
334 // alias-safe way.
335 Result.s.M00 =
336 (NewObj->s.M00 * m1->s.M00) + (NewObj->s.M01 * m1->s.M10) +
337 (NewObj->s.M02 * m1->s.M20);
338 Result.s.M01 =
339 (NewObj->s.M00 * m1->s.M01) + (NewObj->s.M01 * m1->s.M11) +
340 (NewObj->s.M02 * m1->s.M21);
341 Result.s.M02 =
342 (NewObj->s.M00 * m1->s.M02) + (NewObj->s.M01 * m1->s.M12) +
343 (NewObj->s.M02 * m1->s.M22);
344
345 Result.s.M10 =
346 (NewObj->s.M10 * m1->s.M00) + (NewObj->s.M11 * m1->s.M10) +
347 (NewObj->s.M12 * m1->s.M20);
348 Result.s.M11 =
349 (NewObj->s.M10 * m1->s.M01) + (NewObj->s.M11 * m1->s.M11) +
350 (NewObj->s.M12 * m1->s.M21);
351 Result.s.M12 =
352 (NewObj->s.M10 * m1->s.M02) + (NewObj->s.M11 * m1->s.M12) +
353 (NewObj->s.M12 * m1->s.M22);
354
355 Result.s.M20 =
356 (NewObj->s.M20 * m1->s.M00) + (NewObj->s.M21 * m1->s.M10) +
357 (NewObj->s.M22 * m1->s.M20);
358 Result.s.M21 =
359 (NewObj->s.M20 * m1->s.M01) + (NewObj->s.M21 * m1->s.M11) +
360 (NewObj->s.M22 * m1->s.M21);
361 Result.s.M22 =
362 (NewObj->s.M20 * m1->s.M02) + (NewObj->s.M21 * m1->s.M12) +
363 (NewObj->s.M22 * m1->s.M22);
364
365 //copy result back to this
366 *NewObj = Result;
367}
368
369
370static void Matrix4fSetRotationScaleFromMatrix4f(Matrix4fT * NewObj,
371 const Matrix4fT * m1)
372{
373 assert(NewObj && m1);
374
375 NewObj->s.XX = m1->s.XX;
376 NewObj->s.YX = m1->s.YX;
377 NewObj->s.ZX = m1->s.ZX;
378 NewObj->s.XY = m1->s.XY;
379 NewObj->s.YY = m1->s.YY;
380 NewObj->s.ZY = m1->s.ZY;
381 NewObj->s.XZ = m1->s.XZ;
382 NewObj->s.YZ = m1->s.YZ;
383 NewObj->s.ZZ = m1->s.ZZ;
384}
385
394static float Matrix4fSVD(const Matrix4fT * NewObj, Matrix3fT * rot3,
395 Matrix4fT * rot4)
396{
397 float s, n;
398
399 assert(NewObj);
400
401 // this is a simple svd.
402 // Not complete but fast and reasonable.
403 // See comment in Matrix3d.
404
405 s = FuncSqrt(((NewObj->s.XX * NewObj->s.XX) +
406 (NewObj->s.XY * NewObj->s.XY) +
407 (NewObj->s.XZ * NewObj->s.XZ) +
408 (NewObj->s.YX * NewObj->s.YX) +
409 (NewObj->s.YY * NewObj->s.YY) +
410 (NewObj->s.YZ * NewObj->s.YZ) +
411 (NewObj->s.ZX * NewObj->s.ZX) +
412 (NewObj->s.ZY * NewObj->s.ZY) +
413 (NewObj->s.ZZ * NewObj->s.ZZ)) / 3.0f);
414
415 if (rot3) //if pointer not null
416 {
417 rot3->s.XX = NewObj->s.XX;
418 rot3->s.XY = NewObj->s.XY;
419 rot3->s.XZ = NewObj->s.XZ;
420 rot3->s.YX = NewObj->s.YX;
421 rot3->s.YY = NewObj->s.YY;
422 rot3->s.YZ = NewObj->s.YZ;
423 rot3->s.ZX = NewObj->s.ZX;
424 rot3->s.ZY = NewObj->s.ZY;
425 rot3->s.ZZ = NewObj->s.ZZ;
426
427 // zero-div may occur.
428
429 n = 1.0f / FuncSqrt((NewObj->s.XX * NewObj->s.XX) +
430 (NewObj->s.XY * NewObj->s.XY) +
431 (NewObj->s.XZ * NewObj->s.XZ));
432 rot3->s.XX *= n;
433 rot3->s.XY *= n;
434 rot3->s.XZ *= n;
435
436 n = 1.0f / FuncSqrt((NewObj->s.YX * NewObj->s.YX) +
437 (NewObj->s.YY * NewObj->s.YY) +
438 (NewObj->s.YZ * NewObj->s.YZ));
439 rot3->s.YX *= n;
440 rot3->s.YY *= n;
441 rot3->s.YZ *= n;
442
443 n = 1.0f / FuncSqrt((NewObj->s.ZX * NewObj->s.ZX) +
444 (NewObj->s.ZY * NewObj->s.ZY) +
445 (NewObj->s.ZZ * NewObj->s.ZZ));
446 rot3->s.ZX *= n;
447 rot3->s.ZY *= n;
448 rot3->s.ZZ *= n;
449 }
450
451 if (rot4) //if pointer not null
452 {
453 if (rot4 != NewObj) {
454 Matrix4fSetRotationScaleFromMatrix4f(rot4, NewObj); // private method
455 }
456 // zero-div may occur.
457
458 n = 1.0f / FuncSqrt((NewObj->s.XX * NewObj->s.XX) +
459 (NewObj->s.XY * NewObj->s.XY) +
460 (NewObj->s.XZ * NewObj->s.XZ));
461 rot4->s.XX *= n;
462 rot4->s.XY *= n;
463 rot4->s.XZ *= n;
464
465 n = 1.0f / FuncSqrt((NewObj->s.YX * NewObj->s.YX) +
466 (NewObj->s.YY * NewObj->s.YY) +
467 (NewObj->s.YZ * NewObj->s.YZ));
468 rot4->s.YX *= n;
469 rot4->s.YY *= n;
470 rot4->s.YZ *= n;
471
472 n = 1.0f / FuncSqrt((NewObj->s.ZX * NewObj->s.ZX) +
473 (NewObj->s.ZY * NewObj->s.ZY) +
474 (NewObj->s.ZZ * NewObj->s.ZZ));
475 rot4->s.ZX *= n;
476 rot4->s.ZY *= n;
477 rot4->s.ZZ *= n;
478 }
479
480 return s;
481}
482
483
484static void Matrix4fSetRotationScaleFromMatrix3f(Matrix4fT * NewObj,
485 const Matrix3fT * m1)
486{
487 assert(NewObj && m1);
488
489 NewObj->s.XX = m1->s.XX;
490 NewObj->s.YX = m1->s.YX;
491 NewObj->s.ZX = m1->s.ZX;
492 NewObj->s.XY = m1->s.XY;
493 NewObj->s.YY = m1->s.YY;
494 NewObj->s.ZY = m1->s.ZY;
495 NewObj->s.XZ = m1->s.XZ;
496 NewObj->s.YZ = m1->s.YZ;
497 NewObj->s.ZZ = m1->s.ZZ;
498}
499
500
501static void Matrix4fMulRotationScale(Matrix4fT * NewObj, float scale)
502{
503 assert(NewObj);
504
505 NewObj->s.XX *= scale;
506 NewObj->s.YX *= scale;
507 NewObj->s.ZX *= scale;
508 NewObj->s.XY *= scale;
509 NewObj->s.YY *= scale;
510 NewObj->s.ZY *= scale;
511 NewObj->s.XZ *= scale;
512 NewObj->s.YZ *= scale;
513 NewObj->s.ZZ *= scale;
514}
515
527static void Matrix4fSetRotationFromMatrix3f(Matrix4fT * NewObj,
528 const Matrix3fT * m1)
529{
530 float scale;
531
532 assert(NewObj && m1);
533
534 scale = Matrix4fSVD(NewObj, NULL, NULL);
535
536 Matrix4fSetRotationScaleFromMatrix3f(NewObj, m1);
537 Matrix4fMulRotationScale(NewObj, scale);
538}
539#endif
540
541// 8<--Snip here if you have your own math types/funcs-->8
555
556
557void init_arcBall(ArcBall_t * a, float NewWidth, float NewHeight);
558void arcmouseClick(void);
559void arcmouseDrag(void);
#define Quat4fT
Definition arcball.h:200
void arcmouseClick(void)
Definition arcball.c:142
void arcmouseDrag(void)
Definition arcball.c:150
void init_arcBall(ArcBall_t *a, float NewWidth, float NewHeight)
Definition arcball.c:88
#define FuncSqrt
Definition arcball.h:205
#define Vector3fT
Definition arcball.h:202
#define Point2fT
Definition arcball.h:198
#define Y(i)
Definition gdefs.h:3
#define X(prefix, name, str, type, subtype,...)
Definition gdefs.h:14
static pointf scale(double c, pointf p)
Definition geomprocs.h:155
node NULL
Definition grammar.y:180
#define M
Definition randomkit.c:90
Vector3fT EnVec
Definition arcball.h:544
Point2fT MousePt
Definition arcball.h:550
Matrix3fT LastRot
Definition arcball.h:548
Matrix3fT ThisRot
Definition arcball.h:549
Matrix4fT Transform
Definition arcball.h:547
float AdjustWidth
Definition arcball.h:545
int isDragging
Definition arcball.h:553
int isClicked
Definition arcball.h:551
float AdjustHeight
Definition arcball.h:546
int isRClicked
Definition arcball.h:552
Vector3fT StVec
Definition arcball.h:543
static mytime_t T
Definition timing.c:41
float YY
Definition arcball.h:98
float M02
Definition arcball.h:106
float YZ
Definition arcball.h:103
struct Matrix3fT::@3 s
float M01
Definition arcball.h:93
float SX
Definition arcball.h:82
float XX
Definition arcball.h:81
float M10
Definition arcball.h:85
float SY
Definition arcball.h:99
float M21
Definition arcball.h:102
float M00
Definition arcball.h:80
float ZY
Definition arcball.h:111
float M22
Definition arcball.h:114
float M20
Definition arcball.h:89
float XY
Definition arcball.h:86
float M12
Definition arcball.h:110
float SZ
Definition arcball.h:116
float XZ
Definition arcball.h:90
float ZZ
Definition arcball.h:115
float M11
Definition arcball.h:97
float ZX
Definition arcball.h:107
float YX
Definition arcball.h:94
float ZX
Definition arcball.h:161
float M00
Definition arcball.h:126
float XX
Definition arcball.h:127
float M02
Definition arcball.h:160
float M13
Definition arcball.h:181
float M01
Definition arcball.h:143
float XW
Definition arcball.h:140
struct Matrix4fT::@22 s
float SY
Definition arcball.h:149
float ZY
Definition arcball.h:165
float M32
Definition arcball.h:173
float TZ
Definition arcball.h:186
float TX
Definition arcball.h:178
float XY
Definition arcball.h:132
float SX
Definition arcball.h:128
float YW
Definition arcball.h:157
float SW
Definition arcball.h:191
float M12
Definition arcball.h:164
float M03
Definition arcball.h:177
float M33
Definition arcball.h:189
float M10
Definition arcball.h:131
float YX
Definition arcball.h:144
float M21
Definition arcball.h:152
float ZW
Definition arcball.h:174
float M31
Definition arcball.h:156
float M11
Definition arcball.h:147
float M30
Definition arcball.h:139
float M22
Definition arcball.h:168
float SZ
Definition arcball.h:170
float XZ
Definition arcball.h:136
float TW
Definition arcball.h:190
float M20
Definition arcball.h:135
float TY
Definition arcball.h:182
float YY
Definition arcball.h:148
float ZZ
Definition arcball.h:169
float YZ
Definition arcball.h:153
float M23
Definition arcball.h:185
float X
Definition arcball.h:53
float X
Definition arcball.h:61
float W
Definition arcball.h:69
Definition grammar.c:89