업그레이드 버튼 스크립트 작성

*이 콘텐츠는 AI(베타)를 사용해 번역되었으며, 오류가 있을 수 있습니다. 이 페이지를 영어로 보려면 여기를 클릭하세요.


플레이어는 이제 코인을 수집하고 사망 시 코인을 잃지만, 코인은 아무런 역할을 하지 않으며, 매우 높은 곳으로 점프할 수 있는 능력이 없으면 3D 세계의 대부분에 접근할 수 없습니다. 이 튜토리얼의 이 부분에서는 코인을 사용하여 점프 능력을 증가시키는 화면 상의 버튼을 추가하여 경험의 논리를 완성하는 방법을 배웁니다.

업그레이드 버튼 만들기

Roblox의 2D 인터페이스는 일반적으로 GUI 컨테이너 내부에 있는 GUI 구성 요소의 모음으로 구성됩니다. 이 경우, TextButton 구성 요소가 필요하며, "점프 업그레이드 (5 코인)"이라는 텍스트를 ScreenGui 컨테이너 안에 넣어야 합니다.

업그레이드 GUI 설정

ReplicatedStorage에 Instances라는 이름의 폴더를 만듭니다.
Instances 폴더 내부에 JumpPurchaseGui라는 이름의 ScreenGui를 만들고 ResetOnSpawn을 비활성화합니다.
JumpPurchaseGui 내부에 JumpButton이라는 이름의 TextButton을 만들고 다음 속성을 설정합니다:
- Text: "점프 업그레이드 (5 코인)"
- TextSize: 25
- AnchorPoint: 1, 1
- Position: {1, 0}, {1, 0}
또한 Instances 폴더 내부에 IncreaseJumpPowerFunction이라는 이름의 RemoteFunction을 만듭니다.
마지막으로 StarterPlayer 서비스에서 CharacterUseJumpPower 속성을 활성화합니다.

점프 능력 데이터 정의하기

현재 PlayerData 모듈 스크립트에는 각 플레이어에 대한 코인 수만 저장됩니다. 점프 능력도 같은 방식으로 저장하고 업데이트해야 합니다. PlayerData의 함수는 변경되는 데이터와는 무관하므로 플레이어의 점프 능력을 저장하기 위해 Jump 키를 추가하고 defaultPlayerData()에서 초기 값을 초기화하면 됩니다.

점프 능력으로 PlayerData 업데이트

ServerStorage에서 기존 PlayerData ModuleScript의 코드를 다음으로 교체합니다:
```lua
local PlayerData = {}
PlayerData.COIN_KEY_NAME = "Coins"
PlayerData.JUMP_KEY_NAME = "Jump"
local playerData = {
--[[
[userId: string] = {
["Coins"] = coinAmount: number,
["Jump"] = jumpPower: number
}
--]]
}
local function defaultPlayerData()
return {
[PlayerData.COIN_KEY_NAME] = 0,
[PlayerData.JUMP_KEY_NAME] = 0,
}
end
local function getData(player)
local data = playerData[tostring(player.UserId)] or defaultPlayerData()
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가 점프 능력을 추적할 수 있으므로, 플레이어의 클라이언트 요청으로 점프 능력을 업그레이드하는 서버 로직을 구현해야 합니다.

서버와 클라이언트는 RemoteEvents 또는 RemoteFunctions를 통해 통신할 수 있습니다. RemoteEvent는 발사 시 대기하지 않으며 한 방향 통신에 사용할 수 있습니다. 반면, RemoteFunction은 응답을 받을 때까지 대기하므로 양방향 통신을 허용합니다.

이 튜토리얼에서는 클라이언트가 서버가 플레이어의 점프 능력을 성공적으로 업그레이드했는지 알아야 하므로, RemoteFunction을 사용하는 것이 좋습니다.

JumpService 생성

ServerScriptService에 JumpService라는 이름의 스크립트를 생성하고 다음 코드를 추가합니다:
```lua
-- 서비스
local ReplicatedStorage = game:GetService("ReplicatedStorage")
local ServerStorage = game:GetService("ServerStorage")
local Players = game:GetService("Players")
-- 모듈
local Leaderboard = require(ServerStorage.Leaderboard)
local PlayerData = require(ServerStorage.PlayerData)
-- 이벤트
local IncreaseJumpPowerFunction = ReplicatedStorage.Instances.IncreaseJumpPowerFunction
local JUMP_KEY_NAME = PlayerData.JUMP_KEY_NAME
local COIN_KEY_NAME = PlayerData.COIN_KEY_NAME
local JUMP_POWER_INCREMENT = 30
local JUMP_COIN_COST = 5
local function updateJumpPower(player, updateFunction)
-- 점프 능력 테이블 업데이트
local newJumpPower = PlayerData.updateValue(player, JUMP_KEY_NAME, updateFunction)
-- 플레이어의 점프 능력 업데이트
local character = player.Character or player.CharacterAdded:Wait()
local humanoid = character:FindFirstChildWhichIsA("Humanoid")
if humanoid then
humanoid.JumpPower = newJumpPower
-- 점프 리더보드 업데이트
Leaderboard.setStat(player, JUMP_KEY_NAME, newJumpPower)
end
end
local function onPurchaseJumpIncrease(player)
local coinAmount = PlayerData.getValue(player, COIN_KEY_NAME)
if coinAmount < JUMP_COIN_COST then
return false
end
-- 플레이어의 점프 능력 증가
updateJumpPower(player, function(oldJumpPower)
oldJumpPower = oldJumpPower or 0
return oldJumpPower + JUMP_POWER_INCREMENT
end)
-- 코인 테이블 업데이트
local newCoinAmount = PlayerData.updateValue(player, COIN_KEY_NAME, function(oldCoinAmount)
return oldCoinAmount - JUMP_COIN_COST
end)
-- 코인 리더보드 업데이트
Leaderboard.setStat(player, COIN_KEY_NAME, newCoinAmount)
return true
end
local function onCharacterAdded(player)
-- 캐릭터가 추가될 때 플레이어의 점프 능력 리셋
updateJumpPower(player, function(_)
return 0
end)
end
-- PlayerAdded 이벤트에 연결하기 전 추가된 플레이어 초기화
for _, player in Players:GetPlayers() do
onCharacterAdded(player)
end
-- PlayerAdded 이벤트에서의 플레이어 정상 초기화
local function onPlayerAdded(player)
player.CharacterAdded:Connect(function()
onCharacterAdded(player)
end)
end
local function onPlayerRemoved(player)
updateJumpPower(player, function(_)
return nil
end)
end
IncreaseJumpPowerFunction.OnServerInvoke = onPurchaseJumpIncrease
Players.PlayerAdded:Connect(onPlayerAdded)
Players.PlayerRemoving:Connect(onPlayerRemoved)
```

다음 섹션에서는 코드를 좀 더 자세히 설명합니다.

  • 점프 능력 데이터 업데이트 - updateJumpPower()는 플레이어의 점프 능력과 리더보드를 업데이트하여 시각적 피드백을 제공합니다. 이 함수는 플레이어에게 피해를 주는 코드와 유사하며 플레이어 위험 생성에서 사용되었습니다. Character 모델과 Humanoid가 업그레이드되는 플레이어에게 존재하는 경우, 이 함수는 JumpPower 속성을 PlayerData에 저장된 새로운 값으로 업데이트하여 30만큼 증가시킵니다. 게임이 조금 더 길어지기를 원한다면 이 숫자를 줄일 수 있습니다.

  • 서버 요청 유효성 검사 - onPurchaseJumpIncrease()는 플레이어가 실제로 업그레이드를 구매하기 위해 필요한 코인 수를 가지고 있는지 먼저 확인합니다. 모든 요청유효성 검사를 해야 하며, 이는 불법적인 요청을 제출하고 게임을 악용하려는 행위를 방지합니다.

플레이어 GUI에 버튼 추가하기

ScreenGui 객체는 플레이어의 PlayerGui 객체에 부모가 되어야만 화면에 표시됩니다. 기본적으로 이곳에는 채팅 창과 같은 시스템 GUI가 포함되어 있습니다. 이제 ReplicatedStorage에 업그레이드 버튼을 각 플레이어 GUI에 복사하고 버튼이 눌리었을 때 동작을 구현하는 스크립트를 생성해야 합니다.

JumpButtonClickHandler 생성

ReplicatedStorage에 JumpButtonClickHandler라는 이름의 스크립트를 생성하고 RunContext를 Client로 설정한 다음 다음 코드를 추가합니다:
```lua
local ReplicatedStorage = game:GetService("ReplicatedStorage")
local Players = game:GetService("Players")
local player = Players.LocalPlayer
local playerGui = player.PlayerGui
local IncreaseJumpPowerFunction = ReplicatedStorage.Instances.IncreaseJumpPowerFunction
local jumpPurchaseGui = ReplicatedStorage.Instances.JumpPurchaseGui
local jumpButton = jumpPurchaseGui.JumpButton
local function onButtonClicked()
local success, purchased = pcall(IncreaseJumpPowerFunction.InvokeServer, IncreaseJumpPowerFunction)
if not success then
-- purchased는 성공이 false일 경우 오류 메시지가 됩니다.
error(purchased)
elseif success and not purchased then
warn("코인이 부족합니다!")
end
end
jumpButton.Activated:Connect(onButtonClicked)
-- 플레이어의 GUI에 JumpPurchaseGui 추가
jumpPurchaseGui.Parent = playerGui
```

다음 섹션에서는 코드를 좀 더 자세히 설명합니다.

  • GUI와 서버 함수 참조 얻기 - IncreaseJumpPowerFunction, jumpPurchaseGui, jumpButton 변수는 함수와 나중에 필요할 GUI에 대한 참조를 포함합니다.
  • 이벤트 핸들러 정의 - onButtonClicked()는 사용자가 업그레이드 버튼을 클릭할 때의 로직을 정의합니다. 이는 pcall() (보호된 호출)을 사용하여 RemoteFunction을 호출합니다. 이와 같은 클라이언트-서버 통신은 오류 처리 또는 연결 문제를 관리하기 위해 pcall()을 필요로 합니다.
  • 버튼에 핸들러 연결하기 - Activated 이벤트는 모든 플랫폼에서 호환됩니다. 클릭, 터치 또는 게임패드 버튼이 해제될 때 트리거됩니다.

플레이테스트

드롭다운에서 Test를 선택하고 Play를 클릭합니다. 점프 업그레이드 버튼이 오른쪽 하단에 나타납니다.

코인을 수집하기 전에 버튼을 클릭하여 추가 점프 능력이 부여되지 않는지 확인한 다음, 코인을 몇 개 수집한 후 다시 클릭하여 업그레이드가 작동하는지 확인하십시오.

코드가 완료되면 난이도를 조절해 보십시오: 템포가 느리게 느껴지면 코인을 추가하고, 업그레이드가 너무 쉽게 진행되면 몇 개를 제거하고 더 까다로운 위치에 배치하세요.

©2026 Roblox Corporation. Roblox 및 Roblox 로고, 'Powering Imagination'은 미국 및 기타 국가 내 당사의 등록 및 미등록 상표입니다.