From 32f3b1522f5ceb18b7891902c7ee79b4ffb399a3 Mon Sep 17 00:00:00 2001 From: c0ffee Date: Sun, 21 Apr 2024 18:49:24 -0700 Subject: [PATCH] added: offsets, dynamically set in animation animation prop graphics, absolute positioning, changing textures, can be used in animation --- 1.5/Assemblies/Rimworld-Animations.dll | Bin 29696 -> 32768 bytes .../AnimationPropDefs/AnimationPropDef.xml | 22 +++++- .../TestGroupAnimation1.xml | 62 ++++------------ .../OffsetDef_GroinToAppropriateHeight.xml | 66 ++++++++++-------- ...onPatch_PawnRenderTree_OffsetSubWorker.xml | 27 +++++++ 1.5/Source/Actors/BodyTypeOffset.cs | 18 ----- .../AnimationOffsets/AnimationOffsetDef.cs | 33 +++++++++ .../Offsets/AnimationOffset_BodyType.cs | 23 ++++++ .../AnimationOffset_BodyTypeGendered.cs | 30 ++++++++ .../Offsets/AnimationOffset_Single.cs | 21 ++++++ .../Offsets/BaseAnimationOffset.cs | 25 +++++++ .../Offsets/BodyTypeOffset.cs | 17 +++++ .../AnimationProps/AnimationPropDef.cs | 2 +- .../AnimationWorker_KeyframesExtended.cs | 1 + .../BaseGroupAnimationContext.cs | 0 .../GroupAnimationContext_RJWSex.cs | 0 .../GroupAnimations/GroupAnimationDef.cs | 9 +++ .../GroupAnimationStages/AnimationStage.cs | 0 .../AnimationStage_Branch.cs | 26 +++++++ .../AnimationStage_LoopRandomSelectChance.cs | 0 .../AnimationStage_TicksDuration.cs | 0 .../Keyframes/ExtendedKeyframe.cs | 0 1.5/Source/Comps/CompExtendedAnimator.cs | 32 +++++++-- .../AnimationStage_Branch.cs | 18 ----- .../HarmonyPatch_PawnRenderTree.cs | 28 +++++++- ...awnRenderNodeProperties_GraphicVariants.cs | 1 + .../PawnRenderNodeWorker_GraphicVariants.cs | 0 .../PawnRenderNode_GraphicVariants.cs | 0 .../PawnRenderSubWorker_ChangeOffset.cs | 30 ++++++++ 1.5/Source/Utilities/AnimationUtility.cs | 12 ++-- .../Assemblies/Patch_HumanoidAlienRaces.dll | Bin 4096 -> 4096 bytes .../1.5/Source/Patches/Harmony_PatchAll.cs | 23 ++++++ .../Patch_HumanoidAlienRaces.csproj | 6 ++ Rimworld-Animations.csproj | 36 ++++++---- 34 files changed, 424 insertions(+), 144 deletions(-) create mode 100644 1.5/Patches/AnimationPatch_PawnRenderTree_OffsetSubWorker.xml delete mode 100644 1.5/Source/Actors/BodyTypeOffset.cs create mode 100644 1.5/Source/Animations/AnimationOffsets/AnimationOffsetDef.cs create mode 100644 1.5/Source/Animations/AnimationOffsets/Offsets/AnimationOffset_BodyType.cs create mode 100644 1.5/Source/Animations/AnimationOffsets/Offsets/AnimationOffset_BodyTypeGendered.cs create mode 100644 1.5/Source/Animations/AnimationOffsets/Offsets/AnimationOffset_Single.cs create mode 100644 1.5/Source/Animations/AnimationOffsets/Offsets/BaseAnimationOffset.cs create mode 100644 1.5/Source/Animations/AnimationOffsets/Offsets/BodyTypeOffset.cs rename 1.5/Source/{ => Animations}/AnimationProps/AnimationPropDef.cs (74%) rename 1.5/Source/{ => Animations}/AnimationWorkers/AnimationWorker_KeyframesExtended.cs (98%) rename 1.5/Source/{ => Animations}/GroupAnimations/GroupAnimationContexts/BaseGroupAnimationContext.cs (100%) rename 1.5/Source/{ => Animations}/GroupAnimations/GroupAnimationContexts/GroupAnimationContext_RJWSex.cs (100%) rename 1.5/Source/{ => Animations}/GroupAnimations/GroupAnimationDef.cs (80%) rename 1.5/Source/{ => Animations}/GroupAnimations/GroupAnimationStages/AnimationStage.cs (100%) create mode 100644 1.5/Source/Animations/GroupAnimations/GroupAnimationStages/AnimationStage_Branch.cs rename 1.5/Source/{ => Animations}/GroupAnimations/GroupAnimationStages/AnimationStage_LoopRandomSelectChance.cs (100%) rename 1.5/Source/{ => Animations}/GroupAnimations/GroupAnimationStages/AnimationStage_TicksDuration.cs (100%) rename 1.5/Source/{ => Animations}/Keyframes/ExtendedKeyframe.cs (100%) delete mode 100644 1.5/Source/GroupAnimations/GroupAnimationStages/AnimationStage_Branch.cs rename 1.5/Source/PawnRenderNode/{ => GraphicVariants}/PawnRenderNodeProperties_GraphicVariants.cs (87%) rename 1.5/Source/PawnRenderNode/{ => GraphicVariants}/PawnRenderNodeWorker_GraphicVariants.cs (100%) rename 1.5/Source/PawnRenderNode/{ => GraphicVariants}/PawnRenderNode_GraphicVariants.cs (100%) create mode 100644 1.5/Source/RenderSubWorkers/PawnRenderSubWorker_ChangeOffset.cs create mode 100644 Patch_HumanoidAlienRaces/1.5/Source/Patches/Harmony_PatchAll.cs diff --git a/1.5/Assemblies/Rimworld-Animations.dll b/1.5/Assemblies/Rimworld-Animations.dll index 87dd739dba5d38491020f29849c918733e269744..1870329e6330cbc13bf56db1e0583ab1c9d90296 100644 GIT binary patch literal 32768 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 literal 29696 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 Ze`+x;zlTacmEXtsQ;Gb~xc{ya_`fQcsq_E< diff --git a/1.5/Defs/AnimationPropDefs/AnimationPropDef.xml b/1.5/Defs/AnimationPropDefs/AnimationPropDef.xml index df53d62..7815092 100644 --- a/1.5/Defs/AnimationPropDefs/AnimationPropDef.xml +++ b/1.5/Defs/AnimationPropDefs/AnimationPropDef.xml @@ -10,7 +10,7 @@ - + AnimProp_Banana Rimworld_Animations.PawnRenderNode_GraphicVariants Rimworld_Animations.PawnRenderNodeWorker_GraphicVariants @@ -26,7 +26,27 @@
  • AnimationProps/Cat/Cat1
  • AnimationProps/Cat/Cat2
  • + + True
    + + + RenderNodeTag_Genitals + + + + AnimationProp_Genitals + + + AnimProp_Genitals + false + RenderNodeTag_Genitals + Body + + Head + 95 + + diff --git a/1.5/Defs/GroupAnimationDefs/TestGroupAnimation1.xml b/1.5/Defs/GroupAnimationDefs/TestGroupAnimation1.xml index 7fb19e6..6be826f 100644 --- a/1.5/Defs/GroupAnimationDefs/TestGroupAnimation1.xml +++ b/1.5/Defs/GroupAnimationDefs/TestGroupAnimation1.xml @@ -24,53 +24,18 @@ + + + - +
  • @@ -87,12 +52,11 @@
  • - + + +
  • GroinToAppropriateHeight
  • +
  • GroinToAppropriateHeight
  • +
    + diff --git a/1.5/Defs/OffsetDefs/OffsetDef_GroinToAppropriateHeight.xml b/1.5/Defs/OffsetDefs/OffsetDef_GroinToAppropriateHeight.xml index 4503f96..6566375 100644 --- a/1.5/Defs/OffsetDefs/OffsetDef_GroinToAppropriateHeight.xml +++ b/1.5/Defs/OffsetDefs/OffsetDef_GroinToAppropriateHeight.xml @@ -1,38 +1,44 @@  - + GroinToAppropriateHeight - -
  • - Male - (0, 0, 0.5) + +
  • + +
  • Alien_Orassan
  • + + (0, 0, 5) -
    - -
  • - MinecraftCreeper - - - (0, 0, 0.5) - (0, 0, 0.3) - - - (0, 0, 0.5) - (0, 0, 0.3) - - + +
  • + +
  • Human
  • + + +
  • Hulk(0, 0, 0.5)
  • +
  • Thin(0, 0, 0.3)
  • +
  • Female(0, 0, 0.4)
  • +
    -
  • - MinecraftPig - Male - (0, 0, -0.5) + +
  • + +
  • MinecraftCreeper
  • + + +
  • Hulk(0, 0, 0.5)
  • +
  • Male(0, 0, 0.5)
  • +
  • Female(0, 0, 0.5)
  • +
  • Thin(0, 0, 0.3)
  • +
    + +
  • Hulk(0, 0, 0.5)
  • +
  • Male(0, 0, 0.5)
  • +
  • Female(0, 0, 0.5)
  • +
  • Thin(0, 0, 0.3)
  • +
    -
  • - MinecraftPig - Female - (0, 0, -0.5) -
  • -
    -
    + +
    \ No newline at end of file diff --git a/1.5/Patches/AnimationPatch_PawnRenderTree_OffsetSubWorker.xml b/1.5/Patches/AnimationPatch_PawnRenderTree_OffsetSubWorker.xml new file mode 100644 index 0000000..6aa36a8 --- /dev/null +++ b/1.5/Patches/AnimationPatch_PawnRenderTree_OffsetSubWorker.xml @@ -0,0 +1,27 @@ + + + + + Always + +
  • + /Defs/PawnRenderTreeDef/root/subworkerClasses + Always + + /Defs/PawnRenderTreeDef/root + + + + +
  • + +
  • + /Defs/PawnRenderTreeDef/root/subworkerClasses + +
  • Rimworld_Animations.PawnRenderSubWorker_ChangeOffset
  • + + +
    +
    + +
    \ No newline at end of file diff --git a/1.5/Source/Actors/BodyTypeOffset.cs b/1.5/Source/Actors/BodyTypeOffset.cs deleted file mode 100644 index 82a23a3..0000000 --- a/1.5/Source/Actors/BodyTypeOffset.cs +++ /dev/null @@ -1,18 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Linq; -using System.Text; -using System.Threading.Tasks; -using UnityEngine; - -namespace Rimworld_Animations { - public class BodyTypeOffset { - - public Vector2? Male; - public Vector2? Female; - public Vector2? Thin; - public Vector2? Hulk; - public Vector2? Fat; - - } -} diff --git a/1.5/Source/Animations/AnimationOffsets/AnimationOffsetDef.cs b/1.5/Source/Animations/AnimationOffsets/AnimationOffsetDef.cs new file mode 100644 index 0000000..a939d66 --- /dev/null +++ b/1.5/Source/Animations/AnimationOffsets/AnimationOffsetDef.cs @@ -0,0 +1,33 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; +using UnityEngine; +using Verse; + +namespace Rimworld_Animations +{ + public class AnimationOffsetDef : Def + { + + public List offsets; + + public Vector3 FindOffset(Pawn pawn) + { + foreach (BaseAnimationOffset animOffset in offsets) + { + if (animOffset.appliesToPawn(pawn)) { + + Vector3? offset = animOffset.getOffset(pawn); + return (offset == null ? Vector3.zero : (Vector3)offset); + + } + } + + return Vector3.zero; + } + + + } +} diff --git a/1.5/Source/Animations/AnimationOffsets/Offsets/AnimationOffset_BodyType.cs b/1.5/Source/Animations/AnimationOffsets/Offsets/AnimationOffset_BodyType.cs new file mode 100644 index 0000000..3ea9f74 --- /dev/null +++ b/1.5/Source/Animations/AnimationOffsets/Offsets/AnimationOffset_BodyType.cs @@ -0,0 +1,23 @@ +using RimWorld; +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; +using UnityEngine; +using Verse; + +namespace Rimworld_Animations +{ + public class AnimationOffset_BodyType : BaseAnimationOffset + { + + public List offsets; + + public override Vector3? getOffset(Pawn pawn) + { + return offsets.Find(x => x.bodyType == pawn.story.bodyType)?.offset; + } + } + +} diff --git a/1.5/Source/Animations/AnimationOffsets/Offsets/AnimationOffset_BodyTypeGendered.cs b/1.5/Source/Animations/AnimationOffsets/Offsets/AnimationOffset_BodyTypeGendered.cs new file mode 100644 index 0000000..3809af2 --- /dev/null +++ b/1.5/Source/Animations/AnimationOffsets/Offsets/AnimationOffset_BodyTypeGendered.cs @@ -0,0 +1,30 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; +using UnityEngine; +using Verse; + +namespace Rimworld_Animations +{ + public class AnimationOffset_BodyTypeGendered : BaseAnimationOffset + { + + public List offsetsMale; + public List offsetsFemale; + + public override Vector3? getOffset(Pawn pawn) + { + if (pawn.gender == Gender.Female) + { + return offsetsFemale.Find(x => x.bodyType == pawn.story.bodyType)?.offset; + } + else + { + return offsetsMale.Find(x => x.bodyType == pawn.story.bodyType)?.offset; + } + + } + } +} diff --git a/1.5/Source/Animations/AnimationOffsets/Offsets/AnimationOffset_Single.cs b/1.5/Source/Animations/AnimationOffsets/Offsets/AnimationOffset_Single.cs new file mode 100644 index 0000000..7ea3135 --- /dev/null +++ b/1.5/Source/Animations/AnimationOffsets/Offsets/AnimationOffset_Single.cs @@ -0,0 +1,21 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; +using UnityEngine; +using Verse; + +namespace Rimworld_Animations +{ + public class AnimationOffset_Single : BaseAnimationOffset + { + + public Vector3 offset; + + public override Vector3? getOffset(Pawn pawn) + { + return offset; + } + } +} diff --git a/1.5/Source/Animations/AnimationOffsets/Offsets/BaseAnimationOffset.cs b/1.5/Source/Animations/AnimationOffsets/Offsets/BaseAnimationOffset.cs new file mode 100644 index 0000000..d0ccd19 --- /dev/null +++ b/1.5/Source/Animations/AnimationOffsets/Offsets/BaseAnimationOffset.cs @@ -0,0 +1,25 @@ +using RimWorld; +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; +using UnityEngine; +using Verse; + +namespace Rimworld_Animations +{ + public abstract class BaseAnimationOffset + { + public List races; + + public abstract Vector3? getOffset(Pawn pawn); + + public bool appliesToPawn(Pawn pawn) + { + return races.Contains(pawn.def); + + } + + } +} diff --git a/1.5/Source/Animations/AnimationOffsets/Offsets/BodyTypeOffset.cs b/1.5/Source/Animations/AnimationOffsets/Offsets/BodyTypeOffset.cs new file mode 100644 index 0000000..92e7b71 --- /dev/null +++ b/1.5/Source/Animations/AnimationOffsets/Offsets/BodyTypeOffset.cs @@ -0,0 +1,17 @@ +using RimWorld; +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; +using UnityEngine; + +namespace Rimworld_Animations +{ + + public class BodyTypeOffset + { + public BodyTypeDef bodyType; + public Vector3 offset; + } +} diff --git a/1.5/Source/AnimationProps/AnimationPropDef.cs b/1.5/Source/Animations/AnimationProps/AnimationPropDef.cs similarity index 74% rename from 1.5/Source/AnimationProps/AnimationPropDef.cs rename to 1.5/Source/Animations/AnimationProps/AnimationPropDef.cs index 1b4c1c3..9acab99 100644 --- a/1.5/Source/AnimationProps/AnimationPropDef.cs +++ b/1.5/Source/Animations/AnimationProps/AnimationPropDef.cs @@ -10,7 +10,7 @@ namespace Rimworld_Animations public class AnimationPropDef : Def { - public PawnRenderNodeProperties_GraphicVariants animPropProperties; + public PawnRenderNodeProperties animPropProperties; } } diff --git a/1.5/Source/AnimationWorkers/AnimationWorker_KeyframesExtended.cs b/1.5/Source/Animations/AnimationWorkers/AnimationWorker_KeyframesExtended.cs similarity index 98% rename from 1.5/Source/AnimationWorkers/AnimationWorker_KeyframesExtended.cs rename to 1.5/Source/Animations/AnimationWorkers/AnimationWorker_KeyframesExtended.cs index ae12151..1b41241 100644 --- a/1.5/Source/AnimationWorkers/AnimationWorker_KeyframesExtended.cs +++ b/1.5/Source/Animations/AnimationWorkers/AnimationWorker_KeyframesExtended.cs @@ -18,6 +18,7 @@ namespace Rimworld_Animations public override Vector3 OffsetAtTick(int tick, PawnDrawParms parms) { //Todo: Use this for bodyoffsets + //or maybe make a rendersubworker for it instead return base.OffsetAtTick(tick, parms); } diff --git a/1.5/Source/GroupAnimations/GroupAnimationContexts/BaseGroupAnimationContext.cs b/1.5/Source/Animations/GroupAnimations/GroupAnimationContexts/BaseGroupAnimationContext.cs similarity index 100% rename from 1.5/Source/GroupAnimations/GroupAnimationContexts/BaseGroupAnimationContext.cs rename to 1.5/Source/Animations/GroupAnimations/GroupAnimationContexts/BaseGroupAnimationContext.cs diff --git a/1.5/Source/GroupAnimations/GroupAnimationContexts/GroupAnimationContext_RJWSex.cs b/1.5/Source/Animations/GroupAnimations/GroupAnimationContexts/GroupAnimationContext_RJWSex.cs similarity index 100% rename from 1.5/Source/GroupAnimations/GroupAnimationContexts/GroupAnimationContext_RJWSex.cs rename to 1.5/Source/Animations/GroupAnimations/GroupAnimationContexts/GroupAnimationContext_RJWSex.cs diff --git a/1.5/Source/GroupAnimations/GroupAnimationDef.cs b/1.5/Source/Animations/GroupAnimations/GroupAnimationDef.cs similarity index 80% rename from 1.5/Source/GroupAnimations/GroupAnimationDef.cs rename to 1.5/Source/Animations/GroupAnimations/GroupAnimationDef.cs index c54984f..55f3bea 100644 --- a/1.5/Source/GroupAnimations/GroupAnimationDef.cs +++ b/1.5/Source/Animations/GroupAnimations/GroupAnimationDef.cs @@ -3,6 +3,7 @@ using System.Collections.Generic; using System.Linq; using System.Text; using System.Threading.Tasks; +using UnityEngine; using Verse; namespace Rimworld_Animations @@ -12,6 +13,7 @@ namespace Rimworld_Animations public int numActors; public List animationStages; public List contexts; + public List offsetDefs; public bool canAnimationBeUsed(List actors, out int reorder) @@ -48,5 +50,12 @@ namespace Rimworld_Animations return animations; } + + public Vector3? GetOffset(int actor, Pawn pawn, int reorder = 0) + { + //element at or default to stop errors + if (offsetDefs == null) return null; + return offsetDefs[(actor + reorder) % numActors].FindOffset(pawn); + } } } diff --git a/1.5/Source/GroupAnimations/GroupAnimationStages/AnimationStage.cs b/1.5/Source/Animations/GroupAnimations/GroupAnimationStages/AnimationStage.cs similarity index 100% rename from 1.5/Source/GroupAnimations/GroupAnimationStages/AnimationStage.cs rename to 1.5/Source/Animations/GroupAnimations/GroupAnimationStages/AnimationStage.cs diff --git a/1.5/Source/Animations/GroupAnimations/GroupAnimationStages/AnimationStage_Branch.cs b/1.5/Source/Animations/GroupAnimations/GroupAnimationStages/AnimationStage_Branch.cs new file mode 100644 index 0000000..abee2e7 --- /dev/null +++ b/1.5/Source/Animations/GroupAnimations/GroupAnimationStages/AnimationStage_Branch.cs @@ -0,0 +1,26 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; +using Verse; + +namespace Rimworld_Animations +{ + public class AnimationStage_Branch : AnimationStage + { + public List paths; + public override List GetAnimations(int actorNumber, int seed) + { + List animationDefs = new List(); + + //loop thru the selected groupanimationdef path + foreach (AnimationStage stage in paths[(seed * 59) % paths.Count].animationStages) + { + animationDefs.AddRange(stage.GetAnimations(actorNumber, seed)); + } + + return animationDefs; + } + } +} diff --git a/1.5/Source/GroupAnimations/GroupAnimationStages/AnimationStage_LoopRandomSelectChance.cs b/1.5/Source/Animations/GroupAnimations/GroupAnimationStages/AnimationStage_LoopRandomSelectChance.cs similarity index 100% rename from 1.5/Source/GroupAnimations/GroupAnimationStages/AnimationStage_LoopRandomSelectChance.cs rename to 1.5/Source/Animations/GroupAnimations/GroupAnimationStages/AnimationStage_LoopRandomSelectChance.cs diff --git a/1.5/Source/GroupAnimations/GroupAnimationStages/AnimationStage_TicksDuration.cs b/1.5/Source/Animations/GroupAnimations/GroupAnimationStages/AnimationStage_TicksDuration.cs similarity index 100% rename from 1.5/Source/GroupAnimations/GroupAnimationStages/AnimationStage_TicksDuration.cs rename to 1.5/Source/Animations/GroupAnimations/GroupAnimationStages/AnimationStage_TicksDuration.cs diff --git a/1.5/Source/Keyframes/ExtendedKeyframe.cs b/1.5/Source/Animations/Keyframes/ExtendedKeyframe.cs similarity index 100% rename from 1.5/Source/Keyframes/ExtendedKeyframe.cs rename to 1.5/Source/Animations/Keyframes/ExtendedKeyframe.cs diff --git a/1.5/Source/Comps/CompExtendedAnimator.cs b/1.5/Source/Comps/CompExtendedAnimator.cs index a34c8ed..a85a5fc 100644 --- a/1.5/Source/Comps/CompExtendedAnimator.cs +++ b/1.5/Source/Comps/CompExtendedAnimator.cs @@ -19,6 +19,7 @@ namespace Rimworld_Animations { private List animationQueue; private BaseExtendedAnimatorAnchor anchor; + private Vector3? offset; private bool isAnimating = false; @@ -38,12 +39,23 @@ namespace Rimworld_Animations { } } + public Vector3? Offset + { + get + { + return offset; + } + set + { + this.offset = value; + } + } + public Vector3 getAnchor() { return anchor.getDrawPos(); } - public override void CompTick() { if (isAnimating) @@ -99,19 +111,21 @@ namespace Rimworld_Animations { isAnimating = false; animationQueue = null; anchor = null; + offset = null; pawn.Drawer.renderer.SetAnimation(null); } - public void PlayGroupAnimation(List groupAnimation) + public void PlayGroupAnimation(List groupAnimation, Vector3? offset) { + this.Offset = offset; animationQueue = groupAnimation; PlayNextAnimation(); } - public void PlayGroupAnimation(List groupAnimation, BaseExtendedAnimatorAnchor anchor) + public void PlayGroupAnimation(List groupAnimation, Vector3? offset, BaseExtendedAnimatorAnchor anchor) { this.anchor = anchor; - PlayGroupAnimation(groupAnimation); + PlayGroupAnimation(groupAnimation, offset); } public override void PostExposeData() @@ -137,8 +151,16 @@ namespace Rimworld_Animations { //if animation makes use of prop, if (AnimationMakesUseOfProp(animationProp)) { + + PawnRenderNodeProperties props = animationProp.animPropProperties; + //create new render node - PawnRenderNode_GraphicVariants animRenderNode = new PawnRenderNode_GraphicVariants(pawn, animationProp.animPropProperties, pawn.Drawer.renderer.renderTree); + PawnRenderNode animRenderNode = (PawnRenderNode)Activator.CreateInstance(props.nodeClass, new object[] { + this.pawn, + props, + pawn.Drawer.renderer.renderTree + }); + animRenderNodes.Add(animRenderNode); } diff --git a/1.5/Source/GroupAnimations/GroupAnimationStages/AnimationStage_Branch.cs b/1.5/Source/GroupAnimations/GroupAnimationStages/AnimationStage_Branch.cs deleted file mode 100644 index a187270..0000000 --- a/1.5/Source/GroupAnimations/GroupAnimationStages/AnimationStage_Branch.cs +++ /dev/null @@ -1,18 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Linq; -using System.Text; -using System.Threading.Tasks; -using Verse; - -namespace Rimworld_Animations -{ - public class AnimationStage_Branch : AnimationStage - { - public List paths; - public override List GetAnimations(int actorNumber, int seed) - { - return paths[(seed * 59) % paths.Count].GetAnimations(actorNumber, seed); - } - } -} diff --git a/1.5/Source/Patches/RimworldPatches/HarmonyPatch_PawnRenderTree.cs b/1.5/Source/Patches/RimworldPatches/HarmonyPatch_PawnRenderTree.cs index 6dc336f..621b881 100644 --- a/1.5/Source/Patches/RimworldPatches/HarmonyPatch_PawnRenderTree.cs +++ b/1.5/Source/Patches/RimworldPatches/HarmonyPatch_PawnRenderTree.cs @@ -5,6 +5,7 @@ using System.Collections.Generic; using System.Linq; using System.Text; using System.Threading.Tasks; +using UnityEngine; using Verse; namespace Rimworld_Animations @@ -13,9 +14,11 @@ namespace Rimworld_Animations [HarmonyPatch(typeof(PawnRenderTree), "TryGetMatrix")] public class HarmonyPatch_PawnRenderTree { - public static void Prefix(PawnRenderTree __instance, Dictionary ___nodesByTag, PawnRenderNode node, ref PawnDrawParms parms) + public static bool Prefix(PawnRenderTree __instance, Dictionary ___nodesByTag, PawnRenderNode node, ref PawnDrawParms parms, ref Matrix4x4 matrix, ref bool __result) { - + /* + * Facing fix + */ //find lowest parent that is animating, or nothing if not animating PawnRenderNode animatingNode = node; while (animatingNode != null @@ -30,6 +33,27 @@ namespace Rimworld_Animations //change parm to facing to animate correctly parms.facing = animatingNodeAnimationWorker.facingAtTick(__instance.AnimationTick); } + + /* + * Set Render Node to absolute position + */ + if (node.Props is PawnRenderNodeProperties_GraphicVariants graphicVariantProp + && graphicVariantProp.absolutePosition) + { + matrix = parms.matrix; + float num = node.Worker.AltitudeFor(node, parms); + if (num != 0f) + { + matrix *= Matrix4x4.Translate(Vector3.up * num); + } + + __result = true; + return false; + + } + + return true; + } } diff --git a/1.5/Source/PawnRenderNode/PawnRenderNodeProperties_GraphicVariants.cs b/1.5/Source/PawnRenderNode/GraphicVariants/PawnRenderNodeProperties_GraphicVariants.cs similarity index 87% rename from 1.5/Source/PawnRenderNode/PawnRenderNodeProperties_GraphicVariants.cs rename to 1.5/Source/PawnRenderNode/GraphicVariants/PawnRenderNodeProperties_GraphicVariants.cs index 7667a26..b1a8720 100644 --- a/1.5/Source/PawnRenderNode/PawnRenderNodeProperties_GraphicVariants.cs +++ b/1.5/Source/PawnRenderNode/GraphicVariants/PawnRenderNodeProperties_GraphicVariants.cs @@ -11,6 +11,7 @@ namespace Rimworld_Animations { public List texPathVariants; + public bool absolutePosition = false; } } diff --git a/1.5/Source/PawnRenderNode/PawnRenderNodeWorker_GraphicVariants.cs b/1.5/Source/PawnRenderNode/GraphicVariants/PawnRenderNodeWorker_GraphicVariants.cs similarity index 100% rename from 1.5/Source/PawnRenderNode/PawnRenderNodeWorker_GraphicVariants.cs rename to 1.5/Source/PawnRenderNode/GraphicVariants/PawnRenderNodeWorker_GraphicVariants.cs diff --git a/1.5/Source/PawnRenderNode/PawnRenderNode_GraphicVariants.cs b/1.5/Source/PawnRenderNode/GraphicVariants/PawnRenderNode_GraphicVariants.cs similarity index 100% rename from 1.5/Source/PawnRenderNode/PawnRenderNode_GraphicVariants.cs rename to 1.5/Source/PawnRenderNode/GraphicVariants/PawnRenderNode_GraphicVariants.cs diff --git a/1.5/Source/RenderSubWorkers/PawnRenderSubWorker_ChangeOffset.cs b/1.5/Source/RenderSubWorkers/PawnRenderSubWorker_ChangeOffset.cs new file mode 100644 index 0000000..2ce182e --- /dev/null +++ b/1.5/Source/RenderSubWorkers/PawnRenderSubWorker_ChangeOffset.cs @@ -0,0 +1,30 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; +using UnityEngine; +using Verse; + +namespace Rimworld_Animations +{ + public class PawnRenderSubWorker_ChangeOffset : PawnRenderSubWorker + { + + public override void TransformOffset(PawnRenderNode node, PawnDrawParms parms, ref Vector3 offset, ref Vector3 pivot) + { + if (node.AnimationWorker is AnimationWorker_KeyframesExtended + && node.tree.pawn.TryGetComp(out CompExtendedAnimator extendedAnimator) + && extendedAnimator.IsAnimating) + { + Vector3? pawnOffset = extendedAnimator.Offset; + if (pawnOffset != null) + { + offset += (Vector3)pawnOffset; + } + + } + } + + } +} diff --git a/1.5/Source/Utilities/AnimationUtility.cs b/1.5/Source/Utilities/AnimationUtility.cs index 71c785a..2431db7 100644 --- a/1.5/Source/Utilities/AnimationUtility.cs +++ b/1.5/Source/Utilities/AnimationUtility.cs @@ -30,20 +30,21 @@ namespace Rimworld_Animations { for (int i = 0; i < participants.Count; i++) { + + Vector3? offset = groupAnimationDef.GetOffset(i, participants[i], reorder); + if (anchor is Pawn pawn && pawn == participants[i]) { List allAnimationsForPawn = groupAnimationDef.GetAllAnimationsForActor(i, seed, reorder); - participants[i].TryGetComp().PlayGroupAnimation(allAnimationsForPawn); + participants[i].TryGetComp().PlayGroupAnimation(allAnimationsForPawn, offset); } else { //each participant gets their own unique extendedanimatoranchor, important for scribe_deep saving - List allAnimationsForPawn = groupAnimationDef.GetAllAnimationsForActor(i, seed, reorder); BaseExtendedAnimatorAnchor animatorAnchor = new ExtendedAnimatorAnchor_Thing(anchor); - - participants[i].TryGetComp().PlayGroupAnimation(allAnimationsForPawn, animatorAnchor); + participants[i].TryGetComp().PlayGroupAnimation(allAnimationsForPawn, offset, animatorAnchor); } } } @@ -56,7 +57,8 @@ namespace Rimworld_Animations { for (int i = 0; i < participants.Count; i++) { List allAnimationsForPawn = groupAnimationDef.GetAllAnimationsForActor(i, seed, reorder); - participants[i].TryGetComp().PlayGroupAnimation(allAnimationsForPawn); + Vector3? offset = groupAnimationDef.GetOffset(i, participants[i], reorder); + participants[i].TryGetComp().PlayGroupAnimation(allAnimationsForPawn, offset); } } diff --git a/Patch_HumanoidAlienRaces/1.5/Assemblies/Patch_HumanoidAlienRaces.dll b/Patch_HumanoidAlienRaces/1.5/Assemblies/Patch_HumanoidAlienRaces.dll index 5673f48e4edaf9c67d24e2109eb45b211dfcd610..dc151310748a11bfce9a81ff5f81c22c3aab5320 100644 GIT binary patch delta 1078 zcmYL|O-vI(6vzKFlr2_MX)DI!2SqSd#EO6+#*c`gfZ9}BAVG=Pmep3a-LktiR1;e~ z_z`=c*^@Vk8WX%|YV@Qg#)}sc^!8dou zHh&@fyHwo5Z~03Lqt0$W5CXNMz@M5@vuE8!U>*6JsAG%S%-hW|=I2Gbd6V7nCMamN zL3%lAG2;UsNB}dN>w0#0Iyk)4!vGgFVn(kA91dxxi;U_fpv??&|6!VpmK%UVcFEEa zLrbPF>oggIwN#jF%SZ&1q$vej21bVZ$r|Lho6or?Kd^yg4MniRy0B5ygoj*8X4MB3 z!}_YW{2F?J7tGRtgul4WB}_4kojAnT;|Wcba1P5%!gs-Uf?;Mwwh8tKPGdPwp%X~Z zx2mp`t-$K5-4kb`Mm*80D5gvD<^z+8f=Es`;#7D`h{GqM>3ESD%u zrBt9l8NHlVb;EQ@Q{hnT3T4HBY#g7F<5`35{%U%3R98(O?oA*H4JoKdBZmxm2I6!I zK=-jFr}zH7p|?NZydS<;H*3yGjazMY<{qN$bq8yGjJbn#uda=cdb_{frQ6TUvh>Sl sqkCu0+nb!@)j!$V-m89d(cZ`te)EU@S=s4Wso{5e$}Z<`R_d_-1BJWL;Q#;t delta 697 zcmXw%%WD%+6vn@Mo6K}#J8jdnnzrDCu@NzZ+NwnqX|xU&SdrQoB^Vn_BE|@b861wGvBWn zd((R{AcIkFY1;lg2wVik7_imiMY`K&fi_ydrHugaY2d2Rj9^7{V3^J`kia`( z;2ZNjb6jYrof&1$vVRQg8}a(#&Fx?SF*SA z*-SZCm`7aoo7KIIw$xYrSp7YkSpK;*{QAKsPyI3btkw^Yu1$xJu0B_8>p#_F?GLUs mej?o^qXfr`^vaDvb=_L7J9b&r?Z9@63>~j`+5d$%WbOc81$a;Z diff --git a/Patch_HumanoidAlienRaces/1.5/Source/Patches/Harmony_PatchAll.cs b/Patch_HumanoidAlienRaces/1.5/Source/Patches/Harmony_PatchAll.cs new file mode 100644 index 0000000..1ce3601 --- /dev/null +++ b/Patch_HumanoidAlienRaces/1.5/Source/Patches/Harmony_PatchAll.cs @@ -0,0 +1,23 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; +using Verse; +using HarmonyLib; +using System.Reflection; + +namespace Patch_SexToysMasturbation +{ + + [StaticConstructorOnStartup] + public static class Harmony_PatchAll { + + static Harmony_PatchAll() { + + Harmony val = new Harmony("harmonypatch"); + val.PatchAll(Assembly.GetExecutingAssembly()); + + } + } +} diff --git a/Patch_HumanoidAlienRaces/Patch_HumanoidAlienRaces.csproj b/Patch_HumanoidAlienRaces/Patch_HumanoidAlienRaces.csproj index 4661863..5841608 100644 --- a/Patch_HumanoidAlienRaces/Patch_HumanoidAlienRaces.csproj +++ b/Patch_HumanoidAlienRaces/Patch_HumanoidAlienRaces.csproj @@ -38,6 +38,7 @@ ..\..\..\..\..\workshop\content\294100\839005762\1.5\Assemblies\AlienRace.dll + False ..\..\..\RimWorldWin64_Data\Managed\Assembly-CSharp.dll @@ -69,7 +70,12 @@ + + + + + \ No newline at end of file diff --git a/Rimworld-Animations.csproj b/Rimworld-Animations.csproj index 5663d12..e676bbd 100644 --- a/Rimworld-Animations.csproj +++ b/Rimworld-Animations.csproj @@ -71,9 +71,14 @@ - - - + + + + + + + + @@ -82,14 +87,14 @@ - - - - - - - - + + + + + + + + @@ -107,9 +112,10 @@ - - - + + + + @@ -127,6 +133,7 @@ + @@ -178,7 +185,6 @@ - \ No newline at end of file