Start explosions

This commit is contained in:
Miloslav Číž 2019-10-21 19:58:11 +02:00
parent 371093b95d
commit 7666fc9be0
5 changed files with 132 additions and 36 deletions

View File

@ -498,7 +498,28 @@ SFG_PROGRAM_MEMORY uint8_t SFG_monsterSprites[][SFG_TEXTURE_STORE_SIZE] =
SFG_PROGRAM_MEMORY uint8_t SFG_effects[][SFG_TEXTURE_STORE_SIZE] = SFG_PROGRAM_MEMORY uint8_t SFG_effects[][SFG_TEXTURE_STORE_SIZE] =
{ {
{ // 0, fireball { // 0, explostion
175,103,95,183,191,7,111,255,31,254,173,87,15,102,23,190,0,0,0,0,0,0,0,0,16,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,1,16,0,0,16,0,0,0,0,0,0,0,0,0,16,0,1,17,0,1,16,0,0,1,16,
0,17,0,0,0,17,0,17,17,16,17,0,0,1,17,0,0,17,17,16,0,1,18,34,50,17,17,0,1,17,17,
0,0,1,23,17,17,187,34,35,241,33,16,1,17,33,16,0,0,1,23,113,18,43,33,19,65,17,16,
17,18,49,16,0,0,1,17,115,146,34,17,115,65,17,17,17,51,17,0,0,0,0,17,19,57,42,17,
35,102,17,19,114,52,16,0,0,0,0,17,34,58,161,23,42,194,35,34,34,68,16,0,0,1,16,1,
34,35,33,18,157,194,50,35,51,65,17,17,0,0,17,18,34,18,19,217,38,85,109,212,68,
34,17,0,0,0,0,18,33,17,51,54,120,85,102,51,68,18,32,0,0,0,1,34,23,34,51,68,133,
85,86,51,65,50,35,16,0,1,17,18,33,68,54,72,85,85,86,99,67,18,33,17,16,17,17,19,
54,104,181,85,85,85,85,91,134,67,51,19,51,0,17,18,33,20,54,104,85,85,88,225,102,
99,35,51,48,0,0,17,33,19,36,69,85,85,88,22,98,41,35,48,0,0,0,0,19,51,52,88,83,
70,88,102,119,50,32,0,0,0,0,17,17,51,51,69,35,68,136,102,114,34,17,0,0,0,1,16,1,
18,52,66,116,68,104,129,18,34,17,16,0,0,0,0,17,114,51,55,68,68,54,102,114,35,16,
17,0,0,0,1,17,115,19,51,52,65,19,145,18,147,48,0,0,0,0,1,17,33,44,50,51,67,34,
169,51,35,49,0,0,0,0,17,18,34,49,50,35,202,34,42,35,114,51,0,0,0,1,17,50,49,17,
17,51,146,34,34,17,23,35,16,0,0,1,19,49,17,17,17,57,34,33,177,17,19,35,16,0,0,
17,17,17,16,1,1,19,17,1,16,1,19,50,48,0,0,17,17,0,0,17,1,19,17,0,16,0,17,17,49,
0,0,0,0,0,0,16,0,17,16,0,17,0,0,17,17,0,0,0,0,0,0,0,0,17,16,0,1,0,0,0,0,0,0,0,0,
0,0,0,0,1,0,0,0,0,0,0,0,0
},
{ // 1, fireball
175,103,183,7,191,111,254,31,95,180,173,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 175,103,183,7,191,111,254,31,95,180,173,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,17,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,17,17,0,0,0,0,0, 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,17,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,17,17,0,0,0,0,0,

BIN
assets/effect_explosion.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 981 B

120
main.c
View File

@ -303,7 +303,9 @@ typedef struct
typedef struct typedef struct
{ {
uint8_t type; uint8_t type;
uint8_t framesToLive; uint8_t doubleFramesToLive; /**< This number times two (because 256 could be
too little at high FPS) says after how many
frames the projectile is destroyed. */
uint16_t position[3]; /**< Current position, stored as u16 to save space, as uint16_t position[3]; /**< Current position, stored as u16 to save space, as
that is exactly enough to store position on 64x64 that is exactly enough to store position on 64x64
map. */ map. */
@ -312,6 +314,16 @@ typedef struct
#define SFG_MAX_PROJECTILES 12 #define SFG_MAX_PROJECTILES 12
#define SFG_PROJECTILE_EXPLOSION 0
#define SFG_PROJECTILE_FIREBALL 1
#define SFG_EXPLOSION_DURATION_DOUBLE_FRAMES \
(SFG_EXPLOSION_DURATION / SFG_MS_PER_FRAME)
#if SFG_EXPLOSION_DURATION_DOUBLE_FRAMES == 0
#define SFG_EXPLOSION_DURATION_FRAMES 1
#endif
/* /*
GLOBAL VARIABLES GLOBAL VARIABLES
=============================================================================== ===============================================================================
@ -1136,6 +1148,27 @@ uint8_t SFG_createProjectile(SFG_ProjectileRecord projectile)
return 1; return 1;
} }
void SFG_createExplosion(RCL_Unit x, RCL_Unit y, RCL_Unit z)
{
SFG_LOG("creating explostion");
SFG_ProjectileRecord explostion;
explostion.type = SFG_PROJECTILE_EXPLOSION;
explostion.position[0] = x;
explostion.position[1] = y;
explostion.position[2] = z;
explostion.direction[0] = 0;
explostion.direction[1] = 0;
explostion.direction[2] = 0;
explostion.doubleFramesToLive = SFG_EXPLOSION_DURATION_DOUBLE_FRAMES;
SFG_createProjectile(explostion);
}
/** /**
Performs one game step (logic, physics), happening SFG_MS_PER_FRAME after Performs one game step (logic, physics), happening SFG_MS_PER_FRAME after
previous frame. previous frame.
@ -1166,12 +1199,11 @@ void SFG_gameStep()
SFG_ProjectileRecord p; SFG_ProjectileRecord p;
p.type = 0; p.type = SFG_PROJECTILE_FIREBALL;
p.framesToLive = 255; p.doubleFramesToLive = 255;
p.position[0] = SFG_player.camera.position.x; p.position[0] = SFG_player.camera.position.x;
p.position[1] = SFG_player.camera.position.y; p.position[1] = SFG_player.camera.position.y;
p.position[2] = SFG_player.camera.height; p.position[2] = SFG_player.camera.height - 256;
RCL_Vector2D dir = RCL_angleToDirection(SFG_player.camera.direction); RCL_Vector2D dir = RCL_angleToDirection(SFG_player.camera.direction);
@ -1179,7 +1211,8 @@ p.direction[0] = (dir.x * SFG_ROCKER_MOVE_UNITS_PER_FRAME) / RCL_UNITS_PER_SQUAR
p.direction[1] = (dir.y * SFG_ROCKER_MOVE_UNITS_PER_FRAME) / RCL_UNITS_PER_SQUARE; p.direction[1] = (dir.y * SFG_ROCKER_MOVE_UNITS_PER_FRAME) / RCL_UNITS_PER_SQUARE;
p.direction[2] = 0; p.direction[2] = 0;
printf("%d\n",SFG_createProjectile(p)); SFG_createProjectile(p);
} }
if (SFG_keyIsDown(SFG_KEY_A)) if (SFG_keyIsDown(SFG_KEY_A))
@ -1367,6 +1400,10 @@ printf("%d\n",SFG_createProjectile(p));
// update projectiles: // update projectiles:
uint8_t substractFrames =
(SFG_gameFrame - SFG_currentLevel.frameStart) & 0x01 ? 1 : 0;
// ^ only substract frames to live every other frame
for (int8_t i = 0; i < SFG_currentLevel.projectileRecordCount; ++i) for (int8_t i = 0; i < SFG_currentLevel.projectileRecordCount; ++i)
{ {
SFG_ProjectileRecord *p = &(SFG_currentLevel.projectileRecords[i]); SFG_ProjectileRecord *p = &(SFG_currentLevel.projectileRecords[i]);
@ -1389,6 +1426,17 @@ printf("%d\n",SFG_createProjectile(p));
} }
} }
if (p->doubleFramesToLive == 0)
{
collides = 1;
}
else if (SFG_floorHeightAt(
pos[0] / RCL_UNITS_PER_SQUARE,pos[1] / RCL_UNITS_PER_SQUARE)
>= pos[2])
{
collides = 1;
}
if (collides) if (collides)
{ {
SFG_LOG("projectile collides"); SFG_LOG("projectile collides");
@ -1402,6 +1450,9 @@ printf("%d\n",SFG_createProjectile(p));
SFG_currentLevel.projectileRecordCount--; SFG_currentLevel.projectileRecordCount--;
i--; i--;
if (p->type == SFG_PROJECTILE_FIREBALL)
SFG_createExplosion(p->position[0],p->position[1],p->position[2]);
} }
else else
{ {
@ -1409,6 +1460,8 @@ printf("%d\n",SFG_createProjectile(p));
p->position[1] = pos[1]; p->position[1] = pos[1];
p->position[2] = pos[2]; p->position[2] = pos[2];
} }
p->doubleFramesToLive -= substractFrames;
} }
// handle door: // handle door:
@ -1731,28 +1784,6 @@ void SFG_draw()
// draw sprites: // draw sprites:
// projecile sprites:
for (uint8_t i = 0; i < SFG_currentLevel.projectileRecordCount; ++i)
{
SFG_ProjectileRecord *proj = &(SFG_currentLevel.projectileRecords[i]);
RCL_Vector2D worldPosition;
worldPosition.x = proj->position[0];
worldPosition.y = proj->position[1];
RCL_PixelInfo p =
RCL_mapToScreen(worldPosition,proj->position[2],SFG_player.camera);
if (p.depth > 0)
SFG_drawScaledSprite(SFG_effects[0],
p.position.x * SFG_RAYCASTING_SUBSAMPLE,p.position.y,
RCL_perspectiveScale(SFG_GAME_RESOLUTION_Y,p.depth),
p.depth / (RCL_UNITS_PER_SQUARE * 2),p.depth);
}
// monster sprites: // monster sprites:
for (uint8_t i = 0; i < SFG_currentLevel.monsterRecordCount; ++i) for (uint8_t i = 0; i < SFG_currentLevel.monsterRecordCount; ++i)
{ {
@ -1809,6 +1840,39 @@ void SFG_draw()
p.depth / (RCL_UNITS_PER_SQUARE * 2),p.depth); p.depth / (RCL_UNITS_PER_SQUARE * 2),p.depth);
} }
// projecile sprites:
for (uint8_t i = 0; i < SFG_currentLevel.projectileRecordCount; ++i)
{
SFG_ProjectileRecord *proj = &(SFG_currentLevel.projectileRecords[i]);
RCL_Vector2D worldPosition;
worldPosition.x = proj->position[0];
worldPosition.y = proj->position[1];
RCL_PixelInfo p =
RCL_mapToScreen(worldPosition,proj->position[2],SFG_player.camera);
const uint8_t *s =
SFG_effects[proj->type == SFG_PROJECTILE_FIREBALL ? 1 : 0];
int16_t spriteSize = SFG_GAME_RESOLUTION_Y / 2;
if (proj->type == SFG_PROJECTILE_EXPLOSION)
{
spriteSize =
(SFG_GAME_RESOLUTION_Y * (SFG_EXPLOSION_DURATION_DOUBLE_FRAMES - proj->doubleFramesToLive) ) /
SFG_EXPLOSION_DURATION_DOUBLE_FRAMES;
}
if (p.depth > 0)
SFG_drawScaledSprite(s,
p.position.x * SFG_RAYCASTING_SUBSAMPLE,p.position.y,
RCL_perspectiveScale(spriteSize,p.depth),
p.depth / (RCL_UNITS_PER_SQUARE * 2),p.depth);
}
#if SFG_HEADBOB_ENABLED #if SFG_HEADBOB_ENABLED
// substract head bob after rendering // substract head bob after rendering
SFG_player.camera.height -= headBobOffset; SFG_player.camera.height -= headBobOffset;

View File

@ -26,7 +26,7 @@
author: Miloslav "drummyfish" Ciz author: Miloslav "drummyfish" Ciz
license: CC0 1.0 license: CC0 1.0
version: 0.90 version: 0.901
*/ */
#include <stdint.h> #include <stdint.h>
@ -855,8 +855,11 @@ void RCL_castRayMultiHit(RCL_Ray ray, RCL_ArrayFunction arrayFunc,
divided by leg B (length along the same axis). */ divided by leg B (length along the same axis). */
h.distance = h.distance =
((h.position.x - ray.start.x) * RCL_UNITS_PER_SQUARE * rayDirXRecip) (((h.position.x - ray.start.x) / 4) *
/ RECIP_SCALE; RCL_UNITS_PER_SQUARE * rayDirXRecip)
/ (RECIP_SCALE / 4);
// ^ / 4 is here to prevent overflow
#endif #endif
} }
else else
@ -877,8 +880,11 @@ void RCL_castRayMultiHit(RCL_Ray ray, RCL_ArrayFunction arrayFunc,
#if RCL_RECTILINEAR #if RCL_RECTILINEAR
h.distance = h.distance =
((h.position.y - ray.start.y) * RCL_UNITS_PER_SQUARE * rayDirYRecip) (((h.position.y - ray.start.y) / 4) *
/ RECIP_SCALE; RCL_UNITS_PER_SQUARE * rayDirYRecip)
/ (RECIP_SCALE / 4);
// ^ / 4 is here to prevent overflow
#endif #endif
} }

View File

@ -32,14 +32,14 @@
game to run at smaller resolution (with bigger pixels), do his using game to run at smaller resolution (with bigger pixels), do his using
SFG_RESOLUTION_SCALEDOWN; SFG_RESOLUTION_SCALEDOWN;
*/ */
#define SFG_SCREEN_RESOLUTION_X 800 #define SFG_SCREEN_RESOLUTION_X 1024
/** /**
Height of the screen in pixels. Set this to ACTUAL resolution. If you want the 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 game to run at smaller resolution (with bigger pixels), do his using
SFG_RESOLUTION_SCALEDOWN; SFG_RESOLUTION_SCALEDOWN;
*/ */
#define SFG_SCREEN_RESOLUTION_Y 600 #define SFG_SCREEN_RESOLUTION_Y 768
/** /**
How many times the screen resolution will be divided (how many times a game How many times the screen resolution will be divided (how many times a game
@ -125,4 +125,9 @@
*/ */
#define SFG_CAMERA_MAX_SHEAR 1024 #define SFG_CAMERA_MAX_SHEAR 1024
/**
Duration in ms of the explosion animation.
*/
#define SFG_EXPLOSION_DURATION 70
#endif // guard #endif // guard