From http://www.jwz.org/xscreensaver/xscreensaver-5.35.tar.gz
[xscreensaver] / hacks / julia.c
index 8e12cd8c9ea9a012e9aa86ae45f38dae39b6c45b..a121711d423aad4dce911732e6305519e1888f52 100644 (file)
@@ -38,38 +38,23 @@ static const char sccsid[] = "@(#)julia.c   4.03 97/04/10 xlockmore";
  */
 
 #ifdef STANDALONE
-# define DEFAULTS      "*count:                1000  \n"                       \
-                                       "*cycles:               20    \n"                       \
-                                       "*delay:                10000 \n"                       \
-                                       "*ncolors:              200   \n"
+# define DEFAULTS      "*count:                  1000   \n" \
+                                       "*cycles:                 20     \n" \
+                                       "*delay:                  10000  \n" \
+                                       "*ncolors:                200    \n" \
+                                       "*fpsSolid:               true   \n" \
+                                       "*ignoreRotation: True   \n" \
+
 # define UNIFORM_COLORS
-# define reshape_julia 0
-# define julia_handle_event 0
 # include "xlockmore.h"                                /* in xscreensaver distribution */
 #else  /* !STANDALONE */
 # include "xlock.h"                                    /* in xlockmore distribution */
 #endif /* !STANDALONE */
 
 
-static Bool track_p;
-
 #define DEF_MOUSE "False"
 
-static XrmOptionDescRec opts[] =
-{
-       {"-mouse", ".julia.mouse", XrmoptionNoArg, "on"},
-       {"+mouse", ".julia.mouse", XrmoptionNoArg, "off"},
-};
-static argtype vars[] =
-{
-       {&track_p, "mouse", "Mouse", DEF_MOUSE, t_Bool},
-};
-static OptionStruct desc[] =
-{
-       {"-/+mouse", "turn on/off mouse tracking"},
-};
-
-ENTRYPOINT ModeSpecOpt julia_opts = { 2, opts, 1, vars, desc };
+ENTRYPOINT ModeSpecOpt julia_opts = { 0, };
 
 
 #define numpoints ((0x2<<jp->depth)-1)
@@ -89,11 +74,13 @@ typedef struct {
        int         nbuffers;
        int         redrawing, redrawpos;
        Pixmap      pixmap;
-#ifndef HAVE_COCOA
+#ifndef HAVE_JWXYZ
        Cursor      cursor;
 #endif
        GC          stippledGC;
        XPoint    **pointBuffer;        /* pointer for XDrawPoints */
+    Bool        button_down_p;
+    int         mouse_x, mouse_y;
 
 } juliastruct;
 
@@ -138,28 +125,13 @@ apply(juliastruct * jp, register double xr, register double xi, int d)
 static void
 incr(ModeInfo * mi, juliastruct * jp)
 {
-       int cx, cy;
-
-       if (track_p)
+       if (jp->button_down_p)
          {
-               Window r, c;
-               int rx, ry;
-               unsigned int m;
-               XQueryPointer(MI_DISPLAY(mi), MI_WINDOW(mi),
-                                         &r, &c, &rx, &ry, &cx, &cy, &m);
-               if (cx <= 0 || cy <= 0 ||
-                       cx >= MI_WIN_WIDTH(mi) || cy >= MI_WIN_HEIGHT(mi))
-                 goto NOTRACK;
-         }
-
-       if (track_p)
-         {
-               jp->cr = ((double) (cx + 2 - jp->centerx)) * 2 / jp->centerx;
-               jp->ci = ((double) (cy + 2 - jp->centery)) * 2 / jp->centery;
+               jp->cr = ((double) (jp->mouse_x + 2 - jp->centerx)) * 2 / jp->centerx;
+               jp->ci = ((double) (jp->mouse_y + 2 - jp->centery)) * 2 / jp->centery;
          }
        else
          {
-         NOTRACK:
 #if 0
                jp->cr = 1.5 * (sin(M_PI * (jp->inc / 300.0)) *
                                                sin(jp->inc * M_PI / 200.0));
@@ -204,8 +176,8 @@ init_julia(ModeInfo * mi)
                jp->depth = 10;
 
 
-#ifndef HAVE_COCOA
-       if (track_p && !jp->cursor)
+#ifndef HAVE_JWXYZ
+       if (jp->button_down_p && !jp->cursor && !jp->cursor)
          {
                Pixmap bit;
                XColor black;
@@ -218,7 +190,7 @@ init_julia(ModeInfo * mi)
                                                                                  0, 0);
                XFreePixmap (display, bit);
          }
-#endif /* HAVE_COCOA */
+#endif /* HAVE_JWXYZ */
 
        if (jp->pixmap != None &&
            jp->circsize != (MIN(jp->centerx, jp->centery) / 60) * 2 + 1) {
@@ -228,7 +200,7 @@ init_julia(ModeInfo * mi)
        if (jp->pixmap == None) {
                GC          fg_gc = None, bg_gc = None;
 
-               jp->circsize = (MIN(jp->centerx, jp->centery) / 96) * 2 + 1;
+               jp->circsize = MAX(8, (MIN(jp->centerx, jp->centery) / 96) * 2 + 1);
                jp->pixmap = XCreatePixmap(display, window, jp->circsize, jp->circsize, 1);
                gcv.foreground = 1;
                fg_gc = XCreateGC(display, jp->pixmap, GCForeground, &gcv);
@@ -247,14 +219,14 @@ init_julia(ModeInfo * mi)
                        XFreeGC(display, bg_gc);
        }
 
-#ifndef HAVE_COCOA
+#ifndef HAVE_JWXYZ
        if (MI_WIN_IS_INROOT(mi))
          ;
        else if (jp->circsize > 0)
          XDefineCursor (display, window, jp->cursor);
        else
          XUndefineCursor (display, window);
-#endif /* HAVE_COCOA */
+#endif /* HAVE_JWXYZ */
 
        if (!jp->stippledGC) {
                gcv.foreground = MI_WIN_BLACK_PIXEL(mi);
@@ -282,6 +254,44 @@ init_julia(ModeInfo * mi)
 }
 
 
+static void
+reshape_julia (ModeInfo *mi, int w, int h)
+{
+  init_julia (mi);
+}
+
+
+ENTRYPOINT Bool
+julia_handle_event (ModeInfo *mi, XEvent *event)
+{
+  juliastruct *jp = &julias[MI_SCREEN(mi)];
+
+  if (event->xany.type == ButtonPress &&
+      event->xbutton.button == Button1)
+    {
+      jp->button_down_p = True;
+      jp->mouse_x = event->xbutton.x;
+      jp->mouse_y = event->xbutton.y;
+      return True;
+    }
+  else if (event->xany.type == ButtonRelease &&
+           event->xbutton.button == Button1)
+    {
+      jp->button_down_p = False;
+      return True;
+    }
+  else if (event->xany.type == MotionNotify && jp->button_down_p)
+    {
+      jp->mouse_x = event->xmotion.x;
+      jp->mouse_y = event->xmotion.y;
+      return True;
+    }
+
+  return False;
+}
+
+
+
 /* hack: moved here by jwz. */
 #define ERASE_IMAGE(d,w,g,x,y,xl,yl,xs,ys) \
 if (yl<y) \
@@ -316,18 +326,25 @@ draw_julia (ModeInfo * mi)
        new_circle.x = (int) (jp->centerx * jp->cr / 2) + jp->centerx - 2;
        new_circle.y = (int) (jp->centery * jp->ci / 2) + jp->centery - 2;
        XSetForeground(display, gc, MI_WIN_BLACK_PIXEL(mi));
-       ERASE_IMAGE(display, window, gc, new_circle.x, new_circle.y,
-                   old_circle.x, old_circle.y, jp->circsize, jp->circsize);
+       XFillArc(display, window, gc, 
+             old_circle.x-jp->circsize/2-2,
+             old_circle.y-jp->circsize/2-2,
+             jp->circsize+4, jp->circsize+4,
+             0, 360*64);
        /* draw a circle at the c-parameter so you can see it's effect on the
           structure of the julia set */
        XSetForeground(display, jp->stippledGC, MI_WIN_WHITE_PIXEL(mi));
-#ifndef HAVE_COCOA
+#ifndef HAVE_JWXYZ
        XSetTSOrigin(display, jp->stippledGC, new_circle.x, new_circle.y);
        XSetStipple(display, jp->stippledGC, jp->pixmap);
        XSetFillStyle(display, jp->stippledGC, FillOpaqueStippled);
-#endif /* HAVE_COCOA */
-       XFillRectangle(display, window, jp->stippledGC, new_circle.x, new_circle.y,
-                      jp->circsize, jp->circsize);
+#endif /* HAVE_JWXYZ */
+       XDrawArc(display, window, jp->stippledGC, 
+             new_circle.x-jp->circsize/2,
+             new_circle.y-jp->circsize/2,
+             jp->circsize, jp->circsize,
+             0, 360*64);
+
        if (jp->erase == 1) {
                XDrawPoints(display, window, gc,
                    jp->pointBuffer[jp->buffer], numpoints, CoordModeOrigin);
@@ -418,7 +435,7 @@ release_julia (ModeInfo * mi)
                                XFreeGC(display, jp->stippledGC);
                        if (jp->pixmap != None)
                                XFreePixmap(display, jp->pixmap);
-#ifndef HAVE_COCOA
+#ifndef HAVE_JWXYZ
                        if (jp->cursor)
                          XFreeCursor (display, jp->cursor);
 #endif