#include "splashes.h" #include Splashes::Splashes(Game_Data *gd, QObject *parent) : QObject(parent) { gameData = gd; nextId = 1; } void Splashes::addSplash(int player, int srcTower, int srcId, QPointF pos, QPointF dest, int aim, QPoint curTower) { srcSplashType src = gameData->players.at(player)->srcTowers.at(srcTower).splashes.at(srcId); SplashType spl; spl.id = nextId; spl.TowerId = curTower; spl.srcTower = srcTower; spl.PlayerId = player; spl.AlienId = aim; spl.pos = pos; spl.destination = dest; if (src.autoControl) { if (gameData->curAliens.contains(aim)) spl.destination = gameData->curAliens.value(aim).pos+QPointF(0.5,0.5); } spl.angle = 180.0f*(- std::atan2(spl.pos.x() - spl.destination.x(),spl.pos.y() - spl.destination.y()))/M_PI; spl.imgType = src.imgType; spl.life = 0; spl.src = srcId; srcTriggerType trig; for(int i=0; iplayers.at(player)->srcTowers.at(srcTower).triggers.at(src.triggerIndexes.at(i)); switch (trig.type) { case srcTriggerType::onDestination : tod.src = src.triggerIndexes.at(i); spl.trigsOnDest.append(tod); break; case srcTriggerType::onAlienInRadius : toa.src = src.triggerIndexes.at(i); spl.trigsOnAlien.append(toa); break; case srcTriggerType::onTimer : tot.src = src.triggerIndexes.at(i); tot.timer = 0; spl.trigsOnTimer.append(tot); break; } } gameData->curSplashes.insert(spl.id,spl); nextId++; } void Splashes::addSplash(QPoint curTowerId) { if (gameData->curTowers.contains(curTowerId)) { TowerType tw = gameData->curTowers.value(curTowerId); addSplash(tw.PlayerId,tw.src,0,QPointF(tw.pos+QPoint(1,1)),gameData->curAliens.value(tw.aim).pos+QPointF(0.5,0.5),tw.aim,tw.pos); } } void Splashes::update() { QList deadIndexes; // FIXME : rewrite loop with iterators, and correct onTrigTimer() for (int i=0; icurSplashes.size(); i++) { float arctg,angl; SplashType spl = gameData->curSplashes.values().at(i); srcSplashType src; // FIXME : if splash is not tower's splash, will be some trouble src = gameData->players.at(spl.PlayerId)->srcTowers.at(spl.srcTower).splashes.at(spl.src); spl.life++; if (spl.life > src.lifetime) deadIndexes.append(spl.id); if (!spl.trigsOnTimer.isEmpty()) { doTriggerOnTimer(&spl,&deadIndexes); } if (src.autoControl) { bool badAl = false; if (gameData->curAliens.contains(spl.AlienId)) spl.destination = gameData->curAliens.value(spl.AlienId).pos+QPointF(0.5,0.5); else badAl = true; if (distance2(spl.pos, spl.destination) < src.speed*src.speed) { if (badAl) deadIndexes.push_back(spl.id); spl.pos = spl.destination; doTriggerOnDest(spl,&deadIndexes,badAl); } arctg = std::atan2(spl.pos.x() - spl.destination.x(),spl.pos.y() - spl.destination.y()); angl = 180.0f*(-arctg)/M_PI; spl.angle = angl; spl.pos.setX(spl.pos.x() -src.speed*std::sin(arctg)); spl.pos.setY(spl.pos.y() -src.speed*std::cos(arctg)); } else { if (!gameData->map->rect().contains(spl.pos.toPoint())) deadIndexes.push_back(spl.id); if (!spl.trigsOnDest.isEmpty()) { if (distance2(spl.pos, spl.destination) < src.speed*src.speed) { spl.pos = spl.destination; doTriggerOnDest(spl,&deadIndexes,true); } } spl.pos.setX(spl.pos.x() -src.speed*std::sin(-spl.angle*M_PI/180.f)); spl.pos.setY(spl.pos.y() -src.speed*std::cos(-spl.angle*M_PI/180.f)); } // TODO: smooth splash rotate gameData->curSplashes.insert(spl.id,spl); } for (int j=0; jcurSplashes.remove(Id); } void Splashes::doTriggerOnTimer(SplashType *spl, QList *deadIndexes) { for (int k=0; ktrigsOnTimer.size(); k++) { srcTriggerType strig = gameData->players. at(spl->PlayerId)->srcTowers. at(spl->srcTower).triggers. at(spl->trigsOnTimer.at(k).src); spl->trigsOnTimer[k].timer++; if (spl->trigsOnTimer.at(k).timer >= strig.timer) { spl->trigsOnTimer[k].timer = 0; if (strig.delParent) deadIndexes->append(spl->id); if (strig.count > 0 && strig.childId > 0) { for (int j=0; jPlayerId,spl->srcTower,strig.childId, spl->pos,spl->destination,-1,spl->TowerId); } } } } } void Splashes::doTriggerOnDest(const SplashType &spl, QList *deadIndexes, bool badAl) { for (int k=0; kplayers. at(spl.PlayerId)->srcTowers. at(spl.srcTower).triggers. at(spl.trigsOnDest.at(k).src); if (strig.delParent) deadIndexes->append(spl.id); if (strig.count > 0 && strig.childId > 0) { for (int j=0; j 0) { if (!(strig.radius > 0)) { if (!badAl) { float hh = gameData->curAliens[spl.AlienId].health -= strig.damage; if (hh < 0) gameData->curAliens.remove(spl.AlienId); } } else { QList dead; for (QHash::iterator i = gameData->curAliens.begin(); i != gameData->curAliens.end(); ++i) { if (distance2(spl.pos, (*i).pos) < strig.radius*strig.radius) { (*i).health -= strig.damage; if ((*i).health < 0) dead.append((*i).id); } } for (int i=0; icurAliens.remove(dead.at(i)); } } } }