refactor(CheatEnabler): reduce duplication in DysonSphere helpers

This commit is contained in:
2026-06-23 04:20:52 +08:00
parent 2dce3a7b93
commit b6657c96c0
4 changed files with 76 additions and 142 deletions
@@ -290,7 +290,7 @@ public static class GeometryHelpers
} }
return vmap.Count; return vmap.Count;
} }
public static bool MyGenerateGeometry(this DysonShell shell) public static bool GenerateCustomShellGeometry(this DysonShell shell)
{ {
VectorLF3 sum = VectorLF3.zero; VectorLF3 sum = VectorLF3.zero;
double num = 0.0; double num = 0.0;
@@ -718,7 +718,7 @@ public static class GeometryHelpers
shell.nodes.Add(dysonNode); shell.nodes.Add(dysonNode);
shell.frames.Add(dysonFrame); shell.frames.Add(dysonFrame);
} }
if (!shell.MyGenerateGeometry() || (limit && DysonShell.s_vmap.Count < 32000)) if (!shell.GenerateCustomShellGeometry() || (limit && DysonShell.s_vmap.Count < 32000))
{ {
CheatEnabler.Logger.LogDebug($"Stripped VertCount: {DysonShell.s_vmap.Count}"); CheatEnabler.Logger.LogDebug($"Stripped VertCount: {DysonShell.s_vmap.Count}");
shell.Free(); shell.Free();
@@ -13,14 +13,54 @@ namespace CheatEnabler.Functions.DysonSphere;
[ModFeature("IllegalShellFunctions")] [ModFeature("IllegalShellFunctions")]
public static class IllegalShellFunctions public static class IllegalShellFunctions
{ {
private static void EnsureDysonShellMaps()
{
DysonShell.s_vmap ??= new Dictionary<int, Vector3>(16384);
DysonShell.s_outvmap ??= new Dictionary<int, Vector3>(16384);
DysonShell.s_ivmap ??= new Dictionary<int, int>(16384);
}
private static void ResetLayerPools(DysonSphereLayer layer)
{
layer.nodePool = new DysonNode[64];
layer.nodeRecycle = new int[64];
layer.nodeRecycleCursor = 0;
layer.nodeCapacity = 64;
layer.nodeCursor = 1;
layer.framePool = new DysonFrame[64];
layer.frameRecycle = new int[64];
layer.frameRecycleCursor = 0;
layer.frameCapacity = 64;
layer.frameCursor = 1;
layer.shellPool = new DysonShell[64];
layer.shellRecycle = new int[64];
layer.shellRecycleCursor = 0;
layer.shellCapacity = 64;
layer.shellCursor = 1;
}
private static void FinalizeDysonSphereChanges(global::DysonSphere sphere, DysonSphereLayer layer, bool notify = false, bool resetRenderMasks = false)
{
if (sphere == null) return;
sphere.CheckAutoNodes();
if (sphere.autoNodeCount <= 0) sphere.PickAutoNode();
sphere.modelRenderer.RebuildModels();
if (notify) GameMain.gameScenario?.NotifyOnPlanDysonShell();
if (resetRenderMasks)
{
sphere.inEditorRenderMaskS = 0;
sphere.inEditorRenderMaskL = 0;
sphere.inGameRenderMaskS = 0;
sphere.inGameRenderMaskL = 0;
}
}
public static void DuplicateShellsWithHighestProduction() public static void DuplicateShellsWithHighestProduction()
{ {
var resolved = DysonSphereResolver.ResolveEditorOrLocalSphere(); var resolved = DysonSphereResolver.ResolveEditorOrLocalSphere();
if (resolved == null) return; if (resolved == null) return;
var (dysonSphere, star) = resolved.Value; var (dysonSphere, star) = resolved.Value;
DysonShell.s_vmap ??= new Dictionary<int, Vector3>(16384); EnsureDysonShellMaps();
DysonShell.s_outvmap ??= new Dictionary<int, Vector3>(16384);
DysonShell.s_ivmap ??= new Dictionary<int, int>(16384);
DysonSphereLayer layer = null; DysonSphereLayer layer = null;
var nodePos = new List<Vector3>(); var nodePos = new List<Vector3>();
var isEuler = new List<bool>(); var isEuler = new List<bool>();
@@ -98,17 +138,7 @@ public static class IllegalShellFunctions
node.RecalcSpReq(); node.RecalcSpReq();
node.RecalcCpReq(); node.RecalcCpReq();
} }
dysonSphere.CheckAutoNodes(); FinalizeDysonSphereChanges(dysonSphere, layer, true, true);
if (dysonSphere.autoNodeCount <= 0)
{
dysonSphere.PickAutoNode();
}
dysonSphere.modelRenderer.RebuildModels();
GameMain.gameScenario?.NotifyOnPlanDysonShell();
dysonSphere.inEditorRenderMaskS = 0;
dysonSphere.inEditorRenderMaskL = 0;
dysonSphere.inGameRenderMaskS = 0;
dysonSphere.inGameRenderMaskL = 0;
} }
public static void KeepMaxProductionShells() public static void KeepMaxProductionShells()
@@ -213,29 +243,16 @@ public static class IllegalShellFunctions
node.RecalcCpReq(); node.RecalcCpReq();
} }
} }
dysonSphere.CheckAutoNodes(); FinalizeDysonSphereChanges(dysonSphere, null);
if (dysonSphere.autoNodeCount <= 0)
{
dysonSphere.PickAutoNode();
}
dysonSphere.modelRenderer.RebuildModels();
} }
public static void CreateIllegalDysonShellQuickly(int triangleCount) public static void CreateIllegalDysonShellQuickly(int triangleCount)
{ {
var star = DysonSphereResolver.ResolveEditorOrLocalStar(); var resolved = DysonSphereResolver.ResolveEditorOrLocalSphere(requireLayer: false);
if (star == null) return; if (resolved == null) return;
var (dysonSphere, _) = resolved.Value;
var dysonSphere = GameMain.data?.dysonSpheres[star.index]; EnsureDysonShellMaps();
if (dysonSphere == null)
{
UIMessageBox.Show("CheatEnabler".Translate(), string.Format("There is no Dyson Sphere data on \"{0}\".".Translate(), star.displayName), "确定".Translate(), UIMessageBox.ERROR, null);
return;
}
DysonShell.s_vmap ??= new Dictionary<int, Vector3>(16384);
DysonShell.s_outvmap ??= new Dictionary<int, Vector3>(16384);
DysonShell.s_ivmap ??= new Dictionary<int, int>(16384);
for (int i = 1; i <= 10; i++) for (int i = 1; i <= 10; i++)
{ {
@@ -298,19 +315,14 @@ public static class IllegalShellFunctions
node.RecalcSpReq(); node.RecalcSpReq();
node.RecalcCpReq(); node.RecalcCpReq();
} }
dysonSphere.CheckAutoNodes(); FinalizeDysonSphereChanges(dysonSphere, layer, true);
if (dysonSphere.autoNodeCount <= 0) dysonSphere.PickAutoNode();
dysonSphere.modelRenderer.RebuildModels();
GameMain.gameScenario?.NotifyOnPlanDysonShell();
return; return;
} }
} }
private static bool CreateIllegalDysonShellWithMaxOutputForLayer(DysonSphereLayer layer) private static bool CreateIllegalDysonShellWithMaxOutputForLayer(DysonSphereLayer layer)
{ {
DysonShell.s_vmap ??= new Dictionary<int, Vector3>(16384); EnsureDysonShellMaps();
DysonShell.s_outvmap ??= new Dictionary<int, Vector3>(16384);
DysonShell.s_ivmap ??= new Dictionary<int, int>(16384);
var shellsChanged = false; var shellsChanged = false;
var mutex = new object(); var mutex = new object();
var supposedShells = new List<SupposedShell>(60 * 59 * 58); var supposedShells = new List<SupposedShell>(60 * 59 * 58);
@@ -370,21 +382,7 @@ public static class IllegalShellFunctions
}); });
if (maxJ >= 0) if (maxJ >= 0)
{ {
layer.nodePool = new DysonNode[64]; ResetLayerPools(layer);
layer.nodeRecycle = new int[64];
layer.nodeRecycleCursor = 0;
layer.nodeCapacity = 64;
layer.nodeCursor = 1;
layer.framePool = new DysonFrame[64];
layer.frameRecycle = new int[64];
layer.frameRecycleCursor = 0;
layer.frameCapacity = 64;
layer.frameCursor = 1;
layer.shellPool = new DysonShell[64];
layer.shellRecycle = new int[64];
layer.shellRecycleCursor = 0;
layer.shellCapacity = 64;
layer.shellCursor = 1;
var sshell = supposedShells[maxJ]; var sshell = supposedShells[maxJ];
DysonNode[] newNodes = [layer.QuickAddDysonNode(0, sshell.posA), layer.QuickAddDysonNode(0, sshell.posB), layer.QuickAddDysonNode(0, sshell.posC)]; DysonNode[] newNodes = [layer.QuickAddDysonNode(0, sshell.posA), layer.QuickAddDysonNode(0, sshell.posB), layer.QuickAddDysonNode(0, sshell.posC)];
DysonFrame[] newFrames = [layer.QuickAddDysonFrame(0, newNodes[0], newNodes[1], false), layer.QuickAddDysonFrame(0, newNodes[1], newNodes[2], false), layer.QuickAddDysonFrame(0, newNodes[2], newNodes[0], false)]; DysonFrame[] newFrames = [layer.QuickAddDysonFrame(0, newNodes[0], newNodes[1], false), layer.QuickAddDysonFrame(0, newNodes[1], newNodes[2], false), layer.QuickAddDysonFrame(0, newNodes[2], newNodes[0], false)];
@@ -401,15 +399,10 @@ public static class IllegalShellFunctions
public static void CreateIllegalDysonShellWithMaxOutput() public static void CreateIllegalDysonShellWithMaxOutput()
{ {
var star = DysonSphereResolver.ResolveEditorOrLocalStar(); var resolved = DysonSphereResolver.ResolveEditorOrLocalSphere(requireLayer: false);
if (star == null) return; if (resolved == null) return;
var (dysonSphere, star) = resolved.Value;
UXAssist.Functions.DysonSphereFunctions.InitCurrentDysonLayer(star, 0); UXAssist.Functions.DysonSphereFunctions.InitCurrentDysonLayer(star, 0);
var dysonSphere = GameMain.data?.dysonSpheres[star.index];
if (dysonSphere == null)
{
UIMessageBox.Show("CheatEnabler".Translate(), string.Format("There is no Dyson Sphere data on \"{0}\".".Translate(), star.displayName), "确定".Translate(), UIMessageBox.ERROR, null);
return;
}
var layer = dysonSphere.layersIdBased[1]; var layer = dysonSphere.layersIdBased[1];
if (layer != null) if (layer != null)
{ {
@@ -421,26 +414,14 @@ public static class IllegalShellFunctions
var shellsChanged = CreateIllegalDysonShellWithMaxOutputForLayer(layer); var shellsChanged = CreateIllegalDysonShellWithMaxOutputForLayer(layer);
dysonSphere.CheckAutoNodes(); FinalizeDysonSphereChanges(dysonSphere, layer, shellsChanged, true);
if (dysonSphere.autoNodeCount <= 0) dysonSphere.PickAutoNode();
dysonSphere.modelRenderer.RebuildModels();
if (shellsChanged) GameMain.gameScenario?.NotifyOnPlanDysonShell();
dysonSphere.inEditorRenderMaskS = 0;
dysonSphere.inEditorRenderMaskL = 0;
dysonSphere.inGameRenderMaskS = 0;
dysonSphere.inGameRenderMaskL = 0;
} }
public static void CreateIllegalDysonShellWithMaxOutput2() public static void CreateIllegalDysonShellWithMaxOutputForAllLayers()
{ {
var star = DysonSphereResolver.ResolveEditorOrLocalStar(); var resolved = DysonSphereResolver.ResolveEditorOrLocalSphere(requireLayer: false);
if (star == null) return; if (resolved == null) return;
var dysonSphere = GameMain.data?.dysonSpheres[star.index]; var (dysonSphere, _) = resolved.Value;
if (dysonSphere == null)
{
UIMessageBox.Show("CheatEnabler".Translate(), string.Format("There is no Dyson Sphere data on \"{0}\".".Translate(), star.displayName), "确定".Translate(), UIMessageBox.ERROR, null);
return;
}
var shellsChanged = false; var shellsChanged = false;
for (int i = dysonSphere.layersSorted.Length - 1; i >= 0; i--) for (int i = dysonSphere.layersSorted.Length - 1; i >= 0; i--)
{ {
@@ -449,14 +430,7 @@ public static class IllegalShellFunctions
shellsChanged = CreateIllegalDysonShellWithMaxOutputForLayer(layer) || shellsChanged; shellsChanged = CreateIllegalDysonShellWithMaxOutputForLayer(layer) || shellsChanged;
} }
dysonSphere.CheckAutoNodes(); FinalizeDysonSphereChanges(dysonSphere, dysonSphere.layersSorted.FirstOrDefault(l => l != null), shellsChanged, true);
if (dysonSphere.autoNodeCount <= 0) dysonSphere.PickAutoNode();
dysonSphere.modelRenderer.RebuildModels();
if (shellsChanged) GameMain.gameScenario?.NotifyOnPlanDysonShell();
dysonSphere.inEditorRenderMaskS = 0;
dysonSphere.inEditorRenderMaskL = 0;
dysonSphere.inGameRenderMaskS = 0;
dysonSphere.inGameRenderMaskL = 0;
} }
public static void CreateIllegalDysonShellsSpecially() public static void CreateIllegalDysonShellsSpecially()
@@ -473,31 +447,12 @@ public static class IllegalShellFunctions
CheatEnabler.Logger.LogDebug($"Grid Scale: {gridScale} from {r}"); CheatEnabler.Logger.LogDebug($"Grid Scale: {gridScale} from {r}");
} }
radiusList.Add(250000); radiusList.Add(250000);
StarData star = null; var resolved = DysonSphereResolver.ResolveEditorOrLocalSphere(requireLayer: false);
var dysonEditor = UIRoot.instance?.uiGame?.dysonEditor; if (resolved == null) return;
if (dysonEditor != null && dysonEditor.gameObject.activeSelf) var (dysonSphere, star) = resolved.Value;
{
star = dysonEditor.selection.viewStar;
}
if (star == null)
{
star = GameMain.localStar;
if (star == null)
{
UIMessageBox.Show("CheatEnabler".Translate(), "You are not in any system.".Translate(), "确定".Translate(), UIMessageBox.ERROR, null);
return;
}
}
UXAssist.Functions.DysonSphereFunctions.InitCurrentDysonLayer(star, 0); UXAssist.Functions.DysonSphereFunctions.InitCurrentDysonLayer(star, 0);
var dysonSphere = GameMain.data?.dysonSpheres[star.index];
if (dysonSphere == null) EnsureDysonShellMaps();
{
UIMessageBox.Show("CheatEnabler".Translate(), string.Format("There is no Dyson Sphere data on \"{0}\".".Translate(), star.displayName), "确定".Translate(), UIMessageBox.ERROR, null);
return;
}
DysonShell.s_vmap ??= new Dictionary<int, Vector3>(16384);
DysonShell.s_outvmap ??= new Dictionary<int, Vector3>(16384);
DysonShell.s_ivmap ??= new Dictionary<int, int>(16384);
var shellsChanged = false; var shellsChanged = false;
var mutex = new object(); var mutex = new object();
@@ -583,21 +538,7 @@ public static class IllegalShellFunctions
{ {
continue; continue;
} }
layer.nodePool = new DysonNode[64]; ResetLayerPools(layer);
layer.nodeRecycle = new int[64];
layer.nodeRecycleCursor = 0;
layer.nodeCapacity = 64;
layer.nodeCursor = 1;
layer.framePool = new DysonFrame[64];
layer.frameRecycle = new int[64];
layer.frameRecycleCursor = 0;
layer.frameCapacity = 64;
layer.frameCursor = 1;
layer.shellPool = new DysonShell[64];
layer.shellRecycle = new int[64];
layer.shellRecycleCursor = 0;
layer.shellCapacity = 64;
layer.shellCursor = 1;
DysonNode[] newNodes = [layer.QuickAddDysonNode(0, sshell.posA * orbitRadius), layer.QuickAddDysonNode(0, sshell.posB * orbitRadius), layer.QuickAddDysonNode(0, sshell.posC * orbitRadius)]; DysonNode[] newNodes = [layer.QuickAddDysonNode(0, sshell.posA * orbitRadius), layer.QuickAddDysonNode(0, sshell.posB * orbitRadius), layer.QuickAddDysonNode(0, sshell.posC * orbitRadius)];
DysonFrame[] newFrames = [layer.QuickAddDysonFrame(0, newNodes[0], newNodes[1], false), layer.QuickAddDysonFrame(0, newNodes[1], newNodes[2], false), layer.QuickAddDysonFrame(0, newNodes[2], newNodes[0], false)]; DysonFrame[] newFrames = [layer.QuickAddDysonFrame(0, newNodes[0], newNodes[1], false), layer.QuickAddDysonFrame(0, newNodes[1], newNodes[2], false), layer.QuickAddDysonFrame(0, newNodes[2], newNodes[0], false)];
layer.QuickAddDysonShell(0, newNodes, newFrames, false); layer.QuickAddDysonShell(0, newNodes, newFrames, false);
@@ -611,13 +552,6 @@ public static class IllegalShellFunctions
} }
} }
dysonSphere.CheckAutoNodes(); FinalizeDysonSphereChanges(dysonSphere, dysonSphere.layersIdBased[2], shellsChanged, true);
if (dysonSphere.autoNodeCount <= 0) dysonSphere.PickAutoNode();
dysonSphere.modelRenderer.RebuildModels();
if (shellsChanged) GameMain.gameScenario?.NotifyOnPlanDysonShell();
dysonSphere.inEditorRenderMaskS = 0;
dysonSphere.inEditorRenderMaskL = 0;
dysonSphere.inGameRenderMaskS = 0;
dysonSphere.inGameRenderMaskL = 0;
} }
} }
@@ -27,6 +27,6 @@ public static class DysonSphereFunctions
public static void KeepMaxProductionShells() => IllegalShellFunctions.KeepMaxProductionShells(); public static void KeepMaxProductionShells() => IllegalShellFunctions.KeepMaxProductionShells();
public static void CreateIllegalDysonShellQuickly(int triangleCount) => IllegalShellFunctions.CreateIllegalDysonShellQuickly(triangleCount); public static void CreateIllegalDysonShellQuickly(int triangleCount) => IllegalShellFunctions.CreateIllegalDysonShellQuickly(triangleCount);
public static void CreateIllegalDysonShellWithMaxOutput() => IllegalShellFunctions.CreateIllegalDysonShellWithMaxOutput(); public static void CreateIllegalDysonShellWithMaxOutput() => IllegalShellFunctions.CreateIllegalDysonShellWithMaxOutput();
public static void CreateIllegalDysonShellWithMaxOutput2() => IllegalShellFunctions.CreateIllegalDysonShellWithMaxOutput2(); public static void CreateIllegalDysonShellWithMaxOutputForAllLayers() => IllegalShellFunctions.CreateIllegalDysonShellWithMaxOutputForAllLayers();
public static void CreateIllegalDysonShellsSpecially() => IllegalShellFunctions.CreateIllegalDysonShellsSpecially(); public static void CreateIllegalDysonShellsSpecially() => IllegalShellFunctions.CreateIllegalDysonShellsSpecially();
} }
+1 -1
View File
@@ -323,7 +323,7 @@ public static class UIConfigWindow
var btn1 = wnd.AddButton(x, y, 300f, tab4, "Generate illegal dyson shell 2", 16, "button-generate-illegal-dyson-shells", () => var btn1 = wnd.AddButton(x, y, 300f, tab4, "Generate illegal dyson shell 2", 16, "button-generate-illegal-dyson-shells", () =>
{ {
UIMessageBox.Show("Generate illegal dyson shell 2".Translate(), "WARNING: This operation can be very slow, continue?".Translate(), "取消".Translate(), "确定".Translate(), UIMessageBox.WARNING, null, UIMessageBox.Show("Generate illegal dyson shell 2".Translate(), "WARNING: This operation can be very slow, continue?".Translate(), "取消".Translate(), "确定".Translate(), UIMessageBox.WARNING, null,
() => { DysonSphereFunctions.CreateIllegalDysonShellWithMaxOutput2(); }); () => { DysonSphereFunctions.CreateIllegalDysonShellWithMaxOutputForAllLayers(); });
}); });
y += 36f; y += 36f;
var btn2 = wnd.AddButton(x, y, 300f, tab4, "Keep max production shells and remove others", 16, "button-keep-max-production-shells", () => var btn2 = wnd.AddButton(x, y, 300f, tab4, "Keep max production shells and remove others", 16, "button-keep-max-production-shells", () =>