  Syntax10.Scn.Fnt     Syntax10i.Scn.Fnt  "       StampElems Alloc 25 May 95  A        (    <                   Syntax10b.Scn.Fnt              3            	    2                    !                        >        	        	        	                	        	        	        	                
        
        
        
                                                                           h        %    /    8           8           C    2    :           g    {            g       f   MODULE DialogAnalogClocks;	(** Markus Knasmller 14 Sep 94 -  *)	(* This sourcecode uses parts of ClockElems - gri 18.3.91 *)	(* to use only INTEGER rd 25 May 95 *)		IMPORT DialogClocks, DialogFrames, Dialogs, Display, In, (* Math, *) Oberon, Printer;		CONST		W* = 65; H* = W; Rmin = 12; Rdef = 8.2; black = 15;	TYPE		Item* = POINTER TO ItemDesc;		ItemDesc* = RECORD(DialogClocks.ItemDesc)		END;		VAR 		(* sin, cos: ARRAY 60 OF REAL; *)		sin, cos: ARRAY 60 OF LONGINT;		Line: PROCEDURE (f: Display.Frame; x1, y1, x2, y2, color, mode: INTEGER);		Circle: PROCEDURE (f: Display.Frame; x0, y0, r, color, mode: INTEGER);		PROCEDURE Min (x, y: INTEGER): INTEGER;	BEGIN IF x < y THEN RETURN x ELSE RETURN y END	END Min;		(*	PROCEDURE Init;		VAR i: INTEGER;	BEGIN i := 0;		WHILE i < 60 DO			sin[i] := Math.sin(2 * Math.pi / 60 * i);			cos[i] := Math.cos(2 * Math.pi / 60 * i);			INC(i)		END	END Init;*)		PROCEDURE Init;		VAR i: INTEGER;	BEGIN		sin[0]:=0;sin[1]:=10453;sin[2]:=20791;sin[3]:=30902;sin[4]:=40674;		sin[5]:=50000;sin[6]:=58779;sin[7]:=66913;sin[8]:=74314;sin[9]:=80902;		sin[10]:=86603;sin[11]:=91355;sin[12]:=95106;sin[13]:=97815;sin[14]:=99452;		sin[15]:=100000;		FOR i:=0 TO 14 DO sin[30-i]:=sin[i];END;		FOR i:=0 TO 29 DO sin[30+i]:=-sin[i];END;		FOR i:=0 TO 29 DO cos[i]:=sin[i+15];END;		FOR i:=0 TO 29 DO cos[i+30]:=-cos[i];END;	END Init;		PROCEDURE Format (time: LONGINT; VAR sec, min, hour, hourm: INTEGER);	BEGIN 		hour := SHORT (time DIV 4096 MOD 32); 		min := SHORT (time DIV 64 MOD 64);		sec := SHORT (time MOD 64);		hourm := (hour MOD 12) * 5 + min DIV 12	END Format;(* graphics *)	PROCEDURE SCircle(f: Display.Frame; x0, y0, r, color, mode: INTEGER);		VAR x, y, dx, dy, d: INTEGER;				PROCEDURE Dot4(x1, x2, y1, y2, color, mode: INTEGER);		BEGIN			Display.DotC (f, color, x1, y1, mode);			Display.DotC (f, color, x1, y2, mode);			Display.DotC (f, color, x2, y1, mode);			Display.DotC (f, color, x2, y2, mode)		END Dot4;			BEGIN		x := r; y := 0; dx := 8*(x-1); dy := 8*y+4; d := 1-4*r;		WHILE x > y DO			Dot4(x0-x, x0+x, y0-y, y0+y, color, mode);			Dot4(x0-y, x0+y, y0-x, y0+x, color, mode);			INC(d, dy); INC(dy, 8); INC(y);			IF d >= 0 THEN DEC(d, dx); DEC(dx, 8); DEC(x) END		END;		IF x = y THEN Dot4(x0-x, x0+x, y0-y, y0+y, color, mode) END	END SCircle;	PROCEDURE SLine(f: Display.Frame; x1, y1, x2, y2, color, mode: INTEGER);		VAR x, y, dx, dy, d, inc: INTEGER;	BEGIN		IF (y2 - y1) < (x1 - x2) THEN x := x1; x1 := x2; x2 := x; y := y1; y1 := y2; y2 := y END;		dx := 2 * (x2 - x1);		dy := 2 * (y2 - y1);		x := x1; y := y1; inc := 1;		IF dy > dx THEN			d := dy DIV 2;			IF dx < 0 THEN inc := -1; dx := -dx END;			WHILE y <= y2 DO				Display.DotC (f, color, x, y, mode); 				INC (y); DEC (d, dx);				IF d < 0 THEN INC (d, dy); INC (x, inc) END			END		ELSE			d := dx DIV 2;			IF dy < 0 THEN inc := -1; dy := -dy END;			WHILE x <= x2 DO				Display.DotC (f, color, x, y, mode);				INC (x); DEC (d, dy);				IF d < 0 THEN INC (d, dx); INC (y, inc) END			END		END 	END SLine;	PROCEDURE PCircle (f: Display.Frame; x0, y0, r, color, mode: INTEGER);	BEGIN Printer.Circle (x0, y0, r)	END PCircle;	PROCEDURE PLine (f: Display.Frame; x1, y1, x2, y2, color, mode: INTEGER);	BEGIN Printer.Line (x1, y1, x2, y2)	END PLine;	(* view update *)	PROCEDURE Line2(f: Display.Frame; ang: INTEGER; x0, y0, r1, r2, color: INTEGER);		VAR x1, y1, x2, y2: INTEGER;	BEGIN		ang := (15-ang) MOD 60;(* 	x1 := SHORT(ENTIER(r1*cos[ang] + 0.5));		y1 := SHORT(ENTIER(r1*sin[ang] + 0.5));		x2 := SHORT(ENTIER(r2*cos[ang] + 0.5));		y2 := SHORT(ENTIER(r2*sin[ang] + 0.5));*)		x1 := SHORT((r1*cos[ang]+50000)DIV 100000);		y1 := SHORT((r1*sin[ang]+50000)DIV 100000);		x2 := SHORT((r2*cos[ang]+50000)DIV 100000);		y2 := SHORT((r2*sin[ang]+50000)DIV 100000);		Line (f, x0 + x1, y0 + y1, x0 + x2, y0 + y2, color, Display.invert) 	END Line2;	PROCEDURE Line3(f: Display.Frame; ang: INTEGER; x0, y0, r1, r2, color: INTEGER);		VAR x1, y1, x2, y2: INTEGER;	BEGIN		ang := (15-ang) MOD 60;(* 	x1 := SHORT(ENTIER(r1*cos[ang] + 0.5));		y1 := SHORT(ENTIER(r1*sin[ang] + 0.5));		x2 := SHORT(ENTIER(r2*cos[ang] + 0.5));		y2 := SHORT(ENTIER(r2*sin[ang] + 0.5));*)		x1 := SHORT((r1*cos[ang]+50000)DIV 100000);		y1 := SHORT((r1*sin[ang]+50000)DIV 100000);		x2 := SHORT((r2*cos[ang]+50000)DIV 100000);		y2 := SHORT((r2*sin[ang]+50000)DIV 100000);		Line (f, x0 + x1, y0 + y1, x0 + x2, y0 + y2, color, Display.paint) 	END Line3;	PROCEDURE (c: Item) Draw* (x, y: INTEGER; f: Display.Frame);	(** displays the object at (x, y) in frame f *)		VAR r, rh, rm, rs, i, sec, min, hour, hourm, mode, ox, oy, w, h: INTEGER;	BEGIN		Line := SLine; Circle := SCircle;		c.GetDim (ox, oy, w, h);		Display.ReplConstC (f, f(DialogFrames.Frame).col, x, y, w, h, Display.paint);		r := Min (w - 1 , h - 1) DIV 2; x := x + r; y := y + r;		IF c.selected THEN mode := Display.invert ELSE mode := Display.replace END;		IF r >= Rmin THEN			rh := 7 * r DIV 11; rm := 9 * r DIV 11; rs := 10 * r DIV 11; i := 0;			WHILE i < 60 DO Line3 (f, i, x, y, rm, r, black); INC (i, 5) END;			Format (DialogClocks.old.timeStamp, sec, min, hour, hourm); 			Line2 (f, sec, x, y, rm-r, rs, black); 			Line2 (f, min, x, y, 0, rm, black); 			Line2 (f, hourm, x, y, 0, rh, black); 			Circle (f, x, y, 2, black, mode)		END;		Circle(f, x, y, r, black, mode)	END Draw;		PROCEDURE (c: Item) Print* (x, y: INTEGER);	(** prints the object at printer coordinates (x, y)  *)		VAR ox, oy, w, h, r, sec, min, hour, hourm, mode, i, rh, rm, rs: INTEGER; f: Display.Frame; 	BEGIN		Line := PLine; Circle := PCircle;		c.GetPDim (ox, oy, w, h);		r := Min (w - 1 , h - 1) DIV 2; x := x + r; y := y + r;				IF r >= Rmin THEN			rh := 7 * r DIV 11; rm := 9 * r DIV 11; rs := 10 * r DIV 11; i := 0;			WHILE i < 60 DO Line2 (f, i, x, y, rm, r, black); INC (i, 5) END;			Format (DialogClocks.old.timeStamp, sec, min, hour, hourm); 			Line2 (f, sec, x, y, rm-r, rs, black); 			Line2 (f, min, x, y, 0, rm, black); 			Line2 (f, hourm, x, y, 0, rh, black); 			Circle (f, x, y, SHORT (2 * Dialogs.dUnit DIV Dialogs.pUnit), black, Display.paint)		END;		Circle(f, x, y, r, black, mode)	END Print;		PROCEDURE (c: Item) Redraw* (f: Display.Frame; x, y: INTEGER; old, new: DialogClocks.Time);	(** handles messages which were sent to frame f *)		VAR rh, rm, rs, olds, oldm, oldh, oldhm, news, newm, newh, newhm, ox, oy, w, h, r, mode: INTEGER;	BEGIN		c.GetDim (ox, oy, w, h);		r := Min (w - 1, h - 1) DIV 2; x := x + r; y := y + r;		IF c.selected THEN RETURN END;		Line := SLine; Circle := SCircle;		IF r >= Rmin THEN			rh := 7*r DIV 11; rm := 9*r DIV 11; rs := 10*r DIV 11;			Format (old.timeStamp, olds, oldm, oldh, oldhm); Format (new.timeStamp, news, newm, newh, newhm);			IF olds # news THEN Line2 (f, olds, x, y, rm-r, rs, black); Line2(f, news, x, y, rm-r, rs, black) END;			IF oldm # newm THEN Line2(f, oldm, x, y, 0, rm, black); Line2(f, newm, x, y, 0, rm, black) END;			IF oldhm # newhm THEN Line2(f, oldhm, x, y, 0, rh, black); Line2(f, newhm, x, y, 0, rh, black) END;			Circle (f, x, y, 2, black, mode)		END	END Redraw;		PROCEDURE (c: Item) Copy* (VAR dup: Dialogs.Object);	(** allocates dup and makes a deep copy of o. Before calling this methode dup should be equal NIL *)		VAR x: Item;	BEGIN		IF dup = NIL THEN NEW (x); dup := x ELSE x := dup(Item) END;		c.Copy^ (dup);	END Copy;	PROCEDURE Insert*;	(** Insert ([name] [x y w h] | ^ ) inserts a clock - item in the panel containing the caret position *)		VAR x, y, x1, y1, w, h: INTEGER; c: Item; p: Dialogs.Panel; name: ARRAY 64 OF CHAR; 	BEGIN 		NEW (c);  		DialogFrames.GetCaretPosition (p, x, y);		IF (p # NIL) THEN 			c.Init; In.Open; In.Name (name);			IF ~In.Done THEN COPY ("", name); In.Open END;			c.SetName (name); 			In.Int (x1); In.Int (y1); In.Int (w); In.Int (h);			IF ~In.Done THEN x1 := x; y1 := y; w := W; h := H 			ELSE				IF w < 0 THEN w := W END;				IF h < 0 THEN h := H END			END;			c.SetDim (x, y, W, H, FALSE); p.Insert (c, FALSE) 		ELSE			Dialogs.res := Dialogs.noPanelSelected		END;		IF Dialogs.res # 0 THEN Dialogs.Error ("DialogClocks") END;	END Insert;	BEGIN InitEND DialogAnalogClocks.