Black Lives Matter. Please consider donating to Black Girls Code today.

Interpolation in plotly.graph_objects.Surface() plots

Hello

I’m plotting slices of a 3d volume with plotly.graph_objects.Surface(). As a standard the surface appears to undergo some kind of interpolation when plotted. See figure below.

I cannot see that it is described anywhere in the documentation, which makes me doubt what is actually going on.

But how do I get rid of this “interpolation”? I wish to show my true data.

Best regards.

@sibowi

Why do you suspect that the slice points are incorrectly colormapped?

Let us say that you get the slice sectioning the volume through the plane x=2. Within the resulting planar shape
you have induced a meshgrid from your volume. If at at given (y,z) in the slice the associated value is val, then exactly this val is mapped to a color in the colorscale. But since your planar shape has a discrete representation (consisting in the points of intersection of the discrete volume with x=2), at the points that are not in the induced meshgrid, the color is interpolated.

@empet

I thought I understood your point. If the grid of the meshgrid is not aligned with the grid of the volume (array), then interpolation will occur?

But according to the example below, I do not understand your point.

import numpy as np
import plotly 
import plotly.graph_objects as go

n = 100
l = 10.0
r = 3.0

# create empty volume
volume = np.zeros((n, n, n))

# draw a cylinder within the volume
x = y = np.linspace(-l/2, l/2, n)
X, Y = np.meshgrid(x, y)

volume[X**2 + Y**2 < r] = 1

# plot
Z = np.zeros(np.shape(volume)[:2])

cross_section = go.Surface(z = Z,
                           x = list(X),
                           y = list(Y),
                           surfacecolor=volume[:, :, 5],)

fig = go.Figure(data=cross_section)
plotly.offline.plot(fig, filename='test.html')

In this case the meshgrid is aligned with the grid that corresponds to the volume/array. The volume contains only zeros and ones. I still see interpolated values in the plot.

Best regards.

@sibowi

Let me explain how the colormapping of some data to a Plotly colorscale works.

First the colorscale is defined by a scale, i.e. a list of ordered values in [0,1]:
and a list of color codes, one for each scale entry:

my_colorscale = [[0.0, 'rgb(253, 253, 204)'],
                 [0.1, 'rgb(201, 235, 177)'],
                 [0.2, 'rgb(145, 216, 163)'],
                 [0.3, 'rgb(102, 194, 163)'],
                 [0.4, 'rgb(81, 168, 162)'],
                 [0.5, 'rgb(72, 141, 157)'],
                 [0.6, 'rgb(64, 117, 152)'],
                 [0.7, 'rgb(61, 90, 146)'],
                 [0.8, 'rgb(65, 64, 123)'],
                 [0.9, 'rgb(55, 44, 80)'],
                 [1.0, 'rgb(39, 26, 44)']]

The scale is the list of values [0, 0.1, 0.2, .....1].
Now suppose that your trace defintion colormaps uni-dimensional data, vals , of range [valmin, valmax] .
First plotly.js normalizes vals, i.e. maps them via the normalization function:

val --> norm_val=(val-valmin)/(valmax-valmin) in [0,1]

if the norm_val coincides with one of the scale entry, then to val is assigned the corresponding color in my_colorscale. Otherwise, plotly.js finds the interval of consecutive values in the scale, that contains the norm_val and calculates the corresponding color by interpolating linearly the color codes corresponding the the interval ends.

From your posted image and the red arrow I do not understand how would you like to get the colormapping.

Could you point out a surface image on the web plotted with another tool that maps values to colors and no interpolation is performed?