vanandel@stout.atd.ucar.edu (Joe Van Andel) (08/21/90)
I am writing an application that uses the Athena widget set, but I would like to write this application in C++ (using g++), if possible. (Yes, I know about the Interviews toolkit, but it doesn't have the ease of use of the Widget Creation Language toolkit, nor does it let a user tailor an application by using X11 resources. Solbourne's OI also looks interesting, but I can't afford to pay AT&T $10000 + just now.) I've heard rumors of some University writing a C++ binding for Motif, that will be released with X11 at some future date. Does anyone know when this might be available? Does this toolkit allow access to the Xt resource database? The biggest hassle I see with using C++ and a non C++ toolkit is that of using callbacks. Since the callbacks are designed to be C functions, how can I possibly invoke C++ functions, particularly if I want to invoke the method of a given object? If I have to, I'll write a bit of "glue" in "C", but I don't know how to do it. Obviously, if writing the glue is too tedious or difficult, using C++ just may not be worth the hassle. Surely, someone has solved the problem of calling a C++ function as a callback function! Does anyone have any other suggestions about how to program X11 applications, have access to the functionality of libXt, and still use C++ ? Thanks much. Please mail me responses, and I'll summarize the results. -- Joe VanAndel Internet:vanandel@ncar.ucar.edu NCAR - RSG P.O Box 3000 Fax: 303-497-2044 Boulder, CO 80307-3000 Voice: 303-497-2071
jp@aurora.com (Jorge Phillips) (08/21/90)
In article <8271@ncar.ucar.edu> vanandel@stout.atd.ucar.edu (Joe Van Andel) writes: >I am writing an application that uses the Athena widget set, but I would like >to write this application in C++ (using g++), if possible. > ...some stuff re. Interviews. >The biggest hassle I see with using C++ and a non C++ toolkit is that >of using callbacks. Since the callbacks are designed to be C >functions, how can I possibly invoke C++ functions, particularly if I >want to invoke the method of a given object? If I have to, I'll write a bit >of "glue" in "C", but I don't know how to do it. Obviously, if writing the >glue is too tedious or difficult, using C++ just may not be worth the hassle. > > ...more stuff... >-- > Joe VanAndel Internet:vanandel@ncar.ucar.edu I had the same problem a while ago while writing g++ code that used Xt widgets and library calls. Initially I thought of rewriting the Xt, Xlib, Xmu, etc. headers as C++ headers, like some people have suggested. Since I did not know of `protoize' and `unprotoize' yet, I gave up on this alternative and decided to use the glue approach. Basically the idea is to write your C++ program in such a way that after it performs all the necessary C++ object initializations, it relinquishes control through glue to an X main program. This program creates all widgets, establishes all callbacks (including those that go to C++ through glue), and enters its event loop, thus effectively driving the application from here on. Here is a code skeleton of how I implemented callbacks to g++ functions following this idea, using a glue file. Admittedly, the resulting code is not as clean and elegant an interface as I would like it to be, but it works quite fine! If you define a lean (i.e. well localized) interface between your C++ program and your X code, the glue file turns out to be quite small. E.g. for a 7,000+ line g++ program using a substantial number of widget classes and Xt and Xlib operations, the glue code turns out to be only 100 lines of includes and glue procedure definitions. I would appreciate any suggestions for a better (different, improved, etc.) interface mechanism. Has anybody tried protoizing X11 headers and writing ONLY c++ code that accesses Xt wdigets and primitives? -Jorge Encl: ========================== X INTERFACE (x.c) /* Xt-based client * Code skeleton */ #include <X11/...> /* all Xt, Xlib, Xmu, Xaw, etc. headers needed */ Widget w1; Widget w2; .... /* declare all widgets */ void W1Callback(Widget w, caddr_t cl, caddr_t cd) { /* here goes code that accesses widgets and X stuff */ XGlueFoo(..args..); /* call c++ callback through glue code */ /* here goes any post-callback code, if needed. */ } /* X driver portion main function */ int XMain(int argc, char** argv) { /* local decls */ top = XtInitialize(...); w1 = XtCreateManagedWidget("w1", ...someWidgetClass..., top, NULL, 0); XtAddCallback(w1, XtNcallback, W1Callback, 0); /* ...more Xt stuff... */ XtRealizeWidget(top); XtMainLoop(); } ========================== GLUE BETWEEN C++ and Xt CODE (glue.cc) #include ...global header defs... #include ...c++ headers needed by glue fns ... #include "glue.h" // declare below all C++ variables and procs used by glue extern Class1* a; // handle to some object used by glue extern void SomeCCProc(); // maybe friend of some classes and objects extern CC_Class someCCObject; // will use this in callback extern "C" { /* declare here all x.c vars and procs used by glue */ extern int XMain(int, char**); extern void XDoSomethingOnScreenFromCC(); /* called from C++ side */ /* declare here all C procs called from X interface */ void XGlueFoo(..arg decls..) { /* This links to c++ callback code. Notice that objects used must be declared in included headers or above */ someCCobject->SomeMethod(arg1, arg2, ... argK); /* the c++ callback */ } someCType XGlueReturnValue(..arg decls..) { return anotherCCobject->AnotherMethod(...args...); /* returns val to x.c */ } /* declare here C++ procs that call the X interface, such as XMain */ int XGlueXMain(int argc, char** argv) { return XMain(argc, argv); // start Xt portion of system } }; // end extern C ========================== C++ CODE (main.cc) // Main C++ program #include ...c++ headers... // include the glue header file for communication extern "C" { #include "glue.h" }; CC_Class someCCobject; // to be used by XGlueFoo() int main(int argc, char** argv) { ...set up world... ...perform any preliminary C++ processing... return XGlueXMain(argc, argv); // relinquish control to X through glue } -- jp@aurora.com --- Sic itur ad astra.