private void monitorAnomScience(CelestialBody B, string s, string name) { if (FlightGlobals.currentMainBody == B) { if (s == scienceContainer.Exp.id) { DMAnomalyList.updateAnomaly(FlightGlobals.ActiveVessel, root.TargetAnomaly); DMUtils.Logging("Distance To Anomaly: {0} ; Altitude Above Anomaly: {1} ; Horizontal Distance To Anomaly: {2}", root.TargetAnomaly.VDistance, root.TargetAnomaly.VHeight, root.TargetAnomaly.VHorizontal); //Draw a cone above the anomaly position up to 100km with a diameter of 60km at its widest if (root.TargetAnomaly.VDistance < 100000) { if (situation == ExperimentSituations.FlyingLow || situation == ExperimentSituations.InSpaceLow || situation == ExperimentSituations.FlyingHigh) { if (root.TargetAnomaly.VHeight > 625 && root.TargetAnomaly.VHeight < 100000) { double vHeight = root.TargetAnomaly.VHeight; if (vHeight > 50000) { vHeight = 50000; } if (root.TargetAnomaly.VHorizontal < (60000 * (root.TargetAnomaly.VHeight / 50000))) { ScreenMessages.PostScreenMessage("Results From Anomalous Signal Recovered", 6f, ScreenMessageStyle.UPPER_CENTER); collected = true; } else { ScreenMessages.PostScreenMessage("Anomalous signal too weak, try again when closer", 6f, ScreenMessageStyle.UPPER_CENTER); } } else if (root.TargetAnomaly.VHeight < 625) { if (root.TargetAnomaly.VHorizontal < 750) { ScreenMessages.PostScreenMessage("Results From Anomalous Signal Recovered", 6f, ScreenMessageStyle.UPPER_CENTER); collected = true; } else { ScreenMessages.PostScreenMessage("Anomalous signal too weak, try again when closer", 6f, ScreenMessageStyle.UPPER_CENTER); } } } else if (situation == ExperimentSituations.SrfLanded) { if (root.TargetAnomaly.VHorizontal < 500) { ScreenMessages.PostScreenMessage("Results From Anomalous Signal Recovered", 6f, ScreenMessageStyle.UPPER_CENTER); collected = true; } else { ScreenMessages.PostScreenMessage("Anomalous signal too weak, try again when closer", 6f, ScreenMessageStyle.UPPER_CENTER); } } } } } }
private void getAnomValues() { anomCloseRange = false; anomInRange = false; closestAnom = ""; foreach (DMAnomalyObject anom in DMScienceScenario.SciScenario.anomalyList.anomObjects()) { DMAnomalyList.updateAnomaly(vessel, anom); if (anom.VDistance < 100000) { if (anom.VHorizontal < (30000 * (1 - anom.VHeight / 15000))) //Determine cutoff distance on sliding scale based on altitude above the anomaly. { DMAnomalyList.bearing(vessel, anom); //Calculate the bearing to the anomaly from the current vessel position. string anomDirection = direction(anom.Bearing); //Get cardinal directions based on the bearing. anomInRange = true; DMUtils.Logging("Anomaly: {0} is at bearing: {1:N1} deg at a distance of {2:N1}m.", anom.Name, anom.Bearing, anom.VDistance); if (anom.VDistance < 250) //Scanning range distance for science experiment. { closestAnom = anom.Name; anomCloseRange = true; break; } else if (anom.VHeight > 10000) //Use alternate message when more than 10km above the anomaly. { ScreenMessages.PostScreenMessage(string.Format("Anomalous signal detected approximately {0:N1} km below current position, get closer for a better signal", anom.VDistance / 1000 + RandomDouble((2 * (anom.VDistance / 1000) / 30), (4 * (anom.VDistance / 1000) / 30))), 6f, ScreenMessageStyle.UPPER_CENTER); } else { ScreenMessages.PostScreenMessage(string.Format("Anomalous signal detected approximately {0:N1} km away to the {1}, get closer for a better signal.", anom.VDistance / 1000 + RandomDouble((2 * (anom.VDistance / 1000) / 30), (4 * (anom.VDistance / 1000) / 30)), anomDirection), 6f, ScreenMessageStyle.UPPER_CENTER); } } } } }
private void inRange() { bool anomInRange = false; foreach (DMAnomalyObject anom in DMScienceScenario.SciScenario.anomalyList.anomObjects()) { DMAnomalyList.updateAnomaly(vessel, anom); if (anom.VDistance < 50000) { if (anom.VHorizontal < (11000 * (1 - anom.VHeight / 6000))) { anomInRange = true; if (anom.VHorizontal < (10000 * (1 - anom.VHeight / 5000))) { if (!camDeployed) { newSecondaryAnimator(camAnimate, 1f, 0f, WrapMode.Default); camDeployed = true; if (anom.VDistance < 250) { newSecondaryAnimator(foundAnimate, 1f, 0f, WrapMode.PingPong); closeRange = true; break; } else { closeRange = false; } } if (camDeployed) { camRotate(anom.WorldLocation); if (anom.VDistance < 250 && closeRange == false) { newSecondaryAnimator(foundAnimate, 1f, 0f, WrapMode.PingPong); closeRange = true; break; } if (anom.VDistance >= 275 && closeRange == true) { animSecondary[foundAnimate].wrapMode = WrapMode.Default; closeRange = false; } } } } } } if (!anomInRange && camDeployed) { animSecondary[foundAnimate].wrapMode = WrapMode.Default; cam.localRotation = Quaternion.Slerp(cam.localRotation, new Quaternion(0, 0, 0, 1), 1f); newSecondaryAnimator(camAnimate, -1f, 1f, WrapMode.Default); camDeployed = false; } }
private bool checkAnomalyDistance(DMAnomalyObject a) { if (a == null) { return(false); } DMAnomalyList.updateAnomaly(vessel, a); //DMUtils.Logging("Checking Anomaly: [{0}]\nDistance: {1:F4}m\nHeight: {2:F4}m\nHorizontal: {3:F4}m", a.Name, a.VDistance, a.VHeight, a.VHorizontal); if (a.VDistance >= 50000) { return(false); } if (a.VHorizontal >= (11000 * (1 - a.VHeight / 6000))) { return(false); } anomInRange = true; if (a.VHorizontal >= (10000 * (1 - a.VHeight / 5000))) { return(false); } if (!camDeployed) { newSecondaryAnimator(camAnimate, 1f, 0f, WrapMode.Default); camDeployed = true; } if (camDeployed) { camRotate(a.WorldLocation); if (a.VDistance < 250 && closeRange == false) { newSecondaryAnimator(foundAnimate, 1f, 0f, WrapMode.PingPong); closeRange = true; return(true); } if (a.VDistance >= 275 && closeRange == true) { animSecondary[foundAnimate].wrapMode = WrapMode.Default; closeRange = false; } } return(false); }
private bool checkAnomalyForScience(DMAnomalyObject a) { if (a == null) { return(false); } DMAnomalyList.updateAnomaly(vessel, a); //DMUtils.Logging("Checking Anomaly For Science: [{0}]\nDistance: {1:F4}m\nHeight: {2:F4}m\nHorizontal: {3:F4}m", a.Name, a.VDistance, a.VHeight, a.VHorizontal); if (a.VDistance >= 50000) { return(false); } //Determine cutoff distance on sliding scale based on altitude above the anomaly. if (a.VHorizontal >= (30000 * (1 - a.VHeight / 15000))) { return(false); } //Calculate the bearing to the anomaly from the current vessel position. DMAnomalyList.bearing(vessel, a); //Get cardinal directions based on the bearing. string anomDirection = direction(a.Bearing); anomScienceInRange = true; DMUtils.Logging("Anomaly: {0} is at bearing: {1:N1} deg at a distance of {2:N1}m.", a.Name, a.Bearing, a.VDistance); //Scanning range distance for science experiment. if (a.VDistance < 250) { closestAnom = a.Name; anomCloseRange = true; return(true); } //Use alternate message when more than 10km above the anomaly. else if (a.VHeight > 10000) { ScreenMessages.PostScreenMessage(string.Format("Anomalous signal detected approximately {0:N1} km below current position, get closer for a better signal.", a.VDistance / 1000 + RandomDouble((2 * (a.VDistance / 1000) / 30), (4 * (a.VDistance / 1000) / 30))), 6f, ScreenMessageStyle.UPPER_CENTER); } else { ScreenMessages.PostScreenMessage(string.Format("Anomalous signal detected approximately {0:N1} km away to the {1}, get closer for a better signal.", a.VDistance / 1000 + RandomDouble((2 * (a.VDistance / 1000) / 30), (4 * (a.VDistance / 1000) / 30)), anomDirection), 6f, ScreenMessageStyle.UPPER_CENTER); } return(false); }
public override void DeployExperiment() { if (Inoperable) { ScreenMessages.PostScreenMessage("Anomalous Signal Scanner is no longer functional; must be reset at a science lab or returned to Kerbin", 6f, ScreenMessageStyle.UPPER_CENTER); } else if (storedScienceReports.Count > 0) { ScreenMessages.PostScreenMessage(storageFullMessage, 6f, ScreenMessageStyle.UPPER_CENTER); } else { if (!IsDeployed) { deployEvent(); } if (!DMAnomalyList.MagUpdating && !DMAnomalyList.ScannerUpdating) { foreach (DMAnomalyObject anom in DMAnomalyList.anomObjects) { DMAnomalyList.updateAnomaly(vessel, anom); } } getAnomValues(); if (anomInRange) { if (anomCloseRange) { runExperiment(); } } else { ScreenMessages.PostScreenMessage("No anomalous signals detected.", 4f, ScreenMessageStyle.UPPER_CENTER); } } }
public void Update() { if (HighLogic.LoadedSceneIsFlight && primaryModule != null) { if (!FlightGlobals.ready || DMScienceScenario.SciScenario == null) { return; } float deltaTime = 1f; if (Time.deltaTime != 0) { deltaTime = TimeWarp.deltaTime / Time.deltaTime; } if (deltaTime > 10) { deltaTime = 10; } float dTime = Time.time * deltaTime; if (dTime - lastUpdate > updateInterval || dTime < updateInterval) { lastUpdate = Time.time; if (primaryModule.IsDeployed && runMagnetometer) { CelestialBody planetID = vessel.mainBody; int ID = planetID.flightGlobalsIndex; //double latDeg; // = (vessel.latitude + 90 + 180) % 180 - 90; //double lonDeg; // = (vessel.longitude + 180 + 360) % 360 - 180; double lat; double lon; double alt; double uDay; double nDay; int localDay; long date; //Paramaters for mag field model int i = 10; double[] field = new double[6]; double lonShift; if (ID == 1 || ID == 2 || ID == 3 || ID == 5 || ID == 6 || ID == 7 || ID == 8 || ID == 9 || ID == 10 || ID == 11 || ID == 12 || ID == 13 || ID == 14) { if (ID == 9 || ID == 10 || ID == 11 || ID == 12 || ID == 14) { //For now the Joolian moons return values relative to Jool Vector3 vesselPosition = vessel.transform.position; alt = FlightGlobals.fetch.bodies[8].GetAltitude(vesselPosition) / 5000; lat = ((FlightGlobals.fetch.bodies[8].GetLatitude(vesselPosition) + 90 + 180) % 180 - 90) * Mathf.Deg2Rad; lon = ((FlightGlobals.fetch.bodies[8].GetLongitude(vesselPosition) + 180 + 360) % 360 - 180) * Mathf.Deg2Rad; planetID = FlightGlobals.fetch.bodies[8]; } else if (ID == 2 || ID == 3) { Vector3 vesselPosition = vessel.transform.position; alt = FlightGlobals.fetch.bodies[1].GetAltitude(vesselPosition) / 1000; lat = ((FlightGlobals.fetch.bodies[1].GetLatitude(vesselPosition) + 90 + 180) % 180 - 90) * Mathf.Deg2Rad; lon = ((FlightGlobals.fetch.bodies[1].GetLongitude(vesselPosition) + 180 + 360) % 360 - 180) * Mathf.Deg2Rad; planetID = FlightGlobals.fetch.bodies[1]; } else if (ID == 7) { Vector3 vesselPosition = vessel.transform.position; alt = FlightGlobals.fetch.bodies[6].GetAltitude(vesselPosition) / 1000; lat = ((FlightGlobals.fetch.bodies[6].GetLatitude(vesselPosition) + 90 + 180) % 180 - 90) * Mathf.Deg2Rad; lon = ((FlightGlobals.fetch.bodies[6].GetLongitude(vesselPosition) + 180 + 360) % 360 - 180) * Mathf.Deg2Rad; planetID = FlightGlobals.fetch.bodies[6]; } else if (ID == 13) { Vector3 vesselPosition = vessel.transform.position; alt = FlightGlobals.fetch.bodies[5].GetAltitude(vesselPosition) / 1000; lat = ((FlightGlobals.fetch.bodies[5].GetLatitude(vesselPosition) + 90 + 180) % 180 - 90) * Mathf.Deg2Rad; lon = ((FlightGlobals.fetch.bodies[5].GetLongitude(vesselPosition) + 180 + 360) % 360 - 180) * Mathf.Deg2Rad; planetID = FlightGlobals.fetch.bodies[5]; } else { lat = ((vessel.latitude + 90 + 180) % 180 - 90) * Mathf.Deg2Rad; lon = ((vessel.longitude + 180 + 360) % 360 - 180) * Mathf.Deg2Rad; alt = vessel.altitude / 1000; if (ID == 8) { alt /= 5; } } uDay = Planetarium.GetUniversalTime() / solarDay(planetID); nDay = uDay % 1; //Shift our current longitide to account for solar day - lonShift should equal zero when crossing solar noon, bring everything down to -Pi to Pi just to be safe //For reference, at time zero the sun is directly above -90.158 Deg West on Kerbin, I'm rounding that to -90, or -Pi/2 lonShift = ((lon + longShift(planetID, nDay)) + Math.PI + Math.PI * 2) % (2 * Math.PI) - Math.PI; //Simulate magnetosphere distortion by solar wind with stretched torus shape, determine our position on the surface of the torus double radiusx = ((3.5 + (1 + 1 / Math.Cos(lonShift)) * Math.Cos(Math.PI + lonShift)) + (3.5 + (1.3 + 1 / Math.Cos(lonShift)) * Math.Cos(Math.PI + lonShift)) * Math.Cos(lat * 2)) * Math.Cos(lonShift); double radiusy = (0.75 + 0.9 * Math.Cos(lat * 2)) * Math.Sin(lonShift); double radiusz = (1 + 0.2 * Math.Cos(lonShift)) * Math.Sin(lat * 2); double Radius = Math.Sqrt((radiusx * radiusx) + (radiusy * radiusy) + (radiusz * radiusz)); if (Radius == 0) { Radius += 0.001; } //Scale our altitude by our position on the simulated torus, ignore at altitudes below one planetary radius, ramp up quickly above high scaled altitude up to a max value if (alt > altScale(planetID)) { alt *= radScale(planetID) / Radius; if (alt < altScale(planetID)) { alt = altScale(planetID); } } if (alt > altScale(planetID) * 2) { alt *= Math.Pow((alt / (altScale(planetID) * 2)), 3); } if (alt > altMax(planetID)) { alt = altMax(planetID); } } else if (ID == 0) { lat = ((vessel.latitude + 90 + 180) % 180 - 90) * Mathf.Deg2Rad; lon = ((vessel.longitude + 180 + 360) % 360 - 180) * Mathf.Deg2Rad; alt = vessel.altitude / 50000; uDay = Planetarium.GetUniversalTime() / solarDay(planetID); } else { //For non-magnetic planets use our position relative to the sun to calculate alt, lat, and long Vector3 vesselPosition = vessel.transform.position; alt = FlightGlobals.fetch.bodies[0].GetAltitude(vesselPosition) / 50000; lat = ((FlightGlobals.fetch.bodies[0].GetLatitude(vesselPosition) + 90 + 180) % 180 - 90) * Mathf.Deg2Rad; lon = ((FlightGlobals.fetch.bodies[0].GetLongitude(vesselPosition) + 180 + 360) % 360 - 180) * Mathf.Deg2Rad; planetID = FlightGlobals.fetch.bodies[0]; uDay = Planetarium.GetUniversalTime() / solarDay(planetID); } localDay = Convert.ToInt32(uDay); date = 2455197 + (localDay % 500) + ID * 25; //Send all of our modified parameters to the field model double[] magComp = getMag(lat, lon, alt, date, i, field); //Magnetic field components //double Brad = magComp[0]; //double BPsi = magComp[2]; //double BTheta = magComp[1]; double Bx = magComp[3] * planetScale(planetID); double By = magComp[4] * planetScale(planetID); double Bz = magComp[5] * planetScale(planetID); //Calculate various magenetic field components based on 3-axis field strength double Bh = Math.Sqrt((Bx * Bx) + (By * By)); //Alter the magnetic field line vector when far away from the planet if (ID > 0) { if (alt > altScale(planetID) * 3) { if (ID == 8) { if (alt < (altMax(planetID) / 7)) { Bh /= (alt / (altScale(planetID) * 3)); Bz *= (alt / (altScale(planetID) * 3)); } else { Bh /= ((altMax(planetID) / 7) / (altScale(planetID) * 3)); Bz *= ((altMax(planetID) / 7) / (altScale(planetID) * 3)); } } else { if (alt < (altMax(planetID) / 2)) { Bh /= (alt / (altScale(planetID) * 3)); Bz *= (alt / (altScale(planetID) * 3)); } else { Bh /= ((altMax(planetID) / 2) / (altScale(planetID) * 3)); Bz *= ((altMax(planetID) / 2) / (altScale(planetID) * 3)); } } } } //Anomaly Detection Cities.Clear(); if (!DMAnomalyList.ScannerUpdating) { currentAnomalies = DMAnomalyList.getAnomalyStorage(vessel.mainBody.name); if (currentAnomalies != null) { for (int a = 0; a < currentAnomalies.AnomalyCount; a++) //foreach (DMAnomalyObject anom in DMScienceScenario.SciScenario.anomalyList.anomObjects()) { DMAnomalyObject anom = currentAnomalies.getAnomaly(a); if (anom == null) { continue; } //foreach (DMAnomalyObject anom in DMScienceScenario.SciScenario.anomalyList.anomObjects()) //{ DMAnomalyList.updateAnomaly(vessel, anom); if (anom.VDistance < 100000) { Cities.Add(anom); } } } } else { currentAnomalies = DMAnomalyList.getAnomalyStorage(vessel.mainBody.name); if (currentAnomalies != null) { for (int a = 0; a < currentAnomalies.AnomalyCount; a++) { //foreach (DMAnomalyObject anom in DMScienceScenario.SciScenario.anomalyList.anomObjects()) //{ DMAnomalyObject anom = currentAnomalies.getAnomaly(a); if (anom == null) { continue; } if (anom.VDistance < 100000) { Cities.Add(anom); } } } } if (Cities.Count > 0) { var sortAnom = from entry in Cities orderby entry.VDistance ascending select entry; var closestAnom = sortAnom.First(); double anomMult = 1d; double anomMultZ = 1d; double anomMultH = 1d; if (closestAnom.VDistance != 0) { anomMult = 1 + ((100000 - closestAnom.VDistance) / 10000); anomMultZ = 1 + (anomMult * ((closestAnom.VDistance - closestAnom.VHorizontal) / closestAnom.VDistance)); anomMultH = 1 + (anomMult * ((closestAnom.VDistance - closestAnom.VHeight) / closestAnom.VDistance)); } Bz *= anomMultZ; Bh *= anomMultH; } double Bti = Math.Sqrt((Bh * Bh) + (Bz * Bz)); double dip = Math.Atan2(Bz, Bh); double decD; //Return 0 declination at magnetic poles if (Bx != 0.0 || By != 0.0) { decD = Math.Atan2(By, Bx); } else { decD = 0.0; } //Convert values for better display dip *= Mathf.Rad2Deg; decD *= Mathf.Rad2Deg; float Btf = (float)Bti; float incf = (float)dip; float decf = (float)decD; float Bzf = (float)Bz; float Bhf = (float)Bh; //float BRf = (float)Brad; //float BPsif = (float)BPsi; //float BThetaf = (float)BTheta; //float Bxf = (float)Bx; //float Byf = (float)By; //Display in right-click menu Bt = Btf.ToString("F2") + " nT"; inc = incf.ToString("F2") + "Deg"; dec = decf.ToString("F2") + "Deg"; BhS = Bhf.ToString("F2") + " nT"; BzS = Bzf.ToString("F2") + " nT"; //Br = BRf.ToString("F2") + " nT"; //Bpsi = BPsif.ToString("F2") + " nT"; //Btheta = BThetaf.ToString("F2") + " nT"; //BX = Bxf.ToString("F2") + " nT"; //BY = Byf.ToString("F2") + " nT"; //BZ = Bzf.ToString("F2") + " nT"; Fields["Bt"].guiActive = primaryModule.IsDeployed; Fields["inc"].guiActive = alt < (altScale(planetID) / 2); Fields["dec"].guiActive = alt < (altScale(planetID) / 2); Fields["BhS"].guiActive = alt >= (altScale(planetID) / 2); Fields["BzS"].guiActive = alt >= (altScale(planetID) / 2); //Extra variables - used in development //nDays = nDay.ToString(); //float altf = (float)alt; //float nDayf = (float)nDay; //Vector3 sunP = FlightGlobals.fetch.bodies[0].position; //Vector3 sunD = transform.InverseTransformPoint(sunP) - part.transform.localPosition; ////lons = nDayf.ToString("F5"); //double sunXd = sunD.x; //double sunZd = sunD.z; //sunX = sunXd.ToString(); //sunZ = sunZd.ToString(); //lats = altf.ToString("F4"); //nDays = nDayf.ToString("F4"); //radius = Radius.ToString(); //float latf = (float)latDeg; //lats = (lon * Mathf.Rad2Deg).ToString(); //lons = (lonShift * Mathf.Rad2Deg).ToString(); //float lonf = (float)lonDeg; //lats = latf.ToString("F3") + " Deg"; //altScaled = alt.ToString(); //lons = lonf.ToString("F3") + " Deg"; //lons = Btf.ToString("F2") + " nT"; //lons = "Shifted long: " + (((lonShift * Mathf.Rad2Deg) + 180 + 360) % 360 - 180).ToString(); //lons = "Scaled Bh: " + Bh.ToString(); //Bznew = "Scaled Bz: " + Bz.ToString(); //Fields["sunX"].guiActive = primaryModule.IsDeployed; //Fields["sunZ"].guiActive = primaryModule.IsDeployed; //Fields["lats"].guiActive = primaryModule.IsDeployed; //Fields["nDays"].guiActive = primaryModule.IsDeployed; //Fields["lons"].guiActive = primaryModule.IsDeployed; //Fields["Bhold"].guiActive = primaryModule.IsDeployed; } else { Fields["Bt"].guiActive = false; Fields["inc"].guiActive = false; Fields["dec"].guiActive = false; Fields["BhS"].guiActive = false; Fields["BzS"].guiActive = false; } } } }