Index: DamEngine/trunk/src/Deltares.DamEngine.Calculators/DikesDesign/DesignCalculator.cs =================================================================== diff -u -r1150 -r1151 --- DamEngine/trunk/src/Deltares.DamEngine.Calculators/DikesDesign/DesignCalculator.cs (.../DesignCalculator.cs) (revision 1150) +++ DamEngine/trunk/src/Deltares.DamEngine.Calculators/DikesDesign/DesignCalculator.cs (.../DesignCalculator.cs) (revision 1151) @@ -22,17 +22,13 @@ using System; using System.Collections.Generic; using System.IO; -using System.Linq; -using System.Text; using Deltares.DamEngine.Calculators.KernelWrappers.Common; using Deltares.DamEngine.Calculators.KernelWrappers.Interfaces; using Deltares.DamEngine.Calculators.Properties; using Deltares.DamEngine.Data.Design; using Deltares.DamEngine.Data.General; using Deltares.DamEngine.Data.General.Results; -using Deltares.DamEngine.Data.Geometry; using Deltares.DamEngine.Data.Geotechnics; -using Deltares.DamEngine.Data.Standard.Calculation; using Deltares.DamEngine.Data.Standard.Logging; namespace Deltares.DamEngine.Calculators.DikesDesign @@ -42,12 +38,6 @@ /// public class DesignCalculator { - private const double CMinimumShoulderElevation = 0.5; - private const double CMinimumShoulderExtraElevation = 0.05; - private const double CMinimumShoulderWidth = 2; - private const double CMinimumShoulderExtraWidth = 1; - private const double CToleranceShoulderChanges = 0.001; - /// /// Performs the design calculation /// @@ -99,12 +89,16 @@ switch (analysisType) { case AnalysisType.AdaptGeometry: - PerformDesignCalculationShoulderIterativePerPoint(kernelWrapper, kernelDataInput, kernelDataOutput, - damKernelInput, designScenario, calculationMessages, damProjectData.DesignCalculations); + DesignCalculatorShoulderPerPoint.PerformDesignCalculationShoulderPerPoint( + kernelWrapper, kernelDataInput, kernelDataOutput, + damKernelInput, designScenario, calculationMessages, + damProjectData.DesignCalculations); break; case AnalysisType.NoAdaption: - PerformSingleCalculation(kernelWrapper, kernelDataInput, kernelDataOutput, - damKernelInput, designScenario, calculationMessages, damProjectData.DesignCalculations); + DesignCalculatorSingle.PerformSingleCalculation( + kernelWrapper, kernelDataInput, kernelDataOutput, + damKernelInput, designScenario, calculationMessages, + damProjectData.DesignCalculations); break; } @@ -212,217 +206,5 @@ } } - private static void PerformSingleCalculation(IKernelWrapper kernelWrapper, IKernelDataInput kernelDataInput, IKernelDataOutput kernelDataOutput, - DamKernelInput damKernelInput, DesignScenario designScenario, - List calculationMessages, List designCalculations) - { - // Perform validation - var designResults = new List(); - List locationCalculationMessages = new List(); - List validationMessages; - try - { - int errorCount = kernelWrapper.Validate(kernelDataInput, kernelDataOutput, out validationMessages); - if (errorCount > 0) - { - locationCalculationMessages.Add(new LogMessage(LogMessageType.Error, null, - string.Format(Resources.DesignCalculatorValidationFailed, - damKernelInput.Location.Name, - damKernelInput.SubSoilScenario.ToString()))); - locationCalculationMessages.AddRange(validationMessages); - } - else - { - // Perform calculation - kernelWrapper.Execute(kernelDataInput, kernelDataOutput, out locationCalculationMessages); - } - // Process output - calculationMessages.AddRange(locationCalculationMessages); - StringBuilder sb = new StringBuilder(); - foreach (var message in locationCalculationMessages) - { - sb.Append(message.Message + Environment.NewLine); - } - string resultMessage = sb.ToString(); - - kernelWrapper.PostProcess(damKernelInput, kernelDataOutput, designScenario, resultMessage, out designResults); - } - catch (Exception exception) - { - string resultMessage = exception.Message; - kernelWrapper.PostProcess(damKernelInput, kernelDataOutput, designScenario, resultMessage, out designResults); - } - finally - { - foreach (var designResult in designResults) - { - designCalculations.Add(designResult); - } - } - } - - /// - /// Ensures that the points on the surface line are never more than cDiff (0.5) apart. - /// - /// - /// - private static IEnumerable GetCheckedSurfaceLine(IEnumerable originalLine) - { - const double cDiff = 0.5; - var newLine = new List(); - double X = originalLine.First().X; - foreach (var point in originalLine) - { - while (point.X > X + cDiff) - { - var newPoint = new GeometryPoint(point) - { - X = X + cDiff - }; - if (newPoint.X > newLine.Last().X) - { - newPoint.Z = newLine.Last().Z + ((newPoint.X - newLine.Last().X) / (point.X - newLine.Last().X)) * - (point.Z - newLine.Last().Z); - newLine.Add(newPoint); - } - X = newPoint.X; - } - newLine.Add(point); - } - return newLine; - } - - /// - /// Calculates the maximum level for the shoulder. - /// - /// The surface line. - /// The fraction of dike height to determine maximimum shoulder height. - /// - private static double CalculateMaximumShoulderLevel(SurfaceLine2 surfaceLine, double maxFractionOfDikeHeightForShoulderHeight) - { - var top = surfaceLine.CharacteristicPoints.GetGeometryPoint(CharacteristicPointType.DikeTopAtPolder).Z; - var bottom = surfaceLine.CharacteristicPoints.GetGeometryPoint(CharacteristicPointType.DikeToeAtPolder).Z; - if (top - bottom <= 0) - { - throw new DesignCalculatorException(Resources.SurfaceLineShoulderAdapterMaxShoulderHeightError); - } - double maxHeight = Math.Abs((top - bottom) * maxFractionOfDikeHeightForShoulderHeight); - return bottom + maxHeight; - } - /// - /// Performs the design calculation shoulder iterative per point. - /// This is a design strategy used for Piping - /// - /// The kernel wrapper. - /// The kernel data input. - /// The kernel data output. - /// The dam kernel input. - /// The calculation messages. - /// The design calculations. - /// - private static void PerformDesignCalculationShoulderIterativePerPoint(IKernelWrapper kernelWrapper, IKernelDataInput kernelDataInput, IKernelDataOutput kernelDataOutput, - DamKernelInput damKernelInput, DesignScenario designScenario, - List calculationMessages, List designCalculations) - { - var designResults = new List(); - var location = damKernelInput.Location; - var surfaceLine = location.SurfaceLine; - var orgSurfaceLine = surfaceLine; - try - { - List locationCalculationMessages = new List(); - double orgShoulderLength = surfaceLine.DetermineShoulderWidth(); - double orgShoulderHeight = surfaceLine.DetermineShoulderHeight(); - - GeometryPoint startSurfacePoint = surfaceLine.GetDikeToeInward(); - - IEnumerable relevantSurfacePointsList = from GeometryPoint point in surfaceLine.Geometry.Points - where point.X >= startSurfacePoint.X - orderby point.X ascending - select point; - relevantSurfacePointsList = GetCheckedSurfaceLine(relevantSurfacePointsList); - double oldDesiredShoulderLength = 0.0; - double desiredShoulderLength = 0.0; - double desiredShoulderHeight = 0.0; - double oldDesiredShoulderHeight = 0.0; - int pointCount = 0; - foreach (var point in relevantSurfacePointsList) - { - pointCount++; - - // Calculate the piping design at the given point. This returns the required adaption (berm length and height) if any. - ShoulderDesign shoulderDesign = kernelWrapper.CalculateDesignAtPoint(damKernelInput, kernelDataInput, kernelDataOutput, point, out locationCalculationMessages); - if (shoulderDesign != null) - { - // Piping is an issue so adapt the surfaceline for it - desiredShoulderLength = shoulderDesign.ShoulderLengthFromToe; - desiredShoulderLength = Math.Max(desiredShoulderLength, oldDesiredShoulderLength); - oldDesiredShoulderLength = desiredShoulderLength; - // shoulder height is height above surfacelevel!! - desiredShoulderHeight = shoulderDesign.ShoulderHeightFromToe; - desiredShoulderHeight = Math.Max(desiredShoulderHeight, oldDesiredShoulderHeight); - oldDesiredShoulderHeight = desiredShoulderHeight; - } - - } - if (desiredShoulderLength > 0) - { - desiredShoulderLength = Math.Max(desiredShoulderLength, CMinimumShoulderWidth); - } - if (desiredShoulderLength > 0) - { - desiredShoulderHeight = Math.Max(desiredShoulderHeight, CMinimumShoulderElevation); - } - bool isNewShoulderSameAsOriginal = ((Math.Abs(desiredShoulderLength - orgShoulderLength) < CToleranceShoulderChanges) && - (Math.Abs(desiredShoulderHeight - orgShoulderHeight) < CToleranceShoulderChanges)); - SurfaceLine2 newSurfaceLine = null; - if (isNewShoulderSameAsOriginal) - { - newSurfaceLine = surfaceLine; - } - else - { - // Adapt the surfaceline for the finally required shoulder dimensions. - double maxShoulderLevel = CalculateMaximumShoulderLevel(surfaceLine, 1.0); // no limit to height of shoulder - var surfaceLineShoulderAdapter = new SurfaceLineShoulderAdapter(surfaceLine, location); - surfaceLineShoulderAdapter.MaxShoulderLevel = maxShoulderLevel; - newSurfaceLine = surfaceLineShoulderAdapter.ConstructNewSurfaceLine(desiredShoulderLength, desiredShoulderHeight, true); - - } - damKernelInput.Location.SurfaceLine = newSurfaceLine; - kernelWrapper.Prepare(damKernelInput, 0, out kernelDataInput, out kernelDataOutput); - kernelWrapper.Execute(kernelDataInput, kernelDataOutput, out locationCalculationMessages); - // Process output - calculationMessages.AddRange(locationCalculationMessages); - StringBuilder sb = new StringBuilder(); - foreach (var message in locationCalculationMessages) - { - sb.Append(message.Message + Environment.NewLine); - } - string resultMessage = sb.ToString(); - kernelWrapper.PostProcess(damKernelInput, kernelDataOutput, designScenario, resultMessage, out designResults); - } - catch (Exception exception) - { - string resultMessage = exception.Message; - kernelWrapper.PostProcess(damKernelInput, kernelDataOutput, designScenario, resultMessage, out designResults); - } - finally - { - damKernelInput.Location.SurfaceLine = orgSurfaceLine; - foreach (var designResult in designResults) - { - designCalculations.Add(designResult); - } - } - - string evaluationMessage; - bool designSuccessful = kernelWrapper.EvaluateDesign(damKernelInput, kernelDataInput, kernelDataOutput, out evaluationMessage); - if (!designSuccessful) - { - throw new DesignCalculatorException(String.Format(Resources.DesignUnsuccessful, - damKernelInput.Location.Name, damKernelInput.SubSoilScenario) + ", " + evaluationMessage); - } - } } }