11

私はこれがうまくいくことを知っています:

void myDisplay()
{
...
}
int main()
{
...
glutDisplayFunc(myDisplay)
...
}

そこで、作成したクラスに myDisplay() 関数を含めようとしました。将来、別のクラスでオーバーロードしたいからです。ただし、コンパイラは次のように不平を言います

argument of type 'void (ClassBlah::)()' does not match 'void(*)()' .

これが私が作ろうとしているものです:

class ClassBlah
{
   ....
   void myDisplay()
   ....
}
......
int main()
{

    ...
    ClassBlah blah
    glutDisplayFunc(blah.myDisplay)
    ...
}

この問題を解決する方法を知っている人はいますか? どうもありがとう。

4

5 に答える 5

9

まず、非静的メンバー関数には暗黙の「this」ポインターがあるため、void myDisplay()inClassBlahを静的に変更する必要があります。この制限を回避するのは厄介です。そのため、C++ の faq lite は回避しないと言っています。

次に、関数をとして渡すことができるはずですClassBlah::myDisplay

オーバーロードの動機 (つまり、実行時に実装をホットスワップするか、コンパイル時にのみ実装をホットスワップするか) に応じて、基本クラスへのポインターを含むユーティリティ "ハンドラー" 静的クラスを検討し、責任を委任することができます。それ。

于 2010-03-23T00:31:37.397 に答える
5

私は自分で C++ Glut エンジンを書いているこの問題に遭遇しました。これが私がそれを回避した方法です:

これらを私のprogram.cpp / main.cppの一番上に置きました

// Function prototypes
void doRendering( void );
void processMouse( int, int ) ;
void processMouseClick(int button, int state, int x, int y);
void keyboardInput(unsigned char c, int x, int y);

これらの関数を glut のコールバックに割り当てます。

glutDisplayFunc(doRendering);
glutIdleFunc(doRendering);
glutPassiveMotionFunc(processMouse);
glutMotionFunc(processMouse);
glutMouseFunc(processMouseClick);
glutKeyboardFunc(keyboardInput);

これらを独自に処理する独自のクラスを作成し、静的関数の内容がこのクラスのインスタンスでメソッドを呼び出すだけになるようにします。メイン関数は、メインにクラスの新しいインスタンスを作成する必要があります (私の場合は... App *newApp)。

void doRendering( void )
{
    newApp->updateScene();
    newApp->drawScene();
}

void processMouse(int x, int y)
{
    newApp->processMouse(x, y);
}

void processMouseClick(int button, int state, int x, int y)
{
    newApp->processMouseClick(button, state, x, y);
}

void keyboardInput(unsigned char c, int x, int y)
{
    newApp->keyboardInput(c, x, y);
}

それがそれを説明することを願っています。

于 2010-03-23T01:19:38.440 に答える
3

これを解決する私の方法は簡単です。
まず、メイン関数の前にポインターを作成します。
メイン関数の開始時に、クラスのインスタンスへのポインターを設定します。
次に、レンダリング用に新しく定義された関数で、グローバルポインターを使用してオブジェクトにアクセスできます。

/**
       Class argon is defined in external header file.
*/

Argon *argonPtr;

void renderScene();

int main()
{      
   Argon argon;
   argonPtr = &argon;

   glutDisplayFunc( render );  
}

void render()
{
   RenderStuff();
   argonPtr->Render();  
}

それがあなたのために働くことを願っています、私にとってはそうです。

于 2013-11-14T12:07:09.157 に答える
1

メンバー関数に Boost bind を使用できます。たとえば、メンバー関数でスレッドを作成できます。

class classA
{
public:
    void memberThreadFunc(int i);
};

void main()
{
    classA a;
    boost::thread( boost::bind(&classA::memberFunc, &a, 123) );
}
于 2010-03-23T00:55:31.427 に答える
0

できません。ではなくglutDisplayFunc型のパラメータを取ります。過剰摂取の原因を変える意思と能力がない限り、あなたは運が悪い.void(*)()void (ClassBlah::)()


コールバックを使用する多くの C API は、ユーザー指定のvoid*パラメーターをコールバックに渡します。これを使用して、クラスへのポインターを格納できます。次に、ユーザー データをクラス ポインターにキャストし、メンバー関数を呼び出すフリー関数を渡すことができます。ただし、 glut の設計方法では、それが許可されていません。

于 2010-03-23T01:10:15.297 に答える