mirror of
https://gitgud.io/lutepickle/rjw_menstruation.git
synced 2024-08-14 22:46:52 +00:00
Compare commits
1 commit
9afb3c0df0
...
4382decbc7
Author | SHA1 | Date | |
---|---|---|---|
|
4382decbc7 |
10 changed files with 122 additions and 57 deletions
Binary file not shown.
|
@ -145,4 +145,10 @@
|
|||
</comps>
|
||||
</value>
|
||||
</Operation>
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
</Patch>
|
|
@ -110,6 +110,9 @@ namespace RJW_Menstruation
|
|||
else return base.ShouldBeInEstrus();
|
||||
}
|
||||
|
||||
protected override float RandomOvulationChance => 0;
|
||||
protected override float RandomOvulationChance()
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -127,6 +127,7 @@ namespace RJW_Menstruation
|
|||
protected float implantationChanceCache = -1.0f;
|
||||
protected int opcache = -1;
|
||||
protected float antisperm = 0.0f;
|
||||
protected float? originvagsize = null;
|
||||
// RJW pregnancy, or Biotech pregnancy/labor/laborpushing
|
||||
protected Hediff pregnancy = null;
|
||||
|
||||
|
@ -178,8 +179,7 @@ namespace RJW_Menstruation
|
|||
|
||||
public float HoursBetweenSimulations => (float)TickInterval / GenDate.TicksPerHour;
|
||||
|
||||
public Hediff Pregnancy
|
||||
{
|
||||
public Hediff Pregnancy {
|
||||
get
|
||||
{
|
||||
if (pregnancy == null) return null;
|
||||
|
@ -322,7 +322,6 @@ namespace RJW_Menstruation
|
|||
// Implant factor will be based solely on pawn age, plus any rollover from ovulation chance
|
||||
float factor = 1.0f;
|
||||
StatDefOf.Fertility.GetStatPart<StatPart_FertilityByGenderAge>()?.TransformValue(StatRequest.For(Pawn), ref factor);
|
||||
if (factor <= 0.0f) return 0.0f;
|
||||
if (OvulationChance > 1.0f) factor *= OvulationChance;
|
||||
return Props.baseImplantationChanceFactor * FertilityModifier * factor;
|
||||
}
|
||||
|
@ -564,6 +563,19 @@ namespace RJW_Menstruation
|
|||
}
|
||||
}
|
||||
|
||||
public float OriginVagSize
|
||||
{
|
||||
get
|
||||
{
|
||||
if (originvagsize == null)
|
||||
{
|
||||
originvagsize = parent.Severity;
|
||||
}
|
||||
return originvagsize ?? 0.1f;
|
||||
}
|
||||
set => originvagsize = value;
|
||||
}
|
||||
|
||||
public int CurStageIntervalTicks
|
||||
{
|
||||
get => currentIntervalTicks;
|
||||
|
@ -644,6 +656,7 @@ namespace RJW_Menstruation
|
|||
Scribe_Values.Look(ref ovarypower, "ovarypower", ovarypower, true);
|
||||
Scribe_Values.Look(ref eggstack, "eggstack", 0);
|
||||
Scribe_Values.Look(ref estrusflag, "estrusflag", false);
|
||||
Scribe_Values.Look(ref originvagsize, "originvagsize", originvagsize, true);
|
||||
Scribe_Values.Look(ref DoCleanWomb, "DoCleanWomb", false);
|
||||
Scribe_References.Look(ref pregnancy, "pregnancy");
|
||||
if (Scribe.mode == LoadSaveMode.PostLoadInit)
|
||||
|
@ -668,8 +681,10 @@ namespace RJW_Menstruation
|
|||
opcache = -1;
|
||||
|
||||
if (Pawn.genes == null || !ModsConfig.BiotechActive) return;
|
||||
foreach (MenstruationModExtension extension in Pawn.genes.GenesListForReading.Select(gene => gene.def.GetModExtension<MenstruationModExtension>()).Where(ext => ext != null))
|
||||
foreach (MenstruationModExtension extension in Pawn.genes.GenesListForReading.Select(gene => gene.def.GetModExtension<MenstruationModExtension>()))
|
||||
{
|
||||
if (extension == null) continue;
|
||||
|
||||
eggLifeSpanTicks = (int)(eggLifeSpanTicks * extension.eggLifeTimeFactor);
|
||||
if (extension.alwaysEstrus) estrusLevel = EstrusLevel.Visible;
|
||||
else if (extension.neverEstrus) estrusLevel = EstrusLevel.None;
|
||||
|
@ -1562,6 +1577,9 @@ namespace RJW_Menstruation
|
|||
return amount;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
protected void EggDecay()
|
||||
{
|
||||
HashSet<Egg> deadeggs = new HashSet<Egg>();
|
||||
|
@ -1638,7 +1656,7 @@ namespace RJW_Menstruation
|
|||
eggnum = 1f;
|
||||
}
|
||||
eggnum *= ovulationFactor;
|
||||
int toOvulate = Math.Max(1, (int)eggnum + eggstack);
|
||||
int toOvulate = (int)eggnum + eggstack;
|
||||
|
||||
int ovulated = 0;
|
||||
for (int i = 0; i < toOvulate; i++)
|
||||
|
@ -1649,7 +1667,7 @@ namespace RJW_Menstruation
|
|||
}
|
||||
ovarypower -= ovulated;
|
||||
eggstack = 0;
|
||||
if (Configurations.Debug && ovulated < toOvulate)
|
||||
if (Configurations.Debug && ovulated != toOvulate)
|
||||
Log.Message($"{Pawn} ovulated {ovulated}/{toOvulate} eggs ({OvulationChance.ToStringPercent()} chance)");
|
||||
|
||||
GoNextStage(Stage.Luteal);
|
||||
|
@ -1896,13 +1914,16 @@ namespace RJW_Menstruation
|
|||
else return Rand.Range(0.6f, 1.0f);
|
||||
}
|
||||
|
||||
protected virtual float RandomOvulationChance => (float)Props.ovulationIntervalHours / GenDate.HoursPerDay;
|
||||
protected virtual float RandomOvulationChance()
|
||||
{
|
||||
return (float)Props.ovulationIntervalHours / GenDate.HoursPerDay;
|
||||
}
|
||||
|
||||
protected Stage RandomStage()
|
||||
{
|
||||
Stage stage = Rand.ElementByWeight(
|
||||
Stage.Follicular, Props.follicularIntervalDays - Props.bleedingIntervalDays,
|
||||
Stage.Ovulatory, RandomOvulationChance,
|
||||
Stage.Ovulatory, RandomOvulationChance(),
|
||||
Stage.Luteal, Props.lutealIntervalDays,
|
||||
Stage.Bleeding, Props.bleedingIntervalDays);
|
||||
|
||||
|
@ -2014,6 +2035,28 @@ namespace RJW_Menstruation
|
|||
|
||||
public class HediffComp_Anus : HediffComp
|
||||
{
|
||||
public CompProperties_Anus Props => (CompProperties_Anus)props;
|
||||
protected float? originanussize;
|
||||
|
||||
public float OriginAnusSize
|
||||
{
|
||||
get
|
||||
{
|
||||
if (originanussize == null)
|
||||
{
|
||||
originanussize = parent.Severity;
|
||||
}
|
||||
return originanussize ?? 0.1f;
|
||||
}
|
||||
}
|
||||
|
||||
public override void CompExposeData()
|
||||
{
|
||||
base.CompExposeData();
|
||||
Scribe_Values.Look(ref originanussize, "originanussize", originanussize, true);
|
||||
}
|
||||
|
||||
public override void CompPostTick(ref float severityAdjustment)
|
||||
{
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -36,7 +36,7 @@ namespace RJW_Menstruation
|
|||
if (ticksToNextCycle < -50000)
|
||||
ticksToNextCycle = Rand.Range(0, averageCycleIntervalTicks);
|
||||
// Make the cutoff halfway into cycle, just to be sure there isn't a double-cycle the first time
|
||||
if ((curStage == Stage.Follicular || curStage == Stage.Ovulatory || curStage == Stage.Luteal || curStage == Stage.Bleeding)
|
||||
if ((curStage == Stage.Follicular || curStage == Stage.Luteal || curStage == Stage.Bleeding)
|
||||
&& (averageCycleIntervalTicks - ticksToNextCycle) / 2 >= GenDate.TicksPerDay * (Props.follicularIntervalDays + Props.lutealIntervalDays) / cycleSpeed)
|
||||
GoNextStage(Stage.Anestrus);
|
||||
}
|
||||
|
|
|
@ -141,7 +141,7 @@ namespace RJW_Menstruation
|
|||
else if (gestationProgress < 0.8f) icon = fetustex + "04";
|
||||
else icon = fetustex + "05";
|
||||
|
||||
return TryGetTwinsIcon(icon, babycount) ?? ContentFinder<Texture2D>.Get(icon, true);
|
||||
return TryGetTwinsIcon(icon, babycount) ?? ContentFinder<Texture2D>.Get((icon), true);
|
||||
}
|
||||
|
||||
public static Texture2D TryGetTwinsIcon(string path, int babycount)
|
||||
|
@ -160,7 +160,7 @@ namespace RJW_Menstruation
|
|||
|
||||
List<Hediff_InsectEgg> insectEggs = new List<Hediff_InsectEgg>();
|
||||
comp.Pawn.health.hediffSet.GetHediffs(ref insectEggs);
|
||||
if (insectEggs?.Sum(hediff => hediff.eggssize) > 1.0f) return null; // same logic as "Stuffed" in GetInsectEggedIcon
|
||||
if (!insectEggs.NullOrEmpty() && insectEggs.Sum(hediff => hediff.eggssize) > 1.0f) return null; // same logic as "Stuffed" in GetInsectEggedIcon
|
||||
|
||||
string icon = comp.WombTex;
|
||||
float cumpercent = comp.TotalCumPercent;
|
||||
|
@ -183,7 +183,7 @@ namespace RJW_Menstruation
|
|||
else if (cumpercent < 0.89f) icon += "_Cum_15";
|
||||
else if (cumpercent < 0.95f) icon += "_Cum_16";
|
||||
else icon += "_Cum_17";
|
||||
Texture2D cumtex = ContentFinder<Texture2D>.Get(icon, true);
|
||||
Texture2D cumtex = ContentFinder<Texture2D>.Get((icon), true);
|
||||
return cumtex;
|
||||
}
|
||||
public static Texture2D GetInsectEggedIcon(this HediffComp_Menstruation comp)
|
||||
|
@ -306,13 +306,15 @@ namespace RJW_Menstruation
|
|||
}
|
||||
|
||||
|
||||
public static Texture2D GetGenitalIcon(this Pawn pawn, HediffComp_Menstruation comp)
|
||||
public static Texture2D GetGenitalIcon(this Pawn pawn, HediffComp_Menstruation comp, bool drawOrigin = false)
|
||||
{
|
||||
Hediff hediff = comp?.parent;
|
||||
if (hediff == null) return ContentFinder<Texture2D>.Get("Genitals/Vagina00", true);
|
||||
//HediffComp_Menstruation comp = hediff.GetMenstruationComp();
|
||||
string icon;
|
||||
float severity = hediff.Severity;
|
||||
float severity;
|
||||
if (drawOrigin) severity = comp.OriginVagSize;
|
||||
else severity = hediff.Severity;
|
||||
if (comp != null) icon = comp.VagTex;
|
||||
else icon = "Genitals/Vagina";
|
||||
|
||||
|
@ -329,18 +331,30 @@ namespace RJW_Menstruation
|
|||
else if (severity < 1.01f) icon += "10"; //cavernous
|
||||
else icon += "11"; //abyssal
|
||||
|
||||
return ContentFinder<Texture2D>.Get(icon, true);
|
||||
return ContentFinder<Texture2D>.Get((icon), true);
|
||||
}
|
||||
|
||||
public static Texture2D GetAnalIcon(this Pawn pawn)
|
||||
public static Texture2D GetAnalIcon(this Pawn pawn, bool drawOrigin = false)
|
||||
{
|
||||
Hediff hediff = pawn.health.hediffSet.hediffs.FirstOrDefault(h => VariousDefOf.AllAnuses.Contains(h.def)) ??
|
||||
pawn.health.hediffSet.hediffs.FirstOrDefault(h => h.def.defName.ToLower().Contains("anus"));
|
||||
if (hediff == null) return ContentFinder<Texture2D>.Get("Genitals/Anal00", true);
|
||||
|
||||
string icon = ((CompProperties_Anus)hediff.GetAnusComp()?.props)?.analTex ?? "Genitals/Anal";
|
||||
float severity = hediff.Severity;
|
||||
if (hediff == null) return ContentFinder<Texture2D>.Get(("Genitals/Anal00"), true);
|
||||
|
||||
string icon;
|
||||
float severity;
|
||||
HediffComp_Anus comp = hediff.GetAnusComp();
|
||||
if (comp != null)
|
||||
{
|
||||
CompProperties_Anus Props = (CompProperties_Anus)comp.props;
|
||||
icon = Props.analTex ?? "Genitals/Anal";
|
||||
if (drawOrigin) severity = comp.OriginAnusSize;
|
||||
else severity = hediff.Severity;
|
||||
}
|
||||
else
|
||||
{
|
||||
icon = "Genitals/Anal";
|
||||
severity = hediff.Severity;
|
||||
}
|
||||
if (severity < 0.20f) icon += "00"; //micro
|
||||
else if (severity < 0.40f) icon += "01"; //tight
|
||||
else if (severity < 0.60f) icon += "02"; //average
|
||||
|
@ -348,7 +362,7 @@ namespace RJW_Menstruation
|
|||
else if (severity < 1.01f) icon += "04"; //cavernous
|
||||
else icon += "05"; //abyssal
|
||||
|
||||
return ContentFinder<Texture2D>.Get(icon, true);
|
||||
return ContentFinder<Texture2D>.Get((icon), true);
|
||||
}
|
||||
|
||||
public static float GestationHours(this Hediff hediff)
|
||||
|
|
|
@ -225,7 +225,9 @@ namespace RJW_Menstruation
|
|||
bool newHasStats = !DirtyDef.equippedStatOffsets.NullOrEmpty();
|
||||
def = DirtyDef;
|
||||
dirty = true;
|
||||
Wearer.outfits?.forcedHandler?.SetForced(this, false);
|
||||
OutfitForcedHandler forcedHandler = Wearer.outfits?.forcedHandler;
|
||||
if (forcedHandler?.IsForced(this) ?? false)
|
||||
forcedHandler.SetForced(this, false);
|
||||
if (oldHasStats || newHasStats)
|
||||
Wearer.health.capacities.Notify_CapacityLevelsDirty();
|
||||
Wearer.apparel.Notify_ApparelChanged();
|
||||
|
@ -272,7 +274,7 @@ namespace RJW_Menstruation
|
|||
public override void DirtyEffect(int tickInterval)
|
||||
{
|
||||
|
||||
if (wearTicks > MinHrstoDirtyEffect * GenDate.TicksPerHour && Rand.MTBEventOccurs(100.0f, GenDate.TicksPerHour, tickInterval) && !(Wearer.apparel?.IsLocked(this) ?? false))
|
||||
if (wearTicks > MinHrstoDirtyEffect * GenDate.TicksPerHour && Rand.MTBEventOccurs(100.0f, GenDate.TicksPerHour, tickInterval) && !Wearer.apparel.IsLocked(this))
|
||||
{
|
||||
Wearer.health.AddHediff(HediffDefOf.WoundInfection, Genital_Helper.get_genitalsBPR(Wearer));
|
||||
}
|
||||
|
|
|
@ -388,9 +388,10 @@ namespace RJW_Menstruation
|
|||
Rect genitalIconRect = new Rect(rect.x, rect.y + fontheight, genitalRectWidth, genitalRectHeight);
|
||||
Rect genitalVaginaLabelRect = new Rect(rect.x, rect.y + 10f, genitalRectWidth, fontheight);
|
||||
Rect genitalAnusLabelRect = new Rect(rect.x, rect.y + fontheight + genitalRectHeight, genitalRectWidth, fontheight);
|
||||
bool showOrigin = Mouse.IsOver(genitalIconRect) && Input.GetMouseButton(0);
|
||||
|
||||
vagina = pawn.GetGenitalIcon(comp);
|
||||
anal = pawn.GetAnalIcon();
|
||||
vagina = pawn.GetGenitalIcon(comp, showOrigin);
|
||||
anal = pawn.GetAnalIcon(showOrigin);
|
||||
GUI.color = new Color(1.00f, 0.47f, 0.47f, 1);
|
||||
GUI.Box(rect, "", boxstyle);
|
||||
GUI.color = Utility.SafeSkinColor(pawn);
|
||||
|
|
|
@ -58,8 +58,9 @@ namespace RJW_Menstruation
|
|||
get
|
||||
{
|
||||
if (allraces != null) return allraces;
|
||||
allraces = DefDatabase<ThingDef>.AllDefsListForReading.Where(thingdef => thingdef.race?.IsFlesh ?? false).ToList();
|
||||
|
||||
List<ThingDef> allThings = DefDatabase<ThingDef>.AllDefsListForReading;
|
||||
allraces = allThings.FindAll(x => x.race != null && x.race.IsFlesh);
|
||||
return allraces;
|
||||
}
|
||||
}
|
||||
|
@ -68,8 +69,9 @@ namespace RJW_Menstruation
|
|||
get
|
||||
{
|
||||
if (allkinds != null) return allkinds;
|
||||
allkinds = DefDatabase<PawnKindDef>.AllDefsListForReading.Where(pawnkinddef => pawnkinddef.race != null).ToList();
|
||||
|
||||
List<PawnKindDef> allKinds = DefDatabase<PawnKindDef>.AllDefsListForReading;
|
||||
allkinds = allKinds.FindAll(x => x.race != null);
|
||||
return allkinds;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,9 +1,7 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<ModMetaData>
|
||||
<packageId>rjw.menstruation</packageId>
|
||||
<name>RJW Menstruation Cycle</name>
|
||||
<author>lutepickle</author>
|
||||
<url>https://gitgud.io/lutepickle/rjw_menstruation/</url>
|
||||
<supportedVersions>
|
||||
<li>1.2</li>
|
||||
<li>1.3</li>
|
||||
|
@ -30,17 +28,13 @@
|
|||
<li>Abraxas.RJW.RaceSupport</li>
|
||||
<li>rjw.milk.humanoid</li>
|
||||
</loadAfter>
|
||||
<incompatibleWithByVersion>
|
||||
<v1.4>
|
||||
<li>conit.thebirdsandthebees</li> <!--Breaks fertility calculations-->
|
||||
</v1.4>
|
||||
</incompatibleWithByVersion>
|
||||
<packageId>rjw.menstruation</packageId>
|
||||
<description>Adds menstruation mechanics to vaginas:
|
||||
|
||||
Wombs cycle between follicular, luteal, and bleeding phases
|
||||
Tracks eggs ovulated and cum in wombs to determine pregnancy
|
||||
Womb icon and status window
|
||||
Estrus and pheromone effects
|
||||
Estrus effects
|
||||
Race-specific fetus images for many vanilla animals
|
||||
Pregnancies from multiple eggs and different fathers
|
||||
Identical siblings
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue