OSDN Git Service

Merge pull request #3532 from sikabane-works/release/3.0.0.87-alpha
[hengbandforosx/hengbandosx.git] / src / save / item-writer.cpp
1 #include "save/item-writer.h"
2 #include "artifact/random-art-effects.h"
3 #include "load/old/item-flag-types-savefile50.h"
4 #include "save/save-util.h"
5 #include "system/baseitem-info.h"
6 #include "system/item-entity.h"
7 #include "util/bit-flags-calculator.h"
8 #include "util/enum-converter.h"
9
10 static void write_item_flags(ItemEntity *o_ptr, BIT_FLAGS *flags)
11 {
12     if (o_ptr->pval) {
13         set_bits(*flags, SaveDataItemFlagType::PVAL);
14     }
15
16     if (o_ptr->discount) {
17         set_bits(*flags, SaveDataItemFlagType::DISCOUNT);
18     }
19
20     if (o_ptr->number != 1) {
21         set_bits(*flags, SaveDataItemFlagType::NUMBER);
22     }
23
24     if (o_ptr->is_fixed_artifact()) {
25         set_bits(*flags, SaveDataItemFlagType::FIXED_ARTIFACT_IDX);
26     }
27
28     if (o_ptr->is_ego()) {
29         set_bits(*flags, SaveDataItemFlagType::EGO_IDX);
30     }
31
32     if (o_ptr->timeout) {
33         set_bits(*flags, SaveDataItemFlagType::TIMEOUT);
34     }
35
36     if (o_ptr->to_h) {
37         set_bits(*flags, SaveDataItemFlagType::TO_H);
38     }
39
40     if (o_ptr->to_d) {
41         set_bits(*flags, SaveDataItemFlagType::TO_D);
42     }
43
44     if (o_ptr->to_a) {
45         set_bits(*flags, SaveDataItemFlagType::TO_A);
46     }
47
48     if (o_ptr->ac) {
49         set_bits(*flags, SaveDataItemFlagType::AC);
50     }
51
52     if (o_ptr->dd) {
53         set_bits(*flags, SaveDataItemFlagType::DD);
54     }
55
56     if (o_ptr->ds) {
57         set_bits(*flags, SaveDataItemFlagType::DS);
58     }
59
60     if (o_ptr->ident) {
61         set_bits(*flags, SaveDataItemFlagType::IDENT);
62     }
63
64     if (o_ptr->marked.any()) {
65         set_bits(*flags, SaveDataItemFlagType::MARKED);
66     }
67
68     if (o_ptr->art_flags.any()) {
69         set_bits(*flags, SaveDataItemFlagType::ART_FLAGS);
70     }
71
72     if (o_ptr->curse_flags.any()) {
73         set_bits(*flags, SaveDataItemFlagType::CURSE_FLAGS);
74     }
75
76     if (o_ptr->held_m_idx) {
77         set_bits(*flags, SaveDataItemFlagType::HELD_M_IDX);
78     }
79
80     if (o_ptr->activation_id > RandomArtActType::NONE) {
81         set_bits(*flags, SaveDataItemFlagType::ACTIVATION_ID);
82     }
83
84     if (o_ptr->chest_level > 0) {
85         set_bits(*flags, SaveDataItemFlagType::CHEST_LEVEL);
86     }
87
88     if (o_ptr->captured_monster_speed > 0) {
89         set_bits(*flags, SaveDataItemFlagType::CAPTURED_MONSTER_SPEED);
90     }
91
92     if (o_ptr->fuel > 0) {
93         set_bits(*flags, SaveDataItemFlagType::FUEL);
94     }
95
96     if (o_ptr->captured_monster_current_hp > 0) {
97         set_bits(*flags, SaveDataItemFlagType::CAPTURED_MONSTER_CURRENT_HP);
98     }
99
100     if (o_ptr->captured_monster_max_hp) {
101         set_bits(*flags, SaveDataItemFlagType::XTRA5);
102     }
103
104     if (o_ptr->feeling) {
105         set_bits(*flags, SaveDataItemFlagType::FEELING);
106     }
107
108     if (o_ptr->is_inscribed()) {
109         set_bits(*flags, SaveDataItemFlagType::INSCRIPTION);
110     }
111
112     if (o_ptr->is_random_artifact()) {
113         set_bits(*flags, SaveDataItemFlagType::ART_NAME);
114     }
115
116     if (o_ptr->stack_idx) {
117         set_bits(*flags, SaveDataItemFlagType::STACK_IDX);
118     }
119
120     if (o_ptr->is_smith()) {
121         set_bits(*flags, SaveDataItemFlagType::SMITH);
122     }
123
124     wr_u32b(*flags);
125 }
126
127 static void write_item_info(ItemEntity *o_ptr, const BIT_FLAGS flags)
128 {
129     wr_s16b((int16_t)o_ptr->weight);
130     if (any_bits(flags, SaveDataItemFlagType::FIXED_ARTIFACT_IDX)) {
131         wr_s16b(enum2i(o_ptr->fixed_artifact_idx));
132     }
133
134     if (any_bits(flags, SaveDataItemFlagType::EGO_IDX)) {
135         wr_byte((byte)o_ptr->ego_idx);
136     }
137
138     if (any_bits(flags, SaveDataItemFlagType::TIMEOUT)) {
139         wr_s16b(o_ptr->timeout);
140     }
141
142     if (any_bits(flags, SaveDataItemFlagType::TO_H)) {
143         wr_s16b(o_ptr->to_h);
144     }
145
146     if (any_bits(flags, SaveDataItemFlagType::TO_D)) {
147         wr_s16b((int16_t)o_ptr->to_d);
148     }
149
150     if (any_bits(flags, SaveDataItemFlagType::TO_A)) {
151         wr_s16b(o_ptr->to_a);
152     }
153
154     if (any_bits(flags, SaveDataItemFlagType::AC)) {
155         wr_s16b(o_ptr->ac);
156     }
157
158     if (any_bits(flags, SaveDataItemFlagType::DD)) {
159         wr_byte((byte)o_ptr->dd);
160     }
161
162     if (any_bits(flags, SaveDataItemFlagType::DS)) {
163         wr_byte((byte)o_ptr->ds);
164     }
165
166     if (any_bits(flags, SaveDataItemFlagType::IDENT)) {
167         wr_byte(o_ptr->ident);
168     }
169
170     if (any_bits(flags, SaveDataItemFlagType::MARKED)) {
171         wr_FlagGroup_bytes(o_ptr->marked, wr_byte, 1);
172     }
173
174     if (any_bits(flags, SaveDataItemFlagType::ART_FLAGS)) {
175         wr_FlagGroup(o_ptr->art_flags, wr_byte);
176     }
177
178     if (any_bits(flags, SaveDataItemFlagType::CURSE_FLAGS)) {
179         wr_FlagGroup(o_ptr->curse_flags, wr_byte);
180     }
181
182     if (any_bits(flags, SaveDataItemFlagType::HELD_M_IDX)) {
183         wr_s16b(o_ptr->held_m_idx);
184     }
185
186     if (any_bits(flags, SaveDataItemFlagType::ACTIVATION_ID)) {
187         wr_s16b(enum2i(o_ptr->activation_id));
188     }
189
190     if (any_bits(flags, SaveDataItemFlagType::CHEST_LEVEL)) {
191         wr_byte(o_ptr->chest_level);
192     }
193
194     if (any_bits(flags, SaveDataItemFlagType::CAPTURED_MONSTER_SPEED)) {
195         wr_byte(o_ptr->captured_monster_speed);
196     }
197
198     if (any_bits(flags, SaveDataItemFlagType::FUEL)) {
199         wr_s16b(o_ptr->fuel);
200     }
201
202     if (any_bits(flags, SaveDataItemFlagType::CAPTURED_MONSTER_CURRENT_HP)) {
203         wr_s16b(o_ptr->captured_monster_current_hp);
204     }
205
206     if (any_bits(flags, SaveDataItemFlagType::XTRA5)) {
207         wr_s16b(o_ptr->captured_monster_max_hp);
208     }
209
210     if (any_bits(flags, SaveDataItemFlagType::FEELING)) {
211         wr_byte(o_ptr->feeling);
212     }
213
214     if (any_bits(flags, SaveDataItemFlagType::STACK_IDX)) {
215         wr_s16b(o_ptr->stack_idx);
216     }
217
218     if (any_bits(flags, SaveDataItemFlagType::SMITH)) {
219         if (o_ptr->smith_effect.has_value()) {
220             wr_s16b(enum2i(o_ptr->smith_effect.value()));
221         } else {
222             wr_s16b(0);
223         }
224
225         if (o_ptr->smith_act_idx.has_value()) {
226             wr_s16b(enum2i(o_ptr->smith_act_idx.value()));
227         } else {
228             wr_s16b(0);
229         }
230
231         wr_byte(o_ptr->smith_hit);
232         wr_byte(o_ptr->smith_damage);
233     }
234 }
235
236 /*!
237  * @brief アイテムオブジェクトを書き込む / Write an "item" record
238  * @param o_ptr アイテムオブジェクト保存元ポインタ
239  */
240 void wr_item(ItemEntity *o_ptr)
241 {
242     BIT_FLAGS flags = 0x00000000;
243     write_item_flags(o_ptr, &flags);
244
245     wr_s16b(o_ptr->bi_id);
246     wr_byte((byte)o_ptr->iy);
247     wr_byte((byte)o_ptr->ix);
248     if (any_bits(flags, SaveDataItemFlagType::PVAL)) {
249         wr_s16b(o_ptr->pval);
250     }
251
252     if (any_bits(flags, SaveDataItemFlagType::DISCOUNT)) {
253         wr_byte(o_ptr->discount);
254     }
255
256     if (any_bits(flags, SaveDataItemFlagType::NUMBER)) {
257         wr_byte((byte)o_ptr->number);
258     }
259
260     write_item_info(o_ptr, flags);
261     if (any_bits(flags, SaveDataItemFlagType::INSCRIPTION)) {
262         wr_string(o_ptr->inscription.value());
263     }
264
265     if (any_bits(flags, SaveDataItemFlagType::ART_NAME)) {
266         wr_string(o_ptr->randart_name.value());
267     }
268 }
269
270 /*!
271  * @brief セーブデータにアイテムの鑑定情報を書き込む / Write an "perception" record
272  * @param bi_id ベースアイテムのID
273  */
274 void wr_perception(short bi_id)
275 {
276     byte tmp8u = 0;
277     const auto &baseitem = baseitems_info[bi_id];
278     if (baseitem.aware) {
279         tmp8u |= 0x01;
280     }
281
282     if (baseitem.tried) {
283         tmp8u |= 0x02;
284     }
285
286     wr_byte(tmp8u);
287 }