+/**************************************************************************
+ * Rendering Functions *
+ * *
+ **************************************************************************/
+
+static void
+show_arms(ModeInfo * mi, unsigned long color)
+{
+ jugglestruct *sp = &juggles[MI_SCREEN(mi)];
+ unsigned int i, j;
+ Hand side;
+ XPoint a[XtNumber(sp->arm[0][0])];
+ if(color == MI_BLACK_PIXEL(mi)) {
+ j = 0;
+ } else {
+ j = 1;
+ }
+ XSetLineAttributes(MI_DISPLAY(mi), MI_GC(mi),
+ ARMWIDTH, LineSolid, CapRound, JoinRound);
+ XSetForeground(MI_DISPLAY(mi), MI_GC(mi), color);
+ for(side = LEFT; side <= RIGHT; side = (Hand)((int)side + 1)) {
+ /* Translate into device coords */
+ for(i = 0; i < XtNumber(a); i++) {
+ a[i].x = (short)(MI_WIDTH(mi)/2 + sp->arm[j][side][i].x*sp->scale);
+ a[i].y = (short)(MI_HEIGHT(mi) - sp->arm[j][side][i].y*sp->scale);
+ if(j == 1)
+ sp->arm[0][side][i] = sp->arm[1][side][i];
+ }
+ XDrawLines(MI_DISPLAY(mi), MI_WINDOW(mi), MI_GC(mi),
+ a, XtNumber(a), CoordModeOrigin);
+ }
+}
+
+static void
+show_figure(ModeInfo * mi, unsigned long color, Bool init)
+{
+ jugglestruct *sp = &juggles[MI_SCREEN(mi)];
+ XPoint p[7];
+ unsigned int i;
+
+ /* +-----+ 9
+ | 6 |
+ 10 +--+--+
+ 2 +---+---+ 3
+ \ 5 /
+ \ /
+ \ /
+ 1 +
+ / \
+ / \
+ 0 +-----+ 4
+ | |
+ | |
+ | |
+ 7 + + 8
+ */
+
+ static const XPoint figure[] = {
+ { 15, 70}, /* 0 Left Hip */
+ { 0, 90}, /* 1 Waist */
+ { SX, 130}, /* 2 Left Shoulder */
+ {-SX, 130}, /* 3 Right Shoulder */
+ {-15, 70}, /* 4 Right Hip */
+ { 0, 130}, /* 5 Neck */
+ { 0, 140}, /* 6 Chin */
+ { SX, 0}, /* 7 Left Foot */
+ {-SX, 0}, /* 8 Right Foot */
+ {-17, 174}, /* 9 Head1 */
+ { 17, 140}, /* 10 Head2 */
+ };
+ XPoint a[XtNumber(figure)];
+
+ /* Translate into device coords */
+ for(i = 0; i < XtNumber(figure); i++) {
+ a[i].x = (short)(MI_WIDTH(mi)/2 + (sp->cx + figure[i].x)*sp->scale);
+ a[i].y = (short)(MI_HEIGHT(mi) - figure[i].y*sp->scale);
+ }
+
+ XSetLineAttributes(MI_DISPLAY(mi), MI_GC(mi),
+ ARMWIDTH, LineSolid, CapRound, JoinRound);
+ XSetForeground(MI_DISPLAY(mi), MI_GC(mi), color);
+
+ i = 0; /* Body */
+ p[i++] = a[0]; p[i++] = a[1]; p[i++] = a[2];
+ p[i++] = a[3]; p[i++] = a[1]; p[i++] = a[4];
+ XDrawLines(MI_DISPLAY(mi), MI_WINDOW(mi), MI_GC(mi),
+ p, i, CoordModeOrigin);
+
+ i = 0; /* Legs */
+ p[i++] = a[7]; p[i++] = a[0]; p[i++] = a[4]; p[i++] = a[8];
+ XDrawLines(MI_DISPLAY(mi), MI_WINDOW(mi), MI_GC(mi),
+ p, i, CoordModeOrigin);
+
+ i = 0; /* Neck */
+ p[i++] = a[5]; p[i++] = a[6];
+ XDrawLines(MI_DISPLAY(mi), MI_WINDOW(mi), MI_GC(mi),
+ p, i, CoordModeOrigin);
+
+ /* Head */
+ XDrawArc(MI_DISPLAY(mi), MI_WINDOW(mi), MI_GC(mi),
+ a[9].x, a[9].y,
+ a[10].x - a[9].x, a[10].y - a[9].y, 0, 64*360);
+ sp->arm[1][LEFT][SHOULDER].x = sp->cx + figure[2].x;
+ sp->arm[1][RIGHT][SHOULDER].x = sp->cx + figure[3].x;
+ if(init) {
+ /* Initialise arms */
+ unsigned int i;
+ for(i = 0; i < 2; i++){
+ sp->arm[i][LEFT][SHOULDER].y = figure[2].y;
+ sp->arm[i][LEFT][ELBOW].x = figure[2].x;
+ sp->arm[i][LEFT][ELBOW].y = figure[1].y;
+ sp->arm[i][LEFT][HAND].x = figure[0].x;
+ sp->arm[i][LEFT][HAND].y = figure[1].y;
+ sp->arm[i][RIGHT][SHOULDER].y = figure[3].y;
+ sp->arm[i][RIGHT][ELBOW].x = figure[3].x;
+ sp->arm[i][RIGHT][ELBOW].y = figure[1].y;
+ sp->arm[i][RIGHT][HAND].x = figure[4].x;
+ sp->arm[i][RIGHT][HAND].y = figure[1].y;
+ }
+ }
+}
+
+static void
+show_ball(ModeInfo *mi, unsigned long color, Trace *s)
+{
+ jugglestruct *sp = &juggles[MI_SCREEN(mi)];
+ int offset = (int)(s->angle*64*180/M_PI);
+ short x = (short)(MI_WIDTH(mi)/2 + s->x * sp->scale);
+ short y = (short)(MI_HEIGHT(mi) - s->y * sp->scale);
+
+ /* Avoid wrapping */
+ if(s->y*sp->scale > MI_HEIGHT(mi) * 2) return;
+
+ XSetForeground(MI_DISPLAY(mi), MI_GC(mi), color);
+ if (s->divisions == 0 || color == MI_BLACK_PIXEL(mi)) {
+ XFillArc(MI_DISPLAY(mi), MI_WINDOW(mi), MI_GC(mi),
+ x - BALLRADIUS, y - BALLRADIUS,
+ 2*BALLRADIUS, 2*BALLRADIUS,
+ 0, 23040);
+ } else if (s->divisions == 4) { /* 90 degree divisions */
+ XFillArc(MI_DISPLAY(mi), MI_WINDOW(mi), MI_GC(mi),
+ x - BALLRADIUS, y - BALLRADIUS,
+ 2*BALLRADIUS, 2*BALLRADIUS,
+ offset % 23040, 5760);
+ XFillArc(MI_DISPLAY(mi), MI_WINDOW(mi), MI_GC(mi),
+ x - BALLRADIUS, y - BALLRADIUS,
+ 2*BALLRADIUS, 2*BALLRADIUS,
+ (offset + 11520) % 23040, 5760);
+
+ XSetForeground(MI_DISPLAY(mi), MI_GC(mi), MI_WHITE_PIXEL(mi));
+ XFillArc(MI_DISPLAY(mi), MI_WINDOW(mi), MI_GC(mi),
+ x - BALLRADIUS, y - BALLRADIUS,
+ 2*BALLRADIUS, 2*BALLRADIUS,
+ (offset + 5760) % 23040, 5760);
+ XFillArc(MI_DISPLAY(mi), MI_WINDOW(mi), MI_GC(mi),
+ x - BALLRADIUS, y - BALLRADIUS,
+ 2*BALLRADIUS, 2*BALLRADIUS,
+ (offset + 17280) % 23040, 5760);
+ } else if (s->divisions == 2) { /* 180 degree divisions */
+ XFillArc(MI_DISPLAY(mi), MI_WINDOW(mi), MI_GC(mi),
+ x - BALLRADIUS, y - BALLRADIUS,
+ 2*BALLRADIUS, 2*BALLRADIUS,
+ offset % 23040, 11520);
+
+ XSetForeground(MI_DISPLAY(mi), MI_GC(mi), MI_WHITE_PIXEL(mi));
+ XFillArc(MI_DISPLAY(mi), MI_WINDOW(mi), MI_GC(mi),
+ x - BALLRADIUS, y - BALLRADIUS,
+ 2*BALLRADIUS, 2*BALLRADIUS,
+ (offset + 11520) % 23040, 11520);
+ } else {
+ (void) fprintf(stderr, "juggle[%d]: unexpected divisions: %d\n",
+ MI_SCREEN(mi), s->divisions);
+ }
+}
+
+static void
+show_europeanclub(ModeInfo *mi, unsigned long color, Trace *s)