public static void ConvertElement2D(GsaElement2d element2d, ref Dictionary <int, Element> existingElements, ref int elementidcounter, ref Dictionary <int, Node> existingNodes, ref int nodeidcounter, ref Dictionary <int, Prop2D> existingProp2Ds, ref Dictionary <Guid, int> prop2d_guid) { List <Point3d> meshVerticies = element2d.Topology; //Loop through all faces in mesh to update topology list to fit model nodes for (int i = 0; i < element2d.Elements.Count; i++) { Element apiMeshElement = element2d.Elements[i]; List <int> meshVertexIndex = element2d.TopoInt[i]; List <int> topo = new List <int>(); // temp topologylist //Loop through topology for (int j = 0; j < meshVertexIndex.Count; j++) { int id = Nodes.GetExistingNodeID(existingNodes, meshVerticies[meshVertexIndex[j]]); if (id > 0) { topo.Add(id); } else { existingNodes.Add(nodeidcounter, Nodes.NodeFromPoint(meshVerticies[meshVertexIndex[j]])); topo.Add(nodeidcounter); nodeidcounter++; } } //update topology in Element apiMeshElement.Topology = new ReadOnlyCollection <int>(topo.ToList()); // section if (apiMeshElement.Property == 0) { apiMeshElement.Property = Prop2ds.ConvertProp2d(element2d.Properties[i], ref existingProp2Ds, ref prop2d_guid); } // set api element in dictionary if (element2d.ID[i] > 0) // if the ID is larger than 0 than means the ID has been set and we sent it to the known list { existingElements[element2d.ID[i]] = apiMeshElement; } else { existingElements.Add(elementidcounter, apiMeshElement); elementidcounter++; } } }
public static void ConvertMember2D(GsaMember2d member2d, ref Dictionary <int, Member> existingMembers, ref int memberidcounter, ref Dictionary <int, Node> existingNodes, ref int nodeidcounter, ref Dictionary <int, Prop2D> existingProp2Ds, ref Dictionary <Guid, int> prop2d_guid) { Member apiMember = member2d.Member; // update topology list to fit model nodes string topo = ""; // Loop through the topology list for (int i = 0; i < member2d.Topology.Count; i++) { Point3d pt = member2d.Topology[i]; string topologyType = member2d.TopologyType[i]; if (i > 0) { if (topologyType == "" | topologyType == " ") { topo += " "; } else { topo += topologyType.ToLower() + " "; // add topology type (nothing or "a") in front of node id } } int id = Nodes.GetExistingNodeID(existingNodes, pt); if (id > 0) { topo += id; } else { existingNodes.Add(nodeidcounter, Nodes.NodeFromPoint(pt)); topo += nodeidcounter; nodeidcounter++; } if (i != member2d.Topology.Count - 1) { topo += " "; } } // Loop through the voidtopology list if (member2d.VoidTopology != null) { for (int i = 0; i < member2d.VoidTopology.Count; i++) { for (int j = 0; j < member2d.VoidTopology[i].Count; j++) { Point3d pt = member2d.VoidTopology[i][j]; string voidtopologytype = member2d.VoidTopologyType[i][j]; if (j == 0) { topo += " V("; } if (voidtopologytype == "" | voidtopologytype == " ") { topo += " "; } else { topo += voidtopologytype.ToLower() + " "; // add topology type (nothing or "a") in front of node id } int id = Nodes.GetExistingNodeID(existingNodes, pt); if (id > 0) { topo += id; } else { existingNodes.Add(nodeidcounter, Nodes.NodeFromPoint(pt)); topo += nodeidcounter; nodeidcounter++; } if (j != member2d.VoidTopology[i].Count - 1) { topo += " "; } else { topo += ")"; } } } } // Loop through the inclusion lines topology list if (member2d.IncLinesTopology != null) { for (int i = 0; i < member2d.IncLinesTopology.Count; i++) { for (int j = 0; j < member2d.IncLinesTopology[i].Count; j++) { Point3d pt = member2d.IncLinesTopology[i][j]; string inclineTopologytype = member2d.IncLinesTopologyType[i][j]; if (j == 0) { topo += " L("; } if (inclineTopologytype == "" | inclineTopologytype == " ") { topo += " "; } else { topo += inclineTopologytype.ToLower() + " "; // add topology type (nothing or "a") in front of node id } int id = Nodes.GetExistingNodeID(existingNodes, pt); if (id > 0) { topo += id; } else { existingNodes.Add(nodeidcounter, Nodes.NodeFromPoint(pt)); topo += nodeidcounter; nodeidcounter++; } if (j != member2d.IncLinesTopology[i].Count - 1) { topo += " "; } else { topo += ")"; } } } } // Loop through the inclucion point topology list if (member2d.InclusionPoints != null) { for (int i = 0; i < member2d.InclusionPoints.Count; i++) { Point3d pt = member2d.InclusionPoints[i]; if (i == 0) { topo += " P("; } int id = Nodes.GetExistingNodeID(existingNodes, pt); if (id > 0) { topo += id; } else { existingNodes.Add(nodeidcounter, Nodes.NodeFromPoint(pt)); topo += nodeidcounter; nodeidcounter++; } if (i != member2d.InclusionPoints.Count - 1) { topo += " "; } else { topo += ")"; } } } // update topology for api member apiMember.Topology = string.Copy(topo); // section if (apiMember.Property == 0) { apiMember.Property = Prop2ds.ConvertProp2d(member2d.Property, ref existingProp2Ds, ref prop2d_guid); } // set apimember in dictionary if (member2d.ID > 0) // if the ID is larger than 0 than means the ID has been set and we sent it to the known list { existingMembers[member2d.ID] = apiMember; } else { existingMembers.Add(memberidcounter, apiMember); memberidcounter++; } }
/// <summary> /// Method to assemble full GSA model /// </summary> /// <param name="model">Existing models to be merged</param> /// <param name="nodes">List of nodes with properties like support conditions</param> /// <param name="elem1ds">List of 1D elements. Nodes at end-points will automatically be added to the model, using existing nodes in model within tolerance. Section will automatically be added to model</param> /// <param name="elem2ds">List of 2D elements. Nodes at mesh-verticies will automatically be added to the model, using existing nodes in model within tolerance. Prop2d will automatically be added to model</param> /// <param name="elem3ds">List of 3D elements. Nodes at mesh-verticies will automatically be added to the model, using existing nodes in model within tolerance</param> /// <param name="mem1ds">List of 1D members. Topology nodes will automatically be added to the model, using existing nodes in model within tolerance. Section will automatically be added to model</param> /// <param name="mem2ds">List of 2D members. Topology nodes will automatically be added to the model, using existing nodes in model within tolerance. Prop2d will automatically be added to model</param> /// <param name="mem3ds">List of 3D members. Topology nodes will automatically be added to the model, using existing nodes in model within tolerance</param> /// <param name="sections">List of Sections</param> /// <param name="prop2Ds">List of 2D Properties</param> /// <param name="loads">List of Loads. For Grid loads the Axis, GridPlane and GridSurface will automatically be added to the model using existing objects where possible within tolerance.</param> /// <param name="gridPlaneSurfaces">List of GridPlaneSurfaces</param> /// <param name="workerInstance">Optional input for AsyncComponents</param> /// <param name="ReportProgress">Optional input for AsyncComponents</param> /// <returns></returns> public static Model AssembleModel(GsaModel model, List <GsaNode> nodes, List <GsaElement1d> elem1ds, List <GsaElement2d> elem2ds, List <GsaElement3d> elem3ds, List <GsaMember1d> mem1ds, List <GsaMember2d> mem2ds, List <GsaMember3d> mem3ds, List <GsaSection> sections, List <GsaProp2d> prop2Ds, List <GsaLoad> loads, List <GsaGridPlaneSurface> gridPlaneSurfaces, GrasshopperAsyncComponent.WorkerInstance workerInstance = null, Action <string, double> ReportProgress = null ) { // Set model to work on Model gsa = new Model(); if (model != null) { gsa = model.Model; } #region Nodes // ### Nodes ### // We take out the existing nodes in the model and work on that dictionary // Get existing nodes IReadOnlyDictionary <int, Node> gsaNodes = gsa.Nodes(); Dictionary <int, Node> apinodes = gsaNodes.ToDictionary(kvp => kvp.Key, kvp => kvp.Value); // Get existing axes IReadOnlyDictionary <int, Axis> gsaAxes = gsa.Axes(); Dictionary <int, Axis> apiaxes = gsaAxes.ToDictionary(kvp => kvp.Key, kvp => kvp.Value); // Set / add nodes to dictionary Nodes.ConvertNode(nodes, ref apinodes, ref apiaxes, workerInstance, ReportProgress); #endregion #region Properties // ### Sections ### // list to keep track of duplicated sextions Dictionary <Guid, int> sections_guid = new Dictionary <Guid, int>(); // Get existing sections IReadOnlyDictionary <int, Section> gsaSections = gsa.Sections(); Dictionary <int, Section> apisections = gsaSections.ToDictionary(kvp => kvp.Key, kvp => kvp.Value); // add / set sections Sections.ConvertSection(sections, ref apisections, ref sections_guid, workerInstance, ReportProgress); // ### Prop2ds ### // list to keep track of duplicated sextions Dictionary <Guid, int> prop2d_guid = new Dictionary <Guid, int>(); // Get existing prop2ds IReadOnlyDictionary <int, Prop2D> gsaProp2ds = gsa.Prop2Ds(); Dictionary <int, Prop2D> apiprop2ds = gsaProp2ds.ToDictionary(kvp => kvp.Key, kvp => kvp.Value); // add / set prop2ds Prop2ds.ConvertProp2d(prop2Ds, ref apiprop2ds, ref prop2d_guid, workerInstance, ReportProgress); #endregion #region Elements // ### Elements ### // We take out the existing elements in the model and work on that dictionary // Get existing elements IReadOnlyDictionary <int, Element> gsaElems = gsa.Elements(); Dictionary <int, Element> elems = gsaElems.ToDictionary(kvp => kvp.Key, kvp => kvp.Value); // create a counter for creating new elements int newElementID = (elems.Count > 0) ? elems.Keys.Max() + 1 : 1; //checking the existing model // as both elem1d and elem2d will be set in the same table, we check the highest ID that may have // been set in the incoming elements and start appending from there to avoid accidentially overwriting if (elem1ds != null) { if (elem1ds.Count > 0) { int existingElem1dMaxID = elem1ds.Max(x => x.ID); // max ID in new Elem1ds if (existingElem1dMaxID > newElementID) { newElementID = existingElem1dMaxID + 1; } } } if (elem2ds != null) { if (elem2ds.Count > 0) { int existingElem2dMaxID = elem2ds.Max(x => x.ID.Max()); // max ID in new Elem2ds if (existingElem2dMaxID > newElementID) { newElementID = existingElem2dMaxID + 1; } } } // Set / add 1D elements to dictionary Elements.ConvertElement1D(elem1ds, ref elems, ref newElementID, ref apinodes, ref apisections, ref sections_guid, workerInstance, ReportProgress); // Set / add 2D elements to dictionary Elements.ConvertElement2D(elem2ds, ref elems, ref newElementID, ref apinodes, ref apiprop2ds, ref prop2d_guid, workerInstance, ReportProgress); // Set / add 3D elements to dictionary Elements.ConvertElement3D(elem3ds, ref elems, ref newElementID, ref apinodes, workerInstance, ReportProgress); #endregion #region Members // ### Members ### // We take out the existing members in the model and work on that dictionary // Get existing members IReadOnlyDictionary <int, Member> gsaMems = gsa.Members(); Dictionary <int, Member> mems = gsaMems.ToDictionary(kvp => kvp.Key, kvp => kvp.Value); // create a counter for creating new members int newMemberID = (mems.Count > 0) ? mems.Keys.Max() + 1 : 1; //checking the existing model // as both mem1d, mem2d and mem3dwill be set in the same table, we check the highest ID that may have // been set in the incoming elements and start appending from there to avoid accidentially overwriting if (mem1ds != null) { if (mem1ds.Count > 0) { int existingMem1dMaxID = mem1ds.Max(x => x.ID); // max ID in new Elem1ds if (existingMem1dMaxID > newMemberID) { newMemberID = existingMem1dMaxID + 1; } } } if (mem2ds != null) { if (mem2ds.Count > 0) { int existingMem2dMaxID = mem2ds.Max(x => x.ID); // max ID in new Elem2ds if (existingMem2dMaxID > newMemberID) { newMemberID = existingMem2dMaxID + 1; } } } if (mem3ds != null) { if (mem3ds.Count > 0) { int existingMem3dMaxID = mem3ds.Max(x => x.ID); // max ID in new Elem2ds if (existingMem3dMaxID > newMemberID) { newMemberID = existingMem3dMaxID + 1; } } } // Set / add 1D members to dictionary Members.ConvertMember1D(mem1ds, ref mems, ref newMemberID, ref apinodes, ref apisections, ref sections_guid, workerInstance, ReportProgress); // Set / add 2D members to dictionary Members.ConvertMember2D(mem2ds, ref mems, ref newMemberID, ref apinodes, ref apiprop2ds, ref prop2d_guid, workerInstance, ReportProgress); // Set / add 3D members to dictionary Members.ConvertMember3D(mem3ds, ref mems, ref newMemberID, ref apinodes, workerInstance, ReportProgress); #endregion #region Loads // ### Loads ### // We let the existing loads (if any) survive and just add new loads // Get existing loads List <GravityLoad> gravityLoads = new List <GravityLoad>(); List <NodeLoad> nodeLoads_node = new List <NodeLoad>(); List <NodeLoad> nodeLoads_displ = new List <NodeLoad>(); List <NodeLoad> nodeLoads_settle = new List <NodeLoad>(); List <BeamLoad> beamLoads = new List <BeamLoad>(); List <FaceLoad> faceLoads = new List <FaceLoad>(); List <GridPointLoad> gridPointLoads = new List <GridPointLoad>(); List <GridLineLoad> gridLineLoads = new List <GridLineLoad>(); List <GridAreaLoad> gridAreaLoads = new List <GridAreaLoad>(); IReadOnlyDictionary <int, GridPlane> gsaGPln = gsa.GridPlanes(); Dictionary <int, GridPlane> apiGridPlanes = gsaGPln.ToDictionary(kvp => kvp.Key, kvp => kvp.Value); IReadOnlyDictionary <int, GridSurface> gsaGSrf = gsa.GridSurfaces(); Dictionary <int, GridSurface> apiGridSurfaces = gsaGSrf.ToDictionary(kvp => kvp.Key, kvp => kvp.Value); // lists to keep track of duplicated grid planes and grid surfaces Dictionary <Guid, int> gp_guid = new Dictionary <Guid, int>(); Dictionary <Guid, int> gs_guid = new Dictionary <Guid, int>(); // Set / add Grid plane surfaces - do this first to set any GridPlane and GridSurfaces with IDs. Loads.ConvertGridPlaneSurface(gridPlaneSurfaces, ref apiaxes, ref apiGridPlanes, ref apiGridSurfaces, ref gp_guid, ref gs_guid, workerInstance, ReportProgress); // Set / add loads to lists Loads.ConvertLoad(loads, ref gravityLoads, ref nodeLoads_node, ref nodeLoads_displ, ref nodeLoads_settle, ref beamLoads, ref faceLoads, ref gridPointLoads, ref gridLineLoads, ref gridAreaLoads, ref apiaxes, ref apiGridPlanes, ref apiGridSurfaces, ref gp_guid, ref gs_guid, workerInstance, ReportProgress); #endregion #region set stuff in model if (workerInstance != null) { if (workerInstance.CancellationToken.IsCancellationRequested) { return(null); } } //nodes ReadOnlyDictionary <int, Node> setnodes = new ReadOnlyDictionary <int, Node>(apinodes); gsa.SetNodes(setnodes); //elements ReadOnlyDictionary <int, Element> setelem = new ReadOnlyDictionary <int, Element>(elems); gsa.SetElements(setelem); //members ReadOnlyDictionary <int, Member> setmem = new ReadOnlyDictionary <int, Member>(mems); gsa.SetMembers(setmem); //gravity load ReadOnlyCollection <GravityLoad> setgrav = new ReadOnlyCollection <GravityLoad>(gravityLoads); gsa.AddGravityLoads(setgrav); //node loads ReadOnlyCollection <NodeLoad> setnode_disp = new ReadOnlyCollection <NodeLoad>(nodeLoads_displ); gsa.AddNodeLoads(NodeLoadType.APPL_DISP, setnode_disp); ReadOnlyCollection <NodeLoad> setnode_node = new ReadOnlyCollection <NodeLoad>(nodeLoads_node); gsa.AddNodeLoads(NodeLoadType.NODE_LOAD, setnode_node); ReadOnlyCollection <NodeLoad> setnode_setl = new ReadOnlyCollection <NodeLoad>(nodeLoads_settle); gsa.AddNodeLoads(NodeLoadType.SETTLEMENT, setnode_setl); //beam loads ReadOnlyCollection <BeamLoad> setbeam = new ReadOnlyCollection <BeamLoad>(beamLoads); gsa.AddBeamLoads(setbeam); //face loads ReadOnlyCollection <FaceLoad> setface = new ReadOnlyCollection <FaceLoad>(faceLoads); gsa.AddFaceLoads(setface); //grid point loads ReadOnlyCollection <GridPointLoad> setpoint = new ReadOnlyCollection <GridPointLoad>(gridPointLoads); gsa.AddGridPointLoads(setpoint); //grid line loads ReadOnlyCollection <GridLineLoad> setline = new ReadOnlyCollection <GridLineLoad>(gridLineLoads); gsa.AddGridLineLoads(setline); //grid area loads ReadOnlyCollection <GridAreaLoad> setarea = new ReadOnlyCollection <GridAreaLoad>(gridAreaLoads); gsa.AddGridAreaLoads(setarea); //axes ReadOnlyDictionary <int, Axis> setax = new ReadOnlyDictionary <int, Axis>(apiaxes); gsa.SetAxes(setax); //gridplanes ReadOnlyDictionary <int, GridPlane> setgp = new ReadOnlyDictionary <int, GridPlane>(apiGridPlanes); gsa.SetGridPlanes(setgp); //gridsurfaces ReadOnlyDictionary <int, GridSurface> setgs = new ReadOnlyDictionary <int, GridSurface>(apiGridSurfaces); gsa.SetGridSurfaces(setgs); //sections ReadOnlyDictionary <int, Section> setsect = new ReadOnlyDictionary <int, Section>(apisections); gsa.SetSections(setsect); //prop2ds ReadOnlyDictionary <int, Prop2D> setpr2d = new ReadOnlyDictionary <int, Prop2D>(apiprop2ds); gsa.SetProp2Ds(setpr2d); if (workerInstance != null) { ReportProgress("Model assembled", -2); } #endregion return(gsa); }