home *** CD-ROM | disk | FTP | other *** search
- ############################################################################
- #
- # File: puzz.icn
- #
- # Subject: Program to create word search puzzle
- #
- # Author: Chris Tenaglia
- #
- # Date: Februrary 21, 1992
- #
- ###########################################################################
-
- global matrix, # the actual puzzle board
- width, # width of the puzzle
- height, # height of the puzzle
- completed # number of completed word placements
-
- procedure main(param)
- local i, j, line, pass, tokens, word, words
-
- #
- # initial set up : x=20, y=20 by default
- #
- width := param[1] | 20
- height := param[2] | 20
- words := []
- #
- # load words to place in a space delimited
- # file. more than one word per line is ok.
- #
- while line := map(read()) do
- {
- tokens := parse(line,' \t')
- while put(words,pop(tokens))
- }
- #
- # get ready for main processing
- #
- matrix := table(" ")
- pass := 0
- completed := 0
- &random:= map(&clock,":","0")
- #
- # here's the actual word placement rouinte
- #
- every word := !words do place(word)
- #
- # fill in the unchosen areas with random alphas
- #
- every i := 1 to height do
- every j := 1 to width do
- if matrix[i||","||j] == " " then
- matrix[i||","||j] := ?(&ucase)
- #
- # output results (for the test giver, words are lcase, noise is ucase)
- #
- write(completed," words inserted out of ",*words," words.\n")
- write("\nNow for the puzzle you've been waiting for! (ANSWER)\n")
- every i := 1 to height do
- {
- every j := 1 to width do writes(matrix[i||","||j]," ")
- write()
- }
- #
- # output results (for the test taker, everything is upper case
- #
- write("\fNow for the puzzle you've been waiting for! (PUZZLE)\n")
- every i := 1 to height do
- {
- every j := 1 to width do writes(map(matrix[i||","||j],&lcase,&ucase)," ")
- write()
- }
- end
-
- #
- # this procedure tries to place the word in a copy of the matrix
- # if successful the updated copy is moved into the original
- # if not, the problem word is skipped after 20 tries
- #
- procedure place(str)
- local byte, construct, direction, item, pass, x, xinc, y, yinc
- static xstep,ystep
-
- initial {
- xstep := [0,1,1,1,0,-1,-1,-1]
- ystep := [-1,-1,0,1,1,1,0,-1]
- }
- pass := 0
-
- repeat {
- if (pass +:= 1) > 20 then
- {
- write("skipping ",str)
- fail
- }
- direction := ?8
- xinc := integer(xstep[direction])
- yinc := integer(ystep[direction])
-
- if xinc < 0 then x := *str + ?(width - *str)
- if xinc = 0 then x := ?height
- if xinc > 0 then x := ?(width - *str)
-
- if yinc < 0 then y := *str + ?(height - *str)
- if yinc = 0 then y := ?width
- if yinc > 0 then y := ?(height - *str)
-
- if (x < 1) | (y < 1) then stop(str," too long.")
-
- construct := copy(matrix)
- item := str
- write("placing ",item)
- every byte := !item do
- {
- if (construct[x||","||y] ~== " ") &
- (construct[x||","||y] ~== byte) then break next
- construct[x||","||y] := byte
- x +:= xinc
- y +:= yinc
- }
- matrix := copy(construct)
- completed +:= 1
- return "ok"
- } # end repeat
- return "ok"
- end
-
- #
- # parse a string into a list with respect to a delimiter (cset)
- #
- procedure parse(line,delims)
- local tokens
- static chars
-
- chars := &cset -- delims
- tokens := []
- line ? while tab(upto(chars)) do put(tokens,tab(many(chars)))
- return tokens
- end
-