Rulesave saves trade.type and trade.bonus correctly.
[freeciv.git] / common / extras.h
blobe8d2f8efa396ad84582e0739f0478fc0c049283b
1 /***********************************************************************
2 Freeciv - Copyright (C) 1996 - A Kjeldberg, L Gregersen, P Unold
3 This program is free software; you can redistribute it and/or modify
4 it under the terms of the GNU General Public License as published by
5 the Free Software Foundation; either version 2, or (at your option)
6 any later version.
8 This program is distributed in the hope that it will be useful,
9 but WITHOUT ANY WARRANTY; without even the implied warranty of
10 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 GNU General Public License for more details.
12 ***********************************************************************/
13 #ifndef FC__EXTRAS_H
14 #define FC__EXTRAS_H
16 #ifdef __cplusplus
17 extern "C" {
18 #endif /* __cplusplus */
20 /* common */
21 #include "base.h"
22 #include "fc_types.h"
23 #include "road.h"
24 #include "terrain.h"
26 /* Used in the network protocol. */
27 #define SPECENUM_NAME extra_flag_id
28 /* Tile with this extra is considered native for units in tile. */
29 #define SPECENUM_VALUE0 EF_NATIVE_TILE
30 #define SPECENUM_VALUE0NAME N_("?extraflag:NativeTile")
31 /* Refuel native units */
32 #define SPECENUM_VALUE1 EF_REFUEL
33 #define SPECENUM_VALUE1NAME N_("?extraflag:Refuel")
34 #define SPECENUM_VALUE2 EF_TERR_CHANGE_REMOVES
35 #define SPECENUM_VALUE2NAME N_("?extraflag:TerrChangeRemoves")
36 /* Extra will be built in cities automatically */
37 #define SPECENUM_VALUE3 EF_AUTO_ON_CITY_CENTER
38 #define SPECENUM_VALUE3NAME N_("?extraflag:AutoOnCityCenter")
39 /* Extra is always present in cities */
40 #define SPECENUM_VALUE4 EF_ALWAYS_ON_CITY_CENTER
41 #define SPECENUM_VALUE4NAME N_("?extraflag:AlwaysOnCityCenter")
42 /* Road style gfx from ocean extra connects to nearby land */
43 #define SPECENUM_VALUE5 EF_CONNECT_LAND
44 #define SPECENUM_VALUE5NAME N_("?extraflag:ConnectLand")
45 /* Counts towards Global Warming */
46 #define SPECENUM_VALUE6 EF_GLOBAL_WARMING
47 #define SPECENUM_VALUE6NAME N_("?extraflag:GlobalWarming")
48 /* Counts towards Nuclear Winter */
49 #define SPECENUM_VALUE7 EF_NUCLEAR_WINTER
50 #define SPECENUM_VALUE7NAME N_("?extraflag:NuclearWinter")
51 /* Owner's flag will be shown on the tile */
52 #define SPECENUM_VALUE8 EF_SHOW_FLAG
53 #define SPECENUM_VALUE8NAME N_("?extraflag:ShowFlag")
54 /* Extra's defense bonus will be counted to
55 * separate "Natural" defense layer. */
56 #define SPECENUM_VALUE9 EF_NATURAL_DEFENSE
57 #define SPECENUM_VALUE9NAME N_("?extraflag:NaturalDefense")
58 #define SPECENUM_COUNT EF_COUNT
59 #define SPECENUM_BITVECTOR bv_extra_flags
60 #include "specenum_gen.h"
62 #define EXTRA_NONE (-1)
64 struct extra_type
66 int id;
67 struct name_translation name;
68 enum extra_category category;
69 uint8_t causes;
70 uint8_t rmcauses;
72 char graphic_str[MAX_LEN_NAME];
73 char graphic_alt[MAX_LEN_NAME];
74 char activity_gfx[MAX_LEN_NAME];
75 char act_gfx_alt[MAX_LEN_NAME];
76 char act_gfx_alt2[MAX_LEN_NAME];
77 char rmact_gfx[MAX_LEN_NAME];
78 char rmact_gfx_alt[MAX_LEN_NAME];
80 struct requirement_vector reqs;
81 struct requirement_vector rmreqs;
83 /* 'buildable' is unclean. Clean solution would be to rely solely on extra_cause:
84 * if the extra cannot be built, it's not in the cause's list.
85 * But we currently rely on actually-not-buildable extras to be on the lists,
86 * for example for the editor to list non-buildable but editor-placeable
87 * extras. */
88 bool buildable;
89 int build_time;
90 int build_time_factor;
91 int removal_time;
92 int removal_time_factor;
94 int defense_bonus;
96 bv_unit_classes native_to;
98 bv_extra_flags flags;
99 bv_extras conflicts;
100 bv_extras hidden_by;
102 /* Same information as in hidden_by, but iterating through this list is much
103 * faster than through all extra types to check which ones are hiding this one.
104 * Only used client side. */
105 struct extra_type_list *hiders;
107 struct strvec *helptext;
109 struct
111 int special_idx;
112 struct base_type *base;
113 struct road_type *road;
114 } data;
117 /* get 'struct extra_type_list' and related functions: */
118 #define SPECLIST_TAG extra_type
119 #define SPECLIST_TYPE struct extra_type
120 #include "speclist.h"
122 #define extra_type_list_iterate(extralist, pextra) \
123 TYPED_LIST_ITERATE(struct extra_type, extralist, pextra)
124 #define extra_type_list_iterate_end LIST_ITERATE_END
126 #define extra_type_list_iterate_rev(extralist, pextra) \
127 TYPED_LIST_ITERATE_REV(struct extra_type, extralist, pextra)
128 #define extra_type_list_iterate_rev_end LIST_ITERATE_REV_END
130 void extras_init(void);
131 void extras_free(void);
133 int extra_count(void);
134 int extra_number(const struct extra_type *pextra);
135 struct extra_type *extra_by_number(int id);
137 /* For optimization purposes (being able to have it as macro instead of function
138 * call) this is now same as extra_number(). extras.c does have semantically correct
139 * implementation too. */
140 #define extra_index(_e_) (_e_)->id
142 struct extra_type *special_extra_get(int spe);
144 const char *extra_name_translation(const struct extra_type *pextra);
145 const char *extra_rule_name(const struct extra_type *pextra);
146 struct extra_type *extra_type_by_rule_name(const char *name);
147 struct extra_type *extra_type_by_translated_name(const char *name);
149 #define extra_base_get(_e_) (_e_)->data.base
150 #define extra_road_get(_e_) (_e_)->data.road
152 void extra_to_caused_by_list(struct extra_type *pextra, enum extra_cause cause);
153 struct extra_type_list *extra_type_list_by_cause(enum extra_cause cause);
154 struct extra_type *rand_extra_for_tile(struct tile *ptile, enum extra_cause cause);
156 void extra_to_category_list(struct extra_type *pextra, enum extra_category cat);
157 struct extra_type_list *extra_type_list_for_category(enum extra_category cat);
159 bool is_extra_caused_by(const struct extra_type *pextra, enum extra_cause cause);
160 bool is_extra_caused_by_worker_action(const struct extra_type *pextra);
161 bool is_extra_caused_by_action(const struct extra_type *pextra,
162 enum unit_activity act);
164 void extra_to_removed_by_list(struct extra_type *pextra, enum extra_rmcause rmcause);
165 struct extra_type_list *extra_type_list_by_rmcause(enum extra_rmcause rmcause);
167 bool is_extra_removed_by(const struct extra_type *pextra, enum extra_rmcause rmcause);
168 bool is_extra_removed_by_worker_action(const struct extra_type *pextra);
169 bool is_extra_removed_by_action(const struct extra_type *pextra,
170 enum unit_activity act);
172 bool is_extra_card_near(const struct tile *ptile, const struct extra_type *pextra);
173 bool is_extra_near_tile(const struct tile *ptile, const struct extra_type *pextra);
175 bool extra_can_be_built(const struct extra_type *pextra, const struct tile *ptile);
176 bool can_build_extra(struct extra_type *pextra,
177 const struct unit *punit,
178 const struct tile *ptile);
179 bool player_can_build_extra(const struct extra_type *pextra,
180 const struct player *pplayer,
181 const struct tile *ptile);
183 bool can_remove_extra(struct extra_type *pextra,
184 const struct unit *punit,
185 const struct tile *ptile);
186 bool player_can_remove_extra(const struct extra_type *pextra,
187 const struct player *pplayer,
188 const struct tile *ptile);
190 bool is_native_extra_to_uclass(const struct extra_type *pextra,
191 const struct unit_class *pclass);
192 bool is_native_extra_to_utype(const struct extra_type *pextra,
193 const struct unit_type *punittype);
194 bool is_native_tile_to_extra(const struct extra_type *pextra,
195 const struct tile *ptile);
197 bool extra_has_flag(const struct extra_type *pextra, enum extra_flag_id flag);
198 bool is_extra_flag_card_near(const struct tile *ptile,
199 enum extra_flag_id flag);
200 bool is_extra_flag_near_tile(const struct tile *ptile,
201 enum extra_flag_id flag);
203 bool extra_causes_env_upset(struct extra_type *pextra,
204 enum environment_upset_type upset);
206 bool can_extras_coexist(const struct extra_type *pextra1,
207 const struct extra_type *pextra2);
209 struct extra_type *next_extra_for_tile(const struct tile *ptile, enum extra_cause cause,
210 const struct player *pplayer,
211 const struct unit *punit);
212 struct extra_type *prev_extra_in_tile(const struct tile *ptile, enum extra_rmcause rmcause,
213 const struct player *pplayer,
214 const struct unit *punit);
216 enum extra_cause activity_to_extra_cause(enum unit_activity act);
217 enum extra_rmcause activity_to_extra_rmcause(enum unit_activity act);
219 struct player *extra_owner(const struct tile *ptile);
221 #define extra_type_iterate(_p) \
223 int _i_##_p; \
224 for (_i_##_p = 0; _i_##_p < game.control.num_extra_types; _i_##_p++) { \
225 struct extra_type *_p = extra_by_number(_i_##_p);
227 #define extra_type_iterate_end \
231 #define extra_type_by_cause_iterate(_cause, _extra) \
233 struct extra_type_list *_etl_##_extra = extra_type_list_by_cause(_cause); \
234 if (_etl_##_extra != NULL) { \
235 extra_type_list_iterate(_etl_##_extra, _extra) {
237 #define extra_type_by_cause_iterate_end \
238 } extra_type_list_iterate_end \
242 #define extra_type_by_cause_iterate_rev(_cause, _extra) \
244 struct extra_type_list *_etl_ = extra_type_list_by_cause(_cause); \
245 extra_type_list_iterate_rev(_etl_, _extra) {
247 #define extra_type_by_cause_iterate_rev_end \
248 } extra_type_list_iterate_rev_end \
251 #define extra_type_by_rmcause_iterate(_rmcause, _extra) \
253 struct extra_type_list *_etl_ = extra_type_list_by_rmcause(_rmcause); \
254 extra_type_list_iterate_rev(_etl_, _extra) {
256 #define extra_type_by_rmcause_iterate_end \
257 } extra_type_list_iterate_rev_end \
260 #define extra_type_by_category_iterate(_cat, _extra) \
262 struct extra_type_list *_etl_##_extra = extra_type_list_for_category(_cat); \
263 if (_etl_##_extra != NULL) { \
264 extra_type_list_iterate(_etl_##_extra, _extra) {
266 #define extra_type_by_category_iterate_end \
267 } extra_type_list_iterate_end \
271 #define extra_deps_iterate(_reqs, _dep) \
273 requirement_vector_iterate(_reqs, preq) { \
274 if (preq->source.kind == VUT_EXTRA \
275 && preq->present) { \
276 struct extra_type *_dep; \
277 _dep = preq->source.value.extra;
279 #define extra_deps_iterate_end \
281 } requirement_vector_iterate_end; \
284 #ifdef __cplusplus
286 #endif /* __cplusplus */
288 #endif /* FC__EXTRAS_H */