Exemple #1
0
void DynamicSkyLight::SetLightParams(float4 newLightDir, float startAngle, float orbitTime) {
	newLightDir.ANormalize();

	sunStartAngle = PI + startAngle; //FIXME WHY +PI?
	sunOrbitTime = orbitTime;
	initialSunAngle = GetRadFromXY(newLightDir.x, newLightDir.z);

	//FIXME This function really really needs comments about what it does!
	if (newLightDir.w == FLT_MAX) {
		// old: newLightDir is position where sun reaches highest altitude
		const float sunLen = newLightDir.Length2D();
		const float sunAzimuth = (sunLen <= 0.001f) ? PI / 2.0f : atan(newLightDir.y / sunLen);
		const float sunHeight = tan(sunAzimuth - 0.001f);

		float3 v1(cos(initialSunAngle), sunHeight, sin(initialSunAngle));
		v1.ANormalize();

		if (v1.y <= orbitMinSunHeight) {
			newLightDir = UpVector;
			sunOrbitHeight = v1.y;
			sunOrbitRad = sqrt(1.0f - sunOrbitHeight * sunOrbitHeight);
		} else {
			float3 v2(cos(initialSunAngle + PI), orbitMinSunHeight, sin(initialSunAngle + PI));
			v2.ANormalize();
			float3 v3 = v2 - v1;
			sunOrbitRad = v3.Length() / 2.0f;
			v3.ANormalize();

			float3 v4 = (v3.cross(UpVector)).ANormalize();
			float3 v5 = (v3.cross(v4)).ANormalize();

			if (v5.y < 0.0f)
				v5 = -v5;

			newLightDir = v5;
			sunOrbitHeight = v5.dot(v1);
		}
	} else {
		// new: newLightDir is center position of orbit, and newLightDir.w is orbit height
		sunOrbitHeight = std::max(-1.0f, std::min(newLightDir.w, 1.0f));
		sunOrbitRad = sqrt(1.0f - sunOrbitHeight * sunOrbitHeight);
	}

	sunRotation.LoadIdentity();
	sunRotation.SetUpVector(newLightDir);

	const float4& peakDir  = CalculateSunPos(0.0f);
	const float peakElev   = std::max(0.01f, peakDir.y);

	shadowDensityFactor = 1.0f / peakElev;

	SetLightDir(CalculateSunPos(sunStartAngle).ANormalize());
}
void CDecalsDrawerGL4::CreateBuildingDecal(const CSolidObject* object)
{
	const SolidObjectDecalDef& decalDef = object->GetDef()->decalDef;
	if (!decalDef.useGroundDecal)
		return;

	const int sizex = decalDef.groundDecalSizeX;
	const int sizey = decalDef.groundDecalSizeY;

	Decal d;
	d.pos   = object->pos;
	d.rot   = GetRadFromXY(object->frontdir.x, object->frontdir.z) - fastmath::HALFPI;
	d.size  = float2(sizex * SQUARE_SIZE, sizey * SQUARE_SIZE);
	d.alpha = 1.0f;
	d.alphaFalloff = decalDef.groundDecalDecaySpeed;
	d.SetTexture(decalDef.groundDecalTypeName);
	d.type  = Decal::BUILDING;
	d.owner = object;
	d.generation = gs->frameNum;

	NewDecal(d);
}