
在运行时,我需要修改纹理坐标。使用变换不是一个选项 – 我需要为网格中的每个顶点计算一个不同的,全新的UV。
我知道几何在SceneKit中是不可变的,我已经读过,建议的方法是手动复制一个副本。我试图这样做,但我总是最终崩溃时试图重新创建SCNSkinner在代码中。崩溃是在C3DSourceAccessorGetMutableValuePtrAtIndex内的EXC_BAD_ACCESS。不幸的是,没有这个源代码,所以我不知道为什么它崩溃。我将它缩小到连接到网格节点的SCNSkinner对象。如果我不设置,我不会崩溃,事情似乎工作。
编辑:这里是一个更完整的调用堆栈的崩溃:
C3DSourceAccessorGetMutableValuePtrAtIndexC3DSkinPrepareMeshForGPUIfNeededC3DSkinnerMakeCurrentMeshC3DSkinnerUpdateCurrentMesh__CFSetApplyFunction_block_invokeCFBasicHashApplyCFSetApplyFunctionC3DAppleEngineRenderScene...
我没有找到任何关于如何手动创建SCNSkinner对象的文档或示例代码。因为我只是基于一个以前工作的网格创建它,它不应该太难。我根据Swift文档创建SCNSkinner,将所有正确的东西传递到init。但是,在SCNSkinner中有一个框架属性,我不知道如何设置。我把它设置到我复制的网格的原始SCNSkinner上的骨架,我认为
应该工作…但它不。设置框架属性时,它似乎未分配。在分配之后立即检查它是否仍然为零。作为一个测试,我试图将原始网格的骨架属性设置为别的东西,并且在分配之后,它也保持不变。
任何人都可以知道发生了什么?或者如何手动正确创建和设置SCNSkinner对象?
这里是我使用的代码手动克隆一个网格,并用一个新的替换(我没有修改任何源数据在这里 – 我只是想确保我可以在这一点上创建一个副本) :
// This is at the start of the app,just so you can see how the scene is set up.// I add the .dae contents into its own node in the scene. This seems to be the// standard way to put multiple .dae models into the same scene. This doesn't seem to// have any impact on the problem I'm having -- I've trIEd without this indirection// and the same problem exists.let scene = SCNScene()let modelNode = SCNNode()modelNode.name = "ModelNode"scene.rootNode.addChildNode(modelNode)let modelScene = SCNScene(named: "model.dae")if modelScene != nil { if let childNodes = modelScene?.rootNode.childNodes { for childNode in childNodes { modelNode.addChildNode(childNode as SCNNode) } }}// This happens later in the app after a tap from the user.let modelNode = scnVIEw.scene!.rootNode.childNodeWithname("ModelNode",recursively: true)let modelMesh = modelNode?.childNodeWithname("Meshname",recursively: true)let verts = modelMesh?.geometry!.geometrySourcesForSemantic(SCNGeometrySourceSemanticVertex)let normals = modelMesh?.geometry!.geometrySourcesForSemantic(SCNGeometrySourceSemanticnormal)let texcoords = modelMesh?.geometry!.geometrySourcesForSemantic(SCNGeometrySourceSemanticTexcoord)let boneWeights = modelMesh?.geometry!.geometrySourcesForSemantic(SCNGeometrySourceSemanticBoneWeights)let boneIndices = modelMesh?.geometry!.geometrySourcesForSemantic(SCNGeometrySourceSemanticBoneIndices)let geometry = modelMesh?.geometry!.geometryElementAtIndex(0)// Note: the vertex and normal data is shared.let vertsData = NSData(data: verts![0].data)let texcoordsData = NSData(data: texcoords![0].data)let boneWeightsData = NSData(data: boneWeights![0].data)let boneIndicesData = NSData(data: boneIndices![0].data)let geometryData = NSData(data: geometry!.data!)let newVerts = SCNGeometrySource(data: vertsData,semantic: SCNGeometrySourceSemanticVertex,vectorCount: verts![0].vectorCount,floatComponents: verts![0].floatComponents,componentsPerVector: verts![0].componentsPerVector,bytesPerComponent: verts![0].bytesPerComponent,dataOffset: verts![0].dataOffset,dataStrIDe: verts![0].dataStrIDe)let newnormals = SCNGeometrySource(data: vertsData,semantic: SCNGeometrySourceSemanticnormal,vectorCount: normals![0].vectorCount,floatComponents: normals![0].floatComponents,componentsPerVector: normals![0].componentsPerVector,bytesPerComponent: normals![0].bytesPerComponent,dataOffset: normals![0].dataOffset,dataStrIDe: normals![0].dataStrIDe)let newTexcoords = SCNGeometrySource(data: texcoordsData,semantic: SCNGeometrySourceSemanticTexcoord,vectorCount: texcoords![0].vectorCount,floatComponents: texcoords![0].floatComponents,componentsPerVector: texcoords![0].componentsPerVector,bytesPerComponent: texcoords![0].bytesPerComponent,dataOffset: texcoords![0].dataOffset,dataStrIDe: texcoords![0].dataStrIDe)let newBoneWeights = SCNGeometrySource(data: boneWeightsData,semantic: SCNGeometrySourceSemanticBoneWeights,vectorCount: boneWeights![0].vectorCount,floatComponents: boneWeights![0].floatComponents,componentsPerVector: boneWeights![0].componentsPerVector,bytesPerComponent: boneWeights![0].bytesPerComponent,dataOffset: boneWeights![0].dataOffset,dataStrIDe: boneWeights![0].dataStrIDe)let newBoneIndices = SCNGeometrySource(data: boneIndicesData,semantic: SCNGeometrySourceSemanticBoneIndices,vectorCount: boneIndices![0].vectorCount,floatComponents: boneIndices![0].floatComponents,componentsPerVector: boneIndices![0].componentsPerVector,bytesPerComponent: boneIndices![0].bytesPerComponent,dataOffset: boneIndices![0].dataOffset,dataStrIDe: boneIndices![0].dataStrIDe)let newGeometry = SCNGeometryElement(data: geometryData,primitiveType: geometry!.primitiveType,primitiveCount: geometry!.primitiveCount,bytesPerIndex: geometry!.bytesPerIndex)let newMeshGeometry = SCNGeometry(sources: [newVerts,newnormals,newTexcoords,newBoneWeights,newBoneIndices],elements: [newGeometry])newMeshGeometry.firstMaterial = modelMesh?.geometry!.firstMateriallet newModelMesh = SCNNode(geometry: newMeshGeometry)let bones = modelMesh?.skinner?.boneslet boneInverseBindtransforms = modelMesh?.skinner?.boneInverseBindtransformslet skeleton = modelMesh!.skinner!.skeleton!let baseGeometryBindtransform = modelMesh!.skinner!.baseGeometryBindtransformnewModelMesh.skinner = SCNSkinner(baseGeometry: newMeshGeometry,bones: bones,boneInverseBindtransforms: boneInverseBindtransforms,boneWeights: newBoneWeights,boneIndices: newBoneIndices)newModelMesh.skinner?.baseGeometryBindtransform = baseGeometryBindtransform// Before this assignment,newModelMesh.skinner?.skeleton is nil.newModelMesh.skinner?.skeleton = skeleton// After,it is still nil... however,skeleton itself is completely valID.modelMesh?.removeFromparentNode()newModelMesh.name = "Meshname"let meshparentNode = modelNode?.childNodeWithname("MeshparentNode",recursively: true)meshparentNode?.addChildNode(newModelMesh) 这三种方法可以帮助您找到解决方案: >
SCNNode *hero = [SCNScene scenenamed:@"Hero"].rootNode;SCNNode *hat = [SCNScene scenenamed:@"FancyFedora"].rootNode;hat.skinner.skeleton = hero.skinner.skeleton;
>
[Export ("initWithFrame:")]public UIVIEw (System.Drawing.RectangleF frame) : base (NSObjectFlag.Empty){// Invoke the init method Now. var initWithFrame = new Selector ("initWithFrame:").Handle; if (IsDirectBinding) Handle = ObjCRuntime.Messaging.IntPtr_objc_msgSend_RectangleF (this.Handle,initWithFrame,frame); else Handle = ObjCRuntime.Messaging.IntPtr_objc_msgSendSuper_RectangleF (this.SuperHandle,frame);} >参见this link。
总结以上是内存溢出为你收集整理的swift – 如何在代码中创建一个SceneKit SCNSkinner对象?全部内容,希望文章能够帮你解决swift – 如何在代码中创建一个SceneKit SCNSkinner对象?所遇到的程序开发问题。
如果觉得内存溢出网站内容还不错,欢迎将内存溢出网站推荐给程序员好友。
欢迎分享,转载请注明来源:内存溢出
微信扫一扫
支付宝扫一扫
评论列表(0条)