Skip to content

Commit

Permalink
Merge pull request #2971 from CombatExtended-Continued/5.6hf-stable
Browse files Browse the repository at this point in the history
Hotfix for current stable
  • Loading branch information
N7Huntsman authored Feb 1, 2024
2 parents 370ed14 + 303ce5e commit 34a2a36
Show file tree
Hide file tree
Showing 5 changed files with 44 additions and 142 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -77,8 +77,8 @@
</li>

<!-- == costList == -->
<li Class="PatchOperationReplace">
<xpath>Defs/ThingDef[defName="Turret_GatlingGun"]/costList</xpath>
<li Class="PatchOperationAdd">
<xpath>Defs/ThingDef[defName="Turret_GatlingGun"]</xpath>
<value>
<costList>
<Steel>325</Steel>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -246,7 +246,7 @@ public void AddSuppression(float amount, IntVec3 origin)
}
public bool IgnoreSuppresion(IntVec3 origin)
{
return BlockerRegistry.PawnUnsuppresableFromCallback(parent as Pawn, origin) || SuppressionUtility.InterceptorZonesFor((Pawn)parent).Where(x => x.Contains(parent.Position)).Any(x => !x.Contains(origin));
return BlockerRegistry.PawnUnsuppressableFromCallback(parent as Pawn, origin) || SuppressionUtility.InterceptorZonesFor((Pawn)parent).Where(x => x.Contains(parent.Position)).Any(x => !x.Contains(origin));
}

public override void CompTick()
Expand Down
163 changes: 35 additions & 128 deletions Source/CombatExtended/CombatExtended/Projectiles/ProjectileCE.cs
Original file line number Diff line number Diff line change
Expand Up @@ -28,17 +28,6 @@ public abstract class ProjectileCE : ThingWithComps
/// </summary>
protected const int collisionCheckSize = 5;

#region Kinetic Projectiles
protected bool lerpPosition = true;
protected bool kinit = false;
protected float ballisticCoefficient;
protected float mass;
protected float radius;
protected float gravity;
protected Vector3 velocity;
protected float initialSpeed;
#endregion

#region Origin destination
public bool OffMapOrigin = false;

Expand Down Expand Up @@ -112,11 +101,7 @@ public virtual float DamageAmount
this.damageAmount = def.projectile.GetDamageAmount(weaponDamageMultiplier);
}

if (lerpPosition)
{
return (float)this.damageAmount;
}
return ((float)this.damageAmount) * (shotSpeed * shotSpeed) / (initialSpeed * initialSpeed);
return (float)this.damageAmount;
}
}

Expand All @@ -139,7 +124,7 @@ public virtual float DamageAmount
#region Vanilla
public bool landed;
public int ticksToImpact;
protected Sustainer ambientSustainer;
private Sustainer ambientSustainer;

#endregion

Expand All @@ -148,25 +133,33 @@ public virtual float DamageAmount
public float AccuracyFactor;

#region Height
protected int lastHeightTick = -1;
protected float heightInt = 0f;
/// <summary>
/// If lastHeightTick is not FlightTicks, Height calculates the quadratic formula (g/2)t^2 + (-v_0y)t + (y-y0) for {g -> gravity, v_0y -> shotSpeed * Mathf.Sin(shotAngle), y0 -> shotHeight, t -> seconds} to find y rounded to the nearest 3 decimals.
///
/// If lastHeightTick equals FlightTicks, it returns a locally stored value heightInt which is the product of previous calculation.
/// </summary>
public virtual float Height
{
get
{
return ExactPosition.y;
if (lastHeightTick != FlightTicks)
{
heightInt = ticksToImpact > 0 ? GetHeightAtTicks(FlightTicks) : 0f;
lastHeightTick = FlightTicks;
}
return heightInt;
}
}
#endregion

#region Ticks/Seconds
protected float startingTicksToImpactInt = -1f;
float startingTicksToImpactInt = -1f;
public float StartingTicksToImpact
{
get
{
if (!lerpPosition)
{
return float.MaxValue;
}
if (startingTicksToImpactInt < 0f)
{
// Optimization in case shotHeight is zero (for example for fragments)
Expand Down Expand Up @@ -203,10 +196,6 @@ public int IntTicksToImpact
{
get
{
if (!lerpPosition)
{
return 1;
}
if (intTicksToImpact < 0)
{
intTicksToImpact = Mathf.CeilToInt(StartingTicksToImpact);
Expand All @@ -215,15 +204,14 @@ public int IntTicksToImpact
}
}

private int flightTicks;
/// <summary>
/// The amount of integer ticks this projectile has remained in the air for, ignoring impact.
/// </summary>
public int FlightTicks
{
get
{
return flightTicks;
return IntTicksToImpact - ticksToImpact;
}
}
/// <summary>
Expand All @@ -248,40 +236,42 @@ protected virtual Vector2 Vec2Position(float ticks = -1f)
return Vector2.Lerp(origin, Destination, ticks / StartingTicksToImpact);
}

private Vector3? exactPosition = null;
private Vector3 impactPosition = new Vector3();
/// <summary>
/// Exact x,y,z (x,height,y) position in terms of Vec2Position.x, .y (lerped origin to Destination) and Height.
/// </summary>
public virtual Vector3 ExactPosition
{
set
{
exactPosition = new Vector3(value.x, value.y, value.z);
Position = ((Vector3)exactPosition).ToIntVec3();
impactPosition = new Vector3(value.x, value.y, value.z);
Position = impactPosition.ToIntVec3();
}
get
{
if (exactPosition == null)
if (landed)
{
exactPosition = new Vector3(origin.x, shotHeight, origin.y);
return impactPosition;
}
return ((Vector3)exactPosition);
var v = Vec2Position();
return new Vector3(v.x, Height, v.y);
}
}

public virtual Vector2 DrawPosV2
{
get
{
return new Vector2(ExactPosition.x, ExactPosition.z);
return Vec2Position() + new Vector2(0, Height - shotHeight * ((StartingTicksToImpact - fTicks) / StartingTicksToImpact));
}
}

public override Vector3 DrawPos
{
get
{
return ExactPosition;
var v = DrawPosV2;
return new Vector3(v.x, def.Altitude, v.y);
}
}

Expand Down Expand Up @@ -380,7 +370,7 @@ public virtual Quaternion ExactRotation
/// </summary>
public float shotHeight = 0f;
/// <summary>
/// The assigned shot speed [cells/s] (not speed in y axis or x-z plane), in general equal to the projectile.def.speed value.
/// The assigned shot speed [cells/s] (not speed in z axis or x-y plane), in general equal to the projectile.def.speed value.
/// </summary>
public float shotSpeed = -1f;

Expand Down Expand Up @@ -472,42 +462,13 @@ public override void ExposeData()
Scribe_Values.Look<bool>(ref canTargetSelf, "canTargetSelf");
Scribe_Values.Look<bool>(ref logMisses, "logMisses", true);
Scribe_Values.Look<bool>(ref castShadow, "castShadow", true);
Scribe_Values.Look<bool>(ref lerpPosition, "lerpPosition", true);

//To fix landed grenades sl problem
Scribe_Values.Look(ref exactPosition, "exactPosition");
Scribe_Values.Look(ref impactPosition, "impactPosition");
// To insure saves don't get affected..
}
#endregion

#region Throw
public virtual void Throw(Thing launcher, Vector3 origin, Vector3 heading, Thing equipment = null)
{
this.ExactPosition = origin;
this.shotHeight = origin.y;
this.origin = new Vector2(origin.x, origin.z);
this.shotSpeed = Math.Max(heading.magnitude, def.projectile.speed);
var projectileProperties = def.projectile as ProjectilePropertiesCE;
this.castShadow = projectileProperties.castShadow;
this.velocity = heading;
this.launcher = launcher;
this.equipment = equipment;
//For explosives/bullets, equipmentDef is important
equipmentDef = (equipment != null) ? equipment.def : null;

if (!def.projectile.soundAmbient.NullOrUndefined())
{
var info = SoundInfo.InMap(this, MaintenanceType.PerTick);
ambientSustainer = def.projectile.soundAmbient.TrySpawnSustainer(info);
}
ballisticCoefficient = projectileProperties.ballisticCoefficient.RandomInRange;
mass = projectileProperties.mass.RandomInRange;
radius = projectileProperties.diameter.RandomInRange / 2000; // half the diameter and mm -> m
gravity = projectileProperties.Gravity;
initialSpeed = shotSpeed;
}
#endregion

#region Raycast
public virtual void RayCast(Thing launcher, VerbProperties verbProps, Vector2 origin, float shotAngle, float shotRotation, float shotHeight = 0f, float shotSpeed = -1f, float spreadDegrees = 0f, float aperatureSize = 0.03f, Thing equipment = null)
{
Expand Down Expand Up @@ -666,7 +627,6 @@ public virtual void Launch(Thing launcher, Vector2 origin, float shotAngle, floa
if (def.projectile is ProjectilePropertiesCE props)
{
this.castShadow = props.castShadow;
this.lerpPosition = props.lerpPosition;
}
Launch(launcher, origin, equipment);
this.ticksToImpact = IntTicksToImpact;
Expand Down Expand Up @@ -926,7 +886,7 @@ protected bool CheckCellForCollision(IntVec3 cell)
roofChecked = true;
}

foreach (var thing in mainThingList.Distinct().Where(x => !(x is ProjectileCE)).OrderBy(x => (x.DrawPos - LastPos).sqrMagnitude))
foreach (var thing in mainThingList.Distinct().OrderBy(x => (x.DrawPos - LastPos).sqrMagnitude))
{
if ((thing == launcher || thing == mount) && !canTargetSelf)
{
Expand Down Expand Up @@ -1166,47 +1126,6 @@ protected void ApplySuppression(Pawn pawn, float suppressionMultiplier = 1f)
}
}

// If anyone wants to override how projectiles move, this can be made virtual.
// For now, it is non-virtual for performance.
protected Vector3 MoveForward()
{
Vector3 curPosition = ExactPosition;
float sr = shotRotation * Mathf.Deg2Rad + 3.14159f / 2.0f;
if (!kinit)
{
kinit = true;
var projectileProperties = def.projectile as ProjectilePropertiesCE;
ballisticCoefficient = projectileProperties.ballisticCoefficient.RandomInRange;
mass = projectileProperties.mass.RandomInRange;
radius = projectileProperties.diameter.RandomInRange / 2000;
gravity = projectileProperties.Gravity;
float sspt = shotSpeed / GenTicks.TicksPerRealSecond;
velocity = new Vector3(Mathf.Cos(sr) * Mathf.Cos(shotAngle) * sspt, Mathf.Sin(shotAngle) * sspt, Mathf.Sin(sr) * Mathf.Cos(shotAngle) * sspt);
initialSpeed = sspt;
}
Vector3 newPosition = curPosition + velocity;
Accelerate();
return newPosition;
}

// This can also be made virtual, and would be the ideal entry point for guided ammunition and rockets.
protected void Accelerate()
{
float crossSectionalArea = radius;
crossSectionalArea *= crossSectionalArea * 3.14159f;
// 2.5f is half the mass of 1m² x 1cell of air.
var q = 2.5f * shotSpeed * shotSpeed;
var dragForce = q * crossSectionalArea / ballisticCoefficient;
// F = mA
// A = F / m
var a = (float)((-dragForce / (float)mass));
var normalized = velocity.normalized;
velocity.x += a * normalized.x;
velocity.y += a * normalized.y - (float)(1 / ballisticCoefficient) * (float)gravity / GenTicks.TicksPerRealSecond;
velocity.z += a * normalized.z;
shotSpeed = velocity.magnitude;
}

#region Tick/Draw
public override void Tick()
{
Expand All @@ -1217,18 +1136,7 @@ public override void Tick()
}
LastPos = ExactPosition;
ticksToImpact--;
flightTicks++;
Vector3 nextPosition;
if (lerpPosition)
{
var v = Vec2Position();
nextPosition = new Vector3(v.x, Height, v.y);
}
else
{
nextPosition = MoveForward();
}
if (!nextPosition.InBounds(Map))
if (!ExactPosition.InBounds(Map))
{
if (globalTargetInfo.IsValid)
{
Expand Down Expand Up @@ -1257,12 +1165,11 @@ public override void Tick()
Destroy();
return;
}
ExactPosition = nextPosition;
if (CheckForCollisionBetween())
{
return;
}
Position = nextPosition.ToIntVec3();
Position = ExactPosition.ToIntVec3();
if (globalTargetInfo.IsValid)
{
return;
Expand All @@ -1272,7 +1179,7 @@ public override void Tick()
def.projectile.soundImpactAnticipate.PlayOneShot(this);
}
//TODO : It appears that the final steps in the arc (past ticksToImpact == 0) don't CheckForCollisionBetween.
if (ticksToImpact <= 0 || nextPosition.y <= 0f)
if (ticksToImpact <= 0)
{
ImpactSomething();
return;
Expand All @@ -1298,7 +1205,7 @@ public override void Tick()
}
float distToOrigin = originInt.DistanceTo(positionInt);
float dangerFactor = (def.projectile as ProjectilePropertiesCE).dangerFactor;
if (dangerFactor > 0f && nextPosition.y < CollisionVertical.WallCollisionHeight && distToOrigin > 3)
if (dangerFactor > 0f && ExactPosition.y < CollisionVertical.WallCollisionHeight && distToOrigin > 3)
{
DangerTracker?.Notify_BulletAt(Position, def.projectile.damageAmountBase * dangerFactor);
}
Expand Down Expand Up @@ -1575,7 +1482,7 @@ public virtual void Impact(Thing hitThing)
/// </summary>
/// <param name="ticks">Integer ticks, since the only time value which is not an integer (accessed by StartingTicksToImpact) has height zero by definition.</param>
/// <returns>Projectile height at time ticks in ticks.</returns>
private float GetHeightAtTicks(int ticks)
protected virtual float GetHeightAtTicks(int ticks)
{
var seconds = ((float)ticks) / GenTicks.TicksPerRealSecond;
return (float)Math.Round(shotHeight + shotSpeed * Mathf.Sin(shotAngle) * seconds - (GravityFactor * seconds * seconds) / 2f, 3);
Expand Down
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
using System;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
Expand Down Expand Up @@ -31,11 +31,6 @@ public class ProjectilePropertiesCE : ProjectileProperties
public float airborneSuppressionFactor = 1;
public float dangerFactor = 1;

public FloatRange ballisticCoefficient = new FloatRange(1f, 1f);
public FloatRange mass = new FloatRange(1f, 1f);
public FloatRange diameter = new FloatRange(1f, 1f);

public bool lerpPosition = true;
public ThingDef detonateMoteDef;
public FleckDef detonateFleckDef;
public float detonateEffectsScaleOverride = -1;
Expand Down
Loading

0 comments on commit 34a2a36

Please sign in to comment.