77 lines
2.9 KiB
C#
77 lines
2.9 KiB
C#
using System;
|
|
using Cielonos.MainGame.Characters;
|
|
using UnityEngine;
|
|
|
|
namespace Cielonos.MainGame
|
|
{
|
|
public class RaycastSubmodule : AttackAreaSubmoduleBase
|
|
{
|
|
public Vector3 direction;
|
|
public bool isDynamicDirection => direction == default;
|
|
public float rayLength;
|
|
public bool isDynamicRayLength => rayLength < 0;
|
|
public float rayRadius;
|
|
public bool isSphereRay => rayRadius > 0;
|
|
public Action<Collider, Vector3> onHit;
|
|
|
|
public RaycastSubmodule(AttackAreaBase owner, Vector3 direction, float rayRadius, float rayLength) : base(owner)
|
|
{
|
|
this.direction = direction;
|
|
this.rayLength = rayLength;
|
|
this.rayRadius = rayRadius;
|
|
this.onHit = (collider, point) =>
|
|
{
|
|
owner.HitCharacter(collider, point);
|
|
owner.HitEnvironment(collider, point);
|
|
};
|
|
}
|
|
|
|
public void Update()
|
|
{
|
|
Vector3 rayDirection = isDynamicDirection ? owner.topParent.forward : direction;
|
|
Ray ray = new Ray(owner.transform.position, rayDirection);
|
|
|
|
float sphereRadius = Mathf.Max(rayRadius, 0.1f);
|
|
Collider[] hitColliders = new Collider[8];
|
|
int size = Physics.OverlapSphereNonAlloc(owner.transform.position, sphereRadius, hitColliders, LayerMask.GetMask("Characters", "Default", "Ground"));
|
|
if (size >= 1)
|
|
{
|
|
Debug.Log("RaycastSubmodule detected colliders: " + size);
|
|
for (int i = 0; i < size; i++)
|
|
{
|
|
CharacterBase character = hitColliders[i].GetComponentInParent<CharacterBase>();
|
|
if (character != null)
|
|
{
|
|
onHit?.Invoke(hitColliders[i], hitColliders[i].ClosestPoint(owner.transform.position));
|
|
return;
|
|
}
|
|
}
|
|
|
|
onHit?.Invoke(hitColliders[0], hitColliders[0].ClosestPoint(owner.transform.position));
|
|
return;
|
|
}
|
|
|
|
if (owner.moveSm != null && isDynamicRayLength)
|
|
{
|
|
rayLength = owner.moveSm.scaledVelocity.magnitude;
|
|
}
|
|
|
|
if (isSphereRay)
|
|
{
|
|
if (Physics.SphereCast(ray, rayRadius, out RaycastHit hit, rayLength * Time.deltaTime,
|
|
LayerMask.GetMask("Characters", "Default", "Ground")))
|
|
{
|
|
onHit?.Invoke(hit.collider, hit.point);
|
|
}
|
|
}
|
|
else
|
|
{
|
|
if (Physics.Raycast(ray, out RaycastHit hit, rayLength * Time.deltaTime,
|
|
LayerMask.GetMask("Characters", "Default", "Ground")))
|
|
{
|
|
onHit?.Invoke(hit.collider, hit.point);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
} |