This commit is contained in:
Miloslav Číž 2018-09-17 17:55:33 +02:00
parent e91fb33a89
commit 6b9de75174
5 changed files with 184 additions and 181 deletions

View file

@ -15,10 +15,10 @@
// redefine some parameters // redefine some parameters
#define FPS 60 #define FPS 60
#define GRAVITY_ACCELERATION (UNITS_PER_SQUARE * 3) #define GRAVITY_ACCELERATION (RCL_UNITS_PER_SQUARE * 3)
#define PLAYER_JUMP_SPEED 700 #define PLAYER_JUMP_SPEED 700
#define CAMERA_COLL_HEIGHT_BELOW ((3 * UNITS_PER_SQUARE) / 2) #define RCL_CAMERA_COLL_HEIGHT_BELOW ((3 * RCL_UNITS_PER_SQUARE) / 2)
#define HORIZONTAL_FOV (UNITS_PER_SQUARE / 5) #define RCL_HORIZONTAL_FOV (RCL_UNITS_PER_SQUARE / 5)
//#define USE_DIST_APPROX 1 //#define USE_DIST_APPROX 1
// ^ This turns on distance approximation, which is a bit uglier and faster. // ^ This turns on distance approximation, which is a bit uglier and faster.
@ -31,7 +31,7 @@
Player player; Player player;
#define SPRITES 17 #define SPRITES 17
#define SPRITE_MAX_DISTANCE 5 * UNITS_PER_SQUARE #define SPRITE_MAX_DISTANCE 5 * RCL_UNITS_PER_SQUARE
Sprite sprites[SPRITES]; Sprite sprites[SPRITES];
@ -961,24 +961,24 @@ const unsigned char *textures[] = {texture1, texture2, texture3, texture4};
else\ else\
return (whatElse); return (whatElse);
Unit textureAt(int16_t x, int16_t y) RCL_Unit textureAt(int16_t x, int16_t y)
{ {
withinMapReturn(levelTexture[index],0) withinMapReturn(levelTexture[index],0)
} }
Unit floorHeightAt(int16_t x, int16_t y) RCL_Unit floorHeightAt(int16_t x, int16_t y)
{ {
if (x == 6 && (y == 13 || y == 14)) // moving lift if (x == 6 && (y == 13 || y == 14)) // moving lift
return return
((absVal(-1 * (pokitto.frameCount % 64) + 32)) * UNITS_PER_SQUARE) / 8; ((RCL_absVal(-1 * (pokitto.frameCount % 64) + 32)) * RCL_UNITS_PER_SQUARE) / 8;
withinMapReturn((levelFloor[index] * UNITS_PER_SQUARE) / 8,0) withinMapReturn((levelFloor[index] * RCL_UNITS_PER_SQUARE) / 8,0)
} }
Unit ceilingHeightAt(int16_t x, int16_t y) RCL_Unit ceilingHeightAt(int16_t x, int16_t y)
{ {
withinMapReturn(levelCeiling[index] * UNITS_PER_SQUARE / 8, withinMapReturn(levelCeiling[index] * RCL_UNITS_PER_SQUARE / 8,
127 * UNITS_PER_SQUARE / 8) 127 * RCL_UNITS_PER_SQUARE / 8)
} }
#undef withinMapReturn #undef withinMapReturn
@ -987,17 +987,17 @@ Unit ceilingHeightAt(int16_t x, int16_t y)
Function for drawing a single pixel (like fragment shader). Bottleneck => Function for drawing a single pixel (like fragment shader). Bottleneck =>
should be as fast as possible. should be as fast as possible.
*/ */
inline void pixelFunc(PixelInfo *pixel) inline void pixelFunc(RCL_PixelInfo *pixel)
{ {
if (pixel->position.y == MIDDLE_ROW) if (pixel->position.y == MIDDLE_ROW)
zBuffer[pixel->position.x] = pixel->depth; zBuffer[pixel->position.x] = pixel->depth;
uint8_t c; uint8_t c;
Unit depth = pixel->depth - UNITS_PER_SQUARE * 3; RCL_Unit depth = pixel->depth - RCL_UNITS_PER_SQUARE * 3;
depth = depth > 0 ? depth : 1; depth = depth > 0 ? depth : 1;
int intensity = 7 - (depth * 7) / (UNITS_PER_SQUARE * 5); int intensity = 7 - (depth * 7) / (RCL_UNITS_PER_SQUARE * 5);
if (intensity < 0) if (intensity < 0)
intensity = 0; intensity = 0;
@ -1010,7 +1010,7 @@ inline void pixelFunc(PixelInfo *pixel)
if (intensity < 0) if (intensity < 0)
intensity = 0; intensity = 0;
#if COMPUTE_WALL_TEXCOORDS == 1 #if RCL_COMPUTE_WALL_TEXCOORDS == 1
c = sampleImage(textures[pixel->hit.type],pixel->texCoords.x,pixel->texCoords.y); c = sampleImage(textures[pixel->hit.type],pixel->texCoords.x,pixel->texCoords.y);
#else #else
c = textures[pixel->hit.type][2]; c = textures[pixel->hit.type][2];
@ -1028,27 +1028,27 @@ inline void pixelFunc(PixelInfo *pixel)
void draw() void draw()
{ {
RayConstraints c; RCL_RayConstraints c;
c.maxHits = 8; c.maxHits = 8;
c.maxSteps = 10; c.maxSteps = 10;
render(player.mCamera,floorHeightAt,ceilingHeightAt,textureAt,c); RCL_render(player.mCamera,floorHeightAt,ceilingHeightAt,textureAt,c);
Unit previousDepth; RCL_Unit previousDepth;
// draw sprites // draw sprites
for (uint8_t i = 0; i < SPRITES; ++i) for (uint8_t i = 0; i < SPRITES; ++i)
{ {
// use Chebyshew distance instead Euclidean, it's faster // use Chebyshew distance instead Euclidean, it's faster
if (absVal(sprites[i].mPosition.x - player.mCamera.position.x) > SPRITE_MAX_DISTANCE) if (RCL_absVal(sprites[i].mPosition.x - player.mCamera.position.x) > SPRITE_MAX_DISTANCE)
continue; continue;
if (absVal(sprites[i].mPosition.y - player.mCamera.position.y) > SPRITE_MAX_DISTANCE) if (RCL_absVal(sprites[i].mPosition.y - player.mCamera.position.y) > SPRITE_MAX_DISTANCE)
continue; continue;
PixelInfo pos = mapToScreen(sprites[i].mPosition,sprites[i].mHeight,player.mCamera); RCL_PixelInfo pos = RCL_mapToScreen(sprites[i].mPosition,sprites[i].mHeight,player.mCamera);
if (pos.depth > 0) if (pos.depth > 0)
{ {
@ -1060,7 +1060,7 @@ void draw()
drawSpriteSquare(image,pos.position.x * SUBSAMPLE, drawSpriteSquare(image,pos.position.x * SUBSAMPLE,
pos.position.y, pos.depth, pos.position.y, pos.depth,
perspectiveScale(sprites[i].mPixelSize,pos.depth)); RCL_perspectiveScale(sprites[i].mPixelSize,pos.depth));
} }
/* trick: sort the sprites by distance with bubble sort as we draw - the /* trick: sort the sprites by distance with bubble sort as we draw - the
@ -1102,7 +1102,7 @@ int main()
sprites[1] = Sprite(spriteStatue,14,5,1,100); sprites[1] = Sprite(spriteStatue,14,5,1,100);
sprites[2] = Sprite(spriteNPC,15,19,1,200); sprites[2] = Sprite(spriteNPC,15,19,1,200);
sprites[3] = Sprite(spriteTree,8,2,1,300); sprites[3] = Sprite(spriteTree,8,2,1,300);
sprites[3].mPosition.y -= UNITS_PER_SQUARE / 2; sprites[3].mPosition.y -= RCL_UNITS_PER_SQUARE / 2;
sprites[4] = Sprite(spriteTree,20,5,1,300); sprites[4] = Sprite(spriteTree,20,5,1,300);
sprites[5] = Sprite(spriteTree,26,18,1,300); sprites[5] = Sprite(spriteTree,26,18,1,300);
sprites[6] = Sprite(spriteTree,16,12,1,300); sprites[6] = Sprite(spriteTree,16,12,1,300);
@ -1113,13 +1113,13 @@ int main()
sprites[11] = Sprite(spriteBarrel,12,16,0,120); sprites[11] = Sprite(spriteBarrel,12,16,0,120);
sprites[12] = Sprite(spriteBarrel,27,5,0,120); sprites[12] = Sprite(spriteBarrel,27,5,0,120);
sprites[13] = Sprite(spriteTorch1,11,9,2,120); sprites[13] = Sprite(spriteTorch1,11,9,2,120);
sprites[13].mPosition.y += UNITS_PER_SQUARE / 3; sprites[13].mPosition.y += RCL_UNITS_PER_SQUARE / 3;
sprites[14] = Sprite(spriteTorch1,13,9,2,120); sprites[14] = Sprite(spriteTorch1,13,9,2,120);
sprites[14].mPosition.y += UNITS_PER_SQUARE / 3; sprites[14].mPosition.y += RCL_UNITS_PER_SQUARE / 3;
sprites[15] = Sprite(spriteTorch1,14,19,2,120); sprites[15] = Sprite(spriteTorch1,14,19,2,120);
sprites[15].mPosition.y += UNITS_PER_SQUARE / 3; sprites[15].mPosition.y += RCL_UNITS_PER_SQUARE / 3;
sprites[16] = Sprite(spriteTorch1,1,19,3,120); sprites[16] = Sprite(spriteTorch1,1,19,3,120);
sprites[16].mPosition.y += UNITS_PER_SQUARE / 3; sprites[16].mPosition.y += RCL_UNITS_PER_SQUARE / 3;
uint32_t previousTime = 0; uint32_t previousTime = 0;
uint32_t dt; uint32_t dt;

View file

@ -34,12 +34,12 @@
//#define NO_MIRROR //#define NO_MIRROR
/* ^ Turns off the floor mirror effect, which should increase FPS. */ /* ^ Turns off the floor mirror effect, which should increase FPS. */
//#define USE_DIST_APPROX 1 //#define RCL_USE_DIST_APPROX 1
/* ^ Turns on distance approximation, which won't compute exact distances but /* ^ Turns on distance approximation, which won't compute exact distances but
only approximations - this should increase performance a little, but only approximations - this should increase performance a little, but
results in slightly distorted walls. */ results in slightly distorted walls. */
//#define USE_COS_LUT 2 //#define RCL_USE_COS_LUT 2
/* ^ Turns on cos look up tables (128 items, USE_COS_LUT 1 will use only 64 /* ^ Turns on cos look up tables (128 items, USE_COS_LUT 1 will use only 64
items), which should theoretically be faster, but will take additional items), which should theoretically be faster, but will take additional
memory and turning can be less precise (can be seen a lot with 64 item memory and turning can be less precise (can be seen a lot with 64 item
@ -50,13 +50,13 @@
right, 0 to both. */ right, 0 to both. */
#ifdef NO_TEXTURES #ifdef NO_TEXTURES
#define COMPUTE_WALL_TEXCOORDS 0 #define RCL_COMPUTE_WALL_TEXCOORDS 0
#endif #endif
#define FPS 256 #define FPS 256
#define HEAD_BOB_HEIGHT 200 #define HEAD_BOB_HEIGHT 200
#define HEAD_BOB_STEP 20 #define HEAD_BOB_STEP 20
#define PLAYER_SPEED (5 * UNITS_PER_SQUARE) #define PLAYER_SPEED (5 * RCL_UNITS_PER_SQUARE)
#include "general.hpp" #include "general.hpp"
@ -65,9 +65,9 @@
Player player; Player player;
#define SHOT_SPEED 10 * UNITS_PER_SQUARE #define SHOT_SPEED 10 * RCL_UNITS_PER_SQUARE
#define INFO_BAR_START 70 #define INFO_BAR_START 70
#define TEXTURE_MAX_DISTANCE (UNITS_PER_SQUARE * 6) #define TEXTURE_MAX_DISTANCE (RCL_UNITS_PER_SQUARE * 6)
// temporary defines for better visibility of walls and floors below // temporary defines for better visibility of walls and floors below
#define D 6 #define D 6
@ -875,34 +875,34 @@ const unsigned char *textures[TEXTURES] =
unsigned char textureAverageColors[TEXTURES]; unsigned char textureAverageColors[TEXTURES];
Unit floorHeightAt(int16_t x, int16_t y) RCL_Unit floorHeightAt(int16_t x, int16_t y)
{ {
if (x < 0 || x >= LEVEL_X_RES || y < 0 || y >= LEVEL_Y_RES) if (x < 0 || x >= LEVEL_X_RES || y < 0 || y >= LEVEL_Y_RES)
return UNITS_PER_SQUARE * 2; return RCL_UNITS_PER_SQUARE * 2;
Unit square = level[(LEVEL_Y_RES - y -1) * LEVEL_X_RES + x]; RCL_Unit square = level[(LEVEL_Y_RES - y -1) * LEVEL_X_RES + x];
#ifdef RENDER_PRECISE #ifdef RENDER_PRECISE
/* algorithm used with this version doesn't support rolling doors, so give /* algorithm used with this version doesn't support rolling doors, so give
door square zero height */ door square zero height */
return square == 0 || square == 6 ? 0 : UNITS_PER_SQUARE * 2; return square == 0 || square == 6 ? 0 : RCL_UNITS_PER_SQUARE * 2;
#else #else
return square == 0 ? 0 : UNITS_PER_SQUARE * 2; return square == 0 ? 0 : RCL_UNITS_PER_SQUARE * 2;
#endif #endif
} }
Unit collisionAt(int16_t x, int16_t y) RCL_Unit collisionAt(int16_t x, int16_t y)
{ {
if (x < 0 || x >= LEVEL_X_RES || y < 0 || y >= LEVEL_Y_RES) if (x < 0 || x >= LEVEL_X_RES || y < 0 || y >= LEVEL_Y_RES)
return UNITS_PER_SQUARE; return RCL_UNITS_PER_SQUARE;
Unit square = level[(LEVEL_Y_RES - y -1) * LEVEL_X_RES + x]; RCL_Unit square = level[(LEVEL_Y_RES - y -1) * LEVEL_X_RES + x];
return square == 0 || square == 6 ? 0 : UNITS_PER_SQUARE; return square == 0 || square == 6 ? 0 : RCL_UNITS_PER_SQUARE;
} }
Unit textureAt(int16_t x, int16_t y) RCL_Unit textureAt(int16_t x, int16_t y)
{ {
Unit t = 0; RCL_Unit t = 0;
if (x >= 0 && x < LEVEL_X_RES && y >= 0 && y < LEVEL_Y_RES) if (x >= 0 && x < LEVEL_X_RES && y >= 0 && y < LEVEL_Y_RES)
t = max(level[(LEVEL_Y_RES - y -1) * LEVEL_X_RES + x] - 1,0); t = max(level[(LEVEL_Y_RES - y -1) * LEVEL_X_RES + x] - 1,0);
@ -910,19 +910,19 @@ Unit textureAt(int16_t x, int16_t y)
return t; return t;
} }
Unit rollAt(int16_t x, int16_t y) RCL_Unit rollAt(int16_t x, int16_t y)
{ {
if (x >= 0 && x < LEVEL_X_RES && y >= 0 && y < LEVEL_Y_RES && if (x >= 0 && x < LEVEL_X_RES && y >= 0 && y < LEVEL_Y_RES &&
level[(LEVEL_Y_RES - y -1) * LEVEL_X_RES + x] == 6) level[(LEVEL_Y_RES - y -1) * LEVEL_X_RES + x] == 6)
return sinInt(pokitto.frameCount * 10) + DOOR_ROLL_SIGN * UNITS_PER_SQUARE; return RCL_sinInt(pokitto.frameCount * 10) + DOOR_ROLL_SIGN * RCL_UNITS_PER_SQUARE;
return 0; return 0;
} }
uint8_t cFloor, cCeiling; uint8_t cFloor, cCeiling;
Vector2D shotPosition; RCL_Vector2D shotPosition;
Vector2D shotDirection; RCL_Vector2D shotDirection;
bool shotFired = false; bool shotFired = false;
uint8_t previousColumn = 255; ///< Helper for pixelIntensity. uint8_t previousColumn = 255; ///< Helper for pixelIntensity.
@ -933,7 +933,7 @@ int16_t mirror = 0;
/** /**
Function for drawing a single pixel (like fragment shader). Function for drawing a single pixel (like fragment shader).
*/ */
inline void pixelFunc(PixelInfo *pixel) inline void pixelFunc(RCL_PixelInfo *pixel)
{ {
if (pixel->position.y == MIDDLE_ROW) if (pixel->position.y == MIDDLE_ROW)
zBuffer[pixel->position.x] = pixel->depth; zBuffer[pixel->position.x] = pixel->depth;
@ -951,9 +951,9 @@ inline void pixelFunc(PixelInfo *pixel)
#ifndef NO_MIRROR #ifndef NO_MIRROR
int16_t intensity = pixel->isFloor ? int16_t intensity = pixel->isFloor ?
-1 * (pixel->depth - mirror * 64) / UNITS_PER_SQUARE : 0; -1 * (pixel->depth - mirror * 64) / RCL_UNITS_PER_SQUARE : 0;
#else #else
int16_t intensity = -1 * pixel->depth / (UNITS_PER_SQUARE * 2); int16_t intensity = -1 * pixel->depth / (RCL_UNITS_PER_SQUARE * 2);
#endif #endif
c = addIntensity(c,intensity); c = addIntensity(c,intensity);
@ -962,7 +962,7 @@ inline void pixelFunc(PixelInfo *pixel)
} }
else else
{ {
Unit textureScroll = pixel->hit.type != 4 ? 0 : 16 * pokitto.frameCount; RCL_Unit textureScroll = pixel->hit.type != 4 ? 0 : 16 * pokitto.frameCount;
#ifdef NO_TEXTURES #ifdef NO_TEXTURES
c = textureAverageColors[pixel->hit.type]; c = textureAverageColors[pixel->hit.type];
@ -980,7 +980,7 @@ inline void pixelFunc(PixelInfo *pixel)
else else
{ {
// optimization: precompute intensity for the whole column // optimization: precompute intensity for the whole column
pixelIntensity = 1 - pixel->depth / (UNITS_PER_SQUARE * 2) + (pixel->hit.direction % 2 == 0 ? 2 : 0); pixelIntensity = 1 - pixel->depth / (RCL_UNITS_PER_SQUARE * 2) + (pixel->hit.direction % 2 == 0 ? 2 : 0);
previousColumn = pixel->position.x; previousColumn = pixel->position.x;
c = addIntensity(c,pixelIntensity); c = addIntensity(c,pixelIntensity);
} }
@ -993,7 +993,7 @@ inline void pixelFunc(PixelInfo *pixel)
void draw() void draw()
{ {
RayConstraints c; RCL_RayConstraints c;
c.maxHits = 1; c.maxHits = 1;
c.maxSteps = 20; c.maxSteps = 20;
@ -1001,20 +1001,20 @@ void draw()
player.mCamera.height += player.mHeadBob; player.mCamera.height += player.mHeadBob;
#ifdef RENDER_PRECISE #ifdef RENDER_PRECISE
render(player.mCamera,floorHeightAt,0,textureAt,c); RCL_render(player.mCamera,floorHeightAt,0,textureAt,c);
#else #else
renderSimple(player.mCamera,floorHeightAt,textureAt,rollAt,c); RCL_renderSimple(player.mCamera,floorHeightAt,textureAt,rollAt,c);
#endif #endif
player.mCamera.height -= player.mHeadBob; player.mCamera.height -= player.mHeadBob;
if (shotFired) if (shotFired)
{ {
PixelInfo pos = mapToScreen(shotPosition,UNITS_PER_SQUARE,player.mCamera); RCL_PixelInfo pos = RCL_mapToScreen(shotPosition,RCL_UNITS_PER_SQUARE,player.mCamera);
drawSpriteSquare(spritePlasma,pos.position.x * SUBSAMPLE, drawSpriteSquare(spritePlasma,pos.position.x * SUBSAMPLE,
pos.position.y,pos.depth, pos.position.y,pos.depth,
perspectiveScale(64,pos.depth)); RCL_perspectiveScale(64,pos.depth));
} }
drawImage(imageBar,0,INFO_BAR_START - 3); drawImage(imageBar,0,INFO_BAR_START - 3);
@ -1031,7 +1031,7 @@ int main()
cCeiling = rgbToIndex(3,2,0); cCeiling = rgbToIndex(3,2,0);
player.setPositionSquare(6,5); player.setPositionSquare(6,5);
player.mCamera.height = CAMERA_COLL_HEIGHT_BELOW; player.mCamera.height = RCL_CAMERA_COLL_HEIGHT_BELOW;
player.mCamera.resolution.y = INFO_BAR_START + 1; player.mCamera.resolution.y = INFO_BAR_START + 1;
@ -1058,22 +1058,22 @@ int main()
{ {
// update the shot // update the shot
Unit shotStep = (dt * SHOT_SPEED) / 1000; RCL_Unit shotStep = (dt * SHOT_SPEED) / 1000;
shotPosition.x += (shotStep * shotDirection.x) / UNITS_PER_SQUARE; shotPosition.x += (shotStep * shotDirection.x) / RCL_UNITS_PER_SQUARE;
shotPosition.y += (shotStep * shotDirection.y) / UNITS_PER_SQUARE; shotPosition.y += (shotStep * shotDirection.y) / RCL_UNITS_PER_SQUARE;
if ( if (
absVal(shotPosition.x - player.mCamera.position.x) > UNITS_PER_SQUARE * 5 || RCL_absVal(shotPosition.x - player.mCamera.position.x) > RCL_UNITS_PER_SQUARE * 5 ||
absVal(shotPosition.y - player.mCamera.position.y) > UNITS_PER_SQUARE * 5 || RCL_absVal(shotPosition.y - player.mCamera.position.y) > RCL_UNITS_PER_SQUARE * 5 ||
(textureAt(shotPosition.x / UNITS_PER_SQUARE,shotPosition.y / UNITS_PER_SQUARE) != 0) (textureAt(shotPosition.x / RCL_UNITS_PER_SQUARE,shotPosition.y / RCL_UNITS_PER_SQUARE) != 0)
) )
shotFired = false; shotFired = false;
} }
else if (pokitto.bBtn()) else if (pokitto.bBtn())
{ {
shotPosition = player.mCamera.position; shotPosition = player.mCamera.position;
shotDirection = angleToDirection(player.mCamera.direction); shotDirection = RCL_angleToDirection(player.mCamera.direction);
shotFired = true; shotFired = true;
} }

View file

@ -11,15 +11,15 @@
*/ */
// redefine player's height // redefine player's height
#define PLAYER_SPEED (UNITS_PER_SQUARE * 6) #define PLAYER_SPEED (RCL_UNITS_PER_SQUARE * 6)
#define HORIZONTAL_FOV ((3 * UNITS_PER_SQUARE) / 10) #define RCL_HORIZONTAL_FOV ((3 * RCL_UNITS_PER_SQUARE) / 10)
#define GRAVITY_ACCELERATION (UNITS_PER_SQUARE * 2) #define GRAVITY_ACCELERATION (RCL_UNITS_PER_SQUARE * 2)
#define CAMERA_COLL_HEIGHT_BELOW ((3 * UNITS_PER_SQUARE) / 2) #define RCL_CAMERA_COLL_HEIGHT_BELOW ((3 * RCL_UNITS_PER_SQUARE) / 2)
#define FPS 40 #define FPS 40
#define HEAD_BOB_HEIGHT 150 #define HEAD_BOB_HEIGHT 150
#define HEAD_BOB_STEP 20 #define HEAD_BOB_STEP 20
#define COMPUTE_WALL_TEXCOORDS 0 // we won't be using textures, so turn them off #define RCL_COMPUTE_WALL_TEXCOORDS 0 // we won't be using textures, so turn them off
#include "general.hpp" #include "general.hpp"
@ -28,12 +28,12 @@
Player player; Player player;
#define SPRITE_MAX_DISTANCE 5 * UNITS_PER_SQUARE #define SPRITE_MAX_DISTANCE 5 * RCL_UNITS_PER_SQUARE
#define JUMP_SPEED 500 #define JUMP_SPEED 500
char floorColor = 0; char floorColor = 0;
Vector2D selectedSquare; ///< Coords of a square selected for editing. RCL_Vector2D selectedSquare; ///< Coords of a square selected for editing.
/** /**
Represents one terrain change against the implicit terrain. Represents one terrain change against the implicit terrain.
@ -41,8 +41,8 @@ Vector2D selectedSquare; ///< Coords of a square selected for editing.
class Change class Change
{ {
public: public:
Vector2D mCoords; RCL_Vector2D mCoords;
Unit mHeight; RCL_Unit mHeight;
int8_t mColor; int8_t mColor;
}; };
@ -423,7 +423,7 @@ const unsigned char imageBackground[] =
,0xc1,0x29,0x38,0x38,0x38,0x38,0x38,0x38,0x38,0x38 ,0xc1,0x29,0x38,0x38,0x38,0x38,0x38,0x38,0x38,0x38
}; };
Unit floorHeightAt(int16_t x, int16_t y) RCL_Unit floorHeightAt(int16_t x, int16_t y)
{ {
/* /*
This for loop may become a bottleneck, since this function is called This for loop may become a bottleneck, since this function is called
@ -434,19 +434,19 @@ Unit floorHeightAt(int16_t x, int16_t y)
if (changes[i].mCoords.x == x && changes[i].mCoords.y == y) if (changes[i].mCoords.x == x && changes[i].mCoords.y == y)
return changes[i].mHeight; return changes[i].mHeight;
return (heightProfile[absVal(x) % HEIGHT_PROFILE_LENGTH] + return (heightProfile[RCL_absVal(x) % HEIGHT_PROFILE_LENGTH] +
heightProfile[absVal(y + 20) % HEIGHT_PROFILE_LENGTH]) * heightProfile[RCL_absVal(y + 20) % HEIGHT_PROFILE_LENGTH]) *
UNITS_PER_SQUARE; RCL_UNITS_PER_SQUARE;
} }
Unit colorAt(int16_t x, int16_t y) RCL_Unit colorAt(int16_t x, int16_t y)
{ {
for (uint16_t i = 0; i < MAX_CHANGES; ++i) for (uint16_t i = 0; i < MAX_CHANGES; ++i)
if (changes[i].mCoords.x == x && changes[i].mCoords.y == y) if (changes[i].mCoords.x == x && changes[i].mCoords.y == y)
return changes[i].mColor; return changes[i].mColor;
return min((heightProfile[absVal(x * 2) % HEIGHT_PROFILE_LENGTH] + return min((heightProfile[RCL_absVal(x * 2) % HEIGHT_PROFILE_LENGTH] +
heightProfile[absVal(y) % HEIGHT_PROFILE_LENGTH]) / 10,3); heightProfile[RCL_absVal(y) % HEIGHT_PROFILE_LENGTH]) / 10,3);
} }
uint16_t previousColumn = 255; ///< Helper for precomputing background. uint16_t previousColumn = 255; ///< Helper for precomputing background.
@ -455,7 +455,7 @@ uint16_t backgroundColumn = 0; ///< Precomputed background column.
/** /**
Function for drawing a single pixel (like fragment shader). Function for drawing a single pixel (like fragment shader).
*/ */
inline void pixelFunc(PixelInfo *pixel) inline void pixelFunc(RCL_PixelInfo *pixel)
{ {
uint8_t c = 0; uint8_t c = 0;
int16_t intensity = 0; int16_t intensity = 0;
@ -465,7 +465,7 @@ inline void pixelFunc(PixelInfo *pixel)
c = pixel->hit.square.x != selectedSquare.x || pixel->hit.square.y != selectedSquare.y || (editing && pokitto.frameCount % 2) == 0 ? c = pixel->hit.square.x != selectedSquare.x || pixel->hit.square.y != selectedSquare.y || (editing && pokitto.frameCount % 2) == 0 ?
squareColors[pixel->hit.type] : 30; squareColors[pixel->hit.type] : 30;
intensity = pixel->depth / (UNITS_PER_SQUARE * 3); intensity = pixel->depth / (RCL_UNITS_PER_SQUARE * 3);
intensity += pixel->hit.direction % 2 == 0 ? 2 : 0; intensity += pixel->hit.direction % 2 == 0 ? 2 : 0;
} }
else if (pixel->isFloor) else if (pixel->isFloor)
@ -473,17 +473,17 @@ inline void pixelFunc(PixelInfo *pixel)
c = floorColor; c = floorColor;
if (!pixel->isHorizon) if (!pixel->isHorizon)
intensity = pixel->depth / (UNITS_PER_SQUARE * 3); intensity = pixel->depth / (RCL_UNITS_PER_SQUARE * 3);
} }
else else
{ {
if (previousColumn == pixel->position.x) if (previousColumn == pixel->position.x)
{ {
c = imageBackground[2 + backgroundColumn * 44 + clamp(pixel->position.y - player.mCamera.shear,0,43)]; c = imageBackground[2 + backgroundColumn * 44 + RCL_clamp(pixel->position.y - player.mCamera.shear,0,43)];
} }
else else
{ {
backgroundColumn = absVal(pixel->position.x + (110 * player.mCamera.direction) / UNITS_PER_SQUARE) % 110; backgroundColumn = RCL_absVal(pixel->position.x + (110 * player.mCamera.direction) / RCL_UNITS_PER_SQUARE) % 110;
previousColumn = pixel->position.x; previousColumn = pixel->position.x;
} }
} }
@ -498,13 +498,13 @@ bool flyBy = true;
void draw() void draw()
{ {
RayConstraints c; RCL_RayConstraints c;
c.maxHits = 6; c.maxHits = 6;
c.maxSteps = 20; c.maxSteps = 20;
player.mCamera.height += player.mHeadBob; player.mCamera.height += player.mHeadBob;
render(player.mCamera,floorHeightAt,0,colorAt,c); RCL_render(player.mCamera,floorHeightAt,0,colorAt,c);
player.mCamera.height -= player.mHeadBob; player.mCamera.height -= player.mHeadBob;
if (flyBy && (pokitto.frameCount >> 3) % 3 != 0) if (flyBy && (pokitto.frameCount >> 3) % 3 != 0)
@ -520,23 +520,23 @@ void draw()
void cameraFlyBy(uint32_t dt) void cameraFlyBy(uint32_t dt)
{ {
Unit height = floorHeightAt( RCL_Unit height = floorHeightAt(
divRoundDown(player.mCamera.position.x,UNITS_PER_SQUARE), RCL_divRoundDown(player.mCamera.position.x,RCL_UNITS_PER_SQUARE),
divRoundDown(player.mCamera.position.y,UNITS_PER_SQUARE)) + UNITS_PER_SQUARE * 3; RCL_divRoundDown(player.mCamera.position.y,RCL_UNITS_PER_SQUARE)) + RCL_UNITS_PER_SQUARE * 3;
Unit heightDiff = player.mCamera.height - height; RCL_Unit heightDiff = player.mCamera.height - height;
Unit step = (200 * dt) / 1000; RCL_Unit step = (200 * dt) / 1000;
if (heightDiff > UNITS_PER_SQUARE * 2) if (heightDiff > RCL_UNITS_PER_SQUARE * 2)
{ {
player.mCamera.height -= step * heightDiff / 200; player.mCamera.height -= step * heightDiff / 200;
player.mCamera.shear = max(player.mCamera.shear - 1,-80); player.mCamera.shear = max(player.mCamera.shear - 1,-80);
} }
else else
{ {
if (heightDiff < UNITS_PER_SQUARE) if (heightDiff < RCL_UNITS_PER_SQUARE)
player.mCamera.height += step * absVal(heightDiff / 70); player.mCamera.height += step * RCL_absVal(heightDiff / 70);
if (player.mCamera.shear < 0 && pokitto.frameCount % 2 == 0) if (player.mCamera.shear < 0 && pokitto.frameCount % 2 == 0)
player.mCamera.shear++; player.mCamera.shear++;
@ -544,7 +544,7 @@ void cameraFlyBy(uint32_t dt)
player.mCamera.position.x += step * 30; player.mCamera.position.x += step * 30;
player.mCamera.position.y += step * 15; player.mCamera.position.y += step * 15;
player.mCamera.direction = sinInt(pokitto.frameCount / 8); player.mCamera.direction = RCL_sinInt(pokitto.frameCount / 8);
} }
int main() int main()
@ -615,30 +615,30 @@ int main()
if (editing) if (editing)
{ {
Vector2D facingOffset; RCL_Vector2D facingOffset;
facingOffset.x = 0; facingOffset.x = 0;
facingOffset.y = 0; facingOffset.y = 0;
if (player.mCamera.direction > (4 * UNITS_PER_SQUARE / 12) && if (player.mCamera.direction > (4 * RCL_UNITS_PER_SQUARE / 12) &&
player.mCamera.direction <= (8 * UNITS_PER_SQUARE / 12)) player.mCamera.direction <= (8 * RCL_UNITS_PER_SQUARE / 12))
facingOffset.x = -1; facingOffset.x = -1;
else if (player.mCamera.direction < (2 * UNITS_PER_SQUARE / 12) || else if (player.mCamera.direction < (2 * RCL_UNITS_PER_SQUARE / 12) ||
player.mCamera.direction >= (10 * UNITS_PER_SQUARE / 12)) player.mCamera.direction >= (10 * RCL_UNITS_PER_SQUARE / 12))
facingOffset.x = 1; facingOffset.x = 1;
else else
facingOffset.x = 0; facingOffset.x = 0;
if (player.mCamera.direction > (UNITS_PER_SQUARE / 12) && if (player.mCamera.direction > (RCL_UNITS_PER_SQUARE / 12) &&
player.mCamera.direction <= (5 * UNITS_PER_SQUARE / 12)) player.mCamera.direction <= (5 * RCL_UNITS_PER_SQUARE / 12))
facingOffset.y = -1; facingOffset.y = -1;
else if (player.mCamera.direction > (6 * UNITS_PER_SQUARE / 12) && else if (player.mCamera.direction > (6 * RCL_UNITS_PER_SQUARE / 12) &&
player.mCamera.direction <= (11 * UNITS_PER_SQUARE / 12)) player.mCamera.direction <= (11 * RCL_UNITS_PER_SQUARE / 12))
facingOffset.y = 1; facingOffset.y = 1;
else else
facingOffset.y = 0; facingOffset.y = 0;
selectedSquare.x = divRoundDown(player.mCamera.position.x,UNITS_PER_SQUARE) + facingOffset.x; selectedSquare.x = RCL_divRoundDown(player.mCamera.position.x,RCL_UNITS_PER_SQUARE) + facingOffset.x;
selectedSquare.y = divRoundDown(player.mCamera.position.y,UNITS_PER_SQUARE) + facingOffset.y; selectedSquare.y = RCL_divRoundDown(player.mCamera.position.y,RCL_UNITS_PER_SQUARE) + facingOffset.y;
changeIndex = (changeIndex + 1) % MAX_CHANGES; changeIndex = (changeIndex + 1) % MAX_CHANGES;
@ -669,7 +669,7 @@ int main()
{ {
if (editCounter == 0) if (editCounter == 0)
{ {
changes[changeIndex].mHeight += UNITS_PER_SQUARE / 4; changes[changeIndex].mHeight += RCL_UNITS_PER_SQUARE / 4;
editCounter = 4; editCounter = 4;
} }
} }
@ -684,7 +684,7 @@ int main()
{ {
if (editCounter == 0) if (editCounter == 0)
{ {
changes[changeIndex].mHeight -= UNITS_PER_SQUARE / 4; changes[changeIndex].mHeight -= RCL_UNITS_PER_SQUARE / 4;
editCounter = 4; editCounter = 4;
} }
} }
@ -719,14 +719,14 @@ int main()
{ {
int16_t heightDiff = changes[changeIndex].mHeight - player.mCamera.height; int16_t heightDiff = changes[changeIndex].mHeight - player.mCamera.height;
if (heightDiff > UNITS_PER_SQUARE / 2) if (heightDiff > RCL_UNITS_PER_SQUARE / 2)
shearDirection = 1; shearDirection = 1;
else if (heightDiff < -1 * UNITS_PER_SQUARE / 2) else if (heightDiff < -1 * RCL_UNITS_PER_SQUARE / 2)
shearDirection = -1; shearDirection = -1;
if (editCounter == 0 && colorAddition != 0) if (editCounter == 0 && colorAddition != 0)
{ {
changes[changeIndex].mColor = wrap(changes[changeIndex].mColor + colorAddition,SQUARE_COLORS); changes[changeIndex].mColor = RCL_wrap(changes[changeIndex].mColor + colorAddition,SQUARE_COLORS);
editCounter = 4; editCounter = 4;
} }
} }

View file

@ -14,9 +14,12 @@
#include "stdio.h" // for debugging raycastlibg #include "stdio.h" // for debugging raycastlibg
#define VERTICAL_FOV UNITS_PER_SQUARE // redefine camera vertical FOV #define RCL_VERTICAL_FOV RCL_UNITS_PER_SQUARE /* redefine camera vertical FOV:
RCL_UNITS_PER_SQUARE would normally mean
#define PIXEL_FUNCTION pixelFunc 360 degrees, but it's not an actual
angle, just linear approximation, so
this is okay */
#define RCL_PIXEL_FUNCTION pixelFunc
/* ^ This has to be defined to the name of the function that will render /* ^ This has to be defined to the name of the function that will render
pixels. */ pixels. */
@ -30,11 +33,11 @@ Pokitto::Core pokitto;
#endif #endif
#ifndef PLAYER_SPEED #ifndef PLAYER_SPEED
#define PLAYER_SPEED (4 * UNITS_PER_SQUARE) #define PLAYER_SPEED (4 * RCL_UNITS_PER_SQUARE)
#endif #endif
#ifndef PLAYER_ROTATION_SPEED #ifndef PLAYER_ROTATION_SPEED
#define PLAYER_ROTATION_SPEED (UNITS_PER_SQUARE / 2) #define PLAYER_ROTATION_SPEED (RCL_UNITS_PER_SQUARE / 2)
#endif #endif
#ifndef PLAYER_JUMP_SPEED #ifndef PLAYER_JUMP_SPEED
@ -50,7 +53,7 @@ Pokitto::Core pokitto;
#endif #endif
#ifndef GRAVITY_ACCELERATION #ifndef GRAVITY_ACCELERATION
#define GRAVITY_ACCELERATION ((3 * UNITS_PER_SQUARE) / 2) #define GRAVITY_ACCELERATION ((3 * RCL_UNITS_PER_SQUARE) / 2)
#endif #endif
#define SCREEN_WIDTH 110 #define SCREEN_WIDTH 110
@ -67,7 +70,7 @@ Pokitto::Core pokitto;
#define TRANSPARENT_COLOR 0b00000111 /// Transparent color for sprites and GUI. #define TRANSPARENT_COLOR 0b00000111 /// Transparent color for sprites and GUI.
Unit zBuffer[SUBSAMPLED_WIDTH]; ///< 1D z-buffer for visibility determination. RCL_Unit zBuffer[SUBSAMPLED_WIDTH]; ///< 1D z-buffer for visibility determination.
unsigned short palette[256]; unsigned short palette[256];
@ -156,27 +159,27 @@ inline uint8_t addRGB(uint8_t color, int16_t red, int16_t green, int16_t blue)
int8_t g = (color & 0b00111000) >> 3; int8_t g = (color & 0b00111000) >> 3;
int8_t b = (color & 0b11000000) >> 6; int8_t b = (color & 0b11000000) >> 6;
r = clamp(r + red,0,7); r = RCL_clamp(r + red,0,7);
g = clamp(g + green,0,7); g = RCL_clamp(g + green,0,7);
b = clamp(b + blue,0,3); b = RCL_clamp(b + blue,0,3);
return rgbToIndex(r,g,b); return rgbToIndex(r,g,b);
} }
/** /**
Samples an image by normalized coordinates - each coordinate is in range Samples an image by normalized coordinates - each coordinate is in range
0 to UNITS_PER_SQUARE (from raycastlib). 0 to RCL_UNITS_PER_SQUARE (from raycastlib).
*/ */
inline uint8_t sampleImage(const unsigned char *image, Unit x, Unit y) inline uint8_t sampleImage(const unsigned char *image, RCL_Unit x, RCL_Unit y)
{ {
// TODO: optimize // TODO: optimize
x = wrap(x,UNITS_PER_SQUARE); x = RCL_wrap(x,RCL_UNITS_PER_SQUARE);
y = wrap(y,UNITS_PER_SQUARE); y = RCL_wrap(y,RCL_UNITS_PER_SQUARE);
int32_t index = int32_t index =
image[1] * ((image[0] * x) / UNITS_PER_SQUARE) + (image[0] * y) / image[1] * ((image[0] * x) / RCL_UNITS_PER_SQUARE) + (image[0] * y) /
UNITS_PER_SQUARE; RCL_UNITS_PER_SQUARE;
return image[2 + index]; return image[2 + index];
} }
@ -185,7 +188,7 @@ inline uint8_t sampleImage(const unsigned char *image, Unit x, Unit y)
Draws a scaled sprite on screen in an optimized way. The sprite has to be Draws a scaled sprite on screen in an optimized way. The sprite has to be
square in resolution. square in resolution.
*/ */
void inline drawSpriteSquare(const unsigned char *sprite, int16_t x, int16_t y, Unit depth, int16_t size) void inline drawSpriteSquare(const unsigned char *sprite, int16_t x, int16_t y, RCL_Unit depth, int16_t size)
{ {
if (size < 0 || size > 200 || // let's not mess up with the incoming array if (size < 0 || size > 200 || // let's not mess up with the incoming array
sprite[0] != sprite[1]) // only draw square sprites sprite[0] != sprite[1]) // only draw square sprites
@ -195,7 +198,7 @@ void inline drawSpriteSquare(const unsigned char *sprite, int16_t x, int16_t y,
// optimization: precompute the indices // optimization: precompute the indices
for (Unit i = 0; i < size; ++i) for (RCL_Unit i = 0; i < size; ++i)
samplingIndices[i] = (i * sprite[0]) / size; samplingIndices[i] = (i * sprite[0]) / size;
x -= size / 2; x -= size / 2;
@ -206,7 +209,7 @@ void inline drawSpriteSquare(const unsigned char *sprite, int16_t x, int16_t y,
int16_t jTo = size - max(0,y + size - 88); int16_t jTo = size - max(0,y + size - 88);
int16_t iTo = size - max(0,x + size - 110); int16_t iTo = size - max(0,x + size - 110);
for (Unit i = max(-1 * x,0); i < iTo; ++i) for (RCL_Unit i = max(-1 * x,0); i < iTo; ++i)
{ {
int16_t xPos = x + i; int16_t xPos = x + i;
@ -215,7 +218,7 @@ void inline drawSpriteSquare(const unsigned char *sprite, int16_t x, int16_t y,
int16_t columnLocation = 2 + samplingIndices[i] * sprite[0]; int16_t columnLocation = 2 + samplingIndices[i] * sprite[0];
for (Unit j = max(-1 * y,0); j < jTo; ++j) for (RCL_Unit j = max(-1 * y,0); j < jTo; ++j)
{ {
c = sprite[columnLocation + samplingIndices[j]]; c = sprite[columnLocation + samplingIndices[j]];
@ -248,20 +251,20 @@ void drawImage(const unsigned char *image, int16_t x, int16_t y)
class Player class Player
{ {
public: public:
Camera mCamera; RCL_Camera mCamera;
Unit mVericalSpeed; RCL_Unit mVericalSpeed;
bool mRunning; bool mRunning;
Unit mHeadBob; RCL_Unit mHeadBob;
bool mHeadBobUp; bool mHeadBobUp;
Player() Player()
{ {
initCamera(&mCamera); RCL_initCamera(&mCamera);
mCamera.position.x = 0; mCamera.position.x = 0;
mCamera.position.y = 0; mCamera.position.y = 0;
mCamera.direction = 0; mCamera.direction = 0;
mCamera.height = UNITS_PER_SQUARE * 3; mCamera.height = RCL_UNITS_PER_SQUARE * 3;
mCamera.resolution.x = SCREEN_WIDTH / SUBSAMPLE; mCamera.resolution.x = SCREEN_WIDTH / SUBSAMPLE;
mCamera.resolution.y = SCREEN_HEIGHT; mCamera.resolution.y = SCREEN_HEIGHT;
mCamera.shear = 0; mCamera.shear = 0;
@ -271,13 +274,13 @@ public:
mHeadBobUp = true; mHeadBobUp = true;
} }
void setPosition(Unit x, Unit y) void setPosition(RCL_Unit x, RCL_Unit y)
{ {
mCamera.position.x = x; mCamera.position.x = x;
mCamera.position.y = y; mCamera.position.y = y;
} }
void setPosition(Unit x, Unit y, Unit z, Unit direction) void setPosition(RCL_Unit x, RCL_Unit y, RCL_Unit z, RCL_Unit direction)
{ {
mCamera.position.x = x; mCamera.position.x = x;
mCamera.position.y = y; mCamera.position.y = y;
@ -288,15 +291,15 @@ public:
void setPositionSquare(int16_t squareX, int16_t squareY) void setPositionSquare(int16_t squareX, int16_t squareY)
{ {
setPosition( setPosition(
squareX * UNITS_PER_SQUARE + UNITS_PER_SQUARE / 2, squareX * RCL_UNITS_PER_SQUARE + RCL_UNITS_PER_SQUARE / 2,
squareY * UNITS_PER_SQUARE + UNITS_PER_SQUARE / 2); squareY * RCL_UNITS_PER_SQUARE + RCL_UNITS_PER_SQUARE / 2);
} }
void update(int16_t moveDirection, bool strafe, int16_t turnDirection, bool jump, void update(int16_t moveDirection, bool strafe, int16_t turnDirection, bool jump,
int16_t shearDirection, ArrayFunction floorHeightFunction, int16_t shearDirection, RCL_ArrayFunction floorHeightFunction,
ArrayFunction ceilingHeightFunction, bool computeHeight, uint32_t dt) RCL_ArrayFunction ceilingHeightFunction, bool computeHeight, uint32_t dt)
{ {
Vector2D moveOffset; RCL_Vector2D moveOffset;
moveOffset.x = 0; moveOffset.x = 0;
moveOffset.y = 0; moveOffset.y = 0;
@ -306,10 +309,10 @@ public:
int16_t horizontalStep = (dt * PLAYER_SPEED * (mRunning ? 2 : 1)) / 1000 * int16_t horizontalStep = (dt * PLAYER_SPEED * (mRunning ? 2 : 1)) / 1000 *
(moveDirection > 0 ? 1 : -1); (moveDirection > 0 ? 1 : -1);
moveOffset = angleToDirection(mCamera.direction + (strafe ? UNITS_PER_SQUARE / 4 : 0)); moveOffset = RCL_angleToDirection(mCamera.direction + (strafe ? RCL_UNITS_PER_SQUARE / 4 : 0));
moveOffset.x = (moveOffset.x * horizontalStep) / UNITS_PER_SQUARE; moveOffset.x = (moveOffset.x * horizontalStep) / RCL_UNITS_PER_SQUARE;
moveOffset.y = (moveOffset.y * horizontalStep) / UNITS_PER_SQUARE; moveOffset.y = (moveOffset.y * horizontalStep) / RCL_UNITS_PER_SQUARE;
mHeadBob += mHeadBobUp ? HEAD_BOB_STEP : -HEAD_BOB_STEP; mHeadBob += mHeadBobUp ? HEAD_BOB_STEP : -HEAD_BOB_STEP;
@ -324,31 +327,31 @@ public:
if (turnDirection != 0) if (turnDirection != 0)
{ {
int16_t rotationStep = (dt * PLAYER_ROTATION_SPEED) / 1000; int16_t rotationStep = (dt * PLAYER_ROTATION_SPEED) / 1000;
mCamera.direction = wrap(mCamera.direction + turnDirection * rotationStep,UNITS_PER_SQUARE); mCamera.direction = RCL_wrap(mCamera.direction + turnDirection * rotationStep,RCL_UNITS_PER_SQUARE);
} }
Unit prevHeight = mCamera.height; RCL_Unit prevHeight = mCamera.height;
moveCameraWithCollision(&mCamera,moveOffset,mVericalSpeed, RCL_moveCameraWithCollision(&mCamera,moveOffset,mVericalSpeed,
floorHeightFunction, ceilingHeightFunction, computeHeight ? 1 : 0, 0); floorHeightFunction, ceilingHeightFunction, computeHeight ? 1 : 0, 0);
Unit heightDiff = mCamera.height - prevHeight; RCL_Unit heightDiff = mCamera.height - prevHeight;
if (heightDiff == 0) if (heightDiff == 0)
mVericalSpeed = 0; // hit floor/ceiling mVericalSpeed = 0; // hit floor/ceiling
if (jump && mVericalSpeed == 0) if (jump && mVericalSpeed == 0)
{ {
int16_t camX = divRoundDown(mCamera.position.x,UNITS_PER_SQUARE); int16_t camX = RCL_divRoundDown(mCamera.position.x,RCL_UNITS_PER_SQUARE);
int16_t camY = divRoundDown(mCamera.position.y,UNITS_PER_SQUARE); int16_t camY = RCL_divRoundDown(mCamera.position.y,RCL_UNITS_PER_SQUARE);
if (mCamera.height - CAMERA_COLL_HEIGHT_BELOW - if (mCamera.height - RCL_CAMERA_COLL_HEIGHT_BELOW -
floorHeightFunction(camX,camY) < 2) floorHeightFunction(camX,camY) < 2)
mVericalSpeed = PLAYER_JUMP_SPEED; // jump mVericalSpeed = PLAYER_JUMP_SPEED; // jump
} }
if (shearDirection != 0) if (shearDirection != 0)
mCamera.shear = clamp(mCamera.shear + shearDirection * 10, mCamera.shear = RCL_clamp(mCamera.shear + shearDirection * 10,
-1 * mCamera.resolution.y, mCamera.resolution.y); -1 * mCamera.resolution.y, mCamera.resolution.y);
else else
mCamera.shear /= 2; mCamera.shear /= 2;
@ -362,18 +365,18 @@ class Sprite
{ {
public: public:
const unsigned char *mImage; const unsigned char *mImage;
Vector2D mPosition; RCL_Vector2D mPosition;
Unit mHeight; RCL_Unit mHeight;
Unit mPixelSize; RCL_Unit mPixelSize;
Sprite(const unsigned char *image, int16_t squareX, int16_t squareY, Unit z, Sprite(const unsigned char *image, int16_t squareX, int16_t squareY, RCL_Unit z,
Unit pixelSize): RCL_Unit pixelSize):
mImage(image), mImage(image),
mPixelSize(pixelSize) mPixelSize(pixelSize)
{ {
mPosition.x = squareX * UNITS_PER_SQUARE + UNITS_PER_SQUARE / 2; mPosition.x = squareX * RCL_UNITS_PER_SQUARE + RCL_UNITS_PER_SQUARE / 2;
mPosition.y = squareY * UNITS_PER_SQUARE + UNITS_PER_SQUARE / 2; mPosition.y = squareY * RCL_UNITS_PER_SQUARE + RCL_UNITS_PER_SQUARE / 2;
mHeight = z * UNITS_PER_SQUARE + UNITS_PER_SQUARE / 2; mHeight = z * RCL_UNITS_PER_SQUARE + RCL_UNITS_PER_SQUARE / 2;
} }
Sprite(): Sprite():

View file

@ -5,7 +5,7 @@
license: CC0 1.0 license: CC0 1.0
*/ */
#define PIXEL_FUNCTION pixelFunc #define RCL_PIXEL_FUNCTION pixelFunc
/* ^ Before including raycastlib, this has to be set to the name of the /* ^ Before including raycastlib, this has to be set to the name of the
function that will render pixels. It allows super performance. */ function that will render pixels. It allows super performance. */
@ -17,18 +17,19 @@
Pokitto::Core pokitto; Pokitto::Core pokitto;
Camera camera; // Defines a view that will be rendered. RCL_Camera camera; // Defines a view that will be rendered.
RCL_RayConstraints constraints;
// Function that for given square coordinates returns height of the floor. // Function that for given square coordinates returns height of the floor.
Unit floorHeightAt(int16_t x, int16_t y) RCL_Unit floorHeightAt(int16_t x, int16_t y)
{ {
return x < 0 || x >= 10 || y < 0 || y >= 10 ? return x < 0 || x >= 10 || y < 0 || y >= 10 ?
UNITS_PER_SQUARE * 2 : 0; RCL_UNITS_PER_SQUARE * 2 : 0;
// ^ UNITS_PER_SQUARE is the length of one side of the game world square. // ^ RCL_UNITS_PER_SQUARE is the length of one side of the game world square.
} }
// Function which the library will call to draw indivifual pixels. // Function which the library will call to draw indivifual pixels.
void pixelFunc(PixelInfo *pixel) void pixelFunc(RCL_PixelInfo *pixel)
{ {
uint8_t color; uint8_t color;
@ -45,14 +46,9 @@ void pixelFunc(PixelInfo *pixel)
void draw() void draw()
{ {
RayConstraints c;
c.maxHits = 1;
c.maxSteps = 20;
/* This triggers the rendering, which will keep calling pixelFunc to render /* This triggers the rendering, which will keep calling pixelFunc to render
the camera view. */ the camera view. */
renderSimple(camera,floorHeightAt,0,0,c); RCL_renderSimple(camera,floorHeightAt,0,0,constraints);
} }
int main() int main()
@ -60,18 +56,22 @@ int main()
pokitto.begin(); pokitto.begin();
pokitto.setFrameRate(60); pokitto.setFrameRate(60);
initCamera(&camera); RCL_initCamera(&camera);
// Set the camera position to square [4;6]. // Set the camera position to square [4;6].
camera.position.x = 4 * UNITS_PER_SQUARE; camera.position.x = 4 * RCL_UNITS_PER_SQUARE;
camera.position.y = 6 * UNITS_PER_SQUARE; camera.position.y = 6 * RCL_UNITS_PER_SQUARE;
camera.height = UNITS_PER_SQUARE; camera.height = RCL_UNITS_PER_SQUARE;
// Set the camera resolution to Pokitto display resolution. // Set the camera resolution to Pokitto display resolution.
camera.resolution.x = 110; camera.resolution.x = 110;
camera.resolution.y = 88; camera.resolution.y = 88;
// This specifies the ray behavior.
constraints.maxHits = 1;
constraints.maxSteps = 20;
while (pokitto.isRunning()) while (pokitto.isRunning())
{ {
if (pokitto.update()) if (pokitto.update())