a
This commit is contained in:
commit
6264446526
BIN
libgearlib.a
Normal file
BIN
libgearlib.a
Normal file
Binary file not shown.
63
main.c
Normal file
63
main.c
Normal file
|
@ -0,0 +1,63 @@
|
|||
#include <gearlib.h>
|
||||
|
||||
int main() {
|
||||
Window window = create_window(800, 600, "raytracing");
|
||||
glfwSwapInterval(0);
|
||||
enable_debugging();
|
||||
|
||||
RenderBatch* surface = create_batch(sizeof(vec2), 6);
|
||||
surface->shader = load_shader_program(
|
||||
compile_shader("raycast.vert", GL_VERTEX_SHADER),
|
||||
compile_shader("raycast.frag", GL_FRAGMENT_SHADER), 0);
|
||||
|
||||
batch_add_attrib(surface, (VertexAttrib){
|
||||
.type = GL_FLOAT, .size = sizeof(float), .count = 2
|
||||
});
|
||||
|
||||
batch_bind_attribs(surface);
|
||||
|
||||
vec2 vertices[] = {
|
||||
vec2(-1.0f, 1.0f), vec2(-1.0f, -1.0f), vec2(1.0f, -1.0f),
|
||||
vec2(1.0f, -1.0f), vec2(1.0f, 1.0f), vec2(-1.0f, 1.0f),
|
||||
};
|
||||
|
||||
glNamedBufferSubData(surface->vbo, 0, surface->vertex_size * 6, vertices);
|
||||
glUseProgram(surface->shader);
|
||||
|
||||
float start_time = glfwGetTime();
|
||||
float elapsed_time = 0.0f;
|
||||
|
||||
uint32_t ssbo;
|
||||
glCreateBuffers(1, &ssbo);
|
||||
glNamedBufferStorage(ssbo, sizeof(int), NULL, GL_DYNAMIC_STORAGE_BIT);
|
||||
glBindBufferBase(GL_SHADER_STORAGE_BUFFER, 0, ssbo);
|
||||
|
||||
int ray_count = 0;
|
||||
|
||||
while(!glfwWindowShouldClose(window)) {
|
||||
//glNamedBufferSubData(ssbo, 0, sizeof(int), &ray_count);
|
||||
int w, h;
|
||||
glfwGetWindowSize(window, &w, &h);
|
||||
float aspect_ratio = (float)w / (float)h;
|
||||
glUniform1f(0, aspect_ratio);
|
||||
glUniform1f(1, sin(elapsed_time));
|
||||
|
||||
renderer_draw(surface->vao, 6);
|
||||
|
||||
glfwSwapBuffers(window);
|
||||
glfwPollEvents();
|
||||
|
||||
float end_time = glfwGetTime();
|
||||
float frame_time = end_time - start_time;
|
||||
start_time = end_time;
|
||||
|
||||
elapsed_time += frame_time;
|
||||
|
||||
float fps = 1.0f / frame_time;
|
||||
printf("fps: %f\n", fps);
|
||||
}
|
||||
|
||||
glfwDestroyWindow(window);
|
||||
glfwTerminate();
|
||||
return 0;
|
||||
}
|
113
raycast.frag
Normal file
113
raycast.frag
Normal file
|
@ -0,0 +1,113 @@
|
|||
#version 460 core
|
||||
|
||||
in vec2 pos;
|
||||
out vec4 color;
|
||||
|
||||
layout(location = 0) uniform float aspect_ratio;
|
||||
layout(location = 1) uniform float sphere_y;
|
||||
|
||||
layout(std430, binding = 0) buffer data
|
||||
{
|
||||
int ray_count;
|
||||
};
|
||||
|
||||
struct Ray {
|
||||
vec3 origin;
|
||||
vec3 direction;
|
||||
};
|
||||
|
||||
struct Sphere {
|
||||
vec3 center;
|
||||
float radius;
|
||||
};
|
||||
|
||||
vec3 unit_vector(vec3 v) {
|
||||
return v / length(v);
|
||||
}
|
||||
|
||||
float length_squared(vec3 v) {
|
||||
float length = length(v);
|
||||
return length * length;
|
||||
}
|
||||
|
||||
float hit_sphere(Ray r, Sphere s) {
|
||||
vec3 oc = s.center - r.origin;
|
||||
float a = length_squared(r.direction);
|
||||
float h = dot(r.direction, oc);
|
||||
float c = length_squared(oc) - s.radius * s.radius;
|
||||
float discriminant = h * h - a * c;
|
||||
|
||||
if(discriminant > 0.0) {
|
||||
return (h - sqrt(discriminant)) / a;
|
||||
}
|
||||
|
||||
return -1.0;
|
||||
}
|
||||
|
||||
vec3 at(Ray r, float time) {
|
||||
return r.origin + time * r.direction;
|
||||
}
|
||||
|
||||
vec3 get_normal_color(Ray r, vec3 pos, Sphere s) {
|
||||
vec3 normal = unit_vector(pos - s.center);
|
||||
return 0.5 * vec3(normal + vec3(1.0, 1.0, 1.0));
|
||||
}
|
||||
|
||||
Sphere spheres[] = {
|
||||
Sphere(vec3(0, sphere_y, -1), 0.5),
|
||||
Sphere(vec3(2, 0, 0), 0.25),
|
||||
Sphere(vec3(0, -100.5, -1), 100.0)
|
||||
};
|
||||
|
||||
struct HitInfo {
|
||||
vec3 pos;
|
||||
bool hit;
|
||||
int index;
|
||||
};
|
||||
|
||||
HitInfo hit_spheres(Ray r) {
|
||||
float t_min = 0;
|
||||
int index;
|
||||
bool hit = false;
|
||||
|
||||
for(int i = 0; i < spheres.length(); i++) {
|
||||
Sphere s = spheres[i];
|
||||
float t = hit_sphere(r, s);
|
||||
if(t > 0.0 && (!hit || t < t_min)) {
|
||||
t_min = t;
|
||||
index = i;
|
||||
hit = true;
|
||||
}
|
||||
}
|
||||
|
||||
return HitInfo(hit ? at(r, t_min) : vec3(0.0), hit, index);
|
||||
}
|
||||
|
||||
vec3 ray_color(Ray r) {
|
||||
HitInfo info = hit_spheres(r);
|
||||
if(info.hit) {
|
||||
vec3 sun_dir = vec3(10, 10, 10) - info.pos;
|
||||
Ray sun_ray = Ray(info.pos, sun_dir);
|
||||
HitInfo sun_hit = hit_spheres(sun_ray);
|
||||
|
||||
return get_normal_color(r, info.pos,
|
||||
spheres[info.index]) -
|
||||
(sun_hit.hit && sun_hit.index != info.index ? 0.4 : 0.0);
|
||||
}
|
||||
|
||||
vec3 unit_direction = unit_vector(r.direction);
|
||||
float a = 0.5 * (unit_direction.y + 1.0);
|
||||
return (1.0 - a) * vec3(1.0, 1.0, 1.0) + a * vec3(0.5, 0.7, 1.0);
|
||||
}
|
||||
|
||||
void main() {
|
||||
vec3 p = vec3(pos, 0.0);
|
||||
p.x *= aspect_ratio;
|
||||
|
||||
vec3 camera_pos = vec3(0.0, 0.0, 0.0);
|
||||
camera_pos.z += 1.0;
|
||||
vec3 ray_dir = p - camera_pos;
|
||||
|
||||
Ray r = Ray(camera_pos, ray_dir);
|
||||
color = vec4(ray_color(r), 1.0);
|
||||
}
|
11
raycast.vert
Normal file
11
raycast.vert
Normal file
|
@ -0,0 +1,11 @@
|
|||
#version 460 core
|
||||
|
||||
in vec2 a_pos;
|
||||
out vec2 pos;
|
||||
out vec2 uv;
|
||||
|
||||
void main() {
|
||||
pos = a_pos;
|
||||
uv = (a_pos / 2.0) + 0.5;
|
||||
gl_Position = vec4(a_pos, 0.0, 1.0);
|
||||
}
|
Loading…
Reference in a new issue