본문 바로가기
셰이더 (Shader)/The Art of Code

[GLSL] Starfield - 5(완) : 마우스 상호작용, 별 팍 사라지는 이슈 수정

by Minkyu Lee 2023. 4. 8.

#define NUM_LAYERS 8.0

mat2 Rot(float a) {
    float s = sin(a), c = cos(a) ;
    return mat2(c, -s, s, c) ;
}

float Star(vec2 uv, float flare) {
    float d = length(uv) ;
    float m = 0.02/d ;
    m*= 1.5 ;
    float rays = max(0.0, 1.0-abs(uv.x*uv.y*1000.0)) ;
    m += rays * flare ;
    
    // 대각선 레이
    uv *= Rot(3.1415/4.0) ;
    rays = max(0.0, 1.0-abs(uv.x*uv.y*1000.0)) ;
    m += rays * 0.3 * flare ;
    
    m *= smoothstep(1.0, 0.2, d) ;
    return m ;
}

float Hash21(vec2 p)
{
    p = fract(p*vec2(123.34, 456.21) ) ;
    p += dot(p, p+45.32) ;
    return fract(p.x*p.y) ;
}

vec3 StarLayer(vec2 uv) {
    vec3 col = vec3(0.0);
    vec2 gv = fract(uv)-0.5 ;
    vec2 id = floor(uv) ;
    
    for(int y=-1; y<=1; y++) {
        for(int x=-1 ; x<=1; x++) {
            vec2 offs = vec2(x, y) ;
            float n = Hash21(id+offs) ;
            
            float size = fract(n*345.32) ;
            float star = Star(gv-offs-vec2(n, fract(n*34.0))+0.5, smoothstep(0.9,0.1,size)*0.6);
            star *= sin((iTime*2.0)+(n*3.14*10.))*0.5+1.0;
            
            vec3 color = sin(vec3(0.2, 0.3, 0.9)*fract(n*2345.2)*6.2831)*0.5+0.5 ;
            color *= vec3(1.0, 0.5, 1.0+size) ;
            col += star * size * color ;
        }
    }
    return col ;
}

void mainImage( out vec4 fragColor, in vec2 fragCoord )
{
    vec2 uv = (fragCoord-0.5*iResolution.xy)/iResolution.y ; 
    vec2 M = (iMouse.xy-iResolution.xy*0.5)/iResolution.y ;
    
    float t = iTime*0.02;
    
    uv += M *4.0 ; // 마우스로 시점 변경, *는 변화량
    uv *= Rot(t) ;
    
    vec3 col = vec3(0.0);
    for(float i=0.0; i<1.0; i+=1.0/NUM_LAYERS) {
        float depth = fract(i+t);
        float fade = depth*smoothstep(1.0, 0.9, depth);
        // 근거리면 밝게 원거리면 어둡게, 완전 근거리(1.0)면 0으로 만들어 팍 안사라지게
        float scale = mix(20.0, 0.5, depth) ;
        float offset = i*453.2;
        col += StarLayer(uv*scale+offset-M)*fade;
        // M이 없으면 재생중 마우스 이동시 페럴렉스가 없어 보인다. 페이크 페럴렉스 역할이다.
    }
    fragColor = vec4(col,1.0);
}

// 마우스 상호작용

마우스 입력에 따라 별의 이동이 달라진다.

시점도 달라진 것처럼 보인다. (페이크)

마우스 시점 변화에 따라 페이크 페럴렉스를 주려면,

starLayer함수 인자의 uv값에 -를 준다.

 

// 팍 사라짐 이슈 수정

깊이값에 smoothstep을 적용해 처리한다.

 

 

댓글