MODULE PointerDemo;
(*$ LargeVars:=FALSE *)
(* 30.8.90/bp
 * Demonstriert 3 Methoden, Daten direkt im ChipRam abzulegen
 *)

(*$ ChipData:=TRUE *) (* legt diriImage ins Chip *)

FROM SYSTEM	IMPORT	ADR;
FROM Arts	IMPORT	Assert;
FROM IntuitionD	IMPORT	WindowPtr,NewWindow,ScreenFlags,ScreenFlagSet,
			WindowFlags,WindowFlagSet,IDCMPFlags,IDCMPFlagSet;
FROM IntuitionL	IMPORT	SetPointer,ClearPointer,OpenWindow,CloseWindow;
FROM ExecL	IMPORT	WaitPort,GetMsg,ReplyMsg;
FROM SleepPointer IMPORT spHeight,spHotx,spHoty,spImage;


CONST
  diriHeight=16;
  diriHotx=0;
  diriHoty=0;
TYPE
  DiriArr = ARRAY [1..2*(diriHeight+2)] OF CARDINAL;
VAR
  (*
   * Da wir diriImage als initialisierte Variable anlegen, kommt
   * sie wegen pboger Option "ChipData:=TRUE" ins Chipmemory.
   * Leider verderben wir uns damit die Möglichkeit, das Programm
   * reentrant linken zu können.
   * Würden wir diriImage als typisierte Konstante deklarieren,
   * müßten wir "ChipCode:=TRUE" sagen, woraufhin allerdings
   * auch alle Prozeduren im langsamen Chipspeicher landeten.
   *)
  diriImage := DiriArr{
	0,0
	1000000000110000L, 0000000000110000L,
       	0100000000110000L, 0000000001111000L,
       	0010000000000000L, 0000000001111000L,
       	0001000001001000L, 0001000001111000L,
       	0001000000110000L, 0001100000110000L,
       	0000000000000000L, 0000110000110000L,
       	0000000000000000L, 0000011111111100L,
       	0000000000000000L, 0000001111111110L,
       	0000000000000000L, 0000000001111110L,
       	0000000000000000L, 0000000001111110L,
       	0000000000010000L, 0000000001111110L,
       	0000000000111010L, 0000000001111110L,
       	0000000000101000L, 0000000000101000L,
       	0000000000101000L, 0000000000101000L,
       	0000000000101000L, 0000000000101000L,
       	0000000000000000L, 0000000001101100L,
	0,0
  };

  myWin:WindowPtr;

  (* nur Platzhalter, um ADR anwenden zu können! *)
  myImage["Pointer_Image"]:ARRAY[1..18] OF LONGINT; (* chipram!! *)

  myHeight[ < "Pointer_height"],
  hotx[ < "Pointer_hotx"],
  hoty[ < "Pointer_hoty"] :INTEGER;
  nw:=NewWindow{
	leftEdge: 100, topEdge: 50,
	width: 400, height: 100,
	detailPen: 3, blockPen: 2,
	idcmpFlags: IDCMPFlagSet{closeWindow},
	flags: WindowFlagSet{windowSizing,windowDrag,windowDepth,
			windowClose,windowActive},
	title: ADR(' Aktiviere mich! (3*Close=Ende)'),
	minWidth: 100, maxWidth: 640,
	minHeight: 30, maxHeight: 256,
	type: ScreenFlagSet{wbenchScreen}
  };

BEGIN

  myWin:=OpenWindow(nw);
  Assert(myWin#NIL,ADR('Kann Window nicht öffnen!'));

  (* Diese Daten sind in einem externen Asembler-Programm! *)
  SetPointer(myWin,ADR(myImage),myHeight,16,hotx,hoty);

  WaitPort(myWin^.userPort);
  ReplyMsg(GetMsg(myWin^.userPort)); (* kann nur Close sein! *)


  (* Diese Daten sind im Modul SleepPointer, das im ChipRAM liegt! *)
  SetPointer(myWin,ADR(spImage),spHeight,16,spHotx,spHoty);

  WaitPort(myWin^.userPort);
  ReplyMsg(GetMsg(myWin^.userPort)); (* kann nur Close sein! *)

  (* Diese Daten sind im Modul SleepPointer, das im ChipRAM liegt! *)
  SetPointer(myWin,ADR(diriImage),diriHeight,16,diriHotx,diriHoty);

  WaitPort(myWin^.userPort);
  ReplyMsg(GetMsg(myWin^.userPort)); (* kann nur Close sein! *)

CLOSE
  IF myWin#NIL THEN
    ClearPointer(myWin);
    CloseWindow(myWin);
    myWin:=NIL
  END;
END PointerDemo.
