ScummVM API documentation
inv_popup.h
1 /* ScummVM - Graphic Adventure Engine
2  *
3  * ScummVM is the legal property of its developers, whose names
4  * are too numerous to list here. Please refer to the COPYRIGHT
5  * file distributed with this source distribution.
6  *
7  * This program is free software: you can redistribute it and/or modify
8  * it under the terms of the GNU General Public License as published by
9  * the Free Software Foundation, either version 3 of the License, or
10  * (at your option) any later version.
11  *
12  * This program is distributed in the hope that it will be useful,
13  * but WITHOUT ANY WARRANTY; without even the implied warranty of
14  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15  * GNU General Public License for more details.
16  *
17  * You should have received a copy of the GNU General Public License
18  * along with this program. If not, see <http://www.gnu.org/licenses/>.
19  *
20  */
21 
22 #ifndef QDENGINE_MINIGAMES_INV_POPUP_H
23 #define QDENGINE_MINIGAMES_INV_POPUP_H
24 
25 #include "common/debug.h"
26 
27 #include "qdengine/qd_fwd.h"
28 #include "qdengine/qdcore/qd_minigame_interface.h"
29 
30 namespace QDEngine {
31 
33 public:
35  ~qdInvPopupMiniGame() {}
36 
37  bool init(const qdEngineInterface *engine_interface) {
38  debugC(1, kDebugMinigames, "InvPopup::init()");
39 
40  _engine = engine_interface;
41  _scene = engine_interface->current_scene_interface();
42  if (!_scene)
43  return false;
44 
45  //_invClickObj = _scene->object_interface("$inv_click_flag");
46  _invDescObj = _scene->object_interface("%inv_desc");
47  _invDescCloseupObj = _scene->object_interface("%inv_desc_closeup");
48  //_invActiveFlagObj = _scene->object_interface("$inv_active_flag");
49  _blockPersObj = _scene->object_interface("\x24\xe1\xeb\xee\xea\xe8\xf0\xee\xe2\xea\xe0\x5f\xef\xe5\xf0\xf1\xee\xed\xe0\xe6\xe0"); // "$блокировка_персонажа"
50  _blockPersFlagObj = _scene->object_interface("\x24\xe1\xeb\xee\xea\xe8\xf0\xee\xe2\xea\xe0\x5f\xef\xe5\xf0\xf1\xee\xed\xe0\xe6\xe0\x5f\xf4\xeb\xe0\xe3"); // "$блокировка_персонажа_флаг"
51 
52  _shveikObj = _scene->personage_interface("\xd8\xe2\xe5\xe9\xea"); // "Швейк"
53 
54  _shveikLookObj = _scene->object_interface("\x24\xf8\xe2\xe5\xe9\xea\x20\xf1\xec\xee\xf2\xf0\xe8\xf2"); // "$швейк смотрит"
55  _shveikMoveObj = _scene->object_interface("\x25\xF3\xEF\xF0\xE0\xE2\xEB\xE5\xED\xE8\xE5\x20\xEE\xE6\xE8\xE2\xEB\xFF\xE6\xE5\xEC\x20\xD8\xE2\xE5\xE9\xEA\xE0"); // "%управление оживляжем Швейка"
56  _shveikMoveEnabledObj = _scene->object_interface("\x25\xEE\xE6\xE8\xE2\xEB\xFF\xE6\x20\xD8\xE2\xE5\xE9\xEA\xE0\x20\xF0\xE0\xE7\xF0\xE5\xF8\xE5\xED"); // "%оживляж Швейка разрешен"
57 
58  _someFlag = false;
59  _scene->activate_personage("\xd8\xe2\xe5\xe9\xea"); // "Швейк"
60 
61  // srand(time(0));
62  _shveikIsMoving = 0;
63  _time = -1.0;
64  _timeout = -1;
65 
66  return true;
67  }
68 
69  bool quant(float dt) {
70  debugC(3, kDebugMinigames, "InvPopup::quant(%f)", dt);
71 
72  if (_blockPersObj->is_state_active("\xe2\xea\xeb\xfe\xf7\xe8\xf2\xfc")) { // "включить"
73  _scene->activate_personage("Lock");
74  } else if (_blockPersObj->is_state_active("\xe2\xfb\xea\xeb\xfe\xf7\xe8\xf2\xfc")) { // "выключить"
75  _scene->activate_personage("\xd8\xe2\xe5\xe9\xea"); // "Швейк"
76  _blockPersObj->set_state("\xe2\xfb\xea\xeb\xfe\xf7\xe5\xed\xe0"); // "выключена"
77  }
78 
80  char buf[5];
81  const char *state = nullptr;
82 
83  if (_scene->mouse_hover_object_interface())
85 
86  if (!_scene->mouse_hover_object_interface() || _scene->mouse_object_interface()) {
87  _invDescObj->set_state("00");
88  obj = _invDescCloseupObj;
89  obj->set_state("00");
90  } else if (!strstr(state, "#inv#")) {
91  obj = _invDescObj;
92  obj->set_state("00");
93  } else {
94  const char *pos = strstr(state, "#inv#");
95  char buf2[5];
96  Common::strlcpy(buf2, pos + 5, 3);
97  Common::strlcpy(buf, _invDescCloseupObj->current_state_name(), 3);
98 
99  if (buf2[0] != buf[0] || buf2[1] != buf[1]) {
100  _invDescObj->set_state(buf2);
101  _hoverObjectPos = _scene->mouse_hover_object_interface()->screen_R();
102  if (_hoverObjectPos.x + _invDescObj->screen_size().x / 2 >= 800
103  || (_hoverObjectPos.x - _invDescObj->screen_size().x / 2 <= 0)) {
104  if (_hoverObjectPos.x + _invDescObj->screen_size().x / 2 < 800) {
105  if (_hoverObjectPos.x - _invDescObj->screen_size().x / 2 <= 0)
106  _invDescPos.x = _invDescObj->screen_size().x / 2 + 10;
107  } else {
108  _invDescPos.x = 790 - _invDescObj->screen_size().x / 2;
109  }
110  } else {
111  _invDescPos.x = _hoverObjectPos.x;
112  }
113  _invDescPos.y = _invDescObj->screen_size().y / 2 + 73;
114  _invDescObj->set_R(_scene->screen2world_coords(_invDescPos, -1000.0));
115  _invDescCloseupObj->set_state("00");
116  }
117  }
118 
119  if (_scene->mouse_right_click_object_interface()) {
120  if (!_scene->mouse_object_interface()) {
122 
123  if (strstr(state, "#closeup#")) {
124  const char *pos = strstr(state, "#inv#");
125  Common::strlcpy(buf, pos + 5, 3);
126  buf[2] = 0;
127 
128  _invDescCloseupObj->set_state(buf);
129  _invDescPos.y = 300;
130  _invDescPos.x = 400;
131  _invDescCloseupObj->set_R( _scene->screen2world_coords(_invDescPos, -1000.0));
132  _invDescObj->set_state("00");
133  }
134  }
135  }
136 
137  if (Common::String(_blockPersFlagObj->current_state_name()) == "\xe4\xe0") { // "да"
138  if (!_blockPersObj->is_state_active("\xe2\xea\xeb\xfe\xf7\xe8\xf2\xfc")) // "включить"
139  _blockPersObj->set_state("\xe2\xea\xeb\xfe\xf7\xe8\xf2\xfc"); // "включить"
140  } else if (_blockPersObj->is_state_active("\xe2\xea\xeb\xfe\xf7\xe8\xf2\xfc")) { // "включить"
141  _blockPersObj->set_state("\xe2\xfb\xea\xeb\xfe\xf7\xe8\xf2\xfc"); // "выключить"
142  }
143 
144  _direction = -10;
145  int angle = (int)(_shveikObj->direction_angle() * 180.0 * 0.3183098865475127);
146 
147  if (angle > 220 && angle < 230)
148  _direction = 1;
149  else if (angle > 265 && angle < 275)
150  _direction = 2;
151  else if (angle > 310 && angle < 320)
152  _direction = 3;
153  else if (angle > 175 && angle < 185)
154  _direction = 4;
155  else if (angle >= 0 && angle < 5)
156  _direction = 6;
157  else if (angle > 40 && angle < 50)
158  _direction = 9;
159  else if (angle > 85 && angle < 95)
160  _direction = 8;
161  else if (angle > 130 && angle < 140)
162  _direction = 7;
163 
164  Common::String curState = _shveikObj->current_state_name();
165  if (curState == "#1#") {
166  _direction = 1;
167  } else if (curState == "#2#") {
168  _direction = 2;
169  } else if (curState == "#3#") {
170  _direction = 3;
171  } else if (curState == "#4#") {
172  _direction = 4;
173  } else if (curState == "#6#") {
174  _direction = 6;
175  } else if (curState == "#7#") {
176  _direction = 7;
177  } else if (curState == "#8#") {
178  _direction = 8;
179  } else if (curState == "#9#") {
180  _direction = 9;
181  }
182 
183  switch (_direction) {
184  case -10:
185  _shveikLookObj->set_state("0");
186  break;
187  case 1:
188  _shveikLookObj->set_state("1");
189  break;
190  case 2:
191  _shveikLookObj->set_state("2");
192  break;
193  case 3:
194  _shveikLookObj->set_state("3");
195  break;
196  case 4:
197  _shveikLookObj->set_state("4");
198  break;
199  case 6:
200  _shveikLookObj->set_state("6");
201  break;
202  case 7:
203  _shveikLookObj->set_state("7");
204  break;
205  case 8:
206  _shveikLookObj->set_state("8");
207  break;
208  case 9:
209  _shveikLookObj->set_state("9");
210  break;
211  default:
212  break;
213  }
214 
215  if (curState == "?1?") {
216  _direction = 10;
217  } else if (curState == "?2?") {
218  _direction = 20;
219  } else if (curState == "?3?") {
220  _direction = 30;
221  } else if (curState == "?4?") {
222  _direction = 40;
223  } else if (curState == "?6?") {
224  _direction = 60;
225  } else if (curState == "?7?") {
226  _direction = 70;
227  } else if (curState == "?8?") {
228  _direction = 80;
229  } else if (curState == "?9?") {
230  _direction = 90;
231  }
232 
233  switch (_direction) {
234  case 10:
235  _shveikObj->set_direction_angle(5 * M_PI / 4);
236  break;
237  case 20:
238  _shveikObj->set_direction_angle(6 * M_PI / 4);
239  break;
240  case 30:
241  _shveikObj->set_direction_angle(7 * M_PI / 4);
242  break;
243  case 40:
244  _shveikObj->set_direction_angle(M_PI);
245  break;
246  case 60:
247  _shveikObj->set_direction_angle(0.0);
248  break;
249  case 70:
250  _shveikObj->set_direction_angle(3 * M_PI / 4);
251  break;
252  case 80:
253  _shveikObj->set_direction_angle(2 * M_PI / 4);
254  break;
255  case 90:
256  _shveikObj->set_direction_angle(1 * M_PI / 4);
257  break;
258  default:
259  break;
260  }
261 
262  if (strstr(_shveikMoveEnabledObj->current_state_name(), "\xe4\xe0")) { // "да"
263  if (!_shveikIsMoving) {
264  _shveikIsMoving = 1;
265  _time = 0.0;
266  _timeout = qd_rnd(10) + 5;
267  }
268 
269  if (_timeout >= _time || _time == -1.0) {
270  _time = dt + _time;
271  } else {
272  _shveikIsMoving = 2;
273  _time = -1.0;
274  _shveikMoveObj->set_state("\xe2\xfb\xef\xee\xeb\xed\xe8\xf2\xfc"); // "выполнить"
275  }
276  }
277 
278  if ((strstr(_shveikMoveEnabledObj->current_state_name(), "\xed\xe5\xf2") // "нет"
279  || _shveikMoveObj->is_state_active("\xee\xf2\xf0\xe0\xe1\xee\xf2\xe0\xed")) // "отработан"
280  && _shveikIsMoving > 0) {
281  _shveikIsMoving = 0;
282  _time = -1.0;
283  _timeout = -1;
284  _shveikMoveObj->set_state("\xee\xe6\xe8\xe4\xe0\xed\xe8\xe5"); // "ожидание"
285  }
286 
287  if ((_shveikObj->R().x != _oldShveikPos.x
288  || _shveikObj->R().y != _oldShveikPos.y)
289  && _shveikIsMoving > 0) {
290  _shveikIsMoving = 0;
291  _time = -1.0;
292  _timeout = -1;
293  _shveikMoveObj->set_state("\xee\xe6\xe8\xe4\xe0\xed\xe8\xe5"); // "ожидание"
294  }
295 
296  _oldShveikPos = _shveikObj->R();
297 
298  return true;
299  }
300 
301  bool finit() {
302  debugC(1, kDebugMinigames, "InvPopup::finit()");
303 
304  if (_scene) {
305  _engine->release_scene_interface(_scene);
306  _scene = 0;
307  }
308 
309  return true;
310  }
311 
312  bool new_game(const qdEngineInterface *engine_interface) {
313  return true;
314  }
315 
316  int save_game(const qdEngineInterface *engine_interface, const qdMinigameSceneInterface *scene_interface, char *buffer, int buffer_size) {
317  return 0;
318  }
319 
320  int load_game(const qdEngineInterface *engine_interface, const qdMinigameSceneInterface *scene_interface, const char *buffer, int buffer_size) {
321  return 0;
322  }
323 
324  enum { INTERFACE_VERSION = 112 };
325  int version() const {
326  return INTERFACE_VERSION;
327  }
328 
329 private:
330  const qdEngineInterface *_engine = nullptr;
331  qdMinigameSceneInterface *_scene = nullptr;
332 
333 // qdMinigameObjectInterface *_invClickObj = nullptr;
334  qdMinigameObjectInterface *_invDescObj = nullptr;
335  qdMinigameObjectInterface *_invDescCloseupObj = nullptr;
336 // qdMinigameObjectInterface *_invActiveFlagObj = nullptr;
337  qdMinigameObjectInterface *_shveikObj = nullptr;
338  qdMinigameObjectInterface *_blockPersObj = nullptr;
339  qdMinigameObjectInterface *_blockPersFlagObj = nullptr;
340  qdMinigameObjectInterface *_shveikMoveObj = nullptr;
341  qdMinigameObjectInterface *_shveikMoveEnabledObj = nullptr;
342  qdMinigameObjectInterface *_shveikLookObj = nullptr;
343 
344  mgVect2i _hoverObjectPos;
345  mgVect2i _invDescPos;
346  bool _someFlag = false;
347  int _direction = 0;
348  int _shveikIsMoving = 0;
349  float _time = 0;
350  int _timeout = 0;
351  mgVect3f _oldShveikPos;
352 };
353 
354 } // namespace QDEngine
355 
356 #endif // QDENGINE_MINIGAMES_INV_POPUP_H
virtual bool set_direction_angle(float direction)=0
Устанавливает направление персонажа.
virtual mgVect3f R() const =0
Возвращает координаты объекта в мировой системе координат.
virtual mgVect3f screen2world_coords(const mgVect2i &screen_pos, float screen_depth=0) const =0
Преобразование из экранных координат в мировые.
Definition: str.h:59
virtual mgVect2i screen_R() const =0
Возвращает координаты объекта в экранной системе координат.
size_t strlcpy(char *dst, const char *src, size_t size)
virtual float direction_angle() const =0
bool new_game(const qdEngineInterface *engine_interface)
Инициализация миниигры, вызывается при старте и перезапуске игры.
Definition: inv_popup.h:312
int save_game(const qdEngineInterface *engine_interface, const qdMinigameSceneInterface *scene_interface, char *buffer, int buffer_size)
Сохранение данных, вызывается при сохранении сцены, на которую повешена миниигра. ...
Definition: inv_popup.h:316
Definition: qd_minigame_interface.h:78
bool quant(float dt)
Обсчёт логики игры, параметр - время, которое должно пройти в игре (в секундах).
Definition: inv_popup.h:69
Definition: qd_minigame_interface.h:365
virtual bool is_state_active(const char *state_name) const =0
Возвращает true, если состояние с именем state_name включено в данный момент.
Базовый класс для игровых ресурсов.
Definition: console.h:28
virtual qdMinigameObjectInterface * mouse_hover_object_interface() const =0
Создаёт интерфейс к объекту, над которым находится мышиный курсор.
bool finit()
Деинициализация игры.
Definition: inv_popup.h:301
Интерфейс к динамическому объекту.
Definition: qd_minigame_interface.h:230
virtual const char * current_state_name() const =0
Интерфейс к сцене.
Definition: qd_minigame_interface.h:315
virtual bool set_state(const char *state_name)=0
Включает состояние с именем state_name.
virtual void set_R(const mgVect3f &r)=0
Устанавливает координаты объекта в мировой системе координат.
virtual qdMinigameObjectInterface * object_interface(const char *object_name)=0
Создаёт интерфейс к объекту с именем object_name.
bool init(const qdEngineInterface *engine_interface)
Инициализация игры.
Definition: inv_popup.h:37
virtual qdMinigameObjectInterface * personage_interface(const char *personage_name)=0
Создаёт интерфейс к персонажу с именем personage_name.
virtual mgVect2i screen_size() const =0
Возвращает текущие экранные размеры объекта в пикселах.
void void void void void debugC(int level, uint32 debugChannels, MSVC_PRINTF const char *s,...) GCC_PRINTF(3
int load_game(const qdEngineInterface *engine_interface, const qdMinigameSceneInterface *scene_interface, const char *buffer, int buffer_size)
Загрузка данных, вызывается при загрузке сцены, на которую повешена миниигра.
Definition: inv_popup.h:320
Definition: inv_popup.h:32
uint32 qd_rnd(uint32 m)
Возвращает случайное значение в интервале [0, m-1].
Definition: qd_rnd.h:30
virtual qdMinigameObjectInterface * mouse_right_click_object_interface() const =0
Создаёт интерфейс к объекту, по которому кликнули правой кнопкой мыши.
virtual bool activate_personage(const char *personage_name)=0
Активация персонажа с именем personage_name.
virtual qdMinigameObjectInterface * mouse_object_interface() const =0
Создаёт интерфейс к объекту, который взят мышью в данный момент.