記錄和顯示玩家資料

*此內容是使用 AI(Beta 測試版)翻譯,可能含有錯誤。若要以英文檢視此頁面,請按一下這裡


現在您可以偵測玩家何時收集了一枚硬幣,本教學的此部分教您如何計算玩家收集了多少硬幣,並將數量顯示在排行榜上。

創建模組腳本來記錄硬幣收藏

要處理每個玩家的硬幣收集數據的儲存和管理,您需要創建一個 ModuleScript 對象來包含每個玩家存取硬幣收集數據的數據結構和功能。模組腳本是其他腳本可能需要 必填的可重複使用代碼。在這種情況下,CoinService需要這個模組腳本,以便當玩家觸碰硬幣時,它可以更新硬幣收集數據。

要創建模組腳指令碼:

  1. 檢索器 窗口中,將鼠標懸停在 伺服器儲存 上,然後單擊 按鈕。一個上下文菜單顯示。

  2. 從上下文選單中,選擇 ModuleScript 。新模組腳本會顯示在 伺服器儲存 下。你正在將模組指令碼放置到 伺服器儲存 中,因為你想管理伺服器上的硬幣收集邏輯。

    Studio's Explorer window with both the ServerScriptService's plus icon and ModuleScript object highlighted.
  3. 將模組腳本重命名為 PlayerData

    Studio's Explorer window with the PlayerData script highlighted under ServerStorage.
  4. 將預設代碼替換為以下代碼:


    local PlayerData = {}
    PlayerData.COIN_KEY_NAME = "Coins"
    local playerData = {
    --[[
    [userId: string] = {
    ["Coins"] = coinAmount: number
    }
    ]]
    }
    local DEFAULT_PLAYER_DATA = {
    [PlayerData.COIN_KEY_NAME] = 0
    }
    local function getData(player)
    local data = playerData[tostring(player.UserId)] or DEFAULT_PLAYER_DATA
    playerData[tostring(player.UserId)] = data
    return data
    end
    function PlayerData.getValue(player, key)
    return getData(player)[key]
    end
    function PlayerData.updateValue(player, key, updateFunction)
    local data = getData(player)
    local oldValue = data[key]
    local newValue = updateFunction(oldValue)
    data[key] = newValue
    return newValue
    end
    return PlayerData

    模組腳本定義了一個 PlayerData 表,包含零或多個 playerData 表,這些表代表玩家的硬幣收集數據。需要此模組腳本的每個腳本都會收到相同的 PlayerData 表,允許多個腳本修改和共享硬幣收集數據。

    宣言資料結構

    模組腳本以空表的宣言開始, PlayerData ,在腳指令碼結束時返回。它也包含取得和設置表中值的配件方法。

    表包含描述表結構的評論,使代碼更容易理解。在這種情況下,一個 playerData 表包含一個 userId 和對應的欄位名稱為 Coins 的欄位,代表該玩家收集的金幣數量。


    local PlayerData = {}
    PlayerData.COIN_KEY_NAME = "Coins"
    local playerData = {
    --[[
    [userId: string] = {
    ["Coins"] = coinAmount: number
    }
    ]]
    }
    ...
    return PlayerData

    定義本地資料檢索器

    getData() 是一個本地功能,會擷取特定 playerData 表的資料。如果玩家尚未收集硬幣,它將返回一個 DEFAULT_PLAYER_DATA 表,以確保每個玩家都有與他們相關的數據。一個常見的做法是創建簡單的、面向公眾的功能,將邏輯轉移到本地範圍的功能來進行重型工作。


    local DEFAULT_PLAYER_DATA = {
    [PlayerData.COIN_KEY_NAME] = 0
    }
    local function getData(player)
    local data = playerData[tostring(player.UserId)] or DEFAULT_PLAYER_DATA
    playerData[tostring(player.UserId)] = data
    return data
    end

    定義公共資料存取者

    getValue()updateValue() 是面向公眾的功能,其他需要此模組腳本的腳本可以呼叫。在我們的情況下, CoinService 使用這些功能來更新玩家的硬幣收集數據,每當該玩家觸碰硬幣時。


    function PlayerData.getValue(player, key)
    return getData(player)[key]
    end
    function PlayerData.updateValue(player, key, updateFunction)
    local data = getData(player)
    local oldValue = data[key]
    local newValue = updateFunction(oldValue)
    data[key] = newValue
    return newValue
    end

實裝排行榜

您可以使用屏幕上的排行榜視覺化代幣收集數據。Roblox 包含一個內置系統,可自動使用預設介面生成排行榜。

要建立排行榜:

  1. 導航器 窗口中,在 伺服器儲存 中創建一個 ModuleScript ,然後將模組腳本重命名為 排行榜

    Studio's Explorer window with the Leaderboard script highlighted under ServerStorage.
  2. 將預設代碼替換為以下代碼:


    local Leaderboard = {}
    -- 創建新的排行榜
    local function setupLeaderboard(player)
    local leaderstats = Instance.new("Folder")
    -- 「leaderstats」是 Roblox 認可的保留名稱,用於創建排行榜
    leaderstats.Name = "leaderstats"
    leaderstats.Parent = player
    return leaderstats
    end
    -- 創建新的排行榜統計值
    local function setupStat(leaderstats, statName)
    local stat = Instance.new("IntValue")
    stat.Name = statName
    stat.Value = 0
    stat.Parent = leaderstats
    return stat
    end
    -- 更新玩家的統計值
    function Leaderboard.setStat(player, statName, value)
    local leaderstats = player:FindFirstChild("leaderstats")
    if not leaderstats then
    leaderstats = setupLeaderboard(player)
    end
    local stat = leaderstats:FindFirstChild(statName)
    if not stat then
    stat = setupStat(leaderstats, statName)
    end
    stat.Value = value
    end
    return Leaderboard

    以下部分詳細說明排行榜如何運作。

    創建排行榜

    setupLeaderboard() 功能創建了一個新的文件夾實例,命名為 leaderstats ,並將其設為指定玩家的子夾。Roblox 會自動認識以 leaderstats 命名的文件夾為統計資料容器,並創建一個介面元素來顯示統計資料。它需要在 leaderstats 中的值存儲為「值」對象(例如 StringValueIntValueNumberValue)。


    -- 創建新的排行榜
    local function setupLeaderboard(player)
    local leaderstats = Instance.new("Folder")
    -- 「leaderstats」是 Roblox 認可的保留名稱,用於創建排行榜
    leaderstats.Name = "leaderstats"
    leaderstats.Parent = player
    return leaderstats
    end
    -- 創建新的排行榜統計值
    local function setupStat(leaderstats, statName)
    local stat = Instance.new("IntValue")
    stat.Name = statName
    stat.Value = 0
    stat.Parent = leaderstats
    return stat
    end

    更新玩家統計資料

    setStat()排行榜 模組中唯一的公共功能。如果尚未存在,它會為指定的玩家或排行榜本身創建狀態值。

    FindFirstChild() 取得對象的名稱,並如果存在返回對象,否則返回 nil 。這是一種常見且安全的方法,可以確認對象在使用之前是否存在。


    -- 更新玩家的統計值
    function Leaderboard.setStat(player, statName, value)
    local leaderstats = player:FindFirstChild("leaderstats")
    if not leaderstats then
    leaderstats = setupLeaderboard(player)
    end
    local stat = leaderstats:FindFirstChild(statName)
    if not stat then
    stat = setupStat(leaderstats, statName)
    end
    stat.Value = value
    end

整合模組腳本

兩個模組 玩家數據排行榜 已完成,需要在 CoinService 腳本中管理和顯示玩家硬幣數據。要更新 CoinService

  1. 檢索器 窗口中,開啟 CoinService 腳指令碼。

  2. 使用以下代碼取代現有代碼:


    -- 初始化服務和變量
    local Workspace = game:GetService("Workspace")
    local Players = game:GetService("Players")
    local ServerStorage = game:GetService("ServerStorage")
    -- 模組
    local Leaderboard = require(ServerStorage.Leaderboard)
    local PlayerData = require(ServerStorage.PlayerData)
    local coinsFolder = Workspace.World.Coins
    local coins = coinsFolder:GetChildren()
    local COIN_KEY_NAME = PlayerData.COIN_KEY_NAME
    local COOLDOWN = 10
    local COIN_AMOUNT_TO_ADD = 1
    local function updatePlayerCoins(player, updateFunction)
    -- 更新硬幣表
    local newCoinAmount = PlayerData.updateValue(player, COIN_KEY_NAME, updateFunction)
    -- 更新金幣排行榜
    Leaderboard.setStat(player, COIN_KEY_NAME, newCoinAmount)
    end
    -- 定義事件處理器
    local function onCoinTouched(otherPart, coin)
    if coin:GetAttribute("Enabled") then
    local character = otherPart.Parent
    local player = Players:GetPlayerFromCharacter(character)
    if player then
    -- 玩家觸碰了一枚硬幣
    coin.Transparency = 1
    coin:SetAttribute("Enabled", false)
    updatePlayerCoins(player, function(oldCoinAmount)
    oldCoinAmount = oldCoinAmount or 0
    return oldCoinAmount + COIN_AMOUNT_TO_ADD
    end)
    task.wait(COOLDOWN)
    coin.Transparency = 0
    coin:SetAttribute("Enabled", true)
    end
    end
    end
    -- 設定事件聆聽器
    for _, coin in coins do
    coin:SetAttribute("Enabled", true)
    coin.Touched:Connect(function(otherPart)
    onCoinTouched(otherPart, coin)
    end)
    end

    對原始 CoinService 腳本的更改包括:

    • 使用 玩家數據排行榜 模組以 require() 函數進行匯入。
    • 宣言 COIN_AMOUNT_TO_ADD 作為玩家收集硬幣時要添加的硬幣數量,以及 COIN_KEY_NAMEPlayerData 中定義的關鍵名稱。
    • 創建幫助函數 updatePlayerCoins() 來更新玩家的硬幣數量和相關排行榜統計。
    • onCoinTouched() 中替換 placeholder print() 聲明以呼叫 updatePlayerCoins()

遊戲測試

是時候看看硬幣收集是否如預期般運作了。當您在遊戲中觸碰並收集硬幣時,您應該能夠在排行榜介面上看到已收集的硬幣數量。要測試您的體驗:

  1. 在工具欄中,單擊 播放 按鈕。Studio 進入播放測試模式。

    Play button highlighted in Studio's playtesting options.
  2. 將角色移動到觸碰硬幣。如果您的腳本正確運行,排行榜介面會顯示並增加您收集更多硬幣時的硬幣數量。