From: Brendan Hansen Date: Thu, 16 Dec 2021 21:10:01 +0000 (-0600) Subject: starting on drawing a cube X-Git-Url: https://git.brendanfh.com/?a=commitdiff_plain;h=8728dcbacf241f4ffbf51aa34864c1eb8ecaea3f;p=voxel-shooter.git starting on drawing a cube --- diff --git a/run_tree/assets/shaders/basic_fragment.glsl b/run_tree/assets/shaders/basic_fragment.glsl new file mode 100644 index 0000000..f81d312 --- /dev/null +++ b/run_tree/assets/shaders/basic_fragment.glsl @@ -0,0 +1,12 @@ +#version 300 es +precision mediump float; + +uniform sampler2D u_sampler; +uniform float u_sampler_enabled; + +in vec2 v_tex; + +out vec4 fragColor; +void main() { + fragColor = mix(vec4(1, 1, 1, 1), texture(u_sampler, v_tex), u_sampler_enabled); +} diff --git a/run_tree/assets/shaders/basic_vertex.glsl b/run_tree/assets/shaders/basic_vertex.glsl new file mode 100644 index 0000000..e8d9f2f --- /dev/null +++ b/run_tree/assets/shaders/basic_vertex.glsl @@ -0,0 +1,15 @@ +#version 300 es +layout(location = 0) in vec3 a_pos; +layout(location = 1) in vec2 a_tex; + +layout(std140) uniform u_matrix_block { + mat4 u_view; + mat4 u_world; +}; + +out vec2 v_tex; + +void main() { + gl_Position = u_view * u_world * vec4(a_pos, 1); + v_tex = a_tex; +} diff --git a/run_tree/lib/onyx_glfw3.so b/run_tree/lib/onyx_glfw3.so index f41064a..f6e354b 100755 Binary files a/run_tree/lib/onyx_glfw3.so and b/run_tree/lib/onyx_glfw3.so differ diff --git a/run_tree/lib/onyx_opengles.so b/run_tree/lib/onyx_opengles.so index 8500f5b..71591b0 100755 Binary files a/run_tree/lib/onyx_opengles.so and b/run_tree/lib/onyx_opengles.so differ diff --git a/src/main.onyx b/src/main.onyx index 158cfd5..5b609e0 100644 --- a/src/main.onyx +++ b/src/main.onyx @@ -2,24 +2,208 @@ use package core use package glfw3 use package opengles +use package stb_truetype -main :: (args) => { - if !glfwInit() { - println("Failed to initialize GLFW"); - os.exit(1); - } +window: GLFWwindow_p; +create_window :: () => { glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 3); glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, 0); - window := glfwCreateWindow(800, 600, #cstr "Voxel Shooter"); + window = glfwCreateWindow(800, 600, #cstr "Voxel Shooter"); + glfwMakeContextCurrent(window); + glfwSetWindowSizeCallback(window, "on_resize"); +} + +#export "on_resize" (window: GLFWwindow_p, width, height: u32) { + glViewport(0, 0, width, height); + update_view_matrix(); +} + +Mesh :: struct { + handle: GLuint; + verticies: [] f32; + indicies: [] u16; +} + +cube_verticies :: (x, y, z: f32) -> [] GLfloat { + vertex_data := GLfloat.[ + x-0.5, y-0.5, z-0.5, + x+0.5, y-0.5, z-0.5, + x+0.5, y+0.5, z-0.5, + x-0.5, y-0.5, z-0.5, + x+0.5, y+0.5, z-0.5, + x-0.5, y+0.5, z-0.5, + + x-0.5, y-0.5, z-0.5, + x-0.5, y+0.5, z-0.5, + x-0.5, y+0.5, z+0.5, + x-0.5, y-0.5, z-0.5, + x-0.5, y+0.5, z+0.5, + x-0.5, y-0.5, z+0.5, + + x-0.5, y-0.5, z-0.5, + x-0.5, y+0.5, z+0.5, + x+0.5, y+0.5, z+0.5, + x-0.5, y-0.5, z-0.5, + x+0.5, y+0.5, z+0.5, + x+0.5, y-0.5, z-0.5, + ]; + + return memory.copy_slice(vertex_data); +} + +vao: GLuint; +matrix_block_buffer: GLuint; + +setup_opengl :: () { glInit(glfwGetLoadProcAddress()); - while !glfwWindowShouldClose(window) { - glClearColor(.2, .2, .2, 1); - glClear(GL_COLOR_BUFFER_BIT); + compile_shader :: (source: str, type: GLenum) -> GLint { + shader := glCreateShader(type); + source_data := source.data; + source_len := source.count; + glShaderSource(shader, 1, ^source_data, ^source_len); + glCompileShader(shader); + + success: GLint; + if glGetShaderiv(shader, GL_COMPILE_STATUS, ^success); success == GL_FALSE { + buf_data: [1024] u8; + buf := str.{ ~~buf_data, 0 }; + glGetShaderInfoLog(shader, 1024, ^buf.count, buf.data); + println(buf); + } + + return shader; + } + + link_program :: (vertex_shader, fragment_shader: GLint) -> GLuint { + prog := glCreateProgram(); + glAttachShader(prog, vertex_shader); + glAttachShader(prog, fragment_shader); + glLinkProgram(prog); + + success: GLint; + if glGetProgramiv(prog, GL_LINK_STATUS, ^success); success == GL_FALSE { + buf_data: [1024] u8; + buf := str.{ ~~buf_data, 0 }; + glGetProgramInfoLog(prog, 1024, ^buf.count, buf.data); + println(buf); + } + + return prog; + } + + vertex_shader := os.get_contents("assets/shaders/basic_vertex.glsl"); + fragment_shader := os.get_contents("assets/shaders/basic_fragment.glsl"); + vs := compile_shader(vertex_shader, GL_VERTEX_SHADER); + fs := compile_shader(fragment_shader, GL_FRAGMENT_SHADER); + + prog := link_program(vs, fs); + glUseProgram(prog); + + matrix: [32] GLfloat; + glGenBuffers(1, ^matrix_block_buffer); + glBindBuffer(GL_UNIFORM_BUFFER, matrix_block_buffer); + glBufferData(GL_UNIFORM_BUFFER, sizeof f32 * (16 + 16), ^matrix, GL_DYNAMIC_DRAW); + glBindBuffer(GL_UNIFORM_BUFFER, -1); + + glBindBufferBase(GL_UNIFORM_BUFFER, 0, matrix_block_buffer); + matrix_block_index := glGetUniformBlockIndex(prog, #cstr "u_matrix_block"); + glUniformBlockBinding(prog, matrix_block_index, 0); + + glGenVertexArrays(1, ^vao); + glBindVertexArray(vao); + + vbo: GLuint; + glGenBuffers(1, ^vbo); + glBindBuffer(GL_ARRAY_BUFFER, vbo); + + vertex_data := cube_verticies(0, 0, -4); + glBufferData(GL_ARRAY_BUFFER, sizeof GLfloat * vertex_data.count, vertex_data.data, GL_STATIC_DRAW); + + glEnableVertexAttribArray(0); + glVertexAttribPointer(0, 3, GL_FLOAT, false, 3 * sizeof GLfloat, ~~0); + + glBindVertexArray(-1); + update_view_matrix(); + update_world_matrix(); +} + +update_view_matrix :: () { + fov := 75 * math.PI / 180; + fov = math.clamp(fov, 0, math.PI - 0.01f); + + width, height: u32; + glfwGetWindowSize(window, ^width, ^height); + ar := cast(f32) width / cast(f32) height; + z_near := 0.01f; + z_far := 100.0f; + z_range := z_far - z_near; + tan_half_fov := math.sin(fov / 2) / math.cos(fov / 2); + + matrix := GLfloat.[ + 1 / (tan_half_fov * ar), 0, 0, 0, + 0, 1 / (tan_half_fov), 0, 0, + 0, 0, (-z_far) / z_range, -1, + 0, 0, -(z_far*z_near)/z_range, 0, + ]; + + glBindBuffer(GL_UNIFORM_BUFFER, matrix_block_buffer); + glBufferSubData(GL_UNIFORM_BUFFER, 0, sizeof typeof matrix, ^matrix); + glBindBuffer(GL_UNIFORM_BUFFER, -1); +} + +update_world_matrix :: () { + #persist t := 0.0f; + t += 0.01; + + c := math.cos(t); + s := math.sin(t); + matrix := GLfloat.[ + c, 0, s, 0, + 0, 1, 0, 0, + -s, 0, c, 0, + 0, 0, 0, 1, + ]; + + glBindBuffer(GL_UNIFORM_BUFFER, matrix_block_buffer); + glBufferSubData(GL_UNIFORM_BUFFER, 16 * sizeof f32, sizeof typeof matrix, ^matrix); + glBindBuffer(GL_UNIFORM_BUFFER, -1); +} + +update :: (dt: f32) { + update_world_matrix(); +} + +draw :: () { + glClearColor(.2, .2, .2, 1); + glClear(GL_COLOR_BUFFER_BIT); + + glBindVertexArray(vao); + glDrawArrays(GL_TRIANGLES, 0, 18); + glBindVertexArray(-1); + + glfwSwapBuffers(window); +} + +main_loop :: () { + while !glfwWindowShouldClose(window) { glfwPollEvents(); - glfwSwapBuffers(window); + + update(1.0f / 60); + draw(); } -} \ No newline at end of file +} + +main :: (args) => { + if !glfwInit() { + println("Failed to initialize GLFW"); + os.exit(1); + } + + create_window(); + setup_opengl(); + main_loop(); +}