From ced721f1adbee448bc0b79f1afcad6505d2079b7 Mon Sep 17 00:00:00 2001 From: Gabriel Kaszewski Date: Sat, 12 Jul 2025 02:34:15 +0200 Subject: [PATCH] Add EnemyWave and EnemyWavesManager classes; implement enemy spawning system for wave-based gameplay --- Assets/Scenes/main.unity | 474 ++++++------------ Assets/Scripts/Data/EnemyWave.cs | 28 ++ Assets/Scripts/Data/EnemyWave.cs.meta | 3 + Assets/Scripts/Systems/EnemyWavesManager.cs | 68 +++ .../Scripts/Systems/EnemyWavesManager.cs.meta | 3 + 5 files changed, 250 insertions(+), 326 deletions(-) create mode 100644 Assets/Scripts/Data/EnemyWave.cs create mode 100644 Assets/Scripts/Data/EnemyWave.cs.meta create mode 100644 Assets/Scripts/Systems/EnemyWavesManager.cs create mode 100644 Assets/Scripts/Systems/EnemyWavesManager.cs.meta diff --git a/Assets/Scenes/main.unity b/Assets/Scenes/main.unity index 66c64c0..5048713 100644 --- a/Assets/Scenes/main.unity +++ b/Assets/Scenes/main.unity @@ -119,7 +119,7 @@ NavMeshSettings: debug: m_Flags: 0 m_NavMeshData: {fileID: 0} ---- !u!1 &401545662 +--- !u!1 &54233098 GameObject: m_ObjectHideFlags: 0 m_CorrespondingSourceObject: {fileID: 0} @@ -127,85 +127,35 @@ GameObject: m_PrefabAsset: {fileID: 0} serializedVersion: 6 m_Component: - - component: {fileID: 401545663} - - component: {fileID: 401545664} + - component: {fileID: 54233099} m_Layer: 0 - m_Name: Square + m_Name: Spawnpoints m_TagString: Untagged m_Icon: {fileID: 0} m_NavMeshLayer: 0 m_StaticEditorFlags: 0 m_IsActive: 1 ---- !u!4 &401545663 +--- !u!4 &54233099 Transform: m_ObjectHideFlags: 0 m_CorrespondingSourceObject: {fileID: 0} m_PrefabInstance: {fileID: 0} m_PrefabAsset: {fileID: 0} - m_GameObject: {fileID: 401545662} + m_GameObject: {fileID: 54233098} serializedVersion: 2 m_LocalRotation: {x: 0, y: 0, z: 0, w: 1} m_LocalPosition: {x: 0, y: 0, z: 0} m_LocalScale: {x: 1, y: 1, z: 1} m_ConstrainProportionsScale: 0 - m_Children: [] - m_Father: {fileID: 2062887720} + m_Children: + - {fileID: 521201812} + - {fileID: 1593097268} + - {fileID: 1984647400} + - {fileID: 695199257} + - {fileID: 1869990421} + - {fileID: 1304208761} + m_Father: {fileID: 0} m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0} ---- !u!212 &401545664 -SpriteRenderer: - m_ObjectHideFlags: 0 - m_CorrespondingSourceObject: {fileID: 0} - m_PrefabInstance: {fileID: 0} - m_PrefabAsset: {fileID: 0} - m_GameObject: {fileID: 401545662} - m_Enabled: 1 - m_CastShadows: 0 - m_ReceiveShadows: 0 - m_DynamicOccludee: 1 - m_StaticShadowCaster: 0 - m_MotionVectors: 1 - m_LightProbeUsage: 1 - m_ReflectionProbeUsage: 1 - m_RayTracingMode: 0 - m_RayTraceProcedural: 0 - m_RayTracingAccelStructBuildFlagsOverride: 0 - m_RayTracingAccelStructBuildFlags: 1 - m_SmallMeshCulling: 1 - m_RenderingLayerMask: 1 - m_RendererPriority: 0 - m_Materials: - - {fileID: 2100000, guid: a97c105638bdf8b4a8650670310a4cd3, type: 2} - m_StaticBatchInfo: - firstSubMesh: 0 - subMeshCount: 0 - m_StaticBatchRoot: {fileID: 0} - m_ProbeAnchor: {fileID: 0} - m_LightProbeVolumeOverride: {fileID: 0} - m_ScaleInLightmap: 1 - m_ReceiveGI: 1 - m_PreserveUVs: 0 - m_IgnoreNormalsForChartDetection: 0 - m_ImportantGI: 0 - m_StitchLightmapSeams: 1 - m_SelectedEditorRenderState: 0 - m_MinimumChartSize: 4 - m_AutoUVMaxDistance: 0.5 - m_AutoUVMaxAngle: 89 - m_LightmapParameters: {fileID: 0} - m_SortingLayerID: 0 - m_SortingLayer: 0 - m_SortingOrder: 0 - m_Sprite: {fileID: 7482667652216324306, guid: 311925a002f4447b3a28927169b83ea6, type: 3} - m_Color: {r: 0.8018868, g: 0.23829654, b: 0.23829654, a: 1} - m_FlipX: 0 - m_FlipY: 0 - m_DrawMode: 0 - m_Size: {x: 1, y: 1} - m_AdaptiveModeThreshold: 0.5 - m_SpriteTileMode: 0 - m_WasSpriteAssigned: 1 - m_MaskInteraction: 0 - m_SpriteSortPoint: 0 --- !u!1 &519420028 GameObject: m_ObjectHideFlags: 0 @@ -343,6 +293,37 @@ Transform: m_Children: [] m_Father: {fileID: 0} m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0} +--- !u!1 &521201811 +GameObject: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + serializedVersion: 6 + m_Component: + - component: {fileID: 521201812} + m_Layer: 0 + m_Name: Spawn + m_TagString: Untagged + m_Icon: {fileID: 0} + m_NavMeshLayer: 0 + m_StaticEditorFlags: 0 + m_IsActive: 1 +--- !u!4 &521201812 +Transform: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + m_GameObject: {fileID: 521201811} + serializedVersion: 2 + m_LocalRotation: {x: 0, y: 0, z: 0, w: 1} + m_LocalPosition: {x: -8.3, y: 5.09, z: 0} + m_LocalScale: {x: 1, y: 1, z: 1} + m_ConstrainProportionsScale: 0 + m_Children: [] + m_Father: {fileID: 54233099} + m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0} --- !u!1 &541374773 GameObject: m_ObjectHideFlags: 0 @@ -514,6 +495,37 @@ Transform: m_Children: [] m_Father: {fileID: 0} m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0} +--- !u!1 &695199256 +GameObject: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + serializedVersion: 6 + m_Component: + - component: {fileID: 695199257} + m_Layer: 0 + m_Name: Spawn (3) + m_TagString: Untagged + m_Icon: {fileID: 0} + m_NavMeshLayer: 0 + m_StaticEditorFlags: 0 + m_IsActive: 1 +--- !u!4 &695199257 +Transform: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + m_GameObject: {fileID: 695199256} + serializedVersion: 2 + m_LocalRotation: {x: 0, y: 0, z: 0, w: 1} + m_LocalPosition: {x: -8.27, y: -5.61, z: 0} + m_LocalScale: {x: 1, y: 1, z: 1} + m_ConstrainProportionsScale: 0 + m_Children: [] + m_Father: {fileID: 54233099} + m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0} --- !u!1 &749274448 GameObject: m_ObjectHideFlags: 0 @@ -524,6 +536,7 @@ GameObject: m_Component: - component: {fileID: 749274450} - component: {fileID: 749274449} + - component: {fileID: 749274451} m_Layer: 0 m_Name: GameManager m_TagString: Untagged @@ -545,7 +558,7 @@ MonoBehaviour: m_EditorClassIdentifier: currentRound: 1 coins: 0 - roundTime: 10 + roundTime: 60 maxRounds: 20 player: {fileID: 1261447603} --- !u!4 &749274450 @@ -563,6 +576,28 @@ Transform: m_Children: [] m_Father: {fileID: 0} m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0} +--- !u!114 &749274451 +MonoBehaviour: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + m_GameObject: {fileID: 749274448} + m_Enabled: 1 + m_EditorHideFlags: 0 + m_Script: {fileID: 11500000, guid: a52015481bb34a49b69096e5eff49e42, type: 3} + m_Name: + m_EditorClassIdentifier: + waves: + - {fileID: 11400000, guid: 4991b70e99800747597a28d7cff2a3d8, type: 2} + spawnPoints: + - {fileID: 521201812} + - {fileID: 1593097268} + - {fileID: 1984647400} + - {fileID: 695199257} + - {fileID: 1869990421} + - {fileID: 1304208761} + gameManager: {fileID: 749274449} --- !u!1 &869793958 GameObject: m_ObjectHideFlags: 0 @@ -987,7 +1022,7 @@ MonoBehaviour: m_Name: m_EditorClassIdentifier: character: {fileID: 1261447603} ---- !u!1 &1414795143 +--- !u!1 &1304208760 GameObject: m_ObjectHideFlags: 0 m_CorrespondingSourceObject: {fileID: 0} @@ -995,86 +1030,30 @@ GameObject: m_PrefabAsset: {fileID: 0} serializedVersion: 6 m_Component: - - component: {fileID: 1414795144} - - component: {fileID: 1414795145} + - component: {fileID: 1304208761} m_Layer: 0 - m_Name: Capsule + m_Name: Spawn (5) m_TagString: Untagged m_Icon: {fileID: 0} m_NavMeshLayer: 0 m_StaticEditorFlags: 0 m_IsActive: 1 ---- !u!4 &1414795144 +--- !u!4 &1304208761 Transform: m_ObjectHideFlags: 0 m_CorrespondingSourceObject: {fileID: 0} m_PrefabInstance: {fileID: 0} m_PrefabAsset: {fileID: 0} - m_GameObject: {fileID: 1414795143} + m_GameObject: {fileID: 1304208760} serializedVersion: 2 m_LocalRotation: {x: 0, y: 0, z: 0, w: 1} - m_LocalPosition: {x: 0, y: 0, z: 0} - m_LocalScale: {x: 0.21374999, y: 0.6375, z: 1} + m_LocalPosition: {x: 8.89, y: 0.1, z: 0} + m_LocalScale: {x: 1, y: 1, z: 1} m_ConstrainProportionsScale: 0 m_Children: [] - m_Father: {fileID: 1516289535} + m_Father: {fileID: 54233099} m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0} ---- !u!212 &1414795145 -SpriteRenderer: - m_ObjectHideFlags: 0 - m_CorrespondingSourceObject: {fileID: 0} - m_PrefabInstance: {fileID: 0} - m_PrefabAsset: {fileID: 0} - m_GameObject: {fileID: 1414795143} - m_Enabled: 1 - m_CastShadows: 0 - m_ReceiveShadows: 0 - m_DynamicOccludee: 1 - m_StaticShadowCaster: 0 - m_MotionVectors: 1 - m_LightProbeUsage: 1 - m_ReflectionProbeUsage: 1 - m_RayTracingMode: 0 - m_RayTraceProcedural: 0 - m_RayTracingAccelStructBuildFlagsOverride: 0 - m_RayTracingAccelStructBuildFlags: 1 - m_SmallMeshCulling: 1 - m_RenderingLayerMask: 1 - m_RendererPriority: 0 - m_Materials: - - {fileID: 2100000, guid: a97c105638bdf8b4a8650670310a4cd3, type: 2} - m_StaticBatchInfo: - firstSubMesh: 0 - subMeshCount: 0 - m_StaticBatchRoot: {fileID: 0} - m_ProbeAnchor: {fileID: 0} - m_LightProbeVolumeOverride: {fileID: 0} - m_ScaleInLightmap: 1 - m_ReceiveGI: 1 - m_PreserveUVs: 0 - m_IgnoreNormalsForChartDetection: 0 - m_ImportantGI: 0 - m_StitchLightmapSeams: 1 - m_SelectedEditorRenderState: 0 - m_MinimumChartSize: 4 - m_AutoUVMaxDistance: 0.5 - m_AutoUVMaxAngle: 89 - m_LightmapParameters: {fileID: 0} - m_SortingLayerID: 0 - m_SortingLayer: 0 - m_SortingOrder: 0 - m_Sprite: {fileID: -9095717837082945937, guid: 207ee8102dd4143d288186ef0be518ee, type: 3} - m_Color: {r: 1, g: 0.023584902, b: 0.51480997, a: 1} - m_FlipX: 0 - m_FlipY: 0 - m_DrawMode: 0 - m_Size: {x: 1, y: 2} - m_AdaptiveModeThreshold: 0.5 - m_SpriteTileMode: 0 - m_WasSpriteAssigned: 1 - m_MaskInteraction: 0 - m_SpriteSortPoint: 0 ---- !u!1 &1516289534 +--- !u!1 &1593097267 GameObject: m_ObjectHideFlags: 0 m_CorrespondingSourceObject: {fileID: 0} @@ -1082,53 +1061,30 @@ GameObject: m_PrefabAsset: {fileID: 0} serializedVersion: 6 m_Component: - - component: {fileID: 1516289535} - - component: {fileID: 1516289536} + - component: {fileID: 1593097268} m_Layer: 0 - m_Name: Melee Weapon + m_Name: Spawn (1) m_TagString: Untagged m_Icon: {fileID: 0} m_NavMeshLayer: 0 m_StaticEditorFlags: 0 m_IsActive: 1 ---- !u!4 &1516289535 +--- !u!4 &1593097268 Transform: m_ObjectHideFlags: 0 m_CorrespondingSourceObject: {fileID: 0} m_PrefabInstance: {fileID: 0} m_PrefabAsset: {fileID: 0} - m_GameObject: {fileID: 1516289534} + m_GameObject: {fileID: 1593097267} serializedVersion: 2 m_LocalRotation: {x: 0, y: 0, z: 0, w: 1} - m_LocalPosition: {x: -0.168, y: -0.498, z: 0} + m_LocalPosition: {x: 7.96, y: 5.09, z: 0} m_LocalScale: {x: 1, y: 1, z: 1} m_ConstrainProportionsScale: 0 - m_Children: - - {fileID: 1414795144} - m_Father: {fileID: 2062887720} + m_Children: [] + m_Father: {fileID: 54233099} m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0} ---- !u!114 &1516289536 -MonoBehaviour: - m_ObjectHideFlags: 0 - m_CorrespondingSourceObject: {fileID: 0} - m_PrefabInstance: {fileID: 0} - m_PrefabAsset: {fileID: 0} - m_GameObject: {fileID: 1516289534} - m_Enabled: 1 - m_EditorHideFlags: 0 - m_Script: {fileID: 11500000, guid: e4ff53f671604189b15fac28115b2b70, type: 3} - m_Name: - m_EditorClassIdentifier: - weaponStats: - damage: 2 - attackSpeed: 1 - range: 0.1 - damageType: 0 - character: {fileID: 2062887717} - targetMask: - serializedVersion: 2 - m_Bits: 64 ---- !u!1 &2062887715 +--- !u!1 &1869990420 GameObject: m_ObjectHideFlags: 0 m_CorrespondingSourceObject: {fileID: 0} @@ -1136,194 +1092,60 @@ GameObject: m_PrefabAsset: {fileID: 0} serializedVersion: 6 m_Component: - - component: {fileID: 2062887720} - - component: {fileID: 2062887719} - - component: {fileID: 2062887718} - - component: {fileID: 2062887717} - - component: {fileID: 2062887716} - - component: {fileID: 2062887723} - - component: {fileID: 2062887722} - - component: {fileID: 2062887721} + - component: {fileID: 1869990421} m_Layer: 0 - m_Name: Test Enemy - m_TagString: Enemy + m_Name: Spawn (4) + m_TagString: Untagged m_Icon: {fileID: 0} m_NavMeshLayer: 0 m_StaticEditorFlags: 0 m_IsActive: 1 ---- !u!114 &2062887716 -MonoBehaviour: - m_ObjectHideFlags: 0 - m_CorrespondingSourceObject: {fileID: 0} - m_PrefabInstance: {fileID: 0} - m_PrefabAsset: {fileID: 0} - m_GameObject: {fileID: 2062887715} - m_Enabled: 1 - m_EditorHideFlags: 0 - m_Script: {fileID: 11500000, guid: 9139aea24fd54a5eb0f5fc1556478cb6, type: 3} - m_Name: - m_EditorClassIdentifier: - character: {fileID: 2062887717} - initialHealth: 100 ---- !u!114 &2062887717 -MonoBehaviour: - m_ObjectHideFlags: 0 - m_CorrespondingSourceObject: {fileID: 0} - m_PrefabInstance: {fileID: 0} - m_PrefabAsset: {fileID: 0} - m_GameObject: {fileID: 2062887715} - m_Enabled: 1 - m_EditorHideFlags: 0 - m_Script: {fileID: 11500000, guid: 44b572240c4243c9954bd19967bfeb64, type: 3} - m_Name: - m_EditorClassIdentifier: - attributes: - health: 100 - maxHealth: 100 - moveSpeed: 5 - luck: 0 - armor: 0 - level: 1 - experience: 0 - baseExperienceToLevelUp: 100 - damage: 1 - rangedDamage: 1 - meleeDamage: 1 - attackRange: 16 - attackSpeed: 1 ---- !u!50 &2062887718 -Rigidbody2D: - serializedVersion: 5 - m_ObjectHideFlags: 0 - m_CorrespondingSourceObject: {fileID: 0} - m_PrefabInstance: {fileID: 0} - m_PrefabAsset: {fileID: 0} - m_GameObject: {fileID: 2062887715} - m_BodyType: 1 - m_Simulated: 1 - m_UseFullKinematicContacts: 0 - m_UseAutoMass: 0 - m_Mass: 60 - m_LinearDamping: 0 - m_AngularDamping: 0.05 - m_GravityScale: 0 - m_Material: {fileID: 0} - m_IncludeLayers: - serializedVersion: 2 - m_Bits: 0 - m_ExcludeLayers: - serializedVersion: 2 - m_Bits: 0 - m_Interpolate: 0 - m_SleepingMode: 1 - m_CollisionDetection: 0 - m_Constraints: 4 ---- !u!61 &2062887719 -BoxCollider2D: - m_ObjectHideFlags: 0 - m_CorrespondingSourceObject: {fileID: 0} - m_PrefabInstance: {fileID: 0} - m_PrefabAsset: {fileID: 0} - m_GameObject: {fileID: 2062887715} - m_Enabled: 1 - serializedVersion: 3 - m_Density: 1 - m_Material: {fileID: 0} - m_IncludeLayers: - serializedVersion: 2 - m_Bits: 0 - m_ExcludeLayers: - serializedVersion: 2 - m_Bits: 0 - m_LayerOverridePriority: 0 - m_ForceSendLayers: - serializedVersion: 2 - m_Bits: 4294967295 - m_ForceReceiveLayers: - serializedVersion: 2 - m_Bits: 4294967295 - m_ContactCaptureLayers: - serializedVersion: 2 - m_Bits: 4294967295 - m_CallbackLayers: - serializedVersion: 2 - m_Bits: 4294967295 - m_IsTrigger: 0 - m_UsedByEffector: 0 - m_CompositeOperation: 0 - m_CompositeOrder: 0 - m_Offset: {x: 0, y: 0} - m_SpriteTilingProperty: - border: {x: 0, y: 0, z: 0, w: 0} - pivot: {x: 0, y: 0} - oldSize: {x: 0, y: 0} - newSize: {x: 0, y: 0} - adaptiveTilingThreshold: 0 - drawMode: 0 - adaptiveTiling: 0 - m_AutoTiling: 0 - m_Size: {x: 1, y: 1} - m_EdgeRadius: 0 ---- !u!4 &2062887720 +--- !u!4 &1869990421 Transform: m_ObjectHideFlags: 0 m_CorrespondingSourceObject: {fileID: 0} m_PrefabInstance: {fileID: 0} m_PrefabAsset: {fileID: 0} - m_GameObject: {fileID: 2062887715} + m_GameObject: {fileID: 1869990420} serializedVersion: 2 m_LocalRotation: {x: 0, y: 0, z: 0, w: 1} - m_LocalPosition: {x: 6.56, y: 3.81, z: 0} + m_LocalPosition: {x: -8.27, y: 0.1, z: 0} m_LocalScale: {x: 1, y: 1, z: 1} m_ConstrainProportionsScale: 0 - m_Children: - - {fileID: 401545663} - - {fileID: 1516289535} - m_Father: {fileID: 0} + m_Children: [] + m_Father: {fileID: 54233099} m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0} ---- !u!114 &2062887721 -MonoBehaviour: +--- !u!1 &1984647399 +GameObject: m_ObjectHideFlags: 0 m_CorrespondingSourceObject: {fileID: 0} m_PrefabInstance: {fileID: 0} m_PrefabAsset: {fileID: 0} - m_GameObject: {fileID: 2062887715} - m_Enabled: 1 - m_EditorHideFlags: 0 - m_Script: {fileID: 11500000, guid: 73900af7351645fdb19d016d621feb35, type: 3} - m_Name: - m_EditorClassIdentifier: - expReward: 5 - coinReward: 1 ---- !u!114 &2062887722 -MonoBehaviour: + serializedVersion: 6 + m_Component: + - component: {fileID: 1984647400} + m_Layer: 0 + m_Name: Spawn (2) + m_TagString: Untagged + m_Icon: {fileID: 0} + m_NavMeshLayer: 0 + m_StaticEditorFlags: 0 + m_IsActive: 1 +--- !u!4 &1984647400 +Transform: m_ObjectHideFlags: 0 m_CorrespondingSourceObject: {fileID: 0} m_PrefabInstance: {fileID: 0} m_PrefabAsset: {fileID: 0} - m_GameObject: {fileID: 2062887715} - m_Enabled: 1 - m_EditorHideFlags: 0 - m_Script: {fileID: 11500000, guid: 5fa2924c6ed8486bbfa95c439bf9e421, type: 3} - m_Name: - m_EditorClassIdentifier: - character: {fileID: 2062887717} - deathBehavior: - _implementer: {fileID: 2062887721} ---- !u!114 &2062887723 -MonoBehaviour: - m_ObjectHideFlags: 0 - m_CorrespondingSourceObject: {fileID: 0} - m_PrefabInstance: {fileID: 0} - m_PrefabAsset: {fileID: 0} - m_GameObject: {fileID: 2062887715} - m_Enabled: 1 - m_EditorHideFlags: 0 - m_Script: {fileID: 11500000, guid: 9139aea24fd54a5eb0f5fc1556478cb6, type: 3} - m_Name: - m_EditorClassIdentifier: - character: {fileID: 2062887717} - initialHealth: 100 + m_GameObject: {fileID: 1984647399} + serializedVersion: 2 + m_LocalRotation: {x: 0, y: 0, z: 0, w: 1} + m_LocalPosition: {x: 7.96, y: -5.61, z: 0} + m_LocalScale: {x: 1, y: 1, z: 1} + m_ConstrainProportionsScale: 0 + m_Children: [] + m_Father: {fileID: 54233099} + m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0} --- !u!1001 &9153788689307318134 PrefabInstance: m_ObjectHideFlags: 0 @@ -1557,7 +1379,7 @@ SceneRoots: - {fileID: 619394802} - {fileID: 1261447604} - {fileID: 541374775} - - {fileID: 2062887720} - {fileID: 9153788689307318134} - {fileID: 1020220801} - {fileID: 749274450} + - {fileID: 54233099} diff --git a/Assets/Scripts/Data/EnemyWave.cs b/Assets/Scripts/Data/EnemyWave.cs new file mode 100644 index 0000000..8a063c2 --- /dev/null +++ b/Assets/Scripts/Data/EnemyWave.cs @@ -0,0 +1,28 @@ +using System; +using System.Collections.Generic; +using Sirenix.OdinInspector; +using Sirenix.Serialization; +using UnityEngine; + +namespace Data +{ + [CreateAssetMenu(menuName = "Game/Wave")] + public class EnemyWave : ScriptableObject + { + [TableList] + [OdinSerialize] public List spawns = new(); + } + + [Serializable] + public class EnemySpawnInfo + { + [HorizontalGroup("Row", width: 80)] + [OdinSerialize, PreviewField(80)] public GameObject enemyPrefab; + + [HorizontalGroup("Row")] + [OdinSerialize] public int count = 1; + + [HorizontalGroup("Row")] [OdinSerialize] + public float spawnInterval = 0.5f; + } +} \ No newline at end of file diff --git a/Assets/Scripts/Data/EnemyWave.cs.meta b/Assets/Scripts/Data/EnemyWave.cs.meta new file mode 100644 index 0000000..acbcb95 --- /dev/null +++ b/Assets/Scripts/Data/EnemyWave.cs.meta @@ -0,0 +1,3 @@ +fileFormatVersion: 2 +guid: 998e0b91932048b1b2abcfcf4936b508 +timeCreated: 1752279009 \ No newline at end of file diff --git a/Assets/Scripts/Systems/EnemyWavesManager.cs b/Assets/Scripts/Systems/EnemyWavesManager.cs new file mode 100644 index 0000000..1ddbcba --- /dev/null +++ b/Assets/Scripts/Systems/EnemyWavesManager.cs @@ -0,0 +1,68 @@ +using System; +using System.Collections; +using System.Collections.Generic; +using Data; +using KBCore.Refs; +using Sirenix.OdinInspector; +using Sirenix.Serialization; +using UnityEngine; +using Random = UnityEngine.Random; + +namespace Systems +{ + public class EnemyWavesManager : MonoBehaviour + { + [OdinSerialize, ListDrawerSettings(NumberOfItemsPerPage = 20), SerializeField] + private List waves = new(); + + [OdinSerialize, SerializeField] private Transform[] spawnPoints; + + private Coroutine spawnCoroutine; + private List aliveEnemies = new(); + [Self, SerializeField] private GameManager gameManager; + + private void OnEnable() + { + gameManager.OnRoundStart += StartWave; + gameManager.OnRoundEnd += EndWave; + } + + private void OnDisable() + { + gameManager.OnRoundStart -= StartWave; + gameManager.OnRoundEnd -= EndWave; + } + + private void StartWave(int round) + { + if (spawnCoroutine != null) StopCoroutine(spawnCoroutine); + if (round - 1 < waves.Count) spawnCoroutine = StartCoroutine(SpawnWave(waves[round - 1])); + } + + private void EndWave(int round) + { + foreach (var enemy in aliveEnemies) + { + if (!enemy) continue; + Destroy(enemy); + } + + aliveEnemies.Clear(); + if (spawnCoroutine != null) StopCoroutine(spawnCoroutine); + } + + private IEnumerator SpawnWave(EnemyWave wave) + { + foreach (var spawn in wave.spawns) + { + for (var i = 0; i < spawn.count; i++) + { + var spawnPoint = spawnPoints[Random.Range(0, spawnPoints.Length)]; + var enemy = Instantiate(spawn.enemyPrefab, spawnPoint.position, Quaternion.identity); + aliveEnemies.Add(enemy); + yield return new WaitForSeconds(spawn.spawnInterval); + } + } + } + } +} \ No newline at end of file diff --git a/Assets/Scripts/Systems/EnemyWavesManager.cs.meta b/Assets/Scripts/Systems/EnemyWavesManager.cs.meta new file mode 100644 index 0000000..b8c762b --- /dev/null +++ b/Assets/Scripts/Systems/EnemyWavesManager.cs.meta @@ -0,0 +1,3 @@ +fileFormatVersion: 2 +guid: a52015481bb34a49b69096e5eff49e42 +timeCreated: 1752279160 \ No newline at end of file