GPU Lightning Weapons

This commit is contained in:
Reinier Vens 2021-02-05 03:21:15 +00:00
commit 8d10e33db0
26 changed files with 1163 additions and 876 deletions

View file

@ -177,7 +177,13 @@ public class ActionGameManager : MonoBehaviour
_input.Global.Dock.performed += context =>
{
if (CurrentShip.Parent == null) Dock();
if (CurrentShip == null)
{
ConfirmationDialog.Clear();
ConfirmationDialog.Title.text = "Can't undock. You dont have a ship!";
ConfirmationDialog.Show();
}
else if (CurrentShip.Parent == null) Dock();
else Undock();
};

View file

@ -0,0 +1,79 @@
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class ConstantLightning : MonoBehaviour
{
public LightningCompute Lightning;
public float HitRadius;
public AnimationCurve FadeCurve;
public float StartWidth = 1;
public float EndWidth = 1;
public float FadeDuration;
public Transform Barrel { get; set; }
public float Damage { get; set; }
public float Penetration { get; set; }
public float Spread { get; set; }
public DamageType DamageType { get; set; }
public EntityInstance Source { get; set; }
public float Range { get; set; }
private bool _stopping;
private float _startTime;
private void OnEnable()
{
_stopping = false;
Lightning.StartAnimation();
}
private void Update()
{
if (Barrel == null) return;
if (_stopping)
{
var lerp = (Time.time - _startTime) / FadeDuration;
Lightning.StartWidth = FadeCurve.Evaluate(lerp) * StartWidth;
Lightning.EndWidth = FadeCurve.Evaluate(lerp) * EndWidth;
if (lerp > 1)
{
GetComponent<Prototype>().ReturnToPool();
return;
}
}
else
{
Lightning.StartWidth = StartWidth;
Lightning.EndWidth = EndWidth;
}
Lightning.FixedEndpoint = false;
var hits = Physics.SphereCastAll(Barrel.position, HitRadius, Barrel.forward, Range, 1);
foreach (var hit in hits)
{
var hull = hit.collider.GetComponent<HullCollider>();
if (hull)
{
if (hull.Entity == Source.Entity) continue;
hull.SendHit(Damage * Time.deltaTime, Penetration, Spread, DamageType, Source.Entity, hit, Barrel.forward);
}
Lightning.FixedEndpoint = true;
Lightning.EndPosition = hit.point;
break;
}
if(!Lightning.FixedEndpoint)
Lightning.EndPosition = Barrel.position + Barrel.forward * Range;
Lightning.StartPosition = Barrel.position;
}
public void Stop()
{
_stopping = true;
_startTime = Time.time;
}
}

View file

@ -0,0 +1,3 @@
fileFormatVersion: 2
guid: b184352ea3694b8d892f1402b8d51153
timeCreated: 1612491884

View file

@ -0,0 +1,32 @@
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.Serialization;
public class ConstantLightningManager : ConstantWeaponEffectManager
{
public Prototype LightningPrototype;
private Dictionary<EquippedItem, ConstantLightning> _bolts = new Dictionary<EquippedItem, ConstantLightning>();
public override void StartFiring(WeaponData data, EquippedItem item, EntityInstance source, EntityInstance target)
{
var p = LightningPrototype.Instantiate<ConstantLightning>();
p.Source = source;
var hp = source.Entity.Hardpoints[item.Position.x, item.Position.y];
var barrel = source.GetBarrel(hp);
p.Barrel = barrel;
p.Damage = source.Entity.ItemManager.Evaluate(data.Damage, item.EquippableItem, source.Entity);
p.Range = source.Entity.ItemManager.Evaluate(data.Range, item.EquippableItem, source.Entity);
p.Penetration = source.Entity.ItemManager.Evaluate(data.Penetration, item.EquippableItem, source.Entity);
p.Spread = source.Entity.ItemManager.Evaluate(data.DamageSpread, item.EquippableItem, source.Entity);
p.DamageType = data.DamageType;
_bolts.Add(item, p);
}
public override void StopFiring(EquippedItem item)
{
_bolts[item].Stop();
_bolts.Remove(item);
}
}

View file

@ -0,0 +1,3 @@
fileFormatVersion: 2
guid: ecabe4f078a147459bba6172582d7bc8
timeCreated: 1612491892

View file

@ -9,23 +9,8 @@ using Random = UnityEngine.Random;
public class Lightning : MonoBehaviour
{
public LineRenderer Trunk;
public Prototype BranchPrototype;
public LightningCompute LightningCompute;
public float HitRadius;
public float Duration;
public AnimationCurve IntensityCurve;
public int BranchCount;
public float BranchDistance;
public int PointCount;
public int BranchPointCount;
public int MorphSpeed;
public int Octaves;
public float Frequency;
public float Offset;
public float Amplitude;
public float Lacunarity;
public float Gain;
public float Damage { get; set; }
public float Penetration { get; set; }
@ -36,46 +21,16 @@ public class Lightning : MonoBehaviour
public EntityInstance Target { get; set; }
public Transform Barrel { get; set; }
private float _startTime;
private LineRenderer[] _branches;
private Vector3[] _points;
private Vector3[][] _branchPoints;
private int[] _branchStarts;
private bool _colliderHit;
private Vector3 _colliderLocalPosition;
private Transform _colliderTransform;
private Vector3 _endpoint;
private float _offset;
private void Awake()
{
_points = new Vector3[PointCount];
_branchPoints = new Vector3[BranchCount][];
_branchStarts = new int[BranchCount];
_branches = new LineRenderer[BranchCount];
for (int i = 0; i < BranchCount; i++)
{
_branchPoints[i] = new Vector3[BranchPointCount];
_branches[i] = BranchPrototype.Instantiate<LineRenderer>();
}
}
public void Fire()
{
_offset = Random.value * 1000;
_startTime = Time.time;
Trunk.widthMultiplier = 0;
foreach(var line in _branches)
line.widthMultiplier = 0;
for (int i = 0; i < BranchCount; i++)
{
_branchStarts[i] = Random.Range(0, PointCount);
var lerp = (float) _branchStarts[i] / PointCount;
_branches[i].startColor = Trunk.colorGradient.Evaluate(lerp);
}
_colliderHit = false;
LightningCompute.OnLeaderComplete = null;
LightningCompute.FixedEndpoint = false;
var hits = Physics.SphereCastAll(Barrel.position, HitRadius, Barrel.forward, Range, 1);
foreach (var hit in hits)
{
@ -83,64 +38,32 @@ public class Lightning : MonoBehaviour
if (hull)
{
if (hull.Entity == Source.Entity) continue;
hull.SendHit(Damage, Penetration, Spread, DamageType, Source.Entity, hit, Barrel.forward);
LightningCompute.OnLeaderComplete = () =>
hull.SendHit(Damage, Penetration, Spread, DamageType, Source.Entity, hit, Barrel.forward);
}
_colliderHit = true;
_colliderLocalPosition = hit.collider.transform.InverseTransformPoint(hit.point);
_colliderTransform = hit.collider.transform;
LightningCompute.FixedEndpoint = true;
break;
}
LightningCompute.OnPulseComplete = () =>
GetComponent<Prototype>().ReturnToPool();
LightningCompute.StartAnimation();
_endpoint = Barrel.position + Barrel.forward * Range;
}
private void Update()
{
if (Barrel == null) return;
var time = (Time.time - _startTime) / Duration;
if (time > 1)
{
GetComponent<Prototype>().ReturnToPool();
return;
}
Trunk.widthMultiplier = IntensityCurve.Evaluate(time);
if (_colliderHit)
{
if(_colliderTransform) _endpoint = _colliderTransform.TransformPoint(_colliderLocalPosition);
if (_colliderTransform) _endpoint = _colliderTransform.TransformPoint(_colliderLocalPosition);
}
else _endpoint = Barrel.position + Barrel.forward * Range + (Vector3) NoiseFbm.fBm3(Time.time, Octaves, Frequency, Offset, Amplitude, Lacunarity, Gain);
var startPoint = Barrel.position;
var dist = (_endpoint - startPoint).magnitude;
var startOffset = -NoiseFbm.fBm3(float2(0+_offset, Time.time*MorphSpeed), Octaves, Frequency, Offset, Amplitude, Lacunarity, Gain);
var endOffset = -NoiseFbm.fBm3(float2(dist+_offset, Time.time*MorphSpeed), Octaves, Frequency, Offset, Amplitude, Lacunarity, Gain);
for (int i = 0; i < PointCount; i++)
{
var l = (float) i / (PointCount - 1);
var sampleDist = dist * l;
var pos = lerp(startPoint, _endpoint, l) +
NoiseFbm.fBm3(float2(sampleDist+_offset, Time.time*MorphSpeed), Octaves, Frequency, Offset, Amplitude, Lacunarity, Gain);
if (l < .5f) pos += startOffset * (1 - l * 2);
else pos += endOffset * (2 * (l - .5f));
_points[i] = pos;
}
Trunk.SetPositions(_points);
for (int i = 0; i < BranchCount; i++)
{
_branches[i].widthMultiplier = Trunk.widthMultiplier * Trunk.widthCurve.Evaluate((float) _branchStarts[i] / PointCount);
var branchStartPoint = _points[_branchStarts[i]];
var branchEndPoint = branchStartPoint + Random.onUnitSphere * BranchDistance;
var branchstartOffset = -NoiseFbm.fBm3(float2(_branchStarts[i]*10, Time.time*MorphSpeed), Octaves, Frequency, Offset, Amplitude, Lacunarity, Gain);
for (int j = 0; j < BranchPointCount; j++)
{
var l = (float) j / (BranchPointCount - 1);
var sampleDist = BranchDistance * l + _branchStarts[i]*10;
var pos = lerp(branchStartPoint, branchEndPoint, l) +
NoiseFbm.fBm3(float2(sampleDist * 2, Time.time * MorphSpeed), Octaves, Frequency, Offset, Amplitude, Lacunarity, Gain);
if (l < .5f) pos += branchstartOffset * (1 - l * 2);
_branchPoints[i][j] = pos;
}
_branches[i].SetPositions(_branchPoints[i]);
}
LightningCompute.EndPosition = _endpoint;
LightningCompute.StartPosition = Barrel.position;
}
}

View file

@ -4,7 +4,7 @@ MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
executionOrder: 53
icon: {instanceID: 0}
userData:
assetBundleName:

View file

@ -373,9 +373,9 @@ public class SectorRenderer : MonoBehaviour
hitShape[v] = true;
}
for (int i = 0; i < hit.Spread - 1; i++)
for (int i = 0; i < Mathf.RoundToInt(hit.Spread); i++)
{
hitShape.Expand();
hitShape = hitShape.Expand();
}
if (hit.Penetration > .5f)