Black Lives Matter. Please consider donating to Black Girls Code today.
Learn how to use COVID-19 data in open source Dash apps. Register for the Sept 23rd webinar with IQT!

How to add contours to a multi surface plot

I’m plotting a multi surfaces plot referring to this.
I wish to add one contour on each surface. According to the error message before:

‘contours’ is a valid attribute to ‘surface’ object.

I tried use contours=go.Contour(z=[1.0]) but it gives me:


But I didn’t include “type” when making my contour…

Then I tried contours=[1.0]:

I checked the webpage and I think I’m doing the correct thing. I don’t know what’s my problem…Could someone help?

Thank you in advance!

@CEiffel From your question it is not clear if you want to plot contour lines on your surface or the contour plot. Here https://plot.ly/~empet/14521 are given examples on how to define data for both plots.

Hi, thank you so much for your help!

I tried your method, but the contours still doesn’t show up on my surface…I read the documentation yet I still couldn’t get it to work.

https://plot.ly/~YuanzeEiffelLuo/21/the-following-cell-is-just-reading-the-f/ Could you please have a look at my notebook and see where the problem might be?

Thanks again!

My filling is that your contours are not computed, because your surface is not defined as z=f(x,y). Your surface is given only by its z-values. Theoretically the algorithm computing the countour lines on a surface solves the system z=f(x,y), z=cst to get their equation or you don’t have any function of x,y.

Try the following trick: if haf is a numpy array of shape (m,n) choose some intervals for x, and y, such that to interpret your surface as being of equation z=haf(x,y), x in [a,b], y in [c,d]

x=np.linspace(a, b,  n)
y=np.linspace(c,d, m)
x,y=np.meshgrid(x,y)

and define:

surf2=dict(x=x, y=y, z=haf, 
       showscale=True, 
       opacity=0.8, showlegend=True, type='surface', 
       cauto=False, 
       colorscale=col,   
       name='H-alpha', 
       reversescale=False, colorbar=go.ColorBar(x=-0.84),
       contours=dict(z=dict(show=True,
                                        project=dict(z=True),
                                        color='rgb(50,50,50)')))

Tried but still doesn’t work…Looks like z has to be a function with exact formula to for plotly to generate the contour lines.
I guess I’ll have to adjust the colorscale to achieve my goal…
But your help is still invaluable!
Thank you very much!

No, the explicit function is not necessary, because we are working with discrete functions. Plotly is not aware of my function z=f(x,y). It works on the numpy arrays x, y and z I defined in the previous message. Something in your code is missing or data are not in a right format or shape.

Hum…I’ve got stuck on this for many days. I checked many times but couldn’t find the error…if it’s because of the original date then I think I won’t be able to do much about it. You remind me of two of my other questions:

  1. how to set the z values where I want to plot contours?
    contours=dict(z=dict(show=True, project=dict(z=True), color='rgb(50,50,50)'), z=[1.0,2.0]) ? put in z values as a list?
  2. if it is possible to pay for the plotly student plan just for a month, rather than subscribing it for a whole year?

Thank you so much!

  1. z is a numpy array of shape(m,n), or a list of equal length lists: z=[[0.8, 1.3, 1], [1.55, 0.93, 1.3], [1.14, 0.8, 1.5]]

Inspecting again your Jupyter notebook I noticed that you defined a layout as for a 2d plot or the surface is in the 3d space. That is why the surfaces are not displayed.
You should change the layout as follows:

axis = dict(showbackground=True, 
            backgroundcolor="rgb(230, 230,230)",
            gridcolor="rgb(255, 255, 255)",      
            zerolinecolor="rgb(255, 255, 255)",  
           )

layout=dict(title='My title'
            autosize=False,
            width=700,
            height=700,# since you  are plooting 3 surface increase height to 900 or 1000
            scene=dict(xaxis=axis,
                              yaxis=axis,  
                              zaxis=dict(axis),
                              aspectratio=dict(x=1, y=1, z=0.5)#z in [0,1]. As z in bigger the plotted surface is taller
         ))

Thanks! This does help to make the axis information show up in the graph.
However I don’t quite understand why should we put the z value for contours as an numpy array or list of the same size. I thought we only need to input the values of z at which we want to plot contour. If I only want one contour at one z value, wouldn’t we just put one value?
I’m confused =_=…Thanks again!!!