reworked the sprite system

This commit is contained in:
djonker 2023-11-05 11:46:44 +01:00
parent 28b1b21186
commit 0962ba9d75
9 changed files with 267 additions and 210 deletions

View File

@ -6,7 +6,7 @@
# By: houtworm <codam@houtworm.net> +#+ #
# +#+ #
# Created: 2023/10/26 10:46:29 by houtworm #+# #+# #
# Updated: 2023/11/05 08:02:39 by houtworm ######## odam.nl #
# Updated: 2023/11/05 10:27:42 by houtworm ######## odam.nl #
# #
# **************************************************************************** #
@ -30,8 +30,8 @@ SRC =src/main/main.c\
src/input/move.c\
src/input/turn.c\
src/input/rest.c\
src/sprite/draw.c\
src/sprite/pickup.c
src/sprite/sprite.c\
src/sprite/drawsprite.c
OBJ =$(SRC:src/%.c=obj/%.o)
all: libft getnextline mlx/build/mlx42.a $(NAME)

25
cub3d.h
View File

@ -6,7 +6,7 @@
/* By: houtworm <codam@houtworm.net> +#+ */
/* +#+ */
/* Created: 2023/10/26 10:46:35 by houtworm #+# #+# */
/* Updated: 2023/11/05 08:22:47 by houtworm ######## odam.nl */
/* Updated: 2023/11/05 11:42:29 by houtworm ######## odam.nl */
/* */
/* ************************************************************************** */
@ -27,8 +27,25 @@ typedef struct s_sprite
double x;
double y;
int type;
int number;
} t_sprite;
typedef struct s_draw
{
double transformx;
double transformy;
int spritescreen;
int vmovescreen;
int spriteheight;
int spritewidth;
int drawstarty;
int drawstartx;
int drawendy;
int drawendx;
int texx;
int texy;
} t_draw;
typedef struct s_varlist
{
mlx_t *mlx;
@ -76,6 +93,7 @@ typedef struct s_varlist
int kills;
int mgun;
int ggun;
int ammo;
} t_varlist;
// MAIN
@ -102,6 +120,9 @@ void ft_drawmap(t_varlist *vl);
int ft_gettextx(t_varlist *vl);
uint32_t ft_gettextcolor(t_varlist *vl, int texty, int textx);
// SPRITE
void ft_drawsprite(t_varlist *vl, t_draw *draw, int x);
t_draw *ft_initdrawsprite(t_varlist *vl, int i);
void ft_getdrawstartend(t_varlist *vl, t_draw *draw);
void ft_drawsprites(t_varlist *vl);
void ft_pickup(t_varlist *vl);
void ft_checkpickup(t_varlist *vl);
#endif

View File

@ -6,7 +6,7 @@
/* By: houtworm <codam@houtworm.net> +#+ */
/* +#+ */
/* Created: 2023/10/26 16:49:12 by houtworm #+# #+# */
/* Updated: 2023/11/05 08:59:03 by houtworm ######## odam.nl */
/* Updated: 2023/11/05 11:42:47 by houtworm ######## odam.nl */
/* */
/* ************************************************************************** */
@ -57,9 +57,9 @@ void ft_initmainstuff(t_varlist *vl)
vl->w = 800;
vl->h = 600;
vl->sprite = ft_calloc(4096, 8);
vl->spritecount = 0;
vl->distance = ft_calloc(4096, 8);
vl->walltext = ft_calloc(4096, 8);
vl->spritecount = 0;
vl->vaim = 0;
vl->jump = 0;
vl->treasure = 0;
@ -68,6 +68,7 @@ void ft_initmainstuff(t_varlist *vl)
vl->kills = 0;
vl->mgun = 0;
vl->ggun = 0;
vl->ammo = 10;
vl->ccolor = 0;
vl->fcolor = 0;
vl->walltext[0] = NULL;

View File

@ -6,7 +6,7 @@
/* By: houtworm <codam@houtworm.net> +#+ */
/* +#+ */
/* Created: 2023/10/26 14:13:07 by houtworm #+# #+# */
/* Updated: 2023/11/05 07:55:52 by houtworm ######## odam.nl */
/* Updated: 2023/11/05 11:42:14 by houtworm ######## odam.nl */
/* */
/* ************************************************************************** */
@ -21,6 +21,51 @@ void ft_replaceimage(t_varlist *vl)
vl->img = mlx_new_image(vl->mlx, vl->w, vl->h);
}
void ft_pickup(t_varlist *vl, int i)
{
if (vl->sprite[i].number < 4)
vl->treasure++;
else if (vl->sprite[i].number < 7)
ft_putendl("Yummy\n");
else if (vl->sprite[i].number == 7)
ft_putendl("Found gold key\n");
else if (vl->sprite[i].number == 8)
ft_putendl("Found blue key\n");
else if (vl->sprite[i].number == 9)
vl->mgun = 1;
else if (vl->sprite[i].number == 10)
vl->ggun = 1;
else if (vl->sprite[i].number == 11)
vl->ammo += 10;
while (vl->sprite[i].x)
{
vl->sprite[i] = vl->sprite[i + 1];
i++;
}
vl->spritecount--;
}
void ft_checkpickup(t_varlist *vl)
{
int i;
i = 0;
while (vl->sprite[i].x)
{
if (vl->sprite[i].type == 2)
{
if ((int)vl->sprite[i].x == (int)vl->posx)
{
if ((int)vl->sprite[i].y == (int)vl->posy)
{
ft_pickup(vl, i);
}
}
}
i++;
}
}
void mainloop(void *param)
{
t_varlist *vl;
@ -28,7 +73,7 @@ void mainloop(void *param)
vl = param;
ft_replaceimage(vl);
ft_drawmap(vl);
ft_pickup(vl);
ft_checkpickup(vl);
ft_drawsprites(vl);
/*ft_drawweapon(vl);*/
vl->frametime = vl->mlx->delta_time;

View File

@ -6,7 +6,7 @@
/* By: houtworm <codam@houtworm.net> +#+ */
/* +#+ */
/* Created: 2023/10/26 17:33:50 by houtworm #+# #+# */
/* Updated: 2023/11/05 04:42:40 by houtworm ######## odam.nl */
/* Updated: 2023/11/05 11:45:14 by houtworm ######## odam.nl */
/* */
/* ************************************************************************** */
@ -47,28 +47,48 @@ char ft_setplayerpos(t_varlist *vl, char dir, int x, int y)
return ('0');
}
char ft_addwalktroughsprite(t_varlist *vl, int x, int y, int type)
char ft_addwalktroughdecor(t_varlist *vl, int x, int y, int number)
{
vl->sprite[vl->spritecount].x = x + 0.5;
vl->sprite[vl->spritecount].y = y + 0.5;
vl->sprite[vl->spritecount].type = type;
if (type == 4)
vl->sprite[vl->spritecount].number = number;
vl->sprite[vl->spritecount].type = 1;
vl->spritecount++;
return ('0');
}
char ft_addsoliddecor(t_varlist *vl, int x, int y, int number)
{
vl->sprite[vl->spritecount].x = x + 0.5;
vl->sprite[vl->spritecount].y = y + 0.5;
vl->sprite[vl->spritecount].number = number;
vl->sprite[vl->spritecount].type = 1;
vl->spritecount++;
return ('2');
}
char ft_addpickup(t_varlist *vl, int x, int y, int number)
{
vl->sprite[vl->spritecount].x = x + 0.5;
vl->sprite[vl->spritecount].y = y + 0.5;
vl->sprite[vl->spritecount].number = number;
vl->sprite[vl->spritecount].type = 2;
if (number < 4)
vl->tottreasure++;
vl->spritecount++;
return ('0');
}
char ft_addsolidsprite(t_varlist *vl, int x, int y, int type)
char ft_addenemy(t_varlist *vl, int x, int y, int number)
{
vl->sprite[vl->spritecount].x = x + 0.5;
vl->sprite[vl->spritecount].y = y + 0.5;
vl->sprite[vl->spritecount].type = type;
if (type == 6)
vl->enemies++;
vl->sprite[vl->spritecount].number = number;
vl->sprite[vl->spritecount].type = 3;
vl->enemies++;
vl->spritecount++;
return ('2');
}
char **ft_getmap(t_varlist *vl, int fd)
{
int y;
@ -111,17 +131,17 @@ char **ft_getmap(t_varlist *vl, int fd)
else if (line[x] == 'D')
map[y][x] = 'D';
else if (line[x] == 'B')
map[y][x] = ft_addsolidsprite(vl, y, x, 1);
map[y][x] = ft_addsoliddecor(vl, y, x, 0);
else if (line[x] == 'G')
map[y][x] = ft_addsolidsprite(vl, y, x, 2);
map[y][x] = ft_addsoliddecor(vl, y, x, 2);
else if (line[x] == 'H')
map[y][x] = ft_addwalktroughsprite(vl, y, x, 3);
map[y][x] = ft_addwalktroughdecor(vl, y, x, 10);
else if (line[x] == 'C')
map[y][x] = ft_addwalktroughsprite(vl, y, x, 4);
map[y][x] = ft_addpickup(vl, y, x, 0);
else if (line[x] == 'X')
map[y][x] = ft_addsolidsprite(vl, y, x, 5);
map[y][x] = ft_addenemy(vl, y, x, 0);
else if (line[x] == 'K')
map[y][x] = ft_addsolidsprite(vl, y, x, 6);
map[y][x] = ft_addenemy(vl, y, x, 0);
else
{
ft_putstr("Invalid character on the map\n Valid options are\n");

View File

@ -1,139 +0,0 @@
/* ************************************************************************** */
/* */
/* :::::::: */
/* draw.c :+: :+: */
/* +:+ */
/* By: houtworm <codam@houtworm.net> +#+ */
/* +#+ */
/* Created: 2023/10/26 16:54:20 by houtworm #+# #+# */
/* Updated: 2023/11/05 08:44:20 by houtworm ######## odam.nl */
/* */
/* ************************************************************************** */
#include "../../cub3d.h"
mlx_texture_t *ft_selectsprite(t_varlist *vl, int type)
{
mlx_texture_t *sprite;
if (type == 1)
sprite = vl->decotext[0];
else if (type == 2)
sprite = vl->decotext[2];
else if (type == 3)
sprite = vl->decotext[10];
else if (type == 4)
sprite = vl->picktext[0];
else if (type == 5)
sprite = vl->picktext[1];
else if (type == 6)
sprite = vl->nazitext[0];
else
ft_errorexit("what?", "what?", 1);
return (sprite);
}
void ft_sortsprites(t_varlist *vl)
{
int i;
t_sprite temp;
i = 0;
while (vl->spritecount > i)
{
vl->sprite[i].distance = pow((vl->posx - vl->sprite[i].x), 2) + pow((vl->posy - vl->sprite[i].y), 2);
i++;
}
while (i)
{
if (vl->sprite[i].distance > vl->sprite[i - 1].distance)
{
temp = vl->sprite[i];
vl->sprite[i] = vl->sprite[i - 1];
vl->sprite[i - 1] = temp;
}
i--;
}
}
void ft_drawsprites(t_varlist *vl)
{
int i;
int x;
int y;
double spritex;
double spritey;
double invdet;
double transformx;
double transformy;
int spritescreenx;
int vmovescreen;
int spriteheight;
int spritewidth;
int drawstarty;
int drawstartx;
int drawendy;
int drawendx;
int texx;
int texy;
int d;
uint32_t color;
i = 0;
ft_sortsprites(vl);
while (vl->spritecount > i)
{
spritex = vl->sprite[i].x - vl->posx;
spritey = vl->sprite[i].y - vl->posy;
vl->temptext = ft_selectsprite(vl, vl->sprite[i].type);
invdet = 1.0 / (vl->planex * vl->diry - vl->dirx * vl->planey);
transformx = invdet * (vl->diry * spritex - vl->dirx * spritey);
transformy = invdet * (-vl->planey * spritex + vl->planex * spritey);
spritescreenx = (vl->w / 2) * (1 + transformx / transformy);
vmovescreen = vl->vaim + vl->jump / transformy;
spriteheight = fabs((vl->h / transformy));
drawstarty = -spriteheight / 2 + vl->h / 2 + vmovescreen;
if (drawstarty < 0)
drawstarty = 0;
drawendy = spriteheight / 2 + vl->h / 2 + vmovescreen;
if (drawendy >= vl->h)
drawendy = vl->h - 1;
spritewidth = abs((int)(vl->h / transformy));
drawstartx = -spritewidth / 2 + spritescreenx;
if (drawstartx < 0)
drawstartx = 0;
drawendx = spritewidth / 2 + spritescreenx;
if (drawendx >= vl->w)
drawendx = vl->w - 1;
x = drawstartx;
while (x < drawendx)
{
texx = (int)(256 * (x - (-spritewidth / 2 + spritescreenx)) * 64 / spritewidth) / 256;
if (transformy > 0 && x > 0 && x < vl->w && transformy < vl->distance[x] + 0.7)
{
y = drawstarty;
while (y < drawendy)
{
d = (y - vmovescreen) * 256 - vl->h * 128 + spriteheight * 128;
texy = (d * 64) / spriteheight / 256;
uint8_t *texel;
if (texy < 0)
texy = 0;
if (texy > 64)
texy = 64;
if (texx < 0)
texx = 0;
if (texx > 64)
texx = 64;
texel = &vl->temptext->pixels[(vl->temptext->width * texy + texx) * 4];
color = texel[0] << 24 | texel[1] << 16 | texel[2] << 8 | texel[3];
if (color != 0x980088FF)
mlx_put_pixel(vl->img, x, y, color);
y++;
}
}
x++;
}
i++;
}
}

91
src/sprite/drawsprite.c Normal file
View File

@ -0,0 +1,91 @@
/* ************************************************************************** */
/* */
/* :::::::: */
/* drawsprite.c :+: :+: */
/* +:+ */
/* By: houtworm <codam@houtworm.net> +#+ */
/* +#+ */
/* Created: 2023/10/26 16:54:20 by houtworm #+# #+# */
/* Updated: 2023/11/05 11:04:09 by houtworm ######## odam.nl */
/* */
/* ************************************************************************** */
#include "../../cub3d.h"
void ft_drawspriteline(t_varlist *vl, t_draw *draw, int y, int x)
{
int d;
uint8_t *texel;
uint32_t color;
d = (y - draw->vmovescreen) * 256 - vl->h * 128 + draw->spriteheight * 128;
draw->texy = (d * 64) / draw->spriteheight / 256;
if (draw->texy < 0)
draw->texy = 0;
if (draw->texy > 64)
draw->texy = 64;
if (draw->texx < 0)
draw->texx = 0;
if (draw->texx > 64)
draw->texx = 64;
texel = &vl->temptext->pixels[(vl->temptext->width * draw->texy + draw->texx) * 4];
color = texel[0] << 24 | texel[1] << 16 | texel[2] << 8 | texel[3];
if (color != 0x980088FF)
mlx_put_pixel(vl->img, x, y, color);
}
void ft_drawsprite(t_varlist *vl, t_draw *draw, int x)
{
int y;
while (x < draw->drawendx)
{
draw->texx = (int)(256 * (x - (-draw->spritewidth / 2 + draw->spritescreen)) * 64 / draw->spritewidth) / 256;
if (draw->transformy > 0 && x > 0 && x < vl->w && draw->transformy < vl->distance[x] + 0.7)
{
y = draw->drawstarty;
while (y < draw->drawendy)
{
ft_drawspriteline(vl, draw, y, x);
y++;
}
}
x++;
}
}
t_draw *ft_initdrawsprite(t_varlist *vl, int i)
{
double spritex;
double spritey;
double invdet;
t_draw *draw;
draw = ft_calloc(12, 8);
spritex = vl->sprite[i].x - vl->posx;
spritey = vl->sprite[i].y - vl->posy;
invdet = 1.0 / (vl->planex * vl->diry - vl->dirx * vl->planey);
draw->transformx = invdet * (vl->diry * spritex - vl->dirx * spritey);
draw->transformy = invdet * (-vl->planey * spritex + vl->planex * spritey);
draw->spritescreen = (vl->w / 2) * (1 + draw->transformx / draw->transformy);
draw->vmovescreen = vl->vaim + vl->jump / draw->transformy;
draw->spriteheight = fabs((vl->h / draw->transformy));
return (draw);
}
void ft_getdrawstartend(t_varlist *vl, t_draw *draw)
{
draw->drawstarty = -draw->spriteheight / 2 + vl->h / 2 + draw->vmovescreen;
if (draw->drawstarty < 0)
draw->drawstarty = 0;
draw->drawendy = draw->spriteheight / 2 + vl->h / 2 + draw->vmovescreen;
if (draw->drawendy >= vl->h)
draw->drawendy = vl->h - 1;
draw->spritewidth = abs((int)(vl->h / draw->transformy));
draw->drawstartx = -draw->spritewidth / 2 + draw->spritescreen;
if (draw->drawstartx < 0)
draw->drawstartx = 0;
draw->drawendx = draw->spritewidth / 2 + draw->spritescreen;
if (draw->drawendx >= vl->w)
draw->drawendx = vl->w - 1;
}

View File

@ -1,47 +0,0 @@
/* ************************************************************************** */
/* */
/* :::::::: */
/* pickup.c :+: :+: */
/* +:+ */
/* By: houtworm <codam@houtworm.net> +#+ */
/* +#+ */
/* Created: 2023/10/26 14:13:07 by houtworm #+# #+# */
/* Updated: 2023/11/05 08:20:00 by houtworm ######## odam.nl */
/* */
/* ************************************************************************** */
#include "../../cub3d.h"
void ft_pickuptreasure(t_varlist *vl)
{
int i;
i = 0;
while (vl->sprite[i].x)
{
if ((int)vl->sprite[i].x == (int)vl->posx)
{
if ((int)vl->sprite[i].y == (int)vl->posy)
{
if (vl->sprite[i].type == 4)
{
while (vl->sprite[i].x)
{
vl->sprite[i] = vl->sprite[i + 1];
i++;
}
vl->spritecount--;
vl->treasure++;
}
}
}
i++;
}
}
void ft_pickup(t_varlist *vl)
{
ft_pickuptreasure(vl);
/*ft_pickuphealth(vl);*/
/*ft_pickupweapon(vl);*/
}

65
src/sprite/sprite.c Normal file
View File

@ -0,0 +1,65 @@
/* ************************************************************************** */
/* */
/* :::::::: */
/* sprite.c :+: :+: */
/* +:+ */
/* By: houtworm <codam@houtworm.net> +#+ */
/* +#+ */
/* Created: 2023/10/26 16:54:20 by houtworm #+# #+# */
/* Updated: 2023/11/05 11:30:18 by houtworm ######## odam.nl */
/* */
/* ************************************************************************** */
#include "../../cub3d.h"
void ft_sortsprites(t_varlist *vl)
{
int i;
t_sprite temp;
i = 0;
while (vl->spritecount > i)
{
vl->sprite[i].distance = pow((vl->posx - vl->sprite[i].x), 2) + pow((vl->posy - vl->sprite[i].y), 2);
i++;
}
while (i)
{
if (vl->sprite[i].distance > vl->sprite[i - 1].distance)
{
temp = vl->sprite[i];
vl->sprite[i] = vl->sprite[i - 1];
vl->sprite[i - 1] = temp;
}
i--;
}
}
mlx_texture_t *ft_getsprite(t_varlist *vl, int i)
{
if (vl->sprite[i].type == 1)
return (vl->decotext[vl->sprite[i].number]);
if (vl->sprite[i].type == 2)
return (vl->picktext[vl->sprite[i].number]);
return (vl->nazitext[vl->sprite[i].number]);
}
void ft_drawsprites(t_varlist *vl)
{
int i;
int x;
t_draw *draw;
ft_sortsprites(vl);
i = 0;
while (vl->spritecount > i)
{
draw = ft_initdrawsprite(vl, i);
ft_getdrawstartend(vl, draw);
x = draw->drawstartx;
vl->temptext = ft_getsprite(vl, i);
ft_drawsprite(vl, draw, x);
free(draw);
i++;
}
}