summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorRangi <remy.oukaour+rangi42@gmail.com>2018-05-24 11:46:41 -0400
committerRangi <remy.oukaour+rangi42@gmail.com>2018-05-24 11:46:41 -0400
commitd61536ab1c56ad341d07e963cb7e8ad7235c29b4 (patch)
tree5c3a78e4463fe1f2f44595023d330b86097be148
parent88ad57fe149008e94468e442117ac7121132196c (diff)
Add a new sprite movement behavior
-rw-r--r--Add-a-new-sprite-movement-behavior.md99
-rw-r--r--Tutorials.md1
2 files changed, 100 insertions, 0 deletions
diff --git a/Add-a-new-sprite-movement-behavior.md b/Add-a-new-sprite-movement-behavior.md
new file mode 100644
index 0000000..740d19b
--- /dev/null
+++ b/Add-a-new-sprite-movement-behavior.md
@@ -0,0 +1,99 @@
+This tutorial is for how to add a new sprite movement behavior.
+
+Sprite movement behaviors are what you specify with the `SPRITEMOVEDATA_*` constants for `object_event`s in map event scripts. They control the object's sprite appearance as well as how it interacts with the map. For example, objects with `SPRITEMOVEDATA_WALK_UP_DOWN` appear as a 16x16 pixel sprite that walks up and down within a certain radius; while objects with `SPRITEMOVEDATA_BIGDOLL` appear as a 32x32 pixel sprite that does not move.
+
+
+## Contents
+
+1. [Define sprite movement constant and data](#1-define-sprite-movement-constant-and-data)
+
+
+## 1. Define sprite movement constant and data
+
+At a minimum, you need to define a new `SPRITEMOVEDATA_*` constant and its corresponding data. As an example, we'll define `SPRITEMOVEDATA_SWIM_UP_DOWN`.
+
+Edit [constants/map_object_constants.asm](../blob/master/constants/map_object_constants.asm):
+
+```diff
+ ; SpriteMovementData indexes (see data/sprites/map_objects.asm)
+ const_def
+ const SPRITEMOVEDATA_00 ; 00
+ ...
+ const SPRITEMOVEDATA_SWIM_WANDER ; 24
++ const SPRITEMOVEDATA_SWIM_UP_DOWN
+ NUM_SPRITEMOVEDATA EQU const_value
+```
+
+And edit [data/sprites/map_objects.asm](../blob/master/data/sprites/map_objects.asm):
+
+```diff
+ SpriteMovementData:: ; 4273
+ ; entries correspond to SPRITEMOVEDATA_* constants
+
+ ; SPRITEMOVEDATA_00
+ db SPRITEMOVEFN_00 ; movement function
+ db DOWN ; facing
+ db OBJECT_ACTION_STAND ; action
+ db WONT_DELETE ; flags1
+ db 0 ; flags2
+ db 0 ; palette flags
+
+ ...
+
+ ; SPRITEMOVEDATA_SWIM_WANDER
+ db SPRITEMOVEFN_RANDOM_WALK_XY ; movement function
+ db DOWN ; facing
+ db OBJECT_ACTION_STAND ; action
+ db 0 ; flags1
+ db 0 ; flags2
+ db SWIMMING ; palette flags
+
+-; 25
+- db SPRITEMOVEFN_00 ; movement function
+- db DOWN ; facing
+- db OBJECT_ACTION_STAND ; action
+- db 0 ; flags1
+- db 0 ; flags2
+- db 0 ; palette flags
++; SPRITEMOVEDATA_SWIM_UP_DOWN
++ db SPRITEMOVEFN_RANDOM_WALK_Y ; movement function
++ db DOWN ; facing
++ db OBJECT_ACTION_STAND ; action
++ db 0 ; flags1
++ db 0 ; flags2
++ db SWIMMING ; palette flags
+
+ ; 4357
+```
+
+Note that we had to delete some unused data at the bottom which didn't correspond to any `SPRITEMOVEDATA_*` constant.
+
+Here's what the individual `db` values mean:
+
+- **movement function:** A `SPRITEMOVEFN_*` constant, as defined in [constants/map_object_constants.asm](../blob/master/constants/map_object_constants.asm).
+- **facing:** `UP`, `DOWN`, `LEFT`, or `RIGHT`.
+- **action:** An `OBJECT_ACTION_*` constant, as defined in [constants/map_object_constants.asm](../blob/master/constants/map_object_constants.asm).
+- **flags1:** A combination of any of these values, or 0 for none of them:
+ - `WONT_DELETE`: The object won't be deleted if it moves off-screen. Example: `SPRITEMOVEDATA_STRENGTH_BOULDER`, which needs to stay where it's been pushed.
+ - `FIXED_FACING`: The object doesn't change its facing direction if it moves. Example: `SPRITEMOVEDATA_SHADOW`, which moves along with the player over a ledge but always looks the same.
+ - `SLIDING`: The object doesn't animate its steps if it moves. Example: `SPRITEMOVEDATA_GRASS`, which moves along with the player through tall grass but doesn't have a "stepping" animation.
+ - `MOVE_ANYWHERE`: The object isn't limited to moving within a particular radius. Example: `SPRITEMOVEDATA_STRENGTH_BOULDER`, which can be pushed anywhere.
+ - `EMOTE_OBJECT`: The object is meant to be transient and gets deleted differently. Example: `SPRITEMOVEDATA_EMOTE`, which pops up briefly above an NPC.
+- **flags2:** A combination of any of these values, or 0 for none of them:
+ - `LOW_PRIORITY`: The object will appear below other objects, which have normal priority by default. Example: `SPRITEMOVEDATA_BOULDERDUST`, which appears below Strength boulders when they're pushed.
+ - `HIGH_PRIORITY`: The object will appear above other objects. Do not combine with `LOW_PRIORITY`. Example: `SPRITEMOVEDATA_GRASS`, which appears above the player when walking through tall grass.
+ - `USE_OBP1`: The object will use SGB palette #1 instead of #0. This was relevant for Gold and Silver since they could be played on the Super Game Boy, but not Crystal.
+- **palette flags:** A combination of any of these values, or 0 for none of them:
+ - `SWIMMING`: The object can move over water but is blocked by land, instead of vice-versa.
+ - `STRENGTH_BOULDER`: The object blocks the player if they haven't used Strength. Example: `SPRITEMOVEDATA_STRENGTH_BOULDER` of course, but also the `SPRITEMOVEDATA_BIGDOLL*` data for some reason.
+ - `BIG_OBJECT`: The object blocks the spaces below it, to its right, and to its bottom-right, not just the space its coordinates are at. Example: `SPRITEMOVEDATA_BIGDOLLSYM`, which is used for the Snorlax in Vermilion City.
+
+In the example, we based `SPRITEMOVEDATA_SWIM_UP_DOWN` off of `SPRITEMOVEDATA_SWIM_WANDER` but gave it the same movement function as `SPRITEMOVEDATA_WALK_UP_DOWN`. In particular, it needed the `SWIMMING` palette flag.
+
+One more thing: there happens to be a bug that affects objects which swim and move randomly; they're not actually limited by their movement radius. So be sure to [fix that](../blob/master/docs/bugs_and_glitches.md#function6ec1-does-not-correctly-limit-object-movement).
+
+Anyway, that's all! Now you can use `SPRITEMOVEDATA_SWIM_UP_DOWN` for `object_event`s just like the rest.
+
+TODO: define new `SPRITEMOVEFN_*`, `OBJECT_ACTION_*`, and `FACING_*` data.
+
+TODO: define new `STEP_TYPE_*` and `STEP_* data.
diff --git a/Tutorials.md b/Tutorials.md
index 07bd98c..8ebbf14 100644
--- a/Tutorials.md
+++ b/Tutorials.md
@@ -18,6 +18,7 @@ Tutorials may use diff syntax to show edits:
- [Item (up to 254)](Add-different-kinds-of-new-items)
- [TM (up to 120)](Add-a-new-TM)
- [Overworld sprite](Add-a-new-overworld-sprite)
+- [Sprite movement behavior](Add-a-new-sprite-movement-behavior)
- [Music song](Add-a-new-music-song)
- [Pack pocket](Add-a-new-Pack-pocket)