Question

class IShaderParam{
 public:
 std::string name_value;
};

template<class TParam>
class TShaderParam:public IShaderParam{

public:
 void (TShaderParam::*send_to_shader)( const TParam&,const std::string&);
 TShaderParam():send_to_shader(NULL){}
 TParam value;
 void up_to_shader();
};
typedef TShaderParam<float> FloatShaderParam;
typedef TShaderParam<D3DXVECTOR3> Vec3ShaderParam;

In another class, I have a vector of IShaderParams* and functions that i want to send to "send_to_shader". I'm trying assign the reference of these functions like this:

Vec3ShaderParam *_param = new Vec3ShaderParam;
_param->send_to_shader = &TShader::setVector3;

This is the function:

void TShader::setVector3(const D3DXVECTOR3 &vec, const std::string &name){

 //...
}

And this is the class with IshaderParams*:

class TShader{

 std::vector<IShaderParam*> params;

public:
 Shader effect;
 std::string technique_name;

 TShader(std::string& afilename):effect(NULL){};
 ~TShader();
 void setVector3(const D3DXVECTOR3 &vec, const std::string &name);

When I compile the project with Visual Studio C++ Express 2008 I recieve this error:

Error 2 error C2440: '=' :can't make the conversion 'void (__thiscall TShader::* )(const D3DXVECTOR3 &,const std::string &)' a 'void (__thiscall TShaderParam::* )(const TParam &,const std::string &)' c:\users\isagoras\documents\mcv\afoc\shader.cpp 127

Can I do the assignment? No? I don't know how :-S Yes, I know that I can achieve the same objective with other techniques, but I want to know how can I do this..

Was it helpful?

Solution

Presumably TShader::send_to_shader is a c-style function pointer?

Member functions cannot be used as function pointer callbacks - they require a this parameter.

Static member functions and global functions can be used as function pointers.

So you can either

  1. pass the this manually as a parameter to a static function callback, which in turn invokes the member function on the appropriate instance

  2. use an interface instead of a function

  3. use a functor

All three require slight architectural changes.

OTHER TIPS

That's because you are trying to use incompatible pointers. setVector3 is a TShader method but send_to_shader wants a TShaderParam method.

Not knowing exactly what you want, you can get your example to compile by changing this:

void (TShaderParam::*send_to_shader)( const TParam&,const std::string&);

to this:

void (TShader::*send_to_shader)( const TParam&,const std::string&);

Pointers to member functions are a bit rigid. It would help if you showed us the line of code that generates the error, but just looking at it,

Error 2 error C2440: '=' :can't make the conversion 'void (__thiscall TShader::* )(const D3DXVECTOR3 &,const std::string &)' a 'void (__thiscall TShaderParam::* )(const TParam &,const std::string &)' c:\users\isagoras\documents\mcv\afoc\shader.cpp 127

So you've passed a void (TShader::* )(const D3DXVECTOR3 &,const std::string &) but someone expects a void (TShaderParam::* )(const TParam &,const std::string &).

You need to reimplement setVector3 as a method of a type derived from TShaderParam and extract your D3DXVECTOR3 & from the first argument, which must be a TParam. (But if it's just passing back your own value, you can static_cast it to your own type derived from TParam.)

Hope this helps!

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top