macos - 在 SceneKit 中,如何在不同大小的对象上平铺纹理,同时保持最小的绘制调用?
问题描述
为了提高 SceneKit 场景中的性能/fps,我想尽量减少绘制调用的数量。该场景包含一个程序生成的城市,我为它生成随机高度的房屋(每个都是一个 SCNBox),并用一个相同的重复立面纹理平铺它们,如下所示:
应用纹理的正确方法如下所示:
let material = SCNMaterial()
material.diffuse.contents = image
material.diffuse.wrapS = SCNWrapMode.repeat
material.diffuse.wrapT = SCNWrapMode.repeat
buildingGeometry.firstMaterial = material
这行得通。但正如所写,它会拉伸材料以适应盒子表面的大小。要调整纹理大小以保持纵横比,需要添加以下代码:
material.diffuse.contentsTransform = SCNMatrix4MakeScale(sx, sy, sz)
其中sx
,sy
和sz
是从几何中的面大小得出的适当比例因子。这也有效。
但后一种方法意味着每个节点都需要自定义材质,这反过来意味着我不能为所有房屋重复使用单一材质,这反过来意味着每个节点都需要额外的绘制调用。
有没有办法使用单一纹理材料来平铺所有房屋(不拉伸纹理)?
解决方案
使用表面着色器修改器 ( SCNShaderModifierEntryPointSurface
),您可以_surface.diffuseTexcoord
根据scn_node.boundingBox
.
由于边界框是动态馈送到着色器的,所有对象都将使用相同的着色器,并将受益于实例化(减少绘制调用的数量)。
SCNShadable.h 头文件对此有更多详细信息。
推荐阅读
- r - 警告:错误:美学必须是长度 1 或与数据 (1) 相同:x、组和颜色
- r - 跨越 NA 值
- otrs - 如何访问 otrs 6 社区版网络服务以进行休息/肥皂电话?
- firebase - Firestore 索引合并是否有工作示例?
- javascript - 无法模拟承诺功能
- python - 我是 Python 和 Spyder 的新手。当我在控制台中输入“pip list”或任何其他命令时,它会返回错误
- ios - iOS 模拟器无法正确滚动(M1 + React Native 项目)
- c# - 如何使用逻辑运算符以及 C# 中的任何语句和数据类型重新创建此逻辑参数(三段论)
- kubernetes - 我使用 kubectl delete deployment coredns -n kube-system 删除了核心 dns
- c++ - 模运算没有返回正确的值