X-Git-Url: http://git.hungrycats.org/cgi-bin/gitweb.cgi?a=blobdiff_plain;f=hacks%2Fglx%2Fpolyhedra-gl.c;h=57a7938787cd0b4c65522fc79b5dcbafb15c9a5f;hb=6afd6db0ae9396cd7ff897ade597cd5483f49b0e;hp=7082a4e36e0a512aa857f056fd8d3b804b6893f5;hpb=c1b9b55ad8d59dc05ef55e316aebf5863e7dfa56;p=xscreensaver diff --git a/hacks/glx/polyhedra-gl.c b/hacks/glx/polyhedra-gl.c index 7082a4e3..57a79387 100644 --- a/hacks/glx/polyhedra-gl.c +++ b/hacks/glx/polyhedra-gl.c @@ -1,4 +1,4 @@ -/* polyhedra, Copyright (c) 2004-2008 Jamie Zawinski +/* polyhedra, Copyright (c) 2004-2014 Jamie Zawinski * * Permission to use, copy, modify, distribute, and sell this software and its * documentation for any purpose is hereby granted without fee, provided that @@ -30,6 +30,17 @@ #include "xlockmore.h" +#ifdef HAVE_COCOA +# include "jwxyz.h" +#else +# include +# include +# include +#endif + +#ifdef HAVE_JWZGLES +# include "jwzgles.h" +#endif /* HAVE_JWZGLES */ #define DEF_SPIN "True" #define DEF_WANDER "True" @@ -51,6 +62,11 @@ # include #endif +#ifndef HAVE_JWZGLES +# define HAVE_TESS +#endif + + #ifdef USE_GL /* whole file */ typedef struct { @@ -73,8 +89,7 @@ typedef struct { int ncolors; XColor *colors; - XFontStruct *xfont1, *xfont2, *xfont3; - GLuint font1_dlist, font2_dlist, font3_dlist; + texture_font_data *font1_data, *font2_data, *font3_data; time_t last_change_time; int change_tick; @@ -156,9 +171,9 @@ static void load_fonts (ModeInfo *mi) { polyhedra_configuration *bp = &bps[MI_SCREEN(mi)]; - load_font (mi->dpy, "titleFont", &bp->xfont1, &bp->font1_dlist); - load_font (mi->dpy, "titleFont2", &bp->xfont2, &bp->font2_dlist); - load_font (mi->dpy, "titleFont3", &bp->xfont3, &bp->font3_dlist); + bp->font1_data = load_texture_font (mi->dpy, "titleFont"); + bp->font2_data = load_texture_font (mi->dpy, "titleFont2"); + bp->font3_data = load_texture_font (mi->dpy, "titleFont3"); } @@ -168,10 +183,14 @@ startup_blurb (ModeInfo *mi) { polyhedra_configuration *bp = &bps[MI_SCREEN(mi)]; const char *s = "Computing polyhedra..."; + texture_font_data *f = bp->font1_data; + glColor3f (0.8, 0.8, 0); - print_gl_string (mi->dpy, bp->xfont1, bp->font1_dlist, + print_gl_string (mi->dpy, bp->font1_data, mi->xgwa.width, mi->xgwa.height, - mi->xgwa.width - (string_width (bp->xfont1, s, 0) + 40), + mi->xgwa.width - ( + texture_string_width (f, s, 0) + + 40), mi->xgwa.height - 10, s, False); glFinish(); @@ -213,63 +232,36 @@ polyhedra_handle_event (ModeInfo *mi, XEvent *event) { polyhedra_configuration *bp = &bps[MI_SCREEN(mi)]; - if (event->xany.type == ButtonPress && - event->xbutton.button == Button1) - { - bp->button_down_p = True; - gltrackball_start (bp->trackball, - event->xbutton.x, event->xbutton.y, - MI_WIDTH (mi), MI_HEIGHT (mi)); - return True; - } - else if (event->xany.type == ButtonRelease && - event->xbutton.button == Button1) - { - bp->button_down_p = False; - return True; - } - else if (event->xany.type == ButtonPress && - (event->xbutton.button == Button4 || - event->xbutton.button == Button5 || - event->xbutton.button == Button6 || - event->xbutton.button == Button7)) - { - gltrackball_mousewheel (bp->trackball, event->xbutton.button, 10, - !!event->xbutton.state); - return True; - } + if (gltrackball_event_handler (event, bp->trackball, + MI_WIDTH (mi), MI_HEIGHT (mi), + &bp->button_down_p)) + return True; else if (event->xany.type == KeyPress) { KeySym keysym; char c = 0; XLookupString (&event->xkey, &c, 1, &keysym, 0); -# ifdef HAVE_COCOA -# define XK_Right -1 -# define XK_Left -1 -# define XK_Up -1 -# define XK_Down -1 -# endif bp->change_to = -1; if (c == ' ' || c == '\t' || c == '\r' || c == '\n') bp->change_to = random() % bp->npolyhedra; else if (c == '>' || c == '.' || c == '+' || c == '=' || - keysym == XK_Right || keysym == XK_Up) + keysym == XK_Right || keysym == XK_Up || keysym == XK_Next) bp->change_to = (bp->which + 1) % bp->npolyhedra; else if (c == '<' || c == ',' || c == '-' || c == '_' || c == '\010' || c == '\177' || - keysym == XK_Left || keysym == XK_Down) + keysym == XK_Left || keysym == XK_Down || keysym == XK_Prior) bp->change_to = (bp->which + bp->npolyhedra - 1) % bp->npolyhedra; + else if (screenhack_event_helper (MI_DISPLAY(mi), MI_WINDOW(mi), event)) + goto DEF; if (bp->change_to != -1) return True; } - else if (event->xany.type == MotionNotify && - bp->button_down_p) + else if (screenhack_event_helper (MI_DISPLAY(mi), MI_WINDOW(mi), event)) { - gltrackball_track (bp->trackball, - event->xmotion.x, event->xmotion.y, - MI_WIDTH (mi), MI_HEIGHT (mi)); + DEF: + bp->change_to = random() % bp->npolyhedra; return True; } @@ -310,17 +302,18 @@ new_label (ModeInfo *mi) p->density, (p->chi < 0 ? "" : " "), p->chi); { - XFontStruct *f; - GLuint fl; + GLfloat color[4] = { 0.8, 0.8, 0.8, 1 }; + texture_font_data *f; if (MI_WIDTH(mi) >= 500 && MI_HEIGHT(mi) >= 375) - f = bp->xfont1, fl = bp->font1_dlist; /* big font */ + f = bp->font1_data; else if (MI_WIDTH(mi) >= 350 && MI_HEIGHT(mi) >= 260) - f = bp->xfont2, fl = bp->font2_dlist; /* small font */ + f = bp->font2_data; /* small font */ else - f = bp->xfont3, fl = bp->font3_dlist; /* tiny font */ + f = bp->font3_data; /* tiny font */ - glColor3f (0.8, 0.8, 0); - print_gl_string (mi->dpy, f, fl, + glColor4fv (color); + glMaterialfv (GL_FRONT_AND_BACK, GL_AMBIENT_AND_DIFFUSE, color); + print_gl_string (mi->dpy, f, mi->xgwa.width, mi->xgwa.height, 10, mi->xgwa.height - 10, label, False); @@ -330,13 +323,16 @@ new_label (ModeInfo *mi) } +#ifdef HAVE_TESS static void tess_error (GLenum errorCode) { fprintf (stderr, "%s: tesselation error: %s\n", progname, gluErrorString(errorCode)); - exit (0); + abort(); } +#endif /* HAVE_TESS */ + static void new_polyhedron (ModeInfo *mi) @@ -349,11 +345,13 @@ new_polyhedron (ModeInfo *mi) /* Use the GLU polygon tesselator so that nonconvex faces are displayed correctly (e.g., for the "pentagrammic concave deltohedron"). */ +# ifdef HAVE_TESS GLUtesselator *tobj = gluNewTess(); gluTessCallback (tobj, GLU_TESS_BEGIN, (void (*) (void)) &glBegin); gluTessCallback (tobj, GLU_TESS_END, (void (*) (void)) &glEnd); gluTessCallback (tobj, GLU_TESS_VERTEX, (void (*) (void)) &glVertex3dv); gluTessCallback (tobj, GLU_TESS_ERROR, (void (*) (void)) &tess_error); +# endif /* HAVE_TESS */ mi->polygon_count = 0; @@ -380,10 +378,20 @@ new_polyhedron (ModeInfo *mi) glNewList (bp->object_list, GL_COMPILE); if (bp->which == bp->npolyhedra-1) { + GLfloat bcolor[4]; + bcolor[0] = bp->colors[0].red / 65536.0; + bcolor[1] = bp->colors[0].green / 65536.0; + bcolor[2] = bp->colors[0].blue / 65536.0; + bcolor[3] = 1.0; + if (wire) + glColor3f (0, 1, 0); + else + glMaterialfv (GL_FRONT_AND_BACK, GL_AMBIENT_AND_DIFFUSE, bcolor); + glScalef (0.8, 0.8, 0.8); p->nfaces = unit_teapot (6, wire); - p->nedges = p->nfaces * 2; /* #### is this right? */ - p->npoints = p->nfaces / 3; /* #### is this right? */ + p->nedges = p->nfaces * 3 / 2; + p->npoints = p->nfaces * 3; p->logical_faces = p->nfaces; p->logical_vertices = p->npoints; } @@ -404,12 +412,13 @@ new_polyhedron (ModeInfo *mi) bcolor[0] = bp->colors[f->color].red / 65536.0; bcolor[1] = bp->colors[f->color].green / 65536.0; bcolor[2] = bp->colors[f->color].blue / 65536.0; - bcolor[2] = 1.0; + bcolor[3] = 1.0; glMaterialfv (GL_FRONT_AND_BACK, GL_AMBIENT_AND_DIFFUSE, bcolor); } kludge_normal (f->npoints, f->points, p->points); +# ifdef HAVE_TESS gluTessBeginPolygon (tobj, 0); gluTessBeginContour (tobj); for (j = 0; j < f->npoints; j++) @@ -419,12 +428,26 @@ new_polyhedron (ModeInfo *mi) } gluTessEndContour (tobj); gluTessEndPolygon (tobj); +# else /* !HAVE_TESS */ + glBegin (wire ? GL_LINE_LOOP : + f->npoints == 3 ? GL_TRIANGLES : + f->npoints == 4 ? GL_QUADS : + GL_POLYGON); + for (j = 0; j < f->npoints; j++) + { + point *pp = &p->points[f->points[j]]; + glVertex3f (pp->x, pp->y, pp->z); + } + glEnd(); +# endif /* !HAVE_TESS */ } } glEndList (); mi->polygon_count += p->nfaces; +# ifdef HAVE_TESS gluDeleteTess (tobj); +# endif } @@ -451,6 +474,11 @@ init_polyhedra (ModeInfo *mi) polyhedra_configuration *bp; int wire = MI_IS_WIREFRAME(mi); +# ifdef HAVE_JWZGLES /* #### glPolygonMode other than GL_FILL unimplemented */ + MI_IS_WIREFRAME(mi) = 0; + wire = 0; +# endif + if (!bps) { bps = (polyhedra_configuration *) calloc (MI_NUM_SCREENS(mi), sizeof (polyhedra_configuration)); @@ -458,8 +486,6 @@ init_polyhedra (ModeInfo *mi) fprintf(stderr, "%s: out of memory\n", progname); exit(1); } - - bp = &bps[MI_SCREEN(mi)]; } bp = &bps[MI_SCREEN(mi)]; @@ -470,8 +496,6 @@ init_polyhedra (ModeInfo *mi) load_fonts (mi); startup_blurb (mi); - reshape_polyhedra (mi, MI_WIDTH(mi), MI_HEIGHT(mi)); - if (!wire) { GLfloat pos[4] = {1.0, 1.0, 1.0, 0.0}; @@ -506,7 +530,7 @@ init_polyhedra (ModeInfo *mi) spin_accel, do_wander ? wander_speed : 0, True); - bp->trackball = gltrackball_init (); + bp->trackball = gltrackball_init (True); } bp->npolyhedra = construct_polyhedra (&bp->polyhedra); @@ -556,6 +580,9 @@ init_polyhedra (ModeInfo *mi) } new_polyhedron (mi); + reshape_polyhedra (mi, MI_WIDTH(mi), MI_HEIGHT(mi)); + clear_gl_error(); /* WTF? sometimes "invalid op" from glViewport! */ + }