-
Notifications
You must be signed in to change notification settings - Fork 1
Tutorial) 7. Cameras
Note: This tutorial is specifically geared towards beginners who have little to no programming experience. Because of this, a lot of simple stuff will be explained. These explanations will become more scarce as the tutorial goes on as every section expects the reader to have read everything prior to it, so repetition is not needed.
When you start this section of the tutorial, you should already know how to create and use spritesheets, frames, animations, entities, and the debugger. Make sure you understand everything in this code, as you should start with it for this section:
#include <3ds.h>
#include <spritetools.h>
#include <stdio.h>
#include <link_overworld_png.h>
int main(void)
{
ST_Init();
ST_Splashscreen(2510);
consoleInit(GFX_BOTTOM, NULL);
st_spritesheet *link_o_s = ST_SpritesheetCreateSpritesheetPNG(link_overworld_png);
st_entity *link_o_e = ST_EntityCreateEntity(50, 50, 8);
ST_EntityAddAnimation(link_o_e,
ST_AnimationCreateAnimation(0, 0, 1,
ST_AnimationCreateFrameOffset(link_o_s, 4, 2, 18, 24, 0, 12)),
"standing south");
ST_EntityAddAnimation(link_o_e,
ST_AnimationCreateAnimation(0, 0, 1,
ST_AnimationCreateFrameOffset(link_o_s, 3, 29, 17, 23, 1, 11)),
"standing east");
ST_EntityAddAnimation(link_o_e,
ST_AnimationCreateAnimation(0, 0, 1,
ST_AnimationCreateFrameOffset(link_o_s, 4, 56, 18, 23, 0, 10)),
"standing north");
ST_EntityAddAnimation(link_o_e,
ST_AnimationCreateAnimation(0, 0, 1,
ST_AnimationCreateFrameOffset(link_o_s, 6, 81, 17, 23, -1, 11)),
"standing west");
ST_EntityAddAnimation(link_o_e,
ST_AnimationCreateAnimation(4, 0, 10,
ST_AnimationCreateFrameOffset(link_o_s, 30, 2, 18, 24, 0, 12),
ST_AnimationCreateFrameOffset(link_o_s, 56, 1, 18, 25, 0, 12),
ST_AnimationCreateFrameOffset(link_o_s, 82, 0, 18, 26, 0, 13),
ST_AnimationCreateFrameOffset(link_o_s, 108, 0, 18, 26, 0, 13),
ST_AnimationCreateFrameOffset(link_o_s, 134, 1, 18, 25, 0, 12),
ST_AnimationCreateFrameOffset(link_o_s, 160, 2, 18, 24, 0, 12),
ST_AnimationCreateFrameOffset(link_o_s, 186, 1, 18, 25, 0, 12),
ST_AnimationCreateFrameOffset(link_o_s, 212, 0, 18, 26, 0, 13),
ST_AnimationCreateFrameOffset(link_o_s, 238, 0, 18, 26, 0, 13),
ST_AnimationCreateFrameOffset(link_o_s, 264, 1, 18, 25, 0, 12)),
"walking south");
ST_EntityAddAnimation(link_o_e,
ST_AnimationCreateAnimation(4, 0, 10,
ST_AnimationCreateFrameOffset(link_o_s, 26, 29, 21, 23, 3, 11),
ST_AnimationCreateFrameOffset(link_o_s, 53, 29, 20, 23, 2, 11),
ST_AnimationCreateFrameOffset(link_o_s, 81, 27, 20, 25, 0, 12),
ST_AnimationCreateFrameOffset(link_o_s, 106, 27, 20, 25, 1, 12),
ST_AnimationCreateFrameOffset(link_o_s, 131, 28, 20, 24, 2, 12),
ST_AnimationCreateFrameOffset(link_o_s, 156, 29, 20, 23, 3, 11),
ST_AnimationCreateFrameOffset(link_o_s, 183, 29, 19, 23, 3, 11),
ST_AnimationCreateFrameOffset(link_o_s, 211, 27, 19, 25, 0, 12),
ST_AnimationCreateFrameOffset(link_o_s, 236, 27, 19, 25, 1, 12),
ST_AnimationCreateFrameOffset(link_o_s, 261, 28, 20, 24, 2, 12)),
"walking east");
ST_EntityAddAnimation(link_o_e,
ST_AnimationCreateAnimation(4, 0, 10,
ST_AnimationCreateFrameOffset(link_o_s, 30, 55, 18, 24, 0, 12),
ST_AnimationCreateFrameOffset(link_o_s, 56, 55, 18, 23, 0, 11),
ST_AnimationCreateFrameOffset(link_o_s, 82, 53, 18, 25, 0, 12),
ST_AnimationCreateFrameOffset(link_o_s, 108, 53, 18, 25, 0, 12),
ST_AnimationCreateFrameOffset(link_o_s, 134, 54, 18, 24, 0, 12),
ST_AnimationCreateFrameOffset(link_o_s, 160, 55, 18, 23, 0, 11),
ST_AnimationCreateFrameOffset(link_o_s, 186, 54, 18, 24, 0, 12),
ST_AnimationCreateFrameOffset(link_o_s, 212, 53, 18, 25, 0, 12),
ST_AnimationCreateFrameOffset(link_o_s, 238, 53, 18, 25, 0, 12),
ST_AnimationCreateFrameOffset(link_o_s, 264, 54, 18, 24, 0, 12)),
"walking north");
ST_EntityAddAnimation(link_o_e,
ST_AnimationCreateAnimation(4, 0, 10,
ST_AnimationCreateFrameOffset(link_o_s, 31, 81, 21, 23, -3, 11),
ST_AnimationCreateFrameOffset(link_o_s, 57, 81, 20, 23, -2, 11),
ST_AnimationCreateFrameOffset(link_o_s, 81, 79, 20, 25, 0, 12),
ST_AnimationCreateFrameOffset(link_o_s, 108, 79, 20, 25, -1, 12),
ST_AnimationCreateFrameOffset(link_o_s, 135, 80, 20, 24, -2, 12),
ST_AnimationCreateFrameOffset(link_o_s, 161, 81, 21, 23, -3, 11),
ST_AnimationCreateFrameOffset(link_o_s, 188, 81, 19, 23, -3, 11),
ST_AnimationCreateFrameOffset(link_o_s, 212, 79, 19, 25, 0, 12),
ST_AnimationCreateFrameOffset(link_o_s, 239, 79, 19, 25, -1, 12),
ST_AnimationCreateFrameOffset(link_o_s, 265, 80, 20, 24, -2, 12)),
"walking west");
ST_RenderSetBackground(0x82, 0xE1, 0x11);
while (aptMainLoop())
{
ST_RenderStartFrame(GFX_TOP);
ST_InputScan();
if (ST_InputButtonPressed(KEY_START))
break;
if (ST_InputButtonDown(KEY_DLEFT))
{
ST_EntityModifyXPosition(link_o_e, -1);
ST_EntitySetDirection(link_o_e, "west");
}
if (ST_InputButtonDown(KEY_DRIGHT))
{
ST_EntityModifyXPosition(link_o_e, 1);
ST_EntitySetDirection(link_o_e, "east");
}
if (ST_InputButtonDown(KEY_DUP))
{
ST_EntityModifyYPosition(link_o_e, -1);
ST_EntitySetDirection(link_o_e, "north");
}
if (ST_InputButtonDown(KEY_DDOWN))
{
ST_EntityModifyYPosition(link_o_e, 1);
ST_EntitySetDirection(link_o_e, "south");
}
sprintf(tempstr, "standing %s", link_o_e->dir);
ST_EntitySetAnimationName(link_o_e, tempstr);
ST_RenderEntity(link_o_e);
if (ST_InputButtonPressed(KEY_SELECT))
{
if(ST_DebugGet())
ST_DebugSetOff();
else
ST_DebugSetOn();
}
if (ST_InputButtonDown(KEY_DUP) && ST_InputButtonDown(KEY_L))
ST_DebugScrollUp(1);
if (ST_InputButtonDown(KEY_DDOWN) && ST_InputButtonDown(KEY_L))
ST_DebugScrollDown(1);
ST_DebugDisplay();
ST_RenderEndRender();
}
ST_SpritesheetFreeSpritesheet(link_o_s);
ST_Fini();
return 0;
}
First, we need to create an entity using the function ST_CameraCreate(double x, double y)
and free it at the end of our program before freeing our spritesheet with the function ST_CameraFree(st_camera *cam)
.
int main(void)
{
/* ...Code... */
st_camera *my_cam = ST_CameraCreate(0, 0);
while (aptMainLoop())
{
/* ...Code... */
}
ST_CameraFree(my_cam);
/* ...Code... */
}
Now let's give our camera some properties like rotation and zoom:
#include <math.h>
/* ...Code... */
st_camera *my_cam = ST_CameraCreate(0, 0);
ST_CameraRotateSet(my_cam, M_PI / 4); // Set rotation to 45 degrees
ST_CameraZoomSet(my_cam, 1.5); // Set zoom to 1.5x
/* ...Code... */
With a camera, we can render entities with it using ST_RenderEntityCamera(st_entity *entity, st_camera *cam)
instead of `ST_RenderEntity(st_entity *entity). The difference between rendering entities with and without a camera is that by using a camera, we can modify all of the entities positions, rotations, and scales at the same time by modifying the camera they're being rendered with.
/* ...Code... */
st_spritesheet *link_o_s = ST_SpritesheetCreateSpritesheetPNG(link_overworld_png);
st_entity *link_o_e = ST_EntityCreateEntity(50, 50, 8);
/* ...Code... */
st_camera *my_cam = ST_CameraCreate(0, 0);
while (aptMainLoop())
{
/* ...Code... */
ST_RenderEntityCamera(link_o_e, cam);
/* ...Code... */
}
ST_CameraFree(my_cam);
ST_EntityFreeEntity(link_o_e);
ST_SpritesheetFreeSpritesheet(link_o_s);
/* ...Code... */
You can also use the following functions to modify how an entity is rendered:
Function | Description |
---|---|
ST_EntitySetXPosition(st_entity *entity, s64 x) |
Sets the entity's X position to the given value |
ST_EntitySetYPosition(st_entity *entity, s64 y) |
Sets the entity's Y position to the given value |
ST_EntitySetPosition(st_entity *entity, s64 x, s64 y) |
Sets the entity's position to the given values |
ST_EntitySetScale(st_entity *entity, double scale) |
Sets the entity's scale to the given value |
ST_EntitySetRotation(st_entity *entity, double rotation) |
Sets the entity's rotation to the given value |
ST_EntitySetRed(st_entity *entity, u8 red) |
Sets the red of an entity's blending color |
ST_EntitySetGreen(st_entity *entity, u8 green) |
Sets the green of an entity's blending color |
ST_EntitySetBlue(st_entity *entity, u8 blue) |
Sets the blue of an entity's blending color |
ST_EntitySetAlpha(st_entity *entity, u8 alpha) |
Sets the alpha of an entity's blending color |
ST_EntitySetColor(st_entity *entity, u8 red, u8 green, u8 blue, u8 alpha) |
Sets the values of an entity's blending color |
ST_EntitySetDirection(st_entity *entity, char *dir) |
Sets the entity's direction by name ie: "west", "south", "north east" |
ST_EntitySetDirectionId(st_entity *entity, u8 dir) |
Sets the entity's direction by id ie: 0 for "east", 3 for "south west", 6 for "north" |
ST_EntitySetAnimationName(st_entity *entity, char *name) |
Sets the entity's current animation by name (if the animation exists) |
ST_EntitySetAnimationId(st_entity *entity, u8 id) |
Sets the entity's current animation by id (if the animation exists) |
Function | Description |
---|---|
ST_EntityModifyXPosition(st_entity *entity, s64 x) |
Adds the given value to the entity's x position |
ST_EntityModifyYPosition(st_entity *entity, s64 y) |
Adds the given value to the entity's y position |
ST_EntityModifyPosition(st_entity *entity, s64 x, s64 y) |
Adds the given values to the entity's position values |
ST_EntityModifyScale(st_entity *entity, double scale) |
Adds the given value to the entity's scale |
ST_EntityModifyRotation(st_entity *entity, double rotation) |
Adds the given value to the entity's rotation |
ST_EntityModifyRotationNoWrap(st_entity *entity, double rotation) |
Same as above, but will not wrap past 0 or 2*pi |
ST_EntityModifyRed(st_entity *entity, u8 red) |
Adds the given value to the red of an entity's blending color |
ST_EntityModifyRedNoWrap(st_entity *entity, u8 red) |
Same as above, but will not wrap past 0 or 255 |
ST_EntityModifyGreen(st_entity *entity, u8 green) |
Adds the given value to the green of an entity's blending color |
ST_EntityModifyGreenNoWrap(st_entity *entity, u8 green) |
Same as above, but will not wrap past 0 or 255 |
ST_EntityModifyBlue(st_entity *entity, u8 blue) |
Adds the given value to the blue of an entity's blending color |
ST_EntityModifyBlueNoWrap(st_entity *entity, u8 blue) |
Same as above, but will not wrap past 0 or 255 |
ST_EntityModifyAlpha(st_entity *entity, u8 alpha) |
Adds the given value to the alpha of an entity's blending color |
ST_EntityModifyAlphaNoWrap(st_entity *entity, u8 alpha) |
Same as above, but will not wrap past 0 or 255 |
ST_EntityModifyColor(st_entity *entity, u8 red, u8 green, u8 blue, u8 alpha) |
Adds the given values to the values of an entity's blending color |
ST_EntityModifyColorNoWrap(st_entity *entity, u8 red, u8 green, u8 blue, u8 alpha) |
Same as above, but will not wrap past 0 or 255 |
ST_EntityModifyDirection(st_entity *entity, s8 dir) |
Modifies the entity's direction by the given value. Positive turns right, negative turns left |
New to SpriteTools? Start here!