1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165
|
#pragma once
#ifndef CATA_SRC_PROFESSION_H
#define CATA_SRC_PROFESSION_H
#include <iosfwd>
#include <list>
#include <map>
#include <set>
#include <string>
#include <utility>
#include <vector>
#include "ret_val.h"
#include "translations.h"
#include "type_id.h"
class JsonObject;
class addiction;
class avatar;
class item;
class Character;
template<typename T>
class generic_factory;
struct trait_and_var;
class profession
{
public:
using StartingSkill = std::pair<skill_id, int>;
using StartingSkillList = std::vector<StartingSkill>;
struct itypedec {
itype_id type_id;
/** Snippet id, @see snippet_library. */
snippet_id snip_id;
// compatible with when this was just a std::string
explicit itypedec( const std::string &t ) :
type_id( t ), snip_id( snippet_id::NULL_ID() ) {
}
itypedec( const std::string &t, const snippet_id &d ) : type_id( t ), snip_id( d ) {
}
};
using itypedecvec = std::vector<itypedec>;
friend class string_id<profession>;
friend class generic_factory<profession>;
friend struct mod_tracker;
private:
string_id<profession> id;
bool was_loaded = false;
translation _name_male;
translation _name_female;
translation _description_male;
translation _description_female;
signed int _point_cost = 0;
// TODO: In professions.json, replace lists of itypes (legacy) with item groups
itypedecvec legacy_starting_items;
itypedecvec legacy_starting_items_male;
itypedecvec legacy_starting_items_female;
item_group_id _starting_items = item_group_id( "EMPTY_GROUP" );
item_group_id _starting_items_male = item_group_id( "EMPTY_GROUP" );
item_group_id _starting_items_female = item_group_id( "EMPTY_GROUP" );
itype_id no_bonus; // See profession::items and class json_item_substitution in profession.cpp
// does this profession require a specific achiement to unlock
std::optional<achievement_id> _requirement;
std::vector<addiction> _starting_addictions;
std::vector<bionic_id> _starting_CBMs;
std::vector<proficiency_id> _starting_proficiencies;
std::vector<recipe_id> _starting_recipes;
std::vector<trait_and_var> _starting_traits;
std::vector<matype_id> _starting_martialarts;
std::vector<matype_id> _starting_martialarts_choices;
std::set<trait_id> _forbidden_traits;
std::vector<mtype_id> _starting_pets;
vproto_id _starting_vehicle = vproto_id::NULL_ID();
// the int is what level the spell starts at
std::map<spell_id, int> _starting_spells;
std::set<std::string> flags; // flags for some special properties of the profession
StartingSkillList _starting_skills;
std::vector<mission_type_id> _missions; // starting missions for profession
std::string _subtype;
void check_item_definitions( const itypedecvec &items ) const;
void load( const JsonObject &jo, std::string_view src );
public:
//these three aren't meant for external use, but had to be made public regardless
profession();
static void load_profession( const JsonObject &jo, const std::string &src );
static void load_item_substitutions( const JsonObject &jo );
// these should be the only ways used to get at professions
static const profession *generic(); // points to the generic, default profession
static const std::vector<profession> &get_all();
static std::vector<string_id<profession>> get_all_hobbies();
static bool has_initialized();
// clear profession map, every profession pointer becomes invalid!
static void reset();
/** calls @ref check_definition for each profession */
static void check_definitions();
/** Check that item/CBM/addiction/skill definitions are valid. */
void check_definition() const;
const string_id<profession> &ident() const;
std::string gender_appropriate_name( bool male ) const;
std::string description( bool male ) const;
signed int point_cost() const;
std::list<item> items( bool male, const std::vector<trait_id> &traits ) const;
std::vector<addiction> addictions() const;
vproto_id vehicle() const;
std::vector<mtype_id> pets() const;
std::vector<bionic_id> CBMs() const;
std::vector<proficiency_id> proficiencies() const;
std::vector<recipe_id> recipes() const;
std::vector<matype_id> ma_known() const;
std::vector<matype_id> ma_choices() const;
int ma_choice_amount;
StartingSkillList skills() const;
const std::vector<mission_type_id> &missions() const;
int age_lower = 21;
int age_upper = 55;
std::vector<std::pair<string_id<profession>, mod_id>> src;
std::optional<achievement_id> get_requirement() const;
std::map<spell_id, int> spells() const;
void learn_spells( avatar &you ) const;
/**
* Check if this type of profession has a certain flag set.
*
* Current flags: none
*/
bool has_flag( const std::string &flag ) const;
/**
* Check if the given player can pick this job with the given amount
* of points.
*
* @return true, if player can pick profession. Otherwise - false.
*/
ret_val<void> can_afford( const Character &you, int points ) const;
/**
* Do you have the necessary achievement state
*/
ret_val<void> can_pick() const;
bool is_locked_trait( const trait_id &trait ) const;
bool is_forbidden_trait( const trait_id &trait ) const;
std::vector<trait_and_var> get_locked_traits() const;
std::set<trait_id> get_forbidden_traits() const;
bool is_hobby() const;
};
#endif // CATA_SRC_PROFESSION_H
|