1/* <Chocolate adventure>, by <Yifeng Zhu(yifengz)>. */
    2
    3:- dynamic i_am_at/1, at/2, holding/1.    4:- retractall(at(_, _)), retractall(i_am_at(_)), retractall(alive(_)).    5
    6/*this defines my current place*/
    7i_am_at(openarea).
    8
    9/*This fact tells that I currently have money and flashlight*/
   10holding(money).
   11holding(flashlight).
   12
   13
   14/*this defines how multiple places are connected*/
   15path(openarea, w, warehouse).
   16path(warehouse, e, openarea).
   17
   18path(openarea, s, house).
   19				
   20path(house, n, openarea).
   21path(openarea, e, grocery).
   22path(grocery, w, openarea).
   23
   24path(openarea, n, door) :- holding(badge).
   25path(openarea, n, door) :-
   26        write('The door is locked, you need to have your badge.'), nl,
   27        !, fail.
   28
   29path(door, s, openarea).
   30
   31path(door, n, cave) :- holding(flashlight), holding(battery).
   32path(door, n, cave) :- 
   33        write('You need to have flashlight and battery to enter the cave.'), nl,
   34        !, fail.
   35
   36path(cave, s, door).
   37
   38/* These facts tell where the various objects in the game
   39   are located. */	
   40at(badge,openarea).   
   41at(battery, warehouse).
   42at(witch, house).
   43at(chocolate , house).
   44at(food, grocery).
   45at(drink, grocery).
   46at(hammer, cave).
   47at(sealedBox,cave).
   48
   49/*This rule tells you how to open a sealedBox in the cave*/
   50open :-
   51		i_am_at(Place),
   52		holding(hammer),
   53		at(sealedBox,Place),
   54		retract(at(sealedBox,cave)),
   55		assert(at(magicStick,cave)),
   56		write('You successfully used your hammer to break the sealedBox'),nl,
   57		write('Now you can would see magicStick, grab them!'),
   58		!,nl.
   59open :-
   60		i_am_at(Place),
   61		at(sealedBox, Place),
   62		write('You need to use a hammer to break the sealedBox.'),
   63		!,nl.
   64open :-
   65		write('Sorry, I dont see anything you can open here.'),nl.
   66		
   67/*This rule tells you how to consume food or drink*/
   68consume(X) :-
   69		holding(X),
   70		retract(holding(X)),
   71		write('You just consumed '),write(X),
   72		!,nl.
   73consume(X) :-
   74	    write('You cannot consume '),write(X),nl,
   75		write('You do not own it'),nl.
   76		
   77/* These rules describe how to buy an object. */
   78buy(X) :-
   79        holding(X),
   80        write('You''re already holding it!'),
   81        !, nl.
   82
   83buy(X) :-
   84        i_am_at(Place),
   85        at(X, Place),
   86		holding(money),
   87        retract(at(X, Place)),
   88		retract(holding(money)),
   89        assert(holding(X)),
   90        write('OK.'),
   91        !, nl.
   92
   93buy(X) :-
   94        i_am_at(Place),
   95        at(X, Place),
   96        write('You dont have money!'),
   97        !, nl.
   98		
   99buy(_) :-
  100        write('I don''t see it here.'),
  101        nl.
  102
  103
  104/* These rules describe how to return an object. */
  105cancel(X) :-
  106        holding(X),
  107        i_am_at(grocery),
  108        retract(holding(X)),
  109        assert(at(X, grocery)),
  110		assert(holding(money)),
  111        write('OK.'),
  112        !, nl.
  113
  114cancel(X) :-
  115        holding(X),
  116        i_am_at(warehouse),
  117        retract(holding(X)),
  118        assert(at(X, warehouse)),
  119		assert(holding(money)),
  120        write('OK.'),
  121        !, nl.
  122		
  123cancel(X) :-
  124        holding(X),
  125        write('You can only return at grocery or warehouse.'),
  126        !, nl.
  127		
  128cancel(_) :-
  129        write('You aren''t holding it!'),
  130        nl.
  131
  132/* These rules describe how to pick up an object in the cave. */
  133take(X) :-
  134        holding(X),
  135        write('You''re already holding it!'),
  136        nl, !.
  137
  138take(X) :-
  139        i_am_at(Place),
  140        at(X, Place),
  141        retract(at(X, Place)),
  142        assert(holding(X)),
  143        write('OK.'),
  144        nl, !.
  145
  146take(_) :-
  147        write('I don''t see it here.'),
  148        nl.
  149
  150/* These rules describe how to put down an object in the cave. */
  151drop(X) :-
  152        holding(X),
  153        i_am_at(Place),
  154        retract(holding(X)),
  155        assert(at(X, Place)),
  156        write('OK.'),
  157        nl, !.
  158
  159drop(_) :-
  160        write('You aren''t holding it!'),
  161        nl.
  162
  163/* These rules define the direction letters as calls to go/1. */
  164
  165n :- go(n).
  166
  167s :- go(s).
  168
  169e :- go(e).
  170
  171w :- go(w).
  172
  173
  174/* This rule tells how to move in a given direction. */
  175
  176go(Direction) :-
  177        i_am_at(Here),
  178        path(Here, Direction, There),
  179        retract(i_am_at(Here)),
  180        assert(i_am_at(There)),
  181        !, look.
  182
  183go(_) :-
  184        write('You can''t go that way.').
  185
  186
  187/* This rule tells how to look about you. */
  188
  189look :-
  190        i_am_at(Place),
  191        describe(Place),
  192        nl,
  193        notice_objects_at(Place),
  194        nl.
  195
  196/*These rules tell you what you have right now*/
  197i :-
  198		holding(X),
  199		write('You have '), write(X),nl,
  200		fail.
  201		
  202/* These rules set up a loop to mention all the objects
  203   in your vicinity. */
  204
  205notice_objects_at(Place) :-
  206        at(X, Place),
  207        write('There is a '), write(X), write(' here.'), nl,
  208        fail.
  209
  210notice_objects_at(_).
  211
  212
  213/* This rule tells how to die. */
  214
  215die :-
  216        finish.
  217
  218
  219/* Under UNIX, the "halt." command quits Prolog but does not
  220   remove the output window. On a PC, however, the window
  221   disappears before the final output can be seen. Hence this
  222   routine requests the user to perform the final "halt." */
  223
  224finish :-
  225        nl,
  226        write('The game is over. Please enter the "halt." command.'),
  227        nl.
  228
  229
  230/* This rule just writes out game instructions. */
  231
  232instructions :-
  233        nl,
  234        write('Enter commands using standard Prolog syntax.'), nl,
  235        write('Available commands are:'), nl,
  236        write('start.             -- to start the game.'), nl,
  237        write('n.  s.  e.  w.     -- to go in that direction.'), nl,
  238        write('take(Object).      -- to pick up an object in the cave or house.'), nl,
  239        write('drop(Object).      -- to put down an object in the cave or house.'), nl,
  240		write('buy(Object).      -- to buy an object in grocery or warehouse.'), nl,
  241        write('cancel(Object).      -- to return an object in grocery or warehouse.'), nl,
  242        write('look.              -- to look around you again.'), nl,
  243		write('i.		 -- to find out what you have in hand right now.'),nl,
  244		write('open				 -- to open sealedBox.'),nl,
  245		write('consume			 --to consume food or drink you have.'),nl,
  246        write('instructions.      -- to see this message again.'), nl,
  247        write('halt.              -- to end the game and quit.'), nl,
  248        nl.
  249
  250
  251/* This rule prints out instructions and tells where you are. */
  252
  253start :-
  254        instructions,
  255        look.
  256
  257
  258/* These rules describe the various rooms.  Depending on
  259   circumstances, a room may have more than one description. */
  260describe(openarea) :-
  261		holding(chocolate),
  262        write('Congratulations!'), nl,
  263		write('You found chocolate for your friends,'),nl,
  264        write('and won the game.'), nl,
  265		finish,!.
  266		
  267describe(openarea) :-
  268        write('You are in the openarea.'), nl,
  269		write('To the north is a locked door which you need to use badge to open;'),nl,
  270        write('to the south is a small shaded black house;'), nl,
  271        write('to the west is a large warehouse; to the east is a modern grocery.'), nl,
  272        write('You task is to safely explore those places'), nl,
  273        write('and find lots of chocolate for your friends.'), nl.
  274		
  275		
  276describe(house) :-
  277		at(witch, house),
  278		holding(magicStick),
  279		retract(at(witch,house)),
  280		retract(holding(magicStick)),
  281        write('Wow! You defeated the witch.'), nl,!.
  282		
  283describe(house) :-
  284		at(witch,house),
  285		write('Woo, you met the witch without magicStick she killed you.'),nl,
  286		write('Next time make sure you grab the magicStick'),nl,
  287		write('you need to enter the door and explore inside.'),nl,
  288		die,
  289		!,fail.
  290describe(house) :-
  291		write('No one is here, take whatever you see if any'),nl.
  292		
  293describe(warehouse) :-
  294		write('You are in a large warehouse'),nl,
  295		write('look around and buy something you need.'),nl,
  296		write('To the east is the openarea where you can go back.'),nl.
  297		
  298describe(grocery) :-
  299		write('You are in a modern grocery store'),nl,
  300		write('look around and buy something you need.'),nl,
  301		write('To the west is the openarea where you can go back.'),nl.
  302
  303describe(door) :-
  304		write('You are at the door with you badge'),nl,
  305		write('and you would find a cave to its north.'),nl,
  306		write('To the south is the openarea where you can go back.'),nl.
  307
  308describe(cave) :-
  309        write('This is the cave you have been looking for!'),nl,
  310		write('Grab as many things as you want.'),nl,
  311		write('To the south is the door you just entered.'),nl