diff options
Diffstat (limited to 'apps/plugins/puzzles/src/HACKING')
-rw-r--r-- | apps/plugins/puzzles/src/HACKING | 4661 |
1 files changed, 0 insertions, 4661 deletions
diff --git a/apps/plugins/puzzles/src/HACKING b/apps/plugins/puzzles/src/HACKING deleted file mode 100644 index e877280e1c..0000000000 --- a/apps/plugins/puzzles/src/HACKING +++ /dev/null | |||
@@ -1,4661 +0,0 @@ | |||
1 | #Developer documentation for Simon Tatham's puzzle collection | ||
2 | |||
3 | This is a guide to the internal structure of Simon Tatham's Portable | ||
4 | Puzzle Collection (henceforth referred to simply as `Puzzles'), for | ||
5 | use by anyone attempting to implement a new puzzle or port to a new | ||
6 | platform. | ||
7 | |||
8 | This guide is believed correct as of r6190. Hopefully it will be updated | ||
9 | along with the code in future, but if not, I've at least left this | ||
10 | version number in here so you can figure out what's changed by tracking | ||
11 | commit comments from there onwards. | ||
12 | |||
13 | #1. Introduction | ||
14 | |||
15 | The Puzzles code base is divided into four parts: a set of | ||
16 | interchangeable front ends, a set of interchangeable back ends, a | ||
17 | universal `middle end' which acts as a buffer between the two, and a | ||
18 | bunch of miscellaneous utility functions. In the following sections I | ||
19 | give some general discussion of each of these parts. | ||
20 | |||
21 | #1.1. Front end | ||
22 | |||
23 | The front end is the non-portable part of the code: it's the bit that | ||
24 | you replace completely when you port to a different platform. So it's | ||
25 | responsible for all system calls, all GUI interaction, and anything else | ||
26 | platform-specific. | ||
27 | |||
28 | The current front ends in the main code base are for Windows, GTK and | ||
29 | MacOS X; I also know of a third-party front end for PalmOS. | ||
30 | |||
31 | The front end contains main() or the local platform's equivalent. Top- | ||
32 | level control over the application's execution flow belongs to the front | ||
33 | end (it isn't, for example, a set of functions called by a universal | ||
34 | main() somewhere else). | ||
35 | |||
36 | The front end has complete freedom to design the GUI for any given | ||
37 | port of Puzzles. There is no centralised mechanism for maintaining the | ||
38 | menu layout, for example. This has a cost in consistency (when I _do_ | ||
39 | want the same menu layout on more than one platform, I have to edit | ||
40 | two pieces of code in parallel every time I make a change), but the | ||
41 | advantage is that local GUI conventions can be conformed to and local | ||
42 | constraints adapted to. For example, MacOS X has strict human interface | ||
43 | guidelines which specify a different menu layout from the one I've used | ||
44 | on Windows and GTK; there's nothing stopping the OS X front end from | ||
45 | providing a menu layout consistent with those guidelines. | ||
46 | |||
47 | Although the front end is mostly caller rather than the callee in its | ||
48 | interactions with other parts of the code, it is required to implement | ||
49 | a small API for other modules to call, mostly of drawing functions for | ||
50 | games to use when drawing their graphics. The drawing API is documented | ||
51 | in chapter 3; the other miscellaneous front end API functions are | ||
52 | documented in section 4.34. | ||
53 | |||
54 | #1.2. Back end | ||
55 | |||
56 | A `back end', in this collection, is synonymous with a `puzzle'. Each | ||
57 | back end implements a different game. | ||
58 | |||
59 | At the top level, a back end is simply a data structure, containing a | ||
60 | few constants (flag words, preferred pixel size) and a large number of | ||
61 | function pointers. Back ends are almost invariably callee rather than | ||
62 | caller, which means there's a limitation on what a back end can do on | ||
63 | its own initiative. | ||
64 | |||
65 | The persistent state in a back end is divided into a number of data | ||
66 | structures, which are used for different purposes and therefore likely | ||
67 | to be switched around, changed without notice, and otherwise updated by | ||
68 | the rest of the code. It is important when designing a back end to put | ||
69 | the right pieces of data into the right structures, or standard midend- | ||
70 | provided features (such as Undo) may fail to work. | ||
71 | |||
72 | The functions and variables provided in the back end data structure are | ||
73 | documented in chapter 2. | ||
74 | |||
75 | #1.3. Middle end | ||
76 | |||
77 | Puzzles has a single and universal `middle end'. This code is common to | ||
78 | all platforms and all games; it sits in between the front end and the | ||
79 | back end and provides standard functionality everywhere. | ||
80 | |||
81 | People adding new back ends or new front ends should generally not need | ||
82 | to edit the middle end. On rare occasions there might be a change that | ||
83 | can be made to the middle end to permit a new game to do something not | ||
84 | currently anticipated by the middle end's present design; however, this | ||
85 | is terribly easy to get wrong and should probably not be undertaken | ||
86 | without consulting the primary maintainer (me). Patch submissions | ||
87 | containing unannounced mid-end changes will be treated on their merits | ||
88 | like any other patch; this is just a friendly warning that mid-end | ||
89 | changes will need quite a lot of merits to make them acceptable. | ||
90 | |||
91 | Functionality provided by the mid-end includes: | ||
92 | |||
93 | - Maintaining a list of game state structures and moving back and | ||
94 | forth along that list to provide Undo and Redo. | ||
95 | |||
96 | - Handling timers (for move animations, flashes on completion, and in | ||
97 | some cases actually timing the game). | ||
98 | |||
99 | - Handling the container format of game IDs: receiving them, picking | ||
100 | them apart into parameters, description and/or random seed, and | ||
101 | so on. The game back end need only handle the individual parts | ||
102 | of a game ID (encoded parameters and encoded game description); | ||
103 | everything else is handled centrally by the mid-end. | ||
104 | |||
105 | - Handling standard keystrokes and menu commands, such as `New Game', | ||
106 | `Restart Game' and `Quit'. | ||
107 | |||
108 | - Pre-processing mouse events so that the game back ends can rely on | ||
109 | them arriving in a sensible order (no missing button-release events, | ||
110 | no sudden changes of which button is currently pressed, etc). | ||
111 | |||
112 | - Handling the dialog boxes which ask the user for a game ID. | ||
113 | |||
114 | - Handling serialisation of entire games (for loading and saving a | ||
115 | half-finished game to a disk file, or for handling application | ||
116 | shutdown and restart on platforms such as PalmOS where state is | ||
117 | expected to be saved). | ||
118 | |||
119 | Thus, there's a lot of work done once by the mid-end so that individual | ||
120 | back ends don't have to worry about it. All the back end has to do is | ||
121 | cooperate in ensuring the mid-end can do its work properly. | ||
122 | |||
123 | The API of functions provided by the mid-end to be called by the front | ||
124 | end is documented in chapter 4. | ||
125 | |||
126 | #1.4. Miscellaneous utilities | ||
127 | |||
128 | In addition to these three major structural components, the Puzzles code | ||
129 | also contains a variety of utility modules usable by all of the above | ||
130 | components. There is a set of functions to provide platform-independent | ||
131 | random number generation; functions to make memory allocation easier; | ||
132 | functions which implement a balanced tree structure to be used as | ||
133 | necessary in complex algorithms; and a few other miscellaneous | ||
134 | functions. All of these are documented in chapter 5. | ||
135 | |||
136 | #1.5. Structure of this guide | ||
137 | |||
138 | There are a number of function call interfaces within Puzzles, and this | ||
139 | guide will discuss each one in a chapter of its own. After that, chapter | ||
140 | 6 discusses how to design new games, with some general design thoughts | ||
141 | and tips. | ||
142 | |||
143 | #2. Interface to the back end | ||
144 | |||
145 | This chapter gives a detailed discussion of the interface that each back | ||
146 | end must implement. | ||
147 | |||
148 | At the top level, each back end source file exports a single global | ||
149 | symbol, which is a `const struct game' containing a large number of | ||
150 | function pointers and a small amount of constant data. This structure is | ||
151 | called by different names depending on what kind of platform the puzzle | ||
152 | set is being compiled on: | ||
153 | |||
154 | - On platforms such as Windows and GTK, which build a separate binary | ||
155 | for each puzzle, the game structure in every back end has the same | ||
156 | name, `thegame'; the front end refers directly to this name, so that | ||
157 | compiling the same front end module against a different back end | ||
158 | module builds a different puzzle. | ||
159 | |||
160 | - On platforms such as MacOS X and PalmOS, which build all the puzzles | ||
161 | into a single monolithic binary, the game structure in each back end | ||
162 | must have a different name, and there's a helper module `list.c' | ||
163 | (constructed automatically by the same Perl script that builds the | ||
164 | Makefiles) which contains a complete list of those game structures. | ||
165 | |||
166 | On the latter type of platform, source files may assume that the | ||
167 | preprocessor symbol `COMBINED' has been defined. Thus, the usual code to | ||
168 | declare the game structure looks something like this: | ||
169 | |||
170 | #ifdef COMBINED | ||
171 | #define thegame net /* or whatever this game is called */ | ||
172 | #endif | ||
173 | |||
174 | const struct game thegame = { | ||
175 | /* lots of structure initialisation in here */ | ||
176 | }; | ||
177 | |||
178 | Game back ends must also internally define a number of data structures, | ||
179 | for storing their various persistent state. This chapter will first | ||
180 | discuss the nature and use of those structures, and then go on to give | ||
181 | details of every element of the game structure. | ||
182 | |||
183 | #2.1. Data structures | ||
184 | |||
185 | Each game is required to define four separate data structures. This | ||
186 | section discusses each one and suggests what sorts of things need to be | ||
187 | put in it. | ||
188 | |||
189 | #2.1.1. `game_params' | ||
190 | |||
191 | The `game_params' structure contains anything which affects the | ||
192 | automatic generation of new puzzles. So if puzzle generation is | ||
193 | parametrised in any way, those parameters need to be stored in | ||
194 | `game_params'. | ||
195 | |||
196 | Most puzzles currently in this collection are played on a grid of | ||
197 | squares, meaning that the most obvious parameter is the grid size. Many | ||
198 | puzzles have additional parameters; for example, Mines allows you to | ||
199 | control the number of mines in the grid independently of its size, Net | ||
200 | can be wrapping or non-wrapping, Solo has difficulty levels and symmetry | ||
201 | settings, and so on. | ||
202 | |||
203 | A simple rule for deciding whether a data item needs to go in | ||
204 | `game_params' is: would the user expect to be able to control this data | ||
205 | item from either the preset-game-types menu or the `Custom' game type | ||
206 | configuration? If so, it's part of `game_params'. | ||
207 | |||
208 | `game_params' structures are permitted to contain pointers to subsidiary | ||
209 | data if they need to. The back end is required to provide functions to | ||
210 | create and destroy `game_params', and those functions can allocate and | ||
211 | free additional memory if necessary. (It has not yet been necessary to | ||
212 | do this in any puzzle so far, but the capability is there just in case.) | ||
213 | |||
214 | `game_params' is also the only structure which the game's compute_size() | ||
215 | function may refer to; this means that any aspect of the game which | ||
216 | affects the size of the window it needs to be drawn in must be stored in | ||
217 | `game_params'. In particular, this imposes the fundamental limitation | ||
218 | that random game generation may not have a random effect on the window | ||
219 | size: game generation algorithms are constrained to work by starting | ||
220 | from the grid size rather than generating it as an emergent phenomenon. | ||
221 | (Although this is a restriction in theory, it has not yet seemed to be a | ||
222 | problem.) | ||
223 | |||
224 | #2.1.2. `game_state' | ||
225 | |||
226 | While the user is actually playing a puzzle, the `game_state' structure | ||
227 | stores all the data corresponding to the current state of play. | ||
228 | |||
229 | The mid-end keeps `game_state's in a list, and adds to the list every | ||
230 | time the player makes a move; the Undo and Redo functions step back and | ||
231 | forth through that list. | ||
232 | |||
233 | Therefore, a good means of deciding whether a data item needs to go in | ||
234 | `game_state' is: would a player expect that data item to be restored on | ||
235 | undo? If so, put it in `game_state', and this will automatically happen | ||
236 | without you having to lift a finger. If not - for example, the deaths | ||
237 | counter in Mines is precisely something that does _not_ want to be reset | ||
238 | to its previous state on an undo - then you might have found a data item | ||
239 | that needs to go in `game_ui' instead. | ||
240 | |||
241 | During play, `game_state's are often passed around without an | ||
242 | accompanying `game_params' structure. Therefore, any information in | ||
243 | `game_params' which is important during play (such as the grid size) | ||
244 | must be duplicated within the `game_state'. One simple method of doing | ||
245 | this is to have the `game_state' structure _contain_ a `game_params' | ||
246 | structure as one of its members, although this isn't obligatory if you | ||
247 | prefer to do it another way. | ||
248 | |||
249 | #2.1.3. `game_drawstate' | ||
250 | |||
251 | `game_drawstate' carries persistent state relating to the current | ||
252 | graphical contents of the puzzle window. The same `game_drawstate' | ||
253 | is passed to every call to the game redraw function, so that it can | ||
254 | remember what it has already drawn and what needs redrawing. | ||
255 | |||
256 | A typical use for a `game_drawstate' is to have an array mirroring the | ||
257 | array of grid squares in the `game_state'; then every time the redraw | ||
258 | function was passed a `game_state', it would loop over all the squares, | ||
259 | and physically redraw any whose description in the `game_state' (i.e. | ||
260 | what the square needs to look like when the redraw is completed) did | ||
261 | not match its description in the `game_drawstate' (i.e. what the square | ||
262 | currently looks like). | ||
263 | |||
264 | `game_drawstate' is occasionally completely torn down and reconstructed | ||
265 | by the mid-end, if the user somehow forces a full redraw. Therefore, no | ||
266 | data should be stored in `game_drawstate' which is _not_ related to the | ||
267 | state of the puzzle window, because it might be unexpectedly destroyed. | ||
268 | |||
269 | The back end provides functions to create and destroy `game_drawstate', | ||
270 | which means it can contain pointers to subsidiary allocated data if it | ||
271 | needs to. A common thing to want to allocate in a `game_drawstate' is a | ||
272 | `blitter'; see section 3.1.13 for more on this subject. | ||
273 | |||
274 | #2.1.4. `game_ui' | ||
275 | |||
276 | `game_ui' contains whatever doesn't fit into the above three structures! | ||
277 | |||
278 | A new `game_ui' is created when the user begins playing a new instance | ||
279 | of a puzzle (i.e. during `New Game' or after entering a game ID etc). It | ||
280 | persists until the user finishes playing that game and begins another | ||
281 | one (or closes the window); in particular, `Restart Game' does _not_ | ||
282 | destroy the `game_ui'. | ||
283 | |||
284 | `game_ui' is useful for implementing user-interface state which is not | ||
285 | part of `game_state'. Common examples are keyboard control (you wouldn't | ||
286 | want to have to separately Undo through every cursor motion) and mouse | ||
287 | dragging. See section 6.3.2 and section 6.3.3, respectively, for more | ||
288 | details. | ||
289 | |||
290 | Another use for `game_ui' is to store highly persistent data such as | ||
291 | the Mines death counter. This is conceptually rather different: where | ||
292 | the Net cursor position was _not important enough_ to preserve for the | ||
293 | player to restore by Undo, the Mines death counter is _too important_ to | ||
294 | permit the player to revert by Undo! | ||
295 | |||
296 | A final use for `game_ui' is to pass information to the redraw function | ||
297 | about recent changes to the game state. This is used in Mines, for | ||
298 | example, to indicate whether a requested `flash' should be a white flash | ||
299 | for victory or a red flash for defeat; see section 6.3.5. | ||
300 | |||
301 | #2.2. Simple data in the back end | ||
302 | |||
303 | In this section I begin to discuss each individual element in the back | ||
304 | end structure. To begin with, here are some simple self-contained data | ||
305 | elements. | ||
306 | |||
307 | #2.2.1. `name' | ||
308 | |||
309 | const char *name; | ||
310 | |||
311 | This is a simple ASCII string giving the name of the puzzle. This name | ||
312 | will be used in window titles, in game selection menus on monolithic | ||
313 | platforms, and anywhere else that the front end needs to know the name | ||
314 | of a game. | ||
315 | |||
316 | #2.2.2. `winhelp_topic' | ||
317 | |||
318 | const char *winhelp_topic; | ||
319 | |||
320 | This member is used on Windows only, to provide online help. Although | ||
321 | the Windows front end provides a separate binary for each puzzle, it has | ||
322 | a single monolithic help file; so when a user selects `Help' from the | ||
323 | menu, the program needs to open the help file and jump to the chapter | ||
324 | describing that particular puzzle. | ||
325 | |||
326 | Therefore, each chapter in `puzzles.but' is labelled with a _help topic_ | ||
327 | name, similar to this: | ||
328 | |||
329 | \cfg{winhelp-topic}{games.net} | ||
330 | |||
331 | And then the corresponding game back end encodes the topic string (here | ||
332 | `games.net') in the `winhelp_topic' element of the game structure. | ||
333 | |||
334 | #2.3. Handling game parameter sets | ||
335 | |||
336 | In this section I present the various functions which handle the | ||
337 | `game_params' structure. | ||
338 | |||
339 | #2.3.1. default_params() | ||
340 | |||
341 | game_params *(*default_params)(void); | ||
342 | |||
343 | This function allocates a new `game_params' structure, fills it with the | ||
344 | default values, and returns a pointer to it. | ||
345 | |||
346 | #2.3.2. fetch_preset() | ||
347 | |||
348 | int (*fetch_preset)(int i, char **name, game_params **params); | ||
349 | |||
350 | This function is one of the two APIs a back end can provide to populate | ||
351 | the `Type' menu, which provides a list of conveniently accessible preset | ||
352 | parameters for most games. | ||
353 | |||
354 | The function is called with `i' equal to the index of the preset | ||
355 | required (numbering from zero). It returns FALSE if that preset does | ||
356 | not exist (if `i' is less than zero or greater than the largest preset | ||
357 | index). Otherwise, it sets `*params' to point at a newly allocated | ||
358 | `game_params' structure containing the preset information, sets `*name' | ||
359 | to point at a newly allocated C string containing the preset title (to | ||
360 | go on the `Type' menu), and returns TRUE. | ||
361 | |||
362 | If the game does not wish to support any presets at all, this function | ||
363 | is permitted to return FALSE always. | ||
364 | |||
365 | If the game wants to return presets in the form of a hierarchical menu | ||
366 | instead of a flat list (and, indeed, even if it doesn't), then it may | ||
367 | set this function pointer to NULL, and instead fill in the alternative | ||
368 | function pointer preset_menu (section 2.3.3). | ||
369 | |||
370 | #2.3.3. preset_menu() | ||
371 | |||
372 | struct preset_menu *(*preset_menu)(void); | ||
373 | |||
374 | This function is the more flexible of the two APIs by which a back end | ||
375 | can define a collection of preset game parameters. | ||
376 | |||
377 | This function simply returns a complete menu hierarchy, in the form | ||
378 | of a `struct preset_menu' (see section 4.15) and further submenus (if | ||
379 | it wishes) dangling off it. There are utility functions described in | ||
380 | section 5.2 to make it easy for the back end to construct this menu. | ||
381 | |||
382 | If the game has no need to return a hierarchy of menus, it may instead | ||
383 | opt to implement the fetch_preset() function (see section 2.3.2). | ||
384 | |||
385 | The game need not fill in the `id' fields in the preset menu structures. | ||
386 | The mid-end will do that after it receives the structure from the game, | ||
387 | and before passing it on to the front end. | ||
388 | |||
389 | #2.3.4. encode_params() | ||
390 | |||
391 | char *(*encode_params)(const game_params *params, int full); | ||
392 | |||
393 | The job of this function is to take a `game_params', and encode it in | ||
394 | a string form for use in game IDs. The return value must be a newly | ||
395 | allocated C string, and _must_ not contain a colon or a hash (since | ||
396 | those characters are used to mark the end of the parameter section in a | ||
397 | game ID). | ||
398 | |||
399 | Ideally, it should also not contain any other potentially controversial | ||
400 | punctuation; bear in mind when designing a string parameter format | ||
401 | that it will probably be used on both Windows and Unix command lines | ||
402 | under a variety of exciting shell quoting and metacharacter rules. | ||
403 | Sticking entirely to alphanumerics is the safest thing; if you really | ||
404 | need punctuation, you can probably get away with commas, periods or | ||
405 | underscores without causing anybody any major inconvenience. If you | ||
406 | venture far beyond that, you're likely to irritate _somebody_. | ||
407 | |||
408 | (At the time of writing this, all existing games have purely | ||
409 | alphanumeric string parameter formats. Usually these involve a letter | ||
410 | denoting a parameter, followed optionally by a number giving the value | ||
411 | of that parameter, with a few mandatory parts at the beginning such as | ||
412 | numeric width and height separated by `x'.) | ||
413 | |||
414 | If the `full' parameter is TRUE, this function should encode absolutely | ||
415 | everything in the `game_params', such that a subsequent call to | ||
416 | decode_params() (section 2.3.5) will yield an identical structure. | ||
417 | If `full' is FALSE, however, you should leave out anything which | ||
418 | is not necessary to describe a _specific puzzle instance_, i.e. | ||
419 | anything which only takes effect when a new puzzle is _generated_. | ||
420 | For example, the Solo `game_params' includes a difficulty rating used | ||
421 | when constructing new puzzles; but a Solo game ID need not explicitly | ||
422 | include the difficulty, since to describe a puzzle once generated it's | ||
423 | sufficient to give the grid dimensions and the location and contents | ||
424 | of the clue squares. (Indeed, one might very easily type in a puzzle | ||
425 | out of a newspaper without _knowing_ what its difficulty level is in | ||
426 | Solo's terminology.) Therefore, Solo's encode_params() only encodes the | ||
427 | difficulty level if `full' is set. | ||
428 | |||
429 | #2.3.5. decode_params() | ||
430 | |||
431 | void (*decode_params)(game_params *params, char const *string); | ||
432 | |||
433 | This function is the inverse of encode_params() (section 2.3.4). It | ||
434 | parses the supplied string and fills in the supplied `game_params' | ||
435 | structure. Note that the structure will _already_ have been allocated: | ||
436 | this function is not expected to create a _new_ `game_params', but to | ||
437 | modify an existing one. | ||
438 | |||
439 | This function can receive a string which only encodes a subset of the | ||
440 | parameters. The most obvious way in which this can happen is if the | ||
441 | string was constructed by encode_params() with its `full' parameter set | ||
442 | to FALSE; however, it could also happen if the user typed in a parameter | ||
443 | set manually and missed something out. Be prepared to deal with a wide | ||
444 | range of possibilities. | ||
445 | |||
446 | When dealing with a parameter which is not specified in the input | ||
447 | string, what to do requires a judgment call on the part of the | ||
448 | programmer. Sometimes it makes sense to adjust other parameters to bring | ||
449 | them into line with the new ones. In Mines, for example, you would | ||
450 | probably not want to keep the same mine count if the user dropped the | ||
451 | grid size and didn't specify one, since you might easily end up with | ||
452 | more mines than would actually fit in the grid! On the other hand, | ||
453 | sometimes it makes sense to leave the parameter alone: a Solo player | ||
454 | might reasonably expect to be able to configure size and difficulty | ||
455 | independently of one another. | ||
456 | |||
457 | This function currently has no direct means of returning an error if the | ||
458 | string cannot be parsed at all. However, the returned `game_params' is | ||
459 | almost always subsequently passed to validate_params() (section 2.3.11), | ||
460 | so if you really want to signal parse errors, you could always have a | ||
461 | `char *' in your parameters structure which stored an error message, and | ||
462 | have validate_params() return it if it is non-NULL. | ||
463 | |||
464 | #2.3.6. free_params() | ||
465 | |||
466 | void (*free_params)(game_params *params); | ||
467 | |||
468 | This function frees a `game_params' structure, and any subsidiary | ||
469 | allocations contained within it. | ||
470 | |||
471 | #2.3.7. dup_params() | ||
472 | |||
473 | game_params *(*dup_params)(const game_params *params); | ||
474 | |||
475 | This function allocates a new `game_params' structure and initialises it | ||
476 | with an exact copy of the information in the one provided as input. It | ||
477 | returns a pointer to the new duplicate. | ||
478 | |||
479 | #2.3.8. `can_configure' | ||
480 | |||
481 | int can_configure; | ||
482 | |||
483 | This boolean data element is set to TRUE if the back end supports | ||
484 | custom parameter configuration via a dialog box. If it is TRUE, then | ||
485 | the functions configure() and custom_params() are expected to work. See | ||
486 | section 2.3.9 and section 2.3.10 for more details. | ||
487 | |||
488 | #2.3.9. configure() | ||
489 | |||
490 | config_item *(*configure)(const game_params *params); | ||
491 | |||
492 | This function is called when the user requests a dialog box for | ||
493 | custom parameter configuration. It returns a newly allocated array of | ||
494 | config_item structures, describing the GUI elements required in the | ||
495 | dialog box. The array should have one more element than the number of | ||
496 | controls, since it is terminated with a C_END marker (see below). Each | ||
497 | array element describes the control together with its initial value; the | ||
498 | front end will modify the value fields and return the updated array to | ||
499 | custom_params() (see section 2.3.10). | ||
500 | |||
501 | The config_item structure contains the following elements: | ||
502 | |||
503 | char *name; | ||
504 | int type; | ||
505 | union { /* type-specific fields */ } u; | ||
506 | |||
507 | `name' is an ASCII string giving the textual label for a GUI control. It | ||
508 | is _not_ expected to be dynamically allocated. | ||
509 | |||
510 | `type' contains one of a small number of `enum' values defining what | ||
511 | type of control is being described. The usable member of the union field | ||
512 | `u' depends on `type'. The valid type values are: | ||
513 | |||
514 | `C_STRING' | ||
515 | |||
516 | Describes a text input box. (This is also used for numeric input. | ||
517 | The back end does not bother informing the front end that the box is | ||
518 | numeric rather than textual; some front ends do have the capacity | ||
519 | to take this into account, but I decided it wasn't worth the extra | ||
520 | complexity in the interface.) | ||
521 | |||
522 | For controls of this type, `u.string' contains a single field | ||
523 | |||
524 | char *sval; | ||
525 | |||
526 | which stores a dynamically allocated string representing the | ||
527 | contents of the input box. | ||
528 | |||
529 | `C_BOOLEAN' | ||
530 | |||
531 | Describes a simple checkbox. | ||
532 | |||
533 | For controls of this type, `u.boolean' contains a single field | ||
534 | |||
535 | int bval; | ||
536 | |||
537 | which is either TRUE or FALSE. | ||
538 | |||
539 | `C_CHOICES' | ||
540 | |||
541 | Describes a drop-down list presenting one of a small number of fixed | ||
542 | choices. | ||
543 | |||
544 | For controls of this type, `u.choices' contains two fields: | ||
545 | |||
546 | const char *choicenames; | ||
547 | int selected; | ||
548 | |||
549 | `choicenames' contains a list of strings describing the choices. | ||
550 | The very first character of `sval' is used as a delimiter when | ||
551 | processing the rest (so that the strings `:zero:one:two', | ||
552 | `!zero!one!two' and `xzeroxonextwo' all define a three-element list | ||
553 | containing `zero', `one' and `two'). | ||
554 | |||
555 | `selected' contains the index of the currently selected element, | ||
556 | numbering from zero (so that in the above example, 0 would mean | ||
557 | `zero' and 2 would mean `two'). | ||
558 | |||
559 | Note that `u.choices.choicenames' is _not_ dynamically allocated, | ||
560 | unlike `u.string.sval'. | ||
561 | |||
562 | `C_END' | ||
563 | |||
564 | Marks the end of the array of `config_item's. There is no associated | ||
565 | member of the union field `u' for this type. | ||
566 | |||
567 | The array returned from this function is expected to have filled in the | ||
568 | initial values of all the controls according to the input `game_params' | ||
569 | structure. | ||
570 | |||
571 | If the game's `can_configure' flag is set to FALSE, this function is | ||
572 | never called and need not do anything at all. | ||
573 | |||
574 | #2.3.10. custom_params() | ||
575 | |||
576 | game_params *(*custom_params)(const config_item *cfg); | ||
577 | |||
578 | This function is the counterpart to configure() (section 2.3.9). It | ||
579 | receives as input an array of `config_item's which was originally | ||
580 | created by configure(), but in which the control values have since been | ||
581 | changed in accordance with user input. Its function is to read the new | ||
582 | values out of the controls and return a newly allocated `game_params' | ||
583 | structure representing the user's chosen parameter set. | ||
584 | |||
585 | (The front end will have modified the controls' _values_, but there will | ||
586 | still always be the same set of controls, in the same order, as provided | ||
587 | by configure(). It is not necessary to check the `name' and `type' | ||
588 | fields, although you could use assert() if you were feeling energetic.) | ||
589 | |||
590 | This function is not expected to (and indeed _must not_) free the input | ||
591 | `config_item' array. (If the parameters fail to validate, the dialog box | ||
592 | will stay open.) | ||
593 | |||
594 | If the game's `can_configure' flag is set to FALSE, this function is | ||
595 | never called and need not do anything at all. | ||
596 | |||
597 | #2.3.11. validate_params() | ||
598 | |||
599 | const char *(*validate_params)(const game_params *params, | ||
600 | int full); | ||
601 | |||
602 | This function takes a `game_params' structure as input, and checks that | ||
603 | the parameters described in it fall within sensible limits. (At the very | ||
604 | least, grid dimensions should almost certainly be strictly positive, for | ||
605 | example.) | ||
606 | |||
607 | Return value is NULL if no problems were found, or alternatively a (non- | ||
608 | dynamically-allocated) ASCII string describing the error in human- | ||
609 | readable form. | ||
610 | |||
611 | If the `full' parameter is set, full validation should be performed: any | ||
612 | set of parameters which would not permit generation of a sensible puzzle | ||
613 | should be faulted. If `full' is _not_ set, the implication is that | ||
614 | these parameters are not going to be used for _generating_ a puzzle; so | ||
615 | parameters which can't even sensibly _describe_ a valid puzzle should | ||
616 | still be faulted, but parameters which only affect puzzle generation | ||
617 | should not be. | ||
618 | |||
619 | (The `full' option makes a difference when parameter combinations are | ||
620 | non-orthogonal. For example, Net has a boolean option controlling | ||
621 | whether it enforces a unique solution; it turns out that it's impossible | ||
622 | to generate a uniquely soluble puzzle with wrapping walls and width | ||
623 | 2, so validate_params() will complain if you ask for one. However, | ||
624 | if the user had just been playing a unique wrapping puzzle of a more | ||
625 | sensible width, and then pastes in a game ID acquired from somebody else | ||
626 | which happens to describe a _non_-unique wrapping width-2 puzzle, then | ||
627 | validate_params() will be passed a `game_params' containing the width | ||
628 | and wrapping settings from the new game ID and the uniqueness setting | ||
629 | from the old one. This would be faulted, if it weren't for the fact that | ||
630 | `full' is not set during this call, so Net ignores the inconsistency. | ||
631 | The resulting `game_params' is never subsequently used to generate a | ||
632 | puzzle; this is a promise made by the mid-end when it asks for a non- | ||
633 | full validation.) | ||
634 | |||
635 | #2.4. Handling game descriptions | ||
636 | |||
637 | In this section I present the functions that deal with a textual | ||
638 | description of a puzzle, i.e. the part that comes after the colon in a | ||
639 | descriptive-format game ID. | ||
640 | |||
641 | #2.4.1. new_desc() | ||
642 | |||
643 | char *(*new_desc)(const game_params *params, random_state *rs, | ||
644 | char **aux, int interactive); | ||
645 | |||
646 | This function is where all the really hard work gets done. This is | ||
647 | the function whose job is to randomly generate a new puzzle, ensuring | ||
648 | solubility and uniqueness as appropriate. | ||
649 | |||
650 | As input it is given a `game_params' structure and a random state | ||
651 | (see section 5.1 for the random number API). It must invent a puzzle | ||
652 | instance, encode it in string form, and return a dynamically allocated C | ||
653 | string containing that encoding. | ||
654 | |||
655 | Additionally, it may return a second dynamically allocated string | ||
656 | in `*aux'. (If it doesn't want to, then it can leave that parameter | ||
657 | completely alone; it isn't required to set it to NULL, although doing | ||
658 | so is harmless.) That string, if present, will be passed to solve() | ||
659 | (section 2.7.4) later on; so if the puzzle is generated in such a way | ||
660 | that a solution is known, then information about that solution can be | ||
661 | saved in `*aux' for solve() to use. | ||
662 | |||
663 | The `interactive' parameter should be ignored by almost all puzzles. | ||
664 | Its purpose is to distinguish between generating a puzzle within a GUI | ||
665 | context for immediate play, and generating a puzzle in a command-line | ||
666 | context for saving to be played later. The only puzzle that currently | ||
667 | uses this distinction (and, I fervently hope, the only one which will | ||
668 | _ever_ need to use it) is Mines, which chooses a random first-click | ||
669 | location when generating puzzles non-interactively, but which waits | ||
670 | for the user to place the first click when interactive. If you think | ||
671 | you have come up with another puzzle which needs to make use of this | ||
672 | parameter, please think for at least ten minutes about whether there is | ||
673 | _any_ alternative! | ||
674 | |||
675 | Note that game description strings are not required to contain an | ||
676 | encoding of parameters such as grid size; a game description is | ||
677 | never separated from the `game_params' it was generated with, so any | ||
678 | information contained in that structure need not be encoded again in the | ||
679 | game description. | ||
680 | |||
681 | #2.4.2. validate_desc() | ||
682 | |||
683 | const char *(*validate_desc)(const game_params *params, | ||
684 | const char *desc); | ||
685 | |||
686 | This function is given a game description, and its job is to validate | ||
687 | that it describes a puzzle which makes sense. | ||
688 | |||
689 | To some extent it's up to the user exactly how far they take the phrase | ||
690 | `makes sense'; there are no particularly strict rules about how hard the | ||
691 | user is permitted to shoot themself in the foot when typing in a bogus | ||
692 | game description by hand. (For example, Rectangles will not verify that | ||
693 | the sum of all the numbers in the grid equals the grid's area. So a user | ||
694 | could enter a puzzle which was provably not soluble, and the program | ||
695 | wouldn't complain; there just wouldn't happen to be any sequence of | ||
696 | moves which solved it.) | ||
697 | |||
698 | The one non-negotiable criterion is that any game description which | ||
699 | makes it through validate_desc() _must not_ subsequently cause a crash | ||
700 | or an assertion failure when fed to new_game() and thence to the rest of | ||
701 | the back end. | ||
702 | |||
703 | The return value is NULL on success, or a non-dynamically-allocated C | ||
704 | string containing an error message. | ||
705 | |||
706 | #2.4.3. new_game() | ||
707 | |||
708 | game_state *(*new_game)(midend *me, const game_params *params, | ||
709 | const char *desc); | ||
710 | |||
711 | This function takes a game description as input, together with its | ||
712 | accompanying `game_params', and constructs a `game_state' describing the | ||
713 | initial state of the puzzle. It returns a newly allocated `game_state' | ||
714 | structure. | ||
715 | |||
716 | Almost all puzzles should ignore the `me' parameter. It is required by | ||
717 | Mines, which needs it for later passing to midend_supersede_game_desc() | ||
718 | (see section 2.11.2) once the user has placed the first click. I | ||
719 | fervently hope that no other puzzle will be awkward enough to require | ||
720 | it, so everybody else should ignore it. As with the `interactive' | ||
721 | parameter in new_desc() (section 2.4.1), if you think you have a reason | ||
722 | to need this parameter, please try very hard to think of an alternative | ||
723 | approach! | ||
724 | |||
725 | #2.5. Handling game states | ||
726 | |||
727 | This section describes the functions which create and destroy | ||
728 | `game_state' structures. | ||
729 | |||
730 | (Well, except new_game(), which is in section 2.4.3 instead of under | ||
731 | here; but it deals with game descriptions _and_ game states and it had | ||
732 | to go in one section or the other.) | ||
733 | |||
734 | #2.5.1. dup_game() | ||
735 | |||
736 | game_state *(*dup_game)(const game_state *state); | ||
737 | |||
738 | This function allocates a new `game_state' structure and initialises it | ||
739 | with an exact copy of the information in the one provided as input. It | ||
740 | returns a pointer to the new duplicate. | ||
741 | |||
742 | #2.5.2. free_game() | ||
743 | |||
744 | void (*free_game)(game_state *state); | ||
745 | |||
746 | This function frees a `game_state' structure, and any subsidiary | ||
747 | allocations contained within it. | ||
748 | |||
749 | #2.6. Handling `game_ui' | ||
750 | |||
751 | #2.6.1. new_ui() | ||
752 | |||
753 | game_ui *(*new_ui)(const game_state *state); | ||
754 | |||
755 | This function allocates and returns a new `game_ui' structure for | ||
756 | playing a particular puzzle. It is passed a pointer to the initial | ||
757 | `game_state', in case it needs to refer to that when setting up the | ||
758 | initial values for the new game. | ||
759 | |||
760 | #2.6.2. free_ui() | ||
761 | |||
762 | void (*free_ui)(game_ui *ui); | ||
763 | |||
764 | This function frees a `game_ui' structure, and any subsidiary | ||
765 | allocations contained within it. | ||
766 | |||
767 | #2.6.3. encode_ui() | ||
768 | |||
769 | char *(*encode_ui)(const game_ui *ui); | ||
770 | |||
771 | This function encodes any _important_ data in a `game_ui' structure in | ||
772 | string form. It is only called when saving a half-finished game to a | ||
773 | file. | ||
774 | |||
775 | It should be used sparingly. Almost all data in a `game_ui' is not | ||
776 | important enough to save. The location of the keyboard-controlled | ||
777 | cursor, for example, can be reset to a default position on reloading | ||
778 | the game without impacting the user experience. If the user should | ||
779 | somehow manage to save a game while a mouse drag was in progress, then | ||
780 | discarding that mouse drag would be an outright _feature_. | ||
781 | |||
782 | A typical thing that _would_ be worth encoding in this function is the | ||
783 | Mines death counter: it's in the `game_ui' rather than the `game_state' | ||
784 | because it's too important to allow the user to revert it by using Undo, | ||
785 | and therefore it's also too important to allow the user to revert it by | ||
786 | saving and reloading. (Of course, the user could edit the save file by | ||
787 | hand... But if the user is _that_ determined to cheat, they could just | ||
788 | as easily modify the game's source.) | ||
789 | |||
790 | #2.6.4. decode_ui() | ||
791 | |||
792 | void (*decode_ui)(game_ui *ui, const char *encoding); | ||
793 | |||
794 | This function parses a string previously output by encode_ui(), and | ||
795 | writes the decoded data back into the provided `game_ui' structure. | ||
796 | |||
797 | #2.6.5. changed_state() | ||
798 | |||
799 | void (*changed_state)(game_ui *ui, const game_state *oldstate, | ||
800 | const game_state *newstate); | ||
801 | |||
802 | This function is called by the mid-end whenever the current game state | ||
803 | changes, for any reason. Those reasons include: | ||
804 | |||
805 | - a fresh move being made by interpret_move() and execute_move() | ||
806 | |||
807 | - a solve operation being performed by solve() and execute_move() | ||
808 | |||
809 | - the user moving back and forth along the undo list by means of the | ||
810 | Undo and Redo operations | ||
811 | |||
812 | - the user selecting Restart to go back to the initial game state. | ||
813 | |||
814 | The job of changed_state() is to update the `game_ui' for consistency | ||
815 | with the new game state, if any update is necessary. For example, | ||
816 | Same Game stores data about the currently selected tile group in its | ||
817 | `game_ui', and this data is intrinsically related to the game state it | ||
818 | was derived from. So it's very likely to become invalid when the game | ||
819 | state changes; thus, Same Game's changed_state() function clears the | ||
820 | current selection whenever it is called. | ||
821 | |||
822 | When anim_length() or flash_length() are called, you can be sure that | ||
823 | there has been a previous call to changed_state(). So changed_state() | ||
824 | can set up data in the `game_ui' which will be read by anim_length() and | ||
825 | flash_length(), and those functions will not have to worry about being | ||
826 | called without the data having been initialised. | ||
827 | |||
828 | #2.7. Making moves | ||
829 | |||
830 | This section describes the functions which actually make moves in | ||
831 | the game: that is, the functions which process user input and end up | ||
832 | producing new `game_state's. | ||
833 | |||
834 | #2.7.1. interpret_move() | ||
835 | |||
836 | char *(*interpret_move)(const game_state *state, game_ui *ui, | ||
837 | const game_drawstate *ds, | ||
838 | int x, int y, int button); | ||
839 | |||
840 | This function receives user input and processes it. Its input parameters | ||
841 | are the current `game_state', the current `game_ui' and the current | ||
842 | `game_drawstate', plus details of the input event. `button' is either | ||
843 | an ASCII value or a special code (listed below) indicating an arrow or | ||
844 | function key or a mouse event; when `button' is a mouse event, `x' and | ||
845 | `y' contain the pixel coordinates of the mouse pointer relative to the | ||
846 | top left of the puzzle's drawing area. | ||
847 | |||
848 | (The pointer to the `game_drawstate' is marked `const', because | ||
849 | `interpret_move' should not write to it. The normal use of that pointer | ||
850 | will be to read the game's tile size parameter in order to divide mouse | ||
851 | coordinates by it.) | ||
852 | |||
853 | interpret_move() may return in three different ways: | ||
854 | |||
855 | - Returning NULL indicates that no action whatsoever occurred in | ||
856 | response to the input event; the puzzle was not interested in it at | ||
857 | all. | ||
858 | |||
859 | - Returning the special value UI_UPDATE indicates that the input event | ||
860 | has resulted in a change being made to the `game_ui' which will | ||
861 | require a redraw of the game window, but that no actual _move_ was | ||
862 | made (i.e. no new `game_state' needs to be created). | ||
863 | |||
864 | - Returning anything else indicates that a move was made and that | ||
865 | a new `game_state' must be created. However, instead of actually | ||
866 | constructing a new `game_state' itself, this function is required to | ||
867 | return a string description of the details of the move. This string | ||
868 | will be passed to execute_move() (section 2.7.2) to actually create | ||
869 | the new `game_state'. (Encoding moves as strings in this way means | ||
870 | that the mid-end can keep the strings as well as the game states, | ||
871 | and the strings can be written to disk when saving the game and fed | ||
872 | to execute_move() again on reloading.) | ||
873 | |||
874 | The return value from interpret_move() is expected to be dynamically | ||
875 | allocated if and only if it is not either NULL _or_ the special string | ||
876 | constant `UI_UPDATE'. | ||
877 | |||
878 | After this function is called, the back end is permitted to rely on some | ||
879 | subsequent operations happening in sequence: | ||
880 | |||
881 | - execute_move() will be called to convert this move description into | ||
882 | a new `game_state' | ||
883 | |||
884 | - changed_state() will be called with the new `game_state'. | ||
885 | |||
886 | This means that if interpret_move() needs to do updates to the `game_ui' | ||
887 | which are easier to perform by referring to the new `game_state', it can | ||
888 | safely leave them to be done in changed_state() and not worry about them | ||
889 | failing to happen. | ||
890 | |||
891 | (Note, however, that execute_move() may _also_ be called in other | ||
892 | circumstances. It is only interpret_move() which can rely on a | ||
893 | subsequent call to changed_state().) | ||
894 | |||
895 | The special key codes supported by this function are: | ||
896 | |||
897 | LEFT_BUTTON, MIDDLE_BUTTON, RIGHT_BUTTON | ||
898 | |||
899 | Indicate that one of the mouse buttons was pressed down. | ||
900 | |||
901 | LEFT_DRAG, MIDDLE_DRAG, RIGHT_DRAG | ||
902 | |||
903 | Indicate that the mouse was moved while one of the mouse buttons was | ||
904 | still down. The mid-end guarantees that when one of these events is | ||
905 | received, it will always have been preceded by a button-down event | ||
906 | (and possibly other drag events) for the same mouse button, and no | ||
907 | event involving another mouse button will have appeared in between. | ||
908 | |||
909 | LEFT_RELEASE, MIDDLE_RELEASE, RIGHT_RELEASE | ||
910 | |||
911 | Indicate that a mouse button was released. The mid-end guarantees | ||
912 | that when one of these events is received, it will always have been | ||
913 | preceded by a button-down event (and possibly some drag events) for | ||
914 | the same mouse button, and no event involving another mouse button | ||
915 | will have appeared in between. | ||
916 | |||
917 | CURSOR_UP, CURSOR_DOWN, CURSOR_LEFT, CURSOR_RIGHT | ||
918 | |||
919 | Indicate that an arrow key was pressed. | ||
920 | |||
921 | CURSOR_SELECT | ||
922 | |||
923 | On platforms which have a prominent `select' button alongside their | ||
924 | cursor keys, indicates that that button was pressed. | ||
925 | |||
926 | In addition, there are some modifiers which can be bitwise-ORed into the | ||
927 | `button' parameter: | ||
928 | |||
929 | MOD_CTRL, MOD_SHFT | ||
930 | |||
931 | These indicate that the Control or Shift key was pressed alongside | ||
932 | the key. They only apply to the cursor keys, not to mouse buttons or | ||
933 | anything else. | ||
934 | |||
935 | MOD_NUM_KEYPAD | ||
936 | |||
937 | This applies to some ASCII values, and indicates that the key code | ||
938 | was input via the numeric keypad rather than the main keyboard. Some | ||
939 | puzzles may wish to treat this differently (for example, a puzzle | ||
940 | might want to use the numeric keypad as an eight-way directional | ||
941 | pad), whereas others might not (a game involving numeric input | ||
942 | probably just wants to treat the numeric keypad as numbers). | ||
943 | |||
944 | MOD_MASK | ||
945 | |||
946 | This mask is the bitwise OR of all the available modifiers; you can | ||
947 | bitwise-AND with ~MOD_MASK to strip all the modifiers off any input | ||
948 | value. | ||
949 | |||
950 | #2.7.2. execute_move() | ||
951 | |||
952 | game_state *(*execute_move)(const game_state *state, char *move); | ||
953 | |||
954 | This function takes an input `game_state' and a move string as output | ||
955 | from interpret_move(). It returns a newly allocated `game_state' which | ||
956 | contains the result of applying the specified move to the input game | ||
957 | state. | ||
958 | |||
959 | This function may return NULL if it cannot parse the move string (and | ||
960 | this is definitely preferable to crashing or failing an assertion, since | ||
961 | one way this can happen is if loading a corrupt save file). However, it | ||
962 | must not return NULL for any move string that really was output from | ||
963 | interpret_move(): this is punishable by assertion failure in the mid- | ||
964 | end. | ||
965 | |||
966 | #2.7.3. `can_solve' | ||
967 | |||
968 | int can_solve; | ||
969 | |||
970 | This boolean field is set to TRUE if the game's solve() function does | ||
971 | something. If it's set to FALSE, the game will not even offer the | ||
972 | `Solve' menu option. | ||
973 | |||
974 | #2.7.4. solve() | ||
975 | |||
976 | char *(*solve)(const game_state *orig, const game_state *curr, | ||
977 | const char *aux, const char **error); | ||
978 | |||
979 | This function is called when the user selects the `Solve' option from | ||
980 | the menu. | ||
981 | |||
982 | It is passed two input game states: `orig' is the game state from the | ||
983 | very start of the puzzle, and `curr' is the current one. (Different | ||
984 | games find one or other or both of these convenient.) It is also passed | ||
985 | the `aux' string saved by new_desc() (section 2.4.1), in case that | ||
986 | encodes important information needed to provide the solution. | ||
987 | |||
988 | If this function is unable to produce a solution (perhaps, for example, | ||
989 | the game has no in-built solver so it can only solve puzzles it invented | ||
990 | internally and has an `aux' string for) then it may return NULL. If it | ||
991 | does this, it must also set `*error' to an error message to be presented | ||
992 | to the user (such as `Solution not known for this puzzle'); that error | ||
993 | message is not expected to be dynamically allocated. | ||
994 | |||
995 | If this function _does_ produce a solution, it returns a move string | ||
996 | suitable for feeding to execute_move() (section 2.7.2). Like a (non- | ||
997 | empty) string returned from interpret_move(), the returned string should | ||
998 | be dynamically allocated. | ||
999 | |||
1000 | #2.8. Drawing the game graphics | ||
1001 | |||
1002 | This section discusses the back end functions that deal with drawing. | ||
1003 | |||
1004 | #2.8.1. new_drawstate() | ||
1005 | |||
1006 | game_drawstate *(*new_drawstate)(drawing *dr, | ||
1007 | const game_state *state); | ||
1008 | |||
1009 | This function allocates and returns a new `game_drawstate' structure for | ||
1010 | drawing a particular puzzle. It is passed a pointer to a `game_state', | ||
1011 | in case it needs to refer to that when setting up any initial data. | ||
1012 | |||
1013 | This function may not rely on the puzzle having been newly started; a | ||
1014 | new draw state can be constructed at any time if the front end requests | ||
1015 | a forced redraw. For games like Pattern, in which initial game states | ||
1016 | are much simpler than general ones, this might be important to keep in | ||
1017 | mind. | ||
1018 | |||
1019 | The parameter `dr' is a drawing object (see chapter 3) which the | ||
1020 | function might need to use to allocate blitters. (However, this isn't | ||
1021 | recommended; it's usually more sensible to wait to allocate a blitter | ||
1022 | until set_size() is called, because that way you can tailor it to the | ||
1023 | scale at which the puzzle is being drawn.) | ||
1024 | |||
1025 | #2.8.2. free_drawstate() | ||
1026 | |||
1027 | void (*free_drawstate)(drawing *dr, game_drawstate *ds); | ||
1028 | |||
1029 | This function frees a `game_drawstate' structure, and any subsidiary | ||
1030 | allocations contained within it. | ||
1031 | |||
1032 | The parameter `dr' is a drawing object (see chapter 3), which might be | ||
1033 | required if you are freeing a blitter. | ||
1034 | |||
1035 | #2.8.3. `preferred_tilesize' | ||
1036 | |||
1037 | int preferred_tilesize; | ||
1038 | |||
1039 | Each game is required to define a single integer parameter which | ||
1040 | expresses, in some sense, the scale at which it is drawn. This is | ||
1041 | described in the APIs as `tilesize', since most puzzles are on a | ||
1042 | square (or possibly triangular or hexagonal) grid and hence a sensible | ||
1043 | interpretation of this parameter is to define it as the size of one grid | ||
1044 | tile in pixels; however, there's no actual requirement that the `tile | ||
1045 | size' be proportional to the game window size. Window size is required | ||
1046 | to increase monotonically with `tile size', however. | ||
1047 | |||
1048 | The data element `preferred_tilesize' indicates the tile size which | ||
1049 | should be used in the absence of a good reason to do otherwise (such as | ||
1050 | the screen being too small, or the user explicitly requesting a resize | ||
1051 | if that ever gets implemented). | ||
1052 | |||
1053 | #2.8.4. compute_size() | ||
1054 | |||
1055 | void (*compute_size)(const game_params *params, int tilesize, | ||
1056 | int *x, int *y); | ||
1057 | |||
1058 | This function is passed a `game_params' structure and a tile size. It | ||
1059 | returns, in `*x' and `*y', the size in pixels of the drawing area that | ||
1060 | would be required to render a puzzle with those parameters at that tile | ||
1061 | size. | ||
1062 | |||
1063 | #2.8.5. set_size() | ||
1064 | |||
1065 | void (*set_size)(drawing *dr, game_drawstate *ds, | ||
1066 | const game_params *params, int tilesize); | ||
1067 | |||
1068 | This function is responsible for setting up a `game_drawstate' to draw | ||
1069 | at a given tile size. Typically this will simply involve copying the | ||
1070 | supplied `tilesize' parameter into a `tilesize' field inside the draw | ||
1071 | state; for some more complex games it might also involve setting up | ||
1072 | other dimension fields, or possibly allocating a blitter (see section | ||
1073 | 3.1.13). | ||
1074 | |||
1075 | The parameter `dr' is a drawing object (see chapter 3), which is | ||
1076 | required if a blitter needs to be allocated. | ||
1077 | |||
1078 | Back ends may assume (and may enforce by assertion) that this function | ||
1079 | will be called at most once for any `game_drawstate'. If a puzzle needs | ||
1080 | to be redrawn at a different size, the mid-end will create a fresh | ||
1081 | drawstate. | ||
1082 | |||
1083 | #2.8.6. colours() | ||
1084 | |||
1085 | float *(*colours)(frontend *fe, int *ncolours); | ||
1086 | |||
1087 | This function is responsible for telling the front end what colours the | ||
1088 | puzzle will need to draw itself. | ||
1089 | |||
1090 | It returns the number of colours required in `*ncolours', and the return | ||
1091 | value from the function itself is a dynamically allocated array of three | ||
1092 | times that many `float's, containing the red, green and blue components | ||
1093 | of each colour respectively as numbers in the range [0,1]. | ||
1094 | |||
1095 | The second parameter passed to this function is a front end handle. | ||
1096 | The only things it is permitted to do with this handle are to call the | ||
1097 | front-end function called frontend_default_colour() (see section 4.39) | ||
1098 | or the utility function called game_mkhighlight() (see section 5.5.7). | ||
1099 | (The latter is a wrapper on the former, so front end implementors only | ||
1100 | need to provide frontend_default_colour().) This allows colours() to | ||
1101 | take local configuration into account when deciding on its own colour | ||
1102 | allocations. Most games use the front end's default colour as their | ||
1103 | background, apart from a few which depend on drawing relief highlights | ||
1104 | so they adjust the background colour if it's too light for highlights to | ||
1105 | show up against it. | ||
1106 | |||
1107 | Note that the colours returned from this function are for _drawing_, | ||
1108 | not for printing. Printing has an entirely different colour allocation | ||
1109 | policy. | ||
1110 | |||
1111 | #2.8.7. anim_length() | ||
1112 | |||
1113 | float (*anim_length)(const game_state *oldstate, | ||
1114 | const game_state *newstate, | ||
1115 | int dir, game_ui *ui); | ||
1116 | |||
1117 | This function is called when a move is made, undone or redone. It is | ||
1118 | given the old and the new `game_state', and its job is to decide whether | ||
1119 | the transition between the two needs to be animated or can be instant. | ||
1120 | |||
1121 | `oldstate' is the state that was current until this call; `newstate' | ||
1122 | is the state that will be current after it. `dir' specifies the | ||
1123 | chronological order of those states: if it is positive, then the | ||
1124 | transition is the result of a move or a redo (and so `newstate' is the | ||
1125 | later of the two moves), whereas if it is negative then the transition | ||
1126 | is the result of an undo (so that `newstate' is the _earlier_ move). | ||
1127 | |||
1128 | If this function decides the transition should be animated, it returns | ||
1129 | the desired length of the animation in seconds. If not, it returns zero. | ||
1130 | |||
1131 | State changes as a result of a Restart operation are never animated; the | ||
1132 | mid-end will handle them internally and never consult this function at | ||
1133 | all. State changes as a result of Solve operations are also not animated | ||
1134 | by default, although you can change this for a particular game by | ||
1135 | setting a flag in `flags' (section 2.10.7). | ||
1136 | |||
1137 | The function is also passed a pointer to the local `game_ui'. It may | ||
1138 | refer to information in here to help with its decision (see section | ||
1139 | 6.3.7 for an example of this), and/or it may _write_ information about | ||
1140 | the nature of the animation which will be read later by redraw(). | ||
1141 | |||
1142 | When this function is called, it may rely on changed_state() having been | ||
1143 | called previously, so if anim_length() needs to refer to information in | ||
1144 | the `game_ui', then changed_state() is a reliable place to have set that | ||
1145 | information up. | ||
1146 | |||
1147 | Move animations do not inhibit further input events. If the user | ||
1148 | continues playing before a move animation is complete, the animation | ||
1149 | will be abandoned and the display will jump straight to the final state. | ||
1150 | |||
1151 | #2.8.8. flash_length() | ||
1152 | |||
1153 | float (*flash_length)(const game_state *oldstate, | ||
1154 | const game_state *newstate, | ||
1155 | int dir, game_ui *ui); | ||
1156 | |||
1157 | This function is called when a move is completed. (`Completed' | ||
1158 | means that not only has the move been made, but any animation which | ||
1159 | accompanied it has finished.) It decides whether the transition from | ||
1160 | `oldstate' to `newstate' merits a `flash'. | ||
1161 | |||
1162 | A flash is much like a move animation, but it is _not_ interrupted by | ||
1163 | further user interface activity; it runs to completion in parallel with | ||
1164 | whatever else might be going on on the display. The only thing which | ||
1165 | will rush a flash to completion is another flash. | ||
1166 | |||
1167 | The purpose of flashes is to indicate that the game has been completed. | ||
1168 | They were introduced as a separate concept from move animations because | ||
1169 | of Net: the habit of most Net players (and certainly me) is to rotate a | ||
1170 | tile into place and immediately lock it, then move on to another tile. | ||
1171 | When you make your last move, at the instant the final tile is rotated | ||
1172 | into place the screen starts to flash to indicate victory - but if you | ||
1173 | then press the lock button out of habit, then the move animation is | ||
1174 | cancelled, and the victory flash does not complete. (And if you _don't_ | ||
1175 | press the lock button, the completed grid will look untidy because there | ||
1176 | will be one unlocked square.) Therefore, I introduced a specific concept | ||
1177 | of a `flash' which is separate from a move animation and can proceed in | ||
1178 | parallel with move animations and any other display activity, so that | ||
1179 | the victory flash in Net is not cancelled by that final locking move. | ||
1180 | |||
1181 | The input parameters to flash_length() are exactly the same as the ones | ||
1182 | to anim_length(). | ||
1183 | |||
1184 | Just like anim_length(), when this function is called, it may rely on | ||
1185 | changed_state() having been called previously, so if it needs to refer | ||
1186 | to information in the `game_ui' then changed_state() is a reliable place | ||
1187 | to have set that information up. | ||
1188 | |||
1189 | (Some games use flashes to indicate defeat as well as victory; Mines, | ||
1190 | for example, flashes in a different colour when you tread on a mine from | ||
1191 | the colour it uses when you complete the game. In order to achieve this, | ||
1192 | its flash_length() function has to store a flag in the `game_ui' to | ||
1193 | indicate which flash type is required.) | ||
1194 | |||
1195 | #2.8.9. status() | ||
1196 | |||
1197 | int (*status)(const game_state *state); | ||
1198 | |||
1199 | This function returns a status value indicating whether the current game | ||
1200 | is still in play, or has been won, or has been conclusively lost. The | ||
1201 | mid-end uses this to implement midend_status() (section 4.26). | ||
1202 | |||
1203 | The return value should be +1 if the game has been successfully solved. | ||
1204 | If the game has been lost in a situation where further play is unlikely, | ||
1205 | the return value should be -1. If neither is true (so play is still | ||
1206 | ongoing), return zero. | ||
1207 | |||
1208 | Front ends may wish to use a non-zero status as a cue to proactively | ||
1209 | offer the option of starting a new game. Therefore, back ends should | ||
1210 | not return -1 if the game has been _technically_ lost but undoing and | ||
1211 | continuing is still a realistic possibility. | ||
1212 | |||
1213 | (For instance, games with hidden information such as Guess or Mines | ||
1214 | might well return a non-zero status whenever they reveal the solution, | ||
1215 | whether or not the player guessed it correctly, on the grounds that a | ||
1216 | player would be unlikely to hide the solution and continue playing after | ||
1217 | the answer was spoiled. On the other hand, games where you can merely | ||
1218 | get into a dead end such as Same Game or Inertia might choose to return | ||
1219 | 0 in that situation, on the grounds that the player would quite likely | ||
1220 | press Undo and carry on playing.) | ||
1221 | |||
1222 | #2.8.10. redraw() | ||
1223 | |||
1224 | void (*redraw)(drawing *dr, game_drawstate *ds, | ||
1225 | const game_state *oldstate, | ||
1226 | const game_state *newstate, | ||
1227 | int dir, const game_ui *ui, | ||
1228 | float anim_time, float flash_time); | ||
1229 | |||
1230 | This function is responsible for actually drawing the contents of | ||
1231 | the game window, and for redrawing every time the game state or the | ||
1232 | `game_ui' changes. | ||
1233 | |||
1234 | The parameter `dr' is a drawing object which may be passed to the | ||
1235 | drawing API functions (see chapter 3 for documentation of the drawing | ||
1236 | API). This function may not save `dr' and use it elsewhere; it must only | ||
1237 | use it for calling back to the drawing API functions within its own | ||
1238 | lifetime. | ||
1239 | |||
1240 | `ds' is the local `game_drawstate', of course, and `ui' is the local | ||
1241 | `game_ui'. | ||
1242 | |||
1243 | `newstate' is the semantically-current game state, and is always non- | ||
1244 | NULL. If `oldstate' is also non-NULL, it means that a move has recently | ||
1245 | been made and the game is still in the process of displaying an | ||
1246 | animation linking the old and new states; in this situation, `anim_time' | ||
1247 | will give the length of time (in seconds) that the animation has already | ||
1248 | been running. If `oldstate' is NULL, then `anim_time' is unused (and | ||
1249 | will hopefully be set to zero to avoid confusion). | ||
1250 | |||
1251 | `flash_time', if it is is non-zero, denotes that the game is in the | ||
1252 | middle of a flash, and gives the time since the start of the flash. See | ||
1253 | section 2.8.8 for general discussion of flashes. | ||
1254 | |||
1255 | The very first time this function is called for a new `game_drawstate', | ||
1256 | it is expected to redraw the _entire_ drawing area. Since this often | ||
1257 | involves drawing visual furniture which is never subsequently altered, | ||
1258 | it is often simplest to arrange this by having a special `first time' | ||
1259 | flag in the draw state, and resetting it after the first redraw. | ||
1260 | |||
1261 | When this function (or any subfunction) calls the drawing API, it is | ||
1262 | expected to pass colour indices which were previously defined by the | ||
1263 | colours() function. | ||
1264 | |||
1265 | #2.9. Printing functions | ||
1266 | |||
1267 | This section discusses the back end functions that deal with printing | ||
1268 | puzzles out on paper. | ||
1269 | |||
1270 | #2.9.1. `can_print' | ||
1271 | |||
1272 | int can_print; | ||
1273 | |||
1274 | This flag is set to TRUE if the puzzle is capable of printing itself | ||
1275 | on paper. (This makes sense for some puzzles, such as Solo, which can | ||
1276 | be filled in with a pencil. Other puzzles, such as Twiddle, inherently | ||
1277 | involve moving things around and so would not make sense to print.) | ||
1278 | |||
1279 | If this flag is FALSE, then the functions print_size() and print() will | ||
1280 | never be called. | ||
1281 | |||
1282 | #2.9.2. `can_print_in_colour' | ||
1283 | |||
1284 | int can_print_in_colour; | ||
1285 | |||
1286 | This flag is set to TRUE if the puzzle is capable of printing itself | ||
1287 | differently when colour is available. For example, Map can actually | ||
1288 | print coloured regions in different _colours_ rather than resorting to | ||
1289 | cross-hatching. | ||
1290 | |||
1291 | If the `can_print' flag is FALSE, then this flag will be ignored. | ||
1292 | |||
1293 | #2.9.3. print_size() | ||
1294 | |||
1295 | void (*print_size)(const game_params *params, float *x, float *y); | ||
1296 | |||
1297 | This function is passed a `game_params' structure and a tile size. It | ||
1298 | returns, in `*x' and `*y', the preferred size in _millimetres_ of that | ||
1299 | puzzle if it were to be printed out on paper. | ||
1300 | |||
1301 | If the `can_print' flag is FALSE, this function will never be called. | ||
1302 | |||
1303 | #2.9.4. print() | ||
1304 | |||
1305 | void (*print)(drawing *dr, const game_state *state, int tilesize); | ||
1306 | |||
1307 | This function is called when a puzzle is to be printed out on paper. It | ||
1308 | should use the drawing API functions (see chapter 3) to print itself. | ||
1309 | |||
1310 | This function is separate from redraw() because it is often very | ||
1311 | different: | ||
1312 | |||
1313 | - The printing function may not depend on pixel accuracy, since | ||
1314 | printer resolution is variable. Draw as if your canvas had infinite | ||
1315 | resolution. | ||
1316 | |||
1317 | - The printing function sometimes needs to display things in a | ||
1318 | completely different style. Net, for example, is very different as | ||
1319 | an on-screen puzzle and as a printed one. | ||
1320 | |||
1321 | - The printing function is often much simpler since it has no need to | ||
1322 | deal with repeated partial redraws. | ||
1323 | |||
1324 | However, there's no reason the printing and redraw functions can't share | ||
1325 | some code if they want to. | ||
1326 | |||
1327 | When this function (or any subfunction) calls the drawing API, the | ||
1328 | colour indices it passes should be colours which have been allocated by | ||
1329 | the print_*_colour() functions within this execution of print(). This is | ||
1330 | very different from the fixed small number of colours used in redraw(), | ||
1331 | because printers do not have a limitation on the total number of colours | ||
1332 | that may be used. Some puzzles' printing functions might wish to | ||
1333 | allocate only one `ink' colour and use it for all drawing; others might | ||
1334 | wish to allocate _more_ colours than are used on screen. | ||
1335 | |||
1336 | One possible colour policy worth mentioning specifically is that a | ||
1337 | puzzle's printing function might want to allocate the _same_ colour | ||
1338 | indices as are used by the redraw function, so that code shared between | ||
1339 | drawing and printing does not have to keep switching its colour indices. | ||
1340 | In order to do this, the simplest thing is to make use of the fact that | ||
1341 | colour indices returned from print_*_colour() are guaranteed to be in | ||
1342 | increasing order from zero. So if you have declared an `enum' defining | ||
1343 | three colours COL_BACKGROUND, COL_THIS and COL_THAT, you might then | ||
1344 | write | ||
1345 | |||
1346 | int c; | ||
1347 | c = print_mono_colour(dr, 1); assert(c == COL_BACKGROUND); | ||
1348 | c = print_mono_colour(dr, 0); assert(c == COL_THIS); | ||
1349 | c = print_mono_colour(dr, 0); assert(c == COL_THAT); | ||
1350 | |||
1351 | If the `can_print' flag is FALSE, this function will never be called. | ||
1352 | |||
1353 | #2.10. Miscellaneous | ||
1354 | |||
1355 | #2.10.1. `can_format_as_text_ever' | ||
1356 | |||
1357 | int can_format_as_text_ever; | ||
1358 | |||
1359 | This boolean field is TRUE if the game supports formatting a game state | ||
1360 | as ASCII text (typically ASCII art) for copying to the clipboard and | ||
1361 | pasting into other applications. If it is FALSE, front ends will not | ||
1362 | offer the `Copy' command at all. | ||
1363 | |||
1364 | If this field is TRUE, the game does not necessarily have to support | ||
1365 | text formatting for _all_ games: e.g. a game which can be played on | ||
1366 | a square grid or a triangular one might only support copy and paste | ||
1367 | for the former, because triangular grids in ASCII art are just too | ||
1368 | difficult. | ||
1369 | |||
1370 | If this field is FALSE, the functions can_format_as_text_now() (section | ||
1371 | 2.10.2) and text_format() (section 2.10.3) are never called. | ||
1372 | |||
1373 | #2.10.2. `can_format_as_text_now()' | ||
1374 | |||
1375 | int (*can_format_as_text_now)(const game_params *params); | ||
1376 | |||
1377 | This function is passed a `game_params' and returns a boolean, which is | ||
1378 | TRUE if the game can support ASCII text output for this particular game | ||
1379 | type. If it returns FALSE, front ends will grey out or otherwise disable | ||
1380 | the `Copy' command. | ||
1381 | |||
1382 | Games may enable and disable the copy-and-paste function for different | ||
1383 | game _parameters_, but are currently constrained to return the same | ||
1384 | answer from this function for all game _states_ sharing the same | ||
1385 | parameters. In other words, the `Copy' function may enable or disable | ||
1386 | itself when the player changes game preset, but will never change during | ||
1387 | play of a single game or when another game of exactly the same type is | ||
1388 | generated. | ||
1389 | |||
1390 | This function should not take into account aspects of the game | ||
1391 | parameters which are not encoded by encode_params() (section 2.3.4) | ||
1392 | when the `full' parameter is set to FALSE. Such parameters will not | ||
1393 | necessarily match up between a call to this function and a subsequent | ||
1394 | call to text_format() itself. (For instance, game _difficulty_ should | ||
1395 | not affect whether the game can be copied to the clipboard. Only the | ||
1396 | actual visible _shape_ of the game can affect that.) | ||
1397 | |||
1398 | #2.10.3. text_format() | ||
1399 | |||
1400 | char *(*text_format)(const game_state *state); | ||
1401 | |||
1402 | This function is passed a `game_state', and returns a newly allocated C | ||
1403 | string containing an ASCII representation of that game state. It is used | ||
1404 | to implement the `Copy' operation in many front ends. | ||
1405 | |||
1406 | This function will only ever be called if the back end field | ||
1407 | `can_format_as_text_ever' (section 2.10.1) is TRUE _and_ the function | ||
1408 | can_format_as_text_now() (section 2.10.2) has returned TRUE for the | ||
1409 | currently selected game parameters. | ||
1410 | |||
1411 | The returned string may contain line endings (and will probably want | ||
1412 | to), using the normal C internal `\n' convention. For consistency | ||
1413 | between puzzles, all multi-line textual puzzle representations should | ||
1414 | _end_ with a newline as well as containing them internally. (There are | ||
1415 | currently no puzzles which have a one-line ASCII representation, so | ||
1416 | there's no precedent yet for whether that should come with a newline or | ||
1417 | not.) | ||
1418 | |||
1419 | #2.10.4. wants_statusbar | ||
1420 | |||
1421 | int wants_statusbar; | ||
1422 | |||
1423 | This boolean field is set to TRUE if the puzzle has a use for a textual | ||
1424 | status line (to display score, completion status, currently active | ||
1425 | tiles, etc). | ||
1426 | |||
1427 | #2.10.5. `is_timed' | ||
1428 | |||
1429 | int is_timed; | ||
1430 | |||
1431 | This boolean field is TRUE if the puzzle is time-critical. If so, the | ||
1432 | mid-end will maintain a game timer while the user plays. | ||
1433 | |||
1434 | If this field is FALSE, then timing_state() will never be called and | ||
1435 | need not do anything. | ||
1436 | |||
1437 | #2.10.6. timing_state() | ||
1438 | |||
1439 | int (*timing_state)(const game_state *state, game_ui *ui); | ||
1440 | |||
1441 | This function is passed the current `game_state' and the local | ||
1442 | `game_ui'; it returns TRUE if the game timer should currently be | ||
1443 | running. | ||
1444 | |||
1445 | A typical use for the `game_ui' in this function is to note when the | ||
1446 | game was first completed (by setting a flag in changed_state() - see | ||
1447 | section 2.6.5), and freeze the timer thereafter so that the user can | ||
1448 | undo back through their solution process without altering their time. | ||
1449 | |||
1450 | #2.10.7. `flags' | ||
1451 | |||
1452 | int flags; | ||
1453 | |||
1454 | This field contains miscellaneous per-backend flags. It consists of the | ||
1455 | bitwise OR of some combination of the following: | ||
1456 | |||
1457 | BUTTON_BEATS(x,y) | ||
1458 | |||
1459 | Given any x and y from the set {LEFT_BUTTON, MIDDLE_BUTTON, | ||
1460 | RIGHT_BUTTON}, this macro evaluates to a bit flag which indicates | ||
1461 | that when buttons x and y are both pressed simultaneously, the mid- | ||
1462 | end should consider x to have priority. (In the absence of any such | ||
1463 | flags, the mid-end will always consider the most recently pressed | ||
1464 | button to have priority.) | ||
1465 | |||
1466 | SOLVE_ANIMATES | ||
1467 | |||
1468 | This flag indicates that moves generated by solve() (section 2.7.4) | ||
1469 | are candidates for animation just like any other move. For most | ||
1470 | games, solve moves should not be animated, so the mid-end doesn't | ||
1471 | even bother calling anim_length() (section 2.8.7), thus saving some | ||
1472 | special-case code in each game. On the rare occasion that animated | ||
1473 | solve moves are actually required, you can set this flag. | ||
1474 | |||
1475 | REQUIRE_RBUTTON | ||
1476 | |||
1477 | This flag indicates that the puzzle cannot be usefully played | ||
1478 | without the use of mouse buttons other than the left one. On some | ||
1479 | PDA platforms, this flag is used by the front end to enable right- | ||
1480 | button emulation through an appropriate gesture. Note that a puzzle | ||
1481 | is not required to set this just because it _uses_ the right button, | ||
1482 | but only if its use of the right button is critical to playing the | ||
1483 | game. (Slant, for example, uses the right button to cycle through | ||
1484 | the three square states in the opposite order from the left button, | ||
1485 | and hence can manage fine without it.) | ||
1486 | |||
1487 | REQUIRE_NUMPAD | ||
1488 | |||
1489 | This flag indicates that the puzzle cannot be usefully played | ||
1490 | without the use of number-key input. On some PDA platforms it | ||
1491 | causes an emulated number pad to appear on the screen. Similarly to | ||
1492 | REQUIRE_RBUTTON, a puzzle need not specify this simply if its use of | ||
1493 | the number keys is not critical. | ||
1494 | |||
1495 | #2.11. Things a back end may do on its own initiative | ||
1496 | |||
1497 | This section describes a couple of things that a back end may choose | ||
1498 | to do by calling functions elsewhere in the program, which would not | ||
1499 | otherwise be obvious. | ||
1500 | |||
1501 | #2.11.1. Create a random state | ||
1502 | |||
1503 | If a back end needs random numbers at some point during normal play, it | ||
1504 | can create a fresh `random_state' by first calling `get_random_seed' | ||
1505 | (section 4.35) and then passing the returned seed data to random_new(). | ||
1506 | |||
1507 | This is likely not to be what you want. If a puzzle needs randomness in | ||
1508 | the middle of play, it's likely to be more sensible to store some sort | ||
1509 | of random state within the `game_state', so that the random numbers are | ||
1510 | tied to the particular game state and hence the player can't simply keep | ||
1511 | undoing their move until they get numbers they like better. | ||
1512 | |||
1513 | This facility is currently used only in Net, to implement the `jumble' | ||
1514 | command, which sets every unlocked tile to a new random orientation. | ||
1515 | This randomness _is_ a reasonable use of the feature, because it's non- | ||
1516 | adversarial - there's no advantage to the user in getting different | ||
1517 | random numbers. | ||
1518 | |||
1519 | #2.11.2. Supersede its own game description | ||
1520 | |||
1521 | In response to a move, a back end is (reluctantly) permitted to call | ||
1522 | midend_supersede_game_desc(): | ||
1523 | |||
1524 | void midend_supersede_game_desc(midend *me, | ||
1525 | char *desc, char *privdesc); | ||
1526 | |||
1527 | When the user selects `New Game', the mid-end calls new_desc() | ||
1528 | (section 2.4.1) to get a new game description, and (as well as using | ||
1529 | that to generate an initial game state) stores it for the save file | ||
1530 | and for telling to the user. The function above overwrites that | ||
1531 | game description, and also splits it in two. `desc' becomes the new | ||
1532 | game description which is provided to the user on request, and is | ||
1533 | also the one used to construct a new initial game state if the user | ||
1534 | selects `Restart'. `privdesc' is a `private' game description, used to | ||
1535 | reconstruct the game's initial state when reloading. | ||
1536 | |||
1537 | The distinction between the two, as well as the need for this function | ||
1538 | at all, comes from Mines. Mines begins with a blank grid and no | ||
1539 | idea of where the mines actually are; new_desc() does almost no | ||
1540 | work in interactive mode, and simply returns a string encoding the | ||
1541 | `random_state'. When the user first clicks to open a tile, _then_ Mines | ||
1542 | generates the mine positions, in such a way that the game is soluble | ||
1543 | from that starting point. Then it uses this function to supersede the | ||
1544 | random-state game description with a proper one. But it needs two: one | ||
1545 | containing the initial click location (because that's what you want to | ||
1546 | happen if you restart the game, and also what you want to send to a | ||
1547 | friend so that they play _the same game_ as you), and one without the | ||
1548 | initial click location (because when you save and reload the game, you | ||
1549 | expect to see the same blank initial state as you had before saving). | ||
1550 | |||
1551 | I should stress again that this function is a horrid hack. Nobody should | ||
1552 | use it if they're not Mines; if you think you need to use it, think | ||
1553 | again repeatedly in the hope of finding a better way to do whatever it | ||
1554 | was you needed to do. | ||
1555 | |||
1556 | #3. The drawing API | ||
1557 | |||
1558 | The back end function redraw() (section 2.8.10) is required to draw | ||
1559 | the puzzle's graphics on the window's drawing area, or on paper if the | ||
1560 | puzzle is printable. To do this portably, it is provided with a drawing | ||
1561 | API allowing it to talk directly to the front end. In this chapter I | ||
1562 | document that API, both for the benefit of back end authors trying to | ||
1563 | use it and for front end authors trying to implement it. | ||
1564 | |||
1565 | The drawing API as seen by the back end is a collection of global | ||
1566 | functions, each of which takes a pointer to a `drawing' structure (a | ||
1567 | `drawing object'). These objects are supplied as parameters to the back | ||
1568 | end's redraw() and print() functions. | ||
1569 | |||
1570 | In fact these global functions are not implemented directly by the front | ||
1571 | end; instead, they are implemented centrally in `drawing.c' and form a | ||
1572 | small piece of middleware. The drawing API as supplied by the front end | ||
1573 | is a structure containing a set of function pointers, plus a `void *' | ||
1574 | handle which is passed to each of those functions. This enables a single | ||
1575 | front end to switch between multiple implementations of the drawing API | ||
1576 | if necessary. For example, the Windows API supplies a printing mechanism | ||
1577 | integrated into the same GDI which deals with drawing in windows, and | ||
1578 | therefore the same API implementation can handle both drawing and | ||
1579 | printing; but on Unix, the most common way for applications to print | ||
1580 | is by producing PostScript output directly, and although it would be | ||
1581 | _possible_ to write a single (say) draw_rect() function which checked | ||
1582 | a global flag to decide whether to do GTK drawing operations or output | ||
1583 | PostScript to a file, it's much nicer to have two separate functions and | ||
1584 | switch between them as appropriate. | ||
1585 | |||
1586 | When drawing, the puzzle window is indexed by pixel coordinates, with | ||
1587 | the top left pixel defined as (0,0) and the bottom right pixel (w-1,h- | ||
1588 | 1), where `w' and `h' are the width and height values returned by the | ||
1589 | back end function compute_size() (section 2.8.4). | ||
1590 | |||
1591 | When printing, the puzzle's print area is indexed in exactly the same | ||
1592 | way (with an arbitrary tile size provided by the printing module | ||
1593 | `printing.c'), to facilitate sharing of code between the drawing and | ||
1594 | printing routines. However, when printing, puzzles may no longer assume | ||
1595 | that the coordinate unit has any relationship to a pixel; the printer's | ||
1596 | actual resolution might very well not even be known at print time, so | ||
1597 | the coordinate unit might be smaller or larger than a pixel. Puzzles' | ||
1598 | print functions should restrict themselves to drawing geometric shapes | ||
1599 | rather than fiddly pixel manipulation. | ||
1600 | |||
1601 | _Puzzles' redraw functions may assume that the surface they draw on is | ||
1602 | persistent_. It is the responsibility of every front end to preserve | ||
1603 | the puzzle's window contents in the face of GUI window expose issues | ||
1604 | and similar. It is not permissible to request that the back end redraw | ||
1605 | any part of a window that it has already drawn, unless something has | ||
1606 | actually changed as a result of making moves in the puzzle. | ||
1607 | |||
1608 | Most front ends accomplish this by having the drawing routines draw on a | ||
1609 | stored bitmap rather than directly on the window, and copying the bitmap | ||
1610 | to the window every time a part of the window needs to be redrawn. | ||
1611 | Therefore, it is vitally important that whenever the back end does any | ||
1612 | drawing it informs the front end of which parts of the window it has | ||
1613 | accessed, and hence which parts need repainting. This is done by calling | ||
1614 | draw_update() (section 3.1.11). | ||
1615 | |||
1616 | Persistence of old drawing is convenient. However, a puzzle should be | ||
1617 | very careful about how it updates its drawing area. The problem is that | ||
1618 | some front ends do anti-aliased drawing: rather than simply choosing | ||
1619 | between leaving each pixel untouched or painting it a specified colour, | ||
1620 | an antialiased drawing function will _blend_ the original and new | ||
1621 | colours in pixels at a figure's boundary according to the proportion of | ||
1622 | the pixel occupied by the figure (probably modified by some heuristic | ||
1623 | fudge factors). All of this produces a smoother appearance for curves | ||
1624 | and diagonal lines. | ||
1625 | |||
1626 | An unfortunate effect of drawing an anti-aliased figure repeatedly | ||
1627 | is that the pixels around the figure's boundary come steadily more | ||
1628 | saturated with `ink' and the boundary appears to `spread out'. Worse, | ||
1629 | redrawing a figure in a different colour won't fully paint over the old | ||
1630 | boundary pixels, so the end result is a rather ugly smudge. | ||
1631 | |||
1632 | A good strategy to avoid unpleasant anti-aliasing artifacts is to | ||
1633 | identify a number of rectangular areas which need to be redrawn, clear | ||
1634 | them to the background colour, and then redraw their contents from | ||
1635 | scratch, being careful all the while not to stray beyond the boundaries | ||
1636 | of the original rectangles. The clip() function (section 3.1.9) comes in | ||
1637 | very handy here. Games based on a square grid can often do this fairly | ||
1638 | easily. Other games may need to be somewhat more careful. For example, | ||
1639 | Loopy's redraw function first identifies portions of the display which | ||
1640 | need to be updated. Then, if the changes are fairly well localised, it | ||
1641 | clears and redraws a rectangle containing each changed area. Otherwise, | ||
1642 | it gives up and redraws the entire grid from scratch. | ||
1643 | |||
1644 | It is possible to avoid clearing to background and redrawing from | ||
1645 | scratch if one is very careful about which drawing functions one | ||
1646 | uses: if a function is documented as not anti-aliasing under some | ||
1647 | circumstances, you can rely on each pixel in a drawing either being left | ||
1648 | entirely alone or being set to the requested colour, with no blending | ||
1649 | being performed. | ||
1650 | |||
1651 | In the following sections I first discuss the drawing API as seen by the | ||
1652 | back end, and then the _almost_ identical function-pointer form seen by | ||
1653 | the front end. | ||
1654 | |||
1655 | #3.1. Drawing API as seen by the back end | ||
1656 | |||
1657 | This section documents the back-end drawing API, in the form of | ||
1658 | functions which take a `drawing' object as an argument. | ||
1659 | |||
1660 | #3.1.1. draw_rect() | ||
1661 | |||
1662 | void draw_rect(drawing *dr, int x, int y, int w, int h, | ||
1663 | int colour); | ||
1664 | |||
1665 | Draws a filled rectangle in the puzzle window. | ||
1666 | |||
1667 | `x' and `y' give the coordinates of the top left pixel of the rectangle. | ||
1668 | `w' and `h' give its width and height. Thus, the horizontal extent of | ||
1669 | the rectangle runs from `x' to `x+w-1' inclusive, and the vertical | ||
1670 | extent from `y' to `y+h-1' inclusive. | ||
1671 | |||
1672 | `colour' is an integer index into the colours array returned by the back | ||
1673 | end function colours() (section 2.8.6). | ||
1674 | |||
1675 | There is no separate pixel-plotting function. If you want to plot a | ||
1676 | single pixel, the approved method is to use draw_rect() with width and | ||
1677 | height set to 1. | ||
1678 | |||
1679 | Unlike many of the other drawing functions, this function is guaranteed | ||
1680 | to be pixel-perfect: the rectangle will be sharply defined and not anti- | ||
1681 | aliased or anything like that. | ||
1682 | |||
1683 | This function may be used for both drawing and printing. | ||
1684 | |||
1685 | #3.1.2. draw_rect_outline() | ||
1686 | |||
1687 | void draw_rect_outline(drawing *dr, int x, int y, int w, int h, | ||
1688 | int colour); | ||
1689 | |||
1690 | Draws an outline rectangle in the puzzle window. | ||
1691 | |||
1692 | `x' and `y' give the coordinates of the top left pixel of the rectangle. | ||
1693 | `w' and `h' give its width and height. Thus, the horizontal extent of | ||
1694 | the rectangle runs from `x' to `x+w-1' inclusive, and the vertical | ||
1695 | extent from `y' to `y+h-1' inclusive. | ||
1696 | |||
1697 | `colour' is an integer index into the colours array returned by the back | ||
1698 | end function colours() (section 2.8.6). | ||
1699 | |||
1700 | From a back end perspective, this function may be considered to be part | ||
1701 | of the drawing API. However, front ends are not required to implement | ||
1702 | it, since it is actually implemented centrally (in misc.c) as a wrapper | ||
1703 | on draw_polygon(). | ||
1704 | |||
1705 | This function may be used for both drawing and printing. | ||
1706 | |||
1707 | #3.1.3. draw_line() | ||
1708 | |||
1709 | void draw_line(drawing *dr, int x1, int y1, int x2, int y2, | ||
1710 | int colour); | ||
1711 | |||
1712 | Draws a straight line in the puzzle window. | ||
1713 | |||
1714 | `x1' and `y1' give the coordinates of one end of the line. `x2' and `y2' | ||
1715 | give the coordinates of the other end. The line drawn includes both | ||
1716 | those points. | ||
1717 | |||
1718 | `colour' is an integer index into the colours array returned by the back | ||
1719 | end function colours() (section 2.8.6). | ||
1720 | |||
1721 | Some platforms may perform anti-aliasing on this function. Therefore, | ||
1722 | do not assume that you can erase a line by drawing the same line over | ||
1723 | it in the background colour; anti-aliasing might lead to perceptible | ||
1724 | ghost artefacts around the vanished line. Horizontal and vertical lines, | ||
1725 | however, are pixel-perfect and not anti-aliased. | ||
1726 | |||
1727 | This function may be used for both drawing and printing. | ||
1728 | |||
1729 | #3.1.4. draw_polygon() | ||
1730 | |||
1731 | void draw_polygon(drawing *dr, int *coords, int npoints, | ||
1732 | int fillcolour, int outlinecolour); | ||
1733 | |||
1734 | Draws an outlined or filled polygon in the puzzle window. | ||
1735 | |||
1736 | `coords' is an array of (2*npoints) integers, containing the `x' and `y' | ||
1737 | coordinates of `npoints' vertices. | ||
1738 | |||
1739 | `fillcolour' and `outlinecolour' are integer indices into the colours | ||
1740 | array returned by the back end function colours() (section 2.8.6). | ||
1741 | `fillcolour' may also be -1 to indicate that the polygon should be | ||
1742 | outlined only. | ||
1743 | |||
1744 | The polygon defined by the specified list of vertices is first filled in | ||
1745 | `fillcolour', if specified, and then outlined in `outlinecolour'. | ||
1746 | |||
1747 | `outlinecolour' may _not_ be -1; it must be a valid colour (and front | ||
1748 | ends are permitted to enforce this by assertion). This is because | ||
1749 | different platforms disagree on whether a filled polygon should include | ||
1750 | its boundary line or not, so drawing _only_ a filled polygon would | ||
1751 | have non-portable effects. If you want your filled polygon not to | ||
1752 | have a visible outline, you must set `outlinecolour' to the same as | ||
1753 | `fillcolour'. | ||
1754 | |||
1755 | Some platforms may perform anti-aliasing on this function. Therefore, do | ||
1756 | not assume that you can erase a polygon by drawing the same polygon over | ||
1757 | it in the background colour. Also, be prepared for the polygon to extend | ||
1758 | a pixel beyond its obvious bounding box as a result of this; if you | ||
1759 | really need it not to do this to avoid interfering with other delicate | ||
1760 | graphics, you should probably use clip() (section 3.1.9). You can rely | ||
1761 | on horizontal and vertical lines not being anti-aliased. | ||
1762 | |||
1763 | This function may be used for both drawing and printing. | ||
1764 | |||
1765 | #3.1.5. draw_circle() | ||
1766 | |||
1767 | void draw_circle(drawing *dr, int cx, int cy, int radius, | ||
1768 | int fillcolour, int outlinecolour); | ||
1769 | |||
1770 | Draws an outlined or filled circle in the puzzle window. | ||
1771 | |||
1772 | `cx' and `cy' give the coordinates of the centre of the circle. `radius' | ||
1773 | gives its radius. The total horizontal pixel extent of the circle is | ||
1774 | from `cx-radius+1' to `cx+radius-1' inclusive, and the vertical extent | ||
1775 | similarly around `cy'. | ||
1776 | |||
1777 | `fillcolour' and `outlinecolour' are integer indices into the colours | ||
1778 | array returned by the back end function colours() (section 2.8.6). | ||
1779 | `fillcolour' may also be -1 to indicate that the circle should be | ||
1780 | outlined only. | ||
1781 | |||
1782 | The circle is first filled in `fillcolour', if specified, and then | ||
1783 | outlined in `outlinecolour'. | ||
1784 | |||
1785 | `outlinecolour' may _not_ be -1; it must be a valid colour (and front | ||
1786 | ends are permitted to enforce this by assertion). This is because | ||
1787 | different platforms disagree on whether a filled circle should include | ||
1788 | its boundary line or not, so drawing _only_ a filled circle would | ||
1789 | have non-portable effects. If you want your filled circle not to | ||
1790 | have a visible outline, you must set `outlinecolour' to the same as | ||
1791 | `fillcolour'. | ||
1792 | |||
1793 | Some platforms may perform anti-aliasing on this function. Therefore, do | ||
1794 | not assume that you can erase a circle by drawing the same circle over | ||
1795 | it in the background colour. Also, be prepared for the circle to extend | ||
1796 | a pixel beyond its obvious bounding box as a result of this; if you | ||
1797 | really need it not to do this to avoid interfering with other delicate | ||
1798 | graphics, you should probably use clip() (section 3.1.9). | ||
1799 | |||
1800 | This function may be used for both drawing and printing. | ||
1801 | |||
1802 | #3.1.6. draw_thick_line() | ||
1803 | |||
1804 | void draw_thick_line(drawing *dr, float thickness, | ||
1805 | float x1, float y1, float x2, float y2, | ||
1806 | int colour) | ||
1807 | |||
1808 | Draws a line in the puzzle window, giving control over the line's | ||
1809 | thickness. | ||
1810 | |||
1811 | `x1' and `y1' give the coordinates of one end of the line. `x2' and `y2' | ||
1812 | give the coordinates of the other end. `thickness' gives the thickness | ||
1813 | of the line, in pixels. | ||
1814 | |||
1815 | Note that the coordinates and thickness are floating-point: the | ||
1816 | continuous coordinate system is in effect here. It's important to be | ||
1817 | able to address points with better-than-pixel precision in this case, | ||
1818 | because one can't otherwise properly express the endpoints of lines with | ||
1819 | both odd and even thicknesses. | ||
1820 | |||
1821 | Some platforms may perform anti-aliasing on this function. The precise | ||
1822 | pixels affected by a thick-line drawing operation may vary between | ||
1823 | platforms, and no particular guarantees are provided. Indeed, even | ||
1824 | horizontal or vertical lines may be anti-aliased. | ||
1825 | |||
1826 | This function may be used for both drawing and printing. | ||
1827 | |||
1828 | If the specified thickness is less than 1.0, 1.0 is used. This ensures | ||
1829 | that thin lines are visible even at small scales. | ||
1830 | |||
1831 | #3.1.7. draw_text() | ||
1832 | |||
1833 | void draw_text(drawing *dr, int x, int y, int fonttype, | ||
1834 | int fontsize, int align, int colour, | ||
1835 | const char *text); | ||
1836 | |||
1837 | Draws text in the puzzle window. | ||
1838 | |||
1839 | `x' and `y' give the coordinates of a point. The relation of this point | ||
1840 | to the location of the text is specified by `align', which is a bitwise | ||
1841 | OR of horizontal and vertical alignment flags: | ||
1842 | |||
1843 | ALIGN_VNORMAL | ||
1844 | |||
1845 | Indicates that `y' is aligned with the baseline of the text. | ||
1846 | |||
1847 | ALIGN_VCENTRE | ||
1848 | |||
1849 | Indicates that `y' is aligned with the vertical centre of the | ||
1850 | text. (In fact, it's aligned with the vertical centre of normal | ||
1851 | _capitalised_ text: displaying two pieces of text with ALIGN_VCENTRE | ||
1852 | at the same y-coordinate will cause their baselines to be aligned | ||
1853 | with one another, even if one is an ascender and the other a | ||
1854 | descender.) | ||
1855 | |||
1856 | ALIGN_HLEFT | ||
1857 | |||
1858 | Indicates that `x' is aligned with the left-hand end of the text. | ||
1859 | |||
1860 | ALIGN_HCENTRE | ||
1861 | |||
1862 | Indicates that `x' is aligned with the horizontal centre of the | ||
1863 | text. | ||
1864 | |||
1865 | ALIGN_HRIGHT | ||
1866 | |||
1867 | Indicates that `x' is aligned with the right-hand end of the text. | ||
1868 | |||
1869 | `fonttype' is either FONT_FIXED or FONT_VARIABLE, for a monospaced | ||
1870 | or proportional font respectively. (No more detail than that may be | ||
1871 | specified; it would only lead to portability issues between different | ||
1872 | platforms.) | ||
1873 | |||
1874 | `fontsize' is the desired size, in pixels, of the text. This size | ||
1875 | corresponds to the overall point size of the text, not to any internal | ||
1876 | dimension such as the cap-height. | ||
1877 | |||
1878 | `colour' is an integer index into the colours array returned by the back | ||
1879 | end function colours() (section 2.8.6). | ||
1880 | |||
1881 | This function may be used for both drawing and printing. | ||
1882 | |||
1883 | The character set used to encode the text passed to this function is | ||
1884 | specified _by the drawing object_, although it must be a superset of | ||
1885 | ASCII. If a puzzle wants to display text that is not contained in ASCII, | ||
1886 | it should use the text_fallback() function (section 3.1.8) to query the | ||
1887 | drawing object for an appropriate representation of the characters it | ||
1888 | wants. | ||
1889 | |||
1890 | #3.1.8. text_fallback() | ||
1891 | |||
1892 | char *text_fallback(drawing *dr, const char *const *strings, | ||
1893 | int nstrings); | ||
1894 | |||
1895 | This function is used to request a translation of UTF-8 text into | ||
1896 | whatever character encoding is expected by the drawing object's | ||
1897 | implementation of draw_text(). | ||
1898 | |||
1899 | The input is a list of strings encoded in UTF-8: nstrings gives the | ||
1900 | number of strings in the list, and strings[0], strings[1], ..., | ||
1901 | strings[nstrings-1] are the strings themselves. | ||
1902 | |||
1903 | The returned string (which is dynamically allocated and must be freed | ||
1904 | when finished with) is derived from the first string in the list that | ||
1905 | the drawing object expects to be able to display reliably; it will | ||
1906 | consist of that string translated into the character set expected by | ||
1907 | draw_text(). | ||
1908 | |||
1909 | Drawing implementations are not required to handle anything outside | ||
1910 | ASCII, but are permitted to assume that _some_ string will be | ||
1911 | successfully translated. So every call to this function must include | ||
1912 | a string somewhere in the list (presumably the last element) which | ||
1913 | consists of nothing but ASCII, to be used by any front end which cannot | ||
1914 | handle anything else. | ||
1915 | |||
1916 | For example, if a puzzle wished to display a string including a | ||
1917 | multiplication sign (U+00D7 in Unicode, represented by the bytes C3 97 | ||
1918 | in UTF-8), it might do something like this: | ||
1919 | |||
1920 | static const char *const times_signs[] = { "\xC3\x97", "x" }; | ||
1921 | char *times_sign = text_fallback(dr, times_signs, 2); | ||
1922 | sprintf(buffer, "%d%s%d", width, times_sign, height); | ||
1923 | draw_text(dr, x, y, font, size, align, colour, buffer); | ||
1924 | sfree(buffer); | ||
1925 | |||
1926 | which would draw a string with a times sign in the middle on platforms | ||
1927 | that support it, and fall back to a simple ASCII `x' where there was no | ||
1928 | alternative. | ||
1929 | |||
1930 | #3.1.9. clip() | ||
1931 | |||
1932 | void clip(drawing *dr, int x, int y, int w, int h); | ||
1933 | |||
1934 | Establishes a clipping rectangle in the puzzle window. | ||
1935 | |||
1936 | `x' and `y' give the coordinates of the top left pixel of the clipping | ||
1937 | rectangle. `w' and `h' give its width and height. Thus, the horizontal | ||
1938 | extent of the rectangle runs from `x' to `x+w-1' inclusive, and the | ||
1939 | vertical extent from `y' to `y+h-1' inclusive. (These are exactly the | ||
1940 | same semantics as draw_rect().) | ||
1941 | |||
1942 | After this call, no drawing operation will affect anything outside the | ||
1943 | specified rectangle. The effect can be reversed by calling unclip() | ||
1944 | (section 3.1.10). The clipping rectangle is pixel-perfect: pixels within | ||
1945 | the rectangle are affected as usual by drawing functions; pixels outside | ||
1946 | are completely untouched. | ||
1947 | |||
1948 | Back ends should not assume that a clipping rectangle will be | ||
1949 | automatically cleared up by the front end if it's left lying around; | ||
1950 | that might work on current front ends, but shouldn't be relied upon. | ||
1951 | Always explicitly call unclip(). | ||
1952 | |||
1953 | This function may be used for both drawing and printing. | ||
1954 | |||
1955 | #3.1.10. unclip() | ||
1956 | |||
1957 | void unclip(drawing *dr); | ||
1958 | |||
1959 | Reverts the effect of a previous call to clip(). After this call, all | ||
1960 | drawing operations will be able to affect the entire puzzle window | ||
1961 | again. | ||
1962 | |||
1963 | This function may be used for both drawing and printing. | ||
1964 | |||
1965 | #3.1.11. draw_update() | ||
1966 | |||
1967 | void draw_update(drawing *dr, int x, int y, int w, int h); | ||
1968 | |||
1969 | Informs the front end that a rectangular portion of the puzzle window | ||
1970 | has been drawn on and needs to be updated. | ||
1971 | |||
1972 | `x' and `y' give the coordinates of the top left pixel of the update | ||
1973 | rectangle. `w' and `h' give its width and height. Thus, the horizontal | ||
1974 | extent of the rectangle runs from `x' to `x+w-1' inclusive, and the | ||
1975 | vertical extent from `y' to `y+h-1' inclusive. (These are exactly the | ||
1976 | same semantics as draw_rect().) | ||
1977 | |||
1978 | The back end redraw function _must_ call this function to report any | ||
1979 | changes it has made to the window. Otherwise, those changes may not | ||
1980 | become immediately visible, and may then appear at an unpredictable | ||
1981 | subsequent time such as the next time the window is covered and re- | ||
1982 | exposed. | ||
1983 | |||
1984 | This function is only important when drawing. It may be called when | ||
1985 | printing as well, but doing so is not compulsory, and has no effect. | ||
1986 | (So if you have a shared piece of code between the drawing and printing | ||
1987 | routines, that code may safely call draw_update().) | ||
1988 | |||
1989 | #3.1.12. status_bar() | ||
1990 | |||
1991 | void status_bar(drawing *dr, const char *text); | ||
1992 | |||
1993 | Sets the text in the game's status bar to `text'. The text is copied | ||
1994 | from the supplied buffer, so the caller is free to deallocate or modify | ||
1995 | the buffer after use. | ||
1996 | |||
1997 | (This function is not exactly a _drawing_ function, but it shares with | ||
1998 | the drawing API the property that it may only be called from within the | ||
1999 | back end redraw function, so this is as good a place as any to document | ||
2000 | it.) | ||
2001 | |||
2002 | The supplied text is filtered through the mid-end for optional rewriting | ||
2003 | before being passed on to the front end; the mid-end will prepend the | ||
2004 | current game time if the game is timed (and may in future perform other | ||
2005 | rewriting if it seems like a good idea). | ||
2006 | |||
2007 | This function is for drawing only; it must never be called during | ||
2008 | printing. | ||
2009 | |||
2010 | #3.1.13. Blitter functions | ||
2011 | |||
2012 | This section describes a group of related functions which save and | ||
2013 | restore a section of the puzzle window. This is most commonly used to | ||
2014 | implement user interfaces involving dragging a puzzle element around the | ||
2015 | window: at the end of each call to redraw(), if an object is currently | ||
2016 | being dragged, the back end saves the window contents under that | ||
2017 | location and then draws the dragged object, and at the start of the next | ||
2018 | redraw() the first thing it does is to restore the background. | ||
2019 | |||
2020 | The front end defines an opaque type called a `blitter', which is | ||
2021 | capable of storing a rectangular area of a specified size. | ||
2022 | |||
2023 | Blitter functions are for drawing only; they must never be called during | ||
2024 | printing. | ||
2025 | |||
2026 | #3.1.13.1. blitter_new() | ||
2027 | |||
2028 | blitter *blitter_new(drawing *dr, int w, int h); | ||
2029 | |||
2030 | Creates a new blitter object which stores a rectangle of size `w' by `h' | ||
2031 | pixels. Returns a pointer to the blitter object. | ||
2032 | |||
2033 | Blitter objects are best stored in the `game_drawstate'. A good time to | ||
2034 | create them is in the set_size() function (section 2.8.5), since it is | ||
2035 | at this point that you first know how big a rectangle they will need to | ||
2036 | save. | ||
2037 | |||
2038 | #3.1.13.2. blitter_free() | ||
2039 | |||
2040 | void blitter_free(drawing *dr, blitter *bl); | ||
2041 | |||
2042 | Disposes of a blitter object. Best called in free_drawstate(). (However, | ||
2043 | check that the blitter object is not NULL before attempting to free it; | ||
2044 | it is possible that a draw state might be created and freed without ever | ||
2045 | having set_size() called on it in between.) | ||
2046 | |||
2047 | #3.1.13.3. blitter_save() | ||
2048 | |||
2049 | void blitter_save(drawing *dr, blitter *bl, int x, int y); | ||
2050 | |||
2051 | This is a true drawing API function, in that it may only be called from | ||
2052 | within the game redraw routine. It saves a rectangular portion of the | ||
2053 | puzzle window into the specified blitter object. | ||
2054 | |||
2055 | `x' and `y' give the coordinates of the top left corner of the saved | ||
2056 | rectangle. The rectangle's width and height are the ones specified when | ||
2057 | the blitter object was created. | ||
2058 | |||
2059 | This function is required to cope and do the right thing if `x' and `y' | ||
2060 | are out of range. (The right thing probably means saving whatever part | ||
2061 | of the blitter rectangle overlaps with the visible area of the puzzle | ||
2062 | window.) | ||
2063 | |||
2064 | #3.1.13.4. blitter_load() | ||
2065 | |||
2066 | void blitter_load(drawing *dr, blitter *bl, int x, int y); | ||
2067 | |||
2068 | This is a true drawing API function, in that it may only be called from | ||
2069 | within the game redraw routine. It restores a rectangular portion of the | ||
2070 | puzzle window from the specified blitter object. | ||
2071 | |||
2072 | `x' and `y' give the coordinates of the top left corner of the rectangle | ||
2073 | to be restored. The rectangle's width and height are the ones specified | ||
2074 | when the blitter object was created. | ||
2075 | |||
2076 | Alternatively, you can specify both `x' and `y' as the special value | ||
2077 | BLITTER_FROMSAVED, in which case the rectangle will be restored to | ||
2078 | exactly where it was saved from. (This is probably what you want to do | ||
2079 | almost all the time, if you're using blitters to implement draggable | ||
2080 | puzzle elements.) | ||
2081 | |||
2082 | This function is required to cope and do the right thing if `x' and | ||
2083 | `y' (or the equivalent ones saved in the blitter) are out of range. | ||
2084 | (The right thing probably means restoring whatever part of the blitter | ||
2085 | rectangle overlaps with the visible area of the puzzle window.) | ||
2086 | |||
2087 | If this function is called on a blitter which had previously been saved | ||
2088 | from a partially out-of-range rectangle, then the parts of the saved | ||
2089 | bitmap which were not visible at save time are undefined. If the blitter | ||
2090 | is restored to a different position so as to make those parts visible, | ||
2091 | the effect on the drawing area is undefined. | ||
2092 | |||
2093 | #3.1.14. print_mono_colour() | ||
2094 | |||
2095 | int print_mono_colour(drawing *dr, int grey); | ||
2096 | |||
2097 | This function allocates a colour index for a simple monochrome colour | ||
2098 | during printing. | ||
2099 | |||
2100 | `grey' must be 0 or 1. If `grey' is 0, the colour returned is black; if | ||
2101 | `grey' is 1, the colour is white. | ||
2102 | |||
2103 | #3.1.15. print_grey_colour() | ||
2104 | |||
2105 | int print_grey_colour(drawing *dr, float grey); | ||
2106 | |||
2107 | This function allocates a colour index for a grey-scale colour during | ||
2108 | printing. | ||
2109 | |||
2110 | `grey' may be any number between 0 (black) and 1 (white); for example, | ||
2111 | 0.5 indicates a medium grey. | ||
2112 | |||
2113 | The chosen colour will be rendered to the limits of the printer's | ||
2114 | halftoning capability. | ||
2115 | |||
2116 | #3.1.16. print_hatched_colour() | ||
2117 | |||
2118 | int print_hatched_colour(drawing *dr, int hatch); | ||
2119 | |||
2120 | This function allocates a colour index which does not represent a | ||
2121 | literal _colour_. Instead, regions shaded in this colour will be hatched | ||
2122 | with parallel lines. The `hatch' parameter defines what type of hatching | ||
2123 | should be used in place of this colour: | ||
2124 | |||
2125 | HATCH_SLASH | ||
2126 | |||
2127 | This colour will be hatched by lines slanting to the right at 45 | ||
2128 | degrees. | ||
2129 | |||
2130 | HATCH_BACKSLASH | ||
2131 | |||
2132 | This colour will be hatched by lines slanting to the left at 45 | ||
2133 | degrees. | ||
2134 | |||
2135 | HATCH_HORIZ | ||
2136 | |||
2137 | This colour will be hatched by horizontal lines. | ||
2138 | |||
2139 | HATCH_VERT | ||
2140 | |||
2141 | This colour will be hatched by vertical lines. | ||
2142 | |||
2143 | HATCH_PLUS | ||
2144 | |||
2145 | This colour will be hatched by criss-crossing horizontal and | ||
2146 | vertical lines. | ||
2147 | |||
2148 | HATCH_X | ||
2149 | |||
2150 | This colour will be hatched by criss-crossing diagonal lines. | ||
2151 | |||
2152 | Colours defined to use hatching may not be used for drawing lines or | ||
2153 | text; they may only be used for filling areas. That is, they may be | ||
2154 | used as the `fillcolour' parameter to draw_circle() and draw_polygon(), | ||
2155 | and as the colour parameter to draw_rect(), but may not be used as the | ||
2156 | `outlinecolour' parameter to draw_circle() or draw_polygon(), or with | ||
2157 | draw_line() or draw_text(). | ||
2158 | |||
2159 | #3.1.17. print_rgb_mono_colour() | ||
2160 | |||
2161 | int print_rgb_mono_colour(drawing *dr, float r, float g, | ||
2162 | float b, float grey); | ||
2163 | |||
2164 | This function allocates a colour index for a fully specified RGB colour | ||
2165 | during printing. | ||
2166 | |||
2167 | `r', `g' and `b' may each be anywhere in the range from 0 to 1. | ||
2168 | |||
2169 | If printing in black and white only, these values will be ignored, and | ||
2170 | either pure black or pure white will be used instead, according to the | ||
2171 | `grey' parameter. (The fallback colour is the same as the one which | ||
2172 | would be allocated by print_mono_colour(grey).) | ||
2173 | |||
2174 | #3.1.18. print_rgb_grey_colour() | ||
2175 | |||
2176 | int print_rgb_grey_colour(drawing *dr, float r, float g, | ||
2177 | float b, float grey); | ||
2178 | |||
2179 | This function allocates a colour index for a fully specified RGB colour | ||
2180 | during printing. | ||
2181 | |||
2182 | `r', `g' and `b' may each be anywhere in the range from 0 to 1. | ||
2183 | |||
2184 | If printing in black and white only, these values will be ignored, and | ||
2185 | a shade of grey given by the `grey' parameter will be used instead. | ||
2186 | (The fallback colour is the same as the one which would be allocated by | ||
2187 | print_grey_colour(grey).) | ||
2188 | |||
2189 | #3.1.19. print_rgb_hatched_colour() | ||
2190 | |||
2191 | int print_rgb_hatched_colour(drawing *dr, float r, float g, | ||
2192 | float b, float hatched); | ||
2193 | |||
2194 | This function allocates a colour index for a fully specified RGB colour | ||
2195 | during printing. | ||
2196 | |||
2197 | `r', `g' and `b' may each be anywhere in the range from 0 to 1. | ||
2198 | |||
2199 | If printing in black and white only, these values will be ignored, and | ||
2200 | a form of cross-hatching given by the `hatch' parameter will be used | ||
2201 | instead; see section 3.1.16 for the possible values of this parameter. | ||
2202 | (The fallback colour is the same as the one which would be allocated by | ||
2203 | print_hatched_colour(hatch).) | ||
2204 | |||
2205 | #3.1.20. print_line_width() | ||
2206 | |||
2207 | void print_line_width(drawing *dr, int width); | ||
2208 | |||
2209 | This function is called to set the thickness of lines drawn during | ||
2210 | printing. It is meaningless in drawing: all lines drawn by draw_line(), | ||
2211 | draw_circle and draw_polygon() are one pixel in thickness. However, in | ||
2212 | printing there is no clear definition of a pixel and so line widths must | ||
2213 | be explicitly specified. | ||
2214 | |||
2215 | The line width is specified in the usual coordinate system. Note, | ||
2216 | however, that it is a hint only: the central printing system may choose | ||
2217 | to vary line thicknesses at user request or due to printer capabilities. | ||
2218 | |||
2219 | #3.1.21. print_line_dotted() | ||
2220 | |||
2221 | void print_line_dotted(drawing *dr, int dotted); | ||
2222 | |||
2223 | This function is called to toggle the drawing of dotted lines during | ||
2224 | printing. It is not supported during drawing. | ||
2225 | |||
2226 | The parameter `dotted' is a boolean; TRUE means that future lines drawn | ||
2227 | by draw_line(), draw_circle and draw_polygon() will be dotted, and FALSE | ||
2228 | means that they will be solid. | ||
2229 | |||
2230 | Some front ends may impose restrictions on the width of dotted lines. | ||
2231 | Asking for a dotted line via this front end will override any line width | ||
2232 | request if the front end requires it. | ||
2233 | |||
2234 | #3.2. The drawing API as implemented by the front end | ||
2235 | |||
2236 | This section describes the drawing API in the function-pointer form in | ||
2237 | which it is implemented by a front end. | ||
2238 | |||
2239 | (It isn't only platform-specific front ends which implement this API; | ||
2240 | the platform-independent module `ps.c' also provides an implementation | ||
2241 | of it which outputs PostScript. Thus, any platform which wants to do PS | ||
2242 | printing can do so with minimum fuss.) | ||
2243 | |||
2244 | The following entries all describe function pointer fields in a | ||
2245 | structure called `drawing_api'. Each of the functions takes a `void *' | ||
2246 | context pointer, which it should internally cast back to a more useful | ||
2247 | type. Thus, a drawing _object_ (`drawing *)' suitable for passing to | ||
2248 | the back end redraw or printing functions is constructed by passing a | ||
2249 | `drawing_api' and a `void *' to the function drawing_new() (see section | ||
2250 | 3.3.1). | ||
2251 | |||
2252 | #3.2.1. draw_text() | ||
2253 | |||
2254 | void (*draw_text)(void *handle, int x, int y, int fonttype, | ||
2255 | int fontsize, int align, int colour, | ||
2256 | const char *text); | ||
2257 | |||
2258 | This function behaves exactly like the back end draw_text() function; | ||
2259 | see section 3.1.7. | ||
2260 | |||
2261 | #3.2.2. draw_rect() | ||
2262 | |||
2263 | void (*draw_rect)(void *handle, int x, int y, int w, int h, | ||
2264 | int colour); | ||
2265 | |||
2266 | This function behaves exactly like the back end draw_rect() function; | ||
2267 | see section 3.1.1. | ||
2268 | |||
2269 | #3.2.3. draw_line() | ||
2270 | |||
2271 | void (*draw_line)(void *handle, int x1, int y1, int x2, int y2, | ||
2272 | int colour); | ||
2273 | |||
2274 | This function behaves exactly like the back end draw_line() function; | ||
2275 | see section 3.1.3. | ||
2276 | |||
2277 | #3.2.4. draw_polygon() | ||
2278 | |||
2279 | void (*draw_polygon)(void *handle, int *coords, int npoints, | ||
2280 | int fillcolour, int outlinecolour); | ||
2281 | |||
2282 | This function behaves exactly like the back end draw_polygon() function; | ||
2283 | see section 3.1.4. | ||
2284 | |||
2285 | #3.2.5. draw_circle() | ||
2286 | |||
2287 | void (*draw_circle)(void *handle, int cx, int cy, int radius, | ||
2288 | int fillcolour, int outlinecolour); | ||
2289 | |||
2290 | This function behaves exactly like the back end draw_circle() function; | ||
2291 | see section 3.1.5. | ||
2292 | |||
2293 | #3.2.6. draw_thick_line() | ||
2294 | |||
2295 | void draw_thick_line(drawing *dr, float thickness, | ||
2296 | float x1, float y1, float x2, float y2, | ||
2297 | int colour) | ||
2298 | |||
2299 | This function behaves exactly like the back end draw_thick_line() | ||
2300 | function; see section 3.1.6. | ||
2301 | |||
2302 | An implementation of this API which doesn't provide high-quality | ||
2303 | rendering of thick lines is permitted to define this function pointer | ||
2304 | to be NULL. The middleware in drawing.c will notice and provide a low- | ||
2305 | quality alternative using draw_polygon(). | ||
2306 | |||
2307 | #3.2.7. draw_update() | ||
2308 | |||
2309 | void (*draw_update)(void *handle, int x, int y, int w, int h); | ||
2310 | |||
2311 | This function behaves exactly like the back end draw_update() function; | ||
2312 | see section 3.1.11. | ||
2313 | |||
2314 | An implementation of this API which only supports printing is permitted | ||
2315 | to define this function pointer to be NULL rather than bothering to | ||
2316 | define an empty function. The middleware in drawing.c will notice and | ||
2317 | avoid calling it. | ||
2318 | |||
2319 | #3.2.8. clip() | ||
2320 | |||
2321 | void (*clip)(void *handle, int x, int y, int w, int h); | ||
2322 | |||
2323 | This function behaves exactly like the back end clip() function; see | ||
2324 | section 3.1.9. | ||
2325 | |||
2326 | #3.2.9. unclip() | ||
2327 | |||
2328 | void (*unclip)(void *handle); | ||
2329 | |||
2330 | This function behaves exactly like the back end unclip() function; see | ||
2331 | section 3.1.10. | ||
2332 | |||
2333 | #3.2.10. start_draw() | ||
2334 | |||
2335 | void (*start_draw)(void *handle); | ||
2336 | |||
2337 | This function is called at the start of drawing. It allows the front end | ||
2338 | to initialise any temporary data required to draw with, such as device | ||
2339 | contexts. | ||
2340 | |||
2341 | Implementations of this API which do not provide drawing services may | ||
2342 | define this function pointer to be NULL; it will never be called unless | ||
2343 | drawing is attempted. | ||
2344 | |||
2345 | #3.2.11. end_draw() | ||
2346 | |||
2347 | void (*end_draw)(void *handle); | ||
2348 | |||
2349 | This function is called at the end of drawing. It allows the front end | ||
2350 | to do cleanup tasks such as deallocating device contexts and scheduling | ||
2351 | appropriate GUI redraw events. | ||
2352 | |||
2353 | Implementations of this API which do not provide drawing services may | ||
2354 | define this function pointer to be NULL; it will never be called unless | ||
2355 | drawing is attempted. | ||
2356 | |||
2357 | #3.2.12. status_bar() | ||
2358 | |||
2359 | void (*status_bar)(void *handle, const char *text); | ||
2360 | |||
2361 | This function behaves exactly like the back end status_bar() function; | ||
2362 | see section 3.1.12. | ||
2363 | |||
2364 | Front ends implementing this function need not worry about it | ||
2365 | being called repeatedly with the same text; the middleware code in | ||
2366 | status_bar() will take care of this. | ||
2367 | |||
2368 | Implementations of this API which do not provide drawing services may | ||
2369 | define this function pointer to be NULL; it will never be called unless | ||
2370 | drawing is attempted. | ||
2371 | |||
2372 | #3.2.13. blitter_new() | ||
2373 | |||
2374 | blitter *(*blitter_new)(void *handle, int w, int h); | ||
2375 | |||
2376 | This function behaves exactly like the back end blitter_new() function; | ||
2377 | see section 3.1.13.1. | ||
2378 | |||
2379 | Implementations of this API which do not provide drawing services may | ||
2380 | define this function pointer to be NULL; it will never be called unless | ||
2381 | drawing is attempted. | ||
2382 | |||
2383 | #3.2.14. blitter_free() | ||
2384 | |||
2385 | void (*blitter_free)(void *handle, blitter *bl); | ||
2386 | |||
2387 | This function behaves exactly like the back end blitter_free() function; | ||
2388 | see section 3.1.13.2. | ||
2389 | |||
2390 | Implementations of this API which do not provide drawing services may | ||
2391 | define this function pointer to be NULL; it will never be called unless | ||
2392 | drawing is attempted. | ||
2393 | |||
2394 | #3.2.15. blitter_save() | ||
2395 | |||
2396 | void (*blitter_save)(void *handle, blitter *bl, int x, int y); | ||
2397 | |||
2398 | This function behaves exactly like the back end blitter_save() function; | ||
2399 | see section 3.1.13.3. | ||
2400 | |||
2401 | Implementations of this API which do not provide drawing services may | ||
2402 | define this function pointer to be NULL; it will never be called unless | ||
2403 | drawing is attempted. | ||
2404 | |||
2405 | #3.2.16. blitter_load() | ||
2406 | |||
2407 | void (*blitter_load)(void *handle, blitter *bl, int x, int y); | ||
2408 | |||
2409 | This function behaves exactly like the back end blitter_load() function; | ||
2410 | see section 3.1.13.4. | ||
2411 | |||
2412 | Implementations of this API which do not provide drawing services may | ||
2413 | define this function pointer to be NULL; it will never be called unless | ||
2414 | drawing is attempted. | ||
2415 | |||
2416 | #3.2.17. begin_doc() | ||
2417 | |||
2418 | void (*begin_doc)(void *handle, int pages); | ||
2419 | |||
2420 | This function is called at the beginning of a printing run. It gives the | ||
2421 | front end an opportunity to initialise any required printing subsystem. | ||
2422 | It also provides the number of pages in advance. | ||
2423 | |||
2424 | Implementations of this API which do not provide printing services may | ||
2425 | define this function pointer to be NULL; it will never be called unless | ||
2426 | printing is attempted. | ||
2427 | |||
2428 | #3.2.18. begin_page() | ||
2429 | |||
2430 | void (*begin_page)(void *handle, int number); | ||
2431 | |||
2432 | This function is called during printing, at the beginning of each page. | ||
2433 | It gives the page number (numbered from 1 rather than 0, so suitable for | ||
2434 | use in user-visible contexts). | ||
2435 | |||
2436 | Implementations of this API which do not provide printing services may | ||
2437 | define this function pointer to be NULL; it will never be called unless | ||
2438 | printing is attempted. | ||
2439 | |||
2440 | #3.2.19. begin_puzzle() | ||
2441 | |||
2442 | void (*begin_puzzle)(void *handle, float xm, float xc, | ||
2443 | float ym, float yc, int pw, int ph, float wmm); | ||
2444 | |||
2445 | This function is called during printing, just before printing a single | ||
2446 | puzzle on a page. It specifies the size and location of the puzzle on | ||
2447 | the page. | ||
2448 | |||
2449 | `xm' and `xc' specify the horizontal position of the puzzle on the page, | ||
2450 | as a linear function of the page width. The front end is expected to | ||
2451 | multiply the page width by `xm', add `xc' (measured in millimetres), and | ||
2452 | use the resulting x-coordinate as the left edge of the puzzle. | ||
2453 | |||
2454 | Similarly, `ym' and `yc' specify the vertical position of the puzzle as | ||
2455 | a function of the page height: the page height times `ym', plus `yc' | ||
2456 | millimetres, equals the desired distance from the top of the page to the | ||
2457 | top of the puzzle. | ||
2458 | |||
2459 | (This unwieldy mechanism is required because not all printing systems | ||
2460 | can communicate the page size back to the software. The PostScript back | ||
2461 | end, for example, writes out PS which determines the page size at print | ||
2462 | time by means of calling `clippath', and centres the puzzles within | ||
2463 | that. Thus, exactly the same PS file works on A4 or on US Letter paper | ||
2464 | without needing local configuration, which simplifies matters.) | ||
2465 | |||
2466 | pw and ph give the size of the puzzle in drawing API coordinates. The | ||
2467 | printing system will subsequently call the puzzle's own print function, | ||
2468 | which will in turn call drawing API functions in the expectation that an | ||
2469 | area pw by ph units is available to draw the puzzle on. | ||
2470 | |||
2471 | Finally, wmm gives the desired width of the puzzle in millimetres. (The | ||
2472 | aspect ratio is expected to be preserved, so if the desired puzzle | ||
2473 | height is also needed then it can be computed as wmm*ph/pw.) | ||
2474 | |||
2475 | Implementations of this API which do not provide printing services may | ||
2476 | define this function pointer to be NULL; it will never be called unless | ||
2477 | printing is attempted. | ||
2478 | |||
2479 | #3.2.20. end_puzzle() | ||
2480 | |||
2481 | void (*end_puzzle)(void *handle); | ||
2482 | |||
2483 | This function is called after the printing of a specific puzzle is | ||
2484 | complete. | ||
2485 | |||
2486 | Implementations of this API which do not provide printing services may | ||
2487 | define this function pointer to be NULL; it will never be called unless | ||
2488 | printing is attempted. | ||
2489 | |||
2490 | #3.2.21. end_page() | ||
2491 | |||
2492 | void (*end_page)(void *handle, int number); | ||
2493 | |||
2494 | This function is called after the printing of a page is finished. | ||
2495 | |||
2496 | Implementations of this API which do not provide printing services may | ||
2497 | define this function pointer to be NULL; it will never be called unless | ||
2498 | printing is attempted. | ||
2499 | |||
2500 | #3.2.22. end_doc() | ||
2501 | |||
2502 | void (*end_doc)(void *handle); | ||
2503 | |||
2504 | This function is called after the printing of the entire document is | ||
2505 | finished. This is the moment to close files, send things to the print | ||
2506 | spooler, or whatever the local convention is. | ||
2507 | |||
2508 | Implementations of this API which do not provide printing services may | ||
2509 | define this function pointer to be NULL; it will never be called unless | ||
2510 | printing is attempted. | ||
2511 | |||
2512 | #3.2.23. line_width() | ||
2513 | |||
2514 | void (*line_width)(void *handle, float width); | ||
2515 | |||
2516 | This function is called to set the line thickness, during printing only. | ||
2517 | Note that the width is a float here, where it was an int as seen by the | ||
2518 | back end. This is because drawing.c may have scaled it on the way past. | ||
2519 | |||
2520 | However, the width is still specified in the same coordinate system as | ||
2521 | the rest of the drawing. | ||
2522 | |||
2523 | Implementations of this API which do not provide printing services may | ||
2524 | define this function pointer to be NULL; it will never be called unless | ||
2525 | printing is attempted. | ||
2526 | |||
2527 | #3.2.24. text_fallback() | ||
2528 | |||
2529 | char *(*text_fallback)(void *handle, const char *const *strings, | ||
2530 | int nstrings); | ||
2531 | |||
2532 | This function behaves exactly like the back end text_fallback() | ||
2533 | function; see section 3.1.8. | ||
2534 | |||
2535 | Implementations of this API which do not support any characters outside | ||
2536 | ASCII may define this function pointer to be NULL, in which case the | ||
2537 | central code in drawing.c will provide a default implementation. | ||
2538 | |||
2539 | #3.3. The drawing API as called by the front end | ||
2540 | |||
2541 | There are a small number of functions provided in drawing.c which the | ||
2542 | front end needs to _call_, rather than helping to implement. They are | ||
2543 | described in this section. | ||
2544 | |||
2545 | #3.3.1. drawing_new() | ||
2546 | |||
2547 | drawing *drawing_new(const drawing_api *api, midend *me, | ||
2548 | void *handle); | ||
2549 | |||
2550 | This function creates a drawing object. It is passed a `drawing_api', | ||
2551 | which is a structure containing nothing but function pointers; and also | ||
2552 | a `void *' handle. The handle is passed back to each function pointer | ||
2553 | when it is called. | ||
2554 | |||
2555 | The `midend' parameter is used for rewriting the status bar contents: | ||
2556 | status_bar() (see section 3.1.12) has to call a function in the mid- | ||
2557 | end which might rewrite the status bar text. If the drawing object | ||
2558 | is to be used only for printing, or if the game is known not to call | ||
2559 | status_bar(), this parameter may be NULL. | ||
2560 | |||
2561 | #3.3.2. drawing_free() | ||
2562 | |||
2563 | void drawing_free(drawing *dr); | ||
2564 | |||
2565 | This function frees a drawing object. Note that the `void *' handle is | ||
2566 | not freed; if that needs cleaning up it must be done by the front end. | ||
2567 | |||
2568 | #3.3.3. print_get_colour() | ||
2569 | |||
2570 | void print_get_colour(drawing *dr, int colour, int printincolour, | ||
2571 | int *hatch, float *r, float *g, float *b) | ||
2572 | |||
2573 | This function is called by the implementations of the drawing API | ||
2574 | functions when they are called in a printing context. It takes a colour | ||
2575 | index as input, and returns the description of the colour as requested | ||
2576 | by the back end. | ||
2577 | |||
2578 | `printincolour' is TRUE iff the implementation is printing in colour. | ||
2579 | This will alter the results returned if the colour in question was | ||
2580 | specified with a black-and-white fallback value. | ||
2581 | |||
2582 | If the colour should be rendered by hatching, `*hatch' is filled with | ||
2583 | the type of hatching desired. See section 3.1.15 for details of the | ||
2584 | values this integer can take. | ||
2585 | |||
2586 | If the colour should be rendered as solid colour, `*hatch' is given a | ||
2587 | negative value, and `*r', `*g' and `*b' are filled with the RGB values | ||
2588 | of the desired colour (if printing in colour), or all filled with the | ||
2589 | grey-scale value (if printing in black and white). | ||
2590 | |||
2591 | #4. The API provided by the mid-end | ||
2592 | |||
2593 | This chapter documents the API provided by the mid-end to be called by | ||
2594 | the front end. You probably only need to read this if you are a front | ||
2595 | end implementor, i.e. you are porting Puzzles to a new platform. If | ||
2596 | you're only interested in writing new puzzles, you can safely skip this | ||
2597 | chapter. | ||
2598 | |||
2599 | All the persistent state in the mid-end is encapsulated within a | ||
2600 | `midend' structure, to facilitate having multiple mid-ends in any | ||
2601 | port which supports multiple puzzle windows open simultaneously. Each | ||
2602 | `midend' is intended to handle the contents of a single puzzle window. | ||
2603 | |||
2604 | #4.1. midend_new() | ||
2605 | |||
2606 | midend *midend_new(frontend *fe, const game *ourgame, | ||
2607 | const drawing_api *drapi, void *drhandle) | ||
2608 | |||
2609 | Allocates and returns a new mid-end structure. | ||
2610 | |||
2611 | The `fe' argument is stored in the mid-end. It will be used when calling | ||
2612 | back to functions such as activate_timer() (section 4.36), and will be | ||
2613 | passed on to the back end function colours() (section 2.8.6). | ||
2614 | |||
2615 | The parameters `drapi' and `drhandle' are passed to drawing_new() | ||
2616 | (section 3.3.1) to construct a drawing object which will be passed to | ||
2617 | the back end function redraw() (section 2.8.10). Hence, all drawing- | ||
2618 | related function pointers defined in `drapi' can expect to be called | ||
2619 | with `drhandle' as their first argument. | ||
2620 | |||
2621 | The `ourgame' argument points to a container structure describing a game | ||
2622 | back end. The mid-end thus created will only be capable of handling that | ||
2623 | one game. (So even in a monolithic front end containing all the games, | ||
2624 | this imposes the constraint that any individual puzzle window is tied to | ||
2625 | a single game. Unless, of course, you feel brave enough to change the | ||
2626 | mid-end for the window without closing the window...) | ||
2627 | |||
2628 | #4.2. midend_free() | ||
2629 | |||
2630 | void midend_free(midend *me); | ||
2631 | |||
2632 | Frees a mid-end structure and all its associated data. | ||
2633 | |||
2634 | #4.3. midend_tilesize() | ||
2635 | |||
2636 | int midend_tilesize(midend *me); | ||
2637 | |||
2638 | Returns the `tilesize' parameter being used to display the current | ||
2639 | puzzle (section 2.8.3). | ||
2640 | |||
2641 | #4.4. midend_set_params() | ||
2642 | |||
2643 | void midend_set_params(midend *me, game_params *params); | ||
2644 | |||
2645 | Sets the current game parameters for a mid-end. Subsequent games | ||
2646 | generated by midend_new_game() (section 4.8) will use these parameters | ||
2647 | until further notice. | ||
2648 | |||
2649 | The usual way in which the front end will have an actual `game_params' | ||
2650 | structure to pass to this function is if it had previously got it from | ||
2651 | midend_get_presets() (section 4.15). Thus, this function is usually | ||
2652 | called in response to the user making a selection from the presets menu. | ||
2653 | |||
2654 | #4.5. midend_get_params() | ||
2655 | |||
2656 | game_params *midend_get_params(midend *me); | ||
2657 | |||
2658 | Returns the current game parameters stored in this mid-end. | ||
2659 | |||
2660 | The returned value is dynamically allocated, and should be freed when | ||
2661 | finished with by passing it to the game's own free_params() function | ||
2662 | (see section 2.3.6). | ||
2663 | |||
2664 | #4.6. midend_size() | ||
2665 | |||
2666 | void midend_size(midend *me, int *x, int *y, int user_size); | ||
2667 | |||
2668 | Tells the mid-end to figure out its window size. | ||
2669 | |||
2670 | On input, `*x' and `*y' should contain the maximum or requested size | ||
2671 | for the window. (Typically this will be the size of the screen that the | ||
2672 | window has to fit on, or similar.) The mid-end will repeatedly call the | ||
2673 | back end function compute_size() (section 2.8.4), searching for a tile | ||
2674 | size that best satisfies the requirements. On exit, `*x' and `*y' will | ||
2675 | contain the size needed for the puzzle window's drawing area. (It is | ||
2676 | of course up to the front end to adjust this for any additional window | ||
2677 | furniture such as menu bars and window borders, if necessary. The status | ||
2678 | bar is also not included in this size.) | ||
2679 | |||
2680 | Use `user_size' to indicate whether `*x' and `*y' are a requested size, | ||
2681 | or just a maximum size. | ||
2682 | |||
2683 | If `user_size' is set to TRUE, the mid-end will treat the input size as | ||
2684 | a request, and will pick a tile size which approximates it _as closely | ||
2685 | as possible_, going over the game's preferred tile size if necessary to | ||
2686 | achieve this. The mid-end will also use the resulting tile size as its | ||
2687 | preferred one until further notice, on the assumption that this size was | ||
2688 | explicitly requested by the user. Use this option if you want your front | ||
2689 | end to support dynamic resizing of the puzzle window with automatic | ||
2690 | scaling of the puzzle to fit. | ||
2691 | |||
2692 | If `user_size' is set to FALSE, then the game's tile size will never go | ||
2693 | over its preferred one, although it may go under in order to fit within | ||
2694 | the maximum bounds specified by `*x' and `*y'. This is the recommended | ||
2695 | approach when opening a new window at default size: the game will use | ||
2696 | its preferred size unless it has to use a smaller one to fit on the | ||
2697 | screen. If the tile size is shrunk for this reason, the change will not | ||
2698 | persist; if a smaller grid is subsequently chosen, the tile size will | ||
2699 | recover. | ||
2700 | |||
2701 | The mid-end will try as hard as it can to return a size which is | ||
2702 | less than or equal to the input size, in both dimensions. In extreme | ||
2703 | circumstances it may fail (if even the lowest possible tile size gives | ||
2704 | window dimensions greater than the input), in which case it will return | ||
2705 | a size greater than the input size. Front ends should be prepared | ||
2706 | for this to happen (i.e. don't crash or fail an assertion), but may | ||
2707 | handle it in any way they see fit: by rejecting the game parameters | ||
2708 | which caused the problem, by opening a window larger than the screen | ||
2709 | regardless of inconvenience, by introducing scroll bars on the window, | ||
2710 | by drawing on a large bitmap and scaling it into a smaller window, or by | ||
2711 | any other means you can think of. It is likely that when the tile size | ||
2712 | is that small the game will be unplayable anyway, so don't put _too_ | ||
2713 | much effort into handling it creatively. | ||
2714 | |||
2715 | If your platform has no limit on window size (or if you're planning to | ||
2716 | use scroll bars for large puzzles), you can pass dimensions of INT_MAX | ||
2717 | as input to this function. You should probably not do that _and_ set the | ||
2718 | `user_size' flag, though! | ||
2719 | |||
2720 | The midend relies on the frontend calling midend_new_game() (section | ||
2721 | 4.8) before calling midend_size(). | ||
2722 | |||
2723 | #4.7. midend_reset_tilesize() | ||
2724 | |||
2725 | void midend_reset_tilesize(midend *me); | ||
2726 | |||
2727 | This function resets the midend's preferred tile size to that of the | ||
2728 | standard puzzle. | ||
2729 | |||
2730 | As discussed in section 4.6, puzzle resizes are typically 'sticky', | ||
2731 | in that once the user has dragged the puzzle to a different window | ||
2732 | size, the resulting tile size will be remembered and used when the | ||
2733 | puzzle configuration changes. If you _don't_ want that, e.g. if you | ||
2734 | want to provide a command to explicitly reset the puzzle size back to | ||
2735 | its default, then you can call this just before calling midend_size() | ||
2736 | (which, in turn, you would probably call with `user_size' set to FALSE). | ||
2737 | |||
2738 | #4.8. midend_new_game() | ||
2739 | |||
2740 | void midend_new_game(midend *me); | ||
2741 | |||
2742 | Causes the mid-end to begin a new game. Normally the game will be a | ||
2743 | new randomly generated puzzle. However, if you have previously called | ||
2744 | midend_game_id() or midend_set_config(), the game generated might be | ||
2745 | dictated by the results of those functions. (In particular, you _must_ | ||
2746 | call midend_new_game() after calling either of those functions, or else | ||
2747 | no immediate effect will be visible.) | ||
2748 | |||
2749 | You will probably need to call midend_size() after calling this | ||
2750 | function, because if the game parameters have been changed since the | ||
2751 | last new game then the window size might need to change. (If you know | ||
2752 | the parameters _haven't_ changed, you don't need to do this.) | ||
2753 | |||
2754 | This function will create a new `game_drawstate', but does not actually | ||
2755 | perform a redraw (since you often need to call midend_size() before | ||
2756 | the redraw can be done). So after calling this function and after | ||
2757 | calling midend_size(), you should then call midend_redraw(). (It is not | ||
2758 | necessary to call midend_force_redraw(); that will discard the draw | ||
2759 | state and create a fresh one, which is unnecessary in this case since | ||
2760 | there's a fresh one already. It would work, but it's usually excessive.) | ||
2761 | |||
2762 | #4.9. midend_restart_game() | ||
2763 | |||
2764 | void midend_restart_game(midend *me); | ||
2765 | |||
2766 | This function causes the current game to be restarted. This is done by | ||
2767 | placing a new copy of the original game state on the end of the undo | ||
2768 | list (so that an accidental restart can be undone). | ||
2769 | |||
2770 | This function automatically causes a redraw, i.e. the front end can | ||
2771 | expect its drawing API to be called from _within_ a call to this | ||
2772 | function. Some back ends require that midend_size() (section 4.6) is | ||
2773 | called before midend_restart_game(). | ||
2774 | |||
2775 | #4.10. midend_force_redraw() | ||
2776 | |||
2777 | void midend_force_redraw(midend *me); | ||
2778 | |||
2779 | Forces a complete redraw of the puzzle window, by means of discarding | ||
2780 | the current `game_drawstate' and creating a new one from scratch before | ||
2781 | calling the game's redraw() function. | ||
2782 | |||
2783 | The front end can expect its drawing API to be called from within a call | ||
2784 | to this function. Some back ends require that midend_size() (section | ||
2785 | 4.6) is called before midend_force_redraw(). | ||
2786 | |||
2787 | #4.11. midend_redraw() | ||
2788 | |||
2789 | void midend_redraw(midend *me); | ||
2790 | |||
2791 | Causes a partial redraw of the puzzle window, by means of simply calling | ||
2792 | the game's redraw() function. (That is, the only things redrawn will be | ||
2793 | things that have changed since the last redraw.) | ||
2794 | |||
2795 | The front end can expect its drawing API to be called from within a call | ||
2796 | to this function. Some back ends require that midend_size() (section | ||
2797 | 4.6) is called before midend_redraw(). | ||
2798 | |||
2799 | #4.12. midend_process_key() | ||
2800 | |||
2801 | int midend_process_key(midend *me, int x, int y, int button); | ||
2802 | |||
2803 | The front end calls this function to report a mouse or keyboard event. | ||
2804 | The parameters `x', `y' and `button' are almost identical to the ones | ||
2805 | passed to the back end function interpret_move() (section 2.7.1), except | ||
2806 | that the front end is _not_ required to provide the guarantees about | ||
2807 | mouse event ordering. The mid-end will sort out multiple simultaneous | ||
2808 | button presses and changes of button; the front end's responsibility | ||
2809 | is simply to pass on the mouse events it receives as accurately as | ||
2810 | possible. | ||
2811 | |||
2812 | (Some platforms may need to emulate absent mouse buttons by means of | ||
2813 | using a modifier key such as Shift with another mouse button. This tends | ||
2814 | to mean that if Shift is pressed or released in the middle of a mouse | ||
2815 | drag, the mid-end will suddenly stop receiving, say, LEFT_DRAG events | ||
2816 | and start receiving RIGHT_DRAGs, with no intervening button release or | ||
2817 | press events. This too is something which the mid-end will sort out for | ||
2818 | you; the front end has no obligation to maintain sanity in this area.) | ||
2819 | |||
2820 | The front end _should_, however, always eventually send some kind of | ||
2821 | button release. On some platforms this requires special effort: Windows, | ||
2822 | for example, requires a call to the system API function SetCapture() in | ||
2823 | order to ensure that your window receives a mouse-up event even if the | ||
2824 | pointer has left the window by the time the mouse button is released. | ||
2825 | On any platform that requires this sort of thing, the front end _is_ | ||
2826 | responsible for doing it. | ||
2827 | |||
2828 | Calling this function is very likely to result in calls back to the | ||
2829 | front end's drawing API and/or activate_timer() (section 4.36). | ||
2830 | |||
2831 | The return value from midend_process_key() is non-zero, unless the | ||
2832 | effect of the keypress was to request termination of the program. A | ||
2833 | front end should shut down the puzzle in response to a zero return. | ||
2834 | |||
2835 | #4.13. midend_colours() | ||
2836 | |||
2837 | float *midend_colours(midend *me, int *ncolours); | ||
2838 | |||
2839 | Returns an array of the colours required by the game, in exactly | ||
2840 | the same format as that returned by the back end function colours() | ||
2841 | (section 2.8.6). Front ends should call this function rather than | ||
2842 | calling the back end's version directly, since the mid-end adds standard | ||
2843 | customisation facilities. (At the time of writing, those customisation | ||
2844 | facilities are implemented hackily by means of environment variables, | ||
2845 | but it's not impossible that they may become more full and formal in | ||
2846 | future.) | ||
2847 | |||
2848 | #4.14. midend_timer() | ||
2849 | |||
2850 | void midend_timer(midend *me, float tplus); | ||
2851 | |||
2852 | If the mid-end has called activate_timer() (section 4.36) to request | ||
2853 | regular callbacks for purposes of animation or timing, this is the | ||
2854 | function the front end should call on a regular basis. The argument | ||
2855 | `tplus' gives the time, in seconds, since the last time either this | ||
2856 | function was called or activate_timer() was invoked. | ||
2857 | |||
2858 | One of the major purposes of timing in the mid-end is to perform move | ||
2859 | animation. Therefore, calling this function is very likely to result in | ||
2860 | calls back to the front end's drawing API. | ||
2861 | |||
2862 | #4.15. midend_get_presets() | ||
2863 | |||
2864 | struct preset_menu *midend_get_presets(midend *me, int *id_limit); | ||
2865 | |||
2866 | Returns a data structure describing this game's collection of preset | ||
2867 | game parameters, organised into a hierarchical structure of menus and | ||
2868 | submenus. | ||
2869 | |||
2870 | The return value is a pointer to a data structure containing the | ||
2871 | following fields (among others, which are not intended for front end | ||
2872 | use): | ||
2873 | |||
2874 | struct preset_menu { | ||
2875 | int n_entries; | ||
2876 | struct preset_menu_entry *entries; | ||
2877 | /* and other things */ | ||
2878 | }; | ||
2879 | |||
2880 | Those fields describe the intended contents of one particular menu in | ||
2881 | the hierarchy. `entries' points to an array of `n_entries' items, each | ||
2882 | of which is a structure containing the following fields: | ||
2883 | |||
2884 | struct preset_menu_entry { | ||
2885 | char *title; | ||
2886 | game_params *params; | ||
2887 | struct preset_menu *submenu; | ||
2888 | int id; | ||
2889 | }; | ||
2890 | |||
2891 | Of these fields, `title' and `id' are present in every entry, giving | ||
2892 | (respectively) the textual name of the menu item and an integer | ||
2893 | identifier for it. The integer id will correspond to the one returned | ||
2894 | by `midend_which_preset' (section 4.16), when that preset is the one | ||
2895 | selected. | ||
2896 | |||
2897 | The other two fields are mutually exclusive. Each | ||
2898 | `struct preset_menu_entry' will have one of those fields NULL and the | ||
2899 | other one non-null. If the menu item is an actual preset, then `params' | ||
2900 | will point to the set of game parameters that go with the name; if it's | ||
2901 | a submenu, then `submenu' instead will be non-null, and will point at a | ||
2902 | subsidiary `struct preset_menu'. | ||
2903 | |||
2904 | The complete hierarchy of these structures is owned by the mid-end, | ||
2905 | and will be freed when the mid-end is freed. The front end should not | ||
2906 | attempt to free any of it. | ||
2907 | |||
2908 | The integer identifiers will be allocated densely from 0 upwards, so | ||
2909 | that it's reasonable for the front end to allocate an array which uses | ||
2910 | them as indices, if it needs to store information per preset menu item. | ||
2911 | For this purpose, the front end may pass the second parameter `id_limit' | ||
2912 | to midend_get_presets as the address of an `int' variable, into which | ||
2913 | midend_get_presets will write an integer one larger than the largest id | ||
2914 | number actually used (i.e. the number of elements the front end would | ||
2915 | need in the array). | ||
2916 | |||
2917 | Submenu-type entries also have integer identifiers. | ||
2918 | |||
2919 | #4.16. midend_which_preset() | ||
2920 | |||
2921 | int midend_which_preset(midend *me); | ||
2922 | |||
2923 | Returns the numeric index of the preset game parameter structure which | ||
2924 | matches the current game parameters, or a negative number if no preset | ||
2925 | matches. Front ends could use this to maintain a tick beside one of the | ||
2926 | items in the menu (or tick the `Custom' option if the return value is | ||
2927 | less than zero). | ||
2928 | |||
2929 | The returned index value (if non-negative) will match the `id' | ||
2930 | field of the corresponding struct preset_menu_entry returned by | ||
2931 | `midend_get_presets()' (section 4.15). | ||
2932 | |||
2933 | #4.17. midend_wants_statusbar() | ||
2934 | |||
2935 | int midend_wants_statusbar(midend *me); | ||
2936 | |||
2937 | This function returns TRUE if the puzzle has a use for a textual status | ||
2938 | line (to display score, completion status, currently active tiles, time, | ||
2939 | or anything else). | ||
2940 | |||
2941 | Front ends should call this function rather than talking directly to the | ||
2942 | back end. | ||
2943 | |||
2944 | #4.18. midend_get_config() | ||
2945 | |||
2946 | config_item *midend_get_config(midend *me, int which, | ||
2947 | char **wintitle); | ||
2948 | |||
2949 | Returns a dialog box description for user configuration. | ||
2950 | |||
2951 | On input, which should be set to one of three values, which select which | ||
2952 | of the various dialog box descriptions is returned: | ||
2953 | |||
2954 | CFG_SETTINGS | ||
2955 | |||
2956 | Requests the GUI parameter configuration box generated by the puzzle | ||
2957 | itself. This should be used when the user selects `Custom' from the | ||
2958 | game types menu (or equivalent). The mid-end passes this request on | ||
2959 | to the back end function configure() (section 2.3.9). | ||
2960 | |||
2961 | CFG_DESC | ||
2962 | |||
2963 | Requests a box suitable for entering a descriptive game ID (and | ||
2964 | viewing the existing one). The mid-end generates this dialog box | ||
2965 | description itself. This should be used when the user selects | ||
2966 | `Specific' from the game menu (or equivalent). | ||
2967 | |||
2968 | CFG_SEED | ||
2969 | |||
2970 | Requests a box suitable for entering a random-seed game ID (and | ||
2971 | viewing the existing one). The mid-end generates this dialog box | ||
2972 | description itself. This should be used when the user selects | ||
2973 | `Random Seed' from the game menu (or equivalent). | ||
2974 | |||
2975 | The returned value is an array of config_items, exactly as described | ||
2976 | in section 2.3.9. Another returned value is an ASCII string giving a | ||
2977 | suitable title for the configuration window, in `*wintitle'. | ||
2978 | |||
2979 | Both returned values are dynamically allocated and will need to be | ||
2980 | freed. The window title can be freed in the obvious way; the config_item | ||
2981 | array is a slightly complex structure, so a utility function free_cfg() | ||
2982 | is provided to free it for you. See section 5.3.6. | ||
2983 | |||
2984 | (Of course, you will probably not want to free the config_item array | ||
2985 | until the dialog box is dismissed, because before then you will probably | ||
2986 | need to pass it to midend_set_config.) | ||
2987 | |||
2988 | #4.19. midend_set_config() | ||
2989 | |||
2990 | const char *midend_set_config(midend *me, int which, | ||
2991 | config_item *cfg); | ||
2992 | |||
2993 | Passes the mid-end the results of a configuration dialog box. `which' | ||
2994 | should have the same value which it had when midend_get_config() was | ||
2995 | called; `cfg' should be the array of `config_item's returned from | ||
2996 | midend_get_config(), modified to contain the results of the user's | ||
2997 | editing operations. | ||
2998 | |||
2999 | This function returns NULL on success, or otherwise (if the | ||
3000 | configuration data was in some way invalid) an ASCII string containing | ||
3001 | an error message suitable for showing to the user. | ||
3002 | |||
3003 | If the function succeeds, it is likely that the game parameters will | ||
3004 | have been changed and it is certain that a new game will be requested. | ||
3005 | The front end should therefore call midend_new_game(), and probably also | ||
3006 | re-think the window size using midend_size() and eventually perform a | ||
3007 | refresh using midend_redraw(). | ||
3008 | |||
3009 | #4.20. midend_game_id() | ||
3010 | |||
3011 | const char *midend_game_id(midend *me, const char *id); | ||
3012 | |||
3013 | Passes the mid-end a string game ID (of any of the valid forms `params', | ||
3014 | `params:description' or `params#seed') which the mid-end will process | ||
3015 | and use for the next generated game. | ||
3016 | |||
3017 | This function returns NULL on success, or otherwise (if the | ||
3018 | configuration data was in some way invalid) an ASCII string containing | ||
3019 | an error message (not dynamically allocated) suitable for showing to the | ||
3020 | user. In the event of an error, the mid-end's internal state will be | ||
3021 | left exactly as it was before the call. | ||
3022 | |||
3023 | If the function succeeds, it is likely that the game parameters will | ||
3024 | have been changed and it is certain that a new game will be requested. | ||
3025 | The front end should therefore call midend_new_game(), and probably | ||
3026 | also re-think the window size using midend_size() and eventually case a | ||
3027 | refresh using midend_redraw(). | ||
3028 | |||
3029 | #4.21. midend_get_game_id() | ||
3030 | |||
3031 | char *midend_get_game_id(midend *me) | ||
3032 | |||
3033 | Returns a descriptive game ID (i.e. one in the form | ||
3034 | `params:description') describing the game currently active in the mid- | ||
3035 | end. The returned string is dynamically allocated. | ||
3036 | |||
3037 | #4.22. midend_get_random_seed() | ||
3038 | |||
3039 | char *midend_get_random_seed(midend *me) | ||
3040 | |||
3041 | Returns a random game ID (i.e. one in the form `params#seedstring') | ||
3042 | describing the game currently active in the mid-end, if there is one. | ||
3043 | If the game was created by entering a description, no random seed will | ||
3044 | currently exist and this function will return NULL. | ||
3045 | |||
3046 | The returned string, if it is non-NULL, is dynamically allocated. | ||
3047 | |||
3048 | #4.23. midend_can_format_as_text_now() | ||
3049 | |||
3050 | int midend_can_format_as_text_now(midend *me); | ||
3051 | |||
3052 | Returns TRUE if the game code is capable of formatting puzzles of the | ||
3053 | currently selected game type as ASCII. | ||
3054 | |||
3055 | If this returns FALSE, then midend_text_format() (section 4.24) will | ||
3056 | return NULL. | ||
3057 | |||
3058 | #4.24. midend_text_format() | ||
3059 | |||
3060 | char *midend_text_format(midend *me); | ||
3061 | |||
3062 | Formats the current game's current state as ASCII text suitable for | ||
3063 | copying to the clipboard. The returned string is dynamically allocated. | ||
3064 | |||
3065 | If the game's `can_format_as_text_ever' flag is FALSE, or if its | ||
3066 | can_format_as_text_now() function returns FALSE, then this function will | ||
3067 | return NULL. | ||
3068 | |||
3069 | If the returned string contains multiple lines (which is likely), it | ||
3070 | will use the normal C line ending convention (\n only). On platforms | ||
3071 | which use a different line ending convention for data in the clipboard, | ||
3072 | it is the front end's responsibility to perform the conversion. | ||
3073 | |||
3074 | #4.25. midend_solve() | ||
3075 | |||
3076 | const char *midend_solve(midend *me); | ||
3077 | |||
3078 | Requests the mid-end to perform a Solve operation. | ||
3079 | |||
3080 | On success, NULL is returned. On failure, an error message (not | ||
3081 | dynamically allocated) is returned, suitable for showing to the user. | ||
3082 | |||
3083 | The front end can expect its drawing API and/or activate_timer() to be | ||
3084 | called from within a call to this function. Some back ends require that | ||
3085 | midend_size() (section 4.6) is called before midend_solve(). | ||
3086 | |||
3087 | #4.26. midend_status() | ||
3088 | |||
3089 | int midend_status(midend *me); | ||
3090 | |||
3091 | This function returns +1 if the midend is currently displaying a game | ||
3092 | in a solved state, -1 if the game is in a permanently lost state, or 0 | ||
3093 | otherwise. This function just calls the back end's status() function. | ||
3094 | Front ends may wish to use this as a cue to proactively offer the option | ||
3095 | of starting a new game. | ||
3096 | |||
3097 | (See section 2.8.9 for more detail about the back end's status() | ||
3098 | function and discussion of what should count as which status code.) | ||
3099 | |||
3100 | #4.27. midend_can_undo() | ||
3101 | |||
3102 | int midend_can_undo(midend *me); | ||
3103 | |||
3104 | Returns TRUE if the midend is currently in a state where the undo | ||
3105 | operation is meaningful (i.e. at least one position exists on the undo | ||
3106 | chain before the present one). Front ends may wish to use this to | ||
3107 | visually activate and deactivate an undo button. | ||
3108 | |||
3109 | #4.28. midend_can_redo() | ||
3110 | |||
3111 | int midend_can_redo(midend *me); | ||
3112 | |||
3113 | Returns TRUE if the midend is currently in a state where the redo | ||
3114 | operation is meaningful (i.e. at least one position exists on the | ||
3115 | redo chain after the present one). Front ends may wish to use this to | ||
3116 | visually activate and deactivate a redo button. | ||
3117 | |||
3118 | #4.29. midend_serialise() | ||
3119 | |||
3120 | void midend_serialise(midend *me, | ||
3121 | void (*write)(void *ctx, const void *buf, int len), void *wctx); | ||
3122 | |||
3123 | Calling this function causes the mid-end to convert its entire internal | ||
3124 | state into a long ASCII text string, and to pass that string (piece by | ||
3125 | piece) to the supplied `write' function. | ||
3126 | |||
3127 | Desktop implementations can use this function to save a game in any | ||
3128 | state (including half-finished) to a disk file, by supplying a `write' | ||
3129 | function which is a wrapper on fwrite() (or local equivalent). Other | ||
3130 | implementations may find other uses for it, such as compressing the | ||
3131 | large and sprawling mid-end state into a manageable amount of memory | ||
3132 | when a palmtop application is suspended so that another one can run; in | ||
3133 | this case write might want to write to a memory buffer rather than a | ||
3134 | file. There may be other uses for it as well. | ||
3135 | |||
3136 | This function will call back to the supplied `write' function a number | ||
3137 | of times, with the first parameter (`ctx') equal to `wctx', and the | ||
3138 | other two parameters pointing at a piece of the output string. | ||
3139 | |||
3140 | #4.30. midend_deserialise() | ||
3141 | |||
3142 | const char *midend_deserialise(midend *me, | ||
3143 | int (*read)(void *ctx, void *buf, int len), void *rctx); | ||
3144 | |||
3145 | This function is the counterpart to midend_serialise(). It calls the | ||
3146 | supplied read function repeatedly to read a quantity of data, and | ||
3147 | attempts to interpret that data as a serialised mid-end as output by | ||
3148 | midend_serialise(). | ||
3149 | |||
3150 | The read function is called with the first parameter (`ctx') equal | ||
3151 | to `rctx', and should attempt to read `len' bytes of data into the | ||
3152 | buffer pointed to by `buf'. It should return FALSE on failure or TRUE | ||
3153 | on success. It should not report success unless it has filled the | ||
3154 | entire buffer; on platforms which might be reading from a pipe or other | ||
3155 | blocking data source, `read' is responsible for looping until the whole | ||
3156 | buffer has been filled. | ||
3157 | |||
3158 | If the de-serialisation operation is successful, the mid-end's internal | ||
3159 | data structures will be replaced by the results of the load, and NULL | ||
3160 | will be returned. Otherwise, the mid-end's state will be completely | ||
3161 | unchanged and an error message (typically some variation on `save file | ||
3162 | is corrupt') will be returned. As usual, the error message string is not | ||
3163 | dynamically allocated. | ||
3164 | |||
3165 | If this function succeeds, it is likely that the game parameters will | ||
3166 | have been changed. The front end should therefore probably re-think the | ||
3167 | window size using midend_size(), and probably cause a refresh using | ||
3168 | midend_redraw(). | ||
3169 | |||
3170 | Because each mid-end is tied to a specific game back end, this function | ||
3171 | will fail if you attempt to read in a save file generated by a different | ||
3172 | game from the one configured in this mid-end, even if your application | ||
3173 | is a monolithic one containing all the puzzles. See section 4.31 for a | ||
3174 | helper function which will allow you to identify a save file before you | ||
3175 | instantiate your mid-end in the first place. | ||
3176 | |||
3177 | #4.31. identify_game() | ||
3178 | |||
3179 | const char *identify_game(char **name, | ||
3180 | int (*read)(void *ctx, void *buf, int len), void *rctx); | ||
3181 | |||
3182 | This function examines a serialised midend stream, of the same kind used | ||
3183 | by midend_serialise() and midend_deserialise(), and returns the name | ||
3184 | field of the game back end from which it was saved. | ||
3185 | |||
3186 | You might want this if your front end was a monolithic one containing | ||
3187 | all the puzzles, and you wanted to be able to load an arbitrary save | ||
3188 | file and automatically switch to the right game. Probably your next step | ||
3189 | would be to iterate through gamelist (section 4.33) looking for a game | ||
3190 | structure whose name field matched the returned string, and give an | ||
3191 | error if you didn't find one. | ||
3192 | |||
3193 | On success, the return value of this function is NULL, and the game name | ||
3194 | string is written into *name. The caller should free that string after | ||
3195 | using it. | ||
3196 | |||
3197 | On failure, *name is NULL, and the return value is an error message | ||
3198 | (which does not need freeing at all). | ||
3199 | |||
3200 | (This isn't strictly speaking a midend function, since it doesn't accept | ||
3201 | or return a pointer to a midend. You'd probably call it just _before_ | ||
3202 | deciding what kind of midend you wanted to instantiate.) | ||
3203 | |||
3204 | #4.32. midend_request_id_changes() | ||
3205 | |||
3206 | void midend_request_id_changes(midend *me, | ||
3207 | void (*notify)(void *), void *ctx); | ||
3208 | |||
3209 | This function is called by the front end to request notification by the | ||
3210 | mid-end when the current game IDs (either descriptive or random-seed) | ||
3211 | change. This can occur as a result of keypresses ('n' for New Game, for | ||
3212 | example) or when a puzzle supersedes its game description (see section | ||
3213 | 2.11.2). After this function is called, any change of the game ids will | ||
3214 | cause the mid-end to call notify(ctx) after the change. | ||
3215 | |||
3216 | This is for use by puzzles which want to present the game description to | ||
3217 | the user constantly (e.g. as an HTML hyperlink) instead of only showing | ||
3218 | it when the user explicitly requests it. | ||
3219 | |||
3220 | This is a function I anticipate few front ends needing to implement, so | ||
3221 | I make it a callback rather than a static function in order to relieve | ||
3222 | most front ends of the need to provide an empty implementation. | ||
3223 | |||
3224 | #4.33. Direct reference to the back end structure by the front end | ||
3225 | |||
3226 | Although _most_ things the front end needs done should be done by | ||
3227 | calling the mid-end, there are a few situations in which the front end | ||
3228 | needs to refer directly to the game back end structure. | ||
3229 | |||
3230 | The most obvious of these is | ||
3231 | |||
3232 | - passing the game back end as a parameter to midend_new(). | ||
3233 | |||
3234 | There are a few other back end features which are not wrapped by the | ||
3235 | mid-end because there didn't seem much point in doing so: | ||
3236 | |||
3237 | - fetching the `name' field to use in window titles and similar | ||
3238 | |||
3239 | - reading the `can_configure', `can_solve' and | ||
3240 | `can_format_as_text_ever' fields to decide whether to add those | ||
3241 | items to the menu bar or equivalent | ||
3242 | |||
3243 | - reading the `winhelp_topic' field (Windows only) | ||
3244 | |||
3245 | - the GTK front end provides a `--generate' command-line option which | ||
3246 | directly calls the back end to do most of its work. This is not | ||
3247 | really part of the main front end code, though, and I'm not sure it | ||
3248 | counts. | ||
3249 | |||
3250 | In order to find the game back end structure, the front end does one of | ||
3251 | two things: | ||
3252 | |||
3253 | - If the particular front end is compiling a separate binary per game, | ||
3254 | then the back end structure is a global variable with the standard | ||
3255 | name `thegame': | ||
3256 | |||
3257 | extern const game thegame; | ||
3258 | |||
3259 | - If the front end is compiled as a monolithic application containing | ||
3260 | all the puzzles together (in which case the preprocessor symbol | ||
3261 | COMBINED must be defined when compiling most of the code base), then | ||
3262 | there will be two global variables defined: | ||
3263 | |||
3264 | extern const game *gamelist[]; | ||
3265 | extern const int gamecount; | ||
3266 | |||
3267 | `gamelist' will be an array of `gamecount' game structures, declared | ||
3268 | in the automatically constructed source module `list.c'. The | ||
3269 | application should search that array for the game it wants, probably | ||
3270 | by reaching into each game structure and looking at its `name' | ||
3271 | field. | ||
3272 | |||
3273 | #4.34. Mid-end to front-end calls | ||
3274 | |||
3275 | This section describes the small number of functions which a front end | ||
3276 | must provide to be called by the mid-end or other standard utility | ||
3277 | modules. | ||
3278 | |||
3279 | #4.35. get_random_seed() | ||
3280 | |||
3281 | void get_random_seed(void **randseed, int *randseedsize); | ||
3282 | |||
3283 | This function is called by a new mid-end, and also occasionally by game | ||
3284 | back ends. Its job is to return a piece of data suitable for using as a | ||
3285 | seed for initialisation of a new `random_state'. | ||
3286 | |||
3287 | On exit, `*randseed' should be set to point at a newly allocated piece | ||
3288 | of memory containing some seed data, and `*randseedsize' should be set | ||
3289 | to the length of that data. | ||
3290 | |||
3291 | A simple and entirely adequate implementation is to return a piece of | ||
3292 | data containing the current system time at the highest conveniently | ||
3293 | available resolution. | ||
3294 | |||
3295 | #4.36. activate_timer() | ||
3296 | |||
3297 | void activate_timer(frontend *fe); | ||
3298 | |||
3299 | This is called by the mid-end to request that the front end begin | ||
3300 | calling it back at regular intervals. | ||
3301 | |||
3302 | The timeout interval is left up to the front end; the finer it is, the | ||
3303 | smoother move animations will be, but the more CPU time will be used. | ||
3304 | Current front ends use values around 20ms (i.e. 50Hz). | ||
3305 | |||
3306 | After this function is called, the mid-end will expect to receive calls | ||
3307 | to midend_timer() on a regular basis. | ||
3308 | |||
3309 | #4.37. deactivate_timer() | ||
3310 | |||
3311 | void deactivate_timer(frontend *fe); | ||
3312 | |||
3313 | This is called by the mid-end to request that the front end stop calling | ||
3314 | midend_timer(). | ||
3315 | |||
3316 | #4.38. fatal() | ||
3317 | |||
3318 | void fatal(const char *fmt, ...); | ||
3319 | |||
3320 | This is called by some utility functions if they encounter a genuinely | ||
3321 | fatal error such as running out of memory. It is a variadic function | ||
3322 | in the style of printf(), and is expected to show the formatted error | ||
3323 | message to the user any way it can and then terminate the application. | ||
3324 | It must not return. | ||
3325 | |||
3326 | #4.39. frontend_default_colour() | ||
3327 | |||
3328 | void frontend_default_colour(frontend *fe, float *output); | ||
3329 | |||
3330 | This function expects to be passed a pointer to an array of three | ||
3331 | floats. It returns the platform's local preferred background colour | ||
3332 | in those three floats, as red, green and blue values (in that order) | ||
3333 | ranging from 0.0 to 1.0. | ||
3334 | |||
3335 | This function should only ever be called by the back end function | ||
3336 | colours() (section 2.8.6). (Thus, it isn't a _midend_-to-frontend | ||
3337 | function as such, but there didn't seem to be anywhere else particularly | ||
3338 | good to put it. Sorry.) | ||
3339 | |||
3340 | #5. Utility APIs | ||
3341 | |||
3342 | This chapter documents a variety of utility APIs provided for the | ||
3343 | general use of the rest of the Puzzles code. | ||
3344 | |||
3345 | #5.1. Random number generation | ||
3346 | |||
3347 | Platforms' local random number generators vary widely in quality and | ||
3348 | seed size. Puzzles therefore supplies its own high-quality random number | ||
3349 | generator, with the additional advantage of giving the same results if | ||
3350 | fed the same seed data on different platforms. This allows game random | ||
3351 | seeds to be exchanged between different ports of Puzzles and still | ||
3352 | generate the same games. | ||
3353 | |||
3354 | Unlike the ANSI C rand() function, the Puzzles random number generator | ||
3355 | has an _explicit_ state object called a `random_state'. One of these | ||
3356 | is managed by each mid-end, for example, and passed to the back end to | ||
3357 | generate a game with. | ||
3358 | |||
3359 | #5.1.1. random_new() | ||
3360 | |||
3361 | random_state *random_new(char *seed, int len); | ||
3362 | |||
3363 | Allocates, initialises and returns a new `random_state'. The input data | ||
3364 | is used as the seed for the random number stream (i.e. using the same | ||
3365 | seed at a later time will generate the same stream). | ||
3366 | |||
3367 | The seed data can be any data at all; there is no requirement to use | ||
3368 | printable ASCII, or NUL-terminated strings, or anything like that. | ||
3369 | |||
3370 | #5.1.2. random_copy() | ||
3371 | |||
3372 | random_state *random_copy(random_state *tocopy); | ||
3373 | |||
3374 | Allocates a new `random_state', copies the contents of another | ||
3375 | `random_state' into it, and returns the new state. If exactly the | ||
3376 | same sequence of functions is subseqently called on both the copy and | ||
3377 | the original, the results will be identical. This may be useful for | ||
3378 | speculatively performing some operation using a given random state, and | ||
3379 | later replaying that operation precisely. | ||
3380 | |||
3381 | #5.1.3. random_free() | ||
3382 | |||
3383 | void random_free(random_state *state); | ||
3384 | |||
3385 | Frees a `random_state'. | ||
3386 | |||
3387 | #5.1.4. random_bits() | ||
3388 | |||
3389 | unsigned long random_bits(random_state *state, int bits); | ||
3390 | |||
3391 | Returns a random number from 0 to 2^bits-1 inclusive. `bits' should be | ||
3392 | between 1 and 32 inclusive. | ||
3393 | |||
3394 | #5.1.5. random_upto() | ||
3395 | |||
3396 | unsigned long random_upto(random_state *state, unsigned long limit); | ||
3397 | |||
3398 | Returns a random number from 0 to limit-1 inclusive. | ||
3399 | |||
3400 | #5.1.6. random_state_encode() | ||
3401 | |||
3402 | char *random_state_encode(random_state *state); | ||
3403 | |||
3404 | Encodes the entire contents of a `random_state' in printable ASCII. | ||
3405 | Returns a dynamically allocated string containing that encoding. This | ||
3406 | can subsequently be passed to random_state_decode() to reconstruct the | ||
3407 | same `random_state'. | ||
3408 | |||
3409 | #5.1.7. random_state_decode() | ||
3410 | |||
3411 | random_state *random_state_decode(char *input); | ||
3412 | |||
3413 | Decodes a string generated by random_state_encode() and reconstructs an | ||
3414 | equivalent `random_state' to the one encoded, i.e. it should produce the | ||
3415 | same stream of random numbers. | ||
3416 | |||
3417 | This function has no error reporting; if you pass it an invalid string | ||
3418 | it will simply generate an arbitrary random state, which may turn out to | ||
3419 | be noticeably non-random. | ||
3420 | |||
3421 | #5.1.8. shuffle() | ||
3422 | |||
3423 | void shuffle(void *array, int nelts, int eltsize, random_state *rs); | ||
3424 | |||
3425 | Shuffles an array into a random order. The interface is much like ANSI C | ||
3426 | qsort(), except that there's no need for a compare function. | ||
3427 | |||
3428 | `array' is a pointer to the first element of the array. `nelts' is the | ||
3429 | number of elements in the array; `eltsize' is the size of a single | ||
3430 | element (typically measured using `sizeof'). `rs' is a `random_state' | ||
3431 | used to generate all the random numbers for the shuffling process. | ||
3432 | |||
3433 | #5.2. Presets menu management | ||
3434 | |||
3435 | The function `midend_get_presets()' (section 4.15) returns a data | ||
3436 | structure describing a menu hierarchy. Back ends can also choose to | ||
3437 | provide such a structure to the mid-end, if they want to group their | ||
3438 | presets hierarchically. To make this easy, there are a few utility | ||
3439 | functions to construct preset menu structures, and also one intended for | ||
3440 | front-end use. | ||
3441 | |||
3442 | #5.2.1. preset_menu_new() | ||
3443 | |||
3444 | struct preset_menu *preset_menu_new(void); | ||
3445 | |||
3446 | Allocates a new `struct preset_menu', and initialises it to hold no menu | ||
3447 | items. | ||
3448 | |||
3449 | #5.2.2. preset_menu_add_submenu() | ||
3450 | |||
3451 | struct preset_menu *preset_menu_add_submenu | ||
3452 | (struct preset_menu *parent, char *title); | ||
3453 | |||
3454 | Adds a new submenu to the end of an existing preset menu, and returns | ||
3455 | a pointer to a newly allocated `struct preset_menu' describing the | ||
3456 | submenu. | ||
3457 | |||
3458 | The string parameter `title' must be dynamically allocated by the | ||
3459 | caller. The preset-menu structure will take ownership of it, so the | ||
3460 | caller must not free it. | ||
3461 | |||
3462 | #5.2.3. preset_menu_add_preset() | ||
3463 | |||
3464 | void preset_menu_add_preset | ||
3465 | (struct preset_menu *menu, char *title, game_params *params); | ||
3466 | |||
3467 | Adds a preset game configuration to the end of a preset menu. | ||
3468 | |||
3469 | Both the string parameter `title' and the game parameter structure | ||
3470 | `params' itself must be dynamically allocated by the caller. The preset- | ||
3471 | menu structure will take ownership of it, so the caller must not free | ||
3472 | it. | ||
3473 | |||
3474 | #5.2.4. preset_menu_lookup_by_id() | ||
3475 | |||
3476 | game_params *preset_menu_lookup_by_id | ||
3477 | (struct preset_menu *menu, int id); | ||
3478 | |||
3479 | Given a numeric index, searches recursively through a preset menu | ||
3480 | hierarchy to find the corresponding menu entry, and returns a pointer to | ||
3481 | its existing `game_params' structure. | ||
3482 | |||
3483 | This function is intended for front end use (but front ends need not use | ||
3484 | it if they prefer to do things another way). If a front end finds it | ||
3485 | inconvenient to store anything more than a numeric index alongside each | ||
3486 | menu item, then this function provides an easy way for the front end to | ||
3487 | get back the actual game parameters corresponding to a menu item that | ||
3488 | the user has selected. | ||
3489 | |||
3490 | #5.3. Memory allocation | ||
3491 | |||
3492 | Puzzles has some central wrappers on the standard memory allocation | ||
3493 | functions, which provide compile-time type checking, and run-time error | ||
3494 | checking by means of quitting the application if it runs out of memory. | ||
3495 | This doesn't provide the best possible recovery from memory shortage, | ||
3496 | but on the other hand it greatly simplifies the rest of the code, | ||
3497 | because nothing else anywhere needs to worry about NULL returns from | ||
3498 | allocation. | ||
3499 | |||
3500 | #5.3.1. snew() | ||
3501 | |||
3502 | var = snew(type); | ||
3503 | |||
3504 | This macro takes a single argument which is a _type name_. It allocates | ||
3505 | space for one object of that type. If allocation fails it will call | ||
3506 | fatal() and not return; so if it does return, you can be confident that | ||
3507 | its return value is non-NULL. | ||
3508 | |||
3509 | The return value is cast to the specified type, so that the compiler | ||
3510 | will type-check it against the variable you assign it into. Thus, this | ||
3511 | ensures you don't accidentally allocate memory the size of the wrong | ||
3512 | type and assign it into a variable of the right one (or vice versa!). | ||
3513 | |||
3514 | #5.3.2. snewn() | ||
3515 | |||
3516 | var = snewn(n, type); | ||
3517 | |||
3518 | This macro is the array form of snew(). It takes two arguments; the | ||
3519 | first is a number, and the second is a type name. It allocates space | ||
3520 | for that many objects of that type, and returns a type-checked non-NULL | ||
3521 | pointer just as snew() does. | ||
3522 | |||
3523 | #5.3.3. sresize() | ||
3524 | |||
3525 | var = sresize(var, n, type); | ||
3526 | |||
3527 | This macro is a type-checked form of realloc(). It takes three | ||
3528 | arguments: an input memory block, a new size in elements, and a type. | ||
3529 | It re-sizes the input memory block to a size sufficient to contain that | ||
3530 | many elements of that type. It returns a type-checked non-NULL pointer, | ||
3531 | like snew() and snewn(). | ||
3532 | |||
3533 | The input memory block can be NULL, in which case this function will | ||
3534 | behave exactly like snewn(). (In principle any ANSI-compliant realloc() | ||
3535 | implementation ought to cope with this, but I've never quite trusted it | ||
3536 | to work everywhere.) | ||
3537 | |||
3538 | #5.3.4. sfree() | ||
3539 | |||
3540 | void sfree(void *p); | ||
3541 | |||
3542 | This function is pretty much equivalent to free(). It is provided with a | ||
3543 | dynamically allocated block, and frees it. | ||
3544 | |||
3545 | The input memory block can be NULL, in which case this function will do | ||
3546 | nothing. (In principle any ANSI-compliant free() implementation ought to | ||
3547 | cope with this, but I've never quite trusted it to work everywhere.) | ||
3548 | |||
3549 | #5.3.5. dupstr() | ||
3550 | |||
3551 | char *dupstr(const char *s); | ||
3552 | |||
3553 | This function dynamically allocates a duplicate of a C string. Like the | ||
3554 | snew() functions, it guarantees to return non-NULL or not return at all. | ||
3555 | |||
3556 | (Many platforms provide the function strdup(). As well as guaranteeing | ||
3557 | never to return NULL, my version has the advantage of being defined | ||
3558 | _everywhere_, rather than inconveniently not quite everywhere.) | ||
3559 | |||
3560 | #5.3.6. free_cfg() | ||
3561 | |||
3562 | void free_cfg(config_item *cfg); | ||
3563 | |||
3564 | This function correctly frees an array of `config_item's, including | ||
3565 | walking the array until it gets to the end and freeing any subsidiary | ||
3566 | data items in each `u' sub-union which are expected to be dynamically | ||
3567 | allocated. | ||
3568 | |||
3569 | (See section 2.3.9 for details of the `config_item' structure.) | ||
3570 | |||
3571 | #5.4. Sorted and counted tree functions | ||
3572 | |||
3573 | Many games require complex algorithms for generating random puzzles, and | ||
3574 | some require moderately complex algorithms even during play. A common | ||
3575 | requirement during these algorithms is for a means of maintaining sorted | ||
3576 | or unsorted lists of items, such that items can be removed and added | ||
3577 | conveniently. | ||
3578 | |||
3579 | For general use, Puzzles provides the following set of functions which | ||
3580 | maintain 2-3-4 trees in memory. (A 2-3-4 tree is a balanced tree | ||
3581 | structure, with the property that all lookups, insertions, deletions, | ||
3582 | splits and joins can be done in O(log N) time.) | ||
3583 | |||
3584 | All these functions expect you to be storing a tree of `void *' | ||
3585 | pointers. You can put anything you like in those pointers. | ||
3586 | |||
3587 | By the use of per-node element counts, these tree structures have the | ||
3588 | slightly unusual ability to look elements up by their numeric index | ||
3589 | within the list represented by the tree. This means that they can be | ||
3590 | used to store an unsorted list (in which case, every time you insert a | ||
3591 | new element, you must explicitly specify the position where you wish to | ||
3592 | insert it). They can also do numeric lookups in a sorted tree, which | ||
3593 | might be useful for (for example) tracking the median of a changing data | ||
3594 | set. | ||
3595 | |||
3596 | As well as storing sorted lists, these functions can be used for storing | ||
3597 | `maps' (associative arrays), by defining each element of a tree to be a | ||
3598 | (key, value) pair. | ||
3599 | |||
3600 | #5.4.1. newtree234() | ||
3601 | |||
3602 | tree234 *newtree234(cmpfn234 cmp); | ||
3603 | |||
3604 | Creates a new empty tree, and returns a pointer to it. | ||
3605 | |||
3606 | The parameter `cmp' determines the sorting criterion on the tree. Its | ||
3607 | prototype is | ||
3608 | |||
3609 | typedef int (*cmpfn234)(void *, void *); | ||
3610 | |||
3611 | If you want a sorted tree, you should provide a function matching this | ||
3612 | prototype, which returns like strcmp() does (negative if the first | ||
3613 | argument is smaller than the second, positive if it is bigger, zero if | ||
3614 | they compare equal). In this case, the function addpos234() will not be | ||
3615 | usable on your tree (because all insertions must respect the sorting | ||
3616 | order). | ||
3617 | |||
3618 | If you want an unsorted tree, pass NULL. In this case you will not be | ||
3619 | able to use either add234() or del234(), or any other function such | ||
3620 | as find234() which depends on a sorting order. Your tree will become | ||
3621 | something more like an array, except that it will efficiently support | ||
3622 | insertion and deletion as well as lookups by numeric index. | ||
3623 | |||
3624 | #5.4.2. freetree234() | ||
3625 | |||
3626 | void freetree234(tree234 *t); | ||
3627 | |||
3628 | Frees a tree. This function will not free the _elements_ of the tree | ||
3629 | (because they might not be dynamically allocated, or you might be | ||
3630 | storing the same set of elements in more than one tree); it will just | ||
3631 | free the tree structure itself. If you want to free all the elements of | ||
3632 | a tree, you should empty it before passing it to freetree234(), by means | ||
3633 | of code along the lines of | ||
3634 | |||
3635 | while ((element = delpos234(tree, 0)) != NULL) | ||
3636 | sfree(element); /* or some more complicated free function */ | ||
3637 | |||
3638 | #5.4.3. add234() | ||
3639 | |||
3640 | void *add234(tree234 *t, void *e); | ||
3641 | |||
3642 | Inserts a new element `e' into the tree `t'. This function expects the | ||
3643 | tree to be sorted; the new element is inserted according to the sort | ||
3644 | order. | ||
3645 | |||
3646 | If an element comparing equal to `e' is already in the tree, then the | ||
3647 | insertion will fail, and the return value will be the existing element. | ||
3648 | Otherwise, the insertion succeeds, and `e' is returned. | ||
3649 | |||
3650 | #5.4.4. addpos234() | ||
3651 | |||
3652 | void *addpos234(tree234 *t, void *e, int index); | ||
3653 | |||
3654 | Inserts a new element into an unsorted tree. Since there is no sorting | ||
3655 | order to dictate where the new element goes, you must specify where you | ||
3656 | want it to go. Setting `index' to zero puts the new element right at the | ||
3657 | start of the list; setting `index' to the current number of elements in | ||
3658 | the tree puts the new element at the end. | ||
3659 | |||
3660 | Return value is `e', in line with add234() (although this function | ||
3661 | cannot fail except by running out of memory, in which case it will bomb | ||
3662 | out and die rather than returning an error indication). | ||
3663 | |||
3664 | #5.4.5. index234() | ||
3665 | |||
3666 | void *index234(tree234 *t, int index); | ||
3667 | |||
3668 | Returns a pointer to the `index'th element of the tree, or NULL if | ||
3669 | `index' is out of range. Elements of the tree are numbered from zero. | ||
3670 | |||
3671 | #5.4.6. find234() | ||
3672 | |||
3673 | void *find234(tree234 *t, void *e, cmpfn234 cmp); | ||
3674 | |||
3675 | Searches for an element comparing equal to `e' in a sorted tree. | ||
3676 | |||
3677 | If `cmp' is NULL, the tree's ordinary comparison function will be used | ||
3678 | to perform the search. However, sometimes you don't want that; suppose, | ||
3679 | for example, each of your elements is a big structure containing a | ||
3680 | `char *' name field, and you want to find the element with a given name. | ||
3681 | You _could_ achieve this by constructing a fake element structure, | ||
3682 | setting its name field appropriately, and passing it to find234(), | ||
3683 | but you might find it more convenient to pass _just_ a name string to | ||
3684 | find234(), supplying an alternative comparison function which expects | ||
3685 | one of its arguments to be a bare name and the other to be a large | ||
3686 | structure containing a name field. | ||
3687 | |||
3688 | Therefore, if `cmp' is not NULL, then it will be used to compare `e' to | ||
3689 | elements of the tree. The first argument passed to `cmp' will always be | ||
3690 | `e'; the second will be an element of the tree. | ||
3691 | |||
3692 | (See section 5.4.1 for the definition of the `cmpfn234' function pointer | ||
3693 | type.) | ||
3694 | |||
3695 | The returned value is the element found, or NULL if the search is | ||
3696 | unsuccessful. | ||
3697 | |||
3698 | #5.4.7. findrel234() | ||
3699 | |||
3700 | void *findrel234(tree234 *t, void *e, cmpfn234 cmp, int relation); | ||
3701 | |||
3702 | This function is like find234(), but has the additional ability to do a | ||
3703 | _relative_ search. The additional parameter `relation' can be one of the | ||
3704 | following values: | ||
3705 | |||
3706 | REL234_EQ | ||
3707 | |||
3708 | Find only an element that compares equal to `e'. This is exactly the | ||
3709 | behaviour of find234(). | ||
3710 | |||
3711 | REL234_LT | ||
3712 | |||
3713 | Find the greatest element that compares strictly less than `e'. `e' | ||
3714 | may be NULL, in which case it finds the greatest element in the | ||
3715 | whole tree (which could also be done by index234(t, count234(t)-1)). | ||
3716 | |||
3717 | REL234_LE | ||
3718 | |||
3719 | Find the greatest element that compares less than or equal to `e'. | ||
3720 | (That is, find an element that compares equal to `e' if possible, | ||
3721 | but failing that settle for something just less than it.) | ||
3722 | |||
3723 | REL234_GT | ||
3724 | |||
3725 | Find the smallest element that compares strictly greater than `e'. | ||
3726 | `e' may be NULL, in which case it finds the smallest element in the | ||
3727 | whole tree (which could also be done by index234(t, 0)). | ||
3728 | |||
3729 | REL234_GE | ||
3730 | |||
3731 | Find the smallest element that compares greater than or equal | ||
3732 | to `e'. (That is, find an element that compares equal to `e' if | ||
3733 | possible, but failing that settle for something just bigger than | ||
3734 | it.) | ||
3735 | |||
3736 | Return value, as before, is the element found or NULL if no element | ||
3737 | satisfied the search criterion. | ||
3738 | |||
3739 | #5.4.8. findpos234() | ||
3740 | |||
3741 | void *findpos234(tree234 *t, void *e, cmpfn234 cmp, int *index); | ||
3742 | |||
3743 | This function is like find234(), but has the additional feature of | ||
3744 | returning the index of the element found in the tree; that index is | ||
3745 | written to `*index' in the event of a successful search (a non-NULL | ||
3746 | return value). | ||
3747 | |||
3748 | `index' may be NULL, in which case this function behaves exactly like | ||
3749 | find234(). | ||
3750 | |||
3751 | #5.4.9. findrelpos234() | ||
3752 | |||
3753 | void *findrelpos234(tree234 *t, void *e, cmpfn234 cmp, int relation, | ||
3754 | int *index); | ||
3755 | |||
3756 | This function combines all the features of findrel234() and | ||
3757 | findpos234(). | ||
3758 | |||
3759 | #5.4.10. del234() | ||
3760 | |||
3761 | void *del234(tree234 *t, void *e); | ||
3762 | |||
3763 | Finds an element comparing equal to `e' in the tree, deletes it, and | ||
3764 | returns it. | ||
3765 | |||
3766 | The input tree must be sorted. | ||
3767 | |||
3768 | The element found might be `e' itself, or might merely compare equal to | ||
3769 | it. | ||
3770 | |||
3771 | Return value is NULL if no such element is found. | ||
3772 | |||
3773 | #5.4.11. delpos234() | ||
3774 | |||
3775 | void *delpos234(tree234 *t, int index); | ||
3776 | |||
3777 | Deletes the element at position `index' in the tree, and returns it. | ||
3778 | |||
3779 | Return value is NULL if the index is out of range. | ||
3780 | |||
3781 | #5.4.12. count234() | ||
3782 | |||
3783 | int count234(tree234 *t); | ||
3784 | |||
3785 | Returns the number of elements currently in the tree. | ||
3786 | |||
3787 | #5.4.13. splitpos234() | ||
3788 | |||
3789 | tree234 *splitpos234(tree234 *t, int index, int before); | ||
3790 | |||
3791 | Splits the input tree into two pieces at a given position, and creates a | ||
3792 | new tree containing all the elements on one side of that position. | ||
3793 | |||
3794 | If `before' is TRUE, then all the items at or after position `index' are | ||
3795 | left in the input tree, and the items before that point are returned in | ||
3796 | the new tree. Otherwise, the reverse happens: all the items at or after | ||
3797 | `index' are moved into the new tree, and those before that point are | ||
3798 | left in the old one. | ||
3799 | |||
3800 | If `index' is equal to 0 or to the number of elements in the input tree, | ||
3801 | then one of the two trees will end up empty (and this is not an error | ||
3802 | condition). If `index' is further out of range in either direction, the | ||
3803 | operation will fail completely and return NULL. | ||
3804 | |||
3805 | This operation completes in O(log N) time, no matter how large the tree | ||
3806 | or how balanced or unbalanced the split. | ||
3807 | |||
3808 | #5.4.14. split234() | ||
3809 | |||
3810 | tree234 *split234(tree234 *t, void *e, cmpfn234 cmp, int rel); | ||
3811 | |||
3812 | Splits a sorted tree according to its sort order. | ||
3813 | |||
3814 | `rel' can be any of the relation constants described in section 5.4.7, | ||
3815 | _except_ for REL234_EQ. All the elements having that relation to `e' | ||
3816 | will be transferred into the new tree; the rest will be left in the old | ||
3817 | one. | ||
3818 | |||
3819 | The parameter `cmp' has the same semantics as it does in find234(): if | ||
3820 | it is not NULL, it will be used in place of the tree's own comparison | ||
3821 | function when comparing elements to `e', in such a way that `e' itself | ||
3822 | is always the first of its two operands. | ||
3823 | |||
3824 | Again, this operation completes in O(log N) time, no matter how large | ||
3825 | the tree or how balanced or unbalanced the split. | ||
3826 | |||
3827 | #5.4.15. join234() | ||
3828 | |||
3829 | tree234 *join234(tree234 *t1, tree234 *t2); | ||
3830 | |||
3831 | Joins two trees together by concatenating the lists they represent. All | ||
3832 | the elements of `t2' are moved into `t1', in such a way that they appear | ||
3833 | _after_ the elements of `t1'. The tree `t2' is freed; the return value | ||
3834 | is `t1'. | ||
3835 | |||
3836 | If you apply this function to a sorted tree and it violates the sort | ||
3837 | order (i.e. the smallest element in `t2' is smaller than or equal to the | ||
3838 | largest element in `t1'), the operation will fail and return NULL. | ||
3839 | |||
3840 | This operation completes in O(log N) time, no matter how large the trees | ||
3841 | being joined together. | ||
3842 | |||
3843 | #5.4.16. join234r() | ||
3844 | |||
3845 | tree234 *join234r(tree234 *t1, tree234 *t2); | ||
3846 | |||
3847 | Joins two trees together in exactly the same way as join234(), but this | ||
3848 | time the combined tree is returned in `t2', and `t1' is destroyed. The | ||
3849 | elements in `t1' still appear before those in `t2'. | ||
3850 | |||
3851 | Again, this operation completes in O(log N) time, no matter how large | ||
3852 | the trees being joined together. | ||
3853 | |||
3854 | #5.4.17. copytree234() | ||
3855 | |||
3856 | tree234 *copytree234(tree234 *t, copyfn234 copyfn, | ||
3857 | void *copyfnstate); | ||
3858 | |||
3859 | Makes a copy of an entire tree. | ||
3860 | |||
3861 | If `copyfn' is NULL, the tree will be copied but the elements will not | ||
3862 | be; i.e. the new tree will contain pointers to exactly the same physical | ||
3863 | elements as the old one. | ||
3864 | |||
3865 | If you want to copy each actual element during the operation, you can | ||
3866 | instead pass a function in `copyfn' which makes a copy of each element. | ||
3867 | That function has the prototype | ||
3868 | |||
3869 | typedef void *(*copyfn234)(void *state, void *element); | ||
3870 | |||
3871 | and every time it is called, the `state' parameter will be set to the | ||
3872 | value you passed in as `copyfnstate'. | ||
3873 | |||
3874 | #5.5. Miscellaneous utility functions and macros | ||
3875 | |||
3876 | This section contains all the utility functions which didn't sensibly | ||
3877 | fit anywhere else. | ||
3878 | |||
3879 | #5.5.1. TRUE and FALSE | ||
3880 | |||
3881 | The main Puzzles header file defines the macros TRUE and FALSE, which | ||
3882 | are used throughout the code in place of 1 and 0 (respectively) to | ||
3883 | indicate that the values are in a boolean context. For code base | ||
3884 | consistency, I'd prefer it if submissions of new code followed this | ||
3885 | convention as well. | ||
3886 | |||
3887 | #5.5.2. max() and min() | ||
3888 | |||
3889 | The main Puzzles header file defines the pretty standard macros max() | ||
3890 | and min(), each of which is given two arguments and returns the one | ||
3891 | which compares greater or less respectively. | ||
3892 | |||
3893 | These macros may evaluate their arguments multiple times. Avoid side | ||
3894 | effects. | ||
3895 | |||
3896 | #5.5.3. PI | ||
3897 | |||
3898 | The main Puzzles header file defines a macro PI which expands to a | ||
3899 | floating-point constant representing pi. | ||
3900 | |||
3901 | (I've never understood why ANSI's <math.h> doesn't define this. It'd be | ||
3902 | so useful!) | ||
3903 | |||
3904 | #5.5.4. obfuscate_bitmap() | ||
3905 | |||
3906 | void obfuscate_bitmap(unsigned char *bmp, int bits, int decode); | ||
3907 | |||
3908 | This function obscures the contents of a piece of data, by cryptographic | ||
3909 | methods. It is useful for games of hidden information (such as Mines, | ||
3910 | Guess or Black Box), in which the game ID theoretically reveals all the | ||
3911 | information the player is supposed to be trying to guess. So in order | ||
3912 | that players should be able to send game IDs to one another without | ||
3913 | accidentally spoiling the resulting game by looking at them, these games | ||
3914 | obfuscate their game IDs using this function. | ||
3915 | |||
3916 | Although the obfuscation function is cryptographic, it cannot properly | ||
3917 | be called encryption because it has no key. Therefore, anybody motivated | ||
3918 | enough can re-implement it, or hack it out of the Puzzles source, | ||
3919 | and strip the obfuscation off one of these game IDs to see what lies | ||
3920 | beneath. (Indeed, they could usually do it much more easily than that, | ||
3921 | by entering the game ID into their own copy of the puzzle and hitting | ||
3922 | Solve.) The aim is not to protect against a determined attacker; the aim | ||
3923 | is simply to protect people who wanted to play the game honestly from | ||
3924 | _accidentally_ spoiling their own fun. | ||
3925 | |||
3926 | The input argument `bmp' points at a piece of memory to be obfuscated. | ||
3927 | `bits' gives the length of the data. Note that that length is in _bits_ | ||
3928 | rather than bytes: if you ask for obfuscation of a partial number of | ||
3929 | bytes, then you will get it. Bytes are considered to be used from the | ||
3930 | top down: thus, for example, setting `bits' to 10 will cover the whole | ||
3931 | of bmp[0] and the _top two_ bits of bmp[1]. The remainder of a partially | ||
3932 | used byte is undefined (i.e. it may be corrupted by the function). | ||
3933 | |||
3934 | The parameter `decode' is FALSE for an encoding operation, and TRUE | ||
3935 | for a decoding operation. Each is the inverse of the other. (There's | ||
3936 | no particular reason you shouldn't obfuscate by decoding and restore | ||
3937 | cleartext by encoding, if you really wanted to; it should still work.) | ||
3938 | |||
3939 | The input bitmap is processed in place. | ||
3940 | |||
3941 | #5.5.5. bin2hex() | ||
3942 | |||
3943 | char *bin2hex(const unsigned char *in, int inlen); | ||
3944 | |||
3945 | This function takes an input byte array and converts it into an | ||
3946 | ASCII string encoding those bytes in (lower-case) hex. It returns a | ||
3947 | dynamically allocated string containing that encoding. | ||
3948 | |||
3949 | This function is useful for encoding the result of obfuscate_bitmap() in | ||
3950 | printable ASCII for use in game IDs. | ||
3951 | |||
3952 | #5.5.6. hex2bin() | ||
3953 | |||
3954 | unsigned char *hex2bin(const char *in, int outlen); | ||
3955 | |||
3956 | This function takes an ASCII string containing hex digits, and converts | ||
3957 | it back into a byte array of length `outlen'. If there aren't enough | ||
3958 | hex digits in the string, the contents of the resulting array will be | ||
3959 | undefined. | ||
3960 | |||
3961 | This function is the inverse of bin2hex(). | ||
3962 | |||
3963 | #5.5.7. game_mkhighlight() | ||
3964 | |||
3965 | void game_mkhighlight(frontend *fe, float *ret, | ||
3966 | int background, int highlight, int lowlight); | ||
3967 | |||
3968 | It's reasonably common for a puzzle game's graphics to use highlights | ||
3969 | and lowlights to indicate `raised' or `lowered' sections. Fifteen, | ||
3970 | Sixteen and Twiddle are good examples of this. | ||
3971 | |||
3972 | Puzzles using this graphical style are running a risk if they just use | ||
3973 | whatever background colour is supplied to them by the front end, because | ||
3974 | that background colour might be too light to see any highlights on at | ||
3975 | all. (In particular, it's not unheard of for the front end to specify a | ||
3976 | default background colour of white.) | ||
3977 | |||
3978 | Therefore, such puzzles can call this utility function from their | ||
3979 | colours() routine (section 2.8.6). You pass it your front end handle, a | ||
3980 | pointer to the start of your return array, and three colour indices. It | ||
3981 | will: | ||
3982 | |||
3983 | - call frontend_default_colour() (section 4.39) to fetch the front | ||
3984 | end's default background colour | ||
3985 | |||
3986 | - alter the brightness of that colour if it's unsuitable | ||
3987 | |||
3988 | - define brighter and darker variants of the colour to be used as | ||
3989 | highlights and lowlights | ||
3990 | |||
3991 | - write those results into the relevant positions in the `ret' array. | ||
3992 | |||
3993 | Thus, ret[background*3] to ret[background*3+2] will be set to RGB values | ||
3994 | defining a sensible background colour, and similary `highlight' and | ||
3995 | `lowlight' will be set to sensible colours. | ||
3996 | |||
3997 | #6. How to write a new puzzle | ||
3998 | |||
3999 | This chapter gives a guide to how to actually write a new puzzle: where | ||
4000 | to start, what to do first, how to solve common problems. | ||
4001 | |||
4002 | The previous chapters have been largely composed of facts. This one is | ||
4003 | mostly advice. | ||
4004 | |||
4005 | #6.1. Choosing a puzzle | ||
4006 | |||
4007 | Before you start writing a puzzle, you have to choose one. Your taste | ||
4008 | in puzzle games is up to you, of course; and, in fact, you're probably | ||
4009 | reading this guide because you've _already_ thought of a game you want | ||
4010 | to write. But if you want to get it accepted into the official Puzzles | ||
4011 | distribution, then there's a criterion it has to meet. | ||
4012 | |||
4013 | The current Puzzles editorial policy is that all games should be _fair_. | ||
4014 | A fair game is one which a player can only fail to complete through | ||
4015 | demonstrable lack of skill - that is, such that a better player in the | ||
4016 | same situation would have _known_ to do something different. | ||
4017 | |||
4018 | For a start, that means every game presented to the user must have _at | ||
4019 | least one solution_. Giving the unsuspecting user a puzzle which is | ||
4020 | actually impossible is not acceptable. (There is an exception: if the | ||
4021 | user has selected some non-default option which is clearly labelled as | ||
4022 | potentially unfair, _then_ you're allowed to generate possibly insoluble | ||
4023 | puzzles, because the user isn't unsuspecting any more. Same Game and | ||
4024 | Mines both have options of this type.) | ||
4025 | |||
4026 | Also, this actually _rules out_ games such as Klondike, or the normal | ||
4027 | form of Mahjong Solitaire. Those games have the property that even if | ||
4028 | there is a solution (i.e. some sequence of moves which will get from | ||
4029 | the start state to the solved state), the player doesn't necessarily | ||
4030 | have enough information to _find_ that solution. In both games, it is | ||
4031 | possible to reach a dead end because you had an arbitrary choice to make | ||
4032 | and made it the wrong way. This violates the fairness criterion, because | ||
4033 | a better player couldn't have known they needed to make the other | ||
4034 | choice. | ||
4035 | |||
4036 | (GNOME has a variant on Mahjong Solitaire which makes it fair: there | ||
4037 | is a Shuffle operation which randomly permutes all the remaining tiles | ||
4038 | without changing their positions, which allows you to get out of a | ||
4039 | sticky situation. Using this operation adds a 60-second penalty to your | ||
4040 | solution time, so it's to the player's advantage to try to minimise | ||
4041 | the chance of having to use it. It's still possible to render the game | ||
4042 | uncompletable if you end up with only two tiles vertically stacked, | ||
4043 | but that's easy to foresee and avoid using a shuffle operation. This | ||
4044 | form of the game _is_ fair. Implementing it in Puzzles would require | ||
4045 | an infrastructure change so that the back end could communicate time | ||
4046 | penalties to the mid-end, but that would be easy enough.) | ||
4047 | |||
4048 | Providing a _unique_ solution is a little more negotiable; it depends | ||
4049 | on the puzzle. Solo would have been of unacceptably low quality if it | ||
4050 | didn't always have a unique solution, whereas Twiddle inherently has | ||
4051 | multiple solutions by its very nature and it would have been meaningless | ||
4052 | to even _suggest_ making it uniquely soluble. Somewhere in between, Flip | ||
4053 | could reasonably be made to have unique solutions (by enforcing a zero- | ||
4054 | dimension kernel in every generated matrix) but it doesn't seem like a | ||
4055 | serious quality problem that it doesn't. | ||
4056 | |||
4057 | Of course, you don't _have_ to care about all this. There's nothing | ||
4058 | stopping you implementing any puzzle you want to if you're happy to | ||
4059 | maintain your puzzle yourself, distribute it from your own web site, | ||
4060 | fork the Puzzles code completely, or anything like that. It's free | ||
4061 | software; you can do what you like with it. But any game that you want | ||
4062 | to be accepted into _my_ Puzzles code base has to satisfy the fairness | ||
4063 | criterion, which means all randomly generated puzzles must have a | ||
4064 | solution (unless the user has deliberately chosen otherwise) and it must | ||
4065 | be possible _in theory_ to find that solution without having to guess. | ||
4066 | |||
4067 | #6.2. Getting started | ||
4068 | |||
4069 | The simplest way to start writing a new puzzle is to copy `nullgame.c'. | ||
4070 | This is a template puzzle source file which does almost nothing, but | ||
4071 | which contains all the back end function prototypes and declares the | ||
4072 | back end data structure correctly. It is built every time the rest of | ||
4073 | Puzzles is built, to ensure that it doesn't get out of sync with the | ||
4074 | code and remains buildable. | ||
4075 | |||
4076 | So start by copying `nullgame.c' into your new source file. Then you'll | ||
4077 | gradually add functionality until the very boring Null Game turns into | ||
4078 | your real game. | ||
4079 | |||
4080 | Next you'll need to add your puzzle to the Makefiles, in order to | ||
4081 | compile it conveniently. _Do not edit the Makefiles_: they are created | ||
4082 | automatically by the script `mkfiles.pl', from the file called `Recipe'. | ||
4083 | Edit `Recipe', and then re-run `mkfiles.pl'. | ||
4084 | |||
4085 | Also, don't forget to add your puzzle to `list.c': if you don't, then it | ||
4086 | will still run fine on platforms which build each puzzle separately, but | ||
4087 | Mac OS X and other monolithic platforms will not include your new puzzle | ||
4088 | in their single binary. | ||
4089 | |||
4090 | Once your source file is building, you can move on to the fun bit. | ||
4091 | |||
4092 | #6.2.1. Puzzle generation | ||
4093 | |||
4094 | Randomly generating instances of your puzzle is almost certain to be | ||
4095 | the most difficult part of the code, and also the task with the highest | ||
4096 | chance of turning out to be completely infeasible. Therefore I strongly | ||
4097 | recommend doing it _first_, so that if it all goes horribly wrong you | ||
4098 | haven't wasted any more time than you absolutely had to. What I usually | ||
4099 | do is to take an unmodified `nullgame.c', and start adding code to | ||
4100 | new_game_desc() which tries to generate a puzzle instance and print it | ||
4101 | out using printf(). Once that's working, _then_ I start connecting it up | ||
4102 | to the return value of new_game_desc(), populating other structures like | ||
4103 | `game_params', and generally writing the rest of the source file. | ||
4104 | |||
4105 | There are many ways to generate a puzzle which is known to be soluble. | ||
4106 | In this section I list all the methods I currently know of, in case any | ||
4107 | of them can be applied to your puzzle. (Not all of these methods will | ||
4108 | work, or in some cases even make sense, for all puzzles.) | ||
4109 | |||
4110 | Some puzzles are mathematically tractable, meaning you can work out in | ||
4111 | advance which instances are soluble. Sixteen, for example, has a parity | ||
4112 | constraint in some settings which renders exactly half the game space | ||
4113 | unreachable, but it can be mathematically proved that any position | ||
4114 | not in that half _is_ reachable. Therefore, Sixteen's grid generation | ||
4115 | simply consists of selecting at random from a well defined subset of the | ||
4116 | game space. Cube in its default state is even easier: _every_ possible | ||
4117 | arrangement of the blue squares and the cube's starting position is | ||
4118 | soluble! | ||
4119 | |||
4120 | Another option is to redefine what you mean by `soluble'. Black Box | ||
4121 | takes this approach. There are layouts of balls in the box which are | ||
4122 | completely indistinguishable from one another no matter how many beams | ||
4123 | you fire into the box from which angles, which would normally be grounds | ||
4124 | for declaring those layouts unfair; but fortunately, detecting that | ||
4125 | indistinguishability is computationally easy. So Black Box doesn't | ||
4126 | demand that your ball placements match its own; it merely demands | ||
4127 | that your ball placements be _indistinguishable_ from the ones it was | ||
4128 | thinking of. If you have an ambiguous puzzle, then any of the possible | ||
4129 | answers is considered to be a solution. Having redefined the rules in | ||
4130 | that way, any puzzle is soluble again. | ||
4131 | |||
4132 | Those are the simple techniques. If they don't work, you have to get | ||
4133 | cleverer. | ||
4134 | |||
4135 | One way to generate a soluble puzzle is to start from the solved state | ||
4136 | and make inverse moves until you reach a starting state. Then you know | ||
4137 | there's a solution, because you can just list the inverse moves you made | ||
4138 | and make them in the opposite order to return to the solved state. | ||
4139 | |||
4140 | This method can be simple and effective for puzzles where you get to | ||
4141 | decide what's a starting state and what's not. In Pegs, for example, | ||
4142 | the generator begins with one peg in the centre of the board and makes | ||
4143 | inverse moves until it gets bored; in this puzzle, valid inverse moves | ||
4144 | are easy to detect, and _any_ state that's reachable from the solved | ||
4145 | state by inverse moves is a reasonable starting position. So Pegs just | ||
4146 | continues making inverse moves until the board satisfies some criteria | ||
4147 | about extent and density, and then stops and declares itself done. | ||
4148 | |||
4149 | For other puzzles, it can be a lot more difficult. Same Game uses | ||
4150 | this strategy too, and it's lucky to get away with it at all: valid | ||
4151 | inverse moves aren't easy to find (because although it's easy to insert | ||
4152 | additional squares in a Same Game position, it's difficult to arrange | ||
4153 | that _after_ the insertion they aren't adjacent to any other squares of | ||
4154 | the same colour), so you're constantly at risk of running out of options | ||
4155 | and having to backtrack or start again. Also, Same Game grids never | ||
4156 | start off half-empty, which means you can't just stop when you run out | ||
4157 | of moves - you have to find a way to fill the grid up _completely_. | ||
4158 | |||
4159 | The other way to generate a puzzle that's soluble is to start from the | ||
4160 | other end, and actually write a _solver_. This tends to ensure that a | ||
4161 | puzzle has a _unique_ solution over and above having a solution at all, | ||
4162 | so it's a good technique to apply to puzzles for which that's important. | ||
4163 | |||
4164 | One theoretical drawback of generating soluble puzzles by using a solver | ||
4165 | is that your puzzles are restricted in difficulty to those which the | ||
4166 | solver can handle. (Most solvers are not fully general: many sets of | ||
4167 | puzzle rules are NP-complete or otherwise nasty, so most solvers can | ||
4168 | only handle a subset of the theoretically soluble puzzles.) It's been | ||
4169 | my experience in practice, however, that this usually isn't a problem; | ||
4170 | computers are good at very different things from humans, and what the | ||
4171 | computer thinks is nice and easy might still be pleasantly challenging | ||
4172 | for a human. For example, when solving Dominosa puzzles I frequently | ||
4173 | find myself using a variety of reasoning techniques that my solver | ||
4174 | doesn't know about; in principle, therefore, I should be able to solve | ||
4175 | the puzzle using only those techniques it _does_ know about, but this | ||
4176 | would involve repeatedly searching the entire grid for the one simple | ||
4177 | deduction I can make. Computers are good at this sort of exhaustive | ||
4178 | search, but it's been my experience that human solvers prefer to do more | ||
4179 | complex deductions than to spend ages searching for simple ones. So in | ||
4180 | many cases I don't find my own playing experience to be limited by the | ||
4181 | restrictions on the solver. | ||
4182 | |||
4183 | (This isn't _always_ the case. Solo is a counter-example; generating | ||
4184 | Solo puzzles using a simple solver does lead to qualitatively easier | ||
4185 | puzzles. Therefore I had to make the Solo solver rather more advanced | ||
4186 | than most of them.) | ||
4187 | |||
4188 | There are several different ways to apply a solver to the problem of | ||
4189 | generating a soluble puzzle. I list a few of them below. | ||
4190 | |||
4191 | The simplest approach is brute force: randomly generate a puzzle, use | ||
4192 | the solver to see if it's soluble, and if not, throw it away and try | ||
4193 | again until you get lucky. This is often a viable technique if all | ||
4194 | else fails, but it tends not to scale well: for many puzzle types, the | ||
4195 | probability of finding a uniquely soluble instance decreases sharply | ||
4196 | as puzzle size goes up, so this technique might work reasonably fast | ||
4197 | for small puzzles but take (almost) forever at larger sizes. Still, if | ||
4198 | there's no other alternative it can be usable: Pattern and Dominosa | ||
4199 | both use this technique. (However, Dominosa has a means of tweaking the | ||
4200 | randomly generated grids to increase the _probability_ of them being | ||
4201 | soluble, by ruling out one of the most common ambiguous cases. This | ||
4202 | improved generation speed by over a factor of 10 on the highest preset!) | ||
4203 | |||
4204 | An approach which can be more scalable involves generating a grid and | ||
4205 | then tweaking it to make it soluble. This is the technique used by Mines | ||
4206 | and also by Net: first a random puzzle is generated, and then the solver | ||
4207 | is run to see how far it gets. Sometimes the solver will get stuck; | ||
4208 | when that happens, examine the area it's having trouble with, and make | ||
4209 | a small random change in that area to allow it to make more progress. | ||
4210 | Continue solving (possibly even without restarting the solver), tweaking | ||
4211 | as necessary, until the solver finishes. Then restart the solver from | ||
4212 | the beginning to ensure that the tweaks haven't caused new problems in | ||
4213 | the process of solving old ones (which can sometimes happen). | ||
4214 | |||
4215 | This strategy works well in situations where the usual solver failure | ||
4216 | mode is to get stuck in an easily localised spot. Thus it works well | ||
4217 | for Net and Mines, whose most common failure mode tends to be that most | ||
4218 | of the grid is fine but there are a few widely separated ambiguous | ||
4219 | sections; but it would work less well for Dominosa, in which the way you | ||
4220 | get stuck is to have scoured the whole grid and not found anything you | ||
4221 | can deduce _anywhere_. Also, it relies on there being a low probability | ||
4222 | that tweaking the grid introduces a new problem at the same time as | ||
4223 | solving the old one; Mines and Net also have the property that most of | ||
4224 | their deductions are local, so that it's very unlikely for a tweak to | ||
4225 | affect something half way across the grid from the location where it was | ||
4226 | applied. In Dominosa, by contrast, a lot of deductions use information | ||
4227 | about half the grid (`out of all the sixes, only one is next to a | ||
4228 | three', which can depend on the values of up to 32 of the 56 squares in | ||
4229 | the default setting!), so this tweaking strategy would be rather less | ||
4230 | likely to work well. | ||
4231 | |||
4232 | A more specialised strategy is that used in Solo and Slant. These | ||
4233 | puzzles have the property that they derive their difficulty from not | ||
4234 | presenting all the available clues. (In Solo's case, if all the possible | ||
4235 | clues were provided then the puzzle would already be solved; in Slant | ||
4236 | it would still require user action to fill in the lines, but it would | ||
4237 | present no challenge at all). Therefore, a simple generation technique | ||
4238 | is to leave the decision of which clues to provide until the last | ||
4239 | minute. In other words, first generate a random _filled_ grid with all | ||
4240 | possible clues present, and then gradually remove clues for as long as | ||
4241 | the solver reports that it's still soluble. Unlike the methods described | ||
4242 | above, this technique _cannot_ fail - once you've got a filled grid, | ||
4243 | nothing can stop you from being able to convert it into a viable puzzle. | ||
4244 | However, it wouldn't even be meaningful to apply this technique to (say) | ||
4245 | Pattern, in which clues can never be left out, so the only way to affect | ||
4246 | the set of clues is by altering the solution. | ||
4247 | |||
4248 | (Unfortunately, Solo is complicated by the need to provide puzzles at | ||
4249 | varying difficulty levels. It's easy enough to generate a puzzle of | ||
4250 | _at most_ a given level of difficulty; you just have a solver with | ||
4251 | configurable intelligence, and you set it to a given level and apply the | ||
4252 | above technique, thus guaranteeing that the resulting grid is solvable | ||
4253 | by someone with at most that much intelligence. However, generating a | ||
4254 | puzzle of _at least_ a given level of difficulty is rather harder; if | ||
4255 | you go for _at most_ Intermediate level, you're likely to find that | ||
4256 | you've accidentally generated a Trivial grid a lot of the time, because | ||
4257 | removing just one number is sufficient to take the puzzle from Trivial | ||
4258 | straight to Ambiguous. In that situation Solo has no remaining options | ||
4259 | but to throw the puzzle away and start again.) | ||
4260 | |||
4261 | A final strategy is to use the solver _during_ puzzle construction: | ||
4262 | lay out a bit of the grid, run the solver to see what it allows you to | ||
4263 | deduce, and then lay out a bit more to allow the solver to make more | ||
4264 | progress. There are articles on the web that recommend constructing | ||
4265 | Sudoku puzzles by this method (which is completely the opposite way | ||
4266 | round to how Solo does it); for Sudoku it has the advantage that you | ||
4267 | get to specify your clue squares in advance (so you can have them make | ||
4268 | pretty patterns). | ||
4269 | |||
4270 | Rectangles uses a strategy along these lines. First it generates a grid | ||
4271 | by placing the actual rectangles; then it has to decide where in each | ||
4272 | rectangle to place a number. It uses a solver to help it place the | ||
4273 | numbers in such a way as to ensure a unique solution. It does this by | ||
4274 | means of running a test solver, but it runs the solver _before_ it's | ||
4275 | placed any of the numbers - which means the solver must be capable of | ||
4276 | coping with uncertainty about exactly where the numbers are! It runs | ||
4277 | the solver as far as it can until it gets stuck; then it narrows down | ||
4278 | the possible positions of a number in order to allow the solver to make | ||
4279 | more progress, and so on. Most of the time this process terminates with | ||
4280 | the grid fully solved, at which point any remaining number-placement | ||
4281 | decisions can be made at random from the options not so far ruled out. | ||
4282 | Note that unlike the Net/Mines tweaking strategy described above, this | ||
4283 | algorithm does not require a checking run after it completes: if it | ||
4284 | finishes successfully at all, then it has definitely produced a uniquely | ||
4285 | soluble puzzle. | ||
4286 | |||
4287 | Most of the strategies described above are not 100% reliable. Each | ||
4288 | one has a failure rate: every so often it has to throw out the whole | ||
4289 | grid and generate a fresh one from scratch. (Solo's strategy would | ||
4290 | be the exception, if it weren't for the need to provide configurable | ||
4291 | difficulty levels.) Occasional failures are not a fundamental problem in | ||
4292 | this sort of work, however: it's just a question of dividing the grid | ||
4293 | generation time by the success rate (if it takes 10ms to generate a | ||
4294 | candidate grid and 1/5 of them work, then it will take 50ms on average | ||
4295 | to generate a viable one), and seeing whether the expected time taken | ||
4296 | to _successfully_ generate a puzzle is unacceptably slow. Dominosa's | ||
4297 | generator has a very low success rate (about 1 out of 20 candidate grids | ||
4298 | turn out to be usable, and if you think _that's_ bad then go and look | ||
4299 | at the source code and find the comment showing what the figures were | ||
4300 | before the generation-time tweaks!), but the generator itself is very | ||
4301 | fast so this doesn't matter. Rectangles has a slower generator, but | ||
4302 | fails well under 50% of the time. | ||
4303 | |||
4304 | So don't be discouraged if you have an algorithm that doesn't always | ||
4305 | work: if it _nearly_ always works, that's probably good enough. The one | ||
4306 | place where reliability is important is that your algorithm must never | ||
4307 | produce false positives: it must not claim a puzzle is soluble when it | ||
4308 | isn't. It can produce false negatives (failing to notice that a puzzle | ||
4309 | is soluble), and it can fail to generate a puzzle at all, provided it | ||
4310 | doesn't do either so often as to become slow. | ||
4311 | |||
4312 | One last piece of advice: for grid-based puzzles, when writing and | ||
4313 | testing your generation algorithm, it's almost always a good idea _not_ | ||
4314 | to test it initially on a grid that's square (i.e. w==h), because if the | ||
4315 | grid is square then you won't notice if you mistakenly write `h' instead | ||
4316 | of `w' (or vice versa) somewhere in the code. Use a rectangular grid for | ||
4317 | testing, and any size of grid will be likely to work after that. | ||
4318 | |||
4319 | #6.2.2. Designing textual description formats | ||
4320 | |||
4321 | Another aspect of writing a puzzle which is worth putting some thought | ||
4322 | into is the design of the various text description formats: the format | ||
4323 | of the game parameter encoding, the game description encoding, and the | ||
4324 | move encoding. | ||
4325 | |||
4326 | The first two of these should be reasonably intuitive for a user to type | ||
4327 | in; so provide some flexibility where possible. Suppose, for example, | ||
4328 | your parameter format consists of two numbers separated by an `x' to | ||
4329 | specify the grid dimensions (`10x10' or `20x15'), and then has some | ||
4330 | suffixes to specify other aspects of the game type. It's almost always a | ||
4331 | good idea in this situation to arrange that decode_params() can handle | ||
4332 | the suffixes appearing in any order, even if encode_params() only ever | ||
4333 | generates them in one order. | ||
4334 | |||
4335 | These formats will also be expected to be reasonably stable: users will | ||
4336 | expect to be able to exchange game IDs with other users who aren't | ||
4337 | running exactly the same version of your game. So make them robust and | ||
4338 | stable: don't build too many assumptions into the game ID format which | ||
4339 | will have to be changed every time something subtle changes in the | ||
4340 | puzzle code. | ||
4341 | |||
4342 | #6.3. Common how-to questions | ||
4343 | |||
4344 | This section lists some common things people want to do when writing a | ||
4345 | puzzle, and describes how to achieve them within the Puzzles framework. | ||
4346 | |||
4347 | #6.3.1. Drawing objects at only one position | ||
4348 | |||
4349 | A common phenomenon is to have an object described in the `game_state' | ||
4350 | or the `game_ui' which can only be at one position. A cursor - probably | ||
4351 | specified in the `game_ui' - is a good example. | ||
4352 | |||
4353 | In the `game_ui', it would _obviously_ be silly to have an array | ||
4354 | covering the whole game grid with a boolean flag stating whether the | ||
4355 | cursor was at each position. Doing that would waste space, would make | ||
4356 | it difficult to find the cursor in order to do anything with it, and | ||
4357 | would introduce the potential for synchronisation bugs in which you | ||
4358 | ended up with two cursors or none. The obviously sensible way to store a | ||
4359 | cursor in the `game_ui' is to have fields directly encoding the cursor's | ||
4360 | coordinates. | ||
4361 | |||
4362 | However, it is a mistake to assume that the same logic applies to the | ||
4363 | `game_drawstate'. If you replicate the cursor position fields in the | ||
4364 | draw state, the redraw code will get very complicated. In the draw | ||
4365 | state, in fact, it _is_ probably the right thing to have a cursor flag | ||
4366 | for every position in the grid. You probably have an array for the whole | ||
4367 | grid in the drawstate already (stating what is currently displayed in | ||
4368 | the window at each position); the sensible approach is to add a `cursor' | ||
4369 | flag to each element of that array. Then the main redraw loop will look | ||
4370 | something like this (pseudo-code): | ||
4371 | |||
4372 | for (y = 0; y < h; y++) { | ||
4373 | for (x = 0; x < w; x++) { | ||
4374 | int value = state->symbol_at_position[y][x]; | ||
4375 | if (x == ui->cursor_x && y == ui->cursor_y) | ||
4376 | value |= CURSOR; | ||
4377 | if (ds->symbol_at_position[y][x] != value) { | ||
4378 | symbol_drawing_subroutine(dr, ds, x, y, value); | ||
4379 | ds->symbol_at_position[y][x] = value; | ||
4380 | } | ||
4381 | } | ||
4382 | } | ||
4383 | |||
4384 | This loop is very simple, pretty hard to get wrong, and _automatically_ | ||
4385 | deals both with erasing the previous cursor and drawing the new one, | ||
4386 | with no special case code required. | ||
4387 | |||
4388 | This type of loop is generally a sensible way to write a redraw | ||
4389 | function, in fact. The best thing is to ensure that the information | ||
4390 | stored in the draw state for each position tells you _everything_ about | ||
4391 | what was drawn there. A good way to ensure that is to pass precisely | ||
4392 | the same information, and _only_ that information, to a subroutine that | ||
4393 | does the actual drawing; then you know there's no additional information | ||
4394 | which affects the drawing but which you don't notice changes in. | ||
4395 | |||
4396 | #6.3.2. Implementing a keyboard-controlled cursor | ||
4397 | |||
4398 | It is often useful to provide a keyboard control method in a basically | ||
4399 | mouse-controlled game. A keyboard-controlled cursor is best implemented | ||
4400 | by storing its location in the `game_ui' (since if it were in the | ||
4401 | `game_state' then the user would have to separately undo every cursor | ||
4402 | move operation). So the procedure would be: | ||
4403 | |||
4404 | - Put cursor position fields in the `game_ui'. | ||
4405 | |||
4406 | - interpret_move() responds to arrow keys by modifying the cursor | ||
4407 | position fields and returning "". | ||
4408 | |||
4409 | - interpret_move() responds to some sort of fire button by actually | ||
4410 | performing a move based on the current cursor location. | ||
4411 | |||
4412 | - You might want an additional `game_ui' field stating whether the | ||
4413 | cursor is currently visible, and having it disappear when a mouse | ||
4414 | action occurs (so that it doesn't clutter the display when not | ||
4415 | actually in use). | ||
4416 | |||
4417 | - You might also want to automatically hide the cursor in | ||
4418 | changed_state() when the current game state changes to one in | ||
4419 | which there is no move to make (which is the case in some types of | ||
4420 | completed game). | ||
4421 | |||
4422 | - redraw() draws the cursor using the technique described in section | ||
4423 | 6.3.1. | ||
4424 | |||
4425 | #6.3.3. Implementing draggable sprites | ||
4426 | |||
4427 | Some games have a user interface which involves dragging some sort of | ||
4428 | game element around using the mouse. If you need to show a graphic | ||
4429 | moving smoothly over the top of other graphics, use a blitter (see | ||
4430 | section 3.1.13 for the blitter API) to save the background underneath | ||
4431 | it. The typical scenario goes: | ||
4432 | |||
4433 | - Have a blitter field in the `game_drawstate'. | ||
4434 | |||
4435 | - Set the blitter field to NULL in the game's new_drawstate() | ||
4436 | function, since you don't yet know how big the piece of saved | ||
4437 | background needs to be. | ||
4438 | |||
4439 | - In the game's set_size() function, once you know the size of the | ||
4440 | object you'll be dragging around the display and hence the required | ||
4441 | size of the blitter, actually allocate the blitter. | ||
4442 | |||
4443 | - In free_drawstate(), free the blitter if it's not NULL. | ||
4444 | |||
4445 | - In interpret_move(), respond to mouse-down and mouse-drag events by | ||
4446 | updating some fields in the game_ui which indicate that a drag is in | ||
4447 | progress. | ||
4448 | |||
4449 | - At the _very end_ of redraw(), after all other drawing has been | ||
4450 | done, draw the moving object if there is one. First save the | ||
4451 | background under the object in the blitter; then set a clip | ||
4452 | rectangle covering precisely the area you just saved (just in case | ||
4453 | anti-aliasing or some other error causes your drawing to go beyond | ||
4454 | the area you saved). Then draw the object, and call unclip(). | ||
4455 | Finally, set a flag in the game_drawstate that indicates that the | ||
4456 | blitter needs restoring. | ||
4457 | |||
4458 | - At the very start of redraw(), before doing anything else at all, | ||
4459 | check the flag in the game_drawstate, and if it says the blitter | ||
4460 | needs restoring then restore it. (Then clear the flag, so that this | ||
4461 | won't happen again in the next redraw if no moving object is drawn | ||
4462 | this time.) | ||
4463 | |||
4464 | This way, you will be able to write the rest of the redraw function | ||
4465 | completely ignoring the dragged object, as if it were floating above | ||
4466 | your bitmap and being completely separate. | ||
4467 | |||
4468 | #6.3.4. Sharing large invariant data between all game states | ||
4469 | |||
4470 | In some puzzles, there is a large amount of data which never changes | ||
4471 | between game states. The array of numbers in Dominosa is a good example. | ||
4472 | |||
4473 | You _could_ dynamically allocate a copy of that array in every | ||
4474 | `game_state', and have dup_game() make a fresh copy of it for every new | ||
4475 | `game_state'; but it would waste memory and time. A more efficient way | ||
4476 | is to use a reference-counted structure. | ||
4477 | |||
4478 | - Define a structure type containing the data in question, and also | ||
4479 | containing an integer reference count. | ||
4480 | |||
4481 | - Have a field in `game_state' which is a pointer to this structure. | ||
4482 | |||
4483 | - In new_game(), when creating a fresh game state at the start of a | ||
4484 | new game, create an instance of this structure, initialise it with | ||
4485 | the invariant data, and set its reference count to 1. | ||
4486 | |||
4487 | - In dup_game(), rather than making a copy of the structure for the | ||
4488 | new game state, simply set the new game state to point at the same | ||
4489 | copy of the structure, and increment its reference count. | ||
4490 | |||
4491 | - In free_game(), decrement the reference count in the structure | ||
4492 | pointed to by the game state; if the count reaches zero, free the | ||
4493 | structure. | ||
4494 | |||
4495 | This way, the invariant data will persist for only as long as it's | ||
4496 | genuinely needed; _as soon_ as the last game state for a particular | ||
4497 | puzzle instance is freed, the invariant data for that puzzle will | ||
4498 | vanish as well. Reference counting is a very efficient form of garbage | ||
4499 | collection, when it works at all. (Which it does in this instance, of | ||
4500 | course, because there's no possibility of circular references.) | ||
4501 | |||
4502 | #6.3.5. Implementing multiple types of flash | ||
4503 | |||
4504 | In some games you need to flash in more than one different way. Mines, | ||
4505 | for example, flashes white when you win, and flashes red when you tread | ||
4506 | on a mine and die. | ||
4507 | |||
4508 | The simple way to do this is: | ||
4509 | |||
4510 | - Have a field in the `game_ui' which describes the type of flash. | ||
4511 | |||
4512 | - In flash_length(), examine the old and new game states to decide | ||
4513 | whether a flash is required and what type. Write the type of flash | ||
4514 | to the `game_ui' field whenever you return non-zero. | ||
4515 | |||
4516 | - In redraw(), when you detect that `flash_time' is non-zero, examine | ||
4517 | the field in `game_ui' to decide which type of flash to draw. | ||
4518 | |||
4519 | redraw() will never be called with `flash_time' non-zero unless | ||
4520 | flash_length() was first called to tell the mid-end that a flash was | ||
4521 | required; so whenever redraw() notices that `flash_time' is non-zero, | ||
4522 | you can be sure that the field in `game_ui' is correctly set. | ||
4523 | |||
4524 | #6.3.6. Animating game moves | ||
4525 | |||
4526 | A number of puzzle types benefit from a quick animation of each move you | ||
4527 | make. | ||
4528 | |||
4529 | For some games, such as Fifteen, this is particularly easy. Whenever | ||
4530 | redraw() is called with `oldstate' non-NULL, Fifteen simply compares the | ||
4531 | position of each tile in the two game states, and if the tile is not in | ||
4532 | the same place then it draws it some fraction of the way from its old | ||
4533 | position to its new position. This method copes automatically with undo. | ||
4534 | |||
4535 | Other games are less obvious. In Sixteen, for example, you can't just | ||
4536 | draw each tile a fraction of the way from its old to its new position: | ||
4537 | if you did that, the end tile would zip very rapidly past all the others | ||
4538 | to get to the other end and that would look silly. (Worse, it would look | ||
4539 | inconsistent if the end tile was drawn on top going one way and on the | ||
4540 | bottom going the other way.) | ||
4541 | |||
4542 | A useful trick here is to define a field or two in the game state that | ||
4543 | indicates what the last move was. | ||
4544 | |||
4545 | - Add a `last move' field to the `game_state' (or two or more fields | ||
4546 | if the move is complex enough to need them). | ||
4547 | |||
4548 | - new_game() initialises this field to a null value for a new game | ||
4549 | state. | ||
4550 | |||
4551 | - execute_move() sets up the field to reflect the move it just | ||
4552 | performed. | ||
4553 | |||
4554 | - redraw() now needs to examine its `dir' parameter. If `dir' is | ||
4555 | positive, it determines the move being animated by looking at the | ||
4556 | last-move field in `newstate'; but if `dir' is negative, it has to | ||
4557 | look at the last-move field in `oldstate', and invert whatever move | ||
4558 | it finds there. | ||
4559 | |||
4560 | Note also that Sixteen needs to store the _direction_ of the move, | ||
4561 | because you can't quite determine it by examining the row or column in | ||
4562 | question. You can in almost all cases, but when the row is precisely | ||
4563 | two squares long it doesn't work since a move in either direction looks | ||
4564 | the same. (You could argue that since moving a 2-element row left and | ||
4565 | right has the same effect, it doesn't matter which one you animate; but | ||
4566 | in fact it's very disorienting to click the arrow left and find the row | ||
4567 | moving right, and almost as bad to undo a move to the right and find the | ||
4568 | game animating _another_ move to the right.) | ||
4569 | |||
4570 | #6.3.7. Animating drag operations | ||
4571 | |||
4572 | In Untangle, moves are made by dragging a node from an old position to a | ||
4573 | new position. Therefore, at the time when the move is initially made, it | ||
4574 | should not be animated, because the node has already been dragged to the | ||
4575 | right place and doesn't need moving there. However, it's nice to animate | ||
4576 | the same move if it's later undone or redone. This requires a bit of | ||
4577 | fiddling. | ||
4578 | |||
4579 | The obvious approach is to have a flag in the `game_ui' which inhibits | ||
4580 | move animation, and to set that flag in interpret_move(). The question | ||
4581 | is, when would the flag be reset again? The obvious place to do so | ||
4582 | is changed_state(), which will be called once per move. But it will | ||
4583 | be called _before_ anim_length(), so if it resets the flag then | ||
4584 | anim_length() will never see the flag set at all. | ||
4585 | |||
4586 | The solution is to have _two_ flags in a queue. | ||
4587 | |||
4588 | - Define two flags in `game_ui'; let's call them `current' and `next'. | ||
4589 | |||
4590 | - Set both to FALSE in `new_ui()'. | ||
4591 | |||
4592 | - When a drag operation completes in interpret_move(), set the `next' | ||
4593 | flag to TRUE. | ||
4594 | |||
4595 | - Every time changed_state() is called, set the value of `current' to | ||
4596 | the value in `next', and then set the value of `next' to FALSE. | ||
4597 | |||
4598 | - That way, `current' will be TRUE _after_ a call to changed_state() | ||
4599 | if and only if that call to changed_state() was the result of a | ||
4600 | drag operation processed by interpret_move(). Any other call to | ||
4601 | changed_state(), due to an Undo or a Redo or a Restart or a Solve, | ||
4602 | will leave `current' FALSE. | ||
4603 | |||
4604 | - So now anim_length() can request a move animation if and only if the | ||
4605 | `current' flag is _not_ set. | ||
4606 | |||
4607 | #6.3.8. Inhibiting the victory flash when Solve is used | ||
4608 | |||
4609 | Many games flash when you complete them, as a visual congratulation for | ||
4610 | having got to the end of the puzzle. It often seems like a good idea to | ||
4611 | disable that flash when the puzzle is brought to a solved state by means | ||
4612 | of the Solve operation. | ||
4613 | |||
4614 | This is easily done: | ||
4615 | |||
4616 | - Add a `cheated' flag to the `game_state'. | ||
4617 | |||
4618 | - Set this flag to FALSE in new_game(). | ||
4619 | |||
4620 | - Have solve() return a move description string which clearly | ||
4621 | identifies the move as a solve operation. | ||
4622 | |||
4623 | - Have execute_move() respond to that clear identification by setting | ||
4624 | the `cheated' flag in the returned `game_state'. The flag will | ||
4625 | then be propagated to all subsequent game states, even if the user | ||
4626 | continues fiddling with the game after it is solved. | ||
4627 | |||
4628 | - flash_length() now returns non-zero if `oldstate' is not completed | ||
4629 | and `newstate' is, _and_ neither state has the `cheated' flag set. | ||
4630 | |||
4631 | #6.4. Things to test once your puzzle is written | ||
4632 | |||
4633 | Puzzle implementations written in this framework are self-testing as far | ||
4634 | as I could make them. | ||
4635 | |||
4636 | Textual game and move descriptions, for example, are generated and | ||
4637 | parsed as part of the normal process of play. Therefore, if you can make | ||
4638 | moves in the game _at all_ you can be reasonably confident that the | ||
4639 | mid-end serialisation interface will function correctly and you will | ||
4640 | be able to save your game. (By contrast, if I'd stuck with a single | ||
4641 | make_move() function performing the jobs of both interpret_move() and | ||
4642 | execute_move(), and had separate functions to encode and decode a game | ||
4643 | state in string form, then those functions would not be used during | ||
4644 | normal play; so they could have been completely broken, and you'd never | ||
4645 | know it until you tried to save the game - which would have meant you'd | ||
4646 | have to test game saving _extensively_ and make sure to test every | ||
4647 | possible type of game state. As an added bonus, doing it the way I did | ||
4648 | leads to smaller save files.) | ||
4649 | |||
4650 | There is one exception to this, which is the string encoding of the | ||
4651 | `game_ui'. Most games do not store anything permanent in the `game_ui', | ||
4652 | and hence do not need to put anything in its encode and decode | ||
4653 | functions; but if there is anything in there, you do need to test game | ||
4654 | loading and saving to ensure those functions work properly. | ||
4655 | |||
4656 | It's also worth testing undo and redo of all operations, to ensure that | ||
4657 | the redraw and the animations (if any) work properly. Failing to animate | ||
4658 | undo properly seems to be a common error. | ||
4659 | |||
4660 | Other than that, just use your common sense. | ||
4661 | |||