Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
rubberduckycooly
GitHub Repository: rubberduckycooly/Sonic-1-Sonic-2-2013-Script-Decompilation
Path: blob/master/Sonic 2/Scripts/MBZ/MBZSetup.txt
1479 views
1
// ----------------------------------
2
// RSDK Project: Sonic 2
3
// Script Description: MBZ Setup Object
4
// Script Author: Christian Whitehead/Simon Thomley
5
// Unpacked by Rubberduckycooly's script unpacker
6
// ----------------------------------
7
8
// ========================
9
// Aliases
10
// ========================
11
12
private alias object.value1 : object.lavaPalTimer
13
private alias object.value2 : object.paletteTimer
14
private alias object.value3 : object.lavaPalIndex1
15
private alias object.value4 : object.lavaPalIndex2
16
private alias object.value5 : object.lavaPalIndex3
17
private alias object.value6 : object.lavaPalIndex4
18
private alias object.value7 : object.oilAniTileDelay
19
private alias object.value8 : object.oilAniTileFrame
20
private alias object.value9 : object.deformTimer
21
private alias object.value10 : object.isDimming
22
23
// Player Aliases
24
private alias object.state : player.state
25
private alias object.xpos : player.xpos
26
private alias object.ypos : player.ypos
27
private alias object.iypos : player.iypos
28
private alias object.yvel : player.yvel
29
private alias object.speed : player.speed
30
private alias object.drawOrder : player.drawOrder
31
private alias object.direction : player.direction
32
private alias object.gravity : player.gravity
33
private alias object.pushing : player.pushing
34
private alias object.left : player.left
35
private alias object.right : player.right
36
private alias object.jumpPress : player.jumpPress
37
private alias object.controlLock : player.controlLock
38
private alias object.angle : player.angle
39
private alias object.frame : player.frame
40
private alias object.animation : player.animation
41
private alias object.animationSpeed : player.animationSpeed
42
private alias object.collisionMode : player.collisionMode
43
private alias object.collisionBottom : player.collisionBottom
44
private alias object.tileCollisions : player.tileCollisions
45
46
private alias object.value1 : player.timer
47
private alias object.value14 : player.skidding
48
private alias object.value18 : player.sortedDrawOrder
49
private alias object.value37 : player.shield
50
51
// Shield Aliases
52
private alias 3 : SHIELD_FIRE
53
54
// Tile Flag Aliases
55
private alias 0 : TILE_NORMAL
56
private alias 1 : TILE_OILPOOL
57
private alias 3 : TILE_LAVA
58
59
// Tile Info ID Aliases
60
private alias 8 : TILEINFO_ANGLEB
61
62
// Tracks
63
private alias 0 : TRACK_STAGE
64
private alias 1 : TRACK_ACTFINISH
65
private alias 2 : TRACK_INVINCIBLE
66
private alias 3 : TRACK_CONTINUE
67
private alias 4 : TRACK_BOSS
68
private alias 5 : TRACK_GAMEOVER
69
private alias 6 : TRACK_DROWNING
70
private alias 7 : TRACK_SUPER
71
72
// Reserved object slots
73
private alias 10 : SLOT_ZONESETUP
74
private alias 25 : SLOT_MUSICEVENT_CHANGE
75
private alias 26 : SLOT_MUSICEVENT_BOSS
76
77
// Music Events
78
private alias 2 : MUSICEVENT_TRANSITION
79
80
private alias 0 : MUSICEVENT_FLAG_NOCHANGE
81
private alias 1 : MUSICEVENT_FLAG_SPEEDUP
82
private alias 2 : MUSICEVENT_FLAG_SLOWDOWN
83
84
85
// ========================
86
// Function Declarations
87
// ========================
88
89
reserve function MBZSetup_State_OilPool
90
91
// These two are unused
92
reserve function MBZSetup_SpeedUpMusic
93
reserve function MBZSetup_SlowDownMusic
94
95
96
// ========================
97
// Static Values
98
// ========================
99
100
// Values here are named this way because the idea is to "mimic" CPZSetup for the CPZ objs in the stage
101
public value CPZSetup_rotatingStairTimer = 0
102
public value Water_flashTimer = 0
103
public value CPZSetup_hasAchievement = 0
104
public value CPZSetup_enteredWater = 0
105
106
// As the name suggests, these are not used
107
private value MBZSetup_unused1 = 0
108
private value MBZSetup_unused2 = 0
109
private value MBZSetup_unused3 = 0
110
private value MBZSetup_unused4 = 0
111
private value MBZSetup_unknownTimer = 0 // This is used to count, but not actually used in any meaningful way
112
113
114
// ========================
115
// Tables
116
// ========================
117
118
// Palette cycle for the stage
119
private table MBZSetup_lavaPalCycle
120
0xE00000, 0xE06000, 0xE0A000, 0xE0E000
121
0xE0E000, 0xE00000, 0xE06000, 0xE0A000
122
0xE0C020, 0xE0E000, 0xE00000, 0xE06000
123
0xE06000, 0xE0E040, 0xE0E080, 0xE02000
124
0xE04000, 0xE08000, 0xE0E060, 0xE0E0A0
125
0xE0E080, 0xE02000, 0xE06000, 0xE0E040
126
0xE0C020, 0xE0E000, 0xE00000, 0xE06000
127
0xE06000, 0xE0C020, 0xE0E000, 0xE00000
128
0xE00000, 0xE06000, 0xE0A000, 0xE0E000
129
0xE0C000, 0xC00000, 0xE04000, 0xE08000
130
0xE06000, 0xC0A000, 0xA00000, 0xE02000
131
0xC00000, 0xC04000, 0xE08000, 0x800000
132
0xA00000, 0xE02000, 0xE06000, 0xC0A000
133
0xE0C000, 0xC00000, 0xE04000, 0xE08000
134
0xE0A000, 0xE0E000, 0xE00000, 0xE06000
135
0xE06000, 0xE0A000, 0xE0E000, 0xE00000
136
end table
137
138
// Stage deformation data, used for animating the water
139
private table MBZSetup_deformationTable
140
1, 2, 1, 3, 1, 2, 2, 1, 2, 3, 1, 2, 1, 2, 0, 0
141
2, 0, 3, 2, 2, 3, 2, 2, 1, 3, 0, 0, 1, 0, 1, 3
142
1, 2, 1, 3, 1, 2, 2, 1, 2, 3, 1, 2, 1, 2, 0, 0
143
2, 0, 3, 2, 2, 3, 2, 2, 1, 3, 0, 0, 1, 0, 1, 3
144
end table
145
146
147
// ========================
148
// Function Definitions
149
// ========================
150
151
// Modified version of Player_State_Ground
152
private function MBZSetup_State_OilPool
153
if player.animation != ANI_SKIDDING
154
temp7 = true
155
else
156
temp7 = false
157
end if
158
159
CallFunction(Player_HandleGroundMovement)
160
161
if player.gravity == GRAVITY_AIR
162
#platform: USE_STANDALONE
163
player.state = Player_State_Air
164
#endplatform
165
#platform: USE_ORIGINS
166
player.state = Player_State_Air_NoDropDash
167
#endplatform
168
CallFunction(Player_HandleAirMovement)
169
else
170
CallFunction(Player_HandleOnGround)
171
172
if player.speed == 0
173
if player.collisionMode == CMODE_FLOOR
174
if player.timer < 240
175
player.animation = ANI_STOPPED
176
player.timer++
177
else
178
player.animation = ANI_WAITING
179
if stage.playerListPos == PLAYER_KNUCKLES_A
180
player.timer++
181
if player.timer == 834
182
player.timer = 0
183
player.animation = ANI_STOPPED
184
end if
185
end if
186
end if
187
end if
188
else
189
player.timer = 0
190
if player.speed > 0
191
if player.speed < 0x5F5C2
192
player.animation = ANI_WALKING
193
CallFunction(Player_HandleWalkAnimSpeed)
194
else
195
if player.speed > 0x9FFFF
196
player.animation = ANI_PEELOUT
197
else
198
player.animation = ANI_RUNNING
199
end if
200
CallFunction(Player_HandleRunAnimSpeed)
201
end if
202
else
203
if player.speed > -0x5F5C2
204
player.animation = ANI_WALKING
205
CallFunction(Player_HandleWalkAnimSpeed)
206
else
207
if player.speed < -0x9FFFF
208
player.animation = ANI_PEELOUT
209
else
210
player.animation = ANI_RUNNING
211
end if
212
CallFunction(Player_HandleRunAnimSpeed)
213
end if
214
end if
215
end if
216
217
if player.skidding > 0
218
if temp7 == true
219
PlaySfx(SfxName[Skidding], false)
220
end if
221
222
player.animation = ANI_SKIDDING
223
player.animationSpeed = 0
224
player.skidding--
225
if ringTimer == 0
226
CreateTempObject(TypeName[Dust Puff], 0, player.xpos, player.ypos)
227
object[tempObjectPos].iypos += player.collisionBottom
228
object[tempObjectPos].drawOrder = player.sortedDrawOrder
229
end if
230
231
if player.speed > 0
232
player.direction = FACING_RIGHT
233
else
234
player.direction = FACING_LEFT
235
end if
236
end if
237
238
if player.collisionMode == CMODE_FLOOR
239
if player.pushing == 2
240
player.animation = ANI_PUSHING
241
player.animationSpeed = 0
242
end if
243
end if
244
245
if player.jumpPress == true
246
CallFunction(Player_Action_Jump)
247
end if
248
end if
249
end function
250
251
252
// Unused - would've been used to speed up stage music
253
// Interestingly, it calls for "MarathonBase_F.ogg" - a song that isn't in the RSDK
254
// Could this have been the stage's original name..?
255
private function MBZSetup_SpeedUpMusic
256
CheckEqual(object[SLOT_MUSICEVENT_CHANGE].type, TypeName[Music Event])
257
temp0 = checkResult
258
CheckEqual(object[SLOT_MUSICEVENT_CHANGE].propertyValue, MUSICEVENT_TRANSITION)
259
temp0 &= checkResult
260
CheckEqual(stage.musicFlag, MUSICEVENT_FLAG_NOCHANGE)
261
temp0 &= checkResult
262
if temp0 == false
263
switch music.currentTrack
264
case TRACK_STAGE
265
SetMusicTrack("Invincibility_F.ogg", TRACK_INVINCIBLE, 30436)
266
SwapMusicTrack("MarathonBase_F.ogg", TRACK_STAGE, 502294, 7920)
267
break
268
269
case TRACK_INVINCIBLE
270
SetMusicTrack("MarathonBase_F.ogg", TRACK_STAGE, 502294)
271
SwapMusicTrack("Invincibility_F.ogg", TRACK_INVINCIBLE, 30436, 8000)
272
break
273
274
case TRACK_BOSS
275
SetMusicTrack("MarathonBase_F.ogg", TRACK_STAGE, 502294)
276
SetMusicTrack("Invincibility_F.ogg", TRACK_INVINCIBLE, 30436)
277
break
278
279
end switch
280
else
281
stage.musicFlag = MUSICEVENT_FLAG_SPEEDUP
282
end if
283
end function
284
285
286
// Unused - would've been used to slow down stage music
287
// Interestingly, it calls for "MarathonBase.ogg" - this song isn't in the RSDK either
288
private function MBZSetup_SlowDownMusic
289
CheckEqual(object[SLOT_MUSICEVENT_CHANGE].type, TypeName[Music Event])
290
temp0 = checkResult
291
CheckEqual(object[SLOT_MUSICEVENT_CHANGE].propertyValue, MUSICEVENT_TRANSITION)
292
temp0 &= checkResult
293
CheckEqual(stage.musicFlag, MUSICEVENT_FLAG_NOCHANGE)
294
temp0 &= checkResult
295
if temp0 == false
296
switch music.currentTrack
297
case TRACK_STAGE
298
SetMusicTrack("Invincibility.ogg", TRACK_INVINCIBLE, 39528)
299
SwapMusicTrack("MarathonBase.ogg", TRACK_STAGE, 635970, 12650)
300
break
301
302
case TRACK_INVINCIBLE
303
SetMusicTrack("MarathonBase.ogg", TRACK_STAGE, 635970)
304
SwapMusicTrack("Invincibility.ogg", TRACK_INVINCIBLE, 39528, 12500)
305
break
306
307
case TRACK_BOSS
308
SetMusicTrack("MarathonBase.ogg", TRACK_STAGE, 635970)
309
SetMusicTrack("Invincibility.ogg", TRACK_INVINCIBLE, 39528)
310
break
311
312
end switch
313
else
314
stage.musicFlag = MUSICEVENT_FLAG_SLOWDOWN
315
end if
316
end function
317
318
319
// ========================
320
// Events
321
// ========================
322
323
event ObjectUpdate
324
// Pulsing palette, for the lava
325
object.lavaPalTimer++
326
if object.lavaPalTimer == 12
327
object.lavaPalTimer = 0
328
329
object.lavaPalIndex1 += 4
330
object.lavaPalIndex1 &= 0x3F
331
GetTableValue(temp0, object.lavaPalIndex1, MBZSetup_lavaPalCycle)
332
SetPaletteEntry(0, 96, temp0)
333
334
object.lavaPalIndex2 += 4
335
object.lavaPalIndex2 &= 0x3F
336
GetTableValue(temp0, object.lavaPalIndex2, MBZSetup_lavaPalCycle)
337
SetPaletteEntry(0, 97, temp0)
338
339
object.lavaPalIndex3 += 4
340
object.lavaPalIndex3 &= 0x3F
341
GetTableValue(temp0, object.lavaPalIndex3, MBZSetup_lavaPalCycle)
342
SetPaletteEntry(0, 98, temp0)
343
344
object.lavaPalIndex4 += 4
345
object.lavaPalIndex4 &= 0x3F
346
GetTableValue(temp0, object.lavaPalIndex4, MBZSetup_lavaPalCycle)
347
SetPaletteEntry(0, 99, temp0)
348
end if
349
350
// Cycling palette
351
object.paletteTimer++
352
if object.paletteTimer == 4
353
object.paletteTimer = 0
354
RotatePalette(0, 100, 105, false)
355
end if
356
357
// Ani Tiles, for the oil
358
if object.oilAniTileDelay < 2
359
temp0 = object.oilAniTileFrame
360
temp0 += 462
361
Copy16x16Tile(408, temp0)
362
363
temp0++
364
Copy16x16Tile(409, temp0)
365
366
temp0++
367
Copy16x16Tile(410, temp0)
368
369
temp0++
370
Copy16x16Tile(411, temp0)
371
372
temp0 += 21
373
Copy16x16Tile(412, temp0)
374
375
temp0++
376
Copy16x16Tile(413, temp0)
377
378
temp0++
379
Copy16x16Tile(414, temp0)
380
381
temp0++
382
Copy16x16Tile(415, temp0)
383
384
object.oilAniTileDelay = 18
385
object.oilAniTileFrame += 4
386
object.oilAniTileFrame %= 24
387
else
388
object.oilAniTileDelay--
389
end if
390
391
// Water shining
392
object.deformTimer++
393
if object.deformTimer > 7
394
tileLayer[1].deformationOffset++
395
object.deformTimer = 0
396
end if
397
398
// Update some value, though this value never really does anything beyond this
399
// This looks similar to how CPZ Setup's CPZSetup_rotatingStairTimer updating works, but this script's CPZSetup_rotatingStairTimer is never changed
400
GetTableValue(temp0, 21, StageSetup_oscillationTable)
401
if temp0 == 0 // (this updates the value every 180 frames)
402
MBZSetup_unknownTimer++
403
MBZSetup_unknownTimer &= 3
404
end if
405
406
// Randomize the animals, looping around all the animals in the game
407
temp0 = oscillation
408
temp0 &= 15
409
if temp0 > 11
410
temp0 = 5
411
end if
412
temp0 += TypeName[Flicky] // In the object type list, all the animals are listed right after one another, starting from the Flicky
413
animalType1 = temp0
414
animalType2 = temp0
415
416
// Check interaction with players
417
foreach (GROUP_PLAYERS, currentPlayer, ACTIVE_ENTITIES)
418
if player[currentPlayer].animation == ANI_TWIRL
419
player[currentPlayer].frame %= 24
420
end if
421
422
temp1 = player[currentPlayer].xpos
423
temp1 >>= 16
424
425
temp2 = player[currentPlayer].ypos
426
temp2 >>= 16
427
temp2 += 6
428
429
// Get the B-plane "angle" of the tile the player is on
430
// "Angle" is actually used to hold flags and such, same goes for other stages
431
Get16x16TileInfo(temp0, temp1, temp2, TILEINFO_ANGLEB)
432
switch temp0
433
default
434
case TILE_NORMAL
435
break
436
437
case TILE_OILPOOL
438
if player[currentPlayer].yvel > -1
439
player[currentPlayer].state = MBZSetup_State_OilPool
440
if player[currentPlayer].animation == ANI_JUMPING
441
player[currentPlayer].animation = ANI_WALKING
442
end if
443
player[currentPlayer].gravity = GRAVITY_GROUND
444
player[currentPlayer].yvel = 0
445
player[currentPlayer].ypos += 0x10000
446
end if
447
break
448
449
case TILE_LAVA
450
// Lava tile
451
// Only harm the player if they don't have a flame shield
452
if player[currentPlayer].shield != SHIELD_FIRE
453
CallFunction(Player_Hit)
454
end if
455
break
456
457
end switch
458
next
459
460
// object.isDimming is set by a BG Dimmer object placed in the scene
461
if object.isDimming == true
462
// Fade in, with a max of halfway full
463
if object.alpha < 0x80
464
object.alpha += 4
465
end if
466
else
467
// Fade out, if not fading in
468
if object.alpha > 0
469
object.alpha -= 4
470
end if
471
end if
472
473
// Reset it for the next frame
474
object.isDimming = false
475
end event
476
477
478
event ObjectDraw
479
// Draw a tint in the background, right between the BG and the FG
480
// -> This is always drawn, it's just that object.alpha is 0 most of the time so nothing is really seen
481
DrawRect(0, 0, 512, 240, 0x00, 0x20, 0x50, object.alpha)
482
end event
483
484
485
event ObjectStartup
486
SetMusicTrack("DeathEgg.ogg", TRACK_STAGE, true)
487
488
// Reset the black color used in boss flashes
489
SetPaletteEntry(0, 192, 0x000000)
490
491
object[SLOT_ZONESETUP].type = TypeName[MBZ Setup]
492
object[SLOT_ZONESETUP].priority = PRIORITY_ACTIVE
493
object[SLOT_ZONESETUP].lavaPalIndex1 = 0
494
object[SLOT_ZONESETUP].lavaPalIndex2 = 1
495
object[SLOT_ZONESETUP].lavaPalIndex3 = 2
496
object[SLOT_ZONESETUP].lavaPalIndex4 = 3
497
498
// Most Zone Setups don't have a Draw Order specified, but this one needs it for the black fade in places like the MCZ boss
499
object[SLOT_ZONESETUP].drawOrder = 1
500
501
// While this is primarily meant for the little snippit water in the normal background,
502
// it's worth noting that the third background layer has deformation enabled for its entirety, rather than just its water
503
arrayPos0 = 0
504
while arrayPos0 < 576
505
temp0 = arrayPos0
506
temp0 &= 0x3F
507
GetTableValue(stage.deformationData2[arrayPos0], temp0, MBZSetup_deformationTable)
508
arrayPos0++
509
loop
510
511
CPZSetup_rotatingStairTimer = 0
512
Water_flashTimer = 0
513
CPZSetup_hasAchievement = false
514
CPZSetup_enteredWater = 0
515
MBZSetup_unused1 = 0
516
MBZSetup_unused2 = 0
517
MBZSetup_unused3 = 0
518
MBZSetup_unused4 = 0
519
end event
520
521
522
// ========================
523
// Editor Events
524
// ========================
525
526
event RSDKDraw
527
DrawSprite(0)
528
end event
529
530
531
event RSDKLoad
532
LoadSpriteSheet("Global/Display.gif")
533
SpriteFrame(-16, -16, 32, 32, 1, 143)
534
535
SetVariableAlias(ALIAS_VAR_PROPVAL, "unused")
536
end event
537
538