cinetec_tech Posted April 7, 2015 Posted April 7, 2015 At work, I was asked to import a OpenGL shader written in GLSL from https://www.shadertoy.com/view/XslGRr into UNIGINE, and I have to add it as "post effect". It's whole bunch cloud with the sky and some lighting. I have been looking for ways to modify the original code, although it did compile, it only shows black screen. Could somebody with shader experience check out my the code that I have modified, or make it work just like the effect shown on shadertoy website in UNIGINE. The code of my world script, material, vertex and fragment are listed bellow. Thank you guys! original code from shadertoy: // Created by inigo quilez - iq/2013// License Creative Commons Attribution-NonCommercial-ShareAlike 3.0 Unported License.// Volumetric clouds. It performs level of detail (LOD) for faster rendering and antialiasingfloat noise( in vec3 x ){ vec3 p = floor(x); vec3 f = fract(x);f = f*f*(3.0-2.0*f);vec2 uv = (p.xy+vec2(37.0,17.0)*p.z) + f.xy;vec2 rg = texture2D( iChannel0, (uv+ 0.5)/256.0, -100.0 ).yx;return -1.0+2.0*mix( rg.x, rg.y, f.z );}float map5( in vec3 p ){vec3 q = p - vec3(0.0,0.1,1.0)*iGlobalTime;float f; f = 0.50000*noise( q ); q = q*2.02; f += 0.25000*noise( q ); q = q*2.03; f += 0.12500*noise( q ); q = q*2.01; f += 0.06250*noise( q ); q = q*2.02; f += 0.03125*noise( q );return clamp( 1.5 - p.y - 2.0 + 1.75*f, 0.0, 1.0 );}float map4( in vec3 p ){vec3 q = p - vec3(0.0,0.1,1.0)*iGlobalTime;float f; f = 0.50000*noise( q ); q = q*2.02; f += 0.25000*noise( q ); q = q*2.03; f += 0.12500*noise( q ); q = q*2.01; f += 0.06250*noise( q );return clamp( 1.5 - p.y - 2.0 + 1.75*f, 0.0, 1.0 );}float map3( in vec3 p ){vec3 q = p - vec3(0.0,0.1,1.0)*iGlobalTime;float f; f = 0.50000*noise( q ); q = q*2.02; f += 0.25000*noise( q ); q = q*2.03; f += 0.12500*noise( q );return clamp( 1.5 - p.y - 2.0 + 1.75*f, 0.0, 1.0 );}float map2( in vec3 p ){vec3 q = p - vec3(0.0,0.1,1.0)*iGlobalTime;float f; f = 0.50000*noise( q ); q = q*2.02; f += 0.25000*noise( q );;return clamp( 1.5 - p.y - 2.0 + 1.75*f, 0.0, 1.0 );}vec3 sundir = normalize( vec3(-1.0,0.0,-1.0) );vec4 integrate( in vec4 sum, in float dif, in float den, in vec3 bgcol, in float t ){ // lighting vec3 lin = vec3(0.65,0.68,0.7)*1.3 + 0.5*vec3(0.7, 0.5, 0.3)*dif; vec4 col = vec4( mix( 1.15*vec3(1.0,0.95,0.8), vec3(0.65), den ), den ); col.xyz *= lin; col.xyz = mix( col.xyz, bgcol, 1.0-exp(-0.003*t*t) ); // front to back blending col.a *= 0.4; col.rgb *= col.a; return sum + col*(1.0-sum.a);}#define MARCH(STEPS,MAPLOD) for(int i=0; i<STEPS; i++) { vec3 pos = ro + t*rd; if( pos.y<-3.0 || pos.y>2.0 || sum.a > 0.99 ) break; float den = MAPLOD( pos ); if( den>0.01 ) { float dif = clamp((den - MAPLOD(pos+0.3*sundir))/0.6, 0.0, 1.0 ); sum = integrate( sum, dif, den, bgcol, t ); } t += max(0.1,0.02*t); }vec4 raymarch( in vec3 ro, in vec3 rd, in vec3 bgcol ){vec4 sum = vec4(0.0);float t = 0.0; MARCH(30,map5); MARCH(30,map4); MARCH(30,map3); MARCH(30,map2); return clamp( sum, 0.0, 1.0 );}mat3 setCamera( in vec3 ro, in vec3 ta, float cr ){vec3 cw = normalize(ta-ro);vec3 cp = vec3(sin(cr), cos(cr),0.0);vec3 cu = normalize( cross(cw,cp) );vec3 cv = normalize( cross(cu,cw) ); return mat3( cu, cv, cw );}vec4 render( in vec3 ro, in vec3 rd ){ // background sky float sun = clamp( dot(sundir,rd), 0.0, 1.0 );vec3 col = vec3(0.6,0.71,0.75) - rd.y*0.2*vec3(1.0,0.5,1.0) + 0.15*0.5;col += 0.2*vec3(1.0,.6,0.1)*pow( sun, 8.0 ); // clouds vec4 res = raymarch( ro, rd, col ); col = col*(1.0-res.w) + res.xyz; // sun glare col += 0.1*vec3(1.0,0.4,0.2)*pow( sun, 3.0 ); return vec4( col, 1.0 );}void mainImage( out vec4 fragColor, in vec2 fragCoord ){ vec2 p = (-iResolution.xy + 2.0*fragCoord.xy)/ iResolution.y; vec2 m = iMouse.xy/iResolution.xy; // camera vec3 ro = 4.0*normalize(vec3(sin(3.0*m.x), 0.4*m.y, cos(3.0*m.x)));vec3 ta = vec3(0.0, -1.0, 0.0); mat3 ca = setCamera( ro, ta, 0.0 ); // ray vec3 rd = ca * normalize( vec3(p.xy,1.5)); fragColor = render( ro, rd );}void mainVR( out vec4 fragColor, in vec2 fragCoord, in vec3 fragRayOri, in vec3 fragRayDir ){ fragColor = render( fragRayOri, fragRayDir );} Material file: post_cloud.mat <?xml version="1.0" encoding="utf-8"?><materials version="1.11"><material name="post_cloud"> <blend src="none" dest="none"/> <state name="states" type="switch" items="one,two">0</state> <shader pass="post" vertex="shaders/post/vertex_post_cloud.shader" fragment="shaders/post/fragment_post_cloud.shader"/> <texture name="color" type="procedural" pass="post" filter="bilinear"/></material></materials> UNIGINE Script file: Tommy.cpp #include <core/unigine.h>Node box; // add a box nodeint init() { PlayerSpectator player = new PlayerSpectator(); player.setPosition(vec3(3.5,0.0,1.3)); player.setDirection(vec3(-1.0,0.0,-0.3)); engine.game.setPlayer(player); // search the node by the specified name int index = engine.editor.findNode("box"); if(index != -1) { box = engine.editor.getNode(index); } engine.render.setPostMaterials("post_cloud"); engine.render.setBackgroundColor(vec4(0.5f,0.8f,1.0f,1.0f)); engine.render.setShadowDistance(50.0f); return 1;}int shutdown() { return 1;}int update() { // check whether the node exists if(box != NULL) { // get the frame duration float ifps = engine.game.getIFps(); // set the angle of rotation float angle = ifps * 90.0f; // get the current transformation of the node and calculate rotation mat4 transform = box.getTransform() * rotateZ(angle); // set new transformation to the node box.setTransform(transform); } return 1;} My Modified Version in the engine: fragment_post_cloud.shader #include <core/shaders/default/common/fragment_base.h>/******************************************************************************\** OpenGL*\******************************************************************************/#ifdef OPENGLuniform sampler2D s_texture_0;uniform sampler2D s_texture_1;uniform sampler2D s_texture_2;uniform sampler2D s_texture_3;uniform vec3 iResolution; // viewport resolution (in pixels)uniform float iGlobalTime; // shader playback time (in seconds)uniform float iChannelTime[4]; // channel playback time (in seconds)uniform vec3 iChannelResolution[4]; // channel resolution (in pixels)uniform vec4 iMouse; // mouse pixel coords. xy: current (if MLB down), zw: clickuniform sampler2D iChannel0; // input channel. XX = 2D/Cubeuniform vec4 iDate; // (year, month, day, time in seconds)uniform float iSampleRate; // sound sample rate (i.e., 44100)float noise( in vec3 x ){ vec3 p = floor(x); vec3 f = fract(x); f = f*f*(3.0-2.0*f); vec2 uv = (p.xy+vec2(37.0,17.0)*p.z) + f.xy; vec2 rg = texture( s_texture_0, (uv+ 0.5)/256.0, -100.0 ).yx; return -1.0+2.0*mix( rg.x, rg.y, f.z );}float map5( in vec3 p ){ vec3 q = p - vec3(0.0,0.1,1.0)*iGlobalTime; float f; f = 0.50000*noise( q ); q = q*2.02; f += 0.25000*noise( q ); q = q*2.03; f += 0.12500*noise( q ); q = q*2.01; f += 0.06250*noise( q ); q = q*2.02; f += 0.03125*noise( q ); return clamp( 1.5 - p.y - 2.0 + 1.75*f, 0.0, 1.0 );}float map4( in vec3 p ){ vec3 q = p - vec3(0.0,0.1,1.0)*iGlobalTime; float f; f = 0.50000*noise( q ); q = q*2.02; f += 0.25000*noise( q ); q = q*2.03; f += 0.12500*noise( q ); q = q*2.01; f += 0.06250*noise( q ); return clamp( 1.5 - p.y - 2.0 + 1.75*f, 0.0, 1.0 );}float map3( in vec3 p ){ vec3 q = p - vec3(0.0,0.1,1.0)*iGlobalTime; float f; f = 0.50000*noise( q ); q = q*2.02; f += 0.25000*noise( q ); q = q*2.03; f += 0.12500*noise( q ); return clamp( 1.5 - p.y - 2.0 + 1.75*f, 0.0, 1.0 );}float map2( in vec3 p ){ vec3 q = p - vec3(0.0,0.1,1.0)*iGlobalTime; float f; f = 0.50000*noise( q ); q = q*2.02; f += 0.25000*noise( q );; return clamp( 1.5 - p.y - 2.0 + 1.75*f, 0.0, 1.0 );}vec3 sundir = normalize( vec3(-1.0,0.0,-1.0) );vec4 integrate( in vec4 sum, in float dif, in float den, in vec3 bgcol, in float t ){ // lighting vec3 lin = vec3(0.65,0.68,0.7)*1.3 + 0.5*vec3(0.7, 0.5, 0.3)*dif; vec4 col = vec4( mix( 1.15*vec3(1.0,0.95,0.8), vec3(0.65), den ), den ); col.xyz *= lin; col.xyz = mix( col.xyz, bgcol, 1.0-exp(-0.003*t*t) ); // front to back blending col.a *= 0.4; col.rgb *= col.a; return sum + col*(1.0-sum.a);}#define MARCH(STEPS,MAPLOD) for(int i=0; i<STEPS; i++) { vec3 pos = ro + t*rd; if( pos.y<-3.0 || pos.y>2.0 || sum.a > 0.99 ) break; float den = MAPLOD( pos ); if( den>0.01 ) { float dif = clamp((den - MAPLOD(pos+0.3*sundir))/0.6, 0.0, 1.0 ); sum = integrate( sum, dif, den, bgcol, t ); } t += max(0.1,0.02*t); }vec4 raymarch( in vec3 ro, in vec3 rd, in vec3 bgcol ){ vec4 sum = vec4(0.0); float t = 0.0; MARCH(30,map5); MARCH(30,map4); MARCH(30,map3); MARCH(30,map2); return clamp( sum, 0.0, 1.0 );}mat3 setCamera( in vec3 ro, in vec3 ta, float cr ){ vec3 cw = normalize(ta-ro); vec3 cp = vec3(sin(cr), cos(cr),0.0); vec3 cu = normalize( cross(cw,cp) ); vec3 cv = normalize( cross(cu,cw) ); return mat3( cu, cv, cw );}vec4 render( in vec3 ro, in vec3 rd ){ // background sky float sun = clamp( dot(sundir,rd), 0.0, 1.0 ); vec3 col = vec3(0.6,0.71,0.75) - rd.y*0.2*vec3(1.0,0.5,1.0) + 0.15*0.5; col += 0.2*vec3(1.0,.6,0.1)*pow( sun, 8.0 ); // clouds vec4 res = raymarch( ro, rd, col ); col = col*(1.0-res.w) + res.xyz; // sun glare col += 0.1*vec3(1.0,0.4,0.2)*pow( sun, 3.0 ); return vec4( col, 1.0 );}void main(){ vec2 p = (-iResolution.xy + 2.0*gl_FragCoord.xy)/ iResolution.y; vec2 m = iMouse.xy/iResolution.xy; // camera vec3 ro = 4.0*normalize(vec3(sin(3.0*m.x), 0.4*m.y, cos(3.0*m.x))); vec3 ta = vec3(0.0, -1.0, 0.0); mat3 ca = setCamera( ro, ta, 0.0 ); // ray vec3 rd = ca * normalize( vec3(p.xy,1.5)); s_frag_color = render( ro, rd );}#endif My vertex shader file: vertex_post_cloud.shader #include <core/shaders/default/common/vertex_base.h>/******************************************************************************\** OpenGL*\******************************************************************************/#ifdef OPENGLin float4 s_attribute_0;in float4 s_attribute_1;/**/void main() {gl_Position = getPosition(s_attribute_0);}#endif
unclebob Posted April 8, 2015 Posted April 8, 2015 Hi Cinetec! Looks like you forgot to set all the input uniforms such as iResolution, iGlobalTime, etc.
cinetec_tech Posted April 14, 2015 Author Posted April 14, 2015 But didn't I have already declare these uniform variables? or should I change or add something else? #include <core/shaders/default/common/fragment_base.h>/******************************************************************************\** OpenGL*\******************************************************************************/#ifdef OPENGLuniform sampler2D s_texture_0;uniform sampler2D s_texture_1;uniform sampler2D s_texture_2;uniform sampler2D s_texture_3;uniform vec3 iResolution; // viewport resolution (in pixels)uniform float iGlobalTime; // shader playback time (in seconds)uniform float iChannelTime[4]; // channel playback time (in seconds)uniform vec3 iChannelResolution[4]; // channel resolution (in pixels)uniform vec4 iMouse; // mouse pixel coords. xy: current (if MLB down), zw: clickuniform sampler2D iChannel0; // input channel. XX = 2D/Cubeuniform vec4 iDate; // (year, month, day, time in seconds)uniform float iSampleRate; // sound sample rate (i.e., 44100)float noise( in vec3 x ){ vec3 p = floor(x); vec3 f = fract(x); f = f*f*(3.0-2.0*f); vec2 uv = (p.xy+vec2(37.0,17.0)*p.z) + f.xy; vec2 rg = texture( s_texture_0, (uv+ 0.5)/256.0, -100.0 ).yx; return -1.0+2.0*mix( rg.x, rg.y, f.z );}float map5( in vec3 p ){ vec3 q = p - vec3(0.0,0.1,1.0)*iGlobalTime; float f; f = 0.50000*noise( q ); q = q*2.02; f += 0.25000*noise( q ); q = q*2.03; f += 0.12500*noise( q ); q = q*2.01; f += 0.06250*noise( q ); q = q*2.02; f += 0.03125*noise( q ); return clamp( 1.5 - p.y - 2.0 + 1.75*f, 0.0, 1.0 );}float map4( in vec3 p ){ vec3 q = p - vec3(0.0,0.1,1.0)*iGlobalTime; float f; f = 0.50000*noise( q ); q = q*2.02; f += 0.25000*noise( q ); q = q*2.03; f += 0.12500*noise( q ); q = q*2.01; f += 0.06250*noise( q ); return clamp( 1.5 - p.y - 2.0 + 1.75*f, 0.0, 1.0 );}float map3( in vec3 p ){ vec3 q = p - vec3(0.0,0.1,1.0)*iGlobalTime; float f; f = 0.50000*noise( q ); q = q*2.02; f += 0.25000*noise( q ); q = q*2.03; f += 0.12500*noise( q ); return clamp( 1.5 - p.y - 2.0 + 1.75*f, 0.0, 1.0 );}float map2( in vec3 p ){ vec3 q = p - vec3(0.0,0.1,1.0)*iGlobalTime; float f; f = 0.50000*noise( q ); q = q*2.02; f += 0.25000*noise( q );; return clamp( 1.5 - p.y - 2.0 + 1.75*f, 0.0, 1.0 );}vec3 sundir = normalize( vec3(-1.0,0.0,-1.0) );vec4 integrate( in vec4 sum, in float dif, in float den, in vec3 bgcol, in float t ){ // lighting vec3 lin = vec3(0.65,0.68,0.7)*1.3 + 0.5*vec3(0.7, 0.5, 0.3)*dif; vec4 col = vec4( mix( 1.15*vec3(1.0,0.95,0.8), vec3(0.65), den ), den ); col.xyz *= lin; col.xyz = mix( col.xyz, bgcol, 1.0-exp(-0.003*t*t) ); // front to back blending col.a *= 0.4; col.rgb *= col.a; return sum + col*(1.0-sum.a);}#define MARCH(STEPS,MAPLOD) for(int i=0; i<STEPS; i++) { vec3 pos = ro + t*rd; if( pos.y<-3.0 || pos.y>2.0 || sum.a > 0.99 ) break; float den = MAPLOD( pos ); if( den>0.01 ) { float dif = clamp((den - MAPLOD(pos+0.3*sundir))/0.6, 0.0, 1.0 ); sum = integrate( sum, dif, den, bgcol, t ); } t += max(0.1,0.02*t); }vec4 raymarch( in vec3 ro, in vec3 rd, in vec3 bgcol ){ vec4 sum = vec4(0.0); float t = 0.0; MARCH(30,map5); MARCH(30,map4); MARCH(30,map3); MARCH(30,map2); return clamp( sum, 0.0, 1.0 );}mat3 setCamera( in vec3 ro, in vec3 ta, float cr ){ vec3 cw = normalize(ta-ro); vec3 cp = vec3(sin(cr), cos(cr),0.0); vec3 cu = normalize( cross(cw,cp) ); vec3 cv = normalize( cross(cu,cw) ); return mat3( cu, cv, cw );}vec4 render( in vec3 ro, in vec3 rd ){ // background sky float sun = clamp( dot(sundir,rd), 0.0, 1.0 ); vec3 col = vec3(0.6,0.71,0.75) - rd.y*0.2*vec3(1.0,0.5,1.0) + 0.15*0.5; col += 0.2*vec3(1.0,.6,0.1)*pow( sun, 8.0 ); // clouds vec4 res = raymarch( ro, rd, col ); col = col*(1.0-res.w) + res.xyz; // sun glare col += 0.1*vec3(1.0,0.4,0.2)*pow( sun, 3.0 ); return vec4( col, 1.0 );}void main(){ vec2 p = (-iResolution.xy + 2.0*gl_FragCoord.xy)/ iResolution.y; vec2 m = iMouse.xy/iResolution.xy; // camera vec3 ro = 4.0*normalize(vec3(sin(3.0*m.x), 0.4*m.y, cos(3.0*m.x))); vec3 ta = vec3(0.0, -1.0, 0.0); mat3 ca = setCamera( ro, ta, 0.0 ); // ray vec3 rd = ca * normalize( vec3(p.xy,1.5)); s_frag_color = render( ro, rd );}#endif
unclebob Posted April 16, 2015 Posted April 16, 2015 Dear Cinetec, Declaration of uniform variable isn't enough, you have to assign some value to it. We have a bunch of built-in uniforms which are filled by the engine (like s_viewport, for example) but all user defined uniforms must be filled by the app. First, you need to declare that uniform as a material parameter in material xml. After that just use Material::setParameter (https://developer.unigine.com/en/docs/1.0/scripting/library/class.material#setParameter_variable_vec4_void) to assign values to that uniform, you can do so both in the script and in C++.
Recommended Posts