void UpdateAI(const uint32 diff) { if (nextMovementTimer) { if (nextMovementTimer <= diff) { nextMovementTimer = 0; float x = 0.0f; float y = 0.0f; SelectNextWaypoint(x, y); me->GetMotionMaster()->MovePoint(POINT_KRIKTHIK_CIRCLE, x, y, myPositionZ); } else nextMovementTimer -= diff; } }
void HeliBrain::GoToCurrentWaypoint(void) { float rng, desHeading; float rollLoad; float rollDir; float desSpeed; float wpX, wpY, wpZ; float dx, dy, time; if ( self->curWaypoint->GetWPAction() == WP_PICKUP && onStation == NotThereYet) { Unit cargo = (Unit) self->curWaypoint->GetWPTarget(); if ( cargo ) { wpX = cargo->XPos(); wpY = cargo->YPos(); wpZ = cargo->ZPos(); } else { self->curWaypoint->GetLocation (&wpX, &wpY, &wpZ); } } else { self->curWaypoint->GetLocation (&wpX, &wpY, &wpZ); } // follow terrain at 1000ft holdAlt = OTWDriver.GetGroundLevel(self->XPos() + self->XDelta(), self->YPos() + self->YDelta()) - 1000.0f; desSpeed = 1.0f; rollDir = 0.0f; rollLoad = 0.0f; if (curMode != lastMode) { onStation = NotThereYet; } /*---------------------------*/ /* Range to current waypoint */ /*---------------------------*/ dx = (wpX - self->XPos()); dy = (wpY - self->YPos()); rng = dx * dx + dy * dy; /*------------------------------------*/ /* Heading error for current waypoint */ /*------------------------------------*/ desHeading = (float)atan2 (dy, dx) - self->Yaw(); if (desHeading > 180.0F * DTR) desHeading -= 360.0F * DTR; else if (desHeading < -180.0F * DTR) desHeading += 360.0F * DTR; // rollLoad is normalized (0-1) factor of how far off-heading we are // to target rollLoad = desHeading / (180.0F * DTR); if (rollLoad < 0.0F) rollLoad = -rollLoad; if ( desHeading > 0.0f ) rollDir = 1.0f; else rollDir = -1.0f; //MonoPrint ("%8.2f %8.2f\n", desHeading * RTD, desLoad); /*---------------------------*/ /* Reached the next waypoint? */ /*---------------------------*/ if (rng < (600.0F * 600.0F) || (onStation != NotThereYet) || SimLibElapsedTime > self->curWaypoint->GetWPDepartureTime()) { if (onStation == NotThereYet) { onStation = Arrived; } else if ( onStation == OnStation && SimLibElapsedTime > self->curWaypoint->GetWPDepartureTime()) { SelectNextWaypoint(); } } // landing? if ( onStation == Landing || onStation == DropOff || onStation == Landed || onStation == PickUp) { LandMe(); return; } /*--------------*/ /* On Station ? */ /*--------------*/ if (onStation == Arrived ) { if ( self->curWaypoint->GetWPFlags() & WPF_LAND ) { LandMe(); return; } onStation = OnStation; } // get waypoint speed based on our dist and arrival time if ( rng < 600.0f * 600.0f ) { rollLoad = 0.0f; desSpeed = 0.0f; } else { rng = (float)sqrt( rng ); if (self->curWaypoint->GetWPArrivalTime() > SimLibElapsedTime) time = (float)(self->curWaypoint->GetWPArrivalTime() - SimLibElapsedTime) / SEC_TO_MSEC; else time = -1.0f; if ( time <= 0.0f ) { // we're late desSpeed = 1.0f; } else { desSpeed = (rng/time)/MAX_HELI_FPS; if ( desSpeed > 1.0f ) desSpeed = 1.0f; } } if ( self->OnGround() ) { self->UnSetFlag( ON_GROUND ); } // if we're close, just point to spot then go if ( fabs(rollLoad) > 0.1f && rng < 1000.0f * 1000.0f ) desSpeed = 0.0f; LevelTurn (rollLoad, rollDir, TRUE); AltitudeHold(holdAlt); MachHold(desSpeed, 0.0F, FALSE); }