From: hgn Date: Sun, 10 Jul 2022 19:53:02 +0000 (+0100) Subject: checkin X-Git-Url: https://skaterift.com/git/?a=commitdiff_plain;h=168eb5c363f510d60703498e01ffcdb52bf9fd07;p=carveJwlIkooP6JGAAIwe30JlM.git checkin --- diff --git a/character.h b/character.h index 59fbdca..c565fc4 100644 --- a/character.h +++ b/character.h @@ -259,11 +259,16 @@ static void character_eval( struct character *ch ) m4x3_mulv( mats[k_chpart_body1], offs[k_chpart_neck], mats[k_chpart_neck][3] ); +#if 1 v4f qhead; q_axis_angle( qhead, (v3f){ 0.0f,1.0f,0.0f }, ch->rhead ); q_m3x3( qhead, mats[k_chpart_head] ); - //m3x3_mul( mats[k_chpart_neck], mats[k_chpart_head], mats[k_chpart_head] ); m4x3_mulv( mats[k_chpart_neck], offs[k_chpart_head], mats[k_chpart_head][3]); + m3x3_mul( mats[k_chpart_neck], mats[k_chpart_head], mats[k_chpart_head] ); +#else + m4x3_mulv( mats[k_chpart_neck], offs[k_chpart_head], mats[k_chpart_head][3]); + m3x3_copy( mats[k_chpart_neck], mats[k_chpart_head] ); +#endif /* Feet */ m3x3_copy( mats[k_chpart_leg_l1], mats[k_chpart_foot_l] ); @@ -538,6 +543,7 @@ static void character_testpose( struct character *ch, float t ) m4x3_identity( ch->matrices[k_chpart_wf] ); } +static float *player_cam_pos(void); static void character_draw( struct character *ch, float temp ) { shader_character_use(); @@ -546,6 +552,8 @@ static void character_draw( struct character *ch, float temp ) vg_tex2d_bind( &tex_pallet, 0 ); shader_character_uTexMain( 0 ); shader_character_uOpacity( temp ); + shader_character_uCamera( player_cam_pos() ); + shader_link_standard_ub( _shader_character.id, 2 ); glEnable( GL_CULL_FACE ); glCullFace( GL_BACK ); @@ -554,6 +562,11 @@ static void character_draw( struct character *ch, float temp ) for( int i=4; imatrices[i] ); submodel_draw( &ch->parts[i] ); } diff --git a/main.c b/main.c index ba6f384..aa90b02 100644 --- a/main.c +++ b/main.c @@ -16,6 +16,7 @@ vg_tex2d tex_water = { .path = "textures/water.qoi" }; /* Convars */ static int debugview = 0; static int sv_debugcam = 0; +static int lightedit = 0; /* Components */ #include "road.h" @@ -104,6 +105,14 @@ void vg_start(void) .persistent = 1 }); + vg_convar_push( (struct vg_convar){ + .name = "ledit", + .data = &lightedit, + .data_type = k_convar_dtype_i32, + .opt_i32 = { .min=0, .max=1, .clamp=1 }, + .persistent = 1 + }); + vg_convar_push( (struct vg_convar){ .name = "walk_speed", .data = &k_walkspeed, @@ -137,7 +146,7 @@ void vg_start(void) init_other(); - character_load( &player.mdl, "ch_default" ); + character_load( &player.mdl, "ch_mike" ); character_init_ragdoll( &player.mdl ); world_load(); @@ -226,7 +235,14 @@ void vg_render(void) glClear( GL_COLOR_BUFFER_BIT|GL_DEPTH_BUFFER_BIT ); else glClear( GL_COLOR_BUFFER_BIT ); - + + if( !player.is_dead ) + { + m4x4_projection( vg_pv, gpipeline.fov, + (float)vg_window_x / (float)vg_window_y, + 0.01f, 100.0f ); + m4x4_mul( vg_pv, world_4x4, vg_pv ); + } draw_player(); /* Draw back in the background @@ -253,10 +269,29 @@ void vg_render(void) glViewport( 0,0, vg_window_x, vg_window_y ); } +static void run_light_widget( struct light_widget *lw ) +{ + struct ui_checkbox c1 = { .data=&lw->enabled }; + + ui_checkbox( &ui_global_ctx, &c1 ); + + if( lw->enabled ) + { + struct ui_slider_vector + colour = { .min=0.0f, .max=2.0f, .len=3, .data=lw->colour }, + dir = { .min=-VG_PIf, .max=VG_PIf, .len=2, .data=lw->dir }; + + ui_slider_vector( &ui_global_ctx, &colour ); + ui_global_ctx.cursor[1] += 4; + ui_slider_vector( &ui_global_ctx, &dir ); + } +} + void vg_ui(void) { char buf[20]; +#if 0 snprintf( buf, 20, "%.2fm/s", v3_length( player.v ) ); gui_text( (ui_px [2]){ 0, 0 }, buf, 1, k_text_align_left ); @@ -281,4 +316,40 @@ void vg_ui(void) gui_text( (ui_px [2]){ 0, 60 }, "Gamepad not ready", 1, k_text_align_left ); } +#endif + + if( lightedit ) + { + ui_global_ctx.cursor[0] = 10; + ui_global_ctx.cursor[1] = 10; + ui_global_ctx.cursor[2] = 200; + ui_global_ctx.cursor[3] = 20; + + struct ub_world_lighting *wl = &gpipeline.ub_world_lighting; + struct ui_slider_vector + s5 = { .min=0.0f, .max=2.0f, .len=3, .data=wl->g_ambient_colour }; + + struct ui_slider + s8 = { .min=0.0f, .max=2.0f, .data = &gpipeline.shadow_spread }, + s9 = { .min=0.0f, .max=25.0f, .data = &gpipeline.shadow_length }; + + for( int i=0; i<3; i++ ) + run_light_widget( &gpipeline.widgets[i] ); + + gui_text( ui_global_ctx.cursor, "Ambient", 1, 0 ); + ui_global_ctx.cursor[1] += 16; + ui_slider_vector( &ui_global_ctx, &s5 ); + + gui_text( ui_global_ctx.cursor, "Shadows", 1, 0 ); + ui_global_ctx.cursor[1] += 16; + ui_slider( &ui_global_ctx, &s8 ); + ui_slider( &ui_global_ctx, &s9 ); + + gui_text( ui_global_ctx.cursor, "Misc", 1, 0 ); + ui_global_ctx.cursor[1] += 16; + struct ui_checkbox c1 = {.data = &wl->g_light_preview}; + ui_checkbox( &ui_global_ctx, &c1 ); + + render_update_lighting_ub(); + } } diff --git a/player.h b/player.h index 34ed469..3501c72 100644 --- a/player.h +++ b/player.h @@ -21,9 +21,6 @@ static struct gplayer float iY; /* Yaw inertia */ int in_air, is_dead, on_board; - /* Input */ - v2f joy_l; - v2f board_xy; float grab; float pitch; @@ -53,6 +50,11 @@ player = .on_board = 1 }; +static float *player_cam_pos(void) +{ + return player.camera_pos; +} + static void player_transform_update(void) { q_normalize( player.rot ); @@ -88,6 +90,9 @@ static int reset_player( int argc, char const *argv[] ) static void player_mouseview(void) { + if( gui_want_mouse() ) + return; + static v2f mouse_last, view_vel = { 0.0f, 0.0f }; @@ -369,8 +374,8 @@ static void player_physics_ground(void) { vel[2] = stable_force( vel[2], vg_signf( vel[2] ) * fwd_resistance ); - /* This used to be -7.0 */ - vel[0] = stable_force( vel[0], vg_signf( vel[0] ) * -10.0f *substep ); + /* This used to be -7.0, then -10.0 */ + vel[0] = stable_force( vel[0], vg_signf( vel[0] ) * -8.5f *substep ); } static double start_push = 0.0; @@ -398,7 +403,7 @@ static void player_physics_ground(void) player.iY -= 3.6f * ktimestep; float steer = vg_get_axis( "horizontal" ); - player.iY -= vg_signf(steer)*powf(steer,2.0f) * 1.5f * ktimestep; + player.iY -= vg_signf(steer)*powf(steer,2.0f) * 2.5f * ktimestep; /* Too much lean and it starts to look like a snowboard here */ v2_lerp( player.board_xy, (v2f){ slip*0.25f, 0.0f }, @@ -530,9 +535,6 @@ static void player_do_motion(void) float horizontal = vg_get_axis("horizontal"), vertical = vg_get_axis("vertical"); - player.joy_l[0] = vg_signf(horizontal) * powf( horizontal, 2.0f ); - player.joy_l[1] = vg_signf(vertical) * powf( vertical, 2.0f ); - if( player.in_air ) player_physics_air(); @@ -590,7 +592,7 @@ static void player_do_motion(void) player.angles[0] = atan2f( player.vl[0], -player.vl[2] ); player.angles[1] = atan2f( -player.vl[1], sqrtf(player.vl[0]*player.vl[0]+ - player.vl[2]*player.vl[2]) ) * 0.3f; + player.vl[2]*player.vl[2]) ) * 0.7f; } static int player_walkgrid_tri_walkable( u32 tri[3] ) @@ -1605,6 +1607,9 @@ static void player_animate(void) character_pose_reset( &player.mdl ); + /* TODO */ + fstand = 1.0f; + float amt_air = ffly*ffly, amt_ground = 1.0f-amt_air, amt_std = (1.0f-fslide) * amt_ground, @@ -1627,9 +1632,11 @@ static void player_animate(void) character_final_pose( &player.mdl, (v3f){0.0f,0.0f,0.0f}, &pose_fly, amt_air ); +#if 0 static float fupper = 0.0f; fupper = vg_lerpf( fupper, -vg_get_axis("horizontal")*0.2f, 0.1f ); character_yaw_upper( &player.mdl, fupper ); +#endif /* Camera position */ v3_lerp( player.smooth_localcam, player.mdl.cam_pos, 0.08f, @@ -1652,8 +1659,11 @@ static void player_animate(void) v3f localv; m3x3_mulv( player.to_local, player.v, localv ); + +#if 0 v3_muladds( arm_l->end, localv, -0.01f, arm_l->end ); v3_muladds( arm_r->end, localv, -0.01f, arm_r->end ); +#endif /* New board transformation */ v4f board_rotation; v3f board_location; @@ -1737,8 +1747,9 @@ static void player_animate(void) /* Head rotation */ static float rhead = 0.0f; + static const float klook_max = 0.8f; rhead = vg_lerpf( rhead, - vg_clampf(atan2f( localv[2], -localv[0] ),-1.0f,1.0f), 0.04f ); + vg_clampf( atan2f(localv[2],-localv[0]),-klook_max,klook_max), 0.04f ); player.mdl.rhead = rhead; } @@ -2134,10 +2145,12 @@ static void player_update(void) player_do_motion(); player_animate(); - v3f offs = { -0.35f, 0.0f, 0.0f }; - m3x3_mulv( player.to_world, offs, offs ); + v3f offs = { -0.29f, 0.08f, 0.0f }; + m3x3_mulv( player.to_world, offs, offs ); m4x3_mulv( player.to_world, player.mdl.ik_body.end, player.camera_pos ); - v3_add( offs, player.camera_pos, player.camera_pos ); + //m4x3_mulv( player.mdl.matrices[k_chpart_head], offs, player.camera_pos ); + // v3_copy( player.mdl.matrices[k_chpart_head][3], player.camera_pos ); + v3_add( offs, player.camera_pos, player.camera_pos ); } else { @@ -2151,7 +2164,7 @@ static void player_update(void) /* Update camera matrices */ m4x3_identity( player.camera ); m4x3_rotate_y( player.camera, -player.angles[0] ); - m4x3_rotate_x( player.camera, -0.33f -player.angles[1] ); + m4x3_rotate_x( player.camera, -0.30f -player.angles[1] ); v3_copy( player.camera_pos, player.camera[3] ); m4x3_invert_affine( player.camera, player.camera_inverse ); } diff --git a/render.h b/render.h index 8285317..aa73842 100644 --- a/render.h +++ b/render.h @@ -16,21 +16,61 @@ static struct pipeline struct ub_world_lighting { /* v3f (padded) */ - v4f g_directional, - g_sun_colour, - g_shadow_colour; + v4f g_light_colours[3], + g_light_directions[3], + g_ambient_colour; v4f g_water_plane, g_depth_bounds; + float g_water_fog; + int g_light_count; + int g_light_preview; } ub_world_lighting; + struct light_widget + { + int enabled; + v2f dir; + v3f colour; + } + widgets[3]; + + float shadow_spread, shadow_length; + GLuint fb_depthmap, rgb_depthmap; GLuint ubo_world_lighting, ubo_world; } -gpipeline; +gpipeline = +{ + .widgets = + { + { + .enabled = 1, + .colour = { 1.36f, 1.35f, 1.01f }, + .dir = { 0.63f, -0.08f } + }, + { + .enabled = 1, + .colour = { 0.33f, 0.56f, 0.64f }, + .dir = { -2.60f, -0.13f } + }, + { + .enabled = 1, + .colour = { 0.05f, 0.05f, 0.23f }, + .dir = { 2.60f, -0.84f } + } + }, + .shadow_spread = 0.65f, + .shadow_length = 9.50f, + + .ub_world_lighting = + { + .g_ambient_colour = { 0.09f, 0.03f, 0.07f } + } +}; static void render_water_texture( m4x3f camera ); static void render_water_surface( m4x4f pv, m4x3f camera ); @@ -84,8 +124,32 @@ static void shader_link_standard_ub( GLuint shader, int texture_id ) static void render_update_lighting_ub(void) { - glBindBuffer( GL_UNIFORM_BUFFER, gpipeline.ubo_world_lighting ); + struct ub_world_lighting *winf = &gpipeline.ub_world_lighting; + int c = 0; + for( int i=0; i<3; i++ ) + { + struct light_widget *lw = &gpipeline.widgets[i]; + + if( lw->enabled ) + { + float pitch = lw->dir[0], + yaw = lw->dir[1], + xz = cosf( pitch ); + + v3_copy( (v3f){ xz*cosf(yaw), sinf(pitch), xz*sinf(yaw) }, + winf->g_light_directions[c] ); + v3_copy( lw->colour, winf->g_light_colours[c] ); + + c ++; + } + } + + winf->g_light_count = c; + winf->g_light_directions[0][3] = gpipeline.shadow_length; + winf->g_light_colours[0][3] = gpipeline.shadow_spread; + + glBindBuffer( GL_UNIFORM_BUFFER, gpipeline.ubo_world_lighting ); glBufferSubData( GL_UNIFORM_BUFFER, 0, sizeof(struct ub_world_lighting), &gpipeline.ub_world_lighting ); } diff --git a/shaders/blit.fs b/shaders/blit.fs index b98d5e8..634e84f 100644 --- a/shaders/blit.fs +++ b/shaders/blit.fs @@ -3,7 +3,39 @@ uniform sampler2D uTexMain; in vec2 aUv; +float kPi = 3.14159265358979; + +vec2 fisheye_distort(vec2 xy) +{ + float aperture = 1350.0; + float apertureHalf = 0.5 * aperture * (kPi / 180.0); + float maxFactor = sin(apertureHalf); + + vec2 uv; + float d = length(xy); + if(d < (2.0-maxFactor)) + { + d = length(xy * maxFactor); + float z = sqrt(1.0 - d * d); + float r = atan(d, z) / kPi; + float phi = atan(xy.y, xy.x); + + uv.x = r * cos(phi) + 0.5; + uv.y = r * sin(phi) + 0.5; + } + else + { + uv = 0.5*xy + 0.5; + } + + return uv; +} + + void main() { + vec2 vwarp = 2.0*aUv - 1.0; + vwarp = fisheye_distort( vwarp ); + FragColor = texture( uTexMain, aUv ); } diff --git a/shaders/blit.h b/shaders/blit.h index f05194e..49e4c80 100644 --- a/shaders/blit.h +++ b/shaders/blit.h @@ -27,8 +27,40 @@ static struct vg_shader _shader_blit = { "\n" "in vec2 aUv;\n" "\n" +"float kPi = 3.14159265358979;\n" +"\n" +"vec2 fisheye_distort(vec2 xy)\n" +"{\n" +" float aperture = 1350.0;\n" +" float apertureHalf = 0.5 * aperture * (kPi / 180.0);\n" +" float maxFactor = sin(apertureHalf);\n" +"\n" +" vec2 uv;\n" +" float d = length(xy);\n" +" if(d < (2.0-maxFactor))\n" +" {\n" +" d = length(xy * maxFactor);\n" +" float z = sqrt(1.0 - d * d);\n" +" float r = atan(d, z) / kPi;\n" +" float phi = atan(xy.y, xy.x);\n" +"\n" +" uv.x = r * cos(phi) + 0.5;\n" +" uv.y = r * sin(phi) + 0.5;\n" +" }\n" +" else\n" +" {\n" +" uv = 0.5*xy + 0.5;\n" +" }\n" +" \n" +" return uv;\n" +"}\n" +"\n" +"\n" "void main()\n" "{\n" +" vec2 vwarp = 2.0*aUv - 1.0;\n" +" vwarp = fisheye_distort( vwarp );\n" +"\n" " FragColor = texture( uTexMain, aUv );\n" "}\n" ""}, diff --git a/shaders/character.fs b/shaders/character.fs index d3c2bea..cf62679 100644 --- a/shaders/character.fs +++ b/shaders/character.fs @@ -2,6 +2,7 @@ out vec4 FragColor; uniform sampler2D uTexMain; uniform vec4 uColour; +uniform vec3 uCamera; in vec4 aColour; in vec2 aUv; @@ -9,8 +10,21 @@ in vec3 aNorm; in vec3 aCo; in float aOpacity; +#include "common_world.glsl" + void main() { - vec3 diffuse = texture( uTexMain, aUv ).rgb; - FragColor = vec4(pow(diffuse,vec3(1.0)),aOpacity); + vec3 vfrag = texture( uTexMain, aUv ).rgb; + + // Lighting + vec3 halfview = uCamera - aCo; + float fdist = length( halfview ); + halfview /= fdist; + + //vfrag = do_light_diffuse( vfrag, aNorm ); + vfrag = do_light_spec( vfrag, aNorm, halfview, 0.1 ); + vfrag = do_light_shadowing( vfrag ); + //vfrag = apply_fog( vfrag, fdist ); + + FragColor = vec4(vfrag,aOpacity); } diff --git a/shaders/character.h b/shaders/character.h index 6c3ce7a..83fdff3 100644 --- a/shaders/character.h +++ b/shaders/character.h @@ -29,13 +29,14 @@ static struct vg_shader _shader_character = { "void main()\n" "{\n" " vec3 world_pos = uMdl * vec4(a_co,1.0);\n" -" gl_Position = uPv * vec4(world_pos,1.0);\n" +" vec4 clip_pos = uPv * vec4(world_pos,1.0);\n" +" gl_Position = clip_pos;\n" "\n" " aColour = a_colour;\n" " aUv = a_uv;\n" " aNorm = mat3(uMdl) * a_norm;\n" -" aCo = a_co;\n" -" aOpacity = 1.0-(gl_Position.y+0.5)*uOpacity;\n" +" aCo = world_pos;\n" +" aOpacity = max(clip_pos.w*3.0,0.1);// 1.0-(gl_Position.y+0.5)*uOpacity;\n" "}\n" ""}, .fs = @@ -46,6 +47,7 @@ static struct vg_shader _shader_character = { "\n" "uniform sampler2D uTexMain;\n" "uniform vec4 uColour;\n" +"uniform vec3 uCamera;\n" "\n" "in vec4 aColour;\n" "in vec2 aUv;\n" @@ -53,10 +55,121 @@ static struct vg_shader _shader_character = { "in vec3 aCo;\n" "in float aOpacity;\n" "\n" +"#line 1 1 \n" +"layout (std140) uniform ub_world_lighting\n" +"{\n" +" vec4 g_light_colours[3];\n" +" vec4 g_light_directions[3];\n" +" vec4 g_ambient_colour;\n" +"\n" +" vec4 g_water_plane;\n" +" vec4 g_depth_bounds;\n" +" float g_water_fog;\n" +" int g_light_count;\n" +" int g_light_preview;\n" +"};\n" +"\n" +"uniform sampler2D g_world_depth;\n" +"\n" +"// Standard diffuse + spec models\n" +"// ==============================\n" +"\n" +"vec3 do_light_diffuse( vec3 vfrag, vec3 wnormal )\n" +"{\n" +" vec3 vtotal = g_ambient_colour.rgb;\n" +"\n" +" for( int i=0; ig_directional ); - v3_copy( (v3f){ 1.2f,1.152f,1.08f }, winfo->g_sun_colour ); - v3_copy( (v3f){ 0.15f,0.1f,0.2f }, winfo->g_shadow_colour ); v4_copy( wrender.plane, winfo->g_water_plane ); v4f bounds; @@ -472,8 +466,8 @@ static void render_sky(m4x3f camera) static void render_world( m4x4f projection, m4x3f camera ) { render_sky( camera ); + render_props( projection, camera[3] ); render_terrain( projection, camera[3] ); - /* render props... */ } static void render_world_depth( m4x4f projection, m4x3f camera ) @@ -489,10 +483,12 @@ static void render_world_depth( m4x4f projection, m4x3f camera ) scene_bind( &world.geo ); scene_draw( &world.geo ); +#if 0 glDisable(GL_CULL_FACE); scene_bind( &world.foliage ); scene_draw( &world.foliage ); glEnable(GL_CULL_FACE); +#endif scene_bind( &world.props ); scene_draw( &world.props );