-
Notifications
You must be signed in to change notification settings - Fork 2
Expand file tree
/
Copy pathrendering.c
More file actions
88 lines (81 loc) · 3.84 KB
/
Copy pathrendering.c
File metadata and controls
88 lines (81 loc) · 3.84 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
#include "lib/raylib/include/raylib.h"
#include <stdlib.h>
#include <stdio.h>
#include <malloc.h>
#include <math.h>
#include "headers/config.h"
#include "headers/player.h"
extern Vector2 linestart[128], linend[128],
linestart_s[MAP_SIDES], linend_s[MAP_SIDES],
border_s[4], border_e[4],
map1_s[4], map1_e[4];
void cast_rays(Vector2 ray_s, Vector2 ray_e, Vector2 wall_s, Vector2 wall_e, Vector2 *collision_point)
{ /* https://web.archive.org/web/20060911055655/http://local.wasp.uwa.edu.au/~pbourke/geometry/lineline2d/
also i know that raylib has a CheckCollisionLines() function, but i can't get it working, fell free to uncomment it and try. */
// CheckCollisionLines(ray_s, ray_e, wall_s, wall_e, collision_point);
float den = (wall_e.y - wall_s.y) * (ray_e.x - ray_s.x) - (wall_e.x - wall_s.x) * (ray_e.y - ray_s.y),
num_a = (wall_e.x - wall_s.x) * (ray_s.y - wall_s.y) - (wall_e.y - wall_s.y) * (ray_s.x - wall_s.x),
num_b = (ray_e.x - ray_s.x) * (ray_s.y - wall_s.y) - (ray_e.y - ray_s.y) * (ray_s.x - wall_s.x);
if (den == 0)
return; // parallel lines
float u_a = num_a / den,
u_b = num_b / den;
if (u_a >= 0 && u_a <= 1 && u_b >= 0 && u_b <= 1)
{
collision_point->x = ray_s.x + u_a * (ray_e.x - ray_s.x);
collision_point->y = ray_s.y + u_a * (ray_e.y - ray_s.y);
}
return;
}
void view(Player *player, Settings *settings)
{ // here we raycast the rays and get the closest hit
for (int i = 0; i < settings->ray_count; i++)
{
// DrawLineEx(player->position, player->rays[i], 1, GRAY); // draw all rays, for debugging
Vector2 closest = {0}, collision_point;
float lowest_value = INFINITY;
for (int j = 0; j < MAP_SIDES; j++)
{
collision_point = (Vector2){0, 0};
// cast_rays(player->rays[i], player->position, map1_s[j], map1_e[j], &collision_point);
cast_rays(player->rays[i], player->position, border_s[0], border_e[0], &collision_point);
cast_rays(player->rays[i], player->position, border_s[1], border_e[1], &collision_point);
cast_rays(player->rays[i], player->position, border_s[2], border_e[2], &collision_point);
cast_rays(player->rays[i], player->position, border_s[3], border_e[3], &collision_point);
cast_rays(player->rays[i], player->position, linestart_s[j], linend_s[j], &collision_point);
if (collision_point.x && collision_point.y)
{
float distance = sqrt(pow(player->position.x - collision_point.x, 2) + pow(player->position.y - collision_point.y, 2));
if (distance < lowest_value)
{
lowest_value = distance;
closest = collision_point;
}
}
}
player->colliding_rays[i] = closest;
// DrawLineEx(player->position, closest, 1 * (closest.x && closest.y), RED);
settings->distance[i] = lowest_value * (lowest_value != NAN);
}
return;
}
float map_value(float value, float from1, float to1, float from2, float to2)
{ // just a math function that i had to write myself.
return (value - from1) / (to1 - from1) * (to2 - from2) + from2;
}
void view_3d(Player *player, Settings *settings)
{ // here i get the intersections and transform them into a "3d" view
for (int i = 0; i < settings->ray_count; i++)
{
float distance_width = (float)WIDTH / settings->ray_count;
float alpha = map_value(settings->distance[i], 0, 200, 1, -0.01);
// we will use this to remove fisheye effect
player->ray_angle_from_start[i] = (settings->fov * PI / 180.0f * i / settings->ray_count) + player->angle;
float norm_distance = settings->distance[i] * 2 * (1 + (sin(1.57 - player->ray_angle_from_start[i])) * settings->fisheye_correction);
// drawing every "3d" line
DrawLineEx((Vector2){i * distance_width + 1, norm_distance * (norm_distance < HEIGHT / 2) + HEIGHT / 2 * (norm_distance > HEIGHT / 2)},
(Vector2){i * distance_width + 1, HEIGHT - (norm_distance * (norm_distance < HEIGHT / 2) + HEIGHT / 2 * (norm_distance > HEIGHT / 2))},
distance_width,
ColorAlpha(GRAY, alpha));
}
}