bool TeamZone::isInside(SpaceObject const& toBeChecked) const { switch(homeSide_) { case 0: return(toBeChecked.location().x_ < SPACE_X_RESOLUTION*0.5f); case 1: return(toBeChecked.location().x_ > SPACE_X_RESOLUTION*0.5f); default : return false; } }
void EarthlingCruiserMk3Beam::calculate() { STACKTRACE; if (!(lpos && lpos->exists())) { lpos = 0; state = 0; } if ((frame < frame_count) && (lpos && lpos->exists())) { pos = lpos->normal_pos() + rotate(rel_pos, lpos->get_angle() - PI/2); vel = lpos->get_vel(); SpaceLine::calculate(); frame += frame_time; } else state = 0; if ((!target) && (switch_counter <= 0)) { SpaceObject *o; double rng = 1e40; SpaceObject *tgt = NULL; Query a; for (a.begin(this, bit(LAYER_SHIPS) + bit(LAYER_SHOTS) + bit(LAYER_SPECIAL) + bit(LAYER_CBODIES), base_length); a.current; a.next()) { o = a.currento; if (!o->isInvisible() && !o->sameTeam(this) && (o->collide_flag_anyone&bit(LAYER_LINES)) && (distance(o) < rng)) { tgt = o; rng = distance(o); } } if (tgt) { target = tgt; // switch_counter = 55; got_spark = false; } } if (target && (distance(target) <= base_length)) { length = base_length; if (target->exists() && canCollide(target) && target->canCollide(this)) { angle = trajectory_angle(target); } if (!target->exists()) target = NULL; } else { target = NULL; if (switch_counter <= 0) // die(); length = 0; else switch_counter -= frame_time; } color = tw_makecol(100+tw_random()%105,100+tw_random()%105,255); }
void KoloryFlamer :: calculate () { // check if the weapons exist weapon1 = flamer1 && flamer1->exists(); weapon2 = flamer2 && flamer2->exists(); // update the flamer pointers if (!weapon1) flamer1 = 0; if (!weapon2) flamer2 = 0; flame_active = weapon1 | weapon2; Ship::calculate(); // regardless of whether the flames are activated or not: if ( this->fire_special ) { // DEFENSIVE MODE // double HalfTime = 1000.0 * 0.5; // 0.5 second to half the speed. // is nearly 1 slowdownfactor = exp(-frame_time*1E-3 / specialHalfTime); } else { slowdownfactor = 1.0; } int layers = bit(LAYER_SHIPS) + bit(LAYER_SHOTS) + bit(LAYER_SPECIAL) + bit(LAYER_CBODIES); double passiveRange = 1000.0;// outside this area, gravity doesn't do anything Query a; for (a.begin(this, layers, passiveRange); a.current; a.next()) { if (!a.current->isObject()) continue; SpaceObject *o = a.currento; if (!(o->isPlanet()) && o != ship ) { // the special introduces drag around the ship, depending on distance o->vel *= slowdownfactor; if ( o->isShot() ) { // shot/missiles/homing-missiles have a different existtime/physics Shot *s = ((Shot*)o); double timeleft = (s->range - s->d) / s->v; s->v *= slowdownfactor; // express in lifetime instead of range s->range = s->d + s->v * timeleft; } } } }
void AndrosynthBubble::calculate() { STACKTRACE; if (!(ship && ship->exists())) { state = 0; return; } double newAngle; AnimatedShot::calculate(); courseFrames += frame_time; if (courseFrames >= 150) { courseFrames -= 150; newAngle = random(PI2); vel = v * unit_vector(newAngle); int i; double r = 99999; newAngle = 99999; // ship->control->ship == 0 (can happen ?!) // ... yeah ... look at control->select_ship. There you can see // that control->ship=0 if the ship does not exist. Perhaps there's // a de-synch between the two calculations (!exists() lags the control->ship) ? if (ship && ship->exists() && ship->control && ship->control->ship) { for (i = 0; i < targets->N; i += 1) { SpaceObject *s = targets->item[i]; if (ship->control->valid_target(s) && (distance(s) < r) && !s->isInvisible()) { r = distance(s); newAngle = trajectory_angle(s); } } } else { for (i = 0; i < targets->N; i += 1) { SpaceObject *s = targets->item[i]; if (s->sameTeam(this) && (distance(s) < r) && !s->isInvisible()) { r = distance(s); newAngle = trajectory_angle(s); } } } if (newAngle < PI * 4) { vel += unit_vector(newAngle) * v / 2; } } return; }
void EarthlingCruiserMk3::calculate() { STACKTRACE; Ship::calculate(); double track_angle = 0; double track_min = PI2; double d_a; SpaceObject *tgt = 0; //!!! pos += unit_vector(angle) * 28; int i; for (i=0; i < targets->N; i++) { tgt = targets->item[i]; if ((tgt != this) && (!tgt->sameShip(this)) && (!tgt->sameTeam(this)) && (!tgt->isInvisible()) && (distance(tgt) <= 1.2*(weaponRange + abs(vel)*game->shot_relativity))) { d_a = trajectory_angle(tgt); double s = unit_vector(d_a + PI/2).dot(tgt->get_vel() - vel * game->shot_relativity) / weaponVelocity; if (fabs(s) > 0.99) track_angle = 0; else { s = atan(s/sqrt(1-s*s)); s = normalize(s + d_a - angle - turn_step, PI2); if (s > PI) s -= PI2; if (fabs(s) <= weaponTrackingAngle) { d_a = s - launch_angle; if (tgt == target) { track_angle = s; break; } if (fabs(d_a) < track_min) { track_angle = s; track_min = fabs(d_a); } } } } } //!!! pos -= unit_vector(angle) * 28; d_a = track_angle - launch_angle; double ta = weaponTrackingRate * frame_time; if (fabs(d_a) < ta) ta = fabs(d_a); if (d_a > 0) launch_angle += ta; else launch_angle -= ta; }
void Scene::OnDeleteObject(IScript::Object* p) { SpaceObject* object = static_cast<SpaceObject*>(p); DeallocateID(object); // test if it's a light if (UniqueType<Light>::Get() == object->QueryUnique()) { DoLock(); lightList.erase(static_cast<Light*>(object)); lightModified = true; UnLock(); } // fire destroy event EventDestroy destroy; onObjectEvent(object, destroy); }
void SpaceStation::calculate() { STACKTRACE; //Healing beam code Query a; SpaceObject *o; for (a.begin(this, bit(LAYER_SHIPS), 200.); a.current; a.next()) { o = a.currento; if (!o->isInvisible()) { game->add(new PointLaser(this, 0x0000ffff, -1, 10, this, o, Vector2(0.0, 10.0))); } } }
int TeronTurret::handle_damage(SpaceLocation *source, double normal, double direct) { STACKTRACE; Ship::handle_damage( source, normal, direct ); if ( !exists() ) base->die(); return 0; }
void TeronTurret::materialize() { STACKTRACE; Ship::materialize(); base = new TeronTurretBase( this, pos, 0, data->TERON_TURRET_BASE_SPRITE ); game->add( base ); base->calculate(); // or else maybe collision variables won't be set before too late }
void MelnormeTrader::calculate() { STACKTRACE; Ship::calculate(); if (weaponObject) { if (!weaponObject->exists()) weaponObject = NULL; if (fire_weapon) recharge_step += frame_time; else weaponObject = NULL; } }
//------------------------------------------------------------------------------ bool Formation::SetRefObject(GmatBase *obj, const Gmat::ObjectType type, const std::string &name) { SpaceObject *so; if (type == Gmat::SPACECRAFT) { so = ((SpaceObject*)(obj)); if (find(components.begin(), components.end(), so) == components.end()) { GmatState *ps = &(so->GetState()); Integer size = ps->GetSize(); dimension += size; Real newepoch = so->GetEpoch(); if (components.size() == 0) state.SetEpoch(newepoch); else if (state.GetEpoch() != newepoch) { char errorMsg[256]; sprintf(errorMsg, "Epochs (%lf) and (%lf) are not synchronized " "in the formation %s", newepoch, state.GetEpoch(), instanceName.c_str()); throw SpaceObjectException(errorMsg); } components.push_back(so); } if (type == Gmat::FORMATION) { throw SpaceObjectException("GMAT does not allow Formations of " "Formations, so the Formation \"" + name + "\" cannot be added " "to the Formation \"" + instanceName + "\"."); } return true; } return FormationInterface::SetRefObject(obj, type, name); }
void Sun::calculate() { STACKTRACE; SpaceObject::calculate(); SpaceObject *o; Query a; a.begin(this, OBJECT_LAYERS, gravity_range); for (;a.currento;a.next()) { o = a.currento; if (o->mass > 0) { double r = distance(o); if (r < gravity_mindist) r = gravity_mindist; double sr = 1; //gravity_power truncated here if (gravity_power > 0) { r /= 40 * 4; for (int i = 0; i < gravity_power; i += 1) sr *= r; o->accelerate(this, trajectory_angle(o) + PI, frame_time * gravity_force / sr, MAX_SPEED); } else { r = 1 - r/gravity_range; for (int i = 0; i < -gravity_power; i += 1) sr *= r; o->accelerate(this, trajectory_angle(o) + PI, frame_time * gravity_force * sr, MAX_SPEED); } } } /*for (;a.currento;a.next()) { o = a.currento; if (o->mass > 0) { double r = distance(o); if (r < gravity_mindist) r = gravity_mindist; r = 1 - r / gravity_range; o->accelerate(this, trajectory_angle(o) + PI, frame_time * gravity_force * r / 40000., GLOBAL_MAXSPEED); } }*/ // return; }
void TeronDroneLaser::calculate() { STACKTRACE; if ( collecting ) { if ( !collecting->exists() ) { if ( ship ) { //ship->fuel_sap -= drone->asteroid_value; //ship->handle_damage( ship ); ship->handle_fuel_sap(this, -drone->asteroid_value); } else { drone->resource += drone->asteroid_value; } } collecting = NULL; } Laser::calculate(); }
void TeronBuilder::calculate() { STACKTRACE; if ( selection_sprite_step < 0 ) { selection_sprite_step += TERON_SELECTION_ANIM_RATE; selection_sprite_index++; if ( selection_sprite_index == data->TERON_SELECTION_SPRITE->frames() ) selection_sprite_index = 0; }else selection_sprite_step -= frame_time; if ( collecting ) { if ( !collecting->exists() ) { //fuel_sap -= asteroid_value; //handle_damage( this ); handle_fuel_sap(this, -asteroid_value); } collecting = NULL; } else { if ( collect_step <= 0 && collectRange ) { Query q; for( q.begin( this, bit(LAYER_CBODIES), collectRange ); q.currento; q.next() ) { if ( q.currento->isAsteroid() ) { collecting = q.currento; game->add( new Laser( this, trajectory_angle( collecting ), pallete_color[TERON_COLLECT_BEAM_COLOR], distance( collecting ), TERON_COLLECT_BEAM_DAMAGE, time_ratio, this, 0, false )); collect_step = TERON_BUILDER_COLLECT_RATE; break; } } q.end(); } else { collect_step -= frame_time; } } if ( !(current_drone && current_drone->exists()) ) current_drone = NULL; Ship::calculate(); }
bool TacticalZone::isInside(SpaceObject const& toBeChecked) const { return((toBeChecked.location()-location_).lengthSquare() <= radius_*radius_); }
void AutoGun::calculate() { STACKTRACE; BigShipPartDevice::calculate(); if (!(ownerpart && !ownerpart->isdisabled())) return; // find the closest target Query a; SpaceObject *oclosest; double R; oclosest = 0; R = 1E99; double da_track; da_track = -a_track; // forces to go back into default position for (a.begin(this, OBJECT_LAYERS, 0.75*shotrange); a.current != 0; a.next()) { SpaceObject *o; o = a.currento; if (!o->isObject()) continue; if (o->sameShip(this) || o->sameTeam(this)) continue; if (o->isPlanet()) continue; if (o->isInvisible()) continue; double L = 0; L = distance(o); if (!oclosest || L < R) { // this is a possible candidate but, is it also within the view angle ? double a, b, da; a = trajectory_angle(o); // check relative to the gun's neutral position b = ownerpart->get_angle() + a_center; da = a - b; while (da < -PI) da += PI2; while (da > PI) da -= PI2; if (da > -a_view && da < a_view) { // okay! it's close, within dist-range, and it's within angle-range oclosest = o; R = L; // required movement is relative to the gun's current position // note that at this moment, you cannot use the value of "angle" // which is overridden by the call to AyronShipPart::calculate; so, // use "b" instead. b += a_track; da_track = a - b; while (da_track < -PI) da_track += PI2; while (da_track > PI) da_track -= PI2; } } } // track the target (or go back to neutral position) // max tracking speed per second (0.1 circles / second). // this tracking angle is relative to the neutral angle of the gun. double da; da = 100 * PI2 * frame_time * 1E-3; if (da_track > da) da_track = da; if (da_track < -da) da_track = -da; a_track += da_track; if (a_track < -a_view) a_track = -a_view; if (a_track > a_view) a_track = a_view; // absolute angle of the gun angle = ownerpart->get_angle() + a_center + a_track; sprite_index = get_index(angle); // fire the weapon ? if (oclosest && ownerpart->ship && ownerpart->ship->batt > shotdrain && !shotbusy) { Shot *s; s = new Shot(this, Vector2(0,0), angle, shotvel, shotdamage, shotrange, shotarmour, this, sprshot, 0); s->set_depth(DEPTH_SHIPS + 0.1); game->add( s ); shotbusy = shotperiod; ownerpart->ship->handle_fuel_sap(this, shotdrain); } if (shotbusy > 0) shotbusy -= frame_time * 1E-3; else shotbusy = 0; }
void AstromorphBasilisk::calculate() { STACKTRACE; // firing the weapon // vel*=0.99; if (aimline && !fire_weapon && batt - weapon_drain >= 0 && weapon_recharge <= 0) { play_sound2(data->sampleWeapon[1]); batt -= weapon_drain; if (recharge_amount > 1) recharge_step = recharge_rate; weapon_recharge += weapon_rate; regrow_delay = regrowTime; double a; if (aimline->target != NULL) { SpaceObject* targ = aimline->target; a = intercept_angle2(pos, vel * game->shot_relativity, weaponVelocity*aimBonus, targ->normal_pos(), targ->get_vel()); } else a = angle; add(new BasiliskGas(0.0, 0.0, a, (aimline->target != NULL) ? weaponVelocity*aimBonus : weaponVelocity, weaponDamage, weaponLife, weaponRange, iround(weaponArmour), poison, this, data->spriteWeapon, 1.0)); aimline->target = NULL; aimline = NULL; } // slithering //if (!(turn_left || turn_right || !thrust)) { //double frac = float(numSegs)/float(specialSegs); //double frac2 = numSegs/specialSegs; //double frac2 = magnitude(this->vel)/speed_max; double frac2 = 1.0; Vector2 normal; normal = Vector2(-vel.y, vel.x); normalize(normal); slitherFrame += frame_time * 1E-3; double a; //a = sin(PI * (frac2)*slitherFrame / 1.0 + (PI/2) ) *( (frac)*slitherAmount); // needs some work! a = (slitherAmount)*sin(slitherFrame * (frac2*slitherTime)/(PI/2) ); vel += (accel_rate*frame_time) * a * normal; /* slitherFrame -= frame_time; slitherTick += frame_time * slitherAmount; frac2 = sin(slitherTick); slitherFrame *= frac;*/ //if (slitherFrame < 0) //{ // slitherFrame = slitherTime; // bOtherWay = !bOtherWay; //} //angle -= (bOtherWay) ? (PI2/64) : -(PI2/64); /*accelerate(this, //normalize(angle - ((bOtherWay) ? (PI/4) : -(PI/4)), PI2), normalize(angle - (frac2*(PI/4))), slitherAccel*frac*frame_time, speed_max);*/ } // else { //slitherFrame = slitherTime/2; //bOtherWay = turn_right; } Ship::calculate(); // ouchification tickdown if (hurty_time <= 0) vel *= 1 - slitherFriction * frame_time; if (hurty_time >= 0) hurty_time -= frame_time * 1E-3; if (hurty_time < 0) hurty_time = 0; // regrowth if (batt == batt_max && regrowTime > 0) { regrow_delay -= frame_time * 1E-3; if (regrow_delay <= 0) if (Head) if (Head->regrow(specialSegs)) { batt -= regrowDrain; regrow_delay = regrowTime; } } }
bool RasterZone::isInside(SpaceObject const& toBeChecked) const { return toBeChecked.location().x_ > bottomLeft_.x_ && toBeChecked.location().y_ > bottomLeft_.y_ && toBeChecked.location().x_ < topRight_.x_ && toBeChecked.location().y_ < topRight_.y_; }
void MapLoader::addChild(SpaceObject* parent, pugi::xml_node parentnode) { for (pugi::xml_node node = parentnode.first_child(); node != 0; node = node.next_sibling()) { SpaceObject* newObj = 0; if(strcmp(node.name(),"star") == 0) { newObj = new Sun( node.attribute("type").as_int(), node.attribute("scale").as_float(), vector3df(node.attribute("x").as_float(), node.attribute("y").as_float(), node.attribute("z").as_float() ), vector3df(node.attribute("rotx").as_float(), node.attribute("roty").as_float(), node.attribute("rotz").as_float() ), SColorf(node.attribute("colR").as_float(), node.attribute("colG").as_float(), node.attribute("colB").as_float()), node.attribute("lightrange").as_float()); } else if(strcmp(node.name(),"planet") == 0) { newObj = new Planet( node.attribute("type").as_int(), node.attribute("scale").as_float(), vector3df(node.attribute("x").as_float(), node.attribute("y").as_float(), node.attribute("z").as_float()), vector3df(node.attribute("rotx").as_float(), node.attribute("roty").as_float(), node.attribute("rotz").as_float())); } else if(strcmp(node.name(),"moon") == 0) { newObj = new Moon( node.attribute("type").as_int(), node.attribute("scale").as_float(), vector3df(node.attribute("x").as_float(), node.attribute("y").as_float(), node.attribute("z").as_float()), vector3df(node.attribute("rotx").as_float(), node.attribute("roty").as_float(), node.attribute("rotz").as_float())); } else if(strcmp(node.name(),"asteroid") == 0) { newObj = new Asteroid( node.attribute("type").as_int(), node.attribute("scale").as_float(), vector3df(node.attribute("x").as_float(), node.attribute("y").as_float(), node.attribute("z").as_float()), vector3df(node.attribute("rotx").as_float(), node.attribute("roty").as_float(), node.attribute("rotz").as_float())); } if(newObj){ if(node.attribute("orbit").as_bool() == true) { newObj->setOrbit(parent, node.attribute("maja").as_float(), vector3df(node.attribute ("centerx").as_float (), node.attribute ("centery").as_float (), node.attribute ("centerz").as_float ()), node.attribute("phase").as_float()); } newObj->setRotationSpeed( vector3df(node.attribute("rotspx").as_float(), node.attribute("rotspy").as_float(), node.attribute("rotspz").as_float())); newObj->setMass(node.attribute("mass").as_float()); map_->addObject (newObj); } addChild(newObj, node); } }