OSDN Git Service

Merge remote-tracking branch 'remotes/origin/CHARGEMAN'
[hengband/hengband.git] / src / flavor.c
1 /*!
2  *  @file flavor.c
3  *  @brief オブジェクトの記述処理 / Mbject flavor code
4  *  @date 2014/01/03
5  *  @author
6  * Copyright (c) 1997 Ben Harrison, James E. Wilson, Robert A. Koeneke\n
7  *\n
8  * This software may be copied and distributed for educational, research,\n
9  * and not for profit purposes provided that this copyright and statement\n
10  * are included in all such copies.  Other copyrights may also apply.\n
11  */
12
13 #include "angband.h"
14
15 /*!
16  * @brief 最初から簡易な名称が明らかになるベースアイテムの判定。 /  Certain items, if aware, are known instantly 
17  * @param i ベースアイテムID
18  * @return 簡易名称を明らかにするならTRUEを返す。
19  * @details
20  * This function is used only by "flavor_init()"
21  */
22 static bool object_easy_know(int i)
23 {
24         object_kind *k_ptr = &k_info[i];
25
26         /* Analyze the "tval" */
27         switch (k_ptr->tval)
28         {
29                 /* Spellbooks */
30                 case TV_LIFE_BOOK:
31                 case TV_SORCERY_BOOK:
32                 case TV_NATURE_BOOK:
33                 case TV_CHAOS_BOOK:
34                 case TV_DEATH_BOOK:
35                 case TV_TRUMP_BOOK:
36                 case TV_ARCANE_BOOK:
37                 case TV_CRAFT_BOOK:
38                 case TV_DAEMON_BOOK:
39                 case TV_CRUSADE_BOOK:
40                 case TV_MUSIC_BOOK:
41                 case TV_HISSATSU_BOOK:
42                 case TV_HEX_BOOK:
43                 {
44                         return (TRUE);
45                 }
46
47                 /* Simple items */
48                 case TV_FLASK:
49                 case TV_JUNK:
50                 case TV_BOTTLE:
51                 case TV_SKELETON:
52                 case TV_SPIKE:
53                 case TV_WHISTLE:
54                 {
55                         return (TRUE);
56                 }
57
58                 /* All Food, Potions, Scrolls, Rods */
59                 case TV_FOOD:
60                 case TV_POTION:
61                 case TV_SCROLL:
62                 case TV_ROD:
63                 {
64                         return (TRUE);
65                 }
66         }
67
68         return (FALSE);
69 }
70
71 /*!
72  * @brief 各種語彙からランダムな名前を作成する / Create a name from random parts.
73  * @param out_string 作成した名を保管する参照ポインタ
74  * @return なし
75  * @details 日本語の場合 aname_j.txt 英語の場合確率に応じて
76  * syllables 配列と elvish.txt を組み合わせる。\n
77  */
78 void get_table_name_aux(char *out_string)
79 {
80 #ifdef JP
81         char Syllable[80];
82         get_rnd_line("aname_j.txt", 1, Syllable);
83         strcpy(out_string, Syllable);
84         get_rnd_line("aname_j.txt", 2, Syllable);
85         strcat(out_string, Syllable);
86 #else
87 #define MAX_SYLLABLES 164       /* Used with scrolls (see below) */
88
89         static concptr syllables[MAX_SYLLABLES] = {
90                 "a", "ab", "ag", "aks", "ala", "an", "ankh", "app",
91                 "arg", "arze", "ash", "aus", "ban", "bar", "bat", "bek",
92                 "bie", "bin", "bit", "bjor", "blu", "bot", "bu",
93                 "byt", "comp", "con", "cos", "cre", "dalf", "dan",
94                 "den", "der", "doe", "dok", "eep", "el", "eng", "er", "ere", "erk",
95                 "esh", "evs", "fa", "fid", "flit", "for", "fri", "fu", "gan",
96                 "gar", "glen", "gop", "gre", "ha", "he", "hyd", "i",
97                 "ing", "ion", "ip", "ish", "it", "ite", "iv", "jo",
98                 "kho", "kli", "klis", "la", "lech", "man", "mar",
99                 "me", "mi", "mic", "mik", "mon", "mung", "mur", "nag", "nej",
100                 "nelg", "nep", "ner", "nes", "nis", "nih", "nin", "o",
101                 "od", "ood", "org", "orn", "ox", "oxy", "pay", "pet",
102                 "ple", "plu", "po", "pot", "prok", "re", "rea", "rhov",
103                 "ri", "ro", "rog", "rok", "rol", "sa", "san", "sat",
104                 "see", "sef", "seh", "shu", "ski", "sna", "sne", "snik",
105                 "sno", "so", "sol", "sri", "sta", "sun", "ta", "tab",
106                 "tem", "ther", "ti", "tox", "trol", "tue", "turs", "u",
107                 "ulk", "um", "un", "uni", "ur", "val", "viv", "vly",
108                 "vom", "wah", "wed", "werg", "wex", "whon", "wun", "x",
109                 "yerg", "yp", "zun", "tri", "blaa", "jah", "bul", "on",
110                 "foo", "ju", "xuxu"
111         };
112
113         int testcounter = randint1(3) + 1;
114
115         strcpy(out_string, "");
116
117         if (randint1(3) == 2)
118         {
119                 while (testcounter--)
120                         strcat(out_string, syllables[randint0(MAX_SYLLABLES)]);
121         }
122         else
123         {
124                 char Syllable[80];
125                 testcounter = randint1(2) + 1;
126                 while (testcounter--)
127                 {
128                         (void)get_rnd_line("elvish.txt", 0, Syllable);
129                         strcat(out_string, Syllable);
130                 }
131         }
132
133         out_string[0] = toupper(out_string[1]);
134
135         out_string[16] = '\0';
136 #endif
137 }
138
139 /*!
140  * @brief ランダムな名前をアーティファクト銘として整形する。 / Create a name from random parts with quotes.
141  * @param out_string 作成した名を保管する参照ポインタ
142  * @return なし
143  * @details get_table_name_aux()ほぼ完全に実装を依存している。
144  */
145 void get_table_name(char *out_string)
146 {
147         char buff[80];
148         get_table_name_aux(buff);
149         sprintf(out_string, _("『%s』", "'%s'"), buff);
150 }
151
152 /*!
153  * @brief ランダムなシンダリン銘を作成する / Make random Sindarin name
154  * @param out_string 作成した名を保管する参照ポインタ
155  * @return なし
156  * @details sname.txtが語幹の辞書となっている。
157  */
158 void get_table_sindarin_aux(char *out_string)
159 {
160         char Syllable[80];
161 #ifdef JP
162         char tmp[80];
163 #endif
164
165         get_rnd_line("sname.txt", 1, Syllable);
166 #ifdef JP
167         strcpy(tmp, Syllable);
168 #else
169         strcpy(out_string, Syllable);
170 #endif
171
172         get_rnd_line("sname.txt", 2, Syllable);
173 #ifdef JP
174         strcat(tmp, Syllable);
175         sindarin_to_kana(out_string, tmp);
176 #else
177         strcat(out_string, Syllable);
178 #endif
179 }
180
181 /*!
182  * @brief シンダリン銘をアーティファクト用に整形する。 / Make random Sindarin name with quotes
183  * @param out_string 作成した名を保管する参照ポインタ
184  * @return なし
185  * @details get_table_sindarin_aux()ほぼ完全に実装を依存している。
186  */
187 void get_table_sindarin(char *out_string)
188 {
189         char buff[80];
190         get_table_sindarin_aux(buff);
191         sprintf(out_string, _("『%s』", "'%s'"), buff);
192 }
193
194
195 /*!
196  * @brief ベースアイテムの未確定名を共通tval間でシャッフルする / Shuffle flavor indices of a group of objects with given tval
197  * @param tval シャッフルしたいtval
198  * @return なし
199  * @details 巻物、各種魔道具などに利用される。
200  */
201 static void shuffle_flavors(OBJECT_TYPE_VALUE tval)
202 {
203         KIND_OBJECT_IDX *k_idx_list;
204         KIND_OBJECT_IDX k_idx_list_num = 0;
205         KIND_OBJECT_IDX i;
206
207         /* Allocate an array for a list of k_idx */
208         C_MAKE(k_idx_list, max_k_idx, KIND_OBJECT_IDX);
209
210         /* Search objects with given tval for shuffle */
211         for (i = 0; i < max_k_idx; i++)
212         {
213                 object_kind *k_ptr = &k_info[i];
214
215                 /* Skip non-Rings */
216                 if (k_ptr->tval != tval) continue;
217
218                 /* Paranoia -- Skip objects without flavor */
219                 if (!k_ptr->flavor) continue;
220
221                 /* Skip objects with a fixed flavor name */
222                 if (have_flag(k_ptr->flags, TR_FIXED_FLAVOR)) continue;
223
224                 /* Remember k_idx */
225                 k_idx_list[k_idx_list_num] = i;
226
227                 /* Increase number of remembered indices */
228                 k_idx_list_num++;
229         }
230
231         /* Shuffle flavors */
232         for (i = 0; i < k_idx_list_num; i++)
233         {
234                 object_kind *k1_ptr = &k_info[k_idx_list[i]];
235                 object_kind *k2_ptr = &k_info[k_idx_list[randint0(k_idx_list_num)]];
236
237                 /* Swap flavors of this pair */
238                 s16b tmp = k1_ptr->flavor;
239                 k1_ptr->flavor = k2_ptr->flavor;
240                 k2_ptr->flavor = tmp;
241         }
242
243         /* Free an array for a list of k_idx */
244         C_KILL(k_idx_list, max_k_idx, s16b);
245 }
246
247 /*!
248  * @brief ゲーム開始時に行われるベースアイテムの初期化ルーチン / Prepare the "variable" part of the "k_info" array.
249  * @return なし
250  * @details
251  * Prepare the "variable" part of the "k_info" array.\n
252  *\n
253  * The "color"/"metal"/"type" of an item is its "flavor".\n
254  * For the most part, flavors are assigned randomly each game.\n
255  *\n
256  * Initialize descriptions for the "colored" objects, including:\n
257  * Rings, Amulets, Staffs, Wands, Rods, Food, Potions, Scrolls.\n
258  *\n
259  * The first 4 entries for potions are fixed (Water, Apple Juice,\n
260  * Slime Mold Juice, Unused Potion).\n
261  *\n
262  * Scroll titles are always between 6 and 14 letters long.  This is\n
263  * ensured because every title is composed of whole words, where every\n
264  * word is from 1 to 8 letters long (one or two syllables of 1 to 4\n
265  * letters each), and that no scroll is finished until it attempts to\n
266  * grow beyond 15 letters.  The first time this can happen is when the\n
267  * current title has 6 letters and the new word has 8 letters, which\n
268  * would result in a 6 letter scroll title.\n
269  *\n
270  * Duplicate titles are avoided by requiring that no two scrolls share\n
271  * the same first four letters (not the most efficient method, and not\n
272  * the least efficient method, but it will always work).\n
273  *\n
274  * Hack -- make sure everything stays the same for each saved game\n
275  * This is accomplished by the use of a saved "random seed", as in\n
276  * "town_gen()".  Since no other functions are called while the special\n
277  * seed is in effect, so this function is pretty "safe".\n
278  *\n
279  * Note that the "hacked seed" may provide an RNG with alternating parity!\n
280  */
281 void flavor_init(void)
282 {
283         KIND_OBJECT_IDX i;
284         u32b state_backup[4];
285
286         /* Hack -- Backup the RNG state */
287         Rand_state_backup(state_backup);
288
289         /* Hack -- Induce consistant flavors */
290         Rand_state_set(seed_flavor);
291
292
293         /* Initialize flavor index of each object by itself */
294         for (i = 0; i < max_k_idx; i++)
295         {
296                 object_kind *k_ptr = &k_info[i];
297
298                 /* Skip objects without flavor name */
299                 if (!k_ptr->flavor_name) continue;
300
301                 /*
302                  * Initialize flavor index to itself
303                  *  -> Shuffle it later
304                  */
305                 k_ptr->flavor = i;
306         }
307
308         /* Shuffle Rings */
309         shuffle_flavors(TV_RING);
310
311         /* Shuffle Amulets */
312         shuffle_flavors(TV_AMULET);
313
314         /* Shuffle Staves */
315         shuffle_flavors(TV_STAFF);
316
317         /* Shuffle Wands */
318         shuffle_flavors(TV_WAND);
319
320         /* Shuffle Rods */
321         shuffle_flavors(TV_ROD);
322
323         /* Shuffle Mushrooms */
324         shuffle_flavors(TV_FOOD);
325
326         /* Shuffle Potions */
327         shuffle_flavors(TV_POTION);
328
329         /* Shuffle Scrolls */
330         shuffle_flavors(TV_SCROLL);
331
332
333         /* Hack -- Restore the RNG state */
334         Rand_state_restore(state_backup);
335
336         /* Analyze every object */
337         for (i = 1; i < max_k_idx; i++)
338         {
339                 object_kind *k_ptr = &k_info[i];
340
341                 /* Skip "empty" objects */
342                 if (!k_ptr->name) continue;
343
344                 /* No flavor yields aware */
345                 if (!k_ptr->flavor) k_ptr->aware = TRUE;
346
347                 /* Check for "easily known" */
348                 k_ptr->easy_know = object_easy_know(i);
349         }
350 }
351
352
353 /*!
354  * @brief 対象文字配列に一文字だけをコピーする。
355  * @param t 保管先文字列ポインタ
356  * @param c 保管したい1文字
357  * @return なし
358  * @details
359  * Print a char "c" into a string "t", as if by sprintf(t, "%c", c),\n
360  * and return a pointer to the terminator (t + 1).\n
361  */
362 static char *object_desc_chr(char *t, char c)
363 {
364         /* Copy the char */
365         *t++ = c;
366
367         /* Terminate */
368         *t = '\0';
369         return (t);
370 }
371
372 /*!
373  * @brief 対象文字配列に文字列をコピーする。
374  * @param t 保管先文字列ポインタ
375  * @param s コピーしたい文字列ポインタ
376  * @return 保管先の末尾アドレス
377  * @details
378  * Print a string "s" into a string "t", as if by strcpy(t, s),
379  * and return a pointer to the terminator.
380  */
381 static char *object_desc_str(char *t, concptr s)
382 {
383         /* Copy the string */
384         while (*s) *t++ = *s++;
385
386         /* Terminate */
387         *t = '\0';
388         return (t);
389 }
390
391 /*!
392  * @brief 対象文字配列に符号なし整数値をコピーする。
393  * @param t 保管先文字列ポインタ
394  * @param n コピーしたい数値
395  * @return なし
396  * @details
397  * Print an unsigned number "n" into a string "t", as if by
398  * sprintf(t, "%u", n), and return a pointer to the terminator.
399  */
400 static char *object_desc_num(char *t, uint n)
401 {
402         uint p;
403
404         /* Find "size" of "n" */
405         for (p = 1; n >= p * 10; p = p * 10) /* loop */;
406
407         /* Dump each digit */
408         while (p >= 1)
409         {
410                 /* Dump the digit */
411                 *t++ = '0' + n / p;
412
413                 /* Remove the digit */
414                 n = n % p;
415
416                 /* Process next digit */
417                 p = p / 10;
418         }
419
420         /* Terminate */
421         *t = '\0';
422         return (t);
423 }
424
425
426
427
428 #ifdef JP
429 /*!
430  * @brief 日本語の個数表示ルーチン
431  * @param t 保管先文字列ポインタ
432  * @param o_ptr 記述したいオブジェクトの構造体参照ポインタ
433  * @return なし
434  * @details
435  * cmd1.c で流用するために object_desc_japanese から移動した。
436  */
437 char *object_desc_kosuu(char *t, object_type *o_ptr)
438 {
439     t = object_desc_num(t, o_ptr->number);
440
441     switch (o_ptr->tval)
442     {
443       case TV_BOLT:
444       case TV_ARROW:
445       case TV_POLEARM:
446       case TV_STAFF:
447       case TV_WAND:
448       case TV_ROD:
449       case TV_DIGGING:
450       {
451           t = object_desc_str(t, "本");
452           break;
453       }
454       case TV_SCROLL:
455       {
456           t = object_desc_str(t, "巻");
457           break;
458       }
459       case TV_POTION:
460       {
461           t = object_desc_str(t, "服");
462           break;
463       }
464       case  TV_LIFE_BOOK:
465       case  TV_SORCERY_BOOK:
466       case  TV_NATURE_BOOK:
467       case  TV_CHAOS_BOOK:
468       case  TV_DEATH_BOOK:
469       case  TV_TRUMP_BOOK:
470       case  TV_ARCANE_BOOK:
471       case  TV_CRAFT_BOOK:
472       case  TV_DAEMON_BOOK:
473       case  TV_CRUSADE_BOOK:
474       case  TV_MUSIC_BOOK:
475       case  TV_HISSATSU_BOOK:
476           case TV_HEX_BOOK:
477       {
478           t = object_desc_str(t, "冊");
479           break;
480       }
481       case TV_SOFT_ARMOR:
482       case TV_HARD_ARMOR:
483       case TV_DRAG_ARMOR:
484       case TV_CLOAK:
485       {
486           t = object_desc_str(t, "着");
487           break;
488       }
489       case TV_SWORD:
490       case TV_HAFTED:
491       case TV_BOW:
492       {
493           t = object_desc_str(t, "振");
494           break;
495       }
496       case TV_BOOTS:
497       {
498           t = object_desc_str(t, "足");
499           break;
500       }
501       case TV_CARD:
502       {
503           t = object_desc_str(t, "枚");
504           break;
505       }
506             /* 食べもの by ita */
507       case TV_FOOD:
508       {
509           if(o_ptr->sval == SV_FOOD_JERKY)
510           {
511               t = object_desc_str(t, "切れ");
512               break;
513           }
514       }
515       default:
516       {
517           if (o_ptr->number < 10)
518           {
519               t = object_desc_str(t, "つ");
520           }
521           else
522           {
523               t = object_desc_str(t, "個");
524           }
525           break;
526       }
527   }
528   return (t);                  
529 }
530 #endif
531
532 /*!
533  * @brief 対象文字配列に符号あり整数値をコピーする。
534  * @param t 保管先文字列ポインタ
535  * @param v コピーしたい数値
536  * @return なし
537  * @details
538  * Print an signed number "v" into a string "t", as if by
539  * sprintf(t, "%+d", n), and return a pointer to the terminator.
540  * Note that we always print a sign, either "+" or "-".
541  */
542 static char *object_desc_int(char *t, sint v)
543 {
544         uint p, n;
545
546         /* Negative */
547         if (v < 0)
548         {
549                 /* Take the absolute value */
550                 n = 0 - v;
551
552                 /* Use a "minus" sign */
553                 *t++ = '-';
554         }
555
556         /* Positive (or zero) */
557         else
558         {
559                 /* Use the actual number */
560                 n = v;
561
562                 /* Use a "plus" sign */
563                 *t++ = '+';
564         }
565
566         /* Find "size" of "n" */
567         for (p = 1; n >= p * 10; p = p * 10) /* loop */;
568
569         /* Dump each digit */
570         while (p >= 1)
571         {
572                 /* Dump the digit */
573                 *t++ = '0' + n / p;
574
575                 /* Remove the digit */
576                 n = n % p;
577
578                 /* Process next digit */
579                 p = p / 10;
580         }
581
582         /* Terminate */
583         *t = '\0';
584         return (t);
585 }
586
587
588 /*!
589  * オブジェクトの特性表示記号テーブルの構造体 / Structs and tables for Auto Inscription for flags
590  */
591 typedef struct flag_insc_table
592 {
593 #ifdef JP
594         concptr japanese;
595 #endif
596         concptr english;
597         int flag;
598         int except_flag;
599 } flag_insc_table;
600
601 #ifdef JP
602 /*! オブジェクトの特性表示記号テーブルの定義(pval要素) */
603 static flag_insc_table flag_insc_plus[] =
604 {
605         { "攻", "At", TR_BLOWS, -1 },
606         { "速", "Sp", TR_SPEED, -1 },
607         { "腕", "St", TR_STR, -1 },
608         { "知", "In", TR_INT, -1 },
609         { "賢", "Wi", TR_WIS, -1 },
610         { "器", "Dx", TR_DEX, -1 },
611         { "耐", "Cn", TR_CON, -1 },
612         { "魅", "Ch", TR_CHR, -1 },
613         { "道", "Md", TR_MAGIC_MASTERY, -1 },
614         { "隠", "Sl", TR_STEALTH, -1 },
615         { "探", "Sr", TR_SEARCH, -1 },
616         { "赤", "If", TR_INFRA, -1 },
617         { "掘", "Dg", TR_TUNNEL, -1 },
618         { NULL, NULL, 0, -1 }
619 };
620
621 /*! オブジェクトの特性表示記号テーブルの定義(免疫) */
622 static flag_insc_table flag_insc_immune[] =
623 {
624         { "酸", "Ac", TR_IM_ACID, -1 },
625         { "電", "El", TR_IM_ELEC, -1 },
626         { "火", "Fi", TR_IM_FIRE, -1 },
627         { "冷", "Co", TR_IM_COLD, -1 },
628         { NULL, NULL, 0, -1 }
629 };
630
631 /*! オブジェクトの特性表示記号テーブルの定義(耐性) */
632 static flag_insc_table flag_insc_resistance[] =
633 {
634         { "酸", "Ac", TR_RES_ACID, TR_IM_ACID },
635         { "電", "El", TR_RES_ELEC, TR_IM_ELEC },
636         { "火", "Fi", TR_RES_FIRE, TR_IM_FIRE },
637         { "冷", "Co", TR_RES_COLD, TR_IM_COLD },
638         { "毒", "Po", TR_RES_POIS, -1 },
639         { "閃", "Li", TR_RES_LITE, -1 },
640         { "暗", "Dk", TR_RES_DARK, -1 },
641         { "破", "Sh", TR_RES_SHARDS, -1 },
642         { "盲", "Bl", TR_RES_BLIND, -1 },
643         { "乱", "Cf", TR_RES_CONF, -1 },
644         { "轟", "So", TR_RES_SOUND, -1 },
645         { "獄", "Nt", TR_RES_NETHER, -1 },
646         { "因", "Nx", TR_RES_NEXUS, -1 },
647         { "沌", "Ca", TR_RES_CHAOS, -1 },
648         { "劣", "Di", TR_RES_DISEN, -1 },
649         { "恐", "Fe", TR_RES_FEAR, -1 },
650         { NULL, NULL, 0, -1 }
651 };
652
653 /*! オブジェクトの特性表示記号テーブルの定義(その他特性) */
654 static flag_insc_table flag_insc_misc[] =
655 {
656         { "易", "Es", TR_EASY_SPELL, -1 },
657         { "減", "Dm", TR_DEC_MANA, -1 },
658         { "投", "Th", TR_THROW, -1 },
659         { "反", "Rf", TR_REFLECT, -1 },
660         { "麻", "Fa", TR_FREE_ACT, -1 },
661         { "視", "Si", TR_SEE_INVIS, -1 },
662         { "経", "Hl", TR_HOLD_EXP, -1 },
663         { "遅", "Sd", TR_SLOW_DIGEST, -1 },
664         { "活", "Rg", TR_REGEN, -1 },
665         { "浮", "Lv", TR_LEVITATION, -1 },
666         { "明", "Lu", TR_LITE_1, -1 },
667         { "明", "Lu", TR_LITE_2, -1 },
668         { "明", "Lu", TR_LITE_3, -1 },
669         { "闇", "Dl", TR_LITE_M1, -1 },
670         { "闇", "Dl", TR_LITE_M2, -1 },
671         { "闇", "Dl", TR_LITE_M3, -1 },
672         { "警", "Wr", TR_WARNING, -1 },
673         { "倍", "Xm", TR_XTRA_MIGHT, -1 },
674         { "射", "Xs", TR_XTRA_SHOTS, -1 },
675         { "瞬", "Te", TR_TELEPORT, -1 },
676         { "怒", "Ag", TR_AGGRAVATE, -1 },
677         { "祝", "Bs", TR_BLESSED, -1 },
678         { "忌", "Ty", TR_TY_CURSE, -1 },
679         { "呪", "C-", TR_ADD_L_CURSE, -1 },
680         { "詛", "C+", TR_ADD_H_CURSE, -1 },
681         { NULL, NULL, 0, -1 }
682 };
683
684 /*! オブジェクトの特性表示記号テーブルの定義(オーラ) */
685 static flag_insc_table flag_insc_aura[] =
686 {
687         { "炎", "F", TR_SH_FIRE, -1 },
688         { "電", "E", TR_SH_ELEC, -1 },
689         { "冷", "C", TR_SH_COLD, -1 },
690         { "魔", "M", TR_NO_MAGIC, -1 },
691         { "瞬", "T", TR_NO_TELE, -1 },
692         { NULL, NULL, 0, -1 }
693 };
694
695 /*! オブジェクトの特性表示記号テーブルの定義(属性スレイ) */
696 static flag_insc_table flag_insc_brand[] =
697 {
698         { "酸", "A", TR_BRAND_ACID, -1 },
699         { "電", "E", TR_BRAND_ELEC, -1 },
700         { "焼", "F", TR_BRAND_FIRE, -1 },
701         { "凍", "Co", TR_BRAND_COLD, -1 },
702         { "毒", "P", TR_BRAND_POIS, -1 },
703         { "沌", "Ca", TR_CHAOTIC, -1 },
704         { "吸", "V", TR_VAMPIRIC, -1 },
705         { "震", "Q", TR_IMPACT, -1 },
706         { "切", "S", TR_VORPAL, -1 },
707         { "理", "M", TR_FORCE_WEAPON, -1 },
708         { NULL, NULL, 0, -1 }
709 };
710
711 /*! オブジェクトの特性表示記号テーブルの定義(種族スレイ) */
712 static flag_insc_table flag_insc_kill[] =
713 {
714         { "邪", "*", TR_KILL_EVIL, -1 },
715         { "人", "p", TR_KILL_HUMAN, -1 },
716         { "龍", "D", TR_KILL_DRAGON, -1 },
717         { "オ", "o", TR_KILL_ORC, -1 },
718         { "ト", "T", TR_KILL_TROLL, -1 },
719         { "巨", "P", TR_KILL_GIANT, -1 },
720         { "デ", "U", TR_KILL_DEMON, -1 },
721         { "死", "L", TR_KILL_UNDEAD, -1 },
722         { "動", "Z", TR_KILL_ANIMAL, -1 },
723         { NULL, NULL, 0, -1 }
724 };
725
726 /*! オブジェクトの特性表示記号テーブルの定義(種族*スレイ*) */
727 static flag_insc_table flag_insc_slay[] =
728 {
729         { "邪", "*", TR_SLAY_EVIL, TR_KILL_EVIL },
730         { "人", "p", TR_SLAY_HUMAN, TR_KILL_HUMAN },
731         { "竜", "D", TR_SLAY_DRAGON, TR_KILL_DRAGON },
732         { "オ", "o", TR_SLAY_ORC, TR_KILL_ORC },
733         { "ト", "T", TR_SLAY_TROLL, TR_KILL_TROLL },
734         { "巨", "P", TR_SLAY_GIANT, TR_KILL_GIANT },
735         { "デ", "U", TR_SLAY_DEMON, TR_KILL_DEMON },
736         { "死", "L", TR_SLAY_UNDEAD, TR_KILL_UNDEAD },
737         { "動", "Z", TR_SLAY_ANIMAL, TR_KILL_ANIMAL },
738         { NULL, NULL, 0, -1 }
739 };
740
741 /*! オブジェクトの特性表示記号テーブルの定義(ESP1) */
742 static flag_insc_table flag_insc_esp1[] =
743 {
744         { "感", "Tele", TR_TELEPATHY, -1 },
745         { "邪", "Evil", TR_ESP_EVIL, -1 },
746         { "善", "Good", TR_ESP_GOOD, -1 },
747         { "無", "Nolv", TR_ESP_NONLIVING, -1 },
748         { "個", "Uniq", TR_ESP_UNIQUE, -1 },
749         { NULL, NULL, 0, -1 }
750 };
751
752 /*! オブジェクトの特性表示記号テーブルの定義(ESP2) */
753 static flag_insc_table flag_insc_esp2[] =
754 {
755         { "人", "p", TR_ESP_HUMAN, -1 },
756         { "竜", "D", TR_ESP_DRAGON, -1 },
757         { "オ", "o", TR_ESP_ORC, -1 },
758         { "ト", "T", TR_ESP_TROLL, -1 },
759         { "巨", "P", TR_ESP_GIANT, -1 },
760         { "デ", "U", TR_ESP_DEMON, -1 },
761         { "死", "L", TR_ESP_UNDEAD, -1 },
762         { "動", "Z", TR_ESP_ANIMAL, -1 },
763         { NULL, NULL, 0, -1 }
764 };
765
766 /*! オブジェクトの特性表示記号テーブルの定義(能力維持) */
767 static flag_insc_table flag_insc_sust[] =
768 {
769         { "腕", "St", TR_SUST_STR, -1 },
770         { "知", "In", TR_SUST_INT, -1 },
771         { "賢", "Wi", TR_SUST_WIS, -1 },
772         { "器", "Dx", TR_SUST_DEX, -1 },
773         { "耐", "Cn", TR_SUST_CON, -1 },
774         { "魅", "Ch", TR_SUST_CHR, -1 },
775         { NULL, NULL, 0, -1 }
776 };
777
778 #else
779 static flag_insc_table flag_insc_plus[] =
780 {
781         { "At", TR_BLOWS, -1 },
782         { "Sp", TR_SPEED, -1 },
783         { "St", TR_STR, -1 },
784         { "In", TR_INT, -1 },
785         { "Wi", TR_WIS, -1 },
786         { "Dx", TR_DEX, -1 },
787         { "Cn", TR_CON, -1 },
788         { "Ch", TR_CHR, -1 },
789         { "Md", TR_MAGIC_MASTERY, -1 },
790         { "Sl", TR_STEALTH, -1 },
791         { "Sr", TR_SEARCH, -1 },
792         { "If", TR_INFRA, -1 },
793         { "Dg", TR_TUNNEL, -1 },
794         { NULL, 0, -1 }
795 };
796
797 static flag_insc_table flag_insc_immune[] =
798 {
799         { "Ac", TR_IM_ACID, -1 },
800         { "El", TR_IM_ELEC, -1 },
801         { "Fi", TR_IM_FIRE, -1 },
802         { "Co", TR_IM_COLD, -1 },
803         { NULL, 0, -1 }
804 };
805
806 static flag_insc_table flag_insc_resistance[] =
807 {
808         { "Ac", TR_RES_ACID, TR_IM_ACID },
809         { "El", TR_RES_ELEC, TR_IM_ELEC },
810         { "Fi", TR_RES_FIRE, TR_IM_FIRE },
811         { "Co", TR_RES_COLD, TR_IM_COLD },
812         { "Po", TR_RES_POIS, -1 },
813         { "Li", TR_RES_LITE, -1 },
814         { "Dk", TR_RES_DARK, -1 },
815         { "Sh", TR_RES_SHARDS, -1 },
816         { "Bl", TR_RES_BLIND, -1 },
817         { "Cf", TR_RES_CONF, -1 },
818         { "So", TR_RES_SOUND, -1 },
819         { "Nt", TR_RES_NETHER, -1 },
820         { "Nx", TR_RES_NEXUS, -1 },
821         { "Ca", TR_RES_CHAOS, -1 },
822         { "Di", TR_RES_DISEN, -1 },
823         { "Fe", TR_RES_FEAR, -1 },
824         { NULL, 0, -1 }
825 };
826
827 static flag_insc_table flag_insc_misc[] =
828 {
829         { "Es", TR_EASY_SPELL, -1 },
830         { "Dm", TR_DEC_MANA, -1 },
831         { "Th", TR_THROW, -1 },
832         { "Rf", TR_REFLECT, -1 },
833         { "Fa", TR_FREE_ACT, -1 },
834         { "Si", TR_SEE_INVIS, -1 },
835         { "Hl", TR_HOLD_EXP, -1 },
836         { "Sd", TR_SLOW_DIGEST, -1 },
837         { "Rg", TR_REGEN, -1 },
838         { "Lv", TR_LEVITATION, -1 },
839         { "Lu", TR_LITE_1, -1 },
840         { "Lu", TR_LITE_2, -1 },
841         { "Lu", TR_LITE_3, -1 },
842         { "Dl", TR_LITE_M1, -1 },
843         { "Dl", TR_LITE_M2, -1 },
844         { "Dl", TR_LITE_M3, -1 },
845         { "Wr", TR_WARNING, -1 },
846         { "Xm", TR_XTRA_MIGHT, -1 },
847         { "Xs", TR_XTRA_SHOTS, -1 },
848         { "Te", TR_TELEPORT, -1 },
849         { "Ag", TR_AGGRAVATE, -1 },
850         { "Bs", TR_BLESSED, -1 },
851         { "Ty", TR_TY_CURSE, -1 },
852         { "C-", TR_ADD_L_CURSE, -1 },
853         { "C+", TR_ADD_H_CURSE, -1 },
854         { NULL, 0, -1 }
855 };
856
857 static flag_insc_table flag_insc_aura[] =
858 {
859         { "F", TR_SH_FIRE, -1 },
860         { "E", TR_SH_ELEC, -1 },
861         { "C", TR_SH_COLD, -1 },
862         { "M", TR_NO_MAGIC, -1 },
863         { "T", TR_NO_TELE, -1 },
864         { NULL, 0, -1 }
865 };
866
867 static flag_insc_table flag_insc_brand[] =
868 {
869         { "A", TR_BRAND_ACID, -1 },
870         { "E", TR_BRAND_ELEC, -1 },
871         { "F", TR_BRAND_FIRE, -1 },
872         { "Co", TR_BRAND_COLD, -1 },
873         { "P", TR_BRAND_POIS, -1 },
874         { "Ca", TR_CHAOTIC, -1 },
875         { "V", TR_VAMPIRIC, -1 },
876         { "Q", TR_IMPACT, -1 },
877         { "S", TR_VORPAL, -1 },
878         { "M", TR_FORCE_WEAPON, -1 },
879         { NULL, 0, -1 }
880 };
881
882 static flag_insc_table flag_insc_kill[] =
883 {
884         { "*", TR_KILL_EVIL, -1 },
885         { "p", TR_KILL_HUMAN, -1 },
886         { "D", TR_KILL_DRAGON, -1 },
887         { "o", TR_KILL_ORC, -1 },
888         { "T", TR_KILL_TROLL, -1 },
889         { "P", TR_KILL_GIANT, -1 },
890         { "U", TR_KILL_DEMON, -1 },
891         { "L", TR_KILL_UNDEAD, -1 },
892         { "Z", TR_KILL_ANIMAL, -1 },
893         { NULL, 0, -1 }
894 };
895
896 static flag_insc_table flag_insc_slay[] =
897 {
898         { "*", TR_SLAY_EVIL, TR_KILL_EVIL },
899         { "p", TR_SLAY_HUMAN, TR_KILL_HUMAN },
900         { "D", TR_SLAY_DRAGON, TR_KILL_DRAGON },
901         { "o", TR_SLAY_ORC, TR_KILL_ORC },
902         { "T", TR_SLAY_TROLL, TR_KILL_TROLL },
903         { "P", TR_SLAY_GIANT, TR_KILL_GIANT },
904         { "U", TR_SLAY_DEMON, TR_KILL_DEMON },
905         { "L", TR_SLAY_UNDEAD, TR_KILL_UNDEAD },
906         { "Z", TR_SLAY_ANIMAL, TR_KILL_ANIMAL },
907         { NULL, 0, -1 }
908 };
909
910 static flag_insc_table flag_insc_esp1[] =
911 {
912         { "Tele", TR_TELEPATHY, -1 },
913         { "Evil", TR_ESP_EVIL, -1 },
914         { "Good", TR_ESP_GOOD, -1 },
915         { "Nolv", TR_ESP_NONLIVING, -1 },
916         { "Uniq", TR_ESP_UNIQUE, -1 },
917         { NULL, 0, -1 }
918 };
919
920 static flag_insc_table flag_insc_esp2[] =
921 {
922         { "p", TR_ESP_HUMAN, -1 },
923         { "D", TR_ESP_DRAGON, -1 },
924         { "o", TR_ESP_ORC, -1 },
925         { "T", TR_ESP_TROLL, -1 },
926         { "P", TR_ESP_GIANT, -1 },
927         { "U", TR_ESP_DEMON, -1 },
928         { "L", TR_ESP_UNDEAD, -1 },
929         { "Z", TR_ESP_ANIMAL, -1 },
930         { NULL, 0, -1 }
931 };
932
933 static flag_insc_table flag_insc_sust[] =
934 {
935         { "St", TR_SUST_STR, -1 },
936         { "In", TR_SUST_INT, -1 },
937         { "Wi", TR_SUST_WIS, -1 },
938         { "Dx", TR_SUST_DEX, -1 },
939         { "Cn", TR_SUST_CON, -1 },
940         { "Ch", TR_SUST_CHR, -1 },
941         { NULL, 0, -1 }
942 };
943 #endif
944
945 /* オブジェクトフラグを追加するための簡易なマクロ / Simple macro for get_inscription() */
946 #define ADD_INSC(STR) (void)(ptr = object_desc_str(ptr, (STR)))
947
948 /*!
949  * @brief get_inscriptionのサブセットとしてオブジェクトの特性フラグを返す / Helper function for get_inscription()
950  * @param fi_ptr 参照する特性表示記号テーブル
951  * @param flgs 対応するオブジェクトのフラグ文字列
952  * @param kanji TRUEならば漢字記述/FALSEならば英語記述
953  * @param ptr フラグ群を保管する文字列参照ポインタ
954  * @return フラグ群を保管する文字列参照ポインタ(ptrと同じ)
955  * @details
956  * Print an signed number "v" into a string "t", as if by
957  * sprintf(t, "%+d", n), and return a pointer to the terminator.
958  * Note that we always print a sign, either "+" or "-".
959  */
960 static char *inscribe_flags_aux(flag_insc_table *fi_ptr, BIT_FLAGS flgs[TR_FLAG_SIZE], bool kanji, char *ptr)
961 {
962 #ifndef JP
963         (void)kanji;
964 #endif
965
966         while (fi_ptr->english)
967         {
968                 if (have_flag(flgs, fi_ptr->flag) &&
969                     (fi_ptr->except_flag == -1 || !have_flag(flgs, fi_ptr->except_flag)))
970 #ifdef JP
971                         ADD_INSC(kanji ? fi_ptr->japanese : fi_ptr->english);
972 #else
973                         ADD_INSC(fi_ptr->english);
974 #endif
975                 fi_ptr++;
976         }
977
978         return ptr;
979 }
980
981
982 /*!
983  * @brief オブジェクトの特性表示記号テーブル1つに従いオブジェクトの特性フラグ配列に1つでも該当の特性があるかを返す / Special variation of have_flag for auto-inscription
984  * @param fi_ptr 参照する特性表示記号テーブル
985  * @param flgs 対応するオブジェクトのフラグ文字列
986  * @return 1つでも該当の特性があったらTRUEを返す。
987  */
988 static bool have_flag_of(flag_insc_table *fi_ptr, BIT_FLAGS flgs[TR_FLAG_SIZE])
989 {
990         while (fi_ptr->english)
991         {
992                 if (have_flag(flgs, fi_ptr->flag) &&
993                    (fi_ptr->except_flag == -1 || !have_flag(flgs, fi_ptr->except_flag)))
994                         return (TRUE);
995                 fi_ptr++;
996         }
997
998         return (FALSE);
999 }
1000
1001 /*!
1002  * @brief オブジェクト名の特性短縮表記をまとめて提示する。
1003  * @param ptr 特性短縮表記を格納する文字列ポインタ
1004  * @param o_ptr 特性短縮表記を得たいオブジェクト構造体の参照ポインタ
1005  * @param kanji TRUEならば漢字表記 / FALSEなら英語表記
1006  * @param all TRUEならばベースアイテム上で明らかなフラグは省略する
1007  * @return ptrと同じアドレス
1008  */
1009 static char *get_ability_abbreviation(char *ptr, object_type *o_ptr, bool kanji, bool all)
1010 {
1011         char *prev_ptr = ptr;
1012         BIT_FLAGS flgs[TR_FLAG_SIZE];
1013         object_flags(o_ptr, flgs);
1014
1015         /* Remove obvious flags */
1016         if (!all)
1017         {
1018                 object_kind *k_ptr = &k_info[o_ptr->k_idx];
1019                 int j;
1020                                 
1021                 /* Base object */
1022                 for (j = 0; j < TR_FLAG_SIZE; j++)
1023                         flgs[j] &= ~k_ptr->flags[j];
1024
1025                 if (object_is_fixed_artifact(o_ptr))
1026                 {
1027                         artifact_type *a_ptr = &a_info[o_ptr->name1];
1028                                         
1029                         for (j = 0; j < TR_FLAG_SIZE; j++)
1030                                 flgs[j] &= ~a_ptr->flags[j];
1031                 }
1032
1033                 if (object_is_ego(o_ptr))
1034                 {
1035                         ego_item_type *e_ptr = &e_info[o_ptr->name2];
1036                                         
1037                         for (j = 0; j < TR_FLAG_SIZE; j++)
1038                                 flgs[j] &= ~e_ptr->flags[j];
1039                 }
1040         }
1041
1042         /* Remove lite flags when this is a dark lite object */
1043         if (have_dark_flag(flgs))
1044         {
1045                 if (have_flag(flgs, TR_LITE_1)) remove_flag(flgs, TR_LITE_1);
1046                 if (have_flag(flgs, TR_LITE_2)) remove_flag(flgs, TR_LITE_2);
1047                 if (have_flag(flgs, TR_LITE_3)) remove_flag(flgs, TR_LITE_3);
1048         }
1049         else if (have_lite_flag(flgs))
1050         {
1051                 add_flag(flgs, TR_LITE_1);
1052                 if (have_flag(flgs, TR_LITE_2)) remove_flag(flgs, TR_LITE_2);
1053                 if (have_flag(flgs, TR_LITE_3)) remove_flag(flgs, TR_LITE_3);
1054         }
1055
1056         /* Plusses */
1057         if (have_flag_of(flag_insc_plus, flgs))
1058         {
1059                 if (kanji)
1060                         ADD_INSC("+");
1061         }
1062         ptr = inscribe_flags_aux(flag_insc_plus, flgs, kanji, ptr);
1063
1064         /* Immunity */
1065         if (have_flag_of(flag_insc_immune, flgs))
1066         {
1067                 if (!kanji && ptr != prev_ptr)
1068                 {
1069                         ADD_INSC(";");
1070                         prev_ptr = ptr;
1071                 }
1072                 ADD_INSC("*");
1073         }
1074         ptr = inscribe_flags_aux(flag_insc_immune, flgs, kanji, ptr);
1075
1076         /* Resistance */
1077         if (have_flag_of(flag_insc_resistance, flgs))
1078         {
1079                 if (kanji)
1080                         ADD_INSC("r");
1081                 else if (ptr != prev_ptr)
1082                 {
1083                         ADD_INSC(";");
1084                         prev_ptr = ptr;
1085                 }
1086         }
1087         ptr = inscribe_flags_aux(flag_insc_resistance, flgs, kanji, ptr);
1088
1089         /* Misc Ability */
1090         if (have_flag_of(flag_insc_misc, flgs))
1091         {
1092                 if (ptr != prev_ptr)
1093                 {
1094                         ADD_INSC(";");
1095                         prev_ptr = ptr;
1096                 }
1097         }
1098         ptr = inscribe_flags_aux(flag_insc_misc, flgs, kanji, ptr);
1099
1100         /* Aura */
1101         if (have_flag_of(flag_insc_aura, flgs))
1102         {
1103                 ADD_INSC("[");
1104         }
1105         ptr = inscribe_flags_aux(flag_insc_aura, flgs, kanji, ptr);
1106
1107         /* Brand Weapon */
1108         if (have_flag_of(flag_insc_brand, flgs))
1109                 ADD_INSC("|");
1110         ptr = inscribe_flags_aux(flag_insc_brand, flgs, kanji, ptr);
1111
1112         /* Kill Weapon */
1113         if (have_flag_of(flag_insc_kill, flgs))
1114                 ADD_INSC("/X");
1115         ptr = inscribe_flags_aux(flag_insc_kill, flgs, kanji, ptr);
1116
1117         /* Slay Weapon */
1118         if (have_flag_of(flag_insc_slay, flgs))
1119                 ADD_INSC("/");
1120         ptr = inscribe_flags_aux(flag_insc_slay, flgs, kanji, ptr);
1121
1122         /* Esp */
1123         if (kanji)
1124         {
1125                 if (have_flag_of(flag_insc_esp1, flgs) ||
1126                     have_flag_of(flag_insc_esp2, flgs))
1127                         ADD_INSC("~");
1128                 ptr = inscribe_flags_aux(flag_insc_esp1, flgs, kanji, ptr);
1129                 ptr = inscribe_flags_aux(flag_insc_esp2, flgs, kanji, ptr);
1130         }
1131         else
1132         {
1133                 if (have_flag_of(flag_insc_esp1, flgs))
1134                         ADD_INSC("~");
1135                 ptr = inscribe_flags_aux(flag_insc_esp1, flgs, kanji, ptr);
1136                 if (have_flag_of(flag_insc_esp2, flgs))
1137                         ADD_INSC("~");
1138                 ptr = inscribe_flags_aux(flag_insc_esp2, flgs, kanji, ptr);
1139         }
1140
1141         /* sustain */
1142         if (have_flag_of(flag_insc_sust, flgs))
1143         {
1144                 ADD_INSC("(");
1145         }
1146         ptr = inscribe_flags_aux(flag_insc_sust, flgs, kanji, ptr);
1147
1148         *ptr = '\0';
1149
1150         return ptr;
1151 }
1152
1153
1154 /*!
1155  * @brief オブジェクト名の特性短縮表記+刻み内容を提示する。 / Get object inscription with auto inscription of object flags.
1156  * @param buff 特性短縮表記を格納する文字列ポインタ
1157  * @param o_ptr 特性短縮表記を得たいオブジェクト構造体の参照ポインタ
1158  * @return なし
1159  */
1160 static void get_inscription(char *buff, object_type *o_ptr)
1161 {
1162         concptr insc = quark_str(o_ptr->inscription);
1163         char *ptr = buff;
1164
1165         /* Not fully identified */
1166         if (!(o_ptr->ident & IDENT_MENTAL))
1167         {
1168                 /* Copy until end of line or '#' */
1169                 while (*insc)
1170                 {
1171                         if (*insc == '#') break;
1172 #ifdef JP
1173                         if (iskanji(*insc)) *buff++ = *insc++;
1174 #endif
1175                         *buff++ = *insc++;
1176                 }
1177
1178                 *buff = '\0';
1179                 return;
1180         }
1181
1182         *buff = '\0';
1183         for (; *insc; insc++)
1184         {
1185                 /* Ignore fake artifact inscription */
1186                 if (*insc == '#') break;
1187
1188                 /* {%} will be automatically converted */
1189                 else if ('%' == *insc)
1190                 {
1191                         bool kanji = FALSE;
1192                         bool all;
1193                         concptr start = ptr;
1194
1195                         /* check for too long inscription */
1196                         if (ptr >= buff + MAX_NLEN) continue;
1197
1198 #ifdef JP
1199                         if ('%' == insc[1])
1200                         {
1201                                 insc++;
1202                                 kanji = FALSE;
1203                         }
1204                         else
1205                         {
1206                                 kanji = TRUE;
1207                         }
1208 #endif
1209                         if ('a' == insc[1] && 'l' == insc[2] && 'l' == insc[3])
1210                         {
1211                                 all = TRUE;
1212                                 insc += 3;
1213                         }
1214                         else
1215                         {
1216                                 all = FALSE;
1217                         }
1218
1219                         ptr = get_ability_abbreviation(ptr, o_ptr, kanji, all);
1220
1221                         if (ptr == start)
1222                                 ADD_INSC(" ");
1223                 }
1224                 else
1225                 {
1226                         *ptr++ = *insc;
1227                 }
1228         }
1229         *ptr = '\0';
1230 }
1231
1232 /*!
1233  * @brief オブジェクトがクエストの達成目的か否かを返す。
1234  * @param o_ptr 特性短縮表記を得たいオブジェクト構造体の参照ポインタ
1235  * @return 現在クエスト達成目的のアイテムならばTRUEを返す。
1236  */
1237 bool object_is_quest_target(object_type *o_ptr)
1238 {
1239         if (p_ptr->inside_quest)
1240         {
1241                 ARTIFACT_IDX a_idx = quest[p_ptr->inside_quest].k_idx;
1242                 if (a_idx)
1243                 {
1244                         artifact_type *a_ptr = &a_info[a_idx];
1245                         if (!(a_ptr->gen_flags & TRG_INSTA_ART))
1246                         {
1247                                 if((o_ptr->tval == a_ptr->tval) && (o_ptr->sval == a_ptr->sval))
1248                                 {
1249                                         return TRUE;
1250                                 }
1251                         }
1252                 }
1253         }
1254         return FALSE;
1255 }
1256
1257
1258 /*!
1259  * @brief オブジェクトの各表記を返すメイン関数 / Creates a description of the item "o_ptr", and stores it in "out_val".
1260  * @param buf 表記を返すための文字列参照ポインタ
1261  * @param o_ptr 特性短縮表記を得たいオブジェクト構造体の参照ポインタ
1262  * @param mode 表記に関するオプション指定
1263  * @return 現在クエスト達成目的のアイテムならばTRUEを返す。
1264  * @details
1265  * One can choose the "verbosity" of the description, including whether\n
1266  * or not the "number" of items should be described, and how much detail\n
1267  * should be used when describing the item.\n
1268  *\n
1269  * The given "buf" must be MAX_NLEN chars long to hold the longest possible\n
1270  * description, which can get pretty long, including incriptions, such as:\n
1271  * "no more Maces of Disruption (Defender) (+10,+10) [+5] (+3 to stealth)".\n
1272  * Note that the inscription will be clipped to keep the total description\n
1273  * under MAX_NLEN-1 chars (plus a terminator).\n
1274  *\n
1275  * Note the use of "object_desc_num()" and "object_desc_int()" as hyper-efficient,\n
1276  * portable, versions of some common "sprintf()" commands.\n
1277  *\n
1278  * Note that all ego-items (when known) append an "Ego-Item Name", unless\n
1279  * the item is also an artifact, which should NEVER happen.\n
1280  *\n
1281  * Note that all artifacts (when known) append an "Artifact Name", so we\n
1282  * have special processing for "Specials" (artifact Lites, Rings, Amulets).\n
1283  * The "Specials" never use "modifiers" if they are "known", since they\n
1284  * have special "descriptions", such as "The Necklace of the Dwarves".\n
1285  *\n
1286  * Special Lite's use the "k_info" base-name (Phial, Star, or Arkenstone),\n
1287  * plus the artifact name, just like any other artifact, if known.\n
1288  *\n
1289  * Special Ring's and Amulet's, if not "aware", use the same code as normal\n
1290  * rings and amulets, and if "aware", use the "k_info" base-name (Ring or\n
1291  * Amulet or Necklace).  They will NEVER "append" the "k_info" name.  But,\n
1292  * they will append the artifact name, just like any artifact, if known.\n
1293  *\n
1294  * Hack -- Display "The One Ring" as "a Plain Gold Ring" until aware.\n
1295  *\n
1296  * Mode:\n
1297  *   OD_NAME_ONLY        : The Cloak of Death\n
1298  *   OD_NAME_AND_ENCHANT : The Cloak of Death [1,+3]\n
1299  *   OD_OMIT_INSCRIPTION : The Cloak of Death [1,+3] (+2 to Stealth)\n
1300  *   0                   : The Cloak of Death [1,+3] (+2 to Stealth) {nifty}\n
1301  *\n
1302  *   OD_OMIT_PREFIX      : Forbidden numeric prefix\n
1303  *   OD_NO_PLURAL        : Forbidden use of plural \n
1304  *   OD_STORE            : Assume to be aware and known\n
1305  *   OD_NO_FLAVOR        : Allow to hidden flavor\n
1306  *   OD_FORCE_FLAVOR     : Get un-shuffled flavor name\n
1307  */
1308 void object_desc(char *buf, object_type *o_ptr, BIT_FLAGS mode)
1309 {
1310         /* Extract object kind name */
1311         concptr            kindname = k_name + k_info[o_ptr->k_idx].name;
1312
1313         /* Extract default "base" string */
1314         concptr            basenm = kindname;
1315
1316         /* Assume no "modifier" string */
1317         concptr            modstr = "";
1318
1319         int power;
1320         int fire_rate;
1321
1322         bool            aware = FALSE;
1323         bool            known = FALSE;
1324         bool            flavor = TRUE;
1325
1326         bool            show_weapon = FALSE;
1327         bool            show_armour = FALSE;
1328
1329         concptr            s, s0;
1330         char            *t;
1331
1332         char            p1 = '(', p2 = ')';
1333         char            b1 = '[', b2 = ']';
1334         char            c1 = '{', c2 = '}';
1335
1336         char            tmp_val[MAX_NLEN+160];
1337         char            tmp_val2[MAX_NLEN+10];
1338         char            fake_insc_buf[30];
1339
1340         BIT_FLAGS flgs[TR_FLAG_SIZE];
1341
1342         object_type *bow_ptr;
1343
1344         object_kind *k_ptr = &k_info[o_ptr->k_idx];
1345         object_kind *flavor_k_ptr = &k_info[k_ptr->flavor];
1346
1347         /* Extract some flags */
1348         object_flags(o_ptr, flgs);
1349
1350         /* See if the object is "aware" */
1351         if (object_is_aware(o_ptr)) aware = TRUE;
1352
1353         /* See if the object is "known" */
1354         if (object_is_known(o_ptr)) known = TRUE;
1355
1356         /* Allow flavors to be hidden when aware */
1357         if (aware && ((mode & OD_NO_FLAVOR) || plain_descriptions)) flavor = FALSE;
1358
1359         /* Object is in the inventory of a store or spoiler */
1360         if ((mode & OD_STORE) || (o_ptr->ident & IDENT_STORE))
1361         {
1362                 /* Don't show flavors */
1363                 flavor = FALSE;
1364
1365                 /* Pretend known and aware */
1366                 aware = TRUE;
1367                 known = TRUE;
1368         }
1369
1370         /* Force to be flavor name only */
1371         if (mode & OD_FORCE_FLAVOR)
1372         {
1373                 aware = FALSE;
1374                 flavor = TRUE;
1375                 known = FALSE;
1376
1377                 /* Cancel shuffling */
1378                 flavor_k_ptr = k_ptr;
1379         }
1380
1381         /* Analyze the object */
1382         switch (o_ptr->tval)
1383         {
1384                 /* Some objects are easy to describe */
1385                 case TV_SKELETON:
1386                 case TV_BOTTLE:
1387                 case TV_JUNK:
1388                 case TV_SPIKE:
1389                 case TV_FLASK:
1390                 case TV_CHEST:
1391                 case TV_WHISTLE:
1392                 {
1393                         break;
1394                 }
1395
1396                 case TV_CAPTURE:
1397                 {
1398                         monster_race *r_ptr = &r_info[o_ptr->pval];
1399
1400                         if (known)
1401                         {
1402                                 if (!o_ptr->pval)
1403                                 {
1404                                         modstr = _(" (空)", " (empty)");
1405                                 }
1406                                 else
1407                                 {
1408 #ifdef JP
1409                                         sprintf(tmp_val2, " (%s)",r_name + r_ptr->name);
1410                                         modstr = tmp_val2;
1411 #else
1412                                         concptr t = r_name + r_ptr->name;
1413
1414                                         if (!(r_ptr->flags1 & RF1_UNIQUE))
1415                                         {
1416                                                 sprintf(tmp_val2, " (%s%s)", (is_a_vowel(*t) ? "an " : "a "), t);
1417
1418                                                 modstr = tmp_val2;
1419                                         }
1420                                         else
1421                                         {
1422                                                 sprintf(tmp_val2, "(%s)", t);
1423
1424                                                 modstr = t;
1425                                         }
1426 #endif
1427                                 }
1428                         }
1429                         break;
1430                 }
1431
1432                 /* Figurines/Statues */
1433                 case TV_FIGURINE:
1434                 case TV_STATUE:
1435                 {
1436                         monster_race *r_ptr = &r_info[o_ptr->pval];
1437
1438 #ifdef JP
1439                         modstr = r_name + r_ptr->name;
1440 #else
1441                         concptr t = r_name + r_ptr->name;
1442
1443                         if (!(r_ptr->flags1 & RF1_UNIQUE))
1444                         {
1445                                 sprintf(tmp_val2, "%s%s", (is_a_vowel(*t) ? "an " : "a "), t);
1446
1447                                 modstr = tmp_val2;
1448                         }
1449                         else
1450                         {
1451                                 modstr = t;
1452                         }
1453 #endif
1454
1455
1456                         break;
1457                 }
1458
1459                 /* Corpses */
1460                 case TV_CORPSE:
1461                 {
1462                         monster_race *r_ptr = &r_info[o_ptr->pval];
1463
1464                         modstr = r_name + r_ptr->name;
1465
1466 #ifdef JP
1467                         basenm = "#%";
1468 #else
1469                         if (r_ptr->flags1 & RF1_UNIQUE)
1470                                 basenm = "& % of #";
1471                         else
1472                                 basenm = "& # %";
1473 #endif
1474
1475                         break;
1476                 }
1477
1478                 /* Missiles/ Bows/ Weapons */
1479                 case TV_SHOT:
1480                 case TV_BOLT:
1481                 case TV_ARROW:
1482                 case TV_BOW:
1483                 case TV_HAFTED:
1484                 case TV_POLEARM:
1485                 case TV_SWORD:
1486                 case TV_DIGGING:
1487                 {
1488                         show_weapon = TRUE;
1489                         break;
1490                 }
1491
1492                 /* Armour */
1493                 case TV_BOOTS:
1494                 case TV_GLOVES:
1495                 case TV_CLOAK:
1496                 case TV_CROWN:
1497                 case TV_HELM:
1498                 case TV_SHIELD:
1499                 case TV_SOFT_ARMOR:
1500                 case TV_HARD_ARMOR:
1501                 case TV_DRAG_ARMOR:
1502                 {
1503                         show_armour = TRUE;
1504                         break;
1505                 }
1506
1507                 /* Lites (including a few "Specials") */
1508                 case TV_LITE:
1509                 {
1510                         break;
1511                 }
1512
1513                 /* Amulets (including a few "Specials") */
1514                 case TV_AMULET:
1515                 {
1516                         /* Known artifacts */
1517                         if (aware)
1518                         {
1519                                 if (object_is_fixed_artifact(o_ptr)) break;
1520                                 if (k_ptr->gen_flags & TRG_INSTA_ART) break;
1521                         }
1522
1523                         /* Color the object */
1524                         modstr = k_name + flavor_k_ptr->flavor_name;
1525
1526 #ifdef JP
1527                         if (!flavor)    basenm = "%のアミュレット";
1528                         else if (aware) basenm = "%の#アミュレット";
1529                         else            basenm = "#アミュレット";
1530 #else
1531                         if (!flavor)    basenm = "& Amulet~ of %";
1532                         else if (aware) basenm = "& # Amulet~ of %";
1533                         else            basenm = "& # Amulet~";
1534 #endif
1535
1536                         break;
1537                 }
1538
1539                 /* Rings (including a few "Specials") */
1540                 case TV_RING:
1541                 {
1542                         /* Known artifacts */
1543                         if (aware)
1544                         {
1545                                 if (object_is_fixed_artifact(o_ptr)) break;
1546                                 if (k_ptr->gen_flags & TRG_INSTA_ART) break;
1547                         }
1548
1549                         /* Color the object */
1550                         modstr = k_name + flavor_k_ptr->flavor_name;
1551
1552 #ifdef JP
1553                         if (!flavor)    basenm = "%の指輪";
1554                         else if (aware) basenm = "%の#指輪";
1555                         else            basenm = "#指輪";
1556 #else
1557                         if (!flavor)    basenm = "& Ring~ of %";
1558                         else if (aware) basenm = "& # Ring~ of %";
1559                         else            basenm = "& # Ring~";
1560 #endif
1561
1562                         if (!k_ptr->to_h && !k_ptr->to_d && (o_ptr->to_h || o_ptr->to_d)) show_weapon = TRUE;
1563
1564                         break;
1565                 }
1566
1567                 case TV_CARD:
1568                 {
1569                         break;
1570                 }
1571
1572                 case TV_STAFF:
1573                 {
1574                         /* Color the object */
1575                         modstr = k_name + flavor_k_ptr->flavor_name;
1576
1577 #ifdef JP
1578                         if (!flavor)    basenm = "%の杖";
1579                         else if (aware) basenm = "%の#杖";
1580                         else            basenm = "#杖";
1581 #else
1582                         if (!flavor)    basenm = "& Staff~ of %";
1583                         else if (aware) basenm = "& # Staff~ of %";
1584                         else            basenm = "& # Staff~";
1585 #endif
1586
1587                         break;
1588                 }
1589
1590                 case TV_WAND:
1591                 {
1592                         /* Color the object */
1593                         modstr = k_name + flavor_k_ptr->flavor_name;
1594
1595 #ifdef JP
1596                         if (!flavor)    basenm = "%の魔法棒";
1597                         else if (aware) basenm = "%の#魔法棒";
1598                         else            basenm = "#魔法棒";
1599 #else
1600                         if (!flavor)    basenm = "& Wand~ of %";
1601                         else if (aware) basenm = "& # Wand~ of %";
1602                         else            basenm = "& # Wand~";
1603 #endif
1604
1605                         break;
1606                 }
1607
1608                 case TV_ROD:
1609                 {
1610                         /* Color the object */
1611                         modstr = k_name + flavor_k_ptr->flavor_name;
1612
1613 #ifdef JP
1614                         if (!flavor)    basenm = "%のロッド";
1615                         else if (aware) basenm = "%の#ロッド";
1616                         else            basenm = "#ロッド";
1617 #else
1618                         if (!flavor)    basenm = "& Rod~ of %";
1619                         else if (aware) basenm = "& # Rod~ of %";
1620                         else            basenm = "& # Rod~";
1621 #endif
1622
1623                         break;
1624                 }
1625
1626                 case TV_SCROLL:
1627                 {
1628                         /* Color the object */
1629                         modstr = k_name + flavor_k_ptr->flavor_name;
1630
1631 #ifdef JP
1632                         if (!flavor)    basenm = "%の巻物";
1633                         else if (aware) basenm = "「#」と書かれた%の巻物";
1634                         else            basenm = "「#」と書かれた巻物";
1635 #else
1636                         if (!flavor)    basenm = "& Scroll~ of %";
1637                         else if (aware) basenm = "& Scroll~ titled \"#\" of %";
1638                         else            basenm = "& Scroll~ titled \"#\"";
1639 #endif
1640
1641                         break;
1642                 }
1643
1644                 case TV_POTION:
1645                 {
1646                         /* Color the object */
1647                         modstr = k_name + flavor_k_ptr->flavor_name;
1648
1649 #ifdef JP
1650                         if (!flavor)    basenm = "%の薬";
1651                         else if (aware) basenm = "%の#薬";
1652                         else            basenm = "#薬";
1653 #else
1654                         if (!flavor)    basenm = "& Potion~ of %";
1655                         else if (aware) basenm = "& # Potion~ of %";
1656                         else            basenm = "& # Potion~";
1657 #endif
1658
1659                         break;
1660                 }
1661
1662                 case TV_FOOD:
1663                 {
1664                         /* Ordinary food is "boring" */
1665                         if (!k_ptr->flavor_name) break;
1666
1667                         /* Color the object */
1668                         modstr = k_name + flavor_k_ptr->flavor_name;
1669
1670 #ifdef JP
1671                         if (!flavor)    basenm = "%のキノコ";
1672                         else if (aware) basenm = "%の#キノコ";
1673                         else            basenm = "#キノコ";
1674 #else
1675                         if (!flavor)    basenm = "& Mushroom~ of %";
1676                         else if (aware) basenm = "& # Mushroom~ of %";
1677                         else            basenm = "& # Mushroom~";
1678 #endif
1679
1680                         break;
1681                 }
1682
1683                 case TV_PARCHMENT:
1684                 {
1685                         basenm = _("羊皮紙 - %", "& Parchment~ - %");
1686                         break;
1687                 }
1688
1689                 /* Magic Books */
1690                 case TV_LIFE_BOOK:
1691                 {
1692 #ifdef JP
1693                         basenm = "生命の魔法書%";
1694 #else
1695                         if (mp_ptr->spell_book == TV_LIFE_BOOK)
1696                                 basenm = "& Book~ of Life Magic %";
1697                         else
1698                                 basenm = "& Life Spellbook~ %";
1699 #endif
1700
1701                         break;
1702                 }
1703
1704                 case TV_SORCERY_BOOK:
1705                 {
1706 #ifdef JP
1707                         basenm = "仙術の魔法書%";
1708 #else
1709                         if (mp_ptr->spell_book == TV_LIFE_BOOK)
1710                                 basenm = "& Book~ of Sorcery %";
1711                         else
1712                                 basenm = "& Sorcery Spellbook~ %";
1713 #endif
1714
1715                         break;
1716                 }
1717
1718                 case TV_NATURE_BOOK:
1719                 {
1720 #ifdef JP
1721                         basenm = "自然の魔法書%";
1722 #else
1723                         if (mp_ptr->spell_book == TV_LIFE_BOOK)
1724                                 basenm = "& Book~ of Nature Magic %";
1725                         else
1726                                 basenm = "& Nature Spellbook~ %";
1727 #endif
1728
1729                         break;
1730                 }
1731
1732                 case TV_CHAOS_BOOK:
1733                 {
1734 #ifdef JP
1735                         basenm = "カオスの魔法書%";
1736 #else
1737                         if (mp_ptr->spell_book == TV_LIFE_BOOK)
1738                                 basenm = "& Book~ of Chaos Magic %";
1739                         else
1740                                 basenm = "& Chaos Spellbook~ %";
1741 #endif
1742
1743                         break;
1744                 }
1745
1746                 case TV_DEATH_BOOK:
1747                 {
1748 #ifdef JP
1749                         basenm = "暗黒の魔法書%";
1750 #else
1751                         if (mp_ptr->spell_book == TV_LIFE_BOOK)
1752                                 basenm = "& Book~ of Death Magic %";
1753                         else
1754                                 basenm = "& Death Spellbook~ %";
1755 #endif
1756
1757                         break;
1758                 }
1759
1760                 case TV_TRUMP_BOOK:
1761                 {
1762 #ifdef JP
1763                         basenm = "トランプの魔法書%";
1764 #else
1765                         if (mp_ptr->spell_book == TV_LIFE_BOOK)
1766                                 basenm = "& Book~ of Trump Magic %";
1767                         else
1768                                 basenm = "& Trump Spellbook~ %";
1769 #endif
1770
1771                         break;
1772                 }
1773
1774                 case TV_ARCANE_BOOK:
1775                 {
1776 #ifdef JP
1777                         basenm = "秘術の魔法書%";
1778 #else
1779                         if (mp_ptr->spell_book == TV_LIFE_BOOK)
1780                                 basenm = "& Book~ of Arcane Magic %";
1781                         else
1782                                 basenm = "& Arcane Spellbook~ %";
1783 #endif
1784
1785                         break;
1786                 }
1787
1788                 case TV_CRAFT_BOOK:
1789                 {
1790 #ifdef JP
1791                         basenm = "匠の魔法書%";
1792 #else
1793                         if (mp_ptr->spell_book == TV_LIFE_BOOK)
1794                                 basenm = "& Book~ of Craft Magic %";
1795                         else
1796                                 basenm = "& Craft Spellbook~ %";
1797 #endif
1798
1799                         break;
1800                 }
1801
1802                 case TV_DAEMON_BOOK:
1803                 {
1804 #ifdef JP
1805                         basenm = "悪魔の魔法書%";
1806 #else
1807                         if (mp_ptr->spell_book == TV_LIFE_BOOK)
1808                                 basenm = "& Book~ of Daemon Magic %";
1809                         else
1810                                 basenm = "& Daemon Spellbook~ %";
1811 #endif
1812
1813                         break;
1814                 }
1815
1816                 case TV_CRUSADE_BOOK:
1817                 {
1818 #ifdef JP
1819                         basenm = "破邪の魔法書%";
1820 #else
1821                         if (mp_ptr->spell_book == TV_LIFE_BOOK)
1822                                 basenm = "& Book~ of Crusade Magic %";
1823                         else
1824                                 basenm = "& Crusade Spellbook~ %";
1825 #endif
1826
1827                         break;
1828                 }
1829
1830                 case TV_MUSIC_BOOK:
1831                 {
1832                         basenm = _("歌集%", "& Song Book~ %");
1833                         break;
1834                 }
1835
1836                 case TV_HISSATSU_BOOK:
1837                 {
1838                         basenm = _("& 武芸の書%", "Book~ of Kendo %");
1839                         break;
1840                 }
1841
1842                 case TV_HEX_BOOK:
1843                 {
1844 #ifdef JP
1845                         basenm = "呪術の魔法書%";
1846 #else
1847                         if (mp_ptr->spell_book == TV_LIFE_BOOK)
1848                                 basenm = "& Book~ of Hex Magic %";
1849                         else
1850                                 basenm = "& Hex Spellbook~ %";
1851 #endif
1852
1853                         break;
1854                 }
1855
1856                 /* Hack -- Gold/Gems */
1857                 case TV_GOLD:
1858                 {
1859                         strcpy(buf, basenm);
1860                         return;
1861                 }
1862
1863                 /* Used in the "inventory" routine */
1864                 default:
1865                 {
1866                         strcpy(buf, _("(なし)", "(nothing)"));
1867                         return;
1868                 }
1869         }
1870
1871         /* Use full name from k_info or a_info */
1872         if (aware && have_flag(flgs, TR_FULL_NAME))
1873         {
1874                 if (known && o_ptr->name1) basenm = a_name + a_info[o_ptr->name1].name;
1875                 else basenm = kindname;
1876         }
1877
1878         /* Start dumping the result */
1879         t = tmp_val;
1880
1881 #ifdef JP
1882         if (basenm[0] == '&')
1883                 s = basenm + 2;
1884         else
1885                 s = basenm;
1886
1887         /* No prefix */
1888         if (mode & OD_OMIT_PREFIX)
1889         {
1890                 /* Nothing */
1891         }
1892         else if (o_ptr->number > 1)
1893         {
1894                 t = object_desc_kosuu(t, o_ptr);
1895                 t = object_desc_str(t, "の ");
1896         }
1897
1898         /* 英語の場合アーティファクトは The が付くので分かるが
1899          * 日本語では分からないのでマークをつける 
1900          */
1901         if (known)
1902         {
1903                 if (object_is_fixed_artifact(o_ptr)) t = object_desc_str(t, "★");
1904                 else if (o_ptr->art_name) t = object_desc_str(t, "☆");
1905         }
1906
1907 #else
1908
1909         /* The object "expects" a "number" */
1910         if (basenm[0] == '&')
1911         {
1912                 /* Skip the ampersand (and space) */
1913                 s = basenm + 2;
1914
1915                 /* No prefix */
1916                 if (mode & OD_OMIT_PREFIX)
1917                 {
1918                         /* Nothing */
1919                 }
1920
1921                 /* Hack -- None left */
1922                 else if (o_ptr->number <= 0)
1923                 {
1924                         t = object_desc_str(t, "no more ");
1925                 }
1926
1927                 /* Extract the number */
1928                 else if (o_ptr->number > 1)
1929                 {
1930                         t = object_desc_num(t, o_ptr->number);
1931                         t = object_desc_chr(t, ' ');
1932                 }
1933
1934                 /* Hack -- The only one of its kind */
1935                 else if ((known && object_is_artifact(o_ptr)) ||
1936                          ((o_ptr->tval == TV_CORPSE) &&
1937                           (r_info[o_ptr->pval].flags1 & RF1_UNIQUE)))
1938                 {
1939                         t = object_desc_str(t, "The ");
1940                 }
1941
1942                 /* A single one */
1943                 else
1944                 {
1945                         bool vowel;
1946
1947                         switch (*s)
1948                         {
1949                         case '#': vowel = is_a_vowel(modstr[0]); break;
1950                         case '%': vowel = is_a_vowel(*kindname); break;
1951                         default:  vowel = is_a_vowel(*s); break;
1952                         }
1953
1954                         if (vowel)
1955                         {
1956                                 /* A single one, with a vowel */
1957                                 t = object_desc_str(t, "an ");
1958                         }
1959                         else
1960                         {
1961                                 /* A single one, without a vowel */
1962                                 t = object_desc_str(t, "a ");
1963                         }
1964                 }
1965         }
1966
1967         /* Hack -- objects that "never" take an article */
1968         else
1969         {
1970                 /* No ampersand */
1971                 s = basenm;
1972
1973                 /* No pref */
1974                 if (mode & OD_OMIT_PREFIX)
1975                 {
1976                         /* Nothing */
1977                 }
1978
1979                 /* Hack -- all gone */
1980                 else if (o_ptr->number <= 0)
1981                 {
1982                         t = object_desc_str(t, "no more ");
1983                 }
1984
1985                 /* Prefix a number if required */
1986                 else if (o_ptr->number > 1)
1987                 {
1988                         t = object_desc_num(t, o_ptr->number);
1989                         t = object_desc_chr(t, ' ');
1990                 }
1991
1992                 /* Hack -- The only one of its kind */
1993                 else if (known && object_is_artifact(o_ptr))
1994                 {
1995                         t = object_desc_str(t, "The ");
1996                 }
1997
1998                 /* Hack -- single items get no prefix */
1999                 else
2000                 {
2001                         /* Nothing */
2002                 }
2003         }
2004 #endif
2005
2006         /* Paranoia -- skip illegal tildes */
2007         /* while (*s == '~') s++; */
2008
2009 #ifdef JP
2010         if (object_is_smith(o_ptr))
2011         {
2012                 t = object_desc_str(t, format("鍛冶師%sの", p_ptr->name));
2013         }
2014
2015         /* 伝説のアイテム、名のあるアイテムの名前を付加する */
2016         if (known)
2017         {
2018                 /* ランダム・アーティファクト */
2019                 if (o_ptr->art_name)
2020                 {
2021                         concptr temp = quark_str(o_ptr->art_name);
2022
2023                         /* '『' から始まらない伝説のアイテムの名前は最初に付加する */
2024                         /* 英語版のセーブファイルから来た 'of XXX' は,「XXXの」と表示する */
2025                         if (strncmp(temp, "of ", 3) == 0)
2026                         {
2027                                 t = object_desc_str(t, &temp[3]);
2028                                 t = object_desc_str(t, "の");
2029                         }
2030                         else if ((strncmp(temp, "『", 2) != 0) &&
2031                                  (strncmp(temp, "《", 2) != 0) &&
2032                                  (temp[0] != '\''))
2033                                 t = object_desc_str(t, temp);
2034                 }
2035                 /* 伝説のアイテム */
2036                 else if (o_ptr->name1 && !have_flag(flgs, TR_FULL_NAME))
2037                 {
2038                         artifact_type *a_ptr = &a_info[o_ptr->name1];
2039                         /* '『' から始まらない伝説のアイテムの名前は最初に付加する */
2040                         if (strncmp(a_name + a_ptr->name, "『", 2) != 0)
2041                         {
2042                                 t = object_desc_str(t, a_name + a_ptr->name);
2043                         }
2044                 }
2045                 /* 名のあるアイテム */
2046                 else if (object_is_ego(o_ptr))
2047                 {
2048                         ego_item_type *e_ptr = &e_info[o_ptr->name2];
2049                         t = object_desc_str(t, e_name + e_ptr->name);
2050                 }
2051         }
2052 #endif
2053
2054         /* Copy the string */
2055         for (s0 = NULL; *s || s0; )
2056         {
2057                 /* The end of the flavour/kind string. */
2058                 if (!*s)
2059                 {
2060                         s = s0 + 1;
2061                         s0 = NULL;
2062                 }
2063
2064                 /* Begin to append the modifier (flavor) */
2065                 else if ((*s == '#') && !s0)
2066                 {
2067                         s0 = s;
2068                         s = modstr;
2069
2070                         /* Paranoia -- Never append multiple modstrs */
2071                         modstr = "";
2072                 }
2073
2074                 /* Begin to append the kind name */
2075                 else if ((*s == '%') && !s0)
2076                 {
2077                         s0 = s;
2078                         s = kindname;
2079
2080                         /* Paranoia -- Never append multiple kindnames */
2081                         kindname = "";
2082                 }
2083
2084 #ifndef JP
2085                 /* Pluralizer */
2086                 else if (*s == '~')
2087                 {
2088                         /* Add a plural if needed */
2089                         if (!(mode & OD_NO_PLURAL) && (o_ptr->number != 1))
2090                         {
2091                                 char k = t[-1];
2092
2093                                 /* Mega-Hack */
2094
2095                                 /* Hack -- "Cutlass-es" and "Torch-es" */
2096                                 if ((k == 's') || (k == 'h')) *t++ = 'e';
2097
2098                                 /* Add an 's' */
2099                                 *t++ = 's';
2100                         }
2101                         s++;
2102                 }
2103 #endif
2104
2105                 /* Normal */
2106                 else
2107                 {
2108                         /* Copy */
2109                         *t++ = *s++;
2110                 }
2111         }
2112
2113         /* Terminate */
2114         *t = '\0';
2115
2116
2117 #ifdef JP
2118         /* '『'から始まる伝説のアイテムの名前は最後に付加する */
2119         if (known)
2120         {
2121                 /* ランダムアーティファクトの名前はセーブファイルに記録
2122                    されるので、英語版の名前もそれらしく変換する */
2123                 if (o_ptr->art_name)
2124                 {
2125                         char temp[256];
2126                         int itemp;
2127                         strcpy(temp, quark_str(o_ptr->art_name));
2128                         /* MEGA HACK by ita */
2129                         if (strncmp(temp, "『", 2) == 0 ||
2130                             strncmp(temp, "《", 2) == 0)
2131                                 t = object_desc_str(t, temp);
2132                         else if (temp[0] == '\'')
2133                         {
2134                                 itemp = strlen(temp);
2135                                 temp[itemp - 1] = 0;
2136                                 t = object_desc_str(t, "『");
2137                                 t = object_desc_str(t, &temp[1]);
2138                                 t = object_desc_str(t, "』");
2139                         }
2140                 }
2141                 else if (object_is_fixed_artifact(o_ptr))
2142                 {
2143                         artifact_type *a_ptr = &a_info[o_ptr->name1];
2144                         if (strncmp(a_name + a_ptr->name, "『", 2) == 0)
2145                         {
2146                                 t = object_desc_str(t, a_name + a_ptr->name);
2147                         }
2148                 }
2149                 else if (o_ptr->inscription)
2150                 {
2151                         concptr str = quark_str(o_ptr->inscription);
2152
2153                         while(*str)
2154                         {
2155                                 if (iskanji(*str))
2156                                 {
2157                                         str += 2;
2158                                         continue;
2159                                 }
2160                                 if (*str == '#') break;
2161                                 str++;
2162                         }
2163                         if (*str)
2164                         {
2165                                 /* Find the '#' */
2166                                 concptr str_aux = my_strchr(quark_str(o_ptr->inscription), '#');
2167
2168                                 /* Add the false name */
2169                                 t = object_desc_str(t,"『");
2170                                 t = object_desc_str(t, &str_aux[1]);
2171                                 t = object_desc_str(t,"』");
2172                         }
2173                 }
2174         }
2175 #else
2176         if (object_is_smith(o_ptr))
2177         {
2178                 t = object_desc_str(t,format(" of %s the Smith",p_ptr->name));
2179         }
2180
2181         /* Hack -- Append "Artifact" or "Special" names */
2182         if (known && !have_flag(flgs, TR_FULL_NAME))
2183         {
2184                 /* Is it a new random artifact ? */
2185                 if (o_ptr->art_name)
2186                 {
2187                         t = object_desc_chr(t, ' ');
2188                         t = object_desc_str(t, quark_str(o_ptr->art_name));
2189                 }
2190
2191                 /* Grab any artifact name */
2192                 else if (object_is_fixed_artifact(o_ptr))
2193                 {
2194                         artifact_type *a_ptr = &a_info[o_ptr->name1];
2195
2196                         t = object_desc_chr(t, ' ');
2197                         t = object_desc_str(t, a_name + a_ptr->name);
2198                 }
2199
2200                 /* Grab any ego-item name */
2201                 else
2202                 {
2203                         if (object_is_ego(o_ptr))
2204                         {
2205                                 ego_item_type *e_ptr = &e_info[o_ptr->name2];
2206
2207                                 t = object_desc_chr(t, ' ');
2208                                 t = object_desc_str(t, e_name + e_ptr->name);
2209                         }
2210
2211                         if (o_ptr->inscription && my_strchr(quark_str(o_ptr->inscription), '#'))
2212                         {
2213                                 /* Find the '#' */
2214                                 concptr str = my_strchr(quark_str(o_ptr->inscription), '#');
2215
2216                                 /* Add the false name */
2217                                 t = object_desc_chr(t, ' ');
2218                                 t = object_desc_str(t, &str[1]);
2219                         }
2220                 }
2221         }
2222 #endif
2223
2224
2225         /* No more details wanted */
2226         if (mode & OD_NAME_ONLY) goto object_desc_done;
2227
2228         /* Hack -- Chests must be described in detail */
2229         if (o_ptr->tval == TV_CHEST)
2230         {
2231                 /* Not searched yet */
2232                 if (!known)
2233                 {
2234                         /* Nothing */
2235                 }
2236
2237                 /* May be "empty" */
2238                 else if (!o_ptr->pval)
2239                 {
2240                         t = object_desc_str(t, _("(空)", " (empty)"));
2241                 }
2242
2243                 /* May be "disarmed" */
2244                 else if (o_ptr->pval < 0)
2245                 {
2246                         if (chest_traps[0 - o_ptr->pval])
2247                         {
2248                                 t = object_desc_str(t, _("(解除済)", " (disarmed)"));
2249                         }
2250                         else
2251                         {
2252                                 t = object_desc_str(t, _("(非施錠)", " (unlocked)"));
2253                         }
2254                 }
2255
2256                 /* Describe the traps, if any */
2257                 else
2258                 {
2259                         /* Describe the traps */
2260                         switch (chest_traps[o_ptr->pval])
2261                         {
2262                                 case 0:
2263                                 {
2264                                         t = object_desc_str(t, _("(施錠)", " (Locked)"));
2265                                         break;
2266                                 }
2267                                 case CHEST_LOSE_STR:
2268                                 {
2269                                         t = object_desc_str(t, _("(毒針)", " (Poison Needle)"));
2270                                         break;
2271                                 }
2272                                 case CHEST_LOSE_CON:
2273                                 {
2274                                         t = object_desc_str(t, _("(毒針)", " (Poison Needle)"));
2275                                         break;
2276                                 }
2277                                 case CHEST_POISON:
2278                                 {
2279                                         t = object_desc_str(t, _("(ガス・トラップ)", " (Gas Trap)"));
2280                                         break;
2281                                 }
2282                                 case CHEST_PARALYZE:
2283                                 {
2284                                         t = object_desc_str(t, _("(ガス・トラップ)", " (Gas Trap)"));
2285                                         break;
2286                                 }
2287                                 case CHEST_EXPLODE:
2288                                 {
2289                                         t = object_desc_str(t, _("(爆発装置)", " (Explosion Device)"));
2290                                         break;
2291                                 }
2292                                 case CHEST_SUMMON:
2293                                 case CHEST_BIRD_STORM:
2294                                 case CHEST_E_SUMMON:
2295                                 case CHEST_H_SUMMON:
2296                                 {
2297                                         t = object_desc_str(t, _("(召喚のルーン)", " (Summoning Runes)"));
2298                                         break;
2299                                 }
2300                                 case CHEST_RUNES_OF_EVIL:
2301                                 {
2302                                         t = object_desc_str(t, _("(邪悪なルーン)", " (Gleaming Black Runes)"));
2303                                         break;
2304                                 }
2305                                 case CHEST_ALARM:
2306                                 {
2307                                         t = object_desc_str(t, _("(警報装置)", " (Alarm)"));
2308                                         break;
2309                                 }
2310                                 default:
2311                                 {
2312                                         t = object_desc_str(t, _("(マルチ・トラップ)", " (Multiple Traps)"));
2313                                         break;
2314                                 }
2315                         }
2316                 }
2317         }
2318
2319
2320         /* Display the item like a weapon */
2321         if (have_flag(flgs, TR_SHOW_MODS)) show_weapon = TRUE;
2322
2323         /* Display the item like a weapon */
2324         if (object_is_smith(o_ptr) && (o_ptr->xtra3 == 1 + ESSENCE_SLAY_GLOVE))
2325                 show_weapon = TRUE;
2326
2327         /* Display the item like a weapon */
2328         if (o_ptr->to_h && o_ptr->to_d) show_weapon = TRUE;
2329
2330         /* Display the item like armour */
2331         if (o_ptr->ac) show_armour = TRUE;
2332
2333
2334         /* Dump base weapon info */
2335         switch (o_ptr->tval)
2336         {
2337                 /* Missiles and Weapons */
2338                 case TV_SHOT:
2339                 case TV_BOLT:
2340                 case TV_ARROW:
2341                 case TV_HAFTED:
2342                 case TV_POLEARM:
2343                 case TV_SWORD:
2344             case TV_DIGGING:
2345                 
2346                 /* In Vault Quest, hide the dice of target weapon. */
2347                 if(object_is_quest_target(o_ptr) && !known)
2348                 {
2349                         break;
2350                 }
2351
2352                 /* Append a "damage" string */
2353                 t = object_desc_chr(t, ' ');
2354                 t = object_desc_chr(t, p1);
2355                 t = object_desc_num(t, o_ptr->dd);
2356                 t = object_desc_chr(t, 'd');
2357                 t = object_desc_num(t, o_ptr->ds);
2358                 t = object_desc_chr(t, p2);
2359
2360                 /* All done */
2361                 break;
2362
2363
2364                 /* Bows get a special "damage string" */
2365                 case TV_BOW:
2366
2367                 /* Mega-Hack -- Extract the "base power" */
2368                 power = bow_tmul(o_ptr->sval);
2369
2370                 /* Apply the "Extra Might" flag */
2371                 if (have_flag(flgs, TR_XTRA_MIGHT)) power++;
2372
2373                 /* Append a special "damage" string */
2374                 t = object_desc_chr(t, ' ');
2375                 t = object_desc_chr(t, p1);
2376                 t = object_desc_chr(t, 'x');
2377                 t = object_desc_num(t, power);
2378                 t = object_desc_chr(t, p2);
2379                 
2380                 fire_rate = calc_num_fire(o_ptr);
2381                 /* Show Fire rate */
2382                 if (fire_rate != 0 && power > 0 && known)
2383                 {       
2384                         fire_rate = bow_energy(o_ptr->sval) / fire_rate;
2385                         
2386                         t = object_desc_chr(t, ' ');
2387                         t = object_desc_chr(t, p1);                     
2388                         t = object_desc_num(t,  fire_rate/100);
2389                         t = object_desc_chr(t,  '.');
2390                         t = object_desc_num(t,  fire_rate%100);
2391                         t = object_desc_str(t, "turn");
2392                         t = object_desc_chr(t, p2);
2393                 }
2394                 
2395                 /* All done */
2396                 break;
2397         }
2398
2399
2400         /* Add the weapon bonuses */
2401         if (known)
2402         {
2403                 /* Show the tohit/todam on request */
2404                 if (show_weapon)
2405                 {
2406                         t = object_desc_chr(t, ' ');
2407                         t = object_desc_chr(t, p1);
2408                         t = object_desc_int(t, o_ptr->to_h);
2409                         t = object_desc_chr(t, ',');
2410                         t = object_desc_int(t, o_ptr->to_d);
2411                         t = object_desc_chr(t, p2);
2412                 }
2413
2414                 /* Show the tohit if needed */
2415                 else if (o_ptr->to_h)
2416                 {
2417                         t = object_desc_chr(t, ' ');
2418                         t = object_desc_chr(t, p1);
2419                         t = object_desc_int(t, o_ptr->to_h);
2420                         t = object_desc_chr(t, p2);
2421                 }
2422
2423                 /* Show the todam if needed */
2424                 else if (o_ptr->to_d)
2425                 {
2426                         t = object_desc_chr(t, ' ');
2427                         t = object_desc_chr(t, p1);
2428                         t = object_desc_int(t, o_ptr->to_d);
2429                         t = object_desc_chr(t, p2);
2430                 }
2431         }
2432
2433         bow_ptr = &inventory[INVEN_BOW];
2434
2435         /* If have a firing weapon + ammo matches bow */
2436         if (bow_ptr->k_idx && (o_ptr->tval == p_ptr->tval_ammo))
2437         {
2438                 int avgdam = o_ptr->dd * (o_ptr->ds + 1) * 10 / 2;
2439                 int tmul = bow_tmul(bow_ptr->sval);
2440                 ENERGY energy_fire = bow_energy(bow_ptr->sval);
2441
2442                 /* See if the bow is "known" - then set damage bonus */
2443                 if (object_is_known(bow_ptr)) avgdam += (bow_ptr->to_d * 10);
2444
2445                 /* Effect of ammo */
2446                 if (known) avgdam += (o_ptr->to_d * 10);
2447
2448                 /* Get extra "power" from "extra might" */
2449                 if (p_ptr->xtra_might) tmul++;
2450
2451                 tmul = tmul * (100 + (int)(adj_str_td[p_ptr->stat_ind[A_STR]]) - 128);
2452
2453                 /* Launcher multiplier */
2454                 avgdam *= tmul;
2455                 avgdam /= (100 * 10);
2456
2457                 /* Get extra damage from concentration */
2458                 if (p_ptr->concent) avgdam = boost_concentration_damage(avgdam);
2459                 
2460                 if (avgdam < 0) avgdam = 0;
2461
2462                 /* Display (shot damage/ shot damage with critical/ avg damage with critical) */
2463                 t = object_desc_chr(t, ' ');
2464                 t = object_desc_chr(t, p1);
2465                 
2466                 if(show_ammo_no_crit)
2467                 {
2468                         /* Damage with no-crit */
2469                         t = object_desc_num(t, avgdam);
2470                         t = object_desc_str(t, show_ammo_detail ? "/shot " : "/");
2471                 }
2472                 
2473                 /* Apply Expect damage of Critical */
2474                 avgdam = calc_expect_crit_shot(o_ptr->weight, o_ptr->to_h, bow_ptr->to_h, avgdam);
2475                 t = object_desc_num(t, avgdam);
2476                 
2477                 t = show_ammo_no_crit ? object_desc_str(t, show_ammo_detail ? "/crit " : "/")
2478                                                           : object_desc_str(t, show_ammo_detail ? "/shot " : "/");
2479         
2480                 if (p_ptr->num_fire == 0)
2481                 {
2482                         t = object_desc_chr(t, '0');
2483                 }
2484                 else
2485                 {
2486                         /* Calc effects of energy */
2487                         avgdam *= (p_ptr->num_fire * 100);
2488                         avgdam /= energy_fire;
2489                         t = object_desc_num(t, avgdam);
2490                         t = object_desc_str(t, show_ammo_detail ? "/turn" : "");
2491                         
2492                         if(show_ammo_crit_ratio)
2493                         {
2494                                 int percent = calc_crit_ratio_shot(known ? o_ptr->to_h : 0, known ? bow_ptr->to_h : 0);
2495                                 
2496                                 t = object_desc_chr(t, '/');
2497                                 t = object_desc_num(t, percent / 100);
2498                                 t = object_desc_chr(t, '.');
2499                 if(percent % 100 < 10)
2500                 {
2501                                     t = object_desc_chr(t, '0');
2502                 }
2503                                 t = object_desc_num(t, percent % 100);
2504                                 t = object_desc_str(t, show_ammo_detail ? "% crit" : "%");
2505                         }
2506                 }
2507
2508                 t = object_desc_chr(t, p2);
2509         }
2510         else if ((p_ptr->pclass == CLASS_NINJA) && (o_ptr->tval == TV_SPIKE))
2511         {
2512                 int avgdam = p_ptr->mighty_throw ? (1 + 3) : 1;
2513                 s16b energy_fire = 100 - p_ptr->lev;
2514
2515                 avgdam += ((p_ptr->lev + 30) * (p_ptr->lev + 30) - 900) / 55;
2516
2517                 /* Display (shot damage/ avg damage) */
2518                 t = object_desc_chr(t, ' ');
2519                 t = object_desc_chr(t, p1);
2520                 t = object_desc_num(t, avgdam);
2521                 t = object_desc_chr(t, '/');
2522
2523                 /* Calc effects of energy */
2524                 avgdam = 100 * avgdam / energy_fire;
2525
2526                 t = object_desc_num(t, avgdam);
2527                 t = object_desc_chr(t, p2);
2528         }
2529
2530         /* Add the armor bonuses */
2531         if (known)
2532         {
2533                 /* Show the armor class info */
2534                 if (show_armour)
2535                 {
2536                         t = object_desc_chr(t, ' ');
2537                         t = object_desc_chr(t, b1);
2538                         t = object_desc_num(t, o_ptr->ac);
2539                         t = object_desc_chr(t, ',');
2540                         t = object_desc_int(t, o_ptr->to_a);
2541                         t = object_desc_chr(t, b2);
2542                 }
2543
2544                 /* No base armor, but does increase armor */
2545                 else if (o_ptr->to_a)
2546                 {
2547                         t = object_desc_chr(t, ' ');
2548                         t = object_desc_chr(t, b1);
2549                         t = object_desc_int(t, o_ptr->to_a);
2550                         t = object_desc_chr(t, b2);
2551                 }
2552         }
2553
2554         /* Hack -- always show base armor */
2555         else if (show_armour)
2556         {
2557                 t = object_desc_chr(t, ' ');
2558                 t = object_desc_chr(t, b1);
2559                 t = object_desc_num(t, o_ptr->ac);
2560                 t = object_desc_chr(t, b2);
2561         }
2562
2563
2564         /* No more details wanted */
2565         if (mode & OD_NAME_AND_ENCHANT) goto object_desc_done;
2566
2567
2568         if (known) /* Known item only */
2569         {
2570                 /*
2571                  * Hack -- Wands and Staffs have charges.  Make certain how many charges
2572                  * a stack of staffs really has is clear. -LM-
2573                  */
2574                 if (((o_ptr->tval == TV_STAFF) || (o_ptr->tval == TV_WAND)))
2575                 {
2576                         /* Dump " (N charges)" */
2577                         t = object_desc_chr(t, ' ');
2578                         t = object_desc_chr(t, p1);
2579
2580                         /* Clear explaination for staffs. */
2581                         if ((o_ptr->tval == TV_STAFF) && (o_ptr->number > 1))
2582                         {
2583                                 t = object_desc_num(t, o_ptr->number);
2584                                 t = object_desc_str(t, "x ");
2585                         }
2586                         t = object_desc_num(t, o_ptr->pval);
2587 #ifdef JP
2588                         t = object_desc_str(t, "回分");
2589 #else
2590                         t = object_desc_str(t, " charge");
2591                         if (o_ptr->pval != 1) t = object_desc_chr(t, 's');
2592 #endif
2593
2594                         t = object_desc_chr(t, p2);
2595                 }
2596                 /* Hack -- Rods have a "charging" indicator.  Now that stacks of rods may
2597                  * be in any state of charge or discharge, this now includes a number. -LM-
2598                  */
2599                 else if (o_ptr->tval == TV_ROD)
2600                 {
2601                         /* Hack -- Dump " (# charging)" if relevant */
2602                         if (o_ptr->timeout)
2603                         {
2604                                 /* Stacks of rods display an exact count of charging rods. */
2605                                 if (o_ptr->number > 1)
2606                                 {
2607                                         /* Paranoia. */
2608                                         if (k_ptr->pval == 0) k_ptr->pval = 1;
2609
2610                                         /* Find out how many rods are charging, by dividing
2611                                          * current timeout by each rod's maximum timeout.
2612                                          * Ensure that any remainder is rounded up.  Display
2613                                          * very discharged stacks as merely fully discharged.
2614                                          */
2615                                         power = (o_ptr->timeout + (k_ptr->pval - 1)) / k_ptr->pval;
2616                                         if (power > o_ptr->number) power = o_ptr->number;
2617
2618                                         /* Display prettily. */
2619                                         t = object_desc_str(t, " (");
2620                                         t = object_desc_num(t, power);
2621                                         t = object_desc_str(t, _("本 充填中)", " charging)"));
2622                                 }
2623
2624                                 /* "one Rod of Perception (1 charging)" would look tacky. */
2625                                 else
2626                                 {
2627                                         t = object_desc_str(t, _("(充填中)", " (charging)"));
2628                                 }
2629                         }
2630                 }
2631
2632                 /* Dump "pval" flags for wearable items */
2633                 if (have_pval_flags(flgs))
2634                 {
2635                         /* Start the display */
2636                         t = object_desc_chr(t, ' ');
2637                         t = object_desc_chr(t, p1);
2638
2639                         /* Dump the "pval" itself */
2640                         t = object_desc_int(t, o_ptr->pval);
2641
2642                         /* Do not display the "pval" flags */
2643                         if (have_flag(flgs, TR_HIDE_TYPE))
2644                         {
2645                                 /* Nothing */
2646                         }
2647
2648                         /* Speed */
2649                         else if (have_flag(flgs, TR_SPEED))
2650                         {
2651                                 /* Dump " to speed" */
2652                                 t = object_desc_str(t, _("加速", " to speed"));
2653                         }
2654
2655                         /* Attack speed */
2656                         else if (have_flag(flgs, TR_BLOWS))
2657                         {
2658                                 /* Add " attack" */
2659 #ifdef JP
2660                                 t = object_desc_str(t, "攻撃");
2661 #else
2662                                 t = object_desc_str(t, " attack");
2663
2664                                 /* Add "attacks" */
2665                                 if (ABS(o_ptr->pval) != 1) t = object_desc_chr(t, 's');
2666 #endif
2667                         }
2668
2669                         /* Stealth */
2670                         else if (have_flag(flgs, TR_STEALTH))
2671                         {
2672                                 /* Dump " to stealth" */
2673                                 t = object_desc_str(t, _("隠密", " to stealth"));
2674                         }
2675
2676                         /* Search */
2677                         else if (have_flag(flgs, TR_SEARCH))
2678                         {
2679                                 /* Dump " to searching" */
2680                                 t = object_desc_str(t, _("探索", " to searching"));
2681                         }
2682
2683                         /* Infravision */
2684                         else if (have_flag(flgs, TR_INFRA))
2685                         {
2686                                 /* Dump " to infravision" */
2687                                 t = object_desc_str(t, _("赤外線視力", " to infravision"));
2688                         }
2689
2690                         /* Finish the display */
2691                         t = object_desc_chr(t, p2);
2692                 }
2693
2694                 /* Hack -- Process Lanterns/Torches */
2695                 if ((o_ptr->tval == TV_LITE) && (!(object_is_fixed_artifact(o_ptr) || (o_ptr->sval == SV_LITE_FEANOR))))
2696                 {
2697                         /* Hack -- Turns of light for normal lites */
2698 #ifdef JP
2699                         t = object_desc_chr(t, '(');
2700 #else
2701                         t = object_desc_str(t, " (with ");
2702 #endif
2703
2704                         if (o_ptr->name2 == EGO_LITE_LONG) t = object_desc_num(t, o_ptr->xtra4 * 2);
2705                         else t = object_desc_num(t, o_ptr->xtra4);
2706                         t = object_desc_str(t, _("ターンの寿命)", " turns of light)"));
2707                 }
2708
2709                 /* Indicate charging objects, but not rods. */
2710                 if (o_ptr->timeout && (o_ptr->tval != TV_ROD))
2711                 {
2712                         /* Hack -- Dump " (charging)" if relevant */
2713                         t = object_desc_str(t, _("(充填中)", " (charging)"));
2714                 }
2715         }
2716
2717
2718         /* No more details wanted */
2719         if (mode & OD_OMIT_INSCRIPTION) goto object_desc_done;
2720
2721
2722         /* Prepare real inscriptions in a buffer */
2723         tmp_val2[0] = '\0';
2724
2725         /* Auto abbreviation inscribe */
2726         if ((abbrev_extra || abbrev_all) && (o_ptr->ident & IDENT_MENTAL))
2727         {
2728                 if (!o_ptr->inscription || !my_strchr(quark_str(o_ptr->inscription), '%'))
2729                 {
2730                         bool kanji, all;
2731
2732 #ifdef JP
2733                         kanji = TRUE;
2734 #else
2735                         kanji = FALSE;
2736 #endif
2737                         all = abbrev_all;
2738
2739                         get_ability_abbreviation(tmp_val2, o_ptr, kanji, all);
2740                 }
2741         }
2742
2743         /* Use the standard inscription if available */
2744         if (o_ptr->inscription)
2745         {
2746                 char buff[1024];
2747
2748                 if (tmp_val2[0]) strcat(tmp_val2, ", ");
2749
2750                 /* Get inscription and convert {%} */
2751                 get_inscription(buff, o_ptr);
2752
2753                 /* strcat with correct treating of kanji */
2754                 my_strcat(tmp_val2, buff, sizeof(tmp_val2));
2755         }
2756
2757
2758         /* No fake inscription yet */
2759         fake_insc_buf[0] = '\0';
2760
2761         /* Use the game-generated "feeling" otherwise, if available */
2762         if (o_ptr->feeling)
2763         {
2764                 strcpy(fake_insc_buf, game_inscriptions[o_ptr->feeling]);
2765         }
2766
2767         /* Note "cursed" if the item is known to be cursed */
2768         else if (object_is_cursed(o_ptr) && (known || (o_ptr->ident & IDENT_SENSE)))
2769         {
2770                 strcpy(fake_insc_buf, _("呪われている", "cursed"));
2771         }
2772
2773         /* Note "unidentified" if the item is unidentified */
2774         else if (((o_ptr->tval == TV_RING) || (o_ptr->tval == TV_AMULET)
2775                    || (o_ptr->tval == TV_LITE) || (o_ptr->tval == TV_FIGURINE))
2776                  && aware && !known
2777                  && !(o_ptr->ident & IDENT_SENSE))
2778         {
2779                 strcpy(fake_insc_buf, _("未鑑定", "unidentified"));
2780         }
2781
2782         /* Mega-Hack -- note empty wands/staffs */
2783         else if (!known && (o_ptr->ident & IDENT_EMPTY))
2784         {
2785                 strcpy(fake_insc_buf, _("空", "empty"));
2786         }
2787
2788         /* Note "tried" if the object has been tested unsuccessfully */
2789         else if (!aware && object_is_tried(o_ptr))
2790         {
2791                 strcpy(fake_insc_buf, _("未判明", "tried"));
2792         }
2793
2794         /* Note the discount, if any */
2795         if (o_ptr->discount)
2796         {
2797                 /* Hidden by real inscription unless in a store */
2798                 if (!tmp_val2[0] || (o_ptr->ident & IDENT_STORE))
2799                 {
2800                         char discount_num_buf[4];
2801
2802                         /* Append to other fake inscriptions if any */
2803                         if (fake_insc_buf[0]) strcat(fake_insc_buf, ", ");
2804
2805                         (void)object_desc_num(discount_num_buf, o_ptr->discount);
2806                         strcat(fake_insc_buf, discount_num_buf);
2807                         strcat(fake_insc_buf, _("%引き", "% off"));
2808                 }
2809         }
2810
2811
2812         /* Append the inscription, if any */
2813         if (fake_insc_buf[0] || tmp_val2[0])
2814         {
2815                 /* Append the inscription */
2816                 t = object_desc_chr(t, ' ');
2817                 t = object_desc_chr(t, c1);
2818
2819                 /* Append fake inscriptions */
2820                 if (fake_insc_buf[0])
2821                 {
2822                         t = object_desc_str(t, fake_insc_buf);
2823                 }
2824
2825                 /* Append a separater */
2826                 if (fake_insc_buf[0] && tmp_val2[0])
2827                 {
2828                         t = object_desc_chr(t, ',');
2829                         t = object_desc_chr(t, ' ');
2830                 }
2831
2832                 /* Append real inscriptions */
2833                 if (tmp_val2[0])
2834                 {
2835                         t = object_desc_str(t, tmp_val2);
2836                 }
2837
2838                 t = object_desc_chr(t, c2);
2839         }
2840
2841 object_desc_done:
2842         my_strcpy(buf, tmp_val, MAX_NLEN);
2843 }
2844
2845