mirror of
https://github.com/Kelsidavis/WoWee.git
synced 2026-03-22 23:30:14 +00:00
Refine sun rendering: remove white washout, add subtle atmospheric turbulence
- render sun with alpha blend while keeping moon additive glow - add dedicated always-running sun haze timer (decoupled from moon phase cycling) - constrain sun sprite with radial alpha mask and low-alpha discard to remove square artifact - tune sun tint warmer without over-yellowing - replace noisy/pulsing haze with slower flow-warp turbulence and lower amplitude
This commit is contained in:
parent
19759d506a
commit
566e7138f3
2 changed files with 61 additions and 9 deletions
|
|
@ -129,6 +129,7 @@ private:
|
|||
float blueChildPhase_ = 0.25f; // 0.0-1.0 (0=new, 0.5=full) - secondary moon
|
||||
bool moonPhaseCycling = true;
|
||||
float moonPhaseTimer = 0.0f; // Fallback for deltaTime mode (development)
|
||||
float sunHazeTimer_ = 0.0f; // Always-running timer for sun haze animation
|
||||
bool dualMoonMode_ = true; // Default: render both moons (Azeroth-specific)
|
||||
|
||||
// WoW lunar cycle constants (in game days)
|
||||
|
|
|
|||
|
|
@ -51,21 +51,56 @@ bool Celestial::initialize() {
|
|||
uniform vec3 celestialColor;
|
||||
uniform float intensity;
|
||||
uniform float moonPhase; // 0.0 = new moon, 0.5 = full moon, 1.0 = new moon
|
||||
uniform float uAnimTime;
|
||||
|
||||
out vec4 FragColor;
|
||||
|
||||
float hash(vec2 p) {
|
||||
return fract(sin(dot(p, vec2(127.1, 311.7))) * 43758.5453);
|
||||
}
|
||||
|
||||
float noise(vec2 p) {
|
||||
vec2 i = floor(p);
|
||||
vec2 f = fract(p);
|
||||
f = f * f * (3.0 - 2.0 * f);
|
||||
float a = hash(i + vec2(0.0, 0.0));
|
||||
float b = hash(i + vec2(1.0, 0.0));
|
||||
float c = hash(i + vec2(0.0, 1.0));
|
||||
float d = hash(i + vec2(1.0, 1.0));
|
||||
return mix(mix(a, b, f.x), mix(c, d, f.x), f.y);
|
||||
}
|
||||
|
||||
void main() {
|
||||
// Create circular disc
|
||||
vec2 center = vec2(0.5, 0.5);
|
||||
float dist = distance(TexCoord, center);
|
||||
|
||||
// Core disc
|
||||
float disc = smoothstep(0.5, 0.4, dist);
|
||||
// Core disc + glow with explicit radial mask to avoid square billboard artifact.
|
||||
float disc = smoothstep(0.50, 0.38, dist);
|
||||
float glow = smoothstep(0.64, 0.00, dist) * 0.24;
|
||||
float radialMask = 1.0 - smoothstep(0.58, 0.70, dist);
|
||||
|
||||
// Glow around disc
|
||||
float glow = smoothstep(0.7, 0.0, dist) * 0.3;
|
||||
float alpha = (disc + glow) * radialMask * intensity;
|
||||
vec3 outColor = celestialColor;
|
||||
|
||||
float alpha = (disc + glow) * intensity;
|
||||
// Very faint animated haze over sun disc/glow (no effect for moon).
|
||||
if (intensity > 0.5) {
|
||||
vec2 uv = (TexCoord - vec2(0.5)) * 3.0;
|
||||
// Slow flow field for atmospheric-like turbulence drift.
|
||||
vec2 flow = vec2(
|
||||
noise(uv * 0.9 + vec2(uAnimTime * 0.012, -uAnimTime * 0.009)),
|
||||
noise(uv * 0.9 + vec2(-uAnimTime * 0.010, uAnimTime * 0.011))
|
||||
) - vec2(0.5);
|
||||
vec2 warped = uv + flow * 0.42;
|
||||
float n1 = noise(warped * 1.7 + vec2(uAnimTime * 0.016, -uAnimTime * 0.013));
|
||||
float n2 = noise(warped * 3.0 + vec2(-uAnimTime * 0.021, uAnimTime * 0.017));
|
||||
float haze = mix(n1, n2, 0.35);
|
||||
float hazeMask = clamp(disc * 0.75 + glow * 0.28, 0.0, 1.0);
|
||||
float hazeMix = hazeMask * 0.55;
|
||||
float lumaMod = mix(1.0, 0.93 + haze * 0.10, hazeMix);
|
||||
outColor *= lumaMod;
|
||||
alpha *= mix(1.0, 0.94 + haze * 0.06, hazeMix);
|
||||
}
|
||||
|
||||
// Apply moon phase shadow (only for moon, indicated by low intensity)
|
||||
if (intensity < 0.5) { // Moon has lower intensity than sun
|
||||
|
|
@ -88,7 +123,7 @@ bool Celestial::initialize() {
|
|||
|
||||
// Apply elliptical terminator for 3D effect
|
||||
float y = (TexCoord.y - 0.5) * 2.0;
|
||||
float ellipse = sqrt(1.0 - y * y);
|
||||
float ellipse = sqrt(max(0.0, 1.0 - y * y));
|
||||
float terminatorX = phasePos / ellipse;
|
||||
|
||||
if (moonPhase < 0.5) {
|
||||
|
|
@ -101,7 +136,11 @@ bool Celestial::initialize() {
|
|||
alpha *= mix(0.05, 1.0, shadow);
|
||||
}
|
||||
|
||||
FragColor = vec4(celestialColor, alpha);
|
||||
if (alpha < 0.01) {
|
||||
discard;
|
||||
}
|
||||
|
||||
FragColor = vec4(outColor, alpha);
|
||||
}
|
||||
)";
|
||||
|
||||
|
|
@ -144,8 +183,12 @@ void Celestial::render(const Camera& camera, float timeOfDay,
|
|||
// Disable culling - billboards can face either way
|
||||
glDisable(GL_CULL_FACE);
|
||||
|
||||
// Render sun and moons (pass lighting parameters)
|
||||
// Render sun with alpha blending (avoids additive white clipping).
|
||||
glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
|
||||
renderSun(camera, timeOfDay, sunDir, sunColor);
|
||||
|
||||
// Render moons additively for glow.
|
||||
glBlendFunc(GL_SRC_ALPHA, GL_ONE);
|
||||
renderMoon(camera, timeOfDay); // White Lady (primary moon)
|
||||
|
||||
if (dualMoonMode_) {
|
||||
|
|
@ -189,11 +232,15 @@ void Celestial::renderSun(const Camera& camera, float timeOfDay,
|
|||
|
||||
// Sun color and intensity (use lighting color if provided)
|
||||
glm::vec3 color = sunColor ? *sunColor : getSunColor(timeOfDay);
|
||||
float intensity = getSunIntensity(timeOfDay);
|
||||
// Force strong warm/yellow tint; avoid white blowout.
|
||||
const glm::vec3 warmSun(1.0f, 0.88f, 0.55f);
|
||||
color = glm::mix(color, warmSun, 0.52f);
|
||||
float intensity = getSunIntensity(timeOfDay) * 0.92f;
|
||||
|
||||
celestialShader->setUniform("celestialColor", color);
|
||||
celestialShader->setUniform("intensity", intensity);
|
||||
celestialShader->setUniform("moonPhase", 0.5f); // Sun doesn't use this, but shader expects it
|
||||
celestialShader->setUniform("uAnimTime", sunHazeTimer_);
|
||||
|
||||
// Render quad
|
||||
glBindVertexArray(vao);
|
||||
|
|
@ -242,6 +289,7 @@ void Celestial::renderMoon(const Camera& camera, float timeOfDay) {
|
|||
celestialShader->setUniform("celestialColor", color);
|
||||
celestialShader->setUniform("intensity", intensity);
|
||||
celestialShader->setUniform("moonPhase", whiteLadyPhase_);
|
||||
celestialShader->setUniform("uAnimTime", sunHazeTimer_);
|
||||
|
||||
// Render quad
|
||||
glBindVertexArray(vao);
|
||||
|
|
@ -296,6 +344,7 @@ void Celestial::renderBlueChild(const Camera& camera, float timeOfDay) {
|
|||
celestialShader->setUniform("celestialColor", color);
|
||||
celestialShader->setUniform("intensity", intensity);
|
||||
celestialShader->setUniform("moonPhase", blueChildPhase_);
|
||||
celestialShader->setUniform("uAnimTime", sunHazeTimer_);
|
||||
|
||||
// Render quad
|
||||
glBindVertexArray(vao);
|
||||
|
|
@ -465,6 +514,8 @@ void Celestial::destroyCelestialQuad() {
|
|||
}
|
||||
|
||||
void Celestial::update(float deltaTime) {
|
||||
sunHazeTimer_ += deltaTime;
|
||||
|
||||
if (!moonPhaseCycling) {
|
||||
return;
|
||||
}
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue