Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
MorsGames
GitHub Repository: MorsGames/sm64plus
Path: blob/master/src/goddard/shape_helper.c
7858 views
1
#include <PR/ultratypes.h>
2
3
#include "debug_utils.h"
4
#include "draw_objects.h"
5
#include "dynlist_proc.h"
6
#include "dynlists/dynlist_macros.h"
7
#include "dynlists/dynlists.h"
8
#include "gd_main.h"
9
#include "gd_math.h"
10
#include "gd_types.h"
11
#include "joints.h"
12
#include "macros.h"
13
#include "objects.h"
14
#include "particles.h"
15
#include "renderer.h"
16
#include "shape_helper.h"
17
#include "skin.h"
18
19
#ifndef VERSION_EU
20
#include <prevent_bss_reordering.h>
21
#endif
22
23
// data
24
struct ObjGroup *gMarioFaceGrp = NULL; // @ 801A82E0; returned by load_dynlist
25
struct ObjShape *gSpotShape = NULL; // Shape used for drawing lights?
26
static struct ObjShape *sGrabJointTestShape = NULL; // Test shape for showing grab joints. This isn't rendered due to make_grabber_joint setting the drawFlags to OBJ_INVISIBLE.
27
struct ObjShape *gShapeRedSpark = NULL; // @ 801A82EC
28
struct ObjShape *gShapeSilverSpark = NULL; // @ 801A82F0
29
struct ObjShape *gShapeRedStar = NULL; // @ 801A82F4
30
struct ObjShape *gShapeSilverStar = NULL; // @ 801A82F8
31
32
// Not sure what this data is, but it looks like stub animation data
33
34
static struct GdAnimTransform unusedAnimData1[] = {
35
{ {1.0, 1.0, 1.0}, {0.0, 0.0, 0.0}, {0.0, 0.0, 0.0} },
36
};
37
38
UNUSED static struct AnimDataInfo unusedAnim1 = { ARRAY_COUNT(unusedAnimData1), GD_ANIM_SCALE3F_ROT3F_POS3F_2, unusedAnimData1 };
39
40
static struct GdAnimTransform unusedAnimData2[] = {
41
{ {1.0, 1.0, 1.0}, {0.0, 0.0, 0.0}, {0.0, 0.0, 0.0} },
42
};
43
44
UNUSED static struct AnimDataInfo unusedAnim2 = { ARRAY_COUNT(unusedAnimData2), GD_ANIM_SCALE3F_ROT3F_POS3F_2, unusedAnimData2 };
45
46
static struct GdAnimTransform unusedAnimData3[] = {
47
{ {1.0, 1.0, 1.0}, {0.0, 0.0, 0.0}, {0.0, 0.0, 0.0} },
48
};
49
50
UNUSED static struct AnimDataInfo unusedAnim3 = { ARRAY_COUNT(unusedAnimData3), GD_ANIM_SCALE3F_ROT3F_POS3F_2, unusedAnimData3 };
51
52
UNUSED static s32 sUnref801A838C[6] = { 0 };
53
struct ObjShape *sSimpleShape = NULL;
54
UNUSED static s32 sUnref801A83A8[31] = { 0 };
55
UNUSED static struct DynList sSimpleDylist[8] = { // unused
56
BeginList(),
57
StartGroup("simpleg"),
58
MakeDynObj(D_NET, "simple"),
59
SetType(3),
60
SetShapePtrPtr(&sSimpleShape),
61
EndGroup("simpleg"),
62
UseObj("simpleg"),
63
EndList(),
64
};
65
static struct DynList sDynlist801A84E4[3] = {
66
BeginList(),
67
SetFlag(0x1800),
68
EndList(),
69
};
70
UNUSED static struct DynList sDynlist801A85B3[5] = {
71
BeginList(), CallList(sDynlist801A84E4), SetFlag(0x400), SetFriction(0.04, 0.01, 0.01),
72
EndList(),
73
};
74
UNUSED static struct DynList sDynlist801A85A4[4] = {
75
BeginList(),
76
CallList(sDynlist801A84E4),
77
SetFriction(0.04, 0.01, 0.01),
78
EndList(),
79
};
80
UNUSED static struct DynList sDynlist801A8604[4] = {
81
BeginList(),
82
CallList(sDynlist801A84E4),
83
SetFriction(0.005, 0.005, 0.005),
84
EndList(),
85
};
86
static f64 D_801A8668 = 0.0;
87
88
// bss
89
UNUSED static u8 sUnrefSpaceB00[0x2C]; // @ 801BAB00
90
static struct ObjGroup *sCubeShapeGroup; // @ 801BAB2C
91
UNUSED static u8 sUnrefSpaceB30[0xC]; // @ 801BAB30
92
static struct ObjShape *sCubeShape; // @ 801BAB3C
93
UNUSED static u8 sUnrefSpaceB40[0x8]; // @ 801BAB40
94
static char sGdLineBuf[0x100]; // @ 801BAB48
95
static s32 sGdLineBufCsr; // @ 801BAC48
96
static struct GdFile *sGdShapeFile; // @ 801BAC4C
97
static struct ObjShape *sGdShapeListHead; // @ 801BAC50
98
static u32 sGdShapeCount; // @ 801BAC54
99
UNUSED static u8 sUnrefSpaceC58[0x8]; // @ 801BAC58
100
static struct GdVec3f D_801BAC60;
101
UNUSED static u32 sUnrefSpaceC6C; // @ 801BAC6C
102
UNUSED static u32 sUnrefSpaceC70; // @ 801BAC70
103
static struct ObjPlane *D_801BAC74;
104
static struct ObjPlane *D_801BAC78; // sShapeNetHead?
105
UNUSED static u8 sUnrefSpaceC80[0x1C]; // @ 801BAC80
106
static struct ObjFace *D_801BAC9C;
107
static struct ObjFace *D_801BACA0;
108
UNUSED static u8 sUnrefSpaceCA8[0x10]; // @ 801BACA8
109
/// factor for scaling vertices in an `ObjShape` when calling `scale_verts_in_shape()`
110
static struct GdVec3f sVertexScaleFactor;
111
/// factor for translating vertices in an `ObjShape` when calling `translate_verts_in_shape()`
112
static struct GdVec3f sVertexTranslateOffset;
113
UNUSED static u8 sUnrefSpaceCD8[0x30]; // @ 801BACD8
114
static struct ObjGroup *D_801BAD08; // group of planes from make_netfromshape
115
UNUSED static u8 sUnrefSpaceD10[0x20]; // @ 801BAD10
116
static struct GdVec3f sShapeCenter; // printed with "c="
117
UNUSED static u8 sUnrefSpaceD40[0x120]; // @ 801BAD40
118
119
// Forward Declarations
120
struct ObjMaterial *find_or_add_new_mtl(struct ObjGroup *, s32, f32, f32, f32);
121
122
/* @ 245A50 for 0x40 */
123
/* Something to do with shape list/group initialization? */
124
void func_80197280(void) {
125
sGdShapeCount = 0;
126
sGdShapeListHead = NULL;
127
gGdLightGroup = make_group(0);
128
}
129
130
/**
131
* Computes the normal vector for a face based on three of its vertices.
132
*/
133
void calc_face_normal(struct ObjFace *face) {
134
UNUSED u32 pad5C;
135
struct GdVec3f p1;
136
struct GdVec3f p2;
137
struct GdVec3f p3;
138
struct GdVec3f normal;
139
struct ObjVertex *vtx1;
140
struct ObjVertex *vtx2;
141
struct ObjVertex *vtx3;
142
UNUSED u32 pad1C;
143
f32 mul = 1000.0f;
144
145
imin("calc_facenormal");
146
147
if (face->vtxCount >= 3) { // need at least three points to compute a normal
148
vtx1 = face->vertices[0];
149
p1.x = vtx1->pos.x;
150
p1.y = vtx1->pos.y;
151
p1.z = vtx1->pos.z;
152
153
vtx2 = face->vertices[1];
154
p2.x = vtx2->pos.x;
155
p2.y = vtx2->pos.y;
156
p2.z = vtx2->pos.z;
157
158
vtx3 = face->vertices[2];
159
p3.x = vtx3->pos.x;
160
p3.y = vtx3->pos.y;
161
p3.z = vtx3->pos.z;
162
163
// calculate the cross product of edges (p2 - p1) and (p3 - p2)
164
// not sure why each component is multiplied by 1000. maybe to avoid loss of precision when normalizing?
165
normal.x = (((p2.y - p1.y) * (p3.z - p2.z)) - ((p2.z - p1.z) * (p3.y - p2.y))) * mul;
166
normal.y = (((p2.z - p1.z) * (p3.x - p2.x)) - ((p2.x - p1.x) * (p3.z - p2.z))) * mul;
167
normal.z = (((p2.x - p1.x) * (p3.y - p2.y)) - ((p2.y - p1.y) * (p3.x - p2.x))) * mul;
168
169
gd_normalize_vec3f(&normal);
170
171
face->normal.x = normal.x;
172
face->normal.y = normal.y;
173
face->normal.z = normal.z;
174
}
175
imout();
176
}
177
178
/* @ 245CDC for 0x118 */
179
struct ObjVertex *gd_make_vertex(f32 x, f32 y, f32 z) {
180
struct ObjVertex *vtx;
181
182
vtx = (struct ObjVertex *) make_object(OBJ_TYPE_VERTICES);
183
vtx->id = 0xD1D4;
184
185
vtx->pos.x = x;
186
vtx->pos.y = y;
187
vtx->pos.z = z;
188
189
vtx->initPos.x = x;
190
vtx->initPos.y = y;
191
vtx->initPos.z = z;
192
193
vtx->scaleFactor = 1.0f;
194
vtx->gbiVerts = NULL;
195
vtx->alpha = 1.0f;
196
197
vtx->normal.x = 0.0f;
198
vtx->normal.y = 1.0f;
199
vtx->normal.z = 0.0f;
200
201
return vtx;
202
}
203
204
/* @ 245DF4 for 0xAC */
205
struct ObjFace *make_face_with_colour(f32 r, f32 g, f32 b) {
206
struct ObjFace *newFace;
207
208
imin("make_face");
209
newFace = (struct ObjFace *) make_object(OBJ_TYPE_FACES);
210
211
newFace->colour.r = r;
212
newFace->colour.g = g;
213
newFace->colour.b = b;
214
215
newFace->vtxCount = 0;
216
newFace->mtlId = -1;
217
newFace->mtl = NULL;
218
219
imout();
220
return newFace;
221
}
222
223
/* @ 245EA0 for 0x6C */
224
struct ObjFace *make_face_with_material(struct ObjMaterial *mtl) {
225
struct ObjFace *newFace;
226
227
newFace = (struct ObjFace *) make_object(OBJ_TYPE_FACES);
228
229
newFace->vtxCount = 0;
230
newFace->mtlId = mtl->id;
231
newFace->mtl = mtl;
232
233
return newFace;
234
}
235
236
/* @ 245F0C for 0x88 */
237
void add_4_vertices_to_face(struct ObjFace *face, struct ObjVertex *vtx1, struct ObjVertex *vtx2,
238
struct ObjVertex *vtx3, struct ObjVertex *vtx4) {
239
face->vertices[0] = vtx1;
240
face->vertices[1] = vtx2;
241
face->vertices[2] = vtx3;
242
face->vertices[3] = vtx4;
243
face->vtxCount = 4;
244
calc_face_normal(face);
245
}
246
247
/* @ 245F94 for 0x78; orig name: func_801977C4 */
248
void add_3_vtx_to_face(struct ObjFace *face, struct ObjVertex *vtx1, struct ObjVertex *vtx2,
249
struct ObjVertex *vtx3) {
250
face->vertices[0] = vtx1;
251
face->vertices[1] = vtx2;
252
face->vertices[2] = vtx3;
253
face->vtxCount = 3;
254
calc_face_normal(face);
255
}
256
257
/**
258
* Creates an `ObjShape` object
259
*/
260
struct ObjShape *make_shape(s32 flag, const char *name) {
261
struct ObjShape *newShape;
262
struct ObjShape *curShapeHead;
263
UNUSED u32 pad;
264
265
newShape = (struct ObjShape *) make_object(OBJ_TYPE_SHAPES);
266
267
if (name != NULL) {
268
gd_strcpy(newShape->name, name);
269
} else {
270
gd_strcpy(newShape->name, "NoName");
271
}
272
273
sGdShapeCount++;
274
275
curShapeHead = sGdShapeListHead;
276
sGdShapeListHead = newShape;
277
278
if (curShapeHead != NULL) {
279
newShape->nextShape = curShapeHead;
280
curShapeHead->prevShape = newShape;
281
}
282
283
newShape->id = sGdShapeCount;
284
newShape->flag = flag;
285
286
newShape->vtxCount = 0;
287
newShape->faceCount = 0;
288
newShape->dlNums[0] = 0;
289
newShape->dlNums[1] = 0;
290
newShape->unk3C = 0;
291
newShape->faceGroup = NULL; /* whoops, NULL-ed twice */
292
293
newShape->alpha = 1.0f;
294
295
newShape->vtxGroup = NULL;
296
newShape->faceGroup = NULL;
297
newShape->mtlGroup = NULL;
298
newShape->unk30 = 0;
299
newShape->unk50 = 0;
300
301
return newShape;
302
}
303
304
/* @ 2461A4 for 0x30; orig name: func_801979D4 */
305
void clear_buf_to_cr(void) {
306
sGdLineBufCsr = 0;
307
sGdLineBuf[sGdLineBufCsr] = '\r';
308
}
309
310
/* @ 2461D4 for 0x2c; orig name: func_80197A04 */
311
s8 get_current_buf_char(void) {
312
return sGdLineBuf[sGdLineBufCsr];
313
}
314
315
/* @ 246200 for 0x64; orig name: func_80197A30 */
316
s8 get_and_advance_buf(void) {
317
if (get_current_buf_char() == '\0') {
318
return '\0';
319
}
320
321
return sGdLineBuf[sGdLineBufCsr++];
322
}
323
324
/* @ 246264 for 0x80; orig name: func_80197A94 */
325
s8 load_next_line_into_buf(void) {
326
sGdLineBufCsr = 0;
327
328
if (gd_feof(sGdShapeFile) != 0) {
329
sGdLineBuf[sGdLineBufCsr] = '\0';
330
} else {
331
gd_fread_line(sGdLineBuf, 0xFF, sGdShapeFile);
332
}
333
334
return get_current_buf_char();
335
}
336
337
/* @ 2462E4 for 0x38; orig name: func_80197B14 */
338
s32 is_line_end(char c) {
339
return c == '\r' || c == '\n';
340
}
341
342
/* @ 24631C for 0x38; orig name: func_80197B4C */
343
s32 is_white_space(char c) {
344
return c == ' ' || c == '\t';
345
}
346
347
/* @ 246354 for 0xEC; orig name: func_80197B84 */
348
/* Advances buffer cursor to next non-white-space character, if possible.
349
* Returns TRUE if a character is found, or FALSE if EOF or \0 */
350
s32 scan_to_next_non_whitespace(void) {
351
char curChar;
352
353
for (curChar = get_current_buf_char(); curChar != '\0'; curChar = get_current_buf_char()) {
354
if (is_white_space(curChar)) {
355
get_and_advance_buf();
356
continue;
357
}
358
359
if (curChar == '\x1a') { //'SUB' character: "soft EOF" in older systems
360
return FALSE;
361
continue; // unreachable
362
}
363
364
if (is_line_end(curChar)) {
365
if (load_next_line_into_buf() == '\0') {
366
return FALSE;
367
}
368
} else {
369
break;
370
}
371
}
372
373
return !!curChar;
374
}
375
376
/* @ 246440 for 0xE0; orig name: func_80197C70 */
377
s32 is_next_buf_word(char *a0) {
378
char curChar;
379
char wordBuf[0xfc];
380
u32 bufLength;
381
382
bufLength = 0;
383
for (curChar = get_and_advance_buf(); curChar != '\0'; curChar = get_and_advance_buf()) {
384
if (is_white_space(curChar) || is_line_end(curChar)) {
385
break;
386
continue; // unreachable + nonsensical
387
}
388
wordBuf[bufLength] = curChar;
389
bufLength++;
390
}
391
392
wordBuf[bufLength] = '\0';
393
394
return !gd_str_not_equal(a0, wordBuf);
395
}
396
397
/* @ 246520 for 0x198; orig name: func_80197D50 */
398
s32 getfloat(f32 *floatPtr) {
399
char charBuf[0x100];
400
u32 bufCsr;
401
char curChar;
402
u32 sp34;
403
f64 parsedDouble;
404
405
imin("getfloat");
406
407
if (is_line_end(get_current_buf_char())) {
408
fatal_printf("getfloat(): Unexpected EOL");
409
}
410
411
while (is_white_space(get_current_buf_char())) {
412
get_and_advance_buf();
413
}
414
415
bufCsr = 0;
416
417
for (curChar = get_and_advance_buf(); curChar != '\0'; curChar = get_and_advance_buf()) {
418
if (!is_white_space(curChar) && !is_line_end(curChar)) {
419
charBuf[bufCsr] = curChar;
420
bufCsr++;
421
} else {
422
break;
423
}
424
}
425
426
charBuf[bufCsr] = '\0';
427
428
parsedDouble = gd_lazy_atof(charBuf, &sp34);
429
*floatPtr = (f32) parsedDouble;
430
431
imout();
432
return !!bufCsr;
433
}
434
435
/* @ 2466B8 for 0x180; orig name: func_80197EE8 */
436
s32 getint(s32 *intPtr) {
437
char charBuf[0x100];
438
u32 bufCsr;
439
char curChar;
440
441
imin("getint");
442
443
if (is_line_end(get_current_buf_char())) {
444
fatal_printf("getint(): Unexpected EOL");
445
}
446
447
while (is_white_space(get_current_buf_char())) {
448
get_and_advance_buf();
449
}
450
451
bufCsr = 0;
452
for (curChar = get_and_advance_buf(); curChar != '\0'; curChar = get_and_advance_buf()) {
453
if (is_white_space(curChar) || is_line_end(curChar)) {
454
break;
455
}
456
457
charBuf[bufCsr] = curChar;
458
bufCsr++;
459
}
460
461
charBuf[bufCsr] = '\0';
462
*intPtr = gd_atoi(charBuf);
463
464
imout();
465
return !!bufCsr;
466
}
467
468
/* @ 246838 for 0x14 */
469
void Unknown80198068(UNUSED f32 a0) {
470
printf("max=%f\n", a0);
471
}
472
473
/* @ 24684C for 0x6C */
474
void func_8019807C(struct ObjVertex *vtx) {
475
gd_rot_2d_vec(D_801BAC60.x, &vtx->pos.y, &vtx->pos.z);
476
gd_rot_2d_vec(D_801BAC60.y, &vtx->pos.x, &vtx->pos.z);
477
gd_rot_2d_vec(D_801BAC60.z, &vtx->pos.x, &vtx->pos.y);
478
}
479
480
/* @ 2468B8 for 0x6C */
481
void func_801980E8(f32 *a0) {
482
gd_rot_2d_vec(D_801BAC60.x, &a0[1], &a0[2]);
483
gd_rot_2d_vec(D_801BAC60.y, &a0[0], &a0[2]);
484
gd_rot_2d_vec(D_801BAC60.z, &a0[0], &a0[1]);
485
}
486
487
/* @ 246924 for 0x30 */
488
void Unknown80198154(f32 x, f32 y, f32 z) {
489
D_801BAC60.x = x;
490
D_801BAC60.y = y;
491
D_801BAC60.z = z;
492
}
493
494
/* @ 246954 for 0x6c */
495
void Unknown80198184(struct ObjShape *shape, f32 x, f32 y, f32 z) {
496
UNUSED struct GdVec3f unusedVec;
497
unusedVec.x = x;
498
unusedVec.y = y;
499
unusedVec.z = z;
500
501
apply_to_obj_types_in_group(OBJ_TYPE_VERTICES, (applyproc_t) func_8019807C, shape->vtxGroup);
502
}
503
504
/* @ 2469C0 for 0xc8 */
505
void scale_obj_position(struct GdObj *obj) {
506
struct GdVec3f pos;
507
508
if (obj->type == OBJ_TYPE_GROUPS) {
509
return;
510
}
511
512
set_cur_dynobj(obj);
513
d_get_rel_pos(&pos);
514
515
pos.x *= sVertexScaleFactor.x;
516
pos.y *= sVertexScaleFactor.y;
517
pos.z *= sVertexScaleFactor.z;
518
519
d_set_rel_pos(pos.x, pos.y, pos.z);
520
d_set_init_pos(pos.x, pos.y, pos.z);
521
}
522
523
/* @ 246A88 for 0x94 */
524
void translate_obj_position(struct GdObj *obj) {
525
struct GdVec3f pos;
526
527
set_cur_dynobj(obj);
528
d_get_rel_pos(&pos);
529
530
pos.x += sVertexTranslateOffset.x;
531
pos.y += sVertexTranslateOffset.y;
532
pos.z += sVertexTranslateOffset.z;
533
534
d_set_rel_pos(pos.x, pos.y, pos.z);
535
}
536
537
/* @ 246B1C for 0x88 */
538
void scale_verts_in_shape(struct ObjShape *shape, f32 x, f32 y, f32 z) {
539
sVertexScaleFactor.x = x;
540
sVertexScaleFactor.y = y;
541
sVertexScaleFactor.z = z;
542
543
if (shape->vtxGroup != NULL) {
544
apply_to_obj_types_in_group(OBJ_TYPE_ALL, (applyproc_t) scale_obj_position, shape->vtxGroup);
545
}
546
}
547
548
/* @ 246BA4 for 0x70; not called */
549
// Guessing on the type of a0
550
void translate_verts_in_shape(struct ObjShape *shape, f32 x, f32 y, f32 z) {
551
sVertexTranslateOffset.x = x;
552
sVertexTranslateOffset.y = y;
553
sVertexTranslateOffset.z = z;
554
555
apply_to_obj_types_in_group(OBJ_TYPE_ALL, (applyproc_t) translate_obj_position, shape->vtxGroup);
556
}
557
558
/* @ 246C14 for 0xe0 */
559
void Unknown80198444(struct ObjVertex *vtx) {
560
f64 distance;
561
562
add_obj_pos_to_bounding_box(&vtx->header);
563
564
distance = vtx->pos.x * vtx->pos.x + vtx->pos.y * vtx->pos.y + vtx->pos.z * vtx->pos.z;
565
566
if (distance != 0.0) {
567
distance = gd_sqrt_d(distance); // sqrtd?
568
569
if (distance > D_801A8668) {
570
D_801A8668 = distance;
571
}
572
}
573
}
574
575
/* @ 246CF4 for 0xc4 */
576
void Unknown80198524(struct ObjVertex *vtx) {
577
vtx->pos.x -= sShapeCenter.x;
578
vtx->pos.y -= sShapeCenter.y;
579
vtx->pos.z -= sShapeCenter.z;
580
581
vtx->pos.x /= D_801A8668;
582
vtx->pos.y /= D_801A8668;
583
vtx->pos.z /= D_801A8668;
584
}
585
586
/* @ 246DB8 for 0x11c */
587
void Unknown801985E8(struct ObjShape *shape) {
588
struct GdBoundingBox bbox;
589
590
D_801A8668 = 0.0;
591
reset_bounding_box();
592
apply_to_obj_types_in_group(OBJ_TYPE_VERTICES, (applyproc_t) Unknown80198444, shape->vtxGroup);
593
594
get_some_bounding_box(&bbox);
595
596
sShapeCenter.x = (f32)((bbox.minX + bbox.maxX) / 2.0); //? 2.0f
597
sShapeCenter.y = (f32)((bbox.minY + bbox.maxY) / 2.0); //? 2.0f
598
sShapeCenter.z = (f32)((bbox.minZ + bbox.maxZ) / 2.0); //? 2.0f
599
600
gd_print_vec("c=", &sShapeCenter);
601
602
apply_to_obj_types_in_group(OBJ_TYPE_VERTICES, (applyproc_t) Unknown80198524, shape->vtxGroup);
603
}
604
605
/* @ 246ED4 for 0x4FC; orig name: func_80198704 */
606
void get_3DG1_shape(struct ObjShape *shape) {
607
UNUSED u8 pad78[8];
608
struct GdVec3f tempNormal; /* maybe? */
609
s32 curFaceVtx;
610
s32 faceVtxID;
611
s32 totalVtx;
612
s32 totalFacePoints;
613
struct GdVec3f tempVec;
614
struct ObjFace *newFace;
615
struct ObjVertex *vtxHead = NULL; // ptr to first made ObjVertex in the Obj* list
616
s32 vtxCount = 0;
617
struct ObjFace *faceHead = NULL; // ptr to first made OBjFace in the Obj* list
618
s32 faceCount = 0;
619
struct ObjFace **facePtrArr;
620
struct ObjVertex **vtxPtrArr;
621
struct ObjMaterial *mtl;
622
623
shape->mtlGroup = make_group(0);
624
imin("get_3DG1_shape");
625
626
vtxPtrArr = gd_malloc_perm(72000 * sizeof(struct ObjVertex *)); // 288,000 = 72,000 * 4
627
facePtrArr = gd_malloc_perm(76000 * sizeof(struct ObjFace *)); // 304,000 = 76,000 * 4
628
629
tempNormal.x = 0.0f;
630
tempNormal.y = 0.0f;
631
tempNormal.z = 1.0f;
632
633
load_next_line_into_buf();
634
if (!getint(&totalVtx)) {
635
fatal_printf("Missing number of points");
636
}
637
638
load_next_line_into_buf();
639
while (scan_to_next_non_whitespace()) {
640
getfloat(&tempVec.x);
641
getfloat(&tempVec.y);
642
getfloat(&tempVec.z);
643
vtxPtrArr[vtxCount] = gd_make_vertex(tempVec.x, tempVec.y, tempVec.z);
644
645
if (vtxHead == NULL) {
646
vtxHead = vtxPtrArr[vtxCount];
647
}
648
649
func_8019807C(vtxPtrArr[vtxCount]);
650
vtxCount++;
651
652
if (vtxCount >= 4000) {
653
fatal_printf("Too many vertices in shape data");
654
}
655
656
shape->vtxCount++;
657
clear_buf_to_cr();
658
659
if (--totalVtx == 0) { /* Count down vertex ponts */
660
break;
661
}
662
}
663
664
while (scan_to_next_non_whitespace()) {
665
if (!getint(&totalFacePoints)) {
666
fatal_printf("Missing number of points in face");
667
}
668
669
mtl = find_or_add_new_mtl(shape->mtlGroup, 0, tempNormal.x, tempNormal.y, tempNormal.z);
670
newFace = make_face_with_material(mtl);
671
672
if (faceHead == NULL) {
673
faceHead = newFace;
674
}
675
676
facePtrArr[faceCount] = newFace;
677
faceCount++;
678
if (faceCount >= 4000) {
679
fatal_printf("Too many faces in shape data");
680
}
681
682
curFaceVtx = 0;
683
while (get_current_buf_char() != '\0') {
684
getint(&faceVtxID);
685
686
if (curFaceVtx > 3) {
687
fatal_printf("Too many points in a face(%d)", curFaceVtx);
688
}
689
690
newFace->vertices[curFaceVtx] = vtxPtrArr[faceVtxID];
691
curFaceVtx++;
692
693
if (is_line_end(get_current_buf_char()) || --totalFacePoints == 0) {
694
break;
695
}
696
}
697
698
newFace->vtxCount = curFaceVtx;
699
700
if (newFace->vtxCount > 3) {
701
fatal_printf("Too many points in a face(%d)", newFace->vtxCount);
702
}
703
704
calc_face_normal(newFace);
705
706
tempNormal.x = newFace->normal.x > 0.0f ? 1.0f : 0.0f;
707
tempNormal.y = newFace->normal.y > 0.0f ? 1.0f : 0.0f;
708
tempNormal.z = newFace->normal.z > 0.0f ? 1.0f : 0.0f;
709
710
shape->faceCount++;
711
712
clear_buf_to_cr();
713
}
714
715
gd_free(vtxPtrArr);
716
gd_free(facePtrArr);
717
718
shape->vtxGroup = make_group_of_type(OBJ_TYPE_VERTICES, (struct GdObj *) vtxHead, NULL);
719
shape->faceGroup = make_group_of_type(OBJ_TYPE_FACES, (struct GdObj *) faceHead, NULL);
720
721
imout();
722
}
723
724
/* @ 2473D0 for 0x390; orig name: func_80198C00 */
725
void get_OBJ_shape(struct ObjShape *shape) {
726
UNUSED u8 pad7D54[4];
727
struct GdColour faceClr;
728
s32 curFaceVtx;
729
s32 faceVtxIndex;
730
struct GdVec3f tempVec;
731
struct ObjFace *newFace;
732
struct ObjVertex *vtxArr[4000];
733
struct ObjFace *faceArr[4000];
734
s32 faceCount = 0;
735
s32 vtxCount = 0;
736
737
faceClr.r = 1.0f;
738
faceClr.g = 0.5f;
739
faceClr.b = 1.0f;
740
741
sGdLineBufCsr = 0;
742
743
while (scan_to_next_non_whitespace()) {
744
switch (get_and_advance_buf()) {
745
case 'v':
746
getfloat(&tempVec.x);
747
getfloat(&tempVec.y);
748
getfloat(&tempVec.z);
749
750
vtxArr[vtxCount] = gd_make_vertex(tempVec.x, tempVec.y, tempVec.z);
751
func_8019807C(vtxArr[vtxCount]);
752
vtxCount++;
753
754
if (vtxCount >= 4000) {
755
fatal_printf("Too many vertices in shape data");
756
}
757
758
shape->vtxCount++;
759
break;
760
761
case 'f':
762
newFace = make_face_with_colour(faceClr.r, faceClr.g, faceClr.b);
763
faceArr[faceCount] = newFace;
764
faceCount++;
765
766
if (faceCount >= 4000) {
767
fatal_printf("Too many faces in shape data");
768
}
769
770
curFaceVtx = 0;
771
while (get_current_buf_char() != '\0') {
772
getint(&faceVtxIndex);
773
774
if (curFaceVtx > 3) {
775
fatal_printf("Too many points in a face(%d)", curFaceVtx);
776
}
777
778
/* .obj vertex list is 1-indexed */
779
newFace->vertices[curFaceVtx] = vtxArr[faceVtxIndex - 1];
780
curFaceVtx++;
781
782
if (is_line_end(get_current_buf_char())) {
783
break;
784
}
785
}
786
787
/* These are already set by make_face_with_colour... */
788
newFace->colour.r = faceClr.r;
789
newFace->colour.g = faceClr.g;
790
newFace->colour.b = faceClr.b;
791
792
newFace->vtxCount = curFaceVtx;
793
794
if (newFace->vtxCount > 3) {
795
fatal_printf("Too many points in a face(%d)", newFace->vtxCount);
796
}
797
798
calc_face_normal(newFace);
799
800
shape->faceCount++;
801
break;
802
803
case 'g':
804
break;
805
case '#':
806
break;
807
default:
808
break;
809
}
810
811
clear_buf_to_cr();
812
}
813
814
shape->vtxGroup = make_group_of_type(OBJ_TYPE_VERTICES, (struct GdObj *) vtxArr[0], NULL);
815
shape->faceGroup = make_group_of_type(OBJ_TYPE_FACES, (struct GdObj *) faceArr[0], NULL);
816
}
817
818
/* @ 247760 for 0x124; orig name: func_80198F90 */
819
struct ObjGroup *group_faces_in_mtl_grp(struct ObjGroup *mtlGroup, struct GdObj *fromObj,
820
struct GdObj *toObj) {
821
struct ObjMaterial *curObjAsMtl;
822
struct ObjGroup *newGroup;
823
struct GdObj *curObj;
824
register struct ListNode *node;
825
struct GdObj *curLinkedObj;
826
827
newGroup = make_group(0);
828
829
for (node = mtlGroup->firstMember; node != NULL; node = node->next) {
830
curLinkedObj = node->obj;
831
curObjAsMtl = (struct ObjMaterial *) curLinkedObj;
832
833
curObj = fromObj;
834
while (curObj != NULL) {
835
if (curObj == toObj) {
836
break;
837
}
838
839
if (curObj->type == OBJ_TYPE_FACES) {
840
if (((struct ObjFace *) curObj)->mtl == curObjAsMtl) {
841
addto_group(newGroup, curObj);
842
}
843
}
844
curObj = curObj->prev;
845
}
846
}
847
848
return newGroup;
849
}
850
851
/* @ 247884 for 0x13c; orig name: func_801990B4 */
852
struct ObjMaterial *find_or_add_new_mtl(struct ObjGroup *group, UNUSED s32 a1, f32 r, f32 g, f32 b) {
853
struct ObjMaterial *newMtl;
854
register struct ListNode *node;
855
struct ObjMaterial *foundMtl;
856
857
for (node = group->firstMember; node != NULL; node = node->next) {
858
foundMtl = (struct ObjMaterial *) node->obj;
859
860
if (foundMtl->header.type == OBJ_TYPE_MATERIALS) {
861
if (foundMtl->Kd.r == r) {
862
if (foundMtl->Kd.g == g) {
863
if (foundMtl->Kd.b == b) {
864
return foundMtl;
865
}
866
}
867
}
868
}
869
}
870
871
newMtl = make_material(0, NULL, 1);
872
set_cur_dynobj((struct GdObj *)newMtl);
873
d_set_diffuse(r, g, b);
874
addto_group(group, (struct GdObj *) newMtl);
875
876
return newMtl;
877
}
878
879
/* @ 2479C0 for 0x470; orig name: func_801991F0 */
880
void read_ARK_shape(struct ObjShape *shape, char *fileName) {
881
union {
882
s8 bytes[0x48];
883
struct {
884
u8 pad[0x40];
885
s32 word40;
886
s32 word44;
887
} data;
888
} fileInfo;
889
890
union {
891
s8 bytes[0x10];
892
struct {
893
f32 v[3];
894
s32 faceCount;
895
} data;
896
} faceInfo; // face normal x,y,z? + count
897
898
union {
899
s8 bytes[0x10];
900
struct {
901
s32 vtxCount;
902
f32 x, y, z;
903
} data;
904
} face; // face vtx count + vtx x,y,z ?
905
906
union {
907
s8 bytes[0x18];
908
struct {
909
f32 v[3];
910
f32 nv[3]; /* Guessing on the normals; they aren't used */
911
} data;
912
} vtx;
913
914
UNUSED u8 pad54[4];
915
struct GdVec3f sp48;
916
struct ObjFace *sp44; // newly made face with mtl sp34;
917
struct ObjFace *sp40 = NULL; // first made face
918
struct ObjVertex *sp3C; // newly made vtx
919
struct ObjVertex *sp38 = NULL; // first made vtx
920
struct ObjMaterial *sp34; // found or new mtl for face
921
UNUSED s32 sp30 = 0;
922
UNUSED s32 sp2C = 0;
923
924
shape->mtlGroup = make_group(0);
925
926
sp48.x = 1.0f;
927
sp48.y = 0.5f;
928
sp48.z = 1.0f;
929
930
sGdShapeFile = gd_fopen(fileName, "rb");
931
932
if (sGdShapeFile == NULL) {
933
fatal_printf("Cant load shape '%s'", fileName);
934
}
935
936
gd_fread(fileInfo.bytes, 0x48, 1, sGdShapeFile);
937
stub_renderer_12(&fileInfo.bytes[0x40]); // face count?
938
stub_renderer_12(&fileInfo.bytes[0x44]);
939
940
while (fileInfo.data.word40-- > 0) {
941
gd_fread(faceInfo.bytes, 0x10, 1, sGdShapeFile);
942
stub_renderer_14(&faceInfo.bytes[0x0]);
943
stub_renderer_14(&faceInfo.bytes[0x4]);
944
stub_renderer_14(&faceInfo.bytes[0x8]);
945
946
sp48.x = faceInfo.data.v[0];
947
sp48.y = faceInfo.data.v[1];
948
sp48.z = faceInfo.data.v[2];
949
950
sp34 = find_or_add_new_mtl(shape->mtlGroup, 0, sp48.x, sp48.y, sp48.z);
951
952
stub_renderer_12(&faceInfo.bytes[0xC]);
953
954
while (faceInfo.data.faceCount-- > 0) {
955
shape->faceCount++;
956
gd_fread(face.bytes, 0x10, 1, sGdShapeFile);
957
stub_renderer_14(&face.bytes[0x4]); // read word as f32?
958
stub_renderer_14(&face.bytes[0x8]);
959
stub_renderer_14(&face.bytes[0xC]);
960
961
sp44 = make_face_with_material(sp34);
962
963
if (sp40 == NULL) {
964
sp40 = sp44;
965
}
966
967
stub_renderer_12(&face.bytes[0x0]);
968
969
if (face.data.vtxCount > 3) {
970
while (face.data.vtxCount-- > 0) {
971
gd_fread(vtx.bytes, 0x18, 1, sGdShapeFile);
972
}
973
continue;
974
}
975
976
while (face.data.vtxCount-- > 0) {
977
shape->vtxCount++;
978
gd_fread(vtx.bytes, 0x18, 1, sGdShapeFile);
979
stub_renderer_14(&vtx.bytes[0x00]);
980
stub_renderer_14(&vtx.bytes[0x04]);
981
stub_renderer_14(&vtx.bytes[0x08]);
982
stub_renderer_14(&vtx.bytes[0x0C]);
983
stub_renderer_14(&vtx.bytes[0x10]);
984
stub_renderer_14(&vtx.bytes[0x14]);
985
986
func_801980E8(vtx.data.v);
987
sp3C = gd_make_vertex(vtx.data.v[0], vtx.data.v[1], vtx.data.v[2]);
988
989
if (sp44->vtxCount > 3) {
990
fatal_printf("Too many points in a face(%d)", sp44->vtxCount);
991
}
992
993
sp44->vertices[sp44->vtxCount] = sp3C;
994
sp44->vtxCount++;
995
996
if (sp38 == NULL) {
997
sp38 = sp3C;
998
}
999
}
1000
1001
calc_face_normal(sp44);
1002
}
1003
}
1004
1005
shape->vtxGroup = make_group_of_type(OBJ_TYPE_VERTICES, (struct GdObj *) sp38, NULL);
1006
shape->faceGroup = group_faces_in_mtl_grp(shape->mtlGroup, (struct GdObj *) sp40, NULL);
1007
gd_fclose(sGdShapeFile);
1008
}
1009
1010
/* @ 247E30 for 0x148; orig name: Unknown80199660 */
1011
struct GdFile *get_shape_from_file(struct ObjShape *shape, char *fileName) {
1012
printf("Loading %s...\n", fileName);
1013
start_memtracker(fileName);
1014
shape->unk3C = 0;
1015
shape->faceCount = 0;
1016
shape->vtxCount = 0;
1017
1018
if (gd_str_contains(fileName, ".ark")) {
1019
read_ARK_shape(shape, fileName);
1020
} else {
1021
sGdShapeFile = gd_fopen(fileName, "r");
1022
1023
if (sGdShapeFile == NULL) {
1024
fatal_printf("Cant open shape '%s'", fileName);
1025
}
1026
1027
sGdLineBufCsr = 0;
1028
sGdLineBuf[sGdLineBufCsr] = '\0';
1029
load_next_line_into_buf();
1030
1031
if (is_next_buf_word("3DG1")) {
1032
get_3DG1_shape(shape);
1033
} else {
1034
get_OBJ_shape(shape);
1035
}
1036
1037
printf("Num Vertices=%d\n", shape->vtxCount);
1038
printf("Num Faces=%d\n", shape->faceCount);
1039
printf("\n");
1040
1041
gd_fclose(sGdShapeFile);
1042
}
1043
1044
stop_memtracker(fileName);
1045
1046
return sGdShapeFile;
1047
}
1048
1049
/* @ 247F78 for 0x69c; orig name: Unknown801997A8 */
1050
struct ObjShape *make_grid_shape(enum ObjTypeFlag gridType, s32 a1, s32 a2, s32 a3, s32 a4) {
1051
UNUSED u32 pad1074;
1052
void *objBuf[32][32]; // vertex or particle depending on gridType
1053
f32 sp70;
1054
f32 sp6C;
1055
f32 sp68;
1056
UNUSED u32 pad64;
1057
UNUSED u32 pad60;
1058
f32 sp5C;
1059
s32 parI;
1060
s32 row;
1061
s32 col;
1062
UNUSED s32 sp4C = 0;
1063
struct ObjShape *gridShape;
1064
f32 sp44;
1065
struct ObjFace *sp40 = NULL; // first made shape?
1066
struct ObjGroup *parOrVtxGrp; // group of made particles or vertices (based on gridType)
1067
UNUSED u32 pad38;
1068
struct ObjGroup *mtlGroup;
1069
struct GdVec3f *sp30; // GdVec3f* ? from gd_get_colour
1070
struct GdVec3f *sp2C; //^
1071
struct ObjMaterial *mtl1; // first made material
1072
struct ObjMaterial *mtl2; // second made material
1073
UNUSED u32 pad20;
1074
1075
sp30 = (struct GdVec3f *) gd_get_colour(a1);
1076
sp2C = (struct GdVec3f *) gd_get_colour(a2);
1077
1078
mtl1 = make_material(0, NULL, 1);
1079
set_cur_dynobj((struct GdObj *) mtl1);
1080
d_set_diffuse(sp30->x, sp30->y, sp30->z);
1081
mtl1->type = 0x40;
1082
1083
mtl2 = make_material(0, NULL, 2);
1084
set_cur_dynobj((struct GdObj *) mtl2);
1085
d_set_diffuse(sp2C->x, sp2C->y, sp2C->z);
1086
mtl2->type = 0x40;
1087
1088
mtlGroup = make_group(2, mtl1, mtl2);
1089
gridShape = make_shape(0, "grid");
1090
gridShape->faceCount = 0;
1091
gridShape->vtxCount = 0;
1092
1093
sp44 = 2.0 / a3; //? 2.0f
1094
sp5C = -1.0f;
1095
sp6C = 0.0f;
1096
sp70 = -1.0f;
1097
1098
for (col = 0; col <= a4; col++) {
1099
sp68 = sp5C;
1100
for (row = 0; row <= a3; row++) {
1101
gridShape->vtxCount++;
1102
if (gridType == OBJ_TYPE_VERTICES) {
1103
objBuf[row][col] = gd_make_vertex(sp68, sp6C, sp70);
1104
} else if (gridType == OBJ_TYPE_PARTICLES) {
1105
objBuf[row][col] = make_particle(0, 0, sp68, sp6C + 2.0f, sp70);
1106
((struct ObjParticle *) objBuf[row][col])->unk44 = (1.0 + sp68) / 2.0;
1107
((struct ObjParticle *) objBuf[row][col])->unk48 = (1.0 + sp70) / 2.0;
1108
}
1109
sp68 += sp44;
1110
}
1111
sp70 += sp44;
1112
}
1113
1114
for (col = 0; col < a4; col++) {
1115
for (row = 0; row < a3; row++) {
1116
gridShape->faceCount += 2;
1117
if (a1 != a2) {
1118
if ((row + col) & 1) {
1119
D_801BAC9C = make_face_with_material(mtl1);
1120
D_801BACA0 = make_face_with_material(mtl1);
1121
} else {
1122
D_801BAC9C = make_face_with_material(mtl2);
1123
D_801BACA0 = make_face_with_material(mtl2);
1124
}
1125
} else {
1126
D_801BAC9C = make_face_with_material(mtl1);
1127
D_801BACA0 = make_face_with_material(mtl2);
1128
}
1129
1130
if (sp40 == NULL) {
1131
sp40 = D_801BAC9C;
1132
}
1133
1134
add_3_vtx_to_face(D_801BAC9C, objBuf[row][col + 1], objBuf[row + 1][col + 1],
1135
objBuf[row][col]);
1136
add_3_vtx_to_face(D_801BACA0, objBuf[row + 1][col + 1], objBuf[row + 1][col],
1137
objBuf[row][col]);
1138
}
1139
}
1140
1141
if (gridType == OBJ_TYPE_PARTICLES) {
1142
for (parI = 0; parI <= a3; parI++) {
1143
((struct ObjParticle *) objBuf[parI][0])->flags |= 2;
1144
((struct ObjParticle *) objBuf[parI][a4])->flags |= 2;
1145
}
1146
1147
for (parI = 0; parI <= a4; parI++) {
1148
((struct ObjParticle *) objBuf[0][parI])->flags |= 2;
1149
((struct ObjParticle *) objBuf[a3][parI])->flags |= 2;
1150
}
1151
}
1152
1153
parOrVtxGrp = make_group_of_type(gridType, (struct GdObj *) objBuf[0][0], NULL);
1154
gridShape->vtxGroup = parOrVtxGrp;
1155
gridShape->mtlGroup = mtlGroup;
1156
1157
gridShape->faceGroup = group_faces_in_mtl_grp(gridShape->mtlGroup, (struct GdObj *) sp40, NULL);
1158
1159
printf("grid: points=%d, faces=%d\n", gridShape->vtxGroup->id, gridShape->faceGroup->id);
1160
return gridShape;
1161
}
1162
1163
/* @ 248614 for 0x44 */
1164
void Unknown80199E44(UNUSED s32 a0, struct GdObj *a1, struct GdObj *a2, UNUSED s32 a3) {
1165
UNUSED struct ObjGroup *sp1C = make_group(2, a1, a2);
1166
}
1167
1168
/* @ 248658 for 0x5c */
1169
void Unknown80199E88(struct ObjFace *face) {
1170
D_801BAC74 = make_plane(FALSE, face);
1171
1172
if (D_801BAC78 == NULL) {
1173
D_801BAC78 = D_801BAC74;
1174
}
1175
}
1176
1177
/* @ 2486B4 for 0xbc; orig name: func_80199EE4 */
1178
struct ObjNet *make_netfromshape(struct ObjShape *shape) {
1179
struct ObjNet *newNet;
1180
1181
if (shape == NULL) {
1182
fatal_printf("make_netfromshape(): null shape ptr");
1183
}
1184
1185
D_801BAC78 = NULL;
1186
apply_to_obj_types_in_group(OBJ_TYPE_FACES, (applyproc_t) Unknown80199E88, shape->faceGroup);
1187
D_801BAD08 = make_group_of_type(OBJ_TYPE_PLANES, (struct GdObj *) D_801BAC78, NULL);
1188
newNet = make_net(0, shape, NULL, D_801BAD08, shape->vtxGroup);
1189
newNet->netType = 1;
1190
1191
return newNet;
1192
}
1193
1194
/**
1195
* Controls the dizzy (game over) animation of Mario's head.
1196
*/
1197
void animate_mario_head_gameover(struct ObjAnimator *self) {
1198
switch (self->state) {
1199
case 0:
1200
self->frame = 1.0f;
1201
self->animSeqNum = 1; // game over anim sequence
1202
self->state = 1;
1203
break;
1204
case 1:
1205
self->frame += 1.0f;
1206
// After the gameover animation ends, switch to the normal animation
1207
if (self->frame == 166.0f) {
1208
self->frame = 69.0f;
1209
self->state = 4;
1210
self->controlFunc = animate_mario_head_normal;
1211
self->animSeqNum = 0; // normal anim sequence
1212
}
1213
break;
1214
}
1215
}
1216
1217
/**
1218
* Controls the normal animation of Mario's head. This functions like a state machine.
1219
*/
1220
void animate_mario_head_normal(struct ObjAnimator *self) {
1221
s32 state = 0; // TODO: label these states
1222
s32 aBtnPressed = gGdCtrl.dragging;
1223
1224
switch (self->state) {
1225
case 0:
1226
// initialize?
1227
self->frame = 1.0f;
1228
self->animSeqNum = 0; // normal anim sequence
1229
state = 2;
1230
self->nods = 5;
1231
break;
1232
case 2:
1233
if (aBtnPressed) {
1234
state = 5;
1235
}
1236
1237
self->frame += 1.0f;
1238
1239
if (self->frame == 810.0f) {
1240
self->frame = 750.0f;
1241
self->nods -= 1;
1242
if (self->nods == 0) {
1243
state = 3;
1244
}
1245
}
1246
break;
1247
case 3:
1248
self->frame += 1.0f;
1249
1250
if (self->frame == 820.0f) {
1251
self->frame = 69.0f;
1252
state = 4;
1253
}
1254
break;
1255
case 4:
1256
self->frame += 1.0f;
1257
1258
if (self->frame == 660.0f) {
1259
self->frame = 661.0f;
1260
state = 2;
1261
self->nods = 5;
1262
}
1263
break;
1264
case 5:
1265
if (self->frame == 660.0f) {
1266
state = 7;
1267
} else if (self->frame > 660.0f) {
1268
self->frame -= 1.0f;
1269
} else if (self->frame < 660.0f) {
1270
self->frame += 1.0f;
1271
}
1272
1273
self->stillTimer = 150;
1274
break;
1275
case 7: // Mario is staying still while his eyes follow the cursor
1276
if (aBtnPressed) {
1277
self->stillTimer = 300;
1278
} else {
1279
self->stillTimer--;
1280
if (self->stillTimer == 0) {
1281
state = 6;
1282
}
1283
}
1284
self->frame = 660.0f;
1285
break;
1286
case 6:
1287
state = 2;
1288
self->nods = 5;
1289
break;
1290
}
1291
1292
if (state != 0) {
1293
self->state = state;
1294
}
1295
}
1296
1297
/**
1298
* Loads the Mario head from `dynlist_mario_master`, sets up grabbers, and makes
1299
* sparkle particles
1300
*/
1301
s32 load_mario_head(void (*aniFn)(struct ObjAnimator *)) {
1302
struct ObjNet *sp54; // net made with sp48 group
1303
UNUSED u8 pad4C[0x54 - 0x4c];
1304
struct ObjGroup *sp48; // Joint group
1305
UNUSED u8 pad40[0x48 - 0x40];
1306
struct ObjGroup *mainShapesGrp;
1307
struct GdObj *sp38; // object list head before making a bunch of joints
1308
struct GdObj *faceJoint; // joint on the face that `grabberJoint` pulls
1309
struct ObjJoint *grabberJoint; // joint that's dragged by the cursor
1310
struct ObjCamera *camera;
1311
struct ObjAnimator *animator;
1312
struct ObjParticle *particle;
1313
1314
// Load Mario head from the dynlist
1315
1316
start_memtracker("mario face");
1317
d_set_name_suffix("l"); // add "l" to the end of all dynobj names generated by the dynlist, for some reason
1318
1319
d_use_integer_names(TRUE);
1320
animator = (struct ObjAnimator *) d_makeobj(D_ANIMATOR, AsDynName(DYNOBJ_MARIO_MAIN_ANIMATOR));
1321
animator->controlFunc = aniFn;
1322
d_use_integer_names(FALSE);
1323
// FIXME: make segment address work once seg4 is disassembled
1324
gMarioFaceGrp = (struct ObjGroup *) load_dynlist(dynlist_mario_master);
1325
stop_memtracker("mario face");
1326
1327
// Make camera
1328
1329
camera = (struct ObjCamera *) d_makeobj(D_CAMERA, NULL);
1330
d_set_rel_pos(0.0f, 200.0f, 2000.0f);
1331
d_set_world_pos(0.0f, 200.0f, 2000.0f);
1332
d_set_flags(4);
1333
camera->lookAt.x = 0.0f;
1334
camera->lookAt.y = 200.0f;
1335
camera->lookAt.z = 0.0f;
1336
1337
addto_group(gMarioFaceGrp, &camera->header);
1338
addto_group(gMarioFaceGrp, &animator->header);
1339
1340
d_set_name_suffix(NULL); // stop adding "l" to generated dynobj names
1341
1342
// Make sparkle particles
1343
1344
particle = make_particle(0, COLOUR_WHITE, 0.0f, 0.0f, 0.0f);
1345
particle->unk60 = 3;
1346
particle->unk64 = 3;
1347
particle->attachedToObj = &camera->header;
1348
particle->shapePtr = gShapeSilverSpark;
1349
addto_group(gGdLightGroup, &particle->header);
1350
1351
particle = make_particle(0, COLOUR_WHITE, 0.0f, 0.0f, 0.0f);
1352
particle->unk60 = 3;
1353
particle->unk64 = 2;
1354
particle->attachedToObj = d_use_obj("N228l"); // DYNOBJ_SILVER_STAR_LIGHT
1355
particle->shapePtr = gShapeSilverSpark;
1356
addto_group(gGdLightGroup, &particle->header);
1357
1358
particle = make_particle(0, COLOUR_RED, 0.0f, 0.0f, 0.0f);
1359
particle->unk60 = 3;
1360
particle->unk64 = 2;
1361
particle->attachedToObj = d_use_obj("N231l"); // DYNOBJ_RED_STAR_LIGHT
1362
particle->shapePtr = gShapeRedSpark;
1363
addto_group(gGdLightGroup, &particle->header);
1364
1365
mainShapesGrp = (struct ObjGroup *) d_use_obj("N1000l"); // DYNOBJ_MARIO_MAIN_SHAPES_GROUP
1366
create_gddl_for_shapes(mainShapesGrp);
1367
sp38 = gGdObjectList;
1368
1369
// Make grabbers to move the face with the cursor
1370
1371
grabberJoint = make_grabber_joint(sGrabJointTestShape, 0, -500.0f, 0.0f, -150.0f);
1372
faceJoint = d_use_obj("N167l"); // DYNOBJ_MARIO_LEFT_EAR_JOINT_1
1373
grabberJoint->attachedObjsGrp = make_group(1, faceJoint);
1374
1375
grabberJoint = make_grabber_joint(sGrabJointTestShape, 0, 500.0f, 0.0f, -150.0f);
1376
faceJoint = d_use_obj("N176l"); // DYNOBJ_MARIO_RIGHT_EAR_JOINT_1
1377
grabberJoint->attachedObjsGrp = make_group(1, faceJoint);
1378
1379
grabberJoint = make_grabber_joint(sGrabJointTestShape, 0, 0.0f, 700.0f, 300.0f);
1380
faceJoint = d_use_obj("N131l"); // DYNOBJ_MARIO_CAP_JOINT_1
1381
grabberJoint->attachedObjsGrp = make_group(1, faceJoint);
1382
1383
// drag eyelids and eyebrows along with cap?
1384
faceJoint = d_use_obj("N206l"); // DYNOBJ_LEFT_EYELID_JOINT_1
1385
addto_group(grabberJoint->attachedObjsGrp, faceJoint);
1386
faceJoint = d_use_obj("N215l"); // DYNOBJ_RIGHT_EYELID_JOINT_1
1387
addto_group(grabberJoint->attachedObjsGrp, faceJoint);
1388
faceJoint = d_use_obj("N31l"); // DYNOBJ_MARIO_LEFT_EYEBROW_MPART_JOINT_1
1389
addto_group(grabberJoint->attachedObjsGrp, faceJoint);
1390
faceJoint = d_use_obj("N65l"); // DYNOBJ_MARIO_RIGHT_EYEBROW_MPART_JOINT_1
1391
addto_group(grabberJoint->attachedObjsGrp, faceJoint);
1392
1393
grabberJoint = make_grabber_joint(sGrabJointTestShape, 0, 0.0f, 0.0f, 600.0f);
1394
faceJoint = d_use_obj("N185l"); // DYNOBJ_MARIO_NOSE_JOINT_1
1395
grabberJoint->attachedObjsGrp = make_group(1, faceJoint);
1396
1397
grabberJoint = make_grabber_joint(sGrabJointTestShape, 0, 0.0f, -300.0f, 300.0f);
1398
faceJoint = d_use_obj("N194l"); // DYNOBJ_MARIO_LEFT_JAW_JOINT
1399
grabberJoint->attachedObjsGrp = make_group(1, faceJoint);
1400
1401
grabberJoint = make_grabber_joint(sGrabJointTestShape, 0, 250.0f, -150.0f, 300.0f);
1402
faceJoint = d_use_obj("N158l"); // DYNOBJ_MARIO_RIGHT_LIP_CORNER_JOINT_1
1403
grabberJoint->attachedObjsGrp = make_group(1, faceJoint);
1404
1405
faceJoint = d_use_obj("N15l"); // DYNOBJ_MARIO_LEFT_MUSTACHE_JOINT_1
1406
addto_group(grabberJoint->attachedObjsGrp, faceJoint);
1407
1408
grabberJoint = make_grabber_joint(sGrabJointTestShape, 0, -250.0f, -150.0f, 300.0f);
1409
faceJoint = d_use_obj("N149l"); // DYNOBJ_MARIO_LEFT_LIP_CORNER_JOINT_1
1410
grabberJoint->attachedObjsGrp = make_group(1, faceJoint);
1411
1412
faceJoint = d_use_obj("N6l"); // DYNOBJ_MARIO_RIGHT_MUSTACHE_JOINT_1
1413
addto_group(grabberJoint->attachedObjsGrp, faceJoint);
1414
1415
// make the left eye follow cursor
1416
grabberJoint = make_grabber_joint(sGrabJointTestShape, 0, 100.0f, 200.0f, 400.0f);
1417
faceJoint = d_use_obj("N112l"); // DYNOBJ_MARIO_RIGHT_EYE_UNKNOWN_NET
1418
grabberJoint->attachedObjsGrp = make_group(1, faceJoint);
1419
grabberJoint->updateFunc = eye_joint_update_func;
1420
grabberJoint->rootAnimator = animator;
1421
grabberJoint->header.drawFlags &= ~OBJ_IS_GRABBALE;
1422
1423
// make the right eye follow cursor
1424
grabberJoint = make_grabber_joint(sGrabJointTestShape, 0, -100.0f, 200.0f, 400.0f);
1425
faceJoint = d_use_obj("N96l"); // DYNOBJ_MARIO_LEFT_EYE_UNKNOWN_NET
1426
grabberJoint->attachedObjsGrp = make_group(1, faceJoint);
1427
grabberJoint->updateFunc = eye_joint_update_func;
1428
grabberJoint->rootAnimator = animator;
1429
grabberJoint->header.drawFlags &= ~OBJ_IS_GRABBALE;
1430
1431
sp48 = make_group_of_type(OBJ_TYPE_JOINTS, sp38, NULL);
1432
sp54 = make_net(0, NULL, sp48, NULL, NULL);
1433
sp54->netType = 3;
1434
addto_group(gMarioFaceGrp, &sp48->header);
1435
addto_groupfirst(gMarioFaceGrp, &sp54->header);
1436
1437
return 0;
1438
}
1439
1440
/* @ 249288 for 0xe0 */
1441
void load_shapes2(void) {
1442
imin("load_shapes2()");
1443
reset_dynlist();
1444
func_80197280();
1445
1446
sCubeShape = make_shape(0, "cube");
1447
1448
gSpotShape = (struct ObjShape *) load_dynlist(dynlist_spot_shape);
1449
scale_verts_in_shape(gSpotShape, 200.0f, 200.0f, 200.0f);
1450
1451
sGrabJointTestShape = (struct ObjShape *) load_dynlist(dynlist_test_cube);
1452
scale_verts_in_shape(sGrabJointTestShape, 30.0f, 30.0f, 30.0f);
1453
1454
sCubeShapeGroup = make_group_of_type(OBJ_TYPE_SHAPES, &sCubeShape->header, NULL);
1455
create_gddl_for_shapes(sCubeShapeGroup);
1456
1457
imout();
1458
}
1459
1460
/* @ 249368 -> 249594 */
1461
struct ObjGroup *Unknown8019AB98(UNUSED u32 a0) {
1462
struct ObjLight *light1;
1463
struct ObjLight *light2;
1464
struct GdObj *oldObjHead = gGdObjectList; // obj head node before making lights
1465
1466
light1 = make_light(0, NULL, 0);
1467
light1->position.x = 100.0f;
1468
light1->position.y = 200.0f;
1469
light1->position.z = 300.0f;
1470
1471
light1->diffuse.r = 1.0f;
1472
light1->diffuse.g = 0.0f;
1473
light1->diffuse.b = 0.0f;
1474
1475
light1->unk30 = 1.0f;
1476
1477
light1->unk68.x = 0.4f;
1478
light1->unk68.y = 0.9f;
1479
1480
light1->unk80.x = 4.0f;
1481
light1->unk80.y = 4.0f;
1482
light1->unk80.z = 2.0f;
1483
1484
light2 = make_light(0, NULL, 1);
1485
light2->position.x = 100.0f;
1486
light2->position.y = 200.0f;
1487
light2->position.z = 300.0f;
1488
1489
light2->diffuse.r = 0.0f;
1490
light2->diffuse.g = 0.0f;
1491
light2->diffuse.b = 1.0f;
1492
1493
light2->unk30 = 1.0f;
1494
1495
light2->unk80.x = -4.0f;
1496
light2->unk80.y = 4.0f;
1497
light2->unk80.z = -2.0f;
1498
1499
gGdLightGroup = make_group_of_type(OBJ_TYPE_LIGHTS, oldObjHead, NULL);
1500
1501
return gGdLightGroup;
1502
}
1503
1504
/* @ 249594 for 0x100 */
1505
struct ObjGroup *Unknown8019ADC4(UNUSED u32 a0) {
1506
UNUSED struct ObjLight *unusedLight;
1507
struct ObjLight *newLight;
1508
struct GdObj *oldObjHead;
1509
1510
unusedLight = make_light(0, NULL, 0);
1511
oldObjHead = gGdObjectList;
1512
newLight = make_light(0, NULL, 0);
1513
1514
newLight->position.x = 0.0f;
1515
newLight->position.y = -500.0f;
1516
newLight->position.z = 0.0f;
1517
1518
newLight->diffuse.r = 1.0f;
1519
newLight->diffuse.g = 0.0f;
1520
newLight->diffuse.b = 0.0f;
1521
1522
newLight->unk30 = 1.0f;
1523
1524
gGdLightGroup = make_group_of_type(OBJ_TYPE_LIGHTS, oldObjHead, NULL);
1525
1526
return gGdLightGroup;
1527
}
1528
1529
/* @ 249694 for 0x5c */
1530
struct ObjGroup *Unknown8019AEC4(UNUSED u32 a0) {
1531
UNUSED u32 sp24;
1532
UNUSED u32 sp20;
1533
UNUSED struct GdObj *sp1C;
1534
1535
sp1C = gGdObjectList;
1536
gGdLightGroup = make_group(0);
1537
return gGdLightGroup;
1538
}
1539
1540