Post

Replies

Boosts

Views

Activity

Reply to SCNNode from MDLMesh not rendered
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 }
Nov ’24
Reply to SCNNode from MDLMesh not rendered
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 }
Replies
Boosts
Views
Activity
Nov ’24
Reply to SCNNode from MDLMesh not rendered
I don't see the image I provided. The first code block should include the 2 lines following it.
Replies
Boosts
Views
Activity
Nov ’24