Menu
CoddyTech

Tembak

Pelajaran 8 dari 18 dalam kursus Game Roblox: Tower Defense di Coddy.

Menghadap musuh adalah setengah dari tugas. shoot melukai target dengan Humanoid:TakeDamage dan memancarkan kilatan cahaya singkat dari kepala ke target: sebuah part neon tipis yang dihapus oleh Debris sepersepuluh detik kemudian.

Debris:AddItem(ray, 0.1) -- dihapus setelah 0.1 detik

Setelah menembak, menara menunggu selama Cooldown sebelum bisa menembak lagi. Itulah yang membuat Archer cepat dan Cannon lambat.

Saat kesehatan Humanoid mencapai 0, event Died-nya terpicu. Musuh yang kalah harus langsung meninggalkan game, jadi spawnEnemy menghubungkan Died agar musuh itu dihancurkan: setelah itu, walkPath melihat bahwa musuh tersebut sudah tidak ada dan berhenti.

challenge icon

Tantangan

Sedang
  1. Dapatkan service Debris. Tulis beam(from, to): sebuah part neon yang ditambatkan, berukuran 0.2 kali 0.2 dan sepanjang jaraknya, atur dengan CFrame.lookAt((from + to) / 2, to), lalu hapus menggunakan Debris setelah 0.1 detik.
  2. Tulis shoot(tower, target, info): terapkan TakeDamage(info.Damage) pada Humanoid target, lalu buat beam dari kepala ke target.
  3. Di runTower, tembak setelah berputar, lalu tunggu selama info.Cooldown alih-alih 0.1 (tetap gunakan 0.1 jika tidak ada target).
  4. Di spawnEnemy, hancurkan musuh saat Humanoid-nya mati.

Tekan Play, lalu Check.

Coba sendiri

local Players = game:GetService("Players")
local ServerStorage = game:GetService("ServerStorage")
local Settings = require(game.ReplicatedStorage.Settings)

local remotes = game.ReplicatedStorage.Remotes
local enemies = workspace.Enemies
local towers = workspace.Towers

print("The base can take " .. Settings.BaseHealth .. " hits")

-- Titik-titik jalur secara berurutan (dinamai 1, 2, 3...)
local waypoints = workspace.Path.Waypoints:GetChildren()
table.sort(waypoints, function(a, b)
	return tonumber(a.Name) < tonumber(b.Name)
end)

-- Kesehatan markas sebagai atribut workspace: setiap client dapat membacanya
workspace:SetAttribute("BaseHealth", Settings.BaseHealth)

-- Setiap pemain mendapat Money di papan peringkat
Players.PlayerAdded:Connect(function(player)
	local leaderstats = Instance.new("Folder")
	leaderstats.Name = "leaderstats"
	leaderstats.Parent = player

	local money = Instance.new("IntValue")
	money.Name = "Money"
	money.Value = Settings.StartMoney
	money.Parent = leaderstats
end)

-- Musuh mencapai markas
local function damageBase(amount)
	local health = math.max(0, workspace:GetAttribute("BaseHealth") - amount)
	workspace:SetAttribute("BaseHealth", health)
end

-- Gerakkan musuh menyusuri jalur. MoveTo berhenti setelah 8 detik dan memberi tahu
-- (MoveToFinished dengan false), jadi musuh yang lambat digerakkan lagi sampai tiba.
local function walkPath(enemy)
	local humanoid = enemy.Humanoid
	for i = 2, #waypoints do
		repeat
			humanoid:MoveTo(waypoints[i].Position)
		until humanoid.MoveToFinished:Wait() or not enemy.Parent
		if not enemy.Parent then
			return
		end
	end
	-- Musuh mencapai markas
	damageBase(Settings.Enemies[enemy.Name].Damage)
	enemy:Destroy()
end

-- Musuh baru di gerbang, menyusuri jalur
local function spawnEnemy(kind)
	local enemy = ServerStorage.Enemies[kind]:Clone()
	-- Ditempatkan tepat di atas titik jalur pertama
	enemy:PivotTo(waypoints[1].CFrame + Vector3.new(0, 5, 0))
	local info = Settings.Enemies[kind]
	enemy.Humanoid.MaxHealth = info.Health
	enemy.Humanoid.Health = info.Health
	enemy.Humanoid.WalkSpeed = info.Speed
	enemy.Parent = enemies
	task.spawn(walkPath, enemy)
	return enemy
end

-- Musuh hidup terdekat dalam jangkauan suatu titik, atau nil
local function nearestEnemy(position, range)
	local best, bestDistance = nil, range
	for _, enemy in enemies:GetChildren() do
		local root = enemy:FindFirstChild("HumanoidRootPart")
		if root and enemy.Humanoid.Health > 0 then
			local distance = (root.Position - position).Magnitude
			if distance <= bestDistance then
				best, bestDistance = enemy, distance
			end
		end
	end
	return best
end

-- Aktivitas menara: bidik musuh terdekat dalam jangkauan
local function runTower(tower)
	local info = Settings.Towers[tower.Name]
	while tower.Parent do
		local target = nearestEnemy(tower.Head.Position, info.Range)
		if target then
			tower.Head.CFrame = CFrame.lookAt(tower.Head.Position, target.HumanoidRootPart.Position)
			task.wait(0.1)
		else
			task.wait(0.1)
		end
	end
end

-- Bangun menara di atas landasan
local function placeTower(pad, kind)
	local tower = ServerStorage.Towers[kind]:Clone()
	tower:PivotTo(pad.CFrame + Vector3.new(0, pad.Size.Y / 2 + 1, 0))
	tower.Parent = towers
	task.spawn(runTower, tower)
end

-- client meminta menara di atas alas
remotes.Place.OnServerEvent:Connect(function(player, pad, kind)
	placeTower(pad, kind)
end)

-- Satu gelombang: musuh muncul satu per satu, lalu tunggu sampai semuanya hilang
local function runWave(list)
	for _, kind in list do
		spawnEnemy(kind)
		task.wait(Settings.SpawnGap)
	end
	while #enemies:GetChildren() > 0 do
		task.wait(0.2)
	end
end

-- Gelombang-gelombang, masing-masing setelah jeda
for i, list in Settings.Waves do
	task.wait(Settings.WaveBreak)
	runWave(list)
end
quiz iconUji dirimu

Pelajaran ini berisi kuis singkat. Mulai pelajarannya untuk menjawab kuis dan melacak progresmu.

Semua pelajaran di Game Roblox: Tower Defense

Latihan sendiri: Playground Roblox