1
2 #include "3dc.h"
3
4 #include <math.h>
5
6 #include "inline.h"
7 #include "module.h"
8 #include "stratdef.h"
9 #include "gamedef.h"
10 #include "bh_types.h"
11 #include "pvisible.h"
12
13 #include "kzsort.h"
14 #include "kshape.h"
15
16 /*
17
18 Platform Specific Functions
19
20 These functions have been written specifically for a given platform.
21
22 They are not necessarily IO or inline functions; these have their own files.
23
24 */
25
26
27 /*
28
29 externs for commonly used global variables and arrays
30
31 */
32
33 extern VECTORCH RotatedPts[];
34 extern unsigned int Outcodes[];
35 extern DISPLAYBLOCK *Global_ODB_Ptr;
36 extern VIEWDESCRIPTORBLOCK *Global_VDB_Ptr;
37 extern SHAPEHEADER *Global_ShapeHeaderPtr;
38 extern MATRIXCH LToVMat;
39 #if SupportMorphing
40 extern VECTORCH MorphedPts[];
41 extern MORPHDISPLAY MorphDisplay;
42 #endif
43
44 extern DISPLAYBLOCK *OnScreenBlockList[];
45 extern int NumOnScreenBlocks;
46 extern int NumActiveBlocks;
47 extern DISPLAYBLOCK *ActiveBlockList[];
48 #if SupportModules
49 extern char *ModuleLocalVisArray;
50 #endif
51
52
53
54 /*
55
56 Global Variables
57
58 */
59
60 LONGLONGCH ll_one14 = {one14, 0};
61 LONGLONGCH ll_zero = {0, 0};
62
63
64
65
66
67
68 /*
69
70 Find out which objects are in the View Volume.
71
72 The list of these objects, "OnScreenBlockList", is constructed in a number
73 of stages.
74
75 The Range Test is a simple outcode of the View Space Location against the
76 Object Radius. The View Volume Test is more involved. The VSL is tested
77 against each of the View Volume Planes. If it is more than one Object Radius
78 outside any plane, the test fails.
79
80 */
81
82 /*
83
84 This is the main view volume test shell
85
86 */
87
88
89
90
91
92
93
94
95 #if StandardShapeLanguage
96
97
98 /*
99
100 Shape Points
101
102 The item array is a table of pointers to item arrays. The points data is
103 in the first and only item array.
104
105 Rotate each point and write it out to the Rotated Points Buffer
106
107 NOTE:
108
109 There is a global pointer to the shape header "Global_ShapeHeaderPtr"
110
111 */
112
113
114 #define print_bfcro_stats No
115
116 #if SupportMorphing
117 #define checkmorphpts No
118 #endif
119
120
ShapePointsInstr(SHAPEINSTR * shapeinstrptr)121 void ShapePointsInstr(SHAPEINSTR *shapeinstrptr)
122
123 {
124
125 int **shapeitemarrayptr;
126 int *shapeitemptr;
127 VECTORCH *rotptsptr;
128 int x, y, z;
129 int numitems;
130 #if print_bfcro_stats
131 int num_rot, num_not_rot;
132 #endif
133
134
135
136 /*
137
138 Kevin, morphed doors WON'T be using shared points, so I've put your
139 patch here, AFTER the intercept for the shared version of the points
140 instruction -- Chris.
141
142 */
143
144 #if KZSORT_ON /* KJL 15:13:46 02/07/97 - used for z-sorting doors correctly! */
145 {
146 extern int *MorphedObjectPointsPtr;
147 MorphedObjectPointsPtr = 0;
148 }
149 #endif
150
151
152 /* Set up pointers */
153
154 shapeitemarrayptr = shapeinstrptr->sh_instr_data;
155 shapeitemptr = *shapeitemarrayptr;
156 rotptsptr = &RotatedPts[0];
157
158
159
160 #if SupportMorphing
161
162 if(Global_ODB_Ptr->ObMorphCtrl) {
163
164
165 #if LazyEvaluationForMorphing
166
167 VECTORCH *morphptsptr;
168
169 if(Global_ODB_Ptr->ObMorphedPts == 0) {
170
171 Global_ODB_Ptr->ObMorphedPts = GetMorphedPts(Global_ODB_Ptr,
172 &MorphDisplay);
173
174 }
175
176 morphptsptr = Global_ODB_Ptr->ObMorphedPts;
177
178 GLOBALASSERT(shapeinstrptr->sh_numitems<maxmorphPts);
179
180 for(numitems = shapeinstrptr->sh_numitems; numitems!=0; numitems--) {
181
182 #if SUPPORT_MMX
183 if (use_mmx_math)
184 MMX_VectorTransformedAndAdd(rotptsptr,morphptsptr,<oVMat,&Global_ODB_Ptr->ObView);
185 else
186 #endif
187 {
188 rotptsptr->vx = MUL_FIXED(LToVMat.mat11, morphptsptr->vx);
189 rotptsptr->vx += MUL_FIXED(LToVMat.mat21, morphptsptr->vy);
190 rotptsptr->vx += MUL_FIXED(LToVMat.mat31, morphptsptr->vz);
191 rotptsptr->vx += Global_ODB_Ptr->ObView.vx;
192
193 rotptsptr->vy = MUL_FIXED(LToVMat.mat12, morphptsptr->vx);
194 rotptsptr->vy += MUL_FIXED(LToVMat.mat22, morphptsptr->vy);
195 rotptsptr->vy += MUL_FIXED(LToVMat.mat32, morphptsptr->vz);
196 rotptsptr->vy += Global_ODB_Ptr->ObView.vy;
197
198 rotptsptr->vz = MUL_FIXED(LToVMat.mat13, morphptsptr->vx);
199 rotptsptr->vz += MUL_FIXED(LToVMat.mat23, morphptsptr->vy);
200 rotptsptr->vz += MUL_FIXED(LToVMat.mat33, morphptsptr->vz);
201 rotptsptr->vz += Global_ODB_Ptr->ObView.vz;
202 }
203
204 rotptsptr->vy = MUL_FIXED(rotptsptr->vy,87381);
205 morphptsptr++;
206 rotptsptr++;
207
208 }
209
210
211 #else /* LazyEvaluationForMorphing */
212
213
214 VECTORCH *morphptsptr = &MorphedPts[0];
215 SHAPEHEADER *sptr1;
216 SHAPEHEADER *sptr2;
217 int *shapeitemptr1;
218 int *shapeitemptr2;
219 int x1, y1, z1;
220 int x2, y2, z2;
221 #if checkmorphpts
222 int num_old_pts = 0;
223 int num_new_pts = 0;
224 #endif
225
226
227 /*textprint("morphing points\n");*/
228
229 sptr1 = MorphDisplay.md_sptr1;
230 sptr2 = MorphDisplay.md_sptr2;
231
232 shapeitemptr1 = *(sptr1->points);
233 shapeitemptr2 = *(sptr2->points);
234
235
236 #if KZSORT_ON /* KJL 15:13:46 02/07/97 - used for z-sorting doors correctly! */
237 {
238 extern int *MorphedObjectPointsPtr;
239 MorphedObjectPointsPtr = shapeitemptr2;
240 }
241 #endif
242
243
244 for(numitems = shapeinstrptr->sh_numitems; numitems!=0; numitems--) {
245
246 x1 = shapeitemptr1[ix];
247 y1 = shapeitemptr1[iy];
248 z1 = shapeitemptr1[iz];
249
250 x2 = shapeitemptr2[ix];
251 y2 = shapeitemptr2[iy];
252 z2 = shapeitemptr2[iz];
253
254 if(x1 == x2 && y1 == y2 && z1 == z2) {
255
256 x = x1;
257 y = y1;
258 z = z1;
259
260 #if checkmorphpts
261 num_old_pts++;
262 #endif
263
264 }
265
266 else if(MorphDisplay.md_lerp == 0) {
267
268 x = x1;
269 y = y1;
270 z = z1;
271
272 }
273
274 else if(MorphDisplay.md_lerp == 0xffff) {
275
276 x = x2;
277 y = y2;
278 z = z2;
279
280 }
281
282 else
283 {
284 /* KJL 15:27:20 05/22/97 - I've changed this to speed things up, If a vertex
285 component has a magnitude greater than 32768 things will go wrong. */
286 x = x1 + (((x2-x1)*MorphDisplay.md_lerp)>>16);
287 y = y1 + (((y2-y1)*MorphDisplay.md_lerp)>>16);
288 z = z1 + (((z2-z1)*MorphDisplay.md_lerp)>>16);
289
290 #if checkmorphpts
291 num_new_pts++;
292 #endif
293
294 }
295
296 morphptsptr->vx = x;
297 morphptsptr->vy = y;
298 morphptsptr->vz = z;
299
300 /* KJL 16:07:15 11/27/97 - I know this test is inside the loop,
301 but all this will go when I change to float everywhere. */
302 #if MIRRORING_ON
303 if(!Global_ODB_Ptr->ObMyModule || MirroringActive)
304 #else
305 if (!Global_ODB_Ptr->ObMyModule)
306 #endif
307 {
308 #if SUPPORT_MMX
309 if (use_mmx_math)
310 MMX_VectorTransformedAndAdd(rotptsptr,morphptsptr,<oVMat,&Global_ODB_Ptr->ObView);
311 else
312 #endif
313 {
314 rotptsptr->vx = MUL_FIXED(LToVMat.mat11, x);
315 rotptsptr->vx += MUL_FIXED(LToVMat.mat21, y);
316 rotptsptr->vx += MUL_FIXED(LToVMat.mat31, z);
317 rotptsptr->vx += Global_ODB_Ptr->ObView.vx;
318
319 rotptsptr->vy = MUL_FIXED(LToVMat.mat12, x);
320 rotptsptr->vy += MUL_FIXED(LToVMat.mat22, y);
321 rotptsptr->vy += MUL_FIXED(LToVMat.mat32, z);
322 rotptsptr->vy += Global_ODB_Ptr->ObView.vy;
323
324 rotptsptr->vz = MUL_FIXED(LToVMat.mat13, x);
325 rotptsptr->vz += MUL_FIXED(LToVMat.mat23, y);
326 rotptsptr->vz += MUL_FIXED(LToVMat.mat33, z);
327 rotptsptr->vz += Global_ODB_Ptr->ObView.vz;
328 }
329 }
330 else /* KJL 14:33:24 11/27/97 - experiment to get rid of tears */
331 {
332 x += Global_ODB_Ptr->ObWorld.vx - Global_VDB_Ptr->VDB_World.vx;
333 y += Global_ODB_Ptr->ObWorld.vy - Global_VDB_Ptr->VDB_World.vy;
334 z += Global_ODB_Ptr->ObWorld.vz - Global_VDB_Ptr->VDB_World.vz;
335
336 rotptsptr->vx = MUL_FIXED(LToVMat.mat11, x);
337 rotptsptr->vx += MUL_FIXED(LToVMat.mat21, y);
338 rotptsptr->vx += MUL_FIXED(LToVMat.mat31, z);
339
340 rotptsptr->vy = MUL_FIXED(LToVMat.mat12, x);
341 rotptsptr->vy += MUL_FIXED(LToVMat.mat22, y);
342 rotptsptr->vy += MUL_FIXED(LToVMat.mat32, z);
343
344 rotptsptr->vz = MUL_FIXED(LToVMat.mat13, x);
345 rotptsptr->vz += MUL_FIXED(LToVMat.mat23, y);
346 rotptsptr->vz += MUL_FIXED(LToVMat.mat33, z);
347 }
348
349
350 shapeitemptr1 += vsize;
351 shapeitemptr2 += vsize;
352 morphptsptr++;
353
354 rotptsptr->vy = MUL_FIXED(rotptsptr->vy,87381);
355 rotptsptr++;
356
357 }
358
359 #if checkmorphpts
360 textprint("num_old_pts = %d\n", num_old_pts);
361 textprint("num_new_pts = %d\n", num_new_pts);
362 #endif
363
364
365 #endif /* LazyEvaluationForMorphing */
366
367
368 }
369
370 else {
371
372 #endif
373
374 #if MIRRORING_ON
375 int useFirstMethod = 0;
376
377
378 if(!Global_ODB_Ptr->ObMyModule || MirroringActive)
379 {
380 useFirstMethod = 1;
381 }
382 if (Global_ODB_Ptr->ObStrategyBlock)
383 {
384 #if 0
385 if(Global_ODB_Ptr->ObStrategyBlock->I_SBtype == I_BehaviourInanimateObject)
386 {
387 INANIMATEOBJECT_STATUSBLOCK* osPtr = Global_ODB_Ptr->ObStrategyBlock->SBdataptr;
388 if(osPtr->typeId==IOT_Static)
389 {
390 useFirstMethod=0;
391 }
392 }
393 #endif
394 }
395
396 if(useFirstMethod)
397 #else
398 if (!Global_ODB_Ptr->ObMyModule)
399 #endif
400 {
401 for(numitems = shapeinstrptr->sh_numitems; numitems!=0; numitems--)
402 {
403 #if SUPPORT_MMX
404 if (use_mmx_math)
405 MMX_VectorTransformedAndAdd(rotptsptr,(VECTORCH *)shapeitemptr,<oVMat,&Global_ODB_Ptr->ObView);
406 else
407 #endif
408 {
409 x = shapeitemptr[ix];
410 y = shapeitemptr[iy];
411 z = shapeitemptr[iz];
412
413 rotptsptr->vx = MUL_FIXED(LToVMat.mat11, x);
414 rotptsptr->vx += MUL_FIXED(LToVMat.mat21, y);
415 rotptsptr->vx += MUL_FIXED(LToVMat.mat31, z);
416 rotptsptr->vx += Global_ODB_Ptr->ObView.vx;
417
418 rotptsptr->vy = MUL_FIXED(LToVMat.mat12, x);
419 rotptsptr->vy += MUL_FIXED(LToVMat.mat22, y);
420 rotptsptr->vy += MUL_FIXED(LToVMat.mat32, z);
421 rotptsptr->vy += Global_ODB_Ptr->ObView.vy;
422
423 rotptsptr->vz = MUL_FIXED(LToVMat.mat13, x);
424 rotptsptr->vz += MUL_FIXED(LToVMat.mat23, y);
425 rotptsptr->vz += MUL_FIXED(LToVMat.mat33, z);
426 rotptsptr->vz += Global_ODB_Ptr->ObView.vz;
427 }
428 shapeitemptr += 3;
429 rotptsptr->vy = MUL_FIXED(rotptsptr->vy,87381);
430 rotptsptr++;
431
432 }
433 }
434 else
435 {
436 /* KJL 14:33:24 11/27/97 - experiment to get rid of tears */
437 for(numitems = shapeinstrptr->sh_numitems; numitems!=0; numitems--)
438 {
439 x = shapeitemptr[ix];
440 y = shapeitemptr[iy];
441 z = shapeitemptr[iz];
442
443 x += Global_ODB_Ptr->ObWorld.vx - Global_VDB_Ptr->VDB_World.vx;
444 y += Global_ODB_Ptr->ObWorld.vy - Global_VDB_Ptr->VDB_World.vy;
445 z += Global_ODB_Ptr->ObWorld.vz - Global_VDB_Ptr->VDB_World.vz;
446
447 rotptsptr->vx = MUL_FIXED(LToVMat.mat11, x);
448 rotptsptr->vx += MUL_FIXED(LToVMat.mat21, y);
449 rotptsptr->vx += MUL_FIXED(LToVMat.mat31, z);
450
451 rotptsptr->vy = MUL_FIXED(LToVMat.mat12, x);
452 rotptsptr->vy += MUL_FIXED(LToVMat.mat22, y);
453 rotptsptr->vy += MUL_FIXED(LToVMat.mat32, z);
454
455 rotptsptr->vz = MUL_FIXED(LToVMat.mat13, x);
456 rotptsptr->vz += MUL_FIXED(LToVMat.mat23, y);
457 rotptsptr->vz += MUL_FIXED(LToVMat.mat33, z);
458 shapeitemptr += 3;
459 rotptsptr->vy = MUL_FIXED(rotptsptr->vy,87381);
460 rotptsptr++;
461 }
462
463 }
464
465 #if SupportMorphing
466 }
467 #endif
468
469
470 }
471
472
473 #endif /* StandardShapeLanguage */
474
475
476
477
478
479
480
481 /*
482
483 WideMul2NarrowDiv
484
485 This function takes two pairs of integers, adds their 64-bit products
486 together, divides the summed product with another integer and then returns
487 the result of that divide, which is also an integer.
488
489 */
490
WideMul2NarrowDiv(int a,int b,int c,int d,int e)491 int WideMul2NarrowDiv(int a, int b, int c, int d, int e)
492
493 {
494
495 LONGLONGCH f;
496 LONGLONGCH g;
497
498
499 MUL_I_WIDE(a, b, &f);
500 MUL_I_WIDE(c, d, &g);
501 ADD_LL_PP(&f, &g);
502
503 return NarrowDivide(&f, e);
504
505 }
506
507
508 /*
509
510 Calculate Plane Normal from three POP's
511
512 The three input vectors are treated as POP's and used to make two vectors.
513 These are then crossed to create the normal.
514
515 Make two vectors; (2-1) & (3-1)
516 Cross them
517 Normalise the vector
518 Find the magnitude of the vector
519 Divide each component by the magnitude
520
521 */
522
MakeNormal(VECTORCH * v1,VECTORCH * v2,VECTORCH * v3,VECTORCH * v4)523 void MakeNormal(VECTORCH *v1, VECTORCH *v2, VECTORCH *v3, VECTORCH *v4)
524
525 {
526
527 VECTORCHF vect0;
528 VECTORCHF vect1;
529 VECTORCHF n;
530
531
532 /* vect0 = v2 - v1 */
533
534 vect0.vx = v2->vx - v1->vx;
535 vect0.vy = v2->vy - v1->vy;
536 vect0.vz = v2->vz - v1->vz;
537
538 /* vect1 = v3 - v1 */
539
540 vect1.vx = v3->vx - v1->vx;
541 vect1.vy = v3->vy - v1->vy;
542 vect1.vz = v3->vz - v1->vz;
543
544
545 /* nx = v0y.v1z - v0z.v1y */
546
547 n.vx = (vect0.vy * vect1.vz) - (vect0.vz * vect1.vy);
548
549 /* ny = v0z.v1x - v0x.v1z */
550
551 n.vy = (vect0.vz * vect1.vx) - (vect0.vx * vect1.vz);
552
553 /* nz = v0x.v1y - v0y.v1x */
554
555 n.vz = (vect0.vx * vect1.vy) - (vect0.vy * vect1.vx);
556
557
558 FNormalise(&n);
559
560 f2i(v4->vx, n.vx * ONE_FIXED);
561 f2i(v4->vy, n.vy * ONE_FIXED);
562 f2i(v4->vz, n.vz * ONE_FIXED);
563
564
565 #if 0
566 textprint("Magnitude of v4 = %d\n", Magnitude(v4));
567 WaitForReturn();
568 #endif
569
570 }
571
572
573 /*
574
575 Normalise a vector.
576
577 The returned vector is a fixed point unit vector.
578
579 WARNING!
580
581 The vector must be no larger than 2<<14 because of the square root.
582 Because this is an integer function, small components produce errors.
583
584 e.g.
585
586 (100,100,0)
587
588 m=141 (141.42)
589
590 nx = 100 * ONE_FIXED / m = 46,479
591 ny = 100 * ONE_FIXED / m = 46,479
592 nz = 0
593
594 New m ought to be 65,536 but in fact is 65,731 i.e. 0.29% too large.
595
596 */
597
Normalise(VECTORCH * nvector)598 void Normalise(VECTORCH *nvector)
599
600 {
601 VECTORCHF n;
602 float m;
603
604
605 n.vx = nvector->vx;
606 n.vy = nvector->vy;
607 n.vz = nvector->vz;
608
609 m = 65536.0/sqrt((n.vx * n.vx) + (n.vy * n.vy) + (n.vz * n.vz));
610
611 f2i(nvector->vx, (n.vx * m) );
612 f2i(nvector->vy, (n.vy * m) );
613 f2i(nvector->vz, (n.vz * m) );
614 }
615
616
617
618
619
620
621
Normalise2d(VECTOR2D * nvector)622 void Normalise2d(VECTOR2D *nvector)
623
624 {
625 VECTOR2DF n;
626 float m;
627
628
629 n.vx = nvector->vx;
630 n.vy = nvector->vy;
631
632 m = sqrt((n.vx * n.vx) + (n.vy * n.vy));
633
634 nvector->vx = (n.vx * ONE_FIXED) / m;
635 nvector->vy = (n.vy * ONE_FIXED) / m;
636 }
637
638
FNormalise(VECTORCHF * n)639 void FNormalise(VECTORCHF *n)
640
641 {
642
643 float m;
644
645
646 m = sqrt((n->vx * n->vx) + (n->vy * n->vy) + (n->vz * n->vz));
647
648 n->vx /= m;
649 n->vy /= m;
650 n->vz /= m;
651
652 }
653
FNormalise2d(VECTOR2DF * n)654 void FNormalise2d(VECTOR2DF *n)
655
656 {
657
658 float m;
659
660
661 m = sqrt((n->vx * n->vx) + (n->vy * n->vy));
662
663 n->vx /= m;
664 n->vy /= m;
665
666 }
667
668
669 /*
670
671 Return the magnitude of a vector
672
673 */
674
Magnitude(VECTORCH * v)675 int Magnitude(VECTORCH *v)
676
677 {
678 VECTORCHF n;
679 int m;
680
681
682 n.vx = v->vx;
683 n.vy = v->vy;
684 n.vz = v->vz;
685
686 f2i(m, sqrt((n.vx * n.vx) + (n.vy * n.vy) + (n.vz * n.vz)));
687
688 return m;
689 }
690
691 /*
692
693 Shift the 64-bit value until is LTE the limit
694
695 Return the shift value
696
697 */
698
FindShift64(LONGLONGCH * value,LONGLONGCH * limit)699 int FindShift64(LONGLONGCH *value, LONGLONGCH *limit)
700
701 {
702
703 int shift = 0;
704 int s;
705 LONGLONGCH value_tmp;
706
707
708 EQUALS_LL(&value_tmp, value);
709
710 s = CMP_LL(&value_tmp, &ll_zero);
711 if(s < 0) NEG_LL(&value_tmp);
712
713
714 while(GT_LL(&value_tmp, limit)) {
715
716 shift++;
717
718 ASR_LL(&value_tmp, 1);
719
720 }
721
722 return shift;
723
724 }
725
726
727 /*
728
729 MaxLONGLONGCH
730
731 Return a pointer to the largest value of a long long array
732
733 */
734
MaxLONGLONGCH(LONGLONGCH * llarrayptr,int llarraysize,LONGLONGCH * llmax)735 void MaxLONGLONGCH(LONGLONGCH *llarrayptr, int llarraysize, LONGLONGCH *llmax)
736
737 {
738
739 int i;
740
741
742 EQUALS_LL(llmax, &ll_zero);
743
744 for(i = llarraysize; i!=0; i--) {
745
746 if(LT_LL(llmax, llarrayptr)) {
747
748 EQUALS_LL(llmax, llarrayptr);
749
750 }
751
752 llarrayptr++;
753
754 }
755
756 }
757
758
759
760
761
762
763
764
765
766
767
768
769 /*
770
771 Some operators derived from the 64-bit CMP function.
772
773 */
774
775
776 /*
777
778 GT_LL
779
780 To express if(a > b)
781
782 use
783
784 if(GT_LL(a, b))
785
786 */
787
GT_LL(LONGLONGCH * a,LONGLONGCH * b)788 int GT_LL(LONGLONGCH *a, LONGLONGCH *b)
789
790 {
791
792 int s = CMP_LL(a, b); /* a-b */
793
794
795 if(s > 0) return (Yes);
796
797 else return (No);
798
799 }
800
801
802 /*
803
804 LT_LL
805
806 To express if(a < b)
807
808 use
809
810 if(LT_LL(a, b))
811
812 */
813
LT_LL(LONGLONGCH * a,LONGLONGCH * b)814 int LT_LL(LONGLONGCH *a, LONGLONGCH *b)
815
816 {
817
818 int s = CMP_LL(a, b); /* a-b */
819
820
821 if(s < 0) return (Yes);
822
823 else return (No);
824
825 }
826
827
828
829
830 /*
831
832 Copy Clip Point Function
833
834 */
835
CopyClipPoint(CLIP_POINT * cp1,CLIP_POINT * cp2)836 void CopyClipPoint(CLIP_POINT *cp1, CLIP_POINT *cp2)
837
838 {
839
840 cp2->ClipPoint.vx = cp1->ClipPoint.vx;
841 cp2->ClipPoint.vy = cp1->ClipPoint.vy;
842 cp2->ClipPoint.vz = cp1->ClipPoint.vz;
843
844 cp2->ClipNormal.vx = cp1->ClipNormal.vx;
845 cp2->ClipNormal.vy = cp1->ClipNormal.vy;
846 cp2->ClipNormal.vz = cp1->ClipNormal.vz;
847
848 cp2->ClipTexel.uuu = cp1->ClipTexel.uuu;
849 cp2->ClipTexel.vee = cp1->ClipTexel.vee;
850
851 cp2->ClipInt = cp1->ClipInt;
852 cp2->ClipZBuffer = cp1->ClipZBuffer;
853
854 }
855
856
857 /*
858
859 Matrix Rotatation of a Vector - Inline Version
860
861 Overwrite the Source Vector with the Rotated Vector
862
863 x' = v.c1
864 y' = v.c2
865 z' = v.c3
866
867 */
868
RotVect(VECTORCH * v,MATRIXCH * m)869 void RotVect(VECTORCH *v, MATRIXCH *m)
870
871 {
872
873 int x, y, z;
874
875 x = MUL_FIXED(m->mat11, v->vx);
876 x += MUL_FIXED(m->mat21, v->vy);
877 x += MUL_FIXED(m->mat31, v->vz);
878
879 y = MUL_FIXED(m->mat12, v->vx);
880 y += MUL_FIXED(m->mat22, v->vy);
881 y += MUL_FIXED(m->mat32, v->vz);
882
883 z = MUL_FIXED(m->mat13, v->vx);
884 z += MUL_FIXED(m->mat23, v->vy);
885 z += MUL_FIXED(m->mat33, v->vz);
886
887 v->vx = x;
888 v->vy = y;
889 v->vz = z;
890
891 }
892
893
894
895 /*
896
897 Dot Product Function - Inline Version
898
899 It accepts two pointers to vectors and returns an int result
900
901 */
902
_Dot(VECTORCH * vptr1,VECTORCH * vptr2)903 int _Dot(VECTORCH *vptr1, VECTORCH *vptr2)
904
905 {
906
907 int dp;
908
909 dp = MUL_FIXED(vptr1->vx, vptr2->vx);
910 dp += MUL_FIXED(vptr1->vy, vptr2->vy);
911 dp += MUL_FIXED(vptr1->vz, vptr2->vz);
912
913 return(dp);
914
915 }
916
917
918 /*
919
920 Make a Vector - Inline Version
921
922 v3 = v1 - v2
923
924 */
925
MakeV(VECTORCH * v1,VECTORCH * v2,VECTORCH * v3)926 void MakeV(VECTORCH *v1, VECTORCH *v2, VECTORCH *v3)
927
928 {
929
930 v3->vx = v1->vx - v2->vx;
931 v3->vy = v1->vy - v2->vy;
932 v3->vz = v1->vz - v2->vz;
933
934 }
935
936 /*
937
938 Add a Vector.
939
940 v2 = v2 + v1
941
942 */
943
AddV(VECTORCH * v1,VECTORCH * v2)944 void AddV(VECTORCH *v1, VECTORCH *v2)
945
946 {
947
948 v2->vx += v1->vx;
949 v2->vy += v1->vy;
950 v2->vz += v1->vz;
951
952 }
953