Authored Unity primitive/object-model shim, VFX layer (control-flow-preserving, InstantVfx never invokes its action -- headless suppression), god-object stubs (GameMgr/EffectMgr/UIManager with faithfully-extracted nested enums), View/UI/Touch tree, LitJson+BetterList+Tuple copied, third-party stubs. Discovered Roslyn header-error masking: fixing class-header type errors unmasks body references, so the true copy closure is ~2570 files (was 782 under masking). Errors: masked-25720 -> 268; our shim files compile clean. Remaining: ~50 residual shim/external types, 24 NGUI UI-base overrides, static-type fixes, plus likely 1-2 more unmask waves.
104 lines
4.0 KiB
C#
104 lines
4.0 KiB
C#
using System.Collections.Generic;
|
|
using System.Linq;
|
|
|
|
namespace Wizard;
|
|
|
|
public class AIRuleBaseBattleSimulator
|
|
{
|
|
private EnemyAI _ai;
|
|
|
|
private PlayPtnWithToken[] _bestPlayPtnWithToken;
|
|
|
|
private bool _canChangeToTimeOverLogic;
|
|
|
|
public AIRuleBaseBattleSimulator(EnemyAI ai, PlayPtnWithToken[] bestPlayPtnWithToken, bool canChangeToTimeOverLogic)
|
|
{
|
|
_ai = ai;
|
|
_bestPlayPtnWithToken = bestPlayPtnWithToken;
|
|
_canChangeToTimeOverLogic = canChangeToTimeOverLogic;
|
|
}
|
|
|
|
public void RunSequence(AIVirtualField originalField, int[] actionPermList, int evoIndex, List<int> enemyTargets, SimulationResult bestRecord, SimulationAdditionalActionInfoSet additionalOptions, InplayMovePatternFilter patternFilter, bool checkActFailure = true)
|
|
{
|
|
AIVirtualField aIVirtualField = new AIVirtualField(originalField);
|
|
bool[] array = new bool[actionPermList.Length];
|
|
for (int i = 0; i < array.Length; i++)
|
|
{
|
|
array[i] = true;
|
|
}
|
|
AIVirtualActionInfo aIVirtualActionInfo = AISimulationUtility.CreateActionInfoOnFieldFromSituation(aIVirtualField, additionalOptions?.ForceEvoAction);
|
|
List<AIVirtualActionInfo> actionInfoSequence = AISimulationUtility.GetActionInfoSequence(aIVirtualField, actionPermList, array, (aIVirtualActionInfo != null) ? (-1) : evoIndex);
|
|
if (aIVirtualActionInfo != null && !actionInfoSequence.Any((AIVirtualActionInfo info) => info.ActionType == AIOperationType.EVOLVE))
|
|
{
|
|
bool flag = false;
|
|
for (int num = 0; num < actionInfoSequence.Count; num++)
|
|
{
|
|
if (actionInfoSequence[num].Actor.IsSameCard(aIVirtualActionInfo.Actor))
|
|
{
|
|
actionInfoSequence.Insert(num, aIVirtualActionInfo);
|
|
flag = true;
|
|
break;
|
|
}
|
|
}
|
|
if (!flag)
|
|
{
|
|
actionInfoSequence.Add(aIVirtualActionInfo);
|
|
}
|
|
}
|
|
List<AIVirtualCard> enemyTargetSequence = AISimulationUtility.GetEnemyTargetSequence(aIVirtualField, enemyTargets);
|
|
SimulationSetting simSetting = new SimulationSetting(isHandRemovalValid: true, useLeaderAttackPreCheck: true, aIVirtualField.IsNoSkipAttackInPlayPtn(), checkActFailure);
|
|
ExecuteSimulationWithActionSequence(aIVirtualField, actionInfoSequence, enemyTargetSequence, simSetting, bestRecord, patternFilter);
|
|
}
|
|
|
|
public void RunPlaySkipWithActionSequence(AIVirtualField originalField, List<AIVirtualActionInfo> actionSequence, List<AIVirtualCard> enemyTargets, SimulationResult bestRecord, SimulationAdditionalActionInfoSet additionalOptions)
|
|
{
|
|
}
|
|
|
|
private void ExecuteSimulationWithActionSequence(AIVirtualField fieldTemp, List<AIVirtualActionInfo> actionInfoSequence, List<AIVirtualCard> enemyTargetSequence, SimulationSetting simSetting, SimulationResult bestRecord, InplayMovePatternFilter patternFilter)
|
|
{
|
|
BattleSequencer.ExecSimulation(fieldTemp, actionInfoSequence, enemyTargetSequence, simSetting);
|
|
if (NeedsChangeToTimeOverLogic())
|
|
{
|
|
return;
|
|
}
|
|
AIVirtualTurnEndInfo aIVirtualTurnEndInfo = new AIVirtualTurnEndInfo(fieldTemp.AllyClass);
|
|
actionInfoSequence.Add(aIVirtualTurnEndInfo);
|
|
BattleSequencer.OnAfterExecuteAttackCommon(fieldTemp, aIVirtualTurnEndInfo, ref actionInfoSequence, isAttackToLeaderAgain: true);
|
|
if (NeedsChangeToTimeOverLogic())
|
|
{
|
|
return;
|
|
}
|
|
float num = AISimulationUtility.EvaluateField(fieldTemp, EvaluationType.SELF_TURN);
|
|
if (NeedsChangeToTimeOverLogic())
|
|
{
|
|
return;
|
|
}
|
|
float num2 = num;
|
|
if (_bestPlayPtnWithToken == null)
|
|
{
|
|
num2 = num - (fieldTemp.EnemyClass.IsDead ? 0f : fieldTemp.EvaluateThreaten());
|
|
}
|
|
if (AISimulationUtility.IsBestRecord(fieldTemp, num2, num, bestRecord))
|
|
{
|
|
bestRecord.BestResultField = fieldTemp;
|
|
bestRecord.MaxFieldValue = num2;
|
|
bestRecord.ActionSequence = actionInfoSequence;
|
|
bestRecord.MaxFieldValueAtSelfTurnEnd = num;
|
|
if (fieldTemp.EnemyClass.IsDead)
|
|
{
|
|
bestRecord.MinActionLengthOfLethal = fieldTemp.ActionLength;
|
|
}
|
|
patternFilter?.ConfirmBestPattern(enemyTargetSequence);
|
|
}
|
|
}
|
|
|
|
private bool NeedsChangeToTimeOverLogic()
|
|
{
|
|
if (_ai.IsRunWeakLogic)
|
|
{
|
|
return !_canChangeToTimeOverLogic;
|
|
}
|
|
return false;
|
|
}
|
|
}
|