OpenTTD Source 20241224-master-gf74b0cf984
company_manager_face.h
Go to the documentation of this file.
1/*
2 * This file is part of OpenTTD.
3 * OpenTTD is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, version 2.
4 * OpenTTD is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
5 * See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with OpenTTD. If not, see <http://www.gnu.org/licenses/>.
6 */
7
10#ifndef COMPANY_MANAGER_FACE_H
11#define COMPANY_MANAGER_FACE_H
12
13#include "core/random_func.hpp"
14#include "core/bitmath_func.hpp"
15#include "table/sprites.h"
16#include "company_type.h"
17
30
31
33 CMFV_GENDER,
34 CMFV_ETHNICITY,
35 CMFV_GEN_ETHN,
36 CMFV_HAS_MOUSTACHE,
37 CMFV_HAS_TIE_EARRING,
38 CMFV_HAS_GLASSES,
39 CMFV_EYE_COLOUR,
40 CMFV_CHEEKS,
41 CMFV_CHIN,
42 CMFV_EYEBROWS,
43 CMFV_MOUSTACHE,
44 CMFV_LIPS,
45 CMFV_NOSE,
46 CMFV_HAIR,
47 CMFV_JACKET,
48 CMFV_COLLAR,
49 CMFV_TIE_EARRING,
50 CMFV_GLASSES,
51 CMFV_END,
52};
54
55
57 uint8_t offset;
58 uint8_t length;
59 uint8_t valid_values[GE_END];
60 SpriteID first_sprite[GE_END];
61};
62
65 /* Index off len WM WF BM BF WM WF BM BF
66 * CMFV_GENDER */ { 0, 1, { 2, 2, 2, 2 }, { 0, 0, 0, 0 } },
67 /* CMFV_ETHNICITY */ { 1, 2, { 2, 2, 2, 2 }, { 0, 0, 0, 0 } },
68 /* CMFV_GEN_ETHN */ { 0, 3, { 4, 4, 4, 4 }, { 0, 0, 0, 0 } },
69 /* CMFV_HAS_MOUSTACHE */ { 3, 1, { 2, 0, 2, 0 }, { 0, 0, 0, 0 } },
70 /* CMFV_HAS_TIE_EARRING */ { 3, 1, { 0, 2, 0, 2 }, { 0, 0, 0, 0 } },
71 /* CMFV_HAS_GLASSES */ { 4, 1, { 2, 2, 2, 2 }, { 0, 0, 0, 0 } },
72 /* CMFV_EYE_COLOUR */ { 5, 2, { 3, 3, 1, 1 }, { 0, 0, 0, 0 } },
73 /* CMFV_CHEEKS */ { 0, 0, { 1, 1, 1, 1 }, { 0x325, 0x326, 0x390, 0x3B0 } },
74 /* CMFV_CHIN */ { 7, 2, { 4, 1, 2, 2 }, { 0x327, 0x327, 0x391, 0x3B1 } },
75 /* CMFV_EYEBROWS */ { 9, 4, { 12, 16, 11, 16 }, { 0x32B, 0x337, 0x39A, 0x3B8 } },
76 /* CMFV_MOUSTACHE */ { 13, 2, { 3, 0, 3, 0 }, { 0x367, 0, 0x397, 0 } },
77 /* CMFV_LIPS */ { 13, 4, { 12, 10, 9, 9 }, { 0x35B, 0x351, 0x3A5, 0x3C8 } },
78 /* CMFV_NOSE */ { 17, 3, { 8, 4, 4, 5 }, { 0x349, 0x34C, 0x393, 0x3B3 } },
79 /* CMFV_HAIR */ { 20, 4, { 9, 5, 5, 5 }, { 0x382, 0x38B, 0x3D4, 0x3D9 } },
80 /* CMFV_JACKET */ { 24, 2, { 3, 3, 3, 3 }, { 0x36B, 0x378, 0x36B, 0x378 } },
81 /* CMFV_COLLAR */ { 26, 2, { 4, 4, 4, 4 }, { 0x36E, 0x37B, 0x36E, 0x37B } },
82 /* CMFV_TIE_EARRING */ { 28, 3, { 6, 3, 6, 3 }, { 0x372, 0x37F, 0x372, 0x3D1 } },
83 /* CMFV_GLASSES */ { 31, 1, { 2, 2, 2, 2 }, { 0x347, 0x347, 0x3AE, 0x3AE } }
84};
86static_assert(lengthof(_cmf_info) == CMFV_END);
87
97{
98 assert(_cmf_info[cmfv].valid_values[ge] != 0);
99
100 return GB(cmf, _cmf_info[cmfv].offset, _cmf_info[cmfv].length);
101}
102
112{
113 assert(val < _cmf_info[cmfv].valid_values[ge]);
114
115 SB(cmf, _cmf_info[cmfv].offset, _cmf_info[cmfv].length, val);
116}
117
131{
132 int8_t val = GetCompanyManagerFaceBits(cmf, cmfv, ge) + amount; // the new value for the cmfv
133
134 /* scales the new value to the correct scope */
135 if (val >= _cmf_info[cmfv].valid_values[ge]) {
136 val = 0;
137 } else if (val < 0) {
138 val = _cmf_info[cmfv].valid_values[ge] - 1;
139 }
140
141 SetCompanyManagerFaceBits(cmf, cmfv, ge, val); // save the new value
142}
143
152{
153 return GB(cmf, _cmf_info[cmfv].offset, _cmf_info[cmfv].length) < _cmf_info[cmfv].valid_values[ge];
154}
155
165{
166 assert(val < (1U << _cmf_info[cmfv].length));
167
168 return (val * _cmf_info[cmfv].valid_values[ge]) >> _cmf_info[cmfv].length;
169}
170
177{
178 IncreaseCompanyManagerFaceBits(cmf, CMFV_ETHNICITY, GE_WM, 0); // scales the ethnicity
179
180 GenderEthnicity ge = (GenderEthnicity)GB(cmf, _cmf_info[CMFV_GEN_ETHN].offset, _cmf_info[CMFV_GEN_ETHN].length); // gender & ethnicity of the face
181
182 /* Is a male face with moustache. Need to reduce CPU load in the loop. */
183 bool is_moust_male = !HasBit(ge, GENDER_FEMALE) && GetCompanyManagerFaceBits(cmf, CMFV_HAS_MOUSTACHE, ge) != 0;
184
185 for (CompanyManagerFaceVariable cmfv = CMFV_EYE_COLOUR; cmfv < CMFV_END; cmfv++) { // scales all other variables
186
187 /* The moustache variable will be scaled only if it is a male face with has a moustache */
188 if (cmfv != CMFV_MOUSTACHE || is_moust_male) {
189 IncreaseCompanyManagerFaceBits(cmf, cmfv, ge, 0);
190 }
191 }
192}
193
207{
208 cmf = randomizer.Next(); // random all company manager's face bits
209
210 /* scale ge: 0 == GE_WM, 1 == GE_WF, 2 == GE_BM, 3 == GE_BF (and maybe in future: ...) */
211 ge = (GenderEthnicity)((uint)ge % GE_END);
212
213 /* set the gender (and ethnicity) for the new company manager's face */
214 if (adv) {
215 SetCompanyManagerFaceBits(cmf, CMFV_GEN_ETHN, ge, ge);
216 } else {
217 SetCompanyManagerFaceBits(cmf, CMFV_GENDER, ge, HasBit(ge, GENDER_FEMALE));
218 }
219
220 /* scales all company manager's face bits to the correct scope */
222}
223
233{
234 assert(_cmf_info[cmfv].valid_values[ge] != 0);
235
236 return _cmf_info[cmfv].first_sprite[ge] + GB(cmf, _cmf_info[cmfv].offset, _cmf_info[cmfv].length);
237}
238
239void DrawCompanyManagerFace(CompanyManagerFace face, Colours colour, const Rect &r);
240
241#endif /* COMPANY_MANAGER_FACE_H */
Functions related to bit mathematics.
debug_inline constexpr bool HasBit(const T x, const uint8_t y)
Checks if a bit in a value is set.
constexpr T SB(T &x, const uint8_t s, const uint8_t n, const U d)
Set n bits in x starting at bit s to d.
debug_inline static constexpr uint GB(const T x, const uint8_t s, const uint8_t n)
Fetch n bits from x, started at bit s.
uint GetCompanyManagerFaceBits(CompanyManagerFace cmf, CompanyManagerFaceVariable cmfv, GenderEthnicity ge)
Make sure the table's size is right.
GenderEthnicity
The gender/race combinations that we have faces for.
@ GE_BM
A male of African origin (black)
@ GE_WF
A female of Caucasian origin (white)
@ GE_WM
A male of Caucasian origin (white)
@ ETHNICITY_BLACK
This bit set means black, otherwise white.
@ GE_BF
A female of African origin (black)
@ GENDER_FEMALE
This bit set means a female, otherwise male.
void SetCompanyManagerFaceBits(CompanyManagerFace &cmf, CompanyManagerFaceVariable cmfv, GenderEthnicity ge, uint val)
Sets the company manager's face bits for the given company manager's face variable.
void RandomCompanyManagerFaceBits(CompanyManagerFace &cmf, GenderEthnicity ge, bool adv, Randomizer &randomizer)
Make a random new face.
void ScaleAllCompanyManagerFaceBits(CompanyManagerFace &cmf)
Scales all company manager's face bits to the correct scope.
void DrawCompanyManagerFace(CompanyManagerFace face, Colours colour, const Rect &r)
Draws the face of a company manager's face.
uint ScaleCompanyManagerFaceValue(CompanyManagerFaceVariable cmfv, GenderEthnicity ge, uint val)
Scales a company manager's face bits variable to the correct scope.
bool AreCompanyManagerFaceBitsValid(CompanyManagerFace cmf, CompanyManagerFaceVariable cmfv, GenderEthnicity ge)
Checks whether the company manager's face bits have a valid range.
static const CompanyManagerFaceBitsInfo _cmf_info[]
Lookup table for indices into the CompanyManagerFace, valid ranges and sprites.
void IncreaseCompanyManagerFaceBits(CompanyManagerFace &cmf, CompanyManagerFaceVariable cmfv, GenderEthnicity ge, int8_t amount)
Increase/Decrease the company manager's face variable by the given amount.
CompanyManagerFaceVariable
Bitgroups of the CompanyManagerFace variable.
SpriteID GetCompanyManagerFaceSprite(CompanyManagerFace cmf, CompanyManagerFaceVariable cmfv, GenderEthnicity ge)
Gets the sprite to draw for the given company manager's face variable.
Types related to companies.
uint32_t CompanyManagerFace
Company manager face bits, info see in company_manager_face.h.
#define DECLARE_ENUM_AS_BIT_SET(enum_type)
Operators to allow to work with enum as with type safe bit set in C++.
Definition enum_type.hpp:35
#define DECLARE_POSTFIX_INCREMENT(enum_type)
Some enums need to have allowed incrementing (i.e.
Definition enum_type.hpp:18
uint32_t SpriteID
The number of a sprite, without mapping bits and colourtables.
Definition gfx_type.h:18
Pseudo random number generator.
This file contains all sprite-related enums and defines.
#define lengthof(array)
Return the length of an fixed size array.
Definition stdafx.h:280
Information about the valid values of CompanyManagerFace bitgroups as well as the sprites to draw.
SpriteID first_sprite[GE_END]
The first sprite per gender/ethnicity.
uint8_t length
Number of bits used in the CompanyManagerFace.
uint8_t valid_values[GE_END]
The number of valid values per gender/ethnicity.
uint8_t offset
Offset in bits into the CompanyManagerFace.
Structure to encapsulate the pseudo random number generators.
uint32_t Next()
Generate the next pseudo random number.
Specification of a rectangle with absolute coordinates of all edges.