I'm using a lib written in C that allows me to read and write midi-files. Although I found an other lib written in C++ that works for me I'm still struggling with the fact: How could I have used the C lib with objects/classes. The lib has a call that takes the path to the midi file and then some function pointers that get called for specific midi-event-types. So it will look like this (abstract):

int main( int argc, char** args )
{
    readMidi( args[ 1 ], onMidiEvent, onSysEvent, onError, ... );
}

I tried to use a pointer to an instance of a class that collects the played notes:

class MidiNoteList;

template < MidiNoteList* VMidi > onError( short errmsg, char* msg ) { ... }
...

int main( int argc, char** args )
{
    MidiNoteList* m( new MidiNoteList( ) );
    readMidi( args[ 1 ], onMidiEvent< m >, onSysEvent< m >, onError< m >, ... );
}

GCC says that m can't be used as constant expression. I understand that m has to be constant at compile time so I'm sure why I can't make it like that. But how can I solve this "problem" in an other way?

有帮助吗?

解决方案

Usually such libraries use an extra void * argument that is passed to the function that takes the function pointers and is passed back to all the callback functions. If you have that, you can use it to pass your object pointer, casting it to void and back:

class MyObject;
void errCallback(void *m, short errcode, char *errmsg) {
    static_cast<MyObject *>(m)->error(errcode, errmsg);
}

    :
    MyObject *m = new MyObject();
    callLibrary(..., errCallback, m, ...);

If the library doesn't give you that extra argument, you have a problem -- the only other way to get extra data into the callback function is to use a global variable:

static MyObject *m;
void errCallback(short errcode, char *errmsg) {
    m->error(errcode, errmsg);
}
    :
    m = new MyObject();
    callLibrary(..., errCallback, ...);

The problem here being that you need to declare a new callback function (and global var) for each distinct object that you want to have receiving callbacks. If you create many such objects dynamically, that becomes unwieldy to manage.

许可以下: CC-BY-SA归因
不隶属于 StackOverflow
scroll top