Add resolution subdivider

This commit is contained in:
Miloslav Číž 2019-10-04 16:32:24 +02:00
parent d3d2e1bdc5
commit 14a49b6373
4 changed files with 83 additions and 27 deletions

54
main.c
View File

@ -89,6 +89,12 @@ void SFG_init();
#include "assets.h"
#include "palette.h"
#define SFG_GAME_RESOLUTION_X \
(SFG_SCREEN_RESOLUTION_X / SFG_RESOLUTION_SCALEDOWN)
#define SFG_GAME_RESOLUTION_Y \
(SFG_SCREEN_RESOLUTION_Y / SFG_RESOLUTION_SCALEDOWN)
#define SFG_MS_PER_FRAME (1000 / SFG_FPS) // ms per frame with target FPS
#define SFG_PLAYER_TURN_UNITS_PER_FRAME\
@ -117,7 +123,7 @@ void SFG_init();
#define SFG_CEILING_MAX_HEIGHT\
(16 * RCL_UNITS_PER_SQUARE - RCL_UNITS_PER_SQUARE / 2 )
int8_t SFG_backgroundScaleMap[SFG_RESOLUTION_Y];
int8_t SFG_backgroundScaleMap[SFG_GAME_RESOLUTION_Y];
uint16_t SFG_backgroundScroll;
struct
@ -130,6 +136,25 @@ struct
air. */
} SFG_player;
#if SFG_RESOLUTION_SCALEDOWN == 1
#define SFG_setGamePixel SFG_setPixel
#else
/**
Sets the game pixel (a pixel that can potentially be bigger than the screen
pixel).
*/
static inline void SFG_setGamePixel(uint16_t x, uint16_t y, uint8_t colorIndex)
{
uint16_t screenY = y * SFG_RESOLUTION_SCALEDOWN;
uint16_t screenX = x * SFG_RESOLUTION_SCALEDOWN;
for (uint16_t j = screenY; j < screenY + SFG_RESOLUTION_SCALEDOWN; ++j)
for (uint16_t i = screenX; i < screenX + SFG_RESOLUTION_SCALEDOWN; ++i)
SFG_setPixel(i,j,colorIndex);
}
#endif
void SFG_recompurePLayerDirection()
{
SFG_player.camera.direction = RCL_wrap(SFG_player.camera.direction,RCL_UNITS_PER_SQUARE);
@ -140,15 +165,15 @@ void SFG_recompurePLayerDirection()
SFG_player.direction.y = (SFG_player.direction.y * SFG_PLAYER_MOVE_UNITS_PER_FRAME) / RCL_UNITS_PER_SQUARE;
SFG_backgroundScroll =
((SFG_player.camera.direction * 8) * SFG_RESOLUTION_Y) / RCL_UNITS_PER_SQUARE;
((SFG_player.camera.direction * 8) * SFG_GAME_RESOLUTION_Y) / RCL_UNITS_PER_SQUARE;
}
void SFG_initPlayer()
{
RCL_initCamera(&SFG_player.camera);
SFG_player.camera.resolution.x = SFG_RESOLUTION_X / SFG_RAYCASTING_SUBSAMPLE;
SFG_player.camera.resolution.y = SFG_RESOLUTION_Y;
SFG_player.camera.resolution.x = SFG_GAME_RESOLUTION_X / SFG_RAYCASTING_SUBSAMPLE;
SFG_player.camera.resolution.y = SFG_GAME_RESOLUTION_Y;
SFG_player.camera.height = RCL_UNITS_PER_SQUARE * 12;
SFG_player.camera.position.x = RCL_UNITS_PER_SQUARE * 15;
SFG_player.camera.position.y = RCL_UNITS_PER_SQUARE * 8;
@ -296,7 +321,7 @@ void SFG_pixelFunc(RCL_PixelInfo *pixel)
else
{
color = SFG_getTexel(SFG_backgrounds[0],
SFG_backgroundScaleMap[(pixel->position.x * SFG_RAYCASTING_SUBSAMPLE + SFG_backgroundScroll) % SFG_RESOLUTION_Y],
SFG_backgroundScaleMap[(pixel->position.x * SFG_RAYCASTING_SUBSAMPLE + SFG_backgroundScroll) % SFG_GAME_RESOLUTION_Y],
// ^ TODO: get rid of mod?
SFG_backgroundScaleMap[pixel->position.y]);
}
@ -305,12 +330,12 @@ void SFG_pixelFunc(RCL_PixelInfo *pixel)
for (uint8_t i = 0; i < SFG_RAYCASTING_SUBSAMPLE; ++i)
{
SFG_setPixel(screenX,pixel->position.y,color);
SFG_setGamePixel(screenX,pixel->position.y,color);
screenX++;
}
}
#define SFG_MAX_SPRITE_SIZE SFG_RESOLUTION_X
#define SFG_MAX_SPRITE_SIZE SFG_GAME_RESOLUTION_X
uint8_t SFG_spriteSamplingPoints[SFG_MAX_SPRITE_SIZE];
@ -343,8 +368,8 @@ void SFG_drawScaledImage(
int16_t x1 = topLeftX + size - 1;
if (x1 >= SFG_RESOLUTION_X)
x1 = SFG_RESOLUTION_X - 1;
if (x1 >= SFG_GAME_RESOLUTION_X)
x1 = SFG_GAME_RESOLUTION_X - 1;
int16_t y0, v0;
@ -361,8 +386,8 @@ void SFG_drawScaledImage(
int16_t y1 = topLeftY + size - 1;
if (y1 >= SFG_RESOLUTION_Y)
y1 = SFG_RESOLUTION_Y - 1;
if (y1 >= SFG_GAME_RESOLUTION_Y)
y1 = SFG_GAME_RESOLUTION_Y - 1;
if ((x0 > x1) || (y0 > y1)) // completely outside screen?
return;
@ -395,7 +420,7 @@ void SFG_drawScaledImage(
for (int16_t x = x0, u = u0; x <= x1; ++x, ++u)
for (int16_t y = y0, v = v0; y <= y1; ++y, ++v)
SFG_setPixel(x,y,SFG_getTexel(image,
SFG_setGamePixel(x,y,SFG_getTexel(image,
SFG_spriteSamplingPoints[u],
SFG_spriteSamplingPoints[v]));
}
@ -497,8 +522,9 @@ void SFG_init()
SFG_rayConstraints.maxHits = SFG_RAYCASTING_MAX_HITS;
SFG_rayConstraints.maxSteps = SFG_RAYCASTING_MAX_STEPS;
for (uint16_t i = 0; i < SFG_RESOLUTION_Y; ++i)
SFG_backgroundScaleMap[i] = (i * SFG_TEXTURE_SIZE) / SFG_RESOLUTION_Y;
for (uint16_t i = 0; i < SFG_GAME_RESOLUTION_Y; ++i)
SFG_backgroundScaleMap[i] =
(i * SFG_TEXTURE_SIZE) / SFG_GAME_RESOLUTION_Y;
SFG_backgroundScroll = 0;

View File

@ -19,11 +19,14 @@
#undef SFG_FPS
#define SFG_FPS 50
#undef SFG_RESOLUTION_X
#define SFG_RESOLUTION_X 110
#undef SFG_SCREEN_RESOLUTION_X
#define SFG_SCREEN_RESOLUTION_X 110
#undef SFG_RESOLUTION_Y
#define SFG_RESOLUTION_Y 88
#undef SFG_SCREEN_RESOLUTION_Y
#define SFG_SCREEN_RESOLUTION_Y 88
#undef SFG_RESOLUTION_SCALEDOWN
#define SFG_RESOLUTION_SCALEDOWN 1
#undef SFG_DITHERED_SHADOW
#define SFG_DITHERED_SHADOW 0
@ -43,7 +46,7 @@ uint8_t *pokittoScreen;
void SFG_setPixel(uint16_t x, uint16_t y, uint8_t colorIndex)
{
pokittoScreen[y * SFG_RESOLUTION_X + x] = colorIndex;
pokittoScreen[y * SFG_SCREEN_RESOLUTION_X + x] = colorIndex;
}
uint32_t SFG_getTimeMs()

View File

@ -28,11 +28,11 @@
const uint8_t *sdlKeyboardState;
uint16_t screen[SFG_RESOLUTION_X * SFG_RESOLUTION_Y]; // RGB565 format
uint16_t screen[SFG_SCREEN_RESOLUTION_X * SFG_SCREEN_RESOLUTION_Y]; // RGB565 format
void SFG_setPixel(uint16_t x, uint16_t y, uint8_t colorIndex)
{
screen[y * SFG_RESOLUTION_X + x] = paletteRGB565[colorIndex];
screen[y * SFG_SCREEN_RESOLUTION_X + x] = paletteRGB565[colorIndex];
}
uint32_t SFG_getTimeMs()
@ -128,7 +128,10 @@ int main(int argc, char *argv[])
printf("possible arguments:\n\n");
printf("-h print this help and end\n");
printf("-w force run in window\n");
printf("-f force run fullscreen\n");
printf("-f force run fullscreen\n\n");
printf("controls:\n");
printf("TODO\n");
return 0;
}
@ -138,14 +141,14 @@ int main(int argc, char *argv[])
SDL_Window *window =
SDL_CreateWindow("raycasting", SDL_WINDOWPOS_UNDEFINED,
SDL_WINDOWPOS_UNDEFINED, SFG_RESOLUTION_X, SFG_RESOLUTION_Y,
SDL_WINDOWPOS_UNDEFINED, SFG_SCREEN_RESOLUTION_X, SFG_SCREEN_RESOLUTION_Y,
SDL_WINDOW_SHOWN);
SDL_Renderer *renderer = SDL_CreateRenderer(window,-1,0);
SDL_Texture *texture =
SDL_CreateTexture(renderer,SDL_PIXELFORMAT_RGB565,SDL_TEXTUREACCESS_STATIC,
SFG_RESOLUTION_X,SFG_RESOLUTION_Y);
SFG_SCREEN_RESOLUTION_X,SFG_SCREEN_RESOLUTION_Y);
SDL_Surface *screenSurface = SDL_GetWindowSurface(window);
@ -174,7 +177,7 @@ int main(int argc, char *argv[])
SFG_mainLoopBody();
SDL_UpdateTexture(texture,NULL,screen,SFG_RESOLUTION_X * sizeof(uint16_t));
SDL_UpdateTexture(texture,NULL,screen,SFG_SCREEN_RESOLUTION_X * sizeof(uint16_t));
SDL_RenderClear(renderer);
SDL_RenderCopy(renderer,texture,NULL,NULL);

View File

@ -17,9 +17,33 @@
#ifndef _SFG_SETTINGS_H
#define _SFG_SETTINGS_H
/**
Target FPS (frames per second). This sets the game logic FPS and will try to
render at the same rate. If such fast rendering can't be achieved, frames will
be droped, but the game logic will still be forced to run at this speed, so
the game may actually become slowed down if FPS is set too high.
*/
#define SFG_FPS 60
#define SFG_RESOLUTION_X 1024
#define SFG_RESOLUTION_Y 768
/**
Width of the screen in pixels. Set this to ACTUAL resolution. If you want the
game to run at smaller resolution (with bigger pixels), do his using
SFG_RESOLUTION_SCALEDOWN;
*/
#define SFG_SCREEN_RESOLUTION_X 1024
/**
Height of the screen in pixels. Set this to ACTUAL resolution. If you want the
game to run at smaller resolution (with bigger pixels), do his using
SFG_RESOLUTION_SCALEDOWN;
*/
#define SFG_SCREEN_RESOLUTION_Y 768
/**
How many times the screen resolution will be divided (how many times a game
pixel will be bigger than the screen pixel).
*/
#define SFG_RESOLUTION_SCALEDOWN 4
/**
Turn on for previes mode for map editing (flying, noclip, fast movement etc.).