diff options
| author | Rozelette <Rozelette@users.noreply.github.com> | 2021-03-27 14:29:30 -0500 |
|---|---|---|
| committer | GitHub <noreply@github.com> | 2021-03-27 14:29:30 -0500 |
| commit | fee7a49abc84fbe91116f969a90570cff15decde (patch) | |
| tree | 972de249287b0f1d11f04aeb33d28d4e7140f75e /src | |
| parent | 012e3c21aeb43437d53a90c2fbd8dfe525d95915 (diff) | |
z_lights fully matched (#80)
* z_lights OK
* Documentation
* Fixup for z_collision_check
* Improve function types of bind functions
* Fixup for types
Diffstat (limited to 'src')
| -rw-r--r-- | src/code/game.c | 52 | ||||
| -rw-r--r-- | src/code/z_collision_check.c | 12 | ||||
| -rw-r--r-- | src/code/z_effect_soft_sprite.c | 8 | ||||
| -rw-r--r-- | src/code/z_lib.c | 18 | ||||
| -rw-r--r-- | src/code/z_lights.c | 514 | ||||
| -rw-r--r-- | src/code/z_scene.c | 2 | ||||
| -rw-r--r-- | src/code/z_scene_proc.c | 16 | ||||
| -rw-r--r-- | src/overlays/actors/ovl_En_Dy_Extra/z_en_dy_extra.c | 20 |
8 files changed, 320 insertions, 322 deletions
diff --git a/src/code/game.c b/src/code/game.c index bde34635e..5f1013a68 100644 --- a/src/code/game.c +++ b/src/code/game.c @@ -27,34 +27,34 @@ void GameState_SetFBFilter(Gfx** gfx, u32 arg1) { if ((R_FB_FILTER_TYPE > 0) && (R_FB_FILTER_TYPE < 5)) { D_801F8010.type = R_FB_FILTER_TYPE; - D_801F8010.color.red = R_FB_FILTER_PRIM_COLOR(0); - D_801F8010.color.green = R_FB_FILTER_PRIM_COLOR(1); - D_801F8010.color.blue = R_FB_FILTER_PRIM_COLOR(2); - D_801F8010.color.alpha = R_FB_FILTER_A; + D_801F8010.color.r = R_FB_FILTER_PRIM_COLOR(0); + D_801F8010.color.g = R_FB_FILTER_PRIM_COLOR(1); + D_801F8010.color.b = R_FB_FILTER_PRIM_COLOR(2); + D_801F8010.color.a = R_FB_FILTER_A; func_80140D10(&D_801F8010, &_gfx, arg1); } else { if ((R_FB_FILTER_TYPE == 5) || (R_FB_FILTER_TYPE == 6)) { D_801F8020.useRgba = (R_FB_FILTER_TYPE == 6); - D_801F8020.primColor.red = R_FB_FILTER_PRIM_COLOR(0); - D_801F8020.primColor.green = R_FB_FILTER_PRIM_COLOR(1); - D_801F8020.primColor.blue = R_FB_FILTER_PRIM_COLOR(2); - D_801F8020.primColor.alpha = R_FB_FILTER_A; - D_801F8020.envColor.red = R_FB_FILTER_ENV_COLOR(0); - D_801F8020.envColor.green = R_FB_FILTER_ENV_COLOR(1); - D_801F8020.envColor.blue = R_FB_FILTER_ENV_COLOR(2); - D_801F8020.envColor.alpha = R_FB_FILTER_A; + D_801F8020.primColor.r = R_FB_FILTER_PRIM_COLOR(0); + D_801F8020.primColor.g = R_FB_FILTER_PRIM_COLOR(1); + D_801F8020.primColor.b = R_FB_FILTER_PRIM_COLOR(2); + D_801F8020.primColor.a = R_FB_FILTER_A; + D_801F8020.envColor.r = R_FB_FILTER_ENV_COLOR(0); + D_801F8020.envColor.g = R_FB_FILTER_ENV_COLOR(1); + D_801F8020.envColor.b = R_FB_FILTER_ENV_COLOR(2); + D_801F8020.envColor.a = R_FB_FILTER_A; func_80142100(&D_801F8020, &_gfx, arg1); } else { if (R_FB_FILTER_TYPE == 7) { sMonoColors.unk_00 = 0; - sMonoColors.primColor.red = R_FB_FILTER_PRIM_COLOR(0); - sMonoColors.primColor.green = R_FB_FILTER_PRIM_COLOR(1); - sMonoColors.primColor.blue = R_FB_FILTER_PRIM_COLOR(2); - sMonoColors.primColor.alpha = R_FB_FILTER_A; - sMonoColors.envColor.red = R_FB_FILTER_ENV_COLOR(0); - sMonoColors.envColor.green = R_FB_FILTER_ENV_COLOR(1); - sMonoColors.envColor.blue = R_FB_FILTER_ENV_COLOR(2); - sMonoColors.envColor.alpha = R_FB_FILTER_A; + sMonoColors.primColor.r = R_FB_FILTER_PRIM_COLOR(0); + sMonoColors.primColor.g = R_FB_FILTER_PRIM_COLOR(1); + sMonoColors.primColor.b = R_FB_FILTER_PRIM_COLOR(2); + sMonoColors.primColor.a = R_FB_FILTER_A; + sMonoColors.envColor.r = R_FB_FILTER_ENV_COLOR(0); + sMonoColors.envColor.g = R_FB_FILTER_ENV_COLOR(1); + sMonoColors.envColor.b = R_FB_FILTER_ENV_COLOR(2); + sMonoColors.envColor.a = R_FB_FILTER_A; VisMono_Draw(&sMonoColors, &_gfx, arg1); } } @@ -81,11 +81,11 @@ void GameState_Draw(GameState *ctxt, GraphicsContext *gCtxt) { if (R_FB_FILTER_TYPE && R_FB_FILTER_ENV_COLOR(3) == 0) { GameState_SetFBFilter(&nextDisplayList, (u32) gCtxt->zbuffer); } - + if (R_ENABLE_ARENA_DBG < 0) { R_ENABLE_ARENA_DBG = 0; } - + gSPEndDisplayList(nextDisplayList++); Graph_BranchDlist(_polyOpa, nextDisplayList); gCtxt->polyOpa.p = nextDisplayList; @@ -111,12 +111,12 @@ void Game_ResetSegments(GraphicsContext *gCtxt) { void func_801736DC(GraphicsContext *gCtxt) { Gfx* nextDisplayList; Gfx* _polyOpa; - + nextDisplayList = Graph_GfxPlusOne(_polyOpa = gCtxt->polyOpa.p); gSPDisplayList(gCtxt->overlay.p++, nextDisplayList); gSPEndDisplayList(nextDisplayList++); Graph_BranchDlist(_polyOpa, nextDisplayList); - + gCtxt->polyOpa.p = nextDisplayList; } @@ -207,7 +207,7 @@ lblUnk:; Gamealloc_Init(&ctxt->alloc); Game_InitHeap(ctxt, 0x100000); Game_SetFramerateDivisor(ctxt, 3); - + gameStateInit(ctxt); func_80140CE0(&D_801F8010); @@ -216,7 +216,7 @@ lblUnk:; func_80140898(&D_801F8048); func_801773A0(&D_801F7FF0); func_8013ED9C(); - + osSendMesg(&ctxt->gfxCtx->unk5C, NULL, 1); } diff --git a/src/code/z_collision_check.c b/src/code/z_collision_check.c index 4d1d0fbf9..cbb29f8a6 100644 --- a/src/code/z_collision_check.c +++ b/src/code/z_collision_check.c @@ -3828,9 +3828,9 @@ void CollisionCheck_SpawnShieldParticles(GlobalContext* ctxt, Vec3f* v) { shieldParticleInitMetal.position.x = v->x; shieldParticleInitMetal.position.y = v->y; shieldParticleInitMetal.position.z = v->z; - shieldParticleInitMetal.lightParams.posX = shieldParticleInitMetal.position.x; - shieldParticleInitMetal.lightParams.posY = shieldParticleInitMetal.position.y; - shieldParticleInitMetal.lightParams.posZ = shieldParticleInitMetal.position.z; + shieldParticleInitMetal.lightPoint.x = shieldParticleInitMetal.position.x; + shieldParticleInitMetal.lightPoint.y = shieldParticleInitMetal.position.y; + shieldParticleInitMetal.lightPoint.z = shieldParticleInitMetal.position.z; Effect_Add(ctxt, &effectIndex, 3, 0, 1, &shieldParticleInitMetal); } @@ -3883,9 +3883,9 @@ void CollisionCheck_SpawnShieldParticlesWood(GlobalContext* ctxt, Vec3f* v, Vec3 shieldParticleInitWood.position.x = v->x; shieldParticleInitWood.position.y = v->y; shieldParticleInitWood.position.z = v->z; - shieldParticleInitWood.lightParams.posX = shieldParticleInitWood.position.x; - shieldParticleInitWood.lightParams.posY = shieldParticleInitWood.position.y; - shieldParticleInitWood.lightParams.posZ = shieldParticleInitWood.position.z; + shieldParticleInitWood.lightPoint.x = shieldParticleInitWood.position.x; + shieldParticleInitWood.lightPoint.y = shieldParticleInitWood.position.y; + shieldParticleInitWood.lightPoint.z = shieldParticleInitWood.position.z; Effect_Add(ctxt, &effectIndex, 3, 0, 1, &shieldParticleInitWood); func_8019F1C0(pos, 0x1837); diff --git a/src/code/z_effect_soft_sprite.c b/src/code/z_effect_soft_sprite.c index be20a2452..3755a7aa2 100644 --- a/src/code/z_effect_soft_sprite.c +++ b/src/code/z_effect_soft_sprite.c @@ -253,12 +253,12 @@ void EffectSS_DrawParticle(GlobalContext* ctxt, s32 index) { } void EffectSS_DrawAllParticles(GlobalContext* ctxt) { - LightMapper* s0; + Lights* s0; s32 i; - s0 = Lights_CreateMapper(&ctxt->lightCtx, ctxt->state.gfxCtx); - Lights_MapLights(s0, ctxt->lightCtx.lightsHead, 0, ctxt); - Lights_UploadLights(s0, ctxt->state.gfxCtx); + s0 = LightContext_NewLights(&ctxt->lightCtx, ctxt->state.gfxCtx); + Lights_BindAll(s0, ctxt->lightCtx.listHead, 0, ctxt); + Lights_Draw(s0, ctxt->state.gfxCtx); for (i = 0; i < EffectSS2Info.size; i++) { if (EffectSS2Info.data_table[i].life > -1) { diff --git a/src/code/z_lib.c b/src/code/z_lib.c index cb48e72d3..9e99b9d85 100644 --- a/src/code/z_lib.c +++ b/src/code/z_lib.c @@ -538,11 +538,11 @@ void Math_SmoothScaleMaxS(s16* start, s16 target, s16 scale, s16 maxStep) { *start += v0; } -void Color_RGBA8_Copy(ColorRGBA8* dst, ColorRGBA8* src) { - dst->red = src->red; - dst->green = src->green; - dst->blue = src->blue; - dst->alpha = src->alpha; +void Color_RGBA8_Copy(Color_RGBA8* dst, Color_RGBA8* src) { + dst->r = src->r; + dst->g = src->g; + dst->b = src->b; + dst->a = src->a; } void func_801000A4(u16 a0) { @@ -569,11 +569,11 @@ void Lib_TranslateAndRotateYVec3f(Vec3f* translation, s16 rotation, Vec3f* src, } #ifdef NON_MATCHING -void Lib_LerpRGB(RGB* a, RGB* b, f32 t, RGB* dst) { +void Lib_LerpRGB(Color_RGB8* a, Color_RGB8* b, f32 t, Color_RGB8* dst) { // XXX regalloc is slightly off - dst->red = (f32)a->red + ((f32)b->red - (f32)a->red) * t; - dst->green = (f32)a->green + ((f32)b->green - (f32)a->green) * t; - dst->blue = (f32)a->blue + ((f32)b->blue - (f32)a->blue) * t; + dst->r = (f32)a->r + ((f32)b->r - (f32)a->r) * t; + dst->g = (f32)a->g + ((f32)b->g - (f32)a->g) * t; + dst->b = (f32)a->b + ((f32)b->b - (f32)a->b) * t; } #else #pragma GLOBAL_ASM("./asm/non_matchings/code/z_lib/Lib_LerpRGB.asm") diff --git a/src/code/z_lights.c b/src/code/z_lights.c index 7ed0b0951..c1c36d35c 100644 --- a/src/code/z_lights.c +++ b/src/code/z_lights.c @@ -1,152 +1,143 @@ #include <ultra64.h> #include <global.h> -void Lights_InitPositionalLight(LightInfoPositional* info, s16 posX, s16 posY, s16 posZ, u8 red, u8 green, u8 blue, s16 radius, u32 type) { +void Lights_PointSetInfo(LightInfo* info, s16 x, s16 y, s16 z, u8 r, u8 g, u8 b, s16 radius, s32 type) { info->type = type; - info->params.posX = posX; - info->params.posY = posY; - info->params.posZ = posZ; - Lights_SetPositionalLightColorAndRadius(info, red, green, blue, radius); + info->params.point.x = x; + info->params.point.y = y; + info->params.point.z = z; + Lights_PointSetColorAndRadius(info, r, g, b, radius); } -void Lights_InitType0PositionalLight(LightInfoPositional* info, s16 posX, s16 posY, s16 posZ, u8 red, u8 green, u8 blue, s16 radius) { - Lights_InitPositionalLight(info, posX, posY, posZ, red, green, blue, radius, 0); +void Lights_PointNoGlowSetInfo(LightInfo* info, s16 x, s16 y, s16 z, u8 r, u8 g, u8 b, s16 radius) { + Lights_PointSetInfo(info, x, y, z, r, g, b, radius, LIGHT_POINT_NOGLOW); } -void Lights_InitType2PositionalLight(LightInfoPositional* info, s16 posX, s16 posY, s16 posZ, u8 red, u8 green, u8 blue, s16 radius) { - Lights_InitPositionalLight(info, posX, posY, posZ, red, green, blue, radius, 2); +void Lights_PointGlowSetInfo(LightInfo* info, s16 x, s16 y, s16 z, u8 r, u8 g, u8 b, s16 radius) { + Lights_PointSetInfo(info, x, y, z, r, g, b, radius, LIGHT_POINT_GLOW); } -void Lights_SetPositionalLightColorAndRadius(LightInfoPositional* info, u8 red, u8 green, u8 blue, s16 radius) { - info->params.red = red; - info->params.green = green; - info->params.blue = blue; - info->params.radius = radius; +void Lights_PointSetColorAndRadius(LightInfo* info, u8 r, u8 g, u8 b, s16 radius) { + info->params.point.color[0] = r; + info->params.point.color[1] = g; + info->params.point.color[2] = b; + info->params.point.radius = radius; } -void Lights_SetPositionalLightPosition(LightInfoPositional* info, s16 posX, s16 posY, s16 posZ) { - info->params.posX = posX; - info->params.posY = posY; - info->params.posZ = posZ; +void Lights_PointSetPosition(LightInfo* info, s16 x, s16 y, s16 z) { + info->params.point.x = x; + info->params.point.y = y; + info->params.point.z = z; } -void Lights_InitDirectional(LightInfoDirectional* info, s8 dirX, s8 dirY, s8 dirZ, u8 red, u8 green, u8 blue) { - info->type = 1; - info->params.dirX = dirX; - info->params.dirY = dirY; - info->params.dirZ = dirZ; - info->params.red = red; - info->params.green = green; - info->params.blue = blue; +void Lights_DirectionalSetInfo(LightInfo* info, s8 x, s8 y, s8 z, u8 r, u8 g, u8 b) { + info->type = LIGHT_DIRECTIONAL; + info->params.dir.x = x; + info->params.dir.y = y; + info->params.dir.z = z; + info->params.dir.color[0] = r; + info->params.dir.color[1] = g; + info->params.dir.color[2] = b; } -void Lights_MapperInit(LightMapper* mapper, u8 red, u8 green, u8 blue) { - mapper->lights.a.l.colc[0] = red; - mapper->lights.a.l.col[0] = red; - mapper->lights.a.l.colc[1] = green; - mapper->lights.a.l.col[1] = green; - mapper->lights.a.l.colc[2] = blue; - mapper->lights.a.l.col[2] = blue; - mapper->numLights = 0; +void Lights_Reset(Lights* lights, u8 r, u8 g, u8 b) { + lights->l.a.l.colc[0] = r; + lights->l.a.l.col[0] = r; + lights->l.a.l.colc[1] = g; + lights->l.a.l.col[1] = g; + lights->l.a.l.colc[2] = b; + lights->l.a.l.col[2] = b; + lights->numLights = 0; } -// XXX regalloc -#ifdef NON_MATCHING -void Lights_UploadLights(LightMapper* mapper, GraphicsContext* gCtxt) { +/* + * Draws every light in the provided Lights group + */ +void Lights_Draw(Lights* lights, GraphicsContext* gfxCtx) { Light* l; s32 i; - gSPNumLights(gCtxt->polyOpa.p++, mapper->numLights); - gSPNumLights(gCtxt->polyXlu.p++, mapper->numLights); + OPEN_DISPS(gfxCtx); - l = &mapper->lights.l[0]; + gSPNumLights(POLY_OPA_DISP++, lights->numLights); + gSPNumLights(POLY_XLU_DISP++, lights->numLights); - for (i = 0; i < mapper->numLights;) { - gSPLight(gCtxt->polyOpa.p++, l, ++i); - gSPLight(gCtxt->polyXlu.p++, l++, i); + l = lights->l.l; + + for (i = 0; i < lights->numLights;) { + gSPLight(POLY_OPA_DISP++, l, ++i); + gSPLight(POLY_XLU_DISP++, l++, i); } - gSPLight(gCtxt->polyOpa.p++, &mapper->lights.a, ++i); - gSPLight(gCtxt->polyXlu.p++, &mapper->lights.a, i); + gSPLight(POLY_OPA_DISP++, &lights->l.a, ++i); + gSPLight(POLY_XLU_DISP++, &lights->l.a, i); + + CLOSE_DISPS(gfxCtx); } -#else -#pragma GLOBAL_ASM("./asm/non_matchings/code/z_lights/Lights_UploadLights.asm") -#endif -Light* Lights_MapperGetNextFreeSlot(LightMapper* mapper) { - if (6 < mapper->numLights) { +Light* Lights_FindSlot(Lights* lights) { + if (lights->numLights >= 7) { return NULL; } - return &mapper->lights.l[mapper->numLights++]; + return &lights->l.l[lights->numLights++]; } -// XXX regalloc, some reorderings -#ifdef NON_MATCHING -void Lights_MapPositionalWithReference(LightMapper* mapper, LightInfoPositionalParams* params, Vec3f* pos) { +void Lights_BindPointWithReference(Lights* lights, LightParams* params, Vec3f* pos) { f32 xDiff; f32 yDiff; f32 zDiff; - f32 dist; - f32 radiusF; + f32 posDiff; + f32 scale; Light* light; - if (pos == NULL) return; - - if (params->radius < 1) return; - - xDiff = params->posX - pos->x; - yDiff = params->posY - pos->y; - zDiff = params->posZ - pos->z; - radiusF = params->radius; - dist = xDiff * xDiff + yDiff * yDiff + zDiff * zDiff; + if ((pos != NULL) && (params->point.radius >= 1)) { + xDiff = params->point.x - pos->x; + yDiff = params->point.y - pos->y; + zDiff = params->point.z - pos->z; + scale = params->point.radius; + posDiff = SQ(xDiff) + SQ(yDiff) + SQ(zDiff); - if (radiusF * radiusF > dist) { - light = Lights_MapperGetNextFreeSlot(mapper); - if (light == NULL) return; + if (SQ(scale) > posDiff) { + light = Lights_FindSlot(lights); - dist = sqrtf(dist); - - light->l.colc[0] = light->l.col[0] = params->red * (1 - (dist / radiusF) * (dist / radiusF)); - light->l.colc[1] = light->l.col[1] = params->green * (1 - (dist / radiusF) * (dist / radiusF)); - light->l.colc[2] = light->l.col[2] = params->blue * (1 - (dist / radiusF) * (dist / radiusF)); - - if (dist < 1) { - dist = 120; - } else { - dist = 120 / dist; + if (light != NULL) { + posDiff = sqrtf(posDiff); + scale = posDiff / scale; + scale = 1 - SQ(scale); + + light->l.col[0] = params->point.color[0] * scale; + light->l.colc[0] = light->l.col[0]; + light->l.col[1] = params->point.color[1] * scale; + light->l.colc[1] = light->l.col[1]; + light->l.col[2] = params->point.color[2] * scale; + light->l.colc[2] = light->l.col[2]; + + scale = (posDiff < 1) ? 120 : 120 / posDiff; + + light->l.dir[0] = xDiff * scale; + light->l.dir[1] = yDiff * scale; + light->l.dir[2] = zDiff * scale; + } } - - xDiff *= dist; - yDiff *= dist; - zDiff *= dist; - - light->l.dir[0] = xDiff; - light->l.dir[1] = yDiff; - light->l.dir[2] = zDiff; } } -#else -#pragma GLOBAL_ASM("./asm/non_matchings/code/z_lights/Lights_MapPositionalWithReference.asm") -#endif -// This function matches, but uses .rodata. We don't have a good way to match partial .rodata for a file yet. -#ifdef NON_MATCHING -void Lights_MapPositional(LightMapper* mapper, LightInfoPositionalParams* params, GlobalContext* ctxt) { +void Lights_BindPoint(Lights* lights, LightParams* params, GlobalContext* globalCtx) { Light* light; - f32 radiusF = params->radius; + f32 radiusF = params->point.radius; Vec3f posF; Vec3f adjustedPos; u32 pad; if (radiusF > 0) { - posF.x = params->posX; - posF.y = params->posY; - posF.z = params->posZ; - Matrix_MultiplyByVectorXYZ(&ctxt->unk187B0,&posF,&adjustedPos); + posF.x = params->point.x; + posF.y = params->point.y; + posF.z = params->point.z; + Matrix_MultiplyByVectorXYZ(&globalCtx->unk187B0,&posF,&adjustedPos); if ((adjustedPos.z > -radiusF) && (600 + radiusF > adjustedPos.z) && (400 > fabsf(adjustedPos.x) - radiusF) && (400 > fabsf(adjustedPos.y) - radiusF)) { - light = Lights_MapperGetNextFreeSlot(mapper); + light = Lights_FindSlot(lights); if (light != NULL) { radiusF = 4500000.0f / (radiusF * radiusF); if (radiusF > 255) { @@ -155,236 +146,250 @@ void Lights_MapPositional(LightMapper* mapper, LightInfoPositionalParams* params radiusF = 20; } - light->lPos.col[0] = params->red; - light->lPos.colc[0] = light->lPos.col[0]; - light->lPos.col[1] = params->green; - light->lPos.colc[1] = light->lPos.col[1]; - light->lPos.col[2] = params->blue; - light->lPos.colc[2] = light->lPos.col[2]; - light->lPos.pos[0] = params->posX; - light->lPos.pos[1] = params->posY; - light->lPos.pos[2] = params->posZ; - light->lPos.pad1 = 0x8; - light->lPos.pad2 = 0xFF; - light->lPos.unkE = (s8)radiusF; + light->p.col[0] = params->point.color[0]; + light->p.colc[0] = light->p.col[0]; + light->p.col[1] = params->point.color[1]; + light->p.colc[1] = light->p.col[1]; + light->p.col[2] = params->point.color[2]; + light->p.colc[2] = light->p.col[2]; + light->p.pos[0] = params->point.x; + light->p.pos[1] = params->point.y; + light->p.pos[2] = params->point.z; + light->p.unk3 = 0x8; + light->p.unk7 = 0xFF; + light->p.unkE = (s32)radiusF; } } } } -#else -#pragma GLOBAL_ASM("./asm/non_matchings/code/z_lights/Lights_MapPositional.asm") -#endif -void Lights_MapDirectional(LightMapper* mapper, LightInfoDirectionalParams* params, GlobalContext* ctxt) { - Light* light = Lights_MapperGetNextFreeSlot(mapper); +void Lights_BindDirectional(Lights* lights, LightParams* params, void* unused) { + Light* light = Lights_FindSlot(lights); if (light != NULL) { - light->l.col[0] = params->red; + light->l.col[0] = params->dir.color[0]; light->l.colc[0] = light->l.col[0]; - light->l.col[1] = params->green; + light->l.col[1] = params->dir.color[1]; light->l.colc[1] = light->l.col[1]; - light->l.col[2] = params->blue; + light->l.col[2] = params->dir.color[2]; light->l.colc[2] = light->l.col[2]; - light->l.dir[0] = params->dirX; - light->l.dir[1] = params->dirY; - light->l.dir[2] = params->dirZ; - light->l.pad1 = 0; + light->l.dir[0] = params->dir.x; + light->l.dir[1] = params->dir.y; + light->l.dir[2] = params->dir.z; + light->l.pad1 = 0; // TODO the fact that pad1 is set here means that it now does something in MM's microcode } } -void Lights_MapLights(LightMapper* mapper, z_Light* lights, Vec3f* refPos, GlobalContext* ctxt) { - if (lights != NULL) { - if ((refPos == NULL) && (mapper->enablePosLights == 1)) { +/** + * For every light in a provided list, try to find a free slot in the provided Lights group and bind + * a light to it. Then apply color and positional/directional info for each light + * based on the parameters supplied by the node. + * + * Note: Lights in a given list can only be binded to however many free slots are + * available in the Lights group. This is at most 7 slots for a new group, but could be less. + */ +void Lights_BindAll(Lights* lights, LightNode* listHead, Vec3f* refPos, GlobalContext* globalCtx) { + static LightsPosBindFunc posBindFuncs[] = { Lights_BindPoint, Lights_BindDirectional, Lights_BindPoint }; + static LightsBindFunc dirBindFuncs[] = { Lights_BindPointWithReference, Lights_BindDirectional, Lights_BindPointWithReference }; + + if (listHead != NULL) { + if ((refPos == NULL) && (lights->enablePosLights == 1)) { do { - lightPositionalMapFuncs[lights->info->type](mapper, &lights->info->params, ctxt); - lights = lights->next; - } while (lights != NULL); + posBindFuncs[listHead->info->type](lights, &listHead->info->params, globalCtx); + listHead = listHead->next; + } while (listHead != NULL); } else { do { - lightDirectionalMapFuncs[lights->info->type](mapper, &lights->info->params, refPos); - lights = lights->next; - } while (lights != NULL); + dirBindFuncs[listHead->info->type](lights, &listHead->info->params, refPos); + listHead = listHead->next; + } while (listHead != NULL); } } } -z_Light* Lights_FindFreeSlot(void) { - z_Light* ret; +LightNode* Lights_FindBufSlot() { + LightNode* ret; - if (0x1f < lightsList.numOccupied) { + if (sLightsBuffer.numOccupied >= LIGHTS_BUFFER_SIZE) { return NULL; } - ret = &lightsList.lights[lightsList.nextFree]; + ret = &sLightsBuffer.lights[sLightsBuffer.searchIndex]; while (ret->info != NULL) { - lightsList.nextFree++; - if (lightsList.nextFree < 0x20) { + sLightsBuffer.searchIndex++; + if (sLightsBuffer.searchIndex < LIGHTS_BUFFER_SIZE) { ret++; } else { - lightsList.nextFree = 0; - ret = &lightsList.lights[0]; + sLightsBuffer.searchIndex = 0; + ret = &sLightsBuffer.lights[0]; } } - lightsList.numOccupied++; + sLightsBuffer.numOccupied++; return ret; } -void Lights_Free(z_Light* light) { +void Lights_FreeNode(LightNode* light) { if (light != NULL) { - lightsList.numOccupied--; + sLightsBuffer.numOccupied--; light->info = NULL; - lightsList.nextFree = (light - lightsList.lights) / (s32)sizeof(z_Light); //! @bug Due to pointer arithmetic, the division is unnecessary + sLightsBuffer.searchIndex = (light - sLightsBuffer.lights) / (s32)sizeof(LightNode); //! @bug Due to pointer arithmetic, the division is unnecessary } } -void Lights_Init(GlobalContext* ctxt, LightingContext* lCtxt) { - Lights_ClearHead(ctxt, lCtxt); - Lights_SetAmbientColor(lCtxt, 80, 80, 80); - func_80102544(lCtxt, 0, 0, 0, 0x3e4, 0x3200); - bzero(&lightsList, sizeof(LightsList)); +void LightContext_Init(GlobalContext* globalCtx, LightContext* lightCtx) { + LightContext_InitList(globalCtx, lightCtx); + LightContext_SetAmbientColor(lightCtx, 80, 80, 80); + func_80102544(lightCtx, 0, 0, 0, 0x3E4, 0x3200); + bzero(&sLightsBuffer, sizeof(LightsBuffer)); } -void Lights_SetAmbientColor(LightingContext* lCtxt, u8 red, u8 green, u8 blue) { - lCtxt->ambientRed = red; - lCtxt->ambientGreen = green; - lCtxt->ambientBlue = blue; +void LightContext_SetAmbientColor(LightContext* lightCtx, u8 r, u8 g, u8 b) { + lightCtx->ambient.r = r; + lightCtx->ambient.g = g; + lightCtx->ambient.b = b; } -void func_80102544(LightingContext* lCtxt, u8 a1, u8 a2, u8 a3, s16 sp12, s16 sp16) { - lCtxt->unk7 = a1; - lCtxt->unk8 = a2; - lCtxt->unk9 = a3; - lCtxt->unkA = sp12; - lCtxt->unkC = sp16; +void func_80102544(LightContext* lightCtx, u8 a1, u8 a2, u8 a3, s16 numLights, s16 sp16) { + lightCtx->unk7 = a1; + lightCtx->unk8 = a2; + lightCtx->unk9 = a3; + lightCtx->unkA = numLights; + lightCtx->unkC = sp16; } -LightMapper* Lights_CreateMapper(LightingContext* lCtxt, GraphicsContext* gCtxt) { - return Lights_MapperAllocateAndInit(gCtxt, lCtxt->ambientRed, lCtxt->ambientGreen, lCtxt->ambientBlue); +/** + * Allocate a new Lights group and initilize the ambient color with that provided by LightContext + */ +Lights* LightContext_NewLights(LightContext* lightCtx, GraphicsContext* gfxCtx) { + return Lights_New(gfxCtx, lightCtx->ambient.r, lightCtx->ambient.g, lightCtx->ambient.b); } -void Lights_ClearHead(GlobalContext* ctxt, LightingContext* lCtxt) { - lCtxt->lightsHead = NULL; +void LightContext_InitList(GlobalContext* globalCtx, LightContext* lightCtx) { + lightCtx->listHead = NULL; } -void Lights_RemoveAll(GlobalContext* ctxt, LightingContext* lCtxt) { - while (lCtxt->lightsHead != NULL) { - Lights_Remove(ctxt, lCtxt, lCtxt->lightsHead); - lCtxt->lightsHead = lCtxt->lightsHead->next; +void LightContext_DestroyList(GlobalContext* globalCtx, LightContext* lightCtx) { + while (lightCtx->listHead != NULL) { + LightContext_RemoveLight(globalCtx, lightCtx, lightCtx->listHead); + lightCtx->listHead = lightCtx->listHead->next; } } -z_Light* Lights_Insert(GlobalContext* ctxt, LightingContext* lCtxt, LightInfo* info) { - z_Light* light; +/** + * Insert a new light into the list pointed to by LightContext + * + * Note: Due to the limited number of slots in a Lights group, inserting too many lights in the + * list may result in older entries not being bound to a Light when calling Lights_BindAll + */ +LightNode* LightContext_InsertLight(GlobalContext* globalCtx, LightContext* lightCtx, LightInfo* info) { + LightNode* light; - light = Lights_FindFreeSlot(); + light = Lights_FindBufSlot(); if (light != NULL) { light->info = info; light->prev = NULL; - light->next = lCtxt->lightsHead; + light->next = lightCtx->listHead; - if (lCtxt->lightsHead != NULL) { - lCtxt->lightsHead->prev = light; + if (lightCtx->listHead != NULL) { + lightCtx->listHead->prev = light; } - lCtxt->lightsHead = light; + lightCtx->listHead = light; } return light; } -void Lights_Remove(GlobalContext* ctxt, LightingContext* lCtxt, z_Light* light) { +void LightContext_RemoveLight(GlobalContext* globalCtx, LightContext* lightCtx, LightNode* light) { if (light != NULL) { if (light->prev != NULL) { light->prev->next = light->next; } else { - lCtxt->lightsHead = light->next; + lightCtx->listHead = light->next; } if (light->next != NULL) { light->next->prev = light->prev; } - Lights_Free(light); + Lights_FreeNode(light); } } -LightMapper* func_801026E8(GraphicsContext* gCtxt, u8 ambientRed, u8 ambientGreen, u8 ambientBlue, u8 numLights, u8 red, u8 green, u8 blue, s8 dirX, s8 dirY, s8 dirZ) { - LightMapper* mapper; +Lights* Lights_NewAndDraw(GraphicsContext* gfxCtx, u8 ambientR, u8 ambientG, u8 ambientB, u8 numLights, u8 r, u8 g, u8 b, s8 x, s8 y, s8 z) { + Lights* lights; s32 i; // TODO allocation should be a macro - mapper = (LightMapper *)((int)gCtxt->polyOpa.d - sizeof(LightMapper)); - gCtxt->polyOpa.d = (void*)mapper; + lights = (Lights *)((int)gfxCtx->polyOpa.d - sizeof(Lights)); + gfxCtx->polyOpa.d = (void*)lights; - mapper->lights.a.l.col[0] = mapper->lights.a.l.colc[0] = ambientRed; - mapper->lights.a.l.col[1] = mapper->lights.a.l.colc[1] = ambientGreen; - mapper->lights.a.l.col[2] = mapper->lights.a.l.colc[2] = ambientBlue; - mapper->enablePosLights = 0; - mapper->numLights = numLights; + lights->l.a.l.col[0] = lights->l.a.l.colc[0] = ambientR; + lights->l.a.l.col[1] = lights->l.a.l.colc[1] = ambientG; + lights->l.a.l.col[2] = lights->l.a.l.colc[2] = ambientB; + lights->enablePosLights = 0; + lights->numLights = numLights; for (i = 0; i < numLights; i++) { - mapper->lights.l[i].l.col[0] = mapper->lights.l[i].l.colc[0] = red; - mapper->lights.l[i].l.col[1] = mapper->lights.l[i].l.colc[1] = green; - mapper->lights.l[i].l.col[2] = mapper->lights.l[i].l.colc[2] = blue; - mapper->lights.l[i].l.dir[0] = dirX; - mapper->lights.l[i].l.dir[1] = dirY; - mapper->lights.l[i].l.dir[2] = dirZ; + lights->l.l[i].l.col[0] = lights->l.l[i].l.colc[0] = r; + lights->l.l[i].l.col[1] = lights->l.l[i].l.colc[1] = g; + lights->l.l[i].l.col[2] = lights->l.l[i].l.colc[2] = b; + lights->l.l[i].l.dir[0] = x; + lights->l.l[i].l.dir[1] = y; + lights->l.l[i].l.dir[2] = z; } - Lights_UploadLights(mapper,gCtxt); + Lights_Draw(lights,gfxCtx); - return mapper; + return lights; } -LightMapper* Lights_MapperAllocateAndInit(GraphicsContext* gCtxt, u8 red, u8 green, u8 blue) { - LightMapper* mapper; +Lights* Lights_New(GraphicsContext* gfxCtx, u8 ambientR, u8 ambientG, u8 ambientB) { + Lights* lights; // TODO allocation should be a macro - mapper = (LightMapper *)((int)gCtxt->polyOpa.d - sizeof(LightMapper)); - gCtxt->polyOpa.d = (void*)mapper; - - mapper->lights.a.l.col[0] = red; - mapper->lights.a.l.colc[0] = red; - mapper->lights.a.l.col[1] = green; - mapper->lights.a.l.colc[1] = green; - mapper->lights.a.l.col[2] = blue; - mapper->lights.a.l.colc[2] = blue; - mapper->enablePosLights = 0; - mapper->numLights = 0; - - return mapper; + lights = (Lights *)((int)gfxCtx->polyOpa.d - sizeof(Lights)); + gfxCtx->polyOpa.d = (void*)lights; + + lights->l.a.l.col[0] = ambientR; + lights->l.a.l.colc[0] = ambientR; + lights->l.a.l.col[1] = ambientG; + lights->l.a.l.colc[1] = ambientG; + lights->l.a.l.col[2] = ambientB; + lights->l.a.l.colc[2] = ambientB; + lights->enablePosLights = 0; + lights->numLights = 0; + + return lights; } -// XXX regalloc -#ifdef NON_MATCHING -void func_80102880(GlobalContext* ctxt) { - z_Light* light = ctxt->lightsContext.lightsHead; - LightInfoPositionalParams* params; - Vec3f local_14; - Vec3f local_20; - f32 local_24; - f32 fVar4; - s32 s2; - u32 pad[2]; +void Lights_GlowCheck(GlobalContext* globalCtx) { + LightNode* light = globalCtx->lightCtx.listHead; while (light != NULL) { - if (light->info->type == 2) { - params = (LightInfoPositionalParams*)&light->info->params; - local_14.x = params->posX; - local_14.y = params->posY; - local_14.z = params->posZ; - func_800B4EDC(ctxt, &local_14, &local_20, &local_24); - - params->unk9 = 0; - - if ((local_20.z > 1) && - (fabsf(local_20.x * local_24) < 1) && - (fabsf(local_20.y * local_24) < 1)) { - fVar4 = local_20.z * local_24; - s2 = (s32)(fVar4 * 16352) + 16352; - if (s2 < func_80178A94(local_20.x * local_24 * 160 + 160, local_20.y * local_24 * -120 + 120)) { - params->unk9 = 1; + LightPoint* params = (LightPoint*)&light->info->params; + + if (light->info->type == LIGHT_POINT_GLOW) { + Vec3f pos; + Vec3f multDest; + f32 wDest; + + pos.x = params->x; + pos.y = params->y; + pos.z = params->z; + func_800B4EDC(globalCtx, &pos, &multDest, &wDest); + + params->drawGlow = 0; + + if ((multDest.z > 1) && (fabsf(multDest.x * wDest) < 1) && (fabsf(multDest.y * wDest) < 1)) { + s32 wX = multDest.x * wDest * 160 + 160; + s32 wY = multDest.y * wDest * -120 + 120; + s32 wZ = (s32)((multDest.z * wDest) * 16352) + 16352; + s32 zBuf = func_80178A94(wX, wY); + + if (wZ < zBuf) { + params->drawGlow = 1; } } } @@ -392,22 +397,16 @@ void func_80102880(GlobalContext* ctxt) { light = light->next; } } -#else -#pragma GLOBAL_ASM("./asm/non_matchings/code/z_lights/func_80102880.asm") -#endif -// XXX regalloc -#ifdef NON_MATCHING -void func_80102A64(GlobalContext* ctxt) { +void Lights_DrawGlow(GlobalContext* globalCtx) { Gfx* dl; - LightInfoPositionalParams* params; - f32 scale; - GraphicsContext* gCtxt; - z_Light* light = ctxt->lightsContext.lightsHead; + LightPoint* params; + LightNode* light = globalCtx->lightCtx.listHead; if (light != NULL) { - gCtxt = ctxt->common.gCtxt; - dl = func_8012C7FC(gCtxt->polyXlu.p); + OPEN_DISPS(globalCtx->state.gfxCtx); + + dl = func_8012C7FC(POLY_XLU_DISP); gSPSetOtherMode(dl++, G_SETOTHERMODE_H, 4, 4, 0x00000080); //! This doesn't resolve to any of the macros in gdi.h @@ -417,17 +416,17 @@ void func_80102A64(GlobalContext* ctxt) { gSPDisplayList(dl++, &D_04029CB0); do { - if (light->info->type == 2) { - params = (LightInfoPositionalParams*)&light->info->params; - if (params->unk9 != 0) { - scale = (f32)params->radius * (f32)params->radius * 2e-6f; + if (light->info->type == LIGHT_POINT_GLOW) { + params = (LightPoint*)&light->info->params; + if (params->drawGlow) { + f32 scale = SQ((f32)params->radius) * 2e-6f; - gDPSetPrimColor(dl++, 0, 0, params->red, params->green, params->blue, 50); + gDPSetPrimColor(dl++, 0, 0, params->color[0], params->color[1], params->color[2], 50); - SysMatrix_InsertTranslation(params->posX, params->posY, params->posZ, 0); + SysMatrix_InsertTranslation(params->x, params->y, params->z, 0); SysMatrix_InsertScale(scale,scale,scale,1); - gSPMatrix(dl++, SysMatrix_AppendStateToPolyOpaDisp((ctxt->common).gCtxt), G_MTX_PUSH | G_MTX_LOAD | G_MTX_MODELVIEW); + gSPMatrix(dl++, SysMatrix_AppendStateToPolyOpaDisp(globalCtx->state.gfxCtx), G_MTX_NOPUSH | G_MTX_LOAD | G_MTX_MODELVIEW); gSPDisplayList(dl++, &D_04029CF0); } @@ -436,9 +435,8 @@ void func_80102A64(GlobalContext* ctxt) { light = light->next; } while (light != NULL); - gCtxt->polyXlu.p = dl; + POLY_XLU_DISP = dl; + + CLOSE_DISPS(globalCtx->state.gfxCtx); } } -#else -#pragma GLOBAL_ASM("./asm/non_matchings/code/z_lights/func_80102A64.asm") -#endif diff --git a/src/code/z_scene.c b/src/code/z_scene.c index e697bd871..8a0ed87b7 100644 --- a/src/code/z_scene.c +++ b/src/code/z_scene.c @@ -310,7 +310,7 @@ void Scene_HeaderCommand0C(GlobalContext* ctxt, SceneCmd* entry) { lightInfo = (LightInfo*)Lib_PtrSegToVirt(entry->lightList.segment); for (i = 0; i < entry->lightList.num; i++) { - Lights_Insert(ctxt, &ctxt->lightCtx, lightInfo); + LightContext_InsertLight(ctxt, &ctxt->lightCtx, lightInfo); lightInfo++; } } diff --git a/src/code/z_scene_proc.c b/src/code/z_scene_proc.c index b7775e868..9dea984ea 100644 --- a/src/code/z_scene_proc.c +++ b/src/code/z_scene_proc.c @@ -66,7 +66,7 @@ void SceneProc_DrawType1Texture(GlobalContext* ctxt, u32 segment, ScrollingTextu #ifdef NON_MATCHING // Slight ordering differences at the beginning -void SceneProc_DrawFlashingTexture(GlobalContext* ctxt, u32 segment, FlashingTexturePrimColor* primColor, RGBA8* envColor) { +void SceneProc_DrawFlashingTexture(GlobalContext* ctxt, u32 segment, FlashingTexturePrimColor* primColor, Color_RGBA8* envColor) { GraphicsContext* gfxCtx; Gfx* dl; @@ -108,7 +108,7 @@ void SceneProc_DrawFlashingTexture(GlobalContext* ctxt, u32 segment, FlashingTex #endif void SceneProc_DrawType2Texture(GlobalContext* ctxt, u32 segment, FlashingTextureParams* params) { - RGBA8* envColor; + Color_RGBA8* envColor; FlashingTexturePrimColor* primColor = (FlashingTexturePrimColor *)Lib_PtrSegToVirt(params->primColors); u32 pad; u32 index = gSceneProcStep % params->cycleLength; @@ -116,7 +116,7 @@ void SceneProc_DrawType2Texture(GlobalContext* ctxt, u32 segment, FlashingTextur primColor += index; if (params->envColors) { - envColor = (RGBA8*)Lib_PtrSegToVirt(params->envColors) + index; + envColor = (Color_RGBA8*)Lib_PtrSegToVirt(params->envColors) + index; } else { envColor = NULL; } @@ -132,18 +132,18 @@ s32 SceneProc_Lerp(s32 a, s32 b, f32 t) { // Slight ordering and regalloc differences around t = ... void SceneProc_DrawType3Texture(GlobalContext* ctxt, u32 segment, FlashingTextureParams* params) { FlashingTextureParams* params2 = params; - RGBA8* envColorTo; + Color_RGBA8* envColorTo; FlashingTexturePrimColor* primColorTo = (FlashingTexturePrimColor *)Lib_PtrSegToVirt(params2->primColors); u16* keyFrames = (u16*)Lib_PtrSegToVirt(params2->keyFrames); s32 index = gSceneProcStep % params2->cycleLength; s32 pad1; s32 keyFrameIndex; - RGBA8* envColorPtrIn; + Color_RGBA8* envColorPtrIn; f32 t; s32 pad2; FlashingTexturePrimColor primColorIn; - RGBA8* envColorFrom; - RGBA8 envColorIn; + Color_RGBA8* envColorFrom; + Color_RGBA8 envColorIn; s32 pad3; FlashingTexturePrimColor* primColorFrom; @@ -169,7 +169,7 @@ void SceneProc_DrawType3Texture(GlobalContext* ctxt, u32 segment, FlashingTextur primColorIn.lodFrac = SceneProc_Lerp(primColorFrom->lodFrac, primColorTo->lodFrac, t); if (params2->envColors) { - envColorTo = (RGBA8*)Lib_PtrSegToVirt(params2->envColors) + keyFrameIndex; + envColorTo = (Color_RGBA8*)Lib_PtrSegToVirt(params2->envColors) + keyFrameIndex; envColorFrom = envColorTo - 1; envColorIn.red = SceneProc_Lerp(envColorFrom->red, envColorTo->red, t); envColorIn.green = SceneProc_Lerp(envColorFrom->green, envColorTo->green, t); diff --git a/src/overlays/actors/ovl_En_Dy_Extra/z_en_dy_extra.c b/src/overlays/actors/ovl_En_Dy_Extra/z_en_dy_extra.c index 1a0c98f30..42a340eb0 100644 --- a/src/overlays/actors/ovl_En_Dy_Extra/z_en_dy_extra.c +++ b/src/overlays/actors/ovl_En_Dy_Extra/z_en_dy_extra.c @@ -82,12 +82,12 @@ void EnDyExtra_Update(Actor* thisx, GlobalContext* globalCtx) { } void EnDyExtra_Draw(Actor* thisx, GlobalContext* globalCtx) { - static ColorRGBA8 D_80A61740[] = { { 255, 255, 170, 255 }, - { 255, 170, 255, 255 }, - { 255, 255, 170, 255 }, - { 170, 255, 255, 255 }, - { 255, 255, 170, 255 } }; - static ColorRGBA8 D_80A61754[] = { + static Color_RGBA8 D_80A61740[] = { { 255, 255, 170, 255 }, + { 255, 170, 255, 255 }, + { 255, 255, 170, 255 }, + { 170, 255, 255, 255 }, + { 255, 255, 170, 255 } }; + static Color_RGBA8 D_80A61754[] = { { 255, 100, 0, 255 }, { 255, 0, 100, 255 }, { 100, 255, 0, 255 }, { 0, 100, 255, 255 }, { 255, 230, 0, 255 } }; static u8 D_80A61768[] = { 0x02, 0x01, 0x01, 0x02, 0x00, 0x00, 0x02, 0x01, 0x00, 0x02, 0x01, 0x00, 0x02, 0x01, @@ -118,10 +118,10 @@ void EnDyExtra_Draw(Actor* thisx, GlobalContext* globalCtx) { gDPPipeSync(POLY_XLU_DISP++); gSPMatrix(POLY_XLU_DISP++, SysMatrix_AppendStateToPolyOpaDisp(globalCtx->state.gfxCtx), G_MTX_NOPUSH | G_MTX_LOAD | G_MTX_MODELVIEW); - gDPSetPrimColor(POLY_XLU_DISP++, 0, 0x80, D_80A61740[this->type].red, D_80A61740[this->type].green, - D_80A61740[this->type].blue, 255); - gDPSetEnvColor(POLY_XLU_DISP++, D_80A61754[this->type].red, D_80A61754[this->type].green, - D_80A61754[this->type].blue, 128); + gDPSetPrimColor(POLY_XLU_DISP++, 0, 0x80, D_80A61740[this->type].r, D_80A61740[this->type].g, + D_80A61740[this->type].b, 255); + gDPSetEnvColor(POLY_XLU_DISP++, D_80A61754[this->type].r, D_80A61754[this->type].g, + D_80A61754[this->type].b, 128); gSPDisplayList(POLY_XLU_DISP++, D_0600DEF0); CLOSE_DISPS(gfxCtx); |
