OSDN Git Service

[Refactor] struct player_type を class PlayerType に置換。
[hengbandforosx/hengbandosx.git] / src / racial / racial-android.cpp
1 #include "racial/racial-android.h"
2 #include "inventory/inventory-slot-types.h"
3 #include "object-enchant/object-ego.h"
4 #include "object-enchant/trg-types.h"
5 #include "object-hook/hook-weapon.h"
6 #include "object/object-kind.h"
7 #include "object/object-value-calc.h"
8 #include "object/object-value.h"
9 #include "player-info/equipment-info.h"
10 #include "player/player-status.h"
11 #include "spell-kind/spells-launcher.h"
12 #include "effect/attribute-types.h"
13 #include "sv-definition/sv-armor-types.h"
14 #include "sv-definition/sv-protector-types.h"
15 #include "sv-definition/sv-weapon-types.h"
16 #include "system/artifact-type-definition.h"
17 #include "system/object-type-definition.h"
18 #include "system/player-type-definition.h"
19 #include "target/target-getter.h"
20 #include "view/display-messages.h"
21
22 bool android_inside_weapon(PlayerType *player_ptr)
23 {
24     DIRECTION dir;
25     if (!get_aim_dir(player_ptr, &dir))
26         return false;
27
28     if (player_ptr->lev < 10) {
29         msg_print(_("レイガンを発射した。", "You fire your ray gun."));
30         fire_bolt(player_ptr, AttributeType::MISSILE, dir, (player_ptr->lev + 1) / 2);
31         return true;
32     }
33
34     if (player_ptr->lev < 25) {
35         msg_print(_("ブラスターを発射した。", "You fire your blaster."));
36         fire_bolt(player_ptr, AttributeType::MISSILE, dir, player_ptr->lev);
37         return true;
38     }
39
40     if (player_ptr->lev < 35) {
41         msg_print(_("バズーカを発射した。", "You fire your bazooka."));
42         fire_ball(player_ptr, AttributeType::MISSILE, dir, player_ptr->lev * 2, 2);
43         return true;
44     }
45
46     if (player_ptr->lev < 45) {
47         msg_print(_("ビームキャノンを発射した。", "You fire a beam cannon."));
48         fire_beam(player_ptr, AttributeType::MISSILE, dir, player_ptr->lev * 2);
49         return true;
50     }
51
52     msg_print(_("ロケットを発射した。", "You fire a rocket."));
53     fire_rocket(player_ptr, AttributeType::ROCKET, dir, player_ptr->lev * 5, 2);
54     return true;
55 }
56
57 void calc_android_exp(PlayerType *player_ptr)
58 {
59     uint32_t total_exp = 0;
60     if (player_ptr->is_dead || (player_ptr->prace != PlayerRaceType::ANDROID))
61         return;
62
63     for (int i = INVEN_MAIN_HAND; i < INVEN_TOTAL; i++) {
64         object_type *o_ptr = &player_ptr->inventory_list[i];
65         object_type forge;
66         object_type *q_ptr = &forge;
67         uint32_t value, exp;
68         DEPTH level = std::max(k_info[o_ptr->k_idx].level - 8, 1);
69
70         if ((i == INVEN_MAIN_RING) || (i == INVEN_SUB_RING) || (i == INVEN_NECK) || (i == INVEN_LITE))
71             continue;
72         if (!o_ptr->k_idx)
73             continue;
74
75         q_ptr->wipe();
76         q_ptr->copy_from(o_ptr);
77         q_ptr->discount = 0;
78         q_ptr->curse_flags.clear();
79
80         if (o_ptr->is_fixed_artifact()) {
81             level = (level + std::max(a_info[o_ptr->name1].level - 8, 5)) / 2;
82             level += std::min(20, a_info[o_ptr->name1].rarity / (a_info[o_ptr->name1].gen_flags.has(ItemGenerationTraitType::INSTA_ART) ? 10 : 3));
83         } else if (o_ptr->is_ego()) {
84             level += std::max(3, (e_info[o_ptr->name2].rating - 5) / 2);
85         } else if (o_ptr->art_name) {
86             int32_t total_flags = flag_cost(o_ptr, o_ptr->pval);
87             int fake_level;
88
89             if (!o_ptr->is_weapon_ammo()) {
90                 if (total_flags < 15000)
91                     fake_level = 10;
92                 else if (total_flags < 35000)
93                     fake_level = 25;
94                 else
95                     fake_level = 40;
96             } else {
97                 if (total_flags < 20000)
98                     fake_level = 10;
99                 else if (total_flags < 45000)
100                     fake_level = 25;
101                 else
102                     fake_level = 40;
103             }
104
105             level = std::max(level, (level + std::max(fake_level - 8, 5)) / 2 + 3);
106         }
107
108         value = object_value_real(q_ptr);
109         if (value <= 0)
110             continue;
111         if ((o_ptr->tval == ItemKindType::SOFT_ARMOR) && (o_ptr->sval == SV_ABUNAI_MIZUGI) && (player_ptr->ppersonality != PERSONALITY_SEXY))
112             value /= 32;
113         if (value > 5000000L)
114             value = 5000000L;
115         if ((o_ptr->tval == ItemKindType::DRAG_ARMOR) || (o_ptr->tval == ItemKindType::CARD))
116             level /= 2;
117
118         if (o_ptr->is_artifact() || o_ptr->is_ego() || (o_ptr->tval == ItemKindType::DRAG_ARMOR) || ((o_ptr->tval == ItemKindType::HELM) && (o_ptr->sval == SV_DRAGON_HELM))
119             || ((o_ptr->tval == ItemKindType::SHIELD) && (o_ptr->sval == SV_DRAGON_SHIELD)) || ((o_ptr->tval == ItemKindType::GLOVES) && (o_ptr->sval == SV_SET_OF_DRAGON_GLOVES))
120             || ((o_ptr->tval == ItemKindType::BOOTS) && (o_ptr->sval == SV_PAIR_OF_DRAGON_GREAVE)) || ((o_ptr->tval == ItemKindType::SWORD) && (o_ptr->sval == SV_DIAMOND_EDGE))) {
121             if (level > 65)
122                 level = 35 + (level - 65) / 5;
123             else if (level > 35)
124                 level = 25 + (level - 35) / 3;
125             else if (level > 15)
126                 level = 15 + (level - 15) / 2;
127             exp = std::min<uint>(100000, value) / 2 * level * level;
128             if (value > 100000L)
129                 exp += (value - 100000L) / 8 * level * level;
130         } else {
131             exp = std::min<uint>(100000, value) * level;
132             if (value > 100000L)
133                 exp += (value - 100000L) / 4 * level;
134         }
135         if ((((i == INVEN_MAIN_HAND) || (i == INVEN_SUB_HAND)) && (has_melee_weapon(player_ptr, i))) || (i == INVEN_BOW))
136             total_exp += exp / 48;
137         else
138             total_exp += exp / 16;
139         if (i == INVEN_BODY)
140             total_exp += exp / 32;
141     }
142
143     player_ptr->exp = player_ptr->max_exp = total_exp;
144     check_experience(player_ptr);
145 }