diff --git a/README.md b/README.md index 37850f2d28..b38b977571 100644 --- a/README.md +++ b/README.md @@ -21,7 +21,7 @@ This is a fork of the ultrasm64 repo by CrashOveride which includes the followin - **Fazana**: PuppyLib, ucode swapping, audio load time optimisations (with Arctic), general hacker qol improvements, visual debug - **Reonu**: Starting the project/repo, widescreen, reonucam, various defines for hacker QoL - **JoshDuMan**: Decomp guy, general assistance -- **Arceveti**: Silhouette, shadow optimisation, better hanging, breath meter, 4 controller support +- **Arceveti**: Silhouette, shadow optimizations, better hanging, breath meter, painting objects, 4 controller support, implementation of frameperfection's rounded corners fix, naming most unknowns, various hacker QOL improvements, and various optimizations/fixes - **axollyon**: Console testing, bugfixes, idea-guying, and had a hand in silhouettes - **Wiseguy**: World scale reimplementation, silhouette, graph node optimisations, instant input patch, cake screen fix, segmented code support, and various optimizations/fixes - **Kaze**: Graph node optimisations, automatic optimal collision distance diff --git a/actors/common1.h b/actors/common1.h index 179032ca2d..bb7be165f0 100644 --- a/actors/common1.h +++ b/actors/common1.h @@ -226,6 +226,9 @@ extern const Gfx mushroom_1up_seg3_dl_0302A660[]; // number extern const GeoLayout number_geo[]; +// painting +extern const GeoLayout painting_geo[]; + // pebble extern const Gfx pebble_seg3_dl_0301CB00[]; diff --git a/actors/common1_geo.c b/actors/common1_geo.c index 7f75637ae3..2788d99aa8 100644 --- a/actors/common1_geo.c +++ b/actors/common1_geo.c @@ -18,6 +18,7 @@ #include "leaves/geo.inc.c" #include "mario_cap/geo.inc.c" #include "number/geo.inc.c" +#include "painting/geo.inc.c" #include "mushroom_1up/geo.inc.c" #include "star/geo.inc.c" #include "dirt/geo.inc.c" diff --git a/actors/painting/geo.inc.c b/actors/painting/geo.inc.c new file mode 100644 index 0000000000..02afff3ee1 --- /dev/null +++ b/actors/painting/geo.inc.c @@ -0,0 +1,9 @@ +#include "game/paintings.h" + +const GeoLayout painting_geo[] = { + GEO_CULLING_RADIUS(2000), + GEO_OPEN_NODE(), + GEO_ASM(0, geo_painting_draw), + GEO_CLOSE_NODE(), + GEO_END(), +}; diff --git a/bin/segment2.c b/bin/segment2.c index 260e007fe7..62ed2566bf 100644 --- a/bin/segment2.c +++ b/bin/segment2.c @@ -6,6 +6,7 @@ #include "types.h" #include "game/ingame_menu.h" #include "game/puppyprint.h" +#include "game/paintings.h" #include "make_const_nonconst.h" @@ -2968,650 +2969,4 @@ const Gfx dl_ia8_up_arrow_end[] = { gsSPEndDisplayList(), }; -// 0x02014958 - 0x02014960 - -// 0x02014970 - 0x020149A8 -const Gfx dl_paintings_rippling_begin[] = { - gsDPPipeSync(), - gsSPSetGeometryMode(G_LIGHTING | G_SHADING_SMOOTH), - gsDPSetCombineMode(G_CC_MODULATERGBA, G_CC_MODULATERGBA), - gsSPLightColor(LIGHT_1, 0xffffffff), - gsSPLightColor(LIGHT_2, 0x505050ff), - gsSPTexture(0xFFFF, 0xFFFF, 0, G_TX_RENDERTILE, G_ON), - gsSPEndDisplayList(), -}; - -// 0x020149A8 - 0x020149C8 -const Gfx dl_paintings_rippling_end[] = { - gsSPTexture(0xFFFF, 0xFFFF, 0, G_TX_RENDERTILE, G_OFF), - gsDPPipeSync(), - gsDPSetCombineMode(G_CC_SHADE, G_CC_SHADE), - gsSPEndDisplayList(), -}; - -// 0x020149C8 - 0x02014A00 -const Gfx dl_paintings_env_mapped_begin[] = { - gsDPPipeSync(), - gsSPSetGeometryMode(G_LIGHTING | G_TEXTURE_GEN), - gsDPSetCombineMode(G_CC_DECALRGB, G_CC_DECALRGB), - gsSPLightColor(LIGHT_1, 0xffffffff), - gsSPLightColor(LIGHT_2, 0x505050ff), - gsSPTexture(0x4000, 0x4000, 0, G_TX_RENDERTILE, G_ON), - gsSPEndDisplayList(), -}; - -// 0x02014A00 - 0x02014A30 -const Gfx dl_paintings_env_mapped_end[] = { - gsSPTexture(0x4000, 0x4000, 0, G_TX_RENDERTILE, G_OFF), - gsDPPipeSync(), - gsSPGeometryModeSetFirst(G_TEXTURE_GEN, G_LIGHTING), - gsDPSetCombineMode(G_CC_SHADE, G_CC_SHADE), - gsSPEndDisplayList(), -}; - -// 0x02014A30 - 0x02014A60 -const Gfx dl_paintings_draw_ripples[] = { - gsSP2Triangles( 0, 1, 2, 0x0, 3, 4, 5, 0x0), - gsSP2Triangles( 6, 7, 8, 0x0, 9, 10, 11, 0x0), - gsSP1Triangle( 12, 13, 14, 0x0), - gsSPEndDisplayList(), -}; - -// 14A60: triangle mesh -// 0x02014A60 -const s16 seg2_painting_triangle_mesh[] = { - 157, // numVtx - // format: - // 2D point (x, y), ripple (0 or 1) - 614, 583, 0, // 0 - 614, 614, 0, // 1 - 562, 614, 0, // 2 - 562, 553, 1, // 3 - 614, 522, 0, // 4 - 511, 583, 1, // 5 - 511, 614, 0, // 6 - 307, 614, 0, // 7 - 307, 583, 1, // 8 - 358, 614, 0, // 9 - 256, 614, 0, // 10 - 256, 553, 1, // 11 - 307, 522, 1, // 12 - 358, 553, 1, // 13 - 409, 583, 1, // 14 - 460, 614, 0, // 15 - 511, 522, 1, // 16 - 460, 553, 1, // 17 - 409, 522, 1, // 18 - 562, 307, 1, // 19 - 614, 338, 0, // 20 - 562, 430, 1, // 21 - 614, 399, 0, // 22 - 562, 368, 1, // 23 - 511, 338, 1, // 24 - 460, 307, 1, // 25 - 460, 430, 1, // 26 - 511, 399, 1, // 27 - 511, 460, 1, // 28 - 409, 338, 1, // 29 - 460, 368, 1, // 30 - 358, 307, 1, // 31 - 409, 460, 1, // 32 - 358, 430, 1, // 33 - 409, 399, 1, // 34 - 358, 368, 1, // 35 - 307, 338, 1, // 36 - 256, 307, 1, // 37 - 307, 399, 1, // 38 - 256, 430, 1, // 39 - 307, 460, 1, // 40 - 614, 460, 0, // 41 - 562, 491, 1, // 42 - 460, 491, 1, // 43 - 358, 491, 1, // 44 - 256, 491, 1, // 45 - 409, 276, 1, // 46 - 511, 276, 1, // 47 - 307, 276, 1, // 48 - 614, 31, 0, // 49 - 614, 0, 0, // 50 - 562, 0, 0, // 51 - 562, 123, 1, // 52 - 614, 92, 0, // 53 - 511, 31, 1, // 54 - 562, 61, 1, // 55 - 460, 0, 0, // 56 - 511, 0, 0, // 57 - 460, 123, 1, // 58 - 511, 92, 1, // 59 - 511, 153, 1, // 60 - 409, 31, 1, // 61 - 460, 61, 1, // 62 - 358, 0, 0, // 63 - 409, 0, 0, // 64 - 409, 92, 1, // 65 - 358, 123, 1, // 66 - 409, 153, 1, // 67 - 307, 31, 1, // 68 - 358, 61, 1, // 69 - 256, 0, 0, // 70 - 307, 0, 0, // 71 - 256, 123, 1, // 72 - 307, 92, 1, // 73 - 307, 153, 1, // 74 - 614, 153, 0, // 75 - 562, 246, 1, // 76 - 614, 215, 0, // 77 - 562, 184, 1, // 78 - 460, 246, 1, // 79 - 511, 215, 1, // 80 - 460, 184, 1, // 81 - 358, 246, 1, // 82 - 409, 215, 1, // 83 - 358, 184, 1, // 84 - 256, 246, 1, // 85 - 307, 215, 1, // 86 - 205, 583, 1, // 87 - 0, 614, 0, // 88 - 0, 583, 0, // 89 - 51, 614, 0, // 90 - 51, 553, 1, // 91 - 102, 583, 1, // 92 - 205, 522, 1, // 93 - 153, 553, 1, // 94 - 153, 614, 0, // 95 - 102, 522, 1, // 96 - 256, 368, 1, // 97 - 205, 338, 1, // 98 - 153, 307, 1, // 99 - 153, 430, 1, // 100 - 205, 399, 1, // 101 - 205, 460, 1, // 102 - 153, 368, 1, // 103 - 102, 338, 1, // 104 - 51, 307, 1, // 105 - 51, 430, 1, // 106 - 102, 399, 1, // 107 - 102, 460, 1, // 108 - 51, 368, 1, // 109 - 0, 338, 0, // 110 - 0, 460, 0, // 111 - 153, 491, 1, // 112 - 51, 491, 1, // 113 - 153, 246, 1, // 114 - 102, 276, 1, // 115 - 205, 276, 1, // 116 - 0, 276, 0, // 117 - 51, 246, 1, // 118 - 205, 31, 1, // 119 - 256, 61, 1, // 120 - 205, 0, 0, // 121 - 153, 0, 0, // 122 - 205, 153, 1, // 123 - 205, 92, 1, // 124 - 153, 123, 1, // 125 - 102, 31, 1, // 126 - 153, 61, 1, // 127 - 102, 0, 0, // 128 - 51, 0, 0, // 129 - 51, 123, 1, // 130 - 102, 92, 1, // 131 - 102, 153, 1, // 132 - 0, 31, 0, // 133 - 51, 61, 1, // 134 - 0, 153, 0, // 135 - 256, 184, 1, // 136 - 205, 215, 1, // 137 - 153, 184, 1, // 138 - 102, 215, 1, // 139 - 51, 184, 1, // 140 - 409, 614, 0, // 141 - 614, 307, 0, // 142 - 614, 276, 0, // 143 - 511, 307, 1, // 144 - 409, 307, 1, // 145 - 307, 307, 1, // 146 - 205, 614, 0, // 147 - 0, 522, 0, // 148 - 102, 614, 0, // 149 - 205, 307, 1, // 150 - 102, 307, 1, // 151 - 0, 399, 0, // 152 - 0, 307, 0, // 153 - 0, 215, 0, // 154 - 0, 92, 0, // 155 - 0, 0, 0, // 156 - // triangles - 264, - 8, 12, 13, // 0 - 0, 1, 2, // 1 - 3, 0, 2, // 2 - 4, 0, 3, // 3 - 5, 2, 6, // 4 - 2, 5, 3, // 5 - 7, 8, 9, // 6 - 8, 7, 10, // 7 - 11, 8, 10, // 8 - 12, 8, 11, // 9 - 9, 8, 13, // 10 - 13, 14, 9, // 11 - 14, 141, 9, // 12 - 5, 6, 15, // 13 - 5, 16, 3, // 14 - 16, 5, 17, // 15 - 17, 5, 15, // 16 - 14, 15, 141, // 17 - 15, 14, 17, // 18 - 18, 14, 13, // 19 - 14, 18, 17, // 20 - 19, 142, 20, // 21 - 19, 20, 23, // 22 - 28, 27, 21, // 23 - 21, 23, 22, // 24 - 22, 41, 21, // 25 - 20, 22, 23, // 26 - 23, 24, 19, // 27 - 21, 27, 23, // 28 - 24, 23, 27, // 29 - 25, 144, 24, // 30 - 19, 24, 144, // 31 - 24, 27, 30, // 32 - 25, 24, 30, // 33 - 26, 30, 27, // 34 - 27, 28, 26, // 35 - 36, 38, 97, // 36 - 26, 34, 30, // 37 - 29, 30, 34, // 38 - 30, 29, 25, // 39 - 25, 29, 145, // 40 - 31, 145, 29, // 41 - 31, 29, 35, // 42 - 29, 34, 35, // 43 - 32, 34, 26, // 44 - 33, 35, 34, // 45 - 34, 32, 33, // 46 - 33, 38, 35, // 47 - 35, 36, 31, // 48 - 36, 35, 38, // 49 - 37, 36, 97, // 50 - 37, 146, 36, // 51 - 31, 36, 146, // 52 - 28, 16, 43, // 53 - 38, 40, 39, // 54 - 39, 97, 38, // 55 - 40, 38, 33, // 56 - 21, 41, 42, // 57 - 41, 4, 42, // 58 - 3, 42, 4, // 59 - 42, 28, 21, // 60 - 28, 42, 16, // 61 - 3, 16, 42, // 62 - 26, 28, 43, // 63 - 17, 43, 16, // 64 - 43, 32, 26, // 65 - 32, 43, 18, // 66 - 17, 18, 43, // 67 - 33, 32, 44, // 68 - 32, 18, 44, // 69 - 13, 44, 18, // 70 - 44, 40, 33, // 71 - 13, 12, 44, // 72 - 40, 44, 12, // 73 - 39, 40, 45, // 74 - 40, 12, 45, // 75 - 48, 31, 146, // 76 - 11, 45, 12, // 77 - 25, 47, 144, // 78 - 46, 25, 145, // 79 - 47, 19, 144, // 80 - 19, 143, 142, // 81 - 31, 46, 145, // 82 - 60, 59, 52, // 83 - 49, 53, 55, // 84 - 50, 49, 51, // 85 - 51, 49, 55, // 86 - 52, 55, 53, // 87 - 53, 75, 52, // 88 - 54, 55, 59, // 89 - 52, 59, 55, // 90 - 55, 54, 51, // 91 - 54, 59, 62, // 92 - 56, 54, 62, // 93 - 57, 54, 56, // 94 - 54, 57, 51, // 95 - 58, 62, 59, // 96 - 59, 60, 58, // 97 - 68, 71, 63, // 98 - 61, 62, 65, // 99 - 58, 65, 62, // 100 - 62, 61, 56, // 101 - 61, 65, 69, // 102 - 63, 61, 69, // 103 - 64, 61, 63, // 104 - 61, 64, 56, // 105 - 65, 67, 66, // 106 - 66, 69, 65, // 107 - 67, 65, 58, // 108 - 68, 69, 73, // 109 - 69, 68, 63, // 110 - 66, 73, 69, // 111 - 68, 73, 120, // 112 - 70, 68, 120, // 113 - 71, 68, 70, // 114 - 72, 120, 73, // 115 - 73, 74, 72, // 116 - 74, 73, 66, // 117 - 75, 77, 78, // 118 - 52, 75, 78, // 119 - 76, 78, 77, // 120 - 77, 143, 76, // 121 - 76, 80, 78, // 122 - 60, 78, 80, // 123 - 78, 60, 52, // 124 - 46, 83, 79, // 125 - 58, 60, 81, // 126 - 60, 80, 81, // 127 - 79, 81, 80, // 128 - 80, 47, 79, // 129 - 47, 80, 76, // 130 - 81, 67, 58, // 131 - 67, 81, 83, // 132 - 79, 83, 81, // 133 - 66, 67, 84, // 134 - 67, 83, 84, // 135 - 82, 84, 83, // 136 - 83, 46, 82, // 137 - 84, 74, 66, // 138 - 82, 86, 84, // 139 - 74, 84, 86, // 140 - 74, 86, 136, // 141 - 72, 74, 136, // 142 - 85, 136, 86, // 143 - 86, 48, 85, // 144 - 48, 86, 82, // 145 - 25, 46, 79, // 146 - 79, 47, 25, // 147 - 82, 46, 31, // 148 - 19, 47, 76, // 149 - 76, 143, 19, // 150 - 31, 48, 82, // 151 - 37, 48, 146, // 152 - 85, 48, 37, // 153 - 10, 87, 11, // 154 - 87, 10, 147, // 155 - 92, 95, 149, // 156 - 88, 89, 90, // 157 - 89, 148, 91, // 158 - 90, 89, 91, // 159 - 91, 92, 90, // 160 - 92, 149, 90, // 161 - 93, 87, 94, // 162 - 87, 93, 11, // 163 - 94, 87, 95, // 164 - 87, 147, 95, // 165 - 95, 92, 94, // 166 - 96, 92, 91, // 167 - 92, 96, 94, // 168 - 39, 101, 97, // 169 - 97, 98, 37, // 170 - 98, 97, 101, // 171 - 99, 98, 103, // 172 - 99, 150, 98, // 173 - 37, 98, 150, // 174 - 98, 101, 103, // 175 - 100, 103, 101, // 176 - 101, 102, 100, // 177 - 102, 101, 39, // 178 - 100, 107, 103, // 179 - 103, 104, 99, // 180 - 104, 103, 107, // 181 - 105, 104, 109, // 182 - 105, 151, 104, // 183 - 99, 104, 151, // 184 - 104, 107, 109, // 185 - 106, 109, 107, // 186 - 107, 108, 106, // 187 - 108, 107, 100, // 188 - 109, 110, 105, // 189 - 106, 152, 109, // 190 - 110, 109, 152, // 191 - 105, 110, 153, // 192 - 111, 152, 106, // 193 - 11, 93, 45, // 194 - 102, 45, 93, // 195 - 45, 102, 39, // 196 - 102, 93, 112, // 197 - 100, 102, 112, // 198 - 94, 112, 93, // 199 - 112, 108, 100, // 200 - 108, 112, 96, // 201 - 94, 96, 112, // 202 - 106, 108, 113, // 203 - 108, 96, 113, // 204 - 91, 113, 96, // 205 - 91, 148, 113, // 206 - 113, 111, 106, // 207 - 111, 113, 148, // 208 - 114, 116, 99, // 209 - 99, 115, 114, // 210 - 115, 99, 151, // 211 - 99, 116, 150, // 212 - 72, 124, 120, // 213 - 116, 37, 150, // 214 - 37, 116, 85, // 215 - 117, 105, 153, // 216 - 105, 115, 151, // 217 - 105, 117, 118, // 218 - 118, 115, 105, // 219 - 119, 120, 124, // 220 - 120, 119, 70, // 221 - 119, 124, 127, // 222 - 119, 121, 70, // 223 - 121, 119, 122, // 224 - 122, 119, 127, // 225 - 123, 124, 72, // 226 - 124, 123, 125, // 227 - 125, 127, 124, // 228 - 126, 127, 131, // 229 - 127, 126, 122, // 230 - 125, 131, 127, // 231 - 126, 131, 134, // 232 - 128, 126, 129, // 233 - 129, 126, 134, // 234 - 126, 128, 122, // 235 - 136, 123, 72, // 236 - 130, 134, 131, // 237 - 131, 132, 130, // 238 - 132, 131, 125, // 239 - 133, 134, 155, // 240 - 134, 133, 129, // 241 - 130, 155, 134, // 242 - 133, 156, 129, // 243 - 135, 155, 130, // 244 - 123, 136, 137, // 245 - 85, 137, 136, // 246 - 139, 115, 118, // 247 - 123, 137, 138, // 248 - 125, 123, 138, // 249 - 114, 138, 137, // 250 - 137, 116, 114, // 251 - 116, 137, 85, // 252 - 114, 139, 138, // 253 - 132, 138, 139, // 254 - 138, 132, 125, // 255 - 132, 139, 140, // 256 - 130, 132, 140, // 257 - 115, 139, 114, // 258 - 118, 140, 139, // 259 - 135, 140, 154, // 260 - 118, 154, 140, // 261 - 140, 135, 130, // 262 - 117, 154, 118, // 263 -}; - -/* 0x02015444: seg2_painting_mesh_neighbor_tris - * Lists the neighboring triangles for each vertex in the mesh. - * Used when applying gouraud shading to the generated ripple mesh - * - * Format: - * num neighbors, neighbor0, neighbor1, ... - * The nth entry corresponds to the nth vertex in seg2_painting_triangle_mesh - */ -const s16 seg2_painting_mesh_neighbor_tris[] = { - 3, 1, 2, 3, - 1, 1, - 4, 1, 2, 4, 5, - 6, 2, 3, 5, 14, 59, 62, - 3, 3, 58, 59, - 6, 4, 5, 13, 14, 15, 16, - 2, 4, 13, - 2, 6, 7, - 6, 0, 6, 7, 8, 9, 10, - 4, 6, 10, 11, 12, - 4, 7, 8, 154, 155, - 6, 8, 9, 77, 154, 163, 194, - 6, 0, 9, 72, 73, 75, 77, - 6, 0, 10, 11, 19, 70, 72, - 6, 11, 12, 17, 18, 19, 20, - 4, 13, 16, 17, 18, - 6, 14, 15, 53, 61, 62, 64, - 6, 15, 16, 18, 20, 64, 67, - 6, 19, 20, 66, 67, 69, 70, - 8, 21, 22, 27, 31, 80, 81, 149, 150, - 3, 21, 22, 26, - 6, 23, 24, 25, 28, 57, 60, - 3, 24, 25, 26, - 6, 22, 24, 26, 27, 28, 29, - 6, 27, 29, 30, 31, 32, 33, - 8, 30, 33, 39, 40, 78, 79, 146, 147, - 6, 34, 35, 37, 44, 63, 65, - 6, 23, 28, 29, 32, 34, 35, - 6, 23, 35, 53, 60, 61, 63, - 6, 38, 39, 40, 41, 42, 43, - 6, 32, 33, 34, 37, 38, 39, - 8, 41, 42, 48, 52, 76, 82, 148, 151, - 6, 44, 46, 65, 66, 68, 69, - 6, 45, 46, 47, 56, 68, 71, - 6, 37, 38, 43, 44, 45, 46, - 6, 42, 43, 45, 47, 48, 49, - 6, 36, 48, 49, 50, 51, 52, - 8, 50, 51, 152, 153, 170, 174, 214, 215, - 6, 36, 47, 49, 54, 55, 56, - 6, 54, 55, 74, 169, 178, 196, - 6, 54, 56, 71, 73, 74, 75, - 3, 25, 57, 58, - 6, 57, 58, 59, 60, 61, 62, - 6, 53, 63, 64, 65, 66, 67, - 6, 68, 69, 70, 71, 72, 73, - 6, 74, 75, 77, 194, 195, 196, - 6, 79, 82, 125, 137, 146, 148, - 6, 78, 80, 129, 130, 147, 149, - 6, 76, 144, 145, 151, 152, 153, - 3, 84, 85, 86, - 1, 85, - 4, 85, 86, 91, 95, - 6, 83, 87, 88, 90, 119, 124, - 3, 84, 87, 88, - 6, 89, 91, 92, 93, 94, 95, - 6, 84, 86, 87, 89, 90, 91, - 4, 93, 94, 101, 105, - 2, 94, 95, - 6, 96, 97, 100, 108, 126, 131, - 6, 83, 89, 90, 92, 96, 97, - 6, 83, 97, 123, 124, 126, 127, - 6, 99, 101, 102, 103, 104, 105, - 6, 92, 93, 96, 99, 100, 101, - 4, 98, 103, 104, 110, - 2, 104, 105, - 6, 99, 100, 102, 106, 107, 108, - 6, 106, 107, 111, 117, 134, 138, - 6, 106, 108, 131, 132, 134, 135, - 6, 98, 109, 110, 112, 113, 114, - 6, 102, 103, 107, 109, 110, 111, - 4, 113, 114, 221, 223, - 2, 98, 114, - 6, 115, 116, 142, 213, 226, 236, - 6, 109, 111, 112, 115, 116, 117, - 6, 116, 117, 138, 140, 141, 142, - 3, 88, 118, 119, - 6, 120, 121, 122, 130, 149, 150, - 3, 118, 120, 121, - 6, 118, 119, 120, 122, 123, 124, - 6, 125, 128, 129, 133, 146, 147, - 6, 122, 123, 127, 128, 129, 130, - 6, 126, 127, 128, 131, 132, 133, - 6, 136, 137, 139, 145, 148, 151, - 6, 125, 132, 133, 135, 136, 137, - 6, 134, 135, 136, 138, 139, 140, - 6, 143, 144, 153, 215, 246, 252, - 6, 139, 140, 141, 143, 144, 145, - 6, 154, 155, 162, 163, 164, 165, - 1, 157, - 3, 157, 158, 159, - 4, 157, 159, 160, 161, - 6, 158, 159, 160, 167, 205, 206, - 6, 156, 160, 161, 166, 167, 168, - 6, 162, 163, 194, 195, 197, 199, - 6, 162, 164, 166, 168, 199, 202, - 4, 156, 164, 165, 166, - 6, 167, 168, 201, 202, 204, 205, - 6, 36, 50, 55, 169, 170, 171, - 6, 170, 171, 172, 173, 174, 175, - 8, 172, 173, 180, 184, 209, 210, 211, 212, - 6, 176, 177, 179, 188, 198, 200, - 6, 169, 171, 175, 176, 177, 178, - 6, 177, 178, 195, 196, 197, 198, - 6, 172, 175, 176, 179, 180, 181, - 6, 180, 181, 182, 183, 184, 185, - 8, 182, 183, 189, 192, 216, 217, 218, 219, - 6, 186, 187, 190, 193, 203, 207, - 6, 179, 181, 185, 186, 187, 188, - 6, 187, 188, 200, 201, 203, 204, - 6, 182, 185, 186, 189, 190, 191, - 3, 189, 191, 192, - 3, 193, 207, 208, - 6, 197, 198, 199, 200, 201, 202, - 6, 203, 204, 205, 206, 207, 208, - 6, 209, 210, 250, 251, 253, 258, - 6, 210, 211, 217, 219, 247, 258, - 6, 209, 212, 214, 215, 251, 252, - 3, 216, 218, 263, - 6, 218, 219, 247, 259, 261, 263, - 6, 220, 221, 222, 223, 224, 225, - 6, 112, 113, 115, 213, 220, 221, - 2, 223, 224, - 4, 224, 225, 230, 235, - 6, 226, 227, 236, 245, 248, 249, - 6, 213, 220, 222, 226, 227, 228, - 6, 227, 228, 231, 239, 249, 255, - 6, 229, 230, 232, 233, 234, 235, - 6, 222, 225, 228, 229, 230, 231, - 2, 233, 235, - 4, 233, 234, 241, 243, - 6, 237, 238, 242, 244, 257, 262, - 6, 229, 231, 232, 237, 238, 239, - 6, 238, 239, 254, 255, 256, 257, - 3, 240, 241, 243, - 6, 232, 234, 237, 240, 241, 242, - 3, 244, 260, 262, - 6, 141, 142, 143, 236, 245, 246, - 6, 245, 246, 248, 250, 251, 252, - 6, 248, 249, 250, 253, 254, 255, - 6, 247, 253, 254, 256, 258, 259, - 6, 256, 257, 259, 260, 261, 262, - 2, 12, 17, - 2, 21, 81, - 3, 81, 121, 150, - 4, 30, 31, 78, 80, - 4, 40, 41, 79, 82, - 4, 51, 52, 76, 152, - 2, 155, 165, - 3, 158, 206, 208, - 2, 156, 161, - 4, 173, 174, 212, 214, - 4, 183, 184, 211, 217, - 3, 190, 191, 193, - 2, 192, 216, - 3, 260, 261, 263, - 3, 240, 242, 244, - 1, 243, -}; +#include "segment2/paintings.c.in" diff --git a/bin/segment2/paintings.c.in b/bin/segment2/paintings.c.in new file mode 100644 index 0000000000..2558fb288b --- /dev/null +++ b/bin/segment2/paintings.c.in @@ -0,0 +1,539 @@ + +// 0x02014970 - 0x020149A8 +const Gfx dl_paintings_rippling_begin[] = { + gsDPPipeSync(), + gsSPSetGeometryMode(G_LIGHTING | G_SHADING_SMOOTH), + gsDPSetCombineMode(G_CC_MODULATERGBA, G_CC_MODULATERGBA), + gsSPLightColor(LIGHT_1, 0xffffffff), + gsSPLightColor(LIGHT_2, 0x505050ff), + gsSPTexture(0xFFFF, 0xFFFF, 0, G_TX_RENDERTILE, G_ON), + gsDPTileSync(), + gsSPEndDisplayList(), +}; + +// 0x020149A8 - 0x020149C8 +const Gfx dl_paintings_rippling_end[] = { + gsSPTexture(0xFFFF, 0xFFFF, 0, G_TX_RENDERTILE, G_OFF), + gsDPPipeSync(), + gsDPSetCombineMode(G_CC_SHADE, G_CC_SHADE), + gsSPEndDisplayList(), +}; + +const Gfx sub_dl_paintings_textured_begin[] = { + gsDPSetCombineMode(G_CC_MODULATERGB, G_CC_MODULATERGB), + // gsDPSetTile(G_IM_FMT_RGBA, G_IM_SIZ_16b, 0, 0, G_TX_LOADTILE, 0, (G_TX_WRAP | G_TX_NOMIRROR), G_TX_NOMASK, G_TX_NOLOD, (G_TX_WRAP | G_TX_NOMIRROR), G_TX_NOMASK, G_TX_NOLOD), + gsSPTexture(0xFFFF, 0xFFFF, 0, G_TX_RENDERTILE, G_ON), + gsDPTileSync(), + gsSPEndDisplayList(), +}; + +// 0x07021A48 - 0x07021AA0 +const Gfx dl_paintings_textured_shaded_begin[] = { + gsDPPipeSync(), + gsSPSetGeometryMode(G_LIGHTING | G_SHADING_SMOOTH), + gsSPLightColor(LIGHT_1, 0xffffffff), + gsSPLightColor(LIGHT_2, 0x505050ff), + gsSPDisplayList(sub_dl_paintings_textured_begin), + gsSPEndDisplayList(), +}; + +// 0x07021A48 - 0x07021AA0 +const Gfx dl_paintings_textured_vertex_colored_begin[] = { + gsDPPipeSync(), + gsSPClearGeometryMode(G_LIGHTING), + gsSPDisplayList(sub_dl_paintings_textured_begin), + gsSPEndDisplayList(), +}; + +// 0x07021AA0 - 0x07021AC0 +const Gfx dl_paintings_textured_end[] = { + gsSPTexture(0xFFFF, 0xFFFF, 0, G_TX_RENDERTILE, G_OFF), + gsDPPipeSync(), + gsDPSetCombineMode(G_CC_SHADE, G_CC_SHADE), + gsSPEndDisplayList(), +}; + +// 0x020149C8 - 0x02014A00 +const Gfx dl_paintings_env_mapped_begin[] = { + gsDPPipeSync(), + gsSPSetGeometryMode(G_LIGHTING | G_TEXTURE_GEN), + gsDPSetCombineMode(G_CC_DECALRGB, G_CC_DECALRGB), + gsSPLightColor(LIGHT_1, 0xffffffff), + gsSPLightColor(LIGHT_2, 0x505050ff), + gsSPTexture(0x4000, 0x4000, 0, G_TX_RENDERTILE, G_ON), + gsDPTileSync(), + gsSPEndDisplayList(), +}; + +// 0x02014A00 - 0x02014A30 +const Gfx dl_paintings_env_mapped_end[] = { + gsSPTexture(0x4000, 0x4000, 0, G_TX_RENDERTILE, G_OFF), + gsDPPipeSync(), + gsSPGeometryModeSetFirst(G_TEXTURE_GEN, G_LIGHTING), + gsDPSetCombineMode(G_CC_SHADE, G_CC_SHADE), + gsSPEndDisplayList(), +}; + +// 0x02014A30 - 0x02014A60 +const Gfx dl_paintings_ripple_triangles[] = { +#ifdef F3DEX_GBI_2 + gsSP2Triangles( 0, 1, 2, 0x0, 3, 4, 5, 0x0), + gsSP2Triangles( 6, 7, 8, 0x0, 9, 10, 11, 0x0), + gsSP2Triangles(12, 13, 14, 0x0, 15, 16, 17, 0x0), + gsSP2Triangles(18, 19, 20, 0x0, 21, 22, 23, 0x0), + gsSP2Triangles(24, 25, 26, 0x0, 27, 28, 29, 0x0), +#else + gsSP2Triangles( 0, 1, 2, 0x0, 3, 4, 5, 0x0), + gsSP2Triangles( 6, 7, 8, 0x0, 9, 10, 11, 0x0), + gsSP1Triangle( 12, 13, 14, 0x0), +#endif + gsSPEndDisplayList(), +}; + +// Painting vertex coordinates +#define PDX(x) ((x) * (PAINTING_SIZE / 12.0f)) // 51.2f +#define PDY(y) ((y) * (PAINTING_SIZE / 20.0f)) // 30.72f +#define PAINTING_VERTEX(x, y, r) PDX(x), PDY(y), (r) + +// 14A60: triangle mesh +// 0x02014A60 +const PaintingData painting_data_vertices[] = { + 157, // numVtx + // format: + // 2D point (x, y), ripple (0 or 1) + PAINTING_VERTEX(12, 19, 0), // 0 + PAINTING_VERTEX(12, 20, 0), // 1 + PAINTING_VERTEX(11, 20, 0), // 2 + PAINTING_VERTEX(11, 18, 1), // 3 + PAINTING_VERTEX(12, 17, 0), // 4 + PAINTING_VERTEX(10, 19, 1), // 5 + PAINTING_VERTEX(10, 20, 0), // 6 + PAINTING_VERTEX( 6, 20, 0), // 7 + PAINTING_VERTEX( 6, 19, 1), // 8 + PAINTING_VERTEX( 7, 20, 0), // 9 + PAINTING_VERTEX( 5, 20, 0), // 10 + PAINTING_VERTEX( 5, 18, 1), // 11 + PAINTING_VERTEX( 6, 17, 1), // 12 + PAINTING_VERTEX( 7, 18, 1), // 13 + PAINTING_VERTEX( 8, 19, 1), // 14 + PAINTING_VERTEX( 9, 20, 0), // 15 + PAINTING_VERTEX(10, 17, 1), // 16 + PAINTING_VERTEX( 9, 18, 1), // 17 + PAINTING_VERTEX( 8, 17, 1), // 18 + PAINTING_VERTEX(11, 10, 1), // 19 + PAINTING_VERTEX(12, 11, 0), // 20 + PAINTING_VERTEX(11, 14, 1), // 21 + PAINTING_VERTEX(12, 13, 0), // 22 + PAINTING_VERTEX(11, 12, 1), // 23 + PAINTING_VERTEX(10, 11, 1), // 24 + PAINTING_VERTEX( 9, 10, 1), // 25 + PAINTING_VERTEX( 9, 14, 1), // 26 + PAINTING_VERTEX(10, 13, 1), // 27 + PAINTING_VERTEX(10, 15, 1), // 28 + PAINTING_VERTEX( 8, 11, 1), // 29 + PAINTING_VERTEX( 9, 12, 1), // 30 + PAINTING_VERTEX( 7, 10, 1), // 31 + PAINTING_VERTEX( 8, 15, 1), // 32 + PAINTING_VERTEX( 7, 14, 1), // 33 + PAINTING_VERTEX( 8, 13, 1), // 34 + PAINTING_VERTEX( 7, 12, 1), // 35 + PAINTING_VERTEX( 6, 11, 1), // 36 + PAINTING_VERTEX( 5, 10, 1), // 37 + PAINTING_VERTEX( 6, 13, 1), // 38 + PAINTING_VERTEX( 5, 14, 1), // 39 + PAINTING_VERTEX( 6, 15, 1), // 40 + PAINTING_VERTEX(12, 15, 0), // 41 + PAINTING_VERTEX(11, 16, 1), // 42 + PAINTING_VERTEX( 9, 16, 1), // 43 + PAINTING_VERTEX( 7, 16, 1), // 44 + PAINTING_VERTEX( 5, 16, 1), // 45 + PAINTING_VERTEX( 8, 9, 1), // 46 + PAINTING_VERTEX(10, 9, 1), // 47 + PAINTING_VERTEX( 6, 9, 1), // 48 + PAINTING_VERTEX(12, 1, 0), // 49 + PAINTING_VERTEX(12, 0, 0), // 50 + PAINTING_VERTEX(11, 0, 0), // 51 + PAINTING_VERTEX(11, 4, 1), // 52 + PAINTING_VERTEX(12, 3, 0), // 53 + PAINTING_VERTEX(10, 1, 1), // 54 + PAINTING_VERTEX(11, 2, 1), // 55 + PAINTING_VERTEX( 9, 0, 0), // 56 + PAINTING_VERTEX(10, 0, 0), // 57 + PAINTING_VERTEX( 9, 4, 1), // 58 + PAINTING_VERTEX(10, 3, 1), // 59 + PAINTING_VERTEX(10, 5, 1), // 60 + PAINTING_VERTEX( 8, 1, 1), // 61 + PAINTING_VERTEX( 9, 2, 1), // 62 + PAINTING_VERTEX( 7, 0, 0), // 63 + PAINTING_VERTEX( 8, 0, 0), // 64 + PAINTING_VERTEX( 8, 3, 1), // 65 + PAINTING_VERTEX( 7, 4, 1), // 66 + PAINTING_VERTEX( 8, 5, 1), // 67 + PAINTING_VERTEX( 6, 1, 1), // 68 + PAINTING_VERTEX( 7, 2, 1), // 69 + PAINTING_VERTEX( 5, 0, 0), // 70 + PAINTING_VERTEX( 6, 0, 0), // 71 + PAINTING_VERTEX( 5, 4, 1), // 72 + PAINTING_VERTEX( 6, 3, 1), // 73 + PAINTING_VERTEX( 6, 5, 1), // 74 + PAINTING_VERTEX(12, 5, 0), // 75 + PAINTING_VERTEX(11, 8, 1), // 76 + PAINTING_VERTEX(12, 7, 0), // 77 + PAINTING_VERTEX(11, 6, 1), // 78 + PAINTING_VERTEX( 9, 8, 1), // 79 + PAINTING_VERTEX(10, 7, 1), // 80 + PAINTING_VERTEX( 9, 6, 1), // 81 + PAINTING_VERTEX( 7, 8, 1), // 82 + PAINTING_VERTEX( 8, 7, 1), // 83 + PAINTING_VERTEX( 7, 6, 1), // 84 + PAINTING_VERTEX( 5, 8, 1), // 85 + PAINTING_VERTEX( 6, 7, 1), // 86 + PAINTING_VERTEX( 4, 19, 1), // 87 + PAINTING_VERTEX( 0, 20, 0), // 88 + PAINTING_VERTEX( 0, 19, 0), // 89 + PAINTING_VERTEX( 1, 20, 0), // 90 + PAINTING_VERTEX( 1, 18, 1), // 91 + PAINTING_VERTEX( 2, 19, 1), // 92 + PAINTING_VERTEX( 4, 17, 1), // 93 + PAINTING_VERTEX( 3, 18, 1), // 94 + PAINTING_VERTEX( 3, 20, 0), // 95 + PAINTING_VERTEX( 2, 17, 1), // 96 + PAINTING_VERTEX( 5, 12, 1), // 97 + PAINTING_VERTEX( 4, 11, 1), // 98 + PAINTING_VERTEX( 3, 10, 1), // 99 + PAINTING_VERTEX( 3, 14, 1), // 100 + PAINTING_VERTEX( 4, 13, 1), // 101 + PAINTING_VERTEX( 4, 15, 1), // 102 + PAINTING_VERTEX( 3, 12, 1), // 103 + PAINTING_VERTEX( 2, 11, 1), // 104 + PAINTING_VERTEX( 1, 10, 1), // 105 + PAINTING_VERTEX( 1, 14, 1), // 106 + PAINTING_VERTEX( 2, 13, 1), // 107 + PAINTING_VERTEX( 2, 15, 1), // 108 + PAINTING_VERTEX( 1, 12, 1), // 109 + PAINTING_VERTEX( 0, 11, 0), // 110 + PAINTING_VERTEX( 0, 15, 0), // 111 + PAINTING_VERTEX( 3, 16, 1), // 112 + PAINTING_VERTEX( 1, 16, 1), // 113 + PAINTING_VERTEX( 3, 8, 1), // 114 + PAINTING_VERTEX( 2, 9, 1), // 115 + PAINTING_VERTEX( 4, 9, 1), // 116 + PAINTING_VERTEX( 0, 9, 0), // 117 + PAINTING_VERTEX( 1, 8, 1), // 118 + PAINTING_VERTEX( 4, 1, 1), // 119 + PAINTING_VERTEX( 5, 2, 1), // 120 + PAINTING_VERTEX( 4, 0, 0), // 121 + PAINTING_VERTEX( 3, 0, 0), // 122 + PAINTING_VERTEX( 4, 5, 1), // 123 + PAINTING_VERTEX( 4, 3, 1), // 124 + PAINTING_VERTEX( 3, 4, 1), // 125 + PAINTING_VERTEX( 2, 1, 1), // 126 + PAINTING_VERTEX( 3, 2, 1), // 127 + PAINTING_VERTEX( 2, 0, 0), // 128 + PAINTING_VERTEX( 1, 0, 0), // 129 + PAINTING_VERTEX( 1, 4, 1), // 130 + PAINTING_VERTEX( 2, 3, 1), // 131 + PAINTING_VERTEX( 2, 5, 1), // 132 + PAINTING_VERTEX( 0, 1, 0), // 133 + PAINTING_VERTEX( 1, 2, 1), // 134 + PAINTING_VERTEX( 0, 5, 0), // 135 + PAINTING_VERTEX( 5, 6, 1), // 136 + PAINTING_VERTEX( 4, 7, 1), // 137 + PAINTING_VERTEX( 3, 6, 1), // 138 + PAINTING_VERTEX( 2, 7, 1), // 139 + PAINTING_VERTEX( 1, 6, 1), // 140 + PAINTING_VERTEX( 8, 20, 0), // 141 + PAINTING_VERTEX(12, 10, 0), // 142 + PAINTING_VERTEX(12, 9, 0), // 143 + PAINTING_VERTEX(10, 10, 1), // 144 + PAINTING_VERTEX( 8, 10, 1), // 145 + PAINTING_VERTEX( 6, 10, 1), // 146 + PAINTING_VERTEX( 4, 20, 0), // 147 + PAINTING_VERTEX( 0, 17, 0), // 148 + PAINTING_VERTEX( 2, 20, 0), // 149 + PAINTING_VERTEX( 4, 10, 1), // 150 + PAINTING_VERTEX( 2, 10, 1), // 151 + PAINTING_VERTEX( 0, 13, 0), // 152 + PAINTING_VERTEX( 0, 10, 0), // 153 + PAINTING_VERTEX( 0, 7, 0), // 154 + PAINTING_VERTEX( 0, 3, 0), // 155 + PAINTING_VERTEX( 0, 0, 0), // 156 +}; + +#undef PDX +#undef PDY +#undef PAINTING_VERTEX + +// 0x07022660 - 0x07023042 +const PaintingData painting_data_triangles[] = { + 264, // num triangles + // Grouped by 5 + one remainder group, + // = 15 vertices per group + a few extra triangles + + // Bottom half + 60, 59, 52, + 49, 53, 55, + 50, 49, 51, + 51, 49, 55, + 52, 55, 53, + 53, 75, 52, + 54, 55, 59, + 52, 59, 55, + 55, 54, 51, + 54, 59, 62, + 56, 54, 62, + 57, 54, 56, + 54, 57, 51, + 58, 62, 59, + 59, 60, 58, + 68, 73, 120, + 61, 62, 65, + 58, 65, 62, + 62, 61, 56, + 63, 61, 69, + 64, 61, 63, + 61, 65, 69, + 61, 64, 56, + 65, 67, 66, + 66, 69, 65, + 67, 65, 58, + 69, 68, 63, + 66, 73, 69, + 68, 69, 73, + 70, 68, 120, + 71, 68, 70, + 68, 71, 63, + 73, 74, 72, + 72, 120, 73, + 74, 73, 66, + 75, 77, 78, + 52, 75, 78, + 76, 78, 77, + 77, 143, 76, + 76, 80, 78, + 60, 78, 80, + 78, 60, 52, + 83, 46, 82, + 58, 60, 81, + 60, 80, 81, + 80, 47, 79, + 47, 80, 76, + 79, 81, 80, + 79, 83, 81, + 81, 67, 58, + 67, 81, 83, + 66, 67, 84, + 67, 83, 84, + 46, 83, 79, + 82, 84, 83, + 84, 74, 66, + 82, 86, 84, + 74, 84, 86, + 72, 74, 136, + 74, 86, 136, + 86, 48, 85, + 85, 136, 86, + 48, 86, 82, + 25, 46, 79, + 79, 47, 25, + 31, 46, 145, + 46, 25, 145, + 82, 46, 31, + 47, 19, 144, + 25, 47, 144, + 19, 47, 76, + 76, 143, 19, + 19, 143, 142, + 119, 124, 127, + 31, 48, 82, + 85, 48, 37, + 48, 31, 146, + 37, 48, 146, + 72, 124, 120, + 120, 119, 70, + 119, 120, 124, + 122, 119, 127, + 121, 119, 122, + 119, 121, 70, + 130, 134, 131, + 124, 123, 125, + 125, 127, 124, + 123, 124, 72, + 125, 131, 127, + 127, 126, 122, + 126, 127, 131, + 126, 128, 122, + 129, 126, 134, + 128, 126, 129, + 126, 131, 134, + 132, 131, 125, + 131, 132, 130, + 130, 155, 134, + 134, 133, 129, + 133, 134, 155, + 133, 156, 129, + 135, 155, 130, + 136, 123, 72, + 85, 137, 136, + 123, 136, 137, + 125, 123, 138, + 123, 137, 138, + 116, 137, 85, + 137, 116, 114, + 114, 138, 137, + 138, 132, 125, + 132, 138, 139, + 114, 139, 138, + 130, 132, 140, + 132, 139, 140, + 139, 115, 118, + 118, 140, 139, + 115, 139, 114, + 140, 135, 130, + 118, 154, 140, + 135, 140, 154, + 117, 105, 153, + 117, 154, 118, + 99, 115, 114, + 114, 116, 99, + 118, 115, 105, + 115, 99, 151, + 105, 115, 151, + 37, 116, 85, + 116, 37, 150, + 99, 116, 150, + 105, 117, 118, + // Top half + 9, 8, 13, + 0, 1, 2, + 3, 0, 2, + 4, 0, 3, + 5, 2, 6, + 2, 5, 3, + 8, 7, 10, + 7, 8, 9, + 11, 8, 10, + 12, 8, 11, + 8, 12, 13, + 13, 14, 9, + 14, 141, 9, + 5, 6, 15, + 5, 16, 3, + 16, 5, 17, + 17, 5, 15, + 14, 15, 141, + 15, 14, 17, + 18, 14, 13, + 14, 18, 17, + 19, 142, 20, + 19, 20, 23, + 28, 27, 21, + 22, 41, 21, + 21, 23, 22, + 20, 22, 23, + 23, 24, 19, + 21, 27, 23, + 24, 23, 27, + 19, 24, 144, + 25, 144, 24, + 25, 24, 30, + 24, 27, 30, + 26, 30, 27, + 27, 28, 26, + 31, 36, 146, + 26, 34, 30, + 30, 29, 25, + 29, 30, 34, + 25, 29, 145, + 31, 145, 29, + 31, 29, 35, + 29, 34, 35, + 32, 34, 26, + 33, 35, 34, + 34, 32, 33, + 35, 36, 31, + 33, 38, 35, + 36, 35, 38, + 37, 36, 97, + 36, 38, 97, + 37, 146, 36, + 28, 16, 43, + 39, 97, 38, + 38, 40, 39, + 40, 38, 33, + 21, 41, 42, + 41, 4, 42, + 3, 42, 4, + 42, 28, 21, + 28, 42, 16, + 3, 16, 42, + 26, 28, 43, + 17, 43, 16, + 43, 32, 26, + 32, 43, 18, + 17, 18, 43, + 33, 32, 44, + 32, 18, 44, + 13, 44, 18, + 13, 12, 44, + 44, 40, 33, + 40, 44, 12, + 39, 40, 45, + 40, 12, 45, + 11, 45, 12, + 10, 87, 11, + 87, 10, 147, + 88, 89, 90, + 90, 89, 91, + 89, 148, 91, + 92, 149, 90, + 91, 92, 90, + 98, 97, 101, + 87, 93, 11, + 94, 87, 95, + 93, 87, 94, + 87, 147, 95, + 95, 92, 94, + 92, 95, 149, + 92, 96, 94, + 96, 92, 91, + 39, 101, 97, + 97, 98, 37, + 99, 98, 103, + 98, 101, 103, + 99, 150, 98, + 37, 98, 150, + 102, 101, 39, + 101, 102, 100, + 100, 103, 101, + 103, 104, 99, + 104, 103, 107, + 100, 107, 103, + 104, 107, 109, + 99, 104, 151, + 105, 151, 104, + 105, 104, 109, + 45, 102, 39, + 108, 107, 100, + 107, 108, 106, + 106, 109, 107, + 110, 109, 152, + 109, 110, 105, + 106, 152, 109, + 105, 110, 153, + 111, 152, 106, + 11, 93, 45, + 102, 45, 93, + 102, 93, 112, + 100, 102, 112, + 94, 112, 93, + 94, 96, 112, + 108, 112, 96, + 112, 108, 100, + 108, 96, 113, + 106, 108, 113, + 91, 113, 96, + 111, 113, 148, + 91, 148, 113, + 113, 111, 106, +}; diff --git a/data/behavior_data.c b/data/behavior_data.c index a0d4303e8c..cfe5977c53 100644 --- a/data/behavior_data.c +++ b/data/behavior_data.c @@ -8,6 +8,7 @@ #include "game/behavior_actions.h" #include "game/mario_actions_cutscene.h" #include "game/mario_misc.h" +#include "game/paintings.h" #include "game/object_helpers.h" #include "game/debug.h" #include "menu/file_select.h" @@ -2227,16 +2228,6 @@ const BehaviorScript bhvWaterLevelPillar[] = { END_LOOP(), }; -const BehaviorScript bhvDddWarp[] = { - BEGIN(OBJ_LIST_SURFACE), - OR_INT(oFlags, OBJ_FLAG_UPDATE_GFX_POS_AND_ANGLE), - SET_FLOAT(oCollisionDistance, 30000), - BEGIN_LOOP(), - CALL_NATIVE(bhv_ddd_warp_loop), - CALL_NATIVE(load_object_collision_model), - END_LOOP(), -}; - const BehaviorScript bhvMoatGrills[] = { BEGIN(OBJ_LIST_SURFACE), #ifdef UNLOCK_ALL @@ -3494,6 +3485,15 @@ const BehaviorScript bhvUnlockDoorStar[] = { END_LOOP(), }; +const BehaviorScript bhvPainting[] = { + BEGIN(OBJ_LIST_LEVEL), + OR_INT(oFlags, OBJ_FLAG_UPDATE_GFX_POS_AND_ANGLE), + CALL_NATIVE(bhv_painting_init), + BEGIN_LOOP(), + CALL_NATIVE(bhv_painting_loop), + END_LOOP(), +}; + const BehaviorScript bhvInstantActiveWarp[] = { BREAK(), }; diff --git a/include/behavior_data.h b/include/behavior_data.h index 9702f974a0..5721c5ea76 100644 --- a/include/behavior_data.h +++ b/include/behavior_data.h @@ -173,7 +173,6 @@ extern const BehaviorScript bhvBowserKeyUnlockDoor[]; extern const BehaviorScript bhvBowserKeyCourseExit[]; extern const BehaviorScript bhvInvisibleObjectsUnderBridge[]; extern const BehaviorScript bhvWaterLevelPillar[]; -extern const BehaviorScript bhvDddWarp[]; extern const BehaviorScript bhvMoatGrills[]; extern const BehaviorScript bhvClockMinuteHand[]; extern const BehaviorScript bhvClockHourHand[]; @@ -294,6 +293,7 @@ extern const BehaviorScript bhvYellowBall[]; extern const BehaviorScript bhvMario[]; extern const BehaviorScript bhvToadMessage[]; extern const BehaviorScript bhvUnlockDoorStar[]; +extern const BehaviorScript bhvPainting[]; extern const BehaviorScript bhvInstantActiveWarp[]; extern const BehaviorScript bhvAirborneWarp[]; extern const BehaviorScript bhvHardAirKnockBackWarp[]; diff --git a/include/config/config_game.h b/include/config/config_game.h index ede580bffa..a3c22c76b6 100644 --- a/include/config/config_game.h +++ b/include/config/config_game.h @@ -7,7 +7,7 @@ /** * Enables some mechanics that change behavior depending on hardcoded level numbers. * TODO: separate this into separate defines, behavior params, or make these mechanics otherwise dynamic. -*/ + */ // #define ENABLE_VANILLA_LEVEL_SPECIFIC_CHECKS /** diff --git a/include/ique/PR/gbi.h b/include/ique/PR/gbi.h index 5f2a1e46f1..30c1765a97 100755 --- a/include/ique/PR/gbi.h +++ b/include/ique/PR/gbi.h @@ -1837,6 +1837,7 @@ typedef union { /* * Macros to assemble the graphics display list */ +#define SIZEOF_GFX_CMD(_cmd) sizeof((Gfx[]){gs##_cmd}) /* * DMA macros diff --git a/include/level_commands.h b/include/level_commands.h index fa8f8d1369..941f959599 100644 --- a/include/level_commands.h +++ b/include/level_commands.h @@ -46,7 +46,7 @@ enum LevelCommands { /*0x24*/ LEVEL_CMD_PLACE_OBJECT, /*0x25*/ LEVEL_CMD_INIT_MARIO, /*0x26*/ LEVEL_CMD_CREATE_WARP_NODE, - /*0x27*/ LEVEL_CMD_CREATE_PAINTING_WARP_NODE, + /*0x27*/ LEVEL_CMD_27, /*0x28*/ LEVEL_CMD_CREATE_INSTANT_WARP, /*0x29*/ LEVEL_CMD_LOAD_AREA, /*0x2A*/ LEVEL_CMD_UNLOAD_AREA, @@ -112,6 +112,8 @@ enum WarpCheckpointFlags { WARP_CHECKPOINT = (1 << 7), // 0x80 }; +#define WARP_DEST_LEVEL_NUM_MASK 0x7F + // Head defines enum GoddardScene { REGULAR_FACE = 0x2, @@ -363,8 +365,12 @@ enum GoddardScene { CMD_BBBB(LEVEL_CMD_CREATE_WARP_NODE, 0x08, id, destLevel), \ CMD_BBBB(destArea, destNode, flags, 0x00) +// Backwards compatibility: #define PAINTING_WARP_NODE(id, destLevel, destArea, destNode, flags) \ - CMD_BBBB(LEVEL_CMD_CREATE_PAINTING_WARP_NODE, 0x08, id, destLevel), \ + WARP_NODE(id, destLevel, destArea, destNode, flags) + +#define CMD27(id, destLevel, destArea, destNode, flags) \ + CMD_BBBB(LEVEL_CMD_27, 0x08, id, destLevel), \ CMD_BBBB(destArea, destNode, flags, 0x00) #define INSTANT_WARP(index, destArea, displaceX, displaceY, displaceZ) \ diff --git a/include/model_ids.h b/include/model_ids.h index 81e92c6a11..a26c749d13 100644 --- a/include/model_ids.h +++ b/include/model_ids.h @@ -550,6 +550,8 @@ #define MODEL_SILVER_COIN_NO_SHADOW 0xE3 // silver_coin_no_shadow_geo #endif +#define MODEL_PAINTING 0xE4 + // Menu Models (overwrites Level Geometry IDs) #define MODEL_MAIN_MENU_MARIO_SAVE_BUTTON MODEL_LEVEL_GEOMETRY_03 // main_menu_geo_0001D0 #define MODEL_MAIN_MENU_RED_ERASE_BUTTON MODEL_LEVEL_GEOMETRY_04 // main_menu_geo_000290 diff --git a/include/n64/PR/gbi.h b/include/n64/PR/gbi.h index 7461fa9170..e1e657d158 100644 --- a/include/n64/PR/gbi.h +++ b/include/n64/PR/gbi.h @@ -1861,6 +1861,7 @@ typedef union { /* * Macros to assemble the graphics display list */ +#define SIZEOF_GFX_CMD(_cmd) sizeof((Gfx[]){gs##_cmd}) /* * DMA macros diff --git a/include/object_constants.h b/include/object_constants.h index 949dd8d6c5..83ab4ddd17 100644 --- a/include/object_constants.h +++ b/include/object_constants.h @@ -2062,10 +2062,11 @@ enum oActionsSnowmansBottom { #define WATER_BOMB_ACT_EXPLODE 0x3 /* TTC Painting Clock Arm */ - /* oAction */ - #define CLOCK_ARM_ACT_CHECK_DEFAULT 0x0 - #define CLOCK_ARM_ACT_MOVING 0x1 - #define CLOCK_ARM_ACT_STOP 0x2 +enum oActionsTTCPaintingClockArm { + TTC_PAINTING_CLOCK_ARM_WAIT, + TTC_PAINTING_CLOCK_ARM_ACT_MOVING, + TTC_PAINTING_CLOCK_ARM_ACT_STOPPED, +}; /* TTC rotating solid */ /* oBehParams2ndByte */ diff --git a/include/object_fields.h b/include/object_fields.h index aa00f163fe..f8c75460d6 100644 --- a/include/object_fields.h +++ b/include/object_fields.h @@ -1255,6 +1255,15 @@ #define /*0x0FC*/ oYoshiChosenHome OBJECT_FIELD_S32(0x1D) #define /*0x100*/ oYoshiTargetYaw OBJECT_FIELD_S32(0x1E) +/* Painting */ +#define /*0x0F4*/ oPaintingImage OBJECT_FIELD_CVPTR(0x1B) +#define /*0x0F8*/ oPaintingRippleAnimation OBJECT_FIELD_CVPTR(0x1C) +#define /*0x0FC*/ oPaintingCurrRippleMag OBJECT_FIELD_F32(0x1D) +#define /*0x100*/ oPaintingRipplePosX OBJECT_FIELD_F32(0x1E) +#define /*0x104*/ oPaintingRipplePosY OBJECT_FIELD_F32(0x1F) +#define /*0x108*/ oPaintingRippleTimer OBJECT_FIELD_S32(0x20) +#define /*0x10C*/ oPaintingStoredAction OBJECT_FIELD_S32(0x21) + /*Custom general defines: diff --git a/include/surface_terrains.h b/include/surface_terrains.h index 765abacdd2..0cdb816cd3 100644 --- a/include/surface_terrains.h +++ b/include/surface_terrains.h @@ -231,20 +231,12 @@ enum SurfaceTypes { #define INSTANT_WARP_INDEX_START 0x00 // Equal and greater than Surface 0x1B #define INSTANT_WARP_INDEX_STOP 0x04 // Less than Surface 0x1F -#define SURFACE_IS_NEW_WATER(cmd) (((cmd) == SURFACE_NEW_WATER) || ((cmd) == SURFACE_NEW_WATER_BOTTOM)) -#define SURFACE_IS_QUICKSAND(cmd) ((((cmd) >= SURFACE_SHALLOW_QUICKSAND) && ((cmd) <= SURFACE_MOVING_QUICKSAND)) || ((cmd) == SURFACE_INSTANT_MOVING_QUICKSAND)) -#define SURFACE_IS_NOT_HARD(cmd) (((cmd) != SURFACE_HARD) && !((cmd) >= SURFACE_HARD_SLIPPERY && ((cmd) <= SURFACE_HARD_NOT_SLIPPERY))) -#define SURFACE_IS_PAINTING_WOBBLE(cmd) (((cmd) >= SURFACE_PAINTING_WOBBLE_A6) && ((cmd) <= SURFACE_PAINTING_WOBBLE_D2)) -#define SURFACE_IS_PAINTING_WOBBLE_LEFT(cmd) ((((cmd) - SURFACE_PAINTING_WOBBLE_A6) % 3) == 0) -#define SURFACE_IS_PAINTING_WOBBLE_MIDDLE(cmd) ((((cmd) - SURFACE_PAINTING_WOBBLE_A7) % 3) == 0) -#define SURFACE_IS_PAINTING_WOBBLE_RIGHT(cmd) ((((cmd) - SURFACE_PAINTING_WOBBLE_A8) % 3) == 0) -#define SURFACE_IS_PAINTING_WARP(cmd) (((cmd) >= SURFACE_PAINTING_WARP_D3) && ((cmd) < SURFACE_WOBBLING_WARP)) // skips SURFACE_WOBBLING_WARP -#define SURFACE_IS_PAINTING_WARP_LEFT(cmd) ((((cmd) - SURFACE_PAINTING_WARP_D3 ) % 3) == 0) -#define SURFACE_IS_PAINTING_WARP_MIDDLE(cmd) ((((cmd) - SURFACE_PAINTING_WARP_D4 ) % 3) == 0) -#define SURFACE_IS_PAINTING_WARP_RIGHT(cmd) ((((cmd) - SURFACE_PAINTING_WARP_D5 ) % 3) == 0) -#define SURFACE_IS_INSTANT_WARP(cmd) (((cmd) >= SURFACE_INSTANT_WARP_1B) && ((cmd) < SURFACE_INSTANT_WARP_1B + INSTANT_WARP_INDEX_STOP)) -#define SURFACE_IS_WARP(cmd) (((cmd) == SURFACE_LOOK_UP_WARP) || ((cmd) == SURFACE_WOBBLING_WARP) || SURFACE_IS_PAINTING_WARP(cmd) || SURFACE_IS_INSTANT_WARP(cmd)) -#define SURFACE_IS_UNSAFE(cmd) (((cmd) == SURFACE_BURNING) || SURFACE_IS_QUICKSAND(cmd) || SURFACE_IS_WARP(cmd)) +#define SURFACE_IS_NEW_WATER(cmd) (((cmd) == SURFACE_NEW_WATER) || ((cmd) == SURFACE_NEW_WATER_BOTTOM)) +#define SURFACE_IS_QUICKSAND(cmd) ((((cmd) >= SURFACE_SHALLOW_QUICKSAND) && ((cmd) <= SURFACE_MOVING_QUICKSAND)) || ((cmd) == SURFACE_INSTANT_MOVING_QUICKSAND)) +#define SURFACE_IS_NOT_HARD(cmd) (((cmd) != SURFACE_HARD) && !((cmd) >= SURFACE_HARD_SLIPPERY && ((cmd) <= SURFACE_HARD_NOT_SLIPPERY))) +#define SURFACE_IS_INSTANT_WARP(cmd) (((cmd) >= SURFACE_INSTANT_WARP_1B) && ((cmd) <= (SURFACE_INSTANT_WARP_1B + INSTANT_WARP_INDEX_STOP))) +#define SURFACE_IS_WARP(cmd) (((cmd) == SURFACE_LOOK_UP_WARP) || SURFACE_IS_INSTANT_WARP(cmd)) +#define SURFACE_IS_UNSAFE(cmd) (((cmd) == SURFACE_BURNING) || ((cmd) == SURFACE_DEATH_PLANE) || SURFACE_IS_QUICKSAND(cmd) || SURFACE_IS_WARP(cmd)) enum SurfaceClass { SURFACE_CLASS_DEFAULT, diff --git a/include/types.h b/include/types.h index 68eb137927..3a497996fd 100644 --- a/include/types.h +++ b/include/types.h @@ -24,6 +24,28 @@ #define SCREEN_CENTER_X (SCREEN_WIDTH / 2) #define SCREEN_CENTER_Y (SCREEN_HEIGHT / 2) +typedef union { + struct PACKED { + /*0x00*/ u32 sign : 1; + /*0x00*/ u32 exponent : 8; + /*0x01*/ u32 mantissa : 23; + }; /*0x04*/ + s32 asS32; + u32 asU32; + f32 asF32; +} IEEE754_f32; /*0x04*/ + +typedef union { + struct PACKED { + /*0x00*/ u64 sign : 1; + /*0x00*/ u64 exponent : 11; + /*0x01*/ u64 mantissa : 52; + }; /*0x08*/ + s64 asS64; + u64 asU64; + f64 asF64; +} IEEE754_f64; /*0x08*/ + struct Config { f32 audioFrequency; #ifdef WIDE @@ -444,6 +466,7 @@ struct MarioState { /*0xC0*/ f32 quicksandDepth; /*0xC4*/ f32 windGravity; // -- HackerSM64 MarioState fields begin -- + struct Object *paintingObj; // The painting Mario is currently entering. #ifdef BREATH_METER s16 breath; u8 breathCounter; diff --git a/levels/castle_inside/areas/1/geo.inc.c b/levels/castle_inside/areas/1/geo.inc.c index 39e863ba43..5918d4de36 100644 --- a/levels/castle_inside/areas/1/geo.inc.c +++ b/levels/castle_inside/areas/1/geo.inc.c @@ -48,8 +48,6 @@ const GeoLayout castle_geo_000FD0[] = { GEO_OPEN_NODE(), GEO_DISPLAY_LIST(LAYER_OPAQUE, inside_castle_seg7_dl_07032FC0), GEO_DISPLAY_LIST(LAYER_ALPHA, inside_castle_seg7_dl_07033158), - GEO_ASM( 0, geo_painting_update), - GEO_ASM(PAINTING_ID(0, 1), geo_painting_draw), GEO_CLOSE_NODE(), GEO_RETURN(), }; @@ -61,8 +59,6 @@ const GeoLayout castle_geo_001000[] = { GEO_DISPLAY_LIST(LAYER_OPAQUE, inside_castle_seg7_dl_07034D88), GEO_DISPLAY_LIST(LAYER_ALPHA, inside_castle_seg7_dl_07035178), GEO_DISPLAY_LIST(LAYER_ALPHA, inside_castle_seg7_dl_07035288), - GEO_ASM( 0, geo_painting_update), - GEO_ASM(PAINTING_ID(2, 1), geo_painting_draw), GEO_CLOSE_NODE(), GEO_RETURN(), }; @@ -77,8 +73,6 @@ const GeoLayout castle_geo_001038[] = { GEO_DISPLAY_LIST(LAYER_TRANSPARENT, inside_castle_seg7_dl_07037DE8), GEO_DISPLAY_LIST(LAYER_TRANSPARENT, dl_castle_aquarium_light), GEO_DISPLAY_LIST(LAYER_ALPHA, inside_castle_seg7_dl_07038350), - GEO_ASM( 0, geo_painting_update), - GEO_ASM(PAINTING_ID(3, 1), geo_painting_draw), GEO_CLOSE_NODE(), GEO_RETURN(), }; @@ -89,10 +83,8 @@ const GeoLayout castle_geo_001088[] = { GEO_OPEN_NODE(), GEO_DISPLAY_LIST(LAYER_OPAQUE, inside_castle_seg7_dl_0703A6C8), GEO_DISPLAY_LIST(LAYER_ALPHA, inside_castle_seg7_dl_0703A808), - GEO_DISPLAY_LIST(LAYER_OPAQUE, inside_castle_seg7_dl_070234C0), - GEO_DISPLAY_LIST(LAYER_OPAQUE, inside_castle_seg7_dl_07023520), - GEO_ASM( 0, geo_painting_update), - GEO_ASM(PAINTING_ID(1, 1), geo_painting_draw), + GEO_DISPLAY_LIST(LAYER_OPAQUE, inside_castle_seg7_dl_ccm_fake_painting_1), + GEO_DISPLAY_LIST(LAYER_OPAQUE, inside_castle_seg7_dl_ccm_fake_painting_2), GEO_CLOSE_NODE(), GEO_RETURN(), }; @@ -172,8 +164,6 @@ const GeoLayout castle_geo_001200[] = { GEO_ASM( 0, geo_exec_inside_castle_light), GEO_DISPLAY_LIST(LAYER_OPAQUE, inside_castle_seg7_dl_07032FC0), GEO_DISPLAY_LIST(LAYER_ALPHA, inside_castle_seg7_dl_07033158), - GEO_ASM( 0, geo_painting_update), - GEO_ASM(PAINTING_ID(0, 1), geo_painting_draw), GEO_CLOSE_NODE(), GEO_RETURN(), }; @@ -191,8 +181,6 @@ const GeoLayout castle_geo_001260[] = { GEO_DISPLAY_LIST(LAYER_OPAQUE, inside_castle_seg7_dl_07034D88), GEO_DISPLAY_LIST(LAYER_ALPHA, inside_castle_seg7_dl_07035178), GEO_DISPLAY_LIST(LAYER_ALPHA, inside_castle_seg7_dl_07035288), - GEO_ASM( 0, geo_painting_update), - GEO_ASM(PAINTING_ID(2, 1), geo_painting_draw), GEO_CLOSE_NODE(), GEO_RETURN(), }; @@ -213,8 +201,6 @@ const GeoLayout castle_geo_0012C8[] = { GEO_DISPLAY_LIST(LAYER_TRANSPARENT, inside_castle_seg7_dl_07037DE8), GEO_DISPLAY_LIST(LAYER_TRANSPARENT, dl_castle_aquarium_light), GEO_DISPLAY_LIST(LAYER_ALPHA, inside_castle_seg7_dl_07038350), - GEO_ASM( 0, geo_painting_update), - GEO_ASM(PAINTING_ID(3, 1), geo_painting_draw), GEO_CLOSE_NODE(), GEO_RETURN(), }; @@ -231,10 +217,8 @@ const GeoLayout castle_geo_001348[] = { GEO_ASM( 0, geo_exec_inside_castle_light), GEO_DISPLAY_LIST(LAYER_OPAQUE, inside_castle_seg7_dl_0703A6C8), GEO_DISPLAY_LIST(LAYER_ALPHA, inside_castle_seg7_dl_0703A808), - GEO_DISPLAY_LIST(LAYER_OPAQUE, inside_castle_seg7_dl_070234C0), - GEO_DISPLAY_LIST(LAYER_OPAQUE, inside_castle_seg7_dl_07023520), - GEO_ASM( 0, geo_painting_update), - GEO_ASM(PAINTING_ID(1, 1), geo_painting_draw), + GEO_DISPLAY_LIST(LAYER_OPAQUE, inside_castle_seg7_dl_ccm_fake_painting_1), + GEO_DISPLAY_LIST(LAYER_OPAQUE, inside_castle_seg7_dl_ccm_fake_painting_2), GEO_CLOSE_NODE(), GEO_RETURN(), }; diff --git a/levels/castle_inside/areas/2/geo.inc.c b/levels/castle_inside/areas/2/geo.inc.c index 2f39672fc2..43803f5856 100644 --- a/levels/castle_inside/areas/2/geo.inc.c +++ b/levels/castle_inside/areas/2/geo.inc.c @@ -14,9 +14,6 @@ const GeoLayout castle_geo_001578[] = { GEO_DISPLAY_LIST(LAYER_OPAQUE, inside_castle_seg7_dl_07043028), GEO_DISPLAY_LIST(LAYER_OPAQUE, inside_castle_seg7_dl_07043B48), GEO_DISPLAY_LIST(LAYER_ALPHA, inside_castle_seg7_dl_07043CD8), - GEO_ASM( 0, geo_painting_update), - GEO_ASM(PAINTING_ID(8, 1), geo_painting_draw), - GEO_ASM(PAINTING_ID(10, 1), geo_painting_draw), GEO_CLOSE_NODE(), GEO_RETURN(), }; @@ -28,8 +25,6 @@ const GeoLayout castle_geo_0015B8[] = { GEO_DISPLAY_LIST(LAYER_OPAQUE, inside_castle_seg7_dl_0704A0E8), GEO_DISPLAY_LIST(LAYER_TRANSPARENT, inside_castle_seg7_dl_0704A2E0), GEO_DISPLAY_LIST(LAYER_OPAQUE, inside_castle_seg7_dl_0704AA98), - GEO_ASM( 0, geo_painting_update), - GEO_ASM(PAINTING_ID(12, 1), geo_painting_draw), GEO_ASM( 0, geo_render_mirror_mario), GEO_CLOSE_NODE(), GEO_RETURN(), @@ -40,9 +35,6 @@ const GeoLayout castle_geo_0015F8[] = { GEO_NODE_START(), GEO_OPEN_NODE(), GEO_DISPLAY_LIST(LAYER_OPAQUE, inside_castle_seg7_dl_0704C7D8), - GEO_ASM( 0, geo_painting_update), - GEO_ASM(PAINTING_ID(9, 1), geo_painting_draw), - GEO_ASM(PAINTING_ID(13, 1), geo_painting_draw), GEO_CLOSE_NODE(), GEO_RETURN(), }; @@ -55,8 +47,6 @@ const GeoLayout castle_geo_001628[] = { GEO_DISPLAY_LIST(LAYER_ALPHA, inside_castle_seg7_dl_07051678), GEO_DISPLAY_LIST(LAYER_TRANSPARENT, inside_castle_seg7_dl_070519C8), GEO_DISPLAY_LIST(LAYER_TRANSPARENT, inside_castle_seg7_dl_07051B60), - GEO_ASM( 0, geo_painting_update), - GEO_ASM(PAINTING_ID(11, 1), geo_painting_draw), GEO_CLOSE_NODE(), GEO_RETURN(), }; @@ -80,9 +70,6 @@ const GeoLayout castle_geo_001690[] = { GEO_DISPLAY_LIST(LAYER_OPAQUE, inside_castle_seg7_dl_07043028), GEO_DISPLAY_LIST(LAYER_OPAQUE, inside_castle_seg7_dl_07043B48), GEO_DISPLAY_LIST(LAYER_ALPHA, inside_castle_seg7_dl_07043CD8), - GEO_ASM( 0, geo_painting_update), - GEO_ASM(PAINTING_ID(8, 1), geo_painting_draw), - GEO_ASM(PAINTING_ID(10, 1), geo_painting_draw), GEO_CLOSE_NODE(), GEO_RETURN(), }; @@ -97,10 +84,6 @@ const GeoLayout castle_geo_0016D8[] = { GEO_DISPLAY_LIST(LAYER_OPAQUE, inside_castle_seg7_dl_0704A0E8), GEO_DISPLAY_LIST(LAYER_TRANSPARENT, inside_castle_seg7_dl_0704A2E0), GEO_DISPLAY_LIST(LAYER_OPAQUE, inside_castle_seg7_dl_0704AA98), - GEO_ASM( 0, geo_painting_update), - GEO_ASM(PAINTING_ID(8, 1), geo_painting_draw), - GEO_ASM(PAINTING_ID(10, 1), geo_painting_draw), - GEO_ASM(PAINTING_ID(12, 1), geo_painting_draw), GEO_ASM( 0, geo_render_mirror_mario), GEO_CLOSE_NODE(), GEO_RETURN(), @@ -114,11 +97,6 @@ const GeoLayout castle_geo_001740[] = { GEO_DISPLAY_LIST(LAYER_OPAQUE, inside_castle_seg7_dl_07043B48), GEO_DISPLAY_LIST(LAYER_ALPHA, inside_castle_seg7_dl_07043CD8), GEO_DISPLAY_LIST(LAYER_OPAQUE, inside_castle_seg7_dl_0704C7D8), - GEO_ASM( 0, geo_painting_update), - GEO_ASM(PAINTING_ID(8, 1), geo_painting_draw), - GEO_ASM(PAINTING_ID(9, 1), geo_painting_draw), - GEO_ASM(PAINTING_ID(10, 1), geo_painting_draw), - GEO_ASM(PAINTING_ID(13, 1), geo_painting_draw), GEO_CLOSE_NODE(), GEO_RETURN(), }; @@ -134,10 +112,6 @@ const GeoLayout castle_geo_001798[] = { GEO_DISPLAY_LIST(LAYER_ALPHA, inside_castle_seg7_dl_07051678), GEO_DISPLAY_LIST(LAYER_TRANSPARENT, inside_castle_seg7_dl_070519C8), GEO_DISPLAY_LIST(LAYER_TRANSPARENT, inside_castle_seg7_dl_07051B60), - GEO_ASM( 0, geo_painting_update), - GEO_ASM(PAINTING_ID(8, 1), geo_painting_draw), - GEO_ASM(PAINTING_ID(10, 1), geo_painting_draw), - GEO_ASM(PAINTING_ID(11, 1), geo_painting_draw), GEO_CLOSE_NODE(), GEO_RETURN(), }; @@ -153,8 +127,6 @@ const GeoLayout castle_geo_001800[] = { GEO_DISPLAY_LIST(LAYER_OPAQUE, inside_castle_seg7_dl_070558D0), GEO_DISPLAY_LIST(LAYER_OPAQUE, inside_castle_seg7_dl_070572A0), GEO_DISPLAY_LIST(LAYER_OPAQUE, inside_castle_seg7_dl_07057F00), - GEO_ASM( 0, geo_painting_update), - GEO_ASM(PAINTING_ID(11, 1), geo_painting_draw), GEO_CLOSE_NODE(), GEO_RETURN(), }; diff --git a/levels/castle_inside/areas/3/collision.inc.c b/levels/castle_inside/areas/3/collision.inc.c index a74959bc68..2d3270d2f1 100644 --- a/levels/castle_inside/areas/3/collision.inc.c +++ b/levels/castle_inside/areas/3/collision.inc.c @@ -134,20 +134,20 @@ const Collision inside_castle_seg7_area_3_collision[] = { COL_VERTEX(358, -1074, 2202), COL_VERTEX(461, -1074, 2253), COL_VERTEX(410, -1074, 2253), - COL_VERTEX(3866, -1074, 2406), - COL_VERTEX(3866, -1074, 1587), - COL_VERTEX(5530, -1074, 2406), - COL_VERTEX(5530, -1074, 1587), + COL_VERTEX(3456, -1074, 2406), + COL_VERTEX(3456, -1074, 1587), + COL_VERTEX(6605, -1074, 2406), + COL_VERTEX(6605, -1074, 1587), COL_VERTEX(3456, -1074, 2406), COL_VERTEX(3456, -1074, 1587), COL_VERTEX(-3225, -1177, -1177), COL_VERTEX(-3225, -1177, -1074), COL_VERTEX(-3225, -1177, -665), COL_VERTEX(-3225, -1177, -1043), - COL_VERTEX(5530, -255, 1587), + COL_VERTEX(6605, -255, 1587), COL_VERTEX(3533, -255, 2406), COL_VERTEX(3533, -255, 1587), - COL_VERTEX(5530, -255, 2406), + COL_VERTEX(6605, -255, 2406), COL_VERTEX(3533, -1074, 2406), COL_VERTEX(3533, -1074, 1587), COL_VERTEX(3482, -1074, 1638), @@ -2523,91 +2523,3 @@ const Collision inside_castle_seg7_area_3_collision[] = { COL_WATER_BOX(2, 5786, -1330, 8038, 410, -1228), COL_END(), }; - -// 0x070775B4 - 0x0707768C -const Collision inside_castle_seg7_collision_ddd_warp[] = { - COL_INIT(), - COL_VERTEX_INIT(0x12), - COL_VERTEX(3866, -1074, 1587), - COL_VERTEX(3487, -1074, 1864), - COL_VERTEX(3866, -1074, 1864), - COL_VERTEX(3487, -1074, 1587), - COL_VERTEX(3487, -1074, 2135), - COL_VERTEX(3866, -1074, 2135), - COL_VERTEX(3487, -1074, 2406), - COL_VERTEX(3866, -1074, 2406), - COL_VERTEX(5939, -1074, 1587), - COL_VERTEX(5530, -1074, 1587), - COL_VERTEX(5530, -1074, 1864), - COL_VERTEX(5939, -1074, 1864), - COL_VERTEX(5530, -1074, 2135), - COL_VERTEX(5939, -1074, 2135), - COL_VERTEX(5530, -1074, 2406), - COL_VERTEX(5939, -1074, 2406), - COL_VERTEX(3456, -1074, 1587), - COL_VERTEX(3456, -1074, 2406), - COL_TRI_INIT(SURFACE_DEFAULT, 8), - COL_TRI(3, 16, 17), - COL_TRI(3, 17, 6), - COL_TRI(8, 9, 10), - COL_TRI(8, 10, 11), - COL_TRI(11, 10, 12), - COL_TRI(11, 12, 13), - COL_TRI(13, 12, 14), - COL_TRI(13, 14, 15), - COL_TRI_INIT(SURFACE_PAINTING_WARP_E8, 2), - COL_TRI(0, 1, 2), - COL_TRI(0, 3, 1), - COL_TRI_INIT(SURFACE_PAINTING_WARP_E9, 2), - COL_TRI(2, 1, 4), - COL_TRI(2, 4, 5), - COL_TRI_INIT(SURFACE_PAINTING_WARP_EA, 2), - COL_TRI(5, 6, 7), - COL_TRI(5, 4, 6), - COL_TRI_STOP(), - COL_END(), -}; - -// 0x0707768C - 0x07077764 -const Collision inside_castle_seg7_collision_ddd_warp_2[] = { - COL_INIT(), - COL_VERTEX_INIT(0x12), - COL_VERTEX(5939, -1074, 1587), - COL_VERTEX(5560, -1074, 1864), - COL_VERTEX(5939, -1074, 1864), - COL_VERTEX(5560, -1074, 1587), - COL_VERTEX(5560, -1074, 2135), - COL_VERTEX(5939, -1074, 2135), - COL_VERTEX(5560, -1074, 2406), - COL_VERTEX(5939, -1074, 2406), - COL_VERTEX(5530, -1074, 1587), - COL_VERTEX(5530, -1074, 2406), - COL_VERTEX(3866, -1074, 1864), - COL_VERTEX(3456, -1074, 2135), - COL_VERTEX(3866, -1074, 2135), - COL_VERTEX(3456, -1074, 2406), - COL_VERTEX(3866, -1074, 2406), - COL_VERTEX(3456, -1074, 1864), - COL_VERTEX(3866, -1074, 1587), - COL_VERTEX(3456, -1074, 1587), - COL_TRI_INIT(SURFACE_DEFAULT, 8), - COL_TRI(8, 9, 6), - COL_TRI(8, 6, 3), - COL_TRI(10, 11, 12), - COL_TRI(12, 13, 14), - COL_TRI(12, 11, 13), - COL_TRI(10, 15, 11), - COL_TRI(16, 15, 10), - COL_TRI(16, 17, 15), - COL_TRI_INIT(SURFACE_PAINTING_WARP_E8, 2), - COL_TRI(0, 1, 2), - COL_TRI(0, 3, 1), - COL_TRI_INIT(SURFACE_PAINTING_WARP_E9, 2), - COL_TRI(2, 4, 5), - COL_TRI(2, 1, 4), - COL_TRI_INIT(SURFACE_PAINTING_WARP_EA, 2), - COL_TRI(5, 4, 6), - COL_TRI(5, 6, 7), - COL_TRI_STOP(), - COL_END(), -}; diff --git a/levels/castle_inside/areas/3/geo.inc.c b/levels/castle_inside/areas/3/geo.inc.c index ad1fbcf691..939ce9c538 100644 --- a/levels/castle_inside/areas/3/geo.inc.c +++ b/levels/castle_inside/areas/3/geo.inc.c @@ -15,9 +15,6 @@ const GeoLayout castle_geo_001980[] = { GEO_OPEN_NODE(), GEO_DISPLAY_LIST(LAYER_OPAQUE, inside_castle_seg7_dl_070616E8), GEO_DISPLAY_LIST(LAYER_TRANSPARENT, inside_castle_seg7_dl_07061C20), - GEO_ASM( 0, geo_painting_update), - GEO_ASM( PAINTING_ID(4, 1), geo_painting_draw), - GEO_ASM( PAINTING_ID(5, 1), geo_painting_draw), GEO_ASM( 0, geo_movtex_pause_control), GEO_ASM(INSIDE_CASTLE_MOVTEX_GREEN_ROOM_WATER, geo_movtex_draw_water_regions), GEO_CLOSE_NODE(), @@ -30,8 +27,6 @@ const GeoLayout castle_geo_0019C8[] = { GEO_OPEN_NODE(), GEO_DISPLAY_LIST(LAYER_OPAQUE, inside_castle_seg7_dl_07064B78), GEO_DISPLAY_LIST(LAYER_ALPHA, inside_castle_seg7_dl_07064D58), - GEO_ASM(0, geo_painting_update), - GEO_ASM(PAINTING_ID(6, 1), geo_painting_draw), GEO_CLOSE_NODE(), GEO_RETURN(), }; @@ -54,8 +49,6 @@ const GeoLayout castle_geo_001A30[] = { GEO_NODE_START(), GEO_OPEN_NODE(), GEO_DISPLAY_LIST(LAYER_OPAQUE, inside_castle_seg7_dl_07068850), - GEO_ASM( 0, geo_painting_update), - GEO_ASM(PAINTING_ID(7, 1), geo_painting_draw), GEO_CLOSE_NODE(), GEO_RETURN(), }; @@ -69,9 +62,6 @@ const GeoLayout castle_geo_001A58[] = { GEO_DISPLAY_LIST(LAYER_TRANSPARENT, inside_castle_seg7_dl_0705E450), GEO_DISPLAY_LIST(LAYER_OPAQUE, inside_castle_seg7_dl_070616E8), GEO_DISPLAY_LIST(LAYER_TRANSPARENT, inside_castle_seg7_dl_07061C20), - GEO_ASM( 0, geo_painting_update), - GEO_ASM( PAINTING_ID(4, 1), geo_painting_draw), - GEO_ASM( PAINTING_ID(5, 1), geo_painting_draw), GEO_ASM( 0, geo_movtex_pause_control), GEO_ASM(INSIDE_CASTLE_MOVTEX_GREEN_ROOM_WATER, geo_movtex_draw_water_regions), GEO_CLOSE_NODE(), @@ -86,8 +76,6 @@ const GeoLayout castle_geo_001AB8[] = { GEO_DISPLAY_LIST(LAYER_ALPHA, inside_castle_seg7_dl_0705E2A0), GEO_DISPLAY_LIST(LAYER_TRANSPARENT, inside_castle_seg7_dl_0705E450), GEO_DISPLAY_LIST(LAYER_OPAQUE, inside_castle_seg7_dl_07068850), - GEO_ASM( 0, geo_painting_update), - GEO_ASM(PAINTING_ID(7, 1), geo_painting_draw), GEO_CLOSE_NODE(), GEO_RETURN(), }; @@ -117,9 +105,6 @@ const GeoLayout castle_geo_001B48[] = { GEO_DISPLAY_LIST(LAYER_OPAQUE, inside_castle_seg7_dl_07066CE0), GEO_DISPLAY_LIST(LAYER_TRANSPARENT, inside_castle_seg7_dl_07066E90), GEO_DISPLAY_LIST(LAYER_ALPHA, inside_castle_seg7_dl_07066FA0), - GEO_ASM( 0, geo_painting_update), - GEO_ASM( PAINTING_ID(4, 1), geo_painting_draw), - GEO_ASM( PAINTING_ID(5, 1), geo_painting_draw), GEO_ASM( 0, geo_movtex_pause_control), GEO_ASM(INSIDE_CASTLE_MOVTEX_GREEN_ROOM_WATER, geo_movtex_draw_water_regions), GEO_ASM(INSIDE_CASTLE_MOVTEX_MOAT_WATER, geo_movtex_draw_water_regions), @@ -135,10 +120,6 @@ const GeoLayout castle_geo_001BB0[] = { GEO_DISPLAY_LIST(LAYER_TRANSPARENT, inside_castle_seg7_dl_07061C20), GEO_DISPLAY_LIST(LAYER_OPAQUE, inside_castle_seg7_dl_07064B78), GEO_DISPLAY_LIST(LAYER_ALPHA, inside_castle_seg7_dl_07064D58), - GEO_ASM( 0, geo_painting_update), - GEO_ASM( PAINTING_ID(4, 1), geo_painting_draw), - GEO_ASM( PAINTING_ID(5, 1), geo_painting_draw), - GEO_ASM( PAINTING_ID(6, 1), geo_painting_draw), GEO_ASM( 0, geo_movtex_pause_control), GEO_ASM(INSIDE_CASTLE_MOVTEX_GREEN_ROOM_WATER, geo_movtex_draw_water_regions), GEO_CLOSE_NODE(), diff --git a/levels/castle_inside/header.h b/levels/castle_inside/header.h index 891fee8273..c91e689157 100644 --- a/levels/castle_inside/header.h +++ b/levels/castle_inside/header.h @@ -55,24 +55,23 @@ extern const GeoLayout castle_geo_001BB0[]; extern const GeoLayout castle_geo_001C10[]; // leveldata -extern const Gfx inside_castle_seg7_dl_070225D8[]; -extern const Gfx inside_castle_seg7_dl_07022610[]; -extern const Gfx inside_castle_seg7_dl_070234C0[]; -extern const Gfx inside_castle_seg7_dl_07023520[]; -extern struct Painting bob_painting; -extern struct Painting ccm_painting; -extern struct Painting wf_painting; -extern struct Painting jrb_painting; -extern struct Painting lll_painting; -extern struct Painting ssl_painting; -extern struct Painting hmc_painting; -extern struct Painting ddd_painting; -extern struct Painting wdw_painting; -extern struct Painting thi_tiny_painting; -extern struct Painting ttm_painting; -extern struct Painting ttc_painting; -extern struct Painting sl_painting; -extern struct Painting thi_huge_painting; +extern const Gfx inside_castle_seg7_dl_ccm_fake_painting_1[]; +extern const Gfx inside_castle_seg7_dl_ccm_fake_painting_2[]; +extern struct PaintingImage bob_painting; +extern struct PaintingImage ccm_painting; +extern struct PaintingImage wf_painting; +extern struct PaintingImage jrb_painting; +extern struct PaintingImage lll_painting; +extern struct PaintingImage ssl_painting; +extern struct PaintingImage hmc_painting; +extern struct PaintingImage ddd_painting; +extern struct PaintingImage wdw_painting; +extern struct PaintingImage thi_tiny_painting; +extern struct PaintingImage ttm_painting; +extern struct PaintingImage ttc_painting; +extern struct PaintingImage sl_painting; +extern struct PaintingImage thi_huge_painting; +extern struct PaintingImage rr_painting; extern const Gfx inside_castle_seg7_dl_bowser_1_painting[]; extern const Gfx inside_castle_seg7_dl_07028FD0[]; extern const Gfx inside_castle_seg7_dl_07029578[]; @@ -136,8 +135,6 @@ extern const Gfx inside_castle_seg7_dl_07068B10[]; extern const Collision inside_castle_seg7_area_1_collision[]; extern const Collision inside_castle_seg7_area_2_collision[]; extern const Collision inside_castle_seg7_area_3_collision[]; -extern const Collision inside_castle_seg7_collision_ddd_warp[]; -extern const Collision inside_castle_seg7_collision_ddd_warp_2[]; extern const MacroObject inside_castle_seg7_area_1_macro_objs[]; extern const MacroObject inside_castle_seg7_area_2_macro_objs[]; extern const MacroObject inside_castle_seg7_area_3_macro_objs[]; diff --git a/levels/castle_inside/painting.inc.c b/levels/castle_inside/painting.inc.c index a428f2a9b5..6fdddfcd57 100644 --- a/levels/castle_inside/painting.inc.c +++ b/levels/castle_inside/painting.inc.c @@ -1,69 +1,57 @@ #include "game/paintings.h" -// 0x07021800 - 0x07021818 +#define CCM_FAKE_SIZE 614 -// 0x07021818 - 0x07021898 -static const Vtx inside_castle_seg7_vertex_07021818[] = { - {{{ 0, 0, 0}, 0, { -32, 992}, {0x00, 0x00, 0x7f, 0xff}}}, - {{{ 614, 0, 0}, 0, { 2012, 992}, {0x00, 0x00, 0x7f, 0xff}}}, - {{{ 614, 307, 0}, 0, { 2012, 0}, {0x00, 0x00, 0x7f, 0xff}}}, - {{{ 0, 307, 0}, 0, { -32, 0}, {0x00, 0x00, 0x7f, 0xff}}}, - {{{ 0, 307, 0}, 0, { -32, 992}, {0x00, 0x00, 0x7f, 0xff}}}, - {{{ 614, 307, 0}, 0, { 2012, 992}, {0x00, 0x00, 0x7f, 0xff}}}, - {{{ 614, 614, 0}, 0, { 2012, -28}, {0x00, 0x00, 0x7f, 0xff}}}, - {{{ 0, 614, 0}, 0, { -32, -28}, {0x00, 0x00, 0x7f, 0xff}}}, -}; - -// 0x07021898 - 0x07021918 -static const Vtx inside_castle_seg7_vertex_07021898[] = { - {{{ 0, 0, 0}, 0, { -32, 992}, {0xdd, 0xdd, 0xdd, 0xff}}}, - {{{ 614, 0, 0}, 0, { 2012, 992}, {0xdd, 0xdd, 0xdd, 0xff}}}, - {{{ 614, 307, 0}, 0, { 2012, 0}, {0xdd, 0xdd, 0xdd, 0xff}}}, - {{{ 0, 307, 0}, 0, { -32, 0}, {0xdd, 0xdd, 0xdd, 0xff}}}, - {{{ 0, 307, 0}, 0, { -32, 992}, {0xdd, 0xdd, 0xdd, 0xff}}}, - {{{ 614, 307, 0}, 0, { 2012, 992}, {0xdd, 0xdd, 0xdd, 0xff}}}, - {{{ 614, 614, 0}, 0, { 2012, -28}, {0xdd, 0xdd, 0xdd, 0xff}}}, - {{{ 0, 614, 0}, 0, { -32, -28}, {0xdd, 0xdd, 0xdd, 0xff}}}, -}; +#define CCM_FAKE_1_X -3046 +#define CCM_FAKE_1_Z -3724 +// yaw ~ 150.33 +#define CCM_FAKE_1_DX 304 // CCM_FAKE_SIZE * sin(yaw) +#define CCM_FAKE_1_DZ -534 // CCM_FAKE_SIZE * cos(yaw) // 0x07021918 - 0x07021998 -static const Vtx inside_castle_seg7_vertex_07021918[] = { - {{{ -3046, -307, -3724}, 0, { -32, 992}, {0x00, 0x00, 0x7f, 0xff}}}, - {{{ -2742, -307, -4258}, 0, { 2012, 992}, {0x00, 0x00, 0x7f, 0xff}}}, - {{{ -2742, 0, -4258}, 0, { 2012, 0}, {0x00, 0x00, 0x7f, 0xff}}}, - {{{ -3046, 0, -3724}, 0, { -32, 0}, {0x00, 0x00, 0x7f, 0xff}}}, - {{{ -3046, 0, -3724}, 0, { -32, 992}, {0x00, 0x00, 0x7f, 0xff}}}, - {{{ -2742, 0, -4258}, 0, { 2012, 992}, {0x00, 0x00, 0x7f, 0xff}}}, - {{{ -2742, 307, -4258}, 0, { 2012, 0}, {0x00, 0x00, 0x7f, 0xff}}}, - {{{ -3046, 307, -3724}, 0, { -32, 0}, {0x00, 0x00, 0x7f, 0xff}}}, -}; +static const Vtx inside_castle_seg7_vertex_painting_ccm_fake_1[] = { + {{{(CCM_FAKE_1_X + 0), -(CCM_FAKE_SIZE / 2), (CCM_FAKE_1_Z + 0)}, 0, { -32, 992}, {0x00, 0x00, 0x7f, 0xff}}}, + {{{(CCM_FAKE_1_X + CCM_FAKE_1_DX), -(CCM_FAKE_SIZE / 2), (CCM_FAKE_1_Z + CCM_FAKE_1_DZ)}, 0, { 2012, 992}, {0x00, 0x00, 0x7f, 0xff}}}, + {{{(CCM_FAKE_1_X + CCM_FAKE_1_DX), 0, (CCM_FAKE_1_Z + CCM_FAKE_1_DZ)}, 0, { 2012, 0}, {0x00, 0x00, 0x7f, 0xff}}}, + {{{(CCM_FAKE_1_X + 0), 0, (CCM_FAKE_1_Z + 0)}, 0, { -32, 0}, {0x00, 0x00, 0x7f, 0xff}}}, + {{{(CCM_FAKE_1_X + 0), 0, (CCM_FAKE_1_Z + 0)}, 0, { -32, 992}, {0x00, 0x00, 0x7f, 0xff}}}, + {{{(CCM_FAKE_1_X + CCM_FAKE_1_DX), 0, (CCM_FAKE_1_Z + CCM_FAKE_1_DZ)}, 0, { 2012, 992}, {0x00, 0x00, 0x7f, 0xff}}}, + {{{(CCM_FAKE_1_X + CCM_FAKE_1_DX), (CCM_FAKE_SIZE / 2), (CCM_FAKE_1_Z + CCM_FAKE_1_DZ)}, 0, { 2012, 0}, {0x00, 0x00, 0x7f, 0xff}}}, + {{{(CCM_FAKE_1_X + 0), (CCM_FAKE_SIZE / 2), (CCM_FAKE_1_Z + 0)}, 0, { -32, 0}, {0x00, 0x00, 0x7f, 0xff}}}, +}; + +#define CCM_FAKE_2_X -1866 +#define CCM_FAKE_2_Z -4258 +// yaw ~ 29.66 +#define CCM_FAKE_2_DX 304 // CCM_FAKE_SIZE * sin(yaw) +#define CCM_FAKE_2_DZ 534 // CCM_FAKE_SIZE * cos(yaw) // 0x07021998 - 0x07021A18 -static const Vtx inside_castle_seg7_vertex_07021998[] = { - {{{ -1866, -307, -4258}, 0, { -32, 992}, {0x00, 0x00, 0x7f, 0xff}}}, - {{{ -1562, -307, -3724}, 0, { 2012, 992}, {0x00, 0x00, 0x7f, 0xff}}}, - {{{ -1562, 0, -3724}, 0, { 2012, 0}, {0x00, 0x00, 0x7f, 0xff}}}, - {{{ -1866, 0, -4258}, 0, { -32, 0}, {0x00, 0x00, 0x7f, 0xff}}}, - {{{ -1866, 0, -4258}, 0, { -32, 992}, {0x00, 0x00, 0x7f, 0xff}}}, - {{{ -1562, 0, -3724}, 0, { 2012, 992}, {0x00, 0x00, 0x7f, 0xff}}}, - {{{ -1562, 307, -3724}, 0, { 2012, 0}, {0x00, 0x00, 0x7f, 0xff}}}, - {{{ -1866, 307, -4258}, 0, { -32, 0}, {0x00, 0x00, 0x7f, 0xff}}}, +static const Vtx inside_castle_seg7_vertex_painting_ccm_fake_2[] = { + {{{(CCM_FAKE_2_X + 0), -(CCM_FAKE_SIZE / 2), (CCM_FAKE_2_Z + 0)}, 0, { -32, 992}, {0x00, 0x00, 0x7f, 0xff}}}, + {{{(CCM_FAKE_2_X + CCM_FAKE_2_DX), -(CCM_FAKE_SIZE / 2), (CCM_FAKE_2_Z + CCM_FAKE_2_DZ)}, 0, { 2012, 992}, {0x00, 0x00, 0x7f, 0xff}}}, + {{{(CCM_FAKE_2_X + CCM_FAKE_2_DX), 0, (CCM_FAKE_2_Z + CCM_FAKE_2_DZ)}, 0, { 2012, 0}, {0x00, 0x00, 0x7f, 0xff}}}, + {{{(CCM_FAKE_2_X + 0), 0, (CCM_FAKE_2_Z + 0)}, 0, { -32, 0}, {0x00, 0x00, 0x7f, 0xff}}}, + {{{(CCM_FAKE_2_X + 0), 0, (CCM_FAKE_2_Z + 0)}, 0, { -32, 992}, {0x00, 0x00, 0x7f, 0xff}}}, + {{{(CCM_FAKE_2_X + CCM_FAKE_2_DX), 0, (CCM_FAKE_2_Z + CCM_FAKE_2_DZ)}, 0, { 2012, 992}, {0x00, 0x00, 0x7f, 0xff}}}, + {{{(CCM_FAKE_2_X + CCM_FAKE_2_DX), (CCM_FAKE_SIZE / 2), (CCM_FAKE_2_Z + CCM_FAKE_2_DZ)}, 0, { 2012, 0}, {0x00, 0x00, 0x7f, 0xff}}}, + {{{(CCM_FAKE_2_X + 0), (CCM_FAKE_SIZE / 2), (CCM_FAKE_2_Z + 0)}, 0, { -32, 0}, {0x00, 0x00, 0x7f, 0xff}}}, }; // 0x07021A18 - 0x07021A30 -static const Gfx inside_castle_seg7_dl_07021A18[] = { +static const Gfx inside_castle_seg7_sub_dl_painting_bottom[] = { gsSP2Triangles( 0, 1, 2, 0x0, 0, 2, 3, 0x0), gsSPEndDisplayList(), }; // 0x07021A30 - 0x07021A48 -static const Gfx inside_castle_seg7_dl_07021A30[] = { +static const Gfx inside_castle_seg7_sub_dl_painting_top[] = { gsSP2Triangles( 4, 5, 6, 0x0, 4, 6, 7, 0x0), gsSPEndDisplayList(), }; // 0x07021A48 - 0x07021AA0 -static const Gfx inside_castle_seg7_dl_07021A48[] = { +static const Gfx inside_castle_seg7_dl_painting_textured_shaded_begin[] = { gsDPPipeSync(), gsSPSetGeometryMode(G_LIGHTING | G_SHADING_SMOOTH), gsDPSetCombineMode(G_CC_MODULATERGB, G_CC_MODULATERGB), @@ -78,1641 +66,329 @@ static const Gfx inside_castle_seg7_dl_07021A48[] = { }; // 0x07021AA0 - 0x07021AC0 -static const Gfx inside_castle_seg7_dl_07021AA0[] = { - gsSPTexture(0xFFFF, 0xFFFF, 0, G_TX_RENDERTILE, G_OFF), - gsDPPipeSync(), - gsDPSetCombineMode(G_CC_SHADE, G_CC_SHADE), - gsSPEndDisplayList(), -}; - -// 0x07021AC0 - 0x07021AE0 -static const Gfx inside_castle_seg7_painting_dl_07021AC0[] = { - gsDPTileSync(), - gsDPSetTile(G_IM_FMT_RGBA, G_IM_SIZ_16b, 16, 0, G_TX_RENDERTILE, 0, G_TX_CLAMP, 5, G_TX_NOLOD, G_TX_CLAMP, 6, G_TX_NOLOD), - gsDPSetTileSize(0, 0, 0, (64 - 1) << G_TEXTURE_IMAGE_FRAC, (32 - 1) << G_TEXTURE_IMAGE_FRAC), - gsSPEndDisplayList(), -}; - -// 0x07021AE0 - 0x07021FFA -static const PaintingData inside_castle_seg7_painting_texture_map_bottom_07021AE0[] = { - 85, // num mappings - // Format: - // mesh vtx ID, texture X, texture Y - 49, 2016, 889, - 53, 2016, 685, - 55, 1843, 787, - 50, 2016, 992, - 51, 1843, 992, - 52, 1843, 583, - 75, 2016, 513, - 54, 1671, 889, - 59, 1671, 685, - 62, 1502, 787, - 56, 1502, 992, - 57, 1671, 992, - 58, 1502, 583, - 60, 1671, 513, - 61, 1330, 889, - 65, 1330, 685, - 63, 1162, 992, - 64, 1330, 992, - 66, 1162, 583, - 67, 1330, 513, - 69, 1162, 787, - 68, 989, 889, - 70, 821, 992, - 71, 989, 992, - 73, 989, 685, - 72, 821, 583, - 74, 989, 513, - 77, 2016, 308, - 78, 1843, 410, - 76, 1843, 204, - 81, 1502, 410, - 80, 1671, 308, - 47, 1671, 102, - 79, 1502, 204, - 46, 1330, 102, - 82, 1162, 204, - 83, 1330, 308, - 84, 1162, 410, - 86, 989, 308, - 85, 821, 204, - 48, 989, 102, - 25, 1502, 0, - 31, 1162, 0, - 19, 1843, 0, - 37, 821, 0, - 120, 821, 787, - 119, 649, 889, - 122, 481, 992, - 121, 649, 992, - 124, 649, 685, - 125, 481, 583, - 123, 649, 513, - 127, 481, 787, - 126, 308, 889, - 129, 140, 992, - 128, 308, 992, - 132, 308, 513, - 131, 308, 685, - 130, 140, 583, - 134, 140, 787, - 133, -32, 889, - 135, -32, 513, - 136, 821, 410, - 116, 649, 102, - 137, 649, 308, - 114, 481, 204, - 138, 481, 410, - 139, 308, 308, - 118, 140, 204, - 115, 308, 102, - 140, 140, 410, - 117, -32, 102, - 99, 481, 0, - 105, 140, 0, - 143, 2016, 102, - 145, 1330, 0, - 144, 1671, 0, - 142, 2016, 0, - 146, 989, 0, - 155, -32, 685, - 156, -32, 992, - 154, -32, 308, - 151, 308, 0, - 150, 649, 0, - 153, -32, 0, - - 132, // num groups - // Grouped by 5 + one remainder group, - // = 15 vertices per group + a few extra triangles - 13, 8, 5, - 0, 1, 2, - 3, 0, 4, - 4, 0, 2, - 5, 2, 1, - 1, 6, 5, - 7, 2, 8, - 5, 8, 2, - 2, 7, 4, - 7, 8, 9, - 10, 7, 9, - 11, 7, 10, - 7, 11, 4, - 12, 9, 8, - 8, 13, 12, - 21, 24, 45, - 14, 9, 15, - 12, 15, 9, - 9, 14, 10, - 16, 14, 20, - 17, 14, 16, - 14, 15, 20, - 14, 17, 10, - 15, 19, 18, - 18, 20, 15, - 19, 15, 12, - 20, 21, 16, - 18, 24, 20, - 21, 20, 24, - 22, 21, 45, - 23, 21, 22, - 21, 23, 16, - 24, 26, 25, - 25, 45, 24, - 26, 24, 18, - 6, 27, 28, - 5, 6, 28, - 29, 28, 27, - 27, 74, 29, - 29, 31, 28, - 13, 28, 31, - 28, 13, 5, - 36, 34, 35, - 12, 13, 30, - 13, 31, 30, - 31, 32, 33, - 32, 31, 29, - 33, 30, 31, - 33, 36, 30, - 30, 19, 12, - 19, 30, 36, - 18, 19, 37, - 19, 36, 37, - 34, 36, 33, - 35, 37, 36, - 37, 26, 18, - 35, 38, 37, - 26, 37, 38, - 25, 26, 62, - 26, 38, 62, - 38, 40, 39, - 39, 62, 38, - 40, 38, 35, - 41, 34, 33, - 33, 32, 41, - 42, 34, 75, - 34, 41, 75, - 35, 34, 42, - 32, 43, 76, - 41, 32, 76, - 43, 32, 29, - 29, 74, 43, - 43, 74, 77, - 46, 49, 52, - 42, 40, 35, - 39, 40, 44, - 40, 42, 78, - 44, 40, 78, - 25, 49, 45, - 45, 46, 22, - 46, 45, 49, - 47, 46, 52, - 48, 46, 47, - 46, 48, 22, - 58, 59, 57, - 49, 51, 50, - 50, 52, 49, - 51, 49, 25, - 50, 57, 52, - 52, 53, 47, - 53, 52, 57, - 53, 55, 47, - 54, 53, 59, - 55, 53, 54, - 53, 57, 59, - 56, 57, 50, - 57, 56, 58, - 58, 79, 59, - 59, 60, 54, - 60, 59, 79, - 60, 80, 54, - 61, 79, 58, - 62, 51, 25, - 39, 64, 62, - 51, 62, 64, - 50, 51, 66, - 51, 64, 66, - 63, 64, 39, - 64, 63, 65, - 65, 66, 64, - 66, 56, 50, - 56, 66, 67, - 65, 67, 66, - 58, 56, 70, - 56, 67, 70, - 67, 69, 68, - 68, 70, 67, - 69, 67, 65, - 70, 61, 58, - 68, 81, 70, - 61, 70, 81, - 71, 73, 84, - 71, 81, 68, - 72, 69, 65, - 65, 63, 72, - 68, 69, 73, - 69, 72, 82, - 73, 69, 82, - 44, 63, 39, - 63, 44, 83, - 72, 63, 83, - 73, 71, 68, -}; - - -// 0x07021FFC - 0x07022516 -static const PaintingData inside_castle_seg7_painting_texture_map_top_07021FFC[] = { - 85, // num mappings - // Format: - // mesh vtx ID, texture X, texture Y - 0, 2016, 72, - 1, 2016, 0, - 2, 1843, 0, - 3, 1843, 174, - 4, 2016, 276, - 5, 1671, 72, - 6, 1671, 0, - 8, 989, 72, - 7, 989, 0, - 10, 821, 0, - 9, 1162, 0, - 11, 821, 174, - 12, 989, 276, - 13, 1162, 174, - 14, 1330, 72, - 15, 1502, 0, - 16, 1671, 276, - 17, 1502, 174, - 18, 1330, 276, - 19, 1843, 992, - 20, 2016, 889, - 22, 2016, 685, - 21, 1843, 583, - 23, 1843, 787, - 24, 1671, 889, - 25, 1502, 992, - 26, 1502, 583, - 27, 1671, 685, - 28, 1671, 481, - 30, 1502, 787, - 29, 1330, 889, - 31, 1162, 992, - 32, 1330, 481, - 33, 1162, 583, - 34, 1330, 685, - 35, 1162, 787, - 36, 989, 889, - 37, 821, 992, - 39, 821, 583, - 38, 989, 685, - 40, 989, 481, - 41, 2016, 481, - 42, 1843, 378, - 43, 1502, 378, - 44, 1162, 378, - 45, 821, 378, - 87, 649, 72, - 88, -32, 0, - 90, 140, 0, - 89, -32, 72, - 92, 308, 72, - 91, 140, 174, - 94, 481, 174, - 93, 649, 276, - 95, 481, 0, - 96, 308, 276, - 97, 821, 787, - 98, 649, 889, - 99, 481, 992, - 102, 649, 481, - 101, 649, 685, - 100, 481, 583, - 103, 481, 787, - 104, 308, 889, - 105, 140, 992, - 108, 308, 481, - 107, 308, 685, - 106, 140, 583, - 110, -32, 889, - 109, 140, 787, - 111, -32, 481, - 112, 481, 378, - 113, 140, 378, - 141, 1330, 0, - 142, 2016, 992, - 144, 1671, 992, - 145, 1330, 992, - 146, 989, 992, - 147, 649, 0, - 148, -32, 276, - 149, 308, 0, - 150, 649, 992, - 151, 308, 992, - 152, -32, 685, - 153, -32, 992, - - 132, // num groups - // Grouped by 5 + one remainder group, - // = 15 vertices per group + a few extra triangles - 10, 7, 13, - 0, 1, 2, - 3, 0, 2, - 4, 0, 3, - 5, 2, 6, - 2, 5, 3, - 7, 8, 9, - 8, 7, 10, - 11, 7, 9, - 12, 7, 11, - 7, 12, 13, - 13, 14, 10, - 14, 73, 10, - 5, 6, 15, - 5, 16, 3, - 16, 5, 17, - 17, 5, 15, - 14, 15, 73, - 15, 14, 17, - 18, 14, 13, - 14, 18, 17, - 19, 74, 20, - 19, 20, 23, - 28, 27, 22, - 21, 41, 22, - 22, 23, 21, - 20, 21, 23, - 23, 24, 19, - 22, 27, 23, - 24, 23, 27, - 19, 24, 75, - 25, 75, 24, - 25, 24, 29, - 24, 27, 29, - 26, 29, 27, - 27, 28, 26, - 31, 36, 77, - 26, 34, 29, - 29, 30, 25, - 30, 29, 34, - 25, 30, 76, - 31, 76, 30, - 31, 30, 35, - 30, 34, 35, - 32, 34, 26, - 33, 35, 34, - 34, 32, 33, - 35, 36, 31, - 33, 39, 35, - 36, 35, 39, - 37, 36, 56, - 36, 39, 56, - 37, 77, 36, - 28, 16, 43, - 38, 56, 39, - 39, 40, 38, - 40, 39, 33, - 22, 41, 42, - 41, 4, 42, - 3, 42, 4, - 42, 28, 22, - 28, 42, 16, - 3, 16, 42, - 26, 28, 43, - 17, 43, 16, - 43, 32, 26, - 32, 43, 18, - 17, 18, 43, - 33, 32, 44, - 32, 18, 44, - 13, 44, 18, - 13, 12, 44, - 44, 40, 33, - 40, 44, 12, - 38, 40, 45, - 40, 12, 45, - 11, 45, 12, - 9, 46, 11, - 46, 9, 78, - 47, 49, 48, - 48, 49, 51, - 49, 79, 51, - 50, 80, 48, - 51, 50, 48, - 57, 56, 60, - 46, 53, 11, - 52, 46, 54, - 53, 46, 52, - 46, 78, 54, - 54, 50, 52, - 50, 54, 80, - 50, 55, 52, - 55, 50, 51, - 38, 60, 56, - 56, 57, 37, - 58, 57, 62, - 57, 60, 62, - 58, 81, 57, - 37, 57, 81, - 59, 60, 38, - 60, 59, 61, - 61, 62, 60, - 62, 63, 58, - 63, 62, 66, - 61, 66, 62, - 63, 66, 69, - 58, 63, 82, - 64, 82, 63, - 64, 63, 69, - 45, 59, 38, - 65, 66, 61, - 66, 65, 67, - 67, 69, 66, - 68, 69, 83, - 69, 68, 64, - 67, 83, 69, - 64, 68, 84, - 70, 83, 67, - 11, 53, 45, - 59, 45, 53, - 59, 53, 71, - 61, 59, 71, - 52, 71, 53, - 52, 55, 71, - 65, 71, 55, - 71, 65, 61, - 65, 55, 72, - 67, 65, 72, - 51, 72, 55, - 70, 72, 79, - 51, 79, 72, - 72, 70, 67, -}; - - -// 0x07022518 -static const PaintingData *const inside_castle_seg7_painting_texture_maps_07022518[] = { - inside_castle_seg7_painting_texture_map_bottom_07021AE0, - inside_castle_seg7_painting_texture_map_top_07021FFC, -}; - -UNUSED static const u64 castle_inside_unused_0 = 0x0; - - -// 0x07022528 - 0x07022540 - -// 0x07022540 - 0x07022558 - -// 0x07022558 - 0x07022598 -static const Vtx inside_castle_seg7_vertex_07022558[] = { - {{{ 0, 0, 0}, 0, { -32, 990}, {0x00, 0x00, 0x7f, 0xff}}}, - {{{ 614, 0, 0}, 0, { 6100, 990}, {0x00, 0x00, 0x7f, 0xff}}}, - {{{ 614, 614, 0}, 0, { 6100, -5142}, {0x00, 0x00, 0x7f, 0xff}}}, - {{{ 0, 614, 0}, 0, { -32, -5142}, {0x00, 0x00, 0x7f, 0xff}}}, -}; - -// 0x07022598 - 0x070225D8 -static const Vtx inside_castle_seg7_vertex_07022598[] = { - {{{ 0, 0, 0}, 0, { 0, 0}, {0x00, 0x00, 0x7f, 0xff}}}, - {{{ 614, 0, 0}, 0, { 0, 0}, {0x00, 0x00, 0x7f, 0xff}}}, - {{{ 614, 614, 0}, 0, { 0, 0}, {0x00, 0x00, 0x7f, 0xff}}}, - {{{ 0, 614, 0}, 0, { 0, 0}, {0x00, 0x00, 0x7f, 0xff}}}, -}; - -// TODO: this is unused -// 0x070225D8 - 0x07022610 -const Gfx inside_castle_seg7_dl_070225D8[] = { - gsDPPipeSync(), - gsDPSetCombineMode(G_CC_MODULATERGB, G_CC_MODULATERGB), - gsSPLightColor(LIGHT_1, 0xffffffff), - gsSPLightColor(LIGHT_2, 0x505050ff), - gsSPTexture(0xFFFF, 0xFFFF, 0, G_TX_RENDERTILE, G_ON), - gsSPVertex(inside_castle_seg7_vertex_07022558, 4, 0), - gsSPEndDisplayList(), -}; - -// TODO: this is unused -// 0x07022610 - 0x07022640 -const Gfx inside_castle_seg7_dl_07022610[] = { - gsSP1Triangle( 0, 1, 2, 0x0), - gsSP1Triangle( 0, 2, 3, 0x0), - gsSPTexture(0xFFFF, 0xFFFF, 0, G_TX_RENDERTILE, G_OFF), - gsDPPipeSync(), - gsDPSetCombineMode(G_CC_SHADE, G_CC_SHADE), - gsSPEndDisplayList(), -}; - -// 0x07022640 - 0x07022660 -static const Gfx inside_castle_seg7_painting_dl_07022640[] = { - gsDPTileSync(), - gsDPSetTile(G_IM_FMT_RGBA, G_IM_SIZ_16b, 8, 0, G_TX_RENDERTILE, 0, G_TX_WRAP | G_TX_NOMIRROR, 5, G_TX_NOLOD, G_TX_WRAP | G_TX_NOMIRROR, 5, G_TX_NOLOD), - gsDPSetTileSize(0, 0, 0, (32 - 1) << G_TEXTURE_IMAGE_FRAC, (32 - 1) << G_TEXTURE_IMAGE_FRAC), - gsSPEndDisplayList(), -}; - -// 0x07022660 - 0x07023042 -static const PaintingData inside_castle_seg7_painting_env_map_texture_map_07022660[] = { - 157, // num mappings - // Format: - // mesh vtx ID, texture X, texture Y - 0, 6100, -4832, - 1, 6100, -5142, - 2, 5582, -5142, - 3, 5582, -4526, - 4, 6100, -4218, - 5, 5070, -4832, - 6, 5070, -5142, - 7, 3030, -5142, - 8, 3030, -4832, - 9, 3540, -5142, - 10, 2520, -5142, - 11, 2520, -4526, - 12, 3030, -4218, - 13, 3540, -4526, - 14, 4050, -4832, - 15, 4560, -5142, - 16, 5070, -4218, - 17, 4560, -4526, - 18, 4050, -4218, - 19, 5582, -2074, - 20, 6100, -2380, - 21, 5582, -3300, - 22, 6100, -2994, - 23, 5582, -2686, - 24, 5070, -2380, - 25, 4560, -2074, - 26, 4560, -3300, - 27, 5070, -2994, - 28, 5070, -3606, - 29, 4050, -2380, - 30, 4560, -2686, - 31, 3540, -2074, - 32, 4050, -3606, - 33, 3540, -3300, - 34, 4050, -2994, - 35, 3540, -2686, - 36, 3030, -2380, - 37, 2520, -2074, - 38, 3030, -2994, - 39, 2520, -3300, - 40, 3030, -3606, - 41, 6100, -3606, - 42, 5582, -3912, - 43, 4560, -3912, - 44, 3540, -3912, - 45, 2520, -3912, - 46, 4050, -1768, - 47, 5070, -1768, - 48, 3030, -1768, - 49, 6100, 684, - 50, 6100, 990, - 51, 5582, 990, - 52, 5582, -236, - 53, 6100, 70, - 54, 5070, 684, - 55, 5582, 378, - 56, 4560, 990, - 57, 5070, 990, - 58, 4560, -236, - 59, 5070, 70, - 60, 5070, -542, - 61, 4050, 684, - 62, 4560, 378, - 63, 3540, 990, - 64, 4050, 990, - 65, 4050, 70, - 66, 3540, -236, - 67, 4050, -542, - 68, 3030, 684, - 69, 3540, 378, - 70, 2520, 990, - 71, 3030, 990, - 72, 2520, -236, - 73, 3030, 70, - 74, 3030, -542, - 75, 6100, -542, - 76, 5582, -1462, - 77, 6100, -1154, - 78, 5582, -848, - 79, 4560, -1462, - 80, 5070, -1154, - 81, 4560, -848, - 82, 3540, -1462, - 83, 4050, -1154, - 84, 3540, -848, - 85, 2520, -1462, - 86, 3030, -1154, - 87, 2010, -4832, - 88, 0, -5142, - 89, 0, -4832, - 90, 478, -5142, - 91, 478, -4526, - 92, 988, -4832, - 93, 2010, -4218, - 94, 1498, -4526, - 95, 1498, -5142, - 96, 988, -4218, - 97, 2520, -2686, - 98, 2010, -2380, - 99, 1498, -2074, - 100, 1498, -3300, - 101, 2010, -2994, - 102, 2010, -3606, - 103, 1498, -2686, - 104, 988, -2380, - 105, 478, -2074, - 106, 478, -3300, - 107, 988, -2994, - 108, 988, -3606, - 109, 478, -2686, - 110, 0, -2380, - 111, 0, -3606, - 112, 1498, -3912, - 113, 478, -3912, - 114, 1498, -1462, - 115, 988, -1768, - 116, 2010, -1768, - 117, 0, -1768, - 118, 478, -1462, - 119, 2010, 684, - 120, 2520, 378, - 121, 2010, 990, - 122, 1498, 990, - 123, 2010, -542, - 124, 2010, 70, - 125, 1498, -236, - 126, 988, 684, - 127, 1498, 378, - 128, 988, 990, - 129, 478, 990, - 130, 478, -236, - 131, 988, 70, - 132, 988, -542, - 133, 0, 684, - 134, 478, 378, - 135, 0, -542, - 136, 2520, -848, - 137, 2010, -1154, - 138, 1498, -848, - 139, 988, -1154, - 140, 478, -848, - 141, 4050, -5142, - 142, 6100, -2074, - 143, 6100, -1768, - 144, 5070, -2074, - 145, 4050, -2074, - 146, 3030, -2074, - 147, 2010, -5142, - 148, 0, -4218, - 149, 988, -5142, - 150, 2010, -2074, - 151, 988, -2074, - 152, 0, -2994, - 153, 0, -2074, - 154, 0, -1154, - 155, 0, 70, - 156, 0, 990, - -// inside_castle_seg7_painting_triangles_07022A10: - 264, // num groups - // Grouped by 5 + one remainder group, - // = 15 vertices per group + a few extra triangles - 8, 12, 13, - 0, 1, 2, - 3, 0, 2, - 4, 0, 3, - 5, 2, 6, - 2, 5, 3, - 7, 8, 9, - 8, 7, 10, - 11, 8, 10, - 12, 8, 11, - 9, 8, 13, - 13, 14, 9, - 14, 141, 9, - 5, 6, 15, - 5, 16, 3, - 16, 5, 17, - 17, 5, 15, - 14, 15, 141, - 15, 14, 17, - 18, 14, 13, - 14, 18, 17, - 19, 142, 20, - 19, 20, 23, - 28, 27, 21, - 21, 23, 22, - 22, 41, 21, - 20, 22, 23, - 23, 24, 19, - 21, 27, 23, - 24, 23, 27, - 25, 144, 24, - 19, 24, 144, - 24, 27, 30, - 25, 24, 30, - 26, 30, 27, - 27, 28, 26, - 36, 38, 97, - 26, 34, 30, - 29, 30, 34, - 30, 29, 25, - 25, 29, 145, - 31, 145, 29, - 31, 29, 35, - 29, 34, 35, - 32, 34, 26, - 33, 35, 34, - 34, 32, 33, - 33, 38, 35, - 35, 36, 31, - 36, 35, 38, - 37, 36, 97, - 37, 146, 36, - 31, 36, 146, - 28, 16, 43, - 38, 40, 39, - 39, 97, 38, - 40, 38, 33, - 21, 41, 42, - 41, 4, 42, - 3, 42, 4, - 42, 28, 21, - 28, 42, 16, - 3, 16, 42, - 26, 28, 43, - 17, 43, 16, - 43, 32, 26, - 32, 43, 18, - 17, 18, 43, - 33, 32, 44, - 32, 18, 44, - 13, 44, 18, - 44, 40, 33, - 13, 12, 44, - 40, 44, 12, - 39, 40, 45, - 40, 12, 45, - 48, 31, 146, - 11, 45, 12, - 25, 47, 144, - 46, 25, 145, - 47, 19, 144, - 19, 143, 142, - 31, 46, 145, - 60, 59, 52, - 49, 53, 55, - 50, 49, 51, - 51, 49, 55, - 52, 55, 53, - 53, 75, 52, - 54, 55, 59, - 52, 59, 55, - 55, 54, 51, - 54, 59, 62, - 56, 54, 62, - 57, 54, 56, - 54, 57, 51, - 58, 62, 59, - 59, 60, 58, - 68, 71, 63, - 61, 62, 65, - 58, 65, 62, - 62, 61, 56, - 61, 65, 69, - 63, 61, 69, - 64, 61, 63, - 61, 64, 56, - 65, 67, 66, - 66, 69, 65, - 67, 65, 58, - 68, 69, 73, - 69, 68, 63, - 66, 73, 69, - 68, 73, 120, - 70, 68, 120, - 71, 68, 70, - 72, 120, 73, - 73, 74, 72, - 74, 73, 66, - 75, 77, 78, - 52, 75, 78, - 76, 78, 77, - 77, 143, 76, - 76, 80, 78, - 60, 78, 80, - 78, 60, 52, - 46, 83, 79, - 58, 60, 81, - 60, 80, 81, - 79, 81, 80, - 80, 47, 79, - 47, 80, 76, - 81, 67, 58, - 67, 81, 83, - 79, 83, 81, - 66, 67, 84, - 67, 83, 84, - 82, 84, 83, - 83, 46, 82, - 84, 74, 66, - 82, 86, 84, - 74, 84, 86, - 74, 86, 136, - 72, 74, 136, - 85, 136, 86, - 86, 48, 85, - 48, 86, 82, - 25, 46, 79, - 79, 47, 25, - 82, 46, 31, - 19, 47, 76, - 76, 143, 19, - 31, 48, 82, - 37, 48, 146, - 85, 48, 37, - 10, 87, 11, - 87, 10, 147, - 92, 95, 149, - 88, 89, 90, - 89, 148, 91, - 90, 89, 91, - 91, 92, 90, - 92, 149, 90, - 93, 87, 94, - 87, 93, 11, - 94, 87, 95, - 87, 147, 95, - 95, 92, 94, - 96, 92, 91, - 92, 96, 94, - 39, 101, 97, - 97, 98, 37, - 98, 97, 101, - 99, 98, 103, - 99, 150, 98, - 37, 98, 150, - 98, 101, 103, - 100, 103, 101, - 101, 102, 100, - 102, 101, 39, - 100, 107, 103, - 103, 104, 99, - 104, 103, 107, - 105, 104, 109, - 105, 151, 104, - 99, 104, 151, - 104, 107, 109, - 106, 109, 107, - 107, 108, 106, - 108, 107, 100, - 109, 110, 105, - 106, 152, 109, - 110, 109, 152, - 105, 110, 153, - 111, 152, 106, - 11, 93, 45, - 102, 45, 93, - 45, 102, 39, - 102, 93, 112, - 100, 102, 112, - 94, 112, 93, - 112, 108, 100, - 108, 112, 96, - 94, 96, 112, - 106, 108, 113, - 108, 96, 113, - 91, 113, 96, - 91, 148, 113, - 113, 111, 106, - 111, 113, 148, - 114, 116, 99, - 99, 115, 114, - 115, 99, 151, - 99, 116, 150, - 72, 124, 120, - 116, 37, 150, - 37, 116, 85, - 117, 105, 153, - 105, 115, 151, - 105, 117, 118, - 118, 115, 105, - 119, 120, 124, - 120, 119, 70, - 119, 124, 127, - 119, 121, 70, - 121, 119, 122, - 122, 119, 127, - 123, 124, 72, - 124, 123, 125, - 125, 127, 124, - 126, 127, 131, - 127, 126, 122, - 125, 131, 127, - 126, 131, 134, - 128, 126, 129, - 129, 126, 134, - 126, 128, 122, - 136, 123, 72, - 130, 134, 131, - 131, 132, 130, - 132, 131, 125, - 133, 134, 155, - 134, 133, 129, - 130, 155, 134, - 133, 156, 129, - 135, 155, 130, - 123, 136, 137, - 85, 137, 136, - 139, 115, 118, - 123, 137, 138, - 125, 123, 138, - 114, 138, 137, - 137, 116, 114, - 116, 137, 85, - 114, 139, 138, - 132, 138, 139, - 138, 132, 125, - 132, 139, 140, - 130, 132, 140, - 115, 139, 114, - 118, 140, 139, - 135, 140, 154, - 118, 154, 140, - 140, 135, 130, - 117, 154, 118, -}; - - -// 0x07023044 - 0x07023048 -static const PaintingData *const inside_castle_seg7_painting_env_map_texture_maps_07023044[] = { - inside_castle_seg7_painting_env_map_texture_map_07022660, -}; - -UNUSED static const u64 castle_inside_unused_1 = 0x0; - - -// 0x07023050 - 0x070230B0 -static const Gfx inside_castle_seg7_painting_dl_07023050[] = { - gsSPDisplayList(inside_castle_seg7_dl_07021A48), - gsSPVertex(inside_castle_seg7_vertex_07021818, 8, 0), - gsDPSetTextureImage(G_IM_FMT_RGBA, G_IM_SIZ_16b, 1, inside_castle_seg7_texture_0700B800), - gsDPLoadSync(), - gsDPLoadBlock(G_TX_LOADTILE, 0, 0, 64 * 32 - 1, CALC_DXT(64, G_IM_SIZ_16b_BYTES)), - gsSPDisplayList(inside_castle_seg7_dl_07021A18), - gsDPSetTextureImage(G_IM_FMT_RGBA, G_IM_SIZ_16b, 1, inside_castle_seg7_texture_0700A800), - gsDPLoadSync(), - gsDPLoadBlock(G_TX_LOADTILE, 0, 0, 64 * 32 - 1, CALC_DXT(64, G_IM_SIZ_16b_BYTES)), - gsSPDisplayList(inside_castle_seg7_dl_07021A30), - gsSPDisplayList(inside_castle_seg7_dl_07021AA0), - gsSPEndDisplayList(), -}; - -// 0x070230B0 - 0x07023110 -static const Gfx inside_castle_seg7_painting_dl_070230B0[] = { - gsSPDisplayList(inside_castle_seg7_dl_07021A48), - gsSPVertex(inside_castle_seg7_vertex_07021818, 8, 0), - gsDPSetTextureImage(G_IM_FMT_RGBA, G_IM_SIZ_16b, 1, inside_castle_seg7_texture_0700D800), - gsDPLoadSync(), - gsDPLoadBlock(G_TX_LOADTILE, 0, 0, 64 * 32 - 1, CALC_DXT(64, G_IM_SIZ_16b_BYTES)), - gsSPDisplayList(inside_castle_seg7_dl_07021A18), - gsDPSetTextureImage(G_IM_FMT_RGBA, G_IM_SIZ_16b, 1, inside_castle_seg7_texture_0700C800), - gsDPLoadSync(), - gsDPLoadBlock(G_TX_LOADTILE, 0, 0, 64 * 32 - 1, CALC_DXT(64, G_IM_SIZ_16b_BYTES)), - gsSPDisplayList(inside_castle_seg7_dl_07021A30), - gsSPDisplayList(inside_castle_seg7_dl_07021AA0), - gsSPEndDisplayList(), -}; - -// 0x07023110 - 0x07023170 -static const Gfx inside_castle_seg7_painting_dl_07023110[] = { - gsSPDisplayList(inside_castle_seg7_dl_07021A48), - gsSPVertex(inside_castle_seg7_vertex_07021818, 8, 0), - gsDPSetTextureImage(G_IM_FMT_RGBA, G_IM_SIZ_16b, 1, inside_castle_seg7_texture_0700F800), - gsDPLoadSync(), - gsDPLoadBlock(G_TX_LOADTILE, 0, 0, 64 * 32 - 1, CALC_DXT(64, G_IM_SIZ_16b_BYTES)), - gsSPDisplayList(inside_castle_seg7_dl_07021A18), - gsDPSetTextureImage(G_IM_FMT_RGBA, G_IM_SIZ_16b, 1, inside_castle_seg7_texture_0700E800), - gsDPLoadSync(), - gsDPLoadBlock(G_TX_LOADTILE, 0, 0, 64 * 32 - 1, CALC_DXT(64, G_IM_SIZ_16b_BYTES)), - gsSPDisplayList(inside_castle_seg7_dl_07021A30), - gsSPDisplayList(inside_castle_seg7_dl_07021AA0), - gsSPEndDisplayList(), -}; - -// 0x07023170 - 0x070231D0 -static const Gfx inside_castle_seg7_painting_dl_07023170[] = { - gsSPDisplayList(inside_castle_seg7_dl_07021A48), - gsSPVertex(inside_castle_seg7_vertex_07021818, 8, 0), - gsDPSetTextureImage(G_IM_FMT_RGBA, G_IM_SIZ_16b, 1, inside_castle_seg7_texture_07011800), - gsDPLoadSync(), - gsDPLoadBlock(G_TX_LOADTILE, 0, 0, 64 * 32 - 1, CALC_DXT(64, G_IM_SIZ_16b_BYTES)), - gsSPDisplayList(inside_castle_seg7_dl_07021A18), - gsDPSetTextureImage(G_IM_FMT_RGBA, G_IM_SIZ_16b, 1, inside_castle_seg7_texture_07010800), - gsDPLoadSync(), - gsDPLoadBlock(G_TX_LOADTILE, 0, 0, 64 * 32 - 1, CALC_DXT(64, G_IM_SIZ_16b_BYTES)), - gsSPDisplayList(inside_castle_seg7_dl_07021A30), - gsSPDisplayList(inside_castle_seg7_dl_07021AA0), - gsSPEndDisplayList(), -}; - -// 0x070231D0 - 0x07023230 -static const Gfx inside_castle_seg7_painting_dl_070231D0[] = { - gsSPDisplayList(inside_castle_seg7_dl_07021A48), - gsSPVertex(inside_castle_seg7_vertex_07021818, 8, 0), - gsDPSetTextureImage(G_IM_FMT_RGBA, G_IM_SIZ_16b, 1, inside_castle_seg7_texture_07012800), - gsDPLoadSync(), - gsDPLoadBlock(G_TX_LOADTILE, 0, 0, 64 * 32 - 1, CALC_DXT(64, G_IM_SIZ_16b_BYTES)), - gsSPDisplayList(inside_castle_seg7_dl_07021A18), - gsDPSetTextureImage(G_IM_FMT_RGBA, G_IM_SIZ_16b, 1, inside_castle_seg7_texture_07013800), - gsDPLoadSync(), - gsDPLoadBlock(G_TX_LOADTILE, 0, 0, 64 * 32 - 1, CALC_DXT(64, G_IM_SIZ_16b_BYTES)), - gsSPDisplayList(inside_castle_seg7_dl_07021A30), - gsSPDisplayList(inside_castle_seg7_dl_07021AA0), - gsSPEndDisplayList(), -}; - -// 0x07023230 - 0x07023290 -static const Gfx inside_castle_seg7_painting_dl_07023230[] = { - gsSPDisplayList(inside_castle_seg7_dl_07021A48), - gsSPVertex(inside_castle_seg7_vertex_07021818, 8, 0), - gsDPSetTextureImage(G_IM_FMT_RGBA, G_IM_SIZ_16b, 1, inside_castle_seg7_texture_07015800), - gsDPLoadSync(), - gsDPLoadBlock(G_TX_LOADTILE, 0, 0, 64 * 32 - 1, CALC_DXT(64, G_IM_SIZ_16b_BYTES)), - gsSPDisplayList(inside_castle_seg7_dl_07021A18), - gsDPSetTextureImage(G_IM_FMT_RGBA, G_IM_SIZ_16b, 1, inside_castle_seg7_texture_07014800), - gsDPLoadSync(), - gsDPLoadBlock(G_TX_LOADTILE, 0, 0, 64 * 32 - 1, CALC_DXT(64, G_IM_SIZ_16b_BYTES)), - gsSPDisplayList(inside_castle_seg7_dl_07021A30), - gsSPDisplayList(inside_castle_seg7_dl_07021AA0), - gsSPEndDisplayList(), -}; - -// 0x07023290 - 0x070232F0 -static const Gfx inside_castle_seg7_painting_dl_07023290[] = { - gsSPDisplayList(inside_castle_seg7_dl_07021A48), - gsSPVertex(inside_castle_seg7_vertex_07021818, 8, 0), - gsDPSetTextureImage(G_IM_FMT_RGBA, G_IM_SIZ_16b, 1, inside_castle_seg7_texture_07018800), - gsDPLoadSync(), - gsDPLoadBlock(G_TX_LOADTILE, 0, 0, 64 * 32 - 1, CALC_DXT(64, G_IM_SIZ_16b_BYTES)), - gsSPDisplayList(inside_castle_seg7_dl_07021A18), - gsDPSetTextureImage(G_IM_FMT_RGBA, G_IM_SIZ_16b, 1, inside_castle_seg7_texture_07017800), - gsDPLoadSync(), - gsDPLoadBlock(G_TX_LOADTILE, 0, 0, 64 * 32 - 1, CALC_DXT(64, G_IM_SIZ_16b_BYTES)), - gsSPDisplayList(inside_castle_seg7_dl_07021A30), - gsSPDisplayList(inside_castle_seg7_dl_07021AA0), - gsSPEndDisplayList(), -}; - -// 0x070232F0 - 0x07023350 -static const Gfx inside_castle_seg7_painting_dl_070232F0[] = { - gsSPDisplayList(inside_castle_seg7_dl_07021A48), - gsSPVertex(inside_castle_seg7_vertex_07021818, 8, 0), - gsDPSetTextureImage(G_IM_FMT_RGBA, G_IM_SIZ_16b, 1, inside_castle_seg7_texture_0701A800), - gsDPLoadSync(), - gsDPLoadBlock(G_TX_LOADTILE, 0, 0, 64 * 32 - 1, CALC_DXT(64, G_IM_SIZ_16b_BYTES)), - gsSPDisplayList(inside_castle_seg7_dl_07021A18), - gsDPSetTextureImage(G_IM_FMT_RGBA, G_IM_SIZ_16b, 1, inside_castle_seg7_texture_07019800), - gsDPLoadSync(), - gsDPLoadBlock(G_TX_LOADTILE, 0, 0, 64 * 32 - 1, CALC_DXT(64, G_IM_SIZ_16b_BYTES)), - gsSPDisplayList(inside_castle_seg7_dl_07021A30), - gsSPDisplayList(inside_castle_seg7_dl_07021AA0), - gsSPEndDisplayList(), -}; - -// 0x07023350 - 0x070233B0 -static const Gfx inside_castle_seg7_painting_dl_07023350[] = { - gsSPDisplayList(inside_castle_seg7_dl_07021A48), - gsSPVertex(inside_castle_seg7_vertex_07021818, 8, 0), - gsDPSetTextureImage(G_IM_FMT_RGBA, G_IM_SIZ_16b, 1, inside_castle_seg7_texture_0701C800), - gsDPLoadSync(), - gsDPLoadBlock(G_TX_LOADTILE, 0, 0, 64 * 32 - 1, CALC_DXT(64, G_IM_SIZ_16b_BYTES)), - gsSPDisplayList(inside_castle_seg7_dl_07021A18), - gsDPSetTextureImage(G_IM_FMT_RGBA, G_IM_SIZ_16b, 1, inside_castle_seg7_texture_0701B800), - gsDPLoadSync(), - gsDPLoadBlock(G_TX_LOADTILE, 0, 0, 64 * 32 - 1, CALC_DXT(64, G_IM_SIZ_16b_BYTES)), - gsSPDisplayList(inside_castle_seg7_dl_07021A30), - gsSPDisplayList(inside_castle_seg7_dl_07021AA0), - gsSPEndDisplayList(), -}; - -// 0x070233B0 - 0x07023410 -static const Gfx inside_castle_seg7_painting_dl_070233B0[] = { - gsSPDisplayList(inside_castle_seg7_dl_07021A48), - gsSPVertex(inside_castle_seg7_vertex_07021818, 8, 0), - gsDPSetTextureImage(G_IM_FMT_RGBA, G_IM_SIZ_16b, 1, inside_castle_seg7_texture_0701E800), - gsDPLoadSync(), - gsDPLoadBlock(G_TX_LOADTILE, 0, 0, 64 * 32 - 1, CALC_DXT(64, G_IM_SIZ_16b_BYTES)), - gsSPDisplayList(inside_castle_seg7_dl_07021A18), - gsDPSetTextureImage(G_IM_FMT_RGBA, G_IM_SIZ_16b, 1, inside_castle_seg7_texture_0701D800), - gsDPLoadSync(), - gsDPLoadBlock(G_TX_LOADTILE, 0, 0, 64 * 32 - 1, CALC_DXT(64, G_IM_SIZ_16b_BYTES)), - gsSPDisplayList(inside_castle_seg7_dl_07021A30), - gsSPDisplayList(inside_castle_seg7_dl_07021AA0), - gsSPEndDisplayList(), -}; - -// 0x07023410 - 0x070234C0 -static const Gfx inside_castle_seg7_painting_dl_07023410[] = { - gsDPPipeSync(), - gsDPSetCombineMode(G_CC_MODULATERGB, G_CC_MODULATERGB), - gsSPClearGeometryMode(G_LIGHTING), - gsDPSetTile(G_IM_FMT_RGBA, G_IM_SIZ_16b, 0, 0, G_TX_LOADTILE, 0, G_TX_WRAP | G_TX_NOMIRROR, G_TX_NOMASK, G_TX_NOLOD, G_TX_WRAP | G_TX_NOMIRROR, G_TX_NOMASK, G_TX_NOLOD), - gsDPTileSync(), - gsDPSetTile(G_IM_FMT_RGBA, G_IM_SIZ_16b, 16, 0, G_TX_RENDERTILE, 0, G_TX_CLAMP, 5, G_TX_NOLOD, G_TX_CLAMP, 6, G_TX_NOLOD), - gsDPSetTileSize(0, 0, 0, (64 - 1) << G_TEXTURE_IMAGE_FRAC, (32 - 1) << G_TEXTURE_IMAGE_FRAC), - gsSPTexture(0xFFFF, 0xFFFF, 0, G_TX_RENDERTILE, G_ON), - gsSPVertex(inside_castle_seg7_vertex_07021898, 8, 0), - gsDPSetTextureImage(G_IM_FMT_RGBA, G_IM_SIZ_16b, 1, inside_castle_seg7_texture_07020800), - gsDPLoadSync(), - gsDPLoadBlock(G_TX_LOADTILE, 0, 0, 64 * 32 - 1, CALC_DXT(64, G_IM_SIZ_16b_BYTES)), - gsSPDisplayList(inside_castle_seg7_dl_07021A18), - gsDPSetTextureImage(G_IM_FMT_RGBA, G_IM_SIZ_16b, 1, inside_castle_seg7_texture_0701F800), - gsDPLoadSync(), - gsDPLoadBlock(G_TX_LOADTILE, 0, 0, 64 * 32 - 1, CALC_DXT(64, G_IM_SIZ_16b_BYTES)), - gsSPDisplayList(inside_castle_seg7_dl_07021A30), +static const Gfx inside_castle_seg7_dl_painting_textured_shaded_end[] = { gsSPTexture(0xFFFF, 0xFFFF, 0, G_TX_RENDERTILE, G_OFF), gsDPPipeSync(), gsDPSetCombineMode(G_CC_SHADE, G_CC_SHADE), - gsSPSetGeometryMode(G_LIGHTING), gsSPEndDisplayList(), }; // 0x070234C0 - 0x07023520 -const Gfx inside_castle_seg7_dl_070234C0[] = { - gsSPDisplayList(inside_castle_seg7_dl_07021A48), - gsSPVertex(inside_castle_seg7_vertex_07021918, 8, 0), +const Gfx inside_castle_seg7_dl_ccm_fake_painting_1[] = { + gsSPDisplayList(inside_castle_seg7_dl_painting_textured_shaded_begin), + gsSPVertex(inside_castle_seg7_vertex_painting_ccm_fake_1, 8, 0), gsDPSetTextureImage(G_IM_FMT_RGBA, G_IM_SIZ_16b, 1, inside_castle_seg7_texture_0700D800), gsDPLoadSync(), gsDPLoadBlock(G_TX_LOADTILE, 0, 0, 64 * 32 - 1, CALC_DXT(64, G_IM_SIZ_16b_BYTES)), - gsSPDisplayList(inside_castle_seg7_dl_07021A18), + gsSPDisplayList(inside_castle_seg7_sub_dl_painting_bottom), gsDPSetTextureImage(G_IM_FMT_RGBA, G_IM_SIZ_16b, 1, inside_castle_seg7_texture_0700C800), gsDPLoadSync(), gsDPLoadBlock(G_TX_LOADTILE, 0, 0, 64 * 32 - 1, CALC_DXT(64, G_IM_SIZ_16b_BYTES)), - gsSPDisplayList(inside_castle_seg7_dl_07021A30), - gsSPDisplayList(inside_castle_seg7_dl_07021AA0), + gsSPDisplayList(inside_castle_seg7_sub_dl_painting_top), + gsSPDisplayList(inside_castle_seg7_dl_painting_textured_shaded_end), gsSPEndDisplayList(), }; // 0x07023520 - 0x07023580 -const Gfx inside_castle_seg7_dl_07023520[] = { - gsSPDisplayList(inside_castle_seg7_dl_07021A48), - gsSPVertex(inside_castle_seg7_vertex_07021998, 8, 0), +const Gfx inside_castle_seg7_dl_ccm_fake_painting_2[] = { + gsSPDisplayList(inside_castle_seg7_dl_painting_textured_shaded_begin), + gsSPVertex(inside_castle_seg7_vertex_painting_ccm_fake_2, 8, 0), gsDPSetTextureImage(G_IM_FMT_RGBA, G_IM_SIZ_16b, 1, inside_castle_seg7_texture_0700D800), gsDPLoadSync(), gsDPLoadBlock(G_TX_LOADTILE, 0, 0, 64 * 32 - 1, CALC_DXT(64, G_IM_SIZ_16b_BYTES)), - gsSPDisplayList(inside_castle_seg7_dl_07021A18), + gsSPDisplayList(inside_castle_seg7_sub_dl_painting_bottom), gsDPSetTextureImage(G_IM_FMT_RGBA, G_IM_SIZ_16b, 1, inside_castle_seg7_texture_0700C800), gsDPLoadSync(), gsDPLoadBlock(G_TX_LOADTILE, 0, 0, 64 * 32 - 1, CALC_DXT(64, G_IM_SIZ_16b_BYTES)), - gsSPDisplayList(inside_castle_seg7_dl_07021A30), - gsSPDisplayList(inside_castle_seg7_dl_07021AA0), - gsSPEndDisplayList(), -}; - -// 0x07023580 - 0x070235B8 -static const Gfx inside_castle_seg7_painting_dl_07023580[] = { - gsDPPipeSync(), - gsSPLightColor(LIGHT_1, 0x6464ffff), - gsSPLightColor(LIGHT_2, 0x404080ff), - gsSPVertex(inside_castle_seg7_vertex_07022598, 4, 0), - gsSP1Triangle( 0, 1, 2, 0x0), - gsSP1Triangle( 0, 2, 3, 0x0), + gsSPDisplayList(inside_castle_seg7_sub_dl_painting_top), + gsSPDisplayList(inside_castle_seg7_dl_painting_textured_shaded_end), gsSPEndDisplayList(), }; -// 0x070235B8 - 0x070235C0 -static const Gfx inside_castle_seg7_painting_dl_070235B8[] = { - gsSPBranchList(inside_castle_seg7_painting_dl_07023580), -}; +/// - PAINTING_ID_CASTLE_BOB - -ALIGNED8 static const Texture *const inside_castle_seg7_painting_textures_070235C0[] = { - inside_castle_seg7_texture_0700B800, inside_castle_seg7_texture_0700A800, +ALIGNED8 static const Texture *const inside_castle_seg7_painting_textures_bob[] = { + inside_castle_seg7_texture_0700B800, + inside_castle_seg7_texture_0700A800, }; -ALIGNED8 static const Texture *const inside_castle_seg7_painting_textures_070235C8[] = { - inside_castle_seg7_texture_0700D800, inside_castle_seg7_texture_0700C800, +const struct PaintingImage bob_painting = { + .textureArray = inside_castle_seg7_painting_textures_bob, + .imageCount = ARRAY_COUNT(inside_castle_seg7_painting_textures_bob), + .textureWidth = 64, + .textureHeight = 32, + .imageType = PAINTING_IMAGE_TYPE_TEXTURE, + .rippleTrigger = RIPPLE_TRIGGER_PROXIMITY, + .shaded = TRUE, + .alpha = 0xFF, + .sizeX = 614.0f, + .sizeY = 614.0f, }; -ALIGNED8 static const Texture *const inside_castle_seg7_painting_textures_070235D0[] = { - inside_castle_seg7_texture_0700F800, inside_castle_seg7_texture_0700E800, -}; +/// - PAINTING_ID_CASTLE_CCM - -ALIGNED8 static const Texture *const inside_castle_seg7_painting_textures_070235D8[] = { - inside_castle_seg7_texture_07011800, inside_castle_seg7_texture_07010800, +ALIGNED8 static const Texture *const inside_castle_seg7_painting_textures_ccm[] = { + inside_castle_seg7_texture_0700D800, + inside_castle_seg7_texture_0700C800, }; -ALIGNED8 static const Texture *const inside_castle_seg7_painting_textures_070235E0[] = { - inside_castle_seg7_texture_07012800, inside_castle_seg7_texture_07013800, +const struct PaintingImage ccm_painting = { + .textureArray = inside_castle_seg7_painting_textures_ccm, + .imageCount = ARRAY_COUNT(inside_castle_seg7_painting_textures_ccm), + .textureWidth = 64, + .textureHeight = 32, + .imageType = PAINTING_IMAGE_TYPE_TEXTURE, + .rippleTrigger = RIPPLE_TRIGGER_PROXIMITY, + .shaded = TRUE, + .alpha = 0xFF, + .sizeX = 614.0f, + .sizeY = 614.0f, }; -ALIGNED8 static const Texture *const inside_castle_seg7_painting_textures_070235E8[] = { - inside_castle_seg7_texture_07015800, inside_castle_seg7_texture_07014800, -}; +/// - PAINTING_ID_CASTLE_WF - -ALIGNED8 static const Texture *const inside_castle_seg7_painting_textures_070235F0[] = { - inside_castle_seg7_texture_07016800, +ALIGNED8 static const Texture *const inside_castle_seg7_painting_textures_wf[] = { + inside_castle_seg7_texture_0700F800, + inside_castle_seg7_texture_0700E800, }; -ALIGNED8 static const Texture *const inside_castle_seg7_painting_textures_070235F4[] = { - inside_castle_seg7_texture_07017000, +const struct PaintingImage wf_painting = { + .textureArray = inside_castle_seg7_painting_textures_wf, + .imageCount = ARRAY_COUNT(inside_castle_seg7_painting_textures_wf), + .textureWidth = 64, + .textureHeight = 32, + .imageType = PAINTING_IMAGE_TYPE_TEXTURE, + .rippleTrigger = RIPPLE_TRIGGER_PROXIMITY, + .shaded = TRUE, + .alpha = 0xFF, + .sizeX = 614.0f, + .sizeY = 614.0f, }; -ALIGNED8 static const Texture *const inside_castle_seg7_painting_textures_070235F8[] = { - inside_castle_seg7_texture_07018800, inside_castle_seg7_texture_07017800, -}; +/// - PAINTING_ID_CASTLE_JRB - -ALIGNED8 static const Texture *const inside_castle_seg7_painting_textures_07023600[] = { - inside_castle_seg7_texture_0701A800, inside_castle_seg7_texture_07019800, +ALIGNED8 static const Texture *const inside_castle_seg7_painting_textures_jrb[] = { + inside_castle_seg7_texture_07011800, + inside_castle_seg7_texture_07010800, }; -ALIGNED8 static const Texture *const inside_castle_seg7_painting_textures_07023608[] = { - inside_castle_seg7_texture_0701C800, inside_castle_seg7_texture_0701B800, +const struct PaintingImage jrb_painting = { + .textureArray = inside_castle_seg7_painting_textures_jrb, + .imageCount = ARRAY_COUNT(inside_castle_seg7_painting_textures_jrb), + .textureWidth = 64, + .textureHeight = 32, + .imageType = PAINTING_IMAGE_TYPE_TEXTURE, + .rippleTrigger = RIPPLE_TRIGGER_PROXIMITY, + .shaded = TRUE, + .alpha = 0xFF, + .sizeX = 614.0f, + .sizeY = 614.0f, }; -ALIGNED8 static const Texture *const inside_castle_seg7_painting_textures_07023610[] = { - inside_castle_seg7_texture_0701E800, inside_castle_seg7_texture_0701D800, -}; +/// - PAINTING_ID_CASTLE_LLL - -ALIGNED8 static const Texture *const inside_castle_seg7_painting_textures_07023618[] = { - inside_castle_seg7_texture_07020800, inside_castle_seg7_texture_0701F800, +ALIGNED8 static const Texture *const inside_castle_seg7_painting_textures_lll[] = { + inside_castle_seg7_texture_07012800, + inside_castle_seg7_texture_07013800, }; -// 0x07023620 - 0x07023698 -struct Painting bob_painting = { - /* id */ 0x0000, - /* Image Count */ 0x02, - /* Texture Type */ PAINTING_IMAGE, - /* Floor Status */ 0x00, 0x00, 0x00 /* which of the painting's nearby special floors Mario's on */, - /* Ripple Status */ 0x00, - /* Rotation */ 0.0f, 90.0f, - /* Position */ -5222.4f, 409.6f, -153.6f, - /* curr passive entry */ - /* Ripple Magnitude */ 0.0f, 20.0f, 80.0f, - /* Ripple Decay */ 1.0f, 0.9608f, 0.9524f, - /* Ripple Rate */ 0.0f, 0.24f, 0.14f, - /* Ripple Dispersion */ 0.0f, 40.0f, 30.0f, - /* Curr Ripple Timer */ 0.0f, - /* Curr Ripple x, y */ 0.0f, 0.0f, - /* Normal DList */ inside_castle_seg7_painting_dl_07023050, - /* Texture Maps */ inside_castle_seg7_painting_texture_maps_07022518, - /* Textures */ inside_castle_seg7_painting_textures_070235C0, - /* Texture w, h */ 64, 32, - /* Ripple DList */ inside_castle_seg7_painting_dl_07021AC0, - /* Ripple Trigger */ RIPPLE_TRIGGER_PROXIMITY, - /* Alpha */ 0xFF, - /* Mario Below */ 0x00, 0x00, 0x00, /* Whether or not Mario is below the painting */ - /* Size */ 614.0f, +const struct PaintingImage lll_painting = { + .textureArray = inside_castle_seg7_painting_textures_lll, + .imageCount = ARRAY_COUNT(inside_castle_seg7_painting_textures_lll), + .textureWidth = 64, + .textureHeight = 32, + .imageType = PAINTING_IMAGE_TYPE_TEXTURE, + .rippleTrigger = RIPPLE_TRIGGER_PROXIMITY, + .shaded = TRUE, + .alpha = 0xFF, + .sizeX = 614.0f, + .sizeY = 614.0f, }; -// 0x07023698 - 0x07023710 -struct Painting ccm_painting = { - /* id */ 0x0001, - /* Image Count */ 0x02, - /* Texture Type */ PAINTING_IMAGE, - /* Floor Status */ 0x00, 0x00, 0x00 /* which of the painting's nearby special floors Mario's on */, - /* Ripple Status */ 0x00, - /* Rotation */ 0.0f, 0.0f, - /* Position */ -2611.2f, -307.2f, -4352.0f, - /* curr passive entry */ - /* Ripple Magnitude */ 0.0f, 20.0f, 80.0f, - /* Ripple Decay */ 1.0f, 0.9608f, 0.9524f, - /* Ripple Rate */ 0.0f, 0.24f, 0.14f, - /* Ripple Dispersion */ 0.0f, 40.0f, 30.0f, - /* Curr Ripple Timer */ 0.0f, - /* Curr Ripple x, y */ 0.0f, 0.0f, - /* Normal DList */ inside_castle_seg7_painting_dl_070230B0, - /* Texture Maps */ inside_castle_seg7_painting_texture_maps_07022518, - /* Textures */ inside_castle_seg7_painting_textures_070235C8, - /* Texture w, h */ 64, 32, - /* Ripple DList */ inside_castle_seg7_painting_dl_07021AC0, - /* Ripple Trigger */ RIPPLE_TRIGGER_PROXIMITY, - /* Alpha */ 0xFF, - /* Mario Below */ 0x00, 0x00, 0x00, /* Whether or not Mario is below the painting */ - /* Size */ 614.0f, -}; +/// - PAINTING_ID_CASTLE_SSL - -// 0x07023710 - 0x07023788 -struct Painting wf_painting = { - /* id */ 0x0002, - /* Image Count */ 0x02, - /* Texture Type */ PAINTING_IMAGE, - /* Floor Status */ 0x00, 0x00, 0x00 /* which of the painting's nearby special floors Mario's on */, - /* Ripple Status */ 0x00, - /* Rotation */ 0.0f, 0.0f, - /* Position */ -51.2f, -204.8f, -4505.6f, - /* curr passive entry */ - /* Ripple Magnitude */ 0.0f, 20.0f, 80.0f, - /* Ripple Decay */ 1.0f, 0.9608f, 0.9524f, - /* Ripple Rate */ 0.0f, 0.24f, 0.14f, - /* Ripple Dispersion */ 0.0f, 40.0f, 30.0f, - /* Curr Ripple Timer */ 0.0f, - /* Curr Ripple x, y */ 0.0f, 0.0f, - /* Normal DList */ inside_castle_seg7_painting_dl_07023110, - /* Texture Maps */ inside_castle_seg7_painting_texture_maps_07022518, - /* Textures */ inside_castle_seg7_painting_textures_070235D0, - /* Texture w, h */ 64, 32, - /* Ripple DList */ inside_castle_seg7_painting_dl_07021AC0, - /* Ripple Trigger */ RIPPLE_TRIGGER_PROXIMITY, - /* Alpha */ 0xFF, - /* Mario Below */ 0x00, 0x00, 0x00, /* Whether or not Mario is below the painting */ - /* Size */ 614.0f, +ALIGNED8 static const Texture *const inside_castle_seg7_painting_textures_ssl[] = { + inside_castle_seg7_texture_07015800, + inside_castle_seg7_texture_07014800, }; -// 0x07023788 - 0x07023800 -struct Painting jrb_painting = { - /* id */ 0x0003, - /* Image Count */ 0x02, - /* Texture Type */ PAINTING_IMAGE, - /* Floor Status */ 0x00, 0x00, 0x00 /* which of the painting's nearby special floors Mario's on */, - /* Ripple Status */ 0x00, - /* Rotation */ 0.0f, 270.0f, - /* Position */ 4300.8f, 409.6f, -537.6f, - /* curr passive entry */ - /* Ripple Magnitude */ 0.0f, 20.0f, 80.0f, - /* Ripple Decay */ 1.0f, 0.9608f, 0.9524f, - /* Ripple Rate */ 0.0f, 0.24f, 0.14f, - /* Ripple Dispersion */ 0.0f, 40.0f, 30.0f, - /* Curr Ripple Timer */ 0.0f, - /* Curr Ripple x, y */ 0.0f, 0.0f, - /* Normal DList */ inside_castle_seg7_painting_dl_07023170, - /* Texture Maps */ inside_castle_seg7_painting_texture_maps_07022518, - /* Textures */ inside_castle_seg7_painting_textures_070235D8, - /* Texture w, h */ 64, 32, - /* Ripple DList */ inside_castle_seg7_painting_dl_07021AC0, - /* Ripple Trigger */ RIPPLE_TRIGGER_PROXIMITY, - /* Alpha */ 0xFF, - /* Mario Below */ 0x00, 0x00, 0x00, /* Whether or not Mario is below the painting */ - /* Size */ 614.0f, +const struct PaintingImage ssl_painting = { + .textureArray = inside_castle_seg7_painting_textures_ssl, + .imageCount = ARRAY_COUNT(inside_castle_seg7_painting_textures_ssl), + .textureWidth = 64, + .textureHeight = 32, + .imageType = PAINTING_IMAGE_TYPE_TEXTURE, + .rippleTrigger = RIPPLE_TRIGGER_PROXIMITY, + .shaded = TRUE, + .alpha = 0xFF, + .sizeX = 614.0f, + .sizeY = 614.0f, }; -// 0x07023800 - 0x07023878 -struct Painting lll_painting = { - /* id */ 0x0004, - /* Image Count */ 0x02, - /* Texture Type */ PAINTING_IMAGE, - /* Floor Status */ 0x00, 0x00, 0x00 /* which of the painting's nearby special floors Mario's on */, - /* Ripple Status */ 0x00, - /* Rotation */ 0.0f, 0.0f, - /* Position */ -1689.6f, -1126.4f, -3942.4f, - /* curr passive entry */ - /* Ripple Magnitude */ 0.0f, 20.0f, 80.0f, - /* Ripple Decay */ 1.0f, 0.9608f, 0.9524f, - /* Ripple Rate */ 0.0f, 0.24f, 0.14f, - /* Ripple Dispersion */ 0.0f, 40.0f, 30.0f, - /* Curr Ripple Timer */ 0.0f, - /* Curr Ripple x, y */ 0.0f, 0.0f, - /* Normal DList */ inside_castle_seg7_painting_dl_070231D0, - /* Texture Maps */ inside_castle_seg7_painting_texture_maps_07022518, - /* Textures */ inside_castle_seg7_painting_textures_070235E0, - /* Texture w, h */ 64, 32, - /* Ripple DList */ inside_castle_seg7_painting_dl_07021AC0, - /* Ripple Trigger */ RIPPLE_TRIGGER_PROXIMITY, - /* Alpha */ 0xFF, - /* Mario Below */ 0x00, 0x00, 0x00, /* Whether or not Mario is below the painting */ - /* Size */ 614.0f, -}; +/// - PAINTING_ID_CASTLE_HMC - -// 0x07023878 - 0x070238F0 -struct Painting ssl_painting = { - /* id */ 0x0005, - /* Image Count */ 0x02, - /* Texture Type */ PAINTING_IMAGE, - /* Floor Status */ 0x00, 0x00, 0x00 /* which of the painting's nearby special floors Mario's on */, - /* Ripple Status */ 0x00, - /* Rotation */ 0.0f, 180.0f, - /* Position */ -2611.2f, -1177.6f, -1075.2f, - /* curr passive entry */ - /* Ripple Magnitude */ 0.0f, 20.0f, 80.0f, - /* Ripple Decay */ 1.0f, 0.9608f, 0.9524f, - /* Ripple Rate */ 0.0f, 0.24f, 0.14f, - /* Ripple Dispersion */ 0.0f, 40.0f, 30.0f, - /* Curr Ripple Timer */ 0.0f, - /* Curr Ripple x, y */ 0.0f, 0.0f, - /* Normal DList */ inside_castle_seg7_painting_dl_07023230, - /* Texture Maps */ inside_castle_seg7_painting_texture_maps_07022518, - /* Textures */ inside_castle_seg7_painting_textures_070235E8, - /* Texture w, h */ 64, 32, - /* Ripple DList */ inside_castle_seg7_painting_dl_07021AC0, - /* Ripple Trigger */ RIPPLE_TRIGGER_PROXIMITY, - /* Alpha */ 0xFF, - /* Mario Below */ 0x00, 0x00, 0x00, /* Whether or not Mario is below the painting */ - /* Size */ 614.0f, +ALIGNED8 static const Texture *const inside_castle_seg7_painting_textures_hmc_env[] = { + inside_castle_seg7_texture_07016800, }; -// 0x070238F0 - 0x07023968 -struct Painting hmc_painting = { - /* id */ 0x000E, - /* Image Count */ 0x01, - /* Texture Type */ PAINTING_ENV_MAP, - /* Floor Status */ 0x00, 0x00, 0x00 /* which of the painting's nearby special floors Mario's on */, - /* Ripple Status */ 0x00, - /* Rotation */ 270.0f, 0.0f, - /* Position */ 2099.2f, -1484.8f, -2278.4f, - /* curr passive entry */ - /* Ripple Magnitude */ 0.0f, 10.0f, 30.0f, - /* Ripple Decay */ 1.0f, 1.0f, 0.98f, - /* Ripple Rate */ 0.0f, 0.05f, 0.05f, - /* Ripple Dispersion */ 0.0f, 15.0f, 15.0f, - /* Curr Ripple Timer */ 0.0f, - /* Curr Ripple x, y */ 0.0f, 0.0f, - /* Normal DList */ inside_castle_seg7_painting_dl_07023580, - /* Texture Maps */ inside_castle_seg7_painting_env_map_texture_maps_07023044, - /* Textures */ inside_castle_seg7_painting_textures_070235F0, - /* Texture w, h */ 32, 32, - /* Ripple DList */ inside_castle_seg7_painting_dl_07022640, - /* Ripple Trigger */ RIPPLE_TRIGGER_CONTINUOUS, - /* Alpha */ 0xFF, - /* Mario Below */ 0x00, 0x00, 0x00, /* Whether or not Mario is below the painting */ - /* Size */ 768.0f, +const struct PaintingImage hmc_painting = { + .textureArray = inside_castle_seg7_painting_textures_hmc_env, + .imageCount = ARRAY_COUNT(inside_castle_seg7_painting_textures_hmc_env), + .textureWidth = 32, + .textureHeight = 32, + .imageType = PAINTING_IMAGE_TYPE_ENV_MAP, + .rippleTrigger = RIPPLE_TRIGGER_CONTINUOUS, + .shaded = TRUE, + .alpha = 0xFF, + .sizeX = 768.0f, + .sizeY = 768.0f, }; -// 0x07023968 - 0x070239E0 -struct Painting ddd_painting = { - /* id */ 0x0007, - /* Image Count */ 0x01, - /* Texture Type */ PAINTING_ENV_MAP, - /* Floor Status */ 0x00, 0x00, 0x00 /* which of the painting's nearby special floors Mario's on */, - /* Ripple Status */ 0x00, - /* Rotation */ 0.0f, 270.0f, - /* Position */ 3456.0f, -1075.2f, 1587.2f, - /* curr passive entry */ - /* Ripple Magnitude */ 0.0f, 10.0f, 30.0f, - /* Ripple Decay */ 1.0f, 1.0f, 0.98f, - /* Ripple Rate */ 0.0f, 0.05f, 0.05f, - /* Ripple Dispersion */ 0.0f, 15.0f, 15.0f, - /* Curr Ripple Timer */ 0.0f, - /* Curr Ripple x, y */ 0.0f, 0.0f, - /* Normal DList */ inside_castle_seg7_painting_dl_070235B8, - /* Texture Maps */ inside_castle_seg7_painting_env_map_texture_maps_07023044, - /* Textures */ inside_castle_seg7_painting_textures_070235F4, - /* Texture w, h */ 32, 32, - /* Ripple DList */ inside_castle_seg7_painting_dl_07022640, - /* Ripple Trigger */ RIPPLE_TRIGGER_CONTINUOUS, - /* Alpha */ 0xB4, - /* Mario Below */ 0x00, 0x00, 0x00, /* Whether or not Mario is below the painting */ - /* Size */ 819.2f, -}; +/// - PAINTING_ID_CASTLE_DDD - -// 0x070239E0 - 0x07023A58 -struct Painting wdw_painting = { - /* id */ 0x0008, - /* Image Count */ 0x02, - /* Texture Type */ PAINTING_IMAGE, - /* Floor Status */ 0x00, 0x00, 0x00 /* which of the painting's nearby special floors Mario's on */, - /* Ripple Status */ 0x00, - /* Rotation */ 0.0f, 0.0f, - /* Position */ -966.656f, 1305.6f, -143.36f, - /* curr passive entry */ - /* Ripple Magnitude */ 0.0f, 20.0f, 80.0f, - /* Ripple Decay */ 1.0f, 0.9608f, 0.9524f, - /* Ripple Rate */ 0.0f, 0.24f, 0.14f, - /* Ripple Dispersion */ 0.0f, 40.0f, 30.0f, - /* Curr Ripple Timer */ 0.0f, - /* Curr Ripple x, y */ 0.0f, 0.0f, - /* Normal DList */ inside_castle_seg7_painting_dl_07023290, - /* Texture Maps */ inside_castle_seg7_painting_texture_maps_07022518, - /* Textures */ inside_castle_seg7_painting_textures_070235F8, - /* Texture w, h */ 64, 32, - /* Ripple DList */ inside_castle_seg7_painting_dl_07021AC0, - /* Ripple Trigger */ RIPPLE_TRIGGER_PROXIMITY, - /* Alpha */ 0xFF, - /* Mario Below */ 0x00, 0x00, 0x00, /* Whether or not Mario is below the painting */ - /* Size */ 614.0f, +ALIGNED8 static const Texture *const inside_castle_seg7_painting_textures_ddd_env[] = { + inside_castle_seg7_texture_07017000, }; -// 0x07023A58 - 0x07023AD0 -struct Painting thi_tiny_painting = { - /* id */ 0x0009, - /* Image Count */ 0x02, - /* Texture Type */ PAINTING_IMAGE, - /* Floor Status */ 0x00, 0x00, 0x00 /* which of the painting's nearby special floors Mario's on */, - /* Ripple Status */ 0x00, - /* Rotation */ 0.0f, 180.0f, - /* Position */ -4598.7842f, 1354.752f, 3005.44f, - /* curr passive entry */ - /* Ripple Magnitude */ 0.0f, 20.0f, 80.0f, - /* Ripple Decay */ 1.0f, 0.9608f, 0.9524f, - /* Ripple Rate */ 0.0f, 0.24f, 0.14f, - /* Ripple Dispersion */ 0.0f, 40.0f, 30.0f, - /* Curr Ripple Timer */ 0.0f, - /* Curr Ripple x, y */ 0.0f, 0.0f, - /* Normal DList */ inside_castle_seg7_painting_dl_070232F0, - /* Texture Maps */ inside_castle_seg7_painting_texture_maps_07022518, - /* Textures */ inside_castle_seg7_painting_textures_07023600, - /* Texture w, h */ 64, 32, - /* Ripple DList */ inside_castle_seg7_painting_dl_07021AC0, - /* Ripple Trigger */ RIPPLE_TRIGGER_PROXIMITY, - /* Alpha */ 0xFF, - /* Mario Below */ 0x00, 0x00, 0x00, /* Whether or not Mario is below the painting */ - /* Size */ 393.216f, +const struct PaintingImage ddd_painting = { + .textureArray = inside_castle_seg7_painting_textures_ddd_env, + .imageCount = ARRAY_COUNT(inside_castle_seg7_painting_textures_ddd_env), + .textureWidth = 32, + .textureHeight = 32, + .imageType = PAINTING_IMAGE_TYPE_ENV_MAP, + .rippleTrigger = RIPPLE_TRIGGER_CONTINUOUS, + .shaded = TRUE, + .alpha = 0xB4, + .sizeX = 819.2f, + .sizeY = 819.2f, }; -// 0x07023AD0 - 0x07023B48 -struct Painting ttm_painting = { - /* id */ 0x000A, - /* Image Count */ 0x02, - /* Texture Type */ PAINTING_IMAGE, - /* Floor Status */ 0x00, 0x00, 0x00 /* which of the painting's nearby special floors Mario's on */, - /* Ripple Status */ 0x00, - /* Rotation */ 0.0f, 180.0f, - /* Position */ -546.816f, 1356.8f, 3813.376f, - /* curr passive entry */ - /* Ripple Magnitude */ 0.0f, 20.0f, 80.0f, - /* Ripple Decay */ 1.0f, 0.9608f, 0.9524f, - /* Ripple Rate */ 0.0f, 0.24f, 0.14f, - /* Ripple Dispersion */ 0.0f, 40.0f, 30.0f, - /* Curr Ripple Timer */ 0.0f, - /* Curr Ripple x, y */ 0.0f, 0.0f, - /* Normal DList */ inside_castle_seg7_painting_dl_07023350, - /* Texture Maps */ inside_castle_seg7_painting_texture_maps_07022518, - /* Textures */ inside_castle_seg7_painting_textures_07023608, - /* Texture w, h */ 64, 32, - /* Ripple DList */ inside_castle_seg7_painting_dl_07021AC0, - /* Ripple Trigger */ RIPPLE_TRIGGER_PROXIMITY, - /* Alpha */ 0xFF, - /* Mario Below */ 0x00, 0x00, 0x00, /* Whether or not Mario is below the painting */ - /* Size */ 256.0f, -}; +/// - PAINTING_ID_CASTLE_WDW - -// 0x07023B48 - 0x07023BC0 -struct Painting ttc_painting = { - /* id */ 0x000B, - /* Image Count */ 0x02, - /* Texture Type */ PAINTING_IMAGE, - /* Floor Status */ 0x00, 0x00, 0x00 /* which of the painting's nearby special floors Mario's on */, - /* Ripple Status */ 0x00, - /* Rotation */ 0.0f, 180.0f, - /* Position */ 0.0f, 2713.6f, 7232.5122f, - /* curr passive entry */ - /* Ripple Magnitude */ 0.0f, 20.0f, 80.0f, - /* Ripple Decay */ 1.0f, 0.9608f, 0.9524f, - /* Ripple Rate */ 0.0f, 0.24f, 0.14f, - /* Ripple Dispersion */ 0.0f, 40.0f, 30.0f, - /* Curr Ripple Timer */ 0.0f, - /* Curr Ripple x, y */ 0.0f, 0.0f, - /* Normal DList */ inside_castle_seg7_painting_dl_070233B0, - /* Texture Maps */ inside_castle_seg7_painting_texture_maps_07022518, - /* Textures */ inside_castle_seg7_painting_textures_07023610, - /* Texture w, h */ 64, 32, - /* Ripple DList */ inside_castle_seg7_painting_dl_07021AC0, - /* Ripple Trigger */ RIPPLE_TRIGGER_PROXIMITY, - /* Alpha */ 0xFF, - /* Mario Below */ 0x00, 0x00, 0x00, /* Whether or not Mario is below the painting */ - /* Size */ 409.6f, +ALIGNED8 static const Texture *const inside_castle_seg7_painting_textures_wdw[] = { + inside_castle_seg7_texture_07018800, + inside_castle_seg7_texture_07017800, }; -// 0x07023BC0 - 0x07023C38 -struct Painting sl_painting = { - /* id */ 0x000C, - /* Image Count */ 0x02, - /* Texture Type */ PAINTING_IMAGE, - /* Floor Status */ 0x00, 0x00, 0x00 /* which of the painting's nearby special floors Mario's on */, - /* Ripple Status */ 0x00, - /* Rotation */ 0.0f, 0.0f, - /* Position */ 3179.52f, 1408.0f, -271.36f, - /* curr passive entry */ - /* Ripple Magnitude */ 0.0f, 20.0f, 80.0f, - /* Ripple Decay */ 1.0f, 0.9608f, 0.9524f, - /* Ripple Rate */ 0.0f, 0.24f, 0.14f, - /* Ripple Dispersion */ 0.0f, 40.0f, 30.0f, - /* Curr Ripple Timer */ 0.0f, - /* Curr Ripple x, y */ 0.0f, 0.0f, - /* Normal DList */ inside_castle_seg7_painting_dl_07023410, - /* Texture Maps */ inside_castle_seg7_painting_texture_maps_07022518, - /* Textures */ inside_castle_seg7_painting_textures_07023618, - /* Texture w, h */ 64, 32, - /* Ripple DList */ inside_castle_seg7_painting_dl_07021AC0, - /* Ripple Trigger */ RIPPLE_TRIGGER_PROXIMITY, - /* Alpha */ 0xFF, - /* Mario Below */ 0x00, 0x00, 0x00, /* Whether or not Mario is below the painting */ - /* Size */ 716.8f, +const struct PaintingImage wdw_painting = { + .textureArray = inside_castle_seg7_painting_textures_wdw, + .imageCount = ARRAY_COUNT(inside_castle_seg7_painting_textures_wdw), + .textureWidth = 64, + .textureHeight = 32, + .imageType = PAINTING_IMAGE_TYPE_TEXTURE, + .rippleTrigger = RIPPLE_TRIGGER_PROXIMITY, + .shaded = TRUE, + .alpha = 0xFF, + .sizeX = 614.0f, + .sizeY = 614.0f, }; -// 0x07023C38 - 0x07023CB0 -struct Painting thi_huge_painting = { - /* id */ 0x000D, - /* Image Count */ 0x02, - /* Texture Type */ PAINTING_IMAGE, - /* Floor Status */ 0x00, 0x00, 0x00 /* which of the painting's nearby special floors Mario's on */, - /* Ripple Status */ 0x00, - /* Rotation */ 0.0f, 0.0f, - /* Position */ -5614.5918f, 1510.4f, -3292.16f, - /* curr passive entry */ - /* Ripple Magnitude */ 0.0f, 40.0f, 160.0f, - /* Ripple Decay */ 1.0f, 0.9608f, 0.9524f, - /* Ripple Rate */ 0.0f, 0.12f, 0.07f, - /* Ripple Dispersion */ 0.0f, 80.0f, 60.0f, - /* Curr Ripple Timer */ 0.0f, - /* Curr Ripple x, y */ 0.0f, 0.0f, - /* Normal DList */ inside_castle_seg7_painting_dl_070232F0, - /* Texture Maps */ inside_castle_seg7_painting_texture_maps_07022518, - /* Textures */ inside_castle_seg7_painting_textures_07023600, - /* Texture w, h */ 64, 32, - /* Ripple DList */ inside_castle_seg7_painting_dl_07021AC0, - /* Ripple Trigger */ RIPPLE_TRIGGER_PROXIMITY, - /* Alpha */ 0xFF, - /* Mario Below */ 0x00, 0x00, 0x00, /* Whether or not Mario is below the painting */ - /* Size */ 1638.4f, +/// - PAINTING_ID_CASTLE_THI_TINY - + +ALIGNED8 static const Texture *const inside_castle_seg7_painting_textures_thi[] = { + inside_castle_seg7_texture_0701A800, + inside_castle_seg7_texture_07019800, +}; + +const struct PaintingImage thi_tiny_painting = { + .textureArray = inside_castle_seg7_painting_textures_thi, + .imageCount = ARRAY_COUNT(inside_castle_seg7_painting_textures_thi), + .textureWidth = 64, + .textureHeight = 32, + .imageType = PAINTING_IMAGE_TYPE_TEXTURE, + .rippleTrigger = RIPPLE_TRIGGER_PROXIMITY, + .shaded = TRUE, + .alpha = 0xFF, + .sizeX = 393.216f, + .sizeY = 393.216f, +}; + +/// - PAINTING_ID_CASTLE_THI_HUGE - + +const struct PaintingImage thi_huge_painting = { + .textureArray = inside_castle_seg7_painting_textures_thi, + .imageCount = ARRAY_COUNT(inside_castle_seg7_painting_textures_thi), + .textureWidth = 64, + .textureHeight = 32, + .imageType = PAINTING_IMAGE_TYPE_TEXTURE, + .rippleTrigger = RIPPLE_TRIGGER_PROXIMITY, + .shaded = TRUE, + .alpha = 0xFF, + .sizeX = 1638.4f, + .sizeY = 1638.4f, +}; + +/// - PAINTING_ID_CASTLE_TTM - + +ALIGNED8 static const Texture *const inside_castle_seg7_painting_textures_ttm[] = { + inside_castle_seg7_texture_0701C800, + inside_castle_seg7_texture_0701B800, +}; + +const struct PaintingImage ttm_painting = { + .textureArray = inside_castle_seg7_painting_textures_ttm, + .imageCount = ARRAY_COUNT(inside_castle_seg7_painting_textures_ttm), + .textureWidth = 64, + .textureHeight = 32, + .imageType = PAINTING_IMAGE_TYPE_TEXTURE, + .rippleTrigger = RIPPLE_TRIGGER_PROXIMITY, + .shaded = TRUE, + .alpha = 0xFF, + .sizeX = 256.0f, + .sizeY = 256.0f, +}; + +/// - PAINTING_ID_CASTLE_TTC - + +ALIGNED8 static const Texture *const inside_castle_seg7_painting_textures_ttc[] = { + inside_castle_seg7_texture_0701E800, + inside_castle_seg7_texture_0701D800, +}; + +const struct PaintingImage ttc_painting = { + .textureArray = inside_castle_seg7_painting_textures_ttc, + .imageCount = ARRAY_COUNT(inside_castle_seg7_painting_textures_ttc), + .textureWidth = 64, + .textureHeight = 32, + .imageType = PAINTING_IMAGE_TYPE_TEXTURE, + .rippleTrigger = RIPPLE_TRIGGER_PROXIMITY, + .shaded = TRUE, + .alpha = 0xFF, + .sizeX = 409.6f, + .sizeY = 409.6f, +}; + +/// - PAINTING_ID_CASTLE_SL - + +ALIGNED8 static const Texture *const inside_castle_seg7_painting_textures_sl[] = { + inside_castle_seg7_texture_07020800, + inside_castle_seg7_texture_0701F800, +}; + +const struct PaintingImage sl_painting = { + .textureArray = inside_castle_seg7_painting_textures_sl, + .imageCount = ARRAY_COUNT(inside_castle_seg7_painting_textures_sl), + .textureWidth = 64, + .textureHeight = 32, + .imageType = PAINTING_IMAGE_TYPE_TEXTURE, + .rippleTrigger = RIPPLE_TRIGGER_PROXIMITY, + .shaded = FALSE, + .alpha = 0xFF, + .sizeX = 716.8f, + .sizeY = 716.8f, +}; + +/// - PAINTING_ID_CASTLE_RR - + +const struct PaintingImage rr_painting = { + .textureArray = NULL, + .imageCount = 0, + .textureWidth = 0, + .textureHeight = 0, + .imageType = PAINTING_IMAGE_TYPE_INVISIBLE, + .rippleTrigger = RIPPLE_TRIGGER_NONE, + .shaded = TRUE, + .alpha = 0x00, + .sizeX = 204.8f, + .sizeY = 204.8f, }; diff --git a/levels/castle_inside/script.c b/levels/castle_inside/script.c index 0011560302..6a80278f88 100644 --- a/levels/castle_inside/script.c +++ b/levels/castle_inside/script.c @@ -30,25 +30,21 @@ static const LevelScript script_func_local_1[] = { WARP_NODE(/*id*/ 0x04, /*destLevel*/ LEVEL_CASTLE, /*destArea*/ 0x02, /*destNode*/ 0x01, /*flags*/ WARP_NO_CHECKPOINT), WARP_NODE(/*id*/ 0x05, /*destLevel*/ LEVEL_CASTLE, /*destArea*/ 0x03, /*destNode*/ 0x00, /*flags*/ WARP_NO_CHECKPOINT), WARP_NODE(/*id*/ 0x06, /*destLevel*/ LEVEL_CASTLE, /*destArea*/ 0x03, /*destNode*/ 0x01, /*flags*/ WARP_NO_CHECKPOINT), - PAINTING_WARP_NODE(/*id*/ 0x00, /*destLevel*/ LEVEL_BOB, /*destArea*/ 0x01, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), - PAINTING_WARP_NODE(/*id*/ 0x01, /*destLevel*/ LEVEL_BOB, /*destArea*/ 0x01, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), - PAINTING_WARP_NODE(/*id*/ 0x02, /*destLevel*/ LEVEL_BOB, /*destArea*/ 0x01, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), - PAINTING_WARP_NODE(/*id*/ 0x03, /*destLevel*/ LEVEL_CCM, /*destArea*/ 0x01, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), - PAINTING_WARP_NODE(/*id*/ 0x04, /*destLevel*/ LEVEL_CCM, /*destArea*/ 0x01, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), - PAINTING_WARP_NODE(/*id*/ 0x05, /*destLevel*/ LEVEL_CCM, /*destArea*/ 0x01, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), - PAINTING_WARP_NODE(/*id*/ 0x06, /*destLevel*/ LEVEL_WF, /*destArea*/ 0x01, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), - PAINTING_WARP_NODE(/*id*/ 0x07, /*destLevel*/ LEVEL_WF, /*destArea*/ 0x01, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), - PAINTING_WARP_NODE(/*id*/ 0x08, /*destLevel*/ LEVEL_WF, /*destArea*/ 0x01, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), - PAINTING_WARP_NODE(/*id*/ 0x09, /*destLevel*/ LEVEL_JRB, /*destArea*/ 0x01, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), - PAINTING_WARP_NODE(/*id*/ 0x0A, /*destLevel*/ LEVEL_JRB, /*destArea*/ 0x01, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), - PAINTING_WARP_NODE(/*id*/ 0x0B, /*destLevel*/ LEVEL_JRB, /*destArea*/ 0x01, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), + OBJECT(/*model*/ MODEL_PAINTING, /*pos*/ -5222, 410, -154, /*angle*/ 0, 90, 0, /*behParam*/ ((PAINTING_ID_CASTLE_BOB << 24) | (0x96 << 16)), /*beh*/ bhvPainting), + OBJECT(/*model*/ MODEL_PAINTING, /*pos*/ -2611, -307, -4352, /*angle*/ 0, 0, 0, /*behParam*/ ((PAINTING_ID_CASTLE_CCM << 24) | (0x97 << 16)), /*beh*/ bhvPainting), + OBJECT(/*model*/ MODEL_PAINTING, /*pos*/ -51, -205, -4506, /*angle*/ 0, 0, 0, /*behParam*/ ((PAINTING_ID_CASTLE_WF << 24) | (0x98 << 16)), /*beh*/ bhvPainting), + OBJECT(/*model*/ MODEL_PAINTING, /*pos*/ 4300, 410, -538, /*angle*/ 0, 270, 0, /*behParam*/ ((PAINTING_ID_CASTLE_JRB << 24) | (0x99 << 16)), /*beh*/ bhvPainting), + WARP_NODE(/*id*/ 0x96, /*destLevel*/ LEVEL_BOB, /*destArea*/ 0x01, /*destNode*/ WARP_NODE_MAIN_ENTRY, /*flags*/ WARP_NO_CHECKPOINT), + WARP_NODE(/*id*/ 0x97, /*destLevel*/ LEVEL_CCM, /*destArea*/ 0x01, /*destNode*/ WARP_NODE_MAIN_ENTRY, /*flags*/ WARP_NO_CHECKPOINT), + WARP_NODE(/*id*/ 0x98, /*destLevel*/ LEVEL_WF, /*destArea*/ 0x01, /*destNode*/ WARP_NODE_MAIN_ENTRY, /*flags*/ WARP_NO_CHECKPOINT), + WARP_NODE(/*id*/ 0x99, /*destLevel*/ LEVEL_JRB, /*destArea*/ 0x01, /*destNode*/ WARP_NODE_MAIN_ENTRY, /*flags*/ WARP_NO_CHECKPOINT), OBJECT(/*model*/ MODEL_NONE, /*pos*/ 2013, 768, -2014, /*angle*/ 0, 0, 0, /*behParam*/ 0x000A0000, /*beh*/ bhvWarp), - WARP_NODE(/*id*/ 0x0A, /*destLevel*/ LEVEL_PSS, /*destArea*/ 0x01, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), + WARP_NODE(/*id*/ 0x0A, /*destLevel*/ LEVEL_PSS, /*destArea*/ 0x01, /*destNode*/ WARP_NODE_MAIN_ENTRY, /*flags*/ WARP_NO_CHECKPOINT), OBJECT(/*model*/ MODEL_NONE, /*pos*/ -5513, 512, -4324, /*angle*/ 0, 0, 0, /*behParam*/ 0x300B0000, /*beh*/ bhvWarp), - WARP_NODE(/*id*/ 0x0B, /*destLevel*/ LEVEL_BITDW, /*destArea*/ 0x01, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), + WARP_NODE(/*id*/ 0x0B, /*destLevel*/ LEVEL_BITDW, /*destArea*/ 0x01, /*destNode*/ WARP_NODE_MAIN_ENTRY, /*flags*/ WARP_NO_CHECKPOINT), OBJECT(/*model*/ MODEL_NONE, /*pos*/ 1963, 819, 1280, /*angle*/ 0, 0, 0, /*behParam*/ 0x050C0000, /*beh*/ bhvWarp), - WARP_NODE(/*id*/ 0x0C, /*destLevel*/ LEVEL_SA, /*destArea*/ 0x01, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), - WARP_NODE(/*id*/ 0xF2, /*destLevel*/ LEVEL_TOTWC, /*destArea*/ 0x01, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), + WARP_NODE(/*id*/ 0x0C, /*destLevel*/ LEVEL_SA, /*destArea*/ 0x01, /*destNode*/ WARP_NODE_MAIN_ENTRY, /*flags*/ WARP_NO_CHECKPOINT), + WARP_NODE(/*id*/ WARP_NODE_LOOK_UP, /*destLevel*/ LEVEL_TOTWC, /*destArea*/ 0x01, /*destNode*/ WARP_NODE_MAIN_ENTRY, /*flags*/ WARP_NO_CHECKPOINT), OBJECT(/*model*/ MODEL_NONE, /*pos*/ -1024, 512, -650, /*angle*/ 0, 0, 0, /*behParam*/ 0x001E0000, /*beh*/ bhvInstantActiveWarp), OBJECT(/*model*/ MODEL_NONE, /*pos*/ -1024, -50, 717, /*angle*/ 0, 180, 0, /*behParam*/ 0x001F0000, /*beh*/ bhvInstantActiveWarp), OBJECT(/*model*/ MODEL_NONE, /*pos*/ -1024, 900, 717, /*angle*/ 0, 180, 0, /*behParam*/ 0x00200000, /*beh*/ bhvAirborneWarp), @@ -99,29 +95,24 @@ static const LevelScript script_func_local_2[] = { OBJECT(/*model*/ MODEL_CASTLE_STAR_DOOR_50_STARS, /*pos*/ -127, 2253, 4762, /*angle*/ 0, 180, 0, /*behParam*/ 0x32000000, /*beh*/ bhvStarDoor), OBJECT(/*model*/ MODEL_CASTLE_STAR_DOOR_70_STARS, /*pos*/ -281, 3174, 3772, /*angle*/ 0, 0, 0, /*behParam*/ 0x46000000, /*beh*/ bhvStarDoor), OBJECT(/*model*/ MODEL_CASTLE_STAR_DOOR_70_STARS, /*pos*/ -127, 3174, 3772, /*angle*/ 0, 180, 0, /*behParam*/ 0x46000000, /*beh*/ bhvStarDoor), - PAINTING_WARP_NODE(/*id*/ 0x18, /*destLevel*/ LEVEL_WDW, /*destArea*/ 0x01, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), - PAINTING_WARP_NODE(/*id*/ 0x19, /*destLevel*/ LEVEL_WDW, /*destArea*/ 0x01, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), - PAINTING_WARP_NODE(/*id*/ 0x1A, /*destLevel*/ LEVEL_WDW, /*destArea*/ 0x01, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), - PAINTING_WARP_NODE(/*id*/ 0x1B, /*destLevel*/ LEVEL_THI, /*destArea*/ 0x02, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), - PAINTING_WARP_NODE(/*id*/ 0x1C, /*destLevel*/ LEVEL_THI, /*destArea*/ 0x02, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), - PAINTING_WARP_NODE(/*id*/ 0x1D, /*destLevel*/ LEVEL_THI, /*destArea*/ 0x02, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), - PAINTING_WARP_NODE(/*id*/ 0x1E, /*destLevel*/ LEVEL_TTM, /*destArea*/ 0x01, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), - PAINTING_WARP_NODE(/*id*/ 0x1F, /*destLevel*/ LEVEL_TTM, /*destArea*/ 0x01, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), - PAINTING_WARP_NODE(/*id*/ 0x20, /*destLevel*/ LEVEL_TTM, /*destArea*/ 0x01, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), - PAINTING_WARP_NODE(/*id*/ 0x21, /*destLevel*/ LEVEL_TTC, /*destArea*/ 0x01, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), - PAINTING_WARP_NODE(/*id*/ 0x22, /*destLevel*/ LEVEL_TTC, /*destArea*/ 0x01, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), - PAINTING_WARP_NODE(/*id*/ 0x23, /*destLevel*/ LEVEL_TTC, /*destArea*/ 0x01, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), - PAINTING_WARP_NODE(/*id*/ 0x24, /*destLevel*/ LEVEL_SL, /*destArea*/ 0x01, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), - PAINTING_WARP_NODE(/*id*/ 0x25, /*destLevel*/ LEVEL_SL, /*destArea*/ 0x01, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), - PAINTING_WARP_NODE(/*id*/ 0x26, /*destLevel*/ LEVEL_SL, /*destArea*/ 0x01, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), - PAINTING_WARP_NODE(/*id*/ 0x27, /*destLevel*/ LEVEL_THI, /*destArea*/ 0x01, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), - PAINTING_WARP_NODE(/*id*/ 0x28, /*destLevel*/ LEVEL_THI, /*destArea*/ 0x01, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), - PAINTING_WARP_NODE(/*id*/ 0x29, /*destLevel*/ LEVEL_THI, /*destArea*/ 0x01, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), - PAINTING_WARP_NODE(/*id*/ 0x2A, /*destLevel*/ LEVEL_RR, /*destArea*/ 0x01, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), + OBJECT(/*model*/ MODEL_PAINTING, /*pos*/ -967, 1306, -143, /*angle*/ 0, 0, 0, /*behParam*/ ((PAINTING_ID_CASTLE_WDW << 24) | (0x96 << 16)), /*beh*/ bhvPainting), + OBJECT(/*model*/ MODEL_PAINTING, /*pos*/ -4599, 1355, 3005, /*angle*/ 0, 180, 0, /*behParam*/ ((PAINTING_ID_CASTLE_THI_TINY << 24) | (0x97 << 16)), /*beh*/ bhvPainting), + OBJECT(/*model*/ MODEL_PAINTING, /*pos*/ -547, 1357, 3813, /*angle*/ 0, 180, 0, /*behParam*/ ((PAINTING_ID_CASTLE_TTM << 24) | (0x98 << 16)), /*beh*/ bhvPainting), + OBJECT(/*model*/ MODEL_PAINTING, /*pos*/ 0, 2714, 7233, /*angle*/ 0, 180, 0, /*behParam*/ ((PAINTING_ID_CASTLE_TTC << 24) | (0x99 << 16)), /*beh*/ bhvPainting), + OBJECT(/*model*/ MODEL_PAINTING, /*pos*/ 3180, 1408, -271, /*angle*/ 0, 0, 0, /*behParam*/ ((PAINTING_ID_CASTLE_SL << 24) | (0x9A << 16)), /*beh*/ bhvPainting), + OBJECT(/*model*/ MODEL_PAINTING, /*pos*/ -5615, 1510, -3292, /*angle*/ 0, 0, 0, /*behParam*/ ((PAINTING_ID_CASTLE_THI_HUGE << 24) | (0x9B << 16)), /*beh*/ bhvPainting), + OBJECT(/*model*/ MODEL_PAINTING, /*pos*/ -3513, 2970, 5989, /*angle*/ 270, 0, 0, /*behParam*/ ((PAINTING_ID_CASTLE_RR << 24) | (0x9C << 16)), /*beh*/ bhvPainting), + WARP_NODE(/*id*/ 0x96, /*destLevel*/ LEVEL_WDW, /*destArea*/ 0x01, /*destNode*/ WARP_NODE_MAIN_ENTRY, /*flags*/ WARP_NO_CHECKPOINT), + WARP_NODE(/*id*/ 0x97, /*destLevel*/ LEVEL_THI, /*destArea*/ 0x02, /*destNode*/ WARP_NODE_MAIN_ENTRY, /*flags*/ WARP_NO_CHECKPOINT), + WARP_NODE(/*id*/ 0x98, /*destLevel*/ LEVEL_TTM, /*destArea*/ 0x01, /*destNode*/ WARP_NODE_MAIN_ENTRY, /*flags*/ WARP_NO_CHECKPOINT), + WARP_NODE(/*id*/ 0x99, /*destLevel*/ LEVEL_TTC, /*destArea*/ 0x01, /*destNode*/ WARP_NODE_MAIN_ENTRY, /*flags*/ WARP_NO_CHECKPOINT), + WARP_NODE(/*id*/ 0x9A, /*destLevel*/ LEVEL_SL, /*destArea*/ 0x01, /*destNode*/ WARP_NODE_MAIN_ENTRY, /*flags*/ WARP_NO_CHECKPOINT), + WARP_NODE(/*id*/ 0x9B, /*destLevel*/ LEVEL_THI, /*destArea*/ 0x01, /*destNode*/ WARP_NODE_MAIN_ENTRY, /*flags*/ WARP_NO_CHECKPOINT), + WARP_NODE(/*id*/ 0x9C, /*destLevel*/ LEVEL_RR, /*destArea*/ 0x01, /*destNode*/ WARP_NODE_MAIN_ENTRY, /*flags*/ WARP_NO_CHECKPOINT), OBJECT(/*model*/ MODEL_NONE, /*pos*/ 3002, 2816, 5886, /*angle*/ 0, 0, 0, /*behParam*/ 0x0F0A0000, /*beh*/ bhvWarp), - WARP_NODE(/*id*/ 0x0A, /*destLevel*/ LEVEL_WMOTR, /*destArea*/ 0x01, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), + WARP_NODE(/*id*/ 0x0A, /*destLevel*/ LEVEL_WMOTR, /*destArea*/ 0x01, /*destNode*/ WARP_NODE_MAIN_ENTRY, /*flags*/ WARP_NO_CHECKPOINT), OBJECT(/*model*/ MODEL_NONE, /*pos*/ -230, 4813, -3352, /*angle*/ 0, 0, 0, /*behParam*/ 0x0F0B0000, /*beh*/ bhvWarp), - WARP_NODE(/*id*/ 0x0B, /*destLevel*/ LEVEL_BITS, /*destArea*/ 0x01, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), + WARP_NODE(/*id*/ 0x0B, /*destLevel*/ LEVEL_BITS, /*destArea*/ 0x01, /*destNode*/ WARP_NODE_MAIN_ENTRY, /*flags*/ WARP_NO_CHECKPOINT), OBJECT(/*model*/ MODEL_NONE, /*pos*/ -659, 1613, -350, /*angle*/ 0, 180, 0, /*behParam*/ 0x00320000, /*beh*/ bhvPaintingStarCollectWarp), OBJECT(/*model*/ MODEL_NONE, /*pos*/ -4693, 2157, 1828, /*angle*/ 0, 270, 0, /*behParam*/ 0x00330000, /*beh*/ bhvAirborneStarCollectWarp), OBJECT(/*model*/ MODEL_NONE, /*pos*/ -675, 1400, 3870, /*angle*/ 0, 0, 0, /*behParam*/ 0x00340000, /*beh*/ bhvPaintingStarCollectWarp), @@ -167,18 +158,16 @@ static const LevelScript script_func_local_3[] = { WARP_NODE(/*id*/ 0x02, /*destLevel*/ LEVEL_CASTLE_GROUNDS, /*destArea*/ 0x01, /*destNode*/ 0x02, /*flags*/ WARP_NO_CHECKPOINT), OBJECT(/*model*/ MODEL_CASTLE_STAR_DOOR_30_STARS, /*pos*/ 307, -1074, 2074, /*angle*/ 0, 90, 0, /*behParam*/ 0x1E000000, /*beh*/ bhvStarDoor), OBJECT(/*model*/ MODEL_CASTLE_STAR_DOOR_30_STARS, /*pos*/ 307, -1074, 1920, /*angle*/ 0, 270, 0, /*behParam*/ 0x1E000000, /*beh*/ bhvStarDoor), - PAINTING_WARP_NODE(/*id*/ 0x0C, /*destLevel*/ LEVEL_LLL, /*destArea*/ 0x01, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), - PAINTING_WARP_NODE(/*id*/ 0x0D, /*destLevel*/ LEVEL_LLL, /*destArea*/ 0x01, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), - PAINTING_WARP_NODE(/*id*/ 0x0E, /*destLevel*/ LEVEL_LLL, /*destArea*/ 0x01, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), - PAINTING_WARP_NODE(/*id*/ 0x0F, /*destLevel*/ LEVEL_SSL, /*destArea*/ 0x01, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), - PAINTING_WARP_NODE(/*id*/ 0x10, /*destLevel*/ LEVEL_SSL, /*destArea*/ 0x01, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), - PAINTING_WARP_NODE(/*id*/ 0x11, /*destLevel*/ LEVEL_SSL, /*destArea*/ 0x01, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), - PAINTING_WARP_NODE(/*id*/ 0x2A, /*destLevel*/ LEVEL_HMC, /*destArea*/ 0x01, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), - PAINTING_WARP_NODE(/*id*/ 0x15, /*destLevel*/ LEVEL_DDD, /*destArea*/ 0x01, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), - PAINTING_WARP_NODE(/*id*/ 0x16, /*destLevel*/ LEVEL_DDD, /*destArea*/ 0x01, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), - PAINTING_WARP_NODE(/*id*/ 0x17, /*destLevel*/ LEVEL_DDD, /*destArea*/ 0x01, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), + OBJECT(/*model*/ MODEL_PAINTING, /*pos*/ -1690, -1126, -3942, /*angle*/ 0, 0, 0, /*behParam*/ ((PAINTING_ID_CASTLE_LLL << 24) | (0x96 << 16)), /*beh*/ bhvPainting), + OBJECT(/*model*/ MODEL_PAINTING, /*pos*/ -2611, -1178, -1075, /*angle*/ 0, 180, 0, /*behParam*/ ((PAINTING_ID_CASTLE_SSL << 24) | (0x97 << 16)), /*beh*/ bhvPainting), + OBJECT(/*model*/ MODEL_PAINTING, /*pos*/ 2099, -1485, -2278, /*angle*/ 270, 0, 0, /*behParam*/ ((PAINTING_ID_CASTLE_HMC << 24) | (0x98 << 16)), /*beh*/ bhvPainting), + OBJECT(/*model*/ MODEL_PAINTING, /*pos*/ 3456, -1075, 1587, /*angle*/ 0, 270, 0, /*behParam*/ ((PAINTING_ID_CASTLE_DDD << 24) | (0x99 << 16)), /*beh*/ bhvPainting), + WARP_NODE(/*id*/ 0x96, /*destLevel*/ LEVEL_LLL, /*destArea*/ 0x01, /*destNode*/ WARP_NODE_MAIN_ENTRY, /*flags*/ WARP_NO_CHECKPOINT), + WARP_NODE(/*id*/ 0x97, /*destLevel*/ LEVEL_SSL, /*destArea*/ 0x01, /*destNode*/ WARP_NODE_MAIN_ENTRY, /*flags*/ WARP_NO_CHECKPOINT), + WARP_NODE(/*id*/ 0x98, /*destLevel*/ LEVEL_HMC, /*destArea*/ 0x01, /*destNode*/ WARP_NODE_MAIN_ENTRY, /*flags*/ WARP_NO_CHECKPOINT), + WARP_NODE(/*id*/ 0x99, /*destLevel*/ LEVEL_DDD, /*destArea*/ 0x01, /*destNode*/ WARP_NODE_MAIN_ENTRY, /*flags*/ WARP_NO_CHECKPOINT), OBJECT(/*model*/ MODEL_NONE, /*pos*/ 4147, -1280, 1997, /*angle*/ 0, 0, 0, /*behParam*/ 0x0F180000, /*beh*/ bhvWarp), - WARP_NODE(/*id*/ 0x18, /*destLevel*/ LEVEL_BITFS, /*destArea*/ 0x01, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), + WARP_NODE(/*id*/ 0x18, /*destLevel*/ LEVEL_BITFS, /*destArea*/ 0x01, /*destNode*/ WARP_NODE_MAIN_ENTRY, /*flags*/ WARP_NO_CHECKPOINT), OBJECT(/*model*/ MODEL_NONE, /*pos*/ -1382, -819, -4150, /*angle*/ 0, 180, 0, /*behParam*/ 0x00320000, /*beh*/ bhvPaintingStarCollectWarp), OBJECT(/*model*/ MODEL_NONE, /*pos*/ -2918, -870, -875, /*angle*/ 0, 0, 0, /*behParam*/ 0x00330000, /*beh*/ bhvPaintingStarCollectWarp), OBJECT(/*model*/ MODEL_NONE, /*pos*/ 2483, -1688, -2662, /*angle*/ 0, 270, 0, /*behParam*/ 0x00340000, /*beh*/ bhvLaunchStarCollectWarp), @@ -290,7 +279,6 @@ const LevelScript level_castle_inside_entry[] = { AREA(/*index*/ 3, castle_geo_001C10), OBJECT(/*model*/ MODEL_CASTLE_WATER_LEVEL_PILLAR, /*pos*/ 7066, -1178, -819, /*angle*/ 0, 0, 0, /*behParam*/ 0x00000000, /*beh*/ bhvWaterLevelPillar), OBJECT(/*model*/ MODEL_CASTLE_WATER_LEVEL_PILLAR, /*pos*/ 7066, -1178, -205, /*angle*/ 0, 0, 0, /*behParam*/ 0x00000000, /*beh*/ bhvWaterLevelPillar), - OBJECT(/*model*/ MODEL_NONE, /*pos*/ 0, 0, 0, /*angle*/ 0, 0, 0, /*behParam*/ 0x00000000, /*beh*/ bhvDddWarp), OBJECT(/*model*/ MODEL_MIPS, /*pos*/ -1509, -1177, -1564, /*angle*/ 0, 0, 0, /*behParam*/ 0x00000000, /*beh*/ bhvMips), OBJECT(/*model*/ MODEL_TOAD, /*pos*/ 1787, -1381, -1957, /*angle*/ 0, 126, 0, /*behParam*/ DIALOG_082 << 24, /*beh*/ bhvToadMessage), OBJECT(/*model*/ MODEL_TOAD, /*pos*/ -4048, -1381, -1334, /*angle*/ 0, 30, 0, /*behParam*/ DIALOG_136 << 24, /*beh*/ bhvToadMessage), diff --git a/levels/hmc/areas/1/geo.inc.c b/levels/hmc/areas/1/geo.inc.c index 7c6d9b3709..d5f5d95f43 100644 --- a/levels/hmc/areas/1/geo.inc.c +++ b/levels/hmc/areas/1/geo.inc.c @@ -83,8 +83,6 @@ const GeoLayout hmc_geo_000748[] = { GEO_NODE_START(), GEO_OPEN_NODE(), GEO_DISPLAY_LIST(LAYER_OPAQUE, hmc_seg7_dl_07020FD0), - GEO_ASM(0, geo_painting_update), - GEO_ASM(PAINTING_ID(0, 0), geo_painting_draw), GEO_CLOSE_NODE(), GEO_RETURN(), }; @@ -246,8 +244,6 @@ const GeoLayout hmc_geo_000A88[] = { GEO_DISPLAY_LIST(LAYER_TRANSPARENT, hmc_seg7_dl_0701F818), GEO_DISPLAY_LIST(LAYER_OPAQUE, hmc_seg7_dl_0701FD58), GEO_DISPLAY_LIST(LAYER_OPAQUE, hmc_seg7_dl_07020FD0), - GEO_ASM( 0, geo_painting_update), - GEO_ASM( PAINTING_ID(0, 0), geo_painting_draw), GEO_ASM( 0, geo_movtex_pause_control), GEO_ASM(HMC_MOVTEX_DORRIE_POOL_WATER, geo_movtex_draw_water_regions), GEO_CLOSE_NODE(), diff --git a/levels/hmc/areas/1/painting.inc.c b/levels/hmc/areas/1/painting.inc.c index b408067a68..ce4e475962 100644 --- a/levels/hmc/areas/1/painting.inc.c +++ b/levels/hmc/areas/1/painting.inc.c @@ -1,536 +1,26 @@ #include "game/paintings.h" -// 0x070241B8 - 0x070241D0 - -// 0x070241D0 - 0x070241E8 - -// Appears to lock 4 of the sides when shimmering and in use. Unused. -// 0x070241E8 - 0x07024228 -static const Vtx hmc_seg7_vertex_070241E8[] = { - {{{ 0, 0, 0}, 0, { -32, 990}, {0x00, 0x00, 0x7f, 0xff}}}, - {{{ 614, 0, 0}, 0, { 6100, 990}, {0x00, 0x00, 0x7f, 0xff}}}, - {{{ 614, 614, 0}, 0, { 6100, -5142}, {0x00, 0x00, 0x7f, 0xff}}}, - {{{ 0, 614, 0}, 0, { -32, -5142}, {0x00, 0x00, 0x7f, 0xff}}}, -}; - -// 0x07024228 - 0x07024268 -static const Vtx hmc_seg7_vertex_07024228[] = { - {{{ 0, 0, 0}, 0, { 0, 0}, {0x00, 0x00, 0x7f, 0xff}}}, - {{{ 614, 0, 0}, 0, { 0, 0}, {0x00, 0x00, 0x7f, 0xff}}}, - {{{ 614, 614, 0}, 0, { 0, 0}, {0x00, 0x00, 0x7f, 0xff}}}, - {{{ 0, 614, 0}, 0, { 0, 0}, {0x00, 0x00, 0x7f, 0xff}}}, -}; - -// Unused -// 0x07024268 - 0x070242A0 -const Gfx hmc_seg7_dl_07024268[] = { - gsDPPipeSync(), - gsDPSetCombineMode(G_CC_MODULATERGB, G_CC_MODULATERGB), - gsSPLightColor(LIGHT_1, 0xffffffff), - gsSPLightColor(LIGHT_2, 0x505050ff), - gsSPTexture(0xFFFF, 0xFFFF, 0, G_TX_RENDERTILE, G_ON), - gsSPVertex(hmc_seg7_vertex_070241E8, 4, 0), - gsSPEndDisplayList(), -}; - -// Unused -// 0x070242A0 - 0x070242D0 -const Gfx hmc_seg7_dl_070242A0[] = { - gsSP2Triangles( 0, 1, 2, 0x0, 0, 2, 3, 0x0), - gsSPTexture(0xFFFF, 0xFFFF, 0, G_TX_RENDERTILE, G_OFF), - gsDPPipeSync(), - gsDPSetCombineMode(G_CC_SHADE, G_CC_SHADE), - gsSPEndDisplayList(), -}; - -// 0x070242D0 - 0x070242F0 -static const Gfx hmc_seg7_painting_dl_070242D0[] = { - gsDPTileSync(), - gsDPSetTile(G_IM_FMT_RGBA, G_IM_SIZ_16b, 8, 0, G_TX_RENDERTILE, 0, G_TX_WRAP | G_TX_NOMIRROR, 5, G_TX_NOLOD, G_TX_WRAP | G_TX_NOMIRROR, 5, G_TX_NOLOD), - gsDPSetTileSize(0, 0, 0, (32 - 1) << G_TEXTURE_IMAGE_FRAC, (32 - 1) << G_TEXTURE_IMAGE_FRAC), - gsSPEndDisplayList(), -}; - -// 0x070242F0 - 0x07024CD2 -static const PaintingData hmc_seg7_pool_texture_map_070242F0[] = { - 157, // num mappings - // Format: - // mesh vtx ID, texture X, texture Y - 0, 6100, -4832, - 1, 6100, -5142, - 2, 5582, -5142, - 3, 5582, -4526, - 4, 6100, -4218, - 5, 5070, -4832, - 6, 5070, -5142, - 7, 3030, -5142, - 8, 3030, -4832, - 9, 3540, -5142, - 10, 2520, -5142, - 11, 2520, -4526, - 12, 3030, -4218, - 13, 3540, -4526, - 14, 4050, -4832, - 15, 4560, -5142, - 16, 5070, -4218, - 17, 4560, -4526, - 18, 4050, -4218, - 19, 5582, -2074, - 20, 6100, -2380, - 21, 5582, -3300, - 22, 6100, -2994, - 23, 5582, -2686, - 24, 5070, -2380, - 25, 4560, -2074, - 26, 4560, -3300, - 27, 5070, -2994, - 28, 5070, -3606, - 29, 4050, -2380, - 30, 4560, -2686, - 31, 3540, -2074, - 32, 4050, -3606, - 33, 3540, -3300, - 34, 4050, -2994, - 35, 3540, -2686, - 36, 3030, -2380, - 37, 2520, -2074, - 38, 3030, -2994, - 39, 2520, -3300, - 40, 3030, -3606, - 41, 6100, -3606, - 42, 5582, -3912, - 43, 4560, -3912, - 44, 3540, -3912, - 45, 2520, -3912, - 46, 4050, -1768, - 47, 5070, -1768, - 48, 3030, -1768, - 49, 6100, 684, - 50, 6100, 990, - 51, 5582, 990, - 52, 5582, -236, - 53, 6100, 70, - 54, 5070, 684, - 55, 5582, 378, - 56, 4560, 990, - 57, 5070, 990, - 58, 4560, -236, - 59, 5070, 70, - 60, 5070, -542, - 61, 4050, 684, - 62, 4560, 378, - 63, 3540, 990, - 64, 4050, 990, - 65, 4050, 70, - 66, 3540, -236, - 67, 4050, -542, - 68, 3030, 684, - 69, 3540, 378, - 70, 2520, 990, - 71, 3030, 990, - 72, 2520, -236, - 73, 3030, 70, - 74, 3030, -542, - 75, 6100, -542, - 76, 5582, -1462, - 77, 6100, -1154, - 78, 5582, -848, - 79, 4560, -1462, - 80, 5070, -1154, - 81, 4560, -848, - 82, 3540, -1462, - 83, 4050, -1154, - 84, 3540, -848, - 85, 2520, -1462, - 86, 3030, -1154, - 87, 2010, -4832, - 88, 0, -5142, - 89, 0, -4832, - 90, 478, -5142, - 91, 478, -4526, - 92, 988, -4832, - 93, 2010, -4218, - 94, 1498, -4526, - 95, 1498, -5142, - 96, 988, -4218, - 97, 2520, -2686, - 98, 2010, -2380, - 99, 1498, -2074, - 100, 1498, -3300, - 101, 2010, -2994, - 102, 2010, -3606, - 103, 1498, -2686, - 104, 988, -2380, - 105, 478, -2074, - 106, 478, -3300, - 107, 988, -2994, - 108, 988, -3606, - 109, 478, -2686, - 110, 0, -2380, - 111, 0, -3606, - 112, 1498, -3912, - 113, 478, -3912, - 114, 1498, -1462, - 115, 988, -1768, - 116, 2010, -1768, - 117, 0, -1768, - 118, 478, -1462, - 119, 2010, 684, - 120, 2520, 378, - 121, 2010, 990, - 122, 1498, 990, - 123, 2010, -542, - 124, 2010, 70, - 125, 1498, -236, - 126, 988, 684, - 127, 1498, 378, - 128, 988, 990, - 129, 478, 990, - 130, 478, -236, - 131, 988, 70, - 132, 988, -542, - 133, 0, 684, - 134, 478, 378, - 135, 0, -542, - 136, 2520, -848, - 137, 2010, -1154, - 138, 1498, -848, - 139, 988, -1154, - 140, 478, -848, - 141, 4050, -5142, - 142, 6100, -2074, - 143, 6100, -1768, - 144, 5070, -2074, - 145, 4050, -2074, - 146, 3030, -2074, - 147, 2010, -5142, - 148, 0, -4218, - 149, 988, -5142, - 150, 2010, -2074, - 151, 988, -2074, - 152, 0, -2994, - 153, 0, -2074, - 154, 0, -1154, - 155, 0, 70, - 156, 0, 990, - - 264, // num groups - // Grouped by 5 + one remainder group, - // = 15 vertices per group + a few extra triangles - 8, 12, 13, - 0, 1, 2, - 3, 0, 2, - 4, 0, 3, - 5, 2, 6, - 2, 5, 3, - 7, 8, 9, - 8, 7, 10, - 11, 8, 10, - 12, 8, 11, - 9, 8, 13, - 13, 14, 9, - 14, 141, 9, - 5, 6, 15, - 5, 16, 3, - 16, 5, 17, - 17, 5, 15, - 14, 15, 141, - 15, 14, 17, - 18, 14, 13, - 14, 18, 17, - 19, 142, 20, - 19, 20, 23, - 28, 27, 21, - 21, 23, 22, - 22, 41, 21, - 20, 22, 23, - 23, 24, 19, - 21, 27, 23, - 24, 23, 27, - 25, 144, 24, - 19, 24, 144, - 24, 27, 30, - 25, 24, 30, - 26, 30, 27, - 27, 28, 26, - 36, 38, 97, - 26, 34, 30, - 29, 30, 34, - 30, 29, 25, - 25, 29, 145, - 31, 145, 29, - 31, 29, 35, - 29, 34, 35, - 32, 34, 26, - 33, 35, 34, - 34, 32, 33, - 33, 38, 35, - 35, 36, 31, - 36, 35, 38, - 37, 36, 97, - 37, 146, 36, - 31, 36, 146, - 28, 16, 43, - 38, 40, 39, - 39, 97, 38, - 40, 38, 33, - 21, 41, 42, - 41, 4, 42, - 3, 42, 4, - 42, 28, 21, - 28, 42, 16, - 3, 16, 42, - 26, 28, 43, - 17, 43, 16, - 43, 32, 26, - 32, 43, 18, - 17, 18, 43, - 33, 32, 44, - 32, 18, 44, - 13, 44, 18, - 44, 40, 33, - 13, 12, 44, - 40, 44, 12, - 39, 40, 45, - 40, 12, 45, - 48, 31, 146, - 11, 45, 12, - 25, 47, 144, - 46, 25, 145, - 47, 19, 144, - 19, 143, 142, - 31, 46, 145, - 60, 59, 52, - 49, 53, 55, - 50, 49, 51, - 51, 49, 55, - 52, 55, 53, - 53, 75, 52, - 54, 55, 59, - 52, 59, 55, - 55, 54, 51, - 54, 59, 62, - 56, 54, 62, - 57, 54, 56, - 54, 57, 51, - 58, 62, 59, - 59, 60, 58, - 68, 71, 63, - 61, 62, 65, - 58, 65, 62, - 62, 61, 56, - 61, 65, 69, - 63, 61, 69, - 64, 61, 63, - 61, 64, 56, - 65, 67, 66, - 66, 69, 65, - 67, 65, 58, - 68, 69, 73, - 69, 68, 63, - 66, 73, 69, - 68, 73, 120, - 70, 68, 120, - 71, 68, 70, - 72, 120, 73, - 73, 74, 72, - 74, 73, 66, - 75, 77, 78, - 52, 75, 78, - 76, 78, 77, - 77, 143, 76, - 76, 80, 78, - 60, 78, 80, - 78, 60, 52, - 46, 83, 79, - 58, 60, 81, - 60, 80, 81, - 79, 81, 80, - 80, 47, 79, - 47, 80, 76, - 81, 67, 58, - 67, 81, 83, - 79, 83, 81, - 66, 67, 84, - 67, 83, 84, - 82, 84, 83, - 83, 46, 82, - 84, 74, 66, - 82, 86, 84, - 74, 84, 86, - 74, 86, 136, - 72, 74, 136, - 85, 136, 86, - 86, 48, 85, - 48, 86, 82, - 25, 46, 79, - 79, 47, 25, - 82, 46, 31, - 19, 47, 76, - 76, 143, 19, - 31, 48, 82, - 37, 48, 146, - 85, 48, 37, - 10, 87, 11, - 87, 10, 147, - 92, 95, 149, - 88, 89, 90, - 89, 148, 91, - 90, 89, 91, - 91, 92, 90, - 92, 149, 90, - 93, 87, 94, - 87, 93, 11, - 94, 87, 95, - 87, 147, 95, - 95, 92, 94, - 96, 92, 91, - 92, 96, 94, - 39, 101, 97, - 97, 98, 37, - 98, 97, 101, - 99, 98, 103, - 99, 150, 98, - 37, 98, 150, - 98, 101, 103, - 100, 103, 101, - 101, 102, 100, - 102, 101, 39, - 100, 107, 103, - 103, 104, 99, - 104, 103, 107, - 105, 104, 109, - 105, 151, 104, - 99, 104, 151, - 104, 107, 109, - 106, 109, 107, - 107, 108, 106, - 108, 107, 100, - 109, 110, 105, - 106, 152, 109, - 110, 109, 152, - 105, 110, 153, - 111, 152, 106, - 11, 93, 45, - 102, 45, 93, - 45, 102, 39, - 102, 93, 112, - 100, 102, 112, - 94, 112, 93, - 112, 108, 100, - 108, 112, 96, - 94, 96, 112, - 106, 108, 113, - 108, 96, 113, - 91, 113, 96, - 91, 148, 113, - 113, 111, 106, - 111, 113, 148, - 114, 116, 99, - 99, 115, 114, - 115, 99, 151, - 99, 116, 150, - 72, 124, 120, - 116, 37, 150, - 37, 116, 85, - 117, 105, 153, - 105, 115, 151, - 105, 117, 118, - 118, 115, 105, - 119, 120, 124, - 120, 119, 70, - 119, 124, 127, - 119, 121, 70, - 121, 119, 122, - 122, 119, 127, - 123, 124, 72, - 124, 123, 125, - 125, 127, 124, - 126, 127, 131, - 127, 126, 122, - 125, 131, 127, - 126, 131, 134, - 128, 126, 129, - 129, 126, 134, - 126, 128, 122, - 136, 123, 72, - 130, 134, 131, - 131, 132, 130, - 132, 131, 125, - 133, 134, 155, - 134, 133, 129, - 130, 155, 134, - 133, 156, 129, - 135, 155, 130, - 123, 136, 137, - 85, 137, 136, - 139, 115, 118, - 123, 137, 138, - 125, 123, 138, - 114, 138, 137, - 137, 116, 114, - 116, 137, 85, - 114, 139, 138, - 132, 138, 139, - 138, 132, 125, - 132, 139, 140, - 130, 132, 140, - 115, 139, 114, - 118, 140, 139, - 135, 140, 154, - 118, 154, 140, - 140, 135, 130, - 117, 154, 118, -}; - -// 0x07024CD4 -static const PaintingData *const hmc_seg7_painting_texture_maps_07024CD4[] = { - hmc_seg7_pool_texture_map_070242F0, -}; +/// - PAINTING_ID_HMC_COTMC - // 0x07024CE0 - 0x070254E0 -ALIGNED8 static const Texture hmc_seg7_texture_07024CE0[] = { +ALIGNED8 static const Texture hmc_seg7_texture_cotmc_pool_env[] = { #include "levels/hmc/7.rgba16.inc.c" }; -// 0x070254E0 - 0x07025518 -static const Gfx hmc_seg7_painting_dl_070254E0[] = { - gsDPPipeSync(), - gsSPLightColor(LIGHT_1, 0x6464ffff), - gsSPLightColor(LIGHT_2, 0x404080ff), - gsSPVertex(hmc_seg7_vertex_07024228, 4, 0), - gsSP2Triangles( 0, 1, 2, 0x0, 0, 2, 3, 0x0), - gsSPEndDisplayList(), -}; - // 0x07025518 - 0x07025594 -const Texture *const hmc_seg7_painting_textures_07025518[] = { - hmc_seg7_texture_07024CE0, -}; - -// 0x0702551C (PaintingData) -struct Painting cotmc_painting = { - /* id */ 0x000E, - /* Image Count */ 0x01, - /* Texture Type */ PAINTING_ENV_MAP, - /* Floor Status */ 0x00, 0x00 , 0x00 /* which of the painting's nearby special floors Mario's on */, - /* Ripple Status */ 0x00, - /* Rotation */ 270.0f, 0.0f, - /* Position */ 2989.055908f, -4485.120117f, 5135.359863f, - /* curr passive entry */ - /* Ripple Magnitude */ 0.0f, 10.0f, 30.0f, - /* Ripple Decay */ 1.0f, 1.0f, 0.98f, - /* Ripple Rate */ 0.0f, 0.05f, 0.05f, - /* Ripple Dispersion */ 0.0f, 15.0f, 15.0f, - /* Curr Ripple Timer */ 0.0f, - /* Curr Ripple x, y */ 0.0f, 0.0f, - /* Normal DList */ hmc_seg7_painting_dl_070254E0, - /* Texture Maps */ hmc_seg7_painting_texture_maps_07024CD4, - /* Textures */ hmc_seg7_painting_textures_07025518, - /* Texture w, h */ 32, 32, - /* Ripple DList */ hmc_seg7_painting_dl_070242D0, - /* Ripple Trigger */ RIPPLE_TRIGGER_CONTINUOUS, - /* Alpha */ 0xFF, - /* Mario Below */ 0x00, 0x00, 0x00, /* Whether or not Mario is below the painting */ - /* Size */ 723.968018f, +const Texture *const hmc_seg7_painting_textures_cotmc[] = { + hmc_seg7_texture_cotmc_pool_env, +}; + +const struct PaintingImage cotmc_painting = { + .textureArray = hmc_seg7_painting_textures_cotmc, + .imageCount = ARRAY_COUNT(hmc_seg7_painting_textures_cotmc), + .textureWidth = 32, + .textureHeight = 32, + .imageType = PAINTING_IMAGE_TYPE_ENV_MAP, + .rippleTrigger = RIPPLE_TRIGGER_CONTINUOUS, + .shaded = TRUE, + .alpha = 0xFF, + .sizeX = 723.968018f, + .sizeY = 723.968018f, }; diff --git a/levels/hmc/header.h b/levels/hmc/header.h index 9ff10e5f39..8e070392dd 100644 --- a/levels/hmc/header.h +++ b/levels/hmc/header.h @@ -72,10 +72,7 @@ extern const Gfx hmc_seg7_dl_07023090[]; extern const Gfx hmc_seg7_dl_07023BC8[]; extern const Gfx hmc_seg7_dl_07023E10[]; extern const Gfx hmc_seg7_dl_07024110[]; -extern const Gfx hmc_seg7_dl_07024268[]; -extern const Gfx hmc_seg7_dl_070242A0[]; -extern const Texture *const hmc_seg7_painting_textures_07025518[]; -extern struct Painting cotmc_painting; +extern struct PaintingImage cotmc_painting; extern const Collision hmc_seg7_collision_level[]; extern const MacroObject hmc_seg7_macro_objs[]; extern const RoomData hmc_seg7_rooms[]; diff --git a/levels/hmc/script.c b/levels/hmc/script.c index a38c1fb173..96c2b7d871 100644 --- a/levels/hmc/script.c +++ b/levels/hmc/script.c @@ -95,10 +95,11 @@ const LevelScript level_hmc_entry[] = { LOAD_MODEL_FROM_GEO(MODEL_HMC_RED_GRILLS, hmc_geo_000530), AREA(/*index*/ 1, hmc_geo_000B90), - OBJECT(/*model*/ MODEL_NONE, /*pos*/ -7152, 3161, 7181, /*angle*/ 0, 135, 0, /*behParam*/ 0x000A0000, /*beh*/ bhvSpinAirborneWarp), - OBJECT(/*model*/ MODEL_NONE, /*pos*/ 3351, -4690, 4773, /*angle*/ 0, 0, 0, /*behParam*/ 0x340B0000, /*beh*/ bhvWarp), - WARP_NODE(/*id*/ 0x0A, /*destLevel*/ LEVEL_HMC, /*destArea*/ 0x01, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), - WARP_NODE(/*id*/ 0x0B, /*destLevel*/ LEVEL_COTMC, /*destArea*/ 0x01, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), + OBJECT(/*model*/ MODEL_PAINTING, /*pos*/ 2989, -4485, 5135, /*angle*/ 270, 0, 0, /*behParam*/ ((PAINTING_ID_HMC_COTMC << 24) | (0x96 << 16)), /*beh*/ bhvPainting), + OBJECT(/*model*/ MODEL_NONE, /*pos*/ -7152, 3161, 7181, /*angle*/ 0, 135, 0, /*behParam*/ 0x000A0000, /*beh*/ bhvSpinAirborneWarp), + OBJECT(/*model*/ MODEL_NONE, /*pos*/ 3351, -4690, 4773, /*angle*/ 0, 0, 0, /*behParam*/ 0x340B0000, /*beh*/ bhvWarp), + WARP_NODE(/*id*/ 0x0A, /*destLevel*/ LEVEL_HMC, /*destArea*/ 0x01, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), + WARP_NODE(/*id*/ 0x0B, /*destLevel*/ LEVEL_COTMC, /*destArea*/ 0x01, /*destNode*/ 0x0A, /*flags*/ WARP_NO_CHECKPOINT), WARP_NODE(/*id*/ 0xF0, /*destLevel*/ LEVEL_CASTLE, /*destArea*/ 0x03, /*destNode*/ 0x34, /*flags*/ WARP_NO_CHECKPOINT), WARP_NODE(/*id*/ 0xF1, /*destLevel*/ LEVEL_CASTLE, /*destArea*/ 0x03, /*destNode*/ 0x66, /*flags*/ WARP_NO_CHECKPOINT), JUMP_LINK(script_func_local_1), diff --git a/levels/scripts.c b/levels/scripts.c index c2cf6d8a4f..6f8d4c9acd 100644 --- a/levels/scripts.c +++ b/levels/scripts.c @@ -108,6 +108,7 @@ const LevelScript level_main_scripts_entry[] = { LOAD_MODEL_FROM_GEO(MODEL_RED_COIN, red_coin_geo), LOAD_MODEL_FROM_GEO(MODEL_RED_COIN_NO_SHADOW, red_coin_no_shadow_geo), LOAD_MODEL_FROM_GEO(MODEL_NUMBER, number_geo), + LOAD_MODEL_FROM_GEO(MODEL_PAINTING, painting_geo), LOAD_MODEL_FROM_GEO(MODEL_EXPLOSION, explosion_geo), LOAD_MODEL_FROM_GEO(MODEL_DIRT_ANIMATION, dirt_animation_geo), LOAD_MODEL_FROM_GEO(MODEL_CARTOON_STAR, cartoon_star_geo), diff --git a/levels/scripts.h b/levels/scripts.h index dc0196828f..1cafd25273 100644 --- a/levels/scripts.h +++ b/levels/scripts.h @@ -3,6 +3,7 @@ #include "types.h" #include "game/puppycam2.h" +#include "game/paintings.h" // scripts extern const LevelScript level_main_scripts_entry[]; diff --git a/levels/ttm/areas/1/geo.inc.c b/levels/ttm/areas/1/geo.inc.c index 024de077b1..8e87fe75ea 100644 --- a/levels/ttm/areas/1/geo.inc.c +++ b/levels/ttm/areas/1/geo.inc.c @@ -18,8 +18,6 @@ const GeoLayout ttm_geo_000A70[] = { GEO_DISPLAY_LIST(LAYER_OPAQUE, ttm_seg7_dl_0700A120), GEO_DISPLAY_LIST(LAYER_OPAQUE, ttm_seg7_dl_0700A2E0), GEO_RENDER_OBJ(), - GEO_ASM(0, geo_painting_update), - GEO_ASM(PAINTING_ID(0, 2), geo_painting_draw), GEO_ASM(0, geo_movtex_pause_control), GEO_ASM(MOVTEX_TTM_BEGIN_WATERFALL, geo_movtex_draw_nocolor), GEO_ASM(MOVTEX_TTM_END_WATERFALL, geo_movtex_draw_nocolor), diff --git a/levels/ttm/areas/1/painting.inc.c b/levels/ttm/areas/1/painting.inc.c index e83bc73bbc..04af167fc7 100644 --- a/levels/ttm/areas/1/painting.inc.c +++ b/levels/ttm/areas/1/painting.inc.c @@ -1,573 +1,22 @@ #include "game/paintings.h" -// 0x070122F0 - 0x07012308 - -// 0x07012308 - 0x07012388 -static const Vtx ttm_seg7_vertex_07012308[] = { - {{{ 0, 0, 0}, 0, { -32, 992}, {0x00, 0x00, 0x7f, 0xff}}}, - {{{ 614, 0, 0}, 0, { 2012, 992}, {0x00, 0x00, 0x7f, 0xff}}}, - {{{ 614, 307, 0}, 0, { 2012, 0}, {0x00, 0x00, 0x7f, 0xff}}}, - {{{ 0, 307, 0}, 0, { -32, 0}, {0x00, 0x00, 0x7f, 0xff}}}, - {{{ 0, 307, 0}, 0, { -32, 992}, {0x00, 0x00, 0x7f, 0xff}}}, - {{{ 614, 307, 0}, 0, { 2012, 992}, {0x00, 0x00, 0x7f, 0xff}}}, - {{{ 614, 614, 0}, 0, { 2012, -28}, {0x00, 0x00, 0x7f, 0xff}}}, - {{{ 0, 614, 0}, 0, { -32, -28}, {0x00, 0x00, 0x7f, 0xff}}}, -}; - -// 0x07012388 - 0x070123A0 -const Gfx ttm_seg7_dl_07012388[] = { - gsSP2Triangles( 0, 1, 2, 0x0, 0, 2, 3, 0x0), - gsSPEndDisplayList(), -}; - -// 0x070123A0 - 0x070123B8 -const Gfx ttm_seg7_dl_070123A0[] = { - gsSP2Triangles( 4, 5, 6, 0x0, 4, 6, 7, 0x0), - gsSPEndDisplayList(), -}; - -// 0x070123B8 - 0x07012410 -const Gfx ttm_seg7_dl_070123B8[] = { - gsDPPipeSync(), - gsSPSetGeometryMode(G_LIGHTING | G_SHADING_SMOOTH), - gsDPSetCombineMode(G_CC_MODULATERGB, G_CC_MODULATERGB), - gsSPLightColor(LIGHT_1, 0xffffffff), - gsSPLightColor(LIGHT_2, 0x505050ff), - gsDPSetTile(G_IM_FMT_RGBA, G_IM_SIZ_16b, 0, 0, G_TX_LOADTILE, 0, G_TX_WRAP | G_TX_NOMIRROR, G_TX_NOMASK, G_TX_NOLOD, G_TX_WRAP | G_TX_NOMIRROR, G_TX_NOMASK, G_TX_NOLOD), - gsDPTileSync(), - gsDPSetTile(G_IM_FMT_RGBA, G_IM_SIZ_16b, 16, 0, G_TX_RENDERTILE, 0, G_TX_CLAMP, 5, G_TX_NOLOD, G_TX_CLAMP, 6, G_TX_NOLOD), - gsDPSetTileSize(0, 0, 0, (64 - 1) << G_TEXTURE_IMAGE_FRAC, (32 - 1) << G_TEXTURE_IMAGE_FRAC), - gsSPTexture(0xFFFF, 0xFFFF, 0, G_TX_RENDERTILE, G_ON), - gsSPEndDisplayList(), -}; - -// 0x07012410 - 0x07012430 -const Gfx ttm_seg7_dl_07012410[] = { - gsSPTexture(0xFFFF, 0xFFFF, 0, G_TX_RENDERTILE, G_OFF), - gsDPPipeSync(), - gsDPSetCombineMode(G_CC_SHADE, G_CC_SHADE), - gsSPEndDisplayList(), -}; - -// 0x07012430 - 0x07012450 -static const Gfx ttm_seg7_painting_dl_07012430[] = { - gsDPTileSync(), - gsDPSetTile(G_IM_FMT_RGBA, G_IM_SIZ_16b, 16, 0, G_TX_RENDERTILE, 0, G_TX_CLAMP, 5, G_TX_NOLOD, G_TX_CLAMP, 6, G_TX_NOLOD), - gsDPSetTileSize(0, 0, 0, (64 - 1) << G_TEXTURE_IMAGE_FRAC, (32 - 1) << G_TEXTURE_IMAGE_FRAC), - gsSPEndDisplayList(), -}; - -// 0x07012450 - 0x0701296A -static const PaintingData ttm_seg7_painting_texture_map_bottom_07012450[] = { - 85, // num mappings - // Format: - // mesh vtx ID, texture X, texture Y - 49, 2016, 889, - 53, 2016, 685, - 55, 1843, 787, - 50, 2016, 992, - 51, 1843, 992, - 52, 1843, 583, - 75, 2016, 513, - 54, 1671, 889, - 59, 1671, 685, - 62, 1502, 787, - 56, 1502, 992, - 57, 1671, 992, - 58, 1502, 583, - 60, 1671, 513, - 61, 1330, 889, - 65, 1330, 685, - 63, 1162, 992, - 64, 1330, 992, - 66, 1162, 583, - 67, 1330, 513, - 69, 1162, 787, - 68, 989, 889, - 70, 821, 992, - 71, 989, 992, - 73, 989, 685, - 72, 821, 583, - 74, 989, 513, - 77, 2016, 308, - 78, 1843, 410, - 76, 1843, 204, - 81, 1502, 410, - 80, 1671, 308, - 47, 1671, 102, - 79, 1502, 204, - 46, 1330, 102, - 82, 1162, 204, - 83, 1330, 308, - 84, 1162, 410, - 86, 989, 308, - 85, 821, 204, - 48, 989, 102, - 25, 1502, 0, - 31, 1162, 0, - 19, 1843, 0, - 37, 821, 0, - 120, 821, 787, - 119, 649, 889, - 122, 481, 992, - 121, 649, 992, - 124, 649, 685, - 125, 481, 583, - 123, 649, 513, - 127, 481, 787, - 126, 308, 889, - 129, 140, 992, - 128, 308, 992, - 132, 308, 513, - 131, 308, 685, - 130, 140, 583, - 134, 140, 787, - 133, -32, 889, - 135, -32, 513, - 136, 821, 410, - 116, 649, 102, - 137, 649, 308, - 114, 481, 204, - 138, 481, 410, - 139, 308, 308, - 118, 140, 204, - 115, 308, 102, - 140, 140, 410, - 117, -32, 102, - 99, 481, 0, - 105, 140, 0, - 143, 2016, 102, - 145, 1330, 0, - 144, 1671, 0, - 142, 2016, 0, - 146, 989, 0, - 155, -32, 685, - 156, -32, 992, - 154, -32, 308, - 151, 308, 0, - 150, 649, 0, - 153, -32, 0, - - 132, // num groups - // Grouped by 5 + one remainder group, - // = 15 vertices per group + a few extra triangles - 13, 8, 5, - 0, 1, 2, - 3, 0, 4, - 4, 0, 2, - 5, 2, 1, - 1, 6, 5, - 7, 2, 8, - 5, 8, 2, - 2, 7, 4, - 7, 8, 9, - 10, 7, 9, - 11, 7, 10, - 7, 11, 4, - 12, 9, 8, - 8, 13, 12, - 21, 24, 45, - 14, 9, 15, - 12, 15, 9, - 9, 14, 10, - 16, 14, 20, - 17, 14, 16, - 14, 15, 20, - 14, 17, 10, - 15, 19, 18, - 18, 20, 15, - 19, 15, 12, - 20, 21, 16, - 18, 24, 20, - 21, 20, 24, - 22, 21, 45, - 23, 21, 22, - 21, 23, 16, - 24, 26, 25, - 25, 45, 24, - 26, 24, 18, - 6, 27, 28, - 5, 6, 28, - 29, 28, 27, - 27, 74, 29, - 29, 31, 28, - 13, 28, 31, - 28, 13, 5, - 36, 34, 35, - 12, 13, 30, - 13, 31, 30, - 31, 32, 33, - 32, 31, 29, - 33, 30, 31, - 33, 36, 30, - 30, 19, 12, - 19, 30, 36, - 18, 19, 37, - 19, 36, 37, - 34, 36, 33, - 35, 37, 36, - 37, 26, 18, - 35, 38, 37, - 26, 37, 38, - 25, 26, 62, - 26, 38, 62, - 38, 40, 39, - 39, 62, 38, - 40, 38, 35, - 41, 34, 33, - 33, 32, 41, - 42, 34, 75, - 34, 41, 75, - 35, 34, 42, - 32, 43, 76, - 41, 32, 76, - 43, 32, 29, - 29, 74, 43, - 43, 74, 77, - 46, 49, 52, - 42, 40, 35, - 39, 40, 44, - 40, 42, 78, - 44, 40, 78, - 25, 49, 45, - 45, 46, 22, - 46, 45, 49, - 47, 46, 52, - 48, 46, 47, - 46, 48, 22, - 58, 59, 57, - 49, 51, 50, - 50, 52, 49, - 51, 49, 25, - 50, 57, 52, - 52, 53, 47, - 53, 52, 57, - 53, 55, 47, - 54, 53, 59, - 55, 53, 54, - 53, 57, 59, - 56, 57, 50, - 57, 56, 58, - 58, 79, 59, - 59, 60, 54, - 60, 59, 79, - 60, 80, 54, - 61, 79, 58, - 62, 51, 25, - 39, 64, 62, - 51, 62, 64, - 50, 51, 66, - 51, 64, 66, - 63, 64, 39, - 64, 63, 65, - 65, 66, 64, - 66, 56, 50, - 56, 66, 67, - 65, 67, 66, - 58, 56, 70, - 56, 67, 70, - 67, 69, 68, - 68, 70, 67, - 69, 67, 65, - 70, 61, 58, - 68, 81, 70, - 61, 70, 81, - 71, 73, 84, - 71, 81, 68, - 72, 69, 65, - 65, 63, 72, - 68, 69, 73, - 69, 72, 82, - 73, 69, 82, - 44, 63, 39, - 63, 44, 83, - 72, 63, 83, - 73, 71, 68, -}; - - -// 0x0701296C - 0x07012E84 -static const PaintingData ttm_seg7_painting_top_0701296C[] = { - 85, // num mappings - // Format: - // mesh vtx ID, texture X, texture Y - 0, 2016, 72, - 1, 2016, 0, - 2, 1843, 0, - 3, 1843, 174, - 4, 2016, 276, - 5, 1671, 72, - 6, 1671, 0, - 8, 989, 72, - 7, 989, 0, - 10, 821, 0, - 9, 1162, 0, - 11, 821, 174, - 12, 989, 276, - 13, 1162, 174, - 14, 1330, 72, - 15, 1502, 0, - 16, 1671, 276, - 17, 1502, 174, - 18, 1330, 276, - 19, 1843, 992, - 20, 2016, 889, - 22, 2016, 685, - 21, 1843, 583, - 23, 1843, 787, - 24, 1671, 889, - 25, 1502, 992, - 26, 1502, 583, - 27, 1671, 685, - 28, 1671, 481, - 30, 1502, 787, - 29, 1330, 889, - 31, 1162, 992, - 32, 1330, 481, - 33, 1162, 583, - 34, 1330, 685, - 35, 1162, 787, - 36, 989, 889, - 37, 821, 992, - 39, 821, 583, - 38, 989, 685, - 40, 989, 481, - 41, 2016, 481, - 42, 1843, 378, - 43, 1502, 378, - 44, 1162, 378, - 45, 821, 378, - 87, 649, 72, - 88, -32, 0, - 90, 140, 0, - 89, -32, 72, - 92, 308, 72, - 91, 140, 174, - 94, 481, 174, - 93, 649, 276, - 95, 481, 0, - 96, 308, 276, - 97, 821, 787, - 98, 649, 889, - 99, 481, 992, - 102, 649, 481, - 101, 649, 685, - 100, 481, 583, - 103, 481, 787, - 104, 308, 889, - 105, 140, 992, - 108, 308, 481, - 107, 308, 685, - 106, 140, 583, - 110, -32, 889, - 109, 140, 787, - 111, -32, 481, - 112, 481, 378, - 113, 140, 378, - 141, 1330, 0, - 142, 2016, 992, - 144, 1671, 992, - 145, 1330, 992, - 146, 989, 992, - 147, 649, 0, - 148, -32, 276, - 149, 308, 0, - 150, 649, 992, - 151, 308, 992, - 152, -32, 685, - 153, -32, 992, - - 132, // num groups - // Grouped by 5 + one remainder group, - // = 15 vertices per group + a few extra triangles - 10, 7, 13, - 0, 1, 2, - 3, 0, 2, - 4, 0, 3, - 5, 2, 6, - 2, 5, 3, - 7, 8, 9, - 8, 7, 10, - 11, 7, 9, - 12, 7, 11, - 7, 12, 13, - 13, 14, 10, - 14, 73, 10, - 5, 6, 15, - 5, 16, 3, - 16, 5, 17, - 17, 5, 15, - 14, 15, 73, - 15, 14, 17, - 18, 14, 13, - 14, 18, 17, - 19, 74, 20, - 19, 20, 23, - 28, 27, 22, - 21, 41, 22, - 22, 23, 21, - 20, 21, 23, - 23, 24, 19, - 22, 27, 23, - 24, 23, 27, - 19, 24, 75, - 25, 75, 24, - 25, 24, 29, - 24, 27, 29, - 26, 29, 27, - 27, 28, 26, - 31, 36, 77, - 26, 34, 29, - 29, 30, 25, - 30, 29, 34, - 25, 30, 76, - 31, 76, 30, - 31, 30, 35, - 30, 34, 35, - 32, 34, 26, - 33, 35, 34, - 34, 32, 33, - 35, 36, 31, - 33, 39, 35, - 36, 35, 39, - 37, 36, 56, - 36, 39, 56, - 37, 77, 36, - 28, 16, 43, - 38, 56, 39, - 39, 40, 38, - 40, 39, 33, - 22, 41, 42, - 41, 4, 42, - 3, 42, 4, - 42, 28, 22, - 28, 42, 16, - 3, 16, 42, - 26, 28, 43, - 17, 43, 16, - 43, 32, 26, - 32, 43, 18, - 17, 18, 43, - 33, 32, 44, - 32, 18, 44, - 13, 44, 18, - 13, 12, 44, - 44, 40, 33, - 40, 44, 12, - 38, 40, 45, - 40, 12, 45, - 11, 45, 12, - 9, 46, 11, - 46, 9, 78, - 47, 49, 48, - 48, 49, 51, - 49, 79, 51, - 50, 80, 48, - 51, 50, 48, - 57, 56, 60, - 46, 53, 11, - 52, 46, 54, - 53, 46, 52, - 46, 78, 54, - 54, 50, 52, - 50, 54, 80, - 50, 55, 52, - 55, 50, 51, - 38, 60, 56, - 56, 57, 37, - 58, 57, 62, - 57, 60, 62, - 58, 81, 57, - 37, 57, 81, - 59, 60, 38, - 60, 59, 61, - 61, 62, 60, - 62, 63, 58, - 63, 62, 66, - 61, 66, 62, - 63, 66, 69, - 58, 63, 82, - 64, 82, 63, - 64, 63, 69, - 45, 59, 38, - 65, 66, 61, - 66, 65, 67, - 67, 69, 66, - 68, 69, 83, - 69, 68, 64, - 67, 83, 69, - 64, 68, 84, - 70, 83, 67, - 11, 53, 45, - 59, 45, 53, - 59, 53, 71, - 61, 59, 71, - 52, 71, 53, - 52, 55, 71, - 65, 71, 55, - 71, 65, 61, - 65, 55, 72, - 67, 65, 72, - 51, 72, 55, - 70, 72, 79, - 51, 79, 72, - 72, 70, 67, -}; - - -// 0x07012E88 -static const PaintingData *const ttm_seg7_painting_texture_maps_07012E88[] = { - ttm_seg7_painting_texture_map_bottom_07012450, - ttm_seg7_painting_top_0701296C, -}; - -UNUSED static const u64 ttm_unused_0 = 0x0; - - -// 0x07012E98 - 0x07012EF8 -static const Gfx ttm_seg7_painting_dl_07012E98[] = { - gsSPDisplayList(ttm_seg7_dl_070123B8), - gsSPVertex(ttm_seg7_vertex_07012308, 8, 0), - gsDPSetTextureImage(G_IM_FMT_RGBA, G_IM_SIZ_16b, 1, ttm_seg7_texture_07004000), - gsDPLoadSync(), - gsDPLoadBlock(G_TX_LOADTILE, 0, 0, 64 * 32 - 1, CALC_DXT(64, G_IM_SIZ_16b_BYTES)), - gsSPDisplayList(ttm_seg7_dl_07012388), - gsDPSetTextureImage(G_IM_FMT_RGBA, G_IM_SIZ_16b, 1, ttm_seg7_texture_07003000), - gsDPLoadSync(), - gsDPLoadBlock(G_TX_LOADTILE, 0, 0, 64 * 32 - 1, CALC_DXT(64, G_IM_SIZ_16b_BYTES)), - gsSPDisplayList(ttm_seg7_dl_070123A0), - gsSPDisplayList(ttm_seg7_dl_07012410), - gsSPEndDisplayList(), -}; +/// - PAINTING_ID_TTM_SLIDE - // 0x07012EF8 - 0x07012F78 -ALIGNED8 static const Texture *const ttm_seg7_painting_textures_07012EF8[] = { - ttm_seg7_texture_07004000, ttm_seg7_texture_07003000, -}; - -// 0x07012F00 (PaintingData) -struct Painting ttm_slide_painting = { - /* id */ 0x0000, - /* Image Count */ 0x02, - /* Texture Type */ PAINTING_IMAGE, - /* Floor Status */ 0x00, 0x00, 0x00 /* which of the painting's nearby special floors Mario's on */, - /* Ripple Status */ 0x00, - /* Rotation */ 0.0f, 90.0f, - /* Position */ 3072.0f, 921.6f, -819.2f, - /* curr passive entry */ - /* Ripple Magnitude */ 0.0f, 20.0f, 80.0f, - /* Ripple Decay */ 1.0f, 0.9608f, 0.9524f, - /* Ripple Rate */ 0.0f, 0.24f, 0.14f, - /* Ripple Dispersion */ 0.0f, 40.0f, 30.0f, - /* Curr Ripple Timer */ 0.0f, - /* Curr Ripple x, y */ 0.0f, 0.0f, - /* Normal DList */ ttm_seg7_painting_dl_07012E98, - /* Texture Maps */ ttm_seg7_painting_texture_maps_07012E88, - /* Textures */ ttm_seg7_painting_textures_07012EF8, - /* Texture w, h */ 64, 32, - /* Ripple DList */ ttm_seg7_painting_dl_07012430, - /* Ripple Trigger */ RIPPLE_TRIGGER_PROXIMITY, - /* Alpha */ 0xFF, - /* Mario Below */ 0x00, 0x00, 0x00, /* Whether or not Mario is below the painting */ - /* Size */ 460.8f, +ALIGNED8 static const Texture *const ttm_seg7_painting_textures_slide[] = { + ttm_seg7_texture_07004000, + ttm_seg7_texture_07003000, +}; + +const struct PaintingImage ttm_slide_painting = { + .textureArray = ttm_seg7_painting_textures_slide, + .imageCount = ARRAY_COUNT(ttm_seg7_painting_textures_slide), + .textureWidth = 64, + .textureHeight = 32, + .imageType = PAINTING_IMAGE_TYPE_TEXTURE, + .rippleTrigger = RIPPLE_TRIGGER_PROXIMITY, + .shaded = TRUE, + .alpha = 0xFF, + .sizeX = 460.8f, + .sizeY = 460.8f, }; diff --git a/levels/ttm/header.h b/levels/ttm/header.h index 3c06052631..7484b029a4 100644 --- a/levels/ttm/header.h +++ b/levels/ttm/header.h @@ -67,11 +67,7 @@ extern const Gfx ttm_seg7_dl_07011608[]; extern const Gfx ttm_seg7_dl_07011C78[]; extern const Gfx ttm_seg7_dl_07011D78[]; extern const Gfx ttm_seg7_dl_07012270[]; -extern const Gfx ttm_seg7_dl_07012388[]; -extern const Gfx ttm_seg7_dl_070123A0[]; -extern const Gfx ttm_seg7_dl_070123B8[]; -extern const Gfx ttm_seg7_dl_07012410[]; -extern struct Painting ttm_slide_painting; +extern struct PaintingImage ttm_slide_painting; extern const Gfx ttm_seg7_dl_07013430[]; extern const Gfx ttm_seg7_dl_07013608[]; extern const Collision ttm_seg7_collision_pitoune_2[]; diff --git a/levels/ttm/script.c b/levels/ttm/script.c index 899aef6196..1791aac8db 100644 --- a/levels/ttm/script.c +++ b/levels/ttm/script.c @@ -95,7 +95,7 @@ const LevelScript level_ttm_entry[] = { JUMP_LINK(script_func_global_7), LOAD_MODEL_FROM_GEO(MODEL_TTM_SLIDE_EXIT_PODIUM, ttm_geo_000DF4), LOAD_MODEL_FROM_GEO(MODEL_TTM_ROLLING_LOG, ttm_geo_000730), - LOAD_MODEL_FROM_GEO(MODEL_TTM_STAR_CAGE, ttm_geo_000710), + LOAD_MODEL_FROM_GEO(MODEL_TTM_STAR_CAGE, ttm_geo_000710), LOAD_MODEL_FROM_GEO(MODEL_TTM_BLUE_SMILEY, ttm_geo_000D14), LOAD_MODEL_FROM_GEO(MODEL_TTM_YELLOW_SMILEY, ttm_geo_000D4C), LOAD_MODEL_FROM_GEO(MODEL_TTM_STAR_SMILEY, ttm_geo_000D84), @@ -129,9 +129,8 @@ const LevelScript level_ttm_entry[] = { WARP_NODE(/*id*/ 0x14, /*destLevel*/ LEVEL_TTM, /*destArea*/ 0x01, /*destNode*/ 0x14, /*flags*/ WARP_NO_CHECKPOINT), WARP_NODE(/*id*/ 0x15, /*destLevel*/ LEVEL_TTM, /*destArea*/ 0x01, /*destNode*/ 0x16, /*flags*/ WARP_NO_CHECKPOINT), WARP_NODE(/*id*/ 0x16, /*destLevel*/ LEVEL_TTM, /*destArea*/ 0x01, /*destNode*/ 0x15, /*flags*/ WARP_NO_CHECKPOINT), - PAINTING_WARP_NODE(/*id*/ 0x00, /*destLevel*/ LEVEL_TTM, /*destArea*/ 0x02, /*destNode*/ 0x0A, /*flags*/ WARP_CHECKPOINT), - PAINTING_WARP_NODE(/*id*/ 0x01, /*destLevel*/ LEVEL_TTM, /*destArea*/ 0x02, /*destNode*/ 0x0A, /*flags*/ WARP_CHECKPOINT), - PAINTING_WARP_NODE(/*id*/ 0x02, /*destLevel*/ LEVEL_TTM, /*destArea*/ 0x02, /*destNode*/ 0x0A, /*flags*/ WARP_CHECKPOINT), + OBJECT(/*model*/ MODEL_PAINTING, /*pos*/ 3072, 922, -819, /*angle*/ 0, 90, 0, /*behParam*/ ((PAINTING_ID_TTM_SLIDE << 24) | (0x96 << 16)), /*beh*/ bhvPainting), + WARP_NODE(/*id*/ 0x96, /*destLevel*/ LEVEL_TTM, /*destArea*/ 0x02, /*destNode*/ WARP_NODE_MAIN_ENTRY, /*flags*/ WARP_CHECKPOINT), WARP_NODE(/*id*/ 0xF0, /*destLevel*/ LEVEL_CASTLE, /*destArea*/ 0x02, /*destNode*/ 0x34, /*flags*/ WARP_NO_CHECKPOINT), WARP_NODE(/*id*/ 0xF1, /*destLevel*/ LEVEL_CASTLE, /*destArea*/ 0x02, /*destNode*/ 0x66, /*flags*/ WARP_NO_CHECKPOINT), JUMP_LINK(script_func_local_1), diff --git a/src/engine/level_script.c b/src/engine/level_script.c index c7a47e6d65..7ab9a2af8f 100644 --- a/src/engine/level_script.c +++ b/src/engine/level_script.c @@ -33,8 +33,6 @@ #include "config.h" -#define NUM_PAINTINGS 45 - #define CMD_GET(type, offset) (*(type *) (CMD_PROCESS_OFFSET(offset) + (u8 *) sCurrentCmd)) // These are equal @@ -567,28 +565,7 @@ static void level_cmd_set_terrain_type(void) { sCurrentCmd = CMD_NEXT; } -static void level_cmd_create_painting_warp_node(void) { - s32 i; - struct WarpNode *node; - - if (sCurrAreaIndex != -1) { - if (gAreas[sCurrAreaIndex].paintingWarpNodes == NULL) { - gAreas[sCurrAreaIndex].paintingWarpNodes = - alloc_only_pool_alloc(sLevelPool, NUM_PAINTINGS * sizeof(struct WarpNode)); - - for (i = 0; i < NUM_PAINTINGS; i++) { - gAreas[sCurrAreaIndex].paintingWarpNodes[i].id = 0; - } - } - - node = &gAreas[sCurrAreaIndex].paintingWarpNodes[CMD_GET(u8, 2)]; - - node->id = 1; - node->destLevel = CMD_GET(u8, 3) + CMD_GET(u8, 6); - node->destArea = CMD_GET(u8, 4); - node->destNode = CMD_GET(u8, 5); - } - +static void level_cmd_27(void) { sCurrentCmd = CMD_NEXT; } @@ -913,7 +890,7 @@ static void (*LevelScriptJumpTable[])(void) = { /*LEVEL_CMD_PLACE_OBJECT */ level_cmd_place_object, /*LEVEL_CMD_INIT_MARIO */ level_cmd_init_mario, /*LEVEL_CMD_CREATE_WARP_NODE */ level_cmd_create_warp_node, - /*LEVEL_CMD_CREATE_PAINTING_WARP_NODE */ level_cmd_create_painting_warp_node, + /*LEVEL_CMD_27 */ level_cmd_27, /*LEVEL_CMD_CREATE_INSTANT_WARP */ level_cmd_create_instant_warp, /*LEVEL_CMD_LOAD_AREA */ level_cmd_load_area, /*LEVEL_CMD_UNLOAD_AREA */ level_cmd_unload_area, diff --git a/src/engine/math_util.c b/src/engine/math_util.c index bcaca282d9..73790d689e 100644 --- a/src/engine/math_util.c +++ b/src/engine/math_util.c @@ -497,6 +497,41 @@ void mtxf_rotate_xy(Mtx *mtx, s16 angle) { ((s16 *) mtx)[15] = 1; } +/** + * @brief Converts a position in a local frame of reference into the same + * position in global world-space, and stores it in 'destWorldPos'. + * + * @param destWorldPos Where the resulting global world-space position is stored. + * @param srcLocalPos The position in the local frame of reference to convert from. + * @param originPos The origin position of the local frame of reference (in global world-space). + * @param rotation The rotation of the local frame of reference (in global world-space). + */ +void vec3f_local_pos_to_world_pos(Vec3f destWorldPos, Vec3f srcLocalPos, Vec3f originPos, Vec3s rotation) { + Mat4 mtx; + + mtxf_rotate_zxy_and_translate(mtx, srcLocalPos, rotation); + linear_mtxf_mul_vec3f(mtx, destWorldPos, srcLocalPos); + vec3f_add(destWorldPos, originPos); +} + +/** + * @brief Converts a global world-space position into the same position but + * from a local frame of reference, and stores the result in 'destLocalPos'. + * + * @param destLocalPos Where the resulting position in the local frame of reference is stored. + * @param srcWorldPos The position in global world-space to convert from. + * @param originPos The origin position of the local frame of reference (in global world-space). + * @param rotation The rotation of the local frame of reference (in global world-space). + */ +void vec3f_world_pos_to_local_pos(Vec3f destLocalPos, Vec3f srcWorldPos, Vec3f originPos, Vec3s rotation) { + Mat4 mtx; + Vec3f relativePos; + + vec3f_diff(relativePos, srcWorldPos, originPos); + mtxf_rotate_zxy_and_translate(mtx, originPos, rotation); + linear_mtxf_transpose_mul_vec3f(mtx, destLocalPos, relativePos); +} + /** * Similar to approach_s32, but converts to s16 and allows for overflow between 32767 and -32768 */ diff --git a/src/engine/math_util.h b/src/engine/math_util.h index 5554791afe..3006dad592 100644 --- a/src/engine/math_util.h +++ b/src/engine/math_util.h @@ -651,6 +651,10 @@ ALWAYS_INLINE void mtxf_to_mtx(void *dest, void *src) { void mtxf_rotate_xy(Mtx *mtx, s16 angle); +// Local/World pos conversions +void vec3f_local_pos_to_world_pos(Vec3f destWorldPos, Vec3f srcLocalPos, Vec3f originPos, Vec3s rotation); +void vec3f_world_pos_to_local_pos(Vec3f destLocalPos, Vec3f srcWorldPos, Vec3f originPos, Vec3s rotation); + s16 approach_s16(s16 current, s16 target, s16 inc, s16 dec); s32 approach_s32(s32 current, s32 target, s32 inc, s32 dec); f32 approach_f32(f32 current, f32 target, f32 inc, f32 dec); diff --git a/src/engine/surface_load.c b/src/engine/surface_load.c index a68362d698..1358e5f0b2 100644 --- a/src/engine/surface_load.c +++ b/src/engine/surface_load.c @@ -618,11 +618,7 @@ void load_object_surfaces(TerrainData **data, TerrainData *vertexData, u32 dynam TerrainData hasForce = surface_has_force(surfaceType); #endif - s32 flags = surf_has_no_cam_collision(surfaceType) | (dynamic ? SURFACE_FLAG_DYNAMIC : 0); - - // The DDD warp is initially loaded at the origin and moved to the proper - // position in paintings.c and doesn't update its room, so set it here. - RoomData room = (o->behavior == segmented_to_virtual(bhvDddWarp)) ? 5 : 0; + s32 flags = (surf_has_no_cam_collision(surfaceType) | (dynamic ? SURFACE_FLAG_DYNAMIC : 0)); for (i = 0; i < numSurfaces; i++) { struct Surface *surface = read_surface_data(vertexData, data, dynamic); @@ -642,7 +638,7 @@ void load_object_surfaces(TerrainData **data, TerrainData *vertexData, u32 dynam #endif surface->flags |= flags; - surface->room = room; + surface->room = 0; add_surface(surface, dynamic); } diff --git a/src/game/area.c b/src/game/area.c index 1e99763f29..23a3d11e79 100644 --- a/src/game/area.c +++ b/src/game/area.c @@ -196,7 +196,6 @@ void clear_areas(void) { gAreaData[i].surfaceRooms = NULL; gAreaData[i].macroObjects = NULL; gAreaData[i].warpNodes = NULL; - gAreaData[i].paintingWarpNodes = NULL; gAreaData[i].instantWarps = NULL; gAreaData[i].objectSpawnInfos = NULL; gAreaData[i].camera = NULL; diff --git a/src/game/area.h b/src/game/area.h index f6dd36100d..ca8ba30c26 100644 --- a/src/game/area.h +++ b/src/game/area.h @@ -64,19 +64,18 @@ struct Area { /*0x0C*/ RoomData *surfaceRooms; // (set from level script cmd 0x2F) /*0x10*/ MacroObject *macroObjects; // Macro Objects Ptr (set from level script cmd 0x39) /*0x14*/ struct ObjectWarpNode *warpNodes; - /*0x18*/ struct WarpNode *paintingWarpNodes; - /*0x1C*/ struct InstantWarp *instantWarps; - /*0x20*/ struct SpawnInfo *objectSpawnInfos; - /*0x24*/ struct Camera *camera; - /*0x28*/ struct UnusedArea28 *unused; // Filled by level script 0x3A, but is unused. - /*0x2C*/ struct Whirlpool *whirlpools[2]; - /*0x34*/ u8 dialog[2]; // Level start dialog number (set by level script cmd 0x30) - /*0x36*/ u16 musicParam; - /*0x38*/ u16 musicParam2; - /*0x3A*/ u8 useEchoOverride; // Should area echo be overridden using echoOverride? - /*0x3B*/ s8 echoOverride; // Value used to override the area echo values defined in level_defines.h + /*0x18*/ struct InstantWarp *instantWarps; + /*0x1C*/ struct SpawnInfo *objectSpawnInfos; + /*0x20*/ struct Camera *camera; + /*0x24*/ struct UnusedArea28 *unused; // Filled by level script 0x3A, but is unused. + /*0x28*/ struct Whirlpool *whirlpools[2]; + /*0x30*/ u8 dialog[2]; // Level start dialog number (set by level script cmd 0x30) + /*0x32*/ u16 musicParam; + /*0x34*/ u16 musicParam2; + /*0x36*/ u8 useEchoOverride; // Should area echo be overridden using echoOverride? + /*0x37*/ s8 echoOverride; // Value used to override the area echo values defined in level_defines.h #ifdef BETTER_REVERB - /*0x3C*/ u8 betterReverbPreset; + /*0x38*/ u8 betterReverbPreset; #endif }; diff --git a/src/game/behavior_actions.c b/src/game/behavior_actions.c index d400977ab6..2a99f91642 100644 --- a/src/game/behavior_actions.c +++ b/src/game/behavior_actions.c @@ -171,7 +171,6 @@ void spawn_sparkle_particles(s32 n, s32 radius, s32 height, s32 r) { #include "behaviors/bowser_flame.inc.c" #include "behaviors/blue_fish.inc.c" #include "behaviors/checkerboard_platform.inc.c" -#include "behaviors/ddd_warp.inc.c" #include "behaviors/water_pillar.inc.c" #include "behaviors/moat_drainer.inc.c" #include "behaviors/bowser_key_cutscene.inc.c" diff --git a/src/game/behavior_actions.h b/src/game/behavior_actions.h index 1bf0d9c413..bf6a0bb0f2 100644 --- a/src/game/behavior_actions.h +++ b/src/game/behavior_actions.h @@ -172,7 +172,6 @@ void bhv_bowser_key_course_exit_loop(void); void bhv_invisible_objects_under_bridge_init(void); void bhv_water_level_pillar_init(void); void bhv_water_level_pillar_loop(void); -void bhv_ddd_warp_loop(void); void bhv_moat_grills_loop(void); void bhv_rotating_clock_arm_loop(void); void bhv_ukiki_init(void); diff --git a/src/game/behaviors/clock_arm.inc.c b/src/game/behaviors/clock_arm.inc.c index f4005eced1..f0986c27b5 100644 --- a/src/game/behaviors/clock_arm.inc.c +++ b/src/game/behaviors/clock_arm.inc.c @@ -4,36 +4,34 @@ * Main loop of the hour and minute hands of the Tick Tock Clock painting. */ void bhv_rotating_clock_arm_loop(void) { - struct Surface *marioSurface = gMarioState->floor; - u16 rollAngle = o->oFaceAngleRoll; - o->oFloorHeight = gMarioState->floorHeight; + struct Object *paintingObj = gMarioState->paintingObj; - // Seems to make sure Mario is on a default surface & 4 frames pass before - // allowing him to change the Tick Tock Clock speed setting. - // Probably a safety check for when you leave the level through the painting - // to make sure the setting isn't accidentally locked in as you fly out. - if (o->oAction == 0) { - if (marioSurface->type == SURFACE_DEFAULT && o->oTimer >= 4) { - o->oAction++; + if (o->oAction == TTC_PAINTING_CLOCK_ARM_WAIT) { + // Make sure Mario not in a painting & 3 frames pass before allowing him to + // change the Tick Tock Clock speed setting. + // Probably a safety check for when you leave the level through the painting + // to make sure the setting isn't accidentally locked in as you fly out. + if (paintingObj == NULL && o->oTimer > 3) { + o->oAction++; // TTC_PAINTING_CLOCK_ARM_ACT_MOVING } - } else if (o->oAction == 1) { - // If Mario is touching the Tick Tock Clock painting... - if (marioSurface != NULL - && (marioSurface->type == SURFACE_TTC_PAINTING_1 - || marioSurface->type == SURFACE_TTC_PAINTING_2 - || marioSurface->type == SURFACE_TTC_PAINTING_3)) { + } else if (o->oAction == TTC_PAINTING_CLOCK_ARM_ACT_MOVING) { + // If Mario is entering the Tick Tock Clock painting... + if (paintingObj != NULL && GET_BPARAM1(paintingObj->oBehParams) == PAINTING_ID_CASTLE_TTC) { // And this is the minute hand... if (cur_obj_has_behavior(bhvClockMinuteHand)) { + u16 rollAngle = o->oFaceAngleRoll; + // Set Tick Tick Clock's speed based on the angle of the hand. // The angle actually counting down from 0xFFFF to 0 so // 11 o'clock is a small value and 1 o'clock is a large value. - if (rollAngle < 0xAAA) { // > 345 degrees from 12 o'clock. + //! These are not perfectly symmetrical. + if (rollAngle < 0x0AAA) { // > 345 degrees from 12 o'clock. gTTCSpeedSetting = TTC_SPEED_STOPPED; - } else if (rollAngle < 0x6AA4) { // 210..345 degrees from 12 o'clock. + } else if (rollAngle < 0x6AA4) { // 210..345 degrees from 12 o'clock. Should be 0x6AAA. gTTCSpeedSetting = TTC_SPEED_FAST; - } else if (rollAngle < 0x954C) { // 150..210 degrees from 12 o'clock. + } else if (rollAngle < 0x954C) { // 150..210 degrees from 12 o'clock. Should be 0x9555. gTTCSpeedSetting = TTC_SPEED_RANDOM; - } else if (rollAngle < 0xF546) { // 15..150 degrees from 12 o'clock. + } else if (rollAngle < 0xF546) { // 15..150 degrees from 12 o'clock. Should be 0xF555. gTTCSpeedSetting = TTC_SPEED_SLOW; } else { // < 15 degrees from 12 o'clock. gTTCSpeedSetting = TTC_SPEED_STOPPED; @@ -41,12 +39,16 @@ void bhv_rotating_clock_arm_loop(void) { } // Increment the action to stop animating the hands. - o->oAction++; + o->oAction++; // TTC_PAINTING_CLOCK_ARM_ACT_STOPPED + } + } else if (o->oAction == TTC_PAINTING_CLOCK_ARM_ACT_STOPPED) { + if (paintingObj == NULL) { + o->oAction = TTC_PAINTING_CLOCK_ARM_ACT_MOVING; } } // Only rotate the hands until Mario enters the painting. - if (o->oAction < 2) { + if (o->oAction != TTC_PAINTING_CLOCK_ARM_ACT_STOPPED) { cur_obj_rotate_face_angle_using_vel(); } } diff --git a/src/game/behaviors/ddd_warp.inc.c b/src/game/behaviors/ddd_warp.inc.c deleted file mode 100644 index 95b92259c0..0000000000 --- a/src/game/behaviors/ddd_warp.inc.c +++ /dev/null @@ -1,13 +0,0 @@ -// ddd_warp.inc.c - -void bhv_ddd_warp_loop(void) { -#ifndef UNLOCK_ALL - if (gDddPaintingStatus & DDD_FLAG_BOWSERS_SUB_BEATEN) { -#endif - o->collisionData = segmented_to_virtual(inside_castle_seg7_collision_ddd_warp_2); -#ifndef UNLOCK_ALL - } else { - o->collisionData = segmented_to_virtual(inside_castle_seg7_collision_ddd_warp); - } -#endif -} diff --git a/src/game/camera.c b/src/game/camera.c index 8cd629d0af..383960eaca 100644 --- a/src/game/camera.c +++ b/src/game/camera.c @@ -4861,9 +4861,6 @@ u8 get_cutscene_from_mario_status(struct Camera *c) { if (sMarioCamState->cameraEvent == CAM_EVENT_CANNON) { cutscene = CUTSCENE_ENTER_CANNON; } - if (SURFACE_IS_PAINTING_WARP(sMarioGeometry.currFloorType)) { - cutscene = CUTSCENE_ENTER_PAINTING; - } switch (sMarioCamState->action) { case ACT_DEATH_EXIT: cutscene = CUTSCENE_DEATH_EXIT; @@ -6597,14 +6594,14 @@ s16 cutscene_object_without_dialog(u8 cutscene, struct Object *obj) { * @return 0 if not started, 1 if started, and -1 if finished */ s16 cutscene_object(u8 cutscene, struct Object *obj) { - s16 status = 0; + s16 status = CUTSCENE_OBJ_STATUS_NOT_STARTED; - if ((gCamera->cutscene == 0) && (sObjectCutscene == 0)) { + if ((gCamera->cutscene == CUTSCENE_NONE) && (sObjectCutscene == CUTSCENE_NONE)) { if (gRecentCutscene != cutscene) { start_object_cutscene(cutscene, obj); - status = 1; + status = CUTSCENE_OBJ_STATUS_STARTED; } else { - status = -1; + status = CUTSCENE_OBJ_STATUS_FINISHED; } } return status; @@ -9576,40 +9573,37 @@ void cutscene_double_doors_end(struct Camera *c) { sStatusFlags |= CAM_FLAG_SMOOTH_MOVEMENT; } -void cutscene_enter_painting_stub(UNUSED struct Camera *c) { -} - /** * Plays when Mario enters a painting. The camera flies up to the painting's center, then it slowly * zooms in until the star select screen appears. */ void cutscene_enter_painting(struct Camera *c) { - struct Surface *floor, *highFloor; + struct Surface *highFloor; Vec3f paintingPos, focus, focusOffset; Vec3s paintingAngle; - f32 floorHeight; + f32 floorHeight, size; - cutscene_event(cutscene_enter_painting_stub, c, 0, 0); // Zoom in set_fov_function(CAM_FOV_APP_20); sStatusFlags |= CAM_FLAG_SMOOTH_MOVEMENT; - if (gRipplingPainting != NULL) { - paintingAngle[0] = 0; - paintingAngle[1] = (s32)((gRipplingPainting->yaw / 360.f) * 65536.f); // convert degrees to IAU - paintingAngle[2] = 0; + struct Object *ripplingPainting = gCutsceneFocus; - focusOffset[0] = gRipplingPainting->size / 2; - focusOffset[1] = focusOffset[0]; - focusOffset[2] = 0; + if (ripplingPainting != NULL) { + vec3f_copy(paintingPos, &ripplingPainting->oPosVec); + vec3i_to_vec3s(paintingAngle, &ripplingPainting->oFaceAngleVec); + + f32 sizeX = ripplingPainting->header.gfx.scale[0]; + f32 sizeY = ripplingPainting->header.gfx.scale[1]; - paintingPos[0] = gRipplingPainting->posX; - paintingPos[1] = gRipplingPainting->posY; - paintingPos[2] = gRipplingPainting->posZ; + focusOffset[0] = (sizeX * 0.5f); + focusOffset[1] = (sizeY * 0.5f); + focusOffset[2] = 0; offset_rotated(focus, paintingPos, focusOffset, paintingAngle); approach_vec3f_asymptotic(c->focus, focus, 0.1f, 0.1f, 0.1f); - focusOffset[2] = -(((gRipplingPainting->size * 1000.f) / 2) / 307.f); + size = ((sizeX + sizeY) / 2.0f); + focusOffset[2] = -(((size * 1000.f) / 2) / 307.f); offset_rotated(focus, paintingPos, focusOffset, paintingAngle); floorHeight = find_floor(focus[0], focus[1] + 500.f, focus[2], &highFloor) + 125.f; @@ -9622,15 +9616,12 @@ void cutscene_enter_painting(struct Camera *c) { } else { approach_vec3f_asymptotic(c->pos, focus, 0.9f, 0.9f, 0.9f); } - - find_floor(sMarioCamState->pos[0], sMarioCamState->pos[1] + 50.f, sMarioCamState->pos[2], &floor); - - if ((floor->type < SURFACE_PAINTING_WOBBLE_A6) || (floor->type > SURFACE_PAINTING_WARP_F9)) { - c->cutscene = 0; - gCutsceneTimer = CUTSCENE_STOP; - sStatusFlags |= CAM_FLAG_SMOOTH_MOVEMENT; - } + } else { + c->cutscene = CUTSCENE_NONE; + gCutsceneTimer = CUTSCENE_STOP; + sStatusFlags |= CAM_FLAG_SMOOTH_MOVEMENT; } + c->mode = CAMERA_MODE_CLOSE; } @@ -9650,10 +9641,12 @@ void cutscene_exit_painting_start(struct Camera *c) { vec3f_set(sCutsceneVars[2].point, 258.f, -352.f, 1189.f); vec3f_set(sCutsceneVars[1].point, 65.f, -155.f, 444.f); +#ifdef ENABLE_VANILLA_CAM_PROCESSING if (gPrevLevel == LEVEL_TTM) { sCutsceneVars[1].point[1] = 0.f; sCutsceneVars[1].point[2] = 0.f; } +#endif vec3f_copy(sCutsceneVars[0].point, sMarioCamState->pos); sCutsceneVars[0].angle[0] = 0; sCutsceneVars[0].angle[1] = sMarioCamState->faceAngle[1]; @@ -9716,10 +9709,12 @@ void cutscene_exit_painting(struct Camera *c) { cutscene_event(cutscene_exit_painting_move_to_mario, c, 5, -1); cutscene_event(cutscene_exit_painting_move_to_floor, c, 5, -1); +#ifdef ENABLE_VANILLA_CAM_PROCESSING //! Hardcoded position. TTM's painting is close to an opposite wall, so just fix the pos. if (gPrevLevel == LEVEL_TTM) { vec3f_set(c->pos, -296.f, 1261.f, 3521.f); } +#endif update_camera_yaw(c); } diff --git a/src/game/camera.h b/src/game/camera.h index fcd1f59f97..7746b9bab7 100644 --- a/src/game/camera.h +++ b/src/game/camera.h @@ -353,6 +353,12 @@ enum AvoidStatus { AVOID_STATUS_WALL_COVERING_MARIO, }; +enum CutsceneObjectStatus { + CUTSCENE_OBJ_STATUS_FINISHED = -1, + CUTSCENE_OBJ_STATUS_NOT_STARTED, + CUTSCENE_OBJ_STATUS_STARTED, +}; + /** * A copy of player information that is relevant to the camera. */ diff --git a/src/game/geo_misc.h b/src/game/geo_misc.h index 8fcfde5e34..ebd63e3f27 100644 --- a/src/game/geo_misc.h +++ b/src/game/geo_misc.h @@ -71,4 +71,12 @@ extern Gfx *geo_exec_cake_end_screen(s32 callContext, struct GraphNode *node, UN gDPLoadBlock((dl), G_TX_LOADTILE, 0, 0, (width) * (height) - 1, CALC_DXT((width), G_IM_SIZ_16b_BYTES)) \ } +#define gsLoadBlockTexture(width, height, format, image) \ + gsDPSetTextureImage((format), G_IM_SIZ_16b, 1, (image)), \ + gsDPTileSync(), \ + gsDPSetTile((format), G_IM_SIZ_16b, 0, 0, G_TX_LOADTILE, 0, G_TX_NOMIRROR, G_TX_NOMASK, G_TX_NOLOD, \ + G_TX_NOMIRROR, G_TX_NOMASK, G_TX_NOLOD), \ + gsDPLoadSync(), \ + gsDPLoadBlock(G_TX_LOADTILE, 0, 0, (width) * (height) - 1, CALC_DXT((width), G_IM_SIZ_16b_BYTES)) \ + #endif // GEO_MISC_H diff --git a/src/game/level_update.c b/src/game/level_update.c index fc4938fd86..d58f5a133e 100644 --- a/src/game/level_update.c +++ b/src/game/level_update.c @@ -31,6 +31,8 @@ #include "puppycam2.h" #include "puppyprint.h" #include "level_commands.h" +#include "behavior_data.h" +#include "paintings.h" #include "config.h" @@ -569,7 +571,7 @@ void check_instant_warp(void) { s16 music_unchanged_through_warp(s16 arg) { struct ObjectWarpNode *warpNode = area_get_warp_node(arg); - s16 levelNum = warpNode->node.destLevel & 0x7F; + s16 levelNum = (warpNode->node.destLevel & WARP_DEST_LEVEL_NUM_MASK); s16 destArea = warpNode->node.destArea; s16 unchanged = TRUE; @@ -636,49 +638,34 @@ void initiate_warp(s16 destLevel, s16 destArea, s16 destWarpNode, s32 warpFlags) #endif } -// From Surface 0xD3 to 0xFC -#define PAINTING_WARP_INDEX_START 0x00 // Value greater than or equal to Surface 0xD3 -#define PAINTING_WARP_INDEX_FA 0x2A // THI Huge Painting index left -#define PAINTING_WARP_INDEX_END 0x2D // Value less than Surface 0xFD - -/** - * Check if Mario is above and close to a painting warp floor, and return the - * corresponding warp node. - */ -struct WarpNode *get_painting_warp_node(void) { - struct WarpNode *warpNode = NULL; - s32 paintingIndex = gMarioState->floor->type - SURFACE_PAINTING_WARP_D3; - - if (paintingIndex >= PAINTING_WARP_INDEX_START && paintingIndex < PAINTING_WARP_INDEX_END) { - if (paintingIndex < PAINTING_WARP_INDEX_FA - || gMarioState->pos[1] - gMarioState->floorHeight < 80.0f) { - warpNode = &gCurrentArea->paintingWarpNodes[paintingIndex]; - } - } - - return warpNode; -} +_Bool gPaintingEjectSoundPlayed = FALSE; /** * Check is Mario has entered a painting, and if so, initiate a warp. */ void initiate_painting_warp(void) { - if (gCurrentArea->paintingWarpNodes != NULL && gMarioState->floor != NULL) { - struct WarpNode warpNode; - struct WarpNode *pWarpNode = get_painting_warp_node(); + struct Object* paintingObj = gMarioState->paintingObj; + + if (paintingObj != NULL) { + struct ObjectWarpNode* warpNode = area_get_warp_node(GET_BPARAM2(paintingObj->oBehParams)); - if (pWarpNode != NULL) { + if (warpNode != NULL) { if (gMarioState->action & ACT_FLAG_INTANGIBLE) { - play_painting_eject_sound(); - } else if (pWarpNode->id != 0) { - warpNode = *pWarpNode; + // Plays the painting eject sound effect if it has not already been played. + if (!gPaintingEjectSoundPlayed) { + gPaintingEjectSoundPlayed = TRUE; + play_sound(SOUND_GENERAL_PAINTING_EJECT, + gMarioState->marioObj->header.gfx.cameraToObject); + } + } else { + struct WarpNode* node = &warpNode->node; - if (!(warpNode.destLevel & WARP_NO_CHECKPOINT)) { - sWarpCheckpointActive = check_warp_checkpoint(&warpNode); + if (!(node->destLevel & WARP_CHECKPOINT)) { + sWarpCheckpointActive = check_warp_checkpoint(node); } - initiate_warp(warpNode.destLevel & 0x7F, warpNode.destArea, warpNode.destNode, WARP_FLAGS_NONE); - check_if_should_set_warp_checkpoint(&warpNode); + initiate_warp((node->destLevel & WARP_DEST_LEVEL_NUM_MASK), node->destArea, node->destNode, WARP_FLAGS_NONE); + check_if_should_set_warp_checkpoint(node); play_transition_after_delay(WARP_TRANSITION_FADE_INTO_COLOR, 30, 255, 255, 255, 45); level_set_transition(74, basic_update); @@ -687,14 +674,17 @@ void initiate_painting_warp(void) { gMarioState->marioObj->header.gfx.node.flags &= ~GRAPH_RENDER_ACTIVE; - play_sound(SOUND_MENU_STAR_SOUND, gGlobalSoundSource); + play_sound(SOUND_MENU_STAR_SOUND, gMarioState->marioObj->header.gfx.cameraToObject); fadeout_music(398); #if ENABLE_RUMBLE queue_rumble_data(80, 70); queue_rumble_decay(1); #endif + cutscene_object(CUTSCENE_ENTER_PAINTING, paintingObj); } } + } else { + gPaintingEjectSoundPlayed = FALSE; } } @@ -752,8 +742,8 @@ s16 level_trigger_warp(struct MarioState *m, s32 warpOp) { break; case WARP_OP_WARP_FLOOR: - if ((m->floor) && (m->floor->force & 0xFF)) { - sSourceWarpNodeId = m->floor->force & 0xFF; + if (m->floor && (m->floor->force & 0xFF)) { + sSourceWarpNodeId = (m->floor->force & 0xFF); } else { sSourceWarpNodeId = WARP_NODE_WARP_FLOOR; if (area_get_warp_node(sSourceWarpNodeId) == NULL) { @@ -896,7 +886,7 @@ void initiate_delayed_warp(void) { default: warpNode = area_get_warp_node(sSourceWarpNodeId); - initiate_warp(warpNode->node.destLevel & 0x7F, warpNode->node.destArea, + initiate_warp((warpNode->node.destLevel & WARP_DEST_LEVEL_NUM_MASK), warpNode->node.destArea, warpNode->node.destNode, sDelayedWarpArg); check_if_should_set_warp_checkpoint(&warpNode->node); diff --git a/src/game/mario.c b/src/game/mario.c index af26781131..5399954ed8 100644 --- a/src/game/mario.c +++ b/src/game/mario.c @@ -1828,6 +1828,8 @@ void init_mario(void) { gMarioState->riddenObj = NULL; gMarioState->usedObj = NULL; + gMarioState->paintingObj = NULL; + gMarioState->waterLevel = find_water_level(gMarioSpawnInfo->startPos[0], gMarioSpawnInfo->startPos[2]); gMarioState->area = gCurrentArea; diff --git a/src/game/mario_actions_cutscene.c b/src/game/mario_actions_cutscene.c index 06684a9ae3..8378fe66c7 100644 --- a/src/game/mario_actions_cutscene.c +++ b/src/game/mario_actions_cutscene.c @@ -2458,7 +2458,8 @@ static void end_peach_cutscene_run_to_castle(struct MarioState *m) { static void end_peach_cutscene_fade_out(struct MarioState *m) { if (m->actionState == ACT_STATE_END_PEACH_CUTSCENE_FADE_OUT_WARP) { level_trigger_warp(m, WARP_OP_CREDITS_NEXT); - gPaintingMarioYEntry = 1500.0f; // ensure medium water level in WDW credits cutscene + // Ensure medium water level in WDW credits cutscene. + gPaintingMarioYEntry = 194.0f; // This would be a little under one third of the painting's height. m->actionState = ACT_STATE_END_PEACH_CUTSCENE_FADE_OUT_END; } } diff --git a/src/game/moving_texture.c b/src/game/moving_texture.c index 194037c058..b3f740caa4 100644 --- a/src/game/moving_texture.c +++ b/src/game/moving_texture.c @@ -123,7 +123,7 @@ enum MovtexVtxColors { s8 gMovtexVtxColor = MOVTEX_VTX_COLOR_DEFAULT; /// The height at which Mario entered the last painting. Used for Wet-Dry World only. -float gPaintingMarioYEntry = 0.0f; +f32 gPaintingMarioYEntry = 0.0f; /// Variable to ensure the initial Wet-Dry World water level is set only once s32 gWdwWaterLevelSet = FALSE; @@ -261,9 +261,9 @@ Gfx *geo_wdw_set_initial_water_level(s32 callContext, UNUSED struct GraphNode *n gWdwWaterLevelSet = FALSE; } else if (callContext == GEO_CONTEXT_RENDER && gEnvironmentRegions != NULL && !gWdwWaterLevelSet) { - if (gPaintingMarioYEntry <= 1382.4f) { + if (gPaintingMarioYEntry <= 76.4f) { // A little under one Mario height above the bottom of the painting. wdwWaterHeight = 31; - } else if (gPaintingMarioYEntry >= 1600.0f) { + } else if (gPaintingMarioYEntry >= 294.0f) { // A little under half the painting's height. wdwWaterHeight = 2816; } else { wdwWaterHeight = 1024; diff --git a/src/game/object_list_processor.c b/src/game/object_list_processor.c index 5dd018e24e..691d26da8e 100644 --- a/src/game/object_list_processor.c +++ b/src/game/object_list_processor.c @@ -19,6 +19,7 @@ #include "object_list_processor.h" #include "platform_displacement.h" #include "spawn_object.h" +#include "paintings.h" #include "puppyprint.h" #include "profiling.h" @@ -322,18 +323,26 @@ s32 update_objects_during_time_stop(struct ObjectNode *objList, struct ObjectNod // Selectively unfreeze certain objects if (!(gTimeStopState & TIME_STOP_ALL_OBJECTS)) { - if (gCurrentObject == gMarioObject && !(gTimeStopState & TIME_STOP_MARIO_AND_DOORS)) { + if (gCurrentObject->activeFlags & (ACTIVE_FLAG_UNIMPORTANT | ACTIVE_FLAG_INITIATED_TIME_STOP)) { unfrozen = TRUE; } - if ((gCurrentObject->oInteractType & (INTERACT_DOOR | INTERACT_WARP_DOOR)) - && !(gTimeStopState & TIME_STOP_MARIO_AND_DOORS)) { - unfrozen = TRUE; - } - - if (gCurrentObject->activeFlags - & (ACTIVE_FLAG_UNIMPORTANT | ACTIVE_FLAG_INITIATED_TIME_STOP)) { - unfrozen = TRUE; + if (!(gTimeStopState & TIME_STOP_MARIO_AND_DOORS)) { + // Mario + if (gCurrentObject == gMarioObject) { + unfrozen = TRUE; + } + + // Doors + if (gCurrentObject->oInteractType & (INTERACT_DOOR | INTERACT_WARP_DOOR)) { + unfrozen = TRUE; + } + + // Paintings + // HackerSM64 TODO: Make this an object flag. + if (cur_obj_has_behavior(bhvPainting)) { + unfrozen = TRUE; + } } } diff --git a/src/game/paintings.c b/src/game/paintings.c index 31d78a61fb..8506e8b032 100644 --- a/src/game/paintings.c +++ b/src/game/paintings.c @@ -18,1258 +18,971 @@ #include "paintings.h" #include "save_file.h" #include "segment2.h" +#include "rendering_graph_node.h" /** * @file paintings.c * - * Implements the rippling painting effect. Paintings are GraphNodes that exist without being connected - * to any particular object. + * Implements the rippling painting effect. Paintings are GraphNodes that are attached to a bhvPainting object. * * Paintings are defined in level data. Look at levels/castle_inside/painting.inc.c for examples. * * The ripple effect uses data that is split into several parts: - * The mesh positions are generated from a base mesh. See seg2_painting_triangle_mesh near the - * bottom of bin/segment2.c - * - * The lighting for the ripple is also generated from a base table, seg2_painting_mesh_neighbor_tris - * in bin/segment2.c - * - * Each painting's texture uses yet another table to map its texture to the mesh. - * These maps are in level data, see levels/castle_inside/painting.inc.c for example. - * - * Finally, each painting has two display lists, normal and rippling, which are defined in the same - * level data file as the Painting itself. See levels/castle_inside/painting.inc.c. - * - * - * Painting state machine: - * Paintings spawn in the PAINTING_IDLE state - * From IDLE, paintings can change to PAINTING_RIPPLE or PAINTING_ENTERED - * - This state checks for ENTERED because if Mario waits long enough, a PROXIMITY painting could - * reset to IDLE - * - * Paintings in the PAINTING_RIPPLE state are passively rippling. - * For RIPPLE_TRIGGER_PROXIMITY paintings, this means Mario bumped the wall in front of the - * painting. - * - * Paintings that use RIPPLE_TRIGGER_CONTINUOUS try to transition to this state as soon as possible, - * usually when Mario enters the room. - * - * A PROXIMITY painting will automatically reset to IDLE if its ripple magnitude becomes small - * enough. - * - * Paintings in the PAINTING_ENTERED state have been entered by Mario. - * A CONTINUOUS painting will automatically reset to RIPPLE if its ripple magnitude becomes small - * enough. - */ - -/** - * Triggers a passive ripple on the left side of the painting. - */ -#define RIPPLE_LEFT 0x20 - -/** - * Triggers a passive ripple in the middle the painting. - */ -#define RIPPLE_MIDDLE 0x10 - -/** - * Triggers a passive ripple on the right side of the painting. - */ -#define RIPPLE_RIGHT 0x8 + * In bin/segment2.c: + * painting_data_vertices: The mesh positions are generated from a base mesh. + * painting_data_mesh_neighbor_tris: The lighting for the ripple is also generated from a base table. + * Each painting's texture uses yet another table to determine the order to map its texture to the mesh. + * In levels/[LEVEL]/painting.inc.c: + * PaintingImage structs, texture pointers. + * + * Painting actions: + * Paintings spawn in the PAINTING_ACT_IDLE action + * From PAINTING_ACT_IDLE, paintings can change to PAINTING_ACT_RIPPLING or PAINTING_ACT_ENTERED + * - This action checks for PAINTING_ACT_ENTERED because if Mario waits long enough, a RIPPLE_TRIGGER_PROXIMITY painting could reset to PAINTING_ACT_IDLE + * + * Paintings in PAINTING_ACT_RIPPLING are passively rippling. + * For RIPPLE_TRIGGER_PROXIMITY paintings, this means Mario bumped the front of the painting. + * + * Paintings that use RIPPLE_TRIGGER_CONTINUOUS try to transition to this action as soon as possible, usually when Mario enters the room. + * + * A PROXIMITY painting will automatically reset to PAINTING_ACT_IDLE if its ripple magnitude becomes small enough. + * + * Paintings in PAINTING_ACT_ENTERED have been entered by Mario. + * A CONTINUOUS painting will automatically reset to PAINTING_ACT_RIPPLING if its ripple magnitude becomes small enough. + */ + +/** + * Array of pointers to painting image data structs. + */ +const struct PaintingImage* sPaintings[] = { + [PAINTING_ID_NULL ] = NULL, + [PAINTING_ID_CASTLE_BOB ] = &bob_painting, + [PAINTING_ID_CASTLE_CCM ] = &ccm_painting, + [PAINTING_ID_CASTLE_WF ] = &wf_painting, + [PAINTING_ID_CASTLE_JRB ] = &jrb_painting, + [PAINTING_ID_CASTLE_LLL ] = &lll_painting, + [PAINTING_ID_CASTLE_SSL ] = &ssl_painting, + [PAINTING_ID_CASTLE_HMC ] = &hmc_painting, + [PAINTING_ID_CASTLE_DDD ] = &ddd_painting, + [PAINTING_ID_CASTLE_WDW ] = &wdw_painting, + [PAINTING_ID_CASTLE_THI_TINY] = &thi_tiny_painting, + [PAINTING_ID_CASTLE_TTM ] = &ttm_painting, + [PAINTING_ID_CASTLE_TTC ] = &ttc_painting, + [PAINTING_ID_CASTLE_SL ] = &sl_painting, + [PAINTING_ID_CASTLE_THI_HUGE] = &thi_huge_painting, + [PAINTING_ID_CASTLE_RR ] = &rr_painting, + [PAINTING_ID_HMC_COTMC ] = &cotmc_painting, + [PAINTING_ID_TTM_SLIDE ] = &ttm_slide_painting, +}; /** - * Triggers an entry ripple on the left side of the painting. - */ -#define ENTER_LEFT 0x4 + * A list of preset constants for the ripple animations. + */ +const struct RippleAnimationPair sRippleAnimations[] = { + [RIPPLE_ANIM_CONTINUOUS] = { + .passive = { .mag = 10.0f, .decay = 1.0f, .rate = 0.05f, .dispersion = 15.0f }, + .entry = { .mag = 30.0f, .decay = 0.98f, .rate = 0.05f, .dispersion = 15.0f }, + }, + [RIPPLE_ANIM_PROXIMITY] = { + .passive = { .mag = 20.0f, .decay = 0.9608f, .rate = 0.24f, .dispersion = 40.0f }, + .entry = { .mag = 80.0f, .decay = 0.9524f, .rate = 0.14f, .dispersion = 30.0f }, + }, + [RIPPLE_ANIM_PROXIMITY_LARGE] = { + .passive = { .mag = 40.0f, .decay = 0.9608f, .rate = 0.12f, .dispersion = 80.0f }, + .entry = { .mag = 160.0f, .decay = 0.9524f, .rate = 0.07f, .dispersion = 60.0f }, + }, +}; -/** - * Triggers an entry ripple in the middle of the painting. - */ -#define ENTER_MIDDLE 0x2 -/** - * Triggers an entry ripple on the right side of the painting. - */ -#define ENTER_RIGHT 0x1 +/// - DRAW - /** - * Use the 1/4th part of the painting that is nearest to Mario's current floor. + * Allocates and generates a mesh for the rippling painting effect by modifying the passed in `mesh` + * based on the painting's current ripple state. + * + * The `mesh` table describes the location of mesh vertices, whether they move when rippling, and what + * triangles they belong to. + * + * The static mesh passed in is organized into two lists. This function only uses the first list, + * painting_calculate_triangle_normals below uses the second one. + * + * The first list describes the vertices in this format: + * numVertices + * v0 x, v0 y, movable + * ... + * vN x, vN y, movable + * Where x and y are from 0 to PAINTING_SIZE, movable is 0 or 1. + * + * The mesh used in game, painting_data_vertices, is in bin/segment2.c. */ -#define NEAREST_4TH 30 +void painting_generate_mesh(struct Object* obj, const PaintingData* vtxData, PaintingData numVtx, struct PaintingMeshVertex* paintingMesh) { + const struct RippleAnimation* objRippleAnim = obj->oPaintingRippleAnimation; + PaintingData i, tri; -/** - * Use Mario's relative x position. - * @see painting_mario_x - */ -#define MARIO_X 40 + /// Controls the peaks of the ripple. + f32 rippleMag = obj->oPaintingCurrRippleMag; + /// Controls the ripple's frequency. + f32 rippleRate = objRippleAnim->rate; + /// Controls how fast the ripple spreads. + f32 dispersionFactor = (1.0f / objRippleAnim->dispersion); + /// How far the ripple has spread. + f32 rippleTimer = obj->oPaintingRippleTimer; + + /// X and Y of the ripple origin. + f32 rippleX = obj->oPaintingRipplePosX; + f32 rippleY = obj->oPaintingRipplePosY; + + f32 sizeRatioX = (obj->header.gfx.scale[0] / PAINTING_SIZE); + f32 sizeRatioY = (obj->header.gfx.scale[1] / PAINTING_SIZE); + + f32 dx, dy; + f32 rippleDistance; -/** - * Use the x center of the painting. - */ -#define MIDDLE_X 50 + PaintingData vtxX, vtxY; -/** - * Use Mario's relative y position. - * @see painting_mario_y - */ -#define MARIO_Y 60 + // Loop through all the painting vertices and calculate the ripple magnitude at each point. + // Accesses are off by 1 since the first entry is the number of vertices. + for (i = 0; i < numVtx; i++) { + tri = (i * 3); + + vtxX = vtxData[tri + 1]; + vtxY = vtxData[tri + 2]; + + paintingMesh->pos[0] = vtxX; + paintingMesh->pos[1] = vtxY; + // The "Z coordinate" of each vertex in painting_data_vertices is either 1 or 0. + // Instead of being an actual coordinate, it just determines whether the vertex can move or not. + if (vtxData[tri + 3]) { + // Scale and calculate the distance to the ripple origin. + dx = ((vtxX * sizeRatioX) - rippleX); + dy = ((vtxY * sizeRatioY) - rippleY); + // A larger dispersionFactor makes the ripple spread slower. + rippleDistance = sqrtf(sqr(dx) + sqr(dy)) * dispersionFactor; + + if (rippleTimer < rippleDistance) { + // If the ripple hasn't reached the point yet, make the point magnitude 0. + paintingMesh->pos[2] = 0; + } else { + // Use a cosine wave to make the ripple go up and down, + // scaled by the painting's ripple magnitude, + // round it to an int and return it. + paintingMesh->pos[2] = roundf(rippleMag * coss((u16)((rippleRate * (rippleTimer - rippleDistance)) * (f32)0x10000))); + } + } else { + paintingMesh->pos[2] = 0; + } -/** - * Use Mario's relative z position. - * @see painting_mario_z - */ -#define MARIO_Z 70 + paintingMesh++; + } +} /** - * Use the y center of the painting. + * Calculate the surface normals of each triangle in the generated ripple mesh. + * + * The static mesh passed in is organized into two lists. This function uses the second list, + * painting_generate_mesh above uses the first one. + * + * The second list in `mesh` describes the mesh's triangles in this format: + * numTris + * tri0 v0, tri0 v1, tri0 v2 + * ... + * triN v0, triN v1, triN v2 + * Where each v0, v1, v2 is an index into the first list in `mesh`. + * + * The mesh used in game, painting_data_vertices, is in bin/segment2.c. */ -#define MIDDLE_Y 80 +void painting_calculate_triangle_normals(const PaintingData* triangleData, struct PaintingNeighborTris* neighborTris, struct PaintingMeshVertex* paintingMesh, Vec3f* paintingTriNorms) { + struct PaintingNeighborTris* vtn = NULL; + PaintingData i, j; + PaintingData numTris = *triangleData++; + Vec3f vp[3]; // Vertex positions -/** - * Does nothing to the timer. - * Why -56 instead of false? Who knows. - */ -#define DONT_RESET -56 + for (i = 0; i < numTris; i++) { + // Get the 3 vertices from the triangle. + for (j = 0; j < 3; j++) { + vec3s_to_vec3f(vp[j], paintingMesh[triangleData[j]].pos); + + // Add the current triangle to each vertex's neighbors list. + vtn = &neighborTris[triangleData[j]]; + if (vtn->numNeighbors < ARRAY_COUNT(vtn->neighborTris)) { + vtn->neighborTris[vtn->numNeighbors++] = i; + } + } -/** - * Reset the timer to 0. - */ -#define RESET_TIMER 100 + // Cross product to find each triangle's normal vector. + find_vector_perpendicular_to_plane(paintingTriNorms[i], vp[0], vp[1], vp[2]); -/// A copy of the type of floor Mario is standing on. -s16 gPaintingMarioFloorType; -// A copy of Mario's position -f32 gPaintingMarioXPos; -f32 gPaintingMarioYPos; -f32 gPaintingMarioZPos; + triangleData += 3; + } +} /** - * When a painting is rippling, this mesh is generated each frame using the Painting's parameters. + * Approximates the painting mesh's vertex normals by averaging the normals of all triangles sharing a + * vertex. Used for Gouraud lighting. + * + * After each triangle's surface normal is calculated, the `neighborTris` table describes which triangles + * each vertex should use when calculating the average normal vector. + * + * The table is a list of entries in this format: + * numNeighbors, tri0, tri1, ..., triN + * + * Where each 'tri' is an index into paintingTriNorms. + * Entry i in `neighborTris` corresponds to the vertex at paintingMesh[i] * - * This mesh only contains the vertex positions and normals. - * Paintings use an additional array to map textures to the mesh. + * The table used in game, painting_data_mesh_neighbor_tris, is in bin/segment2.c. */ -struct PaintingMeshVertex *gPaintingMesh; +void painting_average_vertex_normals(struct PaintingNeighborTris* neighborTris, PaintingData numVtx, struct PaintingMeshVertex* paintingMesh, Vec3f* paintingTriNorms) { + PaintingData tri; + PaintingData i, j; + PaintingData numNeighbors; -/** - * The painting's surface normals, used to approximate each of the vertex normals (for gouraud shading). - */ -Vec3f *gPaintingTriNorms; + for (i = 0; i < numVtx; i++) { + Vec3f n = { 0.0f, 0.0f, 0.0f }; -/** - * The painting that is currently rippling. Only one painting can be rippling at once. - */ -struct Painting *gRipplingPainting; + // The first number of each entry is the number of adjacent tris. + struct PaintingNeighborTris* vtn = &neighborTris[i]; + numNeighbors = vtn->numNeighbors; -/** - * Whether the DDD painting is moved forward, should being moving backwards, or has already moved backwards. - */ -s8 gDddPaintingStatus; + // Average the surface normals from each neighboring tri. + for (j = 0; j < numNeighbors; j++) { + tri = vtn->neighborTris[j]; + vec3f_add(n, paintingTriNorms[tri]); + } -struct Painting *sHmcPaintings[] = { - &cotmc_painting, - NULL, -}; + n[0] /= numNeighbors; + n[1] /= numNeighbors; + n[2] /= numNeighbors; -struct Painting *sInsideCastlePaintings[] = { - &bob_painting, &ccm_painting, &wf_painting, &jrb_painting, &lll_painting, - &ssl_painting, &hmc_painting, &ddd_painting, &wdw_painting, &thi_tiny_painting, - &ttm_painting, &ttc_painting, &sl_painting, &thi_huge_painting, NULL, -}; + f32 nlen = vec3_sumsq(n); -struct Painting *sTtmPaintings[] = { - &ttm_slide_painting, - NULL, -}; + if (FLT_IS_NONZERO(nlen)) { + nlen = (127.0f / sqrtf(nlen)); + paintingMesh[i].norm[0] = (n[0] * nlen); + paintingMesh[i].norm[1] = (n[1] * nlen); + paintingMesh[i].norm[2] = (n[2] * nlen); + } else { + vec3_zero(paintingMesh[i].norm); + } + } +} -struct Painting **sPaintingGroups[] = { - sHmcPaintings, - sInsideCastlePaintings, - sTtmPaintings, -}; +#ifdef F3DEX_GBI_2 + #define VTX_BUF_MAX 32 +#else + #define VTX_BUF_MAX 16 +#endif +#define TRI_PER_GRP (VTX_BUF_MAX / 3) // Rounded, 5 or 10 +#define VTX_PER_GRP (TRI_PER_GRP * 3) // Rounded, 15 or 30 + +/** + * Creates a display list that draws the rippling painting, with 'img' mapped to the painting's mesh, using 'triangleMap'. + * + * If the triangleMap doesn't describe the whole mesh, then multiple calls are needed to draw the whole painting. + * + * TODO: Automatically create seams between segments based on the image count. + */ +Gfx* render_painting_segment(const Texture* img, s16 index, s16 imageCount, s16 tWidth, s16 tHeight, struct PaintingMeshVertex* paintingMesh, const PaintingData* triangleMap, PaintingData numTris, Alpha alpha) { + struct PaintingMeshVertex* currVtx = NULL; + PaintingData group; + PaintingData groupIndex; + PaintingData map; + PaintingData triGroup; + + // We can fit VTX_PER_GRP vertices in the RSP's vertex buffer. + // Group triangles by TRI_PER_GRP, with one remainder group. + PaintingData triGroups = (numTris / TRI_PER_GRP); + PaintingData remGroupTris = (numTris % TRI_PER_GRP); + PaintingData numVtx = (numTris * 3); // 3 verts per tri + + Vtx* verts = alloc_display_list(numVtx * sizeof(Vtx)); + Gfx* dlist = alloc_display_list( + SIZEOF_GFX_CMD(LoadBlockTexture(0,0,0,0)) + + (triGroups * ( + SIZEOF_GFX_CMD(SPVertex(0,0,0)) + + SIZEOF_GFX_CMD(SPDisplayList(0)) + )) + + SIZEOF_GFX_CMD(SPVertex(0,0,0)) + + (remGroupTris * ( + SIZEOF_GFX_CMD(SP1Triangle(0,0,0,0)) + )) + + SIZEOF_GFX_CMD(SPEndDisplayList()) + ); + Gfx* gfx = dlist; -s16 gPaintingUpdateCounter = 1; -s16 gLastPaintingUpdateCounter = 0; + gLoadBlockTexture(gfx++, tWidth, tHeight, G_IM_FMT_RGBA, img); -/** - * Stop paintings in paintingGroup from rippling if their id is different from *idptr. - */ -void stop_other_paintings(s16 *idptr, struct Painting *paintingGroup[]) { - s16 index; - s16 id = *idptr; + // Width and height of each section. + const f32 dx = (PAINTING_SIZE / 1); + const f32 dy = (PAINTING_SIZE / imageCount); + + // These are used to scale the texture positions into vertex positions. + const f32 tWidthScale = (TC(tWidth ) / dx); + const f32 tHeightScale = (TC(tHeight) / dy); - index = 0; - while (paintingGroup[index] != NULL) { - struct Painting *painting = segmented_to_virtual(paintingGroup[index]); + // Bottom Y position of the current section. + const s16 y2 = ((index + 1) * dy); - // stop all rippling except for the selected painting - if (painting->id != id) { - painting->state = 0; + // Draw the groups of TRI_PER_GRP first. + for (group = 0; group < triGroups; group++) { + // The index of the first vertex in the group. + groupIndex = (group * VTX_PER_GRP); + + // Each group is a list of VTX_PER_GRP mappings. + triGroup = (1 + groupIndex); + + // Vertices within the group + for (map = 0; map < VTX_PER_GRP; map++) { + // Get a pointer to the current vertex. + currVtx = &paintingMesh[triangleMap[triGroup + map]]; + make_vertex(verts, (groupIndex + map), + currVtx->pos[0], + currVtx->pos[1], + currVtx->pos[2], + (currVtx->pos[0] * tWidthScale), + ((y2 - currVtx->pos[1]) * tHeightScale), + currVtx->norm[0], + currVtx->norm[1], + currVtx->norm[2], + alpha + ); } - index++; - } -} -/** - * @return Mario's y position inside the painting (bounded). - */ -f32 painting_mario_y(struct Painting *painting) { - // Add 50 to make the ripple closer to Mario's center of mass. - f32 relY = gPaintingMarioYPos - painting->posY + 50.0f; - - if (relY < 0.0f) { - relY = 0.0f; - } else if (relY > painting->size) { - relY = painting->size; + // Load the vertices and draw the TRI_PER_GRP triangles. + gSPVertex(gfx++, VIRTUAL_TO_PHYSICAL(verts + groupIndex), VTX_PER_GRP, 0); + gSPDisplayList(gfx++, dl_paintings_ripple_triangles); } - return relY; -} -/** - * @return Mario's z position inside the painting (bounded). - */ -f32 painting_mario_z(struct Painting *painting) { - f32 relZ = painting->posZ - gPaintingMarioZPos; + // One group left with < TRI_PER_GRP triangles. + triGroup = (1 + (triGroups * VTX_PER_GRP)); - if (relZ < 0.0f) { - relZ = 0.0f; - } else if (relZ > painting->size) { - relZ = painting->size; + // Map the texture to the triangles. + for (map = 0; map < (remGroupTris * 3); map++) { + // Get a pointer to the current vertex. + currVtx = &paintingMesh[triangleMap[triGroup + map]]; + make_vertex(verts, ((triGroups * VTX_PER_GRP) + map), + currVtx->pos[0], + currVtx->pos[1], + currVtx->pos[2], + (currVtx->pos[0] * tWidthScale), + ((y2 - currVtx->pos[1]) * tHeightScale), + currVtx->norm[0], + currVtx->norm[1], + currVtx->norm[2], + alpha + ); } - return relZ; -} -/** - * @return The y origin for the ripple, based on ySource. - * For floor paintings, the z-axis is treated as y. - */ -f32 painting_ripple_y(struct Painting *painting, s8 ySource) { - switch (ySource) { - case MARIO_Y: - return painting_mario_y(painting); // normal wall paintings - break; - case MARIO_Z: - return painting_mario_z(painting); // floor paintings use X and Z - break; - case MIDDLE_Y: - return painting->size / 2.0; // some concentric ripples don't care about Mario - break; - } - return 0.0f; -} + // Draw the remaining triangles individually. + gSPVertex(gfx++, VIRTUAL_TO_PHYSICAL(verts + (triGroups * VTX_PER_GRP)), (remGroupTris * 3), 0); -/** - * Return the quarter of the painting that is closest to the floor Mario entered. - */ -f32 painting_nearest_4th(struct Painting *painting) { - f32 firstQuarter = painting->size / 4.0; // 1/4 of the way across the painting - f32 secondQuarter = painting->size / 2.0; // 1/2 of the way across the painting - f32 thirdQuarter = painting->size * 3.0 / 4.0; // 3/4 of the way across the painting - - if (painting->floorEntered & RIPPLE_LEFT) { - return firstQuarter; - } else if (painting->floorEntered & RIPPLE_MIDDLE) { - return secondQuarter; - } else if (painting->floorEntered & RIPPLE_RIGHT) { - return thirdQuarter; - - // Same as ripple floors. - } else if (painting->floorEntered & ENTER_LEFT) { - return firstQuarter; - } else if (painting->floorEntered & ENTER_MIDDLE) { - return secondQuarter; - } else if (painting->floorEntered & ENTER_RIGHT) { - return thirdQuarter; + for (group = 0; group < (remGroupTris * 3); group += 3) { + gSP1Triangle(gfx++, + (group + 0), + (group + 1), + (group + 2), + 0x0 + ); } - return 0.0f; -} - -/** - * @return Mario's x position inside the painting (bounded). - */ -f32 painting_mario_x(struct Painting *painting) { - f32 relX = gPaintingMarioXPos - painting->posX; + gSPEndDisplayList(gfx); - if (relX < 0.0f) { - relX = 0.0f; - } else if (relX > painting->size) { - relX = painting->size; - } - return relX; + return dlist; } +#undef VTX_BUF_MAX +#undef TRI_PER_GRP +#undef VTX_PER_GRP + /** - * @return The x origin for the ripple, based on xSource. + * Gets the exponent of an integer by converting it into a float and extracting the exponent bits. + * Equivalent to log2(x) or __builtin_ctz(x) but faster. */ -f32 painting_ripple_x(struct Painting *painting, s8 xSource) { - switch (xSource) { - case NEAREST_4TH: // normal wall paintings - return painting_nearest_4th(painting); - break; - case MARIO_X: // horizontally placed paintings use X and Z - return painting_mario_x(painting); - break; - case MIDDLE_X: // concentric rippling may not care about Mario - return painting->size / 2.0f; - break; - } - - return 0.0f; +static s32 get_exponent(s32 x) { + IEEE754_f32 val = { .asF32 = x }; + return (val.exponent - 127); } /** - * Set the painting's state, causing it to start a passive ripple or a ripple from Mario entering. - * - * @param state The state to enter - * @param painting,paintingGroup identifies the painting that is changing state - * @param xSource,ySource what to use for the x and y origin of the ripple - * @param resetTimer if 100, set the timer to 0 + * Set up the texture format in the display list. */ -void painting_state(s8 state, struct Painting *painting, struct Painting *paintingGroup[], - s8 xSource, s8 ySource, s8 resetTimer) { - // make sure no other paintings are rippling - stop_other_paintings(&painting->id, paintingGroup); - - // use a different set of variables depending on the state - switch (state) { - case PAINTING_RIPPLE: - painting->currRippleMag = painting->passiveRippleMag; - painting->rippleDecay = painting->passiveRippleDecay; - painting->currRippleRate = painting->passiveRippleRate; - painting->dispersionFactor = painting->passiveDispersionFactor; - break; +void painting_setup_textures(Gfx** gfx, s16 tWidth, s16 tHeight, _Bool isEnvMap) { + s16 cm = (isEnvMap ? (G_TX_WRAP | G_TX_NOMIRROR) : G_TX_CLAMP); + u32 masks = get_exponent(tWidth); + u32 maskt = get_exponent(tHeight); - case PAINTING_ENTERED: - painting->currRippleMag = painting->entryRippleMag; - painting->rippleDecay = painting->entryRippleDecay; - painting->currRippleRate = painting->entryRippleRate; - painting->dispersionFactor = painting->entryDispersionFactor; - break; - } - painting->state = state; - painting->rippleX = painting_ripple_x(painting, xSource); - painting->rippleY = painting_ripple_y(painting, ySource); - gPaintingMarioYEntry = gPaintingMarioYPos; - - // Because true or false would be too simple... - if (resetTimer == RESET_TIMER) { - painting->rippleTimer = 0.0f; - } - gRipplingPainting = painting; + gDPSetTile((*gfx)++, G_IM_FMT_RGBA, G_IM_SIZ_16b, + (tWidth >> 2), 0, G_TX_RENDERTILE, 0, + cm, maskt, G_TX_NOLOD, + cm, masks, G_TX_NOLOD + ); + gDPSetTileSize((*gfx)++, 0, + 0, 0, + ((tWidth - 1) << G_TEXTURE_IMAGE_FRAC), + ((tHeight - 1) << G_TEXTURE_IMAGE_FRAC) + ); } /** - * Idle update function for wall paintings that use RIPPLE_TRIGGER_PROXIMITY. + * Ripple a painting that has 1 or more images that need to be mapped. */ -void wall_painting_proximity_idle(struct Painting *painting, struct Painting *paintingGroup[]) { - // Check for Mario triggering a ripple - if (painting->floorEntered & RIPPLE_LEFT) { - painting_state(PAINTING_RIPPLE, painting, paintingGroup, NEAREST_4TH, MARIO_Y, RESET_TIMER); - } else if (painting->floorEntered & RIPPLE_MIDDLE) { - painting_state(PAINTING_RIPPLE, painting, paintingGroup, NEAREST_4TH, MARIO_Y, RESET_TIMER); - } else if (painting->floorEntered & RIPPLE_RIGHT) { - painting_state(PAINTING_RIPPLE, painting, paintingGroup, NEAREST_4TH, MARIO_Y, RESET_TIMER); - - // Check for Mario entering - } else if (painting->floorEntered & ENTER_LEFT) { - painting_state(PAINTING_ENTERED, painting, paintingGroup, NEAREST_4TH, MARIO_Y, RESET_TIMER); - } else if (painting->floorEntered & ENTER_MIDDLE) { - painting_state(PAINTING_ENTERED, painting, paintingGroup, NEAREST_4TH, MARIO_Y, RESET_TIMER); - } else if (painting->floorEntered & ENTER_RIGHT) { - painting_state(PAINTING_ENTERED, painting, paintingGroup, NEAREST_4TH, MARIO_Y, RESET_TIMER); - } -} +Gfx* dl_painting_rippling(const struct PaintingImage* paintingImage, struct PaintingMeshVertex* paintingMesh, const PaintingData* triangleMap) { + s16 imageCount = paintingImage->imageCount; + s16 tWidth = paintingImage->textureWidth; + s16 tHeight = paintingImage->textureHeight; + const Texture** tArray = segmented_to_virtual(paintingImage->textureArray); + _Bool isEnvMap = (paintingImage->imageType == PAINTING_IMAGE_TYPE_ENV_MAP); -/** - * Rippling update function for wall paintings that use RIPPLE_TRIGGER_PROXIMITY. - */ -void wall_painting_proximity_rippling(struct Painting *painting, struct Painting *paintingGroup[]) { - if (painting->floorEntered & ENTER_LEFT) { - painting_state(PAINTING_ENTERED, painting, paintingGroup, NEAREST_4TH, MARIO_Y, RESET_TIMER); - } else if (painting->floorEntered & ENTER_MIDDLE) { - painting_state(PAINTING_ENTERED, painting, paintingGroup, NEAREST_4TH, MARIO_Y, RESET_TIMER); - } else if (painting->floorEntered & ENTER_RIGHT) { - painting_state(PAINTING_ENTERED, painting, paintingGroup, NEAREST_4TH, MARIO_Y, RESET_TIMER); - } -} + Gfx* dlist = alloc_display_list( + SIZEOF_GFX_CMD(SPMatrix(0,0)) + + SIZEOF_GFX_CMD(SPDisplayList(0)) + + SIZEOF_GFX_CMD(DPSetTile(0,0,0,0,0,0,0,0,0,0,0,0)) + + SIZEOF_GFX_CMD(DPSetTileSize(0,0,0,0,0)) + + (imageCount * ( + SIZEOF_GFX_CMD(SPDisplayList(0)) + )) + + SIZEOF_GFX_CMD(SPDisplayList(0)) + + SIZEOF_GFX_CMD(SPPopMatrix(0)) + + SIZEOF_GFX_CMD(SPEndDisplayList()) + ); + Gfx* gfx = dlist; -/** - * Idle update function for wall paintings that use RIPPLE_TRIGGER_CONTINUOUS. - */ -void wall_painting_continuous_idle(struct Painting *painting, struct Painting *paintingGroup[]) { - // Check for Mario triggering a ripple - if (painting->floorEntered & RIPPLE_LEFT) { - painting_state(PAINTING_RIPPLE, painting, paintingGroup, MIDDLE_X, MIDDLE_Y, RESET_TIMER); - } else if (painting->floorEntered & RIPPLE_MIDDLE) { - painting_state(PAINTING_RIPPLE, painting, paintingGroup, MIDDLE_X, MIDDLE_Y, RESET_TIMER); - } else if (painting->floorEntered & RIPPLE_RIGHT) { - painting_state(PAINTING_RIPPLE, painting, paintingGroup, MIDDLE_X, MIDDLE_Y, RESET_TIMER); - - // Check for Mario entering - } else if (painting->floorEntered & ENTER_LEFT) { - painting_state(PAINTING_ENTERED, painting, paintingGroup, NEAREST_4TH, MARIO_Y, RESET_TIMER); - } else if (painting->floorEntered & ENTER_MIDDLE) { - painting_state(PAINTING_ENTERED, painting, paintingGroup, NEAREST_4TH, MARIO_Y, RESET_TIMER); - } else if (painting->floorEntered & ENTER_RIGHT) { - painting_state(PAINTING_ENTERED, painting, paintingGroup, NEAREST_4TH, MARIO_Y, RESET_TIMER); + if (dlist == NULL) { + return dlist; } -} + // Scale + Mtx* scale = alloc_display_list(sizeof(Mtx)); + guScale( + scale, + (1.0f / PAINTING_SIZE), + (1.0f / PAINTING_SIZE), + 1.0f + ); + gSPMatrix(gfx++, scale, (G_MTX_MODELVIEW | G_MTX_MUL | G_MTX_PUSH)); -/** - * Rippling update function for wall paintings that use RIPPLE_TRIGGER_CONTINUOUS. - */ -void wall_painting_continuous_rippling(struct Painting *painting, struct Painting *paintingGroup[]) { - if (painting->floorEntered & ENTER_LEFT) { - painting_state(PAINTING_ENTERED, painting, paintingGroup, NEAREST_4TH, MARIO_Y, DONT_RESET); - } else if (painting->floorEntered & ENTER_MIDDLE) { - painting_state(PAINTING_ENTERED, painting, paintingGroup, NEAREST_4TH, MARIO_Y, DONT_RESET); - } else if (painting->floorEntered & ENTER_RIGHT) { - painting_state(PAINTING_ENTERED, painting, paintingGroup, NEAREST_4TH, MARIO_Y, DONT_RESET); - } -} + Gfx* beginDl = (isEnvMap ? dl_paintings_env_mapped_begin : dl_paintings_rippling_begin); + gSPDisplayList(gfx++, beginDl); -/** - * Idle update function for floor paintings that use RIPPLE_TRIGGER_PROXIMITY. - * - * No floor paintings use RIPPLE_TRIGGER_PROXIMITY in the game. - */ -void floor_painting_proximity_idle(struct Painting *painting, struct Painting *paintingGroup[]) { - // Check for Mario triggering a ripple - if (painting->floorEntered & RIPPLE_LEFT) { - painting_state(PAINTING_RIPPLE, painting, paintingGroup, MARIO_X, MARIO_Z, RESET_TIMER); - } else if (painting->floorEntered & RIPPLE_MIDDLE) { - painting_state(PAINTING_RIPPLE, painting, paintingGroup, MARIO_X, MARIO_Z, RESET_TIMER); - } else if (painting->floorEntered & RIPPLE_RIGHT) { - painting_state(PAINTING_RIPPLE, painting, paintingGroup, MARIO_X, MARIO_Z, RESET_TIMER); - - // Only check for Mario entering if he jumped below the surface - } else if (painting->marioWentUnder) { - if (painting->currFloor & ENTER_LEFT) { - painting_state(PAINTING_ENTERED, painting, paintingGroup, MARIO_X, MARIO_Z, RESET_TIMER); - } else if (painting->currFloor & ENTER_MIDDLE) { - painting_state(PAINTING_ENTERED, painting, paintingGroup, MARIO_X, MARIO_Z, RESET_TIMER); - } else if (painting->currFloor & ENTER_RIGHT) { - painting_state(PAINTING_ENTERED, painting, paintingGroup, MARIO_X, MARIO_Z, RESET_TIMER); - } - } -} + painting_setup_textures(&gfx, tWidth, tHeight, isEnvMap); -/** - * Rippling update function for floor paintings that use RIPPLE_TRIGGER_PROXIMITY. - * - * No floor paintings use RIPPLE_TRIGGER_PROXIMITY in the game. - */ -void floor_painting_proximity_rippling(struct Painting *painting, struct Painting *paintingGroup[]) { - if (painting->marioWentUnder) { - if (painting->currFloor & ENTER_LEFT) { - painting_state(PAINTING_ENTERED, painting, paintingGroup, MARIO_X, MARIO_Z, RESET_TIMER); - } else if (painting->currFloor & ENTER_MIDDLE) { - painting_state(PAINTING_ENTERED, painting, paintingGroup, MARIO_X, MARIO_Z, RESET_TIMER); - } else if (painting->currFloor & ENTER_RIGHT) { - painting_state(PAINTING_ENTERED, painting, paintingGroup, MARIO_X, MARIO_Z, RESET_TIMER); - } - } -} + PaintingData numTris = (triangleMap[0] / imageCount); + // Map each image to the mesh's vertices. + for (s16 i = 0; i < imageCount; i++) { + // Render a section of the painting. + gSPDisplayList(gfx++, render_painting_segment(tArray[i], i, imageCount, tWidth, tHeight, paintingMesh, triangleMap, numTris, paintingImage->alpha)); -/** - * Idle update function for floor paintings that use RIPPLE_TRIGGER_CONTINUOUS. - * - * Both floor paintings (HMC and CotMC) are hidden behind a door, which hides the ripple's start up. - * The floor just inside the doorway is RIPPLE_LEFT, so the painting starts rippling as soon as Mario - * enters the room. - */ -void floor_painting_continuous_idle(struct Painting *painting, struct Painting *paintingGroup[]) { - // Check for Mario triggering a ripple - if (painting->floorEntered & RIPPLE_LEFT) { - painting_state(PAINTING_RIPPLE, painting, paintingGroup, MIDDLE_X, MIDDLE_Y, RESET_TIMER); - } else if (painting->floorEntered & RIPPLE_MIDDLE) { - painting_state(PAINTING_RIPPLE, painting, paintingGroup, MIDDLE_X, MIDDLE_Y, RESET_TIMER); - } else if (painting->floorEntered & RIPPLE_RIGHT) { - painting_state(PAINTING_RIPPLE, painting, paintingGroup, MIDDLE_X, MIDDLE_Y, RESET_TIMER); - - // Check for Mario entering - } else if (painting->currFloor & ENTER_LEFT) { - painting_state(PAINTING_ENTERED, painting, paintingGroup, MARIO_X, MARIO_Z, RESET_TIMER); - } else if (painting->currFloor & ENTER_MIDDLE) { - painting_state(PAINTING_ENTERED, painting, paintingGroup, MARIO_X, MARIO_Z, RESET_TIMER); - } else if (painting->currFloor & ENTER_RIGHT) { - painting_state(PAINTING_ENTERED, painting, paintingGroup, MARIO_X, MARIO_Z, RESET_TIMER); + triangleMap += (numTris * 3); } -} -/** - * Rippling update function for floor paintings that use RIPPLE_TRIGGER_CONTINUOUS. - */ -void floor_painting_continuous_rippling(struct Painting *painting, struct Painting *paintingGroup[]) { - if (painting->marioWentUnder) { - if (painting->currFloor & ENTER_LEFT) { - painting_state(PAINTING_ENTERED, painting, paintingGroup, MARIO_X, MARIO_Z, DONT_RESET); - } else if (painting->currFloor & ENTER_MIDDLE) { - painting_state(PAINTING_ENTERED, painting, paintingGroup, MARIO_X, MARIO_Z, DONT_RESET); - } else if (painting->currFloor & ENTER_RIGHT) { - painting_state(PAINTING_ENTERED, painting, paintingGroup, MARIO_X, MARIO_Z, DONT_RESET); - } - } + Gfx* endDl = (isEnvMap ? dl_paintings_env_mapped_end : dl_paintings_rippling_end); + gSPDisplayList(gfx++, endDl); + gSPPopMatrix(gfx++, G_MTX_MODELVIEW); + gSPEndDisplayList(gfx); + + return dlist; } /** - * Check for Mario entering one of the special floors associated with the painting. + * Generates a mesh, calculates vertex normals for lighting, and renders a rippling painting. + * The mesh and vertex normals are regenerated and freed every frame. */ -void painting_update_floors(struct Painting *painting) { - s16 paintingId = painting->id; - s8 rippleLeft = 0; - s8 rippleMiddle = 0; - s8 rippleRight = 0; - s8 enterLeft = 0; - s8 enterMiddle = 0; - s8 enterRight = 0; - - /* The area in front of every painting in the game (except HMC and CotMC, which *\ - |* act a little differently) is made up of 3 special floor triangles with special *| - |* (unique) surface types. This code checks which surface Mario is currently on *| - \* and sets a bitfield accordingly. */ - - // check if Mario's current floor is one of the special floors - if (gPaintingMarioFloorType == paintingId * 3 + SURFACE_PAINTING_WOBBLE_A6) { - rippleLeft = RIPPLE_LEFT; - } - if (gPaintingMarioFloorType == paintingId * 3 + SURFACE_PAINTING_WOBBLE_A7) { - rippleMiddle = RIPPLE_MIDDLE; - } - if (gPaintingMarioFloorType == paintingId * 3 + SURFACE_PAINTING_WOBBLE_A8) { - rippleRight = RIPPLE_RIGHT; - } - if (gPaintingMarioFloorType == paintingId * 3 + SURFACE_PAINTING_WARP_D3) { - enterLeft = ENTER_LEFT; - } - if (gPaintingMarioFloorType == paintingId * 3 + SURFACE_PAINTING_WARP_D4) { - enterMiddle = ENTER_MIDDLE; - } - if (gPaintingMarioFloorType == paintingId * 3 + SURFACE_PAINTING_WARP_D5) { - enterRight = ENTER_RIGHT; - } +Gfx* display_painting_rippling(struct Object* obj) { + const struct PaintingImage* paintingImage = obj->oPaintingImage; + const PaintingData* vtxData = segmented_to_virtual(painting_data_vertices); + const PaintingData* triangleData = segmented_to_virtual(painting_data_triangles); + PaintingData numVtx = vtxData[0]; + PaintingData numTris = triangleData[0]; + Gfx* dlist = NULL; + // When a painting is rippling, this mesh is generated each frame using the Painting's parameters. + // This mesh only contains the vertex positions and normals. + // Paintings use an additional array to map textures to the mesh. + //! TODO: Find out why clearing this between frames causes flickering. + struct PaintingMeshVertex* paintingMesh = mem_pool_alloc(gEffectsMemoryPool, (numVtx * sizeof(struct PaintingMeshVertex))); + // A list of neighbor triangles for each vertes. This gets cleared each frame while 'paintingMesh' isn't. + struct PaintingNeighborTris* neighborTris = mem_pool_alloc(gEffectsMemoryPool, (numVtx * sizeof(struct PaintingNeighborTris))); + bzero(neighborTris, (numVtx * sizeof(struct PaintingNeighborTris))); + // The painting's surface normals, used to approximate each of the vertex normals (for gouraud shading). + Vec3f *paintingTriNorms = mem_pool_alloc(gEffectsMemoryPool, (numTris * sizeof(Vec3f))); - painting->lastFloor = painting->currFloor; - // at most 1 of these will be nonzero; - painting->currFloor = rippleLeft + rippleMiddle + rippleRight + enterLeft + enterMiddle + enterRight; + // Generate the mesh and its lighting data + painting_generate_mesh(obj, vtxData, numVtx, paintingMesh); + painting_calculate_triangle_normals(triangleData, neighborTris, paintingMesh, paintingTriNorms); + painting_average_vertex_normals(neighborTris, numVtx, paintingMesh, paintingTriNorms); - // floorEntered is true iff currFloor is true and lastFloor is false - // (Mario just entered the floor on this frame) - painting->floorEntered = (painting->lastFloor ^ painting->currFloor) & painting->currFloor; + // Map the painting's texture depending on the painting's texture type. + dlist = dl_painting_rippling(paintingImage, paintingMesh, triangleData); - painting->marioWasUnder = painting->marioIsUnder; - // Check if Mario has fallen below the painting (used for floor paintings) - if (gPaintingMarioYPos < painting->posY) { - painting->marioIsUnder = TRUE; - } else { - painting->marioIsUnder = FALSE; - } + // The mesh data is freed every frame. + //! This data is not actually cleared. + mem_pool_free(gEffectsMemoryPool, paintingMesh); + mem_pool_free(gEffectsMemoryPool, neighborTris); + mem_pool_free(gEffectsMemoryPool, paintingTriNorms); - // Mario "went under" if he was not under last frame, but is under now - painting->marioWentUnder = (painting->marioWasUnder ^ painting->marioIsUnder) & painting->marioIsUnder; + return dlist; } -/** - * Update the ripple's timer and magnitude, making it propagate outwards. - * - * Automatically changes the painting back to IDLE state (or RIPPLE for continuous paintings) if the - * ripple's magnitude becomes small enough. - */ -void painting_update_ripple_state(struct Painting *painting) { - if (gPaintingUpdateCounter != gLastPaintingUpdateCounter) { - painting->currRippleMag *= painting->rippleDecay; +Gfx* dl_painting_not_rippling(struct Object* obj) { + const struct PaintingImage* paintingImage = obj->oPaintingImage; + Alpha alpha = paintingImage->alpha; + s16 imageCount = paintingImage->imageCount; + s32 shaded = paintingImage->shaded; + Gfx* dlist = alloc_display_list( + SIZEOF_GFX_CMD(SPMatrix(0,0)) + + SIZEOF_GFX_CMD(SPDisplayList(0)) + + SIZEOF_GFX_CMD(SPVertex(0,0,0)) + + SIZEOF_GFX_CMD(DPSetTile(0,0,0,0,0,0,0,0,0,0,0,0)) + + SIZEOF_GFX_CMD(DPSetTileSize(0,0,0,0,0)) + + (imageCount * ( + SIZEOF_GFX_CMD(DPSetTextureImage(0,0,0,0)) + + SIZEOF_GFX_CMD(DPLoadSync()) + + SIZEOF_GFX_CMD(DPLoadBlock(0,0,0,0,0)) + + SIZEOF_GFX_CMD(SP2Triangles(0,0,0,0,0,0,0,0)) + )) + + SIZEOF_GFX_CMD(SPDisplayList(0)) + + (!shaded * ( + SIZEOF_GFX_CMD(SPSetGeometryMode(0)) + )) + + SIZEOF_GFX_CMD(SPPopMatrix(0)) + + SIZEOF_GFX_CMD(SPEndDisplayList()) + ); + Gfx* gfx = dlist; - if (painting->rippleTimer >= ((1 << 24) - 1.0f)) { - painting->rippleTimer = 0.0f; - } - painting->rippleTimer += 1.0f; + if (dlist == NULL) { + return dlist; } - if (painting->rippleTrigger == RIPPLE_TRIGGER_PROXIMITY) { - // if the painting is barely rippling, make it stop rippling - if (painting->currRippleMag <= 1.0f) { - painting->state = PAINTING_IDLE; - gRipplingPainting = NULL; - } - } else if (painting->rippleTrigger == RIPPLE_TRIGGER_CONTINUOUS) { - // if the painting is doing the entry ripple but the ripples are as small as those from the - // passive ripple, make it do a passive ripple - // If Mario goes below the surface but doesn't warp, the painting will eventually reset. - if (painting->state == PAINTING_ENTERED && painting->currRippleMag <= painting->passiveRippleMag) { + // Scale + Mtx* scale = alloc_display_list(sizeof(Mtx)); + guScale( + scale, + (1.0f / PAINTING_SIZE), + (1.0f / PAINTING_SIZE), + 1.0f + ); + gSPMatrix(gfx++, scale, (G_MTX_MODELVIEW | G_MTX_MUL | G_MTX_PUSH)); - painting->state = PAINTING_RIPPLE; - painting->currRippleMag = painting->passiveRippleMag; - painting->rippleDecay = painting->passiveRippleDecay; - painting->currRippleRate = painting->passiveRippleRate; - painting->dispersionFactor = painting->passiveDispersionFactor; - } - } -} + Vtx* verts = alloc_display_list((imageCount * 4) * sizeof(*verts)); + Vec3c n; -/** - * @return the ripple function at posX, posY - * note that posX and posY correspond to a point on the face of the painting, not actual axes - */ -s16 calculate_ripple_at_point(struct Painting *painting, f32 posX, f32 posY) { - /// Controls the peaks of the ripple. - f32 rippleMag = painting->currRippleMag; - /// Controls the ripple's frequency - f32 rippleRate = painting->currRippleRate; - /// Controls how fast the ripple spreads - f32 dispersionFactor = painting->dispersionFactor; - /// How far the ripple has spread - f32 rippleTimer = painting->rippleTimer; - /// x and y ripple origin - f32 rippleX = painting->rippleX; - f32 rippleY = painting->rippleY; - - f32 distanceToOrigin; - f32 rippleDistance; + const Texture** textures = segmented_to_virtual(paintingImage->textureArray); - posX *= painting->size / PAINTING_SIZE; - posY *= painting->size / PAINTING_SIZE; - distanceToOrigin = sqrtf((posX - rippleX) * (posX - rippleX) + (posY - rippleY) * (posY - rippleY)); - // A larger dispersionFactor makes the ripple spread slower - rippleDistance = distanceToOrigin / dispersionFactor; - if (rippleTimer < rippleDistance) { - // if the ripple hasn't reached the point yet, make the point magnitude 0 - return 0; - } else { - // use a cosine wave to make the ripple go up and down, - // scaled by the painting's ripple magnitude - f32 rippleZ = rippleMag * cosf(rippleRate * (2 * M_PI) * (rippleTimer - rippleDistance)); + _Bool isEnvMap = (paintingImage->imageType == PAINTING_IMAGE_TYPE_ENV_MAP); - // round it to an int and return it - return round_float(rippleZ); + if (isEnvMap) { + vec3_set(n, 0x00, 0x00, 0x7f); + gSPDisplayList(gfx++, dl_paintings_env_mapped_begin); + } else if (shaded) { + vec3_set(n, 0x00, 0x00, 0x7f); + gSPDisplayList(gfx++, dl_paintings_textured_shaded_begin); + } else { + vec3_same(n, 0xdd); + gSPDisplayList(gfx++, dl_paintings_textured_vertex_colored_begin); } -} -/** - * If movable, return the ripple function at (posX, posY) - * else return 0 - */ -s16 ripple_if_movable(struct Painting *painting, s16 movable, s16 posX, s16 posY) { - s16 rippleZ = 0; + s16 tWidth = paintingImage->textureWidth; + s16 tHeight = paintingImage->textureHeight; - if (movable) { - rippleZ = calculate_ripple_at_point(painting, posX, posY); - } - return rippleZ; -} + // Width and height of each section. + const f32 dx = (PAINTING_SIZE / 1); + const f32 dy = (PAINTING_SIZE / imageCount); -/** - * Allocates and generates a mesh for the rippling painting effect by modifying the passed in `mesh` - * based on the painting's current ripple state. - * - * The `mesh` table describes the location of mesh vertices, whether they move when rippling, and what - * triangles they belong to. - * - * The static mesh passed in is organized into two lists. This function only uses the first list, - * painting_calculate_triangle_normals below uses the second one. - * - * The first list describes the vertices in this format: - * numVertices - * v0 x, v0 y, movable - * ... - * vN x, vN y, movable - * Where x and y are from 0 to PAINTING_SIZE, movable is 0 or 1. - * - * The mesh used in game, seg2_painting_triangle_mesh, is in bin/segment2.c. - */ -void painting_generate_mesh(struct Painting *painting, s16 *mesh, s16 numTris) { - s16 i; + // These are used to scale the vertex positions into texture positions. + const f32 tWidthScale = (TC(tWidth ) / dx); + const f32 tHeightScale = (TC(tHeight) / dy); - gPaintingMesh = mem_pool_alloc(gEffectsMemoryPool, numTris * sizeof(struct PaintingMeshVertex)); + s16 x1 = 0; // Left + s16 x2 = dx; // Right + s16 s1 = (x1 * tWidthScale); // Left + s16 s2 = (x2 * tWidthScale); // Right + s16 y1, y2; + s16 t1, t2; - // accesses are off by 1 since the first entry is the number of vertices - for (i = 0; i < numTris; i++) { - gPaintingMesh[i].pos[0] = mesh[i * 3 + 1]; - gPaintingMesh[i].pos[1] = mesh[i * 3 + 2]; - // The "z coordinate" of each vertex in the mesh is either 1 or 0. Instead of being an - // actual coordinate, it just determines whether the vertex moves - gPaintingMesh[i].pos[2] = ripple_if_movable(painting, mesh[i * 3 + 3], - gPaintingMesh[i].pos[0], gPaintingMesh[i].pos[1]); + s32 vertIndex = 0; + s32 quadIndex; + s32 i; + + // Generate vertices + for (i = 0; i < imageCount; i++) { + y1 = (i * dy); // Top + y2 = (y1 + dy); // Bottom + t1 = ((y2 - y1) * tHeightScale); // Top + t2 = ((y2 - y2) * tHeightScale); // Bottom + make_vertex(verts, vertIndex++, 0, y1, 0, s1, t1, n[0], n[1], n[2], alpha); // Bottom Left + make_vertex(verts, vertIndex++, dx, y1, 0, s2, t1, n[0], n[1], n[2], alpha); // Bottom Right + make_vertex(verts, vertIndex++, dx, y2, 0, s2, t2, n[0], n[1], n[2], alpha); // Top Right + make_vertex(verts, vertIndex++, 0, y2, 0, s1, t2, n[0], n[1], n[2], alpha); // Top left } -} -/** - * Calculate the surface normals of each triangle in the generated ripple mesh. - * - * The static mesh passed in is organized into two lists. This function uses the second list, - * painting_generate_mesh above uses the first one. - * - * The second list in `mesh` describes the mesh's triangles in this format: - * numTris - * tri0 v0, tri0 v1, tri0 v2 - * ... - * triN v0, triN v1, triN v2 - * Where each v0, v1, v2 is an index into the first list in `mesh`. - * - * The mesh used in game, seg2_painting_triangle_mesh, is in bin/segment2.c. - */ -void painting_calculate_triangle_normals(PaintingData *mesh, PaintingData numVtx, PaintingData numTris) { - s16 i; + gSPVertex(gfx++, verts, vertIndex, 0); - gPaintingTriNorms = mem_pool_alloc(gEffectsMemoryPool, numTris * sizeof(Vec3f)); + painting_setup_textures(&gfx, tWidth, tHeight, isEnvMap); - for (i = 0; i < numTris; i++) { - s16 tri = numVtx * 3 + i * 3 + 2; // Add 2 because of the 2 length entries preceding the list - s16 v0 = mesh[tri]; - s16 v1 = mesh[tri + 1]; - s16 v2 = mesh[tri + 2]; - - f32 x0 = gPaintingMesh[v0].pos[0]; - f32 y0 = gPaintingMesh[v0].pos[1]; - f32 z0 = gPaintingMesh[v0].pos[2]; - - f32 x1 = gPaintingMesh[v1].pos[0]; - f32 y1 = gPaintingMesh[v1].pos[1]; - f32 z1 = gPaintingMesh[v1].pos[2]; - - f32 x2 = gPaintingMesh[v2].pos[0]; - f32 y2 = gPaintingMesh[v2].pos[1]; - f32 z2 = gPaintingMesh[v2].pos[2]; - - // Cross product to find each triangle's normal vector - gPaintingTriNorms[i][0] = (y1 - y0) * (z2 - z1) - (z1 - z0) * (y2 - y1); - gPaintingTriNorms[i][1] = (z1 - z0) * (x2 - x1) - (x1 - x0) * (z2 - z1); - gPaintingTriNorms[i][2] = (x1 - x0) * (y2 - y1) - (y1 - y0) * (x2 - x1); + for (i = 0; i < imageCount; i++) { + gDPSetTextureImage(gfx++, G_IM_FMT_RGBA, G_IM_SIZ_16b, 1, textures[i]); + gDPLoadSync(gfx++); + gDPLoadBlock(gfx++, G_TX_LOADTILE, 0, 0, ((tWidth * tHeight) - 1), CALC_DXT(tWidth, G_IM_SIZ_16b_BYTES)); + quadIndex = (i * 4); + gSP2Triangles(gfx++, + (quadIndex + 0), (quadIndex + 1), (quadIndex + 2), 0x0, + (quadIndex + 0), (quadIndex + 2), (quadIndex + 3), 0x0 + ); } -} -/** - * Rounds a floating-point component of a normal vector to an s8 by multiplying it by 127 or 128 and - * rounding away from 0. - */ -s8 normalize_component(f32 comp) { - s8 rounded; + Gfx* endDl = (isEnvMap ? dl_paintings_env_mapped_end : dl_paintings_textured_end); + gSPDisplayList(gfx++, endDl); - if (comp > 0.0) { - rounded = comp * 127.0 + 0.5; // round up - } else if (comp < 0.0) { - rounded = comp * 128.0 - 0.5; // round down - } else { - rounded = 0; // don't round 0 + if (!shaded) { + gSPSetGeometryMode(gfx++, G_LIGHTING); } - return rounded; -} -/** - * Approximates the painting mesh's vertex normals by averaging the normals of all triangles sharing a - * vertex. Used for Gouraud lighting. - * - * After each triangle's surface normal is calculated, the `neighborTris` table describes which triangles - * each vertex should use when calculating the average normal vector. - * - * The table is a list of entries in this format: - * numNeighbors, tri0, tri1, ..., triN - * - * Where each 'tri' is an index into gPaintingTriNorms. - * Entry i in `neighborTris` corresponds to the vertex at gPaintingMesh[i] - * - * The table used in game, seg2_painting_mesh_neighbor_tris, is in bin/segment2.c. - */ -void painting_average_vertex_normals(PaintingData *neighborTris, PaintingData numVtx) { - s16 tri; - s16 i; - s16 j; - s16 neighbors; - s16 entry = 0; + gSPPopMatrix(gfx++, G_MTX_MODELVIEW); + gSPEndDisplayList(gfx); - for (i = 0; i < numVtx; i++) { - f32 nx = 0.0f; - f32 ny = 0.0f; - f32 nz = 0.0f; - f32 nlen; - - // The first number of each entry is the number of adjacent tris - neighbors = neighborTris[entry]; - for (j = 0; j < neighbors; j++) { - tri = neighborTris[entry + j + 1]; - nx += gPaintingTriNorms[tri][0]; - ny += gPaintingTriNorms[tri][1]; - nz += gPaintingTriNorms[tri][2]; - } - // Move to the next vertex's entry - entry += neighbors + 1; - - // average the surface normals from each neighboring tri - nx /= neighbors; - ny /= neighbors; - nz /= neighbors; - nlen = sqrtf(nx * nx + ny * ny + nz * nz); - - if (nlen == 0.0f) { - gPaintingMesh[i].norm[0] = 0; - gPaintingMesh[i].norm[1] = 0; - gPaintingMesh[i].norm[2] = 0; - } else { - gPaintingMesh[i].norm[0] = normalize_component(nx / nlen); - gPaintingMesh[i].norm[1] = normalize_component(ny / nlen); - gPaintingMesh[i].norm[2] = normalize_component(nz / nlen); - } - } + return dlist; } /** - * Creates a display list that draws the rippling painting, with 'img' mapped to the painting's mesh, - * using 'textureMap'. - * - * If the textureMap doesn't describe the whole mesh, then multiple calls are needed to draw the whole - * painting. + * Draw the painting. */ -Gfx *render_painting(u8 *img, s16 tWidth, s16 tHeight, s16 *textureMap, s16 mapVerts, s16 mapTris, u8 alpha) { - s16 group; - s16 map; - s16 triGroup; - s16 mapping; - s16 meshVtx; - s16 tx; - s16 ty; - - // We can fit 15 (16 / 3) vertices in the RSP's vertex buffer. - // Group triangles by 5, with one remainder group. - s16 triGroups = mapTris / 5; - s16 remGroupTris = mapTris % 5; - s16 numVtx = mapTris * 3; - - s16 commands = triGroups * 2 + remGroupTris + 7; - Vtx *verts = alloc_display_list(numVtx * sizeof(Vtx)); - Gfx *dlist = alloc_display_list(commands * sizeof(Gfx)); - Gfx *gfx = dlist; +Gfx* geo_painting_draw(s32 callContext, struct GraphNode* node, UNUSED void* context) { + struct Object* obj = gCurGraphNodeObjectNode; - gLoadBlockTexture(gfx++, tWidth, tHeight, G_IM_FMT_RGBA, img); - - // Draw the groups of 5 first - for (group = 0; group < triGroups; group++) { + if (obj == NULL) { + return NULL; + } - // The triangle groups are the second part of the texture map. - // Each group is a list of 15 mappings - triGroup = mapVerts * 3 + group * 15 + 2; - for (map = 0; map < 15; map++) { - // The mapping is just an index into the earlier part of the textureMap - // Some mappings are repeated, for example, when multiple triangles share a vertex - mapping = textureMap[triGroup + map]; - - // The first entry is the ID of the vertex in the mesh - meshVtx = textureMap[mapping * 3 + 1]; - - // The next two are the texture coordinates for that vertex - tx = textureMap[mapping * 3 + 2]; - ty = textureMap[mapping * 3 + 3]; - - // Map the texture and place it in the verts array - make_vertex(verts, group * 15 + map, gPaintingMesh[meshVtx].pos[0], gPaintingMesh[meshVtx].pos[1], - gPaintingMesh[meshVtx].pos[2], tx, ty, gPaintingMesh[meshVtx].norm[0], - gPaintingMesh[meshVtx].norm[1], gPaintingMesh[meshVtx].norm[2], alpha); - } + // Get the const painting image data. + const struct PaintingImage* paintingImage = obj->oPaintingImage; - // Load the vertices and draw the 5 triangles - gSPVertex(gfx++, VIRTUAL_TO_PHYSICAL(verts + group * 15), 15, 0); - gSPDisplayList(gfx++, dl_paintings_draw_ripples); + if (paintingImage == NULL) { + return NULL; } - // One group left with < 5 triangles - triGroup = mapVerts * 3 + triGroups * 15 + 2; - // Map the texture to the triangles - for (map = 0; map < remGroupTris * 3; map++) { - mapping = textureMap[triGroup + map]; - meshVtx = textureMap[mapping * 3 + 1]; - tx = textureMap[mapping * 3 + 2]; - ty = textureMap[mapping * 3 + 3]; - make_vertex(verts, triGroups * 15 + map, gPaintingMesh[meshVtx].pos[0], gPaintingMesh[meshVtx].pos[1], - gPaintingMesh[meshVtx].pos[2], tx, ty, gPaintingMesh[meshVtx].norm[0], - gPaintingMesh[meshVtx].norm[1], gPaintingMesh[meshVtx].norm[2], alpha); - } + Gfx* paintingDlist = NULL; - // Draw the triangles individually - gSPVertex(gfx++, VIRTUAL_TO_PHYSICAL(verts + triGroups * 15), remGroupTris * 3, 0); - for (group = 0; group < remGroupTris; group++) { - gSP1Triangle(gfx++, group * 3, group * 3 + 1, group * 3 + 2, 0); + if (callContext == GEO_CONTEXT_RENDER) { + // Draw the painting. + if ( + (paintingImage->textureArray != NULL) && + (paintingImage->imageCount > 0) && + (paintingImage->textureWidth > 0) && + (paintingImage->textureHeight > 0) && + (paintingImage->imageType != PAINTING_IMAGE_TYPE_INVISIBLE) && + (paintingImage->alpha > 0x00) + ) { + // Determine whether the painting is opaque or transparent. + if (paintingImage->alpha == 0xFF) { + SET_GRAPH_NODE_LAYER(node->flags, LAYER_OCCLUDE_SILHOUETTE_OPAQUE); + } else { + SET_GRAPH_NODE_LAYER(node->flags, LAYER_TRANSPARENT); + } + + if (obj->oAction == PAINTING_ACT_IDLE) { + paintingDlist = dl_painting_not_rippling(obj); + } else { + paintingDlist = display_painting_rippling(obj); + } + } } - gSPEndDisplayList(gfx); - return dlist; + return paintingDlist; } +/// - INIT - + /** - * Orient the painting mesh for rendering. + * Updates a painting object's room from a point in front of the center of the painting. */ -Gfx *painting_model_view_transform(struct Painting *painting) { - f32 sizeRatio = painting->size / PAINTING_SIZE; - Mtx *rotX = alloc_display_list(sizeof(Mtx)); - Mtx *rotY = alloc_display_list(sizeof(Mtx)); - Mtx *translate = alloc_display_list(sizeof(Mtx)); - Mtx *scale = alloc_display_list(sizeof(Mtx)); - Gfx *dlist = alloc_display_list(5 * sizeof(Gfx)); - Gfx *gfx = dlist; - - guTranslate(translate, painting->posX, painting->posY, painting->posZ); - guRotate(rotX, painting->pitch, 1.0f, 0.0f, 0.0f); - guRotate(rotY, painting->yaw, 0.0f, 1.0f, 0.0f); - guScale(scale, sizeRatio, sizeRatio, sizeRatio); - - gSPMatrix(gfx++, translate, G_MTX_MODELVIEW | G_MTX_MUL | G_MTX_PUSH); - gSPMatrix(gfx++, rotX, G_MTX_MODELVIEW | G_MTX_MUL | G_MTX_NOPUSH); - gSPMatrix(gfx++, rotY, G_MTX_MODELVIEW | G_MTX_MUL | G_MTX_NOPUSH); - gSPMatrix(gfx++, scale, G_MTX_MODELVIEW | G_MTX_MUL | G_MTX_NOPUSH); - gSPEndDisplayList(gfx); +void painting_update_room(struct Object* obj) { + // The center of the painting, but with an offset since paintings are usually between floor triangle edges laterally. + Vec3f distPos = { + (obj->header.gfx.scale[0] * 0.5f), + (obj->header.gfx.scale[1] * 0.5f), + PAINTING_WOBBLE_DEPTH // Distance in front of the painting to check for a room floor. + }; - return dlist; + // Get the painting object's rotation. + Vec3s rotation; + vec3i_to_vec3s(rotation, &obj->oFaceAngleVec); + + // Set 'roomCheckPos' to the world space coords of 'distPos'. + Vec3f roomCheckPos; + vec3f_local_pos_to_world_pos(roomCheckPos, distPos, &obj->oPosVec, rotation); + + // Set the object's room so that paintings only render in their room. + obj->oRoom = get_room_at_pos( + roomCheckPos[0], + roomCheckPos[1], + roomCheckPos[2] + ); } /** - * Ripple a painting that has 1 or more images that need to be mapped + * @brief Initializes a painting object. */ -Gfx *painting_ripple_image(struct Painting *painting) { - PaintingData meshVerts; - PaintingData meshTris; - PaintingData i; - PaintingData *textureMap; - PaintingData imageCount = painting->imageCount; - PaintingData tWidth = painting->textureWidth; - PaintingData tHeight = painting->textureHeight; - PaintingData **textureMaps = segmented_to_virtual(painting->textureMaps); - Texture **textures = segmented_to_virtual(painting->textureArray); - Gfx *dlist = alloc_display_list((imageCount + 6) * sizeof(Gfx)); - Gfx *gfx = dlist; +void bhv_painting_init(void) { + struct Object* obj = o; - if (dlist == NULL) { - return dlist; - } + // Get the painting id from the first byte of the behavior params. The second byte is used for the warp node ID. + enum PaintingImageIDs id = GET_BPARAM1(obj->oBehParams); - gSPDisplayList(gfx++, painting_model_view_transform(painting)); - gSPDisplayList(gfx++, dl_paintings_rippling_begin); - gSPDisplayList(gfx++, painting->rippleDisplayList); + const struct PaintingImage* paintingImage = segmented_to_virtual(sPaintings[id]); - // Map each image to the mesh's vertices - for (i = 0; i < imageCount; i++) { - textureMap = segmented_to_virtual(textureMaps[i]); - meshVerts = textureMap[0]; - meshTris = textureMap[meshVerts * 3 + 1]; - gSPDisplayList(gfx++, render_painting(textures[i], tWidth, tHeight, textureMap, meshVerts, meshTris, painting->alpha)); - } + // Set the object's painting image data pointer. + obj->oPaintingImage = paintingImage; - // Update the ripple, may automatically reset the painting's state. - painting_update_ripple_state(painting); + // Set the object's initial scale. + obj->header.gfx.scale[0] = paintingImage->sizeX; + obj->header.gfx.scale[1] = paintingImage->sizeY; - gSPPopMatrix(gfx++, G_MTX_MODELVIEW); - gSPDisplayList(gfx++, dl_paintings_rippling_end); - gSPEndDisplayList(gfx); - return dlist; + // Update the painting object's room. + painting_update_room(obj); } +/// - LOOP - + /** - * Ripple a painting that has 1 "environment map" texture. + * Check for Mario entering the painting. Returns changed action. */ -Gfx *painting_ripple_env_mapped(struct Painting *painting) { - s16 meshVerts; - s16 meshTris; - s16 *textureMap; - s16 tWidth = painting->textureWidth; - s16 tHeight = painting->textureHeight; - s16 **textureMaps = segmented_to_virtual(painting->textureMaps); - u8 **tArray = segmented_to_virtual(painting->textureArray); - Gfx *dlist = alloc_display_list(7 * sizeof(Gfx)); - Gfx *gfx = dlist; +enum oActionsPainting painting_update_mario_pos(struct Object* obj, Vec3f marioLocalPos) { + struct MarioState* m = gMarioState; - if (dlist == NULL) { - return dlist; - } + // PAINTING_ACT_IDLE will not change the action. + enum oActionsPainting newAction = PAINTING_ACT_IDLE; - gSPDisplayList(gfx++, painting_model_view_transform(painting)); - gSPDisplayList(gfx++, dl_paintings_env_mapped_begin); - gSPDisplayList(gfx++, painting->rippleDisplayList); + Vec3f marioWorldPos; + Vec3s rotation; - // Map the image to the mesh's vertices - textureMap = segmented_to_virtual(textureMaps[0]); - meshVerts = textureMap[0]; - meshTris = textureMap[meshVerts * 3 + 1]; - gSPDisplayList(gfx++, render_painting(tArray[0], tWidth, tHeight, textureMap, meshVerts, meshTris, painting->alpha)); + // Add PAINTING_MARIO_Y_OFFSET to make the ripple closer to Mario's center of mass. + vec3f_copy_y_off(marioWorldPos, m->pos, PAINTING_MARIO_Y_OFFSET); - // Update the ripple, may automatically reset the painting's state. - painting_update_ripple_state(painting); - - gSPPopMatrix(gfx++, G_MTX_MODELVIEW); - gSPDisplayList(gfx++, dl_paintings_env_mapped_end); - gSPEndDisplayList(gfx); - return dlist; -} + // Get the painting's rotation. + vec3i_to_vec3s(rotation, &obj->oFaceAngleVec); -/** - * Generates a mesh, calculates vertex normals for lighting, and renders a rippling painting. - * The mesh and vertex normals are regenerated and freed every frame. - */ -Gfx *display_painting_rippling(struct Painting *painting) { - s16 *mesh = segmented_to_virtual(seg2_painting_triangle_mesh); - s16 *neighborTris = segmented_to_virtual(seg2_painting_mesh_neighbor_tris); - s16 numVtx = mesh[0]; - s16 numTris = mesh[numVtx * 3 + 1]; - Gfx *dlist = NULL; + // Get Mario's position in the painting's frame of reference. + vec3f_world_pos_to_local_pos(marioLocalPos, marioWorldPos, &obj->oPosVec, rotation); - // Generate the mesh and its lighting data - painting_generate_mesh(painting, mesh, numVtx); - painting_calculate_triangle_normals(mesh, numVtx, numTris); - painting_average_vertex_normals(neighborTris, numVtx); + // Check if Mario is within the painting bounds laterally in local space. + if ( + (marioLocalPos[0] > -PAINTING_EDGE_MARGIN) && + (marioLocalPos[0] < (obj->header.gfx.scale[0] + PAINTING_EDGE_MARGIN)) && + (marioLocalPos[1] > -PAINTING_EDGE_MARGIN) && + (marioLocalPos[1] < (obj->header.gfx.scale[1] + PAINTING_EDGE_MARGIN)) + ) { + if (marioLocalPos[2] > PAINTING_WOBBLE_WARP_THRESHOLD) { + // In front of the painting, check whether Mario is inside the wobble zone. + if (marioLocalPos[2] < PAINTING_WOBBLE_DEPTH) { + newAction = PAINTING_ACT_RIPPLING; + } + } else { + // Behind the painting, check whether Mario is inside the warp zone. + if (marioLocalPos[2] > -PAINTING_WARP_DEPTH) { + newAction = PAINTING_ACT_ENTERED; + } + } + } - // Map the painting's texture depending on the painting's texture type. - switch (painting->textureType) { - case PAINTING_IMAGE: - dlist = painting_ripple_image(painting); - break; - case PAINTING_ENV_MAP: - dlist = painting_ripple_env_mapped(painting); - break; + // Detect whether Mario is entering this painting, and set paintingObj accordingly + if (newAction == PAINTING_ACT_ENTERED) { + // Mario has entered the painting. + m->paintingObj = obj; + } else if (m->paintingObj == obj) { + // Reset m->paintingObj if it's this painting and this painting is not entered. + m->paintingObj = NULL; } - // The mesh data is freed every frame. - mem_pool_free(gEffectsMemoryPool, gPaintingMesh); - mem_pool_free(gEffectsMemoryPool, gPaintingTriNorms); - return dlist; + enum oActionsPainting oldAction = obj->oPaintingStoredAction; + + obj->oPaintingStoredAction = newAction; + + // The action to change to later. PAINTING_ACT_IDLE will not update the action. + if (newAction != oldAction) { + return newAction; + } else { + return PAINTING_ACT_IDLE; + } } /** - * Render a normal painting. + * Returns a pointer to the RippleAnimationPair that best fits the painting type. */ -Gfx *display_painting_not_rippling(struct Painting *painting) { - Gfx *dlist = alloc_display_list(4 * sizeof(Gfx)); - Gfx *gfx = dlist; +const struct RippleAnimationPair* painting_get_ripple_animation_type_info(struct Object* obj) { + const struct PaintingImage* paintingImage = obj->oPaintingImage; + enum PaintingRippleAnimations rippleAnimationType = RIPPLE_ANIM_CONTINUOUS; - if (dlist == NULL) { - return dlist; + if (paintingImage->rippleTrigger == RIPPLE_TRIGGER_PROXIMITY) { + rippleAnimationType = RIPPLE_ANIM_PROXIMITY; + + if ( + (obj->header.gfx.scale[0] >= PAINTING_SCALE_LARGE_RIPPLE_THRESHOLD) || + (obj->header.gfx.scale[1] >= PAINTING_SCALE_LARGE_RIPPLE_THRESHOLD) + ) { + rippleAnimationType = RIPPLE_ANIM_PROXIMITY_LARGE; + } } - gSPDisplayList(gfx++, painting_model_view_transform(painting)); - gSPDisplayList(gfx++, painting->normalDisplayList); - gSPPopMatrix(gfx++, G_MTX_MODELVIEW); - gSPEndDisplayList(gfx); - return dlist; + + return &sRippleAnimations[rippleAnimationType]; } /** - * Clear Mario-related state and clear gRipplingPainting. + * Set a painting's ripple animation and magnitude. */ -void reset_painting(struct Painting *painting) { - painting->lastFloor = 0; - painting->currFloor = 0; - painting->floorEntered = 0; - painting->marioWasUnder = 0; - painting->marioIsUnder = 0; - painting->marioWentUnder = 0; - - gRipplingPainting = NULL; - -#ifdef NO_SEGMENTED_MEMORY - // Make sure all variables are reset correctly. - // With segmented memory the segments that contain the relevant - // Painting structs are reloaded from ROM upon level load. - painting->state = PAINTING_IDLE; - painting->currRippleMag = 0.0f; - painting->rippleDecay = 1.0f; - painting->currRippleRate = 0.0f; - painting->dispersionFactor = 0.0f; - painting->rippleTimer = 0.0f; - painting->rippleX = 0.0f; - painting->rippleY = 0.0f; - if (painting == &ddd_painting) { - // Move DDD painting to initial position, in case the animation - // that moves the painting stops during level unload. - painting->posX = 3456.0f; - } -#endif +void painting_set_ripple_animation_type(struct Object* obj, const struct RippleAnimation* baseRippleAnim) { + obj->oPaintingRippleAnimation = baseRippleAnim; + obj->oPaintingCurrRippleMag = baseRippleAnim->mag; } +#if defined(ENABLE_VANILLA_LEVEL_SPECIFIC_CHECKS) || defined(UNLOCK_ALL) +// Whether the painting should be moved or not. +_Bool gDDDPaintingNotMoved = FALSE; + /** * Controls the x coordinate of the DDD painting. * - * Before Mario gets the "Board Bowser's Sub" star in DDD, the painting spawns at frontPos. + * Before Mario gets the "Board Bowser's Sub" star in DDD, the painting spawns at frontPos, and set gDDDPaintingNotMoved to TRUE. * - * If Mario just got the star, the painting's x coordinate moves to backPos at a rate of `speed` units. - * - * When the painting reaches backPos, a save flag is set so that the painting will spawn at backPos - * whenever it loads. - * - * This function also sets gDddPaintingStatus, which controls the warp: - * 0 (0b00): set x coordinate to frontPos - * 2 (0b10): set x coordinate to backPos - * 3 (0b11): same as 2. Bit 0 is ignored + * If Mario has the star, and the painting was last seen at frontPos (gDDDPaintingNotMoved == TRUE), the painting's x coordinate moves to backPos at a rate of `speed` units. + * When the painting reaches backPos, gDDDPaintingNotMoved is set to FALSE. + * + * If Mario has the star, and the painting was never seen at frontPos or it has already moved (gDDDPaintingNotMoved == FALSE), the painting will spawn at backPos. */ +void move_ddd_painting(struct Object* obj, f32 frontPos, f32 backPos, f32 speed) { #ifdef UNLOCK_ALL -void move_ddd_painting(struct Painting *painting, UNUSED f32 frontPos, f32 backPos, UNUSED f32 speed) { - painting->posX = backPos; - gDddPaintingStatus = (DDD_FLAG_BOWSERS_SUB_BEATEN | DDD_FLAG_BACK); -} -#else -void move_ddd_painting(struct Painting *painting, f32 frontPos, f32 backPos, f32 speed) { - // Obtain the DDD star flags - u32 dddFlags = save_file_get_star_flags(gCurrSaveFileNum - 1, COURSE_NUM_TO_INDEX(COURSE_DDD)); - // Get the other save file flags - u32 saveFileFlags = save_file_get_flags(); - // Find out whether Board Bowser's Sub was collected - u32 bowsersSubBeaten = dddFlags & BOARD_BOWSERS_SUB; - // Check whether DDD has already moved back - u32 dddBack = saveFileFlags & SAVE_FLAG_DDD_MOVED_BACK; - - if (!bowsersSubBeaten && !dddBack) { - // If we haven't collected the star or moved the painting, put the painting at the front - painting->posX = frontPos; - gDddPaintingStatus = DDD_FLAGS_NONE; - } else if (bowsersSubBeaten && !dddBack) { - // If we've collected the star but not moved the painting back, - // Each frame, move the painting by a certain speed towards the back area. - painting->posX += speed; - gDddPaintingStatus = DDD_FLAG_BOWSERS_SUB_BEATEN; - if (painting->posX >= backPos) { - painting->posX = backPos; - // Tell the save file that we've moved DDD back. - save_file_set_flags(SAVE_FLAG_DDD_MOVED_BACK); - } - } else if (bowsersSubBeaten && dddBack) { - // If the painting has already moved back, place it in the back position. - painting->posX = backPos; - gDddPaintingStatus = (DDD_FLAG_BOWSERS_SUB_BEATEN | DDD_FLAG_BACK); - } -} + obj->oPosX = backPos; + return; #endif - -/** - * Set the painting's node's layer based on its alpha - */ -void set_painting_layer(struct GraphNodeGenerated *gen, struct Painting *painting) { - if (painting->alpha == 0xFF) { // Opaque - SET_GRAPH_NODE_LAYER(gen->fnNode.node.flags, LAYER_OCCLUDE_SILHOUETTE_OPAQUE); + // Obtain the DDD star flags and find out whether Board Bowser's Sub was collected. + if ( + save_file_get_star_flags( + (gCurrSaveFileNum - 1), + COURSE_NUM_TO_INDEX(COURSE_DDD) + ) & STAR_FLAG_ACT_1 + ) { + // Check whether DDD has already moved back. + if (gDDDPaintingNotMoved) { + // If we've collected the star but not moved the painting back... + // Each frame, move the painting by a certain speed towards the back area. + obj->oPosX += speed; + if (obj->oPosX >= backPos) { + obj->oPosX = backPos; + + gDDDPaintingNotMoved = FALSE; + } + } else { + // If the painting has already moved back, place it in the back position. + obj->oPosX = backPos; + } } else { - SET_GRAPH_NODE_LAYER(gen->fnNode.node.flags, LAYER_TRANSPARENT); + // If we haven't collected the star, put the painting at the front. + obj->oPosX = frontPos; + + // Set this so the painting gets moved once the star is collected. + gDDDPaintingNotMoved = TRUE; } } +#endif // (ENABLE_VANILLA_LEVEL_SPECIFIC_CHECKS || UNLOCK_ALL) /** - * Display either a normal painting or a rippling one depending on the painting's ripple status + * Set the painting's action, causing it to start a passive ripple or a ripple from Mario entering. + * + * @param obj identifies the painting that is changing state. + * @param ripplePosX,ripplePosY the position of the ripples. + * @param shouldResetTimer if TRUE, set the timer to 0. */ -Gfx *display_painting(struct Painting *painting) { - switch (painting->state) { - case PAINTING_IDLE: - return display_painting_not_rippling(painting); +void painting_start_ripples(struct Object* obj, f32 ripplePosX, f32 ripplePosY, _Bool shouldResetTimer) { + const struct RippleAnimationPair* rippleAnim = painting_get_ripple_animation_type_info(obj); + + // Use a different set of variables depending on the state + switch (obj->oAction) { + case PAINTING_ACT_RIPPLING: + painting_set_ripple_animation_type(obj, &rippleAnim->passive); break; - default: - return display_painting_rippling(painting); + + case PAINTING_ACT_ENTERED: + painting_set_ripple_animation_type(obj, &rippleAnim->entry); break; } -} -/** - * Update function for wall paintings. - * Calls a different update function depending on the painting's ripple trigger and current state. - */ -void wall_painting_update(struct Painting *painting, struct Painting *paintingGroup[]) { - if (painting->rippleTrigger == RIPPLE_TRIGGER_PROXIMITY) { - switch (painting->state) { - case PAINTING_IDLE: - wall_painting_proximity_idle(painting, paintingGroup); - break; - case PAINTING_RIPPLE: - wall_painting_proximity_rippling(painting, paintingGroup); - break; - } - } else if (painting->rippleTrigger == RIPPLE_TRIGGER_CONTINUOUS) { - switch (painting->state) { - case PAINTING_IDLE: - wall_painting_continuous_idle(painting, paintingGroup); - break; - case PAINTING_RIPPLE: - wall_painting_continuous_rippling(painting, paintingGroup); - break; - } + // Set the ripple position. + obj->oPaintingRipplePosX = ripplePosX; + obj->oPaintingRipplePosY = ripplePosY; + +#ifdef ENABLE_VANILLA_LEVEL_SPECIFIC_CHECKS + if (GET_BPARAM1(obj->oBehParams) == PAINTING_ID_CASTLE_WDW) { + // Set Mario's Y position for the WDW water level. + // The WDW painting is at 1306 in vanilla. + gPaintingMarioYEntry = gMarioObject->oPosY - obj->oPosY; } -} +#endif -/** - * Update function for floor paintings (HMC and CotMC) - * Calls a different update function depending on the painting's ripple trigger and current state. - * - * No floor paintings use RIPPLE_TRIGGER_PROXIMITY in the game. - */ -void floor_painting_update(struct Painting *painting, struct Painting *paintingGroup[]) { - if (painting->rippleTrigger == RIPPLE_TRIGGER_PROXIMITY) { - switch (painting->state) { - case PAINTING_IDLE: - floor_painting_proximity_idle(painting, paintingGroup); - break; - case PAINTING_RIPPLE: - floor_painting_proximity_rippling(painting, paintingGroup); - break; - } - } else if (painting->rippleTrigger == RIPPLE_TRIGGER_CONTINUOUS) { - switch (painting->state) { - case PAINTING_IDLE: - floor_painting_continuous_idle(painting, paintingGroup); - break; - case PAINTING_RIPPLE: - floor_painting_continuous_rippling(painting, paintingGroup); - break; - } + if (shouldResetTimer) { + obj->oPaintingRippleTimer = 0; } } -/** - * Render and update the painting whose id and group matches the values in the GraphNode's parameter. - * Use PAINTING_ID(id, group) to set the right parameter in a level's geo layout. - */ -Gfx *geo_painting_draw(s32 callContext, struct GraphNode *node, UNUSED void *context) { - struct GraphNodeGenerated *gen = (struct GraphNodeGenerated *) node; - s32 group = (gen->parameter >> 8) & 0xFF; - s32 id = gen->parameter & 0xFF; - Gfx *paintingDlist = NULL; - struct Painting **paintingGroup = sPaintingGroups[group]; - struct Painting *painting = segmented_to_virtual(paintingGroup[id]); - - if (callContext != GEO_CONTEXT_RENDER) { - reset_painting(painting); - } else if (callContext == GEO_CONTEXT_RENDER) { - - // Update the ddd painting before drawing - if (group == 1 && id == PAINTING_ID_DDD) { - move_ddd_painting(painting, 3456.0f, 5529.6f, 20.0f); +void bhv_painting_loop(void) { + struct Object* obj = o; + const struct PaintingImage* paintingImage = obj->oPaintingImage; + Vec3f marioLocalPos; + + // Update the painting's next action based on Mario's relative position. + enum oActionsPainting newAction = painting_update_mario_pos(obj, marioLocalPos); + + const struct RippleAnimation* objRippleAnim = obj->oPaintingRippleAnimation; + + // Decay the ripple over time. + if (objRippleAnim != NULL) { + obj->oPaintingCurrRippleMag *= objRippleAnim->decay; + } + + // Update the ripple's timer, making it propagate outwards. + if (obj->oPaintingRippleTimer++ < 0) { + // Reset the timer to 0 if it overflows. + obj->oPaintingRippleTimer = 0; + } + + if (paintingImage->rippleTrigger == RIPPLE_TRIGGER_PROXIMITY) { + // Proximity trigger type: + + // If the painting is barely rippling, make it stop rippling. + if (obj->oPaintingCurrRippleMag <= 1.0f) { + obj->oAction = PAINTING_ACT_IDLE; } - // Determine if the painting is transparent - set_painting_layer(gen, painting); + if (newAction == PAINTING_ACT_ENTERED) { + obj->oAction = newAction; + painting_start_ripples(obj, marioLocalPos[0], marioLocalPos[1], TRUE); // Start entering + } else if ((obj->oAction != PAINTING_ACT_ENTERED) && (newAction == PAINTING_ACT_RIPPLING)) { + obj->oAction = newAction; + painting_start_ripples(obj, marioLocalPos[0], marioLocalPos[1], TRUE); // Start wobbling + } + } else if (paintingImage->rippleTrigger == RIPPLE_TRIGGER_CONTINUOUS) { + // Continuous trigger type: - // Draw before updating - paintingDlist = display_painting(painting); + const struct RippleAnimationPair* rippleAnim = painting_get_ripple_animation_type_info(obj); + // If the painting is doing the entry ripple but the ripples are as small as those from the + // passive ripple, make it do a passive ripple. + // If Mario goes below the surface but doesn't warp, the painting will eventually reset. + if ( + (obj->oAction == PAINTING_ACT_ENTERED) && + (obj->oPaintingCurrRippleMag <= rippleAnim->passive.mag) + ) { + painting_set_ripple_animation_type(obj, &rippleAnim->passive); + obj->oAction = PAINTING_ACT_RIPPLING; + } - // Update the painting - painting_update_floors(painting); - if (painting->pitch == 0x0) { - // only paintings with 0 pitch are treated as walls - wall_painting_update(painting, paintingGroup); - } else { - floor_painting_update(painting, paintingGroup); + if (newAction == PAINTING_ACT_ENTERED) { + obj->oAction = newAction; + painting_start_ripples(obj, marioLocalPos[0], marioLocalPos[1], FALSE); // Start entering + } else if (obj->oAction == PAINTING_ACT_IDLE) { + obj->oAction = PAINTING_ACT_RIPPLING; + painting_start_ripples(obj, (obj->header.gfx.scale[0] * 0.5f), (obj->header.gfx.scale[1] * 0.5f), TRUE); // Start idle wobbling } } - return paintingDlist; -} - -/** - * Update the painting system's local copy of Mario's current floor and position. - */ -Gfx *geo_painting_update(s32 callContext, UNUSED struct GraphNode *node, UNUSED Mat4 mtx) { - struct Surface *surface; - // Reset the update counter - if (callContext != GEO_CONTEXT_RENDER) { - gLastPaintingUpdateCounter = gAreaUpdateCounter - 1; - gPaintingUpdateCounter = gAreaUpdateCounter; - } else { - gLastPaintingUpdateCounter = gPaintingUpdateCounter; - gPaintingUpdateCounter = gAreaUpdateCounter; - - // Store Mario's position - find_floor(gMarioObject->oPosX, gMarioObject->oPosY, gMarioObject->oPosZ, &surface); - gPaintingMarioFloorType = surface->type; - gPaintingMarioXPos = gMarioObject->oPosX; - gPaintingMarioYPos = gMarioObject->oPosY; - gPaintingMarioZPos = gMarioObject->oPosZ; +#if defined(ENABLE_VANILLA_LEVEL_SPECIFIC_CHECKS) || defined(UNLOCK_ALL) + // Update the DDD painting before drawing. + if (GET_BPARAM1(obj->oBehParams) == PAINTING_ID_CASTLE_DDD) { + move_ddd_painting(obj, 3456.0f, 5529.6f, 20.0f); } - return NULL; +#endif // (ENABLE_VANILLA_LEVEL_SPECIFIC_CHECKS || UNLOCK_ALL) } diff --git a/src/game/paintings.h b/src/game/paintings.h index eaae28d899..8136d261f7 100644 --- a/src/game/paintings.h +++ b/src/game/paintings.h @@ -7,138 +7,160 @@ #include "macros.h" #include "types.h" -/// Use to properly set a GraphNodeGenerated's parameter to point to the right painting -#define PAINTING_ID(id, grp) id | (grp << 8) -/// The default painting side length -#define PAINTING_SIZE 614.0f - -#define PAINTING_ID_DDD 0x7 - -#define BOARD_BOWSERS_SUB (1 << 0) +// The size of the stored painting mesh model, before it is created and scaled down to 1x1. +// Vanilla is 614.4f, changed to 600.0f in HackerSM64 to prevent rounding issues. +// Changing this affects the painting's lighting. The larger the difference between this and +// the final size of the painting, the greater the difference in lighting. +#define PAINTING_SIZE 600.0f + +// The threshold of scale at which to use a larger ripple animation in sRippleAnimations. Default is 1200.0f. +#define PAINTING_SCALE_LARGE_RIPPLE_THRESHOLD 1200.0f + +// The depth of the area in front of the painting which triggers ripples without warping. Default is 102.4f. +#define PAINTING_WOBBLE_DEPTH 102.4f + +// The depth of the area behind the painting which triggers the warp. Default is 409.6f. +#define PAINTING_WARP_DEPTH 409.6f + +// The threshold relative to the painting's plane between wobbling and warping. Default is -30.72f. +#define PAINTING_WOBBLE_WARP_THRESHOLD -30.72f + +// The size of the buffer around the edges of the painting in which Mario is still considered within bounds. +#define PAINTING_EDGE_MARGIN 160.0f + +// This is added to Mario's Y position to make the ripple closer to Mario's center of mass. Default is 50.0f +#define PAINTING_MARIO_Y_OFFSET 50.0f + +// Convert image coordinates to texel coordinates. +#define TC(t) (((t) - 1) << 5) + + +enum PaintingImageIDs { + /* Painting ID */ + /* 0x00 */ PAINTING_ID_NULL, + /* 0x01 */ PAINTING_ID_CASTLE_BOB, + /* 0x02 */ PAINTING_ID_CASTLE_CCM, + /* 0x03 */ PAINTING_ID_CASTLE_WF, + /* 0x04 */ PAINTING_ID_CASTLE_JRB, + /* 0x05 */ PAINTING_ID_CASTLE_LLL, + /* 0x06 */ PAINTING_ID_CASTLE_SSL, + /* 0x07 */ PAINTING_ID_CASTLE_HMC, + /* 0x08 */ PAINTING_ID_CASTLE_DDD, + /* 0x09 */ PAINTING_ID_CASTLE_WDW, + /* 0x0A */ PAINTING_ID_CASTLE_THI_TINY, + /* 0x0B */ PAINTING_ID_CASTLE_TTM, + /* 0x0C */ PAINTING_ID_CASTLE_TTC, + /* 0x0D */ PAINTING_ID_CASTLE_SL, + /* 0x0E */ PAINTING_ID_CASTLE_THI_HUGE, + /* 0x0F */ PAINTING_ID_CASTLE_RR, + /* 0x10 */ PAINTING_ID_HMC_COTMC, + /* 0x11 */ PAINTING_ID_TTM_SLIDE, +}; -enum DDDPaintingFlags { - DDD_FLAGS_NONE = (0 << 0), // 0x0 - DDD_FLAG_BACK = (1 << 0), // 0x1 - DDD_FLAG_BOWSERS_SUB_BEATEN = (1 << 1), // 0x2 +// Types of ripple animations. +enum PaintingRippleAnimations { + RIPPLE_ANIM_CONTINUOUS, + RIPPLE_ANIM_PROXIMITY, + RIPPLE_ANIM_PROXIMITY_LARGE, }; -enum PaintingState { - PAINTING_IDLE, - PAINTING_RIPPLE, - PAINTING_ENTERED +// Painting->imageType +enum PaintingType { + /// Painting that is invisible. + PAINTING_IMAGE_TYPE_INVISIBLE, + /// Painting that uses 1 or more textures as a texture. + PAINTING_IMAGE_TYPE_TEXTURE, + /// Painting that has one texture used for an environment map effect. + PAINTING_IMAGE_TYPE_ENV_MAP }; +// Painting->rippleTrigger enum RippleTriggers { - RIPPLE_TRIGGER_PROXIMITY = 10, - RIPPLE_TRIGGER_CONTINUOUS = 20, + RIPPLE_TRIGGER_NONE, + RIPPLE_TRIGGER_PROXIMITY, + RIPPLE_TRIGGER_CONTINUOUS, }; -enum PaintingType { - /// Painting that uses 1 or more images as a texture - PAINTING_IMAGE, - /// Painting that has one texture used for an environment map effect - PAINTING_ENV_MAP +// oAction +enum oActionsPainting { + PAINTING_ACT_IDLE, + PAINTING_ACT_RIPPLING, + PAINTING_ACT_ENTERED, }; -struct Painting { - s16 id; - /// How many images should be drawn when the painting is rippling. - s8 imageCount; - /// Either PAINTING_IMAGE or PAINTING_ENV_MAP - s8 textureType; - - /// The floor Mario was on last frame - s8 lastFloor; - /// The floor Mario is currently on - s8 currFloor; - /// The floor Mario just entered - s8 floorEntered; - - /// The painting's state, see top of paintings.c - s8 state; - - /// The painting's rotation - f32 pitch; - f32 yaw; - - /// The painting's position - f32 posX; - f32 posY; - f32 posZ; - - /// Controls how high the peaks of the ripple are. - f32 currRippleMag; - f32 passiveRippleMag; - f32 entryRippleMag; - - /// Multiplier that controls how fast the ripple regresses to the IDLE state. - f32 rippleDecay; - f32 passiveRippleDecay; - f32 entryRippleDecay; - - /// Controls the ripple's frequency - f32 currRippleRate; - f32 passiveRippleRate; - f32 entryRippleRate; - - /// The rate at which the magnitude of the ripple decreases as you move farther from the central - /// point of the ripple - f32 dispersionFactor; - f32 passiveDispersionFactor; - f32 entryDispersionFactor; - - /// How far the ripple has spread - f32 rippleTimer; - - /// The x and y origin of the ripple - f32 rippleX; - f32 rippleY; - - /// Display list used when the painting is normal. - const Gfx *normalDisplayList; - /// Data used to map the texture to the mesh - const s16 *const *textureMaps; - - // Texture data - const Texture *const *textureArray; - s16 textureWidth; - s16 textureHeight; - - /// Display list used when the painting is rippling. - const Gfx *rippleDisplayList; - /// Controls when a passive ripple starts. RIPPLE_TRIGGER_CONTINUOUS or RIPPLE_TRIGGER_PROXIMITY. - s8 rippleTrigger; - - /// The painting's transparency. Determines what layer the painting is in. - Alpha alpha; - - /// True if Mario was under the painting's y coordinate last frame - s8 marioWasUnder; - /// True if Mario is currently under the painting's y coordinate - s8 marioIsUnder; - /// True if Mario just went under the painting's y coordinate on this frame - s8 marioWentUnder; - - /// Uniformly scales the painting to a multiple of PAINTING_SIZE. - /// By default a painting is 614.0 x 614.0 - f32 size; -}; + +/** + * A list of preset constants for the ripple animations. + */ +typedef struct RippleAnimation { + /*0x00*/ const f32 mag; /// Controls how high the peaks of the ripple are when the animation starts. + /*0x04*/ const f32 decay; /// Multiplier that controls how fast the ripple regresses to the IDLE state. + /*0x08*/ const f32 rate; /// Controls the ripple's frequency. + /*0x0C*/ const f32 dispersion; /// The rate at which the magnitude of the ripple decreases as you move farther from the central point of the ripple. +} RippleAnimation; /*0x10*/ + +/** + * A ripple animation pair. + */ +typedef struct RippleAnimationPair { + /*0x00*/ const struct RippleAnimation passive; /// The ripple when the painting is continuously rippling or is lightly touched. + /*0x10*/ const struct RippleAnimation entry; /// The ripple when the painting is entered. +} RippleAnimationPair; /*0x20*/ + +/** + * Painting info struct. + */ +typedef struct PaintingImage { + /// Texture data. + /*0x00*/ const Texture* const* textureArray; + + /// How many textures the painting uses. + /*0x04*/ const s32 imageCount; + + /// Texture size. + /*0x08*/ const s16 textureWidth; + /*0x0A*/ const s16 textureHeight; + + /// Controls how the painting image is displayed. enum PaintingType. + /*0x0C*/ const s8 imageType; + + /// Controls when a passive ripple starts. enum RippleTriggers. + /*0x0D*/ const s8 rippleTrigger; + + /// Whether the painting uses shading when not rippling. Only used for Snowman's Land in vanilla and makes the transition to/from rippling not seamless. + /*0x0E*/ const _Bool shaded; + + /// The painting's transparency (0..255). Determines the drawing layer of the painting. + /*0x0F*/ const Alpha alpha; + + /// By default a painting is 614.0f x 614.0f (PAINTING_SIZE). + /*0x10*/ const f32 sizeX; + /*0x14*/ const f32 sizeY; +} PaintingImage; /*0x18*/ /** * Contains the position and normal of a vertex in the painting's generated mesh. */ -struct PaintingMeshVertex { +typedef struct PaintingMeshVertex { /*0x00*/ Vec3s pos; /*0x06*/ Vec3c norm; -}; +} PaintingMeshVertex; /*0x0C*/ + +/** + * Lists the neighboring triangles for each vertex in the mesh. + * Used when applying gouraud shading to the generated ripple mesh. + */ +typedef struct PaintingNeighborTris { + /*0x00*/ s16 numNeighbors; + /*0x02*/ s16 neighborTris[9]; +} PaintingNeighborTris; /*0x14*/ + + +Gfx* geo_painting_draw(s32 callContext, struct GraphNode* node, UNUSED void* context); -extern struct PaintingMeshVertex *gPaintingMesh; -extern Vec3f *gPaintingTriNorms; -extern struct Painting *gRipplingPainting; -extern s8 gDddPaintingStatus; +void bhv_painting_init(void); +void bhv_painting_loop(void); -Gfx *geo_painting_draw(s32 callContext, struct GraphNode *node, UNUSED void *context); -Gfx *geo_painting_update(s32 callContext, UNUSED struct GraphNode *node, UNUSED Mat4 mtx); #endif // PAINTINGS_H diff --git a/src/game/save_file.c b/src/game/save_file.c index bb9eed9c69..0f245343c1 100644 --- a/src/game/save_file.c +++ b/src/game/save_file.c @@ -586,7 +586,6 @@ u32 save_file_get_flags(void) { SAVE_FLAG_HAVE_VANISH_CAP | SAVE_FLAG_UNLOCKED_BASEMENT_DOOR | SAVE_FLAG_UNLOCKED_UPSTAIRS_DOOR | - SAVE_FLAG_DDD_MOVED_BACK | SAVE_FLAG_MOAT_DRAINED | SAVE_FLAG_UNLOCKED_PSS_DOOR | SAVE_FLAG_UNLOCKED_WF_DOOR | @@ -766,11 +765,11 @@ void disable_warp_checkpoint(void) { void check_if_should_set_warp_checkpoint(struct WarpNode *warpNode) { if (warpNode->destLevel & WARP_CHECKPOINT) { // Overwrite the warp checkpoint variables. - gWarpCheckpoint.actNum = gCurrActNum; + gWarpCheckpoint.actNum = gCurrActNum; gWarpCheckpoint.courseNum = gCurrCourseNum; - gWarpCheckpoint.levelID = warpNode->destLevel & 0x7F; - gWarpCheckpoint.areaNum = warpNode->destArea; - gWarpCheckpoint.warpNode = warpNode->destNode; + gWarpCheckpoint.levelID = (warpNode->destLevel & WARP_DEST_LEVEL_NUM_MASK); + gWarpCheckpoint.areaNum = warpNode->destArea; + gWarpCheckpoint.warpNode = warpNode->destNode; } } @@ -781,14 +780,17 @@ void check_if_should_set_warp_checkpoint(struct WarpNode *warpNode) { */ s32 check_warp_checkpoint(struct WarpNode *warpNode) { s16 warpCheckpointActive = FALSE; - s16 currCourseNum = gLevelToCourseNumTable[(warpNode->destLevel & 0x7F) - 1]; + s16 currCourseNum = gLevelToCourseNumTable[(warpNode->destLevel & WARP_DEST_LEVEL_NUM_MASK) - 1]; // gSavedCourseNum is only used in this function. - if (gWarpCheckpoint.courseNum != COURSE_NONE && gSavedCourseNum == currCourseNum - && gWarpCheckpoint.actNum == gCurrActNum) { - warpNode->destLevel = gWarpCheckpoint.levelID; - warpNode->destArea = gWarpCheckpoint.areaNum; - warpNode->destNode = gWarpCheckpoint.warpNode; + if ( + (gWarpCheckpoint.courseNum != COURSE_NONE) && + (gSavedCourseNum == currCourseNum) && + (gWarpCheckpoint.actNum == gCurrActNum) + ) { + warpNode->destLevel = gWarpCheckpoint.levelID; + warpNode->destArea = gWarpCheckpoint.areaNum; + warpNode->destNode = gWarpCheckpoint.warpNode; warpCheckpointActive = TRUE; } else { // Disable the warp checkpoint just in case the other 2 conditions failed? diff --git a/src/game/save_file.h b/src/game/save_file.h index 146685946f..a38620bd61 100644 --- a/src/game/save_file.h +++ b/src/game/save_file.h @@ -114,7 +114,7 @@ enum SaveProgressFlags { SAVE_FLAG_HAVE_KEY_2 = (1 << 5), /* 0x00000020 */ SAVE_FLAG_UNLOCKED_BASEMENT_DOOR = (1 << 6), /* 0x00000040 */ SAVE_FLAG_UNLOCKED_UPSTAIRS_DOOR = (1 << 7), /* 0x00000080 */ - SAVE_FLAG_DDD_MOVED_BACK = (1 << 8), /* 0x00000100 */ + SAVE_FLAG_UNUSED_8 = (1 << 8), /* 0x00000100 */ SAVE_FLAG_MOAT_DRAINED = (1 << 9), /* 0x00000200 */ SAVE_FLAG_UNLOCKED_PSS_DOOR = (1 << 10), /* 0x00000400 */ SAVE_FLAG_UNLOCKED_WF_DOOR = (1 << 11), /* 0x00000800 */ diff --git a/src/game/segment2.h b/src/game/segment2.h index 239e213958..fc6549cf04 100644 --- a/src/game/segment2.h +++ b/src/game/segment2.h @@ -38,13 +38,16 @@ extern Gfx dl_skybox_end[]; extern Gfx dl_waterbox_ia16_begin[]; extern Gfx dl_waterbox_rgba16_begin[]; extern Gfx dl_waterbox_end[]; -extern Gfx dl_paintings_draw_ripples[]; +extern Gfx dl_paintings_ripple_triangles[]; extern Gfx dl_paintings_rippling_begin[]; extern Gfx dl_paintings_rippling_end[]; +extern Gfx dl_paintings_textured_shaded_begin[]; +extern Gfx dl_paintings_textured_vertex_colored_begin[]; +extern Gfx dl_paintings_textured_end[]; extern Gfx dl_paintings_env_mapped_begin[]; extern Gfx dl_paintings_env_mapped_end[]; -extern s16 seg2_painting_triangle_mesh[]; -extern s16 seg2_painting_mesh_neighbor_tris[]; +extern PaintingData painting_data_vertices[]; +extern PaintingData painting_data_triangles[]; extern Texture *main_hud_lut[58]; extern Gfx dl_hud_img_load_tex_block[]; extern Gfx dl_hud_img_begin[]; diff --git a/src/game/sound_init.c b/src/game/sound_init.c index fe60afcb1f..8e6debd5d8 100644 --- a/src/game/sound_init.c +++ b/src/game/sound_init.c @@ -75,7 +75,6 @@ static u32 sMenuSoundsExtra[] = { SOUND_AIR_BLOW_FIRE, SOUND_ENV_ELEVATOR4, }; -static s8 sPaintingEjectSoundPlayed = FALSE; void play_menu_sounds_extra(s32 a, void *b); @@ -181,24 +180,6 @@ void play_menu_sounds(s16 soundMenuFlags) { #endif } -/** - * Plays the painting eject sound effect if it has not already been played - * - * Called from threads: thread5_game_loop - */ -void play_painting_eject_sound(void) { - if (gRipplingPainting != NULL && gRipplingPainting->state == PAINTING_ENTERED) { - // ripple when Mario enters painting - if (!sPaintingEjectSoundPlayed) { - play_sound(SOUND_GENERAL_PAINTING_EJECT, - gMarioStates[0].marioObj->header.gfx.cameraToObject); - } - sPaintingEjectSoundPlayed = TRUE; - } else { - sPaintingEjectSoundPlayed = FALSE; - } -} - /** * Called from threads: thread5_game_loop */ diff --git a/src/game/sound_init.h b/src/game/sound_init.h index 0681c2d56a..a2dac1e694 100644 --- a/src/game/sound_init.h +++ b/src/game/sound_init.h @@ -24,7 +24,6 @@ void disable_background_sound(void); void enable_background_sound(void); void set_sound_mode(u16 soundMode); void play_menu_sounds(s16 soundMenuFlags); -void play_painting_eject_sound(void); void play_infinite_stairs_music(void); void set_background_music(u16 a, u16 seqArgs, s16 fadeTimer); void fadeout_music(s16 fadeOutTime);