more accurate submarine body generation, multiplayer fixes, saving takes HiddenSubPosition into account, fire coordinate fixes, editscreen fixes, checking item triggers in AIObjectiveGoto, netlobbyscreen sync fixes, re-enabled level start/end positions, water edit fixed
This commit is contained in:
@@ -0,0 +1,208 @@
|
||||
using Microsoft.Xna.Framework;
|
||||
using Microsoft.Xna.Framework.Graphics;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Text;
|
||||
using System.Xml.Linq;
|
||||
|
||||
namespace Barotrauma
|
||||
{
|
||||
|
||||
class BackgroundCreature : ISteerable
|
||||
{
|
||||
const float MaxDepth = 100.0f;
|
||||
|
||||
const float CheckWallsInterval = 5.0f;
|
||||
|
||||
public bool Enabled;
|
||||
|
||||
private BackgroundCreaturePrefab prefab;
|
||||
|
||||
private Vector2 position;
|
||||
|
||||
private Vector3 velocity;
|
||||
|
||||
private float depth;
|
||||
|
||||
private SteeringManager steeringManager;
|
||||
|
||||
private float checkWallsTimer;
|
||||
|
||||
public Swarm Swarm;
|
||||
|
||||
Vector2 drawPosition;
|
||||
public Vector2 TransformedPosition
|
||||
{
|
||||
get { return drawPosition; }
|
||||
}
|
||||
|
||||
public Vector2 SimPosition
|
||||
{
|
||||
get { return position; }
|
||||
}
|
||||
|
||||
public Vector2 Velocity
|
||||
{
|
||||
get { return new Vector2(velocity.X, velocity.Y); }
|
||||
}
|
||||
|
||||
public Vector2 Steering
|
||||
{
|
||||
get;
|
||||
set;
|
||||
}
|
||||
|
||||
public BackgroundCreature(BackgroundCreaturePrefab prefab, Vector2 position)
|
||||
{
|
||||
this.prefab = prefab;
|
||||
|
||||
this.position = position;
|
||||
|
||||
drawPosition = position;
|
||||
|
||||
steeringManager = new SteeringManager(this);
|
||||
|
||||
velocity = new Vector3(
|
||||
Rand.Range(-prefab.Speed, prefab.Speed),
|
||||
Rand.Range(-prefab.Speed, prefab.Speed),
|
||||
Rand.Range(0.0f, prefab.WanderZAmount));
|
||||
|
||||
checkWallsTimer = Rand.Range(0.0f, CheckWallsInterval);
|
||||
|
||||
}
|
||||
|
||||
float ang;
|
||||
Vector2 obstacleDiff;
|
||||
|
||||
public void Update(float deltaTime)
|
||||
{
|
||||
position += new Vector2(velocity.X, velocity.Y) * deltaTime;
|
||||
depth = MathHelper.Clamp(depth + velocity.Z * deltaTime, 0.0f, MaxDepth);
|
||||
|
||||
checkWallsTimer -= deltaTime;
|
||||
if (checkWallsTimer<=0.0f && Level.Loaded!=null)
|
||||
{
|
||||
checkWallsTimer = CheckWallsInterval;
|
||||
|
||||
obstacleDiff = Vector2.Zero;
|
||||
|
||||
var cells = Level.Loaded.GetCells(position, 1);
|
||||
if (cells.Count > 0)
|
||||
{
|
||||
|
||||
foreach (Voronoi2.VoronoiCell cell in cells)
|
||||
{
|
||||
obstacleDiff += cell.Center - position;
|
||||
}
|
||||
|
||||
obstacleDiff = Vector2.Normalize(obstacleDiff) * prefab.Speed;
|
||||
}
|
||||
}
|
||||
|
||||
if (Swarm!=null)
|
||||
{
|
||||
Vector2 midPoint = Swarm.MidPoint();
|
||||
float midPointDist = Vector2.Distance(position, midPoint);
|
||||
|
||||
if (midPointDist > Swarm.MaxDistance)
|
||||
{
|
||||
steeringManager.SteeringSeek(midPoint, (midPointDist / Swarm.MaxDistance) * prefab.Speed);
|
||||
}
|
||||
}
|
||||
|
||||
if (prefab.WanderAmount > 0.0f)
|
||||
{
|
||||
steeringManager.SteeringWander(prefab.Speed);
|
||||
}
|
||||
|
||||
if (obstacleDiff != Vector2.Zero)
|
||||
{
|
||||
steeringManager.SteeringSeek(-obstacleDiff, prefab.Speed);
|
||||
}
|
||||
|
||||
steeringManager.Update(prefab.Speed);
|
||||
|
||||
if (prefab.WanderZAmount>0.0f)
|
||||
{
|
||||
ang += Rand.Range(-prefab.WanderZAmount, prefab.WanderZAmount);
|
||||
velocity.Z = (float)Math.Sin(ang)*prefab.Speed;
|
||||
}
|
||||
|
||||
velocity = Vector3.Lerp(velocity, new Vector3(Steering.X, Steering.Y, velocity.Z), deltaTime);
|
||||
}
|
||||
|
||||
public void Draw(SpriteBatch spriteBatch)
|
||||
{
|
||||
float rotation = 0.0f;
|
||||
if (!prefab.DisableRotation)
|
||||
{
|
||||
rotation = MathUtils.VectorToAngle(new Vector2(velocity.X, -velocity.Y));
|
||||
if (velocity.X < 0.0f) rotation -= MathHelper.Pi;
|
||||
}
|
||||
|
||||
drawPosition = position;// +Level.Loaded.Position;
|
||||
|
||||
if (depth > 0.0f)
|
||||
{
|
||||
Vector2 camOffset = drawPosition - GameMain.GameScreen.Cam.WorldViewCenter;
|
||||
|
||||
drawPosition -= camOffset * (depth / MaxDepth) * 0.05f;
|
||||
}
|
||||
|
||||
prefab.Sprite.Draw(spriteBatch, new Vector2(drawPosition.X, -drawPosition.Y), Color.Lerp(Color.White, Color.DarkBlue, (depth/MaxDepth)*0.3f),
|
||||
rotation, 1.0f - (depth / MaxDepth) * 0.2f, velocity.X > 0.0f ? SpriteEffects.None : SpriteEffects.FlipHorizontally, (depth / MaxDepth));
|
||||
}
|
||||
}
|
||||
|
||||
class Swarm
|
||||
{
|
||||
public List<BackgroundCreature> Members;
|
||||
|
||||
public readonly float MaxDistance;
|
||||
|
||||
public Vector2 MidPoint()
|
||||
{
|
||||
if (Members.Count == 0) return Vector2.Zero;
|
||||
|
||||
Vector2 midPoint = Vector2.Zero;
|
||||
|
||||
foreach (BackgroundCreature member in Members)
|
||||
{
|
||||
midPoint += member.SimPosition;
|
||||
}
|
||||
|
||||
midPoint /= Members.Count;
|
||||
|
||||
return midPoint;
|
||||
}
|
||||
|
||||
public Vector2 AvgVelocity()
|
||||
{
|
||||
if (Members.Count == 0) return Vector2.Zero;
|
||||
|
||||
Vector2 avgVel = Vector2.Zero;
|
||||
|
||||
foreach (BackgroundCreature member in Members)
|
||||
{
|
||||
avgVel += member.Velocity;
|
||||
}
|
||||
|
||||
avgVel /= Members.Count;
|
||||
|
||||
return avgVel;
|
||||
}
|
||||
|
||||
public Swarm(List<BackgroundCreature> members, float maxDistance)
|
||||
{
|
||||
this.Members = members;
|
||||
|
||||
this.MaxDistance = maxDistance;
|
||||
|
||||
foreach (BackgroundCreature bgSprite in members)
|
||||
{
|
||||
bgSprite.Swarm = this;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user