0

I don't have much experience with Shader or GLSL. I am trying to practice with them. To this end I'm trying to port this shader. https://www.shadertoy.com/view/XsXGR7 Into a project to use with SFML. I am having issue doing this and I'm not sure what to do to start fixing the issues.

I messed around with the uniforms and a few varaiable but the shader itself keeps giving the same error message. That it won't compile. Not sure why, I assume it's because without converting it to work with SFML it's asking for input from OpenGL.

Shader file

   uniform vec3      iResolution;           // viewport resolution (in pixels)
   uniform float     iTime;                 // shader playback time (in seconds)
   uniform float     iTimeDelta;            // render time (in seconds)
   uniform int       iFrame;                // shader playback frame
   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: click
    uniform samplerXX iChannel0..3;          // input channel. XX = 2D/Cube
    uniform vec4      iDate;                 // (year, month, day, time in seconds)
    uniform float     iSampleRate;           // sound sample rate (i.e., 44100)

    void mainImage( out vec4 fragColor, in vec2 fragCoord )
    {
     vec3 waveParams = vec3( 10.0, 0.8, 0.1 );
     vec2 tmp = vec2( iMouse.xy / iResolution.xy );
     vec2 uv = fragCoord.xy / iResolution.xy;
     vec2 texCoord = uv;
     float distance = distance(uv, tmp);

     if ( (distance <= ((iTime ) + waveParams.z )) && ( distance >= ((iTime ) - waveParams.z)) ) 
     {
            float diff = (distance - (iTime)); 
            float powDiff = 1.0 - pow(abs(diff*waveParams.x), waveParams.y); 

            float diffTime = diff  * powDiff; 
            vec2 diffUV = normalize(uv - tmp); 
            texCoord = uv + (diffUV * diffTime);

     } 
     vec4 original = texture( iChannel0, texCoord);
     fragColor = original; 
   }

Currently all the shader does is get loaded in.

shader.loadFromFile("ASSETS/SHADERS/Shockwave1.txt",sf::Shader::Fragment);    
 //load the shader

if (!shader.isAvailable()) {
 std::cout << "The shader is not available\n";
}

Error message trying to load the above shader. No uniforms set, nothing is done with the shader aside from loading it.

   Failed to compile fragment shader:
   WARNING: 0:1 '' : #version directive missing
   ERROR: 0:8 'iChannel0 : syntax error syntax error

Edit:

Having replaced "samplerXX" with "sampler2D" and inserted a void main() function the shader loads properly. Getting the code to work is now the issue.

The Main()

void main(out vec4 fragColor, in vec2 fragCoord )
{
     vec3 waveParams = vec3( 10.0, 0.8, 0.1 );
     vec2 tmp = vec2( iMouse.xy / iResolution.xy );
     vec2 uv = fragCoord.xy / iResolution.xy;
     vec2 texCoord = uv;
     float distance = distance(uv, tmp);

     if ( (distance <= ((iTime ) + waveParams.z )) && ( distance >= ((iTime ) - waveParams.z)) ) 
     {
            float diff = (distance - (iTime)); 
            float powDiff = 1.0 - pow(abs(diff*waveParams.x), waveParams.y); 

            float diffTime = diff  * powDiff; 
            vec2 diffUV = normalize(uv - tmp); 
            texCoord = uv + (diffUV * diffTime);

     } 
     vec4 original = texture( iChannel0, texCoord);
     fragColor = original; 

}

This produces these errors

Failed to compile fragment shader:
WARNING: 0:1: '' :  #version directive missing
WARNING: 0:32: 'function' : is not available in current GLSL version texture
ERROR: 0:34: 'main' : function cannot take any parameter(s)
WARNING: 0:53: 'function' : is not available in current GLSL version texture

While the main not taking parameters is straightforward I would like to know would values be passed in strictly using uniforms? I am not sure what the 'function' errors relate to.

Edit:

Main()

void main( )
{
     vec2 fragCoord = vec2(20,20);
     vec3 waveParams = vec3( 10.0, 0.8, 0.1 );
     vec2 tmp = vec2( iMouse.xy / iResolution.xy );
     vec2 uv = fragCoord.xy / iResolution.xy;
     vec2 texCoord = uv;
     float distance = distance(uv, tmp);

     if ( (distance <= ((iTime ) + waveParams.z )) && ( distance >= ((iTime ) - waveParams.z)) ) 
     {
            float diff = (distance - (iTime)); 
            float powDiff = 1.0 - pow(abs(diff*waveParams.x), waveParams.y); 

            float diffTime = diff  * powDiff; 
            vec2 diffUV = normalize(uv - tmp); 
            texCoord = uv + (diffUV * diffTime);

     } 
     vec4 original = texture( iChannel0, texCoord);
     gl_FragColor = original; 

}

Removing the main parameters, hardcode defining vec2 fragCoord as vec2(20,20) made the shader run without issue. My question now is this enough to output the shader effect? (Little experience with glsl, sorry if this is a dumb question)

 gl_FragColor = original; 

And if it is this seems to be the position of the pixel to be shaded. Is there a way to pass this in automatically?

 vec2 fragCoord
SeanAbner
  • 63
  • 6
  • The shader compiler errors seem self-explanatory enough. Are you sure that `iChannel0..3` is legal? What happens when you change that and add a `#version XXX` directive? – alter_igel May 29 '19 at 18:18
  • It's not compiling due to those errors yes, I'm trying to find out what converts to what for SFML. The iChannel sampler is what OpenGL uses to bind texture bits to shaders but I'm not sure what to the equivalent for sfml is. Messing with the #version directive hasn't gotten anything, trying different ways to define it. – SeanAbner May 29 '19 at 18:46
  • As far as I know, SFML doesn't do anything special with shaders; it just wraps a set of pure OpenGL calls. [The documentation](https://www.sfml-dev.org/tutorials/2.5/graphics-shader.php#minimal-shaders) describes the most basic ins and outs of vertex and fragment shaders for SFML, but I can't spot anything specific to SFML. – alter_igel May 29 '19 at 19:09
  • 1
    After doing some searching, it appears `SamplerXX` is unique to ShaderToy. You're not the first one to have this problem. My guess is that ShaderToy does some kind of non-standard, non-portable text substitution and replaces `iChannel0..3` with something like `iChannel0, iChannel1, iChannel2, iChannel3`, but that's a shot in the dark. `SamplerXX` probably gets replaced with `Sampler2D` or `SamplerCube` but I couldn't tell you how. – alter_igel May 29 '19 at 19:27
  • It wouldn't be the first coding website to do something weird and hackish like this either. https://stackoverflow.com/questions/55269252/what-is-going-on-with-getsstdin-on-the-site-coderbyte – alter_igel May 29 '19 at 19:28
  • Alright I edited the sampler from "samplerXX" to "sampler2D" and it did fix that issue. The problem from there came that it was failing to link the shader. There was no definition to the void main(). When I add the empty main method the shader loads without errors. – SeanAbner May 29 '19 at 19:51
  • Edited to show new issues. – SeanAbner May 29 '19 at 19:56

0 Answers0