1 module nudsfml.graphics.shader;
2 
3 import bindbc.sfml.graphics;
4 
5 import nudsfml.graphics.texture;
6 import nudsfml.graphics.transform;
7 import nudsfml.graphics.color;
8 import nudsfml.graphics.glsl;
9 
10 import std.string;
11 
12 import nudsfml.system.inputstream;
13 import nudsfml.system.vector2;
14 import nudsfml.system.vector3;
15 //import nudsfml.system.err;
16 
17 
18 /**
19  * Shader class (vertex and fragment).
20  */
21 class Shader {
22     /// Types of shaders.
23     enum Type{
24         Vertex,  /// Vertex shader
25         Geometry,/// Geometry shader
26         Fragment /// Fragment (pixel) shader.
27     }
28 
29     package sfShader* sfPtr = null;
30 
31     /**
32      * Special type/value that can be passed to `setParameter`, and that
33      * represents the texture of the object being drawn.
34      */
35     struct CurrentTextureType {}
36     /// ditto
37     static CurrentTextureType CurrentTexture;
38 
39     /// Default constructor.
40     this() {
41         //creates an empty shader
42         //sfPtr=sfShader_construct();
43     }
44 
45     package this(sfShader* shader){
46         sfPtr = shader;
47     }
48 
49     /// Destructor.
50     ~this(){
51         //import nudsfml.system.config;
52         //mixin(destructorOutput);
53         sfShader_destroy(sfPtr);
54     }
55 
56     /**
57      * Load the vertex, geometry, or fragment shader from a file.
58      *
59      * This function loads a single shader, vertex, geometry, or fragment,
60      * identified by the second argument. The source must be a text file
61      * containing a valid shader in GLSL language. GLSL is a C-like language
62      * dedicated to OpenGL shaders; you'll probably need to read a good
63      * documentation for it before writing your own shaders.
64      *
65      * Params:
66      * 		filename	= Path of the vertex, geometry, or fragment shader file to load
67      * 		type		= Type of shader (vertex geometry, or fragment)
68      *
69      * Returns: true if loading succeeded, false if it failed.
70      */
71     bool loadFromFile(const(char)[] filename, Type type) {
72         import std.string;
73         if (sfPtr !is null){
74             sfShader_destroy(sfPtr);
75         }
76         
77         if(type == Type.Vertex){
78             sfPtr = sfShader_createFromFile(filename.toStringz, null,null);
79         }
80         else if(type == Type.Geometry){
81             sfPtr = sfShader_createFromFile(null,filename.toStringz,null);
82         }
83         else if(type == Type.Fragment){
84             sfPtr = sfShader_createFromFile(null,null, filename.toStringz);
85         }
86         
87         return sfPtr !is null;
88     }
89 
90     /**
91      * Load both the vertex and fragment shaders from files.
92      *
93      * This function loads both the vertex and the fragment shaders. If one of
94      * them fails to load, the shader is left empty (the valid shader is
95      * unloaded). The sources must be text files containing valid shaders in
96      * GLSL language. GLSL is a C-like language dedicated to OpenGL shaders;
97      * you'll probably need to read a good documentation for it before writing
98      * your own shaders.
99      *
100      * Params:
101      * 		vertexShaderFilename	= Path of the vertex shader file to load
102      * 		fragmentShaderFilename	= Path of the fragment shader file to load
103      *
104      * Returns: true if loading succeeded, false if it failed.
105      */
106     bool loadFromFile(const(char)[] vertexShaderFilename, const(char)[] fragmentShaderFilename){
107         if(sfPtr !is null){
108             sfShader_destroy(sfPtr);
109         }
110         sfPtr = sfShader_createFromFile(vertexShaderFilename.toStringz, null, fragmentShaderFilename.toStringz);
111         return sfPtr !is null;
112     }
113 
114     /**
115      * Load the vertex, geometry, and fragment shaders from files.
116      *
117      * This function loads the vertex, geometry and the fragment shaders. If one
118      * of them fails to load, the shader is left empty (the valid shader is
119      * unloaded). The sources must be text files containing valid shaders in
120      * GLSL language. GLSL is a C-like language dedicated to OpenGL shaders;
121      * you'll probably need to read a good documentation for it before writing
122      * your own shaders.
123      *
124      * Params:
125      * 		vertexShaderFilename	= Path of the vertex shader file to load
126      * 		geometryShaderFilename	= Path of the geometry shader file to load
127      * 		fragmentShaderFilename	= Path of the fragment shader file to load
128      *
129      * Returns: true if loading succeeded, false if it failed.
130      */
131     /*bool loadFromFile(const(char)[] vertexShaderFilename, const(char)[] geometryShaderFilename, const(char)[] fragmentShaderFilename)
132     {
133         return sfShader_loadAllFromFile(sfPtr, vertexShaderFilename.ptr, vertexShaderFilename.length,
134                                          geometryShaderFilename.ptr, geometryShaderFilename.length,
135                                          fragmentShaderFilename.ptr, fragmentShaderFilename.length);
136     }*/
137 
138     /**
139      * Load the vertex, geometry, or fragment shader from a source code in memory.
140      *
141      * This function loads a single shader, vertex, geometry, or fragment,
142      * identified by the second argument. The source code must be a valid shader
143      * in GLSL language. GLSL is a C-like language dedicated to OpenGL shaders;
144      * you'll probably need to read a good documentation for it before writing
145      * your own shaders.
146      *
147      * Params:
148      * 		shader	= String containing the source code of the shader
149      * 		type	= Type of shader (vertex geometry, or fragment)
150      *
151      * Returns: true if loading succeeded, false if it failed.
152      */
153     bool loadFromMemory(const(char)[] shader, Type type)
154     {
155         if(sfPtr !is null){
156             sfShader_destroy(sfPtr);
157         }
158 
159         if(type == Type.Vertex){
160             sfPtr = sfShader_createFromMemory(shader.toStringz, null, null);
161         }
162         else if(type == Type.Geometry){
163             sfPtr = sfShader_createFromMemory(null, shader.toStringz, null);
164         }
165         else if(type == Type.Fragment){
166             sfPtr = sfShader_createFromMemory(null, null, shader.toStringz);
167         }
168 
169         return sfPtr !is null;
170     }
171 
172     /**
173      * Load both the vertex and fragment shaders from source codes in memory.
174      *
175      * This function loads both the vertex and the fragment shaders. If one of
176      * them fails to load, the shader is left empty (the valid shader is
177      * unloaded). The sources must be valid shaders in GLSL language. GLSL is a
178      * C-like language dedicated to OpenGL shaders; you'll probably need to read
179      * a good documentation for it before writing your own shaders.
180      *
181      * Params:
182      * 	vertexShader   = String containing the source code of the vertex shader
183      * 	fragmentShader = String containing the source code of the fragment
184                          shader
185      *
186      * Returns: true if loading succeeded, false if it failed.
187      */
188     bool loadFromMemory(const(char)[] vertexShader, const(char)[] geometryShader, const(char)[] fragmentShader)
189     {
190         if(sfPtr !is null){
191             sfShader_destroy(sfPtr);
192         }
193 
194         sfPtr = sfShader_createFromMemory(vertexShader.toStringz, geometryShader.toStringz, fragmentShader.toStringz);
195 
196         return sfPtr !is null;
197     }
198 
199 
200 }