]> git.tdb.fi Git - libs/gl.git/commitdiff
Use different heuristics for applying shader data
authorMikko Rasa <tdb@tdb.fi>
Sat, 14 Apr 2018 22:13:56 +0000 (01:13 +0300)
committerMikko Rasa <tdb@tdb.fi>
Sat, 14 Apr 2018 22:13:56 +0000 (01:13 +0300)
Since later shdata can override values from earlier ones, the stack must
be replayed even if items are only removed.  However we can detect if the
exact same items are added back as might happen when multiple objects
using the same technique are rendered in succession.

source/renderer.cpp
source/renderer.h

index c3a6923f17338cb51d4221f02f6aa158e07fa0fe..76ac5846f2aad1e9417780e39d87f3c816a81088 100644 (file)
@@ -24,7 +24,6 @@ namespace GL {
 Renderer::Renderer(const Camera *c):
        changed(0),
        matrices_loaded(false),
-       shdata_applied(0),
        state_stack(1)
 {
        state_stack.reserve(16);
@@ -125,9 +124,16 @@ void Renderer::set_shader_program(const Program *p, const ProgramData *d)
 
 void Renderer::add_shader_data(const ProgramData &d)
 {
-       shdata_stack.push_back(&d);
-       state->shdata_count = shdata_stack.size();
-       changed |= SHADER_DATA;
+       if(state->shdata_count<shdata_stack.size() && shdata_stack[state->shdata_count]==&d)
+               ++state->shdata_count;
+       else
+       {
+               if(shdata_stack.size()>state->shdata_count)
+                       shdata_stack.erase(shdata_stack.begin()+state->shdata_count, shdata_stack.end());
+               shdata_stack.push_back(&d);
+               state->shdata_count = shdata_stack.size();
+               changed |= SHADER_DATA;
+       }
 }
 
 void Renderer::set_mesh(const Mesh *m)
@@ -161,12 +167,6 @@ void Renderer::pop_state()
        const Clipping *old_clipping = state->clipping;
        state_stack.pop_back();
        state = &state_stack.back();
-       if(shdata_stack.size()>state->shdata_count)
-       {
-               shdata_stack.erase(shdata_stack.begin()+state->shdata_count, shdata_stack.end());
-               changed |= SHADER_DATA;
-       }
-       shdata_applied = min<unsigned>(shdata_applied, shdata_stack.size());
        changed |= MATRIX;
        bool camera_changed = (state->camera!=old_camera);
        if(camera_changed)
@@ -343,15 +343,15 @@ void Renderer::apply_state()
                        }
                }
 
-               if((changed&SHADER_DATA) || shprog_changed)
+               bool extra_shdata = (shdata_stack.size()>state->shdata_count);
+
+               if((changed&SHADER_DATA) || shprog_changed || extra_shdata)
                {
-                       vector<const ProgramData *>::const_iterator i = shdata_stack.begin();
-                       if(!shprog_changed)
-                               i += shdata_applied;
-                       for(; i!=shdata_stack.end(); ++i)
+                       if(extra_shdata)
+                               shdata_stack.erase(shdata_stack.begin()+state->shdata_count, shdata_stack.end());
+                       for(vector<const ProgramData *>::const_iterator i=shdata_stack.begin(); i!=shdata_stack.end(); ++i)
                                (*i)->apply();
                        changed &= ~SHADER_DATA;
-                       shdata_applied = shdata_stack.size();
                }
        }
        else
index 79557eab20b5e368c65be3b50d021cbb124d32a6..af4bd65b594beb85c53bf76905e47698fb577f07 100644 (file)
@@ -98,7 +98,6 @@ private:
 
        unsigned char changed;
        bool matrices_loaded;
-       unsigned shdata_applied;
        std::vector<State> state_stack;
        State *state;
        ProgramData standard_shdata;