171 lines
3.8 KiB
C#
171 lines
3.8 KiB
C#
using System.Collections;
|
|
using System.Collections.Generic;
|
|
using Invector;
|
|
using Invector.vCharacterController.AI;
|
|
using PixelCrushers;
|
|
using UnityEngine;
|
|
using UnityEngine.Events;
|
|
|
|
namespace Beyond
|
|
{
|
|
public class EnemySpawner : Saver
|
|
{
|
|
public GameObject m_prefab;
|
|
public Transform m_distanceFrom;
|
|
//public bool m_distanceFromMainCam;
|
|
public float m_spawnCheckInterval = .5f;
|
|
public float m_distance = 20f;
|
|
public int m_numToSpawn = -1;
|
|
public bool m_respawnOnPlayersDeath = true;
|
|
public LayerMask raycastMask = 1; //default
|
|
private SaveData m_spawnData;
|
|
//private bool m_spawned;
|
|
private vControlAI m_spawnedAI;
|
|
public UnityEvent<EnemySpawner> m_OnDead;
|
|
public UnityEvent<EnemySpawner> m_onReceivedDamage;
|
|
class SaveData
|
|
{
|
|
public int numSpawned;
|
|
public bool spawned;
|
|
}
|
|
|
|
public override void Awake()
|
|
{
|
|
#if ENEMIES_DISABLED && UNITY_EDITOR
|
|
enabled = false;
|
|
return;
|
|
#endif
|
|
base.Awake();
|
|
//m_spawned = false;
|
|
m_spawnData = new SaveData();
|
|
m_spawnData.numSpawned = 0;
|
|
m_spawnData.spawned = false;
|
|
}
|
|
|
|
void OnDestroy()
|
|
{
|
|
if (m_respawnOnPlayersDeath && Player.Instance != null)
|
|
{
|
|
var respawner = Player.Instance.GetComponent<Respawner>();
|
|
respawner.m_onRespawned.RemoveListener(OnPlayerRespawned);
|
|
}
|
|
|
|
if (m_spawnedAI)
|
|
{
|
|
m_spawnedAI.onDead.RemoveListener(OnDead);
|
|
}
|
|
}
|
|
|
|
public override void Start()
|
|
{
|
|
|
|
base.Start();
|
|
if (Player.Instance != null)
|
|
m_distanceFrom = Player.Instance.transform;
|
|
else
|
|
{
|
|
m_distanceFrom = Camera.main.transform;
|
|
}
|
|
|
|
if (m_respawnOnPlayersDeath)
|
|
{
|
|
var respawner = Player.Instance.GetComponent<Respawner>();
|
|
respawner.m_onRespawned.AddListener(OnPlayerRespawned);
|
|
}
|
|
InvokeRepeating("CheckSpawn", m_spawnCheckInterval + (Random.value * m_spawnCheckInterval), m_spawnCheckInterval);
|
|
}
|
|
|
|
void CheckRespawnCondition()
|
|
{
|
|
if ((m_numToSpawn < 0 || m_numToSpawn > m_spawnData.numSpawned) && m_spawnedAI == null )
|
|
m_spawnData.spawned = false;
|
|
|
|
}
|
|
private void OnPlayerRespawned()
|
|
{
|
|
CheckRespawnCondition();
|
|
}
|
|
|
|
public override string RecordData()
|
|
{
|
|
return SaveSystem.Serialize(m_spawnData);
|
|
}
|
|
|
|
public override void ApplyData(string s)
|
|
{
|
|
var data = SaveSystem.Deserialize<SaveData>(s);
|
|
if (data != null)
|
|
{
|
|
m_spawnData = data;
|
|
//m_spawned = true;
|
|
CheckRespawnCondition();
|
|
}
|
|
}
|
|
|
|
public bool SpawnedAndLive()
|
|
{
|
|
return m_spawnedAI != null;
|
|
}
|
|
|
|
public bool SpawnedAndDead()
|
|
{
|
|
return m_spawnData.spawned && m_spawnedAI == null;
|
|
}
|
|
|
|
public void Spawn()
|
|
{
|
|
if (m_prefab == null)
|
|
return;
|
|
|
|
Vector3 pos;
|
|
const float RAY_OFFSET = 30f;
|
|
const float Y_OFFSET = .1f;
|
|
pos = transform.position;
|
|
pos.y += RAY_OFFSET;
|
|
RaycastHit hit = new RaycastHit();
|
|
if (Physics.Raycast(pos, Vector3.down, out hit, 100f, raycastMask))
|
|
{
|
|
pos.y -= RAY_OFFSET;
|
|
if (pos.y < hit.point.y + Y_OFFSET)
|
|
{
|
|
pos.y = hit.point.y + Y_OFFSET;
|
|
}
|
|
}
|
|
else
|
|
{
|
|
Debug.LogError("EnemySpawner error: raycast failed");
|
|
return;
|
|
}
|
|
|
|
//m_spawned = true;
|
|
m_spawnData.spawned = true;
|
|
m_spawnData.numSpawned++;
|
|
var enemy = Instantiate(m_prefab, pos, transform.rotation, transform);
|
|
m_spawnedAI = enemy.GetComponent<vControlAI>();
|
|
if (m_spawnedAI)
|
|
{
|
|
m_spawnedAI.onDead.AddListener(OnDead);
|
|
m_spawnedAI.onReceiveDamage.AddListener(OnReceiveDamage);
|
|
}
|
|
|
|
}
|
|
|
|
private void OnReceiveDamage(vDamage arg0)
|
|
{
|
|
m_onReceivedDamage?.Invoke(this);
|
|
}
|
|
|
|
private void OnDead(GameObject arg0)
|
|
{
|
|
m_spawnedAI = null;
|
|
m_OnDead?.Invoke(this);
|
|
}
|
|
|
|
public void CheckSpawn(){
|
|
if (!m_spawnData.spawned && gameObject.activeInHierarchy && (transform.position - m_distanceFrom.position).sqrMagnitude < m_distance * m_distance){
|
|
Spawn();
|
|
}
|
|
}
|
|
|
|
}
|
|
} |