Reputation: 4869
So I have a vec4 class that uses members x,y,z,w which you can access using
point.x point.y etc.
However I want to reuse this vec4 class to be my color class (it already supports scalar multiplication, operator overloading lots of other nice stuff) I just want to be able to refer to the members using another notation:
color.r color.g color.b
etc.
Is there anyway I can do this using a macro or other syntactic sugar?
Upvotes: 0
Views: 963
Reputation: 136208
You can easily do that with standalone accessor functions:
struct vec4 { double x, y, z; };
double& get_r(vec4& v) { return v.z; }
// and so on
Upvotes: 0
Reputation: 67479
Unless you have a good amount of common behavior between a vector and a color I think this is a bad idea. But since you asked, here is a possible way to do that.
If you make the x, y, z and w members private and provide accessor methods to get to them, then it is easy to provide two alternative ways to refer to the same member variables. For example:
class vec4 {
private:
float _x, _y, _z, _w;
public:
// vector getter/setters
float& x() { return _x; }
float& y() { return _y; }
float& z() { return _z; }
float& w() { return _w; }
// color getter/setters
float& r() { return _x; }
float& g() { return _y; }
float& b() { return _z; }
float& a() { return _w; }
};
vec4 my_color;
my_color.r() = 1.0f;
my_color.g() = 0.0f;
my_color.b() = 0.0f;
my_color.a() = 1.0f;
Upvotes: 0
Reputation: 6329
If you are using Visual Studio (and are sure that it is the only target IDE...) you can use the following:
#include <cassert>
union vec4
{
struct
{
float x;
float y;
float z;
float w;
};
struct
{
float r;
float g;
float b;
float a;
};
};
int main()
{
vec4 vec = { 0 };
vec.y = 10.0f;
assert(vec.g == 10.0f);
return 0;
}
It will yield warnings warning C4201: nonstandard extension used : nameless struct/union
, though you can disable it.
EDIT: as it turns out gcc supports this extension as well.
Upvotes: 1