Particles using display coordinates, particle growtime, character death&stun animations

This commit is contained in:
Regalis
2015-09-05 12:13:44 +03:00
parent 0cbcdd0b03
commit 04d55891f0
22 changed files with 346 additions and 206 deletions

View File

@@ -7,8 +7,9 @@
startcolor="1.0, 1.0, 1.0" startalpha="0.8"
colorchange="0.0, 0.0, 0.0, -0.25"
lifetime="3"
deleteonhit="true"
velocitychange="0.0, -9.8">
growtime ="0.2"
deleteoncollision="true"
velocitychange="0.0, -9.8">
<sprite texture="Content/Particles/spatter.png"/>
</watersplash>
@@ -18,6 +19,7 @@
startrotationmin ="0.0" startrotationmax="6.28"
startcolor="1.0, 1.0, 1.0" startalpha="0.5"
colorchange="0.0, 0.0, 0.0, -0.25"
growtime ="0.2"
lifetime="3"
velocitychange="0.0, -0.05">
<sprite texture="Content/Particles/spatter.png"/>
@@ -25,7 +27,7 @@
<dustcloud
startsizemin="0.8,0.8" startsizemax="1.0,1.0"
sizechangemin="0.0,0.0" sizechangemax="0.0,0.0"
sizechange="0.0,0.0"
startrotationmin ="0.0" startrotationmax="6.28"
startcolor="0.2, 0.2, 0.2" startalpha="0.5"
colorchange="0.0, 0.0, 0.0, -0.3"
@@ -36,12 +38,12 @@
<bubbles
startsizemin="0.4,0.4" startsizemax="0.5,0.5"
sizechangemin="0.0,0.0" sizechangemax="0.1,0.1"
sizechangemin="0.1,0.1" sizechangemax="0.3,0.3"
startrotationmin ="0.0" startrotationmax="3.14"
startcolor="1.0, 1.0, 1.0" startalpha="0.8"
colorchange="0.0, 0.0, 0.0, -0.5"
lifetime="3"
deleteonhit="true"
deleteoncollision="true"
drawtarget="water"
velocitychange="0.0, 0.1">
<sprite texture="Content/Particles/bubbles.png"/>
@@ -54,15 +56,16 @@
startcolor="0.5, 0.0, 0.0" startalpha="1.0"
colorchange="0.0, 0.0, 0.0, -1.0"
lifetime="2"
deleteonhit="true"
growtime ="0.1"
deleteoncollision="true"
rotatetodirection="true"
velocitychange="0.0, -9.8">
<sprite texture="Content/Particles/blood.png"/>
</blood>
<waterblood
startsizemin="0.1,0.1" startsizemax="0.1,0.1"
sizechangemin="0.15,0.15" sizechangemax="0.2,0.2"
startsize="0.05,0.05"
sizechangemin="0.1,0.1" sizechangemax="0.15,0.15"
startrotationmin ="0.0" startrotationmax="6.28"
startcolor="0.5, 0.0, 0.0" startalpha="1.0"
colorchange="0.0, 0.0, 0.0, -0.25"
@@ -80,15 +83,16 @@
colorchange="0.0, 0.0, 0.0, -0.3"
lifetime="5.0"
drawtarget="air"
deleteonhit="true"
growtime ="0.1"
deleteoncollision="true"
rotatetodirection="true"
velocitychange="0.0, -5.0">
<sprite texture="Content/Particles/explosion.png" sourcerect="128,0,128,64"/>
</spark>
<shockwave
startsizemin="0.1,0.1" startsizemax="0.1,0.1"
sizechangemin="15.0,15.0" sizechangemax="15.0,15.0"
startsize="0.1,0.1"
sizechange="15.0,15.0"
startrotationmin ="0.0" startrotationmax="6.28"
startcolor="1.0, 1.0, 1.0" startalpha="1.0"
colorchange="0.0, 0.0, 0.0, -2.0"
@@ -105,8 +109,9 @@
startcolor="1.0, 1.0, 1.0" startalpha="1.0"
colorchange="-0.6, -0.6, -0.6, -0.5"
lifetime="5.0"
growtime ="0.05"
drawtarget="air"
deleteonhit="true"
deleteoncollision="true"
velocitychange="0.0, 0.5">
<sprite texture="Content/Particles/explosion.png" sourcerect="0,0,128,128"/>
</explosionfire>
@@ -124,10 +129,10 @@
<plasma
startsizemin="0.9,0.9" startsizemax="1.1,1.1"
sizechangemin="-4.0,-0.5" sizechangemax="-4.0,-0.5"
sizechange="-4.0,-0.5"
startcolor="1.0, 1.0, 1.0" startalpha="1.0"
colorchange="0.0, 0.0, 0.0, -4.0"
lifetime="0.25"
lifetime="0.25"
drawtarget="both"
velocitychange="0.0, 0.0">
<sprite texture="Content/Particles/flames.png" sourcerect="0,64,128,64" origin="0.15,0.5"/>

View File

@@ -29,34 +29,53 @@ namespace Subsurface
}
}
public void Update(float deltaTime)
public void SpawnSprites(int count)
{
if (activeSprites.Count < MaxSprites)
{
WayPoint wp = WayPoint.WayPointList[Rand.Int(WayPoint.WayPointList.Count)];
count = Math.Min(count, MaxSprites);
Vector2 pos = new Vector2(wp.Rect.X, wp.Rect.Y);
pos += Rand.Vector(200.0f);
activeSprites.Clear();
for (int i = 0; i < count; i++ )
{
Vector2 pos = Vector2.Zero;
if (WayPoint.WayPointList.Count>0)
{
WayPoint wp = WayPoint.WayPointList[Rand.Int(WayPoint.WayPointList.Count)];
pos = new Vector2(wp.Rect.X, wp.Rect.Y);
pos += Rand.Vector(200.0f);
}
else
{
pos = Rand.Vector(2000.0f);
}
var prefab = prefabs[Rand.Int(prefabs.Count)];
int amount = Rand.Range(prefab.SwarmMin,prefab.SwarmMax);
int amount = Rand.Range(prefab.SwarmMin, prefab.SwarmMax);
List<BackgroundSprite> swarmMembers = new List<BackgroundSprite>();
for (int i = 0; i<amount; i++)
for (int n = 0; n < amount; n++)
{
var newSprite = new BackgroundSprite(prefab, pos);
activeSprites.Add(newSprite);
swarmMembers.Add(newSprite);
}
if (amount>0)
if (amount > 0)
{
Swarm swarm = new Swarm(swarmMembers, prefab.SwarmRadius);
}
}
}
public void ClearSprites()
{
activeSprites.Clear();
}
public void Update(float deltaTime)
{
foreach (BackgroundSprite sprite in activeSprites)
{
sprite.Update(deltaTime);

View File

@@ -940,13 +940,13 @@ namespace Subsurface
for (int i = 0; i < 10; i++)
{
Particle p = Game1.ParticleManager.CreateParticle("waterblood",
torso.SimPosition + new Vector2(Rand.Range(-0.5f, 0.5f), Rand.Range(-0.5f, 0.5f)),
torso.Position + new Vector2(Rand.Range(-50f, 50f), Rand.Range(-50f, 50f)),
Vector2.Zero);
if (p!=null) p.Size *= 2.0f;
Game1.ParticleManager.CreateParticle("bubbles",
torso.SimPosition,
new Vector2(Rand.Range(-0.5f, 0.5f), Rand.Range(-1.0f,0.5f)));
new Vector2(Rand.Range(-50f, 50f), Rand.Range(-100f,50f)));
}
foreach (var joint in AnimController.limbJoints)
@@ -956,6 +956,21 @@ namespace Subsurface
Kill(true);
}
private IEnumerable<object> DeathAnim()
{
float timer = 8.0f;
while (timer > 0.0f)
{
AnimController.UpdateAnim(1.0f / 60.0f);
timer -= 1.0f / 60.0f;
yield return CoroutineStatus.Running;
}
yield return CoroutineStatus.Success;
}
public void Kill(bool networkMessage = false)
{
if (isDead) return;
@@ -973,6 +988,8 @@ namespace Subsurface
}
}
CoroutineManager.StartCoroutine(DeathAnim());
health = 0.0f;
isDead = true;
@@ -1086,11 +1103,8 @@ namespace Subsurface
}
else
{
Limb torso = AnimController.GetLimb(LimbType.Torso);
if (torso == null) torso = AnimController.GetLimb(LimbType.Head);
message.Write(torso.body.Position.X);
message.Write(torso.body.Position.Y);
message.Write(AnimController.RefLimb.Position.X);
message.Write(AnimController.RefLimb.Position.Y);
LargeUpdateTimer = Math.Max(0, LargeUpdateTimer-1);
}

View File

@@ -34,7 +34,11 @@ namespace Subsurface
swimSpeed = ToolBox.GetAttributeFloat(element, "swimspeed", 1.0f);
float footRot = ToolBox.GetAttributeFloat(element,"footrotation", float.NaN);
if (!float.IsNaN(footRot))
if (float.IsNaN(footRot))
{
footRotation = null;
}
else
{
footRotation = MathHelper.ToRadians(footRot);
}
@@ -44,6 +48,12 @@ namespace Subsurface
public override void UpdateAnim(float deltaTime)
{
if (character.IsDead)
{
UpdateStruggling(deltaTime);
return;
}
ResetPullJoints();
if (strongestImpact > 0.0f)
@@ -54,7 +64,7 @@ namespace Subsurface
if (stunTimer>0.0f)
{
UpdateStruggling();
UpdateStruggling(deltaTime);
stunTimer -= deltaTime;
return;
}
@@ -204,25 +214,27 @@ namespace Subsurface
movement = MathUtils.SmoothStep(movement, TargetMovement * walkSpeed, 0.2f);
if (movement == Vector2.Zero) return;
IgnorePlatforms = (TargetMovement.Y < -Math.Abs(TargetMovement.X));
Limb colliderLimb;
float colliderHeight;
Limb torso = GetLimb(LimbType.Torso);
Limb head = GetLimb(LimbType.Head);
Limb torso = GetLimb(LimbType.Torso);
Limb head = GetLimb(LimbType.Head);
if (torso!=null)
if (torso != null)
{
colliderLimb = torso;
colliderHeight = TorsoPosition;
colliderLimb.body.SmoothRotate(TorsoAngle*Dir, 10.0f);
colliderLimb.body.SmoothRotate(TorsoAngle * Dir, 10.0f);
}
else
{
colliderLimb = head;
colliderHeight = HeadPosition;
if (onGround) colliderLimb.body.SmoothRotate(HeadAngle*Dir, 100.0f);
if (onGround) colliderLimb.body.SmoothRotate(HeadAngle * Dir, 100.0f);
}
Vector2 colliderPos = colliderLimb.SimPosition;
@@ -331,13 +343,24 @@ namespace Subsurface
}
}
void UpdateStruggling()
void UpdateStruggling(float deltaTime)
{
Limb head = GetLimb(LimbType.Head);
Limb tail = GetLimb(LimbType.Tail);
if (head != null) head.body.ApplyTorque(head.Mass * Dir * 0.1f);
if (tail != null) tail.body.ApplyTorque(tail.Mass * -Dir * 0.1f);
if (head != null) head.body.ApplyTorque(head.Mass * Dir * (float)Math.Sin(walkPos) * 5.0f);
if (tail != null) tail.body.ApplyTorque(tail.Mass * -Dir * (float)Math.Sin(walkPos) * 5.0f);
walkPos += deltaTime * 5.0f;
Vector2 centerOfMass = GetCenterOfMass();
foreach (Limb limb in limbs)
{
if (limb.type == LimbType.Head || limb.type == LimbType.Tail) continue;
limb.body.ApplyForce((centerOfMass - limb.SimPosition) * (float)Math.Sin(walkPos) * limb.Mass * 10.0f);
}
}
public override void Flip()

View File

@@ -18,6 +18,12 @@ namespace Subsurface
public override void UpdateAnim(float deltaTime)
{
if (character.IsDead)
{
UpdateStruggling();
return;
}
Vector2 colliderPos = GetLimb(LimbType.Torso).SimPosition;
if (inWater) stairs = null;
@@ -543,12 +549,9 @@ namespace Subsurface
leftHandPos = Vector2.Transform(leftHandPos, rotationMatrix);
MoveLimb(leftHand, handPos + leftHandPos, 3.5f);
}
}
}
void UpdateClimbing()
{
if (character.SelectedConstruction == null || character.SelectedConstruction.GetComponent<Ladder>()==null)
@@ -662,14 +665,17 @@ namespace Subsurface
Limb rightLeg = GetLimb(LimbType.RightFoot);
Limb torso = GetLimb(LimbType.Torso);
walkPos += 0.2f;
//walkPos += 0.2f;
if (inWater) return;
Vector2 footPos = torso.body.Position+ new Vector2(TorsoPosition*Dir,0.0f);
HandIK(GetLimb(LimbType.RightHand), GetLimb(LimbType.Head).SimPosition,0.1f);
HandIK(GetLimb(LimbType.LeftHand), GetLimb(LimbType.Head).SimPosition,0.1f);
//Vector2 footPos = torso.body.Position+ new Vector2(TorsoPosition*Dir,0.0f);
MoveLimb(leftLeg, footPos, 0.7f);
MoveLimb(rightLeg, footPos, 0.7f);
//MoveLimb(leftLeg, footPos, 0.7f);
//MoveLimb(rightLeg, footPos, 0.7f);
}
public override void HoldItem(float deltaTime, Camera cam, Item item, Vector2[] handlePos, Vector2 holdPos, Vector2 aimPos, float holdAngle)
@@ -690,7 +696,7 @@ namespace Subsurface
Vector2 itemPos = character.GetInputState(InputType.SecondaryHeld) ? aimPos : holdPos;
float itemAngle;
if (character.GetInputState(InputType.SecondaryHeld) && itemPos != Vector2.Zero)
if (stunTimer <= 0.0f && character.GetInputState(InputType.SecondaryHeld) && itemPos != Vector2.Zero)
{
Vector2 mousePos = ConvertUnits.ToSimUnits(character.CursorPosition);
@@ -767,27 +773,54 @@ namespace Subsurface
if (itemPos == Vector2.Zero) continue;
Limb hand = (i == 0) ? rightHand : leftHand;
Limb arm = (i == 0) ? rightArm : leftArm;
//hand length
float a = 37.0f;
HandIK(hand, transformedHoldPos + transformedHandlePos[i]);
//arm length
float b = 28.0f;
//Limb arm = (i == 0) ? rightArm : leftArm;
//distance from shoulder to holdpos
float c = ConvertUnits.ToDisplayUnits(Vector2.Distance(transformedHoldPos + transformedHandlePos[i], shoulderPos));
c = MathHelper.Clamp(a + b - 1, b-a, c);
////hand length
//float a = 37.0f;
float ang2 = MathUtils.VectorToAngle((transformedHoldPos + transformedHandlePos[i]) - shoulderPos)+MathHelper.PiOver2;
////arm length
//float b = 28.0f;
float armAngle = MathUtils.SolveTriangleSSS(a, b, c);
float handAngle = MathUtils.SolveTriangleSSS(b, a, c);
////distance from shoulder to holdpos
//float c = ConvertUnits.ToDisplayUnits(Vector2.Distance(transformedHoldPos + transformedHandlePos[i], shoulderPos));
//c = MathHelper.Clamp(a + b - 1, b-a, c);
arm.body.SmoothRotate((ang2 - armAngle * Dir), 20.0f);
hand.body.SmoothRotate((ang2 + handAngle * Dir), 100.0f);
}
//float ang2 = MathUtils.VectorToAngle((transformedHoldPos + transformedHandlePos[i]) - shoulderPos)+MathHelper.PiOver2;
//float armAngle = MathUtils.SolveTriangleSSS(a, b, c);
//float handAngle = MathUtils.SolveTriangleSSS(b, a, c);
//arm.body.SmoothRotate((ang2 - armAngle * Dir), 20.0f);
//hand.body.SmoothRotate((ang2 + handAngle * Dir), 100.0f);
}
}
private void HandIK(Limb hand, Vector2 pos, float force = 1.0f)
{
Vector2 shoulderPos = limbJoints[2].WorldAnchorA;
Limb arm = (hand.type == LimbType.LeftHand) ? GetLimb(LimbType.LeftArm) : GetLimb(LimbType.RightArm);
//hand length
float a = 37.0f;
//arm length
float b = 28.0f;
//distance from shoulder to holdpos
float c = ConvertUnits.ToDisplayUnits(Vector2.Distance(pos, shoulderPos));
c = MathHelper.Clamp(a + b - 1, b - a, c);
float ang2 = MathUtils.VectorToAngle(pos - shoulderPos) + MathHelper.PiOver2;
float armAngle = MathUtils.SolveTriangleSSS(a, b, c);
float handAngle = MathUtils.SolveTriangleSSS(b, a, c);
arm.body.SmoothRotate((ang2 - armAngle * Dir), 20.0f*force);
hand.body.SmoothRotate((ang2 + handAngle * Dir), 100.0f*force);
}
public override void Flip()

View File

@@ -337,13 +337,13 @@ namespace Subsurface
if (particleVel != Vector2.Zero) particleVel = Vector2.Normalize(particleVel);
Game1.ParticleManager.CreateParticle("blood",
SimPosition,
particleVel * Rand.Range(1.0f, 3.0f));
Position,
particleVel * Rand.Range(100.0f, 300.0f));
}
for (int i = 0; i < bloodAmount / 2; i++)
{
Game1.ParticleManager.CreateParticle("waterblood", SimPosition, Vector2.Zero);
Game1.ParticleManager.CreateParticle("waterblood", Position, Vector2.Zero);
}
return new AttackResult(amount, bleedingAmount, hitArmor);

View File

@@ -49,6 +49,8 @@ namespace Subsurface
public bool onGround;
private bool ignorePlatforms;
private Limb refLimb;
protected Structure stairs;
protected Direction dir;
@@ -60,6 +62,14 @@ namespace Subsurface
get { return lowestLimb; }
}
public Limb RefLimb
{
get
{
return refLimb;
}
}
public float Mass
{
get;
@@ -226,6 +236,10 @@ namespace Subsurface
}
refLimb = GetLimb(LimbType.Torso);
if (refLimb == null) refLimb = GetLimb(LimbType.Head);
if (refLimb == null) DebugConsole.ThrowError("Character ''" + character + "'' doesn't have a head or torso!");
foreach (var joint in limbJoints)
{
@@ -348,14 +362,12 @@ namespace Subsurface
if (limb.pullJoint != null)
{
Vector2 pos = ConvertUnits.ToDisplayUnits(limb.pullJoint.WorldAnchorA);
pos.Y = -pos.Y;
GUI.DrawRectangle(spriteBatch, new Rectangle((int)pos.X, (int)pos.Y, 5, 5), Color.Red, true, 0.01f);
GUI.DrawRectangle(spriteBatch, new Rectangle((int)pos.X, (int)-pos.Y, 5, 5), Color.Red, true, 0.01f);
if (limb.AnimTargetPos == Vector2.Zero) continue;
Vector2 pos2 = ConvertUnits.ToDisplayUnits(limb.AnimTargetPos);
pos2.Y = -pos2.Y;
GUI.DrawRectangle(spriteBatch, new Rectangle((int)pos2.X, (int)pos2.Y, 5, 5), Color.Blue, true, 0.01f);
GUI.DrawRectangle(spriteBatch, new Rectangle((int)pos2.X, (int)-pos2.Y, 5, 5), Color.Blue, true, 0.01f);
GUI.DrawLine(spriteBatch, pos, pos2, Color.Green);
}
@@ -368,7 +380,14 @@ namespace Subsurface
pos = ConvertUnits.ToDisplayUnits(joint.WorldAnchorB);
GUI.DrawRectangle(spriteBatch, new Rectangle((int)pos.X, (int)-pos.Y, 5, 5), Color.White, true);
}
}
if (refLimb.body.TargetPosition != Vector2.Zero)
{
Vector2 pos = ConvertUnits.ToDisplayUnits(refLimb.body.TargetPosition);
GUI.DrawRectangle(spriteBatch, new Rectangle((int)pos.X-5, (int)-pos.Y-5, 10, 10), Color.LightBlue, false);
}
}
@@ -531,17 +550,17 @@ namespace Subsurface
//create a splash particle
Subsurface.Particles.Particle splash = Game1.ParticleManager.CreateParticle("watersplash",
new Vector2(limb.SimPosition.X, ConvertUnits.ToSimUnits(limbHull.Surface)),
new Vector2(0.0f, Math.Abs(-limb.LinearVelocity.Y * 0.1f)),
new Vector2(limb.Position.X, limbHull.Surface),
new Vector2(0.0f, Math.Abs(-limb.LinearVelocity.Y * 10.0f)),
0.0f);
if (splash != null) splash.yLimits = ConvertUnits.ToSimUnits(
new Vector2(
limbHull.Rect.Y,
limbHull.Rect.Y - limbHull.Rect.Height));
//if (splash != null) splash.yLimits = ConvertUnits.ToSimUnits(
// new Vector2(
// limbHull.Rect.Y,
// limbHull.Rect.Y - limbHull.Rect.Height));
Game1.ParticleManager.CreateParticle("bubbles",
new Vector2(limb.SimPosition.X, ConvertUnits.ToSimUnits(limbHull.Surface)),
new Vector2(limb.Position.X, limbHull.Surface),
limb.LinearVelocity*0.001f,
0.0f);
@@ -572,9 +591,6 @@ namespace Subsurface
private void UpdateNetplayerPosition()
{
Limb refLimb = GetLimb(LimbType.Torso);
if (refLimb == null) refLimb = GetLimb(LimbType.Head);
if (refLimb.body.TargetPosition == Vector2.Zero) return;
//if the limb is further away than resetdistance, all limbs are immediately snapped to their targetpositions
@@ -583,7 +599,7 @@ namespace Subsurface
//if the limb is closer than alloweddistance, just ignore the difference
float allowedDistance = NetConfig.AllowedRagdollDistance;
float dist = Vector2.Distance(limbs[0].body.Position, refLimb.body.TargetPosition);
float dist = Vector2.Distance(refLimb.body.Position, refLimb.body.TargetPosition);
bool resetAll = (dist > resetDistance && character.LargeUpdateTimer == 1);
Vector2 newMovement = (refLimb.body.TargetPosition - refLimb.body.Position);

View File

@@ -117,6 +117,8 @@ namespace Subsurface
{
level.Generate(submarine == null ? 100.0f : Math.Max(Submarine.Borders.Width, Submarine.Borders.Height));
submarine.SetPosition(level.StartPosition - new Vector2(0.0f, 2000.0f));
Game1.GameScreen.BackgroundSpriteManager.SpawnSprites(80);
}
if (Quest!=null) Quest.Start(Level.Loaded);

View File

@@ -200,7 +200,7 @@ namespace Subsurface.Items.Components
if (!string.IsNullOrWhiteSpace(particles))
{
Game1.ParticleManager.CreateParticle(particles, TransformedBarrelPos,
Game1.ParticleManager.CreateParticle(particles, ConvertUnits.ToDisplayUnits(TransformedBarrelPos),
-item.body.Rotation + ((item.body.Dir>0.0f) ? 0.0f : MathHelper.Pi), 0.0f);
}

View File

@@ -72,8 +72,8 @@ namespace Subsurface.Items.Components
for (int i = 0; i < 5; i++)
{
Game1.ParticleManager.CreateParticle("bubbles", item.SimPosition,
-currForce/500.0f + new Vector2(Rand.Range(-1.0f, 1.0f), Rand.Range(-0.5f, 0.5f)));
Game1.ParticleManager.CreateParticle("bubbles", item.Position,
-currForce/5.0f + new Vector2(Rand.Range(-100.0f, 100.0f), Rand.Range(-50f, 50f)));
}
}

View File

@@ -62,11 +62,11 @@ namespace Subsurface.Items.Components
{
sparkSounds[Rand.Int(sparkSounds.Length)].Play(1.0f, 600.0f, item.Position);
Vector2 baseVel = Rand.Vector(3.0f);
Vector2 baseVel = Rand.Vector(300.0f);
for (int i = 0; i < 10; i++)
{
var particle = Game1.ParticleManager.CreateParticle("spark", pt.item.SimPosition,
baseVel + Rand.Vector(1.0f), 0.0f);
var particle = Game1.ParticleManager.CreateParticle("spark", pt.item.Position,
baseVel + Rand.Vector(100.0f), 0.0f);
if (particle != null) particle.Size *= Rand.Range(0.5f,1.0f);
}

View File

@@ -51,21 +51,22 @@ namespace Subsurface
public void Explode(Vector2 simPosition)
{
Game1.ParticleManager.CreateParticle("shockwave", simPosition,
Vector2 displayPosition = ConvertUnits.ToDisplayUnits(simPosition);
Game1.ParticleManager.CreateParticle("shockwave", displayPosition,
Vector2.Zero, 0.0f);
for (int i = 0; i < range * 10; i++)
{
Game1.ParticleManager.CreateParticle("spark", simPosition,
Rand.Vector(Rand.Range(5.0f, 8.0f)), 0.0f);
Game1.ParticleManager.CreateParticle("spark", displayPosition,
Rand.Vector(Rand.Range(500.0f, 800.0f)), 0.0f);
Game1.ParticleManager.CreateParticle("explosionfire", simPosition + Rand.Vector(0.5f),
Rand.Vector(Rand.Range(0.5f, 1.0f)), 0.0f);
Game1.ParticleManager.CreateParticle("explosionfire", displayPosition + Rand.Vector(50f),
Rand.Vector(Rand.Range(50f, 100.0f)), 0.0f);
}
Vector2 displayPosition = ConvertUnits.ToDisplayUnits(simPosition);
float displayRange = ConvertUnits.ToDisplayUnits(range);
light = new LightSource(displayPosition, displayRange, Color.LightYellow);

View File

@@ -244,38 +244,38 @@ namespace Subsurface
{
//UpdateFlowForce();
Vector2 pos = SimPosition;
Vector2 pos = Position;
if (isHorizontal)
{
pos.Y = ConvertUnits.ToSimUnits(MathHelper.Clamp(lowerSurface, rect.Y-rect.Height, rect.Y));
pos.Y = MathHelper.Clamp(lowerSurface, rect.Y - rect.Height, rect.Y);
var particle = Game1.ParticleManager.CreateParticle("watersplash",
new Vector2(pos.X, pos.Y - Rand.Range(0.0f, 0.1f)),
new Vector2(pos.X, pos.Y - Rand.Range(0.0f, 10.0f)),
new Vector2(
MathHelper.Clamp(flowForce.X, -5000.0f, 5000.0f) * Rand.Range(0.005f, 0.007f),
flowForce.Y * Rand.Range(0.005f, 0.007f)));
if (particle!=null)
MathHelper.Clamp(flowForce.X, -5000.0f, 5000.0f) * Rand.Range(0.5f, 0.7f),
flowForce.Y * Rand.Range(0.5f, 0.7f)));
if (particle != null)
{
particle.Size = particle.Size * Math.Abs(flowForce.X / 1000.0f);
}
pos.Y = ConvertUnits.ToSimUnits(Rand.Range(lowerSurface, rect.Y - rect.Height));
pos.Y = Rand.Range(lowerSurface, rect.Y - rect.Height);
Game1.ParticleManager.CreateParticle("bubbles", pos, flowForce / 200.0f);
}
else
{
pos.Y += Math.Sign(flowForce.Y) * ConvertUnits.ToSimUnits(rect.Height / 2.0f);
pos.Y += Math.Sign(flowForce.Y) * rect.Height / 2.0f;
for (int i = 0; i < rect.Width; i += (int)Rand.Range(80, 100))
{
pos.X = ConvertUnits.ToSimUnits(Rand.Range(rect.X, rect.X+rect.Width));
pos.X = Rand.Range(rect.X, rect.X + rect.Width);
Subsurface.Particles.Particle splash = Game1.ParticleManager.CreateParticle("watersplash", pos,
new Vector2(flowForce.X * Rand.Range(0.005f, 0.008f), flowForce.Y * Rand.Range(0.005f, 0.008f)));
new Vector2(0, Math.Max(flowForce.Y * Rand.Range(0.5f, 0.8f), 0.0f)));
if (splash!=null) splash.Size = splash.Size * MathHelper.Clamp(rect.Width / 50.0f, 0.8f, 4.0f);
if (splash != null) splash.Size = splash.Size * MathHelper.Clamp(rect.Width / 50.0f, 0.8f, 4.0f);
Game1.ParticleManager.CreateParticle("bubbles", pos, flowForce / 200.0f);
Game1.ParticleManager.CreateParticle("bubbles", pos, flowForce / 2.0f);
}
}

View File

@@ -212,8 +212,8 @@ namespace Subsurface
if (maxDelta > Rand.Range(0.2f,10.0f))
{
Game1.ParticleManager.CreateParticle("mist",
ConvertUnits.ToSimUnits(new Vector2(rect.X + WaveWidth * i,surface + waveY[i])),
new Vector2(0.0f, -0.5f));
new Vector2(rect.X + WaveWidth * i,surface + waveY[i]),
new Vector2(0.0f, -50.0f));
}
waveY[i] = waveY[i] + waveVel[i];

View File

@@ -419,7 +419,7 @@ namespace Subsurface
int i = FindSectionIndex(ConvertUnits.ToDisplayUnits(position));
if (i == -1) return new AttackResult(0.0f, 0.0f);
Game1.ParticleManager.CreateParticle("dustcloud", ConvertUnits.ToSimUnits(SectionPosition(i)), 0.0f, 0.0f);
Game1.ParticleManager.CreateParticle("dustcloud", SectionPosition(i), 0.0f, 0.0f);
if (playSound && !SectionHasHole(i))
{

View File

@@ -24,25 +24,22 @@ namespace Subsurface.Particles
private Color color;
private float alpha;
private float totalLifeTime;
private float lifeTime;
private Vector2 velocityChange;
private Vector2 drawPosition;
private float checkCollisionTimer;
//private float checkCollisionTimer;
private Hull currentHull;
public ParticlePrefab.DrawTargetType DrawTarget
{
get { return prefab.DrawTarget; }
}
public Vector2 yLimits
{
get;
set;
}
public Vector2 Size
{
get { return size; }
@@ -62,29 +59,33 @@ namespace Subsurface.Particles
this.position = position;
prevPosition = position;
drawPosition = ConvertUnits.ToDisplayUnits(position);
drawPosition = position;
velocity = speed;
this.rotation = rotation + Rand.Range(prefab.startRotationMin, prefab.startRotationMax);
this.rotation = rotation + Rand.Range(prefab.StartRotationMin, prefab.StartRotationMax);
prevRotation = rotation;
angularVelocity = prefab.angularVelocityMin + (prefab.angularVelocityMax - prefab.angularVelocityMin) * Rand.Range(0.0f, 1.0f);
angularVelocity = prefab.AngularVelocityMin + (prefab.AngularVelocityMax - prefab.AngularVelocityMin) * Rand.Range(0.0f, 1.0f);
lifeTime = prefab.lifeTime;
size = prefab.startSizeMin + (prefab.startSizeMax - prefab.startSizeMin) * Rand.Range(0.0f, 1.0f);
sizeChange = prefab.sizeChangeMin + (prefab.sizeChangeMax - prefab.sizeChangeMin) * Rand.Range(0.0f, 1.0f);
yLimits = Vector2.Zero;
color = prefab.startColor;
alpha = prefab.startAlpha;
totalLifeTime = prefab.LifeTime;
lifeTime = prefab.LifeTime;
velocityChange = prefab.velocityChange;
size = prefab.StartSizeMin + (prefab.StartSizeMax - prefab.StartSizeMin) * Rand.Range(0.0f, 1.0f);
if (prefab.rotateToDirection)
sizeChange = prefab.SizeChangeMin + (prefab.SizeChangeMax - prefab.SizeChangeMin) * Rand.Range(0.0f, 1.0f);
color = prefab.StartColor;
alpha = prefab.StartAlpha;
velocityChange = prefab.VelocityChange;
if (prefab.DeleteOnCollision)
{
currentHull = Hull.FindHull(position);
}
if (prefab.RotateToDirection)
{
this.rotation = MathUtils.VectorToAngle(new Vector2(velocity.X, -velocity.Y));
@@ -98,7 +99,7 @@ namespace Subsurface.Particles
position.X += velocity.X * deltaTime;
position.Y += velocity.Y * deltaTime;
if (prefab.rotateToDirection)
if (prefab.RotateToDirection)
{
if (velocityChange != Vector2.Zero || angularVelocity != 0.0f)
{
@@ -114,37 +115,18 @@ namespace Subsurface.Particles
velocity.Y += velocityChange.Y * deltaTime;
size.X += sizeChange.X * deltaTime;
size.Y += sizeChange.Y * deltaTime;
size.Y += sizeChange.Y * deltaTime;
alpha += prefab.colorChange.W * deltaTime;
alpha += prefab.ColorChange.W * deltaTime;
color = new Color(
color.R / 255.0f + prefab.colorChange.X * deltaTime,
color.G / 255.0f + prefab.colorChange.Y * deltaTime,
color.B / 255.0f + prefab.colorChange.Z * deltaTime);
if (yLimits!=Vector2.Zero)
color.R / 255.0f + prefab.ColorChange.X * deltaTime,
color.G / 255.0f + prefab.ColorChange.Y * deltaTime,
color.B / 255.0f + prefab.ColorChange.Z * deltaTime);
if (prefab.DeleteOnCollision && currentHull!=null)
{
if (position.Y>yLimits.X || position.Y<yLimits.Y)
{
return false;
}
}
if (prefab.deleteOnHit)
{
if (checkCollisionTimer > 0.0f)
{
checkCollisionTimer -= deltaTime;
}
else
{
if (Submarine.InsideWall(new Vector2(drawPosition.X, -drawPosition.Y)))
{
return false;
}
checkCollisionTimer = 0.05f;
}
if (!Submarine.RectContains(currentHull.Rect, position)) return false;
}
lifeTime -= deltaTime;
@@ -160,9 +142,17 @@ namespace Subsurface.Particles
drawPosition.Y = -drawPosition.Y;
float drawRotation = Physics.Interpolate(prevRotation, rotation);
drawPosition = ConvertUnits.ToDisplayUnits(drawPosition);
prefab.sprite.Draw(spriteBatch, drawPosition, color*alpha, prefab.sprite.origin, drawRotation, size, SpriteEffects.None, prefab.sprite.Depth);
//drawPosition = ConvertUnits.ToDisplayUnits(drawPosition);
Vector2 drawSize = size;
if (prefab.GrowTime>0.0f && totalLifeTime-lifeTime < prefab.GrowTime)
{
drawSize *= ((totalLifeTime - lifeTime) / prefab.GrowTime);
}
prefab.Sprite.Draw(spriteBatch, drawPosition, color*alpha, prefab.Sprite.origin, drawRotation, drawSize, SpriteEffects.None, prefab.Sprite.Depth);
//spriteBatch.Draw(
// prefab.sprite.Texture,

View File

@@ -61,7 +61,7 @@ namespace Subsurface.Particles
public Particle CreateParticle(ParticlePrefab prefab, Vector2 position, Vector2 speed, float rotation=0.0f)
{
if (!Submarine.RectContains(cam.WorldView, ConvertUnits.ToDisplayUnits(position))) return null;
if (!Submarine.RectContains(cam.WorldView, position)) return null;
if (particleCount >= MaxParticles) return null;
if (particles[particleCount] == null) particles[particleCount] = new Particle();

View File

@@ -1,5 +1,6 @@
using System.Xml.Linq;
using Microsoft.Xna.Framework;
using FarseerPhysics;
namespace Subsurface.Particles
{
@@ -7,67 +8,104 @@ namespace Subsurface.Particles
{
public enum DrawTargetType { Air = 1, Water = 2, Both = 3 }
public readonly string name;
public readonly string Name;
public readonly Sprite sprite;
public readonly Sprite Sprite;
public readonly float angularVelocityMin, angularVelocityMax;
public readonly float AngularVelocityMin, AngularVelocityMax;
public readonly float startRotationMin, startRotationMax;
public readonly float StartRotationMin, StartRotationMax;
public readonly Vector2 startSizeMin, startSizeMax;
public readonly Vector2 sizeChangeMin, sizeChangeMax;
public readonly Vector2 StartSizeMin, StartSizeMax;
public readonly Vector2 SizeChangeMin, SizeChangeMax;
public readonly Color startColor;
public readonly float startAlpha;
public readonly Color StartColor;
public readonly float StartAlpha;
public readonly Vector4 colorChange;
public readonly Vector4 ColorChange;
public readonly float lifeTime;
public readonly float LifeTime;
public readonly bool deleteOnHit;
public readonly float GrowTime;
public readonly Vector2 velocityChange;
public readonly bool DeleteOnCollision;
public readonly Vector2 VelocityChange;
public readonly DrawTargetType DrawTarget;
public readonly bool rotateToDirection;
public readonly bool RotateToDirection;
public ParticlePrefab(XElement element)
{
name = element.Name.ToString();
Name = element.Name.ToString();
foreach (XElement subElement in element.Elements())
{
if (subElement.Name.ToString().ToLower() != "sprite") continue;
sprite = new Sprite(subElement);
Sprite = new Sprite(subElement);
}
angularVelocityMin = ToolBox.GetAttributeFloat(element, "angularvelocitymin", 0.0f);
angularVelocityMax = ToolBox.GetAttributeFloat(element, "angularvelocitymax", 0.0f);
if (element.Attribute("angularvelocity") == null)
{
AngularVelocityMin = ToolBox.GetAttributeFloat(element, "angularvelocitymin", 0.0f);
AngularVelocityMax = ToolBox.GetAttributeFloat(element, "angularvelocitymax", 0.0f);
}
else
{
AngularVelocityMin = ToolBox.GetAttributeFloat(element, "angularvelocity", 0.0f);
AngularVelocityMax = AngularVelocityMin;
}
startSizeMin = ToolBox.GetAttributeVector2(element, "startsizemin", Vector2.One);
startSizeMax = ToolBox.GetAttributeVector2(element, "startsizemax", Vector2.One);
if (element.Attribute("startsize") == null)
{
StartSizeMin = ToolBox.GetAttributeVector2(element, "startsizemin", Vector2.One);
StartSizeMax = ToolBox.GetAttributeVector2(element, "startsizemax", Vector2.One);
}
else
{
StartSizeMin = ToolBox.GetAttributeVector2(element, "startsize", Vector2.One);
StartSizeMax = StartSizeMin;
}
sizeChangeMin = ToolBox.GetAttributeVector2(element, "sizechangemin", Vector2.Zero);
sizeChangeMax = ToolBox.GetAttributeVector2(element, "sizechangemax", Vector2.Zero);
if (element.Attribute("sizechange") == null)
{
SizeChangeMin = ToolBox.GetAttributeVector2(element, "sizechangemin", Vector2.Zero);
SizeChangeMax = ToolBox.GetAttributeVector2(element, "sizechangemax", Vector2.Zero);
}
else
{
SizeChangeMin = ToolBox.GetAttributeVector2(element, "sizechange", Vector2.Zero);
SizeChangeMax = SizeChangeMin;
}
startRotationMin = ToolBox.GetAttributeFloat(element, "startrotationmin", 0.0f);
startRotationMax = ToolBox.GetAttributeFloat(element, "startrotationmax", 0.0f);
GrowTime = ToolBox.GetAttributeFloat(element, "growtime", 0.0f);
startColor = new Color(ToolBox.GetAttributeVector4(element, "startcolor", Vector4.One));
startAlpha = ToolBox.GetAttributeFloat(element, "startalpha", 1.0f);
if (element.Attribute("startrotation") == null)
{
StartRotationMin = ToolBox.GetAttributeFloat(element, "startrotationmin", 0.0f);
StartRotationMax = ToolBox.GetAttributeFloat(element, "startrotationmax", 0.0f);
}
else
{
StartRotationMin = ToolBox.GetAttributeFloat(element, "startrotatio", 0.0f);
StartRotationMax = StartRotationMin;
}
deleteOnHit = ToolBox.GetAttributeBool(element, "deleteonhit", false);
StartColor = new Color(ToolBox.GetAttributeVector4(element, "startcolor", Vector4.One));
StartAlpha = ToolBox.GetAttributeFloat(element, "startalpha", 1.0f);
colorChange = ToolBox.GetAttributeVector4(element, "colorchange", Vector4.Zero);
DeleteOnCollision = ToolBox.GetAttributeBool(element, "deleteoncollision", false);
lifeTime = ToolBox.GetAttributeFloat(element, "lifetime", 5.0f);
ColorChange = ToolBox.GetAttributeVector4(element, "colorchange", Vector4.Zero);
velocityChange = ToolBox.GetAttributeVector2(element, "velocitychange", Vector2.Zero);
LifeTime = ToolBox.GetAttributeFloat(element, "lifetime", 5.0f);
rotateToDirection = ToolBox.GetAttributeBool(element, "rotatetodirection", false);
VelocityChange = ToolBox.GetAttributeVector2(element, "velocitychange", Vector2.Zero);
VelocityChange = ConvertUnits.ToDisplayUnits(VelocityChange);
RotateToDirection = ToolBox.GetAttributeBool(element, "rotatetodirection", false);
switch (ToolBox.GetAttributeString(element, "drawtarget", "air").ToLower())
{

View File

@@ -16,7 +16,7 @@ namespace Subsurface
readonly Sprite background, backgroundTop;
private BackgroundSpriteManager backgroundSpriteManager;
public BackgroundSpriteManager BackgroundSpriteManager;
public Camera Cam
{
@@ -35,7 +35,7 @@ namespace Subsurface
background = new Sprite("Content/Map/background.png", Vector2.Zero);
backgroundTop = new Sprite("Content/Map/background2.png", Vector2.Zero);
backgroundSpriteManager = new BackgroundSpriteManager("Content/BackgroundSprites/BackgroundSpritePrefabs.xml");
BackgroundSpriteManager = new BackgroundSpriteManager("Content/BackgroundSprites/BackgroundSpritePrefabs.xml");
}
public override void Select()
@@ -75,7 +75,7 @@ namespace Subsurface
Character.UpdateAll(cam, (float)deltaTime);
backgroundSpriteManager.Update((float)deltaTime);
BackgroundSpriteManager.Update((float)deltaTime);
Game1.ParticleManager.Update((float)deltaTime);
@@ -186,7 +186,7 @@ namespace Subsurface
null, null, null, null,
cam.Transform);
backgroundSpriteManager.Draw(spriteBatch);
BackgroundSpriteManager.Draw(spriteBatch);
spriteBatch.End();

View File

@@ -160,9 +160,8 @@ namespace Subsurface
}
this.game = game;
}
public bool SelectTab(GUIButton button, object obj)
{
selectedTab = (int)obj;

View File

@@ -721,7 +721,7 @@ namespace Subsurface
return;
}
if (!string.IsNullOrWhiteSpace(mapName)) TrySelectMap(mapName, md5Hash);
//if (!string.IsNullOrWhiteSpace(mapName)) TrySelectMap(mapName, md5Hash);
modeList.Select(modeIndex);

Binary file not shown.