map3drendering/LandblockExtraction/AtlasMaker/TerrainAtlasManager.cs
2024-03-01 21:56:18 +01:00

105 lines
4.5 KiB
C#

using AC2RE.Definitions;
using ImageMagick;
using LandblockExtraction.DatEngine;
using LandblockExtraction.Tools;
using System.Numerics;
namespace LandblockExtraction.AtlasMaker;
public class TerrainAtlasManager {
private PortalEngine portalEngine;
private Dictionary<int, DataId> mapTerrain;
public Dictionary<int, Vector2> textureCoord;
public Dictionary<int, MagickImage> terrainTexture;
public Dictionary<int, Terrain> terrains;
public TerrainAtlasManager(PortalEngine portalEngine) {
this.portalEngine = portalEngine;
mapTerrain = new();
textureCoord = new Dictionary<int, Vector2>();
terrainTexture = new Dictionary<int, MagickImage>();
terrains = new Dictionary<int, Terrain>();
InitialiseTerrainDic();
GenerateTerrain();
}
public void ExtractTexture() {
using (var atlasBuilder = new AtlasBuilder(portalEngine)) {
foreach (var terrain in portalEngine.cTerrainDesc.terrains) {
foreach (var surface in portalEngine.cSurfaceDesc.surfaces) {
if (surface.surfIndex == terrain.surfaceInfo) {
atlasBuilder.AddTexture((int)terrain.terrainIndex, surface.terrainMaterials.First().baseMaterials.First().materialDid);
//terrains.Add((int)terrain.terrainIndex, GenerateSubTerrain((int)terrain.terrainIndex, surface.terrainMaterials));
}
}
textureCoord.Add((int)terrain.terrainIndex, Vector2.Zero);
}
atlasBuilder.GenerateAtlas();
foreach (var img in atlasBuilder.textures) {
terrainTexture.Add(img.Key, img.Value);
}
}
}
private void GenerateTerrain() {
foreach(var terrain in portalEngine.cTerrainDesc.terrains) {
Terrain tmpTer = new((int)terrain.terrainIndex);
foreach(var surface in portalEngine.cSurfaceDesc.surfaces) {
if(terrain.surfaceInfo == surface.surfIndex) {
foreach(var mat in surface.terrainMaterials) {
tmpTer.subTerrains.Add(new(GetIndex(mat.baseMaterials.First().materialDid),
mat.minPitch,
mat.maxPitch,
MathOperations.RGBAColorToVector4(mat.vertexColor.First().vertexColor),
MathOperations.RGBAColorToVector4(mat.vertexColor.First().farVertexColor)));
}
}
}
terrains.Add((int)terrain.terrainIndex, tmpTer);
Console.WriteLine("Init: " + terrain.terrainIndex);
}
}
private void testGenerateList() {
foreach (var terrain in portalEngine.cTerrainDesc.terrains) {
foreach (var surfaces in portalEngine.cSurfaceDesc.surfaces) {
if (surfaces.surfIndex != terrain.surfaceInfo) continue;
foreach (var surface in surfaces.terrainMaterials) {
uint test = 0;
//foreach(var m in map) { if (m.Key == surface.baseMaterials.First().materialDid) test = m.Value; }
Console.Write($"({test})[{terrain.terrainName}]{surfaces.surfIndex} :");
Console.WriteLine($"\t[{surface.minPitch} < {surface.maxPitch}]({surface.baseMaterials.First().materialDid}) - Vec3: {surface.vertexColor.First().vertexColor}");
}
Console.WriteLine("--------");
}
}
}
private void InitialiseTerrainDic() {
foreach(var terrain in portalEngine.cTerrainDesc.terrains) {
foreach (var surface in portalEngine.cSurfaceDesc.surfaces) {
if (terrain.surfaceInfo == surface.surfIndex) {
var id = surface.terrainMaterials.First().baseMaterials.First().materialDid;
mapTerrain.Add((int)terrain.terrainIndex, id);
break;
}
}
}
}
private int GetIndex(DataId id) {
foreach(var mat in mapTerrain) {
if(mat.Value == id) return mat.Key;
}
return 0;
}
public void GenerateUV() {
int count = (int)Math.Ceiling(Math.Sqrt(textureCoord.Count));
int atlasSize = (int)64 * count;
int index = 0;
foreach (var terrain in textureCoord) {
int x = (index % count) * (int)64;
int y = (index / count) * (int)64;
textureCoord[index] = new Vector2(x, y);
index++;
}
}
}