question-mark
Stuck on an issue?

Lightrun Answers was designed to reduce the constant googling that comes with debugging 3rd party libraries. It collects links to all the places you might be looking at while hunting down a tough bug.

And, if you’re still stuck at the end, we’re happy to hop on a call to see how we can help out.

Save `pyvista.MultiBlock` in STL format

See original GitHub issue

Hello everyone.

I think that the option to save the pyvista.MultiBlock type in STL format would be helpful. Various software (e.g., Beta Ansa preprocessing tool for Computational Fluid Dynamics or Meshmixer) only accepts STL format for the input geometry. Multiple parts are allowed in the STL format by adding the solid [solid_name] .... endsolid [solid_name] keywords. This is an example (for STL ASCII, of course):

solid "front"
  facet normal -0.161384269595 0.98523491621 -0.0571600198746
    outer loop
      vertex 2.43927001953 -3.28291988373 31.002199173
      vertex 2.58858990669 -4.39023017883 31.0909004211
      vertex 3.39857983589 -3.73215985298 31.1854000092
    endloop
  endfacet
  facet normal -0.0869731009007 0.839549422264 -0.536276459694
    outer loop
      vertex 3.77996993065 1.47368001938 29.9706001282
      vertex 4.10769987106 2.22097992897 29.5272006989
      vertex 3.07201004028 2.18530011177 29.4426994324
    endloop
  endfacet
.........
endsolid "front"
solid "back"
  facet normal 0.348130375147 0.823633670807 0.447697281837
    outer loop
      vertex 10.0833997726 -10.0583000183 29.6856994629
      vertex 10.8774995804 -9.29601955414 29.7644004822
      vertex 9.88414001465 -9.12524032593 30.2770996094
    endloop
  endfacet
  facet normal -0.140576228499 0.74150198698 0.6560587883
    outer loop
      vertex 3.84086990356 -11.9118995667 28.7719993591
      vertex 3.13609004021 -11.3332004547 29.1504001617
      vertex 2.98072004318 -12.218000412 28.3381004333
    endloop
  endfacet
.........
endsolid "back"

I came up with a temporary solution using the already present function to save individual pyvista.PolyData in STL format:

def save_multiblock_stl(multiblock, filename):

    names = multiblock.keys()
    oname, ext = osp.splitext(filename)
    assert ext == '.stl'
    
    # each individual stl file saved (output_filenames)
    ofiles = [f'{oname}_{ii}' + '.stl' for ii in range(len(names))]

    for ii, subpart in enumerate(multiblock):
        subpart.save(ofiles[ii], binary=False)
        change_first_line_of_file(ofiles[ii], f'solid {names[ii]}') # basically changes "solid" to "solid <solid_name>"

    # merge files together
    total_stl = ''
    for fn in ofiles:
        f = open(fn)
        total_stl += f.read()
        f.close()

    # writes total stl file
    with open(oname + '.stl', 'w') as f:
        f.write(total_stl)

    # deletes previously written stl files
    for fn in ofiles:
        os.remove(fn)

    return

def change_first_line_of_file(filename, new_first_line):

    fr = open(filename, 'r')
    first_line = fr.readline()
    fr.close()
    first_line_len = len(first_line)

    new_first_line_len = len(new_first_line)
    spaces_num = first_line_len - new_first_line_len
    new_first_line = new_first_line + ' '*(spaces_num-1) + '\n'
    fw = StringIO(new_first_line)
    fr = open(filename, 'r+')
    shutil.copyfileobj(fw, fr)
    fr.close()
    fw.close()
    return

Basically, I write to disk in STL ascii every single part of the pyvista.MultiBlock, I change the first line of each file from “solid” to “solid <solid_name>” and then I merge the files together. This works because the syntax

solid <solid_name>
...
...
endsolid

is allowed.

Obviously, this is not an efficient solution, so maybe someone has a better idea.

Thanks !

Issue Analytics

  • State:closed
  • Created 2 years ago
  • Comments:13 (7 by maintainers)

github_iconTop GitHub Comments

1reaction
scarpmacommented, Mar 16, 2022

Thank you for your reply! Actually, I’m not familiar with vtk alone. I could paste this same post in their forum at https://discourse.vtk.org/c/development/7/l/latest. What do you think?

0reactions
scarpmacommented, Mar 22, 2022

Ok, thanks very much for the explanation.

I think you convinced me. Adding this option in the vtk library would not be a good solution.

If I was the only one interested, I will close the issue.

Read more comments on GitHub >

github_iconTop Results From Across the Web

save — PyVista 0.37.0 documentation
MultiBlock.save(filename: str, binary=True, texture=None)#. Save this vtk object to file. Parameters: filename str , pathlib.Path. Filename of output file.
Read more >
save — PyVista 0.37.0 documentation
Write a surface mesh to disk. Written file may be an ASCII or binary ply, stl, or vtk mesh file. If ply or...
Read more >
read — PyVista 0.37.0 documentation
Read any file type supported by vtk or meshio . ... MultiBlock dataset is returned with each file being a separate block in...
Read more >
Source code for pyvista.examples.downloads
Files are all hosted in https://github.com/pyvista/vtk-data/ and are downloaded ... MultiBlock or tuple DataSet or tuple of filenames depending on ``load``.
Read more >
Source code for pyvista.utilities.fileio
vtkSTLWriter )): if use_binary: vtk_writer. ... MultiBlock` dataset is returned with each file being a separate block in the dataset. attrs : dict, ......
Read more >

github_iconTop Related Medium Post

No results found

github_iconTop Related StackOverflow Question

No results found

github_iconTroubleshoot Live Code

Lightrun enables developers to add logs, metrics and snapshots to live code - no restarts or redeploys required.
Start Free

github_iconTop Related Reddit Thread

No results found

github_iconTop Related Hackernoon Post

No results found

github_iconTop Related Tweet

No results found

github_iconTop Related Dev.to Post

No results found

github_iconTop Related Hashnode Post

No results found