我们正在尝试在服务器端合并多个gltf,并将合并后的gltf作为最终结果导出到服务器上。
我们所做的那些行之有效但没有奏效的事情:
-
我们使用了三个js GLTFLoader解析方法来加载多个gltf文件,合并加载对象的父对象和子对象,并使用GLTFExporter导出最终模型。
-
我们已经使用jsdom来解决与窗口、文档等相关的问题。
-
上面提到的点适用于没有纹理的gltfs
-
在加载带有纹理的GLTF时,响应被卡住。
a( 我们尝试在服务器上托管文件,并使用GLTFLoader加载方法;localhost:******"作为加载器路径。
b( 内部TextureLoader调用ImageLoader,而onLoad事件根本没有被触发。可能是jsdom没有调用这个。
c( 为了解决这个问题,我们将ImageLoader更改为具有画布图像:
const { Image } = require("canvas");
const image = new Image();
image.onload = onImageLoad;
image.onerror = onImageError;
d( 经过上述修改,荷载法得到了解决。
e( 下一步-导出GLTF-由于找不到ImageData错误,我们陷入了困境。我们从画布中添加了ImageData,并导出了GLTF。
f( 导出的GLTF无法查看,因为图像中的数据已损坏
"images": [
{
"mimeType": "image/png",
"uri": "data:,"
}
],
如果有人纯粹在服务器端加载并合并了带有纹理图像的GLTfs,请帮助!
由于three.js主要是一个用于web的3D渲染库,并且依赖于各种web图像和WebGL API,我不确定是否使用three。GLTFLoader是在Node.js服务器上合并glTF文件的最有效方法。我建议这样做:
import { Document, NodeIO } from '@gltf-transform/core';
import { KHRONOS_EXTENSIONS } from '@gltf-transform/extensions';
const io = new NodeIO().registerExtensions(KHRONOS_EXTENSIONS);
const document = new Document();
const root = document.getRoot();
// Merge all files.
for (const path of filePaths) {
document.merge(io.read(path));
}
// (Optional) Consolidate buffers.
const buffer = root.listBuffers()[0];
root.listAccessors().forEach((a) => a.setBuffer(buffer));
root.listBuffers().forEach((b, index) => index > 0 ? b.dispose() : null);
io.write('./output.glb', document);
值得注意的是,这个过程将产生一个包含多个独立场景的glTF文件。如果你想将它们组合成一个单独的场景,以某种方式排列,你需要使用场景API来做到这一点。如果文件不在磁盘上,则有其他NodeIO API用于处理内存中的二进制或JSON文件。