private static void SetupInBackground(object obj) { GenData rootData = (GenData)obj; Conditions conditions = rootData.conditions; CalculationManager manager = rootData.storeState.manager; CalculationManager seedManager = new CalculationManager(); CalculationManager.State[,] results = null; Conditions seedConditions = new Conditions(conditions.body, conditions.lowerBoundSpeed, conditions.upperBoundSpeed, 11, conditions.lowerBoundAltitude, conditions.upperBoundAltitude, 11); GenerateLevel(seedConditions, seedManager, ref results, rootData.vessel); if (!seedManager.WaitForCompletion(30000)) { Debug.LogError("KerbalWindTunnel: Seed data timed out!"); return; } seedManager.Dispose(); GenerateLevel(conditions, manager, ref results, rootData.vessel); if (rootData.storeState.manager.Cancelled) { return; } rootData.storeState.StoreResult(results); }
private IEnumerator ProcessOptimalLine(string graphName, AeroPredictor vessel, Conditions conditions, float exitSpeed, float exitAlt, float initialSpeed, float initialAlt, CostIncreaseFunction costIncreaseFunc, Predicate <float> neighborPredicate, float[,] predicateData, CostIncreaseFunction timeDifferenceFunc) { CalculationManager singleUseManager = new CalculationManager(); LineGenData lineGenData = new LineGenData(singleUseManager, vessel, conditions, exitSpeed, exitAlt, initialSpeed, initialAlt, costIncreaseFunc, neighborPredicate, predicateData, timeDifferenceFunc); ThreadPool.QueueUserWorkItem(OptimalLineTask, lineGenData); while (!singleUseManager.Completed) { yield return(0); } List <AscentPathPoint> results = (List <AscentPathPoint>)lineGenData.state.Result; if (timeDifferenceFunc != costIncreaseFunc) { ((MetaLineGraph)graphables[graphName]).SetValues(results.Select(pt => new Vector2(pt.speed, pt.altitude)).ToArray(), new float[][] { results.Select(pt => pt.climbAngle * Mathf.Rad2Deg).ToArray(), results.Select(pt => pt.climbRate).ToArray(), results.Select(pt => pt.cost).ToArray(), results.Select(pt => pt.time).ToArray() }); } else { ((MetaLineGraph)graphables[graphName]).SetValues(results.Select(pt => new Vector2(pt.speed, pt.altitude)).ToArray(), new float[][] { results.Select(pt => pt.climbAngle * Mathf.Rad2Deg).ToArray(), results.Select(pt => pt.climbRate).ToArray(), results.Select(pt => pt.cost).ToArray() }); } //this.GetOptimalPath(vessel, conditions, 1410, 17700, 0, 0, fuelToClimb, f => f > 0, excessP).Select(pt => new Vector2(pt.speed, pt.altitude)).ToArray()); //((LineGraph)graphables["Time-Optimal Path"]).SetValues( //this.GetOptimalPath(vessel, conditions, 1410, 17700, 0, 0, timeToClimb, f => f > 0, excessP).Select(pt => new Vector2(pt.speed, pt.altitude)).ToArray()); singleUseManager.Dispose(); }
private IEnumerator RefinementProcessing(CalculationManager manager, Conditions conditions, AeroPredictor vessel, EnvelopePoint[,] basisData, Conditions basisConditions = new Conditions(), Queue <Conditions> followOnConditions = null, bool forcePushToGraph = false) { int numPtsX = (int)Math.Ceiling((conditions.upperBoundSpeed - conditions.lowerBoundSpeed) / conditions.stepSpeed); int numPtsY = (int)Math.Ceiling((conditions.upperBoundAltitude - conditions.lowerBoundAltitude) / conditions.stepAltitude); EnvelopePoint[,] newEnvelopePoints = new EnvelopePoint[numPtsX + 1, numPtsY + 1]; CalculationManager backgroundManager = new CalculationManager(); manager.OnCancelCallback += backgroundManager.Cancel; CalculationManager.State[,] results = new CalculationManager.State[numPtsX + 1, numPtsY + 1]; GenData rootData = new GenData(vessel, conditions, 0, 0, backgroundManager); ThreadPool.QueueUserWorkItem(ContinueInBackground, new object[] { rootData, results, basisData, basisConditions }); while (!backgroundManager.Completed) { if (manager.Status == CalculationManager.RunStatus.Cancelled) { backgroundManager.Cancel(); yield break; } yield return(0); } manager.OnCancelCallback -= backgroundManager.Cancel; newEnvelopePoints = ((CalculationManager.State[, ])rootData.storeState.Result) .SelectToArray(pt => (EnvelopePoint)pt.Result); AddToCache(conditions, newEnvelopePoints); if (currentConditions.Equals(conditions) || (forcePushToGraph && !backgroundManager.Cancelled)) { envelopePoints = newEnvelopePoints; currentConditions = conditions; UpdateGraphs(); valuesSet = true; } backgroundManager.Dispose(); if (!manager.Cancelled && followOnConditions != null && followOnConditions.Count > 0) { yield return(0); Conditions nextConditions = followOnConditions.Dequeue(); WindTunnel.Instance.StartCoroutine(RefinementProcessing(manager, nextConditions, vessel, newEnvelopePoints, conditions, followOnConditions, forcePushToGraph)); } }