
/*! \addtogroup interfaceC interface C openGL

## une api3d est...

un ensemble de fonctions. openGL est utilisable à travers un ensemble de fonctions C, ce qui signifie, pas de surchage, 
mais une famille de fonctions, des types opaques, pas d'objet, mais des identifiants.

une interface C++ pourrait ressembler à ça :
\code
Context *context= new Context();

std::vector<Point> positions= { ... };
Buffer *buffer= context->createBuffer();
buffer->data(positions);
\endcode

tout est explicite, on connait le contexte, le buffer, etc.

la version C pur pourrait ressembler à ça :
\code
struct Context *context= context_create();

Point positions[]= { ... };
struct Buffer *buffer= context_createBuffer(context);
buffer_data(buffer, sizeof(positions), positions);
\endcode

tout est explicite, mais un peu plus long à écrire.

l'interface d'openGL utilise une _convention_ différente : au lieu de rendre explicite l'objet / la structure manipulée, elle est 
d'abord "sélectionnée" pour une opération particulière, puis manipulée implicitement :
\code
createContext();                                // crée un contexte, et le sélectionne, 

uint buffer= createBuffer();                    // crée un buffer, représenté par un identifiant numérique, parametre implicite, context
bindBuffer(0, buffer);                          // sélectionne le buffer, pour une utilisation particulière, parametre implicite, buffer

Point positions[]= { ... };
bufferData(0, sizeof(positions), positions);    // alloue le buffer et l'initialise avec le contenu de positions, parametre implicite, buffer.
// le buffer manipulé est celui sélectionné sur l'attribut 0...
\endcode

ce qui permet d'obtenir une syntaxe compacte, mais peut être source de nombreuses erreurs, si l'on n'y prête pas attention.

## pas de surcharge 

autre détail important, il n'y a pas de surchage en C, on ne peut écrire ça pour modifier la valeur d'un paramètre de shader :

\code
Program *program= context->createProgram( ... );
program->uniform("color", Color(1, 1, 0));      // affecter une couleur
program->uniform("time", 12);                   // affecter un float
\endcode

ni ça :
\code
struct Program *program= context_createProgram( context, ... );
program_uniform(program, "color", make_color(1, 1, 0));
program_uniform(program, "time", 12);
\endcode

mais plutot ça :
\code
// creer le shader program
uint program= createProgram( ... );
// selectionner le shader program
use_program(program);

// modifier les uniforms
uniform3f("color", 1.0f, 1.0f, 0.0f);   // parametre implicite, program, surcharge 3 float
uniform1f("time", 12.0f);               // parametre implicite, program, surcharge 1 float
\endcode

chaque surcharge est nommée explicitement, puisque seul le nom de la fonction est utilisé. selon le type de valeur à manipuler,
les noms de fonctions sont décorés par un suffixe indiquant le nombre de paramètres (1, 2, 3, ou 4) et leur type (f pour float, 
i pour int, u pour unsigned int, v pour vector, un pointeur sur une ou plusieurs valeurs, etc.)


## création des objets openGL

pour dessiner, il faut en général créer plusieurs types d'objets openGL, la démarche est toujours la même :
    - créer un ou plusieurs identifiants, type `GLuint`, cf la famille de fonctions glGenXXX( ),
    - sélectionner l'objet pour le configurer.

exemple, pour créer plusieurs buffers openGL, cf `glGenBuffers( )` :
\code
GLuint buffers[4];
glGenBuffers(4, buffers);
\endcode

### créer un buffer 

pour créer un seul buffer, il suffit de passer le pointeur sur l'identifiant :
\code
GLuint buffer;
glGenBuffers(1, &buffer);
\endcode

le buffer sera ensuite sélectionné avec `glBindBuffer( )`. cf \ref tuto4GL pour plus de détails sur l'utilisation des buffers.


### créer un vertex array object

\code
GLuint vao;
glGenVertexArrays(1, &vao);
\endcode

le vao sera ensuite sélectionné avec `glBindVertexArray( )`. cf \ref tuto4GL pour plus de détails.


### créer une texture

\code
GLuint texture;
glGenTextures(1, &texture);
\endcode

la texture sera ensuite sélectionnée avec `glBindTexture( )`, cf \ref tuto5GL.


### créer un shader, un shader program

les shaders et les programs sont un peu à part, leur fonction de création ne crée qu'un seul objet à la fois :
\code
GLuint vertex_shader= glCreateShader(GL_VERTEX_SHADER);
GLuint shader_program= glCreateProgram();
\endcode

le program sera sélectionné avec `glUseProgram( )`. cf \ref tuto2GL pour les détails.

# documentation complète 

l'api complète et sa documentation est consultable sur [opengl.org](https://www.opengl.org/sdk/docs/man/)
 */
