예제 #1
0
void TerrainTextureOverlay::RenderAfterWater()
{
	CTerrain* terrain = g_Game->GetWorld()->GetTerrain();

	ssize_t w = (ssize_t)(terrain->GetTilesPerSide() * m_TexelsPerTile);
	ssize_t h = (ssize_t)(terrain->GetTilesPerSide() * m_TexelsPerTile);

	pglActiveTextureARB(GL_TEXTURE0);

	// Recreate the texture with new size if necessary
	if (round_up_to_pow2(w) != m_TextureW || round_up_to_pow2(h) != m_TextureH)
	{
		m_TextureW = round_up_to_pow2(w);
		m_TextureH = round_up_to_pow2(h);

		glBindTexture(GL_TEXTURE_2D, m_Texture);
		glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, m_TextureW, m_TextureH, 0, GL_RGBA, GL_UNSIGNED_BYTE, NULL);

		glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
		glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
		glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
		glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
	}

	u8* data = (u8*)calloc(w * h, 4);
	BuildTextureRGBA(data, w, h);

	glBindTexture(GL_TEXTURE_2D, m_Texture);
	glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, w, h, GL_RGBA, GL_UNSIGNED_BYTE, data);

	free(data);

	CMatrix3D matrix;
	matrix.SetZero();
	matrix._11 = m_TexelsPerTile / (m_TextureW * TERRAIN_TILE_SIZE);
	matrix._23 = m_TexelsPerTile / (m_TextureH * TERRAIN_TILE_SIZE);
	matrix._44 = 1;

	g_Renderer.GetTerrainRenderer().RenderTerrainOverlayTexture(matrix);
}
예제 #2
0
///////////////////////////////////////////////////////////////////////////////////////////////////
// CalcShadowMatrices: calculate required matrices for shadow map generation - the light's
// projection and transformation matrices
void ShadowMapInternals::CalcShadowMatrices()
{
	CRenderer& renderer = g_Renderer;

	float minZ = ShadowBound[0].Z;

	ShadowBound.IntersectFrustumConservative(LightspaceCamera.GetFrustum());

	// round off the shadow boundaries to sane increments to help reduce swim effect
	float boundInc = 16.0f;
	ShadowBound[0].X = floor(ShadowBound[0].X / boundInc) * boundInc;
	ShadowBound[0].Y = floor(ShadowBound[0].Y / boundInc) * boundInc;
	ShadowBound[1].X = ceil(ShadowBound[1].X / boundInc) * boundInc;
	ShadowBound[1].Y = ceil(ShadowBound[1].Y / boundInc) * boundInc;

	// minimum Z bound must not be clipped too much, because objects that lie outside
	// the shadow bounds cannot cast shadows either
	// the 2.0 is rather arbitrary: it should be big enough so that we won't accidently miss
	// a shadow generator, and small enough not to affect Z precision
	ShadowBound[0].Z = minZ - 2.0;

	// Setup orthogonal projection (lightspace -> clip space) for shadowmap rendering
	CVector3D scale = ShadowBound[1] - ShadowBound[0];
	CVector3D shift = (ShadowBound[1] + ShadowBound[0]) * -0.5;

	if (scale.X < 1.0)
		scale.X = 1.0;
	if (scale.Y < 1.0)
		scale.Y = 1.0;
	if (scale.Z < 1.0)
		scale.Z = 1.0;

	scale.X = 2.0 / scale.X;
	scale.Y = 2.0 / scale.Y;
	scale.Z = 2.0 / scale.Z;

	// make sure a given world position falls on a consistent shadowmap texel fractional offset
	float offsetX = fmod(ShadowBound[0].X - LightTransform._14, 2.0f/(scale.X*EffectiveWidth));
	float offsetY = fmod(ShadowBound[0].Y - LightTransform._24, 2.0f/(scale.Y*EffectiveHeight));

	LightProjection.SetZero();
	LightProjection._11 = scale.X;
	LightProjection._14 = (shift.X + offsetX) * scale.X;
	LightProjection._22 = scale.Y;
	LightProjection._24 = (shift.Y + offsetY) * scale.Y;
	LightProjection._33 = scale.Z;
	LightProjection._34 = shift.Z * scale.Z + renderer.m_ShadowZBias;
	LightProjection._44 = 1.0;


	// Calculate texture matrix by creating the clip space to texture coordinate matrix
	// and then concatenating all matrices that have been calculated so far
	CMatrix3D lightToTex;
	float texscalex = scale.X * 0.5f * (float)EffectiveWidth / (float)Width;
	float texscaley = scale.Y * 0.5f * (float)EffectiveHeight / (float)Height;
	float texscalez = scale.Z * 0.5f;

	lightToTex.SetZero();
	lightToTex._11 = texscalex;
	lightToTex._14 = (offsetX - ShadowBound[0].X) * texscalex;
	lightToTex._22 = texscaley;
	lightToTex._24 = (offsetY - ShadowBound[0].Y) * texscaley;
	lightToTex._33 = texscalez;
	lightToTex._34 = -ShadowBound[0].Z * texscalez;
	lightToTex._44 = 1.0;

	TextureMatrix = lightToTex * LightTransform;
}