Question GCC, stringification et GLSL en ligne?


Je voudrais déclarer les chaînes de shader GLSL en ligne en utilisant la macro-chaîne:

#define STRINGIFY(A)  #A
const GLchar* vert = STRINGIFY(
#version 120\n
attribute vec2 position;
void main()
{
    gl_Position = vec4( position, 0.0, 1.0 );
}
);

Cela construit et fonctionne bien avec VS2010 mais ne réussit pas à compiler gcc avec:

error: invalid preprocessing directive #version

Existe-t-il un moyen d'utiliser cette méthode de manière portable?

J'essaie d'éviter les citations par ligne:

const GLchar* vert = 
"#version 120\n"
"attribute vec2 position;"
"void main()"
"{"
"    gl_Position = vec4( position, 0.0, 1.0 );"
"}"
;

... et / ou suite de ligne:

const GLchar* vert = "\
#version 120\n                                 \
attribute vec2 position;                       \
void main()                                    \
{                                              \
    gl_Position = vec4( position, 0.0, 1.0 );  \
}                                              \
";

15
2017-12-14 04:14


origine


Réponses:


Malheureusement, avoir des directives de préprocesseur dans l'argument d'une macro n'est pas défini, vous ne pouvez donc pas le faire directement. Mais tant qu'aucun de vos shaders n'a besoin de directives de préprocesseur autres que #version, vous pourriez faire quelque chose comme:

#define GLSL(version, shader)  "#version " #version "\n" #shader

const GLchar* vert = GLSL(120,
    attribute vec2 position;
    void main()
    {
        gl_Position = vec4( position, 0.0, 1.0 );
    }
);

17
2017-12-14 07:40



Pouvez-vous utiliser C ++ 11? Si vous pouviez utiliser littéraux de chaînes brutes:

const GLchar* vert = R"END(
#version 120
attribute vec2 position;
void main()
{
    gl_Position = vec4( position, 0.0, 1.0 );
}
)END";

Pas besoin d'évasions ou de nouvelles lignes explicites. Ces chaînes commencent par un R (ou un r). Vous avez besoin d'un délimiteur (j'ai choisi FIN) entre la citation et la première parenthèse pour échapper les parenthèses que vous avez dans l'extrait de code.


22
2017-12-14 04:19



Le problème est dû aux macros de prétraitement gcc destinées à GLSL. Travailler pour moi en utilisant des directives de préprocesseur standard et d'échappement standard avec de nouvelles lignes dans le code GLSL.

#define STRINGIFY(A)  #A

const GLchar* vert = STRINGIFY(

\n#version 120\n
\n#define MY_MACRO 999\n

attribute vec2 position;
void main()
{
    gl_Position = vec4( position, 0.0, 1.0 );
}
);

5
2017-07-09 07:17



Pour atteindre cet objectif, j'ai utilisé sed. J'ai des fichiers séparés avec GLSL que j'édite (avec une coloration syntaxique correcte), et en même temps GLSL en ligne en C ++. Pas très cross plate-forme, mais avec msys cela fonctionne sous Windows.

En code C ++:

const GLchar* vert = 
#include "shader_processed.vert"
;

Dans Makefile:

shader_processed.vert: shader.vert
    sed -f shader.sed shader.vert > shader_processed.vert

programm: shader_processed.vert main.cpp
    g++ ...

shader.sed

s|\\|\\\\|g
s|"|\\"|g
s|$|\\n"|g
s|^|"|g

3
2017-12-14 07:38