コード例 #1
0
ファイル: ModuleTurret.cs プロジェクト: KAmaia/BDArmory
        public void AimToTarget(Vector3 targetPosition, bool pitch = true, bool yaw = true)
        {
            if (!yawTransform)
            {
                return;
            }

            float deltaTime = Time.fixedDeltaTime;

            Vector3 localTargetYaw = yawTransform.parent.InverseTransformPoint(targetPosition - (yawTargetOffset * pitchTransform.right));
            Vector3 targetYaw      = Vector3.ProjectOnPlane(localTargetYaw, Vector3.up);
            float   targetYawAngle = VectorUtils.SignedAngle(Vector3.forward, targetYaw, Vector3.right);

            targetYawAngle = Mathf.Clamp(targetYawAngle, -yawRange / 2, yawRange / 2);

            Quaternion currYawRot = yawTransform.localRotation;

            yawTransform.localRotation = Quaternion.Euler(0, targetYawAngle, 0);
            Vector3 localTargetPitch = pitchTransform.parent.InverseTransformPoint(targetPosition - (pitchTargetOffset * pitchTransform.up));

            yawTransform.localRotation = currYawRot;
            localTargetPitch.z         = Mathf.Abs(localTargetPitch.z);    //prevents from aiming wonky if target is behind
            Vector3 targetPitch      = Vector3.ProjectOnPlane(localTargetPitch, Vector3.right);
            float   targetPitchAngle = VectorUtils.SignedAngle(Vector3.forward, targetPitch, Vector3.up);

            targetPitchAngle = Mathf.Clamp(targetPitchAngle, minPitch, maxPitch);

            float yawOffset      = Vector3.Angle(yawTransform.parent.InverseTransformDirection(yawTransform.forward), targetYaw);
            float currentYawSign = Mathf.Sign(Vector3.Dot(yawTransform.localRotation * Vector3.forward, Vector3.right));
            float pitchOffset    = Vector3.Angle(pitchTransform.parent.InverseTransformDirection(pitchTransform.forward), targetPitch);

            float linPitchMult = yawOffset > 0 ? Mathf.Clamp01((pitchOffset / yawOffset) * (yawSpeedDPS / pitchSpeedDPS)) : 1;
            float linYawMult   = pitchOffset > 0 ? Mathf.Clamp01((yawOffset / pitchOffset) * (pitchSpeedDPS / yawSpeedDPS)) : 1;

            float yawSpeed;
            float pitchSpeed;

            if (smoothRotation)
            {
                yawSpeed   = Mathf.Clamp(yawOffset * smoothMultiplier, 1f, yawSpeedDPS) * deltaTime;
                pitchSpeed = Mathf.Clamp(pitchOffset * smoothMultiplier, 1f, pitchSpeedDPS) * deltaTime;
            }
            else
            {
                yawSpeed   = yawSpeedDPS * deltaTime;
                pitchSpeed = pitchSpeedDPS * deltaTime;
            }

            yawSpeed   *= linYawMult;
            pitchSpeed *= linPitchMult;

            if (yawRange < 360 && Mathf.Abs(targetYawAngle) > 90 && currentYawSign != Mathf.Sign(targetYawAngle))
            {
                targetYawAngle = 5 * Mathf.Sign(targetYawAngle);
            }

            if (yaw)
            {
                yawTransform.localRotation = Quaternion.RotateTowards(yawTransform.localRotation, Quaternion.Euler(0, targetYawAngle, 0), yawSpeed);
            }
            if (pitch)
            {
                pitchTransform.localRotation = Quaternion.RotateTowards(pitchTransform.localRotation, Quaternion.Euler(-targetPitchAngle, 0, 0), pitchSpeed);
            }
        }
コード例 #2
0
        void FlyToPosition(FlightCtrlState s, Vector3 targetPosition)
        {
            if (!startedLanded)
            {
                targetPosition = FlightPosition(targetPosition, minAltitude);
            }


            Vector3d srfVel = vessel.srf_velocity;

            if (srfVel != Vector3d.zero)
            {
                velocityTransform.rotation = Quaternion.LookRotation(srfVel, -vesselTransform.forward);
            }
            velocityTransform.rotation = Quaternion.AngleAxis(90, velocityTransform.right) * velocityTransform.rotation;
            Vector3 localAngVel = vessel.angularVelocity;

            if (steerMode == SteerModes.NormalFlight)
            {
                float   angleToTarget   = Vector3.Angle(targetPosition - vesselTransform.position, vesselTransform.up);
                Vector3 dampedDirection = Vector3.RotateTowards(vesselTransform.up, targetPosition - vesselTransform.position, (angleToTarget / 2) * Mathf.Deg2Rad, 0).normalized;
                targetPosition = vesselTransform.position + (500 * dampedDirection);
            }

            if (BDArmorySettings.DRAW_DEBUG_LINES)
            {
                flyingToPosition = targetPosition;
            }

            Vector3 targetDirection;
            Vector3 targetDirectionYaw;
            float   yawError;
            float   pitchError;
            float   postYawFactor;
            float   postPitchFactor;

            if (steerMode == SteerModes.NormalFlight)
            {
                targetDirection = velocityTransform.InverseTransformDirection(targetPosition - velocityTransform.position).normalized;
                targetDirection = Vector3.RotateTowards(Vector3.up, targetDirection, 45 * Mathf.Deg2Rad, 0);

                targetDirectionYaw = vesselTransform.InverseTransformDirection(vessel.srf_velocity).normalized;
                targetDirectionYaw = Vector3.RotateTowards(Vector3.up, targetDirectionYaw, 45 * Mathf.Deg2Rad, 0);


                postYawFactor   = 1;
                postPitchFactor = 1;
            }
            else            //(steerMode == SteerModes.Aiming)
            {
                targetDirection    = vesselTransform.InverseTransformDirection(targetPosition - vesselTransform.position).normalized;
                targetDirection    = Vector3.RotateTowards(Vector3.up, targetDirection, 45 * Mathf.Deg2Rad, 0);
                targetDirectionYaw = targetDirection;

                if (command == PilotCommands.Follow)
                {
                    postYawFactor   = 1.5f;
                    postPitchFactor = 1f;
                }
                else
                {
                    postYawFactor   = 1.6f;
                    postPitchFactor = 2.4f;
                }
            }

            pitchError = VectorUtils.SignedAngle(Vector3.up, Vector3.ProjectOnPlane(targetDirection, Vector3.right), Vector3.back);
            yawError   = VectorUtils.SignedAngle(Vector3.up, Vector3.ProjectOnPlane(targetDirectionYaw, Vector3.forward), Vector3.right);



            float finalMaxSteer = threatLevel * maxSteer;

            float steerPitch = (postPitchFactor * 0.015f * steerMult * pitchError) - (postPitchFactor * steerDamping * -localAngVel.x);
            float steerYaw   = (postYawFactor * 0.022f * steerMult * yawError) - (postPitchFactor * steerDamping * -localAngVel.z);


            s.yaw   = Mathf.Clamp(steerYaw, -finalMaxSteer, finalMaxSteer);
            s.pitch = Mathf.Clamp(steerPitch, Mathf.Min(-finalMaxSteer, -0.2f), finalMaxSteer);


            //roll
            Vector3 currentRoll = -vesselTransform.forward;
            Vector3 rollTarget;

            if (steerMode == SteerModes.Aiming || Vector3.Angle(vesselTransform.up, targetPosition - vesselTransform.position) > 2)
            {
                rollTarget = (targetPosition + ((steerMode == SteerModes.Aiming ? 10 : 45f) * upDirection)) - vesselTransform.position;
            }
            else
            {
                rollTarget = upDirection;
            }

            if (command == PilotCommands.Follow && useRollHint)
            {
                rollTarget = -commandLeader.vessel.ReferenceTransform.forward;
            }

            rollTarget = Vector3.ProjectOnPlane(rollTarget, vesselTransform.up);



            float rollError = Misc.SignedAngle(currentRoll, rollTarget, vesselTransform.right);

            debugString += "\nRoll offset: " + rollError;
            float steerRoll = (steerMult * 0.0015f * rollError);

            debugString += "\nSteerRoll: " + steerRoll;
            float rollDamping = (.10f * steerDamping * -localAngVel.y);

            steerRoll   -= rollDamping;
            debugString += "\nRollDamping: " + rollDamping;



            float roll = Mathf.Clamp(steerRoll, -maxSteer, maxSteer);

            s.roll = roll;
            //
        }
コード例 #3
0
ファイル: ModuleWingCommander.cs プロジェクト: yaus/BDArmory
        IEnumerator CommandPosition(BDModulePilotAI wingman, BDModulePilotAI.PilotCommands command)
        {
            if (focusIndexes.Count == 0 && !commandSelf)
            {
                yield break;
            }

            DisplayScreenMessage("Select target coordinates.\nRight-click to cancel.");

            if (command == BDModulePilotAI.PilotCommands.FlyTo)
            {
                waitingForFlytoPos = true;
            }
            else if (command == BDModulePilotAI.PilotCommands.Attack)
            {
                waitingForAttackPos = true;
            }

            yield return(null);

            bool waitingForPos = true;

            drawMouseDiamond = true;
            while (waitingForPos)
            {
                if (Input.GetMouseButtonDown(1))
                {
                    break;
                }
                if (Input.GetMouseButtonDown(0))
                {
                    Vector3 mousePos  = new Vector3(Input.mousePosition.x / Screen.width, Input.mousePosition.y / Screen.height, 0);
                    Plane   surfPlane = new Plane(vessel.upAxis, vessel.transform.position - (vessel.altitude * vessel.upAxis));
                    Ray     ray       = FlightCamera.fetch.mainCamera.ViewportPointToRay(mousePos);
                    float   dist;
                    if (surfPlane.Raycast(ray, out dist))
                    {
                        Vector3  worldPoint = ray.GetPoint(dist);
                        Vector3d gps        = VectorUtils.WorldPositionToGeoCoords(worldPoint, vessel.mainBody);

                        if (command == BDModulePilotAI.PilotCommands.FlyTo)
                        {
                            wingman.CommandFlyTo(gps);
                        }
                        else if (command == BDModulePilotAI.PilotCommands.Attack)
                        {
                            wingman.CommandAttack(gps);
                        }

                        StartCoroutine(CommandPositionGUIRoutine(wingman, new GPSTargetInfo(gps, command.ToString())));
                    }

                    break;
                }
                yield return(null);
            }

            waitingForAttackPos = false;
            waitingForFlytoPos  = false;
            drawMouseDiamond    = false;
            ScreenMessages.RemoveMessage(screenMessage);
        }
コード例 #4
0
ファイル: RadarUtils.cs プロジェクト: Arcamenal/BDArmory
        public static void UpdateRadarLock(MissileFire myWpnManager, float directionAngle, Transform referenceTransform, float fov, Vector3 position, float minSignature, ref TargetSignatureData[] dataArray, float dataPersistTime, bool pingRWR, RadarWarningReceiver.RWRThreatTypes rwrType, bool radarSnapshot)
        {
            Vector3d geoPos        = VectorUtils.WorldPositionToGeoCoords(position, FlightGlobals.currentMainBody);
            Vector3  forwardVector = referenceTransform.forward;
            Vector3  upVector      = referenceTransform.up;      //VectorUtils.GetUpDirection(position);
            Vector3  lookDirection = Quaternion.AngleAxis(directionAngle, upVector) * forwardVector;

            int dataIndex = 0;

            foreach (var vessel in BDATargetManager.LoadedVessels)
            {
                if (vessel == null)
                {
                    continue;
                }
                if (!vessel.loaded)
                {
                    continue;
                }

                if (myWpnManager)
                {
                    if (vessel == myWpnManager.vessel)
                    {
                        continue;                                                   //ignore self
                    }
                }
                else if ((vessel.transform.position - position).sqrMagnitude < 3600)
                {
                    continue;
                }

                Vector3 vesselDirection = Vector3.ProjectOnPlane(vessel.CoM - position, upVector);

                if (Vector3.Angle(vesselDirection, lookDirection) < fov / 2)
                {
                    if (TerrainCheck(referenceTransform.position, vessel.transform.position))
                    {
                        continue;                                                                                          //blocked by terrain
                    }
                    float sig = float.MaxValue;
                    if (radarSnapshot && minSignature > 0)
                    {
                        sig = GetModifiedSignature(vessel, position);
                    }

                    RadarWarningReceiver.PingRWR(vessel, position, rwrType, dataPersistTime);

                    float detectSig = sig;

                    VesselECMJInfo vesselJammer = vessel.GetComponent <VesselECMJInfo>();
                    if (vesselJammer)
                    {
                        sig       *= vesselJammer.rcsReductionFactor;
                        detectSig += vesselJammer.jammerStrength;
                    }

                    if (detectSig > minSignature)
                    {
                        if (vessel.vesselType == VesselType.Debris)
                        {
                            vessel.gameObject.AddComponent <TargetInfo>();
                        }
                        else if (myWpnManager != null)
                        {
                            BDATargetManager.ReportVessel(vessel, myWpnManager);
                        }

                        while (dataIndex < dataArray.Length - 1)
                        {
                            if ((dataArray[dataIndex].exists && Time.time - dataArray[dataIndex].timeAcquired > dataPersistTime) || !dataArray[dataIndex].exists)
                            {
                                break;
                            }
                            dataIndex++;
                        }
                        if (dataIndex >= dataArray.Length)
                        {
                            break;
                        }
                        dataArray[dataIndex] = new TargetSignatureData(vessel, sig);
                        dataIndex++;
                        if (dataIndex >= dataArray.Length)
                        {
                            break;
                        }
                    }
                }
            }
        }
コード例 #5
0
        void AutoPilot(FlightCtrlState s)
        {
            if (!vessel || !vessel.transform || vessel.packed || !vessel.mainBody)
            {
                return;
            }
            vesselTransform = vessel.ReferenceTransform;

            //default brakes off full throttle
            s.mainThrottle = 1;
            vessel.ActionGroups.SetGroup(KSPActionGroup.Brakes, false);
            vessel.ActionGroups.SetGroup(KSPActionGroup.SAS, true);

            steerMode = SteerModes.NormalFlight;


            GetGuardTarget();
            if (vessel.Landed && standbyMode && weaponManager && BDATargetManager.TargetDatabase[BDATargetManager.BoolToTeam(weaponManager.team)].Count == 0)
            {
                s.mainThrottle = 0;
                vessel.ActionGroups.SetGroup(KSPActionGroup.Brakes, true);
                return;
            }
            //upDirection = -FlightGlobals.getGeeForceAtPosition(transform.position).normalized;
            upDirection = VectorUtils.GetUpDirection(vessel.transform.position);
            debugString = string.Empty;
            if (MissileGuidance.GetRadarAltitude(vessel) < minAltitude)
            {
                startedLanded = true;
            }



            if (startedLanded)
            {
                TakeOff(s);
                turningTimer = 0;
            }
            else
            {
                if (FlyAvoidCollision(s))
                {
                    turningTimer = 0;
                }
                else if (command != PilotCommands.Free)
                {
                    UpdateCommand(s);
                }
                else
                {
                    UpdateAI(s);
                }
            }

            //brake and cut throttle if exceeding max speed
            if (vessel.srfSpeed > maxSpeed)
            {
                vessel.ActionGroups.SetGroup(KSPActionGroup.Brakes, true);
                s.mainThrottle = 0;
            }

            debugString += "\nthreatLevel: " + threatLevel;
        }
コード例 #6
0
        protected void UpdateLaserTarget()
        {
            if (TargetAcquired)
            {
                if (lockedCamera && lockedCamera.groundStabilized && !lockedCamera.gimbalLimitReached && lockedCamera.surfaceDetected) //active laser target
                {
                    TargetPosition     = lockedCamera.groundTargetPosition;
                    TargetVelocity     = (TargetPosition - lastLaserPoint) / Time.fixedDeltaTime;
                    TargetAcceleration = Vector3.zero;
                    lastLaserPoint     = TargetPosition;

                    if (GuidanceMode == GuidanceModes.BeamRiding && TimeIndex > 0.25f && Vector3.Dot(GetForwardTransform(), part.transform.position - lockedCamera.transform.position) < 0)
                    {
                        TargetAcquired = false;
                        lockedCamera   = null;
                    }
                }
                else //lost active laser target, home on last known position
                {
                    if (CMSmoke.RaycastSmoke(new Ray(transform.position, lastLaserPoint - transform.position)))
                    {
                        //Debug.Log("Laser missileBase affected by smoke countermeasure");
                        float angle = VectorUtils.FullRangePerlinNoise(0.75f * Time.time, 10) * BDArmorySettings.SMOKE_DEFLECTION_FACTOR;
                        TargetPosition     = VectorUtils.RotatePointAround(lastLaserPoint, transform.position, VectorUtils.GetUpDirection(transform.position), angle);
                        TargetVelocity     = Vector3.zero;
                        TargetAcceleration = Vector3.zero;
                        lastLaserPoint     = TargetPosition;
                    }
                    else
                    {
                        TargetPosition = lastLaserPoint;
                    }
                }
            }
            else
            {
                ModuleTargetingCamera foundCam = null;
                bool parentOnly = (GuidanceMode == GuidanceModes.BeamRiding);
                foundCam = BDATargetManager.GetLaserTarget(this, parentOnly);
                if (foundCam != null && foundCam.cameraEnabled && foundCam.groundStabilized && BDATargetManager.CanSeePosition(foundCam.groundTargetPosition, vessel.transform.position, MissileReferenceTransform.position))
                {
                    Debug.Log("[BDArmory]: Laser guided missileBase actively found laser point. Enabling guidance.");
                    lockedCamera   = foundCam;
                    TargetAcquired = true;
                }
            }
        }
コード例 #7
0
ファイル: RadarUtils.cs プロジェクト: Arcamenal/BDArmory
        /// <summary>
        /// Scans for targets in direction with field of view.
        /// Returns the direction scanned for debug
        /// </summary>
        /// <returns>The scan direction.</returns>
        /// <param name="myWpnManager">My wpn manager.</param>
        /// <param name="directionAngle">Direction angle.</param>
        /// <param name="referenceTransform">Reference transform.</param>
        /// <param name="fov">Fov.</param>
        /// <param name="results">Results.</param>
        /// <param name="maxDistance">Max distance.</param>
        public static Vector3 GuardScanInDirection(MissileFire myWpnManager, float directionAngle, Transform referenceTransform, float fov, out ViewScanResults results, float maxDistance)
        {
            fov    *= 1.1f;
            results = new ViewScanResults();
            results.foundMissile          = false;
            results.foundHeatMissile      = false;
            results.foundRadarMissile     = false;
            results.foundAGM              = false;
            results.firingAtMe            = false;
            results.missileThreatDistance = float.MaxValue;
            results.threatVessel          = null;
            results.threatWeaponManager   = null;

            if (!myWpnManager || !referenceTransform)
            {
                return(Vector3.zero);
            }

            Vector3  position      = referenceTransform.position;
            Vector3d geoPos        = VectorUtils.WorldPositionToGeoCoords(position, FlightGlobals.currentMainBody);
            Vector3  forwardVector = referenceTransform.forward;
            Vector3  upVector      = referenceTransform.up;
            Vector3  lookDirection = Quaternion.AngleAxis(directionAngle, upVector) * forwardVector;



            foreach (var vessel in BDATargetManager.LoadedVessels)
            {
                if (vessel == null)
                {
                    continue;
                }

                if (vessel.loaded)
                {
                    if (vessel == myWpnManager.vessel)
                    {
                        continue;                                                   //ignore self
                    }
                    Vector3 vesselProjectedDirection = Vector3.ProjectOnPlane(vessel.transform.position - position, upVector);
                    Vector3 vesselDirection          = vessel.transform.position - position;


                    if (Vector3.Dot(vesselDirection, lookDirection) < 0)
                    {
                        continue;
                    }

                    float vesselDistance = (vessel.transform.position - position).magnitude;

                    if (vesselDistance < maxDistance && Vector3.Angle(vesselProjectedDirection, lookDirection) < fov / 2 && Vector3.Angle(vessel.transform.position - position, -myWpnManager.transform.forward) < myWpnManager.guardAngle / 2)
                    {
                        //Debug.Log("Found vessel: " + vessel.vesselName);
                        if (TerrainCheck(referenceTransform.position, vessel.transform.position))
                        {
                            continue;                                                                                              //blocked by terrain
                        }
                        BDATargetManager.ReportVessel(vessel, myWpnManager);

                        TargetInfo tInfo;
                        if ((tInfo = vessel.GetComponent <TargetInfo>()))
                        {
                            if (tInfo.isMissile)
                            {
                                MissileBase missileBase;
                                if (missileBase = tInfo.MissileBaseModule)
                                {
                                    results.foundMissile = true;
                                    results.threatVessel = missileBase.vessel;
                                    Vector3 vectorFromMissile = myWpnManager.vessel.CoM - missileBase.part.transform.position;
                                    Vector3 relV        = missileBase.vessel.srf_velocity - myWpnManager.vessel.srf_velocity;
                                    bool    approaching = Vector3.Dot(relV, vectorFromMissile) > 0;
                                    if (missileBase.HasFired && missileBase.TimeIndex > 1 && approaching && (missileBase.TargetPosition - (myWpnManager.vessel.CoM + (myWpnManager.vessel.srf_velocity * Time.fixedDeltaTime))).sqrMagnitude < 3600)
                                    {
                                        if (missileBase.TargetingMode == MissileBase.TargetingModes.Heat)
                                        {
                                            results.foundHeatMissile      = true;
                                            results.missileThreatDistance = Mathf.Min(results.missileThreatDistance, Vector3.Distance(missileBase.part.transform.position, myWpnManager.part.transform.position));
                                            results.threatPosition        = missileBase.transform.position;
                                            break;
                                        }
                                        else if (missileBase.TargetingMode == MissileBase.TargetingModes.Radar)
                                        {
                                            results.foundRadarMissile     = true;
                                            results.missileThreatDistance = Mathf.Min(results.missileThreatDistance, Vector3.Distance(missileBase.part.transform.position, myWpnManager.part.transform.position));
                                            results.threatPosition        = missileBase.transform.position;
                                        }
                                        else if (missileBase.TargetingMode == MissileBase.TargetingModes.Laser)
                                        {
                                            results.foundAGM = true;
                                            results.missileThreatDistance = Mathf.Min(results.missileThreatDistance, Vector3.Distance(missileBase.part.transform.position, myWpnManager.part.transform.position));
                                            break;
                                        }
                                    }
                                    else
                                    {
                                        break;
                                    }
                                }
                            }
                            else
                            {
                                //check if its shooting guns at me
                                //if(!results.firingAtMe)       //more work, but we can't afford to be incorrect picking the closest threat
                                //{
                                foreach (var weapon in vessel.FindPartModulesImplementing <ModuleWeapon>())
                                {
                                    if (!weapon.recentlyFiring)
                                    {
                                        continue;
                                    }
                                    if (Vector3.Dot(weapon.fireTransforms[0].forward, vesselDirection) > 0)
                                    {
                                        continue;
                                    }

                                    if (Vector3.Angle(weapon.fireTransforms[0].forward, -vesselDirection) < 6500 / vesselDistance && (!results.firingAtMe || (weapon.vessel.ReferenceTransform.position - position).magnitude < (results.threatPosition - position).magnitude))
                                    {
                                        results.firingAtMe          = true;
                                        results.threatPosition      = weapon.vessel.transform.position;
                                        results.threatVessel        = weapon.vessel;
                                        results.threatWeaponManager = weapon.weaponManager;
                                        break;
                                    }
                                }
                                //}
                            }
                        }
                    }
                }
            }

            return(lookDirection);
        }
コード例 #8
0
        void Update()
        {
            if (HighLogic.LoadedSceneIsFlight)
            {
                if (cameraEnabled && !vessel.IsControllable)
                {
                    DisableCamera();
                }

                if (cameraEnabled && TargetingCamera.ReadyForUse && vessel.IsControllable)
                {
                    if (delayedEnabling)
                    {
                        return;
                    }


                    if (!TargetingCamera.Instance || FlightGlobals.currentMainBody == null)
                    {
                        return;
                    }

                    if (activeCam == this)
                    {
                        if (zoomFovs != null)
                        {
                            TargetingCamera.Instance.SetFOV(fov);
                        }
                    }



                    if (radarLock)
                    {
                        UpdateRadarLock();
                    }

                    if (groundStabilized)
                    {
                        groundTargetPosition = VectorUtils.GetWorldSurfacePostion(bodyRelativeGTP, vessel.mainBody);                        //vessel.mainBody.GetWorldSurfacePosition(bodyRelativeGTP.x, bodyRelativeGTP.y, bodyRelativeGTP.z);
                        Vector3 lookVector = groundTargetPosition - cameraParentTransform.position;
                        cameraParentTransform.rotation = Quaternion.LookRotation(lookVector);
                    }



                    Vector3 lookDirection = cameraParentTransform.forward;
                    if (Vector3.Angle(lookDirection, cameraParentTransform.parent.forward) > gimbalLimit)
                    {
                        lookDirection      = Vector3.RotateTowards(cameraParentTransform.transform.parent.forward, lookDirection, gimbalLimit * Mathf.Deg2Rad, 0);
                        gimbalLimitReached = true;
                    }
                    else
                    {
                        gimbalLimitReached = false;
                    }

                    cameraParentTransform.rotation = Quaternion.LookRotation(lookDirection, VectorUtils.GetUpDirection(transform.position));

                    if (eyeHolderTransform)
                    {
                        Vector3 projectedForward = Vector3.ProjectOnPlane(cameraParentTransform.forward, eyeHolderTransform.parent.up);
                        if (projectedForward != Vector3.zero)
                        {
                            eyeHolderTransform.rotation = Quaternion.LookRotation(projectedForward, eyeHolderTransform.parent.up);
                        }
                    }

                    UpdateControls();
                }
            }
        }
コード例 #9
0
 void UpdateRadarLock()
 {
     if (weaponManager && weaponManager.radar && weaponManager.radar.locked)
     {
         Vector3    radarTargetPos = weaponManager.radar.lockedTarget.predictedPosition + (weaponManager.radar.lockedTarget.velocity * Time.fixedDeltaTime);
         Quaternion lookRotation   = Quaternion.LookRotation(radarTargetPos - cameraParentTransform.position, VectorUtils.GetUpDirection(cameraParentTransform.position));
         if (Vector3.Angle(radarTargetPos - cameraParentTransform.position, cameraParentTransform.forward) < 1.5f)
         {
             cameraParentTransform.rotation = lookRotation;
             GroundStabilize();
         }
         else
         {
             if (groundStabilized)
             {
                 ClearTarget();
             }
             cameraParentTransform.rotation = Quaternion.RotateTowards(cameraParentTransform.rotation, lookRotation, 80 * Time.fixedDeltaTime);
         }
     }
     else
     {
         radarLock = false;
     }
 }
コード例 #10
0
        public IEnumerator PointToPositionRoutine(Vector3 position)
        {
            yield return(StopPTPRRoutine());

            stopPTPR          = false;
            slewingToPosition = true;
            radarLock         = false;
            StopResetting();
            ClearTarget();
            while (!stopPTPR && Vector3.Angle(cameraParentTransform.transform.forward, position - (cameraParentTransform.transform.position + (part.rb.velocity * Time.fixedDeltaTime))) > 0.75f)
            {
                Vector3 newForward = Vector3.RotateTowards(cameraParentTransform.transform.forward, position - cameraParentTransform.transform.position, 60 * Mathf.Deg2Rad * Time.fixedDeltaTime, 0);
                cameraParentTransform.rotation = Quaternion.LookRotation(newForward, VectorUtils.GetUpDirection(transform.position));

                yield return(new WaitForFixedUpdate());

                if (gimbalLimitReached)
                {
                    ClearTarget();
                    StartCoroutine("ResetCamera");
                    slewingToPosition = false;
                    yield break;
                }
            }
            if (surfaceDetected && !stopPTPR)
            {
                cameraParentTransform.transform.rotation = Quaternion.LookRotation(position - cameraParentTransform.position, VectorUtils.GetUpDirection(transform.position));
                GroundStabilize();
            }
            slewingToPosition = false;
            yield break;
        }
コード例 #11
0
        // Update is called once per frame
        void Update()
        {
            if (HighLogic.LoadedSceneIsFlight && FlightGlobals.ready && !vessel.packed && radarEnabled)
            {
                if (omnidirectional)
                {
                    referenceTransform.position = vessel.transform.position;
                    referenceTransform.rotation = Quaternion.LookRotation(VectorUtils.GetNorthVector(transform.position, vessel.mainBody), VectorUtils.GetUpDirection(transform.position));
                }
                else
                {
                    referenceTransform.position = vessel.transform.position;
                    referenceTransform.rotation = Quaternion.LookRotation(part.transform.up, VectorUtils.GetUpDirection(referenceTransform.position));
                }
                //UpdateInputs();
            }

            drawGUI = (HighLogic.LoadedSceneIsFlight && FlightGlobals.ready && !vessel.packed && radarEnabled && vessel.isActiveVessel && BDArmorySettings.GAME_UI_ENABLED && !MapView.MapIsEnabled);

            //UpdateSlaveData();
        }
コード例 #12
0
        public static TargetSignatureData GetHeatTarget(Ray ray, float scanRadius, float highpassThreshold, bool allAspect)
        {
            float minScore = highpassThreshold;
            float minMass  = 0.5f;
            TargetSignatureData finalData = TargetSignatureData.noTarget;
            float finalScore = 0;

            foreach (var vessel in BDATargetManager.LoadedVessels)
            {
                if (!vessel || !vessel.loaded)
                {
                    continue;
                }
                if (vessel.GetTotalMass() < minMass)
                {
                    continue;
                }

                if (RadarUtils.TerrainCheck(ray.origin, vessel.transform.position))
                {
                    continue;
                }

                float angle = Vector3.Angle(vessel.CoM - ray.origin, ray.direction);
                if (angle < scanRadius)
                {
                    float score = 0;
                    foreach (var part in vessel.Parts)
                    {
                        if (!part)
                        {
                            continue;
                        }
                        if (!allAspect)
                        {
                            if (!Misc.CheckSightLine(ray.origin, part.transform.position, 10000, 5, 5))
                            {
                                continue;
                            }
                        }

                        float thisScore = (float)(part.thermalInternalFluxPrevious + part.skinTemperature) * Mathf.Clamp01(15 / angle);
                        thisScore *= Mathf.Pow(1400, 2) / Mathf.Clamp((vessel.CoM - ray.origin).sqrMagnitude, 90000, 36000000);
                        score      = Mathf.Max(score, thisScore);
                    }

                    if (vessel.LandedOrSplashed)
                    {
                        score /= 4;
                    }

                    score *= Mathf.Clamp(Vector3.Angle(vessel.transform.position - ray.origin, -VectorUtils.GetUpDirection(ray.origin)) / 90, 0.5f, 1.5f);

                    if (score > finalScore)
                    {
                        finalScore = score;
                        finalData  = new TargetSignatureData(vessel, score);
                    }
                }
            }

            heatScore  = finalScore;    //DEBUG
            flareScore = 0;             //DEBUG
            foreach (var flare in BDArmorySettings.Flares)
            {
                if (!flare)
                {
                    continue;
                }

                float angle = Vector3.Angle(flare.transform.position - ray.origin, ray.direction);
                if (angle < scanRadius)
                {
                    float score = flare.thermal * Mathf.Clamp01(15 / angle);
                    score *= Mathf.Pow(1400, 2) / Mathf.Clamp((flare.transform.position - ray.origin).sqrMagnitude, 90000, 36000000);

                    score *= Mathf.Clamp(Vector3.Angle(flare.transform.position - ray.origin, -VectorUtils.GetUpDirection(ray.origin)) / 90, 0.5f, 1.5f);

                    if (score > finalScore)
                    {
                        flareScore = score;                        //DEBUG
                        finalScore = score;
                        finalData  = new TargetSignatureData(flare, score);
                    }
                }
            }



            if (finalScore < minScore)
            {
                finalData = TargetSignatureData.noTarget;
            }

            return(finalData);
        }
コード例 #13
0
        IEnumerator DogfightCompetitionModeRoutine(float distance)
        {
            competitionStarting = true;
            competitionStatus   = "Competition: Pilots are taking off.";
            Dictionary <BDArmorySettings.BDATeams, List <BDModulePilotAI> > pilots =
                new Dictionary <BDArmorySettings.BDATeams, List <BDModulePilotAI> >();

            pilots.Add(BDArmorySettings.BDATeams.A, new List <BDModulePilotAI>());
            pilots.Add(BDArmorySettings.BDATeams.B, new List <BDModulePilotAI>());
            foreach (var v in BDATargetManager.LoadedVessels)
            {
                if (!v || !v.loaded)
                {
                    continue;
                }
                BDModulePilotAI pilot = null;
                foreach (var p in v.FindPartModulesImplementing <BDModulePilotAI>())
                {
                    pilot = p;
                    break;
                }

                if (!pilot || !pilot.weaponManager)
                {
                    continue;
                }

                pilots[BDATargetManager.BoolToTeam(pilot.weaponManager.team)].Add(pilot);
                pilot.ActivatePilot();
                pilot.standbyMode = false;
                if (pilot.weaponManager.guardMode)
                {
                    pilot.weaponManager.ToggleGuardMode();
                }
            }

            //clear target database so pilots don't attack yet
            BDATargetManager.ClearDatabase();

            if (pilots[BDArmorySettings.BDATeams.A].Count == 0 || pilots[BDArmorySettings.BDATeams.B].Count == 0)
            {
                Debug.Log("[BDArmory]: Unable to start competition mode - one or more teams is empty");
                competitionStatus = "Competition: Failed!  One or more teams is empty.";
                yield return(new WaitForSeconds(2));

                competitionStarting = false;
                yield break;
            }

            BDModulePilotAI aLeader = pilots[BDArmorySettings.BDATeams.A][0];
            BDModulePilotAI bLeader = pilots[BDArmorySettings.BDATeams.B][0];

            aLeader.weaponManager.wingCommander.CommandAllFollow();
            bLeader.weaponManager.wingCommander.CommandAllFollow();


            //wait till the leaders are airborne
            while (aLeader && bLeader && (aLeader.vessel.LandedOrSplashed || bLeader.vessel.LandedOrSplashed))
            {
                yield return(null);
            }

            if (!aLeader || !bLeader)
            {
                StopCompetition();
            }

            competitionStatus = "Competition: Sending pilots to start position.";
            Vector3 aDirection =
                Vector3.ProjectOnPlane(aLeader.vessel.CoM - bLeader.vessel.CoM, aLeader.vessel.upAxis).normalized;
            Vector3 bDirection =
                Vector3.ProjectOnPlane(bLeader.vessel.CoM - aLeader.vessel.CoM, bLeader.vessel.upAxis).normalized;

            Vector3 center       = (aLeader.vessel.CoM + bLeader.vessel.CoM) / 2f;
            Vector3 aDestination = center + (aDirection * (distance + 1250f));
            Vector3 bDestination = center + (bDirection * (distance + 1250f));

            aDestination = VectorUtils.WorldPositionToGeoCoords(aDestination, FlightGlobals.currentMainBody);
            bDestination = VectorUtils.WorldPositionToGeoCoords(bDestination, FlightGlobals.currentMainBody);

            aLeader.CommandFlyTo(aDestination);
            bLeader.CommandFlyTo(bDestination);

            Vector3 centerGPS = VectorUtils.WorldPositionToGeoCoords(center, FlightGlobals.currentMainBody);

            //wait till everyone is in position
            bool waiting = true;

            while (waiting)
            {
                waiting = false;

                if (!aLeader || !bLeader)
                {
                    StopCompetition();
                }

                if (Vector3.Distance(aLeader.transform.position, bLeader.transform.position) < distance * 1.95f)
                {
                    waiting = true;
                }
                else
                {
                    foreach (var t in pilots.Keys)
                    {
                        foreach (var p in pilots[t])
                        {
                            if (p.currentCommand == BDModulePilotAI.PilotCommands.Follow &&
                                Vector3.Distance(p.vessel.CoM, p.commandLeader.vessel.CoM) > 1000f)
                            {
                                competitionStatus = "Competition: Waiting for teams to get in position.";
                                waiting           = true;
                            }
                        }
                    }
                }

                yield return(null);
            }

            //start the match
            foreach (var t in pilots.Keys)
            {
                foreach (var p in pilots[t])
                {
                    if (!p)
                    {
                        continue;
                    }

                    //enable guard mode
                    if (!p.weaponManager.guardMode)
                    {
                        p.weaponManager.ToggleGuardMode();
                    }

                    //report all vessels
                    if (BDATargetManager.BoolToTeam(p.weaponManager.team) == BDArmorySettings.BDATeams.B)
                    {
                        BDATargetManager.ReportVessel(p.vessel, aLeader.weaponManager);
                    }
                    else
                    {
                        BDATargetManager.ReportVessel(p.vessel, bLeader.weaponManager);
                    }

                    //release command
                    p.ReleaseCommand();
                    p.defaultOrbitCoords = centerGPS;
                }
            }
            competitionStatus = "Competition starting!  Good luck!";
            yield return(new WaitForSeconds(2));

            competitionStarting = false;
        }
コード例 #14
0
        //public static TargetSignatureData GetHeatTarget(Ray ray, float scanRadius, float highpassThreshold, bool allAspect, MissileFire mf = null)
        public static TargetSignatureData GetHeatTarget(Ray ray, float scanRadius, float highpassThreshold, bool allAspect, MissileFire mf = null, bool favorGroundTargets = false)
        {
            float minScore = highpassThreshold;
            float minMass  = 0.15f; //otherwise the RAMs have trouble shooting down incoming missiles
            TargetSignatureData finalData = TargetSignatureData.noTarget;
            float finalScore = 0;

            foreach (var vessel in BDATargetManager.LoadedVessels)
            {
                if (!vessel || !vessel.loaded)
                {
                    continue;
                }

                if (favorGroundTargets && !vessel.LandedOrSplashed) // for AGM heat guidance
                {
                    continue;
                }

                TargetInfo tInfo = vessel.gameObject.GetComponent <TargetInfo>();
                if (mf == null ||
                    !tInfo ||
                    !(mf && tInfo.isMissile && tInfo.team != BDATargetManager.BoolToTeam(mf.team) && (tInfo.MissileBaseModule.MissileState == MissileBase.MissileStates.Boost || tInfo.MissileBaseModule.MissileState == MissileBase.MissileStates.Cruise)))
                {
                    if (vessel.GetTotalMass() < minMass)
                    {
                        continue;
                    }
                }

                if (RadarUtils.TerrainCheck(ray.origin, vessel.transform.position))
                {
                    continue;
                }

                float angle = Vector3.Angle(vessel.CoM - ray.origin, ray.direction);
                if (angle < scanRadius)
                {
                    float score = 0;
                    foreach (var part in vessel.Parts)
                    {
                        if (!part)
                        {
                            continue;
                        }
                        if (!allAspect)
                        {
                            if (!Misc.CheckSightLineExactDistance(ray.origin, part.transform.position + vessel.srf_velocity, Vector3.Distance(part.transform.position, ray.origin), 5, 5))
                            {
                                continue;
                            }
                        }

                        float thisScore = (float)(part.thermalInternalFluxPrevious + part.skinTemperature) * (15 / Mathf.Max(15, angle));
                        thisScore *= Mathf.Pow(1400, 2) / Mathf.Clamp((vessel.CoM - ray.origin).sqrMagnitude, 90000, 36000000);
                        score      = Mathf.Max(score, thisScore);
                    }

                    if (vessel.LandedOrSplashed && !favorGroundTargets)
                    {
                        score /= 4;
                    }

                    score *= Mathf.Clamp(Vector3.Angle(vessel.transform.position - ray.origin, -VectorUtils.GetUpDirection(ray.origin)) / 90, 0.5f, 1.5f);

                    if (score > finalScore)
                    {
                        finalScore = score;
                        finalData  = new TargetSignatureData(vessel, score);
                    }
                }
            }

            heatScore  = finalScore;    //DEBUG
            flareScore = 0;             //DEBUG
            foreach (var flare in BDArmorySettings.Flares)
            {
                if (!flare)
                {
                    continue;
                }

                float angle = Vector3.Angle(flare.transform.position - ray.origin, ray.direction);
                if (angle < scanRadius)
                {
                    float score = flare.thermal * Mathf.Clamp01(15 / angle);
                    score *= Mathf.Pow(1400, 2) / Mathf.Clamp((flare.transform.position - ray.origin).sqrMagnitude, 90000, 36000000);

                    score *= Mathf.Clamp(Vector3.Angle(flare.transform.position - ray.origin, -VectorUtils.GetUpDirection(ray.origin)) / 90, 0.5f, 1.5f);

                    if (score > finalScore)
                    {
                        flareScore = score;                        //DEBUG
                        finalScore = score;
                        finalData  = new TargetSignatureData(flare, score);
                    }
                }
            }



            if (finalScore < minScore)
            {
                finalData = TargetSignatureData.noTarget;
            }

            return(finalData);
        }