Stupid typo
[ibg.git] / chapters / 10.rst
1 ====================
2 Captain Fate: take 1
3 ====================
4
5 .. epigraph::
6
7    | *S was a sailor, and spent all he got;*
8    | *T was a tinker, and mended a pot.*
9
10 .. only:: html
11
12   .. image:: /images/picS.png
13      :align: left
14
15 .. raw:: latex
16
17    \dropcap{s}
18
19 imple though they are, our two games have covered most of the basic
20 functionality of Inform, providing enough solid ground underfoot
21 for you to start creating simple stories. Even if some of what you've
22 encountered doesn't make sense yet, you should be able to browse a
23 game's source code and form a general understanding of what is going on.
24
25 We'll now design a third game, to show you a few additional features and 
26 give you some more sample code to analyse. In "Heidi" we tried to make 
27 progress step by step, explaining every bit of code that went into the 
28 game as we laid the objects sequentially; in "William Tell" you'll have 
29 noticed that we took a few necessary explanatory detours, as the 
30 concepts grew more interesting and complicated. Here we'll organise the 
31 information in logical didactic chunks, defining some of the objects 
32 minimally at first and then adding complexity as need arises. Again, 
33 this means that you won't be able to compile for testing purposes after 
34 the addition of every code snippet, so, if you're typing in the game as 
35 you read, you’ll need to check the advice in "Compile-as-you-go" on page 
36 255.
37
38 A lot of what goes into this game we have already seen; you may deduce 
39 from this that the game design business is fairly repetitious and that 
40 most games are, when you reach the programming bottom line, another 
41 remake of the same old theme. Well, yes and no: you've got a camera and 
42 have seen some short home videos in the making, but it’s a long way from 
43 here to Casablanca. To stick with the analogy, we'll now construct the 
44 opening sequence of an indie B-movie, a tribute to the style of 
45 super-hero made famous by a childhood of comic books:
46
47 .. pull-quote::
48
49         "Impersonating mild mannered John Covarth, assistant help boy at 
50         an Impersonating insignificant drugstore, you suddenly STOP 
51         when your acute hearing deciphers a stray radio call from the 
52         POLICE. There’s some MADMAN attacking the population in Granary 
53         Park! You must change into your Captain FATE costume fast...!"
54
55 which won't be so easy to do. In this short example, players will win 
56 when they manage to change into their super-hero costume and fly away to 
57 meet the foe. The confrontation will -- perhaps -- take place in some 
58 other game, where we can but hope that Captain Fate will vanquish the 
59 forces of evil, thanks to his mysterious (and here unspecified) 
60 superpowers.
61
62 Fade up on: a nondescript city street
63 =====================================
64
65 The game starts with meek John Covarth walking down the street. We set 
66 up the game as usual:
67
68 .. code-block:: inform6
69
70   !% -SD
71   !============================================================================
72   Constant Story "Captain Fate";
73   Constant Headline
74              "^A simple Inform example
75               ^by Roger Firth and Sonja Kesserich.^";
76   Release 3; Serial "040804";    ! for keeping track of public releases
77
78   Constant MANUAL_PRONOUNS;
79   Constant MAX_SCORE     2;
80   Constant OBJECT_SCORE  1;
81   Constant ROOM_SCORE    1;
82
83   Include "Parser";
84   Include "VerbLib";
85
86   !============================================================================
87   ! Object classes
88
89   Class  Room
90     with description "UNDER CONSTRUCTION",
91     has  light;
92
93   Class  Appliance
94     with before [;
95            Take,Pull,Push,PushDir:
96              "Even though your SCULPTED adamantine muscles are up to the task,
97               you don't favour property damage.";
98          ],
99     has  scenery;
100
101   !============================================================================
102   ! The game objects
103
104   Room    street "On the street"
105     with  name 'city' 'buildings' 'skyscrapers' 'shops' 'apartments' 'cars',
106           description
107               "On one side -- which your HEIGHTENED sense of direction
108                indicates is NORTH -- there's an open cafe now serving
109                lunch. To the south, you can see a phone booth.";
110
111   !============================================================================
112   ! The player's possessions
113
114   !============================================================================
115   ! Entry point routines
116
117   [ Initialise;
118       location = street;
119       lookmode = 2;
120       "^^Impersonating mild mannered John Covarth, assistant help boy at an
121        insignificant drugstore, you suddenly STOP when your acute hearing
122        deciphers a stray radio call from the POLICE. There's some MADMAN
123        attacking the population in Granary Park! You must change into your
124        Captain FATE costume fast...!^^";
125   ];
126
127   !============================================================================
128   ! Standard and extended grammar
129
130   Include "Grammar";
131   !============================================================================
132
133 Almost everything is familar, apart from a few details:
134
135 .. code-block:: inform6
136
137   Constant MANUAL_PRONOUNS;
138   Constant MAX_SCORE     2;
139   Constant OBJECT_SCORE  1;
140   Constant ROOM_SCORE    1;
141
142 By default, Inform uses a system of automatic pronouns: as the player 
143 character moves into a room, the library assigns pronouns like IT and 
144 HIM to likely objects (if you play "Heidi" or "William Tell" and type 
145 PRONOUNS, you can see how the settings change). There is another option. 
146 If we declare the ``MANUAL_PRONOUNS`` onstant, we force the library to 
147 assign pronouns to objects only as the player mentions them (that is, IT 
148 will be unassigned until the player types, say, EXAMINE TREE, at which 
149 point, IT becomes the TREE ). The behaviour of pronoun assignment is a 
150 matter of personal taste; no system is objectively perfect.
151
152 Apart from the constant ``MAX_SCORE`` that we have seen in "William 
153 Tell", which defines the maximum number of points to be scored, we now 
154 see two more constants: ``OBJECT_SCORE`` and ``ROOM_SCORE``. There are 
155 several scoring systems predefined in Inform. In "William Tell" we've 
156 seen how you can manually add (or subtract) points by changing the value 
157 of the variable ``score``. Another approach is to award points to 
158 players on the first occasion that they (a) enter a particular room, or 
159 (b) pick up a particular object. To define that a room or object is 
160 indeed “particular”, all you have to do is give it the attribute 
161 ``scored``; the library take cares of the rest. The predefined scores 
162 are five points for finally reached rooms and four points for wondrous 
163 acquisition of objects. With the constants ``OBJECT_SCORE`` and 
164 ``ROOM_SCORE`` we can change those defaults; for the sake of example, 
165 we've decided to modestly award one point for each. By the way, the use 
166 of an equals sign ``=`` is optional with ``Constant``; these two lines 
167 have identical effect:
168
169 .. code-block:: inform6
170
171   Constant ROOM_SCORE    1;
172
173   Constant ROOM_SCORE  = 1;
174
175 Another difference has to do with a special short-hand method that 
176 Inform provides for displaying strings of text. Until now, we have shown 
177 you:
178
179 .. code-block:: inform6
180
181   print "And now for something completely different...^"; return true;
182   ...
183   print_ret "And now for something completely different...";
184
185 Both lines do the same thing: they display the quoted string, output a 
186 newline character, and return true. As you have seen in the previous 
187 example games, this happens quite a lot, so there is a yet shorter way 
188 of achieving the same result:
189
190 .. code-block:: inform6
191
192   "And now for something completely different...";
193
194 That is, *in a routine* (where the compiler is expecting to find a 
195 collection of statements each terminated by a semicolon), a string in 
196 double quotes by itself, without the need for any explicit keywords, 
197 works exactly as if there were a ``print_ret`` in front of it. Remember 
198 that this way of displaying text implies a ``return true`` at the end 
199 (which therefore exits from the routine immediately). This detail 
200 becomes important if we *don't* want to return true after the string 
201 has been displayed on the screen -- we should use the explicit ``print`` 
202 statement instead.
203
204 You'll notice that -- unusually for a room -- our ``street`` object has 
205 a ``name`` property:
206
207 .. code-block:: inform6
208
209   Room    street "On the street"
210     with  name 'city' 'buildings' 'skyscrapers' 'shops' 'apartments' 'cars',
211     ...
212
213 Rooms aren't normally referenced by name, so this may seem odd. In fact, 
214 we're illustrating a feature of Inform: the ability to define dictionary 
215 words as "known but irrelevant" in this location. If the player types 
216 EXAMINE CITY here, the interpreter will reply "That's not something you 
217 need to refer to in order to SAVE the day", rather than the misleading 
218 "You can't see any such thing". We mostly prefer to deal with such 
219 scenic words using classes like ``Prop`` and ``Furniture``, but 
220 sometimes a room's ``name`` property is a quick and convenient solution.
221
222 In this game, we provide a class named ``Appliance`` to take care of 
223 furniture and unmovable objects. You’ll notice that the starting room we 
224 have defined has no connections yet. The description mentions a phone 
225 booth and a café, so we might want to code those. While the café will be 
226 a normal room, it would seem logical that the phone booth is actually a 
227 big box on the sidewalk; therefore we define a ``container`` set in the 
228 street, which players may enter:
229
230 .. code-block:: inform6
231
232   Appliance booth "phone booth" street
233     with name 'old' 'red' 'picturesque' 'phone' 'booth' 'cabin'
234              'telephone' 'box',
235          description
236              "It's one of the old picturesque models, a red cabin with room
237               for one caller.",
238          before [;
239            Open:
240              "The booth is already open.";
241            Close:
242              "There's no way to close this booth.";
243          ],
244          after [;
245            Enter:
246              "With implausible celerity, you dive inside the phone booth.";
247          ],
248     has  enterable container open;
249
250 What's interesting are the attributes at the end of the definition. 
251 You'll recall from Heidi's ``nest`` object that a ``container`` is an 
252 object capable of having other objects placed in it. If we make 
253 something ``enterable``, players count as one of those objects, so that 
254 they may squeeze inside. Finally, ``containers`` are, by default, 
255 supposed to be closed. You can make them ``openable`` if you wish 
256 players to be able to OPEN and CLOSE them at will, but this doesn't seem 
257 appropriate behaviour for a public cabin -- it would become tedious to 
258 have to type OPEN BOOTH and CLOSE BOOTH when these actions provide 
259 nothing special -- so we add instead the attribute ``open`` (as we did 
260 with the nest), telling the interpreter that the container is open from 
261 the word go. Players aren't aware of our design, of course; they may 
262 indeed try to OPEN and CLOSE the booth, so we trap those actions in a 
263 ``before`` property which just tells them that these are not relevant 
264 options. The ``after`` property gives a customised message to override 
265 the library’s default for commands like ENTER BOOTH or GO INSIDE BOOTH.
266
267 Since in the street's description we have told players that the phone 
268 booth is to the south, they might also try typing SOUTH. We must 
269 intercept this attempt and redirect it (while we're at it, we add a 
270 connection to the as-yet-undefined café room and a default message for 
271 the movement which is not allowed):
272
273 .. code-block:: inform6
274
275   Room    street "On the street"
276     with  name city' 'buildings' 'skyscrapers' 'shops' 'apartments' 'cars',
277           description
278               "On one side -- which your HEIGHTENED sense of direction
279                indicates is NORTH -- there's an open cafe now serving
280                lunch. To the south, you can see a phone booth.",
281           n_to cafe,
282           s_to [; <<Enter booth>>; ],
283           cant_go
284               "No time now for exploring! You'll move much faster in your
285                Captain FATE costume.";
286
287 .. todo::
288
289    Notice how the syntax coloring thinks that the exclaimation point 
290    above is a comment.  This is another problem with the built-in inform6 
291    syntax colorer.
292
293 That takes care of entering the booth. But what about leaving it? 
294 Players may type EXIT or OUT while they are inside an enterable 
295 container and the interpreter will oblige but, again, they might type 
296 NORTH. This is a problem, since we are actually in the street (albeit 
297 inside the booth) and to the north we have the café. We may provide for 
298 this condition in the room's ``before`` property:
299
300 .. code-block:: inform6
301
302   before [;
303     Go:
304       if (player in booth && noun == n_obj) <<Exit booth>>;
305   ],
306
307 Since we are outdoors and the booth provides a shelter, it's not 
308 impossible that a player may try just IN, which is a perfectly valid 
309 connection. However, that would be an ambiguous command, for it could 
310 also refer to the café, so we express our bafflement and force the 
311 player to try something else:
312
313 .. code-block:: inform6
314
315   n_to cafe,
316   s_to [; <<Enter booth>>; ],
317   in_to "But which way?",
318
319 Now everything seems to be fine, except for a tiny detail. We've said 
320 that, while in the booth, the player character’s location is still the 
321 ``street`` room, regardless of being inside a ``container``; if players 
322 chanced to type LOOK, they'd get:
323
324 .. code-block:: transcript
325
326   On the street (in the phone booth)
327   On one side -- which your HEIGHTENED sense of direction indicates is NORTH --
328   there's an open cafe now serving lunch. To the south, you can see a 
329   phone booth.
330
331 Hardly an adequate description while *inside* the booth. There are 
332 several ways to fix the problem, depending on the result you wish to 
333 achieve. The library provides a property called ``inside_description`` 
334 which you can utilise with enterable containers. It works pretty much 
335 like the normal ``description`` property, but it gets printed only when 
336 the player is inside the container. The library makes use of this 
337 property in a very clever way, because for every LOOK action it checks 
338 whether we can see outside the container: if the container has the 
339 ``transparent`` attribute set, or if it happens to be ``open``, the 
340 library displays the normal ``description`` of the room first and then 
341 the ``inside_description`` of the container. If the library decides we 
342 can’t see outside the container, only the inside_description is 
343 displayed. Take for instance the following (simplified) example:
344
345 .. code-block:: inform6
346
347   Room    stage "On stage"
348     with  description
349               "The stage is filled with David Copperfield's
350                magical contraptions.",
351           ...
352
353   Object  magic_box "magic box" stage
354     with  description
355               "A big elongated box decorated with silver stars, where
356                scantily clad ladies make a disappearing act.",
357           inside_description
358               "The inside panels of the magic box are covered with black
359                velvet. There is a tiny switch by your right foot.",
360           ...
361     has   container openable enterable light;
362
363 Now, the player would be able to OPEN BOX and ENTER BOX. A player who
364 tried a LOOK would get:
365
366 .. code-block:: transcript
367
368   On stage (in the magic box)
369   The stage is filled with David Copperfield's magical contraptions.
370
371   The inside panels of the magic box are covered with black velvet. There is a
372   tiny switch by your right foot.
373
374 If now the player closes the box and LOOKs:
375
376 .. code-block:: transcript
377
378   On stage (in the magic box)
379   The inside panels of the magic box are covered with black velvet. There is a
380   tiny switch by your right foot.
381
382 In our case, however, we don't wish the description of the street to be 
383 displayed at all (even if a caller is supposedly able to see the street 
384 while inside a booth). The problem is that we have made the booth an 
385 ``open`` container, so the street's description would be displayed every 
386 time. There is another solution. We can make the ``description`` 
387 property of the ``street`` room a bit more complex, and change its 
388 value: instead of a string, we write an embedded routine. Here's the 
389 (almost) finished room:
390
391 .. code-block:: inform6
392
393   Room    street "On the street"
394     with  name 'city' 'buildings' 'skyscrapers' 'shops' 'apartments' 'cars',
395           description [;
396               if (player in booth)
397                   "From this VANTAGE point, you are rewarded with a broad view
398                    of the sidewalk and the entrance to Benny's cafe.";
399               else
400                   "On one side -- which your HEIGHTENED sense of direction
401                    indicates is NORTH -- there's an open cafe now serving
402                    lunch. To the south, you can see a phone booth.";
403           ],
404           before [;
405             Go:
406               if (player in booth && noun == n_obj) <<Exit booth>>;
407           ],
408           n_to cafe,
409           s_to [; <<Enter booth>>; ],
410           in_to "But which way?",
411           cant_go
412                "No time now for exploring! You'll move much faster in your
413                 Captain FATE costume.";
414
415 The description while inside the booth mentions the sidewalk, which 
416 might invite the player to EXAMINE it. No problem:
417
418 .. code-block:: inform6
419
420   Appliance "sidewalk" street
421     with  name sidewalk' 'pavement' 'street',
422           article "the",
423           description
424               "You make a quick surveillance of the sidewalk and discover much
425                to your surprise that it looks JUST like any other sidewalk in
426                the CITY!";
427
428 Unfortunately, both descriptions also mention the café, which will be a 
429 room and therefore not, from the outside, an examinable object. The 
430 player may enter it and will get whatever description we code as the 
431 result of a LOOK action (which will have to do with the way the café 
432 looks from the *inside*); but while we are on the street we need 
433 something else to describe it:
434
435 .. code-block:: inform6
436
437   Appliance outside_of_cafe "Benny's cafe" street
438     with  name 'benny^s' 'cafe' 'entrance',
439           description
440               "The town's favourite for a quick snack, Benny's cafe has a 50's
441                ROCKETSHIP look.",
442           before [;
443             Enter:
444               print "With an impressive mixture of hurry and nonchalance
445                   you step into the open cafe.^";
446               PlayerTo(cafe);
447               return true;
448           ],
449     has   enterable proper;
450
451 .. todo::
452
453    Figure out how to set off this entire note section as an indented block
454
455 NOTE : although the text of our guide calls Benny's establishment a 
456 "café" -- note the acute "e" -- the game itself simplifies this to 
457 "cafe". We do this for clarity, not because Inform doesn't support 
458 accented characters. The *Inform Designer's Manual* explains in detail 
459 how to display these characters in "§1.11 *How text is printed*" and 
460 provides the whole Z-machine character set in Table 2. In our case, we 
461 could have displayed this::
462
463   The town's favourite for a quick snack, Benny's café has a 50's ROCKETSHIP look.
464
465 by defining the ``description`` property as any of these:
466
467 .. code-block:: inform6
468
469   description
470       "The town's favourite for a quick snack, Benny's caf@'e has a 50's
471        ROCKETSHIP look.",
472
473   description
474       "The town's favourite for a quick snack, Benny's caf@@170 has a 50's
475        ROCKETSHIP look.",
476
477   description
478       "The town's favourite for a quick snack, Benny's caf@{E9} has a 50's
479        ROCKETSHIP look.",
480
481 However, all three forms are harder to read than the vanilla "cafe", so 
482 we've opted for the simple life.
483
484 .. todo::
485
486    Indented block ends here
487
488 Unlike the sidewalk object, we offer more than a mere description. Since 
489 the player may try ENTER CAFE as a reasonable way of access -- which 
490 would have confused the interpreter immensely -- we take the opportunity 
491 of making this object also ``enterable``, and we cheat a little. The 
492 attribute ``enterable`` has permitted the verb ENTER to be applied to 
493 this object, but this is not a ``container``; we want the player to be 
494 sent into the *real* café room instead. The ``before`` property handles 
495 this, intercepting the action, displaying a message and teleporting the 
496 player into the café. We ``return true`` to inform the interpreter that 
497 we have taken care of the ``Enter`` action ourselves, so it can stop 
498 right there.
499
500 As a final detail, note that we now have two ways of going into the 
501 café: the ``n_to`` property of the ``street`` room and the ``Enter`` 
502 action of the ``outside_of_cafe`` object. A perfectionist might point 
503 out that it would be neater to handle the actual movement of the player 
504 in just one place of our code, because this helps clarity. To achieve 
505 this, we redirect the street's ``n_to`` property thus:
506
507 .. code-block:: inform6
508
509   n_to [; <<Enter outside_of_cafe>>; ],
510
511 You may think that this is unnecessary madness, but a word to the wise: 
512 in a large game, you want action handling going on just in one place 
513 when possible, because it will help you to keep track of where things 
514 are a-happening if something goes *ploof* (as, believe us, it will; see 
515 "Debugging your game" on page 197). You don't need to be a 
516 perfectionist, just cautious.
517
518 A booth in this kind of situation is an open invitation for the player 
519 to step inside and try to change into Captain Fate's costume. We won't 
520 let this happen -- the player isn't Clark Kent, after all; later we'll 
521 explain how we forbid this action -- and that will force the player to 
522 go inside the café, looking for a discreet place to disrobe; but first, 
523 let''s freeze John Covarth outside Benny''s and reflect about a 
524 fundamental truth.
525
526 A hero is not an ordinary person
527 ================================
528
529 Which is to say, normal actions won't be the same for him.
530
531 As you have probably inferred from the previous chapters, some of the 
532 library’s standard defined actions are less important than others in 
533 making the game advance towards one of its conclusions. The library 
534 defines PRAY and SING, for instance, which are of little consequence in 
535 a normal gaming situation; each displays an all-purpose message, 
536 sufficiently non-committal, and that's it. Of course, if your game 
537 includes a magic portal that will reveal itself only if the player lets 
538 rip with a snatch of Wagner, you may intercept the ``Sing`` action in a 
539 ``before`` property and alter its default, pretty useless behaviour. If 
540 not, it's "Your singing is abominable" for you.
541
542 All actions, useful or not, have a stock of messages associated with 
543 them (the messages are held in the ``english.h`` library file and listed 
544 in Appendix 4 of the *Inform Designer's Manual*). We have already seen 
545 one way of altering the player character's description -- "As good 
546 looking as ever" -- in "William Tell", but the other defaults may also 
547 be redefined to suit your tastes and circumstantial needs.
548
549 John Covarth, aka Captain Fate, could happily settle for most of these 
550 default messages, but we deem it worthwhile to give him some customised 
551 responses. If nothing else, this adds to the general atmosphere, a 
552 nicety that many players regard as important. For this mission, we make 
553 use of the ``LibraryMessages`` object.
554
555 .. code-block:: inform6
556
557   Include "Parser";
558
559   Object  LibraryMessages         ! must be defined between Parser and VerbLib
560     with  before [;
561             Buy:    "Petty commerce interests you only on COUNTED occasions.";
562             Dig:    "Your keen senses detect NOTHING underground worth your
563                      immediate attention.";
564             Pray:   "You won't need to bother almighty DIVINITIES to save
565                      the day.";
566             Sing:   "Alas! That is not one of your many superpowers.";
567             Sleep:  "A hero is ALWAYS on the watch.";
568             Strong: "An unlikely vocabulary for a HERO like you.";
569             Swim:   "You quickly turn all your ATTENTION towards locating a
570                      suitable place to EXERCISE your superior strokes,
571                      but alas! you find none.";
572             Miscellany:
573               if (lm_n == 19)
574                   if (clothes has worn)
575                       "In your secret identity's outfit, you manage most
576                        efficaciously to look like a two-cent loser, a
577                        good-for-nothing wimp.";
578                   else
579                       "Now that you are wearing your costume, you project
580                        the image of power UNBOUND, of ballooned,
581                        multicoloured MUSCLE, of DASHING yet MODEST chic.";
582               if (lm_n == 38)
583                   "That's not a verb you need to SUCCESSFULLY save the day.";
584               if (lm_n == 39)
585                   "That's not something you need to refer to in order to
586                    SAVE the day.";
587         ];
588
589   Include "VerbLib";
590
591 If you provide it, the ``LibraryMessages`` object must be defined 
592 *between* the inclusion of ``Parser`` and ``VerbLib`` (it won't work 
593 otherwise and you’ll get a compiler error). The object contains a single 
594 property -- ``before`` -- which intercepts display of the default 
595 messages that you want to change. An attempt to SING, for example, will 
596 now result in "Alas! That is not one of your many superpowers" being 
597 displayed.
598
599 In addition to such verb-specific responses, the library defines other 
600 messages not directly associated with an action, like the default 
601 response when a verb is unrecognised, or if you refer to an object which 
602 is not in scope, or indeed many other things. Most of these messages can 
603 be accessed through the ``Miscellany entry``, which has a numbered list 
604 of responses. The variable ``lm_n`` holds the current value of the 
605 number of the message to be displayed, so you can change the default 
606 with a test like this:
607
608 .. code-block:: inform6
609
610   if (lm_n == 39)
611       "That's not something you need to refer to in order to SAVE the day.";
612
613 .. todo::
614
615    That block of code above should be colored.  Is there a defect in the 
616    syntax coloring code?
617
618 where 39 is the number for the standard message "That's not something 
619 you need to refer to in the course of this game" -- displayed when the 
620 player mentions a noun which is listed in a room's name property, as we 
621 did for the ``street``.
622
623 .. todo::
624
625    Begin big chunk of indented text. Also, NOTE should be in bigcaps.
626
627 NOTE : remember that when we are testing for different values of the 
628 same variable, we can also use the switch statement. For the Miscellany 
629 entry, the following code would work just as nicely:
630
631 .. code-block:: inform6
632
633   ...
634   Miscellany:
635     switch (lm_n) {
636       19:
637         if (clothes has worn)
638             "In your secret identity's outfit, you manage most
639              efficaciously to look like a two-cent loser, a
640              good-for-nothing wimp.";
641         else
642             "Now that you are wearing your costume, you project
643              the image of power UNBOUND, of ballooned,
644              multicoloured MUSCLE, of DASHING yet MODEST chic.";
645       38:
646         "That's not a verb you need to SUCCESSFULLY save the day.";
647       39:
648         "That's not something you need to refer to in order to SAVE the day.";
649     }
650
651 .. todo::
652
653    End big indented chunk
654
655 Not surprisingly, the default message for self-examination: "As good 
656 looking as ever" is a ``Miscellany`` entry -- it's number 19 -- so we 
657 can change it through the ``LibraryMessages`` object instead of, as 
658 before, assigning a new string to the ``player.description property``. 
659 In our game, the description of the player character has two states: 
660 with street clothes as John Covarth and with the super-hero outfit as 
661 Captain Fate; hence the ``if (clothes has worn)`` clause.
662
663 This discussion of changing our hero's appearance shows that there are 
664 different ways of achieving the same result, which is a common situation 
665 while designing a game. Problems may be approached from different 
666 angles; why use one technique and not another? Usually, the context tips 
667 the balance in favour of one solution, though it might happen that you 
668 opt for the not-so-hot approach for some overriding reason. Don't feel 
669 discouraged; choices like this become more common (and easier) as your 
670 experience grows.
671
672 .. todo::
673
674    Begin big indented chunk.  That "whatever new look" needs to be italicized.
675
676 NOTE: going back to our example, an alternative approach would be to set 
677 the variable ``player.description`` in the ``Initialise`` routine (as we 
678 did with "William Tell") to the "ordinary clothes" string, and then 
679 later change it as the need arises. It is a variable, after all, and you 
680 can alter its value with another statement like ``player.description = 
681 *whatever new look*`` anywhere in your code. This alternative solution 
682 might be better if we intended changing the description of the player 
683 many times through the game. Since we plan to have only two states, the 
684 ``LibraryMessages`` approach will do just fine.
685
686 .. todo::
687
688    End big indented chunk
689
690 A final warning: as we explained when extending the standard verb 
691 grammars, you *could* edit the appropriate library file and change all 
692 the default messages, but that wouldn't be a sound practice, because 
693 your library file will probably not be right for the next game. Use of 
694 the ``LibraryMessages`` object is strongly advised.
695
696 If you're typing in the game, you'll probably want to read the brief 
697 section on "Compile-as-you-go" on page 255 prior to performing a test 
698 compile. Once everything's correct, it’s time that our hero entered that 
699 enticing café.