stuff
[carveJwlIkooP6JGAAIwe30JlM.git] / gate.h
diff --git a/gate.h b/gate.h
index 9350d2be13996cfad60ff146cad927fa87d51b61..7088c7dc5c236dc03223e5b3948904a6011278d0 100644 (file)
--- a/gate.h
+++ b/gate.h
@@ -6,15 +6,28 @@
 #include "model.h"
 #include "render.h"
 #include "shaders/gate.h"
+#include "shaders/gatelq.h"
+#include "water.h"
 
 typedef struct teleport_gate teleport_gate;
 
 static struct
 {
-   GLuint fb, rgb, rb;
+   struct framebuffer fb;
    glmesh mdl;
+
+   int high_qual; /* If in high performance mode, we don't use RT's, and
+                      instead use stencil buffers.
+                      There is therefore no heat warp effect. */
 }
-grender;
+grender =
+{
+   .high_qual = 0,
+   .fb = {
+      .format = GL_RGB,
+      .div = 1
+   }
+};
 
 struct teleport_gate
 { 
@@ -42,11 +55,12 @@ static void gate_transform_update( teleport_gate *gate )
 static void gate_register(void)
 {
    shader_gate_register();
+   shader_gatelq_register();
 }
 
 static void gate_init(void)
 {
-   create_renderbuffer_std( &grender.fb, &grender.rgb, &grender.rb );
+   fb_init( &grender.fb );
 
    model *mgate = vg_asset_read( "models/rs_gate.mdl" );
    model_unpack( mgate, &grender.mdl );
@@ -55,7 +69,7 @@ static void gate_init(void)
 
 static void gate_fb_resize(void)
 {
-   resize_renderbuffer_std( &grender.fb, &grender.rgb, &grender.rb );
+   fb_resize( &grender.fb );
 }
 
 static void render_gate( teleport_gate *gate, m4x3f camera )
@@ -70,6 +84,9 @@ static void render_gate( teleport_gate *gate, m4x3f camera )
    if( v3_dot(v0, gatedir) >= 0.0f )
       return;
 
+   if( v3_dist( viewpos, gate->co[0] ) > 100.0f )
+      return;
+
    v3f a,b,c,d;
 
    float sx = gate->dims[0],
@@ -91,10 +108,10 @@ static void render_gate( teleport_gate *gate, m4x3f camera )
    
    vg_line_pt3( cam_new[3], 0.3f, 0xff00ff00 );
 
-   glBindFramebuffer( GL_FRAMEBUFFER, grender.fb );
-   glClearColor( 0.11f, 0.35f, 0.37f, 1.0f );
-   glClear( GL_COLOR_BUFFER_BIT|GL_DEPTH_BUFFER_BIT );
-
+   m4x3f gate_xform;
+   m4x3_copy( gate->to_world, gate_xform );
+   m4x3_scalev( gate_xform, (v3f){ gate->dims[0], gate->dims[1], 1.0f } );
+   
    m4x3f inverse;
    m4x3_invert_affine( cam_new, inverse );
 
@@ -107,47 +124,88 @@ static void render_gate( teleport_gate *gate, m4x3f camera )
 
    m4x4f projection;
    pipeline_projection( projection, 0.1f, 900.0f );
-
    
    m4x3_mulp( inverse, surface, surface );
    surface[3] = -fabsf(surface[3]);
    plane_clip_projection( projection, surface );
 
    m4x4_mul( projection, view, projection );
-   
+
+   if( grender.high_qual )
+   {
+      fb_use( &grender.fb );
+      glClearColor( 0.11f, 0.35f, 0.37f, 1.0f );
+      glClear( GL_COLOR_BUFFER_BIT|GL_DEPTH_BUFFER_BIT );
+   }
+   else
+   {
+      shader_gatelq_use();
+      shader_gatelq_uPv( vg_pv );
+      shader_gatelq_uMdl( gate_xform );
+      shader_gatelq_uCam( viewpos );
+      shader_gatelq_uTime( vg_time*0.25f );
+      shader_gatelq_uInvRes( (v2f){
+            1.0f / (float)vg_window_x,
+            1.0f / (float)vg_window_y });
+
+      glEnable( GL_STENCIL_TEST );
+      glStencilOp( GL_KEEP, GL_KEEP, GL_REPLACE );  
+      glStencilFunc( GL_ALWAYS, 1, 0xFF ); 
+      glStencilMask( 0xFF );
+
+      mesh_bind( &grender.mdl );
+      mesh_draw( &grender.mdl );
+
+      glClear( GL_DEPTH_BUFFER_BIT );
+      glStencilFunc( GL_EQUAL, 1, 0xFF );
+      glStencilMask( 0x00 ); 
+   }
+
    render_world( projection, cam_new );
-   render_water_texture( cam_new );
-   glBindFramebuffer( GL_FRAMEBUFFER, grender.fb );
-   render_water_surface( projection );
-   glBindFramebuffer( GL_FRAMEBUFFER, 0 );
-
-   shader_gate_use();
-
-   m4x3f full;
-   m4x3_copy( gate->to_world, full );
-   m4x3_scalev( full, (v3f){ gate->dims[0], gate->dims[1], 1.0f } );
-
-   shader_gate_uPv( vg_pv );
-   shader_gate_uMdl( full );
-
-   glActiveTexture( GL_TEXTURE0 );
-   glBindTexture( GL_TEXTURE_2D, grender.rgb );
-   shader_gate_uCam( viewpos );
-   shader_gate_uTexMain( 0 );
-   shader_gate_uTexWater( 1 );
-   shader_gate_uTime( vg_time*0.25f );
-   shader_gate_uInvRes( (v2f){
-         1.0f / (float)vg_window_x,
-         1.0f / (float)vg_window_y });
    
-   glEnable(GL_BLEND);
-   glBlendFunc(GL_SRC_ALPHA,GL_ONE_MINUS_SRC_ALPHA);
-   glBlendEquation(GL_FUNC_ADD);
+   if( grender.high_qual )
+   {
+      /*
+       * TODO: Need to find a way to draw a stencil buffer into the water 
+       *       rendering 
+       */
+
+      render_water_texture( cam_new );
+      fb_use( &grender.fb );
+
+      render_water_surface( projection, cam_new );
+      fb_use( NULL );
+
+      shader_gate_use();
 
-   mesh_bind( &grender.mdl );
-   mesh_draw( &grender.mdl );
+      shader_gate_uPv( vg_pv );
+      shader_gate_uMdl( gate_xform );
 
-   glDisable(GL_BLEND);
+      fb_bindtex( &grender.fb, 0 );
+
+      shader_gate_uCam( viewpos );
+      shader_gate_uTexMain( 0 );
+      shader_gate_uTexWater( 1 );
+      shader_gate_uTime( vg_time*0.25f );
+      shader_gate_uInvRes( (v2f){
+            1.0f / (float)vg_window_x,
+            1.0f / (float)vg_window_y });
+      
+      glEnable(GL_BLEND);
+      glBlendFunc(GL_SRC_ALPHA,GL_ONE_MINUS_SRC_ALPHA);
+      glBlendEquation(GL_FUNC_ADD);
+
+      mesh_bind( &grender.mdl );
+      mesh_draw( &grender.mdl );
+
+      glDisable(GL_BLEND);
+   }
+   else
+   {
+      glStencilMask( 0xFF );
+      glStencilFunc( GL_ALWAYS, 1, 0xFF );
+      glDisable( GL_STENCIL_TEST );
+   }
 }
 
 static int gate_intersect( teleport_gate *gate, v3f pos, v3f last )