Cool working
This commit is contained in:
1 parent
27fb7a448c
commit
af550f56a7
12 files changed
+379
-11
No files matched your search
@@ -0,0 +1,41 @@
|
||||
varying vec3 color;
|
||||
varying vec3 vViewPosition; // Получаем позицию фрагмента в пространстве вида
|
||||
|
||||
uniform vec3 uCenterPos; // Центр планеты/атмосферы (в пространстве вида)
|
||||
uniform float uCenterRadius; // Радиус атмосферы (точка, где прозрачность = 0.5)
|
||||
|
||||
// Определение зоны плавного спада alpha
|
||||
const float FADE_WIDTH = 0.05; // Например, 5% от радиуса для плавного перехода
|
||||
|
||||
void main()
|
||||
{
|
||||
// 1. Расчет расстояния от фрагмента до центра
|
||||
float distanceToCenter = length(vViewPosition - uCenterPos);
|
||||
|
||||
// 2. Расчет границ для плавного перехода
|
||||
// Начало спада (R)
|
||||
float startRadius = uCenterRadius;
|
||||
// Конец спада (R + dR)
|
||||
float endRadius = uCenterRadius + FADE_WIDTH * uCenterRadius;
|
||||
|
||||
// 3. Расчет коэффициента прозрачности с помощью smoothstep
|
||||
// smoothstep(edge0, edge1, x) возвращает 0.0, если x < edge0,
|
||||
// 1.0, если x > edge1, и плавно меняется между ними.
|
||||
|
||||
// Нам нужно, чтобы alpha была 0.5 при startRadius и 0.0 при endRadius.
|
||||
// Если мы используем smoothstep(start, end, distance), то получим:
|
||||
// - 0.0, когда distance < start
|
||||
// - 1.0, когда distance > end
|
||||
// Нам нужен обратный результат (1.0 - smoothstep), чтобы 0.5 было внутри, а 0.0 - снаружи.
|
||||
|
||||
// Вычисляем множитель прозрачности (от 1.0 до 0.0)
|
||||
float fadeFactor = 1.0 - smoothstep(startRadius, endRadius, distanceToCenter);
|
||||
|
||||
// 4. Применение нового alpha
|
||||
// Если fadeFactor = 1.0 (внутри R), alpha = 0.5 * 1.0 = 0.5
|
||||
// Если fadeFactor = 0.0 (вне R+dR), alpha = 0.5 * 0.0 = 0.0
|
||||
// Если между ними - плавная интерполяция.
|
||||
float finalAlpha = 0.5 * fadeFactor;
|
||||
|
||||
gl_FragColor = vec4(color, 0.5);
|
||||
}
|
||||
@@ -0,0 +1,20 @@
|
||||
attribute vec3 vPosition;
|
||||
attribute vec3 vColor;
|
||||
|
||||
uniform mat4 ProjectionModelViewMatrix;
|
||||
uniform mat4 ModelViewMatrix;
|
||||
|
||||
varying vec3 color;
|
||||
varying vec3 vViewPosition; // Новая переменная: позиция вершины в пространстве вида
|
||||
|
||||
void main()
|
||||
{
|
||||
// Расчет позиции в пространстве отсечения (как у вас)
|
||||
gl_Position = ProjectionModelViewMatrix * vec4(vPosition.xyz, 1.0);
|
||||
|
||||
// Передача позиции в пространстве вида во фрагментный шейдер
|
||||
vViewPosition = vec3(ModelViewMatrix * vec4(vPosition.xyz, 1.0));
|
||||
//vViewPosition = vPosition.xyz;
|
||||
|
||||
color = vColor;
|
||||
}
|
||||
@@ -0,0 +1,32 @@
|
||||
// Вершинный шейдер (Vertex Shader)
|
||||
|
||||
attribute vec3 vPosition;
|
||||
attribute vec3 vColor;
|
||||
attribute vec3 vNormal;
|
||||
attribute vec2 vTexCoord;
|
||||
|
||||
varying vec3 color;
|
||||
varying vec3 normal;
|
||||
varying vec2 TexCoord;
|
||||
varying float viewZ; // <--- НОВОЕ: Z-координата в пространстве вида (View Space)
|
||||
|
||||
uniform mat4 ProjectionModelViewMatrix;
|
||||
uniform mat4 ModelViewMatrix; // Нужна для преобразования vPosition в View Space
|
||||
uniform vec3 uLightDirection;
|
||||
|
||||
void main()
|
||||
{
|
||||
// Преобразование позиции в пространство вида (View Space)
|
||||
vec4 viewPosition = ModelViewMatrix * vec4(vPosition.xyz, 1.0);
|
||||
|
||||
// Сохраняем отрицательную Z-координату. В OpenGL Z-координата (глубина)
|
||||
// в пространстве вида обычно отрицательна, но для расчета тумана
|
||||
// удобнее использовать положительное значение.
|
||||
viewZ = -viewPosition.z;
|
||||
|
||||
gl_Position = ProjectionModelViewMatrix * vec4(vPosition.xyz, 1.0);
|
||||
|
||||
normal = normalize((ModelViewMatrix * vec4(vNormal, 0.0)).xyz);
|
||||
color = vColor;
|
||||
TexCoord = vTexCoord;
|
||||
}
|
||||
@@ -0,0 +1,89 @@
|
||||
// ---Фрагментный шейдер (Fragment Shader)
|
||||
|
||||
varying vec3 color;
|
||||
varying vec3 normal;
|
||||
varying vec2 TexCoord;
|
||||
varying float viewZ;
|
||||
|
||||
uniform sampler2D Texture;
|
||||
uniform vec3 uLightDirection;
|
||||
uniform float uDistanceToPlanetSurface;
|
||||
uniform float uCurrentZFar;
|
||||
|
||||
// Константы для тумана:
|
||||
const vec4 FOG_COLOR = vec4(0.0, 0.5, 1.0, 1.0); // Синий туман
|
||||
|
||||
// Параметры "Distance Fog"
|
||||
const float DIST_FOG_MAX = 2000.0;
|
||||
const float DIST_FOG_MIN = 1000.0;
|
||||
|
||||
// Параметры "Z-Far Fog"
|
||||
// Насколько близко к Zfar должен начинаться туман (например, 10% от Zfar)
|
||||
const float Z_FOG_START_RATIO = 0.9;
|
||||
// Какую долю от Zfar должен покрывать туман (например, 10% от Zfar)
|
||||
const float Z_FOG_RANGE_RATIO = 0.1;
|
||||
|
||||
|
||||
void main()
|
||||
{
|
||||
// ... (1. Получаем цвет и 2. Расчет освещения)
|
||||
vec4 textureColor = texture2D(Texture, TexCoord);
|
||||
vec3 finalColor = textureColor.rgb * color;
|
||||
|
||||
float diffuse = max(0.0, dot(normal, uLightDirection));
|
||||
float ambient = 0.2;
|
||||
float lightingFactor = min(1.0, ambient + diffuse);
|
||||
vec3 litColor = finalColor * lightingFactor;
|
||||
|
||||
|
||||
// 3. Расчет коэффициента тумана (fogFactor)
|
||||
float fogFactor = 0.0;
|
||||
|
||||
// --- 3.1. Расчет коэффициента тумана на основе расстояния до поверхности (Distance Fog) ---
|
||||
// Этот туман работает на больших расстояниях и постепенно исчезает,
|
||||
// уступая место Z-Far Fog при приближении к планете.
|
||||
|
||||
if (uDistanceToPlanetSurface >= DIST_FOG_MIN && uDistanceToPlanetSurface <DIST_FOG_MAX) {
|
||||
// Нормализация: 0.0f при DIST_FOG_MAX, 1.0f при DIST_FOG_MIN
|
||||
float distRange = DIST_FOG_MAX - DIST_FOG_MIN;
|
||||
float distNormalized = clamp((uDistanceToPlanetSurface - DIST_FOG_MIN) / distRange, 0.0, 1.0);
|
||||
|
||||
// alpha = 0.0 (Далеко) ... 1.0 (Близко к 1000.f)
|
||||
fogFactor = 1.0 - distNormalized;
|
||||
}
|
||||
if (uDistanceToPlanetSurface < DIST_FOG_MIN)
|
||||
{
|
||||
fogFactor = 1.0;
|
||||
}
|
||||
// Если uDistanceToPlanetSurface < 1000.0f, то fogFactor = 0.0f (пока не пересчитан ниже),
|
||||
// что позволяет Z-Far Fog взять контроль.
|
||||
|
||||
|
||||
// --- 3.2. Расчет коэффициента тумана на основе Z-глубины (Z-Far Fog) ---
|
||||
// Этот туман работает всегда, но его эффект усиливается при уменьшении uCurrentZFar,
|
||||
// гарантируя, что все, что подходит к границе uCurrentZFar, будет скрыто.
|
||||
|
||||
// Точка начала тумана: 90% от uCurrentZFar
|
||||
float farFogStart = 2000.0;
|
||||
// Длина перехода тумана: 10% от uCurrentZFar
|
||||
float depthRange = 2500.0;
|
||||
|
||||
float farFogFactor = 0.0;
|
||||
|
||||
if (depthRange > 0.0) {
|
||||
// Нормализация Z-глубины: 0.0f при farFogStart, 1.0f при farFogStart + depthRange
|
||||
farFogFactor = clamp((viewZ - farFogStart) / depthRange, 0.0, 1.0);
|
||||
}
|
||||
|
||||
// --- 3.3. Объединение ---
|
||||
|
||||
// Когда мы далеко (fogFactor > 0.0), Distance Fog доминирует.
|
||||
// Когда мы близко (fogFactor = 0.0), Z-Far Fog берет управление.
|
||||
// Если оба активны, берем максимум (например, когда фрагмент далек от игрока, но игрок все еще в зоне Distance Fog).
|
||||
//fogFactor = max(fogFactor, farFogFactor);
|
||||
fogFactor = fogFactor * farFogFactor;
|
||||
|
||||
|
||||
// 4. Смешивание цвета с туманом
|
||||
gl_FragColor = mix(vec4(litColor, 1.0), FOG_COLOR, fogFactor);
|
||||
}
|
||||
@@ -0,0 +1,12 @@
|
||||
attribute vec3 vPosition;
|
||||
|
||||
uniform mat4 ProjectionModelViewMatrix;
|
||||
|
||||
varying vec3 dir;
|
||||
|
||||
void main(){
|
||||
vec4 realVertexPos = vec4(vPosition.xyz, 1.0);
|
||||
gl_Position = ProjectionModelViewMatrix * realVertexPos;
|
||||
|
||||
dir = vPosition;
|
||||
}
|
||||
@@ -0,0 +1,11 @@
|
||||
uniform samplerCube Texture;
|
||||
uniform float skyPercent;
|
||||
|
||||
varying vec3 dir;
|
||||
|
||||
void main(){
|
||||
vec4 skyBoxColor = textureCube(Texture, normalize(dir));
|
||||
vec4 skyColor = vec4(0.0, 0.5, 1.0, 1.0);
|
||||
gl_FragColor = skyPercent*skyColor + (1.0 - skyPercent) * skyBoxColor;
|
||||
|
||||
}
|
||||
Reference in new issue
Block a user