Bill3D,
Thank you for your help. Unfortunately, the node is still not being rendered. Here is the modified code plus the bsplinePath function. I will be grateful if you would try it.
```func cabinetKnob() -> SCNNode {
let controlPoints: [(x: Float, y: Float)] = [
(0.728,-0.237), (0.176,-0.06), (0.202,0.475), (0.989,0.842),
(-0.066,1.093), (-0.726,0.787) ]
let pairs = bsplinePath(controlPoints)
var knobProfile = [SCNVector3]()
for (x,y) in pairs {
knobProfile += [ SCNVector3(x: CGFloat(x), y: CGFloat(y), z: 0)]
}
let nProfiles = 64
// create knob by rotating knobProfile about y-axis
let aIncrement: CGFloat = 2 * CGFloat.pi / CGFloat(nProfiles) // ~6 degrees
var angle: CGFloat = 0
var knobVertices = knobProfile.map( { $0 } )
angle = 0
for _ in 1...nProfiles {
angle += aIncrement
// rotate knobProfile about y-axis
knobVertices += knobProfile.map( { $0.rotate(about: .y, by: angle) } )
}
let source = SCNGeometrySource(vertices: knobVertices)
var indices = [[UInt16]]()
var i: UInt16 = 0
var j: UInt16 = UInt16(knobProfile.count) // 1st vertex of next profile
for k in 0...nProfiles {
var stripIndices = [UInt16]()
if k == nProfiles { j = 0 }
for _ in 0...knobProfile.count-1 {
stripIndices += [i, j]
i += 1; j += 1
}
indices += [stripIndices]
}
let elements: [SCNGeometryElement] = indices.map( {
SCNGeometryElement(indices: $0, primitiveType: .triangleStrip) } )
let surfaceGeometry = SCNGeometry(sources: [source], elements: elements)
let aluminum = SCNMaterial()
aluminum.lightingModel = SCNMaterial.LightingModel.physicallyBased
aluminum.diffuse.contents = NSColor(srgbRed: 0.95, green: 0.95, blue: 0.95, alpha: 1.0)
aluminum.roughness.contents = 0.2
aluminum.metalness.contents = 0.9
aluminum.isDoubleSided = true
let modelMesh = MDLMesh(scnGeometry: surfaceGeometry)
do{
try modelMesh.makeVerticesUniqueAndReturnError()
modelMesh.addNormals(withAttributeNamed: "normal", creaseThreshold: 0.9)
let flattenedGeom = SCNGeometry(mdlMesh: modelMesh)
let flattenedNode = SCNNode(geometry: flattenedGeom)
flattenedNode.geometry?.materials = [aluminum]
return flattenedNode
}catch{
fatalError("mesh vert error")
}
}
func bsplinePath(_ p: [(x: Float, y: Float)]) -> [(Float, Float)] {
var pairs = [(Float, Float)]()
let nSegements: Int = 10
let tIncr: Float = 1.0/Float(nSegements)
let bmat = simd_float4x4([ simd_float4(-1/6, 0.5, -0.5, 1/6),
simd_float4(0.5, -1, 0, 4/6),
simd_float4(-0.5, 0.5, 0.5, 1/6),
simd_float4(1/6, 0, 0, 0) ])
for i in 0...p.count-4 {
let px = simd_float4(p[i].x, p[i+1].x, p[i+2].x, p[i+3].x)
let py = simd_float4(p[i].y, p[i+1].y, p[i+2].y, p[i+3].y)
let vx: simd_float4 = simd_mul(bmat, px)
let vy: simd_float4 = simd_mul(bmat, py)
// print("bmat * P = (\(vx), \(vy))")
var t: Float = 0
let last: Int = (i == p.count-4) ? nSegements : nSegements-1
for _ in 0...last {
let qx = simd_dot(simd_float4(t*t*t, t*t, t, 1), vx)
let qy = simd_dot(simd_float4(t*t*t, t*t, t, 1), vy)
pairs += [(qx, qy)]
t += tIncr
}
}
return pairs
}
Post
Replies
Boosts
Views
Activity
I don't see the image I provided.
The first code block should include the 2 lines following it.