/** * Updates all soldier stats when the soldier changes. */ void InventoryState::init() { State::init(); BattleUnit *unit = _battleGame->getSelectedUnit(); // no selected unit, close inventory if (unit == 0) { btnOkClick(0); return; } // skip to the first unit with inventory if (!unit->hasInventory()) { if (_parent) { _parent->selectNextPlayerUnit(false, false, true); } else { _battleGame->selectNextPlayerUnit(false, false, true); } // no available unit, close inventory if (_battleGame->getSelectedUnit() == 0 || !_battleGame->getSelectedUnit()->hasInventory()) { // starting a mission with just vehicles btnOkClick(0); return; } else { unit = _battleGame->getSelectedUnit(); } } unit->setCache(0); _soldier->clear(); _rank->clear(); _txtName->setBig(); _txtName->setText(unit->getName(_game->getLanguage())); _inv->setSelectedUnit(unit); Soldier *s = unit->getGeoscapeSoldier(); if (s) { SurfaceSet *texture = _game->getMod()->getSurfaceSet("SMOKE.PCK"); texture->getFrame(20 + s->getRank())->setX(0); texture->getFrame(20 + s->getRank())->setY(0); texture->getFrame(20 + s->getRank())->blit(_rank); std::string look = s->getArmor()->getSpriteInventory(); if (s->getGender() == GENDER_MALE) look += "M"; else look += "F"; if (s->getLook() == LOOK_BLONDE) look += "0"; if (s->getLook() == LOOK_BROWNHAIR) look += "1"; if (s->getLook() == LOOK_ORIENTAL) look += "2"; if (s->getLook() == LOOK_AFRICAN) look += "3"; look += ".SPK"; const std::set<std::string> &ufographContents = FileMap::getVFolderContents("UFOGRAPH"); std::string lcaseLook = look; std::transform(lcaseLook.begin(), lcaseLook.end(), lcaseLook.begin(), tolower); if (ufographContents.find("lcaseLook") == ufographContents.end() && !_game->getMod()->getSurface(look)) { look = s->getArmor()->getSpriteInventory() + ".SPK"; } _game->getMod()->getSurface(look)->blit(_soldier); } else { Surface *armorSurface = _game->getMod()->getSurface(unit->getArmor()->getSpriteInventory()); if (armorSurface) { armorSurface->blit(_soldier); } } updateStats(); _refreshMouse(); }
/** * Calculates the effects of the explosion. */ void ExplosionBState::explode() { bool terrainExplosion = false; SavedBattleGame *save = _parent->getSave(); // after the animation is done, the real explosion/hit takes place if (_item) { if (!_unit && _item->getPreviousOwner()) { _unit = _item->getPreviousOwner(); } BattleUnit *victim = 0; if (_areaOfEffect) { save->getTileEngine()->explode(_center, _power, _item->getRules()->getDamageType(), _item->getRules()->getExplosionRadius(), _unit); } else if (!_cosmetic) { ItemDamageType type = _item->getRules()->getDamageType(); victim = save->getTileEngine()->hit(_center, _power, type, _unit); } // check if this unit turns others into zombies if (!_item->getRules()->getZombieUnit().empty() && victim && victim->getArmor()->getSize() == 1 && (victim->getGeoscapeSoldier() || victim->getUnitRules()->getRace() == "STR_CIVILIAN") && victim->getSpawnUnit().empty()) { // converts the victim to a zombie on death victim->setRespawn(true); victim->setSpawnUnit(_item->getRules()->getZombieUnit()); } } if (_tile) { ItemDamageType DT; switch (_tile->getExplosiveType()) { case 0: DT = DT_HE; break; case 5: DT = DT_IN; break; case 6: DT = DT_STUN; break; default: DT = DT_SMOKE; break; } if (DT != DT_HE) { _tile->setExplosive(0,0,true); } save->getTileEngine()->explode(_center, _power, DT, _power/10); terrainExplosion = true; } if (!_tile && !_item) { int radius = 6; // explosion not caused by terrain or an item, must be by a unit (cyberdisc) if (_unit && (_unit->getSpecialAbility() == SPECAB_EXPLODEONDEATH || _unit->getSpecialAbility() == SPECAB_BURN_AND_EXPLODE)) { radius = _parent->getMod()->getItem(_unit->getArmor()->getCorpseGeoscape())->getExplosionRadius(); } save->getTileEngine()->explode(_center, _power, DT_HE, radius); terrainExplosion = true; } if (!_cosmetic) { // now check for new casualties _parent->checkForCasualties(_item, _unit, false, terrainExplosion); } // if this explosion was caused by a unit shooting, now it's the time to put the gun down if (_unit && !_unit->isOut() && _lowerWeapon) { _unit->aim(false); _unit->setCache(0); } _parent->getMap()->cacheUnits(); _parent->popState(); // check for terrain explosions Tile *t = save->getTileEngine()->checkForTerrainExplosions(); if (t) { Position p = Position(t->getPosition().x * 16, t->getPosition().y * 16, t->getPosition().z * 24); p += Position(8,8,0); _parent->statePushFront(new ExplosionBState(_parent, p, 0, _unit, t)); } if (_item && (_item->getRules()->getBattleType() == BT_GRENADE || _item->getRules()->getBattleType() == BT_PROXIMITYGRENADE)) { for (std::vector<BattleItem*>::iterator j = _parent->getSave()->getItems()->begin(); j != _parent->getSave()->getItems()->end(); ++j) { if (_item->getId() == (*j)->getId()) { _parent->getSave()->removeItem(_item); break; } } } }