private void CalcPackage(FilePackageContent filePackage) { // The package must ALWAYS exist at this point! EM_TemplateCalculator calculator = calculators[filePackage.Key]; ResultsPackage resultsPackage = resultsPackages.Find(x => x.packageKey == filePackage.Key); try { bool success = calculator.CalculateStatistics(resultsPackage.microData); lock (resultsPackages) { resultsPackage.displayResults = calculator.GetDisplayResults(); resultsPackage.error = calculator.GetErrorMessage(); // this may also just be warnings if (!success) { resultsPackage.displayResults.calculated = true; // if did not succeed, declare this done } // cleanup calculators.Remove(filePackage.Key); resultsPackage.microData = null; filePackage = null; } } catch (Exception exception) { lock (resultsPackages) { resultsPackage.error = exception.Message; } } }
private void PrepareAndStartCalculatingResults() { foreach (FilePackageContent filePackage in filePackages) // tested multi-threading this, but there was no noticeable gain! { List <string> filenames = new List <string>(); // Prepare the filenames and microdata List <StringBuilder> microData = new List <StringBuilder>(); if (template.info.templateType != HardDefinitions.TemplateType.Multi) { if (filePackage.MicroDataBase != null) { filenames.Add(string.Empty); microData.Add(filePackage.MicroDataBase); } else { filenames.Add(filePackage.PathBase); microData.Add(null); } } for (int f = 0; f < Math.Max(filePackage.PathsAlt.Count, filePackage.MicroDataAlt.Count); ++f) { filenames.Add(f < filePackage.PathsAlt.Count ? filePackage.PathsAlt[f] : string.Empty); microData.Add(f < filePackage.MicroDataAlt.Count ? filePackage.MicroDataAlt[f] : null); } if (filePackage.MicroDataBase == null && filePackage.MicroDataAlt.Count == 0) { microData = null; } // Prepare the resultsPackage ResultsPackage resultsPackage = new ResultsPackage(); EM_TemplateCalculator calculator = new EM_TemplateCalculator(template, filePackage.Key); bool prepared = calculator.Prepare(filenames, out ErrorCollector errorCollector); calculators.Add(filePackage.Key, calculator); resultsPackage.displayResults = calculator.GetDisplayResults(); if (!prepared) { resultsPackage.displayResults.calculated = true; // if preperation went wrong, there will not be any results comming later! } resultsPackage.packageKey = filePackage.Key; resultsPackage.error = errorCollector.GetErrorMessage(); resultsPackage.microData = microData; resultsPackages.Add(resultsPackage); } new System.Threading.Thread(() => { Parallel.ForEach <FilePackageContent>(filePackages, filePackage => { CalcPackage(filePackage); }); }).Start(); }
/// <summary> /// The top level command. /// </summary> /// <param name="commandData">An object that is passed to the external application /// which contains data related to the command, /// such as the application object and active view.</param> /// <param name="message">A message that can be set by the external application /// which will be displayed if a failure or cancellation is returned by /// the external command.</param> /// <param name="elements">A set of elements to which the external application /// can add elements that are to be highlighted in case of failure or cancellation.</param> /// <returns>Return the status of the external command. /// A result of Succeeded means that the API external method functioned as expected. /// Cancelled can be used to signify that the user cancelled the external operation /// at some point. Failure should be returned if the application is unable to proceed with /// the operation.</returns> public Autodesk.Revit.UI.Result Execute(ExternalCommandData commandData, ref string message, Autodesk.Revit.DB.ElementSet elements) { // Set reference to the document and then check if this command is run on the inclueded "ResultsInRevit.rvt" file document = commandData.Application.ActiveUIDocument.Document; String outputDocumentPathName = commandData.Application.ActiveUIDocument.Document.PathName + ".ECTesting.txt"; Autodesk.Revit.UI.Result res = Result.Failed; if (document.Title != "ResultsInRevit.rvt") { // Report error if this is a wrong file Autodesk.Revit.UI.TaskDialog.Show("Wrong Revit file", "Cannot use :\n" + document.PathName + "\n\nPlease use attached " + "\"ResultsInRevit.rvt\" file."); } else { // Go ahead and read some results from elements otherwise try { // Set ElementIds for Revit elements and loads used in this example. ElementIds are hardcoded ElementId loadCaseId1 = new ElementId(37232); ElementId loadCaseId2 = new ElementId(37234); ElementId combinationId = new ElementId(261966); ElementId [] loadCaseIds = new ElementId[] { loadCaseId1, loadCaseId2, combinationId }; ResultsPackage resultsPackage = null; try { // Get results package resultsPackage = GetResultsPackage(document); } catch { Autodesk.Revit.UI.TaskDialog.Show("Cannot get result package.", "\nTry to store results first."); } // Read Results from the created result package and store them in the textfile using (System.IO.StreamWriter writer = new System.IO.StreamWriter(outputDocumentPathName, false)) { writer.WriteLine(ReadLinearResults(resultsPackage, linearElementId, loadCaseIds)); writer.WriteLine(ReadArbitraryLinearResults(resultsPackage, linearElementId)); writer.WriteLine(ReadSurfaceResults(resultsPackage, surfaceElementId, loadCaseIds)); writer.WriteLine(ReadArbitrarySurfaceResults(resultsPackage, surfaceElementId)); } res = Result.Succeeded; } catch (Exception ex) { Autodesk.Revit.UI.TaskDialog.Show("Failed to read results from Revit", ex.Message.ToString()); } } return(res); }
/// <summary> /// Reads surface analitical results for a specific element, for a set of load cases /// </summary> /// <param name="resultsPackage">Package from which to results are to be read</param> /// <param name="elementId">Revit Element id</param> /// <param name="loadCaseIds">Collection of load case Ids</param> /// <returns>Results formatted into a string</returns> private String ReadSurfaceResults(ResultsPackage resultsPackage, ElementId elementId, ElementId [] loadCaseIds) { // Set a list of result type elements SurfaceResultType[] surfaceResultTypes = { SurfaceResultType.Fxx, SurfaceResultType.Fyy, SurfaceResultType.Fxy, SurfaceResultType.Mxx, SurfaceResultType.Myy, SurfaceResultType.Mxy }; List <ElementId> elementIds = new List <ElementId>() { elementId }; // Read results from the package IList <SurfaceGraph> graphs = resultsPackage.GetSurfaceGraphs(elementIds, loadCaseIds, surfaceResultTypes, new SurfaceGraphParameters(UnitsSystem.Metric)); // Format results return(FormatSurfaceResultsOutput("Surface results", graphs)); }
/// <summary> /// Reads surface arbitrary results for a specific element in a similar way to analitical results /// </summary> /// <param name="resultsPackage">Package from which to results are to be read</param> /// <param name="elementId">Revit Element id</param> /// <returns>Results formatted into a string</returns> private String ReadArbitrarySurfaceResults(ResultsPackage resultsPackage, ElementId elementId) { String[] surfaceResultTypes = { "AxxBottom", "AyyBottom", "AxxTop", "AyyTop" }; List <ElementId> elementIds = new List <ElementId>() { elementId }; List <ElementId> loadCaseIds = new List <ElementId>() { null }; IList <SurfaceGraph> graphs = resultsPackage.GetSurfaceGraphs(elementIds, loadCaseIds, surfaceResultTypes, new SurfaceGraphParameters(UnitsSystem.Metric)); return(FormatSurfaceResultsOutput("Linear arbitrary results", graphs)); }
/// <summary> /// Reads linear analitical results for a specific element, for a set of load cases /// </summary> /// <param name="resultsPackage">Package from which to results are to be read</param> /// <param name="elementId">Revit Element id</param> /// <param name="loadCaseIds">Collection of load case Ids</param> /// <returns>Results formatted into a string</returns> private String ReadLinearResults(ResultsPackage resultsPackage, ElementId elementId, ElementId [] loadCaseIds) { // Set a list of result type elements IList <LinearResultType> linearResultTypes = new List <LinearResultType>() { LinearResultType.Fx, LinearResultType.Fy, LinearResultType.Fz, LinearResultType.Mx, LinearResultType.My, LinearResultType.Mz }; List <ElementId> elementIds = new List <ElementId>() { elementId }; // Read results from the package IList <LineGraph> graphs = resultsPackage.GetLineGraphs(elementIds, loadCaseIds, linearResultTypes, new LineGraphParameters(UnitsSystem.Metric)); // Format results return(FormatLinearResultsOutput("Linear results", graphs)); }
/// <summary> /// Reads linear arbitrary results for a specific element in a similar way to analitical results /// No load cases are used as arbitrary results are load independent /// </summary> /// <param name="resultsPackage">Package from which to results are to be read</param> /// <param name="elementId">Revit Element id</param> /// <returns>Results formatted into a string</returns> private String ReadArbitraryLinearResults(ResultsPackage resultsPackage, ElementId elementId) { IList <String> rnfTypes = new List <String>() { "RnfBarsAngleBottom", "RnfBarsAngleTop", "RnfBarsAngleLeft", "RnfBarsAngleRight" }; List <ElementId> elementIds = new List <ElementId>() { elementId }; List <ElementId> loadCaseIds = new List <ElementId>() { null }; IList <LineGraph> graphs = resultsPackage.GetLineGraphs(elementIds, loadCaseIds, rnfTypes, new LineGraphParameters(UnitsSystem.Metric)); return(FormatLinearResultsOutput("Linear arbitrary results", graphs)); }
private void BuildResponse_SaveAsExcel(HttpContext context, EM_BackEndResponder beResponder) { try { EM_StatisticsBackEndResponder me = beResponder as EM_StatisticsBackEndResponder; if (resultsPackages == null || resultsPackages.Count == 0) { BackEnd.WriteResponseError(context, "No files for analysing defined!"); return; } List <ResultsPackage> allResults = new List <ResultsPackage>(); if (context.Request.Query.ContainsKey("packageKey")) { string packageKey = context.Request.Query["packageKey"].First().ToString(); ResultsPackage resultsPackage = (from rp in resultsPackages.ToList() where rp.packageKey == packageKey select rp).FirstOrDefault(); // .ToList() here is extremely important for thread-safety if (resultsPackage == null) { BackEnd.WriteResponseError(context, "Package not found!"); return; } allResults.Add(resultsPackage); } else { allResults.AddRange(resultsPackages.ToList()); } if (allResults.Count < 1) { BackEnd.WriteResponseError(context, "No Results found!"); return; } bool allReady = true; foreach (ResultsPackage resultsPackage in allResults) { if (resultsPackage.displayResults == null || !resultsPackage.displayResults.calculated) { allReady = false; } } if (allReady) { MemoryStream excelStream; string errMsg = string.Empty; foreach (ResultsPackage resultsPackage in allResults) { errMsg += (errMsg == string.Empty ? "" : Environment.NewLine) + resultsPackage.error; } context.Response.ContentType = "application/vnd.openxmlformats-officedocument.spreadsheetml.sheet"; if (allResults.Count == 1) { context.Response.Headers.Append("Content-Disposition", $"attachment; filename={allResults[0].displayResults.info.button}.xlsx"); ExportHandling.ExportSinglePackage(allResults[0].displayResults, out errMsg, out excelStream); } else { context.Response.Headers.Append("Content-Disposition", $"attachment; filename=EM_Statistics_export.xlsx"); List <DisplayResults> allDisplayResults = new List <DisplayResults>(); foreach (ResultsPackage resultsPackage in allResults) { allDisplayResults.Add(resultsPackage.displayResults); } ExportHandling.ExportMultiPackages(allDisplayResults, out errMsg, out excelStream); } context.Response.Body.WriteAsync(excelStream.ToArray(), 0, (int)excelStream.Length); return; } else { System.Threading.Thread.Sleep(500); BuildResponse_SaveAsExcel(context, beResponder); return; } } catch (Exception exception) { BackEnd.WriteResponseError(context, exception.Message); } }
private void BuildResponse_LoadStatistics(HttpContext context, EM_BackEndResponder beResponder) { try { EM_StatisticsBackEndResponder me = beResponder as EM_StatisticsBackEndResponder; context.Response.ContentType = "text/json"; if (resultsPackages == null || resultsPackages.Count == 0) { BackEnd.WriteResponseError(context, "No files for analysing defined!"); return; } bool hasForm = context.Request.HasFormContentType && context.Request.Form.Count > 0; string packageKey = hasForm && context.Request.Form.ContainsKey("packageKey") ? context.Request.Form["packageKey"].ToString() : resultsPackages[0].packageKey; ResultsPackage resultsPackage = (from rp in resultsPackages.ToList() where rp.packageKey == packageKey select rp).FirstOrDefault(); // .ToList() here is extremely important for thread-safety // package does not yet exist! if (resultsPackage == null) { BackEnd.WriteResponseError(context, "No Results?!? This should never happen!"); return; // FilePackageContent filePackage = (from fp in filePackages where fp.Key == packageKey select fp).FirstOrDefault(); // if (filePackage == null) { BackEnd.WriteResponseError(context, $"Unknown package-key: '{packageKey}'!"); return; } // resultsPackage = CalcPackage(filePackage); resultsPackages.Add(resultsPackage); } // statistics not yet calculated if (!resultsPackage.displayResults.calculated) { DisplayResults results = new DisplayResults() { info = resultsPackage.displayResults.info }; LoadInfo loadInfo = new LoadInfo() { packageKey = packageKey, completed = false, results = results }; context.Response.WriteAsync(JsonConvert.SerializeObject(loadInfo)); return; } if (resultsPackage.displayResults != null) { LoadInfo loadInfo = new LoadInfo() { packageKey = packageKey, completed = true }; string json = ""; lock (resultsPackages) { loadInfo.results = resultsPackage.displayResults; loadInfo.warnings = resultsPackage.error; json = JsonConvert.SerializeObject(loadInfo); } context.Response.WriteAsync(json); } else { BackEnd.WriteResponseError(context, resultsPackage.error); } } catch (Exception exception) { BackEnd.WriteResponseError(context, exception.Message); } }