Surfaces
Two type of surfaces are available:
- B-splines surfaces
- NURBS surfaces
Both are defined by initializing corresponding structures.
Defining Structures
NURBS and B-spline surfaces are defined by initializing a BsplineSurface
or a NURBSsurface
structure, respectively.
using StaticArrays
# --- parameters
kVec = Float64[0, 0, 0, 1, 2, 3, 4, 5, 5, 5] # knot vector
kVec ./= maximum(kVec) # normalize it
p = 2 # degree of the basis
# --- control points
controlPoints = [[SVector(0.0,0.0,3.0), SVector(0.0,1.0,3.0), SVector(0.0,2.0,2.0), SVector(0.0,3.0,2.0), SVector(0.0,4.0,2.0), SVector(0.0,5.0,2.0), SVector(0.0,6.0,2.0)],
[SVector(1.0,0.0,3.0), SVector(1.0,1.0,3.0), SVector(1.0,2.0,2.0), SVector(1.0,3.0,2.0), SVector(1.0,4.0,2.0), SVector(1.0,5.0,2.0), SVector(1.0,6.0,2.0)],
[SVector(2.0,0.0,2.0), SVector(2.0,1.0,2.0), SVector(2.0,2.0,1.0), SVector(2.0,3.0,1.0), SVector(2.0,4.0,1.0), SVector(2.0,5.0,1.0), SVector(2.0,6.0,1.0)],
[SVector(3.0,0.0,2.0), SVector(3.0,1.0,2.0), SVector(3.0,2.0,1.0), SVector(3.0,3.0,1.0), SVector(3.0,4.0,1.0), SVector(3.0,5.0,0.0), SVector(3.0,7.0,0.0)],
[SVector(4.0,0.0,1.0), SVector(4.0,1.0,1.0), SVector(4.0,2.0,0.0), SVector(4.0,3.0,0.0), SVector(4.0,4.0,1.0), SVector(4.0,5.0,0.0), SVector(4.0,6.0,0.0)],
[SVector(5.0,0.0,1.0), SVector(5.0,1.0,1.0), SVector(5.0,2.0,0.0), SVector(5.0,3.0,0.0), SVector(5.0,4.0,0.0), SVector(5.0,5.0,0.0), SVector(5.0,6.0,0.0)],
[SVector(6.0,0.0,1.0), SVector(6.0,1.0,1.0), SVector(6.0,2.0,0.0), SVector(6.0,3.0,0.0), SVector(6.0,4.0,0.0), SVector(6.0,5.0,0.0), SVector(6.0,6.0,0.0)]]
controlPoints = [controlPoints[i][j] for i in 1:7, j in 1:7]
# --- weights for the NURBS basis
w = ones(size(controlPoints))
w[5,5] = 2.0
w[7,2] = 0.8
# --- initialize structures (using the same basis in both parametric directions)
BSurface = BsplineSurface(Bspline(p, kVec), Bspline(p, kVec), controlPoints)
NSurface = NURBSsurface(Bspline(p, kVec), Bspline(p, kVec), controlPoints, w)
Evaluate Points on a Surface
To evaluate the surfaces at parametric points hand over the latter.
uEvalpoints = collect(0:0.01:1.0)
vEvalpoints = collect(0:0.01:1.0)
SBspline = BSurface(uEvalpoints, vEvalpoints)
SNurbs = NSurface(uEvalpoints, vEvalpoints)
To plot the surfaces the plotSurface
or the plotPatches
functions are provided, where the latter evaluates the surface points itself.
The PlotlyJS.jl package has to be loaded in order to make the functions available. (It is a weak dependency.)
using PlotlyJS
plotSurface(SNurbs, controlPoints=controlPoints)
# alternatively
#plotPatches([NSurface], plotControlPoints=true)
Evaluate Derivatives of a Surface
To evaluate derivatives of surfaces at parametric points hand over the latter and the maximum derivative to be evaluated.
uEvalpoints = collect(0:0.01:1.0)
vEvalpoints = collect(0:0.01:1.0)
S = NSurface(uEvalpoints, vEvalpoints, 2) # 0-th, 1st, and 2nd derivatives
In case points (e.g., single points) shall be evaluated many times on demand, memory can be preallocated and reused in subsequent calls:
pM = NURBS.preAllocNURBSsurface(p, p, uEvalpoints, vEvalpoints, 2)
S = NSurface(uEvalpoints, vEvalpoints, 2, pM)
The plotSurface
function has an optional argument tangents
to plot vectors at the points of the curve.
using PlotlyJS
plotSurface(S[1, 1], tangents=S[2,1], controlPoints=NSurface.controlPoints, enforceRatio=false)