Torque3D Documentation / _generateds / shaderCompGLSL.cpp

shaderCompGLSL.cpp

Engine/source/shaderGen/GLSL/shaderCompGLSL.cpp

More...

Public Functions

Detailed Description

Public Functions

initDeprecadedDefines()

  1
  2//-----------------------------------------------------------------------------
  3// Copyright (c) 2012 GarageGames, LLC
  4//
  5// Permission is hereby granted, free of charge, to any person obtaining a copy
  6// of this software and associated documentation files (the "Software"), to
  7// deal in the Software without restriction, including without limitation the
  8// rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
  9// sell copies of the Software, and to permit persons to whom the Software is
 10// furnished to do so, subject to the following conditions:
 11//
 12// The above copyright notice and this permission notice shall be included in
 13// all copies or substantial portions of the Software.
 14//
 15// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
 16// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
 17// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
 18// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
 19// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
 20// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
 21// IN THE SOFTWARE.
 22//-----------------------------------------------------------------------------
 23
 24#include "platform/platform.h"
 25#include "shaderGen/GLSL/shaderCompGLSL.h"
 26
 27#include "shaderGen/shaderComp.h"
 28#include "shaderGen/langElement.h"
 29#include "gfx/gfxDevice.h"
 30#include "gfx/gl/gfxGLVertexAttribLocation.h"
 31
 32
 33Var * AppVertConnectorGLSL::getElement(   RegisterType type, 
 34                                          U32 numElements, 
 35                                          U32 numRegisters )
 36{
 37   switch( type )
 38   { 
 39      case RT_POSITION:
 40      {
 41         Var *newVar = new Var;
 42         mElementList.push_back( newVar );
 43         newVar->setConnectName( "vPosition" );
 44         return newVar;
 45      }
 46
 47      case RT_NORMAL:
 48      {
 49         Var *newVar = new Var;
 50         mElementList.push_back( newVar );
 51         newVar->setConnectName( "vNormal" );
 52         return newVar;
 53      }
 54
 55      case RT_BINORMAL:
 56      {
 57         Var *newVar = new Var;
 58         mElementList.push_back( newVar );
 59         newVar->setConnectName( "vBinormal" );
 60         return newVar;
 61      }      
 62
 63      case RT_COLOR:
 64      {
 65         Var *newVar = new Var;
 66         mElementList.push_back( newVar );
 67         newVar->setConnectName( "vColor" );
 68         return newVar;
 69      }
 70
 71      case RT_TANGENT:
 72      {
 73         Var *newVar = new Var;
 74         mElementList.push_back( newVar );         
 75         newVar->setConnectName( "vTangent" );
 76         return newVar;
 77      }
 78
 79      case RT_TANGENTW:
 80      {
 81         Var *newVar = new Var;
 82         mElementList.push_back( newVar );         
 83         newVar->setConnectName( "vTangentW" );
 84         return newVar;
 85      }
 86
 87      case RT_TEXCOORD:
 88      {
 89         Var *newVar = new Var;
 90         mElementList.push_back( newVar );
 91         
 92         char out[32];
 93         dSprintf( (char*)out, sizeof(out), "vTexCoord%d", mCurTexElem );
 94         newVar->setConnectName( out );
 95         newVar->constNum = mCurTexElem;
 96         newVar->arraySize = numElements;
 97
 98         if ( numRegisters != -1 )
 99            mCurTexElem += numRegisters;
100         else
101            mCurTexElem += numElements;
102
103         return newVar;
104      }
105
106      case RT_BLENDINDICES:
107      {
108         Var *newVar = new Var;
109         newVar->constNum = mCurBlendIndicesElem;
110         mElementList.push_back(newVar);
111         char out[32];
112         const U32 blendIndicesOffset = Torque::GL_VertexAttrib_BlendIndex0 - Torque::GL_VertexAttrib_TexCoord0;
113         dSprintf((char*)out, sizeof(out), "vTexCoord%d", blendIndicesOffset + mCurBlendIndicesElem);
114         mCurBlendIndicesElem += 1;
115         newVar->setConnectName(out);
116         return newVar;
117      }
118
119      case RT_BLENDWEIGHT:
120      {
121         Var *newVar = new Var;
122         newVar->constNum = mCurBlendWeightsElem;
123         mElementList.push_back(newVar);
124         char out[32];
125         const U32 blendWeightsOffset = Torque::GL_VertexAttrib_BlendWeight0 - Torque::GL_VertexAttrib_TexCoord0;
126         dSprintf((char*)out, sizeof(out), "vTexCoord%d", blendWeightsOffset + mCurBlendWeightsElem);
127         mCurBlendWeightsElem += 1;
128         newVar->setConnectName(out);
129         return newVar;
130      }
131
132      default:
133         break;
134   }
135   
136   return NULL;
137}
138
139void AppVertConnectorGLSL::sortVars()
140{
141   // Not required in GLSL
142}
143
144void AppVertConnectorGLSL::setName( char *newName )
145{
146   dStrcpy( (char*)mName, newName, 32 );
147}
148
149void AppVertConnectorGLSL::reset()
150{
151   for( U32 i=0; i<mElementList.size(); i++ )
152   {
153      mElementList[i] = NULL;
154   }
155
156   mElementList.setSize( 0 );
157   mCurTexElem = 0;
158}
159
160void AppVertConnectorGLSL::print( Stream &stream, bool isVertexShader )
161{
162   if(!isVertexShader)
163      return;
164
165   U8 output[256];
166
167   // print struct
168   dSprintf( (char*)output, sizeof(output), "struct VertexData\r\n" );
169   stream.write( dStrlen((char*)output), output );
170   dSprintf( (char*)output, sizeof(output), "{\r\n" );
171   stream.write( dStrlen((char*)output), output );
172
173   for( U32 i=0; i<mElementList.size(); i++ )
174   {
175      Var *var = mElementList[i];
176      
177      if( var->arraySize == 1)
178      {         
179         dSprintf( (char*)output, sizeof(output), "   %s %s;\r\n", var->type, (char*)var->name );
180         stream.write( dStrlen((char*)output), output );
181      }
182      else
183      {
184         dSprintf( (char*)output, sizeof(output), "   %s %s[%d];\r\n", var->type, (char*)var->name, var->arraySize );
185         stream.write( dStrlen((char*)output), output );
186      }
187   }
188
189   dSprintf( (char*)output, sizeof(output), "} IN;\r\n\r\n" );
190   stream.write( dStrlen((char*)output), output );   
191
192   // print in elements
193   for( U32 i=0; i<mElementList.size(); i++ )
194   {
195      Var *var = mElementList[i];
196      
197      for(int j = 0; j < var->arraySize; ++j)
198      {        
199         const char *name = j == 0 ? var->connectName : avar("vTexCoord%d", var->constNum + j) ;
200         dSprintf( (char*)output, sizeof(output), "in %s %s;\r\n", var->type, name );
201         stream.write( dStrlen((char*)output), output );         
202      }
203
204      dSprintf( (char*)output, sizeof(output), "#define IN_%s IN.%s\r\n", var->name, var->name ); // TODO REMOVE
205      stream.write( dStrlen((char*)output), output );
206   }
207   const char* newLine ="\r\n";
208   stream.write( dStrlen((char*)newLine), newLine );
209}
210
211Var * VertPixelConnectorGLSL::getElement( RegisterType type, 
212                                          U32 numElements, 
213                                          U32 numRegisters )
214{
215   switch( type )
216   {
217   case RT_POSITION:
218      {
219         Var *newVar = new Var;
220         mElementList.push_back( newVar );
221         newVar->setConnectName( "POSITION" );
222         return newVar;
223      }
224
225   case RT_NORMAL:
226      {
227         Var *newVar = new Var;
228         mElementList.push_back( newVar );
229         newVar->setConnectName( "NORMAL" );
230         return newVar;
231      }
232
233   case RT_COLOR:
234      {
235         Var *newVar = new Var;
236         mElementList.push_back( newVar );
237         newVar->setConnectName( "COLOR" );
238         return newVar;
239      }
240
241   /*case RT_BINORMAL:
242      {
243         Var *newVar = new Var;
244         mElementList.push_back( newVar );
245         newVar->setConnectName( "BINORMAL" );
246         return newVar;
247      }
248
249   case RT_TANGENT:
250      {
251         Var *newVar = new Var;
252         mElementList.push_back( newVar );
253         newVar->setConnectName( "TANGENT" );
254         return newVar;
255      }   */
256
257   case RT_TEXCOORD:
258   case RT_BINORMAL:
259   case RT_TANGENT:
260      {
261         Var *newVar = new Var;
262         newVar->arraySize = numElements;
263
264         char out[32];
265         dSprintf( (char*)out, sizeof(out), "TEXCOORD%d", mCurTexElem );
266         newVar->setConnectName( out );
267
268         if ( numRegisters != -1 )
269            mCurTexElem += numRegisters;
270         else
271            mCurTexElem += numElements;
272         
273         mElementList.push_back( newVar );
274         return newVar;
275      }
276
277   default:
278      break;
279   }
280
281   return NULL;
282}
283
284void VertPixelConnectorGLSL::sortVars()
285{
286   // Not needed in GLSL
287}
288
289void VertPixelConnectorGLSL::setName( char *newName )
290{
291   dStrcpy( (char*)mName, newName, 32 );
292}
293
294void VertPixelConnectorGLSL::reset()
295{
296   for( U32 i=0; i<mElementList.size(); i++ )
297   {
298      mElementList[i] = NULL;
299   }
300
301   mElementList.setSize( 0 );
302   mCurTexElem = 0;
303}
304
305void VertPixelConnectorGLSL::print( Stream &stream, bool isVerterShader )
306{
307   // print out elements
308   for( U32 i=0; i<mElementList.size(); i++ )
309   {
310      U8 output[256];
311
312      Var *var = mElementList[i];
313      if(!String::compare((const char*)var->name, "gl_Position"))
314         continue;
315
316      if(var->arraySize <= 1)
317         dSprintf((char*)output, sizeof(output), "%s %s _%s_;\r\n", (isVerterShader ? "out" : "in"), var->type, var->connectName);
318      else
319         dSprintf((char*)output, sizeof(output), "%s %s _%s_[%d];\r\n", (isVerterShader ? "out" : "in"),var->type, var->connectName, var->arraySize);      
320
321      stream.write( dStrlen((char*)output), output );
322   }
323
324   printStructDefines(stream, !isVerterShader);
325}
326
327void VertPixelConnectorGLSL::printOnMain( Stream &stream, bool isVerterShader )
328{
329   if(isVerterShader)
330      return;
331
332   const char *newLine = "\r\n";
333   const char *header = "   //-------------------------\r\n";
334   stream.write( dStrlen((char*)newLine), newLine );
335   stream.write( dStrlen((char*)header), header );
336
337   // print out elements
338   for( U32 i=0; i<mElementList.size(); i++ )
339   {
340      U8 output[256];
341
342      Var *var = mElementList[i];
343      if(!String::compare((const char*)var->name, "gl_Position"))
344         continue;
345  
346      dSprintf((char*)output, sizeof(output), "   %s IN_%s = _%s_;\r\n", var->type, var->name, var->connectName);      
347
348      stream.write( dStrlen((char*)output), output );
349   }
350
351   stream.write( dStrlen((char*)header), header );
352   stream.write( dStrlen((char*)newLine), newLine );
353}
354
355
356void AppVertConnectorGLSL::printOnMain( Stream &stream, bool isVerterShader )
357{
358   if(!isVerterShader)
359      return;   
360
361   const char *newLine = "\r\n";
362   const char *header = "   //-------------------------\r\n";
363   stream.write( dStrlen((char*)newLine), newLine );
364   stream.write( dStrlen((char*)header), header );
365
366   // print out elements
367   for( U32 i=0; i<mElementList.size(); i++ )
368   {
369      Var *var = mElementList[i];
370      U8 output[256];  
371
372      if(var->arraySize <= 1)
373      {
374         dSprintf((char*)output, sizeof(output), "   IN.%s = %s;\r\n", var->name, var->connectName);
375         stream.write( dStrlen((char*)output), output );
376      }
377      else
378      {
379         for(int j = 0; j < var->arraySize; ++j)
380         {
381            const char *name = j == 0 ? var->connectName : avar("vTexCoord%d", var->constNum + j) ;
382            dSprintf((char*)output, sizeof(output), "   IN.%s[%d] = %s;\r\n", var->name, j, name );
383            stream.write( dStrlen((char*)output), output );
384         }
385      }
386   }
387
388   stream.write( dStrlen((char*)header), header );
389   stream.write( dStrlen((char*)newLine), newLine );
390}
391
392
393
394
395Vector<String> initDeprecadedDefines()
396{
397   Vector<String> vec;
398   vec.push_back( "isBack"); 
399   return vec;
400}
401
402void VertPixelConnectorGLSL::printStructDefines( Stream &stream, bool in )
403{
404   const char* connectionDir = in ? "IN" : "OUT";
405
406   static Vector<String> deprecatedDefines = initDeprecadedDefines();
407
408   const char *newLine = "\r\n";
409   const char *header = "// Struct defines\r\n";
410   stream.write( dStrlen((char*)newLine), newLine );
411   stream.write( dStrlen((char*)header), header );
412
413   // print out elements
414   for( U32 i=0; i<mElementList.size(); i++ )
415   {
416      U8 output[256];
417
418      Var *var = mElementList[i];
419      if(!String::compare((const char*)var->name, "gl_Position"))
420         continue;      
421  
422      if(!in)
423      {
424         dSprintf((char*)output, sizeof(output), "#define %s_%s _%s_\r\n", connectionDir, var->name, var->connectName);
425         stream.write( dStrlen((char*)output), output );
426         continue;
427      }
428   }
429
430   stream.write( dStrlen((char*)newLine), newLine );
431}
432
433void VertexParamsDefGLSL::print( Stream &stream, bool isVerterShader )
434{
435   // find all the uniform variables and print them out
436   for( U32 i=0; i<LangElement::elementList.size(); i++)
437   {
438      Var *var = dynamic_cast<Var*>(LangElement::elementList[i]);
439      if( var )
440      {
441         if( var->uniform )
442         {
443            U8 output[256];
444            if(var->arraySize <= 1)
445               dSprintf((char*)output, sizeof(output), "uniform %-8s %-15s;\r\n", var->type, var->name);
446            else
447               dSprintf((char*)output, sizeof(output), "uniform %-8s %-15s[%d];\r\n", var->type, var->name, var->arraySize);
448
449            stream.write( dStrlen((char*)output), output );
450         }
451      }
452   }
453
454   const char *closer = "\r\n\r\nvoid main()\r\n{\r\n";
455   stream.write( dStrlen(closer), closer );
456}
457
458void PixelParamsDefGLSL::print( Stream &stream, bool isVerterShader )
459{
460   // find all the uniform variables and print them out
461   for( U32 i=0; i<LangElement::elementList.size(); i++)
462   {
463      Var *var = dynamic_cast<Var*>(LangElement::elementList[i]);
464      if( var )
465      {
466         if( var->uniform )
467         {
468            U8 output[256];
469            if(var->arraySize <= 1)
470               dSprintf((char*)output, sizeof(output), "uniform %-8s %-15s;\r\n", var->type, var->name);
471            else
472               dSprintf((char*)output, sizeof(output), "uniform %-8s %-15s[%d];\r\n", var->type, var->name, var->arraySize);
473
474            stream.write( dStrlen((char*)output), output );
475         }
476      }
477   }
478
479   const char *closer = "\r\nvoid main()\r\n{\r\n";
480   stream.write( dStrlen(closer), closer );
481
482   for( U32 i=0; i<LangElement::elementList.size(); i++)
483   {
484      Var *var = dynamic_cast<Var*>(LangElement::elementList[i]);
485      if( var )
486      {
487         if( var->uniform && !var->sampler)
488         {
489            U8 output[256];
490            if(var->arraySize <= 1)
491               dSprintf((char*)output, sizeof(output), "   %s %s = %s;\r\n", var->type, var->name, var->name);
492            else
493               dSprintf((char*)output, sizeof(output), "   %s %s[%d] = %s;\r\n", var->type, var->name, var->arraySize, var->name);
494
495            stream.write( dStrlen((char*)output), output );
496         }
497      }
498   }
499}
500