summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--Eyes.c66
-rw-r--r--Eyes.h3
-rw-r--r--EyesP.h1
-rw-r--r--xeyes.c3
-rw-r--r--xeyes.man3
5 files changed, 69 insertions, 7 deletions
diff --git a/Eyes.c b/Eyes.c
index 3fa5b4f..e792445 100644
--- a/Eyes.c
+++ b/Eyes.c
@@ -79,6 +79,8 @@ static XtResource resources[] = {
{XtNrender, XtCBoolean, XtRBoolean, sizeof(Boolean),
offset(render), XtRImmediate, (XtPointer) TRUE },
#endif
+ {XtNdistance, XtCBoolean, XtRBoolean, sizeof(Boolean),
+ offset(distance), XtRImmediate, (XtPointer) FALSE },
};
#undef offset
@@ -100,6 +102,8 @@ static XtResource resources[] = {
# define TPOINT_NONE (-1000) /* special value meaning "not yet set" */
# define TPointEqual(a, b) ((a).x == (b).x && (a).y == (b).y)
# define XPointEqual(a, b) ((a).x == (b).x && (a).y == (b).y)
+# define AngleBetween(A, A0, A1) (A0 <= A1 ? A0 <= A && A <= A1 : \
+ A0 <= A || A <= A1)
static int delays[] = { 50, 100, 200, 400, 0 };
@@ -299,7 +303,8 @@ eyeLiner(EyesWidget w,
static TPoint computePupil (
int num,
- TPoint mouse)
+ TPoint mouse,
+ const TRectangle *screen)
{
double cx, cy;
double dist;
@@ -316,6 +321,42 @@ static TPoint computePupil (
cosa = cos (angle);
sina = sin (angle);
dist = BALL_DIST;
+ if (screen)
+ {
+ /* use distance mapping */
+ double x0, y0, x1, y1;
+ double a[4];
+ x0 = screen->x - cx;
+ y0 = screen->y - cy;
+ x1 = x0 + screen->width;
+ y1 = y0 + screen->height;
+ a[0] = atan2(y0, x0);
+ a[1] = atan2(y1, x0);
+ a[2] = atan2(y1, x1);
+ a[3] = atan2(y0, x1);
+ if (AngleBetween(angle, a[0], a[1]))
+ {
+ /* left */
+ dist *= dx / x0;
+ }
+ else if (AngleBetween(angle, a[1], a[2]))
+ {
+ /* bottom */
+ dist *= dy / y1;
+ }
+ else if (AngleBetween(angle, a[2], a[3]))
+ {
+ /* right */
+ dist *= dx / x1;
+ }
+ else if (AngleBetween(angle, a[3], a[0]))
+ {
+ /* top */
+ dist *= dy / y0;
+ }
+ if (dist > BALL_DIST)
+ dist = BALL_DIST;
+ }
if (dist > hypot ((double) dx, (double) dy)) {
cx += dx;
cy += dy;
@@ -330,11 +371,26 @@ static TPoint computePupil (
}
static void computePupils (
+ EyesWidget w,
TPoint mouse,
TPoint pupils[2])
{
- pupils[0] = computePupil (0, mouse);
- pupils[1] = computePupil (1, mouse);
+ TRectangle screen, *sp = NULL;
+ if (w->eyes.distance) {
+ Window r, cw;
+ int x, y;
+ r = RootWindowOfScreen(w->core.screen);
+ XTranslateCoordinates(XtDisplay(w), XtWindow(w), r, 0, 0, &x, &y, &cw);
+ screen.x = Tx(-x, -y, &w->eyes.t);
+ screen.y = Ty(-x, -y, &w->eyes.t);
+ screen.width = Twidth (w->core.screen->width, w->core.screen->height,
+ &w->eyes.t);
+ screen.height = Theight(w->core.screen->width, w->core.screen->height,
+ &w->eyes.t);
+ sp = &screen;
+ }
+ pupils[0] = computePupil (0, mouse, sp);
+ pupils[1] = computePupil (1, mouse, sp);
}
static void
@@ -354,7 +410,7 @@ static void repaint_window (EyesWidget w)
if (XtIsRealized ((Widget) w)) {
eyeLiner (w, TRUE, 0);
eyeLiner (w, TRUE, 1);
- computePupils (w->eyes.mouse, w->eyes.pupil);
+ computePupils (w, w->eyes.mouse, w->eyes.pupil);
eyeBall (w, TRUE, NULL, 0);
eyeBall (w, TRUE, NULL, 1);
}
@@ -391,7 +447,7 @@ drawEyes(EyesWidget w, TPoint mouse)
++w->eyes.update;
return;
}
- computePupils (mouse, newpupil);
+ computePupils (w, mouse, newpupil);
for (num = 0; num < 2; num ++) {
drawEye(w, newpupil[num], num);
}
diff --git a/Eyes.h b/Eyes.h
index d9893a3..424967b 100644
--- a/Eyes.h
+++ b/Eyes.h
@@ -35,7 +35,8 @@
#define XtNshapeWindow "shapeWindow"
#define XtCShapeWindow "ShapeWindow"
-#define XtNrender "render"
+#define XtNrender "render"
+#define XtNdistance "distance"
enum EyesPart {
PART_CLEAR = -1,
diff --git a/EyesP.h b/EyesP.h
index 1cffdb4..3a04b13 100644
--- a/EyesP.h
+++ b/EyesP.h
@@ -34,6 +34,7 @@ typedef struct {
Picture picture;
Picture fill[PART_SHAPE];
#endif
+ Boolean distance;
} EyesPart;
/* Full instance record declaration */
diff --git a/xeyes.c b/xeyes.c
index 1bca7ab..276a084 100644
--- a/xeyes.c
+++ b/xeyes.c
@@ -57,7 +57,7 @@ usage(void)
fprintf(stderr, " [-shape | +shape]");
fprintf(stderr, "\n");
fprintf(stderr,
-" [-outline {color}] [-center {color}] [-backing {backing-store}]\n");
+" [-outline {color}] [-center {color}] [-backing {backing-store}] [-distance]\n");
#ifdef XRENDER
fprintf(stderr,
" [-render | +render]\n");
@@ -78,6 +78,7 @@ static XrmOptionDescRec options[] = {
{"-render", "*eyes.render", XrmoptionNoArg, "TRUE"},
{"+render", "*eyes.render", XrmoptionNoArg, "FALSE"},
#endif
+{"-distance", "*eyes.distance", XrmoptionNoArg, "TRUE"},
};
static Atom wm_delete_window;
diff --git a/xeyes.man b/xeyes.man
index 4484d3d..1685af2 100644
--- a/xeyes.man
+++ b/xeyes.man
@@ -52,6 +52,9 @@ This is the default if \fIxeyes\fP has been compiled with Xrender support.
.TP 8
.B \+render
disables Xrender and draws traditional eyes.
+.TP 8
+.B \-distance
+uses an alternative mapping, as if the eyes were set back from the screen, thus following the mouse more precisely.
.SH "SEE ALSO"
X(__miscmansuffix__), X Toolkit documentation
.br