commit 8db56f9768069c4a4f6f616f6011b14d8838a45e parent f5c6767f4dabffe9fd2427bd4a5a315049213964 Author: Michael Savage <mikejsavage@gmail.com> Date: Mon Sep 5 22:00:49 -0700 Split up BTT code and btt.so code Diffstat:
Makefile | | | 2 | +- |
btt.cc | | | 213 | +------------------------------------------------------------------------------ |
mod_btt.cc | | | 226 | +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
diff --git a/Makefile b/Makefile @@ -12,7 +12,7 @@ sound: audio.o mixer.o log.o memory_arena.o wave.o # Module dependencies bsp.so: bsp.o bsp_renderer.o hm.so: hm.o heightmap.o terrain_manager.o lz4.o -btt.so: btt.o heightmap.o gpubtt.o skybox.o stb_image.o +btt.so: mod_btt.o btt.o gpubtt.o heightmap.o skybox.o stb_image.o sm.so: shadow_map.o test_lockfree: relacy.cc nonblocking_fixed_spmc_queue.h nonblocking_fixed_spsc_queue.h diff --git a/btt.cc b/btt.cc @@ -1,94 +1,10 @@ -#include "glad.h" #include "glsl.h" #include <glm/glm.hpp> -#include <glm/gtc/matrix_transform.hpp> -#include <glm/gtc/type_ptr.hpp> -#include "game.h" #include "intrinsics.h" -#include "log.h" +#include "memory_arena.h" #include "btt.h" #include "heightmap.h" -#include "gl.h" -#include "stb_image.h" - -static ImmediateTriangle triangles[ 512000 ]; -static ImmediateContext imm; - -static const GLchar * const vert_src = GLSL( - in vec3 position; - - out vec3 smooth_position; - out float depth; - - uniform mat4 vp; - - void main() { - gl_Position = vp * vec4( position, 1.0 ); - smooth_position = position; - depth = gl_Position.z; - } -); - -static const GLchar * frag_src = GLSL( - in vec3 smooth_position; - in float depth; - - out vec4 colour; - - uniform float sun; - uniform sampler2D normals; - uniform sampler2D horizons; - uniform vec2 dimensions; - - void main() { - vec3 normal = normalize( texture( normals, smooth_position.xy / dimensions ).xyz ); - - vec3 ground; - if( normal.z > 0.9 ) { - ground = vec3( 0.4, 1.0, 0.4 ); - } - else { - ground = vec3( 0.7, 0.7, 0.5 ); - } - - vec3 sunv = normalize( vec3( 1, 1, -sun ) ); - float l = sun > texture( horizons, smooth_position.xy / dimensions ).x ? 1.0 : 0.0; - - float d = max( 0, -dot( normal, sunv ) ); - float light = max( 0.2, l * d ); - - vec3 fog = vec3( 0.6, 0.6, 0.6 ); - - float t = smoothstep( 400, 600, depth ); - - colour = vec4( ( 1.0 - t ) * ground * light + t * fog, 1.0 ); - } -); - -static const GLchar * const vert_outline_src = GLSL( - in vec3 position; - in vec3 colour; - - out vec3 frag_colour; - - uniform mat4 vp; - - void main() { - frag_colour = colour; - gl_Position = vp * vec4( position, 1.0 ); - } -); - -static const GLchar * frag_outline_src = GLSL( - in vec3 frag_colour; - - out vec4 screen_colour; - - void main() { - screen_colour = vec4( frag_colour, 1.0 ); - } -); // triangles should look like this: // @@ -149,10 +65,6 @@ static void btt_split( MemoryArena * const arena, BTT * const node ) { } } -static int iabs( const int x ) { - return x < 0 ? -x : x; -} - static int square_distance( const glm::ivec2 u, const glm::ivec2 v ) { const glm::ivec2 d = v - u; return d.x * d.x + d.y * d.y; @@ -178,8 +90,6 @@ static void btt_build( BTT * const node, const glm::ivec2 v0, const glm::ivec2 v1, const glm::ivec2 v2 ) { - TIMED_FUNCTION(); - const glm::ivec2 mid = ( v0 + v2 ) / 2; if( !node->left ) { @@ -215,124 +125,3 @@ BTTs btt_from_heightmap( const Heightmap * const hm, MemoryArena * const arena ) return roots; } - -static const glm::mat4 P( glm::perspective( glm::radians( 120.0f ), ( float ) WIDTH / ( float ) HEIGHT, NEAR_PLANE_DEPTH, FAR_PLANE_DEPTH ) ); - -extern "C" GAME_INIT( game_init ) { - state->pos = glm::vec3( 100, 100, 50 ); - state->angles = glm::radians( glm::vec3( -90, 45, 0 ) ); - - state->test_sun = 0.3f; - - state->test_shader = compile_shader( vert_src, frag_src, "screen_colour" ); - state->test_at_position = glGetAttribLocation( state->test_shader, "position" ); - state->test_un_VP = glGetUniformLocation( state->test_shader, "vp" ); - state->test_un_sun = glGetUniformLocation( state->test_shader, "sun" ); - state->test_un_normals = glGetUniformLocation( state->test_shader, "normals" ); - state->test_un_dimensions = glGetUniformLocation( state->test_shader, "dimensions" ); - - state->test_outline_shader = compile_shader( vert_outline_src, frag_outline_src, "screen_colour" ); - state->test_outline_at_position = glGetAttribLocation( state->test_outline_shader, "position" ); - state->test_outline_at_colour = glGetAttribLocation( state->test_outline_shader, "colour" ); - state->test_outline_un_vp = glGetUniformLocation( state->test_outline_shader, "vp" ); - - int w, h; - u8 * pixels = stbi_load( "terrains/mountains512.png", &w, &h, NULL, 1 ); - heightmap_init( &state->hm, &mem->persistent_arena, pixels, w, h, 0, 0, - state->test_at_position, state->test_at_normal, state->test_at_lit ); - - state->btt = btt_from_heightmap( &state->hm, &mem->persistent_arena ); - - const OffsetHeightmap ohm = { state->hm, 0, 0 }; - gpubtt_init( &mem->persistent_arena, &state->gpubtt, &ohm, state->btt, state->test_at_position ); - - glClearColor( 0, 0.5, 0.7, 1 ); -} - -static glm::vec3 angles_to_vector_xy( const glm::vec3 & angles ) { - return glm::vec3( sin( angles.y ), cos( angles.y ), 0 ); -} - -static void draw_btt( - const BTT * const btt, const Heightmap * const hm, - ImmediateContext * const imm, - const glm::ivec2 iv0, const glm::ivec2 iv1, const glm::ivec2 iv2 -) { - const glm::vec4 white( 1, 1, 1, 1 ); - const glm::vec3 offset( 0.0f, 0.0f, 0.5f ); - - const glm::vec3 v0( hm->point( iv0.x, iv0.y ) + offset ); - const glm::vec3 v1( hm->point( iv1.x, iv1.y ) + offset ); - const glm::vec3 v2( hm->point( iv2.x, iv2.y ) + offset ); - - if( btt->left ) { - assert( btt->right ); - - const glm::ivec2 mid = ( iv0 + iv2 ) / 2; - - draw_btt( btt->left, hm, imm, iv1, mid, iv0 ); - draw_btt( btt->right, hm, imm, iv2, mid, iv1 ); - } - else { - immediate_triangle( imm, v0, v1, v2, white ); - } -} - -extern "C" GAME_FRAME( game_frame ) { - glClear( GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT ); - - const int fb = input->keys[ 'w' ] - input->keys[ 's' ]; - const int lr = input->keys[ 'a' ] - input->keys[ 'd' ]; - const int dz = input->keys[ KEY_SPACE ] - input->keys[ KEY_LEFTSHIFT ]; - - const float dsun = ( input->keys[ KEY_EQUALS ] - input->keys[ KEY_MINUS ] ) * dt; - state->test_sun += dsun; - - const int pitch = input->keys[ KEY_UPARROW ] - input->keys[ KEY_DOWNARROW ]; - const int yaw = input->keys[ KEY_RIGHTARROW ] - input->keys[ KEY_LEFTARROW ]; - - state->angles.x += pitch * dt * 2; - state->angles.y += yaw * dt * 2; - - // const float speed = 6.0f; - const float speed = 100.0f; - state->pos += angles_to_vector_xy( state->angles ) * speed * dt * ( float ) fb; - const glm::vec3 sideways = glm::vec3( -cosf( state->angles.y ), sinf( state->angles.y ), 0 ); - state->pos += sideways * speed * dt * ( float ) lr; - state->pos.z += dz * 50.0f * dt; - - const glm::mat4 VP = glm::translate( - glm::rotate( - glm::rotate( - P, - state->angles.x, - glm::vec3( 1, 0, 0 ) - ), - state->angles.y, - glm::vec3( 0, 0, 1 ) - ), - -state->pos - ); - const glm::vec3 sun = glm::normalize( glm::vec3( 1, 0, -0.3 ) ); - - glPolygonMode( GL_FRONT_AND_BACK, GL_FILL ); - glUseProgram( state->test_shader ); - glUniformMatrix4fv( state->test_un_VP, 1, GL_FALSE, glm::value_ptr( VP ) ); - glUniform1f( state->test_un_sun, state->test_sun ); - glUniform2f( state->test_un_dimensions, state->hm.width, state->hm.height ); - gpubtt_render( &state->gpubtt, state->test_un_normals ); - glUseProgram( 0 ); - - immediate_init( &imm, triangles, array_count( triangles ) ); - draw_btt( state->btt.left_root, &state->hm, &imm, glm::ivec2( 0, 0 ), glm::ivec2( 0, state->hm.height - 1 ), glm::ivec2( state->hm.width - 1, state->hm.height - 1 ) ); - draw_btt( state->btt.right_root, &state->hm, &imm, glm::ivec2( state->hm.width - 1, state->hm.height - 1 ), glm::ivec2( state->hm.width - 1, 0 ), glm::ivec2( 0, 0 ) ); - - glPolygonMode( GL_FRONT_AND_BACK, GL_LINE ); - - glUseProgram( state->test_outline_shader ); - glUniformMatrix4fv( state->test_outline_un_vp, 1, GL_FALSE, glm::value_ptr( VP ) ); - immediate_render( &imm, state->test_outline_at_position, state->test_outline_at_colour ); - glUseProgram( 0 ); - - benchmark_print_timers(); -} diff --git a/mod_btt.cc b/mod_btt.cc @@ -0,0 +1,226 @@ +#include "glad.h" +#include "glsl.h" +#include <glm/glm.hpp> +#include <glm/gtc/matrix_transform.hpp> +#include <glm/gtc/type_ptr.hpp> + +#include "game.h" +#include "intrinsics.h" +#include "immediate.h" +#include "skybox.h" +#include "stb_image.h" + +static ImmediateTriangle triangles[ 512000 ]; +static ImmediateContext imm; + +static const GLchar * const vert_src = GLSL( + in vec3 position; + + out vec3 smooth_position; + out float depth; + + uniform mat4 vp; + + void main() { + gl_Position = vp * vec4( position, 1.0 ); + smooth_position = position; + depth = gl_Position.z; + } +); + +static const GLchar * frag_src = GLSL( + in vec3 smooth_position; + in float depth; + + out vec4 colour; + + uniform float sun; + uniform sampler2D normals; + uniform sampler2D horizons; + uniform vec2 dimensions; + + void main() { + vec3 normal = normalize( texture( normals, smooth_position.xy / dimensions ).xyz ); + + vec3 ground; + if( normal.z > 0.9 ) { + ground = vec3( 0.4, 1.0, 0.4 ); + } + else { + ground = vec3( 0.7, 0.7, 0.5 ); + } + + vec3 sunv = normalize( vec3( 1, 1, -sun ) ); + float horizon = texture( horizons, smooth_position.xy / dimensions ).x; + float l = sun > horizon ? 1.0 : 0.0; + + float d = max( 0, -dot( normal, sunv ) ); + // float light = max( 0.2, l * ( d * 0 + 1 ) ); + float light = max( 0.2, l * d ); + + vec3 fog = vec3( 0.6, 0.6, 0.6 ); + + float t = smoothstep( 400, 600, depth ); + + colour = vec4( ( 1.0 - t ) * ground * light + t * fog, 1.0 ); + // colour *= 0; + // colour = vec4( horizon, horizon, horizon, 1.0 ); + + // if( smooth_position.y > 10.5 && smooth_position.y < 11.5 ) { + // colour.r = 1; + // } + // + // int a = int( smooth_position.x ) / 10; + // if( a % 2 == 0 ) colour.g = 1; + } +); + +static const GLchar * const vert_outline_src = GLSL( + in vec3 position; + in vec3 colour; + + out vec3 frag_colour; + + uniform mat4 vp; + + void main() { + frag_colour = colour; + gl_Position = vp * vec4( position, 1.0 ); + } +); + +static const GLchar * frag_outline_src = GLSL( + in vec3 frag_colour; + + out vec4 screen_colour; + + void main() { + screen_colour = vec4( frag_colour, 1.0 ); + } +); + +static glm::vec3 angles_to_vector_xy( const glm::vec3 & angles ) { + return glm::vec3( sin( angles.y ), cos( angles.y ), 0 ); +} + +static void draw_btt( + const BTT * const btt, const Heightmap * const hm, + ImmediateContext * const imm, + const glm::ivec2 iv0, const glm::ivec2 iv1, const glm::ivec2 iv2 +) { + const glm::vec4 white( 1, 1, 1, 1 ); + const glm::vec3 offset( 0.0f, 0.0f, 0.5f ); + + const glm::vec3 v0( hm->point( iv0.x, iv0.y ) + offset ); + const glm::vec3 v1( hm->point( iv1.x, iv1.y ) + offset ); + const glm::vec3 v2( hm->point( iv2.x, iv2.y ) + offset ); + + if( btt->left ) { + assert( btt->right ); + + const glm::ivec2 mid = ( iv0 + iv2 ) / 2; + + draw_btt( btt->left, hm, imm, iv1, mid, iv0 ); + draw_btt( btt->right, hm, imm, iv2, mid, iv1 ); + } + else { + immediate_triangle( imm, v0, v1, v2, white ); + } +} + +static const glm::mat4 P( glm::perspective( glm::radians( 120.0f ), ( float ) WIDTH / ( float ) HEIGHT, NEAR_PLANE_DEPTH, FAR_PLANE_DEPTH ) ); + +extern "C" GAME_INIT( game_init ) { + state->pos = glm::vec3( 100, 200, 100 ); + state->angles = glm::radians( glm::vec3( -90, 45, 0 ) ); + + state->test_sun = 0.3f; + + state->test_shader = compile_shader( vert_src, frag_src, "screen_colour" ); + state->test_at_position = glGetAttribLocation( state->test_shader, "position" ); + state->test_un_VP = glGetUniformLocation( state->test_shader, "vp" ); + state->test_un_sun = glGetUniformLocation( state->test_shader, "sun" ); + state->test_un_normals = glGetUniformLocation( state->test_shader, "normals" ); + state->test_un_dimensions = glGetUniformLocation( state->test_shader, "dimensions" ); + + state->test_outline_shader = compile_shader( vert_outline_src, frag_outline_src, "screen_colour" ); + state->test_outline_at_position = glGetAttribLocation( state->test_outline_shader, "position" ); + state->test_outline_at_colour = glGetAttribLocation( state->test_outline_shader, "colour" ); + state->test_outline_un_vp = glGetUniformLocation( state->test_outline_shader, "vp" ); + + int w, h; + u8 * pixels = stbi_load( "terrains/mountains512.png", &w, &h, NULL, 1 ); + heightmap_init( &state->hm, &mem->persistent_arena, pixels, w, h, 0, 0, + state->test_at_position, state->test_at_normal, state->test_at_lit ); + + state->btt = btt_from_heightmap( &state->hm, &mem->persistent_arena ); + + const OffsetHeightmap ohm = { state->hm, 0, 0 }; + gpubtt_init( &mem->persistent_arena, &state->gpubtt, &ohm, state->btt, state->test_at_position ); + + glClearColor( 0, 0.5, 0.7, 1 ); + + skybox_init( &state->skybox ); +} + +extern "C" GAME_FRAME( game_frame ) { + glClear( GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT ); + + const int fb = input->keys[ 'w' ] - input->keys[ 's' ]; + const int lr = input->keys[ 'a' ] - input->keys[ 'd' ]; + const int dz = input->keys[ KEY_SPACE ] - input->keys[ KEY_LEFTSHIFT ]; + + const float dsun = ( input->keys[ KEY_EQUALS ] - input->keys[ KEY_MINUS ] ) * dt; + state->test_sun += dsun; + if( dsun != 0 ) printf( "sun: %.4f\n", state->test_sun ); + + const int pitch = input->keys[ KEY_UPARROW ] - input->keys[ KEY_DOWNARROW ]; + const int yaw = input->keys[ KEY_RIGHTARROW ] - input->keys[ KEY_LEFTARROW ]; + + state->angles.x += pitch * dt * 2; + state->angles.y += yaw * dt * 2; + + // const float speed = 6.0f; + const float speed = 100.0f; + state->pos += angles_to_vector_xy( state->angles ) * speed * dt * ( float ) fb; + const glm::vec3 sideways = glm::vec3( -cosf( state->angles.y ), sinf( state->angles.y ), 0 ); + state->pos += sideways * speed * dt * ( float ) lr; + state->pos.z += dz * 50.0f * dt; + + const glm::mat4 VP = glm::translate( + glm::rotate( + glm::rotate( + P, + state->angles.x, + glm::vec3( 1, 0, 0 ) + ), + state->angles.y, + glm::vec3( 0, 0, 1 ) + ), + -state->pos + ); + const glm::vec3 sun = glm::normalize( glm::vec3( 1, 0, -0.3 ) ); + + glPolygonMode( GL_FRONT_AND_BACK, GL_FILL ); + glUseProgram( state->test_shader ); + glUniformMatrix4fv( state->test_un_VP, 1, GL_FALSE, glm::value_ptr( VP ) ); + glUniform1f( state->test_un_sun, state->test_sun ); + glUniform2f( state->test_un_dimensions, state->hm.width, state->hm.height ); + gpubtt_render( &state->gpubtt, state->test_un_normals ); + glUseProgram( 0 ); + + // immediate_init( &imm, triangles, array_count( triangles ) ); + // draw_btt( state->btt.left_root, &state->hm, &imm, glm::ivec2( 0, 0 ), glm::ivec2( 0, state->hm.height - 1 ), glm::ivec2( state->hm.width - 1, state->hm.height - 1 ) ); + // draw_btt( state->btt.right_root, &state->hm, &imm, glm::ivec2( state->hm.width - 1, state->hm.height - 1 ), glm::ivec2( state->hm.width - 1, 0 ), glm::ivec2( 0, 0 ) ); + // + // glPolygonMode( GL_FRONT_AND_BACK, GL_LINE ); + // + // glUseProgram( state->test_outline_shader ); + // glUniformMatrix4fv( state->test_outline_un_vp, 1, GL_FALSE, glm::value_ptr( VP ) ); + // immediate_render( &imm, state->test_outline_at_position, state->test_outline_at_colour ); + // glUseProgram( 0 ); + + skybox_render( &state->skybox, state->angles ); + + // benchmark_print_timers(); +}