【问题标题】:How to draw ellipsoid with plotly如何用plotly绘制椭球
【发布时间】:2016-06-19 16:41:26
【问题描述】:

有没有办法用 plotly 3D 绘制像椭球这样的表面?

目前文档中只讨论了 z=f(x,y) 形式的表面。还有Mesh 3D,但我没有找到它的例子。似乎可以手动对椭球进行三角剖分,然后使用 Mesh 得到椭球,但这对我来说似乎有点困难。有没有更好的办法?

【问题讨论】:

    标签: python r 3d plotly r-plotly


    【解决方案1】:

    好吧,这比我想象的要容易。有alphahull 选项要求自动计算相应的三角剖分。

    from plotly.offline import iplot, init_notebook_mode
    from plotly.graph_objs import Mesh3d
    from numpy import sin, cos, pi
    
    # some math: generate points on the surface of ellipsoid
    
    phi = np.linspace(0, 2*pi)
    theta = np.linspace(-pi/2, pi/2)
    phi, theta=np.meshgrid(phi, theta)
    
    x = cos(theta) * sin(phi) * 3
    y = cos(theta) * cos(phi) * 2
    z = sin(theta)
    
    # to use with Jupyter notebook
    
    init_notebook_mode()
    
    iplot([Mesh3d({
                    'x': x.flatten(), 
                    'y': y.flatten(), 
                    'z': z.flatten(), 
                    'alphahull': 0
    })])
    

    这是 R 版本:

    library(pracma)
    theta <- seq(-pi/2, pi/2, by=0.1)
    phi <- seq(0, 2*pi, by=0.1)
    mgrd <- meshgrid(phi, theta)
    phi <- mgrd$X
    theta <-  mgrd$Y
    x <- cos(theta) * cos(phi) * 3
    dim(x) <- NULL
    y <- cos(theta) * sin(phi) * 2
    dim(y) <- NULL
    z <- sin(theta) * scale
    dim(z) <- NULL
    
    ell <- cbind(x, y, z)
    
    ell <- setNames(ell, c('x', 'y', 'z'))
    
    library(plotly)
    p <- plot_ly(as.data.frame(ell), x=x, y=y, z=z, type='mesh3d', alphahull = 0)
    
    p %>% layout(scene = list(aspectmode = 'data'))
    

    编辑:也可以使用type='surface' 生成参数图:在这种情况下,必须提供二维xy

    library(plotly)
    library(pracma)
    mgrd <- meshgrid(seq(-pi, pi, length.out = 100), seq(-pi/2, pi/2, length.out = 100))
    U <- mgrd$X
    V <- mgrd$Y
    frame <- list(x=cos(V)*cos(U)*3, y=cos(V)*sin(U)*2, z=sin(V))
    plot_ly(frame, type='surface', x=x, y=y, z=z, showlegend=F, showscale=F,
            colorscale=list(list(0, 'blue'), list(1, 'blue')))
    

    【讨论】:

    • 哇。我回来时以为这会比我的投票更多,但发现有人在没有解释的情况下投了反对票。
    • @42-,这是因为你的答案有图片,而我的没有。 :)
    • 你的形象现在好多了。而且您的代码看起来处于“更高”的抽象级别。我很高兴你保持幽默感。
    【解决方案2】:

    假设椭圆体由公式(X-c)'A(X-c) = r 给出。

    library(Rvcg)
    sphr <- vcgSphere()
    library(rgl)
    ell <- scale3d(transform3d(sphr, chol(A)), r, r, r)
    vs <- ell$vb[1:3,] + c
    idx <- ell$it - 1
    library(plotly)
    p <- plot_ly(type="mesh3d",
      x = vs[1,], y = vs[2,], z = vs[3,],
      i = idx[1,], j = idx[2,], k = idx[3,],
      opacity = 0.3) 
    

    【讨论】:

      【解决方案3】:

      为什么不在椭圆体上的数学项目中解出这个方程中的 z:

      require(plotly)
      a=5; b=7; c=9
      x=rep(seq(-10,10,by=1), each=21)
      y=rep( seq(-10,10,by=1), times=21)
      z <- c^2*sqrt(1-x^2/a^2-y^2/b^2)
      #Warning message:
      #In sqrt(1 - x^2/a^2 - y^2/b^2) : NaNs produced
      
       plot_ly(z = matrix(z,21,21), type = "surface")
      

      【讨论】:

      • 是的,我想过,但我不需要半个椭球体,而是整个椭球体。我不确定,是否可以使用表面图创建两个半椭圆体(可能是),但恐怕它不会像 Mesh 3d 椭圆体那么好(表面图在表面几乎垂直的情况下可能会很奇怪切平面)。
      • 你的答案显然更好。你应该给自己打勾。我想知道是否有办法将 Mesh3d 调用嵌入到 R 接口中,但目前这超出了我的能力范围。
      • 最后,我找到了一个你和我的线性组合的答案:使用type="surface",但提供二维xy 并以这种方式获得参数图。 (请参阅我的答案的更新。)
      • 强大的工作。几天后,我希望我能记得回来并添加赏金,以便您的工作能够得到适当的认可。
      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2018-10-28
      • 2013-09-14
      • 2022-06-18
      • 2021-11-05
      • 1970-01-01
      相关资源
      最近更新 更多