morph tangent + cull facing

This commit is contained in:
4sval 2023-01-02 20:36:38 +01:00
parent 76a9f88eee
commit 174401ec42
11 changed files with 61 additions and 16 deletions

@ -1 +1 @@
Subproject commit 59b004c355647a22c0ad7945443d0de509ecdaf1
Subproject commit db65a8e98518cfaef7fa935b28a8f83e9a2f39d0

View File

@ -9,7 +9,8 @@ layout (location = 6) in vec4 vColor;
layout (location = 7) in vec4 vBoneIds;
layout (location = 8) in vec4 vBoneWeights;
layout (location = 9) in mat4 vInstanceMatrix;
layout (location = 13) in vec3 vMorphTarget;
layout (location = 13) in vec3 vMorphTargetPos;
layout (location = 14) in vec3 vMorphTargetTangent;
//const int MAX_BONES = 0;
//const int MAX_BONE_INFLUENCE = 0;
@ -28,7 +29,8 @@ out vec4 fColor;
void main()
{
vec4 pos = vec4(mix(vPos, vMorphTarget, uMorphTime), 1.0);
vec4 pos = vec4(mix(vPos, vMorphTargetPos, uMorphTime), 1.0);
vec3 tangent = mix(vTangent, vMorphTargetTangent, uMorphTime);
// for(int i = 0 ; i < MAX_BONE_INFLUENCE; i++)
// {
// if(vBoneIds[i] == -1) continue;
@ -45,7 +47,7 @@ void main()
fPos = vec3(vInstanceMatrix * pos);
fNormal = mat3(transpose(inverse(vInstanceMatrix))) * vNormal;
fTangent = mat3(transpose(inverse(vInstanceMatrix))) * vTangent;
fTangent = mat3(transpose(inverse(vInstanceMatrix))) * tangent;
fTexCoords = vTexCoords;
fTexLayer = vTexLayer;
fColor = vColor;

View File

@ -43,6 +43,7 @@ public class Grid : IDisposable
public void Render(Matrix4x4 viewMatrix, Matrix4x4 projMatrix, float near, float far)
{
GL.Disable(EnableCap.CullFace);
GL.Disable(EnableCap.DepthTest);
_vao.Bind();
@ -55,6 +56,7 @@ public class Grid : IDisposable
GL.DrawArrays(PrimitiveType.Triangles, 0, Indices.Length);
GL.Enable(EnableCap.DepthTest);
GL.Enable(EnableCap.CullFace);
}
public void Dispose()

View File

@ -47,6 +47,7 @@ public class Model : IDisposable
public float[] Vertices;
public Section[] Sections;
public Material[] Materials;
public bool bMirrored;
public bool HasSkeleton => Skeleton is { IsLoaded: true };
public readonly Skeleton Skeleton;
@ -106,6 +107,7 @@ public class Model : IDisposable
{
var hasCustomUvs = lod.ExtraUV.IsValueCreated;
UvCount = hasCustomUvs ? Math.Max(lod.NumTexCoords, numLods) : lod.NumTexCoords;
bMirrored = lod.IsMirrored;
Materials = new Material[materials.Length];
for (int m = 0; m < Materials.Length; m++)
@ -252,7 +254,8 @@ public class Model : IDisposable
_morphVbo = new BufferObject<float>(Morphs[morph].Vertices, BufferTarget.ArrayBuffer);
}
_vao.Bind();
_vao.VertexAttributePointer(13, 3, VertexAttribPointerType.Float, 3, 0); // morph position
_vao.VertexAttributePointer(13, 3, VertexAttribPointerType.Float, Morph.VertexSize, 0); // morph position
_vao.VertexAttributePointer(14, 3, VertexAttribPointerType.Float, Morph.VertexSize, 0); // morph tangent
_vao.Unbind();
}
@ -267,6 +270,7 @@ public class Model : IDisposable
public void Render(Shader shader)
{
if (bMirrored) GL.Disable(EnableCap.CullFace);
if (IsSelected)
{
GL.Enable(EnableCap.StencilTest);
@ -292,6 +296,7 @@ public class Model : IDisposable
GL.StencilFunc(StencilFunction.Always, 0, 0xFF);
GL.Disable(EnableCap.StencilTest);
}
if (bMirrored) GL.Enable(EnableCap.CullFace);
}
public void SimpleRender(Shader shader)

View File

@ -9,7 +9,7 @@ public class Morph : IDisposable
{
private int _handle;
private readonly int _vertexSize = 3; // Position
public static readonly int VertexSize = 6; // Position + Tangent
public readonly string Name;
public readonly float[] Vertices;
@ -17,37 +17,45 @@ public class Morph : IDisposable
public Morph(float[] vertices, int vertexSize, UMorphTarget morphTarget)
{
Name = morphTarget.Name;
Vertices = new float[vertices.Length / vertexSize * _vertexSize];
Vertices = new float[vertices.Length / vertexSize * VertexSize];
bool TryFindVertex(uint index, out FVector positionDelta)
bool TryFindVertex(uint index, out FVector positionDelta, out FVector tangentDelta)
{
foreach (var vertex in morphTarget.MorphLODModels[0].Vertices)
{
if (vertex.SourceIdx == index)
{
positionDelta = vertex.PositionDelta;
tangentDelta = vertex.TangentZDelta;
return true;
}
}
positionDelta = FVector.ZeroVector;
tangentDelta = FVector.ZeroVector;
return false;
}
for (int i = 0; i < vertices.Length; i += vertexSize)
{
var count = 0;
var baseIndex = i / vertexSize * _vertexSize;
if (TryFindVertex((uint) vertices[i + 0], out var positionDelta))
var baseIndex = i / vertexSize * VertexSize;
if (TryFindVertex((uint) vertices[i + 0], out var positionDelta, out var tangentDelta))
{
Vertices[baseIndex + count++] = vertices[i + 1] + positionDelta.X * Constants.SCALE_DOWN_RATIO;
Vertices[baseIndex + count++] = vertices[i + 2] + positionDelta.Z * Constants.SCALE_DOWN_RATIO;
Vertices[baseIndex + count++] = vertices[i + 3] + positionDelta.Y * Constants.SCALE_DOWN_RATIO;
Vertices[baseIndex + count++] = vertices[i + 7] + tangentDelta.X * Constants.SCALE_DOWN_RATIO;
Vertices[baseIndex + count++] = vertices[i + 8] + tangentDelta.Z * Constants.SCALE_DOWN_RATIO;
Vertices[baseIndex + count++] = vertices[i + 9] + tangentDelta.Y * Constants.SCALE_DOWN_RATIO;
}
else
{
Vertices[baseIndex + count++] = vertices[i + 1];
Vertices[baseIndex + count++] = vertices[i + 2];
Vertices[baseIndex + count++] = vertices[i + 3];
Vertices[baseIndex + count++] = vertices[i + 7];
Vertices[baseIndex + count++] = vertices[i + 8];
Vertices[baseIndex + count++] = vertices[i + 9];
}
}
}

View File

@ -27,7 +27,7 @@ public class Section : IDisposable
public Section(int index, int facesCount, int firstFaceIndex, Material material) : this(index, facesCount, firstFaceIndex)
{
material.IsUsed = true;
Show = !material.Parameters.IsNull && !material.Parameters.IsTransparent;
Show = !material.Parameters.IsNull && !material.Parameters.IsTranslucent;
}
public void Setup()

View File

@ -83,6 +83,7 @@ public class Skybox : IDisposable
public void Render(Matrix4x4 viewMatrix, Matrix4x4 projMatrix)
{
GL.Disable(EnableCap.CullFace);
GL.DepthFunc(DepthFunction.Lequal);
_vao.Bind();
@ -101,6 +102,7 @@ public class Skybox : IDisposable
GL.DrawArrays(PrimitiveType.Triangles, 0, 36);
GL.DepthFunc(DepthFunction.Less);
GL.Enable(EnableCap.CullFace);
}
public void Dispose()

View File

@ -285,6 +285,7 @@ public class Renderer : IDisposable
else if (m.TryConvert(out var mesh))
{
model = new Model(m, mesh, t);
model.bMirrored = actor.GetOrDefault("bMirrored", model.bMirrored);
if (actor.TryGetValue(out FPackageIndex baseMaterial, "BaseMaterial") &&
actor.TryGetAllValues(out FPackageIndex[] textureData, "TextureData"))
{

View File

@ -6,6 +6,7 @@ using CUE4Parse.UE4.Assets.Exports.Material;
using CUE4Parse.UE4.Assets.Exports.Texture;
using CUE4Parse.UE4.Objects.Core.Math;
using CUE4Parse.UE4.Objects.Core.Misc;
using FModel.Extensions;
using FModel.Views.Snooper.Models;
using ImGuiNET;
using OpenTK.Graphics.OpenGL4;
@ -265,17 +266,23 @@ public class Material : IDisposable
}
}
public void ImGuiBaseProperties(string id)
{
if (ImGui.BeginTable(id, 2, ImGuiTableFlags.SizingStretchProp))
{
Layout("Blend", Parameters.BlendMode.GetDescription(), true, true);
Layout("Shading", Parameters.ShadingModel.GetDescription(), true, true);
ImGui.EndTable();
}
}
public void ImGuiDictionaries<T>(string id, Dictionary<string, T> dictionary, bool center = false, bool wrap = false)
{
if (ImGui.BeginTable(id, 2))
{
foreach ((string key, T value) in dictionary.Reverse())
{
SnimGui.Layout(key, true);
var text = $"{value:N}";
if (center) ImGui.SetCursorPosX(ImGui.GetCursorPosX() + (ImGui.GetColumnWidth() - ImGui.CalcTextSize(text).X) / 2);
if (wrap) ImGui.TextWrapped(text); else ImGui.Text(text);
SnimGui.TooltipCopy(text);
Layout(key, value, center, wrap);
}
ImGui.EndTable();
}
@ -363,6 +370,15 @@ public class Material : IDisposable
};
}
private void Layout<T>(string key, T value, bool center = false, bool wrap = false)
{
SnimGui.Layout(key, true);
var text = $"{value:N}";
if (center) ImGui.SetCursorPosX(ImGui.GetCursorPosX() + (ImGui.GetColumnWidth() - ImGui.CalcTextSize(text).X) / 2);
if (wrap) ImGui.TextWrapped(text); else ImGui.Text(text);
SnimGui.TooltipCopy(text);
}
public void Dispose()
{
for (int i = 0; i < Diffuse.Length; i++)

View File

@ -430,6 +430,7 @@ Snooper aims to give an accurate preview of models, materials, skeletal animatio
{
Layout("Entity");ImGui.Text($" : ({model.Type}) {model.Name}");
Layout("Guid");ImGui.Text($" : {s.Renderer.Options.SelectedModel.ToString(EGuidFormats.UniqueObjectGuid)}");
Layout("Mirrored");ImGui.Text($" : {model.bMirrored}");
if (model.HasSkeleton)
{
Layout("Skeleton");ImGui.Text($" : {model.Skeleton.RefSkel.Name}");
@ -591,6 +592,13 @@ Snooper aims to give an accurate preview of models, materials, skeletal animatio
ImGui.SetNextItemOpen(true, ImGuiCond.Appearing);
if (ImGui.CollapsingHeader("Properties"))
{
ImGui.SetNextItemOpen(true, ImGuiCond.Appearing);
if (ImGui.TreeNode("Base"))
{
material.ImGuiBaseProperties("base");
ImGui.TreePop();
}
ImGui.SetNextItemOpen(true, ImGuiCond.Appearing);
if (ImGui.TreeNode("Scalars"))
{

View File

@ -99,6 +99,7 @@ public class Snooper : GameWindow
GL.ClearColor(OpenTK.Mathematics.Color4.Black);
GL.Enable(EnableCap.Blend);
GL.Enable(EnableCap.CullFace);
GL.Enable(EnableCap.DepthTest);
GL.Enable(EnableCap.Multisample);
GL.StencilOp(StencilOp.Keep, StencilOp.Replace, StencilOp.Replace);