1 (* Copyright (C) 2005, 2006, 2007, 2008, 2009, 2010
2 Free Software Foundation, Inc. *)
3 (* This file is part of GNU Modula-2.
5 GNU Modula-2 is free software; you can redistribute it and/or modify it under
6 the terms of the GNU General Public License as published by the Free
7 Software Foundation; either version 3, or (at your option) any later
10 GNU Modula-2 is distributed in the hope that it will be useful, but WITHOUT ANY
11 WARRANTY; without even the implied warranty of MERCHANTABILITY or
12 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
15 You should have received a copy of the GNU General Public License along
16 with gm2; see the file COPYING. If not, write to the Free Software
17 Foundation, 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. *)
19 IMPLEMENTATION MODULE StoreCoords ;
22 FROM StrIO IMPORT WriteString, WriteLn ;
23 FROM NumberIO IMPORT WriteCard ;
24 FROM Chance IMPORT GetRand ;
38 Start, (* Start of the Coord list *)
39 End : CARDINAL ; (* End of the Coord list *)
43 CoordIndex : ARRAY [0..MaxIndex] OF Index ;
44 Coords : ARRAY [1..MaxCoord] OF Coord ;
45 NoOfCoords : CARDINAL ; (* Number of coordinates in array Coords *)
46 NoOfIndices: CARDINAL ; (* Number of indices in CoordIndex *)
50 InitCoords - Initializes a potential list of coordinates.
51 An index to this potential coordinate list is returned.
54 PROCEDURE InitCoords () : CARDINAL ;
56 IF NoOfIndices=MaxIndex
58 WriteString('Too many coordinate list indices in Module StoreCoords') ;
60 WriteString('Increase MaxIndex') ;
65 WITH CoordIndex[NoOfIndices] DO
66 Start := NoOfCoords+1 ;
69 AddCoord(NoOfIndices, 0, 0) ; (* Dummy coordinate that we keep *)
70 RETURN(NoOfIndices) (* for the life of this list. *)
76 KillCoords - Kills a complete coordinate list.
79 PROCEDURE KillCoords (CoordListIndex: CARDINAL) ;
83 (* Destroy index to Coord list *)
84 WITH CoordIndex[CoordListIndex] DO
85 WriteString('No of coords') ; WriteCard(End-Start+1, 4) ; WriteLn ;
90 If killed last Coord list see if we can garbage collect
91 previously killed middle indices.
93 IF NoOfIndices=CoordListIndex
97 UNTIL (NoOfIndices=0) OR (CoordIndex[NoOfIndices].Start#0)
99 NoOfCoords := CoordIndex[NoOfIndices].End
101 WriteString('All Coordinate lists have been killed - Module StoreCoords') ;
110 AddCoord - places a coordinate into the specified list.
113 PROCEDURE AddCoord (CoordListIndex: CARDINAL; x, y: CARDINAL) ;
115 IF NoOfCoords=MaxCoord
117 WriteString('Too many coordinates in a list in Module StoreCoords') ;
119 WriteString('Increase MaxCoord') ;
122 ELSIF UniqueCoord(CoordListIndex, x, y)
125 WITH Coords[NoOfCoords] DO
129 WITH CoordIndex[CoordListIndex] DO
137 UniqueCoord - returns true if x and y are unique in the coord list.
140 PROCEDURE UniqueCoord (CoordListIndex: CARDINAL;
141 x, y: CARDINAL) : BOOLEAN ;
146 WITH CoordIndex[CoordListIndex] DO
149 WHILE (NOT Found) AND (i<=End) DO
151 Found := (X=x) AND (Y=y)
161 GetAndDeleteRandomCoord - Returns a random coordinate from the coordinate
162 list and then it is deleted from the list.
165 PROCEDURE GetAndDeleteRandomCoord (CoordListIndex: CARDINAL;
166 VAR x, y: CARDINAL) ;
170 WITH CoordIndex[CoordListIndex] DO
171 i := Start+GetRand(End-Start+1) ; (* +1 for GetRand *)
182 UNTIL (j=i) OR (Coords[j].X#0) ;
186 X := 0 ; (* Now delete this box *)
190 END GetAndDeleteRandomCoord ;
194 CoordsExist - returns true if a coordinate exists
195 within the CoordListIndex.
198 PROCEDURE CoordsExist (CoordListIndex: CARDINAL) : BOOLEAN ;
204 WITH CoordIndex[CoordListIndex] DO
207 (* Was at least one coordinate *)
209 WHILE (NOT ok) AND (i<=End) DO
210 ok := (Coords[i].X#0) ; (* #0 means coordinate still exists *)
223 WITH CoordIndex[NoOfIndices] DO