Bộ đếm thời gian và sự kiện

*Nội dung này được dịch bằng AI (Beta) và có thể có lỗi. Để xem trang này bằng tiếng Anh, hãy nhấp vào đây.

Trong suốt một vòng, các kịch bản sẽ cần theo dõi thời gian và gửi tín hiệu giữa các kịch bản khác nhau.Thời gian sẽ được quản lý bằng cách sử dụng một kịch bản thời gian, trong khi sự kiện, một khái niệm trong lập trình Roblox, sẽ tín hiệu các thay đổi như kết thúc của một tương thích.

Gửi tín hiệu với sự kiện

Với người chơi hiện đang ở trong đấu trường, các sự kiện có thể được sử dụng để tín hiệu bắt đầu trận đấu và mã cho thời gian có thể bắt đầu.Sau đó, một sự kiện cũng có thể được sử dụng để tín hiệu kết thúc trận tương thích, và đã đến lúc chuyển các người chơi trở lại sảnh.

Các sự kiện này không được xây dựng trước, vì vậy các đối tượng sự kiện tùy chỉnh được gọi là sự kiện có thể gắn kết sẽ cần phải được tạo.Các sự kiện có thể gắn kết thường được sử dụng cho các hành động bắn người chơi và tương tự như các sự kiện như Touched hoặc Changed .

Nhiều kịch bản có thể lắng nghe các sự kiện gắn kết tương tự.Điều này giữ cho mã của bạn được tổ chức và dễ dàng thêm mã bổ sung cho khởi đầu hoặc kết thúc trận đấu sau nếu cần thiết.

Tạo sự kiện có thể gắn kết

Bắt đầu bằng cách tạo các đối tượng sự kiện có thể gắn kết cho đầu và cuối của trận tương thích.Vì các sự kiện có thể gắn kết không tương tác với khách hàng, chúng có thể được lưu trong Kho lưu trữ máy chủ.

  1. Trong ServerStorage, tạo một thư mục mới có tên là Sự kiện. Trong thư mục đó, tạo hai BindableEvents có tên là MatchStart và MatchEnd.

Sử dụng sự kiện

Hiện tại, khi người chơi vào sân, khoảng nghỉ tiếp tục khởi động lại thay vì bắt đầu bộ đếm thời gian.Vòng lặp chính của trò chơi cần phải được bảo cho dừng lại và chờ đợi cho đến khi sự kiện MatchEnd bắt lửa trước khi chuyển sang phần tiếp theo của mã.

Sự kiện có hai chức năng tích hợp sẵn: Connect()Wait().Thay vì sử dụng Connect() như trước, gọi Wait() tại MatchEnd để tạm dừng kịch bản quản lý trò chơi cho đến khi MatchEnd bị kích hoạt.Trong trường hợp này, chức năng chờ tạm dừng mã cho đến khi quản lý trò chơi nhận được một tín hiệu cho thấy trận đấu kết thúc.

  1. Trong Quản lý trò chơi , tạo biến cho thư mục Events và sự kiện MatchEnd.


    -- Tập lệnh mô-đun
    local moduleScripts = ServerStorage:WaitForChild("ModuleScripts")
    local matchManager = require(moduleScripts:WaitForChild("MatchManager"))
    local gameSettings = require(moduleScripts:WaitForChild("GameSettings"))
    -- Sự kiện
    local events = ServerStorage:WaitForChild("Events")
    local matchEnd = events:WaitForChild("MatchEnd")
  2. Có kịch bản chờ sự kiện kết thúc trận đấu bắn trước khi di chuyển tiếp theo. Trong vòng lặp , tại cuối , đánh máy: matchEnd.Event:Wait()


    while true do
    repeat
    task.wait(gameSettings.intermissionDuration)
    print("Restarting intermission")
    until #Players:GetPlayers() >= gameSettings.minimumPlayers
    print("Intermission over")
    task.wait(gameSettings.transitionTime)
    matchManager.prepareGame()
    -- Placeholder chờ đợi thời gian của trò chơi.
    matchEnd.Event:Wait()
    end
  3. Thử nghiệm trò chơi.Xác nhận rằng một khi các người chơi ở trong đấu trường, vòng lặp nghỉ giải lao không tiếp tục.Tập lệnh đang chờ tín hiệu matchEnd bắt lửa.

Mẹo khắc phục sự cố

Tại thời điểm này, mã không hoạt động như mong đợi, hãy thử một trong những điều sau.

  • Xem lại việc sử dụng các phép tính dot hoặc colon trong matchEnd.Event:Wait() .
  • Hãy chắc chắn rằng MatchEnd là một BindableEvent, chứ không phải là một đánh máykhác, chẳng hạn như một RemoteEvent.

Sử dụng một bộ đếm thời gian

Một trong những điều kiện sẽ gây ra kết thúc của trận đấu là hết hạn thời gian, sẽ được xử lý thông qua kịch bản.

Thiết lập bộ đếm thời gian

Để thêm một bộ đếm thời gian vào trò chơi, hãy sử dụng kịch bản mô-đun sẵn có trong các bước dưới đây.Nó bao gồm các chức năng để bắt đầu và kết thúc một bộ đếm thời gian, cũng như trả lại số thời gian còn lại.

  1. Trong ServerStorage > ModuleScripts, tạo một kịch bản mới có tên là Timer.

    Thay thế mã bằng mã dưới đây.


    local Timer = {}
    Timer.__index = Timer
    function Timer.new()
    local self = setmetatable({}, Timer)
    self._finishedEvent = Instance.new("BindableEvent")
    self.finished = self._finishedEvent.Event
    self._running = false
    self._startTime = nil
    self._duration = nil
    return self
    end
    function Timer:start(duration)
    if not self._running then
    task.spawn(function()
    self._running = true
    self._duration = duration
    self._startTime = tick()
    while self._running and tick() - self._startTime < duration do
    task.wait()
    end
    local completed = self._running
    self._running = false
    self._startTime = nil
    self._duration = nil
    self._finishedEvent:Fire(completed)
    end)
    else
    warn("Warning: timer could not start again as it is already running.")
    end
    end
    function Timer:getTimeLeft()
    if self._running then
    local now = tick()
    local timeLeft = self._startTime + self._duration - now
    if timeLeft < 0 then
    timeLeft = 0
    end
    return timeLeft
    else
    warn("Warning: could not get remaining time, timer is not running.")
    end
    end
    function Timer:isRunning()
    return self._running
    end
    function Timer:stop()
    self._running = false
    end
    return Timer
  2. Trong MatchManager, yêu cầu các mô-đun GameSettings và Timer.


    local MatchManager = {}
    -- Dịch vụ
    local ServerStorage = game:GetService("ServerStorage")
    -- Tập lệnh mô-đun
    local moduleScripts = ServerStorage:WaitForChild("ModuleScripts")
    local playerManager = require(moduleScripts:WaitForChild("PlayerManager"))
    local gameSettings = require(moduleScripts:WaitForChild("GameSettings"))
    local timer = require(moduleScripts:WaitForChild("Timer"))
  3. Bên dưới các biến, tạo một đối tượng bộ đếm thời gian mới bằng cách đặt một biến có tên là myTimer bằng đúng với timer.new().Vật này sẽ được sử dụng để gọi các chức năng bắt đầu và dừng bộ đếm thời gian.


    local gameSettings = require(moduleScripts:WaitForChild("GameSettings"))
    local timer = require(moduleScripts:WaitForChild("Timer"))
    -- Tạo một đối tượng hẹn giờ mới để được sử dụng để theo dõi thời gian trận đấu.
    local myTimer = timer.new()

Bắt đầu và dừng lại

Bây giờ một bộ đếm thời gian đã được tạo, sử dụng các chức năng bao gồm start()stop() trong một tương thích.Dưới đây là mô tả về mỗi chức năng và tham số nó chấp nhận.

  • start(time) - Bắt đầu bộ đếm thời gian, với thời gian bằng giây là tham số.
  • finished:Connect(functionName) - Khi hẹn giờ kết thúc, chạy chức năng được truyền đến như một tham số.
  1. Trong MatchManager , tạo một chức năng mới có tên timeUp() để chạy khi nào hết thời gian. Bao gồm một tuyên bố in thử nghiệm.


    local myTimer = timer.new()
    -- Chức năng địa phương
    local function timeUp()
    print("Time is up!")
    end
    -- Chức năng mô-đun
    function MatchManager.prepareGame()
    playerManager.sendPlayersToMatch()
    end
    return MatchManager
  2. Dưới timeUp(), thêm một chức năng có tên startTimer() với một tuyên bố in. Bạn sẽ hiển thị bộ đếm thời gian trong trò chơi sau.


    -- Chức năng địa phương
    local function timeUp()
    print("Time is up!")
    end
    local function startTimer()
    print("Timer started")
    end
  3. Để khởi động và ngừng bộ đếm thời gian, trong startTimer() :

    • Gọi myTimer.start() . Truyền đến gameSettings.matchDuration .
    • Gọi myTimer.finished:Connect() . Truyền đến timeUp() .

    -- Chức năng địa phương
    local function startTimer()
    print("Timer started")
    myTimer:start(gameSettings.matchDuration)
    myTimer.finished:Connect(timeUp)
    end

Bắt đầu bộ đếm thời gian

Bộ đếm thời gian có thể được kích hoạt tại mở đầu của một trận bằng sự kiện Bắt đầu trận.

  1. Trong MatchManager, dưới các biến của mô-đun, tạo các biến để lưu thư mục Sự kiện, Bắt đầu trận đấu, và Kết thúc trận đấu (được sử dụng trong bài học trong tương lai).


    -- Tập lệnh mô-đun
    local moduleScripts = ServerStorage:WaitForChild("ModuleScripts")
    local playerManager = require(moduleScripts:WaitForChild("PlayerManager"))
    local gameSettings = require(moduleScripts:WaitForChild("GameSettings"))
    local timer = require(moduleScripts:WaitForChild("Timer"))
    -- Sự kiện
    local events = ServerStorage:WaitForChild("Events")
    local matchStart = events:WaitForChild("MatchStart")
    local matchEnd = events:WaitForChild("MatchEnd")
    --Tạo bộ đếm thời gian
    local myTimer = timer.new()
  2. Trên return MatchManager , kết nối sự kiện bắt đầu trận đấu với startTimer() .


    -- Chức năng mô-đun
    function MatchManager.prepareGame()
    playerManager.sendPlayersToMatch()
    end
    matchStart.Event:Connect(startTimer)
    return MatchManager
  3. Để kích hoạt sự kiện khởi động trận đấu, trong prepareGame(), nhập matchStart:Fire().


    -- Chức năng mô-đun
    function MatchManager.prepareGame()
    playerManager.sendPlayersToMatch()
    matchStart:Fire()
    end
  4. Thử trò chơi. Trong cửa sổ Thành phẩm, xác nhận rằng bạn có thể xem các tuyên bố in cho các chức năng bắt đầu và dừng của bộ đếm thời gian.

Hoàn thành các kịch bản

Dưới đây là các kịch bản hoàn thành để kiểm tra lại công việc của bạn.

Tập lệnh MatchManager


local MatchManager = {}
-- Dịch vụ
local ServerStorage = game:GetService("ServerStorage")
-- Tập lệnh mô-đun
local moduleScripts = ServerStorage:WaitForChild("ModuleScripts")
local playerManager = require(moduleScripts:WaitForChild("PlayerManager"))
local gameSettings = require(moduleScripts:WaitForChild("GameSettings"))
local timer = require(moduleScripts:WaitForChild("Timer"))
-- Sự kiện
local events = ServerStorage:WaitForChild("Events")
local matchStart = events:WaitForChild("MatchStart")
local matchEnd = events:WaitForChild("MatchEnd")
-- Tạo một đối tượng hẹn giờ mới để được sử dụng để theo dõi thời gian trận đấu.
local myTimer = timer.new()
-- Chức năng địa phương
local function timeUp()
print("Time is up!")
end
local function startTimer()
print("Timer started")
myTimer:start(gameSettings.matchDuration)
myTimer.finished:Connect(timeUp)
end
-- Chức năng mô-đun
function MatchManager.prepareGame()
playerManager.sendPlayersToMatch()
matchStart:Fire()
end
matchStart.Event:Connect(startTimer)
return MatchManager

Tập lệnh GameManager


-- Dịch vụ
local ServerStorage = game:GetService("ServerStorage")
local Players = game:GetService("Players")
-- Tập lệnh mô-đun
local moduleScripts = ServerStorage:WaitForChild("ModuleScripts")
local matchManager = require(moduleScripts:WaitForChild("MatchManager"))
local gameSettings = require(moduleScripts:WaitForChild("GameSettings"))
-- Sự kiện
local events = ServerStorage:WaitForChild("Events")
local matchEnd = events:WaitForChild("MatchEnd")
while true do
repeat
task.wait(gameSettings.intermissionDuration)
print("Restarting intermission")
until #Players:GetPlayers() >= gameSettings.minimumPlayers
print("Intermission over")
task.wait(gameSettings.transitionTime)
matchManager.prepareGame()
-- Placeholder chờ đợi thời gian của trò chơi.
matchEnd.Event:Wait()
end