Exemplo n.º 1
0
/*
 * Render all states in the ShaderCache along with their renderables. This
 * is where the actual OpenGL rendering starts.
 */
void OpenGLRenderSystem::render(RenderStateFlags globalstate,
                               const Matrix4& modelview,
                               const Matrix4& projection,
                               const Vector3& viewer)
{
	glPushAttrib(GL_ALL_ATTRIB_BITS);

	// Set the projection and modelview matrices
	glMatrixMode(GL_PROJECTION);
	glLoadMatrixd(projection);

	glMatrixMode(GL_MODELVIEW);
	glLoadMatrixd(modelview);

	// global settings that are not set in renderstates
    glFrontFace(GL_CW);
    glCullFace(GL_BACK);
    glPolygonOffset(-1, 1);

	// Set polygon stipple pattern from constant
	glPolygonStipple(POLYGON_STIPPLE_PATTERN);

    glEnableClientState(GL_VERTEX_ARRAY);
    glColorMaterial(GL_FRONT_AND_BACK, GL_AMBIENT_AND_DIFFUSE);

    if (GLEW_VERSION_1_3) {
		glActiveTexture(GL_TEXTURE0);
		glClientActiveTexture(GL_TEXTURE0);
    }

    if (GLEW_ARB_shader_objects) {
		glUseProgramObjectARB(0);
		glDisableVertexAttribArrayARB(c_attr_TexCoord0);
		glDisableVertexAttribArrayARB(c_attr_Tangent);
		glDisableVertexAttribArrayARB(c_attr_Binormal);
    }

    if (globalstate & RENDER_TEXTURE_2D) {
		glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
		glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);
    }

	// Construct default OpenGL state
	OpenGLState current;

    // Set up initial GL state. This MUST MATCH the defaults in the OpenGLState
    // object, otherwise required state changes may not occur.
    glLineStipple(current.m_linestipple_factor,
    			  current.m_linestipple_pattern);
    glPolygonMode(GL_FRONT_AND_BACK, GL_LINE);
    glDisable(GL_LIGHTING);
    glDisable(GL_TEXTURE_2D);
    glDisableClientState(GL_TEXTURE_COORD_ARRAY);
    glDisableClientState(GL_COLOR_ARRAY);
    glDisableClientState(GL_NORMAL_ARRAY);
    glDisable(GL_BLEND);
    glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE);
    glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
    glDisable(GL_CULL_FACE);
    glShadeModel(GL_FLAT);
    glDisable(GL_DEPTH_TEST);

    // RENDER_DEPTHWRITE defaults to 0
    glDepthMask(GL_FALSE);

    // RENDER_MASKCOLOUR defaults to 0
    glColorMask(GL_TRUE, GL_TRUE, GL_TRUE, GL_TRUE);

    glDisable(GL_ALPHA_TEST);

    glDisable(GL_LINE_STIPPLE);
    glDisable(GL_POLYGON_STIPPLE);
    glDisable(GL_POLYGON_OFFSET_LINE);
	glDisable(GL_POLYGON_OFFSET_FILL); // greebo: otherwise tiny gap lines between brushes are visible

    glBindTexture(GL_TEXTURE_2D, 0);
    glColor4f(1,1,1,1);
    glDepthFunc(current.getDepthFunc());
    glAlphaFunc(GL_ALWAYS, 0);
    glLineWidth(1);
    glPointSize(1);

	glHint(GL_FOG_HINT, GL_NICEST);
    glDisable(GL_FOG);

#if 0
	std::size_t count = 0 ;

	for (OpenGLStates::iterator i = _state_sorted.begin();
		i != _state_sorted.end();
		++i)
	{
		// Render the OpenGLShaderPass
		if (!i->second->empty())
		{
			count++;
		}
	}

	rMessage() << "R1 " << count << " of " << _state_sorted.size() << "\n";

	std::size_t curObject = 0;
#endif

    // Iterate over the sorted mapping between OpenGLStates and their
    // OpenGLShaderPasses (containing the renderable geometry), and render the
    // contents of each bucket. Each pass is passed a reference to the "current"
    // state, which it can change.
	for (OpenGLStates::iterator i = _state_sorted.begin();
		i != _state_sorted.end();
		++i)
	{
		// Render the OpenGLShaderPass
        if (!i->second->empty())
        {
#if 0
			rMessage() << curObject << " " << (*i->second);
			curObject++;
#endif

            i->second->render(current, globalstate, viewer, _time);
        }
	}

	glPopAttrib();
}