This commit is contained in:
2025-11-11 17:31:52 +08:00
parent 4a48d5093d
commit 40b0cdbb05
13 changed files with 376 additions and 811 deletions

View File

@@ -0,0 +1,14 @@
using Verse;
namespace WulaFallenEmpire
{
/// <summary>
/// A marker component that holds custom flight properties.
/// The actual flight logic is handled by Harmony patches that check for this component
/// and use its properties to override or trigger vanilla flight behavior.
/// </summary>
public class CompPawnFlight : ThingComp
{
public CompProperties_PawnFlight Props => (CompProperties_PawnFlight)props;
}
}

View File

@@ -0,0 +1,55 @@
using Verse;
using RimWorld;
using System.Collections.Generic;
namespace WulaFallenEmpire
{
public enum FlightCondition
{
Drafted,
MechAlwaysExceptSpecialJobs // 新增:机械族在非特殊工作状态下始终飞行
}
public class CompProperties_PawnFlight : CompProperties
{
// --- Custom Flight Logic ---
public FlightCondition flightCondition = FlightCondition.Drafted;
// --- 新增:机械族特殊工作检查 ---
public List<JobDef> mechForbiddenJobs = new List<JobDef>
{
JobDefOf.MechCharge, // 充电工作
JobDefOf.SelfShutdown // 关机工作
};
// --- Vanilla PawnKindDef Flight Parameters ---
[NoTranslate]
public string flyingAnimationFramePathPrefix;
[NoTranslate]
public string flyingAnimationFramePathPrefixFemale;
public int flyingAnimationFrameCount;
public int flyingAnimationTicksPerFrame = -1;
public float flyingAnimationDrawSize = 1f;
public bool flyingAnimationDrawSizeIsMultiplier;
public bool flyingAnimationInheritColors;
// --- Vanilla PawnKindLifeStage Flight Parameters ---
public AnimationDef flyingAnimationEast;
public AnimationDef flyingAnimationNorth;
public AnimationDef flyingAnimationSouth;
public AnimationDef flyingAnimationEastFemale;
public AnimationDef flyingAnimationNorthFemale;
public AnimationDef flyingAnimationSouthFemale;
public CompProperties_PawnFlight()
{
compClass = typeof(CompPawnFlight);
}
}
}

View File

@@ -0,0 +1,22 @@
using Verse;
using UnityEngine;
namespace WulaFallenEmpire
{
public class PawnRenderNodeWorker_AttachmentBody_NoFlight : PawnRenderNodeWorker_AttachmentBody
{
public override bool CanDrawNow(PawnRenderNode node, PawnDrawParms parms)
{
if (parms.pawn.Flying)
{
return false;
}
return base.CanDrawNow(node, parms);
}
public override Vector3 ScaleFor(PawnRenderNode node, PawnDrawParms parms)
{
return base.ScaleFor(node, parms);
}
}
}

View File

@@ -0,0 +1,81 @@
using HarmonyLib;
using Verse;
using RimWorld;
using Verse.AI;
namespace WulaFallenEmpire
{
[HarmonyPatch]
public static class FlightHarmonyPatches
{
// Corrected Patch 1: The method signature now correctly matches the static target method.
[HarmonyPrefix]
[HarmonyPatch(typeof(Pawn_FlightTracker), "GetBestFlyAnimation")]
public static bool GetBestFlyAnimation_Prefix(Pawn pawn, ref AnimationDef __result) // Correct parameters: Pawn pawn, not __instance and ___pawn
{
var flightComp = pawn?.TryGetComp<CompPawnFlight>();
if (flightComp == null) // No props check needed, as the crash was due to wrong signature
{
return true;
}
var compProps = flightComp.Props;
AnimationDef selectedAnim = null;
if (pawn.gender == Gender.Female && compProps.flyingAnimationNorthFemale != null)
{
switch (pawn.Rotation.AsInt)
{
case 0: selectedAnim = compProps.flyingAnimationNorthFemale; break;
case 1: selectedAnim = compProps.flyingAnimationEastFemale; break;
case 2: selectedAnim = compProps.flyingAnimationSouthFemale; break;
case 3: selectedAnim = compProps.flyingAnimationEastFemale ?? compProps.flyingAnimationEast; break;
}
}
else
{
switch (pawn.Rotation.AsInt)
{
case 0: selectedAnim = compProps.flyingAnimationNorth; break;
case 1: selectedAnim = compProps.flyingAnimationEast; break;
case 2: selectedAnim = compProps.flyingAnimationSouth; break;
case 3: selectedAnim = compProps.flyingAnimationEast; break;
}
}
if (selectedAnim != null)
{
__result = selectedAnim;
return false;
}
return true;
}
// Patch 2 remains correct as Notify_JobStarted is a non-static method.
[HarmonyPrefix]
[HarmonyPatch(typeof(Pawn_FlightTracker), "Notify_JobStarted")]
public static bool Notify_JobStarted_Prefix(Job job, Pawn_FlightTracker __instance, Pawn ___pawn)
{
var flightComp = ___pawn?.TryGetComp<CompPawnFlight>();
if (flightComp == null || __instance == null || !__instance.CanEverFly || ___pawn == null || ___pawn.Dead)
{
return true;
}
var compProps = flightComp.Props;
bool shouldBeFlying = (compProps.flightCondition == FlightCondition.Drafted && ___pawn.Drafted);
if (shouldBeFlying)
{
if (!__instance.Flying) __instance.StartFlying();
job.flying = true;
}
else
{
if (__instance.Flying) __instance.ForceLand();
job.flying = false;
}
return false;
}
}
}

View File

@@ -175,6 +175,10 @@
<Compile Include="Pawn\WULA_Energy\WorkGiver_Warden_DeliverEnergy.cs" />
<Compile Include="Pawn\WULA_Energy\WorkGiver_Warden_FeedWula.cs" />
<Compile Include="Pawn\WULA_Energy\WulaCaravanEnergyDef.cs" />
<Compile Include="Pawn\WULA_Flight\CompPawnFlight.cs" />
<Compile Include="Pawn\WULA_Flight\CompProperties_PawnFlight.cs" />
<Compile Include="Pawn\WULA_Flight\PawnRenderNodeWorker_AttachmentBody_NoFlight.cs" />
<Compile Include="Pawn\WULA_Flight\Pawn_FlightTrackerPatches.cs" />
<Compile Include="Pawn\WULA_Maintenance\Building_MaintenancePod.cs" />
<Compile Include="Pawn\WULA_Maintenance\CompMaintenancePod.cs" />
<Compile Include="Pawn\WULA_Maintenance\HediffCompProperties_MaintenanceDamage.cs" />