OSDN Git Service

変わり身状態の忍者が幻覚などの状態異常を持っていると変わり身が無効に
[hengbandforosx/hengbandosx.git] / src / cmd4.c
1 /* File: cmd4.c */
2
3 /*
4  * Copyright (c) 1997 Ben Harrison, James E. Wilson, Robert A. Koeneke
5  *
6  * This software may be copied and distributed for educational, research,
7  * and not for profit purposes provided that this copyright and statement
8  * are included in all such copies.  Other copyrights may also apply.
9  */
10
11 /* Purpose: Interface commands */
12
13 #include "angband.h"
14
15
16
17 /*
18  * A set of functions to maintain automatic dumps of various kinds.
19  * -Mogami-
20  *
21  * remove_auto_dump(orig_file, mark)
22  *     Remove the old automatic dump of type "mark".
23  * auto_dump_printf(fmt, ...)
24  *     Dump a formatted string using fprintf().
25  * open_auto_dump(buf, mark)
26  *     Open a file, remove old dump, and add new header.
27  * close_auto_dump(void)
28  *     Add a footer, and close the file.
29  *
30  *    The dump commands of original Angband simply add new lines to
31  * existing files; these files will become bigger and bigger unless
32  * an user deletes some or all of these files by hand at some
33  * point.
34  *
35  *     These three functions automatically delete old dumped lines 
36  * before adding new ones.  Since there are various kinds of automatic 
37  * dumps in a single file, we add a header and a footer with a type 
38  * name for every automatic dump, and kill old lines only when the 
39  * lines have the correct type of header and footer.
40  *
41  *     We need to be quite paranoid about correctness; the user might 
42  * (mistakenly) edit the file by hand, and see all their work come
43  * to nothing on the next auto dump otherwise.  The current code only 
44  * detects changes by noting inconsistencies between the actual number 
45  * of lines and the number written in the footer.  Note that this will 
46  * not catch single-line edits.
47  */
48
49 /*
50  *  Mark strings for auto dump
51  */
52 static char auto_dump_header[] = "# vvvvvvv== %s ==vvvvvvv";
53 static char auto_dump_footer[] = "# ^^^^^^^== %s ==^^^^^^^";
54
55 /*
56  * Variables for auto dump
57  */
58 static FILE *auto_dump_stream;
59 static cptr auto_dump_mark;
60 static int auto_dump_line_num;
61
62 /*
63  * Remove old lines automatically generated before.
64  */
65 static void remove_auto_dump(cptr orig_file)
66 {
67         FILE *tmp_fff, *orig_fff;
68
69         char tmp_file[1024];
70         char buf[1024];
71         bool between_mark = FALSE;
72         bool changed = FALSE;
73         int line_num = 0;
74         long header_location = 0;
75         char header_mark_str[80];
76         char footer_mark_str[80];
77         size_t mark_len;
78
79         /* Prepare a header/footer mark string */
80         sprintf(header_mark_str, auto_dump_header, auto_dump_mark);
81         sprintf(footer_mark_str, auto_dump_footer, auto_dump_mark);
82
83         mark_len = strlen(footer_mark_str);
84
85         /* Open an old dump file in read-only mode */
86         orig_fff = my_fopen(orig_file, "r");
87
88         /* If original file does not exist, nothing to do */
89         if (!orig_fff) return;
90
91         /* Open a new (temporary) file */
92         tmp_fff = my_fopen_temp(tmp_file, 1024);
93
94         if (!tmp_fff)
95         {
96 #ifdef JP
97             msg_format("°ì»þ¥Õ¥¡¥¤¥ë %s ¤òºîÀ®¤Ç¤­¤Þ¤»¤ó¤Ç¤·¤¿¡£", tmp_file);
98 #else
99             msg_format("Failed to create temporary file %s.", tmp_file);
100 #endif
101             msg_print(NULL);
102             return;
103         }
104
105         /* Loop for every line */
106         while (TRUE)
107         {
108                 /* Read a line */
109                 if (my_fgets(orig_fff, buf, sizeof(buf)))
110                 {
111                         /* Read error: Assume End of File */
112
113                         /*
114                          * Was looking for the footer, but not found.
115                          *
116                          * Since automatic dump might be edited by hand,
117                          * it's dangerous to kill these lines.
118                          * Seek back to the next line of the (pseudo) header,
119                          * and read again.
120                          */
121                         if (between_mark)
122                         {
123                                 fseek(orig_fff, header_location, SEEK_SET);
124                                 between_mark = FALSE;
125                                 continue;
126                         }
127
128                         /* Success -- End the loop */
129                         else
130                         {
131                                 break;
132                         }
133                 }
134
135                 /* We are looking for the header mark of automatic dump */
136                 if (!between_mark)
137                 {
138                         /* Is this line a header? */
139                         if (!strcmp(buf, header_mark_str))
140                         {
141                                 /* Memorise seek point of this line */
142                                 header_location = ftell(orig_fff);
143
144                                 /* Initialize counter for number of lines */
145                                 line_num = 0;
146
147                                 /* Look for the footer from now */
148                                 between_mark = TRUE;
149
150                                 /* There are some changes */
151                                 changed = TRUE;
152                         }
153
154                         /* Not a header */
155                         else
156                         {
157                                 /* Copy orginally lines */
158                                 fprintf(tmp_fff, "%s\n", buf);
159                         }
160                 }
161
162                 /* We are looking for the footer mark of automatic dump */
163                 else
164                 {
165                         /* Is this line a footer? */
166                         if (!strncmp(buf, footer_mark_str, mark_len))
167                         {
168                                 int tmp;
169
170                                 /*
171                                  * Compare the number of lines
172                                  *
173                                  * If there is an inconsistency between
174                                  * actual number of lines and the
175                                  * number here, the automatic dump
176                                  * might be edited by hand.  So it's
177                                  * dangerous to kill these lines.
178                                  * Seek back to the next line of the
179                                  * (pseudo) header, and read again.
180                                  */
181                                 if (!sscanf(buf + mark_len, " (%d)", &tmp)
182                                     || tmp != line_num)
183                                 {
184                                         fseek(orig_fff, header_location, SEEK_SET);
185                                 }
186
187                                 /* Look for another header */
188                                 between_mark = FALSE;
189                         }
190
191                         /* Not a footer */
192                         else
193                         {
194                                 /* Ignore old line, and count number of lines */
195                                 line_num++;
196                         }
197                 }
198         }
199
200         /* Close files */
201         my_fclose(orig_fff);
202         my_fclose(tmp_fff);
203
204         /* If there are some changes, overwrite the original file with new one */
205         if (changed)
206         {
207                 /* Copy contents of temporary file */
208
209                 tmp_fff = my_fopen(tmp_file, "r");
210                 orig_fff = my_fopen(orig_file, "w");
211
212                 while (!my_fgets(tmp_fff, buf, sizeof(buf)))
213                         fprintf(orig_fff, "%s\n", buf);
214
215                 my_fclose(orig_fff);
216                 my_fclose(tmp_fff);
217         }
218
219         /* Kill the temporary file */
220         fd_kill(tmp_file);
221
222         return;
223 }
224
225
226 /*
227  * Dump a formatted line, using "vstrnfmt()".
228  */
229 static void auto_dump_printf(cptr fmt, ...)
230 {
231         cptr p;
232         va_list vp;
233
234         char buf[1024];
235
236         /* Begin the Varargs Stuff */
237         va_start(vp, fmt);
238
239         /* Format the args, save the length */
240         (void)vstrnfmt(buf, sizeof(buf), fmt, vp);
241
242         /* End the Varargs Stuff */
243         va_end(vp);
244
245         /* Count number of lines */
246         for (p = buf; *p; p++)
247         {
248                 if (*p == '\n') auto_dump_line_num++;
249         }
250
251         /* Dump it */
252         fprintf(auto_dump_stream, "%s", buf);
253 }
254
255
256 /*
257  *  Open file to append auto dump.
258  */
259 static bool open_auto_dump(cptr buf, cptr mark)
260 {
261
262         char header_mark_str[80];
263
264         /* Save the mark string */
265         auto_dump_mark = mark;
266
267         /* Prepare a header mark string */
268         sprintf(header_mark_str, auto_dump_header, auto_dump_mark);
269
270         /* Remove old macro dumps */
271         remove_auto_dump(buf);
272
273         /* Append to the file */
274         auto_dump_stream = my_fopen(buf, "a");
275
276         /* Failure */
277         if (!auto_dump_stream) {
278 #ifdef JP
279                 msg_format("%s ¤ò³«¤¯¤³¤È¤¬¤Ç¤­¤Þ¤»¤ó¤Ç¤·¤¿¡£", buf);
280 #else
281                 msg_format("Failed to open %s.", buf);
282 #endif
283                 msg_print(NULL);
284
285                 /* Failed */
286                 return FALSE;
287         }
288
289         /* Start dumping */
290         fprintf(auto_dump_stream, "%s\n", header_mark_str);
291
292         /* Initialize counter */
293         auto_dump_line_num = 0;
294
295 #ifdef JP
296         auto_dump_printf("# *·Ù¹ð!!* °Ê¹ß¤Î¹Ô¤Ï¼«Æ°À¸À®¤µ¤ì¤¿¤â¤Î¤Ç¤¹¡£\n");
297         auto_dump_printf("# *·Ù¹ð!!* ¸å¤Ç¼«Æ°Åª¤Ëºï½ü¤µ¤ì¤ë¤Î¤ÇÊÔ½¸¤·¤Ê¤¤¤Ç¤¯¤À¤µ¤¤¡£\n");
298 #else
299         auto_dump_printf("# *Warning!*  The lines below are an automatic dump.\n");
300         auto_dump_printf("# Don't edit them; changes will be deleted and replaced automatically.\n");
301 #endif
302
303         /* Success */
304         return TRUE;
305 }
306
307 /*
308  *  Append foot part and close auto dump.
309  */
310 static void close_auto_dump(void)
311 {
312         char footer_mark_str[80];
313
314         /* Prepare a footer mark string */
315         sprintf(footer_mark_str, auto_dump_footer, auto_dump_mark);
316
317 #ifdef JP
318         auto_dump_printf("# *·Ù¹ð!!* °Ê¾å¤Î¹Ô¤Ï¼«Æ°À¸À®¤µ¤ì¤¿¤â¤Î¤Ç¤¹¡£\n");
319         auto_dump_printf("# *·Ù¹ð!!* ¸å¤Ç¼«Æ°Åª¤Ëºï½ü¤µ¤ì¤ë¤Î¤ÇÊÔ½¸¤·¤Ê¤¤¤Ç¤¯¤À¤µ¤¤¡£\n");
320 #else
321         auto_dump_printf("# *Warning!*  The lines above are an automatic dump.\n");
322         auto_dump_printf("# Don't edit them; changes will be deleted and replaced automatically.\n");
323 #endif
324
325         /* End of dump */
326         fprintf(auto_dump_stream, "%s (%d)\n", footer_mark_str, auto_dump_line_num);
327
328         /* Close */
329         my_fclose(auto_dump_stream);
330
331         return;
332 }
333
334
335 #ifndef JP
336 /*
337  * Return suffix of ordinal number
338  */
339 cptr get_ordinal_number_suffix(int num)
340 {
341         num = ABS(num) % 100;
342         switch (num % 10)
343         {
344         case 1:
345                 return (num == 11) ? "th" : "st";
346         case 2:
347                 return (num == 12) ? "th" : "nd";
348         case 3:
349                 return (num == 13) ? "th" : "rd";
350         default:
351                 return "th";
352         }
353 }
354 #endif
355
356
357 /*
358  *   Take note to the diary.
359  */
360 errr do_cmd_write_nikki(int type, int num, cptr note)
361 {
362         int day, hour, min;
363         FILE *fff = NULL;
364         char file_name[80];
365         char buf[1024];
366         cptr note_level = "";
367         bool do_level = TRUE;
368         char note_level_buf[40];
369         int q_idx;
370
371         static bool disable_nikki = FALSE;
372
373         extract_day_hour_min(&day, &hour, &min);
374
375         if (disable_nikki) return(-1);
376
377         if (type == NIKKI_FIX_QUEST_C ||
378             type == NIKKI_FIX_QUEST_F ||
379             type == NIKKI_RAND_QUEST_C ||
380             type == NIKKI_RAND_QUEST_F ||
381             type == NIKKI_TO_QUEST)
382         {
383                 int old_quest;
384
385                 old_quest = p_ptr->inside_quest;
386                 p_ptr->inside_quest = (quest[num].type == QUEST_TYPE_RANDOM) ? 0 : num;
387
388                 /* Get the quest text */
389                 init_flags = INIT_ASSIGN;
390
391                 process_dungeon_file("q_info.txt", 0, 0, 0, 0);
392
393                 /* Reset the old quest number */
394                 p_ptr->inside_quest = old_quest;
395         }
396
397 #ifdef JP
398         sprintf(file_name,"playrecord-%s.txt",savefile_base);
399 #else
400         /* different filne name to avoid mixing */
401         sprintf(file_name,"playrec-%s.txt",savefile_base);
402 #endif
403
404         /* Build the filename */
405         path_build(buf, sizeof(buf), ANGBAND_DIR_USER, file_name);
406
407         /* File type is "TEXT" */
408         FILE_TYPE(FILE_TYPE_TEXT);
409
410         fff = my_fopen(buf, "a");
411
412         /* Failure */
413         if (!fff)
414         {
415 #ifdef JP
416                 msg_format("%s ¤ò³«¤¯¤³¤È¤¬¤Ç¤­¤Þ¤»¤ó¤Ç¤·¤¿¡£¥×¥ì¥¤µ­Ï¿¤ò°ì»þÄä»ß¤·¤Þ¤¹¡£", buf);
417 #else
418                 msg_format("Failed to open %s. Play-Record is disabled temporally.", buf);
419 #endif
420                 msg_format(NULL);
421                 disable_nikki=TRUE;
422                 return (-1);
423         }
424
425         q_idx = quest_number(dun_level);
426
427         if (write_level)
428         {
429                 if (p_ptr->inside_arena)
430 #ifdef JP
431                         note_level = "¥¢¥ê¡¼¥Ê:";
432 #else
433                         note_level = "Arane:";
434 #endif
435                 else if (!dun_level)
436 #ifdef JP
437                         note_level = "ÃϾå:";
438 #else
439                         note_level = "Surface:";
440 #endif
441                 else if (q_idx && (is_fixed_quest_idx(q_idx)
442                          && !((q_idx == QUEST_OBERON) || (q_idx == QUEST_SERPENT))))
443 #ifdef JP
444                         note_level = "¥¯¥¨¥¹¥È:";
445 #else
446                         note_level = "Quest:";
447 #endif
448                 else
449                 {
450 #ifdef JP
451                         sprintf(note_level_buf, "%d³¬(%s):", dun_level, d_name+d_info[dungeon_type].name);
452 #else
453                         sprintf(note_level_buf, "%s L%d:", d_name+d_info[dungeon_type].name, dun_level);
454 #endif
455                         note_level = note_level_buf;
456                 }
457         }
458
459         switch(type)
460         {
461                 case NIKKI_HIGAWARI:
462                 {
463 #ifdef JP
464                         if (day < MAX_DAYS) fprintf(fff, "%dÆüÌÜ\n", day);
465                         else fputs("*****ÆüÌÜ\n", fff);
466 #else
467                         if (day < MAX_DAYS) fprintf(fff, "Day %d\n", day);
468                         else fputs("Day *****\n", fff);
469 #endif
470                         do_level = FALSE;
471                         break;
472                 }
473                 case NIKKI_BUNSHOU:
474                 {
475                         if (num)
476                         {
477                                 fprintf(fff, "%s\n",note);
478                                 do_level = FALSE;
479                         }
480                         else
481                                 fprintf(fff, " %2d:%02d %20s %s\n",hour, min, note_level, note);
482                         break;
483                 }
484                 case NIKKI_ART:
485                 {
486 #ifdef JP
487                         fprintf(fff, " %2d:%02d %20s %s¤òȯ¸«¤·¤¿¡£\n", hour, min, note_level, note);
488 #else
489                         fprintf(fff, " %2d:%02d %20s discovered %s.\n", hour, min, note_level, note);
490 #endif
491                         break;
492                 }
493                 case NIKKI_UNIQUE:
494                 {
495 #ifdef JP
496                         fprintf(fff, " %2d:%02d %20s %s¤òÅݤ·¤¿¡£\n", hour, min, note_level, note);
497 #else
498                         fprintf(fff, " %2d:%02d %20s defeated %s.\n", hour, min, note_level, note);
499 #endif
500                         break;
501                 }
502                 case NIKKI_FIX_QUEST_C:
503                 {
504                         if (quest[num].flags & QUEST_FLAG_SILENT) break;
505 #ifdef JP
506                         fprintf(fff, " %2d:%02d %20s ¥¯¥¨¥¹¥È¡Ö%s¡×¤òãÀ®¤·¤¿¡£\n", hour, min, note_level, quest[num].name);
507 #else
508                         fprintf(fff, " %2d:%02d %20s completed quest '%s'.\n", hour, min, note_level, quest[num].name);
509 #endif
510                         break;
511                 }
512                 case NIKKI_FIX_QUEST_F:
513                 {
514                         if (quest[num].flags & QUEST_FLAG_SILENT) break;
515 #ifdef JP
516                         fprintf(fff, " %2d:%02d %20s ¥¯¥¨¥¹¥È¡Ö%s¡×¤«¤éÌ¿¤«¤é¤¬¤éƨ¤²µ¢¤Ã¤¿¡£\n", hour, min, note_level, quest[num].name);
517 #else
518                         fprintf(fff, " %2d:%02d %20s run away from quest '%s'.\n", hour, min, note_level, quest[num].name);
519 #endif
520                         break;
521                 }
522                 case NIKKI_RAND_QUEST_C:
523                 {
524                         char name[80];
525                         strcpy(name, r_name+r_info[quest[num].r_idx].name);
526 #ifdef JP
527                         fprintf(fff, " %2d:%02d %20s ¥é¥ó¥À¥à¥¯¥¨¥¹¥È(%s)¤òãÀ®¤·¤¿¡£\n", hour, min, note_level, name);
528 #else
529                         fprintf(fff, " %2d:%02d %20s completed random quest '%s'\n", hour, min, note_level, name);
530 #endif
531                         break;
532                 }
533                 case NIKKI_RAND_QUEST_F:
534                 {
535                         char name[80];
536                         strcpy(name, r_name+r_info[quest[num].r_idx].name);
537 #ifdef JP
538                         fprintf(fff, " %2d:%02d %20s ¥é¥ó¥À¥à¥¯¥¨¥¹¥È(%s)¤«¤éƨ¤²½Ð¤·¤¿¡£\n", hour, min, note_level, name);
539 #else
540                         fprintf(fff, " %2d:%02d %20s ran away from quest '%s'.\n", hour, min, note_level, name);
541 #endif
542                         break;
543                 }
544                 case NIKKI_MAXDEAPTH:
545                 {
546 #ifdef JP
547                         fprintf(fff, " %2d:%02d %20s %s¤ÎºÇ¿¼³¬%d³¬¤ËÅþ㤷¤¿¡£\n", hour, min, note_level, d_name+d_info[dungeon_type].name, num);
548 #else
549                         fprintf(fff, " %2d:%02d %20s reached level %d of %s for the first time.\n", hour, min, note_level, num, d_name+d_info[dungeon_type].name);
550 #endif
551                         break;
552                 }
553                 case NIKKI_TRUMP:
554                 {
555 #ifdef JP
556                         fprintf(fff, " %2d:%02d %20s %s%s¤ÎºÇ¿¼³¬¤ò%d³¬¤Ë¥»¥Ã¥È¤·¤¿¡£\n", hour, min, note_level, note, d_name + d_info[num].name, max_dlv[num]);
557 #else
558                         fprintf(fff, " %2d:%02d %20s reset recall level of %s to %d %s.\n", hour, min, note_level, d_name + d_info[num].name, max_dlv[num], note);
559 #endif
560                         break;
561                 }
562                 case NIKKI_STAIR:
563                 {
564                         cptr to;
565                         if (q_idx && (is_fixed_quest_idx(q_idx)
566                              && !((q_idx == QUEST_OBERON) || (q_idx == QUEST_SERPENT))))
567                         {
568 #ifdef JP
569                                 to = "ÃϾå";
570 #else
571                                 to = "the surface";
572 #endif
573                         }
574                         else
575                         {
576 #ifdef JP
577                                 if (!(dun_level+num)) to = "ÃϾå";
578                                 else to = format("%d³¬", dun_level+num);
579 #else
580                                 if (!(dun_level+num)) to = "the surface";
581                                 else to = format("level %d", dun_level+num);
582 #endif
583                         }
584
585 #ifdef JP 
586                         fprintf(fff, " %2d:%02d %20s %s¤Ø%s¡£\n", hour, min, note_level, to, note);
587 #else
588                         fprintf(fff, " %2d:%02d %20s %s %s.\n", hour, min, note_level, note, to);
589 #endif
590                         break;
591                 }
592                 case NIKKI_RECALL:
593                 {
594                         if (!num)
595 #ifdef JP
596                                 fprintf(fff, " %2d:%02d %20s µ¢´Ô¤ò»È¤Ã¤Æ%s¤Î%d³¬¤Ø²¼¤ê¤¿¡£\n", hour, min, note_level, d_name+d_info[dungeon_type].name, max_dlv[dungeon_type]);
597 #else
598                                 fprintf(fff, " %2d:%02d %20s recalled to dungeon level %d of %s.\n", hour, min, note_level, max_dlv[dungeon_type], d_name+d_info[dungeon_type].name);
599 #endif
600                         else
601 #ifdef JP
602                                 fprintf(fff, " %2d:%02d %20s µ¢´Ô¤ò»È¤Ã¤ÆÃϾå¤Ø¤ÈÌá¤Ã¤¿¡£\n", hour, min, note_level);
603 #else
604                                 fprintf(fff, " %2d:%02d %20s recalled from dungeon to surface.\n", hour, min, note_level);
605 #endif
606                         break;
607                 }
608                 case NIKKI_TO_QUEST:
609                 {
610                         if (quest[num].flags & QUEST_FLAG_SILENT) break;
611 #ifdef JP
612                         fprintf(fff, " %2d:%02d %20s ¥¯¥¨¥¹¥È¡Ö%s¡×¤Ø¤ÈÆÍÆþ¤·¤¿¡£\n", hour, min, note_level, quest[num].name);
613 #else
614                         fprintf(fff, " %2d:%02d %20s entered the quest '%s'.\n", hour, min, note_level, quest[num].name);
615 #endif
616                         break;
617                 }
618                 case NIKKI_TELE_LEV:
619                 {
620 #ifdef JP
621                         fprintf(fff, " %2d:%02d %20s ¥ì¥Ù¥ë¡¦¥Æ¥ì¥Ý¡¼¥È¤Çæ½Ð¤·¤¿¡£\n", hour, min, note_level);
622 #else
623                         fprintf(fff, " %2d:%02d %20s Got out using teleport level.\n", hour, min, note_level);
624 #endif
625                         break;
626                 }
627                 case NIKKI_BUY:
628                 {
629 #ifdef JP
630                         fprintf(fff, " %2d:%02d %20s %s¤ò¹ØÆþ¤·¤¿¡£\n", hour, min, note_level, note);
631 #else
632                         fprintf(fff, " %2d:%02d %20s bought %s.\n", hour, min, note_level, note);
633 #endif
634                         break;
635                 }
636                 case NIKKI_SELL:
637                 {
638 #ifdef JP
639                         fprintf(fff, " %2d:%02d %20s %s¤òÇäµÑ¤·¤¿¡£\n", hour, min, note_level, note);
640 #else
641                         fprintf(fff, " %2d:%02d %20s sold %s.\n", hour, min, note_level, note);
642 #endif
643                         break;
644                 }
645                 case NIKKI_ARENA:
646                 {
647                         if (num < 0)
648                         {
649 #ifdef JP
650                                 fprintf(fff, " %2d:%02d %20s Æ®µ»¾ì¤Î%d²óÀï¤Ç¡¢%s¤ÎÁ°¤ËÇÔ¤ìµî¤Ã¤¿¡£\n", hour, min, note_level, -num, note);
651 #else
652                                 int n = -num;
653                                 fprintf(fff, " %2d:%02d %20s beaten by %s in the %d%s fight.\n", hour, min, note_level, note, n, get_ordinal_number_suffix(n));
654 #endif
655                                 break;
656                         }
657 #ifdef JP
658                         fprintf(fff, " %2d:%02d %20s Æ®µ»¾ì¤Î%d²óÀï(%s)¤Ë¾¡Íø¤·¤¿¡£\n", hour, min, note_level, num, note);
659 #else
660                         fprintf(fff, " %2d:%02d %20s won the %d%s fight (%s).\n", hour, min, note_level, num, get_ordinal_number_suffix(num), note);
661 #endif
662                         if (num == MAX_ARENA_MONS)
663                         {
664 #ifdef JP
665                                 fprintf(fff, "                 Æ®µ»¾ì¤Î¤¹¤Ù¤Æ¤ÎŨ¤Ë¾¡Íø¤·¡¢¥Á¥ã¥ó¥Ô¥ª¥ó¤È¤Ê¤Ã¤¿¡£\n");
666 #else
667                                 fprintf(fff, "                 won all fight to become a Chanpion.\n");
668 #endif
669                                 do_level = FALSE;
670                         }
671                         break;
672                 }
673                 case NIKKI_HANMEI:
674                 {
675 #ifdef JP
676                         fprintf(fff, " %2d:%02d %20s %s¤ò¼±Ê̤·¤¿¡£\n", hour, min, note_level, note);
677 #else
678                         fprintf(fff, " %2d:%02d %20s identified %s.\n", hour, min, note_level, note);
679 #endif
680                         break;
681                 }
682                 case NIKKI_WIZ_TELE:
683                 {
684                         cptr to;
685                         if (!dun_level)
686 #ifdef JP
687                                 to = "ÃϾå";
688 #else
689                                 to = "the surface";
690 #endif
691                         else
692 #ifdef JP
693                                 to = format("%d³¬(%s)", dun_level, d_name+d_info[dungeon_type].name);
694 #else
695                                 to = format("level %d of %s", dun_level, d_name+d_info[dungeon_type].name);
696 #endif
697
698 #ifdef JP
699                         fprintf(fff, " %2d:%02d %20s %s¤Ø¤È¥¦¥£¥¶¡¼¥É¡¦¥Æ¥ì¥Ý¡¼¥È¤Ç°ÜÆ°¤·¤¿¡£\n", hour, min, note_level, to);
700 #else
701                         fprintf(fff, " %2d:%02d %20s wizard-teleport to %s.\n", hour, min, note_level, to);
702 #endif
703                         break;
704                 }
705                 case NIKKI_PAT_TELE:
706                 {
707                         cptr to;
708                         if (!dun_level)
709 #ifdef JP
710                                 to = "ÃϾå";
711 #else
712                                 to = "the surface";
713 #endif
714                         else
715 #ifdef JP
716                                 to = format("%d³¬(%s)", dun_level, d_name+d_info[dungeon_type].name);
717 #else
718                                 to = format("level %d of %s", dun_level, d_name+d_info[dungeon_type].name);
719 #endif
720
721 #ifdef JP
722                         fprintf(fff, " %2d:%02d %20s %s¤Ø¤È¥Ñ¥¿¡¼¥ó¤ÎÎϤǰÜÆ°¤·¤¿¡£\n", hour, min, note_level, to);
723 #else
724                         fprintf(fff, " %2d:%02d %20s used Pattern to teleport to %s.\n", hour, min, note_level, to);
725 #endif
726                         break;
727                 }
728                 case NIKKI_LEVELUP:
729                 {
730 #ifdef JP
731                         fprintf(fff, " %2d:%02d %20s ¥ì¥Ù¥ë¤¬%d¤Ë¾å¤¬¤Ã¤¿¡£\n", hour, min, note_level, num);
732 #else
733                         fprintf(fff, " %2d:%02d %20s reached player level %d.\n", hour, min, note_level, num);
734 #endif
735                         break;
736                 }
737                 case NIKKI_GAMESTART:
738                 {
739                         time_t ct = time((time_t*)0);
740                         do_level = FALSE;
741                         if (num)
742                         {
743                                 fprintf(fff, "%s %s",note, ctime(&ct));
744                         }
745                         else
746                                 fprintf(fff, " %2d:%02d %20s %s %s",hour, min, note_level, note, ctime(&ct));
747                         break;
748                 }
749                 case NIKKI_NAMED_PET:
750                 {
751                         fprintf(fff, " %2d:%02d %20s ", hour, min, note_level);
752                         switch (num)
753                         {
754                                 case 0:
755 #ifdef JP
756                                         fprintf(fff, "%s¤òι¤Îͧ¤Ë¤¹¤ë¤³¤È¤Ë·è¤á¤¿¡£\n", note);
757 #else
758                                         fprintf(fff, "decided to travel together with %s.\n", note);
759 #endif
760                                         break;
761                                 case 1:
762 #ifdef JP
763                                         fprintf(fff, "%s¤Î̾Á°¤ò¾Ã¤·¤¿¡£\n", note);
764 #else
765                                         fprintf(fff, "unnamed %s.\n", note);
766 #endif
767                                         break;
768                                 case 2:
769 #ifdef JP
770                                         fprintf(fff, "%s¤ò²òÊü¤·¤¿¡£\n", note);
771 #else
772                                         fprintf(fff, "dismissed %s.\n", note);
773 #endif
774                                         break;
775                                 case 3:
776 #ifdef JP
777                                         fprintf(fff, "%s¤¬»à¤ó¤Ç¤·¤Þ¤Ã¤¿¡£\n", note);
778 #else
779                                         fprintf(fff, "%s died.\n", note);
780 #endif
781                                         break;
782                                 case 4:
783 #ifdef JP
784                                         fprintf(fff, "%s¤ò¤ª¤¤¤ÆÊ̤ΥޥåפذÜÆ°¤·¤¿¡£\n", note);
785 #else
786                                         fprintf(fff, "moved to another map leaving %s behind.\n", note);
787 #endif
788                                         break;
789                                 case 5:
790 #ifdef JP
791                                         fprintf(fff, "%s¤È¤Ï¤°¤ì¤Æ¤·¤Þ¤Ã¤¿¡£\n", note);
792 #else
793                                         fprintf(fff, "lost sight of %s.\n", note);
794 #endif
795                                         break;
796                                 case 6:
797 #ifdef JP
798                                         fprintf(fff, "%s¤¬*Ç˲õ*¤Ë¤è¤Ã¤Æ¾Ã¤¨µî¤Ã¤¿¡£\n", note);
799 #else
800                                         fprintf(fff, "%s was made disappeared by *destruction*.\n", note);
801 #endif
802                                         break;
803                                 case 7:
804 #ifdef JP
805                                         fprintf(fff, "%s¤¬´äÀФ˲¡¤·ÄÙ¤µ¤ì¤¿¡£\n", note);
806 #else
807                                         fprintf(fff, "%s was crushed by falling rocks.\n", note);
808 #endif
809                                         break;
810                                 case 8:
811 #ifdef JP
812                                         fprintf(fff, "%s¤¬¥Æ¥ì¥Ý¡¼¥È¡¦¥ì¥Ù¥ë¤Ë¤è¤Ã¤Æ¾Ã¤¨µî¤Ã¤¿¡£\n", note);
813 #else
814                                         fprintf(fff, "%s was made disappeared by teleport level.\n", note);
815 #endif
816                                         break;
817                                 default:
818                                         fprintf(fff, "\n");
819                                         break;
820                         }
821                         break;
822                 }
823                 default:
824                         break;
825         }
826
827         my_fclose(fff);
828
829         if (do_level) write_level = FALSE;
830
831         return (0);
832 }
833
834
835 #define MAX_SUBTITLE (sizeof(subtitle)/sizeof(subtitle[0]))
836
837 static void do_cmd_disp_nikki(void)
838 {
839         char nikki_title[256];
840         char file_name[80];
841         char buf[1024];
842         char tmp[80];
843 #ifdef JP
844         static const char subtitle[][30] = {"ºÇ¶¯¤ÎÆùÂΤòµá¤á¤Æ",
845                                            "¿ÍÀ¸¤½¤ì¤Ï¤Ï¤«¤Ê¤¤",
846                                            "ÌÀÆü¤Ë¸þ¤«¤Ã¤Æ",
847                                            "꤫¤é¤Ü¤¿¤â¤Á",
848                                            "¤¢¤È¤Îº×¤ê",
849                                            "¤½¤ì¤Ï¤¤¤¤¹Í¤¨¤À",
850                                            "²¿¤È¤Ç¤â¸À¤¨",
851                                            "ÅƤˤâ³Ñ¤Ë¤â",
852                                            "¥¦¥½¤À¤±¤É",
853                                            "¤â¤Ï¤ä¤³¤ì¤Þ¤Ç",
854                                            "¤Ê¤ó¤Ç¤³¤¦¤Ê¤ë¤Î",
855                                            "¤½¤ì¤Ï̵Íý¤À",
856                                            "Åݤ¹¤Ù¤­Å¨¤Ï¥²¡û¥Ä",
857                                            "¤ó¡Á¡©Ê¹¤³¤¨¤ó¤Ê¤¡",
858                                            "¥ª¥ì¤Î̾¤ò¸À¤Ã¤Æ¤ß¤í",
859                                            "Ƭ¤¬ÊѤˤʤäÁ¤ã¤Ã¤¿",
860                                            "¸ß´¹¤·¤Þ¤»¤ó",
861                                            "¤»¤Ã¤«¤¯¤À¤«¤é",
862                                            "¤Þ¤À¤Þ¤À´Å¤¤¤Í",
863                                            "¤à¤´¤¤¤à¤´¤¹¤®¤ë",
864                                            "¤³¤ó¤Ê¤â¤ó¤¸¤ã¤Ê¤¤",
865                                            "¤À¤á¤À¤³¤ê¤ã",
866                                            "¼¡¤¤¤Ã¤Æ¤ß¤è¤¦",
867                                            "¤Á¤ç¤Ã¤È¤À¤±¤è",
868                                            "°¥¤·¤­ËÁ¸±¼Ô",
869                                            "Ìî˾¤Î²Ì¤Æ",
870                                            "̵¸ÂÃϹö",
871                                            "¿À¤Ë·ö²Þ¤òÇä¤ë¼Ô",
872                                            "̤ÃΤÎÀ¤³¦¤Ø",
873                                            "ºÇ¹â¤ÎƬǾ¤òµá¤á¤Æ"};
874 #else
875         static const char subtitle[][51] ={"Quest of The World's Toughest Body",
876                                            "Attack is the best form of defence.",
877                                            "Might is right.",
878                                            "An unexpected windfall",
879                                            "A drowning man will catch at a straw",
880                                            "Don't count your chickens before they are hatched.",
881                                            "It is no use crying over spilt milk.",
882                                            "Seeing is believing.",
883                                            "Strike the iron while it is hot.",
884                                            "I don't care what follows.",
885                                            "To dig a well to put out a house on fire.",
886                                            "Tomorrow is another day.",
887                                            "Easy come, easy go.",
888                                            "The more haste, the less speed.",
889                                            "Where there is life, there is hope.",
890                                            "There is no royal road to *WINNER*.",
891                                            "Danger past, God forgotten.",
892                                            "The best thing to do now is to run away.",
893                                            "Life is but an empty dream.",
894                                            "Dead men tell no tales.",
895                                            "A book that remains shut is but a block.",
896                                            "Misfortunes never come singly.",
897                                            "A little knowledge is a dangerous thing.",
898                                            "History repeats itself.",
899                                            "*WINNER* was not built in a day.",
900                                            "Ignorance is bliss.",
901                                            "To lose is to win?",
902                                            "No medicine can cure folly.",
903                                            "All good things come to an end.",
904                                            "M$ Empire strikes back.",
905                                            "To see is to believe",
906                                            "Time is money.",
907                                            "Quest of The World's Greatest Brain"};
908 #endif
909 #ifdef JP
910         sprintf(file_name,"playrecord-%s.txt",savefile_base);
911 #else
912         sprintf(file_name,"playrec-%s.txt",savefile_base);
913 #endif
914
915         /* Build the filename */
916         path_build(buf, sizeof(buf), ANGBAND_DIR_USER, file_name);
917
918         if (p_ptr->pclass == CLASS_WARRIOR || p_ptr->pclass == CLASS_MONK || p_ptr->pclass == CLASS_SAMURAI || p_ptr->pclass == CLASS_BERSERKER)
919                 strcpy(tmp,subtitle[randint0(MAX_SUBTITLE-1)]);
920         else if (p_ptr->pclass == CLASS_MAGE || p_ptr->pclass == CLASS_HIGH_MAGE || p_ptr->pclass == CLASS_SORCERER)
921                 strcpy(tmp,subtitle[randint0(MAX_SUBTITLE-1)+1]);
922         else strcpy(tmp,subtitle[randint0(MAX_SUBTITLE-2)+1]);
923
924 #ifdef JP
925         sprintf(nikki_title, "¡Ö%s%s%s¤ÎÅÁÀâ -%s-¡×",
926                 ap_ptr->title, ap_ptr->no ? "¤Î" : "", player_name, tmp);
927 #else
928         sprintf(nikki_title, "Legend of %s %s '%s'",
929                 ap_ptr->title, player_name, tmp);
930 #endif
931
932         /* Display the file contents */
933         show_file(FALSE, buf, nikki_title, -1, 0);
934 }
935
936 static void do_cmd_bunshou(void)
937 {
938         char tmp[80] = "\0";
939         char bunshou[80] = "\0";
940
941 #ifdef JP
942         if (get_string("ÆâÍÆ: ", tmp, 79))
943 #else
944         if (get_string("diary note: ", tmp, 79))
945 #endif
946         {
947                 strcpy(bunshou, tmp);
948
949                 do_cmd_write_nikki(NIKKI_BUNSHOU, 0, bunshou);
950         }
951 }
952
953 static void do_cmd_last_get(void)
954 {
955         char buf[256];
956         s32b turn_tmp;
957
958         if (record_o_name[0] == '\0') return;
959
960 #ifdef JP
961         sprintf(buf,"%s¤ÎÆþ¼ê¤òµ­Ï¿¤·¤Þ¤¹¡£",record_o_name);
962 #else
963         sprintf(buf,"Do you really want to record getting %s? ",record_o_name);
964 #endif
965         if (!get_check(buf)) return;
966
967         turn_tmp = turn;
968         turn = record_turn;
969 #ifdef JP
970         sprintf(buf,"%s¤ò¼ê¤ËÆþ¤ì¤¿¡£", record_o_name);
971 #else
972         sprintf(buf,"descover %s.", record_o_name);
973 #endif
974         do_cmd_write_nikki(NIKKI_BUNSHOU, 0, buf);
975         turn = turn_tmp;
976 }
977
978 static void do_cmd_erase_nikki(void)
979 {
980         char file_name[80];
981         char buf[256];
982         FILE *fff = NULL;
983
984 #ifdef JP
985         if (!get_check("ËÜÅö¤Ëµ­Ï¿¤ò¾Ãµî¤·¤Þ¤¹¤«¡©")) return;
986 #else
987         if (!get_check("Do you really want to delete all your record? ")) return;
988 #endif
989
990 #ifdef JP
991         sprintf(file_name,"playrecord-%s.txt",savefile_base);
992 #else
993         sprintf(file_name,"playrec-%s.txt",savefile_base);
994 #endif
995
996         /* Build the filename */
997         path_build(buf, sizeof(buf), ANGBAND_DIR_USER, file_name);
998
999         /* Remove the file */
1000         fd_kill(buf);
1001
1002         fff = my_fopen(buf, "w");
1003         if(fff){
1004                 my_fclose(fff);
1005 #ifdef JP
1006                 msg_format("µ­Ï¿¤ò¾Ãµî¤·¤Þ¤·¤¿¡£");
1007 #else
1008                 msg_format("deleted record.");
1009 #endif
1010         }else{
1011 #ifdef JP
1012                 msg_format("%s ¤Î¾Ãµî¤Ë¼ºÇÔ¤·¤Þ¤·¤¿¡£", buf);
1013 #else
1014                 msg_format("failed to delete %s.", buf);
1015 #endif
1016         }
1017         msg_print(NULL);
1018 }
1019
1020
1021 void do_cmd_nikki(void)
1022 {
1023         int i;
1024
1025         /* File type is "TEXT" */
1026         FILE_TYPE(FILE_TYPE_TEXT);
1027
1028         /* Save the screen */
1029         screen_save();
1030
1031         /* Interact until done */
1032         while (1)
1033         {
1034                 /* Clear screen */
1035                 Term_clear();
1036
1037                 /* Ask for a choice */
1038 #ifdef JP
1039                 prt("[ µ­Ï¿¤ÎÀßÄê ]", 2, 0);
1040 #else
1041                 prt("[ Play Record ]", 2, 0);
1042 #endif
1043
1044
1045                 /* Give some choices */
1046 #ifdef JP
1047                 prt("(1) µ­Ï¿¤ò¸«¤ë", 4, 5);
1048                 prt("(2) Ê¸¾Ï¤òµ­Ï¿¤¹¤ë", 5, 5);
1049                 prt("(3) Ä¾Á°¤ËÆþ¼êËô¤Ï´ÕÄꤷ¤¿¤â¤Î¤òµ­Ï¿¤¹¤ë", 6, 5);
1050                 prt("(4) µ­Ï¿¤ò¾Ãµî¤¹¤ë", 7, 5);
1051 #else
1052                 prt("(1) Display your record", 4, 5);
1053                 prt("(2) Add record", 5, 5);
1054                 prt("(3) Record item you last get/identify", 6, 5);
1055                 prt("(4) Delete your record", 7, 5);
1056 #endif
1057
1058
1059                 /* Prompt */
1060 #ifdef JP
1061                 prt("¥³¥Þ¥ó¥É:", 18, 0);
1062 #else
1063                 prt("Command: ", 18, 0);
1064 #endif
1065
1066
1067                 /* Prompt */
1068                 i = inkey();
1069
1070                 /* Done */
1071                 if (i == ESCAPE) break;
1072
1073                 switch (i)
1074                 {
1075                 case '1':
1076                         do_cmd_disp_nikki();
1077                         break;
1078                 case '2':
1079                         do_cmd_bunshou();
1080                         break;
1081                 case '3':
1082                         do_cmd_last_get();
1083                         break;
1084                 case '4':
1085                         do_cmd_erase_nikki();
1086                         break;
1087                 default: /* Unknown option */
1088                         bell();
1089                 }
1090
1091                 /* Flush messages */
1092                 msg_print(NULL);
1093         }
1094
1095         /* Restore the screen */
1096         screen_load();
1097 }
1098
1099 /*
1100  * Hack -- redraw the screen
1101  *
1102  * This command performs various low level updates, clears all the "extra"
1103  * windows, does a total redraw of the main window, and requests all of the
1104  * interesting updates and redraws that I can think of.
1105  *
1106  * This command is also used to "instantiate" the results of the user
1107  * selecting various things, such as graphics mode, so it must call
1108  * the "TERM_XTRA_REACT" hook before redrawing the windows.
1109  */
1110 void do_cmd_redraw(void)
1111 {
1112         int j;
1113
1114         term *old = Term;
1115
1116
1117         /* Hack -- react to changes */
1118         Term_xtra(TERM_XTRA_REACT, 0);
1119
1120
1121         /* Combine and Reorder the pack (later) */
1122         p_ptr->notice |= (PN_COMBINE | PN_REORDER);
1123
1124
1125         /* Update torch */
1126         p_ptr->update |= (PU_TORCH);
1127
1128         /* Update stuff */
1129         p_ptr->update |= (PU_BONUS | PU_HP | PU_MANA | PU_SPELLS);
1130
1131         /* Forget lite/view */
1132         p_ptr->update |= (PU_UN_VIEW | PU_UN_LITE);
1133
1134         /* Update lite/view */
1135         p_ptr->update |= (PU_VIEW | PU_LITE | PU_MON_LITE);
1136
1137         /* Update monsters */
1138         p_ptr->update |= (PU_MONSTERS);
1139
1140         /* Redraw everything */
1141         p_ptr->redraw |= (PR_WIPE | PR_BASIC | PR_EXTRA | PR_MAP | PR_EQUIPPY);
1142
1143         /* Window stuff */
1144         p_ptr->window |= (PW_INVEN | PW_EQUIP | PW_SPELL | PW_PLAYER);
1145
1146         /* Window stuff */
1147         p_ptr->window |= (PW_MESSAGE | PW_OVERHEAD | PW_DUNGEON | PW_MONSTER | PW_OBJECT);
1148
1149         update_playtime();
1150
1151         /* Hack -- update */
1152         handle_stuff();
1153
1154         if (p_ptr->prace == RACE_ANDROID) calc_android_exp();
1155
1156
1157         /* Redraw every window */
1158         for (j = 0; j < 8; j++)
1159         {
1160                 /* Dead window */
1161                 if (!angband_term[j]) continue;
1162
1163                 /* Activate */
1164                 Term_activate(angband_term[j]);
1165
1166                 /* Redraw */
1167                 Term_redraw();
1168
1169                 /* Refresh */
1170                 Term_fresh();
1171
1172                 /* Restore */
1173                 Term_activate(old);
1174         }
1175 }
1176
1177
1178 /*
1179  * Hack -- change name
1180  */
1181 void do_cmd_change_name(void)
1182 {
1183         char    c;
1184
1185         int             mode = 0;
1186
1187         char    tmp[160];
1188
1189
1190         /* Save the screen */
1191         screen_save();
1192
1193         /* Forever */
1194         while (1)
1195         {
1196                 update_playtime();
1197
1198                 /* Display the player */
1199                 display_player(mode);
1200
1201                 if (mode == 4)
1202                 {
1203                         mode = 0;
1204                         display_player(mode);
1205                 }
1206
1207                 /* Prompt */
1208 #ifdef JP
1209                 Term_putstr(2, 23, -1, TERM_WHITE,
1210                             "['c'¤Ç̾Á°Êѹ¹, 'f'¤Ç¥Õ¥¡¥¤¥ë¤Ø½ñ½Ð, 'h'¤Ç¥â¡¼¥ÉÊѹ¹, ESC¤Ç½ªÎ»]");
1211 #else
1212                 Term_putstr(2, 23, -1, TERM_WHITE,
1213                         "['c' to change name, 'f' to file, 'h' to change mode, or ESC]");
1214 #endif
1215
1216
1217                 /* Query */
1218                 c = inkey();
1219
1220                 /* Exit */
1221                 if (c == ESCAPE) break;
1222
1223                 /* Change name */
1224                 if (c == 'c')
1225                 {
1226                         get_name();
1227
1228                         /* Process the player name */
1229                         process_player_name(FALSE);
1230                 }
1231
1232                 /* File dump */
1233                 else if (c == 'f')
1234                 {
1235                         sprintf(tmp, "%s.txt", player_base);
1236 #ifdef JP
1237                         if (get_string("¥Õ¥¡¥¤¥ë̾: ", tmp, 80))
1238 #else
1239                         if (get_string("File name: ", tmp, 80))
1240 #endif
1241
1242                         {
1243                                 if (tmp[0] && (tmp[0] != ' '))
1244                                 {
1245                                         file_character(tmp);
1246                                 }
1247                         }
1248                 }
1249
1250                 /* Toggle mode */
1251                 else if (c == 'h')
1252                 {
1253                         mode++;
1254                 }
1255
1256                 /* Oops */
1257                 else
1258                 {
1259                         bell();
1260                 }
1261
1262                 /* Flush messages */
1263                 msg_print(NULL);
1264         }
1265
1266         /* Restore the screen */
1267         screen_load();
1268
1269         /* Redraw everything */
1270         p_ptr->redraw |= (PR_WIPE | PR_BASIC | PR_EXTRA | PR_MAP | PR_EQUIPPY);
1271
1272         handle_stuff();
1273 }
1274
1275
1276 /*
1277  * Recall the most recent message
1278  */
1279 void do_cmd_message_one(void)
1280 {
1281         /* Recall one message XXX XXX XXX */
1282         prt(format("> %s", message_str(0)), 0, 0);
1283 }
1284
1285
1286 /*
1287  * Show previous messages to the user   -BEN-
1288  *
1289  * The screen format uses line 0 and 23 for headers and prompts,
1290  * skips line 1 and 22, and uses line 2 thru 21 for old messages.
1291  *
1292  * This command shows you which commands you are viewing, and allows
1293  * you to "search" for strings in the recall.
1294  *
1295  * Note that messages may be longer than 80 characters, but they are
1296  * displayed using "infinite" length, with a special sub-command to
1297  * "slide" the virtual display to the left or right.
1298  *
1299  * Attempt to only hilite the matching portions of the string.
1300  */
1301 void do_cmd_messages(int num_now)
1302 {
1303         int i, n;
1304
1305         char shower[80];
1306         char finder[80];
1307         int wid, hgt;
1308         int num_lines;
1309
1310         /* Get size */
1311         Term_get_size(&wid, &hgt);
1312
1313         /* Number of message lines in a screen */
1314         num_lines = hgt - 4;
1315
1316         /* Wipe finder */
1317         strcpy(finder, "");
1318
1319         /* Wipe shower */
1320         strcpy(shower, "");
1321
1322
1323         /* Total messages */
1324         n = message_num();
1325
1326         /* Start on first message */
1327         i = 0;
1328
1329         /* Save the screen */
1330         screen_save();
1331
1332         /* Clear screen */
1333         Term_clear();
1334
1335         /* Process requests until done */
1336         while (1)
1337         {
1338                 int j;
1339                 int skey;
1340
1341                 /* Dump up to 20 lines of messages */
1342                 for (j = 0; (j < num_lines) && (i + j < n); j++)
1343                 {
1344                         cptr msg = message_str(i+j);
1345
1346                         /* Dump the messages, bottom to top */
1347                         c_prt((i+j < num_now ? TERM_WHITE : TERM_SLATE), msg, num_lines + 1 - j, 0);
1348
1349                         /* Hilite "shower" */
1350                         if (shower[0])
1351                         {
1352                                 cptr str = msg;
1353
1354                                 /* Display matches */
1355                                 while ((str = my_strstr(str, shower)) != NULL)
1356                                 {
1357                                         int len = strlen(shower);
1358
1359                                         /* Display the match */
1360                                         Term_putstr(str-msg, num_lines + 1 - j, len, TERM_YELLOW, shower);
1361
1362                                         /* Advance */
1363                                         str += len;
1364                                 }
1365                         }
1366                 }
1367
1368                 /* Erase remaining lines */
1369                 for (; j < num_lines; j++)
1370                 {
1371                         Term_erase(0, num_lines + 1 - j, 255);
1372                 }
1373
1374                 /* Display header XXX XXX XXX */
1375 #ifdef JP
1376                 /* translation */
1377                 prt(format("°ÊÁ°¤Î¥á¥Ã¥»¡¼¥¸ %d-%d Á´Éô¤Ç(%d)",
1378                            i, i+j-1, n), 0, 0);
1379 #else
1380                 prt(format("Message Recall (%d-%d of %d)",
1381                            i, i+j-1, n), 0, 0);
1382 #endif
1383
1384
1385                 /* Display prompt (not very informative) */
1386 #ifdef JP
1387                 prt("[ 'p' ¤Ç¹¹¤Ë¸Å¤¤¤â¤Î, 'n' ¤Ç¹¹¤Ë¿·¤·¤¤¤â¤Î, '/' ¤Ç¸¡º÷, ESC ¤ÇÃæÃÇ ]", hgt - 1, 0);
1388 #else
1389                 prt("[Press 'p' for older, 'n' for newer, ..., or ESCAPE]", hgt - 1, 0);
1390 #endif
1391
1392
1393                 /* Get a command */
1394                 skey = inkey_special(TRUE);
1395
1396                 /* Exit on Escape */
1397                 if (skey == ESCAPE) break;
1398
1399                 /* Hack -- Save the old index */
1400                 j = i;
1401
1402                 /* Hack -- handle show */
1403                 if (skey == '=')
1404                 {
1405                         /* Prompt */
1406 #ifdef JP
1407                         prt("¶¯Ä´: ", hgt - 1, 0);
1408 #else
1409                         prt("Show: ", hgt - 1, 0);
1410 #endif
1411
1412
1413                         /* Get a "shower" string, or continue */
1414                         if (!askfor(shower, 80)) continue;
1415
1416                         /* Okay */
1417                         continue;
1418                 }
1419
1420                 /* Hack -- handle find */
1421                 if (skey == '/' || skey == KTRL('s'))
1422                 {
1423                         int z;
1424
1425                         /* Prompt */
1426 #ifdef JP
1427                         prt("¸¡º÷: ", hgt - 1, 0);
1428 #else
1429                         prt("Find: ", hgt - 1, 0);
1430 #endif
1431
1432
1433                         /* Get a "finder" string, or continue */
1434                         if (!askfor(finder, 80)) continue;
1435
1436                         /* Show it */
1437                         strcpy(shower, finder);
1438
1439                         /* Scan messages */
1440                         for (z = i + 1; z < n; z++)
1441                         {
1442                                 cptr msg = message_str(z);
1443
1444                                 /* Search for it */
1445                                 if (my_strstr(msg, finder))
1446                                 {
1447                                         /* New location */
1448                                         i = z;
1449
1450                                         /* Done */
1451                                         break;
1452                                 }
1453                         }
1454                 }
1455
1456                 /* Recall 1 older message */
1457                 if (skey == SKEY_TOP)
1458                 {
1459                         /* Go to the oldest line */
1460                         i = n - num_lines;
1461                 }
1462
1463                 /* Recall 1 newer message */
1464                 if (skey == SKEY_BOTTOM)
1465                 {
1466                         /* Go to the newest line */
1467                         i = 0;
1468                 }
1469
1470                 /* Recall 1 older message */
1471                 if (skey == '8' || skey == SKEY_UP || skey == '\n' || skey == '\r')
1472                 {
1473                         /* Go older if legal */
1474                         i = MIN(i + 1, n - num_lines);
1475                 }
1476
1477                 /* Recall 10 older messages */
1478                 if (skey == '+')
1479                 {
1480                         /* Go older if legal */
1481                         i = MIN(i + 10, n - num_lines);
1482                 }
1483
1484                 /* Recall 20 older messages */
1485                 if (skey == 'p' || skey == KTRL('P') || skey == ' ' || skey == SKEY_PGUP)
1486                 {
1487                         /* Go older if legal */
1488                         i = MIN(i + num_lines, n - num_lines);
1489                 }
1490
1491                 /* Recall 20 newer messages */
1492                 if (skey == 'n' || skey == KTRL('N') || skey == SKEY_PGDOWN)
1493                 {
1494                         /* Go newer (if able) */
1495                         i = MAX(0, i - num_lines);
1496                 }
1497
1498                 /* Recall 10 newer messages */
1499                 if (skey == '-')
1500                 {
1501                         /* Go newer (if able) */
1502                         i = MAX(0, i - 10);
1503                 }
1504
1505                 /* Recall 1 newer messages */
1506                 if (skey == '2' || skey == SKEY_DOWN)
1507                 {
1508                         /* Go newer (if able) */
1509                         i = MAX(0, i - 1);
1510                 }
1511
1512                 /* Hack -- Error of some kind */
1513                 if (i == j) bell();
1514         }
1515
1516         /* Restore the screen */
1517         screen_load();
1518 }
1519
1520
1521
1522 /*
1523  * Number of cheating options
1524  */
1525 #define CHEAT_MAX 7
1526
1527 /*
1528  * Cheating options
1529  */
1530 static option_type cheat_info[CHEAT_MAX] =
1531 {
1532         { &cheat_peek,          FALSE,  255,    0x01, 0x00,
1533 #ifdef JP
1534         "cheat_peek",           "¥¢¥¤¥Æ¥à¤ÎÀ¸À®¤ò¤Î¤¾¤­¸«¤ë"
1535 #else
1536         "cheat_peek",           "Peek into object creation"
1537 #endif
1538         },
1539
1540         { &cheat_hear,          FALSE,  255,    0x02, 0x00,
1541 #ifdef JP
1542         "cheat_hear",           "¥â¥ó¥¹¥¿¡¼¤ÎÀ¸À®¤ò¤Î¤¾¤­¸«¤ë"
1543 #else
1544         "cheat_hear",           "Peek into monster creation"
1545 #endif
1546         },
1547
1548         { &cheat_room,          FALSE,  255,    0x04, 0x00,
1549 #ifdef JP
1550         "cheat_room",           "¥À¥ó¥¸¥ç¥ó¤ÎÀ¸À®¤ò¤Î¤¾¤­¸«¤ë"
1551 #else
1552         "cheat_room",           "Peek into dungeon creation"
1553 #endif
1554         },
1555
1556         { &cheat_xtra,          FALSE,  255,    0x08, 0x00,
1557 #ifdef JP
1558         "cheat_xtra",           "¤½¤Î¾¤Î»ö¤ò¤Î¤¾¤­¸«¤ë"
1559 #else
1560         "cheat_xtra",           "Peek into something else"
1561 #endif
1562         },
1563
1564         { &cheat_know,          FALSE,  255,    0x10, 0x00,
1565 #ifdef JP
1566         "cheat_know",           "´°Á´¤Ê¥â¥ó¥¹¥¿¡¼¤Î»×¤¤½Ð¤òÃΤë"
1567 #else
1568         "cheat_know",           "Know complete monster info"
1569 #endif
1570         },
1571
1572         { &cheat_live,          FALSE,  255,    0x20, 0x00,
1573 #ifdef JP
1574         "cheat_live",           "»à¤ò²óÈò¤¹¤ë¤³¤È¤ò²Äǽ¤Ë¤¹¤ë"
1575 #else
1576         "cheat_live",           "Allow player to avoid death"
1577 #endif
1578         },
1579
1580         { &cheat_save,          FALSE,  255,    0x40, 0x00,
1581 #ifdef JP
1582         "cheat_save",           "»à¤ó¤À»þ¥»¡¼¥Ö¤¹¤ë¤«³Îǧ¤¹¤ë"
1583 #else
1584         "cheat_save",           "Ask for saving death"
1585 #endif
1586         }
1587 };
1588
1589 /*
1590  * Interact with some options for cheating
1591  */
1592 static void do_cmd_options_cheat(cptr info)
1593 {
1594         char    ch;
1595
1596         int             i, k = 0, n = CHEAT_MAX;
1597
1598         char    buf[80];
1599
1600
1601         /* Clear screen */
1602         Term_clear();
1603
1604         /* Interact with the player */
1605         while (TRUE)
1606         {
1607                 int dir;
1608
1609                 /* Prompt XXX XXX XXX */
1610 #ifdef JP
1611                 sprintf(buf, "%s ( ¥ê¥¿¡¼¥ó¤Ç¼¡¤Ø, y/n ¤Ç¥»¥Ã¥È, ESC ¤Ç·èÄê )", info);
1612 #else
1613                 sprintf(buf, "%s (RET to advance, y/n to set, ESC to accept) ", info);
1614 #endif
1615
1616                 prt(buf, 0, 0);
1617
1618 #ifdef JP
1619                 /* º¾µ½¥ª¥×¥·¥ç¥ó¤ò¤¦¤Ã¤«¤ê¤¤¤¸¤Ã¤Æ¤·¤Þ¤¦¿Í¤¬¤¤¤ë¤è¤¦¤Ê¤Î¤ÇÃí°Õ */
1620                 prt("                                 <<  Ãí°Õ  >>", 11, 0);
1621                 prt("      º¾µ½¥ª¥×¥·¥ç¥ó¤ò°ìÅ٤ǤâÀßÄꤹ¤ë¤È¡¢¥¹¥³¥¢µ­Ï¿¤¬»Ä¤é¤Ê¤¯¤Ê¤ê¤Þ¤¹¡ª", 12, 0);
1622                 prt("      ¸å¤Ë²ò½ü¤·¤Æ¤â¥À¥á¤Ç¤¹¤Î¤Ç¡¢¾¡Íø¼Ô¤òÌܻؤ¹Êý¤Ï¤³¤³¤Î¥ª¥×¥·¥ç¥ó¤Ï¤¤", 13, 0);
1623                 prt("      ¤¸¤é¤Ê¤¤¤è¤¦¤Ë¤·¤Æ²¼¤µ¤¤¡£", 14, 0);
1624 #endif
1625                 /* Display the options */
1626                 for (i = 0; i < n; i++)
1627                 {
1628                         byte a = TERM_WHITE;
1629
1630                         /* Color current option */
1631                         if (i == k) a = TERM_L_BLUE;
1632
1633                         /* Display the option text */
1634                         sprintf(buf, "%-48s: %s (%s)",
1635                             cheat_info[i].o_desc,
1636 #ifdef JP
1637                             (*cheat_info[i].o_var ? "¤Ï¤¤  " : "¤¤¤¤¤¨"),
1638 #else
1639                             (*cheat_info[i].o_var ? "yes" : "no "),
1640 #endif
1641
1642                             cheat_info[i].o_text);
1643                         c_prt(a, buf, i + 2, 0);
1644                 }
1645
1646                 /* Hilite current option */
1647                 move_cursor(k + 2, 50);
1648
1649                 /* Get a key */
1650                 ch = inkey();
1651
1652                 /*
1653                  * HACK - Try to translate the key into a direction
1654                  * to allow using the roguelike keys for navigation.
1655                  */
1656                 dir = get_keymap_dir(ch);
1657                 if ((dir == 2) || (dir == 4) || (dir == 6) || (dir == 8))
1658                         ch = I2D(dir);
1659
1660                 /* Analyze */
1661                 switch (ch)
1662                 {
1663                         case ESCAPE:
1664                         {
1665                                 return;
1666                         }
1667
1668                         case '-':
1669                         case '8':
1670                         {
1671                                 k = (n + k - 1) % n;
1672                                 break;
1673                         }
1674
1675                         case ' ':
1676                         case '\n':
1677                         case '\r':
1678                         case '2':
1679                         {
1680                                 k = (k + 1) % n;
1681                                 break;
1682                         }
1683
1684                         case 'y':
1685                         case 'Y':
1686                         case '6':
1687                         {
1688                                 if(!p_ptr->noscore)
1689 #ifdef JP
1690                                         do_cmd_write_nikki(NIKKI_BUNSHOU, 0, "º¾µ½¥ª¥×¥·¥ç¥ó¤òON¤Ë¤·¤Æ¡¢¥¹¥³¥¢¤ò»Ä¤»¤Ê¤¯¤Ê¤Ã¤¿¡£");
1691 #else
1692                                         do_cmd_write_nikki(NIKKI_BUNSHOU, 0, "give up sending score to use cheating options.");
1693 #endif
1694                                 p_ptr->noscore |= (cheat_info[k].o_set * 256 + cheat_info[k].o_bit);
1695                                 (*cheat_info[k].o_var) = TRUE;
1696                                 k = (k + 1) % n;
1697                                 break;
1698                         }
1699
1700                         case 'n':
1701                         case 'N':
1702                         case '4':
1703                         {
1704                                 (*cheat_info[k].o_var) = FALSE;
1705                                 k = (k + 1) % n;
1706                                 break;
1707                         }
1708
1709                         case '?':
1710                         {
1711 #ifdef JP
1712                                 strnfmt(buf, sizeof(buf), "joption.txt#%s", cheat_info[k].o_text);
1713 #else
1714                                 strnfmt(buf, sizeof(buf), "option.txt#%s", cheat_info[k].o_text);
1715 #endif
1716                                 /* Peruse the help file */
1717                                 (void)show_file(TRUE, buf, NULL, 0, 0);
1718
1719                                 Term_clear(); 
1720                                 break;
1721                         }
1722
1723                         default:
1724                         {
1725                                 bell();
1726                                 break;
1727                         }
1728                 }
1729         }
1730 }
1731
1732
1733 static option_type autosave_info[2] =
1734 {
1735         { &autosave_l,      FALSE, 255, 0x01, 0x00,
1736 #ifdef JP
1737             "autosave_l",    "¿·¤·¤¤³¬¤ËÆþ¤ëÅ٤˼«Æ°¥»¡¼¥Ö¤¹¤ë" },
1738 #else
1739             "autosave_l",    "Autosave when entering new levels" },
1740 #endif
1741
1742
1743         { &autosave_t,      FALSE, 255, 0x02, 0x00,
1744 #ifdef JP
1745             "autosave_t",   "°ìÄ꥿¡¼¥óËè¤Ë¼«Æ°¥»¡¼¥Ö¤¹¤ë" },
1746 #else
1747             "autosave_t",   "Timed autosave" },
1748 #endif
1749
1750 };
1751
1752
1753 static s16b toggle_frequency(s16b current)
1754 {
1755         switch (current)
1756         {
1757         case 0: return 50;
1758         case 50: return 100;
1759         case 100: return 250;
1760         case 250: return 500;
1761         case 500: return 1000;
1762         case 1000: return 2500;
1763         case 2500: return 5000;
1764         case 5000: return 10000;
1765         case 10000: return 25000;
1766         default: return 0;
1767         }
1768 }
1769
1770
1771 /*
1772  * Interact with some options for cheating
1773  */
1774 static void do_cmd_options_autosave(cptr info)
1775 {
1776         char    ch;
1777
1778         int     i, k = 0, n = 2;
1779
1780         char    buf[80];
1781
1782
1783         /* Clear screen */
1784         Term_clear();
1785
1786         /* Interact with the player */
1787         while (TRUE)
1788         {
1789                 /* Prompt XXX XXX XXX */
1790 #ifdef JP
1791                 sprintf(buf, "%s ( ¥ê¥¿¡¼¥ó¤Ç¼¡¤Ø, y/n ¤Ç¥»¥Ã¥È, F ¤ÇÉÑÅÙ¤òÆþÎÏ, ESC ¤Ç·èÄê ) ", info);
1792 #else
1793                 sprintf(buf, "%s (RET to advance, y/n to set, 'F' for frequency, ESC to accept) ", info);
1794 #endif
1795
1796                 prt(buf, 0, 0);
1797
1798                 /* Display the options */
1799                 for (i = 0; i < n; i++)
1800                 {
1801                         byte a = TERM_WHITE;
1802
1803                         /* Color current option */
1804                         if (i == k) a = TERM_L_BLUE;
1805
1806                         /* Display the option text */
1807                         sprintf(buf, "%-48s: %s (%s)",
1808                             autosave_info[i].o_desc,
1809 #ifdef JP
1810                             (*autosave_info[i].o_var ? "¤Ï¤¤  " : "¤¤¤¤¤¨"),
1811 #else
1812                             (*autosave_info[i].o_var ? "yes" : "no "),
1813 #endif
1814
1815                             autosave_info[i].o_text);
1816                         c_prt(a, buf, i + 2, 0);
1817                 }
1818
1819 #ifdef JP
1820                 prt(format("¼«Æ°¥»¡¼¥Ö¤ÎÉÑÅÙ¡§ %d ¥¿¡¼¥óËè",  autosave_freq), 5, 0);
1821 #else
1822                 prt(format("Timed autosave frequency: every %d turns",  autosave_freq), 5, 0);
1823 #endif
1824
1825
1826
1827                 /* Hilite current option */
1828                 move_cursor(k + 2, 50);
1829
1830                 /* Get a key */
1831                 ch = inkey();
1832
1833                 /* Analyze */
1834                 switch (ch)
1835                 {
1836                         case ESCAPE:
1837                         {
1838                                 return;
1839                         }
1840
1841                         case '-':
1842                         case '8':
1843                         {
1844                                 k = (n + k - 1) % n;
1845                                 break;
1846                         }
1847
1848                         case ' ':
1849                         case '\n':
1850                         case '\r':
1851                         case '2':
1852                         {
1853                                 k = (k + 1) % n;
1854                                 break;
1855                         }
1856
1857                         case 'y':
1858                         case 'Y':
1859                         case '6':
1860                         {
1861
1862                                 (*autosave_info[k].o_var) = TRUE;
1863                                 k = (k + 1) % n;
1864                                 break;
1865                         }
1866
1867                         case 'n':
1868                         case 'N':
1869                         case '4':
1870                         {
1871                                 (*autosave_info[k].o_var) = FALSE;
1872                                 k = (k + 1) % n;
1873                                 break;
1874                         }
1875
1876                         case 'f':
1877                         case 'F':
1878                         {
1879                                 autosave_freq = toggle_frequency(autosave_freq);
1880 #ifdef JP
1881                                 prt(format("¼«Æ°¥»¡¼¥Ö¤ÎÉÑÅÙ¡§ %d ¥¿¡¼¥óËè", 
1882                                            autosave_freq), 5, 0);
1883 #else
1884                                 prt(format("Timed autosave frequency: every %d turns",
1885                                            autosave_freq), 5, 0);
1886 #endif
1887                                 break;
1888                         }
1889
1890                         case '?':
1891                         {
1892 #ifdef JP
1893                                 (void)show_file(TRUE, "joption.txt#Autosave", NULL, 0, 0);
1894 #else
1895                                 (void)show_file(TRUE, "option.txt#Autosave", NULL, 0, 0);
1896 #endif
1897
1898
1899                                 Term_clear(); 
1900                                 break;
1901                         }
1902
1903                         default:
1904                         {
1905                                 bell();
1906                                 break;
1907                         }
1908                 }
1909         }
1910 }
1911
1912
1913 /*
1914  * Interact with some options
1915  */
1916 void do_cmd_options_aux(int page, cptr info)
1917 {
1918         char    ch;
1919         int     i, k = 0, n = 0, l;
1920         int     opt[24];
1921         char    buf[80];
1922         bool    browse_only = (page == OPT_PAGE_BIRTH) && character_generated &&
1923                               (!p_ptr->wizard || !allow_debug_opts);
1924
1925
1926         /* Lookup the options */
1927         for (i = 0; i < 24; i++) opt[i] = 0;
1928
1929         /* Scan the options */
1930         for (i = 0; option_info[i].o_desc; i++)
1931         {
1932                 /* Notice options on this "page" */
1933                 if (option_info[i].o_page == page) opt[n++] = i;
1934         }
1935
1936
1937         /* Clear screen */
1938         Term_clear();
1939
1940         /* Interact with the player */
1941         while (TRUE)
1942         {
1943                 int dir;
1944
1945                 /* Prompt XXX XXX XXX */
1946 #ifdef JP
1947                 sprintf(buf, "%s (¥ê¥¿¡¼¥ó:¼¡, %sESC:½ªÎ», ?:¥Ø¥ë¥×) ", info, browse_only ? "" : "y/n:Êѹ¹, ");
1948 #else
1949                 sprintf(buf, "%s (RET:next, %s, ?:help) ", info, browse_only ? "ESC:exit" : "y/n:change, ESC:accept");
1950 #endif
1951
1952                 prt(buf, 0, 0);
1953
1954
1955                 /* HACK -- description for easy-auto-destroy options */
1956 #ifdef JP
1957                 if (page == OPT_PAGE_AUTODESTROY) c_prt(TERM_YELLOW, "°Ê²¼¤Î¥ª¥×¥·¥ç¥ó¤Ï¡¢´Ê°×¼«Æ°Ç˲õ¤ò»ÈÍѤ¹¤ë¤È¤­¤Î¤ßÍ­¸ú", 6, 6);
1958 #else
1959                 if (page == OPT_PAGE_AUTODESTROY) c_prt(TERM_YELLOW, "Following options will protect items from easy auto-destroyer.", 6, 3);
1960 #endif
1961
1962                 /* Display the options */
1963                 for (i = 0; i < n; i++)
1964                 {
1965                         byte a = TERM_WHITE;
1966
1967                         /* Color current option */
1968                         if (i == k) a = TERM_L_BLUE;
1969
1970                         /* Display the option text */
1971                         sprintf(buf, "%-48s: %s (%.19s)",
1972                                 option_info[opt[i]].o_desc,
1973 #ifdef JP
1974                                 (*option_info[opt[i]].o_var ? "¤Ï¤¤  " : "¤¤¤¤¤¨"),
1975 #else
1976                                 (*option_info[opt[i]].o_var ? "yes" : "no "),
1977 #endif
1978
1979                                 option_info[opt[i]].o_text);
1980                         if ((page == OPT_PAGE_AUTODESTROY) && i > 2) c_prt(a, buf, i + 5, 0);
1981                         else c_prt(a, buf, i + 2, 0);
1982                 }
1983
1984                 if ((page == OPT_PAGE_AUTODESTROY) && (k > 2)) l = 3;
1985                 else l = 0;
1986
1987                 /* Hilite current option */
1988                 move_cursor(k + 2 + l, 50);
1989
1990                 /* Get a key */
1991                 ch = inkey();
1992
1993                 /*
1994                  * HACK - Try to translate the key into a direction
1995                  * to allow using the roguelike keys for navigation.
1996                  */
1997                 dir = get_keymap_dir(ch);
1998                 if ((dir == 2) || (dir == 4) || (dir == 6) || (dir == 8))
1999                         ch = I2D(dir);
2000
2001                 /* Analyze */
2002                 switch (ch)
2003                 {
2004                         case ESCAPE:
2005                         {
2006                                 return;
2007                         }
2008
2009                         case '-':
2010                         case '8':
2011                         {
2012                                 k = (n + k - 1) % n;
2013                                 break;
2014                         }
2015
2016                         case ' ':
2017                         case '\n':
2018                         case '\r':
2019                         case '2':
2020                         {
2021                                 k = (k + 1) % n;
2022                                 break;
2023                         }
2024
2025                         case 'y':
2026                         case 'Y':
2027                         case '6':
2028                         {
2029                                 if (browse_only) break;
2030                                 (*option_info[opt[k]].o_var) = TRUE;
2031                                 k = (k + 1) % n;
2032                                 break;
2033                         }
2034
2035                         case 'n':
2036                         case 'N':
2037                         case '4':
2038                         {
2039                                 if (browse_only) break;
2040                                 (*option_info[opt[k]].o_var) = FALSE;
2041                                 k = (k + 1) % n;
2042                                 break;
2043                         }
2044
2045                         case 't':
2046                         case 'T':
2047                         {
2048                                 if (!browse_only) (*option_info[opt[k]].o_var) = !(*option_info[opt[k]].o_var);
2049                                 break;
2050                         }
2051
2052                         case '?':
2053                         {
2054 #ifdef JP
2055                                 strnfmt(buf, sizeof(buf), "joption.txt#%s", option_info[opt[k]].o_text);
2056 #else
2057                                 strnfmt(buf, sizeof(buf), "option.txt#%s", option_info[opt[k]].o_text);
2058 #endif
2059                                 /* Peruse the help file */
2060                                 (void)show_file(TRUE, buf, NULL, 0, 0);
2061
2062                                 Term_clear();
2063                                 break;
2064                         }
2065
2066                         default:
2067                         {
2068                                 bell();
2069                                 break;
2070                         }
2071                 }
2072         }
2073 }
2074
2075
2076 /*
2077  * Modify the "window" options
2078  */
2079 static void do_cmd_options_win(void)
2080 {
2081         int i, j, d;
2082
2083         int y = 0;
2084         int x = 0;
2085
2086         char ch;
2087
2088         bool go = TRUE;
2089
2090         u32b old_flag[8];
2091
2092
2093         /* Memorize old flags */
2094         for (j = 0; j < 8; j++)
2095         {
2096                 /* Acquire current flags */
2097                 old_flag[j] = window_flag[j];
2098         }
2099
2100
2101         /* Clear screen */
2102         Term_clear();
2103
2104         /* Interact */
2105         while (go)
2106         {
2107                 /* Prompt XXX XXX XXX */
2108 #ifdef JP
2109                 prt("¥¦¥£¥ó¥É¥¦¡¦¥Õ¥é¥° (<Êý¸þ>¤Ç°ÜÆ°, t¤Ç¥Á¥§¥ó¥¸, y/n ¤Ç¥»¥Ã¥È, ESC)", 0, 0);
2110 #else
2111                 prt("Window Flags (<dir>, t, y, n, ESC) ", 0, 0);
2112 #endif
2113
2114
2115                 /* Display the windows */
2116                 for (j = 0; j < 8; j++)
2117                 {
2118                         byte a = TERM_WHITE;
2119
2120                         cptr s = angband_term_name[j];
2121
2122                         /* Use color */
2123                         if (j == x) a = TERM_L_BLUE;
2124
2125                         /* Window name, staggered, centered */
2126                         Term_putstr(35 + j * 5 - strlen(s) / 2, 2 + j % 2, -1, a, s);
2127                 }
2128
2129                 /* Display the options */
2130                 for (i = 0; i < 16; i++)
2131                 {
2132                         byte a = TERM_WHITE;
2133
2134                         cptr str = window_flag_desc[i];
2135
2136                         /* Use color */
2137                         if (i == y) a = TERM_L_BLUE;
2138
2139                         /* Unused option */
2140 #ifdef JP
2141                         if (!str) str = "(̤»ÈÍÑ)";
2142 #else
2143                         if (!str) str = "(Unused option)";
2144 #endif
2145
2146
2147                         /* Flag name */
2148                         Term_putstr(0, i + 5, -1, a, str);
2149
2150                         /* Display the windows */
2151                         for (j = 0; j < 8; j++)
2152                         {
2153                                 byte a = TERM_WHITE;
2154
2155                                 char c = '.';
2156
2157                                 /* Use color */
2158                                 if ((i == y) && (j == x)) a = TERM_L_BLUE;
2159
2160                                 /* Active flag */
2161                                 if (window_flag[j] & (1L << i)) c = 'X';
2162
2163                                 /* Flag value */
2164                                 Term_putch(35 + j * 5, i + 5, a, c);
2165                         }
2166                 }
2167
2168                 /* Place Cursor */
2169                 Term_gotoxy(35 + x * 5, y + 5);
2170
2171                 /* Get key */
2172                 ch = inkey();
2173
2174                 /* Analyze */
2175                 switch (ch)
2176                 {
2177                         case ESCAPE:
2178                         {
2179                                 go = FALSE;
2180                                 break;
2181                         }
2182
2183                         case 'T':
2184                         case 't':
2185                         {
2186                                 /* Clear windows */
2187                                 for (j = 0; j < 8; j++)
2188                                 {
2189                                         window_flag[j] &= ~(1L << y);
2190                                 }
2191
2192                                 /* Clear flags */
2193                                 for (i = 0; i < 16; i++)
2194                                 {
2195                                         window_flag[x] &= ~(1L << i);
2196                                 }
2197
2198                                 /* Fall through */
2199                         }
2200
2201                         case 'y':
2202                         case 'Y':
2203                         {
2204                                 /* Ignore screen */
2205                                 if (x == 0) break;
2206
2207                                 /* Set flag */
2208                                 window_flag[x] |= (1L << y);
2209                                 break;
2210                         }
2211
2212                         case 'n':
2213                         case 'N':
2214                         {
2215                                 /* Clear flag */
2216                                 window_flag[x] &= ~(1L << y);
2217                                 break;
2218                         }
2219
2220                         case '?':
2221                         {
2222 #ifdef JP
2223                                 (void)show_file(TRUE, "joption.txt#Window", NULL, 0, 0);
2224 #else
2225                                 (void)show_file(TRUE, "option.txt#Window", NULL, 0, 0);
2226 #endif
2227
2228
2229                                 Term_clear(); 
2230                                 break;
2231                         }
2232
2233                         default:
2234                         {
2235                                 d = get_keymap_dir(ch);
2236
2237                                 x = (x + ddx[d] + 8) % 8;
2238                                 y = (y + ddy[d] + 16) % 16;
2239
2240                                 if (!d) bell();
2241                         }
2242                 }
2243         }
2244
2245         /* Notice changes */
2246         for (j = 0; j < 8; j++)
2247         {
2248                 term *old = Term;
2249
2250                 /* Dead window */
2251                 if (!angband_term[j]) continue;
2252
2253                 /* Ignore non-changes */
2254                 if (window_flag[j] == old_flag[j]) continue;
2255
2256                 /* Activate */
2257                 Term_activate(angband_term[j]);
2258
2259                 /* Erase */
2260                 Term_clear();
2261
2262                 /* Refresh */
2263                 Term_fresh();
2264
2265                 /* Restore */
2266                 Term_activate(old);
2267         }
2268 }
2269
2270
2271
2272
2273 /*
2274  * Set or unset various options.
2275  *
2276  * The user must use the "Ctrl-R" command to "adapt" to changes
2277  * in any options which control "visual" aspects of the game.
2278  */
2279 void do_cmd_options(void)
2280 {
2281         int k;
2282
2283
2284         /* Save the screen */
2285         screen_save();
2286
2287         /* Interact */
2288         while (1)
2289         {
2290                 /* Clear screen */
2291                 Term_clear();
2292
2293                 /* Why are we here */
2294 #ifdef JP
2295                 prt("[ ¥ª¥×¥·¥ç¥ó¤ÎÀßÄê ]", 1, 0);
2296 #else
2297                 prt("Options", 1, 0);
2298 #endif
2299
2300
2301                 /* Give some choices */
2302 #ifdef JP
2303                 prt("(1)      ¥­¡¼ÆþÎÏ        ¥ª¥×¥·¥ç¥ó", 2, 5);
2304                 prt("(2)     ¥Þ¥Ã¥×²èÌÌ       ¥ª¥×¥·¥ç¥ó", 3, 5);
2305                 prt("(3)    ¥Æ¥­¥¹¥Èɽ¼¨      ¥ª¥×¥·¥ç¥ó", 4, 5);
2306                 prt("(4)    ¥²¡¼¥à¥×¥ì¥¤      ¥ª¥×¥·¥ç¥ó", 5, 5);
2307                 prt("(5)    ¹ÔÆ°Ãæ»ß´Ø·¸      ¥ª¥×¥·¥ç¥ó", 6, 5);
2308                 prt("(6)    ´Ê°×¼«Æ°Ç˲õ      ¥ª¥×¥·¥ç¥ó", 7, 5);
2309                 prt("(R)     ¥×¥ì¥¤µ­Ï¿       ¥ª¥×¥·¥ç¥ó", 8, 5);
2310
2311                 /* Special choices */
2312                 prt("(P)  ¼«Æ°½¦¤¤¥¨¥Ç¥£¥¿", 10, 5);
2313                 prt("(D)   ´ðËÜ¥¦¥§¥¤¥ÈÎÌ", 11, 5);
2314                 prt("(H) Äã¥Ò¥Ã¥È¥Ý¥¤¥ó¥È·Ù¹ð", 12, 5);
2315                 prt("(M)    ÄãËâÎÏ¿§ïçÃÍ", 13, 5);
2316                 prt("(A)     ¼«Æ°¥»¡¼¥Ö       ¥ª¥×¥·¥ç¥ó", 14, 5);
2317                 /* Window flags */
2318                 prt("(W)  ¥¦¥¤¥ó¥É¥¦¥Õ¥é¥°", 15, 5);
2319 #else
2320                 prt("(1) Input Options", 2, 5);
2321                 prt("(2) Map Screen Options", 3, 5);
2322                 prt("(3) Text Display Options", 4, 5);
2323                 prt("(4) Game-Play Options", 5, 5);
2324                 prt("(5) Disturbance Options", 6, 5);
2325                 prt("(6) Easy Auto-Destroyer Options", 7, 5);
2326                 prt("(R) Play-record Options", 8, 5);
2327                 /* Special choices */
2328                 prt("(P) Auto-picker/destroyer editor", 10, 5);
2329                 prt("(D) Base Delay Factor", 11, 5);
2330                 prt("(H) Hitpoint Warning", 12, 5);
2331                 prt("(M) Mana Color Threshold", 13, 5);
2332                 prt("(A) Autosave Options", 14, 5);
2333                 /* Window flags */
2334                 prt("(W) Window Flags", 15, 5);
2335 #endif
2336
2337                 if (!p_ptr->wizard || !allow_debug_opts)
2338                 {
2339                         /* Birth */
2340 #ifdef JP
2341                         prt("(B)        ½é´ü          ¥ª¥×¥·¥ç¥ó (»²¾È¤Î¤ß)", 16, 5);
2342 #else
2343                         prt("(B) Birth Options (Browse Only)", 16, 5);
2344 #endif
2345                 }
2346                 else
2347                 {
2348                         /* Birth */
2349 #ifdef JP
2350                         prt("(B)        ½é´ü          ¥ª¥×¥·¥ç¥ó", 16, 5);
2351 #else
2352                         prt("(B) Birth Options", 16, 5);
2353 #endif
2354                 }
2355
2356
2357                 if (p_ptr->noscore || allow_debug_opts)
2358                 {
2359                         /* Cheating */
2360 #ifdef JP
2361                         prt("(C)        º¾µ½          ¥ª¥×¥·¥ç¥ó", 17, 5);
2362 #else
2363                         prt("(C) Cheating Options", 17, 5);
2364 #endif
2365                 }
2366
2367
2368                 /* Prompt */
2369 #ifdef JP
2370                 prt("¥³¥Þ¥ó¥É:", 19, 0);
2371 #else
2372                 prt("Command: ", 19, 0);
2373 #endif
2374
2375
2376                 /* Get command */
2377                 k = inkey();
2378
2379                 /* Exit */
2380                 if (k == ESCAPE) break;
2381
2382                 /* Analyze */
2383                 switch (k)
2384                 {
2385                         case '1':
2386                         {
2387                                 /* Process the general options */
2388 #ifdef JP
2389                                 do_cmd_options_aux(OPT_PAGE_INPUT, "¥­¡¼ÆþÎÏ¥ª¥×¥·¥ç¥ó");
2390 #else
2391                                 do_cmd_options_aux(OPT_PAGE_INPUT, "Input Options");
2392 #endif
2393
2394                                 break;
2395                         }
2396
2397                         case '2':
2398                         {
2399                                 /* Process the general options */
2400 #ifdef JP
2401                                 do_cmd_options_aux(OPT_PAGE_MAPSCREEN, "¥Þ¥Ã¥×²èÌÌ¥ª¥×¥·¥ç¥ó");
2402 #else
2403                                 do_cmd_options_aux(OPT_PAGE_MAPSCREEN, "Map Screen Options");
2404 #endif
2405
2406                                 break;
2407                         }
2408
2409                         case '3':
2410                         {
2411                                 /* Spawn */
2412 #ifdef JP
2413                                 do_cmd_options_aux(OPT_PAGE_TEXT, "¥Æ¥­¥¹¥Èɽ¼¨¥ª¥×¥·¥ç¥ó");
2414 #else
2415                                 do_cmd_options_aux(OPT_PAGE_TEXT, "Text Display Options");
2416 #endif
2417
2418                                 break;
2419                         }
2420
2421                         case '4':
2422                         {
2423                                 /* Spawn */
2424 #ifdef JP
2425                                 do_cmd_options_aux(OPT_PAGE_GAMEPLAY, "¥²¡¼¥à¥×¥ì¥¤¡¦¥ª¥×¥·¥ç¥ó");
2426 #else
2427                                 do_cmd_options_aux(OPT_PAGE_GAMEPLAY, "Game-Play Options");
2428 #endif
2429
2430                                 break;
2431                         }
2432
2433                         case '5':
2434                         {
2435                                 /* Spawn */
2436 #ifdef JP
2437                                 do_cmd_options_aux(OPT_PAGE_DISTURBANCE, "¹ÔÆ°Ãæ»ß´Ø·¸¤Î¥ª¥×¥·¥ç¥ó");
2438 #else
2439                                 do_cmd_options_aux(OPT_PAGE_DISTURBANCE, "Disturbance Options");
2440 #endif
2441
2442                                 break;
2443                         }
2444
2445                         case '6':
2446                         {
2447                                 /* Spawn */
2448 #ifdef JP
2449                                 do_cmd_options_aux(OPT_PAGE_AUTODESTROY, "´Ê°×¼«Æ°Ç˲õ¥ª¥×¥·¥ç¥ó");
2450 #else
2451                                 do_cmd_options_aux(OPT_PAGE_AUTODESTROY, "Easy Auto-Destroyer Options");
2452 #endif
2453                                 break;
2454                         }
2455
2456                         /* Play-record Options */
2457                         case 'R':
2458                         case 'r':
2459                         {
2460                                 /* Spawn */
2461 #ifdef JP
2462                                 do_cmd_options_aux(OPT_PAGE_PLAYRECORD, "¥×¥ì¥¤µ­Ï¿¥ª¥×¥·¥ç¥ó");
2463 #else
2464                                 do_cmd_options_aux(OPT_PAGE_PLAYRECORD, "Play-record Options");
2465 #endif
2466                                 break;
2467                         }
2468
2469                         /* Birth Options */
2470                         case 'B':
2471                         case 'b':
2472                         {
2473                                 /* Spawn */
2474 #ifdef JP
2475                                 do_cmd_options_aux(OPT_PAGE_BIRTH, (!p_ptr->wizard || !allow_debug_opts) ? "½é´ü¥ª¥×¥·¥ç¥ó(»²¾È¤Î¤ß)" : "½é´ü¥ª¥×¥·¥ç¥ó((*)¤Ï¥¹¥³¥¢¤Ë±Æ¶Á)");
2476 #else
2477                                 do_cmd_options_aux(OPT_PAGE_BIRTH, (!p_ptr->wizard || !allow_debug_opts) ? "Birth Options(browse only)" : "Birth Options((*)s effect score)");
2478 #endif
2479
2480                                 break;
2481                         }
2482
2483                         /* Cheating Options */
2484                         case 'C':
2485                         {
2486                                 if (!p_ptr->noscore && !allow_debug_opts)
2487                                 {
2488                                         /* Cheat options are not permitted */
2489                                         bell();
2490                                         break;
2491                                 }
2492
2493                                 /* Spawn */
2494 #ifdef JP
2495                                 do_cmd_options_cheat("º¾µ½»Õ¤Ï·è¤·¤Æ¾¡Íø¤Ç¤­¤Ê¤¤¡ª");
2496 #else
2497                                 do_cmd_options_cheat("Cheaters never win");
2498 #endif
2499
2500                                 break;
2501                         }
2502
2503                         case 'a':
2504                         case 'A':
2505                         {
2506 #ifdef JP
2507                                 do_cmd_options_autosave("¼«Æ°¥»¡¼¥Ö");
2508 #else
2509                                 do_cmd_options_autosave("Autosave");
2510 #endif
2511
2512                                 break;
2513                         }
2514
2515                         /* Window flags */
2516                         case 'W':
2517                         case 'w':
2518                         {
2519                                 /* Spawn */
2520                                 do_cmd_options_win();
2521                                 p_ptr->window |= (PW_INVEN | PW_EQUIP | PW_SPELL |
2522                                                   PW_PLAYER | PW_MESSAGE | PW_OVERHEAD |
2523                                                   PW_MONSTER | PW_OBJECT | PW_SNAPSHOT |
2524                                                   PW_BORG_1 | PW_BORG_2 | PW_DUNGEON);
2525                                 break;
2526                         }
2527
2528                         /* Auto-picker/destroyer editor */
2529                         case 'P':
2530                         case 'p':
2531                         {
2532                                 do_cmd_edit_autopick();
2533                                 break;
2534                         }
2535
2536                         /* Hack -- Delay Speed */
2537                         case 'D':
2538                         case 'd':
2539                         {
2540                                 /* Prompt */
2541 #ifdef JP
2542                                 prt("¥³¥Þ¥ó¥É: ´ðËÜ¥¦¥§¥¤¥ÈÎÌ", 19, 0);
2543 #else
2544                                 prt("Command: Base Delay Factor", 19, 0);
2545 #endif
2546
2547
2548                                 /* Get a new value */
2549                                 while (1)
2550                                 {
2551                                         int msec = delay_factor * delay_factor * delay_factor;
2552 #ifdef JP
2553                                         prt(format("¸½ºß¤Î¥¦¥§¥¤¥È: %d (%d¥ß¥êÉÃ)",
2554                                                    delay_factor, msec), 22, 0);
2555 #else
2556                                         prt(format("Current base delay factor: %d (%d msec)",
2557                                                    delay_factor, msec), 22, 0);
2558 #endif
2559
2560 #ifdef JP
2561                                         prt("¥¦¥§¥¤¥È (0-9) ESC¤Ç·èÄê: ", 20, 0);
2562 #else
2563                                         prt("Delay Factor (0-9 or ESC to accept): ", 20, 0);
2564 #endif
2565
2566                                         k = inkey();
2567                                         if (k == ESCAPE) break;
2568                                         else if (k == '?')
2569                                         {
2570 #ifdef JP
2571                                                 (void)show_file(TRUE, "joption.txt#BaseDelay", NULL, 0, 0);
2572 #else
2573                                                 (void)show_file(TRUE, "option.txt#BaseDelay", NULL, 0, 0);
2574 #endif
2575                                                 Term_clear(); 
2576                                         }
2577                                         else if (isdigit(k)) delay_factor = D2I(k);
2578                                         else bell();
2579                                 }
2580
2581                                 break;
2582                         }
2583
2584                         /* Hack -- hitpoint warning factor */
2585                         case 'H':
2586                         case 'h':
2587                         {
2588                                 /* Prompt */
2589 #ifdef JP
2590                                 prt("¥³¥Þ¥ó¥É: Äã¥Ò¥Ã¥È¥Ý¥¤¥ó¥È·Ù¹ð", 19, 0);
2591 #else
2592                                 prt("Command: Hitpoint Warning", 19, 0);
2593 #endif
2594
2595
2596                                 /* Get a new value */
2597                                 while (1)
2598                                 {
2599 #ifdef JP
2600                                         prt(format("¸½ºß¤ÎÄã¥Ò¥Ã¥È¥Ý¥¤¥ó¥È·Ù¹ð: %d0%%",
2601                                                    hitpoint_warn), 22, 0);
2602 #else
2603                                         prt(format("Current hitpoint warning: %d0%%",
2604                                                    hitpoint_warn), 22, 0);
2605 #endif
2606
2607 #ifdef JP
2608                                         prt("Äã¥Ò¥Ã¥È¥Ý¥¤¥ó¥È·Ù¹ð (0-9) ESC¤Ç·èÄê: ", 20, 0);
2609 #else
2610                                         prt("Hitpoint Warning (0-9 or ESC to accept): ", 20, 0);
2611 #endif
2612
2613                                         k = inkey();
2614                                         if (k == ESCAPE) break;
2615                                         else if (k == '?')
2616                                         {
2617 #ifdef JP
2618                                                 (void)show_file(TRUE, "joption.txt#Hitpoint", NULL, 0, 0);
2619 #else
2620                                                 (void)show_file(TRUE, "option.txt#Hitpoint", NULL, 0, 0);
2621 #endif
2622                                                 Term_clear(); 
2623                                         }
2624                                         else if (isdigit(k)) hitpoint_warn = D2I(k);
2625                                         else bell();
2626                                 }
2627
2628                                 break;
2629                         }
2630
2631                         /* Hack -- mana color factor */
2632                         case 'M':
2633                         case 'm':
2634                         {
2635                                 /* Prompt */
2636 #ifdef JP
2637                                 prt("¥³¥Þ¥ó¥É: ÄãËâÎÏ¿§ïçÃÍ", 19, 0);
2638 #else
2639                                 prt("Command: Mana Color Threshold", 19, 0);
2640 #endif
2641
2642
2643                                 /* Get a new value */
2644                                 while (1)
2645                                 {
2646 #ifdef JP
2647                                         prt(format("¸½ºß¤ÎÄãËâÎÏ¿§ïçÃÍ: %d0%%",
2648                                                    mana_warn), 22, 0);
2649 #else
2650                                         prt(format("Current mana color threshold: %d0%%",
2651                                                    mana_warn), 22, 0);
2652 #endif
2653
2654 #ifdef JP
2655                                         prt("ÄãËâÎÏïçÃÍ (0-9) ESC¤Ç·èÄê: ", 20, 0);
2656 #else
2657                                         prt("Mana color Threshold (0-9 or ESC to accept): ", 20, 0);
2658 #endif
2659
2660                                         k = inkey();
2661                                         if (k == ESCAPE) break;
2662                                         else if (k == '?')
2663                                         {
2664 #ifdef JP
2665                                                 (void)show_file(TRUE, "joption.txt#Manapoint", NULL, 0, 0);
2666 #else
2667                                                 (void)show_file(TRUE, "option.txt#Manapoint", NULL, 0, 0);
2668 #endif
2669                                                 Term_clear(); 
2670                                         }
2671                                         else if (isdigit(k)) mana_warn = D2I(k);
2672                                         else bell();
2673                                 }
2674
2675                                 break;
2676                         }
2677
2678                         case '?':
2679 #ifdef JP
2680                                 (void)show_file(TRUE, "joption.txt", NULL, 0, 0);
2681 #else
2682                                 (void)show_file(TRUE, "option.txt", NULL, 0, 0);
2683 #endif
2684                                 Term_clear(); 
2685                                 break;
2686
2687                         /* Unknown option */
2688                         default:
2689                         {
2690                                 /* Oops */
2691                                 bell();
2692                                 break;
2693                         }
2694                 }
2695
2696                 /* Flush messages */
2697                 msg_print(NULL);
2698         }
2699
2700
2701         /* Restore the screen */
2702         screen_load();
2703
2704         /* Hack - Redraw equippy chars */
2705         p_ptr->redraw |= (PR_EQUIPPY);
2706 }
2707
2708
2709
2710 /*
2711  * Ask for a "user pref line" and process it
2712  *
2713  * XXX XXX XXX Allow absolute file names?
2714  */
2715 void do_cmd_pref(void)
2716 {
2717         char buf[80];
2718
2719         /* Default */
2720         strcpy(buf, "");
2721
2722         /* Ask for a "user pref command" */
2723 #ifdef JP
2724         if (!get_string("ÀßÄêÊѹ¹¥³¥Þ¥ó¥É: ", buf, 80)) return;
2725 #else
2726         if (!get_string("Pref: ", buf, 80)) return;
2727 #endif
2728
2729
2730         /* Process that pref command */
2731         (void)process_pref_file_command(buf);
2732 }
2733
2734 void do_cmd_reload_autopick(void)
2735 {
2736 #ifdef JP
2737         if (!get_check("¼«Æ°½¦¤¤ÀßÄê¥Õ¥¡¥¤¥ë¤ò¥í¡¼¥É¤·¤Þ¤¹¤«? ")) return;
2738 #else
2739         if (!get_check("Reload auto-pick preference file? ")) return;
2740 #endif
2741
2742         /* Load the file with messages */
2743         autopick_load_pref(TRUE);
2744 }
2745
2746 #ifdef ALLOW_MACROS
2747
2748 /*
2749  * Hack -- append all current macros to the given file
2750  */
2751 static errr macro_dump(cptr fname)
2752 {
2753         static cptr mark = "Macro Dump";
2754
2755         int i;
2756
2757         char buf[1024];
2758
2759         /* Build the filename */
2760         path_build(buf, sizeof(buf), ANGBAND_DIR_USER, fname);
2761
2762         /* File type is "TEXT" */
2763         FILE_TYPE(FILE_TYPE_TEXT);
2764
2765         /* Append to the file */
2766         if (!open_auto_dump(buf, mark)) return (-1);
2767
2768         /* Start dumping */
2769 #ifdef JP
2770         auto_dump_printf("\n# ¼«Æ°¥Þ¥¯¥í¥»¡¼¥Ö\n\n");
2771 #else
2772         auto_dump_printf("\n# Automatic macro dump\n\n");
2773 #endif
2774
2775         /* Dump them */
2776         for (i = 0; i < macro__num; i++)
2777         {
2778                 /* Extract the action */
2779                 ascii_to_text(buf, macro__act[i]);
2780
2781                 /* Dump the macro */
2782                 auto_dump_printf("A:%s\n", buf);
2783
2784                 /* Extract the action */
2785                 ascii_to_text(buf, macro__pat[i]);
2786
2787                 /* Dump normal macros */
2788                 auto_dump_printf("P:%s\n", buf);
2789
2790                 /* End the macro */
2791                 auto_dump_printf("\n");
2792         }
2793
2794         /* Close */
2795         close_auto_dump();
2796
2797         /* Success */
2798         return (0);
2799 }
2800
2801
2802 /*
2803  * Hack -- ask for a "trigger" (see below)
2804  *
2805  * Note the complex use of the "inkey()" function from "util.c".
2806  *
2807  * Note that both "flush()" calls are extremely important.
2808  */
2809 static void do_cmd_macro_aux(char *buf)
2810 {
2811         int i, n = 0;
2812
2813         char tmp[1024];
2814
2815
2816         /* Flush */
2817         flush();
2818
2819         /* Do not process macros */
2820         inkey_base = TRUE;
2821
2822         /* First key */
2823         i = inkey();
2824
2825         /* Read the pattern */
2826         while (i)
2827         {
2828                 /* Save the key */
2829                 buf[n++] = i;
2830
2831                 /* Do not process macros */
2832                 inkey_base = TRUE;
2833
2834                 /* Do not wait for keys */
2835                 inkey_scan = TRUE;
2836
2837                 /* Attempt to read a key */
2838                 i = inkey();
2839         }
2840
2841         /* Terminate */
2842         buf[n] = '\0';
2843
2844         /* Flush */
2845         flush();
2846
2847
2848         /* Convert the trigger */
2849         ascii_to_text(tmp, buf);
2850
2851         /* Hack -- display the trigger */
2852         Term_addstr(-1, TERM_WHITE, tmp);
2853 }
2854
2855 #endif
2856
2857
2858 /*
2859  * Hack -- ask for a keymap "trigger" (see below)
2860  *
2861  * Note that both "flush()" calls are extremely important.  This may
2862  * no longer be true, since "util.c" is much simpler now.  XXX XXX XXX
2863  */
2864 static void do_cmd_macro_aux_keymap(char *buf)
2865 {
2866         char tmp[1024];
2867
2868
2869         /* Flush */
2870         flush();
2871
2872
2873         /* Get a key */
2874         buf[0] = inkey();
2875         buf[1] = '\0';
2876
2877
2878         /* Convert to ascii */
2879         ascii_to_text(tmp, buf);
2880
2881         /* Hack -- display the trigger */
2882         Term_addstr(-1, TERM_WHITE, tmp);
2883
2884
2885         /* Flush */
2886         flush();
2887 }
2888
2889
2890 /*
2891  * Hack -- append all keymaps to the given file
2892  */
2893 static errr keymap_dump(cptr fname)
2894 {
2895         static cptr mark = "Keymap Dump";
2896         int i;
2897
2898         char key[1024];
2899         char buf[1024];
2900
2901         int mode;
2902
2903         /* Roguelike */
2904         if (rogue_like_commands)
2905         {
2906                 mode = KEYMAP_MODE_ROGUE;
2907         }
2908
2909         /* Original */
2910         else
2911         {
2912                 mode = KEYMAP_MODE_ORIG;
2913         }
2914
2915
2916         /* Build the filename */
2917         path_build(buf, sizeof(buf), ANGBAND_DIR_USER, fname);
2918
2919         /* File type is "TEXT" */
2920         FILE_TYPE(FILE_TYPE_TEXT);
2921
2922         /* Append to the file */
2923         if (!open_auto_dump(buf, mark)) return -1;
2924
2925         /* Start dumping */
2926 #ifdef JP
2927         auto_dump_printf("\n# ¼«Æ°¥­¡¼ÇÛÃÖ¥»¡¼¥Ö\n\n");
2928 #else
2929         auto_dump_printf("\n# Automatic keymap dump\n\n");
2930 #endif
2931
2932         /* Dump them */
2933         for (i = 0; i < 256; i++)
2934         {
2935                 cptr act;
2936
2937                 /* Loop up the keymap */
2938                 act = keymap_act[mode][i];
2939
2940                 /* Skip empty keymaps */
2941                 if (!act) continue;
2942
2943                 /* Encode the key */
2944                 buf[0] = i;
2945                 buf[1] = '\0';
2946                 ascii_to_text(key, buf);
2947
2948                 /* Encode the action */
2949                 ascii_to_text(buf, act);
2950
2951                 /* Dump the macro */
2952                 auto_dump_printf("A:%s\n", buf);
2953                 auto_dump_printf("C:%d:%s\n", mode, key);
2954         }
2955
2956         /* Close */
2957         close_auto_dump();
2958
2959         /* Success */
2960         return (0);
2961 }
2962
2963
2964
2965 /*
2966  * Interact with "macros"
2967  *
2968  * Note that the macro "action" must be defined before the trigger.
2969  *
2970  * Could use some helpful instructions on this page.  XXX XXX XXX
2971  */
2972 void do_cmd_macros(void)
2973 {
2974         int i;
2975
2976         char tmp[1024];
2977
2978         char buf[1024];
2979
2980         int mode;
2981
2982
2983         /* Roguelike */
2984         if (rogue_like_commands)
2985         {
2986                 mode = KEYMAP_MODE_ROGUE;
2987         }
2988
2989         /* Original */
2990         else
2991         {
2992                 mode = KEYMAP_MODE_ORIG;
2993         }
2994
2995         /* File type is "TEXT" */
2996         FILE_TYPE(FILE_TYPE_TEXT);
2997
2998
2999         /* Save screen */
3000         screen_save();
3001
3002
3003         /* Process requests until done */
3004         while (1)
3005         {
3006                 /* Clear screen */
3007                 Term_clear();
3008
3009                 /* Describe */
3010 #ifdef JP
3011                 prt("[ ¥Þ¥¯¥í¤ÎÀßÄê ]", 2, 0);
3012 #else
3013                 prt("Interact with Macros", 2, 0);
3014 #endif
3015
3016
3017
3018                 /* Describe that action */
3019 #ifdef JP
3020                 prt("¥Þ¥¯¥í¹ÔÆ°¤¬(¤â¤·¤¢¤ì¤Ð)²¼¤Ëɽ¼¨¤µ¤ì¤Þ¤¹:", 20, 0);
3021 #else
3022                 prt("Current action (if any) shown below:", 20, 0);
3023 #endif
3024
3025
3026                 /* Analyze the current action */
3027                 ascii_to_text(buf, macro__buf);
3028
3029                 /* Display the current action */
3030                 prt(buf, 22, 0);
3031
3032
3033                 /* Selections */
3034 #ifdef JP
3035                 prt("(1) ¥æ¡¼¥¶¡¼ÀßÄê¥Õ¥¡¥¤¥ë¤Î¥í¡¼¥É", 4, 5);
3036 #else
3037                 prt("(1) Load a user pref file", 4, 5);
3038 #endif
3039
3040 #ifdef ALLOW_MACROS
3041 #ifdef JP
3042                 prt("(2) ¥Õ¥¡¥¤¥ë¤Ë¥Þ¥¯¥í¤òÄɲÃ", 5, 5);
3043                 prt("(3) ¥Þ¥¯¥í¤Î³Îǧ", 6, 5);
3044                 prt("(4) ¥Þ¥¯¥í¤ÎºîÀ®", 7, 5);
3045                 prt("(5) ¥Þ¥¯¥í¤Îºï½ü", 8, 5);
3046                 prt("(6) ¥Õ¥¡¥¤¥ë¤Ë¥­¡¼ÇÛÃÖ¤òÄɲÃ", 9, 5);
3047                 prt("(7) ¥­¡¼ÇÛÃ֤γÎǧ", 10, 5);
3048                 prt("(8) ¥­¡¼ÇÛÃ֤κîÀ®", 11, 5);
3049                 prt("(9) ¥­¡¼ÇÛÃ֤κï½ü", 12, 5);
3050                 prt("(0) ¥Þ¥¯¥í¹ÔÆ°¤ÎÆþÎÏ", 13, 5);
3051 #else
3052                 prt("(2) Append macros to a file", 5, 5);
3053                 prt("(3) Query a macro", 6, 5);
3054                 prt("(4) Create a macro", 7, 5);
3055                 prt("(5) Remove a macro", 8, 5);
3056                 prt("(6) Append keymaps to a file", 9, 5);
3057                 prt("(7) Query a keymap", 10, 5);
3058                 prt("(8) Create a keymap", 11, 5);
3059                 prt("(9) Remove a keymap", 12, 5);
3060                 prt("(0) Enter a new action", 13, 5);
3061 #endif
3062
3063 #endif /* ALLOW_MACROS */
3064
3065                 /* Prompt */
3066 #ifdef JP
3067                 prt("¥³¥Þ¥ó¥É: ", 16, 0);
3068 #else
3069                 prt("Command: ", 16, 0);
3070 #endif
3071
3072
3073                 /* Get a command */
3074                 i = inkey();
3075
3076                 /* Leave */
3077                 if (i == ESCAPE) break;
3078
3079                 /* Load a 'macro' file */
3080                 else if (i == '1')
3081                 {
3082                         errr err;
3083
3084                         /* Prompt */
3085 #ifdef JP
3086                         prt("¥³¥Þ¥ó¥É: ¥æ¡¼¥¶¡¼ÀßÄê¥Õ¥¡¥¤¥ë¤Î¥í¡¼¥É", 16, 0);
3087 #else
3088                         prt("Command: Load a user pref file", 16, 0);
3089 #endif
3090
3091
3092                         /* Prompt */
3093 #ifdef JP
3094                         prt("¥Õ¥¡¥¤¥ë: ", 18, 0);
3095 #else
3096                         prt("File: ", 18, 0);
3097 #endif
3098
3099
3100                         /* Default filename */
3101                         sprintf(tmp, "%s.prf", player_name);
3102
3103                         /* Ask for a file */
3104                         if (!askfor(tmp, 80)) continue;
3105
3106                         /* Process the given filename */
3107                         err = process_pref_file(tmp);
3108                         if (-2 == err)
3109                         {
3110 #ifdef JP
3111                                 msg_format("ɸ½à¤ÎÀßÄê¥Õ¥¡¥¤¥ë'%s'¤òÆɤ߹þ¤ß¤Þ¤·¤¿¡£", tmp);
3112 #else
3113                                 msg_format("Loaded default '%s'.", tmp);
3114 #endif
3115                         }
3116                         else if (err)
3117                         {
3118                                 /* Prompt */
3119 #ifdef JP
3120                                 msg_format("'%s'¤ÎÆɤ߹þ¤ß¤Ë¼ºÇÔ¤·¤Þ¤·¤¿¡ª", tmp);
3121 #else
3122                                 msg_format("Failed to load '%s'!");
3123 #endif
3124                         }
3125                         else
3126                         {
3127 #ifdef JP
3128                                 msg_format("'%s'¤òÆɤ߹þ¤ß¤Þ¤·¤¿¡£", tmp);
3129 #else
3130                                 msg_format("Loaded '%s'.", tmp);
3131 #endif
3132                         }
3133                 }
3134
3135 #ifdef ALLOW_MACROS
3136
3137                 /* Save macros */
3138                 else if (i == '2')
3139                 {
3140                         /* Prompt */
3141 #ifdef JP
3142                         prt("¥³¥Þ¥ó¥É: ¥Þ¥¯¥í¤ò¥Õ¥¡¥¤¥ë¤ËÄɲ乤ë", 16, 0);
3143 #else
3144                         prt("Command: Append macros to a file", 16, 0);
3145 #endif
3146
3147
3148                         /* Prompt */
3149 #ifdef JP
3150                         prt("¥Õ¥¡¥¤¥ë: ", 18, 0);
3151 #else
3152                         prt("File: ", 18, 0);
3153 #endif
3154
3155
3156                         /* Default filename */
3157                         sprintf(tmp, "%s.prf", player_name);
3158
3159                         /* Ask for a file */
3160                         if (!askfor(tmp, 80)) continue;
3161
3162                         /* Dump the macros */
3163                         (void)macro_dump(tmp);
3164
3165                         /* Prompt */
3166 #ifdef JP
3167                         msg_print("¥Þ¥¯¥í¤òÄɲä·¤Þ¤·¤¿¡£");
3168 #else
3169                         msg_print("Appended macros.");
3170 #endif
3171
3172                 }
3173
3174                 /* Query a macro */
3175                 else if (i == '3')
3176                 {
3177                         int k;
3178
3179                         /* Prompt */
3180 #ifdef JP
3181                         prt("¥³¥Þ¥ó¥É: ¥Þ¥¯¥í¤Î³Îǧ", 16, 0);
3182 #else
3183                         prt("Command: Query a macro", 16, 0);
3184 #endif
3185
3186
3187                         /* Prompt */
3188 #ifdef JP
3189                         prt("¥È¥ê¥¬¡¼¥­¡¼: ", 18, 0);
3190 #else
3191                         prt("Trigger: ", 18, 0);
3192 #endif
3193
3194
3195                         /* Get a macro trigger */
3196                         do_cmd_macro_aux(buf);
3197
3198                         /* Acquire action */
3199                         k = macro_find_exact(buf);
3200
3201                         /* Nothing found */
3202                         if (k < 0)
3203                         {
3204                                 /* Prompt */
3205 #ifdef JP
3206                                 msg_print("¤½¤Î¥­¡¼¤Ë¤Ï¥Þ¥¯¥í¤ÏÄêµÁ¤µ¤ì¤Æ¤¤¤Þ¤»¤ó¡£");
3207 #else
3208                                 msg_print("Found no macro.");
3209 #endif
3210
3211                         }
3212
3213                         /* Found one */
3214                         else
3215                         {
3216                                 /* Obtain the action */
3217                                 strcpy(macro__buf, macro__act[k]);
3218
3219                                 /* Analyze the current action */
3220                                 ascii_to_text(buf, macro__buf);
3221
3222                                 /* Display the current action */
3223                                 prt(buf, 22, 0);
3224
3225                                 /* Prompt */
3226 #ifdef JP
3227                                 msg_print("¥Þ¥¯¥í¤ò³Îǧ¤·¤Þ¤·¤¿¡£");
3228 #else
3229                                 msg_print("Found a macro.");
3230 #endif
3231
3232                         }
3233                 }
3234
3235                 /* Create a macro */
3236                 else if (i == '4')
3237                 {
3238                         /* Prompt */
3239 #ifdef JP
3240                         prt("¥³¥Þ¥ó¥É: ¥Þ¥¯¥í¤ÎºîÀ®", 16, 0);
3241 #else
3242                         prt("Command: Create a macro", 16, 0);
3243 #endif
3244
3245
3246                         /* Prompt */
3247 #ifdef JP
3248                         prt("¥È¥ê¥¬¡¼¥­¡¼: ", 18, 0);
3249 #else
3250                         prt("Trigger: ", 18, 0);
3251 #endif
3252
3253
3254                         /* Get a macro trigger */
3255                         do_cmd_macro_aux(buf);
3256
3257                         /* Clear */
3258                         clear_from(20);
3259
3260                         /* Help message */
3261 #ifdef JP
3262                         c_prt(TERM_L_RED, "¥«¡¼¥½¥ë¥­¡¼¤Îº¸±¦¤Ç¥«¡¼¥½¥ë°ÌÃÖ¤ò°ÜÆ°¡£Backspace¤«Delete¤Ç°ìʸ»úºï½ü¡£", 22, 0);
3263 #else
3264                         c_prt(TERM_L_RED, "Press Left/Right arrow keys to move cursor. Backspace/Delete to delete a char.", 22, 0);
3265 #endif
3266
3267                         /* Prompt */
3268 #ifdef JP
3269                         prt("¥Þ¥¯¥í¹ÔÆ°: ", 20, 0);
3270 #else
3271                         prt("Action: ", 20, 0);
3272 #endif
3273
3274
3275                         /* Convert to text */
3276                         ascii_to_text(tmp, macro__buf);
3277
3278                         /* Get an encoded action */
3279                         if (askfor(tmp, 80))
3280                         {
3281                                 /* Convert to ascii */
3282                                 text_to_ascii(macro__buf, tmp);
3283
3284                                 /* Link the macro */
3285                                 macro_add(buf, macro__buf);
3286
3287                                 /* Prompt */
3288 #ifdef JP
3289                                 msg_print("¥Þ¥¯¥í¤òÄɲä·¤Þ¤·¤¿¡£");
3290 #else
3291                                 msg_print("Added a macro.");
3292 #endif
3293
3294                         }
3295                 }
3296
3297                 /* Remove a macro */
3298                 else if (i == '5')
3299                 {
3300                         /* Prompt */
3301 #ifdef JP
3302                         prt("¥³¥Þ¥ó¥É: ¥Þ¥¯¥í¤Îºï½ü", 16, 0);
3303 #else
3304                         prt("Command: Remove a macro", 16, 0);
3305 #endif
3306
3307
3308                         /* Prompt */
3309 #ifdef JP
3310                         prt("¥È¥ê¥¬¡¼¥­¡¼: ", 18, 0);
3311 #else
3312                         prt("Trigger: ", 18, 0);
3313 #endif
3314
3315
3316                         /* Get a macro trigger */
3317                         do_cmd_macro_aux(buf);
3318
3319                         /* Link the macro */
3320                         macro_add(buf, buf);
3321
3322                         /* Prompt */
3323 #ifdef JP
3324                         msg_print("¥Þ¥¯¥í¤òºï½ü¤·¤Þ¤·¤¿¡£");
3325 #else
3326                         msg_print("Removed a macro.");
3327 #endif
3328
3329                 }
3330
3331                 /* Save keymaps */
3332                 else if (i == '6')
3333                 {
3334                         /* Prompt */
3335 #ifdef JP
3336                         prt("¥³¥Þ¥ó¥É: ¥­¡¼ÇÛÃÖ¤ò¥Õ¥¡¥¤¥ë¤ËÄɲ乤ë", 16, 0);
3337 #else
3338                         prt("Command: Append keymaps to a file", 16, 0);
3339 #endif
3340
3341
3342                         /* Prompt */
3343 #ifdef JP
3344                         prt("¥Õ¥¡¥¤¥ë: ", 18, 0);
3345 #else
3346                         prt("File: ", 18, 0);
3347 #endif
3348
3349
3350                         /* Default filename */
3351                         sprintf(tmp, "%s.prf", player_name);
3352
3353                         /* Ask for a file */
3354                         if (!askfor(tmp, 80)) continue;
3355
3356                         /* Dump the macros */
3357                         (void)keymap_dump(tmp);
3358
3359                         /* Prompt */
3360 #ifdef JP
3361                         msg_print("¥­¡¼ÇÛÃÖ¤òÄɲä·¤Þ¤·¤¿¡£");
3362 #else
3363                         msg_print("Appended keymaps.");
3364 #endif
3365
3366                 }
3367
3368                 /* Query a keymap */
3369                 else if (i == '7')
3370                 {
3371                         cptr act;
3372
3373                         /* Prompt */
3374 #ifdef JP
3375                         prt("¥³¥Þ¥ó¥É: ¥­¡¼ÇÛÃ֤γÎǧ", 16, 0);
3376 #else
3377                         prt("Command: Query a keymap", 16, 0);
3378 #endif
3379
3380
3381                         /* Prompt */
3382 #ifdef JP
3383                         prt("²¡¤¹¥­¡¼: ", 18, 0);
3384 #else
3385                         prt("Keypress: ", 18, 0);
3386 #endif
3387
3388
3389                         /* Get a keymap trigger */
3390                         do_cmd_macro_aux_keymap(buf);
3391
3392                         /* Look up the keymap */
3393                         act = keymap_act[mode][(byte)(buf[0])];
3394
3395                         /* Nothing found */
3396                         if (!act)
3397                         {
3398                                 /* Prompt */
3399 #ifdef JP
3400                                 msg_print("¥­¡¼ÇÛÃÖ¤ÏÄêµÁ¤µ¤ì¤Æ¤¤¤Þ¤»¤ó¡£");
3401 #else
3402                                 msg_print("Found no keymap.");
3403 #endif
3404
3405                         }
3406
3407                         /* Found one */
3408                         else
3409                         {
3410                                 /* Obtain the action */
3411                                 strcpy(macro__buf, act);
3412
3413                                 /* Analyze the current action */
3414                                 ascii_to_text(buf, macro__buf);
3415
3416                                 /* Display the current action */
3417                                 prt(buf, 22, 0);
3418
3419                                 /* Prompt */
3420 #ifdef JP
3421                                 msg_print("¥­¡¼ÇÛÃÖ¤ò³Îǧ¤·¤Þ¤·¤¿¡£");
3422 #else
3423                                 msg_print("Found a keymap.");
3424 #endif
3425
3426                         }
3427                 }
3428
3429                 /* Create a keymap */
3430                 else if (i == '8')
3431                 {
3432                         /* Prompt */
3433 #ifdef JP
3434                         prt("¥³¥Þ¥ó¥É: ¥­¡¼ÇÛÃ֤κîÀ®", 16, 0);
3435 #else
3436                         prt("Command: Create a keymap", 16, 0);
3437 #endif
3438
3439
3440                         /* Prompt */
3441 #ifdef JP
3442                         prt("²¡¤¹¥­¡¼: ", 18, 0);
3443 #else
3444                         prt("Keypress: ", 18, 0);
3445 #endif
3446
3447
3448                         /* Get a keymap trigger */
3449                         do_cmd_macro_aux_keymap(buf);
3450
3451                         /* Clear */
3452                         clear_from(20);
3453
3454                         /* Help message */
3455 #ifdef JP
3456                         c_prt(TERM_L_RED, "¥«¡¼¥½¥ë¥­¡¼¤Îº¸±¦¤Ç¥«¡¼¥½¥ë°ÌÃÖ¤ò°ÜÆ°¡£Backspace¤«Delete¤Ç°ìʸ»úºï½ü¡£", 22, 0);
3457 #else
3458                         c_prt(TERM_L_RED, "Press Left/Right arrow keys to move cursor. Backspace/Delete to delete a char.", 22, 0);
3459 #endif
3460
3461                         /* Prompt */
3462 #ifdef JP
3463                         prt("¹ÔÆ°: ", 20, 0);
3464 #else
3465                         prt("Action: ", 20, 0);
3466 #endif
3467
3468
3469                         /* Convert to text */
3470                         ascii_to_text(tmp, macro__buf);
3471
3472                         /* Get an encoded action */
3473                         if (askfor(tmp, 80))
3474                         {
3475                                 /* Convert to ascii */
3476                                 text_to_ascii(macro__buf, tmp);
3477
3478                                 /* Free old keymap */
3479                                 string_free(keymap_act[mode][(byte)(buf[0])]);
3480
3481                                 /* Make new keymap */
3482                                 keymap_act[mode][(byte)(buf[0])] = string_make(macro__buf);
3483
3484                                 /* Prompt */
3485 #ifdef JP
3486                                 msg_print("¥­¡¼ÇÛÃÖ¤òÄɲä·¤Þ¤·¤¿¡£");
3487 #else
3488                                 msg_print("Added a keymap.");
3489 #endif
3490
3491                         }
3492                 }
3493
3494                 /* Remove a keymap */
3495                 else if (i == '9')
3496                 {
3497                         /* Prompt */
3498 #ifdef JP
3499                         prt("¥³¥Þ¥ó¥É: ¥­¡¼ÇÛÃ֤κï½ü", 16, 0);
3500 #else
3501                         prt("Command: Remove a keymap", 16, 0);
3502 #endif
3503
3504
3505                         /* Prompt */
3506 #ifdef JP
3507                         prt("²¡¤¹¥­¡¼: ", 18, 0);
3508 #else
3509                         prt("Keypress: ", 18, 0);
3510 #endif
3511
3512
3513                         /* Get a keymap trigger */
3514                         do_cmd_macro_aux_keymap(buf);
3515
3516                         /* Free old keymap */
3517                         string_free(keymap_act[mode][(byte)(buf[0])]);
3518
3519                         /* Make new keymap */
3520                         keymap_act[mode][(byte)(buf[0])] = NULL;
3521
3522                         /* Prompt */
3523 #ifdef JP
3524                         msg_print("¥­¡¼ÇÛÃÖ¤òºï½ü¤·¤Þ¤·¤¿¡£");
3525 #else
3526                         msg_print("Removed a keymap.");
3527 #endif
3528
3529                 }
3530
3531                 /* Enter a new action */
3532                 else if (i == '0')
3533                 {
3534                         /* Prompt */
3535 #ifdef JP
3536                         prt("¥³¥Þ¥ó¥É: ¥Þ¥¯¥í¹ÔÆ°¤ÎÆþÎÏ", 16, 0);
3537 #else
3538                         prt("Command: Enter a new action", 16, 0);
3539 #endif
3540
3541                         /* Clear */
3542                         clear_from(20);
3543
3544                         /* Help message */
3545 #ifdef JP
3546                         c_prt(TERM_L_RED, "¥«¡¼¥½¥ë¥­¡¼¤Îº¸±¦¤Ç¥«¡¼¥½¥ë°ÌÃÖ¤ò°ÜÆ°¡£Backspace¤«Delete¤Ç°ìʸ»úºï½ü¡£", 22, 0);
3547 #else
3548                         c_prt(TERM_L_RED, "Press Left/Right arrow keys to move cursor. Backspace/Delete to delete a char.", 22, 0);
3549 #endif
3550
3551                         /* Prompt */
3552 #ifdef JP
3553                         prt("¥Þ¥¯¥í¹ÔÆ°: ", 20, 0);
3554 #else
3555                         prt("Action: ", 20, 0);
3556 #endif
3557
3558                         /* Hack -- limit the value */
3559                         tmp[80] = '\0';
3560
3561                         /* Get an encoded action */
3562                         if (!askfor(buf, 80)) continue;
3563
3564                         /* Extract an action */
3565                         text_to_ascii(macro__buf, buf);
3566                 }
3567
3568 #endif /* ALLOW_MACROS */
3569
3570                 /* Oops */
3571                 else
3572                 {
3573                         /* Oops */
3574                         bell();
3575                 }
3576
3577                 /* Flush messages */
3578                 msg_print(NULL);
3579         }
3580
3581         /* Load screen */
3582         screen_load();
3583 }
3584
3585
3586 static cptr lighting_level_str[F_LIT_MAX] =
3587 {
3588 #ifdef JP
3589         "ɸ½à¿§",
3590         "ÌÀ¿§",
3591         "°Å¿§",
3592 #else
3593         "standard",
3594         "brightly lit",
3595         "darkened",
3596 #endif
3597 };
3598
3599
3600 static bool cmd_visuals_aux(int i, int *num, int max)
3601 {
3602         if (iscntrl(i))
3603         {
3604                 char str[10] = "";
3605                 int tmp;
3606
3607                 sprintf(str, "%d", *num);
3608
3609                 if (!get_string(format("Input new number(0-%d): ", max-1), str, 4))
3610                         return FALSE;
3611
3612                 tmp = strtol(str, NULL, 0);
3613                 if (tmp >= 0 && tmp < max)
3614                         *num = tmp;
3615         }
3616         else if (isupper(i))
3617                 *num = (*num + max - 1) % max;
3618         else
3619                 *num = (*num + 1) % max;
3620
3621         return TRUE;
3622 }
3623
3624 static void print_visuals_menu(cptr choice_msg)
3625 {
3626 #ifdef JP
3627         prt("²èÌÌɽ¼¨¤ÎÀßÄê", 1, 0);
3628 #else
3629         prt("Interact with Visuals", 1, 0);
3630 #endif
3631
3632         /* Give some choices */
3633 #ifdef JP
3634         prt("(0) ¥æ¡¼¥¶¡¼ÀßÄê¥Õ¥¡¥¤¥ë¤Î¥í¡¼¥É", 3, 5);
3635 #else
3636         prt("(0) Load a user pref file", 3, 5);
3637 #endif
3638
3639 #ifdef ALLOW_VISUALS
3640 #ifdef JP
3641         prt("(1) ¥â¥ó¥¹¥¿¡¼¤Î ¿§/ʸ»ú ¤ò¥Õ¥¡¥¤¥ë¤Ë½ñ¤­½Ð¤¹", 4, 5);
3642         prt("(2) ¥¢¥¤¥Æ¥à¤Î   ¿§/ʸ»ú ¤ò¥Õ¥¡¥¤¥ë¤Ë½ñ¤­½Ð¤¹", 5, 5);
3643         prt("(3) ÃÏ·Á¤Î       ¿§/ʸ»ú ¤ò¥Õ¥¡¥¤¥ë¤Ë½ñ¤­½Ð¤¹", 6, 5);
3644         prt("(4) ¥â¥ó¥¹¥¿¡¼¤Î ¿§/ʸ»ú ¤òÊѹ¹¤¹¤ë (¿ôÃÍÁàºî)", 7, 5);
3645         prt("(5) ¥¢¥¤¥Æ¥à¤Î   ¿§/ʸ»ú ¤òÊѹ¹¤¹¤ë (¿ôÃÍÁàºî)", 8, 5);
3646         prt("(6) ÃÏ·Á¤Î       ¿§/ʸ»ú ¤òÊѹ¹¤¹¤ë (¿ôÃÍÁàºî)", 9, 5);
3647         prt("(7) ¥â¥ó¥¹¥¿¡¼¤Î ¿§/ʸ»ú ¤òÊѹ¹¤¹¤ë (¥·¥ó¥Ü¥ë¥¨¥Ç¥£¥¿)", 10, 5);
3648         prt("(8) ¥¢¥¤¥Æ¥à¤Î   ¿§/ʸ»ú ¤òÊѹ¹¤¹¤ë (¥·¥ó¥Ü¥ë¥¨¥Ç¥£¥¿)", 11, 5);
3649         prt("(9) ÃÏ·Á¤Î       ¿§/ʸ»ú ¤òÊѹ¹¤¹¤ë (¥·¥ó¥Ü¥ë¥¨¥Ç¥£¥¿)", 12, 5);
3650 #else
3651         prt("(1) Dump monster attr/chars", 4, 5);
3652         prt("(2) Dump object attr/chars", 5, 5);
3653         prt("(3) Dump feature attr/chars", 6, 5);
3654         prt("(4) Change monster attr/chars (numeric operation)", 7, 5);
3655         prt("(5) Change object attr/chars (numeric operation)", 8, 5);
3656         prt("(6) Change feature attr/chars (numeric operation)", 9, 5);
3657         prt("(7) Change monster attr/chars (visual mode)", 10, 5);
3658         prt("(8) Change object attr/chars (visual mode)", 11, 5);
3659         prt("(9) Change feature attr/chars (visual mode)", 12, 5);
3660 #endif
3661
3662 #endif /* ALLOW_VISUALS */
3663
3664 #ifdef JP
3665         prt("(R) ²èÌÌɽ¼¨ÊýË¡¤Î½é´ü²½", 13, 5);
3666 #else
3667         prt("(R) Reset visuals", 13, 5);
3668 #endif
3669
3670         /* Prompt */
3671 #ifdef JP
3672         prt(format("¥³¥Þ¥ó¥É: %s", choice_msg ? choice_msg : ""), 15, 0);
3673 #else
3674         prt(format("Command: %s", choice_msg ? choice_msg : ""), 15, 0);
3675 #endif
3676 }
3677
3678 static void do_cmd_knowledge_monsters(bool *need_redraw, bool visual_only, int direct_r_idx);
3679 static void do_cmd_knowledge_objects(bool *need_redraw, bool visual_only, int direct_k_idx);
3680 static void do_cmd_knowledge_features(bool *need_redraw, bool visual_only, int direct_f_idx, int *lighting_level);
3681
3682 /*
3683  * Interact with "visuals"
3684  */
3685 void do_cmd_visuals(void)
3686 {
3687         int i;
3688         char tmp[160];
3689         char buf[1024];
3690         bool need_redraw = FALSE;
3691         const char *empty_symbol = "<< ? >>";
3692
3693         if (use_bigtile) empty_symbol = "<< ?? >>";
3694
3695         /* File type is "TEXT" */
3696         FILE_TYPE(FILE_TYPE_TEXT);
3697
3698         /* Save the screen */
3699         screen_save();
3700
3701         /* Interact until done */
3702         while (1)
3703         {
3704                 /* Clear screen */
3705                 Term_clear();
3706
3707                 /* Ask for a choice */
3708                 print_visuals_menu(NULL);
3709
3710                 /* Prompt */
3711                 i = inkey();
3712
3713                 /* Done */
3714                 if (i == ESCAPE) break;
3715
3716                 switch (i)
3717                 {
3718                 /* Load a 'pref' file */
3719                 case '0':
3720                         /* Prompt */
3721 #ifdef JP
3722                         prt("¥³¥Þ¥ó¥É: ¥æ¡¼¥¶¡¼ÀßÄê¥Õ¥¡¥¤¥ë¤Î¥í¡¼¥É", 15, 0);
3723 #else
3724                         prt("Command: Load a user pref file", 15, 0);
3725 #endif
3726
3727                         /* Prompt */
3728 #ifdef JP
3729                         prt("¥Õ¥¡¥¤¥ë: ", 17, 0);
3730 #else
3731                         prt("File: ", 17, 0);
3732 #endif
3733
3734                         /* Default filename */
3735                         sprintf(tmp, "%s.prf", player_name);
3736
3737                         /* Query */
3738                         if (!askfor(tmp, 70)) continue;
3739
3740                         /* Process the given filename */
3741                         (void)process_pref_file(tmp);
3742
3743                         need_redraw = TRUE;
3744                         break;
3745
3746 #ifdef ALLOW_VISUALS
3747
3748                 /* Dump monster attr/chars */
3749                 case '1':
3750                 {
3751                         static cptr mark = "Monster attr/chars";
3752
3753                         /* Prompt */
3754 #ifdef JP
3755                         prt("¥³¥Þ¥ó¥É: ¥â¥ó¥¹¥¿¡¼¤Î[¿§/ʸ»ú]¤ò¥Õ¥¡¥¤¥ë¤Ë½ñ¤­½Ð¤·¤Þ¤¹", 15, 0);
3756 #else
3757                         prt("Command: Dump monster attr/chars", 15, 0);
3758 #endif
3759
3760                         /* Prompt */
3761 #ifdef JP
3762                         prt("¥Õ¥¡¥¤¥ë: ", 17, 0);
3763 #else
3764                         prt("File: ", 17, 0);
3765 #endif
3766
3767                         /* Default filename */
3768                         sprintf(tmp, "%s.prf", player_name);
3769
3770                         /* Get a filename */
3771                         if (!askfor(tmp, 70)) continue;
3772
3773                         /* Build the filename */
3774                         path_build(buf, sizeof(buf), ANGBAND_DIR_USER, tmp);
3775
3776                         /* Append to the file */
3777                         if (!open_auto_dump(buf, mark)) continue;
3778
3779                         /* Start dumping */
3780 #ifdef JP
3781                         auto_dump_printf("\n# ¥â¥ó¥¹¥¿¡¼¤Î[¿§/ʸ»ú]¤ÎÀßÄê\n\n");
3782 #else
3783                         auto_dump_printf("\n# Monster attr/char definitions\n\n");
3784 #endif
3785
3786                         /* Dump monsters */
3787                         for (i = 1; i < max_r_idx; i++)
3788                         {
3789                                 monster_race *r_ptr = &r_info[i];
3790
3791                                 /* Skip non-entries */
3792                                 if (!r_ptr->name) continue;
3793
3794                                 /* Dump a comment */
3795                                 auto_dump_printf("# %s\n", (r_name + r_ptr->name));
3796
3797                                 /* Dump the monster attr/char info */
3798                                 auto_dump_printf("R:%d:0x%02X/0x%02X\n\n", i,
3799                                         (byte)(r_ptr->x_attr), (byte)(r_ptr->x_char));
3800                         }
3801
3802                         /* Close */
3803                         close_auto_dump();
3804
3805                         /* Message */
3806 #ifdef JP
3807                         msg_print("¥â¥ó¥¹¥¿¡¼¤Î[¿§/ʸ»ú]¤ò¥Õ¥¡¥¤¥ë¤Ë½ñ¤­½Ð¤·¤Þ¤·¤¿¡£");
3808 #else
3809                         msg_print("Dumped monster attr/chars.");
3810 #endif
3811
3812                         break;
3813                 }
3814
3815                 /* Dump object attr/chars */
3816                 case '2':
3817                 {
3818                         static cptr mark = "Object attr/chars";
3819
3820                         /* Prompt */
3821 #ifdef JP
3822                         prt("¥³¥Þ¥ó¥É: ¥¢¥¤¥Æ¥à¤Î[¿§/ʸ»ú]¤ò¥Õ¥¡¥¤¥ë¤Ë½ñ¤­½Ð¤·¤Þ¤¹", 15, 0);
3823 #else
3824                         prt("Command: Dump object attr/chars", 15, 0);
3825 #endif
3826
3827                         /* Prompt */
3828 #ifdef JP
3829                         prt("¥Õ¥¡¥¤¥ë: ", 17, 0);
3830 #else
3831                         prt("File: ", 17, 0);
3832 #endif
3833
3834                         /* Default filename */
3835                         sprintf(tmp, "%s.prf", player_name);
3836
3837                         /* Get a filename */
3838                         if (!askfor(tmp, 70)) continue;
3839
3840                         /* Build the filename */
3841                         path_build(buf, sizeof(buf), ANGBAND_DIR_USER, tmp);
3842
3843                         /* Append to the file */
3844                         if (!open_auto_dump(buf, mark)) continue;
3845
3846                         /* Start dumping */
3847 #ifdef JP
3848                         auto_dump_printf("\n# ¥¢¥¤¥Æ¥à¤Î[¿§/ʸ»ú]¤ÎÀßÄê\n\n");
3849 #else
3850                         auto_dump_printf("\n# Object attr/char definitions\n\n");
3851 #endif
3852
3853                         /* Dump objects */
3854                         for (i = 1; i < max_k_idx; i++)
3855                         {
3856                                 char o_name[80];
3857                                 object_kind *k_ptr = &k_info[i];
3858
3859                                 /* Skip non-entries */
3860                                 if (!k_ptr->name) continue;
3861
3862                                 if (!k_ptr->flavor)
3863                                 {
3864                                         /* Tidy name */
3865                                         strip_name(o_name, i);
3866                                 }
3867                                 else
3868                                 {
3869                                         object_type forge;
3870
3871                                         /* Prepare dummy object */
3872                                         object_prep(&forge, i);
3873
3874                                         /* Get un-shuffled flavor name */
3875                                         object_desc(o_name, &forge, OD_FORCE_FLAVOR);
3876                                 }
3877
3878                                 /* Dump a comment */
3879                                 auto_dump_printf("# %s\n", o_name);
3880
3881                                 /* Dump the object attr/char info */
3882                                 auto_dump_printf("K:%d:0x%02X/0x%02X\n\n", i,
3883                                         (byte)(k_ptr->x_attr), (byte)(k_ptr->x_char));
3884                         }
3885
3886                         /* Close */
3887                         close_auto_dump();
3888
3889                         /* Message */
3890 #ifdef JP
3891                         msg_print("¥¢¥¤¥Æ¥à¤Î[¿§/ʸ»ú]¤ò¥Õ¥¡¥¤¥ë¤Ë½ñ¤­½Ð¤·¤Þ¤·¤¿¡£");
3892 #else
3893                         msg_print("Dumped object attr/chars.");
3894 #endif
3895
3896                         break;
3897                 }
3898
3899                 /* Dump feature attr/chars */
3900                 case '3':
3901                 {
3902                         static cptr mark = "Feature attr/chars";
3903
3904                         /* Prompt */
3905 #ifdef JP
3906                         prt("¥³¥Þ¥ó¥É: ÃÏ·Á¤Î[¿§/ʸ»ú]¤ò¥Õ¥¡¥¤¥ë¤Ë½ñ¤­½Ð¤·¤Þ¤¹", 15, 0);
3907 #else
3908                         prt("Command: Dump feature attr/chars", 15, 0);
3909 #endif
3910
3911                         /* Prompt */
3912 #ifdef JP
3913                         prt("¥Õ¥¡¥¤¥ë: ", 17, 0);
3914 #else
3915                         prt("File: ", 17, 0);
3916 #endif
3917
3918                         /* Default filename */
3919                         sprintf(tmp, "%s.prf", player_name);
3920
3921                         /* Get a filename */
3922                         if (!askfor(tmp, 70)) continue;
3923
3924                         /* Build the filename */
3925                         path_build(buf, sizeof(buf), ANGBAND_DIR_USER, tmp);
3926
3927                         /* Append to the file */
3928                         if (!open_auto_dump(buf, mark)) continue;
3929
3930                         /* Start dumping */
3931 #ifdef JP
3932                         auto_dump_printf("\n# ÃÏ·Á¤Î[¿§/ʸ»ú]¤ÎÀßÄê\n\n");
3933 #else
3934                         auto_dump_printf("\n# Feature attr/char definitions\n\n");
3935 #endif
3936
3937                         /* Dump features */
3938                         for (i = 1; i < max_f_idx; i++)
3939                         {
3940                                 feature_type *f_ptr = &f_info[i];
3941
3942                                 /* Skip non-entries */
3943                                 if (!f_ptr->name) continue;
3944
3945                                 /* Skip mimiccing features */
3946                                 if (f_ptr->mimic != i) continue;
3947
3948                                 /* Dump a comment */
3949                                 auto_dump_printf("# %s\n", (f_name + f_ptr->name));
3950
3951                                 /* Dump the feature attr/char info */
3952                                 auto_dump_printf("F:%d:0x%02X/0x%02X:0x%02X/0x%02X:0x%02X/0x%02X\n\n", i,
3953                                         (byte)(f_ptr->x_attr[F_LIT_STANDARD]), (byte)(f_ptr->x_char[F_LIT_STANDARD]),
3954                                         (byte)(f_ptr->x_attr[F_LIT_LITE]), (byte)(f_ptr->x_char[F_LIT_LITE]),
3955                                         (byte)(f_ptr->x_attr[F_LIT_DARK]), (byte)(f_ptr->x_char[F_LIT_DARK]));
3956                         }
3957
3958                         /* Close */
3959                         close_auto_dump();
3960
3961                         /* Message */
3962 #ifdef JP
3963                         msg_print("ÃÏ·Á¤Î[¿§/ʸ»ú]¤ò¥Õ¥¡¥¤¥ë¤Ë½ñ¤­½Ð¤·¤Þ¤·¤¿¡£");
3964 #else
3965                         msg_print("Dumped feature attr/chars.");
3966 #endif
3967
3968                         break;
3969                 }
3970
3971                 /* Modify monster attr/chars (numeric operation) */
3972                 case '4':
3973                 {
3974 #ifdef JP
3975                         static cptr choice_msg = "¥â¥ó¥¹¥¿¡¼¤Î[¿§/ʸ»ú]¤òÊѹ¹¤·¤Þ¤¹";
3976 #else
3977                         static cptr choice_msg = "Change monster attr/chars";
3978 #endif
3979                         static int r = 0;
3980
3981 #ifdef JP
3982                         prt(format("¥³¥Þ¥ó¥É: %s", choice_msg), 15, 0);
3983 #else
3984                         prt(format("Command: %s", choice_msg), 15, 0);
3985 #endif
3986
3987                         /* Hack -- query until done */
3988                         while (1)
3989                         {
3990                                 monster_race *r_ptr = &r_info[r];
3991                                 char c;
3992                                 int t;
3993
3994                                 byte da = r_ptr->d_attr;
3995                                 byte dc = r_ptr->d_char;
3996                                 byte ca = r_ptr->x_attr;
3997                                 byte cc = r_ptr->x_char;
3998
3999                                 /* Label the object */
4000 #ifdef JP
4001                                 Term_putstr(5, 17, -1, TERM_WHITE,
4002                                             format("¥â¥ó¥¹¥¿¡¼ = %d, Ì¾Á° = %-40.40s",
4003                                                    r, (r_name + r_ptr->name)));
4004 #else
4005                                 Term_putstr(5, 17, -1, TERM_WHITE,
4006                                             format("Monster = %d, Name = %-40.40s",
4007                                                    r, (r_name + r_ptr->name)));
4008 #endif
4009
4010                                 /* Label the Default values */
4011 #ifdef JP
4012                                 Term_putstr(10, 19, -1, TERM_WHITE,
4013                                             format("½é´üÃÍ  ¿§ / Ê¸»ú = %3u / %3u", da, dc));
4014 #else
4015                                 Term_putstr(10, 19, -1, TERM_WHITE,
4016                                             format("Default attr/char = %3u / %3u", da, dc));
4017 #endif
4018
4019                                 Term_putstr(40, 19, -1, TERM_WHITE, empty_symbol);
4020                                 Term_queue_bigchar(43, 19, da, dc, 0, 0);
4021
4022                                 /* Label the Current values */
4023 #ifdef JP
4024                                 Term_putstr(10, 20, -1, TERM_WHITE,
4025                                             format("¸½ºßÃÍ  ¿§ / Ê¸»ú = %3u / %3u", ca, cc));
4026 #else
4027                                 Term_putstr(10, 20, -1, TERM_WHITE,
4028                                             format("Current attr/char = %3u / %3u", ca, cc));
4029 #endif
4030
4031                                 Term_putstr(40, 20, -1, TERM_WHITE, empty_symbol);
4032                                 Term_queue_bigchar(43, 20, ca, cc, 0, 0);
4033
4034                                 /* Prompt */
4035 #ifdef JP
4036                                 Term_putstr(0, 22, -1, TERM_WHITE,
4037                                             "¥³¥Þ¥ó¥É (n/N/^N/a/A/^A/c/C/^C/v/V/^V): ");
4038 #else
4039                                 Term_putstr(0, 22, -1, TERM_WHITE,
4040                                             "Command (n/N/^N/a/A/^A/c/C/^C/v/V/^V): ");
4041 #endif
4042
4043                                 /* Get a command */
4044                                 i = inkey();
4045
4046                                 /* All done */
4047                                 if (i == ESCAPE) break;
4048
4049                                 if (iscntrl(i)) c = 'a' + i - KTRL('A');
4050                                 else if (isupper(i)) c = 'a' + i - 'A';
4051                                 else c = i;
4052
4053                                 switch (c)
4054                                 {
4055                                 case 'n':
4056                                         {
4057                                                 int prev_r = r;
4058                                                 do
4059                                                 {
4060                                                         if (!cmd_visuals_aux(i, &r, max_r_idx))
4061                                                         {
4062                                                                 r = prev_r;
4063                                                                 break;
4064                                                         }
4065                                                 }
4066                                                 while (!r_info[r].name);
4067                                         }
4068                                         break;
4069                                 case 'a':
4070                                         t = (int)r_ptr->x_attr;
4071                                         (void)cmd_visuals_aux(i, &t, 256);
4072                                         r_ptr->x_attr = (byte)t;
4073                                         need_redraw = TRUE;
4074                                         break;
4075                                 case 'c':
4076                                         t = (int)r_ptr->x_char;
4077                                         (void)cmd_visuals_aux(i, &t, 256);
4078                                         r_ptr->x_char = (byte)t;
4079                                         need_redraw = TRUE;
4080                                         break;
4081                                 case 'v':
4082                                         do_cmd_knowledge_monsters(&need_redraw, TRUE, r);
4083
4084                                         /* Clear screen */
4085                                         Term_clear();
4086                                         print_visuals_menu(choice_msg);
4087                                         break;
4088                                 }
4089                         }
4090
4091                         break;
4092                 }
4093
4094                 /* Modify object attr/chars (numeric operation) */
4095                 case '5':
4096                 {
4097 #ifdef JP
4098                         static cptr choice_msg = "¥¢¥¤¥Æ¥à¤Î[¿§/ʸ»ú]¤òÊѹ¹¤·¤Þ¤¹";
4099 #else
4100                         static cptr choice_msg = "Change object attr/chars";
4101 #endif
4102                         static int k = 0;
4103
4104 #ifdef JP
4105                         prt(format("¥³¥Þ¥ó¥É: %s", choice_msg), 15, 0);
4106 #else
4107                         prt(format("Command: %s", choice_msg), 15, 0);
4108 #endif
4109
4110                         /* Hack -- query until done */
4111                         while (1)
4112                         {
4113                                 object_kind *k_ptr = &k_info[k];
4114                                 char c;
4115                                 int t;
4116
4117                                 byte da = k_ptr->d_attr;
4118                                 byte dc = k_ptr->d_char;
4119                                 byte ca = k_ptr->x_attr;
4120                                 byte cc = k_ptr->x_char;
4121
4122                                 /* Label the object */
4123 #ifdef JP
4124                                 Term_putstr(5, 17, -1, TERM_WHITE,
4125                                             format("¥¢¥¤¥Æ¥à = %d, Ì¾Á° = %-40.40s",
4126                                                    k, (k_name + k_ptr->name)));
4127 #else
4128                                 Term_putstr(5, 17, -1, TERM_WHITE,
4129                                             format("Object = %d, Name = %-40.40s",
4130                                                    k, (k_name + k_ptr->name)));
4131 #endif
4132
4133                                 /* Label the Default values */
4134 #ifdef JP
4135                                 Term_putstr(10, 19, -1, TERM_WHITE,
4136                                             format("½é´üÃÍ  ¿§ / Ê¸»ú = %3d / %3d", da, dc));
4137 #else
4138                                 Term_putstr(10, 19, -1, TERM_WHITE,
4139                                             format("Default attr/char = %3d / %3d", da, dc));
4140 #endif
4141
4142                                 Term_putstr(40, 19, -1, TERM_WHITE, empty_symbol);
4143                                 Term_queue_bigchar(43, 19, da, dc, 0, 0);
4144
4145                                 /* Label the Current values */
4146 #ifdef JP
4147                                 Term_putstr(10, 20, -1, TERM_WHITE,
4148                                             format("¸½ºßÃÍ  ¿§ / Ê¸»ú = %3d / %3d", ca, cc));
4149 #else
4150                                 Term_putstr(10, 20, -1, TERM_WHITE,
4151                                             format("Current attr/char = %3d / %3d", ca, cc));
4152 #endif
4153
4154                                 Term_putstr(40, 20, -1, TERM_WHITE, empty_symbol);
4155                                 Term_queue_bigchar(43, 20, ca, cc, 0, 0);
4156
4157                                 /* Prompt */
4158 #ifdef JP
4159                                 Term_putstr(0, 22, -1, TERM_WHITE,
4160                                             "¥³¥Þ¥ó¥É (n/N/^N/a/A/^A/c/C/^C/v/V/^V): ");
4161 #else
4162                                 Term_putstr(0, 22, -1, TERM_WHITE,
4163                                             "Command (n/N/^N/a/A/^A/c/C/^C/v/V/^V): ");
4164 #endif
4165
4166                                 /* Get a command */
4167                                 i = inkey();
4168
4169                                 /* All done */
4170                                 if (i == ESCAPE) break;
4171
4172                                 if (iscntrl(i)) c = 'a' + i - KTRL('A');
4173                                 else if (isupper(i)) c = 'a' + i - 'A';
4174                                 else c = i;
4175
4176                                 switch (c)
4177                                 {
4178                                 case 'n':
4179                                         {
4180                                                 int prev_k = k;
4181                                                 do
4182                                                 {
4183                                                         if (!cmd_visuals_aux(i, &k, max_k_idx))
4184                                                         {
4185                                                                 k = prev_k;
4186                                                                 break;
4187                                                         }
4188                                                 }
4189                                                 while (!k_info[k].name || k_info[k].flavor);
4190                                         }
4191                                         break;
4192                                 case 'a':
4193                                         t = (int)k_ptr->x_attr;
4194                                         (void)cmd_visuals_aux(i, &t, 256);
4195                                         k_ptr->x_attr = (byte)t;
4196                                         need_redraw = TRUE;
4197                                         break;
4198                                 case 'c':
4199                                         t = (int)k_ptr->x_char;
4200                                         (void)cmd_visuals_aux(i, &t, 256);
4201                                         k_ptr->x_char = (byte)t;
4202                                         need_redraw = TRUE;
4203                                         break;
4204                                 case 'v':
4205                                         do_cmd_knowledge_objects(&need_redraw, TRUE, k);
4206
4207                                         /* Clear screen */
4208                                         Term_clear();
4209                                         print_visuals_menu(choice_msg);
4210                                         break;
4211                                 }
4212                         }
4213
4214                         break;
4215                 }
4216
4217                 /* Modify feature attr/chars (numeric operation) */
4218                 case '6':
4219                 {
4220 #ifdef JP
4221                         static cptr choice_msg = "ÃÏ·Á¤Î[¿§/ʸ»ú]¤òÊѹ¹¤·¤Þ¤¹";
4222 #else
4223                         static cptr choice_msg = "Change feature attr/chars";
4224 #endif
4225                         static int f = 0;
4226                         static int lighting_level = F_LIT_STANDARD;
4227
4228 #ifdef JP
4229                         prt(format("¥³¥Þ¥ó¥É: %s", choice_msg), 15, 0);
4230 #else
4231                         prt(format("Command: %s", choice_msg), 15, 0);
4232 #endif
4233
4234                         /* Hack -- query until done */
4235                         while (1)
4236                         {
4237                                 feature_type *f_ptr = &f_info[f];
4238                                 char c;
4239                                 int t;
4240
4241                                 byte da = f_ptr->d_attr[lighting_level];
4242                                 byte dc = f_ptr->d_char[lighting_level];
4243                                 byte ca = f_ptr->x_attr[lighting_level];
4244                                 byte cc = f_ptr->x_char[lighting_level];
4245
4246                                 /* Label the object */
4247                                 prt("", 17, 5);
4248 #ifdef JP
4249                                 Term_putstr(5, 17, -1, TERM_WHITE,
4250                                             format("ÃÏ·Á = %d, Ì¾Á° = %s, ÌÀÅÙ = %s",
4251                                                    f, (f_name + f_ptr->name), lighting_level_str[lighting_level]));
4252 #else
4253                                 Term_putstr(5, 17, -1, TERM_WHITE,
4254                                             format("Terrain = %d, Name = %s, Lighting = %s",
4255                                                    f, (f_name + f_ptr->name), lighting_level_str[lighting_level]));
4256 #endif
4257
4258                                 /* Label the Default values */
4259 #ifdef JP
4260                                 Term_putstr(10, 19, -1, TERM_WHITE,
4261                                             format("½é´üÃÍ  ¿§ / Ê¸»ú = %3d / %3d", da, dc));
4262 #else
4263                                 Term_putstr(10, 19, -1, TERM_WHITE,
4264                                             format("Default attr/char = %3d / %3d", da, dc));
4265 #endif
4266
4267                                 Term_putstr(40, 19, -1, TERM_WHITE, empty_symbol);
4268
4269                                 Term_queue_bigchar(43, 19, da, dc, 0, 0);
4270
4271                                 /* Label the Current values */
4272 #ifdef JP
4273                                 Term_putstr(10, 20, -1, TERM_WHITE,
4274                                             format("¸½ºßÃÍ  ¿§ / Ê¸»ú = %3d / %3d", ca, cc));
4275 #else
4276                                 Term_putstr(10, 20, -1, TERM_WHITE,
4277                                             format("Current attr/char = %3d / %3d", ca, cc));
4278 #endif
4279
4280                                 Term_putstr(40, 20, -1, TERM_WHITE, empty_symbol);
4281                                 Term_queue_bigchar(43, 20, ca, cc, 0, 0);
4282
4283                                 /* Prompt */
4284 #ifdef JP
4285                                 Term_putstr(0, 22, -1, TERM_WHITE,
4286                                             "¥³¥Þ¥ó¥É (n/N/^N/a/A/^A/c/C/^C/l/L/^L/d/D/^D/v/V/^V): ");
4287 #else
4288                                 Term_putstr(0, 22, -1, TERM_WHITE,
4289                                             "Command (n/N/^N/a/A/^A/c/C/^C/l/L/^L/d/D/^D/v/V/^V): ");
4290 #endif
4291
4292                                 /* Get a command */
4293                                 i = inkey();
4294
4295                                 /* All done */
4296                                 if (i == ESCAPE) break;
4297
4298                                 if (iscntrl(i)) c = 'a' + i - KTRL('A');
4299                                 else if (isupper(i)) c = 'a' + i - 'A';
4300                                 else c = i;
4301
4302                                 switch (c)
4303                                 {
4304                                 case 'n':
4305                                         {
4306                                                 int prev_f = f;
4307                                                 do
4308                                                 {
4309                                                         if (!cmd_visuals_aux(i, &f, max_f_idx))
4310                                                         {
4311                                                                 f = prev_f;
4312                                                                 break;
4313                                                         }
4314                                                 }
4315                                                 while (!f_info[f].name || (f_info[f].mimic != f));
4316                                         }
4317                                         break;
4318                                 case 'a':
4319                                         t = (int)f_ptr->x_attr[lighting_level];
4320                                         (void)cmd_visuals_aux(i, &t, 256);
4321                                         f_ptr->x_attr[lighting_level] = (byte)t;
4322                                         need_redraw = TRUE;
4323                                         break;
4324                                 case 'c':
4325                                         t = (int)f_ptr->x_char[lighting_level];
4326                                         (void)cmd_visuals_aux(i, &t, 256);
4327                                         f_ptr->x_char[lighting_level] = (byte)t;
4328                                         need_redraw = TRUE;
4329                                         break;
4330                                 case 'l':
4331                                         (void)cmd_visuals_aux(i, &lighting_level, F_LIT_MAX);
4332                                         break;
4333                                 case 'd':
4334                                         apply_default_feat_lighting(f_ptr->x_attr, f_ptr->x_char);
4335                                         need_redraw = TRUE;
4336                                         break;
4337                                 case 'v':
4338                                         do_cmd_knowledge_features(&need_redraw, TRUE, f, &lighting_level);
4339
4340                                         /* Clear screen */
4341                                         Term_clear();
4342                                         print_visuals_menu(choice_msg);
4343                                         break;
4344                                 }
4345                         }
4346
4347                         break;
4348                 }
4349
4350                 /* Modify monster attr/chars (visual mode) */
4351                 case '7':
4352                         do_cmd_knowledge_monsters(&need_redraw, TRUE, -1);
4353                         break;
4354
4355                 /* Modify object attr/chars (visual mode) */
4356                 case '8':
4357                         do_cmd_knowledge_objects(&need_redraw, TRUE, -1);
4358                         break;
4359
4360                 /* Modify feature attr/chars (visual mode) */
4361                 case '9':
4362                 {
4363                         int lighting_level = F_LIT_STANDARD;
4364                         do_cmd_knowledge_features(&need_redraw, TRUE, -1, &lighting_level);
4365                         break;
4366                 }
4367
4368 #endif /* ALLOW_VISUALS */
4369
4370                 /* Reset visuals */
4371                 case 'R':
4372                 case 'r':
4373                         /* Reset */
4374                         reset_visuals();
4375
4376                         /* Message */
4377 #ifdef JP
4378                         msg_print("²èÌ̾å¤Î[¿§/ʸ»ú]¤ò½é´üÃͤ˥ꥻ¥Ã¥È¤·¤Þ¤·¤¿¡£");
4379 #else
4380                         msg_print("Visual attr/char tables reset.");
4381 #endif
4382
4383                         need_redraw = TRUE;
4384                         break;
4385
4386                 /* Unknown option */
4387                 default:
4388                         bell();
4389                         break;
4390                 }
4391
4392                 /* Flush messages */
4393                 msg_print(NULL);
4394         }
4395
4396         /* Restore the screen */
4397         screen_load();
4398
4399         if (need_redraw) do_cmd_redraw();
4400 }
4401
4402
4403 /*
4404  * Interact with "colors"
4405  */
4406 void do_cmd_colors(void)
4407 {
4408         int i;
4409
4410         char tmp[160];
4411
4412         char buf[1024];
4413
4414
4415         /* File type is "TEXT" */
4416         FILE_TYPE(FILE_TYPE_TEXT);
4417
4418
4419         /* Save the screen */
4420         screen_save();
4421
4422
4423         /* Interact until done */
4424         while (1)
4425         {
4426                 /* Clear screen */
4427                 Term_clear();
4428
4429                 /* Ask for a choice */
4430 #ifdef JP
4431                 prt("[ ¥«¥é¡¼¤ÎÀßÄê ]", 2, 0);
4432 #else
4433                 prt("Interact with Colors", 2, 0);
4434 #endif
4435
4436
4437                 /* Give some choices */
4438 #ifdef JP
4439                 prt("(1) ¥æ¡¼¥¶¡¼ÀßÄê¥Õ¥¡¥¤¥ë¤Î¥í¡¼¥É", 4, 5);
4440 #else
4441                 prt("(1) Load a user pref file", 4, 5);
4442 #endif
4443
4444 #ifdef ALLOW_COLORS
4445 #ifdef JP
4446                 prt("(2) ¥«¥é¡¼¤ÎÀßÄê¤ò¥Õ¥¡¥¤¥ë¤Ë½ñ¤­½Ð¤¹", 5, 5);
4447                 prt("(3) ¥«¥é¡¼¤ÎÀßÄê¤òÊѹ¹¤¹¤ë", 6, 5);
4448 #else
4449                 prt("(2) Dump colors", 5, 5);
4450                 prt("(3) Modify colors", 6, 5);
4451 #endif
4452
4453 #endif
4454
4455                 /* Prompt */
4456 #ifdef JP
4457                 prt("¥³¥Þ¥ó¥É: ", 8, 0);
4458 #else
4459                 prt("Command: ", 8, 0);
4460 #endif
4461
4462
4463                 /* Prompt */
4464                 i = inkey();
4465
4466                 /* Done */
4467                 if (i == ESCAPE) break;
4468
4469                 /* Load a 'pref' file */
4470                 if (i == '1')
4471                 {
4472                         /* Prompt */
4473 #ifdef JP
4474                         prt("¥³¥Þ¥ó¥É: ¥æ¡¼¥¶¡¼ÀßÄê¥Õ¥¡¥¤¥ë¤ò¥í¡¼¥É¤·¤Þ¤¹", 8, 0);
4475 #else
4476                         prt("Command: Load a user pref file", 8, 0);
4477 #endif
4478
4479
4480                         /* Prompt */
4481 #ifdef JP
4482                         prt("¥Õ¥¡¥¤¥ë: ", 10, 0);
4483 #else
4484                         prt("File: ", 10, 0);
4485 #endif
4486
4487
4488                         /* Default file */
4489                         sprintf(tmp, "%s.prf", player_name);
4490
4491                         /* Query */
4492                         if (!askfor(tmp, 70)) continue;
4493
4494                         /* Process the given filename */
4495                         (void)process_pref_file(tmp);
4496
4497                         /* Mega-Hack -- react to changes */
4498                         Term_xtra(TERM_XTRA_REACT, 0);
4499
4500                         /* Mega-Hack -- redraw */
4501                         Term_redraw();
4502                 }
4503
4504 #ifdef ALLOW_COLORS
4505
4506                 /* Dump colors */
4507                 else if (i == '2')
4508                 {
4509                         static cptr mark = "Colors";
4510
4511                         /* Prompt */
4512 #ifdef JP
4513                         prt("¥³¥Þ¥ó¥É: ¥«¥é¡¼¤ÎÀßÄê¤ò¥Õ¥¡¥¤¥ë¤Ë½ñ¤­½Ð¤·¤Þ¤¹", 8, 0);
4514 #else
4515                         prt("Command: Dump colors", 8, 0);
4516 #endif
4517
4518
4519                         /* Prompt */
4520 #ifdef JP
4521                         prt("¥Õ¥¡¥¤¥ë: ", 10, 0);
4522 #else
4523                         prt("File: ", 10, 0);
4524 #endif
4525
4526
4527                         /* Default filename */
4528                         sprintf(tmp, "%s.prf", player_name);
4529
4530                         /* Get a filename */
4531                         if (!askfor(tmp, 70)) continue;
4532
4533                         /* Build the filename */
4534                         path_build(buf, sizeof(buf), ANGBAND_DIR_USER, tmp);
4535
4536                         /* Append to the file */
4537                         if (!open_auto_dump(buf, mark)) continue;
4538
4539                         /* Start dumping */
4540 #ifdef JP
4541                         auto_dump_printf("\n# ¥«¥é¡¼¤ÎÀßÄê\n\n");
4542 #else
4543                         auto_dump_printf("\n# Color redefinitions\n\n");
4544 #endif
4545
4546                         /* Dump colors */
4547                         for (i = 0; i < 256; i++)
4548                         {
4549                                 int kv = angband_color_table[i][0];
4550                                 int rv = angband_color_table[i][1];
4551                                 int gv = angband_color_table[i][2];
4552                                 int bv = angband_color_table[i][3];
4553
4554 #ifdef JP
4555                                 cptr name = "̤ÃÎ";
4556 #else
4557                                 cptr name = "unknown";
4558 #endif
4559
4560
4561                                 /* Skip non-entries */
4562                                 if (!kv && !rv && !gv && !bv) continue;
4563
4564                                 /* Extract the color name */
4565                                 if (i < 16) name = color_names[i];
4566
4567                                 /* Dump a comment */
4568 #ifdef JP
4569                                 auto_dump_printf("# ¥«¥é¡¼ '%s'\n", name);
4570 #else
4571                                 auto_dump_printf("# Color '%s'\n", name);
4572 #endif
4573
4574                                 /* Dump the monster attr/char info */
4575                                 auto_dump_printf("V:%d:0x%02X:0x%02X:0x%02X:0x%02X\n\n",
4576                                         i, kv, rv, gv, bv);
4577                         }
4578
4579                         /* Close */
4580                         close_auto_dump();
4581
4582                         /* Message */
4583 #ifdef JP
4584                         msg_print("¥«¥é¡¼¤ÎÀßÄê¤ò¥Õ¥¡¥¤¥ë¤Ë½ñ¤­½Ð¤·¤Þ¤·¤¿¡£");
4585 #else
4586                         msg_print("Dumped color redefinitions.");
4587 #endif
4588
4589                 }
4590
4591                 /* Edit colors */
4592                 else if (i == '3')
4593                 {
4594                         static byte a = 0;
4595
4596                         /* Prompt */
4597 #ifdef JP
4598                         prt("¥³¥Þ¥ó¥É: ¥«¥é¡¼¤ÎÀßÄê¤òÊѹ¹¤·¤Þ¤¹", 8, 0);
4599 #else
4600                         prt("Command: Modify colors", 8, 0);
4601 #endif
4602
4603
4604                         /* Hack -- query until done */
4605                         while (1)
4606                         {
4607                                 cptr name;
4608                                 byte j;
4609
4610                                 /* Clear */
4611                                 clear_from(10);
4612
4613                                 /* Exhibit the normal colors */
4614                                 for (j = 0; j < 16; j++)
4615                                 {
4616                                         /* Exhibit this color */
4617                                         Term_putstr(j*4, 20, -1, a, "###");
4618
4619                                         /* Exhibit all colors */
4620                                         Term_putstr(j*4, 22, -1, j, format("%3d", j));
4621                                 }
4622
4623                                 /* Describe the color */
4624 #ifdef JP
4625                                 name = ((a < 16) ? color_names[a] : "̤ÄêµÁ");
4626 #else
4627                                 name = ((a < 16) ? color_names[a] : "undefined");
4628 #endif
4629
4630
4631                                 /* Describe the color */
4632 #ifdef JP
4633                                 Term_putstr(5, 10, -1, TERM_WHITE,
4634                                             format("¥«¥é¡¼ = %d, Ì¾Á° = %s", a, name));
4635 #else
4636                                 Term_putstr(5, 10, -1, TERM_WHITE,
4637                                             format("Color = %d, Name = %s", a, name));
4638 #endif
4639
4640
4641                                 /* Label the Current values */
4642                                 Term_putstr(5, 12, -1, TERM_WHITE,
4643                                             format("K = 0x%02x / R,G,B = 0x%02x,0x%02x,0x%02x",
4644                                                    angband_color_table[a][0],
4645                                                    angband_color_table[a][1],
4646                                                    angband_color_table[a][2],
4647                                                    angband_color_table[a][3]));
4648
4649                                 /* Prompt */
4650 #ifdef JP
4651                                 Term_putstr(0, 14, -1, TERM_WHITE,
4652                                             "¥³¥Þ¥ó¥É (n/N/k/K/r/R/g/G/b/B): ");
4653 #else
4654                                 Term_putstr(0, 14, -1, TERM_WHITE,
4655                                             "Command (n/N/k/K/r/R/g/G/b/B): ");
4656 #endif
4657
4658
4659                                 /* Get a command */
4660                                 i = inkey();
4661
4662                                 /* All done */
4663                                 if (i == ESCAPE) break;
4664
4665                                 /* Analyze */
4666                                 if (i == 'n') a = (byte)(a + 1);
4667                                 if (i == 'N') a = (byte)(a - 1);
4668                                 if (i == 'k') angband_color_table[a][0] = (byte)(angband_color_table[a][0] + 1);
4669                                 if (i == 'K') angband_color_table[a][0] = (byte)(angband_color_table[a][0] - 1);
4670                                 if (i == 'r') angband_color_table[a][1] = (byte)(angband_color_table[a][1] + 1);
4671                                 if (i == 'R') angband_color_table[a][1] = (byte)(angband_color_table[a][1] - 1);
4672                                 if (i == 'g') angband_color_table[a][2] = (byte)(angband_color_table[a][2] + 1);
4673                                 if (i == 'G') angband_color_table[a][2] = (byte)(angband_color_table[a][2] - 1);
4674                                 if (i == 'b') angband_color_table[a][3] = (byte)(angband_color_table[a][3] + 1);
4675                                 if (i == 'B') angband_color_table[a][3] = (byte)(angband_color_table[a][3] - 1);
4676
4677                                 /* Hack -- react to changes */
4678                                 Term_xtra(TERM_XTRA_REACT, 0);
4679
4680                                 /* Hack -- redraw */
4681                                 Term_redraw();
4682                         }
4683                 }
4684
4685 #endif
4686
4687                 /* Unknown option */
4688                 else
4689                 {
4690                         bell();
4691                 }
4692
4693                 /* Flush messages */
4694                 msg_print(NULL);
4695         }
4696
4697
4698         /* Restore the screen */
4699         screen_load();
4700 }
4701
4702
4703 /*
4704  * Note something in the message recall
4705  */
4706 void do_cmd_note(void)
4707 {
4708         char buf[80];
4709
4710         /* Default */
4711         strcpy(buf, "");
4712
4713         /* Input */
4714 #ifdef JP
4715         if (!get_string("¥á¥â: ", buf, 60)) return;
4716 #else
4717         if (!get_string("Note: ", buf, 60)) return;
4718 #endif
4719
4720
4721         /* Ignore empty notes */
4722         if (!buf[0] || (buf[0] == ' ')) return;
4723
4724         /* Add the note to the message recall */
4725 #ifdef JP
4726         msg_format("¥á¥â: %s", buf);
4727 #else
4728         msg_format("Note: %s", buf);
4729 #endif
4730
4731 }
4732
4733
4734 /*
4735  * Mention the current version
4736  */
4737 void do_cmd_version(void)
4738 {
4739
4740         /* Silly message */
4741 #ifdef JP
4742         msg_format("ÊѶòÈÚÅÜ(Hengband) %d.%d.%d",
4743                     FAKE_VER_MAJOR-10, FAKE_VER_MINOR, FAKE_VER_PATCH);
4744 #else
4745         msg_format("You are playing Hengband %d.%d.%d.",
4746                     FAKE_VER_MAJOR-10, FAKE_VER_MINOR, FAKE_VER_PATCH);
4747 #endif
4748 }
4749
4750
4751
4752 /*
4753  * Array of feeling strings
4754  */
4755 static cptr do_cmd_feeling_text[11] =
4756 {
4757 #ifdef JP
4758         "¤³¤Î³¬¤ÎÊ·°Ïµ¤¤ò´¶¤¸¤È¤ì¤Ê¤«¤Ã¤¿...",
4759 #else
4760         "Looks like any other level.",
4761 #endif
4762
4763 #ifdef JP
4764         "¤³¤Î³¬¤Ë¤Ï²¿¤«ÆÃÊ̤ʤâ¤Î¤¬¤¢¤ë¤è¤¦¤Êµ¤¤¬¤¹¤ë¡£",
4765 #else
4766         "You feel there is something special about this level.",
4767 #endif
4768
4769 #ifdef JP
4770         "¶²¤í¤·¤¤»à¤Î¸¸¤¬ÌܤËÉ⤫¤Ó¡¢µ¤À䤷¤½¤¦¤Ë¤Ê¤Ã¤¿¡ª",
4771 #else
4772         "You nearly faint as horrible visions of death fill your mind!",
4773 #endif
4774
4775 #ifdef JP
4776         "¤³¤Î³¬¤Ï¤È¤Æ¤â´í¸±¤Ê¤è¤¦¤À¡£",
4777 #else
4778         "This level looks very dangerous.",
4779 #endif
4780
4781 #ifdef JP
4782         "¤È¤Æ¤â°­¤¤Í½´¶¤¬¤¹¤ë...",
4783 #else
4784         "You have a very bad feeling...",
4785 #endif
4786
4787 #ifdef JP
4788         "°­¤¤Í½´¶¤¬¤¹¤ë...",
4789 #else
4790         "You have a bad feeling...",
4791 #endif
4792
4793 #ifdef JP
4794         "²¿¤«¶ÛÄ¥¤¹¤ë¡£",
4795 #else
4796         "You feel nervous.",
4797 #endif
4798
4799 #ifdef JP
4800         "¾¯¤·ÉÔ±¿¤Êµ¤¤¬¤¹¤ë...",
4801 #else
4802         "You feel your luck is turning...",
4803 #endif
4804
4805 #ifdef JP
4806         "¤³¤Î¾ì½ê¤Ï¹¥¤­¤Ë¤Ê¤ì¤Ê¤¤¡£",
4807 #else
4808         "You don't like the look of this place.",
4809 #endif
4810
4811 #ifdef JP
4812         "¤³¤Î³¬¤Ï¤½¤ì¤Ê¤ê¤Ë°ÂÁ´¤Ê¤è¤¦¤À¡£",
4813 #else
4814         "This level looks reasonably safe.",
4815 #endif
4816
4817 #ifdef JP
4818         "¤Ê¤ó¤ÆÂà¶þ¤Ê¤È¤³¤í¤À..."
4819 #else
4820         "What a boring place..."
4821 #endif
4822
4823 };
4824
4825 static cptr do_cmd_feeling_text_combat[11] =
4826 {
4827 #ifdef JP
4828         "¤³¤Î³¬¤ÎÊ·°Ïµ¤¤ò´¶¤¸¤È¤ì¤Ê¤«¤Ã¤¿...",
4829 #else
4830         "Looks like any other level.",
4831 #endif
4832
4833 #ifdef JP
4834         "¤³¤Î³¬¤Ë¤Ï²¿¤«ÆÃÊ̤ʤâ¤Î¤¬¤¢¤ë¤è¤¦¤Êµ¤¤¬¤¹¤ë¡£",
4835 #else
4836         "You feel there is something special about this level.",
4837 #endif
4838
4839 #ifdef JP
4840         "º£Ìë¤â¤Þ¤¿¡¢Ã¯¤«¤¬Ì¿¤òÍî¤È¤¹...",
4841 #else
4842         "You nearly faint as horrible visions of death fill your mind!",
4843 #endif
4844
4845 #ifdef JP
4846         "¤³¤Î³¬¤Ï¤È¤Æ¤â´í¸±¤Ê¤è¤¦¤À¡£",
4847 #else
4848         "This level looks very dangerous.",
4849 #endif
4850
4851 #ifdef JP
4852         "¤È¤Æ¤â°­¤¤Í½´¶¤¬¤¹¤ë...",
4853 #else
4854         "You have a very bad feeling...",
4855 #endif
4856
4857 #ifdef JP
4858         "°­¤¤Í½´¶¤¬¤¹¤ë...",
4859 #else
4860         "You have a bad feeling...",
4861 #endif
4862
4863 #ifdef JP
4864         "²¿¤«¶ÛÄ¥¤¹¤ë¡£",
4865 #else
4866         "You feel nervous.",
4867 #endif
4868
4869 #ifdef JP
4870         "¾¯¤·ÉÔ±¿¤Êµ¤¤¬¤¹¤ë...",
4871 #else
4872         "You feel your luck is turning...",
4873 #endif
4874
4875 #ifdef JP
4876         "¤³¤Î¾ì½ê¤Ï¹¥¤­¤Ë¤Ê¤ì¤Ê¤¤¡£",
4877 #else
4878         "You don't like the look of this place.",
4879 #endif
4880
4881 #ifdef JP
4882         "¤³¤Î³¬¤Ï¤½¤ì¤Ê¤ê¤Ë°ÂÁ´¤Ê¤è¤¦¤À¡£",
4883 #else
4884         "This level looks reasonably safe.",
4885 #endif
4886
4887 #ifdef JP
4888         "¤Ê¤ó¤ÆÂà¶þ¤Ê¤È¤³¤í¤À..."
4889 #else
4890         "What a boring place..."
4891 #endif
4892
4893 };
4894
4895 static cptr do_cmd_feeling_text_lucky[11] =
4896 {
4897 #ifdef JP
4898         "¤³¤Î³¬¤ÎÊ·°Ïµ¤¤ò´¶¤¸¤È¤ì¤Ê¤«¤Ã¤¿...",
4899         "¤³¤Î³¬¤Ë¤Ï²¿¤«ÆÃÊ̤ʤâ¤Î¤¬¤¢¤ë¤è¤¦¤Êµ¤¤¬¤¹¤ë¡£",
4900         "¤³¤Î³¬¤Ï¤³¤Î¾å¤Ê¤¯ÁÇÀ²¤é¤·¤¤´¶¤¸¤¬¤¹¤ë¡£",
4901         "ÁÇÀ²¤é¤·¤¤´¶¤¸¤¬¤¹¤ë...",
4902         "¤È¤Æ¤âÎɤ¤´¶¤¸¤¬¤¹¤ë...",
4903         "Îɤ¤´¶¤¸¤¬¤¹¤ë...",
4904         "¤Á¤ç¤Ã¤È¹¬±¿¤Ê´¶¤¸¤¬¤¹¤ë...",
4905         "¿¾¯¤Ï±¿¤¬¸þ¤¤¤Æ¤­¤¿¤«...",
4906         "¸«¤¿´¶¤¸°­¤¯¤Ï¤Ê¤¤...",
4907         "Á´Á³ÂÌÌܤȤ¤¤¦¤³¤È¤Ï¤Ê¤¤¤¬...",
4908         "¤Ê¤ó¤ÆÂà¶þ¤Ê¤È¤³¤í¤À..."
4909 #else
4910         "Looks like any other level.",
4911         "You feel there is something special about this level.",
4912         "You have a superb feeling about this level.",
4913         "You have an excellent feeling...",
4914         "You have a very good feeling...",
4915         "You have a good feeling...",
4916         "You feel strangely lucky...",
4917         "You feel your luck is turning...",
4918         "You like the look of this place...",
4919         "This level can't be all bad...",
4920         "What a boring place..."
4921 #endif
4922 };
4923
4924
4925 /*
4926  * Note that "feeling" is set to zero unless some time has passed.
4927  * Note that this is done when the level is GENERATED, not entered.
4928  */
4929 void do_cmd_feeling(void)
4930 {
4931         /* No useful feeling in quests */
4932         if (p_ptr->inside_quest && !random_quest_number(dun_level))
4933         {
4934 #ifdef JP
4935                 msg_print("ŵ·¿Åª¤Ê¥¯¥¨¥¹¥È¤Î¥À¥ó¥¸¥ç¥ó¤Î¤è¤¦¤À¡£");
4936 #else
4937                 msg_print("Looks like a typical quest level.");
4938 #endif
4939
4940                 return;
4941         }
4942
4943         /* No useful feeling in town */
4944         else if (p_ptr->town_num && !dun_level)
4945         {
4946 #ifdef JP
4947                 if (!strcmp(town[p_ptr->town_num].name, "¹ÓÌî"))
4948 #else
4949                 if (!strcmp(town[p_ptr->town_num].name, "wilderness"))
4950 #endif
4951                 {
4952 #ifdef JP
4953                         msg_print("²¿¤«¤¢¤ê¤½¤¦¤Ê¹ÓÌî¤Î¤è¤¦¤À¡£");
4954 #else
4955                         msg_print("Looks like a strange wilderness.");
4956 #endif
4957
4958                         return;
4959                 }
4960                 else
4961                 {
4962 #ifdef JP
4963                         msg_print("ŵ·¿Åª¤ÊÄ®¤Î¤è¤¦¤À¡£");
4964 #else
4965                         msg_print("Looks like a typical town.");
4966 #endif
4967
4968                         return;
4969                 }
4970         }
4971
4972         /* No useful feeling in the wilderness */
4973         else if (!dun_level)
4974         {
4975 #ifdef JP
4976                 msg_print("ŵ·¿Åª¤Ê¹ÓÌî¤Î¤è¤¦¤À¡£");
4977 #else
4978                 msg_print("Looks like a typical wilderness.");
4979 #endif
4980
4981                 return;
4982         }
4983
4984         /* Display the feeling */
4985         if (p_ptr->muta3 & MUT3_GOOD_LUCK)
4986                 msg_print(do_cmd_feeling_text_lucky[p_ptr->feeling]);
4987         else if (p_ptr->pseikaku == SEIKAKU_COMBAT ||
4988                  inventory[INVEN_BOW].name1 == ART_CRIMSON)
4989                 msg_print(do_cmd_feeling_text_combat[p_ptr->feeling]);
4990         else
4991                 msg_print(do_cmd_feeling_text[p_ptr->feeling]);
4992 }
4993
4994
4995
4996 /*
4997  * Description of each monster group.
4998  */
4999 static cptr monster_group_text[] = 
5000 {
5001 #ifdef JP
5002         "¥æ¥Ë¡¼¥¯",     /* "Uniques" */
5003         "¾èÇϲÄǽ¤Ê¥â¥ó¥¹¥¿¡¼", /* "Riding" */
5004         "¥¢¥ê",
5005         "¥³¥¦¥â¥ê",
5006         "¥à¥«¥Ç",
5007         "¥É¥é¥´¥ó",
5008         "ÌܶÌ",
5009         "¥Í¥³",
5010         "¥´¡¼¥ì¥à",
5011         "ɸ½à¿Í´Ö·¿À¸Êª",
5012         "¥Ù¥È¥Ù¥È",
5013         "¥¼¥ê¡¼",
5014         "¥³¥Ü¥ë¥É",
5015         "¿åÀ³À¸Êª",
5016         "¥â¥ë¥É",
5017         "¥Ê¡¼¥¬",
5018         "¥ª¡¼¥¯",
5019         "¿Í´Ö",
5020         "»Í­½Ã",
5021         "¥Í¥º¥ß",
5022         "¥¹¥±¥ë¥È¥ó",
5023         "¥Ç¡¼¥â¥ó",
5024         "¥Ü¥ë¥Æ¥Ã¥¯¥¹",
5025         "¥¤¥â¥à¥·/Âç·²",
5026         /* "unused", */
5027         "¥¤¡¼¥¯",
5028         "¥¾¥ó¥Ó/¥ß¥¤¥é",
5029         "Å·»È",
5030         "Ļ",
5031         "¸¤",
5032         /* "¸ÅÂå¥É¥é¥´¥ó/¥ï¥¤¥¢¡¼¥à", */
5033         "¥¨¥ì¥á¥ó¥¿¥ë",
5034         "¥È¥ó¥Ü",
5035         "¥´¡¼¥¹¥È",
5036         "»¨¼ï",
5037         "º«Ãî",
5038         "¥Ø¥Ó",
5039         "¥­¥é¡¼¡¦¥Ó¡¼¥È¥ë",
5040         "¥ê¥Ã¥Á",
5041         "¿¼ó¤Îà¨ÃîÎà",
5042         "Ææ¤ÎÀ¸Êª",
5043         "¥ª¡¼¥¬",
5044         "µðÂç¿Í´Ö·¿À¸Êª",
5045         "¥¯¥¤¥ë¥¹¥ë¥°",
5046         "à¨ÃîÎà/ξÀ¸Îà",
5047         "ÃØéá/¥µ¥½¥ê/¥À¥Ë",
5048         "¥È¥í¥ë",
5049         /* "¾åµé¥Ç¡¼¥â¥ó", */
5050         "¥Ð¥ó¥Ñ¥¤¥¢",
5051         "¥ï¥¤¥È/¥ì¥¤¥¹/Åù",
5052         "¥¾¡¼¥ó/¥¶¥ì¥ó/Åù",
5053         "¥¤¥¨¥Æ¥£",
5054         "¥Ï¥¦¥ó¥É",
5055         "¥ß¥ß¥Ã¥¯",
5056         "ÊÉ/¿¢Êª/µ¤ÂÎ",
5057         "¤ª¤Ð¤±¥­¥Î¥³",
5058         "µåÂÎ",
5059         "¥×¥ì¥¤¥ä¡¼",
5060 #else
5061         "Uniques",
5062         "Ridable monsters",
5063         "Ant",
5064         "Bat",
5065         "Centipede",
5066         "Dragon",
5067         "Floating Eye",
5068         "Feline",
5069         "Golem",
5070         "Hobbit/Elf/Dwarf",
5071         "Icky Thing",
5072         "Jelly",
5073         "Kobold",
5074         "Aquatic monster",
5075         "Mold",
5076         "Naga",
5077         "Orc",
5078         "Person/Human",
5079         "Quadruped",
5080         "Rodent",
5081         "Skeleton",
5082         "Demon",
5083         "Vortex",
5084         "Worm/Worm-Mass",
5085         /* "unused", */
5086         "Yeek",
5087         "Zombie/Mummy",
5088         "Angel",
5089         "Bird",
5090         "Canine",
5091         /* "Ancient Dragon/Wyrm", */
5092         "Elemental",
5093         "Dragon Fly",
5094         "Ghost",
5095         "Hybrid",
5096         "Insect",
5097         "Snake",
5098         "Killer Beetle",
5099         "Lich",
5100         "Multi-Headed Reptile",
5101         "Mystery Living",
5102         "Ogre",
5103         "Giant Humanoid",
5104         "Quylthulg",
5105         "Reptile/Amphibian",
5106         "Spider/Scorpion/Tick",
5107         "Troll",
5108         /* "Major Demon", */
5109         "Vampire",
5110         "Wight/Wraith/etc",
5111         "Xorn/Xaren/etc",
5112         "Yeti",
5113         "Zephyr Hound",
5114         "Mimic",
5115         "Wall/Plant/Gas",
5116         "Mushroom patch",
5117         "Ball",
5118         "Player",
5119 #endif
5120         NULL
5121 };
5122
5123
5124 /*
5125  * Symbols of monsters in each group. Note the "Uniques" group
5126  * is handled differently.
5127  */
5128 static cptr monster_group_char[] =
5129 {
5130         (char *) -1L,
5131         (char *) -2L,
5132         "a",
5133         "b",
5134         "c",
5135         "dD",
5136         "e",
5137         "f",
5138         "g",
5139         "h",
5140         "i",
5141         "j",
5142         "k",
5143         "l",
5144         "m",
5145         "n",
5146         "o",
5147         "pt",
5148         "q",
5149         "r",
5150         "s",
5151         "uU",
5152         "v",
5153         "w",
5154         /* "x", */
5155         "y",
5156         "z",
5157         "A",
5158         "B",
5159         "C",
5160         /* "D", */
5161         "E",
5162         "F",
5163         "G",
5164         "H",
5165         "I",
5166         "J",
5167         "K",
5168         "L",
5169         "M",
5170         "N",
5171         "O",
5172         "P",
5173         "Q",
5174         "R",
5175         "S",
5176         "T",
5177         /* "U", */
5178         "V",
5179         "W",
5180         "X",
5181         "Y",
5182         "Z",
5183         "!$&()+./=>?[\\]`{|~",
5184         "#%",
5185         ",",
5186         "*",
5187         "@",
5188         NULL
5189 };
5190
5191
5192 /*
5193  * hook function to sort monsters by level
5194  */
5195 static bool ang_sort_comp_monster_level(vptr u, vptr v, int a, int b)
5196 {
5197         u16b *who = (u16b*)(u);
5198
5199         int w1 = who[a];
5200         int w2 = who[b];
5201
5202         monster_race *r_ptr1 = &r_info[w1];
5203         monster_race *r_ptr2 = &r_info[w2];
5204
5205         /* Unused */
5206         (void)v;
5207
5208         if (r_ptr2->level > r_ptr1->level) return TRUE;
5209         if (r_ptr1->level > r_ptr2->level) return FALSE;
5210
5211         if ((r_ptr2->flags1 & RF1_UNIQUE) && !(r_ptr1->flags1 & RF1_UNIQUE)) return TRUE;
5212         if ((r_ptr1->flags1 & RF1_UNIQUE) && !(r_ptr2->flags1 & RF1_UNIQUE)) return FALSE;
5213         return w1 <= w2;
5214 }
5215
5216 /*
5217  * Build a list of monster indexes in the given group. Return the number
5218  * of monsters in the group.
5219  *
5220  * mode & 0x01 : check for non-empty group
5221  * mode & 0x02 : visual operation only
5222  */
5223 static int collect_monsters(int grp_cur, s16b mon_idx[], byte mode)
5224 {
5225         int i, mon_cnt = 0;
5226         int dummy_why;
5227
5228         /* Get a list of x_char in this group */
5229         cptr group_char = monster_group_char[grp_cur];
5230
5231         /* XXX Hack -- Check if this is the "Uniques" group */
5232         bool grp_unique = (monster_group_char[grp_cur] == (char *) -1L);
5233
5234         /* XXX Hack -- Check if this is the "Riding" group */
5235         bool grp_riding = (monster_group_char[grp_cur] == (char *) -2L);
5236
5237         /* Check every race */
5238         for (i = 0; i < max_r_idx; i++)
5239         {
5240                 /* Access the race */
5241                 monster_race *r_ptr = &r_info[i];
5242
5243                 /* Skip empty race */
5244                 if (!r_ptr->name) continue ;
5245
5246                 /* Require known monsters */
5247                 if (!(mode & 0x02) && !cheat_know && !r_ptr->r_sights) continue;
5248
5249                 if (grp_unique)
5250                 {
5251                         if (!(r_ptr->flags1 & RF1_UNIQUE)) continue;
5252                 }
5253
5254                 else if (grp_riding)
5255                 {
5256                         if (!(r_ptr->flags7 & RF7_RIDING)) continue;
5257                 }
5258
5259                 else
5260                 {
5261                         /* Check for race in the group */
5262                         if (!my_strchr(group_char, r_ptr->d_char)) continue;
5263                 }
5264
5265                 /* Add the race */
5266                 mon_idx[mon_cnt++] = i;
5267
5268                 /* XXX Hack -- Just checking for non-empty group */
5269                 if (mode & 0x01) break;
5270         }
5271
5272         /* Terminate the list */
5273         mon_idx[mon_cnt] = -1;
5274
5275         /* Select the sort method */
5276         ang_sort_comp = ang_sort_comp_monster_level;
5277         ang_sort_swap = ang_sort_swap_hook;
5278
5279         /* Sort by monster level */
5280         ang_sort(mon_idx, &dummy_why, mon_cnt);
5281
5282         /* Return the number of races */
5283         return mon_cnt;
5284 }
5285
5286
5287 /*
5288  * Description of each monster group.
5289  */
5290 static cptr object_group_text[] = 
5291 {
5292 #ifdef JP
5293         "¥­¥Î¥³",       /* "Mushrooms" */
5294         "Ìô",           /* "Potions" */
5295         "Ìý¤Ä¤Ü",       /* "Flasks" */
5296         "´¬Êª",         /* "Scrolls" */
5297         "»ØÎØ",         /* "Rings" */
5298         "¥¢¥ß¥å¥ì¥Ã¥È", /* "Amulets" */
5299         "ū",           /* "Whistle" */
5300         "¸÷¸»",         /* "Lanterns" */
5301         "ËâË¡ËÀ",       /* "Wands" */
5302         "¾ó",           /* "Staffs" */
5303         "¥í¥Ã¥É",       /* "Rods" */
5304         "¥«¡¼¥É",       /* "Cards" */
5305         "¥­¥ã¥×¥Á¥ã¡¼¡¦¥Ü¡¼¥ë",
5306         "ÍÓÈé»æ",       
5307         "¤¯¤µ¤Ó",
5308         "Ȣ",
5309         "¿Í·Á",
5310         "Áü",
5311         "¥´¥ß",
5312         "¶õ¤Î¥Ó¥ó",
5313         "¹ü",
5314         "»àÂÎ",
5315         "Åá·õÎà",       /* "Swords" */
5316         "Æß´ï",         /* "Blunt Weapons" */
5317         "ĹÊÁÉð´ï",     /* "Polearms" */
5318         "ºÎ·¡Æ»¶ñ",     /* "Diggers" */
5319         "Èô¤ÓÆ»¶ñ",     /* "Bows" */
5320         "ÃÆ",
5321         "Ìð",
5322         "¥Ü¥ë¥È",
5323         "·ÚÁõ³»",       /* "Soft Armor" */
5324         "½ÅÁõ³»",       /* "Hard Armor" */
5325         "¥É¥é¥´¥ó³»",   /* "Dragon Armor" */
5326         "½â",   /* "Shields" */
5327         "¥¯¥í¡¼¥¯",     /* "Cloaks" */
5328         "äƼê", /* "Gloves" */
5329         "¥Ø¥ë¥á¥Ã¥È",   /* "Helms" */
5330         "´§",   /* "Crowns" */
5331         "¥Ö¡¼¥Ä",       /* "Boots" */
5332         "ËâË¡½ñ",
5333         "ºâÊõ",
5334         "²¿¤«",
5335 #else
5336         "Mushrooms",
5337         "Potions",
5338         "Flasks",
5339         "Scrolls",
5340         "Rings",
5341         "Amulets",
5342         "Whistle",
5343         "Lanterns",
5344         "Wands",
5345         "Staves",
5346         "Rods",
5347         "Cards",
5348         "Capture Balls",
5349         "Parchments",
5350         "Spikes",
5351         "Boxs",
5352         "Figurines",
5353         "Statues",
5354         "Junks",
5355         "Bottles",
5356         "Skeletons",
5357         "Corpses",
5358         "Swords",
5359         "Blunt Weapons",
5360         "Polearms",
5361         "Diggers",
5362         "Bows",
5363         "Shots",
5364         "Arrows",
5365         "Bolts",
5366         "Soft Armor",
5367         "Hard Armor",
5368         "Dragon Armor",
5369         "Shields",
5370         "Cloaks",
5371         "Gloves",
5372         "Helms",
5373         "Crowns",
5374         "Boots",
5375         "Spellbooks",
5376         "Treasure",
5377         "Something",
5378 #endif
5379         NULL
5380 };
5381
5382
5383 /*
5384  * TVALs of items in each group
5385  */
5386 static byte object_group_tval[] = 
5387 {
5388         TV_FOOD,
5389         TV_POTION,
5390         TV_FLASK,
5391         TV_SCROLL,
5392         TV_RING,
5393         TV_AMULET,
5394         TV_WHISTLE,
5395         TV_LITE,
5396         TV_WAND,
5397         TV_STAFF,
5398         TV_ROD,
5399         TV_CARD,
5400         TV_CAPTURE,
5401         TV_PARCHMENT,
5402         TV_SPIKE,
5403         TV_CHEST,
5404         TV_FIGURINE,
5405         TV_STATUE,
5406         TV_JUNK,
5407         TV_BOTTLE,
5408         TV_SKELETON,
5409         TV_CORPSE,
5410         TV_SWORD,
5411         TV_HAFTED,
5412         TV_POLEARM,
5413         TV_DIGGING,
5414         TV_BOW,
5415         TV_SHOT,
5416         TV_ARROW,
5417         TV_BOLT,
5418         TV_SOFT_ARMOR,
5419         TV_HARD_ARMOR,
5420         TV_DRAG_ARMOR,
5421         TV_SHIELD,
5422         TV_CLOAK,
5423         TV_GLOVES,
5424         TV_HELM,
5425         TV_CROWN,
5426         TV_BOOTS,
5427         TV_LIFE_BOOK, /* Hack -- all spellbooks */
5428         TV_GOLD,
5429         0,
5430         0,
5431 };
5432
5433
5434 /*
5435  * Build a list of object indexes in the given group. Return the number
5436  * of objects in the group.
5437  *
5438  * mode & 0x01 : check for non-empty group
5439  * mode & 0x02 : visual operation only
5440  */
5441 static int collect_objects(int grp_cur, int object_idx[], byte mode)
5442 {
5443         int i, j, k, object_cnt = 0;
5444
5445         /* Get a list of x_char in this group */
5446         byte group_tval = object_group_tval[grp_cur];
5447
5448         /* Check every object */
5449         for (i = 0; i < max_k_idx; i++)
5450         {
5451                 /* Access the object */
5452                 object_kind *k_ptr = &k_info[i];
5453
5454                 /* Skip empty objects */
5455                 if (!k_ptr->name) continue;
5456
5457                 if (mode & 0x02)
5458                 {
5459                         /* Any objects will be displayed */
5460                 }
5461                 else
5462                 {
5463                         if (!p_ptr->wizard)
5464                         {
5465                                 /* Skip non-flavoured objects */
5466                                 if (!k_ptr->flavor) continue;
5467
5468                                 /* Require objects ever seen */
5469                                 if (!k_ptr->aware) continue;
5470                         }
5471
5472                         /* Skip items with no distribution (special artifacts) */
5473                         for (j = 0, k = 0; j < 4; j++) k += k_ptr->chance[j];
5474                         if (!k) continue;
5475                 }
5476
5477                 /* Check for objects in the group */
5478                 if (TV_LIFE_BOOK == group_tval)
5479                 {
5480                         /* Hack -- All spell books */
5481                         if (TV_LIFE_BOOK <= k_ptr->tval && k_ptr->tval <= TV_HISSATSU_BOOK)
5482                         {
5483                                 /* Add the object */
5484                                 object_idx[object_cnt++] = i;
5485                         }
5486                         else continue;
5487                 }
5488                 else if (k_ptr->tval == group_tval)
5489                 {
5490                         /* Add the object */
5491                         object_idx[object_cnt++] = i;
5492                 }
5493                 else continue;
5494
5495                 /* XXX Hack -- Just checking for non-empty group */
5496                 if (mode & 0x01) break;
5497         }
5498
5499         /* Terminate the list */
5500         object_idx[object_cnt] = -1;
5501
5502         /* Return the number of objects */
5503         return object_cnt;
5504 }
5505
5506
5507 /*
5508  * Description of each feature group.
5509  */
5510 static cptr feature_group_text[] = 
5511 {
5512         "terrains",
5513         NULL
5514 };
5515
5516
5517 /*
5518  * Build a list of feature indexes in the given group. Return the number
5519  * of features in the group.
5520  *
5521  * mode & 0x01 : check for non-empty group
5522  */
5523 static int collect_features(int grp_cur, int *feat_idx, byte mode)
5524 {
5525         int i, feat_cnt = 0;
5526
5527         /* Unused;  There is a single group. */
5528         (void)grp_cur;
5529
5530         /* Check every feature */
5531         for (i = 0; i < max_f_idx; i++)
5532         {
5533                 /* Access the index */
5534                 feature_type *f_ptr = &f_info[i];
5535
5536                 /* Skip empty index */
5537                 if (!f_ptr->name) continue;
5538
5539                 /* Skip mimiccing features */
5540                 if (f_ptr->mimic != i) continue;
5541
5542                 /* Add the index */
5543                 feat_idx[feat_cnt++] = i;
5544
5545                 /* XXX Hack -- Just checking for non-empty group */
5546                 if (mode & 0x01) break;
5547         }
5548
5549         /* Terminate the list */
5550         feat_idx[feat_cnt] = -1;
5551
5552         /* Return the number of races */
5553         return feat_cnt;
5554 }
5555
5556
5557 #if 0
5558 /*
5559  * Build a list of monster indexes in the given group. Return the number
5560  * of monsters in the group.
5561  */
5562 static int collect_artifacts(int grp_cur, int object_idx[])
5563 {
5564         int i, object_cnt = 0;
5565
5566         /* Get a list of x_char in this group */
5567         byte group_tval = object_group_tval[grp_cur];
5568
5569         /* Check every object */
5570         for (i = 0; i < max_a_idx; i++)
5571         {
5572                 /* Access the artifact */
5573                 artifact_type *a_ptr = &a_info[i];
5574
5575                 /* Skip empty artifacts */
5576                 if (!a_ptr->name) continue;
5577
5578                 /* Skip "uncreated" artifacts */
5579                 if (!a_ptr->cur_num) continue;
5580
5581                 /* Check for race in the group */
5582                 if (a_ptr->tval == group_tval)
5583                 {
5584                         /* Add the race */
5585                         object_idx[object_cnt++] = i;
5586                 }
5587         }
5588
5589         /* Terminate the list */
5590         object_idx[object_cnt] = 0;
5591
5592         /* Return the number of races */
5593         return object_cnt;
5594 }
5595 #endif /* 0 */
5596
5597
5598 /*
5599  * Encode the screen colors
5600  */
5601 static char hack[17] = "dwsorgbuDWvyRGBU";
5602
5603
5604 /*
5605  * Hack -- load a screen dump from a file
5606  */
5607 void do_cmd_load_screen(void)
5608 {
5609         int i, y, x;
5610
5611         byte a = 0;
5612         char c = ' ';
5613
5614         bool okay = TRUE;
5615
5616         FILE *fff;
5617
5618         char buf[1024];
5619
5620         int wid, hgt;
5621
5622         Term_get_size(&wid, &hgt);
5623
5624         /* Build the filename */
5625         path_build(buf, sizeof(buf), ANGBAND_DIR_USER, "dump.txt");
5626
5627         /* Append to the file */
5628         fff = my_fopen(buf, "r");
5629
5630         /* Oops */
5631         if (!fff) {
5632 #ifdef JP
5633                 msg_format("%s ¤ò³«¤¯¤³¤È¤¬¤Ç¤­¤Þ¤»¤ó¤Ç¤·¤¿¡£", buf);
5634 #else
5635                 msg_format("Failed to open %s.", buf);
5636 #endif
5637                 msg_print(NULL);
5638                 return;
5639         }
5640
5641
5642         /* Save the screen */
5643         screen_save();
5644
5645         /* Clear the screen */
5646         Term_clear();
5647
5648
5649         /* Load the screen */
5650         for (y = 0; okay; y++)
5651         {
5652                 /* Get a line of data including control code */
5653                 if (!fgets(buf, 1024, fff)) okay = FALSE;
5654
5655                 /* Get the blank line */
5656                 if (buf[0] == '\n' || buf[0] == '\0') break;
5657
5658                 /* Ignore too large screen image */
5659                 if (y >= hgt) continue;
5660
5661                 /* Show each row */
5662                 for (x = 0; x < wid - 1; x++)
5663                 {
5664                         /* End of line */
5665                         if (buf[x] == '\n' || buf[x] == '\0') break;
5666
5667                         /* Put the attr/char */
5668                         Term_draw(x, y, TERM_WHITE, buf[x]);
5669                 }
5670         }
5671
5672         /* Dump the screen */
5673         for (y = 0; okay; y++)
5674         {
5675                 /* Get a line of data including control code */
5676                 if (!fgets(buf, 1024, fff)) okay = FALSE;
5677
5678                 /* Get the blank line */
5679                 if (buf[0] == '\n' || buf[0] == '\0') break;
5680
5681                 /* Ignore too large screen image */
5682                 if (y >= hgt) continue;
5683
5684                 /* Dump each row */
5685                 for (x = 0; x < wid - 1; x++)
5686                 {
5687                         /* End of line */
5688                         if (buf[x] == '\n' || buf[x] == '\0') break;
5689
5690                         /* Get the attr/char */
5691                         (void)(Term_what(x, y, &a, &c));
5692
5693                         /* Look up the attr */
5694                         for (i = 0; i < 16; i++)
5695                         {
5696                                 /* Use attr matches */
5697                                 if (hack[i] == buf[x]) a = i;
5698                         }
5699
5700                         /* Put the attr/char */
5701                         Term_draw(x, y, a, c);
5702                 }
5703         }
5704
5705
5706         /* Close it */
5707         my_fclose(fff);
5708
5709
5710         /* Message */
5711 #ifdef JP
5712         prt("¥Õ¥¡¥¤¥ë¤Ë½ñ¤­½Ð¤µ¤ì¤¿²èÌÌ(µ­Ç°»£±Æ)¤ò¥í¡¼¥É¤·¤Þ¤·¤¿¡£", 0, 0);
5713 #else
5714         msg_print("Screen dump loaded.");
5715 #endif
5716
5717         flush();
5718         inkey();
5719
5720
5721         /* Restore the screen */
5722         screen_load();
5723 }
5724
5725
5726
5727
5728 cptr inven_res_label = 
5729 #ifdef JP
5730  "                               »ÀÅŲÐÎäÆǸ÷°ÇÇ˹ì¹ö°øÆÙÎô ÌÕÉÝÍðáãÆ©Ì¿´¶¾ÃÉüÉâ";
5731 #else
5732  "                               AcElFiCoPoLiDkShSoNtNxCaDi BlFeCfFaSeHlEpSdRgLv";
5733 #endif
5734
5735
5736 #ifdef JP
5737 #define IM_FLAG_STR  "¡ö"
5738 #define HAS_FLAG_STR "¡Ü"
5739 #define NO_FLAG_STR  "¡¦"
5740 #else
5741 #define IM_FLAG_STR  "* "
5742 #define HAS_FLAG_STR "+ "
5743 #define NO_FLAG_STR  ". "
5744 #endif
5745
5746 #define print_im_or_res_flag(IM, RES) \
5747 { \
5748         fputs(have_flag(flgs, (IM)) ? IM_FLAG_STR : \
5749               (have_flag(flgs, (RES)) ? HAS_FLAG_STR : NO_FLAG_STR), fff); \
5750 }
5751
5752 #define print_flag(TR) \
5753 { \
5754         fputs(have_flag(flgs, (TR)) ? HAS_FLAG_STR : NO_FLAG_STR, fff); \
5755 }
5756
5757
5758 /* XTRA HACK RESLIST */
5759 static void do_cmd_knowledge_inven_aux(FILE *fff, object_type *o_ptr, int *j, byte tval, char *where)
5760 {
5761         char o_name[MAX_NLEN];
5762         u32b flgs[TR_FLAG_SIZE];
5763
5764         if (!o_ptr->k_idx) return;
5765         if (o_ptr->tval != tval) return;
5766
5767         /* Identified items only */
5768         if (!object_is_known(o_ptr)) return;
5769
5770         /*
5771          * HACK:Ring of Lordly protection and Dragon equipment
5772          * have random resistances.
5773          */
5774         if ((object_is_wearable(o_ptr) && object_is_ego(o_ptr))
5775             || ((tval == TV_AMULET) && (o_ptr->sval == SV_AMULET_RESISTANCE))
5776             || ((tval == TV_RING) && (o_ptr->sval == SV_RING_LORDLY))
5777             || ((tval == TV_SHIELD) && (o_ptr->sval == SV_DRAGON_SHIELD))
5778             || ((tval == TV_HELM) && (o_ptr->sval == SV_DRAGON_HELM))
5779             || ((tval == TV_GLOVES) && (o_ptr->sval == SV_SET_OF_DRAGON_GLOVES))
5780             || ((tval == TV_BOOTS) && (o_ptr->sval == SV_PAIR_OF_DRAGON_GREAVE))
5781             || object_is_artifact(o_ptr))
5782         {
5783                 int i = 0;
5784                 object_desc(o_name, o_ptr, OD_NAME_ONLY);
5785
5786                 while (o_name[i] && (i < 26))
5787                 {
5788 #ifdef JP
5789                         if (iskanji(o_name[i])) i++;
5790 #endif
5791                         i++;
5792                 }
5793
5794                 if (i < 28)
5795                 {
5796                         while (i < 28)
5797                         {
5798                                 o_name[i] = ' '; i++;
5799                         }
5800                 }
5801                 o_name[i] = '\0';
5802
5803                 fprintf(fff, "%s %s", where, o_name);
5804
5805                 if (!(o_ptr->ident & (IDENT_MENTAL)))
5806                 {
5807 #ifdef JP
5808                         fputs("-------ÉÔÌÀ--------------- -------ÉÔÌÀ---------\n", fff);
5809 #else
5810                         fputs("-------unknown------------ -------unknown------\n", fff);
5811 #endif
5812                 }
5813                 else
5814                 {
5815                         object_flags_known(o_ptr, flgs);
5816
5817                         print_im_or_res_flag(TR_IM_ACID, TR_RES_ACID);
5818                         print_im_or_res_flag(TR_IM_ELEC, TR_RES_ELEC);
5819                         print_im_or_res_flag(TR_IM_FIRE, TR_RES_FIRE);
5820                         print_im_or_res_flag(TR_IM_COLD, TR_RES_COLD);
5821                         print_flag(TR_RES_POIS);
5822                         print_flag(TR_RES_LITE);
5823                         print_flag(TR_RES_DARK);
5824                         print_flag(TR_RES_SHARDS);
5825                         print_flag(TR_RES_SOUND);
5826                         print_flag(TR_RES_NETHER);
5827                         print_flag(TR_RES_NEXUS);
5828                         print_flag(TR_RES_CHAOS);
5829                         print_flag(TR_RES_DISEN);
5830
5831                         fputs(" ", fff);
5832
5833                         print_flag(TR_RES_BLIND);
5834                         print_flag(TR_RES_FEAR);
5835                         print_flag(TR_RES_CONF);
5836                         print_flag(TR_FREE_ACT);
5837                         print_flag(TR_SEE_INVIS);
5838                         print_flag(TR_HOLD_LIFE);
5839                         print_flag(TR_TELEPATHY);
5840                         print_flag(TR_SLOW_DIGEST);
5841                         print_flag(TR_REGEN);
5842                         print_flag(TR_LEVITATION);
5843
5844                         fputc('\n', fff);
5845                 }
5846                 (*j)++;
5847                 if (*j == 9)
5848                 {
5849                         *j = 0;
5850                         fprintf(fff, "%s\n", inven_res_label);
5851                 }
5852         }
5853 }
5854
5855 /*
5856  * Display *ID* ed weapons/armors's resistances
5857  */
5858 static void do_cmd_knowledge_inven(void)
5859 {
5860         FILE *fff;
5861
5862         char file_name[1024];
5863
5864         store_type  *st_ptr;
5865
5866         byte tval;
5867         int i = 0;
5868         int j = 0;
5869
5870         char  where[32];
5871
5872         /* Open a new file */
5873         fff = my_fopen_temp(file_name, 1024);
5874         if (!fff)
5875         {
5876 #ifdef JP
5877             msg_format("°ì»þ¥Õ¥¡¥¤¥ë %s ¤òºîÀ®¤Ç¤­¤Þ¤»¤ó¤Ç¤·¤¿¡£", file_name);
5878 #else
5879             msg_format("Failed to create temporary file %s.", file_name);
5880 #endif
5881             msg_print(NULL);
5882             return;
5883         }
5884         fprintf(fff, "%s\n", inven_res_label);
5885
5886         for (tval = TV_WEARABLE_BEGIN; tval <= TV_WEARABLE_END; tval++)
5887         {
5888                 if (j != 0)
5889                 {
5890                         for (; j < 9; j++) fputc('\n', fff);
5891                         j = 0;
5892                         fprintf(fff, "%s\n", inven_res_label);
5893                 }
5894
5895 #ifdef JP
5896                 strcpy(where, "Áõ");
5897 #else
5898                 strcpy(where, "E ");
5899 #endif
5900                 for (i = INVEN_RARM; i < INVEN_TOTAL; i++)
5901                 {
5902                         do_cmd_knowledge_inven_aux(fff, &inventory[i], &j, tval, where);
5903                 }
5904
5905 #ifdef JP
5906                 strcpy(where, "»ý");
5907 #else
5908                 strcpy(where, "I ");
5909 #endif
5910                 for (i = 0; i < INVEN_PACK; i++)
5911                 {
5912                         do_cmd_knowledge_inven_aux(fff, &inventory[i], &j, tval, where);
5913                 }
5914
5915                 st_ptr = &town[1].store[STORE_HOME];
5916 #ifdef JP
5917                 strcpy(where, "²È");
5918 #else
5919                 strcpy(where, "H ");
5920 #endif
5921
5922                 for (i = 0; i < st_ptr->stock_num; i++)
5923                 {
5924                         do_cmd_knowledge_inven_aux(fff, &st_ptr->stock[i], &j, tval, where);
5925                 }
5926         }
5927
5928         /* Close the file */
5929         my_fclose(fff);
5930
5931         /* Display the file contents */
5932 #ifdef JP
5933         show_file(TRUE, file_name, "*´ÕÄê*ºÑ¤ßÉð´ï/Ëɶñ¤ÎÂÑÀ­¥ê¥¹¥È", 0, 0);
5934 #else
5935         show_file(TRUE, file_name, "Resistances of *identified* equipment", 0, 0);
5936 #endif
5937
5938         /* Remove the file */
5939         fd_kill(file_name);
5940 }
5941
5942
5943 void do_cmd_save_screen_html_aux(char *filename, int message)
5944 {
5945         int y, x, i;
5946
5947         byte a = 0, old_a = 0;
5948         char c = ' ';
5949
5950         FILE *fff, *tmpfff;
5951         char buf[2048];
5952
5953         int yomikomu = 0;
5954         cptr tags[4] = {
5955                 "HEADER_START:",
5956                 "HEADER_END:",
5957                 "FOOTER_START:",
5958                 "FOOTER_END:",
5959         };
5960
5961         cptr html_head[] = {
5962                 "<html>\n<body text=\"#ffffff\" bgcolor=\"#000000\">\n",
5963                 "<pre>",
5964                 0,
5965         };
5966         cptr html_foot[] = {
5967                 "</pre>\n",
5968                 "</body>\n</html>\n",
5969                 0,
5970         };
5971
5972         int wid, hgt;
5973
5974         Term_get_size(&wid, &hgt);
5975
5976         /* File type is "TEXT" */
5977         FILE_TYPE(FILE_TYPE_TEXT);
5978
5979         /* Append to the file */
5980         fff = my_fopen(filename, "w");
5981
5982         /* Oops */
5983         if (!fff) {
5984                 if (message) {
5985 #ifdef JP
5986                     msg_format("¥Õ¥¡¥¤¥ë %s ¤ò³«¤±¤Þ¤»¤ó¤Ç¤·¤¿¡£", filename);
5987 #else
5988                     msg_format("Failed to open file %s.", filename);
5989 #endif
5990                     msg_print(NULL);
5991                 }
5992                 
5993                 return;
5994         }
5995
5996         /* Save the screen */
5997         if (message)
5998                 screen_save();
5999
6000         /* Build the filename */
6001         path_build(buf, sizeof(buf), ANGBAND_DIR_USER, "htmldump.prf");
6002         tmpfff = my_fopen(buf, "r");
6003         if (!tmpfff) {
6004                 for (i = 0; html_head[i]; i++)
6005                         fprintf(fff, html_head[i]);
6006         }
6007         else {
6008                 yomikomu = 0;
6009                 while (!my_fgets(tmpfff, buf, sizeof(buf))) {
6010                         if (!yomikomu) {
6011                                 if (strncmp(buf, tags[0], strlen(tags[0])) == 0)
6012                                         yomikomu = 1;
6013                         }
6014                         else {
6015                                 if (strncmp(buf, tags[1], strlen(tags[1])) == 0)
6016                                         break;
6017                                 fprintf(fff, "%s\n", buf);
6018                         }
6019                 }
6020         }
6021
6022         /* Dump the screen */
6023         for (y = 0; y < hgt; y++)
6024         {
6025                 /* Start the row */
6026                 if (y != 0)
6027                         fprintf(fff, "\n");
6028
6029                 /* Dump each row */
6030                 for (x = 0; x < wid - 1; x++)
6031                 {
6032                         int rv, gv, bv;
6033                         cptr cc = NULL;
6034                         /* Get the attr/char */
6035                         (void)(Term_what(x, y, &a, &c));
6036
6037                         switch (c)
6038                         {
6039                         case '&': cc = "&amp;"; break;
6040                         case '<': cc = "&lt;"; break;
6041                         case '>': cc = "&gt;"; break;
6042 #ifdef WINDOWS
6043                         case 0x1f: c = '.'; break;
6044                         case 0x7f: c = (a == 0x09) ? '%' : '#'; break;
6045 #endif
6046                         }
6047
6048                         a = a & 0x0F;
6049                         if ((y == 0 && x == 0) || a != old_a) {
6050                                 rv = angband_color_table[a][1];
6051                                 gv = angband_color_table[a][2];
6052                                 bv = angband_color_table[a][3];
6053                                 fprintf(fff, "%s<font color=\"#%02x%02x%02x\">", 
6054                                         ((y == 0 && x == 0) ? "" : "</font>"), rv, gv, bv);
6055                                 old_a = a;
6056                         }
6057                         if (cc)
6058                                 fprintf(fff, "%s", cc);
6059                         else
6060                                 fprintf(fff, "%c", c);
6061                 }
6062         }
6063         fprintf(fff, "</font>");
6064
6065         if (!tmpfff) {
6066                 for (i = 0; html_foot[i]; i++)
6067                         fprintf(fff, html_foot[i]);
6068         }
6069         else {
6070                 rewind(tmpfff);
6071                 yomikomu = 0;
6072                 while (!my_fgets(tmpfff, buf, sizeof(buf))) {
6073                         if (!yomikomu) {
6074                                 if (strncmp(buf, tags[2], strlen(tags[2])) == 0)
6075                                         yomikomu = 1;
6076                         }
6077                         else {
6078                                 if (strncmp(buf, tags[3], strlen(tags[3])) == 0)
6079                                         break;
6080                                 fprintf(fff, "%s\n", buf);
6081                         }
6082                 }
6083                 my_fclose(tmpfff);
6084         }
6085
6086         /* Skip a line */
6087         fprintf(fff, "\n");
6088
6089         /* Close it */
6090         my_fclose(fff);
6091
6092         /* Message */
6093         if (message) {
6094 #ifdef JP
6095         msg_print("²èÌÌ(µ­Ç°»£±Æ)¤ò¥Õ¥¡¥¤¥ë¤Ë½ñ¤­½Ð¤·¤Þ¤·¤¿¡£");
6096 #else
6097                 msg_print("Screen dump saved.");
6098 #endif
6099                 msg_print(NULL);
6100         }
6101
6102         /* Restore the screen */
6103         if (message)
6104                 screen_load();
6105 }
6106
6107 /*
6108  * Hack -- save a screen dump to a file
6109  */
6110 static void do_cmd_save_screen_html(void)
6111 {
6112         char buf[1024], tmp[256] = "screen.html";
6113
6114 #ifdef JP
6115         if (!get_string("¥Õ¥¡¥¤¥ë̾: ", tmp, 80))
6116 #else
6117         if (!get_string("File name: ", tmp, 80))
6118 #endif
6119                 return;
6120
6121         /* Build the filename */
6122         path_build(buf, sizeof(buf), ANGBAND_DIR_USER, tmp);
6123
6124         msg_print(NULL);
6125
6126         do_cmd_save_screen_html_aux(buf, 1);
6127 }
6128
6129
6130 /*
6131  * Redefinable "save_screen" action
6132  */
6133 void (*screendump_aux)(void) = NULL;
6134
6135
6136 /*
6137  * Hack -- save a screen dump to a file
6138  */
6139 void do_cmd_save_screen(void)
6140 {
6141         bool old_use_graphics = use_graphics;
6142         bool html_dump = FALSE;
6143
6144         int wid, hgt;
6145
6146 #ifdef JP
6147         prt("µ­Ç°»£±Æ¤·¤Þ¤¹¤«¡© [(y)es/(h)tml/(n)o] ", 0, 0);
6148 #else
6149         prt("Save screen dump? [(y)es/(h)tml/(n)o] ", 0, 0);
6150 #endif
6151         while(TRUE)
6152         {
6153                 char c = inkey();
6154                 if (c == 'Y' || c == 'y')
6155                         break;
6156                 else if (c == 'H' || c == 'h')
6157                 {
6158                         html_dump = TRUE;
6159                         break;
6160                 }
6161                 else
6162                 {
6163                         prt("", 0, 0);
6164                         return;
6165                 }
6166         }
6167
6168         Term_get_size(&wid, &hgt);
6169
6170         if (old_use_graphics)
6171         {
6172                 use_graphics = FALSE;
6173                 reset_visuals();
6174
6175                 /* Redraw everything */
6176                 p_ptr->redraw |= (PR_WIPE | PR_BASIC | PR_EXTRA | PR_MAP | PR_EQUIPPY);
6177
6178                 /* Hack -- update */
6179                 handle_stuff();
6180         }
6181
6182         if (html_dump)
6183         {
6184                 do_cmd_save_screen_html();
6185                 do_cmd_redraw();
6186         }
6187
6188         /* Do we use a special screendump function ? */
6189         else if (screendump_aux)
6190         {
6191                 /* Dump the screen to a graphics file */
6192                 (*screendump_aux)();
6193         }
6194         else /* Dump the screen as text */
6195         {
6196                 int y, x;
6197
6198                 byte a = 0;
6199                 char c = ' ';
6200
6201                 FILE *fff;
6202
6203                 char buf[1024];
6204
6205                 /* Build the filename */
6206                 path_build(buf, sizeof(buf), ANGBAND_DIR_USER, "dump.txt");
6207
6208                 /* File type is "TEXT" */
6209                 FILE_TYPE(FILE_TYPE_TEXT);
6210
6211                 /* Append to the file */
6212                 fff = my_fopen(buf, "w");
6213
6214                 /* Oops */
6215                 if (!fff)
6216                 {
6217 #ifdef JP
6218                         msg_format("¥Õ¥¡¥¤¥ë %s ¤ò³«¤±¤Þ¤»¤ó¤Ç¤·¤¿¡£", buf);
6219 #else
6220                         msg_format("Failed to open file %s.", buf);
6221 #endif
6222                         msg_print(NULL);
6223                         return;
6224                 }
6225
6226
6227                 /* Save the screen */
6228                 screen_save();
6229
6230
6231                 /* Dump the screen */
6232                 for (y = 0; y < hgt; y++)
6233                 {
6234                         /* Dump each row */
6235                         for (x = 0; x < wid - 1; x++)
6236                         {
6237                                 /* Get the attr/char */
6238                                 (void)(Term_what(x, y, &a, &c));
6239
6240                                 /* Dump it */
6241                                 buf[x] = c;
6242                         }
6243
6244                         /* Terminate */
6245                         buf[x] = '\0';
6246
6247                         /* End the row */
6248                         fprintf(fff, "%s\n", buf);
6249                 }
6250
6251                 /* Skip a line */
6252                 fprintf(fff, "\n");
6253
6254
6255                 /* Dump the screen */
6256                 for (y = 0; y < hgt; y++)
6257                 {
6258                         /* Dump each row */
6259                         for (x = 0; x < wid - 1; x++)
6260                         {
6261                                 /* Get the attr/char */
6262                                 (void)(Term_what(x, y, &a, &c));
6263
6264                                 /* Dump it */
6265                                 buf[x] = hack[a&0x0F];
6266                         }
6267
6268                         /* Terminate */
6269                         buf[x] = '\0';
6270
6271                         /* End the row */
6272                         fprintf(fff, "%s\n", buf);
6273                 }
6274
6275                 /* Skip a line */
6276                 fprintf(fff, "\n");
6277
6278
6279                 /* Close it */
6280                 my_fclose(fff);
6281
6282                 /* Message */
6283 #ifdef JP
6284         msg_print("²èÌÌ(µ­Ç°»£±Æ)¤ò¥Õ¥¡¥¤¥ë¤Ë½ñ¤­½Ð¤·¤Þ¤·¤¿¡£");
6285 #else
6286                 msg_print("Screen dump saved.");
6287 #endif
6288
6289                 msg_print(NULL);
6290
6291
6292                 /* Restore the screen */
6293                 screen_load();
6294         }
6295
6296         if (old_use_graphics)
6297         {
6298                 use_graphics = TRUE;
6299                 reset_visuals();
6300
6301                 /* Redraw everything */
6302                 p_ptr->redraw |= (PR_WIPE | PR_BASIC | PR_EXTRA | PR_MAP | PR_EQUIPPY);
6303
6304                 /* Hack -- update */
6305                 handle_stuff();
6306         }
6307 }
6308
6309
6310 /*
6311  * Sorting hook -- Comp function -- see below
6312  *
6313  * We use "u" to point to array of monster indexes,
6314  * and "v" to select the type of sorting to perform on "u".
6315  */
6316 static bool ang_sort_art_comp(vptr u, vptr v, int a, int b)
6317 {
6318         u16b *who = (u16b*)(u);
6319
6320         u16b *why = (u16b*)(v);
6321
6322         int w1 = who[a];
6323         int w2 = who[b];
6324
6325         int z1, z2;
6326
6327         /* Sort by total kills */
6328         if (*why >= 3)
6329         {
6330                 /* Extract total kills */
6331                 z1 = a_info[w1].tval;
6332                 z2 = a_info[w2].tval;
6333
6334                 /* Compare total kills */
6335                 if (z1 < z2) return (TRUE);
6336                 if (z1 > z2) return (FALSE);
6337         }
6338
6339
6340         /* Sort by monster level */
6341         if (*why >= 2)
6342         {
6343                 /* Extract levels */
6344                 z1 = a_info[w1].sval;
6345                 z2 = a_info[w2].sval;
6346
6347                 /* Compare levels */
6348                 if (z1 < z2) return (TRUE);
6349                 if (z1 > z2) return (FALSE);
6350         }
6351
6352
6353         /* Sort by monster experience */
6354         if (*why >= 1)
6355         {
6356                 /* Extract experience */
6357                 z1 = a_info[w1].level;
6358                 z2 = a_info[w2].level;
6359
6360                 /* Compare experience */
6361                 if (z1 < z2) return (TRUE);
6362                 if (z1 > z2) return (FALSE);
6363         }
6364
6365
6366         /* Compare indexes */
6367         return (w1 <= w2);
6368 }
6369
6370
6371 /*
6372  * Sorting hook -- Swap function -- see below
6373  *
6374  * We use "u" to point to array of monster indexes,
6375  * and "v" to select the type of sorting to perform.
6376  */
6377 static void ang_sort_art_swap(vptr u, vptr v, int a, int b)
6378 {
6379         u16b *who = (u16b*)(u);
6380
6381         u16b holder;
6382
6383         /* Unused */
6384         (void)v;
6385
6386         /* Swap */
6387         holder = who[a];
6388         who[a] = who[b];
6389         who[b] = holder;
6390 }
6391
6392
6393 /*
6394  * Check the status of "artifacts"
6395  */
6396 static void do_cmd_knowledge_artifacts(void)
6397 {
6398         int i, k, z, x, y, n = 0;
6399         u16b why = 3;
6400         s16b *who;
6401
6402         FILE *fff;
6403
6404         char file_name[1024];
6405
6406         char base_name[MAX_NLEN];
6407
6408         bool *okay;
6409
6410         /* Open a new file */
6411         fff = my_fopen_temp(file_name, 1024);
6412
6413         if (!fff) {
6414 #ifdef JP
6415             msg_format("°ì»þ¥Õ¥¡¥¤¥ë %s ¤òºîÀ®¤Ç¤­¤Þ¤»¤ó¤Ç¤·¤¿¡£", file_name);
6416 #else
6417             msg_format("Failed to create temporary file %s.", file_name);
6418 #endif
6419             msg_print(NULL);
6420             return;
6421         }
6422
6423         /* Allocate the "who" array */
6424         C_MAKE(who, max_a_idx, s16b);
6425
6426         /* Allocate the "okay" array */
6427         C_MAKE(okay, max_a_idx, bool);
6428
6429         /* Scan the artifacts */
6430         for (k = 0; k < max_a_idx; k++)
6431         {
6432                 artifact_type *a_ptr = &a_info[k];
6433
6434                 /* Default */
6435                 okay[k] = FALSE;
6436
6437                 /* Skip "empty" artifacts */
6438                 if (!a_ptr->name) continue;
6439
6440                 /* Skip "uncreated" artifacts */
6441                 if (!a_ptr->cur_num) continue;
6442
6443                 /* Assume okay */
6444                 okay[k] = TRUE;
6445         }
6446
6447         /* Check the dungeon */
6448         for (y = 0; y < cur_hgt; y++)
6449         {
6450                 for (x = 0; x < cur_wid; x++)
6451                 {
6452                         cave_type *c_ptr = &cave[y][x];
6453
6454                         s16b this_o_idx, next_o_idx = 0;
6455
6456                         /* Scan all objects in the grid */
6457                         for (this_o_idx = c_ptr->o_idx; this_o_idx; this_o_idx = next_o_idx)
6458                         {
6459                                 object_type *o_ptr;
6460
6461                                 /* Acquire object */
6462                                 o_ptr = &o_list[this_o_idx];
6463
6464                                 /* Acquire next object */
6465                                 next_o_idx = o_ptr->next_o_idx;
6466
6467                                 /* Ignore non-artifacts */
6468                                 if (!object_is_fixed_artifact(o_ptr)) continue;
6469
6470                                 /* Ignore known items */
6471                                 if (object_is_known(o_ptr)) continue;
6472
6473                                 /* Note the artifact */
6474                                 okay[o_ptr->name1] = FALSE;
6475                         }
6476                 }
6477         }
6478
6479         /* Check the inventory and equipment */
6480         for (i = 0; i < INVEN_TOTAL; i++)
6481         {
6482                 object_type *o_ptr = &inventory[i];
6483
6484                 /* Ignore non-objects */
6485                 if (!o_ptr->k_idx) continue;
6486
6487                 /* Ignore non-artifacts */
6488                 if (!object_is_fixed_artifact(o_ptr)) continue;
6489
6490                 /* Ignore known items */
6491                 if (object_is_known(o_ptr)) continue;
6492
6493                 /* Note the artifact */
6494                 okay[o_ptr->name1] = FALSE;
6495         }
6496
6497         for (k = 0; k < max_a_idx; k++)
6498         {
6499                 if (okay[k]) who[n++] = k;
6500         }
6501
6502         /* Select the sort method */
6503         ang_sort_comp = ang_sort_art_comp;
6504         ang_sort_swap = ang_sort_art_swap;
6505
6506         /* Sort the array by dungeon depth of monsters */
6507         ang_sort(who, &why, n);
6508
6509         /* Scan the artifacts */
6510         for (k = 0; k < n; k++)
6511         {
6512                 artifact_type *a_ptr = &a_info[who[k]];
6513
6514                 /* Paranoia */
6515 #ifdef JP
6516                 strcpy(base_name, "̤ÃΤÎÅÁÀâ¤Î¥¢¥¤¥Æ¥à");
6517 #else
6518                 strcpy(base_name, "Unknown Artifact");
6519 #endif
6520
6521
6522                 /* Obtain the base object type */
6523                 z = lookup_kind(a_ptr->tval, a_ptr->sval);
6524
6525                 /* Real object */
6526                 if (z)
6527                 {
6528                         object_type forge;
6529                         object_type *q_ptr;
6530
6531                         /* Get local object */
6532                         q_ptr = &forge;
6533
6534                         /* Create fake object */
6535                         object_prep(q_ptr, z);
6536
6537                         /* Make it an artifact */
6538                         q_ptr->name1 = (byte)who[k];
6539
6540                         /* Display as if known */
6541                         q_ptr->ident |= IDENT_STORE;
6542
6543                         /* Describe the artifact */
6544                         object_desc(base_name, q_ptr, (OD_OMIT_PREFIX | OD_NAME_ONLY));
6545                 }
6546
6547                 /* Hack -- Build the artifact name */
6548 #ifdef JP
6549                 fprintf(fff, "     %s\n", base_name);
6550 #else
6551                 fprintf(fff, "     The %s\n", base_name);
6552 #endif
6553
6554         }
6555
6556         /* Free the "who" array */
6557         C_KILL(who, max_a_idx, s16b);
6558
6559         /* Free the "okay" array */
6560         C_KILL(okay, max_a_idx, bool);
6561
6562         /* Close the file */
6563         my_fclose(fff);
6564
6565         /* Display the file contents */
6566 #ifdef JP
6567         show_file(TRUE, file_name, "´ûÃΤÎÅÁÀâ¤Î¥¢¥¤¥Æ¥à", 0, 0);
6568 #else
6569         show_file(TRUE, file_name, "Artifacts Seen", 0, 0);
6570 #endif
6571
6572
6573         /* Remove the file */
6574         fd_kill(file_name);
6575 }
6576
6577
6578 /*
6579  * Display known uniques
6580  * With "XTRA HACK UNIQHIST" (Originally from XAngband)
6581  */
6582 static void do_cmd_knowledge_uniques(void)
6583 {
6584         int i, k, n = 0;
6585         u16b why = 2;
6586         s16b *who;
6587
6588         FILE *fff;
6589
6590         char file_name[1024];
6591
6592         int n_alive[10];
6593         int n_alive_surface = 0;
6594         int n_alive_over100 = 0;
6595         int n_alive_total = 0;
6596         int max_lev = -1;
6597
6598         for (i = 0; i < 10; i++) n_alive[i] = 0;
6599
6600         /* Open a new file */
6601         fff = my_fopen_temp(file_name, 1024);
6602
6603         if (!fff)
6604         {
6605 #ifdef JP
6606             msg_format("°ì»þ¥Õ¥¡¥¤¥ë %s ¤òºîÀ®¤Ç¤­¤Þ¤»¤ó¤Ç¤·¤¿¡£", file_name);
6607 #else
6608             msg_format("Failed to create temporary file %s.", file_name);
6609 #endif
6610             msg_print(NULL);
6611             return;
6612         }
6613
6614         /* Allocate the "who" array */
6615         C_MAKE(who, max_r_idx, s16b);
6616
6617         /* Scan the monsters */
6618         for (i = 1; i < max_r_idx; i++)
6619         {
6620                 monster_race *r_ptr = &r_info[i];
6621                 int          lev;
6622
6623                 if (!r_ptr->name) continue;
6624
6625                 /* Require unique monsters */
6626                 if (!(r_ptr->flags1 & RF1_UNIQUE)) continue;
6627
6628                 /* Only display "known" uniques */
6629                 if (!cheat_know && !r_ptr->r_sights) continue;
6630
6631                 /* Only print rarity <= 100 uniques */
6632                 if (!r_ptr->rarity || ((r_ptr->rarity > 100) && !(r_ptr->flags1 & RF1_QUESTOR))) continue;
6633
6634                 /* Only "alive" uniques */
6635                 if (r_ptr->max_num == 0) continue;
6636
6637                 if (r_ptr->level)
6638                 {
6639                         lev = (r_ptr->level - 1) / 10;
6640                         if (lev < 10)
6641                         {
6642                                 n_alive[lev]++;
6643                                 if (max_lev < lev) max_lev = lev;
6644                         }
6645                         else n_alive_over100++;
6646                 }
6647                 else n_alive_surface++;
6648
6649                 /* Collect "appropriate" monsters */
6650                 who[n++] = i;
6651         }
6652
6653         /* Select the sort method */
6654         ang_sort_comp = ang_sort_comp_hook;
6655         ang_sort_swap = ang_sort_swap_hook;
6656
6657         /* Sort the array by dungeon depth of monsters */
6658         ang_sort(who, &why, n);
6659
6660         if (n_alive_surface)
6661         {
6662 #ifdef JP
6663                 fprintf(fff, "     ÃϾ堠À¸Â¸: %3dÂÎ\n", n_alive_surface);
6664 #else
6665                 fprintf(fff, "      Surface  alive: %3d\n", n_alive_surface);
6666 #endif
6667                 n_alive_total += n_alive_surface;
6668         }
6669         for (i = 0; i <= max_lev; i++)
6670         {
6671 #ifdef JP
6672                 fprintf(fff, "%3d-%3d³¬  À¸Â¸: %3dÂÎ\n", 1 + i * 10, 10 + i * 10, n_alive[i]);
6673 #else
6674                 fprintf(fff, "Level %3d-%3d  alive: %3d\n", 1 + i * 10, 10 + i * 10, n_alive[i]);
6675 #endif
6676                 n_alive_total += n_alive[i];
6677         }
6678         if (n_alive_over100)
6679         {
6680 #ifdef JP
6681                 fprintf(fff, "101-   ³¬  À¸Â¸: %3dÂÎ\n", n_alive_over100);
6682 #else
6683                 fprintf(fff, "Level 101-     alive: %3d\n", n_alive_over100);
6684 #endif
6685                 n_alive_total += n_alive_over100;
6686         }
6687
6688         if (n_alive_total)
6689         {
6690 #ifdef JP
6691                 fputs("---------  -----------\n", fff);
6692                 fprintf(fff, "     ¹ç·×  À¸Â¸: %3dÂÎ\n\n", n_alive_total);
6693 #else
6694                 fputs("-------------  ----------\n", fff);
6695                 fprintf(fff, "        Total  alive: %3d\n\n", n_alive_total);
6696 #endif
6697         }
6698         else
6699         {
6700 #ifdef JP
6701                 fputs("¸½ºß¤Ï´ûÃΤÎÀ¸Â¸¥æ¥Ë¡¼¥¯¤Ï¤¤¤Þ¤»¤ó¡£\n", fff);
6702 #else
6703                 fputs("No known uniques alive.\n", fff);
6704 #endif
6705         }
6706
6707         /* Scan the monster races */
6708         for (k = 0; k < n; k++)
6709         {
6710                 monster_race *r_ptr = &r_info[who[k]];
6711
6712                 /* Print a message */
6713 #ifdef JP
6714                 fprintf(fff, "     %s (¥ì¥Ù¥ë%d)\n", r_name + r_ptr->name, r_ptr->level);
6715 #else
6716                 fprintf(fff, "     %s (level %d)\n", r_name + r_ptr->name, r_ptr->level);
6717 #endif
6718         }
6719
6720         /* Free the "who" array */
6721         C_KILL(who, max_r_idx, s16b);
6722
6723         /* Close the file */
6724         my_fclose(fff);
6725
6726         /* Display the file contents */
6727 #ifdef JP
6728         show_file(TRUE, file_name, "¤Þ¤ÀÀ¸¤­¤Æ¤¤¤ë¥æ¥Ë¡¼¥¯¡¦¥â¥ó¥¹¥¿¡¼", 0, 0);
6729 #else
6730         show_file(TRUE, file_name, "Alive Uniques", 0, 0);
6731 #endif
6732
6733
6734         /* Remove the file */
6735         fd_kill(file_name);
6736 }
6737
6738
6739 /*
6740  * Display weapon-exp
6741  */
6742 static void do_cmd_knowledge_weapon_exp(void)
6743 {
6744         int i, j, num, weapon_exp;
6745
6746         FILE *fff;
6747
6748         char file_name[1024];
6749         char tmp[30];
6750
6751         /* Open a new file */
6752         fff = my_fopen_temp(file_name, 1024);
6753         if (!fff) {
6754 #ifdef JP
6755             msg_format("°ì»þ¥Õ¥¡¥¤¥ë %s ¤òºîÀ®¤Ç¤­¤Þ¤»¤ó¤Ç¤·¤¿¡£", file_name);
6756 #else
6757             msg_format("Failed to create temporary file %s.", file_name);
6758 #endif
6759             msg_print(NULL);
6760             return;
6761         }
6762
6763         for (i = 0; i < 5; i++)
6764         {
6765                 for (num = 0; num < 64; num++)
6766                 {
6767                         for (j = 0; j < max_k_idx; j++)
6768                         {
6769                                 object_kind *k_ptr = &k_info[j];
6770
6771                                 if ((k_ptr->tval == TV_SWORD - i) && (k_ptr->sval == num))
6772                                 {
6773                                         if ((k_ptr->tval == TV_BOW) && (k_ptr->sval == SV_CRIMSON)) continue;
6774
6775                                         weapon_exp = p_ptr->weapon_exp[4 - i][num];
6776                                         strip_name(tmp, j);
6777                                         fprintf(fff, "%-25s ", tmp);
6778                                         if (weapon_exp >= s_info[p_ptr->pclass].w_max[4 - i][num]) fprintf(fff, "!");
6779                                         else fprintf(fff, " ");
6780                                         fprintf(fff, "%s", exp_level_str[weapon_exp_level(weapon_exp)]);
6781                                         if (cheat_xtra) fprintf(fff, " %d", weapon_exp);
6782                                         fprintf(fff, "\n");
6783                                         break;
6784                                 }
6785                         }
6786                 }
6787         }
6788
6789         /* Close the file */
6790         my_fclose(fff);
6791
6792         /* Display the file contents */
6793 #ifdef JP
6794         show_file(TRUE, file_name, "Éð´ï¤Î·Ð¸³ÃÍ", 0, 0);
6795 #else
6796         show_file(TRUE, file_name, "Weapon Proficiency", 0, 0);
6797 #endif
6798
6799
6800         /* Remove the file */
6801         fd_kill(file_name);
6802 }
6803
6804
6805 /*
6806  * Display spell-exp
6807  */
6808 static void do_cmd_knowledge_spell_exp(void)
6809 {
6810         int i = 0, spell_exp, exp_level;
6811
6812         FILE *fff;
6813         magic_type *s_ptr;
6814
6815         char file_name[1024];
6816
6817         /* Open a new file */
6818         fff = my_fopen_temp(file_name, 1024);
6819         if (!fff) {
6820 #ifdef JP
6821             msg_format("°ì»þ¥Õ¥¡¥¤¥ë %s ¤òºîÀ®¤Ç¤­¤Þ¤»¤ó¤Ç¤·¤¿¡£", file_name);
6822 #else
6823             msg_format("Failed to create temporary file %s.", file_name);
6824 #endif
6825             msg_print(NULL);
6826             return;
6827         }
6828
6829         if (p_ptr->realm1 != REALM_NONE)
6830         {
6831 #ifdef JP
6832                 fprintf(fff, "%s¤ÎËâË¡½ñ\n", realm_names[p_ptr->realm1]);
6833 #else
6834                 fprintf(fff, "%s Spellbook\n", realm_names[p_ptr->realm1]);
6835 #endif
6836                 for (i = 0; i < 32; i++)
6837                 {
6838                         if (!is_magic(p_ptr->realm1))
6839                         {
6840                                 s_ptr = &technic_info[p_ptr->realm1 - MIN_TECHNIC][i];
6841                         }
6842                         else
6843                         {
6844                                 s_ptr = &mp_ptr->info[p_ptr->realm1 - 1][i];
6845                         }
6846                         if (s_ptr->slevel >= 99) continue;
6847                         spell_exp = p_ptr->spell_exp[i];
6848                         exp_level = spell_exp_level(spell_exp);
6849                         fprintf(fff, "%-25s ", do_spell(p_ptr->realm1, i, SPELL_NAME));
6850                         if (p_ptr->realm1 == REALM_HISSATSU)
6851                                 fprintf(fff, "[--]");
6852                         else
6853                         {
6854                                 if (exp_level >= EXP_LEVEL_MASTER) fprintf(fff, "!");
6855                                 else fprintf(fff, " ");
6856                                 fprintf(fff, "%s", exp_level_str[exp_level]);
6857                         }
6858                         if (cheat_xtra) fprintf(fff, " %d", spell_exp);
6859                         fprintf(fff, "\n");
6860                 }
6861         }
6862
6863         if (p_ptr->realm2 != REALM_NONE)
6864         {
6865 #ifdef JP
6866                 fprintf(fff, "%s¤ÎËâË¡½ñ\n", realm_names[p_ptr->realm2]);
6867 #else
6868                 fprintf(fff, "\n%s Spellbook\n", realm_names[p_ptr->realm2]);
6869 #endif
6870                 for (i = 0; i < 32; i++)
6871                 {
6872                         if (!is_magic(p_ptr->realm1))
6873                         {
6874                                 s_ptr = &technic_info[p_ptr->realm2 - MIN_TECHNIC][i];
6875                         }
6876                         else
6877                         {
6878                                 s_ptr = &mp_ptr->info[p_ptr->realm2 - 1][i];
6879                         }
6880                         if (s_ptr->slevel >= 99) continue;
6881
6882                         spell_exp = p_ptr->spell_exp[i + 32];
6883                         exp_level = spell_exp_level(spell_exp);
6884                         fprintf(fff, "%-25s ", do_spell(p_ptr->realm2, i, SPELL_NAME));
6885                         if (exp_level >= EXP_LEVEL_EXPERT) fprintf(fff, "!");
6886                         else fprintf(fff, " ");
6887                         fprintf(fff, "%s", exp_level_str[exp_level]);
6888                         if (cheat_xtra) fprintf(fff, " %d", spell_exp);
6889                         fprintf(fff, "\n");
6890                 }
6891         }
6892
6893         /* Close the file */
6894         my_fclose(fff);
6895
6896         /* Display the file contents */
6897 #ifdef JP
6898         show_file(TRUE, file_name, "ËâË¡¤Î·Ð¸³ÃÍ", 0, 0);
6899 #else
6900         show_file(TRUE, file_name, "Spell Proficiency", 0, 0);
6901 #endif
6902
6903
6904         /* Remove the file */
6905         fd_kill(file_name);
6906 }
6907
6908
6909 /*
6910  * Display skill-exp
6911  */
6912 static void do_cmd_knowledge_skill_exp(void)
6913 {
6914         int i = 0, skill_exp;
6915
6916         FILE *fff;
6917
6918         char file_name[1024];
6919 #ifdef JP
6920         char skill_name[3][17]={"¥Þ¡¼¥·¥ã¥ë¥¢¡¼¥Ä", "ÆóÅáή          ", "¾èÇÏ            "};
6921 #else
6922         char skill_name[3][20]={"Martial Arts    ", "Dual Wielding   ", "Riding          "};
6923 #endif
6924
6925         /* Open a new file */
6926         fff = my_fopen_temp(file_name, 1024);
6927         if (!fff) {
6928 #ifdef JP
6929             msg_format("°ì»þ¥Õ¥¡¥¤¥ë %s ¤òºîÀ®¤Ç¤­¤Þ¤»¤ó¤Ç¤·¤¿¡£", file_name);
6930 #else
6931             msg_format("Failed to create temporary file %s.", file_name);
6932 #endif
6933             msg_print(NULL);
6934             return;
6935         }
6936
6937         for (i = 0; i < 3; i++)
6938         {
6939                 skill_exp = p_ptr->skill_exp[i];
6940                 fprintf(fff, "%-20s ", skill_name[i]);
6941                 if (skill_exp >= s_info[p_ptr->pclass].s_max[i]) fprintf(fff, "!");
6942                 else fprintf(fff, " ");
6943                 fprintf(fff, "%s", exp_level_str[(i == GINOU_RIDING) ? riding_exp_level(skill_exp) : weapon_exp_level(skill_exp)]);
6944                 if (cheat_xtra) fprintf(fff, " %d", skill_exp);
6945                 fprintf(fff, "\n");
6946         }
6947
6948         /* Close the file */
6949         my_fclose(fff);
6950
6951         /* Display the file contents */
6952 #ifdef JP
6953         show_file(TRUE, file_name, "µ»Ç½¤Î·Ð¸³ÃÍ", 0, 0);
6954 #else
6955         show_file(TRUE, file_name, "Miscellaneous Proficiency", 0, 0);
6956 #endif
6957
6958
6959         /* Remove the file */
6960         fd_kill(file_name);
6961 }
6962
6963
6964 /*
6965  * Pluralize a monster name
6966  */
6967 void plural_aux(char *Name)
6968 {
6969         int NameLen = strlen(Name);
6970
6971         if (my_strstr(Name, "Disembodied hand"))
6972         {
6973                 strcpy(Name, "Disembodied hands that strangled people");
6974         }
6975         else if (my_strstr(Name, "Colour out of space"))
6976         {
6977                 strcpy(Name, "Colours out of space");
6978         }
6979         else if (my_strstr(Name, "stairway to hell"))
6980         {
6981                 strcpy(Name, "stairways to hell");
6982         }
6983         else if (my_strstr(Name, "Dweller on the threshold"))
6984         {
6985                 strcpy(Name, "Dwellers on the threshold");
6986         }
6987         else if (my_strstr(Name, " of "))
6988         {
6989                 cptr aider = my_strstr(Name, " of ");
6990                 char dummy[80];
6991                 int i = 0;
6992                 cptr ctr = Name;
6993
6994                 while (ctr < aider)
6995                 {
6996                         dummy[i] = *ctr;
6997                         ctr++; i++;
6998                 }
6999
7000                 if (dummy[i-1] == 's')
7001                 {
7002                         strcpy(&(dummy[i]), "es");
7003                         i++;
7004                 }
7005                 else
7006                 {
7007                         strcpy(&(dummy[i]), "s");
7008                 }
7009
7010                 strcpy(&(dummy[i+1]), aider);
7011                 strcpy(Name, dummy);
7012         }
7013         else if (my_strstr(Name, "coins"))
7014         {
7015                 char dummy[80];
7016                 strcpy(dummy, "piles of ");
7017                 strcat(dummy, Name);
7018                 strcpy(Name, dummy);
7019                 return;
7020         }
7021         else if (my_strstr(Name, "Manes"))
7022         {
7023                 return;
7024         }
7025         else if (streq(&(Name[NameLen - 2]), "ey"))
7026         {
7027                 strcpy(&(Name[NameLen - 2]), "eys");
7028         }
7029         else if (Name[NameLen - 1] == 'y')
7030         {
7031                 strcpy(&(Name[NameLen - 1]), "ies");
7032         }
7033         else if (streq(&(Name[NameLen - 4]), "ouse"))
7034         {
7035                 strcpy(&(Name[NameLen - 4]), "ice");
7036         }
7037         else if (streq(&(Name[NameLen - 2]), "us"))
7038         {
7039                 strcpy(&(Name[NameLen - 2]), "i");
7040         }
7041         else if (streq(&(Name[NameLen - 6]), "kelman"))
7042         {
7043                 strcpy(&(Name[NameLen - 6]), "kelmen");
7044         }
7045         else if (streq(&(Name[NameLen - 8]), "wordsman"))
7046         {
7047                 strcpy(&(Name[NameLen - 8]), "wordsmen");
7048         }
7049         else if (streq(&(Name[NameLen - 7]), "oodsman"))
7050         {
7051                 strcpy(&(Name[NameLen - 7]), "oodsmen");
7052         }
7053         else if (streq(&(Name[NameLen - 7]), "eastman"))
7054         {
7055                 strcpy(&(Name[NameLen - 7]), "eastmen");
7056         }
7057         else if (streq(&(Name[NameLen - 8]), "izardman"))
7058         {
7059                 strcpy(&(Name[NameLen - 8]), "izardmen");
7060         }
7061         else if (streq(&(Name[NameLen - 5]), "geist"))
7062         {
7063                 strcpy(&(Name[NameLen - 5]), "geister");
7064         }
7065         else if (streq(&(Name[NameLen - 2]), "ex"))
7066         {
7067                 strcpy(&(Name[NameLen - 2]), "ices");
7068         }
7069         else if (streq(&(Name[NameLen - 2]), "lf"))
7070         {
7071                 strcpy(&(Name[NameLen - 2]), "lves");
7072         }
7073         else if (suffix(Name, "ch") ||
7074                  suffix(Name, "sh") ||
7075                          suffix(Name, "nx") ||
7076                          suffix(Name, "s") ||
7077                          suffix(Name, "o"))
7078         {
7079                 strcpy(&(Name[NameLen]), "es");
7080         }
7081         else
7082         {
7083                 strcpy(&(Name[NameLen]), "s");
7084         }
7085 }
7086
7087 /*
7088  * Display current pets
7089  */
7090 static void do_cmd_knowledge_pets(void)
7091 {
7092         int             i;
7093         FILE            *fff;
7094         monster_type    *m_ptr;
7095         char            pet_name[80];
7096         int             t_friends = 0;
7097         int             show_upkeep = 0;
7098         char            file_name[1024];
7099
7100
7101         /* Open a new file */
7102         fff = my_fopen_temp(file_name, 1024);
7103         if (!fff) {
7104 #ifdef JP
7105             msg_format("°ì»þ¥Õ¥¡¥¤¥ë %s ¤òºîÀ®¤Ç¤­¤Þ¤»¤ó¤Ç¤·¤¿¡£", file_name);
7106 #else
7107             msg_format("Failed to create temporary file %s.", file_name);
7108 #endif
7109             msg_print(NULL);
7110             return;
7111         }
7112
7113         /* Process the monsters (backwards) */
7114         for (i = m_max - 1; i >= 1; i--)
7115         {
7116                 /* Access the monster */
7117                 m_ptr = &m_list[i];
7118
7119                 /* Ignore "dead" monsters */
7120                 if (!m_ptr->r_idx) continue;
7121
7122                 /* Calculate "upkeep" for pets */
7123                 if (is_pet(m_ptr))
7124                 {
7125                         t_friends++;
7126                         monster_desc(pet_name, m_ptr, MD_ASSUME_VISIBLE | MD_INDEF_VISIBLE);
7127                         fprintf(fff, "%s (%s)\n", pet_name, look_mon_desc(m_ptr, 0x00));
7128                 }
7129         }
7130
7131         show_upkeep = calculate_upkeep();
7132
7133         fprintf(fff, "----------------------------------------------\n");
7134 #ifdef JP
7135         fprintf(fff, "    ¹ç·×: %d ÂΤΥڥåÈ\n", t_friends);
7136         fprintf(fff, " °Ý»ý¥³¥¹¥È: %d%% MP\n", show_upkeep);
7137 #else
7138         fprintf(fff, "   Total: %d pet%s.\n",
7139                 t_friends, (t_friends == 1 ? "" : "s"));
7140         fprintf(fff, "   Upkeep: %d%% mana.\n", show_upkeep);
7141 #endif
7142
7143
7144
7145         /* Close the file */
7146         my_fclose(fff);
7147
7148         /* Display the file contents */
7149 #ifdef JP
7150         show_file(TRUE, file_name, "¸½ºß¤Î¥Ú¥Ã¥È", 0, 0);
7151 #else
7152         show_file(TRUE, file_name, "Current Pets", 0, 0);
7153 #endif
7154
7155
7156         /* Remove the file */
7157         fd_kill(file_name);
7158 }
7159
7160
7161 /*
7162  * Total kill count
7163  *
7164  * Note that the player ghosts are ignored.  XXX XXX XXX
7165  */
7166 static void do_cmd_knowledge_kill_count(void)
7167 {
7168         int i, k, n = 0;
7169         u16b why = 2;
7170         s16b *who;
7171
7172         FILE *fff;
7173
7174         char file_name[1024];
7175
7176         s32b Total = 0;
7177
7178
7179         /* Open a new file */
7180         fff = my_fopen_temp(file_name, 1024);
7181
7182         if (!fff) {
7183 #ifdef JP
7184             msg_format("°ì»þ¥Õ¥¡¥¤¥ë %s ¤òºîÀ®¤Ç¤­¤Þ¤»¤ó¤Ç¤·¤¿¡£", file_name);
7185 #else
7186             msg_format("Failed to create temporary file %s.", file_name);
7187 #endif
7188             msg_print(NULL);
7189             return;
7190         }
7191
7192         /* Allocate the "who" array */
7193         C_MAKE(who, max_r_idx, s16b);
7194
7195         {
7196                 /* Monsters slain */
7197                 int kk;
7198
7199                 for (kk = 1; kk < max_r_idx; kk++)
7200                 {
7201                         monster_race *r_ptr = &r_info[kk];
7202
7203                         if (r_ptr->flags1 & (RF1_UNIQUE))
7204                         {
7205                                 bool dead = (r_ptr->max_num == 0);
7206
7207                                 if (dead)
7208                                 {
7209                                         Total++;
7210                                 }
7211                         }
7212                         else
7213                         {
7214                                 s16b This = r_ptr->r_pkills;
7215
7216                                 if (This > 0)
7217                                 {
7218                                         Total += This;
7219                                 }
7220                         }
7221                 }
7222
7223                 if (Total < 1)
7224 #ifdef JP
7225                         fprintf(fff,"¤¢¤Ê¤¿¤Ï¤Þ¤ÀŨ¤òÅݤ·¤Æ¤¤¤Ê¤¤¡£\n\n");
7226 #else
7227                         fprintf(fff,"You have defeated no enemies yet.\n\n");
7228 #endif
7229                 else
7230 #ifdef JP
7231                         fprintf(fff,"¤¢¤Ê¤¿¤Ï%ldÂΤÎŨ¤òÅݤ·¤Æ¤¤¤ë¡£\n\n", Total);
7232 #else
7233                         fprintf(fff,"You have defeated %ld %s.\n\n", Total, (Total == 1) ? "enemy" : "enemies");
7234 #endif
7235         }
7236
7237         Total = 0;
7238
7239         /* Scan the monsters */
7240         for (i = 1; i < max_r_idx; i++)
7241         {
7242                 monster_race *r_ptr = &r_info[i];
7243
7244                 /* Use that monster */
7245                 if (r_ptr->name) who[n++] = i;
7246         }
7247
7248         /* Select the sort method */
7249         ang_sort_comp = ang_sort_comp_hook;
7250         ang_sort_swap = ang_sort_swap_hook;
7251
7252         /* Sort the array by dungeon depth of monsters */
7253         ang_sort(who, &why, n);
7254
7255         /* Scan the monster races */
7256         for (k = 0; k < n; k++)
7257         {
7258                 monster_race *r_ptr = &r_info[who[k]];
7259
7260                 if (r_ptr->flags1 & (RF1_UNIQUE))
7261                 {
7262                         bool dead = (r_ptr->max_num == 0);
7263
7264                         if (dead)
7265                         {
7266                                 /* Print a message */
7267                                 fprintf(fff, "     %s\n",
7268                                     (r_name + r_ptr->name));
7269                                 Total++;
7270                         }
7271                 }
7272                 else
7273                 {
7274                         s16b This = r_ptr->r_pkills;
7275
7276                         if (This > 0)
7277                         {
7278 #ifdef JP
7279                                 /* p,t¤Ï¿Í¤È¿ô¤¨¤ë by ita */
7280                                 if (my_strchr("pt", r_ptr->d_char))
7281                                         fprintf(fff, "     %3d ¿Í¤Î %s\n", This, r_name + r_ptr->name);
7282                                 else
7283                                         fprintf(fff, "     %3d ÂΤΠ%s\n", This, r_name + r_ptr->name);
7284 #else
7285                                 if (This < 2)
7286                                 {
7287                                         if (my_strstr(r_name + r_ptr->name, "coins"))
7288                                         {
7289                                                 fprintf(fff, "     1 pile of %s\n", (r_name + r_ptr->name));
7290                                         }
7291                                         else
7292                                         {
7293                                                 fprintf(fff, "     1 %s\n", (r_name + r_ptr->name));
7294                                         }
7295                                 }
7296                                 else
7297                                 {
7298                                         char ToPlural[80];
7299                                         strcpy(ToPlural, (r_name + r_ptr->name));
7300                                         plural_aux(ToPlural);
7301                                         fprintf(fff, "     %d %s\n", This, ToPlural);
7302                                 }
7303 #endif
7304
7305
7306                                 Total += This;
7307                         }
7308                 }
7309         }
7310
7311         fprintf(fff,"----------------------------------------------\n");
7312 #ifdef JP
7313         fprintf(fff,"    ¹ç·×: %lu ÂΤòÅݤ·¤¿¡£\n", Total);
7314 #else
7315         fprintf(fff,"   Total: %lu creature%s killed.\n",
7316                 Total, (Total == 1 ? "" : "s"));
7317 #endif
7318
7319
7320         /* Free the "who" array */
7321         C_KILL(who, max_r_idx, s16b);
7322
7323         /* Close the file */
7324         my_fclose(fff);
7325
7326         /* Display the file contents */
7327 #ifdef JP
7328         show_file(TRUE, file_name, "Åݤ·¤¿Å¨¤Î¿ô", 0, 0);
7329 #else
7330         show_file(TRUE, file_name, "Kill Count", 0, 0);
7331 #endif
7332
7333
7334         /* Remove the file */
7335         fd_kill(file_name);
7336 }
7337
7338
7339 /*
7340  * Display the object groups.
7341  */
7342 static void display_group_list(int col, int row, int wid, int per_page,
7343         int grp_idx[], cptr group_text[], int grp_cur, int grp_top)
7344 {
7345         int i;
7346
7347         /* Display lines until done */
7348         for (i = 0; i < per_page && (grp_idx[i] >= 0); i++)
7349         {
7350                 /* Get the group index */
7351                 int grp = grp_idx[grp_top + i];
7352
7353                 /* Choose a color */
7354                 byte attr = (grp_top + i == grp_cur) ? TERM_L_BLUE : TERM_WHITE;
7355
7356                 /* Erase the entire line */
7357                 Term_erase(col, row + i, wid);
7358
7359                 /* Display the group label */
7360                 c_put_str(attr, group_text[grp], row + i, col);
7361         }
7362 }
7363
7364
7365 /* 
7366  * Move the cursor in a browser window 
7367  */
7368 static void browser_cursor(char ch, int *column, int *grp_cur, int grp_cnt, 
7369                                                    int *list_cur, int list_cnt)
7370 {
7371         int d;
7372         int col = *column;
7373         int grp = *grp_cur;
7374         int list = *list_cur;
7375
7376         /* Extract direction */
7377         if (ch == ' ')
7378         {
7379                 /* Hack -- scroll up full screen */
7380                 d = 3;
7381         }
7382         else if (ch == '-')
7383         {
7384                 /* Hack -- scroll down full screen */
7385                 d = 9;
7386         }
7387         else
7388         {
7389                 d = get_keymap_dir(ch);
7390         }
7391
7392         if (!d) return;
7393
7394         /* Diagonals - hack */
7395         if ((ddx[d] > 0) && ddy[d])
7396         {
7397                 int browser_rows;
7398                 int wid, hgt;
7399
7400                 /* Get size */
7401                 Term_get_size(&wid, &hgt);
7402
7403                 browser_rows = hgt - 8;
7404
7405                 /* Browse group list */
7406                 if (!col)
7407                 {
7408                         int old_grp = grp;
7409
7410                         /* Move up or down */
7411                         grp += ddy[d] * (browser_rows - 1);
7412
7413                         /* Verify */
7414                         if (grp >= grp_cnt)     grp = grp_cnt - 1;
7415                         if (grp < 0) grp = 0;
7416                         if (grp != old_grp)     list = 0;
7417                 }
7418
7419                 /* Browse sub-list list */
7420                 else
7421                 {
7422                         /* Move up or down */
7423                         list += ddy[d] * browser_rows;
7424
7425                         /* Verify */
7426                         if (list >= list_cnt) list = list_cnt - 1;
7427                         if (list < 0) list = 0;
7428                 }
7429
7430                 (*grp_cur) = grp;
7431                 (*list_cur) = list;
7432
7433                 return;
7434         }
7435
7436         if (ddx[d])
7437         {
7438                 col += ddx[d];
7439                 if (col < 0) col = 0;
7440                 if (col > 1) col = 1;
7441
7442                 (*column) = col;
7443
7444                 return;
7445         }
7446
7447         /* Browse group list */
7448         if (!col)
7449         {
7450                 int old_grp = grp;
7451
7452                 /* Move up or down */
7453                 grp += ddy[d];
7454
7455                 /* Verify */
7456                 if (grp >= grp_cnt)     grp = grp_cnt - 1;
7457                 if (grp < 0) grp = 0;
7458                 if (grp != old_grp)     list = 0;
7459         }
7460
7461         /* Browse sub-list list */
7462         else
7463         {
7464                 /* Move up or down */
7465                 list += ddy[d];
7466
7467                 /* Verify */
7468                 if (list >= list_cnt) list = list_cnt - 1;
7469                 if (list < 0) list = 0;
7470         }
7471
7472         (*grp_cur) = grp;
7473         (*list_cur) = list;
7474 }
7475
7476
7477 /*
7478  * Display visuals.
7479  */
7480 static void display_visual_list(int col, int row, int height, int width, byte attr_top, byte char_left)
7481 {
7482         int i, j;
7483
7484         /* Clear the display lines */
7485         for (i = 0; i < height; i++)
7486         {
7487                 Term_erase(col, row + i, width);
7488         }
7489
7490         /* Bigtile mode uses double width */
7491         if (use_bigtile) width /= 2;
7492
7493         /* Display lines until done */
7494         for (i = 0; i < height; i++)
7495         {
7496                 /* Display columns until done */
7497                 for (j = 0; j < width; j++)
7498                 {
7499                         byte a;
7500                         char c;
7501                         int x = col + j;
7502                         int y = row + i;
7503                         int ia, ic;
7504
7505                         /* Bigtile mode uses double width */
7506                         if (use_bigtile) x += j;
7507
7508                         ia = attr_top + i;
7509                         ic = char_left + j;
7510
7511                         /* Ignore illegal characters */
7512                         if (ia > 0x7f || ic > 0xff || ic < ' ' ||
7513                             (!use_graphics && ic > 0x7f))
7514                                 continue;
7515
7516                         a = (byte)ia;
7517                         c = (char)ic;
7518
7519                         /* Force correct code for both ASCII character and tile */
7520                         if (c & 0x80) a |= 0x80;
7521
7522                         /* Display symbol */
7523                         Term_queue_bigchar(x, y, a, c, 0, 0);
7524                 }
7525         }
7526 }
7527
7528
7529 /*
7530  * Place the cursor at the collect position for visual mode
7531  */
7532 static void place_visual_list_cursor(int col, int row, byte a, byte c, byte attr_top, byte char_left)
7533 {
7534         int i = (a & 0x7f) - attr_top;
7535         int j = c - char_left;
7536
7537         int x = col + j;
7538         int y = row + i;
7539
7540         /* Bigtile mode uses double width */
7541         if (use_bigtile) x += j;
7542
7543         /* Place the cursor */
7544         Term_gotoxy(x, y);
7545 }
7546
7547
7548 /*
7549  *  Clipboard variables for copy&paste in visual mode
7550  */
7551 static byte attr_idx = 0;
7552 static byte char_idx = 0;
7553
7554 /* Hack -- for feature lighting */
7555 static byte attr_idx_feat[F_LIT_MAX];
7556 static byte char_idx_feat[F_LIT_MAX];
7557
7558 /*
7559  *  Do visual mode command -- Change symbols
7560  */
7561 static bool visual_mode_command(char ch, bool *visual_list_ptr,
7562                                 int height, int width,
7563                                 byte *attr_top_ptr, byte *char_left_ptr,
7564                                 byte *cur_attr_ptr, byte *cur_char_ptr, bool *need_redraw)
7565 {
7566         static byte attr_old = 0, char_old = 0;
7567
7568         switch (ch)
7569         {
7570         case ESCAPE:
7571                 if (*visual_list_ptr)
7572                 {
7573                         /* Cancel change */
7574                         *cur_attr_ptr = attr_old;
7575                         *cur_char_ptr = char_old;
7576                         *visual_list_ptr = FALSE;
7577
7578                         return TRUE;
7579                 }
7580                 break;
7581
7582         case '\n':
7583         case '\r':
7584                 if (*visual_list_ptr)
7585                 {
7586                         /* Accept change */
7587                         *visual_list_ptr = FALSE;
7588                         *need_redraw = TRUE;
7589
7590                         return TRUE;
7591                 }
7592                 break;
7593
7594         case 'V':
7595         case 'v':
7596                 if (!*visual_list_ptr)
7597                 {
7598                         *visual_list_ptr = TRUE;
7599
7600                         *attr_top_ptr = MAX(0, (*cur_attr_ptr & 0x7f) - 5);
7601                         *char_left_ptr = MAX(0, *cur_char_ptr - 10);
7602
7603                         attr_old = *cur_attr_ptr;
7604                         char_old = *cur_char_ptr;
7605
7606                         return TRUE;
7607                 }
7608                 break;
7609
7610         case 'C':
7611         case 'c':
7612                 {
7613                         int i;
7614
7615                         /* Set the visual */
7616                         attr_idx = *cur_attr_ptr;
7617                         char_idx = *cur_char_ptr;
7618
7619                         /* Hack -- for feature lighting */
7620                         for (i = 0; i < F_LIT_MAX; i++)
7621                         {
7622                                 attr_idx_feat[i] = 0;
7623                                 char_idx_feat[i] = 0;
7624                         }
7625                 }
7626                 return TRUE;
7627
7628         case 'P':
7629         case 'p':
7630                 if (attr_idx || (!(char_idx & 0x80) && char_idx)) /* Allow TERM_DARK text */
7631                 {
7632                         /* Set the char */
7633                         *cur_attr_ptr = attr_idx;
7634                         *attr_top_ptr = MAX(0, (*cur_attr_ptr & 0x7f) - 5);
7635                         if (!*visual_list_ptr) *need_redraw = TRUE;
7636                 }
7637
7638                 if (char_idx)
7639                 {
7640                         /* Set the char */
7641                         *cur_char_ptr = char_idx;
7642                         *char_left_ptr = MAX(0, *cur_char_ptr - 10);
7643                         if (!*visual_list_ptr) *need_redraw = TRUE;
7644                 }
7645
7646                 return TRUE;
7647
7648         default:
7649                 if (*visual_list_ptr)
7650                 {
7651                         int eff_width;
7652                         int d = get_keymap_dir(ch);
7653                         byte a = (*cur_attr_ptr & 0x7f);
7654                         byte c = *cur_char_ptr;
7655
7656                         if (use_bigtile) eff_width = width / 2;
7657                         else eff_width = width;
7658
7659                         /* Restrict direction */
7660                         if ((a == 0) && (ddy[d] < 0)) d = 0;
7661                         if ((c == 0) && (ddx[d] < 0)) d = 0;
7662                         if ((a == 0x7f) && (ddy[d] > 0)) d = 0;
7663                         if ((c == 0xff) && (ddx[d] > 0)) d = 0;
7664
7665                         a += ddy[d];
7666                         c += ddx[d];
7667
7668                         /* Force correct code for both ASCII character and tile */
7669                         if (c & 0x80) a |= 0x80;
7670
7671                         /* Set the visual */
7672                         *cur_attr_ptr = a;
7673                         *cur_char_ptr = c;
7674
7675
7676                         /* Move the frame */
7677                         if ((ddx[d] < 0) && *char_left_ptr > MAX(0, (int)c - 10)) (*char_left_ptr)--;
7678                         if ((ddx[d] > 0) && *char_left_ptr + eff_width < MIN(0xff, (int)c + 10)) (*char_left_ptr)++;
7679                         if ((ddy[d] < 0) && *attr_top_ptr > MAX(0, (int)(a & 0x7f) - 4)) (*attr_top_ptr)--;
7680                         if ((ddy[d] > 0) && *attr_top_ptr + height < MIN(0x7f, (a & 0x7f) + 4)) (*attr_top_ptr)++;
7681                         return TRUE;
7682                 }
7683                 break;
7684         }
7685
7686         /* Visual mode command is not used */
7687         return FALSE;
7688 }
7689
7690
7691 /*
7692  * Display the monsters in a group.
7693  */
7694 static void display_monster_list(int col, int row, int per_page, s16b mon_idx[],
7695         int mon_cur, int mon_top, bool visual_only)
7696 {
7697         int i;
7698
7699         /* Display lines until done */
7700         for (i = 0; i < per_page && (mon_idx[mon_top + i] >= 0); i++)
7701         {
7702                 byte attr;
7703
7704                 /* Get the race index */
7705                 int r_idx = mon_idx[mon_top + i] ;
7706
7707                 /* Access the race */
7708                 monster_race *r_ptr = &r_info[r_idx];
7709
7710                 /* Choose a color */
7711                 attr = ((i + mon_top == mon_cur) ? TERM_L_BLUE : TERM_WHITE);
7712
7713                 /* Display the name */
7714                 c_prt(attr, (r_name + r_ptr->name), row + i, col);
7715
7716                 /* Hack -- visual_list mode */
7717                 if (per_page == 1)
7718                 {
7719                         c_prt(attr, format("%02x/%02x", r_ptr->x_attr, r_ptr->x_char), row + i, (p_ptr->wizard || visual_only) ? 56 : 61);
7720                 }
7721                 if (p_ptr->wizard || visual_only)
7722                 {
7723                         c_prt(attr, format("%d", r_idx), row + i, 62);
7724                 }
7725
7726                 /* Erase chars before overwritten by the race letter */
7727                 Term_erase(69, row + i, 255);
7728
7729                 /* Display symbol */
7730                 Term_queue_bigchar(use_bigtile ? 69 : 70, row + i, r_ptr->x_attr, r_ptr->x_char, 0, 0);
7731
7732                 if (!visual_only)
7733                 {
7734                         /* Display kills */
7735                         if (!(r_ptr->flags1 & RF1_UNIQUE)) put_str(format("%5d", r_ptr->r_pkills), row + i, 73);
7736 #ifdef JP
7737                         else c_put_str((r_ptr->max_num == 0 ? TERM_L_DARK : TERM_WHITE), (r_ptr->max_num == 0 ? "»àË´" : "À¸Â¸"), row + i, 74);
7738 #else
7739                         else c_put_str((r_ptr->max_num == 0 ? TERM_L_DARK : TERM_WHITE), (r_ptr->max_num == 0 ? " dead" : "alive"), row + i, 73);
7740 #endif
7741                 }
7742         }
7743
7744         /* Clear remaining lines */
7745         for (; i < per_page; i++)
7746         {
7747                 Term_erase(col, row + i, 255);
7748         }
7749 }
7750
7751
7752 /*
7753  * Display known monsters.
7754  */
7755 static void do_cmd_knowledge_monsters(bool *need_redraw, bool visual_only, int direct_r_idx)
7756 {
7757         int i, len, max;
7758         int grp_cur, grp_top, old_grp_cur;
7759         int mon_cur, mon_top;
7760         int grp_cnt, grp_idx[100];
7761         int mon_cnt;
7762         s16b *mon_idx;
7763
7764         int column = 0;
7765         bool flag;
7766         bool redraw;
7767
7768         bool visual_list = FALSE;
7769         byte attr_top = 0, char_left = 0;
7770
7771         int browser_rows;
7772         int wid, hgt;
7773
7774         byte mode;
7775
7776         /* Get size */
7777         Term_get_size(&wid, &hgt);
7778
7779         browser_rows = hgt - 8;
7780
7781         /* Allocate the "mon_idx" array */
7782         C_MAKE(mon_idx, max_r_idx, s16b);
7783
7784         max = 0;
7785         grp_cnt = 0;
7786
7787         if (direct_r_idx < 0)
7788         {
7789                 mode = visual_only ? 0x03 : 0x01;
7790
7791                 /* Check every group */
7792                 for (i = 0; monster_group_text[i] != NULL; i++)
7793                 {
7794                         /* Measure the label */
7795                         len = strlen(monster_group_text[i]);
7796
7797                         /* Save the maximum length */
7798                         if (len > max) max = len;
7799
7800                         /* See if any monsters are known */
7801                         if ((monster_group_char[i] == ((char *) -1L)) || collect_monsters(i, mon_idx, mode))
7802                         {
7803                                 /* Build a list of groups with known monsters */
7804                                 grp_idx[grp_cnt++] = i;
7805                         }
7806                 }
7807
7808                 mon_cnt = 0;
7809         }
7810         else
7811         {
7812                 mon_idx[0] = direct_r_idx;
7813                 mon_cnt = 1;
7814
7815                 /* Terminate the list */
7816                 mon_idx[1] = -1;
7817
7818                 (void)visual_mode_command('v', &visual_list, browser_rows - 1, wid - (max + 3),
7819                         &attr_top, &char_left, &r_info[direct_r_idx].x_attr, &r_info[direct_r_idx].x_char, need_redraw);
7820         }
7821
7822         /* Terminate the list */
7823         grp_idx[grp_cnt] = -1;
7824
7825         old_grp_cur = -1;
7826         grp_cur = grp_top = 0;
7827         mon_cur = mon_top = 0;
7828
7829         flag = FALSE;
7830         redraw = TRUE;
7831
7832         mode = visual_only ? 0x02 : 0x00;
7833
7834         while (!flag)
7835         {
7836                 char ch;
7837                 monster_race *r_ptr;
7838
7839                 if (redraw)
7840                 {
7841                         clear_from(0);
7842
7843 #ifdef JP
7844                         prt(format("%s - ¥â¥ó¥¹¥¿¡¼", !visual_only ? "Ãμ±" : "ɽ¼¨"), 2, 0);
7845                         if (direct_r_idx < 0) prt("¥°¥ë¡¼¥×", 4, 0);
7846                         prt("̾Á°", 4, max + 3);
7847                         if (p_ptr->wizard || visual_only) prt("Idx", 4, 62);
7848                         prt("ʸ»ú", 4, 67);
7849                         if (!visual_only) prt("»¦³²¿ô", 4, 72);
7850 #else
7851                         prt(format("%s - monsters", !visual_only ? "Knowledge" : "Visuals"), 2, 0);
7852                         if (direct_r_idx < 0) prt("Group", 4, 0);
7853                         prt("Name", 4, max + 3);
7854                         if (p_ptr->wizard || visual_only) prt("Idx", 4, 62);
7855                         prt("Sym", 4, 68);
7856                         if (!visual_only) prt("Kills", 4, 73);
7857 #endif
7858
7859                         for (i = 0; i < 78; i++)
7860                         {
7861                                 Term_putch(i, 5, TERM_WHITE, '=');
7862                         }
7863
7864                         if (direct_r_idx < 0)
7865                         {
7866                                 for (i = 0; i < browser_rows; i++)
7867                                 {
7868                                         Term_putch(max + 1, 6 + i, TERM_WHITE, '|');
7869                                 }
7870                         }
7871
7872                         redraw = FALSE;
7873                 }
7874
7875                 if (direct_r_idx < 0)
7876                 {
7877                         /* Scroll group list */
7878                         if (grp_cur < grp_top) grp_top = grp_cur;
7879                         if (grp_cur >= grp_top + browser_rows) grp_top = grp_cur - browser_rows + 1;
7880
7881                         /* Display a list of monster groups */
7882                         display_group_list(0, 6, max, browser_rows, grp_idx, monster_group_text, grp_cur, grp_top);
7883
7884                         if (old_grp_cur != grp_cur)
7885                         {
7886                                 old_grp_cur = grp_cur;
7887
7888                                 /* Get a list of monsters in the current group */
7889                                 mon_cnt = collect_monsters(grp_idx[grp_cur], mon_idx, mode);
7890                         }
7891
7892                         /* Scroll monster list */
7893                         while (mon_cur < mon_top)
7894                                 mon_top = MAX(0, mon_top - browser_rows/2);
7895                         while (mon_cur >= mon_top + browser_rows)
7896                                 mon_top = MIN(mon_cnt - browser_rows, mon_top + browser_rows/2);
7897                 }
7898
7899                 if (!visual_list)
7900                 {
7901                         /* Display a list of monsters in the current group */
7902                         display_monster_list(max + 3, 6, browser_rows, mon_idx, mon_cur, mon_top, visual_only);
7903                 }
7904                 else
7905                 {
7906                         mon_top = mon_cur;
7907
7908                         /* Display a monster name */
7909                         display_monster_list(max + 3, 6, 1, mon_idx, mon_cur, mon_top, visual_only);
7910
7911                         /* Display visual list below first monster */
7912                         display_visual_list(max + 3, 7, browser_rows-1, wid - (max + 3), attr_top, char_left);
7913                 }
7914
7915                 /* Prompt */
7916 #ifdef JP
7917                 prt(format("<Êý¸þ>%s%s%s, ESC",
7918                         (!visual_list && !visual_only) ? ", 'r'¤Ç»×¤¤½Ð¤ò¸«¤ë" : "",
7919                         visual_list ? ", ENTER¤Ç·èÄê" : ", 'v'¤Ç¥·¥ó¥Ü¥ëÊѹ¹",
7920                         (attr_idx || char_idx) ? ", 'c', 'p'¤Ç¥Ú¡¼¥¹¥È" : ", 'c'¤Ç¥³¥Ô¡¼"),
7921                         hgt - 1, 0);
7922 #else
7923                 prt(format("<dir>%s%s%s, ESC",
7924                         (!visual_list && !visual_only) ? ", 'r' to recall" : "",
7925                         visual_list ? ", ENTER to accept" : ", 'v' for visuals",
7926                         (attr_idx || char_idx) ? ", 'c', 'p' to paste" : ", 'c' to copy"),
7927                         hgt - 1, 0);
7928 #endif
7929
7930                 /* Get the current monster */
7931                 r_ptr = &r_info[mon_idx[mon_cur]];
7932
7933                 if (!visual_only)
7934                 {
7935                         /* Mega Hack -- track this monster race */
7936                         if (mon_cnt) monster_race_track(mon_idx[mon_cur]);
7937
7938                         /* Hack -- handle stuff */
7939                         handle_stuff();
7940                 }
7941
7942                 if (visual_list)
7943                 {
7944                         place_visual_list_cursor(max + 3, 7, r_ptr->x_attr, r_ptr->x_char, attr_top, char_left);
7945                 }
7946                 else if (!column)
7947                 {
7948                         Term_gotoxy(0, 6 + (grp_cur - grp_top));
7949                 }
7950                 else
7951                 {
7952                         Term_gotoxy(max + 3, 6 + (mon_cur - mon_top));
7953                 }
7954
7955                 ch = inkey();
7956
7957                 /* Do visual mode command if needed */
7958                 if (visual_mode_command(ch, &visual_list, browser_rows-1, wid - (max + 3), &attr_top, &char_left, &r_ptr->x_attr, &r_ptr->x_char, need_redraw))
7959                 {
7960                         if (direct_r_idx >= 0)
7961                         {
7962                                 switch (ch)
7963                                 {
7964                                 case '\n':
7965                                 case '\r':
7966                                 case ESCAPE:
7967                                         flag = TRUE;
7968                                         break;
7969                                 }
7970                         }
7971                         continue;
7972                 }
7973
7974                 switch (ch)
7975                 {
7976                         case ESCAPE:
7977                         {
7978                                 flag = TRUE;
7979                                 break;
7980                         }
7981
7982                         case 'R':
7983                         case 'r':
7984                         {
7985                                 /* Recall on screen */
7986                                 if (!visual_list && !visual_only && (mon_idx[mon_cur] > 0))
7987                                 {
7988                                         screen_roff(mon_idx[mon_cur], 0);
7989
7990                                         (void)inkey();
7991
7992                                         redraw = TRUE;
7993                                 }
7994                                 break;
7995                         }
7996
7997                         default:
7998                         {
7999                                 /* Move the cursor */
8000                                 browser_cursor(ch, &column, &grp_cur, grp_cnt, &mon_cur, mon_cnt);
8001
8002                                 break;
8003                         }
8004                 }
8005         }
8006
8007         /* Free the "mon_idx" array */
8008         C_KILL(mon_idx, max_r_idx, s16b);
8009 }
8010
8011
8012 /*
8013  * Display the objects in a group.
8014  */
8015 static void display_object_list(int col, int row, int per_page, int object_idx[],
8016         int object_cur, int object_top, bool visual_only)
8017 {
8018         int i;
8019
8020         /* Display lines until done */
8021         for (i = 0; i < per_page && (object_idx[object_top + i] >= 0); i++)
8022         {
8023                 char o_name[80];
8024                 byte a, c;
8025                 object_kind *flavor_k_ptr;
8026
8027                 /* Get the object index */
8028                 int k_idx = object_idx[object_top + i];
8029
8030                 /* Access the object */
8031                 object_kind *k_ptr = &k_info[k_idx];
8032
8033                 /* Choose a color */
8034                 byte attr = ((k_ptr->aware || visual_only) ? TERM_WHITE : TERM_SLATE);
8035                 byte cursor = ((k_ptr->aware || visual_only) ? TERM_L_BLUE : TERM_BLUE);
8036
8037
8038                 if (k_ptr->flavor)
8039                 {
8040                         /* Appearance of this object is shuffled */
8041                         flavor_k_ptr = &k_info[k_ptr->flavor];
8042                 }
8043                 else
8044                 {
8045                         /* Appearance of this object is very normal */
8046                         flavor_k_ptr = k_ptr;
8047                 }
8048
8049
8050
8051                 attr = ((i + object_top == object_cur) ? cursor : attr);
8052
8053                 if (!k_ptr->flavor || k_ptr->aware)
8054                 {
8055                         /* Tidy name */
8056                         strip_name(o_name, k_idx);
8057                 }
8058                 else
8059                 {
8060                         /* Flavor name */
8061                         strcpy(o_name, k_name + flavor_k_ptr->flavor_name);
8062                 }
8063
8064                 /* Display the name */
8065                 c_prt(attr, o_name, row + i, col);
8066
8067                 /* Hack -- visual_list mode */
8068                 if (per_page == 1)
8069                 {
8070                         c_prt(attr, format("%02x/%02x", flavor_k_ptr->x_attr, flavor_k_ptr->x_char), row + i, (p_ptr->wizard || visual_only) ? 64 : 68);
8071                 }
8072                 if (p_ptr->wizard || visual_only)
8073                 {
8074                         c_prt(attr, format("%d", k_idx), row + i, 70);
8075                 }
8076
8077                 a = flavor_k_ptr->x_attr;
8078                 c = flavor_k_ptr->x_char;
8079
8080                 /* Display symbol */
8081                 Term_queue_bigchar(use_bigtile ? 76 : 77, row + i, a, c, 0, 0);
8082         }
8083
8084         /* Clear remaining lines */
8085         for (; i < per_page; i++)
8086         {
8087                 Term_erase(col, row + i, 255);
8088         }
8089 }
8090
8091 /*
8092  * Describe fake object
8093  */
8094 static void desc_obj_fake(int k_idx)
8095 {
8096         object_type *o_ptr;
8097         object_type object_type_body;
8098
8099         /* Get local object */
8100         o_ptr = &object_type_body;
8101
8102         /* Wipe the object */
8103         object_wipe(o_ptr);
8104
8105         /* Create the artifact */
8106         object_prep(o_ptr, k_idx);
8107
8108         /* It's fully know */
8109         o_ptr->ident |= IDENT_KNOWN;
8110
8111         /* Track the object */
8112         /* object_actual_track(o_ptr); */
8113
8114         /* Hack - mark as fake */
8115         /* term_obj_real = FALSE; */
8116
8117         /* Hack -- Handle stuff */
8118         handle_stuff();
8119
8120         if (!screen_object(o_ptr, SCROBJ_FAKE_OBJECT | SCROBJ_FORCE_DETAIL))
8121         {
8122 #ifdef JP
8123                 msg_print("ÆäËÊѤï¤Ã¤¿¤È¤³¤í¤Ï¤Ê¤¤¤è¤¦¤À¡£");
8124 #else
8125                 msg_print("You see nothing special.");
8126 #endif
8127                 msg_print(NULL);
8128         }
8129 }
8130
8131
8132
8133 /*
8134  * Display known objects
8135  */
8136 static void do_cmd_knowledge_objects(bool *need_redraw, bool visual_only, int direct_k_idx)
8137 {
8138         int i, len, max;
8139         int grp_cur, grp_top, old_grp_cur;
8140         int object_old, object_cur, object_top;
8141         int grp_cnt, grp_idx[100];
8142         int object_cnt;
8143         int *object_idx;
8144
8145         int column = 0;
8146         bool flag;
8147         bool redraw;
8148
8149         bool visual_list = FALSE;
8150         byte attr_top = 0, char_left = 0;
8151
8152         int browser_rows;
8153         int wid, hgt;
8154
8155         byte mode;
8156
8157         /* Get size */
8158         Term_get_size(&wid, &hgt);
8159
8160         browser_rows = hgt - 8;
8161
8162         /* Allocate the "object_idx" array */
8163         C_MAKE(object_idx, max_k_idx, int);
8164
8165         max = 0;
8166         grp_cnt = 0;
8167
8168         if (direct_k_idx < 0)
8169         {
8170                 mode = visual_only ? 0x03 : 0x01;
8171
8172                 /* Check every group */
8173                 for (i = 0; object_group_text[i] != NULL; i++)
8174                 {
8175                         /* Measure the label */
8176                         len = strlen(object_group_text[i]);
8177
8178                         /* Save the maximum length */
8179                         if (len > max) max = len;
8180
8181                         /* See if any monsters are known */
8182                         if (collect_objects(i, object_idx, mode))
8183                         {
8184                                 /* Build a list of groups with known monsters */
8185                                 grp_idx[grp_cnt++] = i;
8186                         }
8187                 }
8188
8189                 object_old = -1;
8190                 object_cnt = 0;
8191         }
8192         else
8193         {
8194                 object_kind *k_ptr = &k_info[direct_k_idx];
8195                 object_kind *flavor_k_ptr;
8196
8197                 if (k_ptr->flavor)
8198                 {
8199                         /* Appearance of this object is shuffled */
8200                         flavor_k_ptr = &k_info[k_ptr->flavor];
8201                 }
8202                 else
8203                 {
8204                         /* Appearance of this object is very normal */
8205                         flavor_k_ptr = k_ptr;
8206                 }
8207
8208                 object_idx[0] = direct_k_idx;
8209                 object_old = direct_k_idx;
8210                 object_cnt = 1;
8211
8212                 /* Terminate the list */
8213                 object_idx[1] = -1;
8214
8215                 (void)visual_mode_command('v', &visual_list, browser_rows - 1, wid - (max + 3),
8216                         &attr_top, &char_left, &flavor_k_ptr->x_attr, &flavor_k_ptr->x_char, need_redraw);
8217         }
8218
8219         /* Terminate the list */
8220         grp_idx[grp_cnt] = -1;
8221
8222         old_grp_cur = -1;
8223         grp_cur = grp_top = 0;
8224         object_cur = object_top = 0;
8225
8226         flag = FALSE;
8227         redraw = TRUE;
8228
8229         mode = visual_only ? 0x02 : 0x00;
8230
8231         while (!flag)
8232         {
8233                 char ch;
8234                 object_kind *k_ptr, *flavor_k_ptr;
8235
8236                 if (redraw)
8237                 {
8238                         clear_from(0);
8239
8240 #ifdef JP
8241                         prt(format("%s - ¥¢¥¤¥Æ¥à", !visual_only ? "Ãμ±" : "ɽ¼¨"), 2, 0);
8242                         if (direct_k_idx < 0) prt("¥°¥ë¡¼¥×", 4, 0);
8243                         prt("̾Á°", 4, max + 3);
8244                         if (p_ptr->wizard || visual_only) prt("Idx", 4, 70);
8245                         prt("ʸ»ú", 4, 74);
8246 #else
8247                         prt(format("%s - objects", !visual_only ? "Knowledge" : "Visuals"), 2, 0);
8248                         if (direct_k_idx < 0) prt("Group", 4, 0);
8249                         prt("Name", 4, max + 3);
8250                         if (p_ptr->wizard || visual_only) prt("Idx", 4, 70);
8251                         prt("Sym", 4, 75);
8252 #endif
8253
8254                         for (i = 0; i < 78; i++)
8255                         {
8256                                 Term_putch(i, 5, TERM_WHITE, '=');
8257                         }
8258
8259                         if (direct_k_idx < 0)
8260                         {
8261                                 for (i = 0; i < browser_rows; i++)
8262                                 {
8263                                         Term_putch(max + 1, 6 + i, TERM_WHITE, '|');
8264                                 }
8265                         }
8266
8267                         redraw = FALSE;
8268                 }
8269
8270                 if (direct_k_idx < 0)
8271                 {
8272                         /* Scroll group list */
8273                         if (grp_cur < grp_top) grp_top = grp_cur;
8274                         if (grp_cur >= grp_top + browser_rows) grp_top = grp_cur - browser_rows + 1;
8275
8276                         /* Display a list of object groups */
8277                         display_group_list(0, 6, max, browser_rows, grp_idx, object_group_text, grp_cur, grp_top);
8278
8279                         if (old_grp_cur != grp_cur)
8280                         {
8281                                 old_grp_cur = grp_cur;
8282
8283                                 /* Get a list of objects in the current group */
8284                                 object_cnt = collect_objects(grp_idx[grp_cur], object_idx, mode);
8285                         }
8286
8287                         /* Scroll object list */
8288                         while (object_cur < object_top)
8289                                 object_top = MAX(0, object_top - browser_rows/2);
8290                         while (object_cur >= object_top + browser_rows)
8291                                 object_top = MIN(object_cnt - browser_rows, object_top + browser_rows/2);
8292                 }
8293
8294                 if (!visual_list)
8295                 {
8296                         /* Display a list of objects in the current group */
8297                         display_object_list(max + 3, 6, browser_rows, object_idx, object_cur, object_top, visual_only);
8298                 }
8299                 else
8300                 {
8301                         object_top = object_cur;
8302
8303                         /* Display a list of objects in the current group */
8304                         display_object_list(max + 3, 6, 1, object_idx, object_cur, object_top, visual_only);
8305
8306                         /* Display visual list below first object */
8307                         display_visual_list(max + 3, 7, browser_rows-1, wid - (max + 3), attr_top, char_left);
8308                 }
8309
8310                 /* Get the current object */
8311                 k_ptr = &k_info[object_idx[object_cur]];
8312
8313                 if (k_ptr->flavor)
8314                 {
8315                         /* Appearance of this object is shuffled */
8316                         flavor_k_ptr = &k_info[k_ptr->flavor];
8317                 }
8318                 else
8319                 {
8320                         /* Appearance of this object is very normal */
8321                         flavor_k_ptr = k_ptr;
8322                 }
8323
8324                 /* Prompt */
8325 #ifdef JP
8326                 prt(format("<Êý¸þ>%s%s%s, ESC",
8327                         (!visual_list && !visual_only) ? ", 'r'¤Ç¾ÜºÙ¤ò¸«¤ë" : "",
8328                         visual_list ? ", ENTER¤Ç·èÄê" : ", 'v'¤Ç¥·¥ó¥Ü¥ëÊѹ¹",
8329                         (attr_idx || char_idx) ? ", 'c', 'p'¤Ç¥Ú¡¼¥¹¥È" : ", 'c'¤Ç¥³¥Ô¡¼"),
8330                         hgt - 1, 0);
8331 #else
8332                 prt(format("<dir>%s%s%s, ESC",
8333                         (!visual_list && !visual_only) ? ", 'r' to recall" : "",
8334                         visual_list ? ", ENTER to accept" : ", 'v' for visuals",
8335                         (attr_idx || char_idx) ? ", 'c', 'p' to paste" : ", 'c' to copy"),
8336                         hgt - 1, 0);
8337 #endif
8338
8339                 if (!visual_only)
8340                 {
8341                         /* Mega Hack -- track this object */
8342                         if (object_cnt) object_kind_track(object_idx[object_cur]);
8343
8344                         /* The "current" object changed */
8345                         if (object_old != object_idx[object_cur])
8346                         {
8347                                 /* Hack -- handle stuff */
8348                                 handle_stuff();
8349
8350                                 /* Remember the "current" object */
8351                                 object_old = object_idx[object_cur];
8352                         }
8353                 }
8354
8355                 if (visual_list)
8356                 {
8357                         place_visual_list_cursor(max + 3, 7, flavor_k_ptr->x_attr, flavor_k_ptr->x_char, attr_top, char_left);
8358                 }
8359                 else if (!column)
8360                 {
8361                         Term_gotoxy(0, 6 + (grp_cur - grp_top));
8362                 }
8363                 else
8364                 {
8365                         Term_gotoxy(max + 3, 6 + (object_cur - object_top));
8366                 }
8367
8368                 ch = inkey();
8369
8370                 /* Do visual mode command if needed */
8371                 if (visual_mode_command(ch, &visual_list, browser_rows-1, wid - (max + 3), &attr_top, &char_left, &flavor_k_ptr->x_attr, &flavor_k_ptr->x_char, need_redraw))
8372                 {
8373                         if (direct_k_idx >= 0)
8374                         {
8375                                 switch (ch)
8376                                 {
8377                                 case '\n':
8378                                 case '\r':
8379                                 case ESCAPE:
8380                                         flag = TRUE;
8381                                         break;
8382                                 }
8383                         }
8384                         continue;
8385                 }
8386
8387                 switch (ch)
8388                 {
8389                         case ESCAPE:
8390                         {
8391                                 flag = TRUE;
8392                                 break;
8393                         }
8394
8395                         case 'R':
8396                         case 'r':
8397                         {
8398                                 /* Recall on screen */
8399                                 if (!visual_list && !visual_only && (grp_cnt > 0))
8400                                 {
8401                                         desc_obj_fake(object_idx[object_cur]);
8402                                         redraw = TRUE;
8403                                 }
8404                                 break;
8405                         }
8406
8407                         default:
8408                         {
8409                                 /* Move the cursor */
8410                                 browser_cursor(ch, &column, &grp_cur, grp_cnt, &object_cur, object_cnt);
8411                                 break;
8412                         }
8413                 }
8414         }
8415
8416         /* Free the "object_idx" array */
8417         C_KILL(object_idx, max_k_idx, int);
8418 }
8419
8420
8421 /*
8422  * Display the features in a group.
8423  */
8424 static void display_feature_list(int col, int row, int per_page, int *feat_idx,
8425         int feat_cur, int feat_top, bool visual_only, int lighting_level)
8426 {
8427         int lit_col[F_LIT_MAX], i, j;
8428         int f_idx_col = use_bigtile ? 62 : 64;
8429
8430         /* Correct columns 1 and 4 */
8431         lit_col[F_LIT_STANDARD] = use_bigtile ? (71 - F_LIT_MAX) : 71;
8432         for (i = F_LIT_NS_BEGIN; i < F_LIT_MAX; i++)
8433                 lit_col[i] = lit_col[F_LIT_STANDARD] + 2 + (i - F_LIT_NS_BEGIN) * 2 + (use_bigtile ? i : 0);
8434
8435         /* Display lines until done */
8436         for (i = 0; i < per_page && (feat_idx[feat_top + i] >= 0); i++)
8437         {
8438                 byte attr;
8439
8440                 /* Get the index */
8441                 int f_idx = feat_idx[feat_top + i];
8442
8443                 /* Access the index */
8444                 feature_type *f_ptr = &f_info[f_idx];
8445
8446                 int row_i = row + i;
8447
8448                 /* Choose a color */
8449                 attr = ((i + feat_top == feat_cur) ? TERM_L_BLUE : TERM_WHITE);
8450
8451                 /* Display the name */
8452                 c_prt(attr, f_name + f_ptr->name, row_i, col);
8453
8454                 /* Hack -- visual_list mode */
8455                 if (per_page == 1)
8456                 {
8457                         /* Display lighting level */
8458                         c_prt(attr, format("(%s)", lighting_level_str[lighting_level]), row_i, col + 1 + strlen(f_name + f_ptr->name));
8459
8460                         c_prt(attr, format("%02x/%02x", f_ptr->x_attr[lighting_level], f_ptr->x_char[lighting_level]), row_i, f_idx_col - ((p_ptr->wizard || visual_only) ? 6 : 2));
8461                 }
8462                 if (p_ptr->wizard || visual_only)
8463                 {
8464                         c_prt(attr, format("%d", f_idx), row_i, f_idx_col);
8465                 }
8466
8467                 /* Display symbol */
8468                 Term_queue_bigchar(lit_col[F_LIT_STANDARD], row_i, f_ptr->x_attr[F_LIT_STANDARD], f_ptr->x_char[F_LIT_STANDARD], 0, 0);
8469
8470                 Term_putch(lit_col[F_LIT_NS_BEGIN], row_i, TERM_SLATE, '(');
8471                 for (j = F_LIT_NS_BEGIN + 1; j < F_LIT_MAX; j++)
8472                 {
8473                         Term_putch(lit_col[j], row_i, TERM_SLATE, '/');
8474                 }
8475                 Term_putch(lit_col[F_LIT_MAX - 1] + (use_bigtile ? 3 : 2), row_i, TERM_SLATE, ')');
8476
8477                 /* Mega-hack -- Use non-standard colour */
8478                 for (j = F_LIT_NS_BEGIN; j < F_LIT_MAX; j++)
8479                 {
8480                         Term_queue_bigchar(lit_col[j] + 1, row_i, f_ptr->x_attr[j], f_ptr->x_char[j], 0, 0);
8481                 }
8482         }
8483
8484         /* Clear remaining lines */
8485         for (; i < per_page; i++)
8486         {
8487                 Term_erase(col, row + i, 255);
8488         }
8489 }
8490
8491
8492 /*
8493  * Interact with feature visuals.
8494  */
8495 static void do_cmd_knowledge_features(bool *need_redraw, bool visual_only, int direct_f_idx, int *lighting_level)
8496 {
8497         int i, len, max;
8498         int grp_cur, grp_top, old_grp_cur;
8499         int feat_cur, feat_top;
8500         int grp_cnt, grp_idx[100];
8501         int feat_cnt;
8502         int *feat_idx;
8503
8504         int column = 0;
8505         bool flag;
8506         bool redraw;
8507
8508         bool visual_list = FALSE;
8509         byte attr_top = 0, char_left = 0;
8510
8511         int browser_rows;
8512         int wid, hgt;
8513
8514         byte attr_old[F_LIT_MAX];
8515         byte char_old[F_LIT_MAX];
8516         byte *cur_attr_ptr, *cur_char_ptr;
8517
8518         C_WIPE(attr_old, F_LIT_MAX, byte);
8519         C_WIPE(char_old, F_LIT_MAX, byte);
8520
8521         /* Get size */
8522         Term_get_size(&wid, &hgt);
8523
8524         browser_rows = hgt - 8;
8525
8526         /* Allocate the "feat_idx" array */
8527         C_MAKE(feat_idx, max_f_idx, int);
8528
8529         max = 0;
8530         grp_cnt = 0;
8531
8532         if (direct_f_idx < 0)
8533         {
8534                 /* Check every group */
8535                 for (i = 0; feature_group_text[i] != NULL; i++)
8536                 {
8537                         /* Measure the label */
8538                         len = strlen(feature_group_text[i]);
8539
8540                         /* Save the maximum length */
8541                         if (len > max) max = len;
8542
8543                         /* See if any features are known */
8544                         if (collect_features(i, feat_idx, 0x01))
8545                         {
8546                                 /* Build a list of groups with known features */
8547                                 grp_idx[grp_cnt++] = i;
8548                         }
8549                 }
8550
8551                 feat_cnt = 0;
8552         }
8553         else
8554         {
8555                 feature_type *f_ptr = &f_info[direct_f_idx];
8556
8557                 feat_idx[0] = direct_f_idx;
8558                 feat_cnt = 1;
8559
8560                 /* Terminate the list */
8561                 feat_idx[1] = -1;
8562
8563                 (void)visual_mode_command('v', &visual_list, browser_rows - 1, wid - (max + 3),
8564                         &attr_top, &char_left, &f_ptr->x_attr[*lighting_level], &f_ptr->x_char[*lighting_level], need_redraw);
8565
8566                 for (i = 0; i < F_LIT_MAX; i++)
8567                 {
8568                         attr_old[i] = f_ptr->x_attr[i];
8569                         char_old[i] = f_ptr->x_char[i];
8570                 }
8571         }
8572
8573         /* Terminate the list */
8574         grp_idx[grp_cnt] = -1;
8575
8576         old_grp_cur = -1;
8577         grp_cur = grp_top = 0;
8578         feat_cur = feat_top = 0;
8579
8580         flag = FALSE;
8581         redraw = TRUE;
8582
8583         while (!flag)
8584         {
8585                 char ch;
8586                 feature_type *f_ptr;
8587
8588                 if (redraw)
8589                 {
8590                         clear_from(0);
8591
8592 #ifdef JP
8593                         prt("ɽ¼¨ - ÃÏ·Á", 2, 0);
8594                         if (direct_f_idx < 0) prt("¥°¥ë¡¼¥×", 4, 0);
8595                         prt("̾Á°", 4, max + 3);
8596                         if (use_bigtile)
8597                         {
8598                                 if (p_ptr->wizard || visual_only) prt("Idx", 4, 62);
8599                                 prt("ʸ»ú ( l/ d)", 4, 66);
8600                         }
8601                         else
8602                         {
8603                                 if (p_ptr->wizard || visual_only) prt("Idx", 4, 64);
8604                                 prt("ʸ»ú (l/d)", 4, 68);
8605                         }
8606 #else
8607                         prt("Visuals - features", 2, 0);
8608                         if (direct_f_idx < 0) prt("Group", 4, 0);
8609                         prt("Name", 4, max + 3);
8610                         if (use_bigtile)
8611                         {
8612                                 if (p_ptr->wizard || visual_only) prt("Idx", 4, 62);
8613                                 prt("Sym ( l/ d)", 4, 67);
8614                         }
8615                         else
8616                         {
8617                                 if (p_ptr->wizard || visual_only) prt("Idx", 4, 64);
8618                                 prt("Sym (l/d)", 4, 69);
8619                         }
8620 #endif
8621
8622                         for (i = 0; i < 78; i++)
8623                         {
8624                                 Term_putch(i, 5, TERM_WHITE, '=');
8625                         }
8626
8627                         if (direct_f_idx < 0)
8628                         {
8629                                 for (i = 0; i < browser_rows; i++)
8630                                 {
8631                                         Term_putch(max + 1, 6 + i, TERM_WHITE, '|');
8632                                 }
8633                         }
8634
8635                         redraw = FALSE;
8636                 }
8637
8638                 if (direct_f_idx < 0)
8639                 {
8640                         /* Scroll group list */
8641                         if (grp_cur < grp_top) grp_top = grp_cur;
8642                         if (grp_cur >= grp_top + browser_rows) grp_top = grp_cur - browser_rows + 1;
8643
8644                         /* Display a list of feature groups */
8645                         display_group_list(0, 6, max, browser_rows, grp_idx, feature_group_text, grp_cur, grp_top);
8646
8647                         if (old_grp_cur != grp_cur)
8648                         {
8649                                 old_grp_cur = grp_cur;
8650
8651                                 /* Get a list of features in the current group */
8652                                 feat_cnt = collect_features(grp_idx[grp_cur], feat_idx, 0x00);
8653                         }
8654
8655                         /* Scroll feature list */
8656                         while (feat_cur < feat_top)
8657                                 feat_top = MAX(0, feat_top - browser_rows/2);
8658                         while (feat_cur >= feat_top + browser_rows)
8659                                 feat_top = MIN(feat_cnt - browser_rows, feat_top + browser_rows/2);
8660                 }
8661
8662                 if (!visual_list)
8663                 {
8664                         /* Display a list of features in the current group */
8665                         display_feature_list(max + 3, 6, browser_rows, feat_idx, feat_cur, feat_top, visual_only, F_LIT_STANDARD);
8666                 }
8667                 else
8668                 {
8669                         feat_top = feat_cur;
8670
8671                         /* Display a list of features in the current group */
8672                         display_feature_list(max + 3, 6, 1, feat_idx, feat_cur, feat_top, visual_only, *lighting_level);
8673
8674                         /* Display visual list below first object */
8675                         display_visual_list(max + 3, 7, browser_rows-1, wid - (max + 3), attr_top, char_left);
8676                 }
8677
8678                 /* Prompt */
8679 #ifdef JP
8680                 prt(format("<Êý¸þ>%s, 'd'¤Çɸ½à¸÷¸»¸ú²Ì%s, ESC",
8681                         visual_list ? ", ENTER¤Ç·èÄê, 'a'¤ÇÂоÝÌÀÅÙÊѹ¹" : ", 'v'¤Ç¥·¥ó¥Ü¥ëÊѹ¹",
8682                         (attr_idx || char_idx) ? ", 'c', 'p'¤Ç¥Ú¡¼¥¹¥È" : ", 'c'¤Ç¥³¥Ô¡¼"),
8683                         hgt - 1, 0);
8684 #else
8685                 prt(format("<dir>%s, 'd' for default lighting%s, ESC",
8686                         visual_list ? ", ENTER to accept, 'a' for lighting level" : ", 'v' for visuals",
8687                         (attr_idx || char_idx) ? ", 'c', 'p' to paste" : ", 'c' to copy"),
8688                         hgt - 1, 0);
8689 #endif
8690
8691                 /* Get the current feature */
8692                 f_ptr = &f_info[feat_idx[feat_cur]];
8693                 cur_attr_ptr = &f_ptr->x_attr[*lighting_level];
8694                 cur_char_ptr = &f_ptr->x_char[*lighting_level];
8695
8696                 if (visual_list)
8697                 {
8698                         place_visual_list_cursor(max + 3, 7, *cur_attr_ptr, *cur_char_ptr, attr_top, char_left);
8699                 }
8700                 else if (!column)
8701                 {
8702                         Term_gotoxy(0, 6 + (grp_cur - grp_top));
8703                 }
8704                 else
8705                 {
8706                         Term_gotoxy(max + 3, 6 + (feat_cur - feat_top));
8707                 }
8708
8709                 ch = inkey();
8710
8711                 if (visual_list && ((ch == 'A') || (ch == 'a')))
8712                 {
8713                         int prev_lighting_level = *lighting_level;
8714
8715                         if (ch == 'A')
8716                         {
8717                                 if (*lighting_level <= 0) *lighting_level = F_LIT_MAX - 1;
8718                                 else (*lighting_level)--;
8719                         }
8720                         else
8721                         {
8722                                 if (*lighting_level >= F_LIT_MAX - 1) *lighting_level = 0;
8723                                 else (*lighting_level)++;
8724                         }
8725
8726                         if (f_ptr->x_attr[prev_lighting_level] != f_ptr->x_attr[*lighting_level])
8727                                 attr_top = MAX(0, (f_ptr->x_attr[*lighting_level] & 0x7f) - 5);
8728
8729                         if (f_ptr->x_char[prev_lighting_level] != f_ptr->x_char[*lighting_level])
8730                                 char_left = MAX(0, f_ptr->x_char[*lighting_level] - 10);
8731
8732                         continue;
8733                 }
8734
8735                 else if ((ch == 'D') || (ch == 'd'))
8736                 {
8737                         byte prev_x_attr = f_ptr->x_attr[*lighting_level];
8738                         byte prev_x_char = f_ptr->x_char[*lighting_level];
8739
8740                         apply_default_feat_lighting(f_ptr->x_attr, f_ptr->x_char);
8741
8742                         if (visual_list)
8743                         {
8744                                 if (prev_x_attr != f_ptr->x_attr[*lighting_level])
8745                                          attr_top = MAX(0, (f_ptr->x_attr[*lighting_level] & 0x7f) - 5);
8746
8747                                 if (prev_x_char != f_ptr->x_char[*lighting_level])
8748                                         char_left = MAX(0, f_ptr->x_char[*lighting_level] - 10);
8749                         }
8750                         else *need_redraw = TRUE;
8751
8752                         continue;
8753                 }
8754
8755                 /* Do visual mode command if needed */
8756                 else if (visual_mode_command(ch, &visual_list, browser_rows-1, wid - (max + 3), &attr_top, &char_left, cur_attr_ptr, cur_char_ptr, need_redraw))
8757                 {
8758                         switch (ch)
8759                         {
8760                         /* Restore previous visual settings */
8761                         case ESCAPE:
8762                                 for (i = 0; i < F_LIT_MAX; i++)
8763                                 {
8764                                         f_ptr->x_attr[i] = attr_old[i];
8765                                         f_ptr->x_char[i] = char_old[i];
8766                                 }
8767
8768                                 /* Fall through */
8769
8770                         case '\n':
8771                         case '\r':
8772                                 if (direct_f_idx >= 0) flag = TRUE;
8773                                 else *lighting_level = F_LIT_STANDARD;
8774                                 break;
8775
8776                         /* Preserve current visual settings */
8777                         case 'V':
8778                         case 'v':
8779                                 for (i = 0; i < F_LIT_MAX; i++)
8780                                 {
8781                                         attr_old[i] = f_ptr->x_attr[i];
8782                                         char_old[i] = f_ptr->x_char[i];
8783                                 }
8784                                 *lighting_level = F_LIT_STANDARD;
8785                                 break;
8786
8787                         case 'C':
8788                         case 'c':
8789                                 if (!visual_list)
8790                                 {
8791                                         for (i = 0; i < F_LIT_MAX; i++)
8792                                         {
8793                                                 attr_idx_feat[i] = f_ptr->x_attr[i];
8794                                                 char_idx_feat[i] = f_ptr->x_char[i];
8795                                         }
8796                                 }
8797                                 break;
8798
8799                         case 'P':
8800                         case 'p':
8801                                 if (!visual_list)
8802                                 {
8803                                         /* Allow TERM_DARK text */
8804                                         for (i = F_LIT_NS_BEGIN; i < F_LIT_MAX; i++)
8805                                         {
8806                                                 if (attr_idx_feat[i] || (!(char_idx_feat[i] & 0x80) && char_idx_feat[i])) f_ptr->x_attr[i] = attr_idx_feat[i];
8807                                                 if (char_idx_feat[i]) f_ptr->x_char[i] = char_idx_feat[i];
8808                                         }
8809                                 }
8810                                 break;
8811                         }
8812                         continue;
8813                 }
8814
8815                 switch (ch)
8816                 {
8817                         case ESCAPE:
8818                         {
8819                                 flag = TRUE;
8820                                 break;
8821                         }
8822
8823                         default:
8824                         {
8825                                 /* Move the cursor */
8826                                 browser_cursor(ch, &column, &grp_cur, grp_cnt, &feat_cur, feat_cnt);
8827                                 break;
8828                         }
8829                 }
8830         }
8831
8832         /* Free the "feat_idx" array */
8833         C_KILL(feat_idx, max_f_idx, int);
8834 }
8835
8836
8837 /*
8838  * List wanted monsters
8839  */
8840 static void do_cmd_knowledge_kubi(void)
8841 {
8842         int i;
8843         FILE *fff;
8844         
8845         char file_name[1024];
8846         
8847         
8848         /* Open a new file */
8849         fff = my_fopen_temp(file_name, 1024);
8850         if (!fff) {
8851 #ifdef JP
8852             msg_format("°ì»þ¥Õ¥¡¥¤¥ë %s ¤òºîÀ®¤Ç¤­¤Þ¤»¤ó¤Ç¤·¤¿¡£", file_name);
8853 #else
8854             msg_format("Failed to create temporary file %s.", file_name);
8855 #endif
8856             msg_print(NULL);
8857             return;
8858         }
8859         
8860         if (fff)
8861         {
8862                 bool listed = FALSE;
8863
8864 #ifdef JP
8865                 fprintf(fff, "º£Æü¤Î¥¿¡¼¥²¥Ã¥È : %s\n", (p_ptr->today_mon ? r_name + r_info[p_ptr->today_mon].name : "ÉÔÌÀ"));
8866                 fprintf(fff, "\n");
8867                 fprintf(fff, "¾Þ¶â¼ó¥ê¥¹¥È\n");
8868 #else
8869                 fprintf(fff, "Today target : %s\n", (p_ptr->today_mon ? r_name + r_info[p_ptr->today_mon].name : "unknown"));
8870                 fprintf(fff, "\n");
8871                 fprintf(fff, "List of wanted monsters\n");
8872 #endif
8873                 fprintf(fff, "----------------------------------------------\n");
8874
8875                 for (i = 0; i < MAX_KUBI; i++)
8876                 {
8877                         if (kubi_r_idx[i] <= 10000)
8878                         {
8879                                 fprintf(fff,"%s\n", r_name + r_info[kubi_r_idx[i]].name);
8880
8881                                 listed = TRUE;
8882                         }
8883                 }
8884
8885                 if (!listed)
8886                 {
8887 #ifdef JP
8888                         fprintf(fff,"\n%s\n", "¾Þ¶â¼ó¤Ï¤â¤¦»Ä¤Ã¤Æ¤¤¤Þ¤»¤ó¡£");
8889 #else
8890                         fprintf(fff,"\n%s\n", "There is no more wanted monster.");
8891 #endif
8892                 }
8893         }
8894         
8895         /* Close the file */
8896         my_fclose(fff);
8897         
8898         /* Display the file contents */
8899 #ifdef JP
8900         show_file(TRUE, file_name, "¾Þ¶â¼ó¤Î°ìÍ÷", 0, 0);
8901 #else
8902         show_file(TRUE, file_name, "Wanted monsters", 0, 0);
8903 #endif
8904
8905         
8906         /* Remove the file */
8907         fd_kill(file_name);
8908 }
8909
8910 /*
8911  * List virtues & status
8912  */
8913 static void do_cmd_knowledge_virtues(void)
8914 {
8915         FILE *fff;
8916         
8917         char file_name[1024];
8918         
8919         
8920         /* Open a new file */
8921         fff = my_fopen_temp(file_name, 1024);
8922         if (!fff) {
8923 #ifdef JP
8924             msg_format("°ì»þ¥Õ¥¡¥¤¥ë %s ¤òºîÀ®¤Ç¤­¤Þ¤»¤ó¤Ç¤·¤¿¡£", file_name);
8925 #else
8926             msg_format("Failed to create temporary file %s.", file_name);
8927 #endif
8928             msg_print(NULL);
8929             return;
8930         }
8931         
8932         if (fff)
8933         {
8934 #ifdef JP
8935                 fprintf(fff, "¸½ºß¤Î°À­ : %s\n\n", your_alignment());
8936 #else
8937                 fprintf(fff, "Your alighnment : %s\n\n", your_alignment());
8938 #endif
8939                 dump_virtues(fff);
8940         }
8941         
8942         /* Close the file */
8943         my_fclose(fff);
8944         
8945         /* Display the file contents */
8946 #ifdef JP
8947         show_file(TRUE, file_name, "Ȭ¤Ä¤ÎÆÁ", 0, 0);
8948 #else
8949         show_file(TRUE, file_name, "Virtues", 0, 0);
8950 #endif
8951
8952         
8953         /* Remove the file */
8954         fd_kill(file_name);
8955 }
8956
8957 /*
8958 * Dungeon
8959 *
8960 */
8961 static void do_cmd_knowledge_dungeon(void)
8962 {
8963         FILE *fff;
8964         
8965         char file_name[1024];
8966         int i;
8967         
8968         
8969         /* Open a new file */
8970         fff = my_fopen_temp(file_name, 1024);
8971         if (!fff) {
8972 #ifdef JP
8973             msg_format("°ì»þ¥Õ¥¡¥¤¥ë %s ¤òºîÀ®¤Ç¤­¤Þ¤»¤ó¤Ç¤·¤¿¡£", file_name);
8974 #else
8975             msg_format("Failed to create temporary file %s.", file_name);
8976 #endif
8977             msg_print(NULL);
8978             return;
8979         }
8980         
8981         if (fff)
8982         {
8983                 for (i = 1; i < max_d_idx; i++)
8984                 {
8985                         bool seiha = FALSE;
8986
8987                         if (!d_info[i].maxdepth) continue;
8988                         if (!max_dlv[i]) continue;
8989                         if (d_info[i].final_guardian)
8990                         {
8991                                 if (!r_info[d_info[i].final_guardian].max_num) seiha = TRUE;
8992                         }
8993                         else if (max_dlv[i] == d_info[i].maxdepth) seiha = TRUE;
8994 #ifdef JP
8995                         fprintf(fff,"%c%-12s :  %3d ³¬\n", seiha ? '!' : ' ', d_name + d_info[i].name, max_dlv[i]);
8996 #else
8997                         fprintf(fff,"%c%-16s :  level %3d\n", seiha ? '!' : ' ', d_name + d_info[i].name, max_dlv[i]);
8998 #endif
8999                 }
9000         }
9001         
9002         /* Close the file */
9003         my_fclose(fff);
9004         
9005         /* Display the file contents */
9006 #ifdef JP
9007         show_file(TRUE, file_name, "º£¤Þ¤Ç¤ËÆþ¤Ã¤¿¥À¥ó¥¸¥ç¥ó", 0, 0);
9008 #else
9009         show_file(TRUE, file_name, "Dungeon", 0, 0);
9010 #endif
9011
9012         
9013         /* Remove the file */
9014         fd_kill(file_name);
9015 }
9016
9017 /*
9018 * List virtues & status
9019 *
9020 */
9021 static void do_cmd_knowledge_stat(void)
9022 {
9023         FILE *fff;
9024         
9025         char file_name[1024];
9026         int percent, v_nr;
9027         
9028         /* Open a new file */
9029         fff = my_fopen_temp(file_name, 1024);
9030         if (!fff) {
9031 #ifdef JP
9032             msg_format("°ì»þ¥Õ¥¡¥¤¥ë %s ¤òºîÀ®¤Ç¤­¤Þ¤»¤ó¤Ç¤·¤¿¡£", file_name);
9033 #else
9034             msg_format("Failed to create temporary file %s.", file_name);
9035 #endif
9036             msg_print(NULL);
9037             return;
9038         }
9039         
9040         if (fff)
9041         {
9042                 percent = (int)(((long)p_ptr->player_hp[PY_MAX_LEVEL - 1] * 200L) /
9043                         (2 * p_ptr->hitdie +
9044                         ((PY_MAX_LEVEL - 1+3) * (p_ptr->hitdie + 1))));
9045
9046 #ifdef JP
9047                 if (p_ptr->knowledge & KNOW_HPRATE) fprintf(fff, "¸½ºß¤ÎÂÎÎÏ¥é¥ó¥¯ : %d/100\n\n", percent);
9048                 else fprintf(fff, "¸½ºß¤ÎÂÎÎÏ¥é¥ó¥¯ : ???\n\n");
9049                 fprintf(fff, "ǽÎϤκÇÂçÃÍ\n\n");
9050 #else
9051                 if (p_ptr->knowledge & KNOW_HPRATE) fprintf(fff, "Your current Life Rating is %d/100.\n\n", percent);
9052                 else fprintf(fff, "Your current Life Rating is ???.\n\n");
9053                 fprintf(fff, "Limits of maximum stats\n\n");
9054 #endif
9055                 for (v_nr = 0; v_nr < 6; v_nr++)
9056                 {
9057                         if ((p_ptr->knowledge & KNOW_STAT) || p_ptr->stat_max[v_nr] == p_ptr->stat_max_max[v_nr]) fprintf(fff, "%s 18/%d\n", stat_names[v_nr], p_ptr->stat_max_max[v_nr]-18);
9058                         else fprintf(fff, "%s ???\n", stat_names[v_nr]);
9059                 }
9060         }
9061
9062         dump_yourself(fff);
9063
9064         /* Close the file */
9065         my_fclose(fff);
9066         
9067         /* Display the file contents */
9068 #ifdef JP
9069         show_file(TRUE, file_name, "¼«Ê¬¤Ë´Ø¤¹¤ë¾ðÊó", 0, 0);
9070 #else
9071         show_file(TRUE, file_name, "HP-rate & Max stat", 0, 0);
9072 #endif
9073
9074         
9075         /* Remove the file */
9076         fd_kill(file_name);
9077 }
9078
9079
9080 /*
9081  * Print all active quests
9082  */
9083 static void do_cmd_knowledge_quests_current(FILE *fff)
9084 {
9085         char tmp_str[120];
9086         char rand_tmp_str[120] = "\0";
9087         char name[80];
9088         monster_race *r_ptr;
9089         int i;
9090         int rand_level = 100;
9091         int total = 0;
9092
9093 #ifdef JP
9094         fprintf(fff, "¡Ô¿ë¹ÔÃæ¤Î¥¯¥¨¥¹¥È¡Õ\n");
9095 #else
9096         fprintf(fff, "< Current Quest >\n");
9097 #endif
9098
9099         for (i = 1; i < max_quests; i++)
9100         {
9101                 if ((quest[i].status == QUEST_STATUS_TAKEN) || (quest[i].status == QUEST_STATUS_COMPLETED))
9102                 {
9103                         /* Set the quest number temporary */
9104                         int old_quest = p_ptr->inside_quest;
9105                         int j;
9106
9107                         /* Clear the text */
9108                         for (j = 0; j < 10; j++) quest_text[j][0] = '\0';
9109                         quest_text_line = 0;
9110
9111                         p_ptr->inside_quest = i;
9112
9113                         /* Get the quest text */
9114                         init_flags = INIT_SHOW_TEXT;
9115
9116                         process_dungeon_file("q_info.txt", 0, 0, 0, 0);
9117
9118                         /* Reset the old quest number */
9119                         p_ptr->inside_quest = old_quest;
9120
9121                         /* No info from "silent" quests */
9122                         if (quest[i].flags & QUEST_FLAG_SILENT) continue;
9123
9124                         total++;
9125
9126                         if (quest[i].type != QUEST_TYPE_RANDOM)
9127                         {
9128                                 char note[80] = "\0";
9129
9130                                 if (quest[i].status == QUEST_STATUS_TAKEN)
9131                                 {
9132                                         switch (quest[i].type)
9133                                         {
9134                                         case QUEST_TYPE_KILL_LEVEL:
9135                                         case QUEST_TYPE_KILL_ANY_LEVEL:
9136                                                 r_ptr = &r_info[quest[i].r_idx];
9137                                                 strcpy(name, r_name + r_ptr->name);
9138                                                 if (quest[i].max_num > 1)
9139                                                 {
9140 #ifdef JP
9141                                                         sprintf(note," - %d ÂΤÎ%s¤òÅݤ¹¡£(¤¢¤È %d ÂÎ)",
9142                                                                 quest[i].max_num, name, quest[i].max_num - quest[i].cur_num);
9143 #else
9144                                                         plural_aux(name);
9145                                                         sprintf(note," - kill %d %s, have killed %d.",
9146                                                                 quest[i].max_num, name, quest[i].cur_num);
9147 #endif
9148                                                 }
9149                                                 else
9150 #ifdef JP
9151                                                         sprintf(note," - %s¤òÅݤ¹¡£",name);
9152 #else
9153                                                         sprintf(note," - kill %s.",name);
9154 #endif
9155                                                 break;
9156
9157                                         case QUEST_TYPE_FIND_ARTIFACT:
9158                                                 strcpy(name, a_name + a_info[quest[i].k_idx].name);
9159 #ifdef JP
9160                                                 sprintf(note," - %s¤ò¸«¤Ä¤±½Ð¤¹¡£", name);
9161 #else
9162                                                 sprintf(note," - Find out %s.", name);
9163 #endif
9164                                                 break;
9165
9166                                         case QUEST_TYPE_FIND_EXIT:
9167 #ifdef JP
9168                                                 sprintf(note," - Ãµº÷¤¹¤ë¡£");
9169 #else
9170                                                 sprintf(note," - Search.");
9171 #endif
9172                                                 break;
9173
9174                                         case QUEST_TYPE_KILL_NUMBER:
9175 #ifdef JP
9176                                                 sprintf(note," - %d ÂΤΥâ¥ó¥¹¥¿¡¼¤òÅݤ¹¡£(¤¢¤È %d ÂÎ)",
9177                                                         quest[i].max_num, quest[i].max_num - quest[i].cur_num);
9178 #else
9179                                                 sprintf(note," - Kill %d monsters, have killed %d.",
9180                                                         quest[i].max_num, quest[i].cur_num);
9181 #endif
9182                                                 break;
9183
9184                                         case QUEST_TYPE_KILL_ALL:
9185 #ifdef JP
9186                                                 sprintf(note," - Á´¤Æ¤Î¥â¥ó¥¹¥¿¡¼¤òÅݤ¹¡£");
9187 #else
9188                                                 sprintf(note," - Kill all monsters.");
9189 #endif
9190                                                 break;
9191                                         }
9192                                 }
9193
9194                                 /* Print the quest info */
9195 #ifdef JP
9196                                 sprintf(tmp_str, "  %s (´í¸±ÅÙ:%d³¬ÁêÅö)%s\n",
9197                                         quest[i].name, quest[i].level, note);
9198 #else
9199                                 sprintf(tmp_str, "  %s (Danger level: %d)%s\n",
9200                                         quest[i].name, quest[i].level, note);
9201 #endif
9202
9203                                 fprintf(fff, tmp_str);
9204
9205                                 if (quest[i].status == QUEST_STATUS_COMPLETED)
9206                                 {
9207 #ifdef JP
9208                                         sprintf(tmp_str, "    ¥¯¥¨¥¹¥ÈãÀ® - ¤Þ¤ÀÊó½·¤ò¼õ¤±¤È¤Ã¤Æ¤Ê¤¤¡£\n");
9209 #else
9210                                         sprintf(tmp_str, "    Quest Completed - Unrewarded\n");
9211 #endif
9212                                         fprintf(fff, tmp_str);
9213                                 }
9214                                 else
9215                                 {
9216                                         j = 0;
9217
9218                                         while (quest_text[j][0] && j < 10)
9219                                         {
9220                                                 fprintf(fff, "    %s\n", quest_text[j]);
9221                                                 j++;
9222                                         }
9223                                 }
9224                         }
9225                         else if (quest[i].level < rand_level) /* QUEST_TYPE_RANDOM */
9226                         {
9227                                 /* New random */
9228                                 rand_level = quest[i].level;
9229
9230                                 if (max_dlv[DUNGEON_ANGBAND] >= rand_level)
9231                                 {
9232                                         /* Print the quest info */
9233                                         r_ptr = &r_info[quest[i].r_idx];
9234                                         strcpy(name, r_name + r_ptr->name);
9235
9236                                         if (quest[i].max_num > 1)
9237                                         {
9238 #ifdef JP
9239                                                 sprintf(rand_tmp_str,"  %s (%d ³¬) - %d ÂΤÎ%s¤òÅݤ¹¡£(¤¢¤È %d ÂÎ)\n",
9240                                                         quest[i].name, quest[i].level,
9241                                                         quest[i].max_num, name, quest[i].max_num - quest[i].cur_num);
9242 #else
9243                                                 plural_aux(name);
9244
9245                                                 sprintf(rand_tmp_str,"  %s (Dungeon level: %d)\n  Kill %d %s, have killed %d.\n",
9246                                                         quest[i].name, quest[i].level,
9247                                                         quest[i].max_num, name, quest[i].cur_num);
9248 #endif
9249                                         }
9250                                         else
9251                                         {
9252 #ifdef JP
9253                                                 sprintf(rand_tmp_str,"  %s (%d ³¬) - %s¤òÅݤ¹¡£\n",
9254                                                         quest[i].name, quest[i].level, name);
9255 #else
9256                                                 sprintf(rand_tmp_str,"  %s (Dungeon level: %d)\n  Kill %s.\n",
9257                                                         quest[i].name, quest[i].level, name);
9258 #endif
9259                                         }
9260                                 }
9261                         }
9262                 }
9263         }
9264
9265         /* Print the current random quest  */
9266         if (rand_tmp_str[0]) fprintf(fff, rand_tmp_str);
9267
9268 #ifdef JP
9269         if (!total) fprintf(fff, "  ¤Ê¤·\n");
9270 #else
9271         if (!total) fprintf(fff, "  Nothing.\n");
9272 #endif
9273 }
9274
9275
9276 /*
9277  * Print all finished quests
9278  */
9279 void do_cmd_knowledge_quests_completed(FILE *fff, int quest_num[])
9280 {
9281         char tmp_str[120];
9282         int i;
9283         int total = 0;
9284
9285 #ifdef JP
9286         fprintf(fff, "¡ÔãÀ®¤·¤¿¥¯¥¨¥¹¥È¡Õ\n");
9287 #else
9288         fprintf(fff, "< Completed Quest >\n");
9289 #endif
9290         for (i = 1; i < max_quests; i++)
9291         {
9292                 int q_idx = quest_num[i];
9293
9294                 if (quest[q_idx].status == QUEST_STATUS_FINISHED)
9295                 {
9296                         if (is_fixed_quest_idx(q_idx))
9297                         {
9298                                 /* Set the quest number temporary */
9299                                 int old_quest = p_ptr->inside_quest;
9300
9301                                 p_ptr->inside_quest = q_idx;
9302
9303                                 /* Get the quest */
9304                                 init_flags = INIT_ASSIGN;
9305
9306                                 process_dungeon_file("q_info.txt", 0, 0, 0, 0);
9307
9308                                 /* Reset the old quest number */
9309                                 p_ptr->inside_quest = old_quest;
9310
9311                                 /* No info from "silent" quests */
9312                                 if (quest[q_idx].flags & QUEST_FLAG_SILENT) continue;
9313                         }
9314
9315                         total++;
9316
9317                         if (!is_fixed_quest_idx(q_idx) && quest[q_idx].r_idx)
9318                         {
9319                                 /* Print the quest info */
9320
9321                                 if (quest[q_idx].complev == 0)
9322                                 {
9323                                         sprintf(tmp_str,
9324 #ifdef JP
9325                                                 "  %-40s (%3d³¬)            -   ÉÔÀᄀ\n",
9326 #else
9327                                                 "  %-40s (Dungeon level: %3d) - (Cancelled)\n",
9328 #endif
9329                                                 r_name+r_info[quest[q_idx].r_idx].name,
9330                                                 quest[q_idx].level);
9331                                 }
9332                                 else
9333                                 {
9334                                         sprintf(tmp_str,
9335 #ifdef JP
9336                                                 "  %-40s (%3d³¬)            - ¥ì¥Ù¥ë%2d\n",
9337 #else
9338                                                 "  %-40s (Dungeon level: %3d) - level %2d\n",
9339 #endif
9340                                                 r_name+r_info[quest[q_idx].r_idx].name,
9341                                                 quest[q_idx].level,
9342                                                 quest[q_idx].complev);
9343                                 }
9344                         }
9345                         else
9346                         {
9347                                 /* Print the quest info */
9348 #ifdef JP
9349                                 sprintf(tmp_str, "  %-40s (´í¸±ÅÙ:%3d³¬ÁêÅö) - ¥ì¥Ù¥ë%2d\n",
9350                                         quest[q_idx].name, quest[q_idx].level, quest[q_idx].complev);
9351 #else
9352                                 sprintf(tmp_str, "  %-40s (Danger  level: %3d) - level %2d\n",
9353                                         quest[q_idx].name, quest[q_idx].level, quest[q_idx].complev);
9354 #endif
9355                         }
9356
9357                         fprintf(fff, tmp_str);
9358                 }
9359         }
9360 #ifdef JP
9361         if (!total) fprintf(fff, "  ¤Ê¤·\n");
9362 #else
9363         if (!total) fprintf(fff, "  Nothing.\n");
9364 #endif
9365 }
9366
9367
9368 /*
9369  * Print all failed quests
9370  */
9371 void do_cmd_knowledge_quests_failed(FILE *fff, int quest_num[])
9372 {
9373         char tmp_str[120];
9374         int i;
9375         int total = 0;
9376
9377 #ifdef JP
9378         fprintf(fff, "¡Ô¼ºÇÔ¤·¤¿¥¯¥¨¥¹¥È¡Õ\n");
9379 #else
9380         fprintf(fff, "< Failed Quest >\n");
9381 #endif
9382         for (i = 1; i < max_quests; i++)
9383         {
9384                 int q_idx = quest_num[i];
9385
9386                 if ((quest[q_idx].status == QUEST_STATUS_FAILED_DONE) || (quest[q_idx].status == QUEST_STATUS_FAILED))
9387                 {
9388                         if (is_fixed_quest_idx(q_idx))
9389                         {
9390                                 /* Set the quest number temporary */
9391                                 int old_quest = p_ptr->inside_quest;
9392
9393                                 p_ptr->inside_quest = q_idx;
9394
9395                                 /* Get the quest text */
9396                                 init_flags = INIT_ASSIGN;
9397
9398                                 process_dungeon_file("q_info.txt", 0, 0, 0, 0);
9399
9400                                 /* Reset the old quest number */
9401                                 p_ptr->inside_quest = old_quest;
9402
9403                                 /* No info from "silent" quests */
9404                                 if (quest[q_idx].flags & QUEST_FLAG_SILENT) continue;
9405                         }
9406
9407                         total++;
9408
9409                         if (!is_fixed_quest_idx(q_idx) && quest[q_idx].r_idx)
9410                         {
9411                                 /* Print the quest info */
9412 #ifdef JP
9413                                 sprintf(tmp_str, "  %-40s (%3d³¬)            - ¥ì¥Ù¥ë%2d\n",
9414                                         r_name+r_info[quest[q_idx].r_idx].name, quest[q_idx].level, quest[q_idx].complev);
9415 #else
9416                                 sprintf(tmp_str, "  %-40s (Dungeon level: %3d) - level %2d\n",
9417                                         r_name+r_info[quest[q_idx].r_idx].name, quest[q_idx].level, quest[q_idx].complev);
9418 #endif
9419                         }
9420                         else
9421                         {
9422                                 /* Print the quest info */
9423 #ifdef JP
9424                                 sprintf(tmp_str, "  %-40s (´í¸±ÅÙ:%3d³¬ÁêÅö) - ¥ì¥Ù¥ë%2d\n",
9425                                         quest[q_idx].name, quest[q_idx].level, quest[q_idx].complev);
9426 #else
9427                                 sprintf(tmp_str, "  %-40s (Danger  level: %3d) - level %2d\n",
9428                                         quest[q_idx].name, quest[q_idx].level, quest[q_idx].complev);
9429 #endif
9430                         }
9431                         fprintf(fff, tmp_str);
9432                 }
9433         }
9434 #ifdef JP
9435         if (!total) fprintf(fff, "  ¤Ê¤·\n");
9436 #else
9437         if (!total) fprintf(fff, "  Nothing.\n");
9438 #endif
9439 }
9440
9441
9442 /*
9443  * Print all random quests
9444  */
9445 static void do_cmd_knowledge_quests_wiz_random(FILE *fff)
9446 {
9447         char tmp_str[120];
9448         int i;
9449         int total = 0;
9450
9451 #ifdef JP
9452         fprintf(fff, "¡Ô»Ä¤ê¤Î¥é¥ó¥À¥à¥¯¥¨¥¹¥È¡Õ\n");
9453 #else
9454         fprintf(fff, "< Remaining Random Quest >\n");
9455 #endif
9456         for (i = 1; i < max_quests; i++)
9457         {
9458                 /* No info from "silent" quests */
9459                 if (quest[i].flags & QUEST_FLAG_SILENT) continue;
9460
9461                 if ((quest[i].type == QUEST_TYPE_RANDOM) && (quest[i].status == QUEST_STATUS_TAKEN))
9462                 {
9463                         total++;
9464
9465                         /* Print the quest info */
9466 #ifdef JP
9467                         sprintf(tmp_str, "  %s (%d³¬, %s)\n",
9468                                 quest[i].name, quest[i].level, r_name+r_info[quest[i].r_idx].name);
9469 #else
9470                         sprintf(tmp_str, "  %s (%d, %s)\n",
9471                                 quest[i].name, quest[i].level, r_name+r_info[quest[i].r_idx].name);
9472 #endif
9473                         fprintf(fff, tmp_str);
9474                 }
9475         }
9476 #ifdef JP
9477         if (!total) fprintf(fff, "  ¤Ê¤·\n");
9478 #else
9479         if (!total) fprintf(fff, "  Nothing.\n");
9480 #endif
9481 }
9482
9483
9484 bool ang_sort_comp_quest_num(vptr u, vptr v, int a, int b)
9485 {
9486         int *q_num = (int *)u;
9487         quest_type *qa = &quest[q_num[a]];
9488         quest_type *qb = &quest[q_num[b]];
9489
9490         /* Unused */
9491         (void)v;
9492
9493         if (qa->complev < qb->complev) return TRUE;
9494         if (qa->complev > qb->complev) return FALSE;
9495         if (qa->level <= qb->level) return TRUE;
9496         return FALSE;
9497 }
9498
9499 void ang_sort_swap_quest_num(vptr u, vptr v, int a, int b)
9500 {
9501         int *q_num = (int *)u;
9502         int tmp;
9503
9504         /* Unused */
9505         (void)v;
9506
9507         tmp = q_num[a];
9508         q_num[a] = q_num[b];
9509         q_num[b] = tmp;
9510 }
9511
9512
9513 /*
9514  * Print quest status of all active quests
9515  */
9516 static void do_cmd_knowledge_quests(void)
9517 {
9518         FILE *fff;
9519         char file_name[1024];
9520         int *quest_num, dummy, i;
9521
9522         /* Open a new file */
9523         fff = my_fopen_temp(file_name, 1024);
9524         if (!fff)
9525         {
9526 #ifdef JP
9527             msg_format("°ì»þ¥Õ¥¡¥¤¥ë %s ¤òºîÀ®¤Ç¤­¤Þ¤»¤ó¤Ç¤·¤¿¡£", file_name);
9528 #else
9529             msg_format("Failed to create temporary file %s.", file_name);
9530 #endif
9531             msg_print(NULL);
9532             return;
9533         }
9534
9535         /* Allocate Memory */
9536         C_MAKE(quest_num, max_quests, int);
9537
9538         /* Sort by compete level */
9539         for (i = 1; i < max_quests; i++) quest_num[i] = i;
9540         ang_sort_comp = ang_sort_comp_quest_num;
9541         ang_sort_swap = ang_sort_swap_quest_num;
9542         ang_sort(quest_num, &dummy, max_quests);
9543
9544         /* Dump Quest Information */
9545         do_cmd_knowledge_quests_current(fff);
9546         fputc('\n', fff);
9547         do_cmd_knowledge_quests_completed(fff, quest_num);
9548         fputc('\n', fff);
9549         do_cmd_knowledge_quests_failed(fff, quest_num);
9550         if (p_ptr->wizard)
9551         {
9552                 fputc('\n', fff);
9553                 do_cmd_knowledge_quests_wiz_random(fff);
9554         }
9555
9556         /* Close the file */
9557         my_fclose(fff);
9558
9559         /* Display the file contents */
9560 #ifdef JP
9561         show_file(TRUE, file_name, "¥¯¥¨¥¹¥ÈãÀ®¾õ¶·", 0, 0);
9562 #else
9563         show_file(TRUE, file_name, "Quest status", 0, 0);
9564 #endif
9565
9566         /* Remove the file */
9567         fd_kill(file_name);
9568
9569         /* Free Memory */
9570         C_KILL(quest_num, max_quests, int);
9571 }
9572
9573
9574 /*
9575  * List my home
9576  */
9577 static void do_cmd_knowledge_home(void)
9578 {
9579         FILE *fff;
9580
9581         int i;
9582         char file_name[1024];
9583         store_type  *st_ptr;
9584         char o_name[MAX_NLEN];
9585         cptr            paren = ")";
9586
9587         process_dungeon_file("w_info.txt", 0, 0, max_wild_y, max_wild_x);
9588
9589         /* Open a new file */
9590         fff = my_fopen_temp(file_name, 1024);
9591         if (!fff) {
9592 #ifdef JP
9593                 msg_format("°ì»þ¥Õ¥¡¥¤¥ë %s ¤òºîÀ®¤Ç¤­¤Þ¤»¤ó¤Ç¤·¤¿¡£", file_name);
9594 #else
9595                 msg_format("Failed to create temporary file %s.", file_name);
9596 #endif
9597                 msg_print(NULL);
9598                 return;
9599         }
9600
9601         if (fff)
9602         {
9603                 /* Print all homes in the different towns */
9604                 st_ptr = &town[1].store[STORE_HOME];
9605
9606                 /* Home -- if anything there */
9607                 if (st_ptr->stock_num)
9608                 {
9609 #ifdef JP
9610                         int x = 1;
9611 #endif
9612                         /* Header with name of the town */
9613 #ifdef JP
9614                         fprintf(fff, "  [ ²æ¤¬²È¤Î¥¢¥¤¥Æ¥à ]\n");
9615 #else
9616                         fprintf(fff, "  [Home Inventory]\n");
9617 #endif
9618
9619                         /* Dump all available items */
9620                         for (i = 0; i < st_ptr->stock_num; i++)
9621                         {
9622 #ifdef JP
9623                                 if ((i % 12) == 0) fprintf(fff, "\n ( %d ¥Ú¡¼¥¸ )\n", x++);
9624                                 object_desc(o_name, &st_ptr->stock[i], 0);
9625                                 if (strlen(o_name) <= 80-3)
9626                                 {
9627                                         fprintf(fff, "%c%s %s\n", I2A(i%12), paren, o_name);
9628                                 }
9629                                 else
9630                                 {
9631                                         int n;
9632                                         char *t;
9633                                         for (n = 0, t = o_name; n < 80-3; n++, t++)
9634                                                 if(iskanji(*t)) {t++; n++;}
9635                                         if (n == 81-3) n = 79-3; /* ºÇ¸å¤¬´Á»úȾʬ */
9636
9637                                         fprintf(fff, "%c%s %.*s\n", I2A(i%12), paren, n, o_name);
9638                                         fprintf(fff, "   %.77s\n", o_name+n);
9639                                 }
9640 #else
9641                                 object_desc(o_name, &st_ptr->stock[i], 0);
9642                                 fprintf(fff, "%c%s %s\n", I2A(i%12), paren, o_name);
9643 #endif
9644
9645                         }
9646
9647                         /* Add an empty line */
9648                         fprintf(fff, "\n\n");
9649                 }
9650         }
9651
9652         /* Close the file */
9653         my_fclose(fff);
9654
9655         /* Display the file contents */
9656 #ifdef JP
9657         show_file(TRUE, file_name, "²æ¤¬²È¤Î¥¢¥¤¥Æ¥à", 0, 0);
9658 #else
9659         show_file(TRUE, file_name, "Home Inventory", 0, 0);
9660 #endif
9661
9662
9663         /* Remove the file */
9664         fd_kill(file_name);
9665 }
9666
9667
9668 /*
9669  * Check the status of "autopick"
9670  */
9671 static void do_cmd_knowledge_autopick(void)
9672 {
9673         int k;
9674         FILE *fff;
9675         char file_name[1024];
9676
9677         /* Open a new file */
9678         fff = my_fopen_temp(file_name, 1024);
9679
9680         if (!fff)
9681         {
9682 #ifdef JP
9683             msg_format("°ì»þ¥Õ¥¡¥¤¥ë %s ¤òºîÀ®¤Ç¤­¤Þ¤»¤ó¤Ç¤·¤¿¡£", file_name);
9684 #else
9685             msg_format("Failed to create temporary file %s.", file_name);
9686 #endif
9687             msg_print(NULL);
9688             return;
9689         }
9690
9691         if (!max_autopick)
9692         {
9693 #ifdef JP
9694             fprintf(fff, "¼«Æ°Ç˲õ/½¦¤¤¤Ë¤Ï²¿¤âÅÐÏ¿¤µ¤ì¤Æ¤¤¤Þ¤»¤ó¡£");
9695 #else
9696             fprintf(fff, "No preference for auto picker/destroyer.");
9697 #endif
9698         }
9699         else
9700         {
9701 #ifdef JP
9702             fprintf(fff, "   ¼«Æ°½¦¤¤/Ç˲õ¤Ë¤Ï¸½ºß %d¹ÔÅÐÏ¿¤µ¤ì¤Æ¤¤¤Þ¤¹¡£\n\n", max_autopick);
9703 #else
9704             fprintf(fff, "   There are %d registered lines for auto picker/destroyer.\n\n", max_autopick);
9705 #endif
9706         }
9707
9708         for (k = 0; k < max_autopick; k++)
9709         {
9710                 cptr tmp;
9711                 byte act = autopick_list[k].action;
9712                 if (act & DONT_AUTOPICK)
9713                 {
9714 #ifdef JP
9715                         tmp = "ÊüÃÖ";
9716 #else
9717                         tmp = "Leave";
9718 #endif
9719                 }
9720                 else if (act & DO_AUTODESTROY)
9721                 {
9722 #ifdef JP
9723                         tmp = "Ç˲õ";
9724 #else
9725                         tmp = "Destroy";
9726 #endif
9727                 }
9728                 else if (act & DO_AUTOPICK)
9729                 {
9730 #ifdef JP
9731                         tmp = "½¦¤¦";
9732 #else
9733                         tmp = "Pickup";
9734 #endif
9735                 }
9736                 else /* if (act & DO_QUERY_AUTOPICK) */ /* Obvious */
9737                 {
9738 #ifdef JP
9739                         tmp = "³Îǧ";
9740 #else
9741                         tmp = "Query";
9742 #endif
9743                 }
9744
9745                 if (act & DO_DISPLAY)
9746                         fprintf(fff, "%11s", format("[%s]", tmp));
9747                 else
9748                         fprintf(fff, "%11s", format("(%s)", tmp));
9749
9750                 tmp = autopick_line_from_entry(&autopick_list[k]);
9751                 fprintf(fff, " %s", tmp);
9752                 string_free(tmp);
9753                 fprintf(fff, "\n");
9754         }
9755         /* Close the file */
9756         my_fclose(fff);
9757         /* Display the file contents */
9758 #ifdef JP
9759         show_file(TRUE, file_name, "¼«Æ°½¦¤¤/Ç˲õ ÀßÄê¥ê¥¹¥È", 0, 0);
9760 #else
9761         show_file(TRUE, file_name, "Auto-picker/Destroyer", 0, 0);
9762 #endif
9763
9764         /* Remove the file */
9765         fd_kill(file_name);
9766 }
9767
9768
9769 /*
9770  * Interact with "knowledge"
9771  */
9772 void do_cmd_knowledge(void)
9773 {
9774         int i, p = 0;
9775         bool need_redraw = FALSE;
9776
9777         /* File type is "TEXT" */
9778         FILE_TYPE(FILE_TYPE_TEXT);
9779
9780         /* Save the screen */
9781         screen_save();
9782
9783         /* Interact until done */
9784         while (1)
9785         {
9786                 /* Clear screen */
9787                 Term_clear();
9788
9789                 /* Ask for a choice */
9790 #ifdef JP
9791                 prt(format("%d/2 ¥Ú¡¼¥¸", (p+1)), 2, 65);
9792                 prt("¸½ºß¤ÎÃ챤ò³Îǧ¤¹¤ë", 3, 0);
9793 #else
9794                 prt(format("page %d/2", (p+1)), 2, 65);
9795                 prt("Display current knowledge", 3, 0);
9796 #endif
9797
9798                 /* Give some choices */
9799 #ifdef JP
9800                 if (p == 0)
9801                 {
9802                         prt("(1) ´ûÃΤÎÅÁÀâ¤Î¥¢¥¤¥Æ¥à                 ¤Î°ìÍ÷", 6, 5);
9803                         prt("(2) ´ûÃΤΥ¢¥¤¥Æ¥à                       ¤Î°ìÍ÷", 7, 5);
9804                         prt("(3) ´ûÃΤÎÀ¸¤­¤Æ¤¤¤ë¥æ¥Ë¡¼¥¯¡¦¥â¥ó¥¹¥¿¡¼ ¤Î°ìÍ÷", 8, 5);
9805                         prt("(4) ´ûÃΤΥâ¥ó¥¹¥¿¡¼                     ¤Î°ìÍ÷", 9, 5);
9806                         prt("(5) Åݤ·¤¿Å¨¤Î¿ô                         ¤Î°ìÍ÷", 10, 5);
9807                         if (!vanilla_town) prt("(6) ¾Þ¶â¼ó                               ¤Î°ìÍ÷", 11, 5);
9808                         prt("(7) ¸½ºß¤Î¥Ú¥Ã¥È                         ¤Î°ìÍ÷", 12, 5);
9809                         prt("(8) ²æ¤¬²È¤Î¥¢¥¤¥Æ¥à                     ¤Î°ìÍ÷", 13, 5);
9810                         prt("(9) *´ÕÄê*ºÑ¤ßÁõÈ÷¤ÎÂÑÀ­                 ¤Î°ìÍ÷", 14, 5);
9811                         prt("(0) ÃÏ·Á¤Îɽ¼¨Ê¸»ú/¥¿¥¤¥ë                ¤Î°ìÍ÷", 15, 5);
9812                 }
9813                 else
9814                 {
9815                         prt("(a) ¼«Ê¬¤Ë´Ø¤¹¤ë¾ðÊó                     ¤Î°ìÍ÷", 6, 5);
9816                         prt("(b) ÆÍÁ³ÊÑ°Û                             ¤Î°ìÍ÷", 7, 5);
9817                         prt("(c) Éð´ï¤Î·Ð¸³ÃÍ                         ¤Î°ìÍ÷", 8, 5);
9818                         prt("(d) ËâË¡¤Î·Ð¸³ÃÍ                         ¤Î°ìÍ÷", 9, 5);
9819                         prt("(e) µ»Ç½¤Î·Ð¸³ÃÍ                         ¤Î°ìÍ÷", 10, 5);
9820                         prt("(f) ¥×¥ì¥¤¥ä¡¼¤ÎÆÁ                       ¤Î°ìÍ÷", 11, 5);
9821                         prt("(g) Æþ¤Ã¤¿¥À¥ó¥¸¥ç¥ó                     ¤Î°ìÍ÷", 12, 5);
9822                         prt("(h) ¼Â¹ÔÃæ¤Î¥¯¥¨¥¹¥È                     ¤Î°ìÍ÷", 13, 5);
9823                         prt("(i) ¸½ºß¤Î¼«Æ°½¦¤¤/Ç˲õÀßÄê              ¤Î°ìÍ÷", 14, 5);
9824                 }
9825 #else
9826                 if (p == 0)
9827                 {
9828                         prt("(1) Display known artifacts", 6, 5);
9829                         prt("(2) Display known objects", 7, 5);
9830                         prt("(3) Display remaining uniques", 8, 5);
9831                         prt("(4) Display known monster", 9, 5);
9832                         prt("(5) Display kill count", 10, 5);
9833                         if (!vanilla_town) prt("(6) Display wanted monsters", 11, 5);
9834                         prt("(7) Display current pets", 12, 5);
9835                         prt("(8) Display home inventory", 13, 5);
9836                         prt("(9) Display *identified* equip.", 14, 5);
9837                         prt("(0) Display terrain symbols.", 15, 5);
9838                 }
9839                 else
9840                 {
9841                         prt("(a) Display about yourself", 6, 5);
9842                         prt("(b) Display mutations", 7, 5);
9843                         prt("(c) Display weapon proficiency", 8, 5);
9844                         prt("(d) Display spell proficiency", 9, 5);
9845                         prt("(e) Display misc. proficiency", 10, 5);
9846                         prt("(f) Display virtues", 11, 5);
9847                         prt("(g) Display dungeons", 12, 5);
9848                         prt("(h) Display current quests", 13, 5);
9849                         prt("(i) Display auto pick/destroy", 14, 5);
9850                 }
9851 #endif
9852                 /* Prompt */
9853 #ifdef JP
9854                 prt("-³¤¯-", 17, 8);
9855                 prt("ESC) È´¤±¤ë", 21, 1);
9856                 prt("SPACE) ¼¡¥Ú¡¼¥¸", 21, 30);
9857                 /*prt("-) Á°¥Ú¡¼¥¸", 21, 60);*/
9858                 prt("¥³¥Þ¥ó¥É:", 20, 0);
9859 #else
9860                 prt("-more-", 17, 8);
9861                 prt("ESC) Exit menu", 21, 1);
9862                 prt("SPACE) Next page", 21, 30);
9863                 /*prt("-) Previous page", 21, 60);*/
9864                 prt("Command: ", 20, 0);
9865 #endif
9866
9867                 /* Prompt */
9868                 i = inkey();
9869
9870                 /* Done */
9871                 if (i == ESCAPE) break;
9872                 switch (i)
9873                 {
9874                 case ' ': /* Page change */
9875                 case '-':
9876                         p = 1 - p;
9877                         break;
9878                 case '1': /* Artifacts */
9879                         do_cmd_knowledge_artifacts();
9880                         break;
9881                 case '2': /* Objects */
9882                         do_cmd_knowledge_objects(&need_redraw, FALSE, -1);
9883                         break;
9884                 case '3': /* Uniques */
9885                         do_cmd_knowledge_uniques();
9886                         break;
9887                 case '4': /* Monsters */
9888                         do_cmd_knowledge_monsters(&need_redraw, FALSE, -1);
9889                         break;
9890                 case '5': /* Kill count  */
9891                         do_cmd_knowledge_kill_count();
9892                         break;
9893                 case '6': /* wanted */
9894                         if (!vanilla_town) do_cmd_knowledge_kubi();
9895                         break;
9896                 case '7': /* Pets */
9897                         do_cmd_knowledge_pets();
9898                         break;
9899                 case '8': /* Home */
9900                         do_cmd_knowledge_home();
9901                         break;
9902                 case '9': /* Resist list */
9903                         do_cmd_knowledge_inven();
9904                         break;
9905                 case '0': /* Feature list */
9906                         {
9907                                 int lighting_level = F_LIT_STANDARD;
9908                                 do_cmd_knowledge_features(&need_redraw, FALSE, -1, &lighting_level);
9909                         }
9910                         break;
9911                 /* Next page */
9912                 case 'a': /* Max stat */
9913                         do_cmd_knowledge_stat();
9914                         break;
9915                 case 'b': /* Mutations */
9916                         do_cmd_knowledge_mutations();
9917                         break;
9918                 case 'c': /* weapon-exp */
9919                         do_cmd_knowledge_weapon_exp();
9920                         break;
9921                 case 'd': /* spell-exp */
9922                         do_cmd_knowledge_spell_exp();
9923                         break;
9924                 case 'e': /* skill-exp */
9925                         do_cmd_knowledge_skill_exp();
9926                         break;
9927                 case 'f': /* Virtues */
9928                         do_cmd_knowledge_virtues();
9929                         break;
9930                 case 'g': /* Dungeon */
9931                         do_cmd_knowledge_dungeon();
9932                         break;
9933                 case 'h': /* Quests */
9934                         do_cmd_knowledge_quests();
9935                         break;
9936                 case 'i': /* Autopick */
9937                         do_cmd_knowledge_autopick();
9938                         break;
9939                 default: /* Unknown option */
9940                         bell();
9941                 }
9942
9943                 /* Flush messages */
9944                 msg_print(NULL);
9945         }
9946
9947         /* Restore the screen */
9948         screen_load();
9949
9950         if (need_redraw) do_cmd_redraw();
9951 }
9952
9953
9954 /*
9955  * Check on the status of an active quest
9956  */
9957 void do_cmd_checkquest(void)
9958 {
9959         /* File type is "TEXT" */
9960         FILE_TYPE(FILE_TYPE_TEXT);
9961
9962         /* Save the screen */
9963         screen_save();
9964
9965         /* Quest info */
9966         do_cmd_knowledge_quests();
9967
9968         /* Restore the screen */
9969         screen_load();
9970 }
9971
9972
9973 /*
9974  * Display the time and date
9975  */
9976 void do_cmd_time(void)
9977 {
9978         int day, hour, min, full, start, end, num;
9979         char desc[1024];
9980
9981         char buf[1024];
9982         char day_buf[10];
9983
9984         FILE *fff;
9985
9986         extract_day_hour_min(&day, &hour, &min);
9987
9988         full = hour * 100 + min;
9989
9990         start = 9999;
9991         end = -9999;
9992
9993         num = 0;
9994
9995 #ifdef JP
9996         strcpy(desc, "ÊѤʻþ¹ï¤À¡£");
9997 #else
9998         strcpy(desc, "It is a strange time.");
9999 #endif
10000
10001
10002         if (day < MAX_DAYS) sprintf(day_buf, "%d", day);
10003         else strcpy(day_buf, "*****");
10004
10005         /* Message */
10006 #ifdef JP
10007         msg_format("%sÆüÌÜ, »þ¹ï¤Ï%d:%02d %s¤Ç¤¹¡£",
10008                    day_buf, (hour % 12 == 0) ? 12 : (hour % 12),
10009                    min, (hour < 12) ? "AM" : "PM");
10010 #else
10011         msg_format("This is day %s. The time is %d:%02d %s.",
10012                    day_buf, (hour % 12 == 0) ? 12 : (hour % 12),
10013                    min, (hour < 12) ? "AM" : "PM");
10014 #endif
10015
10016
10017         /* Find the path */
10018         if (!randint0(10) || p_ptr->image)
10019         {
10020 #ifdef JP
10021                 path_build(buf, sizeof(buf), ANGBAND_DIR_FILE, "timefun_j.txt");
10022 #else
10023                 path_build(buf, sizeof(buf), ANGBAND_DIR_FILE, "timefun.txt");
10024 #endif
10025
10026         }
10027         else
10028         {
10029 #ifdef JP
10030                 path_build(buf, sizeof(buf), ANGBAND_DIR_FILE, "timenorm_j.txt");
10031 #else
10032                 path_build(buf, sizeof(buf), ANGBAND_DIR_FILE, "timenorm.txt");
10033 #endif
10034
10035         }
10036
10037         /* Open this file */
10038         fff = my_fopen(buf, "rt");
10039
10040         /* Oops */
10041         if (!fff) return;
10042
10043         /* Find this time */
10044         while (!my_fgets(fff, buf, sizeof(buf)))
10045         {
10046                 /* Ignore comments */
10047                 if (!buf[0] || (buf[0] == '#')) continue;
10048
10049                 /* Ignore invalid lines */
10050                 if (buf[1] != ':') continue;
10051
10052                 /* Process 'Start' */
10053                 if (buf[0] == 'S')
10054                 {
10055                         /* Extract the starting time */
10056                         start = atoi(buf + 2);
10057
10058                         /* Assume valid for an hour */
10059                         end = start + 59;
10060
10061                         /* Next... */
10062                         continue;
10063                 }
10064
10065                 /* Process 'End' */
10066                 if (buf[0] == 'E')
10067                 {
10068                         /* Extract the ending time */
10069                         end = atoi(buf + 2);
10070
10071                         /* Next... */
10072                         continue;
10073                 }
10074
10075                 /* Ignore incorrect range */
10076                 if ((start > full) || (full > end)) continue;
10077
10078                 /* Process 'Description' */
10079                 if (buf[0] == 'D')
10080                 {
10081                         num++;
10082
10083                         /* Apply the randomizer */
10084                         if (!randint0(num)) strcpy(desc, buf + 2);
10085
10086                         /* Next... */
10087                         continue;
10088                 }
10089         }
10090
10091         /* Message */
10092         msg_print(desc);
10093
10094         /* Close the file */
10095         my_fclose(fff);
10096 }