如何为在金属上加载了模型I / O框架的3D资产(.obj)文件设置动画

时间:2018-11-16 16:01:12

标签: swift 3d metal vertex-buffer metalkit

加载有模型I / O的obj文件。我从网格和子网格接收顶点缓冲区和索引缓冲区。我用索引缓冲区绘制它。在GPU缓冲区中解压缩并加载所有三角形。 加载资产时,我正在创建顶点描述符,以说应该从3D资产加载什么。当我将其传递给着色器时,我正在使用[[ stage_in ]]顶点参数。

但是我需要以某种方式更改在顶点着色器函数的参数中加载模型资产而创建的顶点的结构,以便为每个顶点传递更多具有动画偏移量的数据。例如,我需要传递3D资产中的数据,以将偏移量应用于所有顶点。

vertex VertexOut vertex_main(VertexIn vertexIn [[ stage_in ]], constant Uniforms &uniforms [[ buffer(1) ]], uint vertexID [[ vertex_id ]]) {
    float4 worldPosition = uniforms.modelMatrix *float4(vertexIn.position, 1);
    VertexOut vertexOut;
    vertexOut.position = uniforms.viewProjectionMatrix * worldPosition;
    vertexOut.worldPosition = worldPosition.xyz;
    vertexOut.worldNormal = uniforms.normalMatrix * vertexIn.normal;
    vertexOut.texCoords = vertexIn.texCoords;
    return vertexOut; 
}

VertexIn看起来如何

struct VertexIn {
    float3 position  [[attribute(0)]];
    float3 normal    [[attribute(1)]];
    float2 texCoords [[attribute(2)]];
};

绘制3D资产

for mesh in meshes {
        for i in 0..<mesh.vertexBuffers.count {
            let vertexBuffer = mesh.vertexBuffers[i]
            commandEncoder.setVertexBuffer(vertexBuffer.buffer, offset: vertexBuffer.offset, index: i)
        }

        for submesh in mesh.submeshes {
            let indexBuffer = submesh.indexBuffer
            commandEncoder.drawIndexedPrimitives(type: submesh.primitiveType,
                                                 indexCount: submesh.indexCount,
                                                 indexType: submesh.indexType,
                                                 indexBuffer: indexBuffer.buffer,
                                                 indexBufferOffset: indexBuffer.offset)
        }
}

用于加载3D模型资源的顶点描述符

    let vertexDescriptor = MDLVertexDescriptor()
    vertexDescriptor.attributes[0] = MDLVertexAttribute(name: MDLVertexAttributePosition, format: .float3, offset: 0, bufferIndex: 0)
    vertexDescriptor.attributes[1] = MDLVertexAttribute(name: MDLVertexAttributeNormal, format: .float3, offset: MemoryLayout<Float>.size * 3, bufferIndex: 0)
    vertexDescriptor.attributes[2] = MDLVertexAttribute(name: MDLVertexAttributeTextureCoordinate, format: .float2, offset: MemoryLayout<Float>.size * 6, bufferIndex: 0)

    vertexDescriptor.layouts[0] = MDLVertexBufferLayout(stride: MemoryLayout<Float>.size * 8)

感谢您的帮助。 附言 加载3d资产后,我试图进行更改,但是失败了,因为我无法更改使用模型I / O创建的顶点缓冲区。

0 个答案:

没有答案