HuntTheWumpus

The classic hunt the Wumpus game based on the AtariArchives game books entry http://www.atariarchives.org/

This is a console based game, rip for modifying / playing with. Like all early games, it relies on your imagination, not fancy graphics - they come later!

--Hunt the Wumpus   
--the classic 70's game   
--converted from the BASIC http://www.atariarchives.org/morebasicgames/showpage.php?page=179   
   
include std/console.e   
include std/text.e   
include std/regex.e as re   
include std/get.e 
   
--trying to stick closer to the spirit of the BASIC Wumpus!  
constant YOU = 1, WUMPUS = 2, PITS1 = 3, PITS2 = 4, BATS1 = 5, BATS2 = 6, ARROWS = 7  
   
---------------------------------------------------------------------------------------------   
procedure instructions()   
---------------------------------------------------------------------------------------------   
clear_screen()   
   
puts(1, "Welcome to Hunt the Wumpus\n")   
puts(1, "The wumpus lives in a cave of 20 rooms. Each room has 3 tunnels\n")   
puts(1, "leading to other rooms. (Look at a dodecahedron to see how this\n")   
puts(1, "works - if you don't know what a dodecahedron is, ask someone).\n")   
puts(1, "\n")   
puts(1, "Hazards\n")   
puts(1, "Bottomless pits - 2 rooms have bottomless pits in them. If you\n")   
puts(1, "  there you fall in (and lose). \n")   
puts(1, "Superbats - 2 other rooms have superbats. If you go there, a \n")   
puts(1, "  superbat grabs you and takes you to some other random room \n")   
puts(1, "  (which could be..... troublesome!\n")   
puts(1, "\n")   
puts(1, "The wumpus is not bothered by such hazards (he has sucker feet,\n")   
puts(1, "and is too big to lift). Usually he is asleep. Two things wake him\n")   
puts(1, "up : your entering his room, and your shooting an arrow.\n")   
puts(1, "If the wumpus wakes up, he moves one room (P=0.75) or stays\n")   
puts(1, "put (P=0.25). After that, if he is in the same room as you\n")   
puts(1, "he eats you up (and you lose), or he goes back to sleep!\n")   
puts(1, "\n")   
   
any_key("Press any key..........")   
   
puts(1, "Each turn, you may move, or shoot a crooked arrow.\n")   
puts(1, "  Moving - you can move one room (through a tunnel)\n")   
puts(1, "  Shooting - you have 5 arrows - you lose when you run out.\n")   
puts(1, "  Each arrow can go through 1 to 5 rooms, you aim by telling\n")   
puts(1, "  the computer the rooms you want it to go through. If the arrow\n")   
puts(1, "  can't go that way (no tunnel, it moves at random to an adjacent \n")   
puts(1, "  room. If the arrow hits the wumpus, you win, if it hits you,\n")   
puts(1, "  you lose.\n")   
puts(1, "\n")   
puts(1, "When you are 1 room away from a hazard, the computer will say\n")   
puts(1, "  Wumpus   - I smell a wumpus\n")   
puts(1, "  Bats     - Bats nearby\n")   
puts(1, "  Pit      - I feel a draft\n")   
puts(1, "\n")   
puts(1, "Good luck!\n")   
   
wait_key()   
   
end procedure   
   
---------------------------------------------------------------------------------------------   
function initialise_caves()    
---------------------------------------------------------------------------------------------   
-- Remember to swap row and column from the BASIC source in future references.    
return {{2,5,8}, {1, 3, 10}, {2, 4, 12}, {3, 5, 14}, {1, 4, 6},    
	{5, 7, 15}, {6, 8, 17}, {1, 7, 9}, {8, 10, 18}, {2, 9, 11},    
	{10, 12, 19}, {3, 11, 13}, {12, 14, 20}, {4, 13, 15}, {6, 14, 16},    
	{15, 17, 20}, {7, 16, 18}, {18, 9, 17}, {19, 11, 18}, {20, 13, 16, 19}}    
end function    
   
---------------------------------------------------------------------------------------------   
function ask(sequence prompt, sequence filter)   
---------------------------------------------------------------------------------------------   
/*   

print prompt and wait for an answer   
filter is a regular expression to filter answer   
*/   
re:regex valid_answer=re:new(filter,CASELESS)   
sequence answer   
   
   puts(1,prompt)   
   while 1  do   
      answer=gets(0)   
      answer=answer[1..$-1]    
      if sequence(re:find(valid_answer,answer)) then   
         exit   
      else   
        puts(1,"\ninvalid answer, try again\n"&prompt)   
      end if   
   end while   
   return answer   
end function   
   
---------------------------------------------------------------------------------------------   
function mkStatusList()    
---------------------------------------------------------------------------------------------   
sequence status = {0,0,0,0,0,0,5} --setting [7] to arrow count   
    sequence list = {1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20}   
    integer r   
    for i = 1 to 6 do   
      r = rand(20) -- select a number between i and 20 inclusive   
      status[i] = list[r]  -- copy the value to status   
      list[r] = list[i]    -- removing list[r] from the list   
    end for    
return status   
end function  
  
---------------------------------------------------------------------------------------------   
procedure show_where_you_are(sequence status, sequence caves)  
---------------------------------------------------------------------------------------------   
printf(1, "You are in room %d\n", {status[YOU]})  
  
printf(1, "There are tunnels leading to rooms ", {})  
  
for i = 1 to length(caves[status[YOU]]) do  
     printf(1, "%d ", {caves[status[YOU]][i]})  
end for  
  
puts(1, "\n")  
  
end procedure  
  
---------------------------------------------------------------------------------------------   
procedure detect_hazards(sequence status, sequence caves)  
---------------------------------------------------------------------------------------------   
sequence hzd = {} 
 
if find(status[BATS1],caves[status[YOU]]) or find(status[BATS2],caves[status[YOU]]) then 
        hzd = append(hzd, "Bats nearby!") 
end if 
 
if find(status[PITS1],caves[status[YOU]]) or find(status[PITS2],caves[status[YOU]]) then 
        hzd = append(hzd, "I feel a draft!") 
end if 
 
if find(status[WUMPUS],caves[status[YOU]]) then 
        hzd = append(hzd, "I smell a wumpus!") 
end if 
 
if length(hzd) = 0 then 
        return 
end if 
 
for i = 1 to length(hzd) do 
        puts(1, hzd[i] & "\n") 
end for 
 
end procedure  
  
---------------------------------------------------------------------------------------------   
function move_hunter(sequence status, sequence caves) 
---------------------------------------------------------------------------------------------   
object dest_room 
sequence s 
 
s = prompt_string("\nMove to which room? ") 
dest_room = value(s) 
dest_room = dest_room[2] 
 
if find(dest_room, caves[status[YOU]] ) = 0 then 
        puts(1, "You cannot get to that room from here!\n\n") 
        return status 
end if 
 
puts(1, "\n") 
status[YOU] = dest_room 
return status 
end function 
 
---------------------------------------------------------------------------------------------   
function detect_entered_hazards(sequence status, sequence caves) 
---------------------------------------------------------------------------------------------   
--bats 
if status[YOU] = status[PITS1] or status[YOU] = status[PITS2] then 
        puts(1, "AAAAARRGGHHHHH! Fell in a pit!\n") 
        status[YOU] = -1 
        return status 
end if 
 
if status[YOU] = status[BATS1] or status[YOU] = status[BATS2] then 
        puts(1, "Bats grabbed you - off to another room!\n") 
        while 1 do 
                status[YOU] = rand(20) 
                --don't want the hunter in a room with the wumpus, bats or pits! 
                if status[YOU] = status[BATS1] or status[YOU] = status[BATS1] or  
                   status[YOU] = status[PITS1] or status[YOU] = status[PITS1] or  
                   status[YOU] = status[WUMPUS] then 
                        continue 
                else 
                        exit 
                end if 
        end while 
        return status 
end if 
 
if status[YOU] = status[WUMPUS] then 
        puts(1, "Munch munch, gobble gobble. Wumpus ate you!\n") 
        status[YOU] = -1 
end if 
 
return status 
end function 
 
---------------------------------------------------------------------------------------------   
function shoot_arrow(sequence status, sequence caves) 
--fires an arrow through a number of rooms 
--if you miss the wumpus, it wakes up, and moves to another room 
--if you hit it, the wumpus is dead. 
---------------------------------------------------------------------------------------------   
object nr, ar, current_arrow_room 
integer nwr 
 
status[ARROWS] -= 1 
current_arrow_room = status[YOU] 
 
puts(1, "\n") 
 
while 1 do 
        nr = prompt_string("No. of rooms : ") 
        nr = value(nr) 
        nr = nr[2] 
        if nr >= 1 and nr <= 5 then exit end if  
        puts(1, "Between 1 and 5 rooms please.\n") 
end while 
 
for i = 1 to nr do 
        while 1 do 
                --? caves[current_arrow_room]  --uncomment this for an easier game 
                ar = prompt_string("Which room : ") 
                ar = value(ar) 
                ar = ar[2] 
 
                if find(ar, caves[current_arrow_room]) = 0 then 
                        puts(1, "Arrows aren't that crooked - try another room!\n") 
                        continue 
                end if 
                exit 
        end while 
 
        current_arrow_room = ar 
 
        --check for pesence of wumpus 
        if current_arrow_room = status[WUMPUS] then 
                status[WUMPUS] = -1 
                return status 
        end if 
 
        --check if you've shot back into your room 
        if current_arrow_room = status[YOU] then 
                puts(1, "Ouch, you shot yourself - luckily in the head, no damage!") 
                exit 
        end if 
end for 
 
--didn't get the Wumpus then, but woke it up 
nwr = rand(3) 
status[WUMPUS] = caves[status[WUMPUS]][nwr] 
if status[WUMPUS] = status[YOU] then 
        puts(1, "Munch munch, gobble gobble. Wumpus ate you!\n") 
        status[YOU] = -1 
        return status 
end if 
 
if status[ARROWS] = 0 then 
        status[YOU] = -1 
        puts(1, "You ran out of arrows!\n") 
end if 
 
return status 
end function 
 
---------------------------------------------------------------------------------------------   
procedure start_game(sequence status, sequence caves)   
---------------------------------------------------------------------------------------------   
sequence response  
  
while 1 do  
     show_where_you_are(status, caves)  
     detect_hazards(status, caves)  
     response = ask("Move or shoot (m/s)", "[ms]")  
  
     if response[1] = 'm' then  
          status = move_hunter(status, caves) 
          status = detect_entered_hazards(status, caves) 
     else  
          status = shoot_arrow(status, caves)  
     end if  
  
     if status[YOU] = -1 then 
          puts(1, "You're dead!\n") 
          return 
     end if 
 
     if status[WUMPUS] = -1 then 
          puts(1, "You heartless fiend - you killed a defenceless Wumpus!\n") 
          return 
     end if 
 
end while  
   
end procedure   
---------------------------------------------------------------------------------------------  
procedure main()  
---------------------------------------------------------------------------------------------  
sequence inp  
sequence caves 
sequence status  
 
inp = upper(prompt_string("Do you want instructions? (y/n)"))  
if inp[1] = 'Y' then  
        instructions()  
end if  
  
while 1 do 
        caves = initialise_caves()  
        status = mkStatusList() 
        start_game(status, caves)  
        inp = upper(ask("Play again?", "[yn]")) 
        if inp[1] = 'N' then exit end if 
end while 
end procedure  
  
main()  
 
/* 

for i = 1 to 10 do 
status = mkStatusList() 
? status 
 end for 
 */ 
--taking a slightly different track to the basic program here,  
--in the basic program, one array holds the hunter, wumpus, pits and bats  
--here each thing is an 'object' with 'properties' (this is not oop!)  
--hunter = {rand(20), 5}     --{current_room, arrows}  
--wumpus = {rand(20), 0}     --{current_room, asleep or awake}  
--pits = {rand(20), rand(20)}  
--bats = {rand(20), rand(20)}  
  
--check hunter doesn't start in room with a wumpus, pits or bats  
 
/*while 1 label "crossover" do  

     if hunter[ROOM] = wumpus[ROOM] then  
        wumpus[ROOM] = rand(20)  
        continue  
     end if  
       
     for i = 1 to 2 do  
        if hunter[ROOM] = pits[i] then  
              pits[i] = rand(20)  
              continue  
        end if  
        if hunter[ROOM] = bats[i] then  
              bats[i] = rand(20)  
              continue  
        end if  
        if wumpus[ROOM] = bats[i] then  
              bats[i] = rand(20)  
              continue  
        end if  
        if wumpus[ROOM] = pits[i] then  
              pits[i] = rand(20)  
              continue  
        end if  
        for j = 1 to 2 do  
              if bats[i] = pits[j] then  
                    pits[j] = rand(20)  
                    continue "crossover" 
              end if  
        end for  
     end for  
     exit  
end while  
*/ 
 
 
  
  
 
 
Not Categorized, Please Help

Search



Quick Links

User menu

Not signed in.

Misc Menu