1 /*
2 * Copyright 2010-2014 OpenXcom Developers.
3 *
4 * This file is part of OpenXcom.
5 *
6 * OpenXcom is free software: you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation, either version 3 of the License, or
9 * (at your option) any later version.
10 *
11 * OpenXcom is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
15 *
16 * You should have received a copy of the GNU General Public License
17 * along with OpenXcom. If not, see <http://www.gnu.org/licenses/>.
18 */
19 #include "SoldierInfoState.h"
20 #include <sstream>
21 #include "../Engine/Game.h"
22 #include "../Engine/Action.h"
23 #include "../Resource/ResourcePack.h"
24 #include "../Engine/Language.h"
25 #include "../Engine/Palette.h"
26 #include "../Engine/Options.h"
27 #include "../Interface/Bar.h"
28 #include "../Interface/TextButton.h"
29 #include "../Interface/Text.h"
30 #include "../Interface/TextEdit.h"
31 #include "../Engine/Surface.h"
32 #include "../Savegame/SavedGame.h"
33 #include "../Ruleset/Ruleset.h"
34 #include "../Savegame/Base.h"
35 #include "../Savegame/Craft.h"
36 #include "../Ruleset/RuleCraft.h"
37 #include "../Savegame/Soldier.h"
38 #include "../Savegame/ItemContainer.h"
39 #include "../Engine/SurfaceSet.h"
40 #include "../Ruleset/Armor.h"
41 #include "../Menu/ErrorMessageState.h"
42 #include "SellState.h"
43 #include "SoldierArmorState.h"
44 #include "SackSoldierState.h"
45
46 namespace OpenXcom
47 {
48
49 /**
50 * Initializes all the elements in the Soldier Info screen.
51 * @param game Pointer to the core game.
52 * @param base Pointer to the base to get info from. NULL to use the dead soldiers list.
53 * @param soldierId ID of the selected soldier.
54 */
SoldierInfoState(Game * game,Base * base,size_t soldierId)55 SoldierInfoState::SoldierInfoState(Game *game, Base *base, size_t soldierId) : State(game), _base(base), _soldierId(soldierId)
56 {
57 if (_base == 0)
58 {
59 _list = _game->getSavedGame()->getDeadSoldiers();
60 if (_soldierId >= _list->size())
61 {
62 _soldierId = 0;
63 }
64 else
65 {
66 _soldierId = _list->size() - (1 + _soldierId);
67 }
68 }
69 else
70 {
71 _list = _base->getSoldiers();
72 }
73
74 // Create objects
75 _bg = new Surface(320, 200, 0, 0);
76 _rank = new Surface(26, 23, 4, 4);
77 _btnPrev = new TextButton(28, 14, 0, 33);
78 _btnOk = new TextButton(48, 14, 30, 33);
79 _btnNext = new TextButton(28, 14, 80, 33);
80 _btnArmor = new TextButton(110, 14, 130, 33);
81 _edtSoldier = new TextEdit(this, 210, 16, 40, 9);
82 _btnSack = new TextButton(60, 14, 260, 33);
83 _txtRank = new Text(130, 9, 0, 48);
84 _txtMissions = new Text(100, 9, 130, 48);
85 _txtKills = new Text(100, 9, 230, 48);
86 _txtCraft = new Text(130, 9, 0, 56);
87 _txtRecovery = new Text(180, 9, 130, 56);
88 _txtPsionic = new Text(150, 9, 0, 66);
89
90 int yPos = 80;
91 int step = 11;
92
93 _txtTimeUnits = new Text(120, 9, 6, yPos);
94 _numTimeUnits = new Text(18, 9, 131, yPos);
95 _barTimeUnits = new Bar(170, 7, 150, yPos);
96 yPos += step;
97
98 _txtStamina = new Text(120, 9, 6, yPos);
99 _numStamina = new Text(18, 9, 131, yPos);
100 _barStamina = new Bar(170, 7, 150, yPos);
101 yPos += step;
102
103 _txtHealth = new Text(120, 9, 6, yPos);
104 _numHealth = new Text(18, 9, 131, yPos);
105 _barHealth = new Bar(170, 7, 150, yPos);
106 yPos += step;
107
108 _txtBravery = new Text(120, 9, 6, yPos);
109 _numBravery = new Text(18, 9, 131, yPos);
110 _barBravery = new Bar(170, 7, 150, yPos);
111 yPos += step;
112
113 _txtReactions = new Text(120, 9, 6, yPos);
114 _numReactions = new Text(18, 9, 131, yPos);
115 _barReactions = new Bar(170, 7, 150, yPos);
116 yPos += step;
117
118 _txtFiring = new Text(120, 9, 6, yPos);
119 _numFiring = new Text(18, 9, 131, yPos);
120 _barFiring = new Bar(170, 7, 150, yPos);
121 yPos += step;
122
123 _txtThrowing = new Text(120, 9, 6, yPos);
124 _numThrowing = new Text(18, 9, 131, yPos);
125 _barThrowing = new Bar(170, 7, 150, yPos);
126 yPos += step;
127
128 _txtMelee = new Text(120, 9, 6, yPos);
129 _numMelee = new Text(18, 9, 131, yPos);
130 _barMelee = new Bar(170, 7, 150, yPos);
131 yPos += step;
132
133 _txtStrength = new Text(120, 9, 6, yPos);
134 _numStrength = new Text(18, 9, 131, yPos);
135 _barStrength = new Bar(170, 7, 150, yPos);
136 yPos += step;
137
138 _txtPsiStrength = new Text(120, 9, 6, yPos);
139 _numPsiStrength = new Text(18, 9, 131, yPos);
140 _barPsiStrength = new Bar(170, 7, 150, yPos);
141 yPos += step;
142
143 _txtPsiSkill = new Text(120, 9, 6, yPos);
144 _numPsiSkill = new Text(18, 9, 131, yPos);
145 _barPsiSkill = new Bar(170, 7, 150, yPos);
146
147 // Set palette
148 setPalette("PAL_BASESCAPE");
149
150 add(_bg);
151 add(_rank);
152 add(_btnOk);
153 add(_btnPrev);
154 add(_btnNext);
155 add(_btnArmor);
156 add(_edtSoldier);
157 add(_btnSack);
158 add(_txtRank);
159 add(_txtMissions);
160 add(_txtKills);
161 add(_txtCraft);
162 add(_txtRecovery);
163 add(_txtPsionic);
164
165 add(_txtTimeUnits);
166 add(_numTimeUnits);
167 add(_barTimeUnits);
168
169 add(_txtStamina);
170 add(_numStamina);
171 add(_barStamina);
172
173 add(_txtHealth);
174 add(_numHealth);
175 add(_barHealth);
176
177 add(_txtBravery);
178 add(_numBravery);
179 add(_barBravery);
180
181 add(_txtReactions);
182 add(_numReactions);
183 add(_barReactions);
184
185 add(_txtFiring);
186 add(_numFiring);
187 add(_barFiring);
188
189 add(_txtThrowing);
190 add(_numThrowing);
191 add(_barThrowing);
192
193 add(_txtMelee);
194 add(_numMelee);
195 add(_barMelee);
196
197 add(_txtStrength);
198 add(_numStrength);
199 add(_barStrength);
200
201 add(_txtPsiStrength);
202 add(_numPsiStrength);
203 add(_barPsiStrength);
204
205 add(_txtPsiSkill);
206 add(_numPsiSkill);
207 add(_barPsiSkill);
208
209 centerAllSurfaces();
210
211 // Set up objects
212 _game->getResourcePack()->getSurface("BACK06.SCR")->blit(_bg);
213
214 _btnOk->setColor(Palette::blockOffset(15)+6);
215 _btnOk->setText(tr("STR_OK"));
216 _btnOk->onMouseClick((ActionHandler)&SoldierInfoState::btnOkClick);
217 _btnOk->onKeyboardPress((ActionHandler)&SoldierInfoState::btnOkClick, Options::keyCancel);
218
219 _btnPrev->setColor(Palette::blockOffset(15)+6);
220 _btnPrev->setText(L"<<");
221 if (_base == 0)
222 {
223 _btnPrev->onMouseClick((ActionHandler)&SoldierInfoState::btnNextClick);
224 _btnPrev->onKeyboardPress((ActionHandler)&SoldierInfoState::btnNextClick, Options::keyBattlePrevUnit);
225 }
226 else
227 {
228 _btnPrev->onMouseClick((ActionHandler)&SoldierInfoState::btnPrevClick);
229 _btnPrev->onKeyboardPress((ActionHandler)&SoldierInfoState::btnPrevClick, Options::keyBattlePrevUnit);
230 }
231
232 _btnNext->setColor(Palette::blockOffset(15)+6);
233 _btnNext->setText(L">>");
234 if (_base == 0)
235 {
236 _btnNext->onMouseClick((ActionHandler)&SoldierInfoState::btnPrevClick);
237 _btnNext->onKeyboardPress((ActionHandler)&SoldierInfoState::btnPrevClick, Options::keyBattleNextUnit);
238 }
239 else
240 {
241 _btnNext->onMouseClick((ActionHandler)&SoldierInfoState::btnNextClick);
242 _btnNext->onKeyboardPress((ActionHandler)&SoldierInfoState::btnNextClick, Options::keyBattleNextUnit);
243 }
244
245 _btnArmor->setColor(Palette::blockOffset(15)+6);
246 _btnArmor->setText(tr("STR_ARMOR"));
247 _btnArmor->onMouseClick((ActionHandler)&SoldierInfoState::btnArmorClick);
248
249 _edtSoldier->setColor(Palette::blockOffset(13)+10);
250 _edtSoldier->setBig();
251 _edtSoldier->onChange((ActionHandler)&SoldierInfoState::edtSoldierChange);
252 _edtSoldier->onMousePress((ActionHandler)&SoldierInfoState::edtSoldierPress);
253
254 _btnSack->setColor(Palette::blockOffset(15)+6);
255 _btnSack->setText(tr("STR_SACK"));
256 _btnSack->onMouseClick((ActionHandler)&SoldierInfoState::btnSackClick);
257
258 _txtRank->setColor(Palette::blockOffset(13)+10);
259 _txtRank->setSecondaryColor(Palette::blockOffset(13));
260
261 _txtMissions->setColor(Palette::blockOffset(13)+10);
262 _txtMissions->setSecondaryColor(Palette::blockOffset(13));
263
264 _txtKills->setColor(Palette::blockOffset(13)+10);
265 _txtKills->setSecondaryColor(Palette::blockOffset(13));
266
267 _txtCraft->setColor(Palette::blockOffset(13)+10);
268 _txtCraft->setSecondaryColor(Palette::blockOffset(13));
269
270 _txtRecovery->setColor(Palette::blockOffset(13)+10);
271 _txtRecovery->setSecondaryColor(Palette::blockOffset(13));
272
273 _txtPsionic->setColor(Palette::blockOffset(15)+1);
274 _txtPsionic->setText(tr("STR_IN_PSIONIC_TRAINING"));
275
276
277 _txtTimeUnits->setColor(Palette::blockOffset(15)+1);
278 _txtTimeUnits->setText(tr("STR_TIME_UNITS"));
279
280 _numTimeUnits->setColor(Palette::blockOffset(13));
281
282 _barTimeUnits->setColor(Palette::blockOffset(3));
283 _barTimeUnits->setColor2(Palette::blockOffset(3)+4);
284 _barTimeUnits->setScale(1.0);
285 _barTimeUnits->setInvert(true);
286
287 _txtStamina->setColor(Palette::blockOffset(15)+1);
288 _txtStamina->setText(tr("STR_STAMINA"));
289
290 _numStamina->setColor(Palette::blockOffset(13));
291
292 _barStamina->setColor(Palette::blockOffset(9));
293 _barStamina->setColor2(Palette::blockOffset(9)+4);
294 _barStamina->setScale(1.0);
295 _barStamina->setInvert(true);
296
297 _txtHealth->setColor(Palette::blockOffset(15)+1);
298 _txtHealth->setText(tr("STR_HEALTH"));
299
300 _numHealth->setColor(Palette::blockOffset(13));
301
302 _barHealth->setColor(Palette::blockOffset(2));
303 _barHealth->setColor2(Palette::blockOffset(2)+4);
304 _barHealth->setScale(1.0);
305 _barHealth->setInvert(true);
306
307 _txtBravery->setColor(Palette::blockOffset(15)+1);
308 _txtBravery->setText(tr("STR_BRAVERY"));
309
310 _numBravery->setColor(Palette::blockOffset(13));
311
312 _barBravery->setColor(Palette::blockOffset(4));
313 _barBravery->setColor2(Palette::blockOffset(4)+4);
314 _barBravery->setScale(1.0);
315 _barBravery->setInvert(true);
316
317 _txtReactions->setColor(Palette::blockOffset(15)+1);
318 _txtReactions->setText(tr("STR_REACTIONS"));
319
320 _numReactions->setColor(Palette::blockOffset(13));
321
322 _barReactions->setColor(Palette::blockOffset(1));
323 _barReactions->setColor2(Palette::blockOffset(1)+4);
324 _barReactions->setScale(1.0);
325 _barReactions->setInvert(true);
326
327 _txtFiring->setColor(Palette::blockOffset(15)+1);
328 _txtFiring->setText(tr("STR_FIRING_ACCURACY"));
329
330 _numFiring->setColor(Palette::blockOffset(13));
331
332 _barFiring->setColor(Palette::blockOffset(8));
333 _barFiring->setColor2(Palette::blockOffset(8)+4);
334 _barFiring->setScale(1.0);
335 _barFiring->setInvert(true);
336
337 _txtThrowing->setColor(Palette::blockOffset(15)+1);
338 _txtThrowing->setText(tr("STR_THROWING_ACCURACY"));
339
340 _numThrowing->setColor(Palette::blockOffset(13));
341
342 _barThrowing->setColor(Palette::blockOffset(10));
343 _barThrowing->setColor2(Palette::blockOffset(10)+4);
344 _barThrowing->setScale(1.0);
345 _barThrowing->setInvert(true);
346
347 _txtMelee->setColor(Palette::blockOffset(15)+1);
348 _txtMelee->setText(tr("STR_MELEE_ACCURACY"));
349
350 _numMelee->setColor(Palette::blockOffset(13));
351
352 _barMelee->setColor(Palette::blockOffset(4));
353 _barMelee->setColor2(Palette::blockOffset(4)+4);
354 _barMelee->setScale(1.0);
355 _barMelee->setInvert(true);
356
357 _txtStrength->setColor(Palette::blockOffset(15)+1);
358 _txtStrength->setText(tr("STR_STRENGTH"));
359
360 _numStrength->setColor(Palette::blockOffset(13));
361
362 _barStrength->setColor(Palette::blockOffset(5));
363 _barStrength->setColor2(Palette::blockOffset(5)+4);
364 _barStrength->setScale(1.0);
365 _barStrength->setInvert(true);
366
367 _txtPsiStrength->setColor(Palette::blockOffset(15)+1);
368 _txtPsiStrength->setText(tr("STR_PSIONIC_STRENGTH"));
369
370 _numPsiStrength->setColor(Palette::blockOffset(13));
371
372 _barPsiStrength->setColor(Palette::blockOffset(11));
373 _barPsiStrength->setColor2(Palette::blockOffset(11)+4);
374 _barPsiStrength->setScale(1.0);
375 _barPsiStrength->setInvert(true);
376
377 _txtPsiSkill->setColor(Palette::blockOffset(15)+1);
378 _txtPsiSkill->setText(tr("STR_PSIONIC_SKILL"));
379
380 _numPsiSkill->setColor(Palette::blockOffset(13));
381
382 _barPsiSkill->setColor(Palette::blockOffset(11));
383 _barPsiSkill->setColor2(Palette::blockOffset(11)+4);
384 _barPsiSkill->setScale(1.0);
385 _barPsiSkill->setInvert(true);
386 }
387
388 /**
389 *
390 */
~SoldierInfoState()391 SoldierInfoState::~SoldierInfoState()
392 {
393
394 }
395
396 /**
397 * Updates soldier stats when
398 * the soldier changes.
399 */
init()400 void SoldierInfoState::init()
401 {
402 State::init();
403 if (_list->empty())
404 {
405 _game->popState();
406 return;
407 }
408 if (_soldierId >= _list->size())
409 {
410 _soldierId = 0;
411 }
412 _soldier = _list->at(_soldierId);
413 _edtSoldier->setBig();
414 _edtSoldier->setText(_soldier->getName());
415 UnitStats *initial = _soldier->getInitStats();
416 UnitStats *current = _soldier->getCurrentStats();
417
418 SurfaceSet *texture = _game->getResourcePack()->getSurfaceSet("BASEBITS.PCK");
419 texture->getFrame(_soldier->getRankSprite())->setX(0);
420 texture->getFrame(_soldier->getRankSprite())->setY(0);
421 texture->getFrame(_soldier->getRankSprite())->blit(_rank);
422
423 std::wostringstream ss;
424 ss << current->tu;
425 _numTimeUnits->setText(ss.str());
426 _barTimeUnits->setMax(current->tu);
427 _barTimeUnits->setValue(current->tu);
428 _barTimeUnits->setValue2(initial->tu);
429
430 std::wostringstream ss2;
431 ss2 << current->stamina;
432 _numStamina->setText(ss2.str());
433 _barStamina->setMax(current->stamina);
434 _barStamina->setValue(current->stamina);
435 _barStamina->setValue2(initial->stamina);
436
437 std::wostringstream ss3;
438 ss3 << current->health;
439 _numHealth->setText(ss3.str());
440 _barHealth->setMax(current->health);
441 _barHealth->setValue(current->health);
442 _barHealth->setValue2(initial->health);
443
444 std::wostringstream ss4;
445 ss4 << current->bravery;
446 _numBravery->setText(ss4.str());
447 _barBravery->setMax(current->bravery);
448 _barBravery->setValue(current->bravery);
449 _barBravery->setValue2(initial->bravery);
450
451 std::wostringstream ss5;
452 ss5 << current->reactions;
453 _numReactions->setText(ss5.str());
454 _barReactions->setMax(current->reactions);
455 _barReactions->setValue(current->reactions);
456 _barReactions->setValue2(initial->reactions);
457
458 std::wostringstream ss6;
459 ss6 << current->firing;
460 _numFiring->setText(ss6.str());
461 _barFiring->setMax(current->firing);
462 _barFiring->setValue(current->firing);
463 _barFiring->setValue2(initial->firing);
464
465 std::wostringstream ss7;
466 ss7 << current->throwing;
467 _numThrowing->setText(ss7.str());
468 _barThrowing->setMax(current->throwing);
469 _barThrowing->setValue(current->throwing);
470 _barThrowing->setValue2(initial->throwing);
471
472 std::wostringstream ss8;
473 ss8 << current->melee;
474 _numMelee->setText(ss8.str());
475 _barMelee->setMax(current->melee);
476 _barMelee->setValue(current->melee);
477 _barMelee->setValue2(initial->melee);
478
479 std::wostringstream ss9;
480 ss9 << current->strength;
481 _numStrength->setText(ss9.str());
482 _barStrength->setMax(current->strength);
483 _barStrength->setValue(current->strength);
484 _barStrength->setValue2(initial->strength);
485
486 std::wstring wsArmor;
487 std::string armorType = _soldier->getArmor()->getType();
488 if (armorType == "STR_NONE_UC")
489 {
490 wsArmor= tr("STR_ARMOR_").arg(tr(armorType));
491 }
492 else
493 {
494 wsArmor = tr(armorType);
495 }
496
497 _btnArmor->setText(wsArmor);
498
499 _btnSack->setVisible(!(_soldier->getCraft() && _soldier->getCraft()->getStatus() == "STR_OUT"));
500
501 _txtRank->setText(tr("STR_RANK_").arg(tr(_soldier->getRankString())));
502
503 _txtMissions->setText(tr("STR_MISSIONS").arg(_soldier->getMissions()));
504
505 _txtKills->setText(tr("STR_KILLS").arg(_soldier->getKills()));
506
507 std::wstring craft;
508 if (_soldier->getCraft() == 0)
509 {
510 craft = tr("STR_NONE_UC");
511 }
512 else
513 {
514 craft = _soldier->getCraft()->getName(_game->getLanguage());
515 }
516 _txtCraft->setText(tr("STR_CRAFT_").arg(craft));
517
518 if (_soldier->getWoundRecovery() > 0)
519 {
520 _txtRecovery->setText(tr("STR_WOUND_RECOVERY").arg(tr("STR_DAY", _soldier->getWoundRecovery())));
521 }
522 else
523 {
524 _txtRecovery->setText(L"");
525 }
526
527 _txtPsionic->setVisible(_soldier->isInPsiTraining());
528
529 if (current->psiSkill > 0 || (Options::psiStrengthEval && _game->getSavedGame()->isResearched(_game->getRuleset()->getPsiRequirements())))
530 {
531 std::wostringstream ss14;
532 ss14 << current->psiStrength;
533 _numPsiStrength->setText(ss14.str());
534 _barPsiStrength->setMax(current->psiStrength);
535 _barPsiStrength->setValue(current->psiStrength);
536 _barPsiStrength->setValue2(initial->psiStrength);
537
538 _txtPsiStrength->setVisible(true);
539 _numPsiStrength->setVisible(true);
540 _barPsiStrength->setVisible(true);
541 }
542 else
543 {
544 _txtPsiStrength->setVisible(false);
545 _numPsiStrength->setVisible(false);
546 _barPsiStrength->setVisible(false);
547 }
548
549 if (current->psiSkill > 0)
550 {
551 std::wostringstream ss15;
552 ss15 << current->psiSkill;
553 _numPsiSkill->setText(ss15.str());
554 _barPsiSkill->setMax(current->psiSkill);
555 _barPsiSkill->setValue(current->psiSkill);
556 _barPsiSkill->setValue2(current->psiSkill - _soldier->getImprovement());
557
558 _txtPsiSkill->setVisible(true);
559 _numPsiSkill->setVisible(true);
560 _barPsiSkill->setVisible(true);
561 }
562 else
563 {
564 _txtPsiSkill->setVisible(false);
565 _numPsiSkill->setVisible(false);
566 _barPsiSkill->setVisible(false);
567 }
568
569 // Dead can't talk
570 if (_base == 0)
571 {
572 _btnArmor->setVisible(false);
573 _btnSack->setVisible(false);
574 _txtCraft->setVisible(false);
575 }
576 else
577 {
578 _btnSack->setVisible(_game->getSavedGame()->getMonthsPassed() > -1);
579 }
580 }
581
582 /**
583 * Disables the soldier input.
584 * @param action Pointer to an action.
585 */
edtSoldierPress(Action * action)586 void SoldierInfoState::edtSoldierPress(Action *action)
587 {
588 if (_base == 0)
589 {
590 _edtSoldier->setFocus(false);
591 }
592 }
593
594 /**
595 * Changes the soldier's name.
596 * @param action Pointer to an action.
597 */
edtSoldierChange(Action * action)598 void SoldierInfoState::edtSoldierChange(Action *action)
599 {
600 _soldier->setName(_edtSoldier->getText());
601 }
602
603 /**
604 * Returns to the previous screen.
605 * @param action Pointer to an action.
606 */
btnOkClick(Action *)607 void SoldierInfoState::btnOkClick(Action *)
608 {
609 _game->popState();
610 if (_game->getSavedGame()->getMonthsPassed() > -1 && Options::storageLimitsEnforced && _base != 0 && _base->storesOverfull())
611 {
612 _game->pushState(new SellState(_game, _base));
613 _game->pushState(new ErrorMessageState(_game, tr("STR_STORAGE_EXCEEDED").arg(_base->getName()).c_str(), _palette, Palette::blockOffset(15)+1, "BACK01.SCR", 0));
614 }
615 }
616
617 /**
618 * Goes to the previous soldier.
619 * @param action Pointer to an action.
620 */
btnPrevClick(Action *)621 void SoldierInfoState::btnPrevClick(Action *)
622 {
623 if (_soldierId == 0)
624 _soldierId = _list->size() - 1;
625 else
626 _soldierId--;
627 init();
628 }
629
630 /**
631 * Goes to the next soldier.
632 * @param action Pointer to an action.
633 */
btnNextClick(Action *)634 void SoldierInfoState::btnNextClick(Action *)
635 {
636 _soldierId++;
637 if (_soldierId >= _list->size())
638 _soldierId = 0;
639 init();
640 }
641
642 /**
643 * Shows the Select Armor window.
644 * @param action Pointer to an action.
645 */
btnArmorClick(Action *)646 void SoldierInfoState::btnArmorClick(Action *)
647 {
648 if (!_soldier->getCraft() || (_soldier->getCraft() && _soldier->getCraft()->getStatus() != "STR_OUT"))
649 {
650 _game->pushState(new SoldierArmorState(_game, _base, _soldierId));
651 }
652 }
653
654 /**
655 * Shows the Sack Soldier window.
656 * @param action Pointer to an action.
657 */
btnSackClick(Action *)658 void SoldierInfoState::btnSackClick(Action *)
659 {
660 _game->pushState(new SackSoldierState(_game, _base, _soldierId));
661 }
662
663 }
664