//=========================================================
// loadtexture
// - load a texture based on glaux load bitmap
//---------------------------------------------------------
void LoadTexture(char *filename)
{
	AUX_RGBImageRec *textureimage[1];	// create space for texture
	memset(textureimage, 0, sizeof(void *)*1);	// set ptr to NULL

	// load the bitmap, from the file
	if (textureimage[0] = LoadBitmap(filename))
	{
		// Bind the texture
		glBindTexture(GL_TEXTURE_2D, GetTexture(textureindex));
		glTexImage2D(GL_TEXTURE_2D, 0, 3, textureimage[0]->sizeX,
			textureimage[0]->sizeY, 0, GL_RGB, GL_UNSIGNED_BYTE, textureimage[0]->data);
		glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
		glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);

	} // end of the if

	if (textureimage[0])
	{
		if (textureimage[0]->data)
		{
			free(textureimage[0]->data);		// free up the allocated memory
		} // end of the if

		free(textureimage[0]);		// free the entire struct

	} // end of the if

	NextTexture();

} // end of the function
Esempio n. 2
0
void FGLRenderBuffers::RenderEffect(const FString &name)
{
	if (hw_postprocess.Effects[name].Size() == 0)
		return;

	FGLDebug::PushGroup(name.GetChars());

	FGLPostProcessState savedState;

	for (const PPStep &step : hw_postprocess.Effects[name])
	{
		// Bind input textures
		for (unsigned int index = 0; index < step.Textures.Size(); index++)
		{
			savedState.SaveTextureBindings(index + 1);

			const PPTextureInput &input = step.Textures[index];
			int filter = (input.Filter == PPFilterMode::Nearest) ? GL_NEAREST : GL_LINEAR;
			int wrap = (input.Wrap == PPWrapMode::Clamp) ? GL_CLAMP : GL_REPEAT;

			switch (input.Type)
			{
			default:
			case PPTextureType::CurrentPipelineTexture:
				BindCurrentTexture(index, filter, wrap);
				break;

			case PPTextureType::NextPipelineTexture:
				I_FatalError("PPTextureType::NextPipelineTexture not allowed as input\n");
				break;

			case PPTextureType::PPTexture:
				GLTextures[input.Texture].Bind(index, filter, wrap);
				break;

			case PPTextureType::SceneColor:
				BindSceneColorTexture(index);
				break;

			case PPTextureType::SceneFog:
				BindSceneFogTexture(index);
				break;

			case PPTextureType::SceneNormal:
				BindSceneNormalTexture(index);
				break;

			case PPTextureType::SceneDepth:
				BindSceneDepthTexture(index);
				break;
			}
		}

		// Set render target
		switch (step.Output.Type)
		{
		default:
			I_FatalError("Unsupported postprocess output type\n");
			break;

		case PPTextureType::CurrentPipelineTexture:
			BindCurrentFB();
			break;

		case PPTextureType::NextPipelineTexture:
			BindNextFB();
			break;

		case PPTextureType::PPTexture:
			if (GLTextureFBs[step.Output.Texture])
				GLTextureFBs[step.Output.Texture].Bind();
			else
				GLTextureFBs[step.Output.Texture] = CreateFrameBuffer(step.Output.Texture.GetChars(), GLTextures[step.Output.Texture]);
			break;

		case PPTextureType::SceneColor:
			BindSceneFB(false);
			break;
		}

		// Set blend mode
		if (step.BlendMode.BlendOp == STYLEOP_Add && step.BlendMode.SrcAlpha == STYLEALPHA_One && step.BlendMode.DestAlpha == STYLEALPHA_Zero && step.BlendMode.Flags == 0)
		{
			glDisable(GL_BLEND);
		}
		else
		{
			// To do: support all the modes
			glEnable(GL_BLEND);
			glBlendEquation(GL_FUNC_ADD);
			if (step.BlendMode.SrcAlpha == STYLEALPHA_One && step.BlendMode.DestAlpha == STYLEALPHA_One)
				glBlendFunc(GL_ONE, GL_ONE);
			else
				glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
		}

		// Setup viewport
		glViewport(step.Viewport.left, step.Viewport.top, step.Viewport.width, step.Viewport.height);

		auto &shader = GLShaders[step.ShaderName];

		// Set uniforms
		if (step.Uniforms.Data.Size() > 0)
		{
			if (!shader->Uniforms)
				shader->Uniforms.reset(screen->CreateDataBuffer(POSTPROCESS_BINDINGPOINT, false));
			shader->Uniforms->SetData(step.Uniforms.Data.Size(), step.Uniforms.Data.Data());
			shader->Uniforms->BindBase();
		}

		// Set shader
		shader->Bind(NOQUEUE);

		// Draw the screen quad
		GLRenderer->RenderScreenQuad();

		// Advance to next PP texture if our output was sent there
		if (step.Output.Type == PPTextureType::NextPipelineTexture)
			NextTexture();
	}

	glViewport(screen->mScreenViewport.left, screen->mScreenViewport.top, screen->mScreenViewport.width, screen->mScreenViewport.height);

	FGLDebug::PopGroup();
}