Pendant le cours d'une manche, les scripts devront suivre le temps et envoyer des signaux entre différents scripts. Le temps sera géré à l'aide d'un script de temps, tandis que les événements, un concept dans le codage Roblox, signaleront des changements tels que la fin d'un correspondre.
Envoyer des signaux avec des événements
Avec les joueurs maintenant dans l'arène, les événements peuvent être utilisés pour signaler le début du match et le code pour le minuteur peut commencer. Plus tard, un événement peut également être utilisé pour signaler la fin du correspondreet que c'est le moment de transférer les joueurs dans le lobby.
Ces événements ne sont pas prévisés, vous devrez donc créer manuellement les objets d'événement personnalisés appelés objets d'événement liables. Les événements liables sont souvent utilisés pour les actions des joueurs et sont similaires aux événements comme Touched ou Changed.
Plusieurs scripts peuvent écouter les mêmes événements liables. Cela organise votre code et facilite l'ajout d'un code supplémentaire pour le début ou la fin du match plus tard si nécessaire.
Créer des événements liables
Commencez par créer des objets d'événement liables pour le début et la fin du correspondre. Étant donné que les événements liables ne s'interagissent pas avec le client, ils peuvent être stockés dans le stockage du serveur.
Dans ServerStorage, créez un nouveau dossier nommé Events. Dans ce dossier, créez deux BindableEvents nommés MatchStart et MatchEnd.
Utiliser événements
En ce moment, lorsque les joueurs entrent dans l'arène, l'intermission se redémarre plutôt que de commencer le minuteur. Le principal game loop doit être dit d'arrêter et d'attendre que l'événement MatchEnd se déclenche avant de passer à la prochaine partie du code.
Les événements ont deux fonctions intégrées : Connect() et Wait(). Au lieu d'utiliser Connect() comme précédemment, appelez 2>Wait2> sur MatchEnd pour暂停游戏管理员脚本直到 MatchEnd est tiré. Dans ce cas, la fonction d'attente暂停代码直到游戏管理员收到信号 que le match est terminé.
Dans GameManager , créez des variables pour le dossier Events et l'événement MatchEnd.
-- Scripts de modulelocal moduleScripts = ServerStorage:WaitForChild("ModuleScripts")local matchManager = require(moduleScripts:WaitForChild("MatchManager"))local gameSettings = require(moduleScripts:WaitForChild("GameSettings"))-- Événementslocal events = ServerStorage:WaitForChild("Events")local matchEnd = events:WaitForChild("MatchEnd")Ayez le script en attente de l'événement de fin de match pour tirer avant de passer à autre chose. Dans le boucle , au bout , taper: matchEnd.Event:Wait()
while true dorepeattask.wait(gameSettings.intermissionDuration)print("Restarting intermission")until #Players:GetPlayers() >= gameSettings.minimumPlayersprint("Intermission over")task.wait(gameSettings.transitionTime)matchManager.prepareGame()-- Le placeholder attend la longueur du jeu.matchEnd.Event:Wait()endTestez le jeu. Confirmez que une fois les joueurs dans l'arène, la boucle d'intermission ne fonctionne pas continuer. Le script est maintenant en attente du signal matchEnd pour lancer.
Conseils de débogage
À ce stade, le code ne fonctionne pas comme prévu, essayez l'un des éléments suivants.
- Vérifiez à nouveau l'utilisation des opérateurs de point ou de colonne dans matchEnd.Event:Wait() .
- Assurez-vous que MatchEnd est un événement liable, et non un autre taper, comme un événement distant.
Utilisation d'un calendrier
L'une des conditions qui entraînera la fin du match est un temps au solde, qui sera gérée via le script.
Configurer le minuteur
Pour ajouter un module de temps dans le jeu, utilisez le script de module prédéfini dans les étapes ci-dessous. Il inclut des fonctions pour démarrer et terminer un minuteur, ainsi que pour retourner le temps restant.
Dans ServerStorage > ModuleScripts, créez un nouveau script de module nommé Timer.
Remplacez le code par le code ci-dessous.
local Timer = {}Timer.__index = Timerfunction Timer.new()local self = setmetatable({}, Timer)self._finishedEvent = Instance.new("BindableEvent")self.finished = self._finishedEvent.Eventself._running = falseself._startTime = nilself._duration = nilreturn selfendfunction Timer:start(duration)if not self._running thentask.spawn(function()self._running = trueself._duration = durationself._startTime = tick()while self._running and tick() - self._startTime < duration dotask.wait()endlocal completed = self._runningself._running = falseself._startTime = nilself._duration = nilself._finishedEvent:Fire(completed)end)elsewarn("Warning: timer could not start again as it is already running.")endendfunction Timer:getTimeLeft()if self._running thenlocal now = tick()local timeLeft = self._startTime + self._duration - nowif timeLeft < 0 thentimeLeft = 0endreturn timeLeftelsewarn("Warning: could not get remaining time, timer is not running.")endendfunction Timer:isRunning()return self._runningendfunction Timer:stop()self._running = falseendreturn TimerDans MatchManager, nécessitez les modules GameSettings et Timer.
local MatchManager = {}-- Serviceslocal ServerStorage = game:GetService("ServerStorage")-- Scripts de modulelocal moduleScripts = ServerStorage:WaitForChild("ModuleScripts")local playerManager = require(moduleScripts:WaitForChild("PlayerManager"))local gameSettings = require(moduleScripts:WaitForChild("GameSettings"))local timer = require(moduleScripts:WaitForChild("Timer"))En dessous des variables, créez un nouvel objet de minuterie en définissant une variable nommée myTimer égale à timer.new(). Cet objet sera utilisé pour appeler des fonctions qui commencent et arrêtent le minuteur.
local gameSettings = require(moduleScripts:WaitForChild("GameSettings"))local timer = require(moduleScripts:WaitForChild("Timer"))-- Crée un nouvel objet de minuterie à utiliser pour suivre le temps du match.local myTimer = timer.new()
Démarrage et arrêt
Maintenant qu'un minuteur a été créé, utilisez les fonctions incluses start() et stop() pendant un correspondre. Voici une description de chaque fonction et du paramètre qu'elle accepte.
- start(time) - D?marre le t?moin, avec le temps en secondes comme le param?tre.
- finished:Connect(functionName) - Lorsque le minuteur se termine, exécute la fonction fournie en tant que paramètre.
Dans MatchManager , créez une nouvelle fonction nommée timeUp() pour exécuter chaque fois que le minuteur est terminé. Incluez une déclaration de test.
local myTimer = timer.new()-- Fonctions localeslocal function timeUp()print("Time is up!")end-- Fonctions de modulefunction MatchManager.prepareGame()playerManager.sendPlayersToMatch()endreturn MatchManagerSous timeUp() , ajoutez une fonction nommée startTimer() avec une déclaration d'impression. Vous afficherez le timer dans le jeu plus tard.
-- Fonctions localeslocal function timeUp()print("Time is up!")endlocal function startTimer()print("Timer started")endPour démarrer et arrêter le minuteur, dans startTimer() :
- Appeler myTimer.start() . Pass in gameSettings.matchDuration .
- Appeler myTimer.finished:Connect() . Pass in timeUp() .
-- Fonctions localeslocal function startTimer()print("Timer started")myTimer:start(gameSettings.matchDuration)myTimer.finished:Connect(timeUp)end
Démarrage du Timer
Le minuteur peut être déclenché au début d'un match en utilisant l'événement Match Start.
Dans MatchManager, sous les variables de module, créez des variables pour stocker le dossier d'événements, MatchStart et MatchEnd (qui est utilisé dans une leçon future).
-- Scripts de modulelocal moduleScripts = ServerStorage:WaitForChild("ModuleScripts")local playerManager = require(moduleScripts:WaitForChild("PlayerManager"))local gameSettings = require(moduleScripts:WaitForChild("GameSettings"))local timer = require(moduleScripts:WaitForChild("Timer"))-- Événementslocal events = ServerStorage:WaitForChild("Events")local matchStart = events:WaitForChild("MatchStart")local matchEnd = events:WaitForChild("MatchEnd")--Crée un créateur de timerlocal myTimer = timer.new()Au-dessus de return MatchManager, connectez l'événement de début du match à startTimer() .
-- Fonctions de modulefunction MatchManager.prepareGame()playerManager.sendPlayersToMatch()endmatchStart.Event:Connect(startTimer)return MatchManagerPour déclencher l'événement de démarrage de la partie, dans prepareGame(), typez matchStart:Fire().
-- Fonctions de modulefunction MatchManager.prepareGame()playerManager.sendPlayersToMatch()matchStart:Fire()endTestez le jeu. Dans la fenêtre d'Output, confirmez que vous pouvez voir les déclarations d'impression pour le démarrage et l'arrêt des fonctions du timer.
Scripts terminés
Ceux-ci sont des scripts terminés pour vérifier vos travaux.
Script de MatchManager
local MatchManager = {}
-- Services
local ServerStorage = game:GetService("ServerStorage")
-- Scripts de module
local moduleScripts = ServerStorage:WaitForChild("ModuleScripts")
local playerManager = require(moduleScripts:WaitForChild("PlayerManager"))
local gameSettings = require(moduleScripts:WaitForChild("GameSettings"))
local timer = require(moduleScripts:WaitForChild("Timer"))
-- Événements
local events = ServerStorage:WaitForChild("Events")
local matchStart = events:WaitForChild("MatchStart")
local matchEnd = events:WaitForChild("MatchEnd")
-- Crée un nouvel objet de minuterie à utiliser pour suivre le temps du match.
local myTimer = timer.new()
-- Fonctions locales
local function timeUp()
print("Time is up!")
end
local function startTimer()
print("Timer started")
myTimer:start(gameSettings.matchDuration)
myTimer.finished:Connect(timeUp)
end
-- Fonctions de module
function MatchManager.prepareGame()
playerManager.sendPlayersToMatch()
matchStart:Fire()
end
matchStart.Event:Connect(startTimer)
return MatchManager
Script de GameManager
-- Serviceslocal ServerStorage = game:GetService("ServerStorage")local Players = game:GetService("Players")-- Scripts de modulelocal moduleScripts = ServerStorage:WaitForChild("ModuleScripts")local matchManager = require(moduleScripts:WaitForChild("MatchManager"))local gameSettings = require(moduleScripts:WaitForChild("GameSettings"))-- Événementslocal events = ServerStorage:WaitForChild("Events")local matchEnd = events:WaitForChild("MatchEnd")while true dorepeattask.wait(gameSettings.intermissionDuration)print("Restarting intermission")until #Players:GetPlayers() >= gameSettings.minimumPlayersprint("Intermission over")task.wait(gameSettings.transitionTime)matchManager.prepareGame()-- Le placeholder attend la longueur du jeu.matchEnd.Event:Wait()end