How to obtain 3D colored surface via Python?

后端 未结 4 2234
眼角桃花
眼角桃花 2020-12-06 12:54

How to obtain the following surface via Matplotlib?

It is easy in matlab via:

mesh(peaks)

It seems matplotlib does not have an exac

4条回答
  •  失恋的感觉
    2020-12-06 13:32

    It seems to be possible with matplotlib even if it is a bit of a hack:

    from mpl_toolkits.mplot3d import axes3d
    from mpl_toolkits.mplot3d import art3d
    import matplotlib.pyplot as plt
    import numpy as np
    import matplotlib as mpl
    
    fig = plt.figure()
    ax = fig.add_subplot(111, projection='3d')
    X, Y, Z = axes3d.get_test_data(0.05)
    wire = ax.plot_wireframe(X, Y, Z, rstride=10, cstride=10)
    
    # Retrive data from internal storage of plot_wireframe, then delete it
    nx, ny, _  = np.shape(wire._segments3d)
    wire_x = np.array(wire._segments3d)[:, :, 0].ravel()
    wire_y = np.array(wire._segments3d)[:, :, 1].ravel()
    wire_z = np.array(wire._segments3d)[:, :, 2].ravel()
    wire.remove()
    
    # create data for a LineCollection
    wire_x1 = np.vstack([wire_x, np.roll(wire_x, 1)])
    wire_y1 = np.vstack([wire_y, np.roll(wire_y, 1)])
    wire_z1 = np.vstack([wire_z, np.roll(wire_z, 1)])
    to_delete = np.arange(0, nx*ny, ny)
    wire_x1 = np.delete(wire_x1, to_delete, axis=1)
    wire_y1 = np.delete(wire_y1, to_delete, axis=1)
    wire_z1 = np.delete(wire_z1, to_delete, axis=1)
    scalars = np.delete(wire_z, to_delete)
    
    segs = [list(zip(xl, yl, zl)) for xl, yl, zl in \
                     zip(wire_x1.T, wire_y1.T, wire_z1.T)]
    
    # Plots the wireframe by a  a line3DCollection
    my_wire = art3d.Line3DCollection(segs, cmap="hsv")
    my_wire.set_array(scalars)
    ax.add_collection(my_wire)
    
    plt.colorbar(my_wire)
    plt.show()
    

    enter image description here

提交回复
热议问题