mirror of
https://github.com/xivdev/Penumbra.git
synced 2025-12-14 20:54:16 +01:00
async is a great idea lets do more of that
This commit is contained in:
parent
df43083101
commit
ed283afe2c
2 changed files with 81 additions and 28 deletions
|
|
@ -1,3 +1,4 @@
|
||||||
|
using OtterGui.Tasks;
|
||||||
using Penumbra.GameData.Files;
|
using Penumbra.GameData.Files;
|
||||||
using SharpGLTF.Geometry;
|
using SharpGLTF.Geometry;
|
||||||
using SharpGLTF.Geometry.VertexTypes;
|
using SharpGLTF.Geometry.VertexTypes;
|
||||||
|
|
@ -6,40 +7,89 @@ using SharpGLTF.Scenes;
|
||||||
|
|
||||||
namespace Penumbra.Import.Models;
|
namespace Penumbra.Import.Models;
|
||||||
|
|
||||||
public sealed class ModelManager
|
public sealed class ModelManager : SingleTaskQueue, IDisposable
|
||||||
{
|
{
|
||||||
|
private readonly ConcurrentDictionary<IAction, (Task, CancellationTokenSource)> _tasks = new();
|
||||||
|
private bool _disposed = false;
|
||||||
|
|
||||||
public ModelManager()
|
public ModelManager()
|
||||||
{
|
{
|
||||||
//
|
//
|
||||||
}
|
}
|
||||||
|
|
||||||
// TODO: Consider moving import/export onto an async queue, check ../textures/texturemanager
|
public void Dispose()
|
||||||
|
|
||||||
public void ExportToGltf(/* MdlFile mdl, */string path)
|
|
||||||
{
|
{
|
||||||
var mesh = new MeshBuilder<VertexPosition>("mesh");
|
_disposed = true;
|
||||||
|
foreach (var (_, cancel) in _tasks.Values.ToArray())
|
||||||
|
cancel.Cancel();
|
||||||
|
_tasks.Clear();
|
||||||
|
}
|
||||||
|
|
||||||
var material1 = new MaterialBuilder()
|
private Task Enqueue(IAction action)
|
||||||
.WithDoubleSide(true)
|
{
|
||||||
.WithMetallicRoughnessShader()
|
if (_disposed)
|
||||||
.WithChannelParam(KnownChannel.BaseColor, KnownProperty.RGBA, new Vector4(1, 0, 0, 1));
|
return Task.FromException(new ObjectDisposedException(nameof(ModelManager)));
|
||||||
var primitive1 = mesh.UsePrimitive(material1);
|
|
||||||
primitive1.AddTriangle(new VertexPosition(-10, 0, 0), new VertexPosition(10, 0, 0), new VertexPosition(0, 10, 0));
|
|
||||||
primitive1.AddTriangle(new VertexPosition(10, 0, 0), new VertexPosition(-10, 0, 0), new VertexPosition(0, -10, 0));
|
|
||||||
|
|
||||||
var material2 = new MaterialBuilder()
|
|
||||||
.WithDoubleSide(true)
|
|
||||||
.WithMetallicRoughnessShader()
|
|
||||||
.WithChannelParam(KnownChannel.BaseColor, KnownProperty.RGBA, new Vector4(1, 0, 1, 1));
|
|
||||||
var primitive2 = mesh.UsePrimitive(material2);
|
|
||||||
primitive2.AddQuadrangle(new VertexPosition(-5, 0, 3), new VertexPosition(0, -5, 3), new VertexPosition(5, 0, 3), new VertexPosition(0, 5, 3));
|
|
||||||
|
|
||||||
var scene = new SceneBuilder();
|
Task task;
|
||||||
scene.AddRigidMesh(mesh, Matrix4x4.Identity);
|
lock (_tasks)
|
||||||
|
{
|
||||||
|
task = _tasks.GetOrAdd(action, action =>
|
||||||
|
{
|
||||||
|
var token = new CancellationTokenSource();
|
||||||
|
var task = Enqueue(action, token.Token);
|
||||||
|
task.ContinueWith(_ => _tasks.TryRemove(action, out var unused), CancellationToken.None);
|
||||||
|
return (task, token);
|
||||||
|
}).Item1;
|
||||||
|
}
|
||||||
|
|
||||||
var model = scene.ToGltf2();
|
return task;
|
||||||
model.SaveGLTF(path);
|
}
|
||||||
|
|
||||||
// TODO: Draw the rest of the owl.
|
public Task ExportToGltf(/* MdlFile mdl, */string path)
|
||||||
|
=> Enqueue(new ExportToGltfAction(path));
|
||||||
|
|
||||||
|
private class ExportToGltfAction : IAction
|
||||||
|
{
|
||||||
|
private readonly string _path;
|
||||||
|
|
||||||
|
public ExportToGltfAction(string path)
|
||||||
|
{
|
||||||
|
_path = path;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void Execute(CancellationToken token)
|
||||||
|
{
|
||||||
|
var mesh = new MeshBuilder<VertexPosition>("mesh");
|
||||||
|
|
||||||
|
var material1 = new MaterialBuilder()
|
||||||
|
.WithDoubleSide(true)
|
||||||
|
.WithMetallicRoughnessShader()
|
||||||
|
.WithChannelParam(KnownChannel.BaseColor, KnownProperty.RGBA, new Vector4(1, 0, 0, 1));
|
||||||
|
var primitive1 = mesh.UsePrimitive(material1);
|
||||||
|
primitive1.AddTriangle(new VertexPosition(-10, 0, 0), new VertexPosition(10, 0, 0), new VertexPosition(0, 10, 0));
|
||||||
|
primitive1.AddTriangle(new VertexPosition(10, 0, 0), new VertexPosition(-10, 0, 0), new VertexPosition(0, -10, 0));
|
||||||
|
|
||||||
|
var material2 = new MaterialBuilder()
|
||||||
|
.WithDoubleSide(true)
|
||||||
|
.WithMetallicRoughnessShader()
|
||||||
|
.WithChannelParam(KnownChannel.BaseColor, KnownProperty.RGBA, new Vector4(1, 0, 1, 1));
|
||||||
|
var primitive2 = mesh.UsePrimitive(material2);
|
||||||
|
primitive2.AddQuadrangle(new VertexPosition(-5, 0, 3), new VertexPosition(0, -5, 3), new VertexPosition(5, 0, 3), new VertexPosition(0, 5, 3));
|
||||||
|
|
||||||
|
var scene = new SceneBuilder();
|
||||||
|
scene.AddRigidMesh(mesh, Matrix4x4.Identity);
|
||||||
|
|
||||||
|
var model = scene.ToGltf2();
|
||||||
|
model.SaveGLTF(_path);
|
||||||
|
}
|
||||||
|
|
||||||
|
public bool Equals(IAction? other)
|
||||||
|
{
|
||||||
|
if (other is not ExportToGltfAction rhs)
|
||||||
|
return false;
|
||||||
|
|
||||||
|
// TODO: compare configuration
|
||||||
|
return true;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -14,10 +14,11 @@ public partial class ModEditWindow
|
||||||
{
|
{
|
||||||
private const int MdlMaterialMaximum = 4;
|
private const int MdlMaterialMaximum = 4;
|
||||||
|
|
||||||
private readonly ModelManager _models;
|
|
||||||
|
|
||||||
private readonly FileEditor<MdlTab> _modelTab;
|
private readonly FileEditor<MdlTab> _modelTab;
|
||||||
|
|
||||||
|
private readonly ModelManager _models;
|
||||||
|
private bool _pendingIo = false;
|
||||||
|
|
||||||
private string _modelNewMaterial = string.Empty;
|
private string _modelNewMaterial = string.Empty;
|
||||||
private readonly List<TagButtons> _subMeshAttributeTagWidgets = [];
|
private readonly List<TagButtons> _subMeshAttributeTagWidgets = [];
|
||||||
|
|
||||||
|
|
@ -34,9 +35,11 @@ public partial class ModEditWindow
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (ImGui.Button("bingo bango"))
|
if (ImGuiUtil.DrawDisabledButton("bingo bango", Vector2.Zero, "description", _pendingIo))
|
||||||
{
|
{
|
||||||
_models.ExportToGltf("C:\\Users\\ackwell\\blender\\gltf-tests\\bingo.gltf");
|
_pendingIo = true;
|
||||||
|
var task = _models.ExportToGltf("C:\\Users\\ackwell\\blender\\gltf-tests\\bingo.gltf");
|
||||||
|
task.ContinueWith(_ => _pendingIo = false);
|
||||||
}
|
}
|
||||||
|
|
||||||
var ret = false;
|
var ret = false;
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue