Description
Bug summary
The initialization of an mpl_toolkits.mplot3d.Poly3DCollection
object cannot properly handle the parameter verts
when verts
= a list of (N, 3) array-like nested tuples, and shade=False
.
Code for reproduction
from mpl_toolkits.mplot3d import art3d
corners = ((0, 0, 0), (0, 5, 0), (5, 5, 0), (5, 0, 0))
tri = art3d.Poly3DCollection([corners], shade=True) # Failed when shade=True
# tri = art3d.Poly3DCollection([corners]) # Passed with the default setting shade=False
Actual outcome
TypeError Traceback (most recent call last)
Cell In[3], line 1
----> 1 tri = art3d.Poly3DCollection([corners], shade=True)
File ~/anaconda3/envs/testmpl/lib/python3.12/site-packages/mpl_toolkits/mplot3d/art3d.py:905, in Poly3DCollection.init(self, verts, zsort, shade, lightsource, *args, **kwargs)
875 """
876 Parameters
877 ----------
(...)
902 and _edgecolors properties.
903 """
904 if shade:
--> 905 normals = _generate_normals(verts)
906 facecolors = kwargs.get('facecolors', None)
907 if facecolors is not None:
File ~/anaconda3/envs/testmpl/lib/python3.12/site-packages/mpl_toolkits/mplot3d/art3d.py:1222, in _generate_normals(polygons)
1220 n = len(ps)
1221 i1, i2, i3 = 0, n//3, 2*n//3
-> 1222 v1[poly_i, :] = ps[i1, :] - ps[i2, :]
1223 v2[poly_i, :] = ps[i2, :] - ps[i3, :]
1224 return np.cross(v1, v2)
TypeError: tuple indices must be integers or slices, not tuple
Expected outcome
No error.
Additional information
When shade=True
, the __init__
function will first call the function _generate_normals(polygons)
, where polygons=verts
. In our case, verts
is not an instance of np.ndarray
but a list, so it enters the for loop:
for poly_i, ps in enumerate(polygons):
n = len(ps)
i1, i2, i3 = 0, n//3, 2*n//3
v1[poly_i, :] = ps[i1, :] - ps[i2, :]
v2[poly_i, :] = ps[i2, :] - ps[i3, :]
polygons
is [((0, 0, 0), (0, 5, 0), (5, 5, 0), (5, 0, 0))]
, and ps
is a nested tuple, so we need to convert ps
to np.ndarray
before using the array slicing like ps[i1, :]
. A possible fix may be setting ps = np.asarray(ps)
before array slicing.
Operating system
No response
Matplotlib Version
3.9.2
Matplotlib Backend
No response
Python version
No response
Jupyter version
No response
Installation
None