i’ve been working on scavenging and waves i made a post on
but it’s just, working really weirdly
wave and difficulty will increment twice for some reason, i just don’t know how to explain it
not to mention the fact the enemies have to be killed in a specific order in order to even get deleted from a folder (this runs in a seperate script, i’ll include it aswell)
visual presentation:
module script
function RNG(enemy)
local totalChance = 0
for _,chance in enemy do
totalChance += chance
end
local rng = math.random(1, totalChance)
for option,chance in enemy do
rng -= chance
if rng <= 0 then return option end
end
end
function SpawnEnemies(enemies, part)
while enemies < spawnCap.Value do
local size = part.Size
local position = part.Position
local halfSize = size * 0.5
local randomX = math.random(-halfSize.X, halfSize.X)
local randomZ = math.random(-halfSize.Z, halfSize.Z)
local randomPosition = position + Vector3.new(randomX, 0, randomZ)
local enemy = RNG(meleeEnemies) -- meleeEnemies is a table of enemies, for now it only has 1 enemy with a 100% spawn chance so don't worry about it
local enemyClone = enemy:Clone()
enemyClone.Parent = workspace.Enemies
enemyClone.HumanoidRootPart.CFrame = CFrame.new(randomPosition)
enemyClone.DetectionPart.Size = Vector3.new(1000,250,1000)
enemies += 1
task.wait()
end
return enemies
end
local wave = {}
-- // SPAWNING ENEMIES FUNCTION
function wave.SpawnEnemies()
if ongoing.Value then return end
ongoing.Value = true
if difficulty.Value >= 5 and waveNumber.Value >= 5 then
-- // SPAWN RANGED AND MELEE ENEMIES (this is unused for now so don't worry)
else
for _,part in spawnParts:GetChildren() do
local enemies = 0
if part.Name == "WaveSpawn" then
if #workspace.Enemies:GetChildren() > 0 then
workspace.Enemies:ClearAllChildren()
enemies = SpawnEnemies(enemies, part)
print(enemies)
return enemies
end
end
end
end
end
-- // REDUCING ENEMY COUNT FUNCTION
function wave.ReduceEnemyCount(storm, stormStart, stormMoving, scavenging)
local enemyCount = workspace.Enemies
enemyCount.ChildRemoved:Connect(function()
if #enemyCount:GetChildren() > 0 then
local enemies = wave.SpawnEnemies()
enemies -= 1 -- this will NOT subtract
print("Enemies remaining: " .. enemies) -- this will NOT print
else
print("The wave is ending...") -- this will run twice
if waveNumber.Value <= 3 then
spawnCap.Value += 3
else
if difficulty.Value > 12 then
spawnCap.Value *= 2
else
spawnCap.Value += 5
end
end
task.wait(3)
waveNumber.Value += 1 -- this will run twice
difficulty.Value += math.random(1,3) -- this will run twice
print("Current wave: " .. waveNumber.Value)
print("Current difficulty: " .. difficulty.Value)
storm.CFrame = stormStart.CFrame
stormMoving.Value = false
scavenging.Value = true
ongoing.Value = false
end
end)
end
return wave
not to mention the fact the enemies have to be killed in a specific order in order to even get deleted from a folder (this runs in a seperate script, i’ll include it aswell)
this script is inside each enemy
local Dummy = script.Parent
local Humanoid = Dummy.Humanoid
local Animator = Humanoid:FindFirstChildOfClass("Animator") or Instance.new("Animator", Humanoid)
local Idle = Dummy:WaitForChild("Idle")
local Walk = Dummy:WaitForChild("Walk")
local mouth = script.Parent:WaitForChild("Mouth")
local IdleAnim = Animator:LoadAnimation(Idle)
local WalkAnim = Animator:LoadAnimation(Walk)
IdleAnim:Play()
local dService = game:GetService("Debris")
local function changeParent()
if Humanoid.Health <= 0 then
Dummy.Parent = workspace
mouth.DeathSound:Play()
WalkAnim:Stop()
IdleAnim:Stop()
dService:AddItem(Dummy, 10)
end
end
Humanoid.Running:Connect(function(speed)
if speed > 1 then
if not WalkAnim.IsPlaying then
WalkAnim:Play()
IdleAnim:Stop()
end
else
if not IdleAnim.IsPlaying then
WalkAnim:Stop()
IdleAnim:Play()
end
end
end)
while IdleAnim.IsPlaying do
mouth.IdleSound:Play()
local randomCooldown = math.random(3,10)
task.wait(randomCooldown)
end
Humanoid:GetPropertyChangedSignal("Health"):Connect(changeParent)
Specific kill order (this was caused by an entirely different script lmao
Wave end triggering twice (this will trigger once now)
buuuuttt
the SpawnEnemies function will always return nil, looking into this but help would be appreciated
current code:
function RNG(enemy)
local totalChance = 0
for _,chance in enemy do
totalChance += chance
end
local rng = math.random(1, totalChance)
for option,chance in enemy do
rng -= chance
if rng <= 0 then return option end
end
end
function SpawnEnemies(enemies, part)
while enemies < spawnCap.Value do
local size = part.Size
local position = part.Position
local halfSize = size * 0.5
local randomX = math.random(-halfSize.X, halfSize.X)
local randomZ = math.random(-halfSize.Z, halfSize.Z)
local randomPosition = position + Vector3.new(randomX, 0, randomZ)
local enemy = RNG(meleeEnemies)
local enemyClone = enemy:Clone()
enemyClone.Parent = workspace.Enemies
enemyClone.HumanoidRootPart.CFrame = CFrame.new(randomPosition)
enemyClone.DetectionPart.Size = Vector3.new(1000,250,1000)
enemies += 1
task.wait()
end
return enemies
end
local wave = {}
-- // SPAWNING ENEMIES FUNCTION
function wave.SpawnEnemies()
if ongoing.Value then return end
ongoing.Value = true
if difficulty.Value >= 5 and waveNumber.Value >= 5 then
-- // SPAWN RANGED AND MELEE ENEMIES
else
for _,part in spawnParts:GetChildren() do
local enemies = 0
if part.Name == "WaveSpawn" then
if #workspace.Enemies:GetChildren() > 0 then
workspace.Enemies:ClearAllChildren()
enemies = SpawnEnemies(enemies, part)
print(enemies)
return enemies
end
end
end
end
end
-- // REDUCING ENEMY COUNT FUNCTION
function wave.ReduceEnemyCount(storm, stormStart, stormMoving, scavenging)
local enemies = wave.SpawnEnemies()
print(enemies) -- this is nil frown frown
local enemyCount = workspace.Enemies
if #enemyCount:GetChildren() > 0 then
print("abc")
enemies -= 1 -- tries to subtract from nil! error!!!!
print("Enemies remaining: " .. enemies)
else
print("The wave is ending...")
if waveNumber.Value <= 3 then
spawnCap.Value += 3
else
if difficulty.Value > 12 then
spawnCap.Value *= 2
else
spawnCap.Value += 5
end
end
task.wait(3)
waveNumber.Value += 1
difficulty.Value += math.random(1,3)
print("Current wave: " .. waveNumber.Value)
print("Current difficulty: " .. difficulty.Value)
storm.CFrame = stormStart.CFrame
stormMoving.Value = false
scavenging.Value = true
ongoing.Value = false
end
end
return wave
i kept calling a function that kept adding +1 to the enemy count, which would result in an endless loop of subtracting 1 and adding 1 lol
had to create a variable outside the spawning enemies function and change + return that instead of having a enemiesvariable inside the function
the code looks like this now
local enemyStats = require(game:GetService("ServerScriptService"):WaitForChild("Enemies").EnemyStats)
local difficulty = game:GetService("ServerScriptService"):WaitForChild("Phases"):WaitForChild("Waves").Difficulty
local waveNumber = game:GetService("ServerScriptService"):WaitForChild("Phases"):WaitForChild("Waves").Wave
local spawnCap = game:GetService("ServerScriptService"):WaitForChild("Phases"):WaitForChild("Waves").SpawnCap
local spawnParts = workspace:WaitForChild("SpawnParts")
local SS = game:GetService("ServerStorage")
local meleeEnemies = {
[SS.Enemies.WaveEnemies.Shambler] = 100
}
local rangedEnemies = { -- UNUSED FOR NOW
}
function RNG(enemy)
local totalChance = 0
for _,chance in enemy do
totalChance += chance
end
local rng = math.random(1, totalChance)
for option,chance in enemy do
rng -= chance
if rng <= 0 then return option end
end
end
local wave = {}
-- // SPAWNING ENEMIES FUNCTION
local totalEnemies = 0
function wave.SpawnEnemies()
totalEnemies = 0
workspace.Enemies:ClearAllChildren()
if difficulty.Value >= 5 and waveNumber.Value >= 5 then
-- // SPAWN RANGED AND MELEE ENEMIES
end
for _,part in spawnParts:GetChildren() do
if part.Name == "WaveSpawn" then
while totalEnemies < spawnCap.Value do
local size = part.Size
local position = part.Position
local halfSize = size * 0.5
local randomX = math.random(-halfSize.X, halfSize.X)
local randomZ = math.random(-halfSize.Z, halfSize.Z)
local randomPosition = position + Vector3.new(randomX, 0, randomZ)
local enemy = RNG(meleeEnemies)
local enemyClone = enemy:Clone()
enemyClone.Parent = workspace.Enemies
enemyClone.HumanoidRootPart.CFrame = CFrame.new(randomPosition)
enemyClone.DetectionPart.Size = Vector3.new(1000,250,1000)
totalEnemies += 1
print("Spawned enemy, total enemies: " .. totalEnemies)
task.wait()
end
return totalEnemies
end
end
end
-- // REDUCING ENEMY COUNT FUNCTION
function wave.ReduceEnemyCount(storm, stormStart, stormMoving, scavenging)
local enemyCount = workspace.Enemies
if #enemyCount:GetChildren() > 0 then
totalEnemies -= 1
print("Enemies remaining: " .. totalEnemies)
else
print("The wave is ending...")
if waveNumber.Value <= 3 then
spawnCap.Value += 3
else
if difficulty.Value > 12 then
spawnCap.Value *= 2
else
spawnCap.Value += 5
end
end
task.wait(3)
waveNumber.Value += 1
difficulty.Value += math.random(1,3)
print("Current wave: " .. waveNumber.Value)
print("Current difficulty: " .. difficulty.Value)
storm.CFrame = stormStart.CFrame
stormMoving.Value = false
scavenging.Value = true
end
end
-- // DESTROY LOOTABLES FUNCTION
function wave.DestroyLootables()
for _,lootable in workspace.SpawnParts:GetChildren() do
if lootable.Name == "Locker" or lootable.Name == "Crate" then
lootable:Destroy()
end
end
end
return wave
if anyone ever gets a genius idea to code something like this i hope they find this helpful lol