Path: utzoo!attcan!uunet!allbery From: allbery@uunet.UU.NET (Brandon S. Allbery - comp.sources.misc) Newsgroups: comp.sources.misc Subject: v08i057: Elk (Extension Language Toolkit) part 09 of 14 Message-ID: <68225@uunet.UU.NET> Date: 23 Sep 89 21:42:12 GMT Sender: allbery@uunet.UU.NET Reply-To: net@tub.UUCP (Oliver Laumann) Lines: 1669 Approved: allbery@uunet.UU.NET (Brandon S. Allbery - comp.sources.misc) Posting-number: Volume 8, Issue 57 Submitted-by: net@tub.UUCP (Oliver Laumann) Archive-name: elk/part09 [Let this be a lesson to submitters: this was submitted as uuencoded, compressed files. I lost the source information while unpacking it; this is the best approximation I could come up with. ++bsa] #! /bin/sh # This is a shell archive. Remove anything before this line, then unpack # it by saving it into a file and typing "sh file". To overwrite existing # files, type "sh file -c". You can also feed this as standard input via # unshar, or by typing "sh tst/billiard <<'END_OF_tst/billiard' X;;; X;;; BILLIARD.SCM: This file contains code for a very simple billiard ball X;;; simulator. The simulation takes place in two dimensions. X;;; The balls are really disks in that their height is not taken X;;; into account. All interactions are assumed to be X;;; frictionless so spin in irrelevant and not accounted for. X;;; (See section on limitations.) X;;; X;;; NOTES: A simulation is initiated by creating a number of balls and bumpers X;;; and and specifying a duration for the simulation. For each ball, X;;; its mass, radius, initial position, and initial velocity must be X;;; specified. For each bumper, the location of its two ends must be X;;; specified. (Bumpers are assumed to have zero width.) X;;; X;;; A sample run might be started as follows: X;;; (simulate X;;; (list (make-ball 2 1 9 5 -1 -1) X;;; (make-ball 4 2 2 5 1 -1)) X;;; (list (make-bumper 0 0 0 10) X;;; (make-bumper 0 0 10 0) X;;; (make-bumper 0 10 10 10) X;;; (make-bumper 10 0 10 10)) X;;; 30) X;;; X;;; It would create one billiard ball of mass 2 and radius 1 at position X;;; (9, 5) with initial velocity (-1, -1) and a second ball of mass 4 X;;; and radius 2 at position (2, 5) with initial velocity (1, -1). The X;;; table would be a 10X10 square. (See diagram below) X;;; X;;; +---------------------------+ X;;; | | X;;; | | X;;; | XXXX | X;;; | XXXXXXXX XX | X;;; |XXXXXX4XXXXX XXX2XX| X;;; | XXXXXXXX /XX | X;;; | XXXX \ | X;;; | | X;;; | | X;;; +---------------------------+ X;;; X;;; LIMITATIONS: This simulator does not handle 3 body problems correctly. If X;;; 3 objects interact at one time, only the interactions of 2 of X;;; the bodies will be accounted for. This can lead to strange X;;; effects like balls tunneling through walls and other balls. X;;; It is also possible to get balls bouncing inside of each X;;; other in this way. X;;; X X X;;MAKE-QUEUE-RECORD returns a queue record with the given next, previous, and X;;value values X;;NEXT = The next record pointer X;;PREV = The previous record pointer X;;REST = A list of values for any optional fields (this can be used for X;; creating structure inheritance) X(define-macro (make-queue-record next prev . rest) X `(vector ,next ,prev ,@rest)) X X;;QUEUE-RECORD-NEXT returns the next field of the given queue record X;;QUEUE-RECORD = The queue record whose next field is to be returned X(define-macro (queue-record-next queue-record) X `(vector-ref ,queue-record 0)) X X;;SET-QUEUE-RECORD-NEXT! sets the next field of the given queue record X;;QUEUE-RECORD = The queue record whose next field is to be set X;;VALUE = The value to which the next field is to be set X(define-macro (set-queue-record-next! queue-record value) X `(vector-set! ,queue-record 0 ,value)) X X;;QUEUE-RECORD-PREV returns the prev field of the given queue record X;;QUEUE-RECORD = The queue record whose prev field is to be returned X(define-macro (queue-record-prev queue-record) X `(vector-ref ,queue-record 1)) X X;;SET-QUEUE-RECORD-PREV! sets the prev field of the given queue record X;;QUEUE-RECORD = The queue record whose prev field is to be set X;;VALUE = The value to which the prev field is to be set X(define-macro (set-queue-record-prev! queue-record value) X `(vector-set! ,queue-record 1 ,value)) X X;;QUEUE-RECORD-LEN returns the length of a queue record which has no optional X;;fields X(define-macro (queue-record-len) 2) X X;;QUEUE-HEAD returns a dummy record at the end of the queue with the record X;;with the smallest key. X;;QUEUE = the queue whose head record is to be returned X(define-macro (queue-head queue) X `(vector-ref ,queue 0)) X X;;QUEUE-TAIL returns a dummy record at the end of the queue with the record X;;with the largest key. X;;QUEUE = the queue whose tail record is to be returned X(define-macro (queue-tail queue) X `(vector-ref ,queue 1)) X X;;QUEUE- dot-product X bumper-length-squared)) X '() ;Return infinity X (+ delta-t ;Else, return the contact time X (ball-collision-time X ball)))))))))))) X X X;;BALL-COLLISION-PROCEDURE calculates the new velocities of the given balls X;;based on their collision at the given time. Also, tells all other balls X;;about the new trajectories of these balls so they can update their event X;;queues X;;BALL1 = The first ball X;;BALL2 = The second ball X;;COLLISION-TIME = The collision time X;;GLOBAL-EVENT-QUEUE = The global queue of earliest events for each ball X(define (ball-collision-procedure ball1 ball2 collision-time X global-event-queue) X (queue-remove ;Remove the earliest event associated X (ball-global-event-queue-record ;with each ball from the global event X ball1)) ;queue X (queue-remove X (ball-global-event-queue-record X ball2)) X (let ((ball1-collision-x-position ;Calculate the positions of both balls X (+ (ball-collision-x-position ;when they collide X ball1) X (* (ball-x-velocity X ball1) X (- collision-time X (ball-collision-time X ball1))))) X (ball1-collision-y-position X (+ (ball-collision-y-position X ball1) X (* (ball-y-velocity X ball1) X (- collision-time X (ball-collision-time X ball1))))) X (ball2-collision-x-position X (+ (ball-collision-x-position X ball2) X (* (ball-x-velocity X ball2) X (- collision-time X (ball-collision-time X ball2))))) X (ball2-collision-y-position X (+ (ball-collision-y-position X ball2) X (* (ball-y-velocity X ball2) X (- collision-time X (ball-collision-time X ball2)))))) X (let ((delta-x ;Calculate the displacements of the X (- ball2-collision-x-position ;centers of the two balls X ball1-collision-x-position)) X (delta-y X (- ball2-collision-y-position X ball1-collision-y-position))) X X X (let* ((denominator ;Calculate the angle of the line X (sqrt (+ (square ;joining the centers at the collision X delta-x) ;time with the x-axis (this line is X (square ;the normal to the balls at the X delta-y)))) ;collision point) X (cos-theta X (/ delta-x denominator)) X (sin-theta X (/ delta-y denominator))) X (let ((ball1-old-normal-velocity ;Convert the velocities of the balls X (+ (* (ball-x-velocity ;into the coordinate system defined by X ball1) ;the normal and tangential lines at X cos-theta) ;the collision point X (* (ball-y-velocity X ball1) X sin-theta))) X (ball1-tang-velocity X (- (* (ball-y-velocity X ball1) X cos-theta) X (* (ball-x-velocity X ball1) X sin-theta))) X (ball2-old-normal-velocity X (+ (* (ball-x-velocity X ball2) X cos-theta) X (* (ball-y-velocity X ball2) X sin-theta))) X (ball2-tang-velocity X (- (* (ball-y-velocity X ball2) X cos-theta) X (* (ball-x-velocity X ball2) X sin-theta))) X (mass1 (ball-mass X ball1)) X (mass2 (ball-mass X ball2))) X (let ((ball1-new-normal-velocity ;Calculate the new velocities X (/ ;following the collision (the X (+ ;tangential velocities are unchanged X (* ;because the balls are assumed to be X (* 2 ;frictionless) X mass2) X ball2-old-normal-velocity) X (* X (- mass1 mass2) X ball1-old-normal-velocity)) X (+ mass1 mass2))) X X X (ball2-new-normal-velocity X (/ X (+ X (* X (* 2 X mass1) X ball1-old-normal-velocity) X (* X (- mass2 mass1) X ball2-old-normal-velocity)) X (+ mass1 mass2)))) X (set-ball-x-velocity! ;Store data about the collision in the X ball1 ;structure for each ball after X (- (* ball1-new-normal-velocity ;converting the information back X cos-theta) ;to the x,y frame X (* ball1-tang-velocity X sin-theta))) X (set-ball-y-velocity! X ball1 X (+ (* ball1-new-normal-velocity X sin-theta) X (* ball1-tang-velocity X cos-theta))) X (set-ball-x-velocity! X ball2 X (- (* ball2-new-normal-velocity X cos-theta) X (* ball2-tang-velocity X sin-theta))) X (set-ball-y-velocity! X ball2 X (+ (* ball2-new-normal-velocity X sin-theta) X (* ball2-tang-velocity X cos-theta))) X (set-ball-collision-time! X ball1 X collision-time) X (set-ball-collision-time! X ball2 X collision-time) X (set-ball-collision-x-position! X ball1 X ball1-collision-x-position) X (set-ball-collision-y-position! X ball1 X ball1-collision-y-position) X (set-ball-collision-x-position! X ball2 X ball2-collision-x-position) X (set-ball-collision-y-position! X ball2 X ball2-collision-y-position)))))) X X X (newline) X (display "Ball ") X (display (ball-number ball1)) X (display " collides with ball ") X (display (ball-number ball2)) X (display " at time ") X (display (ball-collision-time ball1)) X (newline) X (display " Ball ") X (display (ball-number ball1)) X (display " has a new velocity of ") X (display (ball-x-velocity ball1)) X (display ",") X (display (ball-y-velocity ball1)) X (display " starting at ") X (display (ball-collision-x-position ball1)) X (display ",") X (display (ball-collision-y-position ball1)) X (newline) X (display " Ball ") X (display (ball-number ball2)) X (display " has a new velocity of ") X (display (ball-x-velocity ball2)) X (display ",") X (display (ball-y-velocity ball2)) X (display " starting at ") X (display (ball-collision-x-position ball2)) X (display ",") X (display (ball-collision-y-position ball2)) X X (recalculate-collisions ball1 global-event-queue) X (recalculate-collisions ball2 global-event-queue)) X X X;;BUMPER-COLLISION-PROCEDURE calculates the new velocity of the given ball X;;following its collision with the given bumper at the given time. Also, tells X;;other balls about the new trajectory of the given ball so they can update X;;their event queues. X;;BALL = The ball X;;BUMPER = The bumper X;;COLLISION-TIME = The collision time X;;GLOBAL-EVENT-QUEUE = The global queue of earliest events for each ball X(define (bumper-collision-procedure ball bumper collision-time X global-event-queue) X (queue-remove ;Remove the earliest event associated X (ball-global-event-queue-record ;with the ball from the global event X ball)) ;queue X (let ((delta-x-bumper ;Compute the bumper's delta-x X (- (bumper-x2 bumper) X (bumper-x1 bumper))) X (delta-y-bumper ;delta-y X (- (bumper-y2 bumper) X (bumper-y1 bumper)))) X (let ((bumper-length ;length X (sqrt X (+ (square X delta-x-bumper) X (square X delta-y-bumper))))) X (let ((cos-theta ;and cosine and sine of its angle with X (/ delta-x-bumper ;respect to the positive x-axis X bumper-length)) X (sin-theta X (/ delta-y-bumper X bumper-length)) X (x-velocity ;Cache the ball's velocity in the x,y X (ball-x-velocity ball)) ;frame X (y-velocity X (ball-y-velocity ball))) X (let ((tang-velocity ;Calculate the ball's velocity in the X (+ (* x-velocity ;bumper frame X cos-theta) X (* y-velocity X sin-theta))) X (normal-velocity X (- (* y-velocity X cos-theta) X (* x-velocity X sin-theta)))) X X X (set-ball-collision-x-position! ;Store the collision position X ball X (+ (ball-collision-x-position X ball) X (* (- collision-time X (ball-collision-time X ball)) X (ball-x-velocity X ball)))) X (set-ball-collision-y-position! X ball X (+ (ball-collision-y-position X ball) X (* (- collision-time X (ball-collision-time X ball)) X (ball-y-velocity X ball)))) X (set-ball-x-velocity! ;Calculate the new velocity in the X ball ;x,y frame based on the fact that X (+ (* tang-velocity ;tangential velocity is unchanged and X cos-theta) ;the normal velocity is inverted when X (* normal-velocity ;the ball collides with the bumper X sin-theta))) X (set-ball-y-velocity! X ball X (- (* tang-velocity X sin-theta) X (* normal-velocity X cos-theta))) X (set-ball-collision-time! X ball X collision-time))))) X (newline) X (display "Ball ") X (display (ball-number ball)) X (display " collides with bumper ") X (display (bumper-number bumper)) X (display " at time ") X (display (ball-collision-time ball)) X (newline) X (display " Ball ") X (display (ball-number ball)) X (display " has a new velocity of ") X (display (ball-x-velocity ball)) X (display ",") X (display (ball-y-velocity ball)) X (display " starting at ") X (display (ball-collision-x-position ball)) X (display ",") X (display (ball-collision-y-position ball)) X X (recalculate-collisions ball global-event-queue)) X X X;;RECALCULATE-COLLISIONS removes all old collisions for the given ball from X;;all other balls' event queues and calcultes new collisions for these balls X;;and places them on the event queues. Also, updates the global event queue if X;;the recalculation of the collision effects the earliest collision for any X;;other balls. X;;BALL = The ball whose collisions are being recalculated X;;GLOBAL-EVENT-QUEUE = The global queue of earliest events for each ball X(define (recalculate-collisions ball global-event-queue) X (clear-queue (ball-event-queue ;Clear the queue of events for this X ball)) ;ball as they have all changed X (let ((event-queue ;Calculate all ball collision events X (ball-event-queue ball))) ;with balls of lower number X (let ((ball-vector X (ball-ball-vector ball))) X (do ((i (-1+ (ball-number ball)) X (-1+ i))) X ((negative? i)) X (let ((ball2-queue-record X (vector-ref X ball-vector X i))) X (set-event-queue-record-collision-time! X ball2-queue-record X (ball-ball-collision-time X ball X (event-queue-record-object X ball2-queue-record))) X (queue-insert X event-queue X ball2-queue-record)))) X (let ((bumper-vector ;Calculate all bumper collision events X (ball-bumper-vector ball))) X (do ((i (-1+ (vector-length X bumper-vector)) X (-1+ i))) X ((negative? i)) X (let ((bumper-queue-record X (vector-ref X bumper-vector X i))) X (set-event-queue-record-collision-time! X bumper-queue-record X (ball-bumper-collision-time X ball X (event-queue-record-object X bumper-queue-record))) X (queue-insert X event-queue X bumper-queue-record)))) X X X (let ((global-queue-record ;Get the global event queue record X (ball-global-event-queue-record ;for this ball X ball))) X (set-event-queue-record-collision-time! ;Set the new earliest event time X global-queue-record ;for this ball X (if (empty-queue? event-queue) X '() X (event-queue-record-collision-time X (queue-smallest event-queue)))) X (queue-insert ;Enqueue on the global event queue X global-event-queue ;the earliest event between this ball X global-queue-record))) ;and any ball of lower number or any X ;bumper X (for-each ;For each ball on the ball list: X (lambda (ball2) X (let ((ball2-event-queue X (ball-event-queue ball2))) X (let ((alter-global-event-queue? ;Set flag to update global event queue X (and ;if the earliest event for ball2 was X (not (empty-queue? ;with the deflected ball X ball2-event-queue)) X (eq? ball X (event-queue-record-object X (queue-smallest X ball2-event-queue))))) X (ball-event-queue-record ;Get the queue record for the deflected X (vector-ref ;ball for this ball X (ball-ball-vector X ball2) X (ball-number ball)))) X (queue-remove ;Remove the queue record for the X ball-event-queue-record) ;deflected ball X (set-event-queue-record-collision-time! ;Recalculate the collision X ball-event-queue-record ;time for this ball and the deflected X (ball-ball-collision-time ;ball X ball X ball2)) X (queue-insert ;Enqueue the new collision event X ball2-event-queue X ball-event-queue-record) X (if (or alter-global-event-queue? ;If the earliest collision event for X (eq? ball ;this ball has changed: X (event-queue-record-object X (queue-smallest X ball2-event-queue)))) X (let ((queue-record ;Remove the old event from the global X (ball-global-event-queue-record ;event queue and replace it X ball2))) ;with the new event X (set-event-queue-record-collision-time! X queue-record X (event-queue-record-collision-time X (queue-smallest X ball2-event-queue))) X (queue-remove X queue-record) X (queue-insert X global-event-queue X queue-record)))))) X (ball-ball-list ball))) X X X;;SIMULATE performs the billiard ball simulation for the given ball list and X;;bumper list until the specified time. X;;BALL-LIST = A list of balls X;;BUMPER-LIST = A list of bumpers X;;END-TIME = The time at which the simulation is to terminate X(define (simulate ball-list bumper-list end-time) X (let ((num-of-balls ;Cache the number of balls and bumpers X (length ball-list)) X (num-of-bumpers X (length bumper-list)) X (global-event-queue ;Build the global event queue X (make-sorted-queue X collision-time-lib/xlib/examples/properties <<'END_OF_lib/xlib/examples/properties' X;;; -*-Scheme-*- X;;; X;;; Display all properties of all windows (with name, type, format, X;;; and data). X X(require 'xlib) X X(define (properties) X (let ((dpy (open-display))) X (unwind-protect X (let* ((w (car (query-tree (display-root-window dpy)))) X (l (map (lambda (win) (cons win (list-properties win))) X (cons (display-root-window dpy) (vector->list w)))) X (tab (lambda (obj n) X (let* ((s (format #f "~s" obj)) X (n (- n (string-length s)))) X (display s) X (if (positive? n) X (do ((i 0 (1+ i))) ((= i n)) (display #\space))))))) X (for-each X (lambda (w) X (format #t "Window ~s:~%" (car w)) X (for-each X (lambda (p) X (tab (atom-name dpy p) 20) X (display "= ") X (let ((p (get-property (car w) p #f 0 20 #f))) X (tab (atom-name dpy (car p)) 18) X (tab (cadr p) 3) X (format #t "~s~%" (caddr p)))) X (vector->list (cdr w))) X (newline)) X l)) X (close-display dpy)))) X X(properties) END_OF_lib/xlib/examples/properties if test 969 -ne `wc -c lib/xlib/examples/track <<'END_OF_lib/xlib/examples/track' X;;; -*-Scheme-*- X X(require 'xlib) X X(define (track) X (let* ((dpy (open-display)) X (root (display-root-window dpy)) X (gc (make-gcontext (window root) X (function 'xor) X (foreground (black-pixel dpy)) X (subwindow-mode 'include-inferiors))) X (lx 0) (ly 0) (lw 0) (lh 0) X (move-outline X (lambda (x y w h) X (if (not (and (= x lx) (= y ly) (= w lw) (= h lh))) X (begin X (draw-rectangle root gc lx ly lw lh) X (draw-rectangle root gc x y w h) X (set! lx x) (set! ly y) X (set! lw w) (set! lh h)))))) X (unwind-protect X (case (grab-pointer root #f '(pointer-motion button-press) X #f #f 'none 'none 'now) X (success X (with-server-grabbed dpy X (draw-rectangle root gc lx ly lw lh) X (display-flush-output dpy) X (handle-events dpy X (motion-notify X (lambda (event root win subwin time x y . rest) X (move-outline x y 300 300) #f)) X (else (lambda args #t))))) X (else X (format #t "Not grabbed!~%"))) X (begin X (draw-rectangle root gc lx ly lw lh) X (close-display dpy))))) X X(track) END_OF_lib/xlib/examples/track if test 1062 -ne `wc -c lib/xlib/examples/picture <<'END_OF_lib/xlib/examples/picture' X;;; -*-Scheme-*- X X;;; -*- Mode:Lisp; Package:XLIB; Syntax:COMMON-LISP; Base:10; Lowercase:T -*- X X;;; CLX - Point Graphing demo program X X;;; Copyright (C) 1988 Michael O. Newton (newton@csvax.caltech.edu) X X;;; Permission is granted to any individual or institution to use, copy, X;;; modify, and distribute this software, provided that this complete X;;; copyright and permission notice is maintained, intact, in all copies and X;;; supporting documentation. X X;;; The author provides this software "as is" without express or X;;; implied warranty. X X;;; This routine plots the recurrance X;;; x <- y(1+sin(0.7x)) - 1.2(|x|)^.5 X;;; y <- .21 - x X;;; As described in a ?? 1983 issue of the Mathematical Intelligencer X;;; It has ONLY been tested under X.V11R2 on a Sun3 running KCL X X(require 'xlib) X X(define (picture point-count) X (let* ((dpy (open-display)) X (width 600) X (height 600) X (black (black-pixel dpy)) X (white (white-pixel dpy)) X (root (display-root-window dpy)) X (win (make-window (parent root) (background-pixel white) X (event-mask '(exposure button-press)) X (width width) (height height))) X (gc (make-gcontext (window win) X (background white) (foreground black)))) X (map-window win) X (unwind-protect X (handle-events dpy X (expose X (lambda ignore X (clear-window win) X (draw-points win gc point-count 0.0 0.0 (* width 0.5) (* height 0.5)) X (draw-poly-text win gc 10 10 (translate "Click a button to exit") X '1-byte) X #f)) X (else (lambda ignore #t))) X (close-display dpy)))) X X;;; Draw points. These should maybe be put into a an array so that they do X;;; not have to be recomputed on exposure. X assumes points are in the range X;;; of width x height, with 0,0 being upper left and 0,H being lower left. X;;; x <- y(1+sin(0.7x)) - 1.2(|x|)^.5 X;;; y <- .21 - x X;;; hw and hh are half-width and half-height of screen X X(define (draw-points win gc count x y hw hh) X (if (zero? (modulo count 100)) X (display-flush-output (window-display win))) X (if (not (zero? count)) X (let ((xf (floor (* (+ 1.2 x) hw ))) ; These lines center the picture X (yf (floor (* (+ 0.5 y) hh )))) X (draw-point win gc xf yf) X (draw-points win gc (1- count) X (- (* y (1+ (sin (* 0.7 x)))) (* 1.2 (sqrt (abs x)))) X (- 0.21 x) X hw hh)))) X X(define (translate string) X (list->vector (map char->integer (string->list string)))) X X(picture 10000) END_OF_lib/xlib/examples/picture if test 2425 -ne `wc -c lib/xlib/examples/useful <<'END_OF_lib/xlib/examples/useful' X;;; -*-Scheme-*- X X(require 'xlib) X X(define dpy X (open-display)) X X(define (f) X (display-wait-output dpy #t)) X X(define root X (display-root-window dpy)) X X(define cmap X (display-colormap dpy)) X X(define white (white-pixel dpy)) X(define black (black-pixel dpy)) X X(define rgb-white (query-color cmap white)) X(define rgb-black (query-color cmap black)) X X(define win X (make-window (parent root) X (width 300) (height 300) X (background-pixel white))) X X(define gc (make-gcontext X (window win) X (background white) (foreground black))) X X(map-window win) END_OF_lib/xlib/examples/useful if test 567 -ne `wc -c lib/xlib/pixel.c <<'END_OF_lib/xlib/pixel.c' X#include "xlib.h" X XGeneric_Predicate (Pixel); X XGeneric_Simple_Equal (Pixel, PIXEL, pix); X XGeneric_Print (Pixel, "#[pixel 0x%lx]", PIXEL(x)->pix); X XObject Make_Pixel (val) unsigned long val; { X register char *p; X Object pix; X X pix = Find_Object (T_Pixel, (GENERIC)0, Match_X_Obj, val); X if (Nullp (pix)) { X p = Get_Bytes (sizeof (struct S_Pixel)); X SET (pix, T_Pixel, (struct S_Pixel *)p); X PIXEL(pix)->tag = Null; X PIXEL(pix)->pix = val; X Register_Object (pix, (GENERIC)0, (PFO)0, 0); X } X return pix; X} X Xunsigned long Get_Pixel (p) Object p; { X Check_Type (p, T_Pixel); X return PIXEL(p)->pix; X} X Xstatic Object P_Pixel_Value (p) Object p; { X return Make_Unsigned ((unsigned)Get_Pixel (p)); X} X Xstatic Object P_Black_Pixel (d) Object d; { X Check_Type (d, T_Display); X return Make_Pixel (BlackPixel (DISPLAY(d)->dpy, X DefaultScreen (DISPLAY(d)->dpy))); X} X Xstatic Object P_White_Pixel (d) Object d; { X Check_Type (d, T_Display); X return Make_Pixel (WhitePixel (DISPLAY(d)->dpy, X DefaultScreen (DISPLAY(d)->dpy))); X} X Xinit_xlib_pixel () { X Generic_Define (Pixel, "pixel", "pixel?"); X Define_Primitive (P_Pixel_Value, "pixel-value", 1, 1, EVAL); X Define_Primitive (P_Black_Pixel, "black-pixel", 1, 1, EVAL); X Define_Primitive (P_White_Pixel, "white-pixel", 1, 1, EVAL); X} END_OF_lib/xlib/pixel.c if test 1332 -ne `wc -c