简体   繁体   English

Python,如何将x; y点列表定义的样条线转换为NURB曲线

[英]Python, how to convert spline defined by x;y list of point into NURB curve

is possible to convert the (x;y) coordinates system into a NURBS definition control points and knots? 是否可以将(x; y)坐标系转换为NURBS定义控制点和结?

The main idea is that I'm trying to develop a modeling tool in python for air wind generator and I want mathematically model the blades as a NURBS surfaces, but the curves that defines the blade transversal sections are normalized into (x;y) coordinates files. 主要思想是我正在尝试使用python开发用于风力发电机的建模工具,并且我想在数学上将叶片建模为NURBS曲面,但是将定义叶片横向截面的曲线归一化为(x; y)坐标文件。

Now I have all the (x;y) points defined into 2D Numpy array. 现在,我将所有(x; y)点定义为2D Numpy数组。

You can use scipy.interpolate for this. 您可以为此使用scipy.interpolate

import numpy as np
import matplotlib.pyplot as plt
from scipy.interpolate import splev, splrep

x = np.linspace(0, 10, 10) # x-coordinates
y = np.sin(x) # y-coordinates
tck = splrep(x, y) # get bspline representation given (x,y) values
x2 = np.linspace(0, 10, 200) # new set of values, just to check
y2 = splev(x2, tck) # evaluate the y values of new coordinates on NURBS curve
plt.plot(x, y, 'o', x2, y2) 
plt.show()

在此处输入图片说明

The tuple tck contains your knot vector and control points (coefficients). 元组tck包含您的结向量和控制点(系数)。 There are also more involved routines in SciPy, look here . SciPy中还有更多涉及的例程,请看这里

Note that these are only for bspline curves. 请注意,这些仅适用于bspline曲线。 As far as I know there are no equivalent methods for surfaces in SciPy. 据我所知,SciPy中没有等效的曲面方法。 If you want to use surfaces, depending on your requirement, you can either use igakit 如果要使用表面,可以根据需要使用igakit

from igakit.cad import ruled, circle
c1 = circle(angle=(0,np.pi/2.))
c2 = circle(radius=2,angle=(0,np.pi/2.))
print "knot vector:", c1.knots
print "control points:", c1.control
srf = ruled(c1,c2)
plt.plot(srf)
plt.show() 

knot vector: (array([ 0.,  0.,  0.,  1.,  1.,  1.]),)
control points: array([[  1.00000000e+00,   0.00000000e+00,   0.00000000e+00, 1.00000000e+00],
   [  7.07106781e-01,   7.07106781e-01,   0.00000000e+00, 7.07106781e-01],
   [  2.22044605e-16,   1.00000000e+00,   0.00000000e+00, 1.00000000e+00]])

在此处输入图片说明

or the NURBS package . NURBS软件包 For fancier stuff Blender and Salome have complete Python API for all family of NURBS curves/surfaces with the latter being based on OpenCascade . 对于更高级的东西, BlenderSalome具有适用于所有NURBS曲线/曲面系列的完整Python API,后者基于OpenCascade

Are you certain that you need NURBS surfaces? 确定要使用NURBS曲面吗? As far as I can tell, their primary advantage over b-spline surfaces is that they can precisely model circular arcs. 据我所知,它们相对于b样条曲面的主要优势在于它们可以精确地建模圆弧。 I've worked with airfoils for many years, and arcs aren't something that are particularly useful to me. 我使用机翼已有很多年了,弧线对我来说并不是特别有用。

Anyway, romeric is correct when he states that there is nothing analogous to scipy.interpolate.splprep for surfaces. 无论如何,当scipy.interpolate.splprep表面没有与scipy.interpolate.splprep类似的东西时,他是正确的。 But if you're not against rolling your own, you can create a 3D array from your section data of shape (3, m, n), where 'm' is the number of points per section, 'n' is the number of sections, and the first dimension holds x, y, and z values on the mxn grid. 但是,如果您不反对自己滚动,则可以根据形状为(3,m,n)的截面数据创建3D数组,其中'm'是每个截面的点数,'n'是截面,第一个维度在mxn网格上保存x,y和z值。 Once you have that, you can use scipy.interpolate.RectBivariateSpline to create 3 separate 2D parametric surfaces for the x, y and z coordinates. 一旦有了这些,就可以使用scipy.interpolate.RectBivariateSpline为x,y和z坐标创建3个单独的2D参数化曲面。 Then write a class to combine these into a single 2D surface in 3D space, so that when you call mysurf.ev(0.5, 0.2) for instance, it evaluates the 3 RectBivariateSpline instances embedded in your class and returns an (x, y, z) coordinate. 然后编写一个类,将它们组合成3D空间中的单个2D曲面,这样,例如,当您调用mysurf.ev(0.5, 0.2) ,它将评估类中嵌入的3个RectBivariateSpline实例并返回(x,y, z)坐标。

I've posted a Gist here that may get you started. 我在这里发布了要点,可能会让您入门。 To try it, either run it from the command line, or do this: 若要尝试,请从命令行运行它,或执行以下操作:

from bsplinesurf import DemoBSplineSurf
srf = DemoBSplineSurf()
srf.plot()

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM