dw_fluffos_v2/
dw_fluffos_v2/fluffos-2.9-ds2.05/
dw_fluffos_v2/fluffos-2.9-ds2.05/ChangeLog.old/
dw_fluffos_v2/fluffos-2.9-ds2.05/Win32/
dw_fluffos_v2/fluffos-2.9-ds2.05/compat/
dw_fluffos_v2/fluffos-2.9-ds2.05/compat/simuls/
dw_fluffos_v2/fluffos-2.9-ds2.05/include/
dw_fluffos_v2/fluffos-2.9-ds2.05/testsuite/
dw_fluffos_v2/fluffos-2.9-ds2.05/testsuite/clone/
dw_fluffos_v2/fluffos-2.9-ds2.05/testsuite/command/
dw_fluffos_v2/fluffos-2.9-ds2.05/testsuite/data/
dw_fluffos_v2/fluffos-2.9-ds2.05/testsuite/etc/
dw_fluffos_v2/fluffos-2.9-ds2.05/testsuite/include/
dw_fluffos_v2/fluffos-2.9-ds2.05/testsuite/inherit/
dw_fluffos_v2/fluffos-2.9-ds2.05/testsuite/inherit/master/
dw_fluffos_v2/fluffos-2.9-ds2.05/testsuite/log/
dw_fluffos_v2/fluffos-2.9-ds2.05/testsuite/single/
dw_fluffos_v2/fluffos-2.9-ds2.05/testsuite/single/tests/compiler/
dw_fluffos_v2/fluffos-2.9-ds2.05/testsuite/single/tests/efuns/
dw_fluffos_v2/fluffos-2.9-ds2.05/testsuite/single/tests/operators/
dw_fluffos_v2/fluffos-2.9-ds2.05/testsuite/u/
dw_fluffos_v2/fluffos-2.9-ds2.05/tmp/
dw_fluffos_v2/fluffos-2.9-ds2.05/windows/
dw_fluffos_v2/lib/
dw_fluffos_v2/lib/binaries/cmds/
dw_fluffos_v2/lib/binaries/cmds/creator/
dw_fluffos_v2/lib/binaries/cmds/living/
dw_fluffos_v2/lib/binaries/cmds/player/
dw_fluffos_v2/lib/binaries/d/admin/obj/
dw_fluffos_v2/lib/binaries/d/liaison/
dw_fluffos_v2/lib/binaries/global/virtual/
dw_fluffos_v2/lib/binaries/global/virtual/setup_compiler/
dw_fluffos_v2/lib/binaries/obj/handlers/autodoc/
dw_fluffos_v2/lib/binaries/obj/handlers/terrain_things/
dw_fluffos_v2/lib/binaries/obj/misc/
dw_fluffos_v2/lib/binaries/obj/misc/buckets/
dw_fluffos_v2/lib/binaries/obj/monster/
dw_fluffos_v2/lib/binaries/obj/reactions/
dw_fluffos_v2/lib/binaries/obj/reagents/
dw_fluffos_v2/lib/binaries/secure/cmds/creator/
dw_fluffos_v2/lib/binaries/secure/master/
dw_fluffos_v2/lib/binaries/std/
dw_fluffos_v2/lib/binaries/std/dom/
dw_fluffos_v2/lib/binaries/std/effects/object/
dw_fluffos_v2/lib/binaries/std/guilds/
dw_fluffos_v2/lib/binaries/std/languages/
dw_fluffos_v2/lib/binaries/std/races/
dw_fluffos_v2/lib/binaries/std/room/
dw_fluffos_v2/lib/binaries/std/room/basic/
dw_fluffos_v2/lib/binaries/std/shops/
dw_fluffos_v2/lib/binaries/std/shops/inherit/
dw_fluffos_v2/lib/binaries/www/
dw_fluffos_v2/lib/cmds/guild-race/
dw_fluffos_v2/lib/cmds/guild-race/crafts/
dw_fluffos_v2/lib/cmds/guild-race/other/
dw_fluffos_v2/lib/cmds/playtester/
dw_fluffos_v2/lib/cmds/playtester/senior/
dw_fluffos_v2/lib/d/admin/
dw_fluffos_v2/lib/d/admin/log/
dw_fluffos_v2/lib/d/admin/mapper/31-10-01/mapmaker/event/
dw_fluffos_v2/lib/d/admin/meetings/
dw_fluffos_v2/lib/d/admin/obj/
dw_fluffos_v2/lib/d/admin/room/we_care/
dw_fluffos_v2/lib/d/admin/save/
dw_fluffos_v2/lib/d/dist/
dw_fluffos_v2/lib/d/dist/mtf/
dw_fluffos_v2/lib/d/dist/pumpkin/
dw_fluffos_v2/lib/d/dist/pumpkin/chars/
dw_fluffos_v2/lib/d/dist/pumpkin/desert/
dw_fluffos_v2/lib/d/dist/pumpkin/gumboot/
dw_fluffos_v2/lib/d/dist/pumpkin/hospital/
dw_fluffos_v2/lib/d/dist/pumpkin/inherit/
dw_fluffos_v2/lib/d/dist/pumpkin/map/
dw_fluffos_v2/lib/d/dist/pumpkin/plain/
dw_fluffos_v2/lib/d/dist/pumpkin/pumpkin/
dw_fluffos_v2/lib/d/dist/pumpkin/save/
dw_fluffos_v2/lib/d/dist/pumpkin/squash/
dw_fluffos_v2/lib/d/dist/pumpkin/terrain/
dw_fluffos_v2/lib/d/dist/pumpkin/woods/
dw_fluffos_v2/lib/d/dist/start/
dw_fluffos_v2/lib/d/learning/TinyTown/buildings/
dw_fluffos_v2/lib/d/learning/TinyTown/map/
dw_fluffos_v2/lib/d/learning/TinyTown/roads/
dw_fluffos_v2/lib/d/learning/add_command/
dw_fluffos_v2/lib/d/learning/arms_and_weps/
dw_fluffos_v2/lib/d/learning/chars/
dw_fluffos_v2/lib/d/learning/cutnpaste/
dw_fluffos_v2/lib/d/learning/examples/npcs/
dw_fluffos_v2/lib/d/learning/examples/player_houses/npcs/
dw_fluffos_v2/lib/d/learning/examples/terrain_map/basic/
dw_fluffos_v2/lib/d/learning/functions/
dw_fluffos_v2/lib/d/learning/handlers/
dw_fluffos_v2/lib/d/learning/help_topics/npcs/
dw_fluffos_v2/lib/d/learning/help_topics/objects/
dw_fluffos_v2/lib/d/learning/help_topics/rcs_demo/
dw_fluffos_v2/lib/d/learning/help_topics/rooms/
dw_fluffos_v2/lib/d/learning/help_topics/rooms/crowd/
dw_fluffos_v2/lib/d/learning/help_topics/rooms/situations/
dw_fluffos_v2/lib/d/learning/items/
dw_fluffos_v2/lib/d/learning/save/
dw_fluffos_v2/lib/d/liaison/
dw_fluffos_v2/lib/d/liaison/NEWBIE/doc/
dw_fluffos_v2/lib/d/liaison/NEWBIE/save/oldlog/
dw_fluffos_v2/lib/db/
dw_fluffos_v2/lib/doc/
dw_fluffos_v2/lib/doc/creator/
dw_fluffos_v2/lib/doc/creator/autodoc/include/reaction/
dw_fluffos_v2/lib/doc/creator/autodoc/include/ritual_system/
dw_fluffos_v2/lib/doc/creator/autodoc/include/talker/
dw_fluffos_v2/lib/doc/creator/autodoc/include/terrain_map/
dw_fluffos_v2/lib/doc/creator/autodoc/obj/baggage/
dw_fluffos_v2/lib/doc/creator/autodoc/obj/clock/
dw_fluffos_v2/lib/doc/creator/autodoc/obj/clothing/
dw_fluffos_v2/lib/doc/creator/autodoc/obj/cont_save/
dw_fluffos_v2/lib/doc/creator/autodoc/obj/corpse/
dw_fluffos_v2/lib/doc/creator/autodoc/obj/money/
dw_fluffos_v2/lib/doc/creator/autodoc/obj/monster/
dw_fluffos_v2/lib/doc/creator/autodoc/obj/scabbard/
dw_fluffos_v2/lib/doc/creator/autodoc/obj/service_provider/
dw_fluffos_v2/lib/doc/creator/autodoc/obj/state_changer/
dw_fluffos_v2/lib/doc/creator/autodoc/obj/wand/
dw_fluffos_v2/lib/doc/creator/autodoc/std/book_dir/
dw_fluffos_v2/lib/doc/creator/autodoc/std/key/
dw_fluffos_v2/lib/doc/creator/autodoc/std/learning/
dw_fluffos_v2/lib/doc/creator/autodoc/std/map/
dw_fluffos_v2/lib/doc/creator/autodoc/std/race/
dw_fluffos_v2/lib/doc/creator/autodoc/std/weapon_logic/
dw_fluffos_v2/lib/doc/creator/files/
dw_fluffos_v2/lib/doc/creator/policy/
dw_fluffos_v2/lib/doc/creator/room/
dw_fluffos_v2/lib/doc/effects/
dw_fluffos_v2/lib/doc/ideas/
dw_fluffos_v2/lib/doc/known_command/
dw_fluffos_v2/lib/doc/lpc/basic_manual/
dw_fluffos_v2/lib/doc/lpc/intermediate/
dw_fluffos_v2/lib/doc/new/add_command/
dw_fluffos_v2/lib/doc/new/handlers/
dw_fluffos_v2/lib/doc/new/living/
dw_fluffos_v2/lib/doc/new/living/race/
dw_fluffos_v2/lib/doc/new/living/spells/
dw_fluffos_v2/lib/doc/new/player/
dw_fluffos_v2/lib/doc/new/room/guild/
dw_fluffos_v2/lib/doc/new/room/outside/
dw_fluffos_v2/lib/doc/new/room/storeroom/
dw_fluffos_v2/lib/doc/object/
dw_fluffos_v2/lib/doc/playtesters/
dw_fluffos_v2/lib/doc/policy/
dw_fluffos_v2/lib/doc/weapons/
dw_fluffos_v2/lib/global/handlers/
dw_fluffos_v2/lib/global/virtual/setup_compiler/
dw_fluffos_v2/lib/include/
dw_fluffos_v2/lib/include/cmds/
dw_fluffos_v2/lib/include/effects/
dw_fluffos_v2/lib/include/npc/
dw_fluffos_v2/lib/include/shops/
dw_fluffos_v2/lib/net/daemon/chars/
dw_fluffos_v2/lib/net/inherit/
dw_fluffos_v2/lib/net/intermud3/
dw_fluffos_v2/lib/net/intermud3/services/
dw_fluffos_v2/lib/net/obj/
dw_fluffos_v2/lib/net/save/
dw_fluffos_v2/lib/net/smnmp/
dw_fluffos_v2/lib/net/snmp/
dw_fluffos_v2/lib/obj/amulets/
dw_fluffos_v2/lib/obj/b_day/
dw_fluffos_v2/lib/obj/examples/
dw_fluffos_v2/lib/obj/food/alcohol/
dw_fluffos_v2/lib/obj/food/chocolates/
dw_fluffos_v2/lib/obj/food/fruits/
dw_fluffos_v2/lib/obj/food/meat/
dw_fluffos_v2/lib/obj/food/nuts/
dw_fluffos_v2/lib/obj/food/seafood/
dw_fluffos_v2/lib/obj/food/vegetables/
dw_fluffos_v2/lib/obj/fungi/
dw_fluffos_v2/lib/obj/furnitures/artwork/
dw_fluffos_v2/lib/obj/furnitures/bathroom/
dw_fluffos_v2/lib/obj/furnitures/beds/
dw_fluffos_v2/lib/obj/furnitures/cabinets/
dw_fluffos_v2/lib/obj/furnitures/chairs/
dw_fluffos_v2/lib/obj/furnitures/chests/
dw_fluffos_v2/lib/obj/furnitures/clocks/
dw_fluffos_v2/lib/obj/furnitures/crockery/
dw_fluffos_v2/lib/obj/furnitures/cupboards/
dw_fluffos_v2/lib/obj/furnitures/cushions/
dw_fluffos_v2/lib/obj/furnitures/fake_plants/
dw_fluffos_v2/lib/obj/furnitures/lamps/
dw_fluffos_v2/lib/obj/furnitures/mirrors/
dw_fluffos_v2/lib/obj/furnitures/outdoor/
dw_fluffos_v2/lib/obj/furnitures/safes/
dw_fluffos_v2/lib/obj/furnitures/shelves/
dw_fluffos_v2/lib/obj/furnitures/sideboards/
dw_fluffos_v2/lib/obj/furnitures/sofas/
dw_fluffos_v2/lib/obj/furnitures/stoves/
dw_fluffos_v2/lib/obj/furnitures/tables/
dw_fluffos_v2/lib/obj/furnitures/wardrobes/
dw_fluffos_v2/lib/obj/handlers/
dw_fluffos_v2/lib/obj/handlers/autodoc/
dw_fluffos_v2/lib/obj/jewellery/anklets/
dw_fluffos_v2/lib/obj/jewellery/bracelets/
dw_fluffos_v2/lib/obj/jewellery/earrings/
dw_fluffos_v2/lib/obj/jewellery/misc/
dw_fluffos_v2/lib/obj/jewellery/necklaces/
dw_fluffos_v2/lib/obj/jewellery/rings/
dw_fluffos_v2/lib/obj/media/
dw_fluffos_v2/lib/obj/misc/buckets/
dw_fluffos_v2/lib/obj/misc/jars/
dw_fluffos_v2/lib/obj/misc/papers/
dw_fluffos_v2/lib/obj/misc/player_shop/
dw_fluffos_v2/lib/obj/misc/shops/
dw_fluffos_v2/lib/obj/misc/traps/
dw_fluffos_v2/lib/obj/monster/
dw_fluffos_v2/lib/obj/monster/godmother/
dw_fluffos_v2/lib/obj/monster/transport/
dw_fluffos_v2/lib/obj/plants/inherit/
dw_fluffos_v2/lib/obj/potions/
dw_fluffos_v2/lib/open/boards/
dw_fluffos_v2/lib/save/autodoc/
dw_fluffos_v2/lib/save/bank_accounts/
dw_fluffos_v2/lib/save/boards/frog/
dw_fluffos_v2/lib/save/books/bed_catalog/
dw_fluffos_v2/lib/save/creators/
dw_fluffos_v2/lib/save/mail/
dw_fluffos_v2/lib/save/mail/p/
dw_fluffos_v2/lib/save/soul/data/
dw_fluffos_v2/lib/save/tasks/
dw_fluffos_v2/lib/save/vaults/
dw_fluffos_v2/lib/secure/cmds/lord/
dw_fluffos_v2/lib/secure/config/
dw_fluffos_v2/lib/secure/items/
dw_fluffos_v2/lib/secure/player/
dw_fluffos_v2/lib/soul/
dw_fluffos_v2/lib/soul/i/
dw_fluffos_v2/lib/soul/j/
dw_fluffos_v2/lib/soul/k/
dw_fluffos_v2/lib/soul/o/
dw_fluffos_v2/lib/soul/q/
dw_fluffos_v2/lib/soul/to_approve/
dw_fluffos_v2/lib/soul/u/
dw_fluffos_v2/lib/soul/v/
dw_fluffos_v2/lib/soul/wish_list/
dw_fluffos_v2/lib/soul/y/
dw_fluffos_v2/lib/soul/z/
dw_fluffos_v2/lib/std/creator/
dw_fluffos_v2/lib/std/effects/
dw_fluffos_v2/lib/std/effects/attached/
dw_fluffos_v2/lib/std/effects/external/
dw_fluffos_v2/lib/std/effects/fighting/
dw_fluffos_v2/lib/std/effects/other/
dw_fluffos_v2/lib/std/environ/
dw_fluffos_v2/lib/std/guilds/
dw_fluffos_v2/lib/std/hospital/
dw_fluffos_v2/lib/std/house/
dw_fluffos_v2/lib/std/house/onebedhouse/
dw_fluffos_v2/lib/std/house/onebedhut/
dw_fluffos_v2/lib/std/house/tworoomflat/
dw_fluffos_v2/lib/std/languages/
dw_fluffos_v2/lib/std/liquids/
dw_fluffos_v2/lib/std/nationality/
dw_fluffos_v2/lib/std/nationality/accents/
dw_fluffos_v2/lib/std/nationality/accents/national/
dw_fluffos_v2/lib/std/nationality/accents/regional/
dw_fluffos_v2/lib/std/npc/goals/
dw_fluffos_v2/lib/std/npc/goals/basic/
dw_fluffos_v2/lib/std/npc/goals/misc/
dw_fluffos_v2/lib/std/npc/inherit/
dw_fluffos_v2/lib/std/npc/plans/
dw_fluffos_v2/lib/std/npc/plans/basic/
dw_fluffos_v2/lib/std/outsides/
dw_fluffos_v2/lib/std/races/shadows/
dw_fluffos_v2/lib/std/room/basic/topography/
dw_fluffos_v2/lib/std/room/controller/
dw_fluffos_v2/lib/std/room/controller/topography/
dw_fluffos_v2/lib/std/room/furniture/games/
dw_fluffos_v2/lib/std/room/furniture/inherit/
dw_fluffos_v2/lib/std/room/inherit/carriage/
dw_fluffos_v2/lib/std/room/inherit/topography/
dw_fluffos_v2/lib/std/room/punishments/
dw_fluffos_v2/lib/std/room/topography/area/
dw_fluffos_v2/lib/std/room/topography/iroom/
dw_fluffos_v2/lib/std/room/topography/milestone/
dw_fluffos_v2/lib/std/shadows/
dw_fluffos_v2/lib/std/shadows/attached/
dw_fluffos_v2/lib/std/shadows/curses/
dw_fluffos_v2/lib/std/shadows/disease/
dw_fluffos_v2/lib/std/shadows/fighting/
dw_fluffos_v2/lib/std/shadows/room/
dw_fluffos_v2/lib/std/shops/controllers/
dw_fluffos_v2/lib/std/shops/objs/
dw_fluffos_v2/lib/std/shops/player_shop/
dw_fluffos_v2/lib/std/shops/player_shop/office_code/
dw_fluffos_v2/lib/std/socket/
dw_fluffos_v2/lib/www/
dw_fluffos_v2/lib/www/external/autodoc/
dw_fluffos_v2/lib/www/external/java/telnet/Documentation/
dw_fluffos_v2/lib/www/external/java/telnet/Documentation/images/
dw_fluffos_v2/lib/www/external/java/telnet/examples/
dw_fluffos_v2/lib/www/external/java/telnet/tools/
dw_fluffos_v2/lib/www/pics/
dw_fluffos_v2/lib/www/secure/creator/
dw_fluffos_v2/lib/www/secure/editors/
dw_fluffos_v2/lib/www/secure/survey_results/
dw_fluffos_v2/win32/
<html><!-- #BeginTemplate "/Templates/Body Text.dwt" -->
<head>
<title> Discworld Documentation </title>
</head>
<body bgcolor="#ffffff" TEXT="#000030" LINK="#4a529c" VLINK="#b57339">
<table width="75%" border="0">
  <tr>
    <td><font face="arial,helvetica"><img align=left src="http://discworld.imaginary.com/external//pics/dw4.gif"></font></td>
    <td><font face="arial,helvetica">
      <h2>Discworld Documentation:</h2>
      <h2>LPC for Dummies</h2>
      </font> 
      <p><font size="+1"><!-- #BeginEditable "Title" --><font size="+1"><font size="+1"><b>Tutorial 
  One: Putting It All Together - Simple Rooms</b></font></font><!-- #EndEditable --></font></p>
      <p><i>N.B - This is a work in progress... a living document if you like. 
        If it appears to be dead when you view it, don't worry. It's most likely 
        just playing possum.</i></p>
      <p>Comments on these chapters and tutorials can be e-mailed to <a href="mailto:drakkos@cableinet.co.uk">Drakkos.</a></p>
    </td>
  </tr>
</table>
<br>
<!-- #BeginEditable "Body" --> 
<p>kay, so now we've coded our first NPC and made it do some nifty things. Now 
  we need a place for it to live, so we're gonna spend this tutorial coding up 
  a nice room for our blob to live in. You should be familiar with what room code 
  looks like... if you're in your workroom, you can use 'more here' to see what 
  the code for your own little slice of the Disc looks like. Otherwise, 'more/w/insert_your_name_here/workroom.c' 
  will show you the code.
<p><b>Comments And Inherits Revisited </b>
<p>But we're going to extend the limits of your creator empire here by adding 
  a new room leading off to the lair of our blob. First things first, like with 
  an NPC, we should comment the file. When something goes wrong, this is very 
  useful for later Assigning Blame: 
<blockquote>
  <p><code>/* <br>
    &nbsp;&nbsp;&nbsp;&nbsp;This is a basic room! <br>
    &nbsp;&nbsp;&nbsp;&nbsp;Written by Drakkos. <br>
    &nbsp;&nbsp;&nbsp;&nbsp;29/09/2000 <br>
    */</code></p>
</blockquote>
<p> Okay, now what? Well, if you look at the code for your workroom, you'll see 
  that like our NPC, we need to inherit a file. The file we inherit for a basic 
  room is /std/room. There are some later specialisations of this inheritable, 
  allowing for outside rooms and so, but for now we'll just stick to the basics: 
<blockquote>
  <p><code>inherit "/std/room"; </code></p>
</blockquote>
<p><b>And Setup Revisted Too! </b>
<p>And we also need a nice setup function to deal with setting up the room. Unlike 
  our NPC example, you'll notice there is no 'set_name' in the setup for a room. 
  This is because players will not be directly manipulating a room, and so do 
  not need a name with which to access the object. We do have the familiar set_short() 
  and set_long(), however. Set_short will set the text that appears when a player 
  does a 'glance' or is walking around in brief mode. The long description is 
  the nice block of text that will appear when they do a look and are in verbose 
  mode. In your workroom, you'll see a function call add_property ("determinate", 
  "the "). Add_property allows a particular value to be stored on an object, referenced 
  by a particular property label. Other code may check for this property and deal 
  differently with an object depending on its presence. In this case, we're adding 
  a property called 'determinate' with a value of 'the '. What this does is set 
  the prefix to the short of the room as 'the'. So instead of just seeing 'workroom 
  of <creator>' when you glance in the room, you see 'the workroom of <creator>'. 
  Properties are very powerful when used properly... however, they are also very 
  difficult to regulate, so please don't go overboard with them. We'll discuss 
  properties in more depth later. 
<p>We also need a set_light() in our room. Unsurprisingly, this sets how bright 
  (or dark) the room is. A room without this function call will be permanently 
  in the dark. 
<p>Right, so let's put what we've got together so far to create a very basic room: 
<blockquote> 
  <p><code>void setup() { <br>
    &nbsp;&nbsp;&nbsp;&nbsp;set_short("blobby lair"); <br>
    &nbsp;&nbsp;&nbsp;&nbsp;set_long("This is where the grey blob lives. All around 
    lie " <br>
    &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;"frogs, and wombles, and strange 
    oozy things. It's a " <br>
    &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;"very nice lair, as lairs 
    go.\n");<br>
    &nbsp;&nbsp;&nbsp;&nbsp;add_property("determinate", "a "); <br>
    &nbsp;&nbsp;&nbsp;&nbsp;set_light(50); <br>
    } </code></p>
</blockquote>
<p><b>Adding Basic Items And Exits! </b>
<p>And there we have a very, very basic room that will load, but it won't let 
  us do very much. 'look frog', for example, will return a depressing 'you do 
  not think that the frog is here'. And there are no exits... we're stick in this 
  depressing, empty room forever. Help! Well, since we're gonna be here for a 
  while, let's make the place a little more interesting. The next function we're 
  going to learn is add_item. add_item adds an object that people can 'look' at 
  when in the room. This adds flavour and realism... you should have an add_item 
  for every object mentioned in your long, and for every item mentioned in the 
  text of each item. Obviously, you don't want to go to silly lengths with this, 
  but not being able to look at objects in a room should be an exception, and 
  not a rule. Anyway, add_item works by first passing in a label that can be looked 
  at, then passing in the text to be returned. Well... that's not entirely true. 
  Add_item is much cleverer than that, but we'll take that as a starting base. 
  So, we would do: 
<blockquote> 
  <p><code>add_item("frog", "The frogs are very nice. Very froggy."); <br>
    add_item("womble", "It's Uncle Bulgaria!"); <br>
    add_item("strange oozy things", "Ewww!"); </code></p>
</blockquote>
<p>Which would give us some stuff to look at while we're in the room. We'll look 
  at add_item in more depth later on in this tutorial, but for now that's all 
  we need to know. Note that the third add_item has multiple words for a label. 
  This allows for adjectives within an add_item... so you can look at 'things', 
  'strange things', 'oozy things', and 'strange oozy things'. Cool! </p>
<p>Note that add_item will automatically pluralise for you too... so 'look frog' 
  will give the description, as will 'look frogs'. Neat? Yes! However, it does 
  not work in reverse... if you had an add item 'frogs', then you couldn't 'look 
  frog'. Where-ever appropriate, you should use the singular add_item, since it'll 
  add the plural for you. </p>
<p>While we're here, it would be nice if we were able to leave the room and go 
  someplace else... so let's stick an add_exit in here. Add_exit() takes three 
  arguments. The first is the direction the exit lies in: 'east', for example. 
  The second is the filename of the room the exit takes us to, and the third argument 
  is the type of exit it is. So, let's try: 
<blockquote>
  <p><code>add_exit("east", "/w/your_name/workroom", "road"); </code></p>
</blockquote>
<p>Update the room, and hey presto, we're in a lovely leetle room with an exit 
  and things to look at! So let's try out our new exit. We type 'east', and sure 
  enough, we get moved to the workroom. But there's something wrong... we can't 
  actually go 'west' to the room we just coded. So we have to add an exit in our 
  workroom that leads back to the lair. Assuming your lair room is called 'lair.c', 
  in your workroom.c file, you add the line: 
<blockquote>
  <p><code>add_exit("west", "/w/your_name/lair", "road"); </code></p>
</blockquote>
<p>And update. Whee, now we have two rooms we can wander between! So let's look 
  at the setup code to date: 
<blockquote> 
  <p><code>void setup() { <br>
    &nbsp;&nbsp;&nbsp;&nbsp;set_short("blobby lair"); <br>
    &nbsp;&nbsp;&nbsp;&nbsp;set_long("This is where the grey blob lives. All around 
    lie " <br>
    &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;"frogs, and wombles, and strange 
    oozy things. It's a " <br>
    &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;"very nice lair, as lairs 
    go.\n"); <br>
    &nbsp;&nbsp;&nbsp;&nbsp;add_property("determinate", "a "); <br>
    &nbsp;&nbsp;&nbsp;&nbsp;set_light(50); </code></p>
  <p><code>&nbsp;&nbsp;&nbsp;&nbsp;add_item("frog", "The frogs are very nice. 
    Very froggy."); <br>
    &nbsp;&nbsp;&nbsp;&nbsp;add_item("womble", "It's Uncle Bulgaria!"); <br>
    &nbsp;&nbsp;&nbsp;&nbsp;add_item("strange oozy things", "Ewww!"); </code></p>
  <p><code>&nbsp;&nbsp;&nbsp;&nbsp;add_exit("east", "/w/your_name/workroom", "road"); 
    <br>
    } </code></p>
</blockquote>
<p>Now we have a nice working room, with things we can look at. But aside from 
  that, it doesn't do much. For one thing, despite being a lair for the grey blob, 
  the blob itself is conspicuous only by its absence. We could manually clone 
  the blob there every time we load the room... but that's far too much work! 
  So instead, we set the room to do it for us. 
<p><b>Moving Our Blob Into The Room </b>
<p>Every so often, Discworld's driver calls the function reset() on every loaded 
  object on the MUD. You can therefore define a function called 'reset()' that 
  will do nifty things in the room when it is called. Generally this is used to 
  regenerate any NPCs or objects that room may contain. Reset() is also called 
  when a room is first created, so we'll use it to clone our NPC into the lair. 
  First thing we have to do is check to see if our NPC already exists somewhere. 
  If he already does, we don't want to clone him again or we may end up being 
  over-run by the buggers. So the first line of code is to declare an object variable, 
  and then use the find_object() efun to see if we have a version of our friend 
  loaded already: 
<blockquote>
  <p><code>object ob = find_object("/w/your_name/simple_npc"); </code></p>
</blockquote>
<p>Then, if we do, we want to check if he actually exists in the game and isn't 
  just stranded in the firament around Discworld. We can do this by checking environment(), 
  which returns the object the NPC is currently in. So we're doing a couple of 
  checks here. One is to make sure that our variable 'ob' points to an object. 
  If it doesn't, we want to load the NPC and move it into the room. If it does, 
  we want to check the environment() of that object to make sure it is in the 
  game. If the NPC exists, but has no environment, we can just move the NPC into 
  the room without needing to load it. If the NPC doesn't exist, we need to load 
  it, then move it into the room: 
<blockquote>
  <p><code>// if (!ob) will return true if ob is 0... in other words, it<br>
    // didn't find an object with find_object(). </code></p>
  <p><code>if(!ob) { <br>
    // There's no object with that filename loaded, so we load it <br>
    // and then move it into this_object()... which in the case of <br>
    // this example, is the room we just coded. </code></p>
  <p><code>&nbsp;&nbsp;&nbsp;&nbsp;ob = load_object("/w/your_name/simple_npc"); 
    <br>
    &nbsp;&nbsp;&nbsp;&nbsp;ob->move(this_object(), "$N appear$s with a wet squelch.\n"); 
    <br>
    } </code></p>
  <p><code>// if (!environment(ob)) will return true if ob returns 0 for <br>
    // environment... in other words, it's loaded, but located in <br>
    // null-space. </code></p>
  <p><code>else if (!environment(ob)) { <br>
    &nbsp;&nbsp;&nbsp;&nbsp;ob->move(this_object(), "$N appear$s with a wet squelch.\n");<br>
    } </code></p>
</blockquote>
<p>So our final reset() function looks like: 
<blockquote> 
  <p><code>void reset() { </code></p>
  <p><code>&nbsp;&nbsp;&nbsp;&nbsp;object ob = find_object("/w/your_name/simple_npc"); 
    </code></p>
  <blockquote> 
    <p><code>// if (!ob) will return true if ob is 0... in other words, it <br>
      // didn't find an object with find_object(). </code></p>
    <p><code>if (!ob) { <br>
      // There's no object with that filename loaded, so we load it <br>
      // and then move it into this_object()... which in the case of <br>
      // this example, is the room we just coded. </code></p>
    <blockquote> 
      <p><code>ob = load_object("/w/your_name/simple_npc"); </code></p>
      <p><code>// For information on how the move() function works, you <br>
        // can check out 'help move'. But briefly, the first argument<br>
        // is where the object is to be moved to... the second is the <br>
        // message that objects in the destination get when the object <br>
        // enters. $N will be replaced with the short of the object. <br>
        // 'appear$s' is a pluralisation code... it will change to <br>
        // 'appear' when more than one object enters at the same time, <br>
        // and 'appears' when only one enters. </code></p>
      <p><code>ob->move(this_object(), "$N appear$s with a wet squelch.");</code></p>
    </blockquote>
    <p><code>} </code></p>
    <p><code>// if (!environment(ob)) will return true if ob returns 0 for<br>
      // environment... in other words, it's loaded, but located in <br>
      // null-space. </code></p>
    <p><code>else if (!environment(ob)) { <br>
      &nbsp;&nbsp;&nbsp;&nbsp;ob->move (this_object(), "$N appear$s with a wet 
      squelch."); <br>
      }</code></p>
  </blockquote>
  <p><code>}</code></p>
</blockquote>
<p> Hurrah! Our room updates, and the Blob is indeed present. But we didn't get 
  the neat message about him appearing with a wet squelch. We will on subsequent 
  resets, but not when we first load the room. This is fixed by changing our function 
  around a little. If we rename our current reset() function to after_reset (to 
  take an example), we can then use reset() to call after_reset() after a small 
  delay using the call_out efun. This efun takes the name of a function as the 
  first argument, and the number of seconds to wait before executing it. If your 
  function has arguments, these are passed in after the delay: 
<blockquote> 
  <p><code>void reset() { <br>
    &nbsp;&nbsp;&nbsp;&nbsp;call_out("after_reset", 3); <br>
    } </code></p>
</blockquote>
<p>So, now our room looks like: 
<blockquote> 
  <p><code>/* <br>
    &nbsp;&nbsp;&nbsp;&nbsp;This is a basic room! <br>
    &nbsp;&nbsp;&nbsp;&nbsp;Written by Drakkos. <br>
    &nbsp;&nbsp;&nbsp;&nbsp;29/09/2000 <br>
    */</code></p>
  <p><code> inherit "/std/room"; </code></p>
  <p><code>void setup() { <br>
    &nbsp;&nbsp;&nbsp;&nbsp;set_short("blobby lair"); <br>
    &nbsp;&nbsp;&nbsp;&nbsp;set_long("This is where the grey blob lives. All around 
    lie " <br>
    &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;"frogs, and wombles, and strange 
    oozy things. It's a " <br>
    &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;"very nice lair, as lairs 
    go.\n"); <br>
    &nbsp;&nbsp;&nbsp;&nbsp;add_property("determinate", "a "); <br>
    &nbsp;&nbsp;&nbsp;&nbsp;set_light(50); <br>
    &nbsp;&nbsp;&nbsp;&nbsp;add_item("frog", "The frogs are very nice. Very froggy."); 
    <br>
    &nbsp;&nbsp;&nbsp;&nbsp;add_item("womble", "It's Uncle Bulgaria!"); <br>
    &nbsp;&nbsp;&nbsp;&nbsp;add_item("strange oozy things", "Ewww!"); </code></p>
  <p><code>&nbsp;&nbsp;&nbsp;&nbsp;add_exit("east", "/w/your_name/workroom", "road"); 
    <br>
    } </code></p>
  <p><code>void reset() {<br>
    &nbsp;&nbsp;&nbsp;&nbsp;call_out (&quot;after_reset&quot;, 3);<br>
    }</code></p>
  <p><code>void after_reset() { </code></p>
  <p><code>&nbsp;&nbsp;&nbsp;&nbsp;object ob = find_object("/w/your_name/simple_npc"); 
    </code></p>
  <blockquote> 
    <p><code>// if (!ob) will return true if ob is 0... in other words, it <br>
      // didn't find an object with find_object(). </code></p>
    <p><code>if (!ob) { <br>
      // There's no object with that filename loaded, so we load it <br>
      // and then move it into this_object()... which in the case of <br>
      // this example, is the room we just coded. </code></p>
    <blockquote> 
      <p><code>ob = load_object("/w/your_name/simple_npc"); </code></p>
      <p><code>// For information on how the move() function works, you <br>
        // can check out 'help move'. But briefly, the first argument<br>
        // is where the object is to be moved to... the second is the <br>
        // message that objects in the destination get when the object <br>
        // enters. $N will be replaced with the short of the object. <br>
        // 'appear$s' is a pluralisation code... it will change to <br>
        // 'appear' when more than one object enters at the same time, <br>
        // and 'appears' when only one enters. </code></p>
      <p><code>ob->move(this_object(), "$N appear$s with a wet squelch.");</code></p>
    </blockquote>
    <p><code>} </code></p>
    <p><code>// if (!environment(ob)) will return true if ob returns 0 for<br>
      // environment... in other words, it's loaded, but located in <br>
      // null-space. </code></p>
    <p><code>else if (!environment(ob)) { <br>
      &nbsp;&nbsp;&nbsp;&nbsp;ob->move (this_object(), "$N appear$s with a wet 
      squelch."); <br>
      }</code></p>
  </blockquote>
  <p><code>}</code></p>
</blockquote>
<p>So, neato... our room now loads, has stuff in it to look at, and clones our 
  leetle NPC into it when loaded. But it still doesn't do an awful lot. So let's 
  look at a few more clever things we can do with our room code. 
<p><b>Being Clever With Add Items </b>
<p>First, let's have a look at add_item some more. Remember how I told you that 
  add_item was much cleverer than just letting you create stuff you can look at? 
  Well, it is! For one very simple example, it's possible to make the same text 
  be returned for multiple different labels simply by passing the first argument 
  of add_item in as an array of synonyms: 
<blockquote> 
  <p><code>add_item(({"frog", "pinkfish", "toad"}), "The frogs are very nice. 
    "<br>
    &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;"Very froggy."); </code></p>
</blockquote>
<p>So 'look frog', 'look pinkfish', and 'look toad' will all produce the text 
  '<i>The frogs are very nice. Very froggy.</i>' You can use this to create lists 
  of logical synonyms for items in your room so people don't have to type exactly 
  what you have in the description. Likewise, if you pass in an array as the second 
  argument of add_item, you can start to do really clever things. If you do this, 
  you must follow the format of ({"flag", "value"}). The basic flags are 'long', 
  which is the long description of the item you get when looking at it. 'position', 
  which lets you set items so people can sit, lie, etc, on them, and 'gather', 
  which is used by the gathering code (we won't look at that in this tutorial), 
  Now, say we want to make it so we can sit on the frog. Poor leetle frogses! 
  But nonetheless, we want to sit on them. So we change our add_item to: 
<blockquote> 
  <p><code>add_item(({"frog", "pinkfish", "toad"}),({"long", "The frogs are very 
    " <br>
    &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;"nice. Very froggy.", "position", 
    "one of the poor leetle frogs."})); </code></p>
</blockquote>
<p>The second argument to the position flag is the string attached to the position. 
  So if I now 'sit on frog', people who enter our room will see: Drakkos Wyrmstalker 
  is sitting on one of the poor leetle frogs. Whee! We can do this for all our 
  add_items if you like, but let's just victimise the frogs for now. Poor leetle 
  frogses! Ahem. 
<p>Anyway, now we get to some more clever stuff of add_item. It is possible to 
  define simple commands to perform on the item that return pieces of text. So 
  say we wanted to make it possible to pet the womble. All we need to do is: 
<blockquote> 
  <p><code>add_item(({"womble", "uncle bulgaria"}),({"long", "It's Uncle " <br>
    &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;"Bulgaria!", "pet", "You pet 
    Uncle Bulgaria. He growls and chews " <br>
    &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;"the nails off your hand.\n"})); 
    </code></p>
</blockquote>
<p>Whee! So now we can add all sorts of functionality to these items using our 
  neat add_item function. If we want to add more commands to perform, we just 
  add them to the end of the array: 
<blockquote> 
  <p><code>add_item(({"womble", "uncle bulgaria"}),({"long", "It's Uncle Bulgaria!", 
    "pet", <br>
    &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;"You pet Uncle Bulgaria. He 
    growls and chews the nails off " <br>
    &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; "your hand.\n", "snuggle", 
    "Uncle Bulgaria gnaws on your teeth.\n"})); </code></p>
</blockquote>
<p>Neato! And there's more! Much more! Add_item also allows add_commands and functions 
  to be embedded, so you can do really, really clever things with it. But don't 
  worry, that's a little too advanced for this stage. For now, let's confine ourselves 
  to what we've just discussed. 
<p><b>Moving NPCs, and Zoning Permits </b>
<p>By now, you've probably noticed that our leetle blob isn't moving anywhere. 
  You'd think he'd be interested in stretching his legs a little, even if his 
  lair is very nice and pretty. Perhaps we should let him wander around when he's 
  bored? We can do this by using add_zone. By doing this, we can define a 'zone' 
  for both an NPC and a room to have. NPCs will only move between rooms with zones 
  that they also have a zone for. So if we add the line: 
<blockquote>
  <p><code>add_zone("my rooms"); </code></p>
</blockquote>
<p>To the setup of our workroom and the lair, and the line:
<blockquote>
  <p><code>add_move_zone (&quot;my rooms&quot;);</code></p>
</blockquote>
<p>To the setup of our blob, then the NPC will then have permission to wander 
  between the workroom and the lair when feeling bored. But we also need a set_move_after() 
  in our NPC that will determine how often the NPC moves. set_move_after takes 
  an integer value that is the fixed time in seconds before the NPC can move, 
  and a second argument that is the random amount of time before it will move: 
<blockquote>
  <p><code>set_move_after(60, 30); </code></p>
</blockquote>
<p>With this line, the NPC will make a move after 60 + random (30) seconds. We 
  add that to our NPC's setup, and update him (and the lair and the workroom). 
  Lo an behold, sometime after a minute, our NPC gets bored and wanders off to 
  the workroom. 
<p><b>Atmospherics! Room Chats And You!</b>
<p>So, what else do we want to do to our room? Well... now our NPC is off wandering 
  around our workroom, it's a little quiet in here without him. It would be nice 
  if there was a way to provide output every now and again to add to the atmosphere 
  of the place when our blob is out there in the Big Bad World. Well, of course, 
  there is! The function is called room_chat(), and is used in the following way: 
<blockquote> 
  <p><code>room_chat(({120,240,({ <br>
    &nbsp;&nbsp;&nbsp;&nbsp;"A thick blob of goo oozes over one of the frogs.", 
    <br>
    &nbsp;&nbsp;&nbsp;&nbsp;"The womble bings quietly.", <br>
    &nbsp;&nbsp;&nbsp;&nbsp;"The frogs ribbit in abstract contemplation.", <br>
    })})); </code></p>
</blockquote>
<p>room_chat() takes a mixed array as an argument type. The first argument of 
  that array is the minimum time between chats, the second is the maximum. The 
  third argument is an array of strings that represent the chats themselves... 
  these will be randomly printed to the screen at a time between the minimum and 
  maximum values. So, we put this into our room, and after a few moments, we get 
  the following printed to our screen: 
<blockquote>
  <p><code>The womble bings quietly. </code></p>
</blockquote>
<p>Woohoo. Remember when using room chats, however, that they can get very repetitive 
  if you only have a small number, and especially if you set the minimum and maximum 
  times too low. Always err on the side of caution in this respect. 
<p><b>Signing Off! </b>
<p>Now, let's finish up with a little sign letting everyone know that this is 
  where we keep our pet blob. We do this with the function add_sign. add_sign 
  takes five arguments, although all but the first two are optional since the 
  function is varags (please read the chapter on functions if you are unfamiliar 
  with this): 
<blockquote> 
  <p><code>add_sign("This is a nice sign.\n", "Do Notte Feed Thee Blob!",<br>
    &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </code><code>"nice sign", 
    "sign", "common"); </code></p>
  </blockquote>
<p>So what does all that mean? Well, the first argument is the long description 
  of the sign... what you see what you look at it. The second argument is the 
  read message... what you see when you read it. The third argument is the short 
  of the sign... if you pass in this argument, the sign will be cloned into the 
  room and appear in the inventory line of the room (along with monsters and objects 
  lying around). If you don't specify this argument, the sign will be invisible 
  unless looked at or read. The fourth argument is the 'name' of the sign... so 
  if I wanted a plaque instead of a sign, I would change this to "plaque" and 
  could: 'look plaque' and 'read plaque' Instead of 'look sign' and read sign'. 
  The final argument is the language the sign is written in... in this case, it's 
  written in common. If you choose another of the Disc's languages... for example, 
  Djelian, what you get returned when reading the sign will be determined by your 
  competence in the language. Whee! 
<p><b>Chapter Summary </b>
<p>And that's it for the second part of our tutorial. We now know how to build 
  rooms containing interactive items, and we also know how to make our NPC appear 
  in the room when it is loaded. We've also seen how to make our NPC wander around 
  our little empire. But we've still got some ground left to cover, and we'll 
  do so in the next tutorial. :-) 
<ul>
  <li><code>Basic inside rooms will inherit "/std/room". </code></li>
  <li><code>Like NPCs, rooms need a setup() function. However, unlike NPCs, we 
    do not need to use set_name(), since the room will never be directly manipulated 
    by any players, NPCs, or creators.</code></li>
  <li><code>The set_light() function sets the default level of light in the room. 
    </code></li>
  <li><code>The add_item() function allows you to add items to your room that 
    can be looked at. You can also use add_item to specify items can be positioned 
    on, and define simple commands to return the specificed text. </code></li>
  <li><code>Every so often, the driver will call the function reset() in all loaded 
    objects. You can therefore define a reset() function to execute code within 
    your room whenever the call is made by the driver. </code></li>
  <li><code>In order for NPCs to move through your rooms, both the room, and the 
    NPC must have a common zone defined. We define what zones are applicable using 
    the add_zone() function. </code></li>
  <li><code>The room_chat() function can be used to add atmospheric messages to 
    your room, much like with load_chat() in our NPC. </code></li>
  <li><code>The add_sign() function can be used to add readable signs to your 
    rooms. These signs can either be hidden, or displayed as objects in the room 
    depending on what arguments you pass in. </code></li>
</ul>
<p><b>Support Files </b>
<blockquote>
  <p><code>/d/learning/newbie/introduction/examples/simple_room.c </code></p>
</blockquote>
<!-- #EndEditable --> 
<p>
<hr>
<center><font size="-1"><a href="/login.html">Discworld MUD</a>'s world wide web pages.<br>brought to you by<br>
  <strong>Cut Me Own Throat Dibbler's <a href="/sausages.html">Sensational Sausages</a>;&nbsp;buy 
  one while they are hot.</strong> <br>
<hr>Lost?  Try Discworld's <a href="/">home page</a>.</font></center><font size="-1"><i><a href="mailto:drakkos@cableinet.co.uk"><font size="-2">Mail Drakkos!</font></a></i>
</font>
</body>
<!-- #EndTemplate --></html>