Apply subobj hierarchy to model
This commit is contained in:
parent
202edd424b
commit
1177474fd6
|
@ -265,14 +265,12 @@ public partial class Mission : Node3D
|
|||
var meshDetails = Timing.TimeStage("Get Models", () => Context.Instance.ModelLoader.Load(modelName));
|
||||
if (meshDetails.Length != 0)
|
||||
{
|
||||
var model = new Node3D();
|
||||
var joints = jointPosProp != null ? jointPosProp.Positions : [0, 0, 0, 0, 0, 0];
|
||||
var model = ModelLoader.TransformMeshes(joints, meshDetails);
|
||||
model.Position = pos;
|
||||
model.RotationDegrees = rot;
|
||||
model.Scale = scale;
|
||||
|
||||
var joints = jointPosProp != null ? jointPosProp.Positions : [0, 0, 0, 0, 0, 0];
|
||||
var meshes = ModelLoader.TransformMeshes(joints, meshDetails);
|
||||
|
||||
bool GetTextReplPath(PropString prop, out string path)
|
||||
{
|
||||
path = "";
|
||||
|
@ -301,26 +299,29 @@ public partial class Mission : Node3D
|
|||
}
|
||||
|
||||
var repls = new PropString[] { txtRepl0, txtRepl1, txtRepl2, txtRepl3 };
|
||||
foreach (var meshInstance in meshes)
|
||||
foreach (var child in model.FindChildren("*", "MeshInstance3D", true, false))
|
||||
{
|
||||
var meshInstance = child as MeshInstance3D;
|
||||
for (var i = 0; i < 4; i++)
|
||||
{
|
||||
if (GetTextReplPath(repls[i], out var path))
|
||||
if (!GetTextReplPath(repls[i], out var path))
|
||||
{
|
||||
var overrideMat = new StandardMaterial3D
|
||||
{
|
||||
AlbedoTexture = TextureLoader.LoadTexture(path),
|
||||
Transparency = BaseMaterial3D.TransparencyEnum.AlphaDepthPrePass,
|
||||
};
|
||||
continue;
|
||||
}
|
||||
|
||||
var overrideMat = new StandardMaterial3D
|
||||
{
|
||||
AlbedoTexture = TextureLoader.LoadTexture(path),
|
||||
Transparency = BaseMaterial3D.TransparencyEnum.AlphaDepthPrePass,
|
||||
};
|
||||
|
||||
var surfaceCount = meshInstance.Mesh.GetSurfaceCount();
|
||||
for (var idx = 0; idx < surfaceCount; idx++)
|
||||
var surfaceCount = meshInstance.Mesh.GetSurfaceCount();
|
||||
for (var idx = 0; idx < surfaceCount; idx++)
|
||||
{
|
||||
var surfaceMat = meshInstance.Mesh.SurfaceGetMaterial(idx);
|
||||
if (surfaceMat.HasMeta($"TxtRepl{i}"))
|
||||
{
|
||||
var surfaceMat = meshInstance.Mesh.SurfaceGetMaterial(idx);
|
||||
if (surfaceMat.HasMeta($"TxtRepl{i}"))
|
||||
{
|
||||
meshInstance.SetSurfaceOverrideMaterial(idx, overrideMat);
|
||||
}
|
||||
meshInstance.SetSurfaceOverrideMaterial(idx, overrideMat);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -329,8 +330,6 @@ public partial class Mission : Node3D
|
|||
{
|
||||
meshInstance.Transparency = 1.0f - renderAlpha.value;
|
||||
}
|
||||
|
||||
model.AddChild(meshInstance);
|
||||
}
|
||||
|
||||
model.AddToGroup(OBJECT_MODELS_GROUP);
|
||||
|
|
|
@ -19,13 +19,8 @@ public partial class Model : Node3D
|
|||
}
|
||||
|
||||
Context.Instance.SetCampaign(campaignName);
|
||||
var model = new Node3D();
|
||||
var meshDetails = Context.Instance.ModelLoader.Load(modelPath);
|
||||
var meshes = ModelLoader.TransformMeshes([0, 0, 0, 0, 0, 0], meshDetails);
|
||||
foreach (var meshInstance in meshes)
|
||||
{
|
||||
model.AddChild(meshInstance);
|
||||
}
|
||||
var model = ModelLoader.TransformMeshes([0, 0, 0, 0, 0, 0], meshDetails);
|
||||
AddChild(model);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -8,11 +8,12 @@ namespace KeepersCompound.TMV;
|
|||
// TODO: Work out a way to share base game models again in the cache
|
||||
public class ModelLoader
|
||||
{
|
||||
public struct MeshDetails(int jointIdx, Transform3D transform, MeshInstance3D mesh)
|
||||
public struct MeshDetails(int jointIdx, Transform3D transform, MeshInstance3D mesh, int parentIdx)
|
||||
{
|
||||
public readonly int JointIdx = jointIdx;
|
||||
public readonly Transform3D Transform = transform;
|
||||
public readonly MeshInstance3D Mesh = mesh;
|
||||
public int ParentIdx = parentIdx;
|
||||
}
|
||||
|
||||
private readonly Dictionary<(string, string), MeshDetails[]> _cache = new();
|
||||
|
@ -40,15 +41,20 @@ public class ModelLoader
|
|||
return details;
|
||||
}
|
||||
|
||||
public static MeshInstance3D[] TransformMeshes(float[] joints, MeshDetails[] meshDetails)
|
||||
public static Node3D TransformMeshes(float[] joints, MeshDetails[] meshDetails)
|
||||
{
|
||||
for (var i = 0; i < joints.Length; i++)
|
||||
{
|
||||
joints[i] = float.DegreesToRadians(joints[i]);
|
||||
}
|
||||
|
||||
var meshes = new List<MeshInstance3D>();
|
||||
foreach (var details in meshDetails)
|
||||
{
|
||||
var mesh = details.Mesh.Duplicate() as MeshInstance3D;
|
||||
if (details.JointIdx != -1)
|
||||
{
|
||||
var ang = float.DegreesToRadians(joints[details.JointIdx]);
|
||||
var ang = joints[details.JointIdx];
|
||||
var r1 = new Quaternion(new Vector3(0, 0, 1), ang);
|
||||
var r2 = details.Transform.Basis.GetRotationQuaternion();
|
||||
var basis = new Basis(r2 * r1);
|
||||
|
@ -61,8 +67,23 @@ public class ModelLoader
|
|||
|
||||
meshes.Add(mesh);
|
||||
}
|
||||
|
||||
var root = new Node3D();
|
||||
for (var i = 0; i < meshes.Count; i++)
|
||||
{
|
||||
var details = meshDetails[i];
|
||||
var parentId = details.ParentIdx;
|
||||
if (parentId == -1)
|
||||
{
|
||||
root.AddChild(meshes[i]);
|
||||
}
|
||||
else
|
||||
{
|
||||
meshes[parentId].AddChild(meshes[i]);
|
||||
}
|
||||
}
|
||||
|
||||
return [..meshes];
|
||||
return root;
|
||||
}
|
||||
|
||||
public static MeshDetails[] LoadModel(string modelName)
|
||||
|
@ -186,7 +207,19 @@ public class ModelLoader
|
|||
|
||||
var pos = -modelFile.Header.Center.ToGodotVec3();
|
||||
var meshInstance = new MeshInstance3D { Mesh = mesh, Position = pos };
|
||||
meshDetails[i] = new MeshDetails(jointIdx, transform, meshInstance);
|
||||
meshDetails[i] = new MeshDetails(jointIdx, transform, meshInstance, -1);
|
||||
}
|
||||
|
||||
// Build parentage
|
||||
for (var i = 0; i < objCount; i++)
|
||||
{
|
||||
var subObj = modelFile.Objects[i];
|
||||
var childIdx = subObj.Child;
|
||||
while (childIdx != -1)
|
||||
{
|
||||
meshDetails[childIdx].ParentIdx = i;
|
||||
childIdx = modelFile.Objects[childIdx].Next;
|
||||
}
|
||||
}
|
||||
|
||||
return meshDetails;
|
||||
|
|
Loading…
Reference in New Issue