Re: spaceball

New Message Reply Date view Thread view Subject view Author view

David Blythe (blythe++at++banshee.asd.sgi.com)
Sat, 22 Feb 1997 13:50:47 -0800


Here is a simple example OpenGL (not performer) program.
        -db

/*
 * sb.c - skeleton for using the Spaceball
 * cc -O -o sb sb.c -lGL -lX11 -lXi
 */

#include <GL/glx.h>
#include <GL/gl.h>
#include "stdio.h"

static int attributeList[] = { GLX_RGBA, GLX_RED_SIZE, 1, None };

void process(void);
void init_devices(Display *dpy, Window window);

Display *dpy;
Window window;

int main(int argc, char **argv) {
    XVisualInfo *vi;
    Colormap cmap;
    XSetWindowAttributes swa;
    GLXContext cx;

    /* get a connection */
    dpy = XOpenDisplay(0);

    /* get an appropriate visual */
    if (!(vi = glXChooseVisual(dpy, DefaultScreen(dpy), attributeList))) {
        printf("can't find requested visual\n");
        exit(1);
    }

    /* create a GLX context */
    cx = glXCreateContext(dpy, vi, 0, GL_TRUE);

    /* create a colormap */
    cmap = XCreateColormap(dpy, RootWindow(dpy, vi->screen),
                           vi->visual, AllocNone);

    /* create a window */
    swa.colormap = cmap;
    swa.border_pixel = 0;
    swa.event_mask = StructureNotifyMask|ExposureMask;
    window = XCreateWindow(dpy, RootWindow(dpy, vi->screen), 0, 0, 100, 100,
                        0, vi->depth, InputOutput, vi->visual,
CWBorderPixel|CWColormap|CWEventMask, &swa);
    XMapWindow(dpy, window);

    /* connect the context to the window */
    glXMakeCurrent(dpy, window, cx);

    glClearColor(.5, .5, .5, 1.);

    init_devices(dpy, window);
    process();
}

#include <X11/extensions/XI.h>
#include <X11/extensions/XInput.h>

int spaceball_ball_event_type,
    spaceball_button_press_event_type,
    spaceball_button_release_event_type;

XDevice *spaceball_device = NULL;

void
init_devices(Display *dpy, Window window) {
    XDeviceInfoPtr list;
    XDevice *XOpenDevice();
    XEventClass ListOfEventClass[3];
    int i, ndevices;
    int spaceball_ball_event_class,
        spaceball_button_press_event_class,
        spaceball_button_release_event_class;

    /* get the list of input devices that are attached to the display */
    list = (XDeviceInfoPtr) XListInputDevices(dpy, &ndevices);
    for(i = 0; i < ndevices; i++) {
#if 0
        printf ("device id = %d\n",list[i].id);
        printf ("device type = %d\n",list[i].type);
        printf ("device name = %s\n",list[i].name);
        printf ("number_of_classes = %d\n",list[i].num_classes);
#endif
        /* open the spaceball device */
        if (strcmp(list[i].name, "spaceball") == NULL) {
            /*
             * Note that the device_id is not guaranteed to be the
             * same all the time
             */
            spaceball_device = XOpenDevice(dpy, list[i].id);
        }
    }
    if (!spaceball_device) {
        fprintf(stderr, "No spaceball box attached to this display\n");
        exit(1);
    }

    /* select extension events for the dial & button box */
    DeviceMotionNotify(spaceball_device,
                        spaceball_ball_event_type,
                        spaceball_ball_event_class);
    ListOfEventClass[0] = spaceball_ball_event_class;
    DeviceButtonPress(spaceball_device,
                        spaceball_button_press_event_type,
                        spaceball_button_press_event_class);
    ListOfEventClass[1]=spaceball_button_press_event_class;
    DeviceButtonRelease(spaceball_device,
                        spaceball_button_release_event_type,
                        spaceball_button_release_event_class);
    ListOfEventClass[2]=spaceball_button_release_event_class;
    XSelectExtensionEvent(dpy,window,ListOfEventClass,3);
}

void
process(void) {
    XEvent event;
    int redraw;

    while(1) {
        redraw = 0;
        XNextEvent(dpy, &event);
        if (event.type == spaceball_ball_event_type) {
            XDeviceMotionEvent *M = (XDeviceMotionEvent *) &event;
            if (M->deviceid == spaceball_device->device_id) {
                int i;
                int sbdata[6];

                for(i=0;i<M->axes_count;i++)
                    sbdata[M->first_axis+i]=M->axis_data[i];

                /* process spaceball data in sbdata[0 .. 5] */
                printf("axis data %d %d %d %d %d %d\n", sbdata[0], sbdata[1], sbdata[2], sbdata[3], sbdata[4], sbdata[5]);
            }
        } else if (event.type == spaceball_button_press_event_type) {
            /* spaceball button presses */
            XDeviceButtonEvent *B = (XDeviceButtonEvent *)&event;
            int butno = B->button;
            if (butno == 9)
                printf("Spaceball PICK button pressed\n");
            else
                printf("Spaceball button %d pressed\n", butno);
        } else if (event.type == spaceball_button_release_event_type) {
            /* spaceball button releases */
            XDeviceButtonEvent *b = (XDeviceButtonEvent *)&event;
            int butno = b->button;
            if (butno == 9)
                printf("Spaceball PICK button released\n");
            else
                printf("Spaceball button %d released\n", butno);
        } else if (event.type == Expose) {
            redraw = 1;
        }
        if (redraw) {
            printf("redraw\n");
            glClear(GL_COLOR_BUFFER_BIT);
        }
    }
}
=======================================================================
List Archives, FAQ, FTP: http://www.sgi.com/Technology/Performer/
            Submissions: info-performer++at++sgi.com
        Admin. requests: info-performer-request++at++sgi.com


New Message Reply Date view Thread view Subject view Author view

This archive was generated by hypermail 2.0b2 on Mon Aug 10 1998 - 17:54:42 PDT

This message has been cleansed for anti-spam protection. Replace '++at++' in any mail addresses with the '@' symbol.