// This does once-per-light work, as well as once-per-material-per-light work. // So this ends up being called multiple times with the same parameters, except // for matObjName. // matObjName is the name of the material being exported // lightObjectName is the name of the light public void ExportLight(LightPayload payload, IExportableMaterial exportableMaterial) { ObjectName lightNodeName = new ObjectName(payload.legacyUniqueName); // does need to be unique // Add the light to the scene -- this does _not_ need to be done per-material. // As a result, the node will generally have already been created. GlTF_Node node = GlTF_Node.GetOrCreate(G, lightNodeName, payload.xform, null, out _); node.lightNameThatDoesNothing = payload.name; // The names of the uniforms can be anything, really. Named after the light is the most // logical choice, but note that nobody checks that two lights don't have the same name. // Thankfully for Tilt Brush, they don't. // This should probably have used a guaranteed-unique name from the start but I don't want // to change it now because it'd break my diffs and be kind of ugly. string lightUniformPrefix = payload.name; AddUniform(exportableMaterial, lightUniformPrefix + "_matrix", GlTF_Technique.Type.FLOAT_MAT4, GlTF_Technique.Semantic.MODELVIEW, node); // Add light color. GlTF_Material mtl = G.materials[exportableMaterial]; var val = new GlTF_Material.ColorKV { key = lightUniformPrefix + "_color", color = payload.lightColor }; mtl.values.Add(val); AddUniform(exportableMaterial, val.key, GlTF_Technique.Type.FLOAT_VEC4, GlTF_Technique.Semantic.UNKNOWN, node); }
// Returns a GlTF_Node; null means "there is no node for this group". public GlTF_Node GetGroupNode(uint groupId) { GlTF_Globals G = m_exporter.G; if (!G.Gltf2 || groupId == 0) { // When exporting for Poly be maximally compatible and don't create interior nodes return(null); } ObjectName name = new ObjectName($"group_{groupId}"); return(GlTF_Node.GetOrCreate(G, name, Matrix4x4.identity, null, out _)); }
// Doesn't do material export; for that see ExportMeshPayload private GlTF_Node ExportMeshPayload_NoMaterial( BaseMeshPayload mesh, [CanBeNull] GlTF_Node parent, Matrix4x4?localXf = null) { ObjectName meshNameAndId = new ObjectName(mesh.legacyUniqueName); GeometryPool pool = mesh.geometry; Matrix4x4 xf = localXf ?? mesh.xform; // Create a Node and (usually) a Mesh, both named after meshNameAndId. // This is safe because the namespaces for Node and Mesh are distinct. // If we have already seen the GeometryPool, the Mesh will be reused. // In this (less common) case, the Node and Mesh will have different names. // We don't actually ever use the "VERTEXID" attribute, even in gltf1. // It's time to cut it away. // Also, in gltf2, it needs to be called _VERTEXID anyway since it's a custom attribute GlTF_VertexLayout gltfLayout = new GlTF_VertexLayout(G, pool.Layout); int numTris = pool.NumTriIndices / 3; if (numTris < 1) { return(null); } NumTris += numTris; GlTF_Mesh gltfMesh; // Share meshes for any repeated geometry pool. if (!m_meshCache.TryGetValue(pool, out gltfMesh)) { gltfMesh = new GlTF_Mesh(G); gltfMesh.name = GlTF_Mesh.GetNameFromObject(meshNameAndId); gltfMesh.PresentationNameOverride = mesh.geometryName; m_meshCache.Add(pool, gltfMesh); // Populate mesh data only once. AddMeshDependencies(meshNameAndId, mesh.exportableMaterial, gltfMesh, gltfLayout); gltfMesh.Populate(pool); G.meshes.Add(gltfMesh); } // The mesh may or may not be shared, but every mesh will have a distinct node to allow them // to have unique transforms. GlTF_Node node = GlTF_Node.GetOrCreate(G, meshNameAndId, xf, parent, out _); node.m_mesh = gltfMesh; node.PresentationNameOverride = mesh.nodeName; return(node); }