numpy-stl
Numpy-stl is a Python library designed to simplify reading, writing, and modifying both binary and ASCII STL (stereolithography) files. Leveraging NumPy, it offers fast and efficient operations for 3D object manipulation. The library is currently at version 3.2.0, with regular updates that include bug fixes, new features, and compatibility enhancements for its core dependencies.
Common errors
-
ImportError: cannot import name 'mesh' from 'stl'
cause This error typically occurs when Python either cannot find the `stl` module from `numpy-stl` or imports a different package also named `stl` that does not expose a `mesh` object. This is often due to a conflicting package or a broken installation.fixVerify that `numpy-stl` is correctly installed (`pip show numpy-stl`). Check for other installed packages named `stl` (e.g., using `pip list | grep stl`) and uninstall them if they are not `numpy-stl`'s module. Reinstall `numpy-stl` if the issue persists: `pip uninstall numpy-stl && pip install numpy-stl`. -
TypeError: 'numpy.ndarray' object cannot be interpreted as an integer
cause This can happen when trying to create a `Mesh` object with an incorrect `dtype` or when improperly initializing the data array for the mesh, especially if `numpy.zeros` is not used with `mesh.Mesh.dtype` for the structure.fixEnsure that when creating a new mesh, the data array is initialized with the correct structured dtype from `mesh.Mesh.dtype`. For example: `data = np.zeros(num_faces, dtype=mesh.Mesh.dtype)`. -
FileNotFoundError: [Errno 2] No such file or directory: 'some_file.stl'
cause This error occurs when `mesh.Mesh.from_file()` cannot find the specified STL file at the given path. This can be due to a typo in the filename, an incorrect relative path, or the file simply not existing.fixDouble-check the filename and its full or relative path. Ensure the file exists in the expected location. Use `os.path.exists()` to verify the file's presence before attempting to load it.
Warnings
- breaking Numpy-stl v3.2.0 adds support for NumPy 2.x, which includes significant API and ABI changes in NumPy itself. If you are using older versions of `numpy-stl` with NumPy 2.x, or if you compile extensions against an older NumPy and then try to run with NumPy 2.x, you may encounter compatibility issues.
- gotcha Prior to versions 3.0.0 and 2.17.1, `numpy-stl` had issues with floating-point number truncation. This could lead to a loss of precision in the saved or processed STL files, potentially affecting the geometry of the 3D models.
- gotcha The primary import for `numpy-stl` is `from stl import mesh`. If you have another Python package named `stl` installed on your system, it can lead to import conflicts and unexpected `ImportError` messages, as Python might import the wrong `stl` module.
Install
-
pip install numpy-stl
Imports
- mesh
from stl import mesh
- numpy
import numpy as np
Quickstart
import numpy as np
from stl import mesh
import os
# --- Create a new mesh from scratch ---
# Define the 8 vertices of the cube
vertices = np.array([
[-1, -1, -1], [+1, -1, -1], [+1, +1, -1], [-1, +1, -1], # Bottom square
[-1, -1, +1], [+1, -1, +1], [+1, +1, +1], [-1, +1, +1] # Top square
])
# Define the 12 triangles (faces) composing the cube
faces = np.array([
[0,3,1], [1,3,2], # Bottom
[0,4,7], [0,7,3], # Front-left
[4,5,6], [4,6,7], # Top
[5,1,2], [5,2,6], # Back-right
[2,3,6], [3,7,6], # Top-right
[0,1,5], [0,5,4] # Bottom-left
])
# Create the mesh object
cube = mesh.Mesh(np.zeros(faces.shape[0], dtype=mesh.Mesh.dtype))
for i, f in enumerate(faces):
for j in range(3):
cube.vectors[i][j] = vertices[f[j],:]
# Save the mesh to a file
output_filename = 'new_cube.stl'
cube.save(output_filename)
print(f"Saved new mesh to {output_filename}")
# --- Load an existing STL file ---
# Create a dummy file for demonstration if it doesn't exist
if not os.path.exists('example.stl'):
# In a real scenario, 'example.stl' would be an existing file.
# For this quickstart, we'll save the cube we just created as 'example.stl'
# just to demonstrate loading.
cube.save('example.stl')
try:
your_mesh = mesh.Mesh.from_file('example.stl')
print(f"Successfully loaded mesh from example.stl with {len(your_mesh.vectors)} triangles.")
# Access mesh properties
print(f"Volume: {your_mesh.get_mass_properties()[0]:.2f}")
except Exception as e:
print(f"Could not load example.stl: {e}")