public void UpdateProgressBar(int value, string labeltext) { this.Invoke((MethodInvoker) delegate { progressBar1.Value = value; label1.Text = labeltext; pb.UpdateTitle(labeltext); if (value == 100) { closebttn.Visible = true; } }); }
//Recursive method for exporting each link (and writing it to the URDF) private void ExportFiles(Link link, URDFPackage package, int count, bool exportSTL = true) { progressBar.UpdateProgress(count); progressBar.UpdateTitle("Exporting mesh: " + link.Name); logger.Info("Exporting link: " + link.Name); // Iterate through each child and export its files logger.Info("Link " + link.Name + " has " + link.Children.Count + " children"); foreach (Link child in link.Children) { count += 1; if (!child.isFixedFrame) { ExportFiles(child, package, count, exportSTL); } } // Copy the texture file (if it was specified) to the textures directory if (!link.isFixedFrame && !String.IsNullOrWhiteSpace(link.Visual.Material.Texture.wFilename)) { if (File.Exists(link.Visual.Material.Texture.wFilename)) { link.Visual.Material.Texture.Filename = package.TexturesDirectory + Path.GetFileName(link.Visual.Material.Texture.wFilename); string textureSavePath = package.WindowsTexturesDirectory + Path.GetFileName(link.Visual.Material.Texture.wFilename); File.Copy(link.Visual.Material.Texture.wFilename, textureSavePath, true); } } // Create the mesh filenames. SolidWorks likes to use / but that will get messy in filenames so use _ instead string linkName = link.Name.Replace('/', '_'); string meshFilename = package.MeshesDirectory + linkName + ".STL"; string windowsMeshFileName = package.WindowsMeshesDirectory + linkName + ".STL"; // Export STL if (exportSTL) { SaveSTL(link, windowsMeshFileName); } link.Visual.Geometry.Mesh.Filename = meshFilename; link.Collision.Geometry.Mesh.Filename = meshFilename; }
//Recursive method for exporting each link (and writing it to the URDF) public string exportFiles(link Link, URDFPackage package, int count) { progressBar.UpdateProgress(count); progressBar.UpdateTitle("Exporting mesh: " + Link.name); // Iterate through each child and export its files foreach (link child in Link.Children) { count += 1; if (!child.isFixedFrame) { string filename = exportFiles(child, package, count); child.Visual.Geometry.Mesh.filename = filename; child.Collision.Geometry.Mesh.filename = filename; } } // Copy the texture file (if it was specified) to the textures directory if (!Link.isFixedFrame && Link.Visual.Material.Texture.wFilename != "") { if (System.IO.File.Exists(Link.Visual.Material.Texture.wFilename)) { Link.Visual.Material.Texture.filename = package.TexturesDirectory + Path.GetFileName(Link.Visual.Material.Texture.wFilename); string textureSavePath = package.WindowsTexturesDirectory + Path.GetFileName(Link.Visual.Material.Texture.wFilename); System.IO.File.Copy(Link.Visual.Material.Texture.wFilename, textureSavePath, true); } } // Create the mesh filenames. SolidWorks likes to use / but that will get messy in filenames so use _ instead string linkName = Link.name.Replace('/', '_'); string meshFileName = package.MeshesDirectory + linkName + ".STL"; string windowsMeshFileName = package.WindowsMeshesDirectory + linkName + ".STL"; // Export STL saveSTL(Link, windowsMeshFileName); return(meshFileName); }
/// Convert a SolidWorks component to Wavefront OBJ mesh /// public static void Convert(Component2 swComp, ref string asciitext, bool saveUV, ref UserProgressBar swProgress) { StringBuilder textbuilder = new StringBuilder(); Body2 swBody = default(Body2); object[] vBodies = null; object[] vBodiesSolid = null; object[] vBodiesSheet = null; object vBodyInfo; int[] BodiesInfo = null; int j = 0; ModelDoc2 swModel; swModel = (ModelDoc2)swComp.GetModelDoc(); vBodiesSolid = (object[])swComp.GetBodies3((int)swBodyType_e.swSolidBody, out vBodyInfo); vBodiesSheet = (object[])swComp.GetBodies3((int)swBodyType_e.swSheetBody, out vBodyInfo); BodiesInfo = (int[])vBodyInfo; if (vBodiesSolid != null && vBodiesSheet == null) { vBodies = vBodiesSolid; } if (vBodiesSolid == null && vBodiesSheet != null) { vBodies = vBodiesSheet; } if (vBodiesSolid != null && vBodiesSheet != null) { vBodies = vBodiesSheet.Concat(vBodiesSolid).ToArray(); } // vBodies = (object[])swComp.GetBodies3((int)swBodyType_e.swSolidBody, out vBodyInfo); if (vBodies != null) { int iNumBodies = vBodies.Length; int iNumSolidBodies = 0; int iNumSheetBodies = 0; int iNumTesselatedBodies = 0; if (iNumBodies > 0) { asciitext += "# Wavefront .OBJ file for tesselated shape: " + swComp.Name2 + " path: " + swModel.GetPathName() + "\n\n"; } int group_vstride = 0; int group_nstride = 0; // Loop through bodies for (j = 0; j <= vBodies.Length - 1; j++) { swBody = (Body2)vBodies[j]; int nBodyType = (int)swBody.GetType(); if (nBodyType == (int)swBodyType_e.swSheetBody) { iNumSheetBodies++; } if (nBodyType == (int)swBodyType_e.swSolidBody) { iNumSolidBodies++; } if ((nBodyType == (int)swBodyType_e.swSheetBody || nBodyType == (int)swBodyType_e.swSolidBody) && !swBody.Name.StartsWith("COLL.") && swBody.Visible) { iNumTesselatedBodies++; CultureInfo bz = new CultureInfo("en-BZ"); //asciitext += "g body_" + iNumTesselatedBodies + "\n"; textbuilder.Append("g body_" + iNumTesselatedBodies + "\n"); Face2 swFace = null; Tessellation swTessellation = null; bool bResult = false; // Pass in null so the whole body will be tessellated swTessellation = (Tessellation)swBody.GetTessellation(null); // Set up the Tessellation object swTessellation.NeedFaceFacetMap = true; swTessellation.NeedVertexParams = true; swTessellation.NeedVertexNormal = true; swTessellation.ImprovedQuality = true; // How to handle matches across common edges swTessellation.MatchType = (int)swTesselationMatchType_e.swTesselationMatchFacetTopology; // Do it if (swProgress != null) { swProgress.UpdateTitle("Exporting (tesselate process) ..."); } bResult = swTessellation.Tessellate(); // Get the number of vertices and facets //System.Windows.Forms.MessageBox.Show("Body n." + j + " vert.num=" + swTessellation.GetVertexCount()); //Debug.Print("Number of vertices: " + swTessellation.GetVertexCount()); //Debug.Print("Number of facets: " + swTessellation.GetFacetCount()); // Now get the facet data per face int[] aFacetIds; int iNumFacetIds; int[] aFinIds; int[] aVertexIds; double[] aNormal; double[] aVertexCoords1; double[] aVertexCoords2; double[] aVertexParams; int numv = swTessellation.GetVertexCount(); // Write all vertexes string mline; for (int iv = 0; iv < numv; iv++) { if ((swProgress != null) && (iv % 200 == 0)) { swProgress.UpdateTitle("Exporting (write " + iv + "-th vertex in .obj) ..."); } aVertexCoords1 = (double[])swTessellation.GetVertexPoint(iv); mline = "v " + (aVertexCoords1[0] * ChScale.L).ToString("f6", bz) + " " + (aVertexCoords1[1] * ChScale.L).ToString("f6", bz) + " " + (aVertexCoords1[2] * ChScale.L).ToString("f6", bz) + "\n"; textbuilder.Append(mline); } // Write all normals for (int iv = 0; iv < numv; iv++) { if ((swProgress != null) && (iv % 200 == 0)) { swProgress.UpdateTitle("Exporting (write " + iv + "-th normal in .obj) ..."); } aNormal = (double[])swTessellation.GetVertexNormal(iv); mline = "vn " + aNormal[0].ToString("f3", bz) + " " + aNormal[1].ToString("f3", bz) + " " + aNormal[2].ToString("f3", bz) + "\n"; textbuilder.Append(mline); } if (nBodyType == (int)swBodyType_e.swSheetBody) // for sheets, save two-sided triangles { for (int iv = 0; iv < numv; iv++) { if ((swProgress != null) && (iv % 200 == 0)) { swProgress.UpdateTitle("Exporting (write " + iv + "-th normal in .obj) ..."); } aNormal = (double[])swTessellation.GetVertexNormal(iv); mline = "vn " + (-aNormal[0]).ToString("f3", bz) + " " + (-aNormal[1]).ToString("f3", bz) + " " + (-aNormal[2]).ToString("f3", bz) + "\n"; textbuilder.Append(mline); } } // Write all UV (also with '0' as third value, for compatibility with some OBJ reader) if (saveUV) { for (int iv = 0; iv < numv; iv++) { if ((swProgress != null) && (iv % 200 == 0)) { swProgress.UpdateTitle("Exporting (write " + iv + "-th UV in .obj) ..."); } aVertexParams = (double[])swTessellation.GetVertexParams(iv); mline = "vt " + aVertexParams[0].ToString("f4", bz) + " " + aVertexParams[1].ToString("f4", bz) + " " + "0" + "\n"; textbuilder.Append(mline); } } // Loop over faces swFace = (Face2)swBody.GetFirstFace(); while (swFace != null) { aFacetIds = (int[])swTessellation.GetFaceFacets(swFace); iNumFacetIds = aFacetIds.Length; for (int iFacetIdIdx = 0; iFacetIdIdx < iNumFacetIds; iFacetIdIdx++) { if ((swProgress != null) && (iFacetIdIdx % 100 == 0)) { swProgress.UpdateTitle("Exporting (write " + iFacetIdIdx + "-th face in .obj) ..."); } mline = "f"; aFinIds = (int[])swTessellation.GetFacetFins(aFacetIds[iFacetIdIdx]); // There should always be three fins per facet for (int iFinIdx = 0; iFinIdx < 3; iFinIdx++) { aVertexIds = (int[])swTessellation.GetFinVertices(aFinIds[iFinIdx]); // Three fins per face, two vertexes each fin, // only the 1st vertex of two is needed (because of sharing) if (saveUV) { mline += " " + (aVertexIds[0] + group_vstride + 1) + "/" + (aVertexIds[0] + group_vstride + 1) + "/" + (aVertexIds[0] + group_nstride + 1); } else { mline += " " + (aVertexIds[0] + group_vstride + 1) + "//" + (aVertexIds[0] + group_nstride + 1); } } mline += "\n"; textbuilder.Append(mline); } swFace = (Face2)swFace.GetNextFace(); } swFace = (Face2)swBody.GetFirstFace(); if (nBodyType == (int)swBodyType_e.swSheetBody) // for sheets, save two-sided triangles { while (swFace != null) { aFacetIds = (int[])swTessellation.GetFaceFacets(swFace); iNumFacetIds = aFacetIds.Length; for (int iFacetIdIdx = 0; iFacetIdIdx < iNumFacetIds; iFacetIdIdx++) { if ((swProgress != null) && (iFacetIdIdx % 100 == 0)) { swProgress.UpdateTitle("Exporting (write " + iFacetIdIdx + "-th face in .obj) ..."); } mline = "f"; aFinIds = (int[])swTessellation.GetFacetFins(aFacetIds[iFacetIdIdx]); for (int iFinIdx = 2; iFinIdx >= 0; iFinIdx--) { aVertexIds = (int[])swTessellation.GetFinVertices(aFinIds[iFinIdx]); if (saveUV) { mline += " " + (aVertexIds[0] + group_vstride + 1) + "/" + (aVertexIds[0] + group_vstride + 1) + "/" + (aVertexIds[0] + swTessellation.GetVertexCount() + group_nstride + 1); } else { mline += " " + (aVertexIds[0] + group_vstride + 1) + "//" + (aVertexIds[0] + swTessellation.GetVertexCount() + group_nstride + 1); } } mline += "\n"; textbuilder.Append(mline); } swFace = (Face2)swFace.GetNextFace(); } } group_vstride += swTessellation.GetVertexCount(); group_nstride += swTessellation.GetVertexCount(); if (nBodyType == (int)swBodyType_e.swSheetBody) // for sheets: two-sided triangles { group_nstride += swTessellation.GetVertexCount(); } } } // end loop on bodies } // not null body asciitext += textbuilder.ToString(); }
/// Convert a SolidWorks component to Wavefront OBJ mesh /// public static void Convert(Component2 swComp, ref string asciitext, bool saveUV, ref UserProgressBar swProgress) { StringBuilder textbuilder = new StringBuilder(); Body2 swBody = default(Body2); object[] vBodies = null; object[] vBodiesSolid = null; object[] vBodiesSheet = null; object vBodyInfo; int[] BodiesInfo = null; int j = 0; ModelDoc2 swModel; swModel = (ModelDoc2)swComp.GetModelDoc(); vBodiesSolid = (object[])swComp.GetBodies3((int)swBodyType_e.swSolidBody, out vBodyInfo); vBodiesSheet = (object[])swComp.GetBodies3((int)swBodyType_e.swSheetBody, out vBodyInfo); BodiesInfo = (int[])vBodyInfo; if (vBodiesSolid != null && vBodiesSheet == null) vBodies = vBodiesSolid; if (vBodiesSolid == null && vBodiesSheet != null) vBodies = vBodiesSheet; if (vBodiesSolid != null && vBodiesSheet != null) vBodies = vBodiesSheet.Concat(vBodiesSolid).ToArray(); // vBodies = (object[])swComp.GetBodies3((int)swBodyType_e.swSolidBody, out vBodyInfo); if (vBodies != null) { int iNumBodies = vBodies.Length; int iNumSolidBodies = 0; int iNumSheetBodies = 0; int iNumTesselatedBodies = 0; if (iNumBodies >0) asciitext += "# Wavefront .OBJ file for tesselated shape: " + swComp.Name2 + " path: " + swModel.GetPathName() + "\n\n"; int group_vstride = 0; int group_nstride = 0; // Loop through bodies for (j = 0; j <= vBodies.Length - 1; j++) { swBody = (Body2)vBodies[j]; int nBodyType = (int)swBody.GetType(); if (nBodyType == (int)swBodyType_e.swSheetBody) iNumSheetBodies++; if (nBodyType == (int)swBodyType_e.swSolidBody) iNumSolidBodies++; if ((nBodyType == (int)swBodyType_e.swSheetBody || nBodyType == (int)swBodyType_e.swSolidBody) && !swBody.Name.StartsWith("COLL.") && swBody.Visible) { iNumTesselatedBodies++; CultureInfo bz = new CultureInfo("en-BZ"); //asciitext += "g body_" + iNumTesselatedBodies + "\n"; textbuilder.Append("g body_" + iNumTesselatedBodies + "\n"); Face2 swFace = null; Tessellation swTessellation = null; bool bResult = false; // Pass in null so the whole body will be tessellated swTessellation = (Tessellation)swBody.GetTessellation(null); // Set up the Tessellation object swTessellation.NeedFaceFacetMap = true; swTessellation.NeedVertexParams = true; swTessellation.NeedVertexNormal = true; swTessellation.ImprovedQuality = true; // How to handle matches across common edges swTessellation.MatchType = (int)swTesselationMatchType_e.swTesselationMatchFacetTopology; // Do it if (swProgress != null) swProgress.UpdateTitle("Exporting (tesselate process) ..."); bResult = swTessellation.Tessellate(); // Get the number of vertices and facets //System.Windows.Forms.MessageBox.Show("Body n." + j + " vert.num=" + swTessellation.GetVertexCount()); //Debug.Print("Number of vertices: " + swTessellation.GetVertexCount()); //Debug.Print("Number of facets: " + swTessellation.GetFacetCount()); // Now get the facet data per face int[] aFacetIds; int iNumFacetIds; int[] aFinIds; int[] aVertexIds; double[] aNormal; double[] aVertexCoords1; double[] aVertexCoords2; double[] aVertexParams; int numv = swTessellation.GetVertexCount(); // Write all vertexes string mline; for (int iv = 0; iv < numv; iv++) { if ((swProgress != null)&&(iv%200==0)) swProgress.UpdateTitle("Exporting (write " + iv + "-th vertex in .obj) ..."); aVertexCoords1 = (double[])swTessellation.GetVertexPoint(iv); mline = "v " + (aVertexCoords1[0]*ChScale.L).ToString("f6", bz) + " " + (aVertexCoords1[1]*ChScale.L).ToString("f6", bz) + " " + (aVertexCoords1[2]*ChScale.L).ToString("f6", bz) + "\n"; textbuilder.Append(mline); } // Write all normals for (int iv = 0; iv < numv; iv++) { if ((swProgress != null) && (iv % 200 == 0)) swProgress.UpdateTitle("Exporting (write " + iv + "-th normal in .obj) ..."); aNormal = (double[])swTessellation.GetVertexNormal(iv); mline = "vn " + aNormal[0].ToString("f3", bz) + " " + aNormal[1].ToString("f3", bz) + " " + aNormal[2].ToString("f3", bz) + "\n"; textbuilder.Append(mline); } if (nBodyType == (int)swBodyType_e.swSheetBody) // for sheets, save two-sided triangles for (int iv = 0; iv < numv; iv++) { if ((swProgress != null) && (iv % 200 == 0)) swProgress.UpdateTitle("Exporting (write " + iv + "-th normal in .obj) ..."); aNormal = (double[])swTessellation.GetVertexNormal(iv); mline = "vn " + (-aNormal[0]).ToString("f3", bz) + " " + (-aNormal[1]).ToString("f3", bz) + " " + (-aNormal[2]).ToString("f3", bz) + "\n"; textbuilder.Append(mline); } // Write all UV (also with '0' as third value, for compatibility with some OBJ reader) if (saveUV) for (int iv = 0; iv < numv; iv++) { if ((swProgress != null) && (iv % 200 == 0)) swProgress.UpdateTitle("Exporting (write " + iv + "-th UV in .obj) ..."); aVertexParams = (double[])swTessellation.GetVertexParams(iv); mline = "vt " + aVertexParams[0].ToString("f4", bz) + " " + aVertexParams[1].ToString("f4", bz) + " " + "0" + "\n"; textbuilder.Append(mline); } // Loop over faces swFace = (Face2)swBody.GetFirstFace(); while (swFace != null) { aFacetIds = (int[])swTessellation.GetFaceFacets(swFace); iNumFacetIds = aFacetIds.Length; for (int iFacetIdIdx = 0; iFacetIdIdx < iNumFacetIds; iFacetIdIdx++) { if ((swProgress != null) && (iFacetIdIdx % 100 == 0)) swProgress.UpdateTitle("Exporting (write " + iFacetIdIdx + "-th face in .obj) ..."); mline = "f"; aFinIds = (int[])swTessellation.GetFacetFins(aFacetIds[iFacetIdIdx]); // There should always be three fins per facet for (int iFinIdx = 0; iFinIdx < 3; iFinIdx++) { aVertexIds = (int[])swTessellation.GetFinVertices(aFinIds[iFinIdx]); // Three fins per face, two vertexes each fin, // only the 1st vertex of two is needed (because of sharing) if (saveUV) mline += " " + (aVertexIds[0] + group_vstride +1) + "/" + (aVertexIds[0] + group_vstride +1) + "/" + (aVertexIds[0] + group_nstride +1); else mline += " " + (aVertexIds[0] + group_vstride + 1) + "//" + (aVertexIds[0] + group_nstride + 1); } mline += "\n"; textbuilder.Append(mline); } swFace = (Face2)swFace.GetNextFace(); } swFace = (Face2)swBody.GetFirstFace(); if (nBodyType == (int)swBodyType_e.swSheetBody) // for sheets, save two-sided triangles while (swFace != null) { aFacetIds = (int[])swTessellation.GetFaceFacets(swFace); iNumFacetIds = aFacetIds.Length; for (int iFacetIdIdx = 0; iFacetIdIdx < iNumFacetIds; iFacetIdIdx++) { if ((swProgress != null) && (iFacetIdIdx % 100 == 0)) swProgress.UpdateTitle("Exporting (write " + iFacetIdIdx + "-th face in .obj) ..."); mline = "f"; aFinIds = (int[])swTessellation.GetFacetFins(aFacetIds[iFacetIdIdx]); for (int iFinIdx = 2; iFinIdx >= 0; iFinIdx--) { aVertexIds = (int[])swTessellation.GetFinVertices(aFinIds[iFinIdx]); if (saveUV) mline += " " + (aVertexIds[0] + group_vstride + 1) + "/" + (aVertexIds[0] + group_vstride + 1) + "/" + (aVertexIds[0] + swTessellation.GetVertexCount() + group_nstride + 1); else mline += " " + (aVertexIds[0] + group_vstride + 1) + "//" + (aVertexIds[0] + swTessellation.GetVertexCount() + group_nstride + 1); } mline += "\n"; textbuilder.Append(mline); } swFace = (Face2)swFace.GetNextFace(); } group_vstride += swTessellation.GetVertexCount(); group_nstride += swTessellation.GetVertexCount(); if (nBodyType == (int)swBodyType_e.swSheetBody) // for sheets: two-sided triangles group_nstride += swTessellation.GetVertexCount(); } } // end loop on bodies } // not null body asciitext += textbuilder.ToString(); }