#include <algorithm>
-#include <msp/gl/extensions/arb_occlusion_query.h>
-#include <msp/gl/extensions/arb_occlusion_query2.h>
#include "camera.h"
#include "occludedscene.h"
#include "renderer.h"
OccludedScene::OccludedScene():
bounding_mesh(Resources::get_global().get<Mesh>("_occluder.mesh")),
bounding_shader(Resources::get_global().get<Program>("_occluder.glsl.shader")),
+ no_depth_write(LEQUAL, false),
occluder_min_size(0.25f),
+ queries(OCCLUSION_QUERY, 0),
cache_dirty(false)
{
- static Require req(ARB_occlusion_query);
- static Require req2(ARB_occlusion_query2);
-}
-
-OccludedScene::~OccludedScene()
-{
- vector<unsigned> queries;
- queries.reserve(occluded_cache.size());
- for(OccludedRenderable &o: occluded_cache)
- queries.push_back(o.query);
- glDeleteQueries(queries.size(), &queries[0]);
+ no_color_write.write_mask = WRITE_NONE;
}
void OccludedScene::add(Renderable &r)
if(!cache_dirty)
return;
+ if(queries.get_size()<renderables.size())
+ queries.resize(renderables.size());
if(occluded_cache.size()<renderables.size())
- {
- unsigned old_size = occluded_cache.size();
occluded_cache.resize(renderables.size());
- vector<unsigned> new_queries(occluded_cache.size()-old_size);
- glGenQueries(new_queries.size(), &new_queries[0]);
- for(unsigned i=0; i<new_queries.size(); ++i)
- occluded_cache[old_size+i].query = new_queries[i];
- }
auto j = occluded_cache.begin();
for(Renderable *r: renderables)
Renderer::Push push(renderer);
renderer.set_shader_program(&bounding_shader);
- glColorMask(false, false, false, false);
- glDepthMask(false);
+ renderer.set_blend(&no_color_write);
+ // XXX Preserve existing depth test predicate
+ renderer.set_depth_test(&no_depth_write);
// Fire off the occlusion queries
for(auto i=occluded_cache.begin(); (i!=occluded_cache.end() && i->in_frustum); ++i)
if(!i->occluder)
{
- glBeginQuery(GL_ANY_SAMPLES_PASSED, i->query);
+ QueryPool::Activate activate_query(renderer, queries, i-occluded_cache.begin());
Renderer::Push push2(renderer);
renderer.transform(Matrix(*i->renderable->get_matrix())
.translate(i->bounding_sphere->get_center())
.scale(i->bounding_sphere->get_radius()));
bounding_mesh.draw(renderer);
- glEndQuery(GL_ANY_SAMPLES_PASSED);
}
-
- glColorMask(true, true, true, true);
- glDepthMask(true);
}
// Render anything that has a chance of being visible
for(auto i=occluded_cache.begin(); (i!=occluded_cache.end() && i->in_frustum); ++i)
- if(!i->occluder)
- {
- unsigned any_passed = 0;
- glGetQueryObjectuiv(i->query, GL_QUERY_RESULT, &any_passed);
- if(any_passed)
- renderer.render(*i->renderable, tag);
- }
+ if(!i->occluder && queries.get_result(i-occluded_cache.begin()))
+ renderer.render(*i->renderable, tag);
}
renderable(0),
bounding_sphere(0),
in_frustum(false),
- occluder(false),
- query(0)
+ occluder(false)
{ }
} // namespace GL