C++ (gcc) Preprocessor Macro: Automatic function generation - OpenGL Shader "Swizzle" Syntax

Viewed 104

Let me start this question by stating that I don't know if what I am aiming to do is possible, and if it is, I don't know how to find the information.

The OpenGL shading language permits a syntax called swizzeling.

If one has a vector

v {x, y, z}

one can construct a new vector by doing

v.xxx, v.xxy, v.xxz, v.xyx, ... etc

There are a total of 3 * 3 * 3 = 27 possible options.

I would like to implement this kind of feature in my own vector library.

Here is one example of such a function:

vec3<T> xxx() const
{
    vec3<T> v(x, x, x);
    return v;
}

I could then write another 26 functions to account for all possible options, but this seems like something I should be able to do using a macro. For example, something like

vec3<T> (#A)(#B)(#C)() const
{
    vec3<T> v(#A, #B, #C);
    return v;
}

where #A, #B and #C are 3 single characters which the compiler expands with possible options being x, y and z.

Is such a thing possible with gcc/g++ ?

2 Answers
#define SWIZZLE(a,b,c)\
vec3<T> a##b##c() const\
{\
    vec3<T> v(a, b, c);\
    return v;\
}

SWIZZLE(x,x,y)
SWIZZLE(x,x,y)
SWIZZLE(x,x,z)
...

For more info on the ## operator, search for "token pasting".

You can define

#define make_method(x,y,z) vec3<T> x##y##z () const { return { x , y, z}; }

Such that

make_method(a,b,c)

expands to

vec3<T> abc () const { return { a , b, c}; }

Now you just have to list all 27 combinations like this:

make_method(x,x,x);
make_method(x,x,y);
make_method(x,x,z);
make_method(x,y,x);
// ....
Related