1// Compatibility #ifdefs needed for parameters 2#ifdef GL_ES 3#define COMPAT_PRECISION mediump 4#else 5#define COMPAT_PRECISION 6#endif 7 8// Parameter lines go here: 9#pragma parameter RETRO_PIXEL_SIZE "Retro Pixel Size" 0.84 0.0 1.0 0.01 10#ifdef PARAMETER_UNIFORM 11// All parameter floats need to have COMPAT_PRECISION in front of them 12uniform COMPAT_PRECISION float RETRO_PIXEL_SIZE; 13#else 14#define RETRO_PIXEL_SIZE 0.84 15#endif 16 17#if defined(VERTEX) 18 19#if __VERSION__ >= 130 20#define COMPAT_VARYING out 21#define COMPAT_ATTRIBUTE in 22#define COMPAT_TEXTURE texture 23#else 24#define COMPAT_VARYING varying 25#define COMPAT_ATTRIBUTE attribute 26#define COMPAT_TEXTURE texture2D 27#endif 28 29#ifdef GL_ES 30#define COMPAT_PRECISION mediump 31#else 32#define COMPAT_PRECISION 33#endif 34 35COMPAT_ATTRIBUTE vec4 VertexCoord; 36COMPAT_ATTRIBUTE vec4 COLOR; 37COMPAT_ATTRIBUTE vec4 TexCoord; 38COMPAT_VARYING vec4 COL0; 39COMPAT_VARYING vec4 TEX0; 40// out variables go here as COMPAT_VARYING whatever 41 42vec4 _oPosition1; 43uniform mat4 MVPMatrix; 44uniform COMPAT_PRECISION int FrameDirection; 45uniform COMPAT_PRECISION int FrameCount; 46uniform COMPAT_PRECISION vec2 OutputSize; 47uniform COMPAT_PRECISION vec2 TextureSize; 48uniform COMPAT_PRECISION vec2 InputSize; 49 50// compatibility #defines 51#define vTexCoord TEX0.xy 52#define SourceSize vec4(TextureSize, 1.0 / TextureSize) //either TextureSize or InputSize 53#define OutSize vec4(OutputSize, 1.0 / OutputSize) 54 55void main() 56{ 57 gl_Position = MVPMatrix * VertexCoord; 58 TEX0.xy = VertexCoord.xy; 59// Paste vertex contents here: 60} 61 62#elif defined(FRAGMENT) 63 64#if __VERSION__ >= 130 65#define COMPAT_VARYING in 66#define COMPAT_TEXTURE texture 67out vec4 FragColor; 68#else 69#define COMPAT_VARYING varying 70#define FragColor gl_FragColor 71#define COMPAT_TEXTURE texture2D 72#endif 73 74#ifdef GL_ES 75#ifdef GL_FRAGMENT_PRECISION_HIGH 76precision highp float; 77#else 78precision mediump float; 79#endif 80#define COMPAT_PRECISION mediump 81#else 82#define COMPAT_PRECISION 83#endif 84 85uniform COMPAT_PRECISION int FrameDirection; 86uniform COMPAT_PRECISION int FrameCount; 87uniform COMPAT_PRECISION vec2 OutputSize; 88uniform COMPAT_PRECISION vec2 TextureSize; 89uniform COMPAT_PRECISION vec2 InputSize; 90uniform sampler2D Texture; 91COMPAT_VARYING vec4 TEX0; 92// in variables go here as COMPAT_VARYING whatever 93 94// compatibility #defines 95#define Source Texture 96#define vTexCoord TEX0.xy 97 98#define SourceSize vec4(TextureSize, 1.0 / TextureSize) //either TextureSize or InputSize 99#define OutSize vec4(OutputSize, 1.0 / OutputSize) 100 101// delete all 'params.' or 'registers.' or whatever in the fragment 102float iGlobalTime = float(FrameCount)*0.025; 103vec2 iResolution = OutputSize.xy; 104 105// Wet Stone - TDM - 2014-10-20 106// https://www.shadertoy.com/view/ldSSzV 107 108// stone generation 109 110/* 111"Wet stone" by Alexander Alekseev aka TDM - 2014 112License Creative Commons Attribution-NonCommercial-ShareAlike 3.0 Unported License. 113Contact: tdmaav@gmail.com 114*/ 115 116#define SMOOTH 117 118const int NUM_STEPS = 32; 119const int AO_SAMPLES = 3; 120const vec2 AO_PARAM = vec2(1.2, 3.8); 121const vec2 CORNER_PARAM = vec2(0.25, 40.0); 122const float INV_AO_SAMPLES = 1.0 / float(AO_SAMPLES); 123const float TRESHOLD = 0.1; 124const float EPSILON = 1e-3; 125const float LIGHT_INTENSITY = 0.25; 126const vec3 RED = vec3(1.0,0.7,0.7) * LIGHT_INTENSITY; 127const vec3 ORANGE = vec3(1.0,0.67,0.43) * LIGHT_INTENSITY; 128const vec3 BLUE = vec3(0.54,0.77,1.0) * LIGHT_INTENSITY; 129const vec3 WHITE = vec3(1.2,1.07,0.98) * LIGHT_INTENSITY; 130 131const float DISPLACEMENT = 0.1; 132 133// math 134mat3 fromEuler(vec3 ang) { 135 vec2 a1 = vec2(sin(ang.x),cos(ang.x)); 136 vec2 a2 = vec2(sin(ang.y),cos(ang.y)); 137 vec2 a3 = vec2(sin(ang.z),cos(ang.z)); 138 mat3 m; 139 m[0] = vec3(a1.y*a3.y+a1.x*a2.x*a3.x,a1.y*a2.x*a3.x+a3.y*a1.x,-a2.y*a3.x); 140 m[1] = vec3(-a2.y*a1.x,a1.y*a2.y,a2.x); 141 m[2] = vec3(a3.y*a1.x*a2.x+a1.y*a3.x,a1.x*a3.x-a1.y*a3.y*a2.x,a2.y*a3.y); 142 return m; 143} 144float hash11(float p) { 145 return fract(sin(p * 727.1)*435.545); 146} 147float hash12(vec2 p) { 148 float h = dot(p,vec2(127.1,311.7)); 149 return fract(sin(h)*437.545); 150} 151vec3 hash31(float p) { 152 vec3 h = vec3(127.231,491.7,718.423) * p; 153 return fract(sin(h)*435.543); 154} 155 156// 3d noise 157float noise_3(in vec3 p) { 158 vec3 i = floor(p); 159 vec3 f = fract(p); 160 vec3 u = f*f*(3.0-2.0*f); 161 162 vec2 ii = i.xy + i.z * vec2(5.0); 163 float a = hash12( ii + vec2(0.0,0.0) ); 164 float b = hash12( ii + vec2(1.0,0.0) ); 165 float c = hash12( ii + vec2(0.0,1.0) ); 166 float d = hash12( ii + vec2(1.0,1.0) ); 167 float v1 = mix(mix(a,b,u.x), mix(c,d,u.x), u.y); 168 169 ii += vec2(5.0); 170 a = hash12( ii + vec2(0.0,0.0) ); 171 b = hash12( ii + vec2(1.0,0.0) ); 172 c = hash12( ii + vec2(0.0,1.0) ); 173 d = hash12( ii + vec2(1.0,1.0) ); 174 float v2 = mix(mix(a,b,u.x), mix(c,d,u.x), u.y); 175 176 return max(mix(v1,v2,u.z),0.0); 177} 178 179// fBm 180float fbm3(vec3 p, float a, float f) { 181 return noise_3(p); 182} 183 184float fbm3_high(vec3 p, float a, float f) { 185 float ret = 0.0; 186 float amp = 1.0; 187 float frq = 1.0; 188 for(int i = 0; i < 4; i++) { 189 float n = pow(noise_3(p * frq),2.0); 190 ret += n * amp; 191 frq *= f; 192 amp *= a * (pow(n,0.2)); 193 } 194 return ret; 195} 196 197// lighting 198float diffuse(vec3 n,vec3 l,float p) { return pow(max(dot(n,l),0.0),p); } 199float specular(vec3 n,vec3 l,vec3 e,float s) { 200 float nrm = (s + 8.0) / (3.1415 * 8.0); 201 return pow(max(dot(reflect(e,n),l),0.0),s) * nrm; 202} 203 204// distance functions 205float plane(vec3 gp, vec4 p) { 206 return dot(p.xyz,gp+p.xyz*p.w); 207} 208float sphere(vec3 p,float r) { 209 return length(p)-r; 210} 211float capsule(vec3 p,float r,float h) { 212 p.y -= clamp(p.y,-h,h); 213 return length(p)-r; 214} 215float cylinder(vec3 p,float r,float h) { 216 return max(abs(p.y/h),capsule(p,r,h)); 217} 218float box(vec3 p,vec3 s) { 219 p = abs(p)-s; 220 return max(max(p.x,p.y),p.z); 221} 222float rbox(vec3 p,vec3 s) { 223 p = abs(p)-s; 224 return length(p-min(p,0.0)); 225} 226float quad(vec3 p,vec2 s) { 227 p = abs(p) - vec3(s.x,0.0,s.y); 228 return max(max(p.x,p.y),p.z); 229} 230 231// boolean operations 232float boolUnion(float a,float b) { return min(a,b); } 233float boolIntersect(float a,float b) { return max(a,b); } 234float boolSub(float a,float b) { return max(a,-b); } 235 236// smooth operations. thanks to iq 237float boolSmoothIntersect(float a, float b, float k ) { 238 float h = clamp(0.5+0.5*(b-a)/k, 0.0, 1.0); 239 return mix(a,b,h) + k*h*(1.0-h); 240} 241float boolSmoothSub(float a, float b, float k ) { 242 return boolSmoothIntersect(a,-b,k); 243} 244 245// world 246float rock(vec3 p) { 247 float d = sphere(p,1.0); 248 for(int i = 0; i < 9; i++) { 249 float ii = float(i); 250 float r = 2.5 + hash11(ii); 251 vec3 v = normalize(hash31(ii) * 2.0 - 1.0); 252 #ifdef SMOOTH 253 d = boolSmoothSub(d,sphere(p+v*r,r * 0.8), 0.03); 254 #else 255 d = boolSub(d,sphere(p+v*r,r * 0.8)); 256 #endif 257 } 258 return d; 259} 260 261float map(vec3 p) { 262 float d = rock(p) + fbm3(p*4.0,0.4,2.96) * DISPLACEMENT; 263 d = boolUnion(d,plane(p,vec4(0.0,1.0,0.0,1.0))); 264 return d; 265} 266 267float map_detailed(vec3 p) { 268 float d = rock(p) + fbm3_high(p*4.0,0.4,2.96) * DISPLACEMENT; 269 d = boolUnion(d,plane(p,vec4(0.0,1.0,0.0,1.0))); 270 return d; 271} 272 273// tracing 274vec3 getNormal(vec3 p, float dens) { 275 vec3 n; 276 n.x = map_detailed(vec3(p.x+EPSILON,p.y,p.z)); 277 n.y = map_detailed(vec3(p.x,p.y+EPSILON,p.z)); 278 n.z = map_detailed(vec3(p.x,p.y,p.z+EPSILON)); 279 return normalize(n-map_detailed(p)); 280} 281vec2 getOcclusion(vec3 p, vec3 n) { 282 vec2 r = vec2(0.0); 283 for(int i = 0; i < AO_SAMPLES; i++) { 284 float f = float(i)*INV_AO_SAMPLES; 285 float hao = 0.01+f*AO_PARAM.x; 286 float hc = 0.01+f*CORNER_PARAM.x; 287 float dao = map(p + n * hao) - TRESHOLD; 288 float dc = map(p - n * hc) - TRESHOLD; 289 r.x += clamp(hao-dao,0.0,1.0) * (1.0-f); 290 r.y += clamp(hc+dc,0.0,1.0) * (1.0-f); 291 } 292 r.x = pow(clamp(1.0-r.x*INV_AO_SAMPLES*AO_PARAM.y,0.0,1.0),0.5); 293 r.y = clamp(r.y*INV_AO_SAMPLES*CORNER_PARAM.y,0.0,1.0); 294 return r; 295} 296vec2 spheretracing(vec3 ori, vec3 dir, out vec3 p) { 297 vec2 td = vec2(0.0); 298 for(int i = 0; i < NUM_STEPS; i++) { 299 p = ori + dir * td.x; 300 td.y = map(p); 301 if(td.y < TRESHOLD) break; 302 td.x += (td.y-TRESHOLD) * 0.9; 303 } 304 return td; 305} 306 307// stone 308vec3 getStoneColor(vec3 p, float c, vec3 l, vec3 n, vec3 e) { 309 c = min(c + pow(noise_3(vec3(p.x*20.0,0.0,p.z*20.0)),70.0) * 8.0, 1.0); 310 float ic = pow(1.0-c,0.5); 311 vec3 base = vec3(0.42,0.3,0.2) * 0.6; 312 vec3 sand = vec3(0.51,0.41,0.32); 313 vec3 color = mix(base,sand,c); 314 315 float f = pow(1.0 - max(dot(n,-e),0.0), 1.5) * 0.75 * ic; 316 color = mix(color,vec3(1.0),f); 317 color += vec3(diffuse(n,l,0.5) * WHITE); 318 color += vec3(specular(n,l,e,8.0) * WHITE * 1.5 * ic); 319 n = normalize(n - normalize(p) * 0.4); 320 color += vec3(specular(n,l,e,80.0) * WHITE * 1.5 * ic); 321 return color; 322} 323 324// main 325void mainImage( out vec4 fragColor, in vec2 fragCoord ) { 326 vec2 iuv = fragCoord.xy / iResolution.xy * 2.0 - 1.0; 327 vec2 uv = iuv; 328 uv.x *= iResolution.x / iResolution.y; 329 float time = iGlobalTime * 0.3; 330 331 // ray 332 vec3 ang = vec3(0.0,0.2,time); 333#ifdef MOUSE 334 if(iMouse.z > 0.0) ang = vec3(0.0,clamp(2.0-iMouse.y*0.01,0.0,3.1415),iMouse.x*0.01); 335#endif 336 mat3 rot = fromEuler(ang); 337 338 vec3 ori = vec3(0.0,0.0,2.8); 339 vec3 dir = normalize(vec3(uv.xy,-2.0)); 340 ori = ori * rot; 341 dir = dir * rot; 342 343 // tracing 344 vec3 p; 345 vec2 td = spheretracing(ori,dir,p); 346 vec3 n = getNormal(p,td.y); 347 vec2 occ = getOcclusion(p,n); 348 vec3 light = normalize(vec3(0.0,1.0,0.0)); 349 350 // color 351 vec3 color = vec3(1.0); 352 if(td.x < 3.5 && p.y > -0.89) color = getStoneColor(p,occ.y,light,n,dir); 353 color *= occ.x; 354 355 // post 356 float vgn = smoothstep(1.2,0.7,abs(iuv.y)) * smoothstep(1.1,0.8,abs(iuv.x)); 357 color *= 1.0 - (1.0 - vgn) * 0.15; 358 fragColor = vec4(color,1.0); 359} 360 361void main(void) 362{ 363 //just some shit to wrap shadertoy's stuff 364 vec2 FragCoord = vTexCoord.xy*OutputSize.xy; 365 mainImage(FragColor,FragCoord); 366} 367#endif 368