OSDN Git Service

[Refactor] #37353 PROJECT_* 定義を新規ファイル projection.h へ移動。 / Move PROJECT_* definition...
[hengband/hengband.git] / src / realm-crusade.c
1 #include "angband.h"
2 #include "cmd-spell.h"
3 #include "spells-summon.h"
4 #include "projection.h"
5
6
7
8 /*!
9 * @brief 破邪領域魔法の各処理を行う
10 * @param spell 魔法ID
11 * @param mode 処理内容 (SPELL_NAME / SPELL_DESC / SPELL_INFO / SPELL_CAST)
12 * @return SPELL_NAME / SPELL_DESC / SPELL_INFO 時には文字列ポインタを返す。SPELL_CAST時はNULL文字列を返す。
13 */
14 concptr do_crusade_spell(SPELL_IDX spell, BIT_FLAGS mode)
15 {
16         bool name = (mode == SPELL_NAME) ? TRUE : FALSE;
17         bool desc = (mode == SPELL_DESC) ? TRUE : FALSE;
18         bool info = (mode == SPELL_INFO) ? TRUE : FALSE;
19         bool cast = (mode == SPELL_CAST) ? TRUE : FALSE;
20
21         DIRECTION dir;
22         PLAYER_LEVEL plev = p_ptr->lev;
23
24         switch (spell)
25         {
26         case 0:
27                 if (name) return _("懲罰", "Punishment");
28                 if (desc) return _("電撃のボルトもしくはビームを放つ。", "Fires a bolt or beam of lightning.");
29                 {
30                         DICE_NUMBER dice = 3 + (plev - 1) / 5;
31                         DICE_SID sides = 4;
32                         if (info) return info_damage(dice, sides, 0);
33                         if (cast)
34                         {
35                                 if (!get_aim_dir(&dir)) return NULL;
36                                 fire_bolt_or_beam(beam_chance() - 10, GF_ELEC, dir, damroll(dice, sides));
37                         }
38                 }
39                 break;
40
41         case 1:
42                 if (name) return _("邪悪存在感知", "Detect Evil");
43                 if (desc) return _("近くの邪悪なモンスターを感知する。", "Detects all evil monsters in your vicinity.");
44                 {
45                         POSITION rad = DETECT_RAD_DEFAULT;
46                         if (info) return info_radius(rad);
47                         if (cast)
48                         {
49                                 detect_monsters_evil(rad);
50                         }
51                 }
52                 break;
53
54         case 2:
55                 if (name) return _("恐怖除去", "Remove Fear");
56                 if (desc) return _("恐怖を取り除く。", "Removes fear.");
57                 {
58                         if (cast) set_afraid(0);
59                 }
60                 break;
61
62         case 3:
63                 if (name) return _("威圧", "Scare Monster");
64                 if (desc) return _("モンスター1体を恐怖させる。抵抗されると無効。", "Attempts to scare a monster.");
65
66                 {
67                         PLAYER_LEVEL power = plev;
68                         if (info) return info_power(power);
69                         if (cast)
70                         {
71                                 if (!get_aim_dir(&dir)) return NULL;
72                                 fear_monster(dir, power);
73                         }
74                 }
75                 break;
76
77         case 4:
78                 if (name) return _("聖域", "Sanctuary");
79                 if (desc) return _("隣接した全てのモンスターを眠らせる。抵抗されると無効。", "Attempts to sleep monsters in the adjacent squares.");
80                 {
81                         PLAYER_LEVEL power = plev;
82                         if (info) return info_power(power);
83                         if (cast) sleep_monsters_touch();
84                 }
85                 break;
86
87         case 5:
88                 if (name) return _("入口", "Portal");
89                 if (desc) return _("中距離のテレポートをする。", "Teleport medium distance.");
90
91                 {
92                         POSITION range = 25 + plev / 2;
93                         if (info) return info_range(range);
94                         if (cast) teleport_player(range, 0L);
95                 }
96                 break;
97
98         case 6:
99                 if (name) return _("スターダスト", "Star Dust");
100                 if (desc) return _("ターゲット付近に閃光のボルトを連射する。", "Fires many bolts of light near the target.");
101
102                 {
103                         DICE_NUMBER dice = 3 + (plev - 1) / 9;
104                         DICE_SID sides = 2;
105                         if (info) return info_multi_damage_dice(dice, sides);
106                         if (cast)
107                         {
108                                 if (!get_aim_dir(&dir)) return NULL;
109                                 fire_blast(GF_LITE, dir, dice, sides, 10, 3);
110                         }
111                 }
112                 break;
113
114         case 7:
115                 if (name) return _("身体浄化", "Purify");
116                 if (desc) return _("傷、毒、朦朧から全快する。", "Heals all cut, stun and poison status.");
117                 {
118                         if (cast)
119                         {
120                                 set_cut(0);
121                                 set_poisoned(0);
122                                 set_stun(0);
123                         }
124                 }
125                 break;
126
127         case 8:
128                 if (name) return _("邪悪飛ばし", "Scatter Evil");
129                 if (desc) return _("邪悪なモンスター1体をテレポートさせる。抵抗されると無効。", "Attempts to teleport an evil monster away.");
130
131                 {
132                         int power = MAX_SIGHT * 5;
133                         if (info) return info_power(power);
134                         if (cast)
135                         {
136                                 if (!get_aim_dir(&dir)) return NULL;
137                                 fire_ball(GF_AWAY_EVIL, dir, power, 0);
138                         }
139                 }
140                 break;
141
142         case 9:
143                 if (name) return _("聖なる光球", "Holy Orb");
144                 if (desc) return _("聖なる力をもつ宝珠を放つ。邪悪なモンスターに対して大きなダメージを与えるが、善良なモンスターには効果がない。",
145                         "Fires a ball with holy power. Hurts evil monsters greatly, but don't effect good monsters.");
146
147                 {
148                         DICE_NUMBER dice = 3;
149                         DICE_SID sides = 6;
150                         POSITION rad = (plev < 30) ? 2 : 3;
151                         int base;
152                         if (p_ptr->pclass == CLASS_PRIEST ||
153                                 p_ptr->pclass == CLASS_HIGH_MAGE ||
154                                 p_ptr->pclass == CLASS_SORCERER)
155                                 base = plev + plev / 2;
156                         else
157                                 base = plev + plev / 4;
158
159
160                         if (info) return info_damage(dice, sides, base);
161
162                         if (cast)
163                         {
164                                 if (!get_aim_dir(&dir)) return NULL;
165
166                                 fire_ball(GF_HOLY_FIRE, dir, damroll(dice, sides) + base, rad);
167                         }
168                 }
169                 break;
170
171         case 10:
172                 if (name) return _("悪魔払い", "Exorcism");
173                 if (desc) return _("視界内の全てのアンデッド及び悪魔にダメージを与え、邪悪なモンスターを恐怖させる。",
174                         "Damages all undead and demons in sight, and scares all evil monsters in sight.");
175                 {
176                         DICE_SID sides = plev;
177                         int power = plev;
178                         if (info) return info_damage(1, sides, 0);
179                         if (cast)
180                         {
181                                 dispel_undead(randint1(sides));
182                                 dispel_demons(randint1(sides));
183                                 turn_evil(power);
184                         }
185                 }
186                 break;
187
188         case 11:
189                 if (name) return _("解呪", "Remove Curse");
190                 if (desc) return _("アイテムにかかった弱い呪いを解除する。", "Removes normal curses from equipped items.");
191                 {
192                         if (cast) (void)remove_curse();
193                 }
194                 break;
195
196         case 12:
197                 if (name) return _("透明視認", "Sense Unseen");
198                 if (desc) return _("一定時間、透明なものが見えるようになる。", "Gives see invisible for a while.");
199
200                 {
201                         int base = 24;
202
203                         if (info) return info_duration(base, base);
204
205                         if (cast)
206                         {
207                                 set_tim_invis(randint1(base) + base, FALSE);
208                         }
209                 }
210                 break;
211
212         case 13:
213                 if (name) return _("対邪悪結界", "Protection from Evil");
214                 if (desc) return _("邪悪なモンスターの攻撃を防ぐバリアを張る。", "Gives aura which protect you from evil monster's physical attack.");
215
216                 {
217                         int base = 25;
218                         DICE_SID sides = 3 * plev;
219
220                         if (info) return info_duration(base, sides);
221
222                         if (cast)
223                         {
224                                 set_protevil(randint1(sides) + base, FALSE);
225                         }
226                 }
227                 break;
228
229         case 14:
230                 if (name) return _("裁きの雷", "Judgment Thunder");
231                 if (desc) return _("強力な電撃のボルトを放つ。", "Fires a powerful bolt of lightning.");
232
233                 {
234                         HIT_POINT dam = plev * 5;
235
236                         if (info) return info_damage(0, 0, dam);
237
238                         if (cast)
239                         {
240                                 if (!get_aim_dir(&dir)) return NULL;
241                                 fire_bolt(GF_ELEC, dir, dam);
242                         }
243                 }
244                 break;
245
246         case 15:
247                 if (name) return _("聖なる御言葉", "Holy Word");
248                 if (desc) return _("視界内の邪悪な存在に大きなダメージを与え、体力を回復し、毒、恐怖、朦朧状態、負傷から全快する。",
249                         "Damages all evil monsters in sight, heals HP somewhat, and completely heals poison, fear, stun and cut status.");
250
251                 {
252                         int dam_sides = plev * 6;
253                         int heal = 100;
254
255                         if (info) return format(_("損:1d%d/回%d", "dam:d%d/h%d"), dam_sides, heal);
256                         if (cast)
257                         {
258                                 dispel_evil(randint1(dam_sides));
259                                 hp_player(heal);
260                                 set_afraid(0);
261                                 set_poisoned(0);
262                                 set_stun(0);
263                                 set_cut(0);
264                         }
265                 }
266                 break;
267
268         case 16:
269                 if (name) return _("開かれた道", "Unbarring Ways");
270                 if (desc) return _("一直線上の全ての罠と扉を破壊する。", "Fires a beam which destroy traps and doors.");
271
272                 {
273                         if (cast)
274                         {
275                                 if (!get_aim_dir(&dir)) return NULL;
276
277                                 destroy_door(dir);
278                         }
279                 }
280                 break;
281
282         case 17:
283                 if (name) return _("封魔", "Arrest");
284                 if (desc) return _("邪悪なモンスターの動きを止める。", "Attempts to paralyze an evil monster.");
285
286                 {
287                         int power = plev * 2;
288
289                         if (info) return info_power(power);
290
291                         if (cast)
292                         {
293                                 if (!get_aim_dir(&dir)) return NULL;
294                                 stasis_evil(dir);
295                         }
296                 }
297                 break;
298
299         case 18:
300                 if (name) return _("聖なるオーラ", "Holy Aura");
301                 if (desc) return _("一定時間、邪悪なモンスターを傷つける聖なるオーラを得る。",
302                         "Gives aura of holy power which injures evil monsters which attacked you for a while.");
303
304                 {
305                         int base = 20;
306
307                         if (info) return info_duration(base, base);
308
309                         if (cast)
310                         {
311                                 set_tim_sh_holy(randint1(base) + base, FALSE);
312                         }
313                 }
314                 break;
315
316         case 19:
317                 if (name) return _("アンデッド&悪魔退散", "Dispel Undead & Demons");
318                 if (desc) return _("視界内の全てのアンデッド及び悪魔にダメージを与える。", "Damages all undead and demons in sight.");
319
320                 {
321                         DICE_SID sides = plev * 4;
322
323                         if (info) return info_damage(1, sides, 0);
324
325                         if (cast)
326                         {
327                                 dispel_undead(randint1(sides));
328                                 dispel_demons(randint1(sides));
329                         }
330                 }
331                 break;
332
333         case 20:
334                 if (name) return _("邪悪退散", "Dispel Evil");
335                 if (desc) return _("視界内の全ての邪悪なモンスターにダメージを与える。", "Damages all evil monsters in sight.");
336
337                 {
338                         DICE_SID sides = plev * 4;
339
340                         if (info) return info_damage(1, sides, 0);
341
342                         if (cast)
343                         {
344                                 dispel_evil(randint1(sides));
345                         }
346                 }
347                 break;
348
349         case 21:
350                 if (name) return _("聖なる刃", "Holy Blade");
351                 if (desc) return _("通常の武器に滅邪の属性をつける。", "Makes current weapon especially deadly against evil monsters.");
352
353                 {
354                         if (cast)
355                         {
356                                 brand_weapon(13);
357                         }
358                 }
359                 break;
360
361         case 22:
362                 if (name) return _("スターバースト", "Star Burst");
363                 if (desc) return _("巨大な閃光の球を放つ。", "Fires a huge ball of powerful light.");
364
365                 {
366                         HIT_POINT dam = 100 + plev * 2;
367                         POSITION rad = 4;
368
369                         if (info) return info_damage(0, 0, dam);
370
371                         if (cast)
372                         {
373                                 if (!get_aim_dir(&dir)) return NULL;
374
375                                 fire_ball(GF_LITE, dir, dam, rad);
376                         }
377                 }
378                 break;
379
380         case 23:
381                 if (name) return _("天使召喚", "Summon Angel");
382                 if (desc) return _("天使を1体召喚する。", "Summons an angel.");
383
384                 {
385                         if (cast)
386                         {
387                                 bool pet = !one_in_(3);
388                                 u32b flg = 0L;
389
390                                 if (pet) flg |= PM_FORCE_PET;
391                                 else flg |= PM_NO_PET;
392                                 if (!(pet && (plev < 50))) flg |= PM_ALLOW_GROUP;
393
394                                 if (summon_specific((pet ? -1 : 0), p_ptr->y, p_ptr->x, (plev * 3) / 2, SUMMON_ANGEL, flg, '\0'))
395                                 {
396                                         if (pet)
397                                         {
398                                                 msg_print(_("「ご用でございますか、ご主人様」", "'What is thy bidding... Master?'"));
399                                         }
400                                         else
401                                         {
402                                                 msg_print(_("「我は汝の下僕にあらず! 悪行者よ、悔い改めよ!」", "Mortal! Repent of thy impiousness."));
403                                         }
404                                 }
405                         }
406                 }
407                 break;
408
409         case 24:
410                 if (name) return _("士気高揚", "Heroism");
411                 if (desc) return _("一定時間、ヒーロー気分になる。", "Removes fear, and gives bonus to hit and 10 more HP for a while.");
412
413                 {
414                         int base = 25;
415
416                         if (info) return info_duration(base, base);
417
418                         if (cast)
419                         {
420                                 (void)heroism(base);
421                         }
422                 }
423                 break;
424
425         case 25:
426                 if (name) return _("呪い退散", "Dispel Curse");
427                 if (desc) return _("アイテムにかかった強力な呪いを解除する。", "Removes normal and heavy curse from equipped items.");
428
429                 {
430                         if (cast) (void)remove_all_curse();
431                 }
432                 break;
433
434         case 26:
435                 if (name) return _("邪悪追放", "Banish Evil");
436                 if (desc) return _("視界内の全ての邪悪なモンスターをテレポートさせる。抵抗されると無効。",
437                         "Teleports all evil monsters in sight away unless resisted.");
438
439                 {
440                         int power = 100;
441
442                         if (info) return info_power(power);
443
444                         if (cast)
445                         {
446                                 if (banish_evil(power))
447                                 {
448                                         msg_print(_("神聖な力が邪悪を打ち払った!", "The holy power banishes evil!"));
449                                 }
450                         }
451                 }
452                 break;
453
454         case 27:
455                 if (name) return _("ハルマゲドン", "Armageddon");
456                 if (desc) return _("周辺のアイテム、モンスター、地形を破壊する。", "Destroy everything in nearby area.");
457
458                 {
459                         int base = 12;
460                         DICE_SID sides = 4;
461
462                         if (cast)
463                         {
464                                 destroy_area(p_ptr->y, p_ptr->x, base + randint1(sides), FALSE);
465                         }
466                 }
467                 break;
468
469         case 28:
470                 if (name) return _("目には目を", "An Eye for an Eye");
471                 if (desc) return _("一定時間、自分がダメージを受けたときに攻撃を行ったモンスターに対して同等のダメージを与える。",
472                         "Gives special aura for a while. When you are attacked by a monster, the monster are injured with same amount of damage as you take.");
473
474                 {
475                         int base = 10;
476
477                         if (info) return info_duration(base, base);
478
479                         if (cast)
480                         {
481                                 set_tim_eyeeye(randint1(base) + base, FALSE);
482                         }
483                 }
484                 break;
485
486         case 29:
487                 if (name) return _("神の怒り", "Wrath of the God");
488                 if (desc) return _("ターゲットの周囲に分解の球を多数落とす。", "Drops many balls of disintegration near the target.");
489
490                 {
491                         HIT_POINT dam = plev * 3 + 25;
492                         POSITION rad = 2;
493
494                         if (info) return info_multi_damage(dam);
495
496                         if (cast)
497                         {
498                                 if (!cast_wrath_of_the_god(dam, rad)) return NULL;
499                         }
500                 }
501                 break;
502
503         case 30:
504                 if (name) return _("神威", "Divine Intervention");
505                 if (desc) return _("隣接するモンスターに聖なるダメージを与え、視界内のモンスターにダメージ、減速、朦朧、混乱、恐怖、眠りを与える。さらに体力を回復する。",
506                         "Damages all adjacent monsters with holy power. Damages and attempt to slow, stun, confuse, scare and freeze all monsters in sight. And heals HP.");
507
508                 {
509                         int b_dam = plev * 11;
510                         int d_dam = plev * 4;
511                         int heal = 100;
512                         int power = plev * 4;
513
514                         if (info) return format(_("回%d/損%d+%d", "h%d/dm%d+%d"), heal, d_dam, b_dam / 2);
515                         if (cast)
516                         {
517                                 project(0, 1, p_ptr->y, p_ptr->x, b_dam, GF_HOLY_FIRE, PROJECT_KILL, -1);
518                                 dispel_monsters(d_dam);
519                                 slow_monsters(plev);
520                                 stun_monsters(power);
521                                 confuse_monsters(power);
522                                 turn_monsters(power);
523                                 stasis_monsters(power);
524                                 hp_player(heal);
525                         }
526                 }
527                 break;
528
529         case 31:
530                 if (name) return _("聖戦", "Crusade");
531                 if (desc) return _("視界内の善良なモンスターをペットにしようとし、ならなかった場合及び善良でないモンスターを恐怖させる。さらに多数の加速された騎士を召喚し、ヒーロー、祝福、加速、対邪悪結界を得る。",
532                         "Attempts to charm all good monsters in sight, and scare all non-charmed monsters, and summons great number of knights, and gives heroism, bless, speed and protection from evil.");
533
534                 {
535                         if (cast)
536                         {
537                                 int base = 25;
538                                 int sp_sides = 20 + plev;
539                                 int sp_base = plev;
540
541                                 int i;
542                                 crusade();
543                                 for (i = 0; i < 12; i++)
544                                 {
545                                         int attempt = 10;
546                                         POSITION my = 0, mx = 0;
547
548                                         while (attempt--)
549                                         {
550                                                 scatter(&my, &mx, p_ptr->y, p_ptr->x, 4, 0);
551
552                                                 /* Require empty grids */
553                                                 if (cave_empty_bold2(my, mx)) break;
554                                         }
555                                         if (attempt < 0) continue;
556                                         summon_specific(-1, my, mx, plev, SUMMON_KNIGHTS, (PM_ALLOW_GROUP | PM_FORCE_PET | PM_HASTE), '\0');
557                                 }
558                                 set_hero(randint1(base) + base, FALSE);
559                                 set_blessed(randint1(base) + base, FALSE);
560                                 set_fast(randint1(sp_sides) + sp_base, FALSE);
561                                 set_protevil(randint1(base) + base, FALSE);
562                                 set_afraid(0);
563                         }
564                 }
565                 break;
566         }
567
568         return "";
569 }
570