В этом упражнении вам необходимо нанести урон игроку, если он не переместится на определённое расстояние от своей точки появления в течение заданного времени. Вы будете использовать выражения с возможным отсутствием результата и контексты с возможным отсутствием результата, чтобы получить информацию о местоположении игрока и определить, насколько далеко он переместился за 10 секунд с момента появления.
Для начала убедитесь, что в вашем файле Verse есть функции HurtPlayer() и CalculateDamage(). Вы будете вызывать функцию HurtPlayer(), если игрок не переместится достаточно далеко. Ниже для справки приведён код этих функций.
HurtPlayer(DamageAmount:float):void=
Playspace:fort_playspace = GetPlayspace()
AllPlayers:[]player = Playspace.GetPlayers()
if (Player:player = AllPlayers[0]):
if (FortniteCharacter:fort_character = Player.GetFortCharacter[]):
MyCharacterHealth:float = FortniteCharacter.GetHealth()
DamageToDo:float = CalculateDamage(MyCharacterHealth, DamageAmount, 1.0)
Print("Наносимый урон: {DamageToDo}")
FortniteCharacter.Damage(DamageToDo)
CalculateDamage(PlayerHealth:float, DesiredDamageAmount:float, MinHealth:float):float=
# Если величина урона не приводит к устранению игрока, нанести урон такой величины
if (PlayerHealth > DesiredDamageAmount):
return DesiredDamageAmount
else if (PlayerHealth > MinHealth):
# Дать игроку ещё один шанс, если у него низкий запас здоровья
return PlayerHealth - MinHealth
else:
# Устранить игрока
return PlayerHealth
Теперь вам нужно получить все объекты player на уровне (в данном случае объект всего один, и это вы!). Вам также нужно создать две переменные, где будет храниться объект transform игрока в разные моменты времени. Объект transform содержит данные о местоположении, повороте и масштабе объекта. В этом упражнении вам понадобится только местоположение, и оно хранится в объекте transform.
Playspace:fort_playspace = GetPlayspace()
AllPlayers:[]player = Playspace.GetPlayers()
var FirstPosition:transform = transform{}
var SecondPosition:transform = transform{}
Пора создать несколько контекстов с возможным отсутствием результата, используя if. Две первые строки ниже получают объект fort_character из объекта player. Этот код может показаться вам знакомым, ведь он очень похож на часть кода функции HurtPlayer(). Его нужно написать здесь ещё раз, потому что он необходим для получения объекта transform персонажа ‘fort_character'. Этот код может не выдать результат, на что указывают скобки [], поэтому он должен находиться в контексте с возможным отсутствием результата.
Присвойте переменной FirstPosition, которую вы создали ранее, значение, возвращаемое функцией FirstPosition. Это выражение не является выражением с возможным отсутствием результата, однако если одно из двух предыдущих выражений не выдаст результат, это выражение не должно выполняться, поэтому оно находится в том же контексте с возможным отсутствием результата.
if:
Player:player = AllPlayers[0]
FortniteCharacter:fort_character = Player.GetFortCharacter[]
set FirstPosition = FortniteCharacter.GetTransform()
Поскольку все выражения с возможным отсутствием результата находятся в блоке кода if, вам нужно написать новый блок кода, который будет выполняться в случае успешного выполнения этих выражений. Для этого нужна ветвь then. При написании блока кода if без () используйте ветвь then для кода, который нужно будет выполнить, если весь код в блоке if выполнится успешно.
Ваш первый блок then должен выглядеть так.
then:
Print("Переместитесь или получите урон!")
Sleep(10.0)
Вы уже знакомы с этими функциями. Print() используется для предупреждения игрока о том, что ему нужно переместиться. Sleep() даёт игроку 10 секунд на перемещение от точки появления до запуска следующего блока кода.
По истечении 10 секунд будет выполнен код, который проверит, переместился ли игрок на определённое расстояние от точки появления. Если нет, ему будет нанесён урон.
if:
Player:player = AllPlayers[0]
FortniteCharacter:fort_character = Player.GetFortCharacter[]
set SecondPosition = FortniteCharacter.GetTransform()
DistanceBetweenPositions:float = DistanceXY(FirstPosition.Translation, SecondPosition.Translation)
DistanceBetweenPositions < 10000.0
Три первые строки очень похожи на первый блок кода if, однако теперь задаётся SecondPosition, а не FirstPosition. Теперь вы можете сравнить два местоположения.
Затем объявите и инициализируйте DistanceBetweenPositions. Для этого используйте встроенную функцию Verse DistanceXY(). Она принимает два аргумента, которые представляют собой координаты в трёхмерном пространстве (векторы). Эта функция использует для измерения расстояния только координаты X и Y и возвращает это расстояние как float. Вам нужно использовать только свойство Translation обеих переменных transform.
Наконец, сравните DistanceBetweenPositions с литеральным значением float. Для проверки работоспособности кода советуем начать с большого числа. Уменьшите его, когда найдёте разумное расстояние для перемещения за заданное время.
Следующий блок кода then запустится, если игрок не переместится на необходимое расстояние в течение заданного времени. Это должна быть часть кода, где игрок получает урон.
then:
Print("Расстояние перемещения: {DistanceBetweenPositions}")
Print("Нанесение урона")
HurtPlayer(50.0)
Этот код выведет фактическое расстояние перемещения игрока, после чего появится уведомление о том, что будет нанесён урон, и будет вызвана функция HurtPlayer(), которую вы написали ранее. При вызове этой функции вам не нужно беспокоиться о том, как она реализована. Вы уже знаете, что она отвечает установленным ранее правилам нанесения урона игроку.
Полный сценарий
using { /Fortnite.com/Devices }
using { /Verse.org/Simulation }
using { /UnrealEngine.com/Temporary/Diagnostics }
using { /Fortnite.com/Characters }
using { /Fortnite.com/Playspaces }
using { /UnrealEngine.com/Temporary/SpatialMath }
hello_world_device := class(creative_device):
# Выполняется при запуске устройства в работающей игре
OnBegin<override>()<suspends>:void=
Playspace:fort_playspace = GetPlayspace()
AllPlayers:[]player = Playspace.GetPlayers()
var FirstPosition:transform = transform{}
var SecondPosition:transform = transform{}
if:
Player:player = AllPlayers[0]
FortniteCharacter:fort_character = Player.GetFortCharacter[]
set FirstPosition = FortniteCharacter.GetTransform()
then:
Print("Переместитесь или получите урон!")
Sleep(10.0)
if:
Player : player = AllPlayers[0]
FortniteCharacter : fort_character = Player.GetFortCharacter[]
set SecondPosition = FortniteCharacter.GetTransform()
DistanceBetweenPositions: float = DistanceXY(FirstPosition.Translation, SecondPosition.Translation)
DistanceBetweenPositions < 10000.0
then:
Print("Расстояние перемещения: {DistanceBetweenPositions}")
Print("Нанесение урона")
HurtPlayer(50.0)
# Функции из предыдущих уроков
#################################
HurtPlayer(DamageAmount : float):void=
Playspace: fort_playspace = GetPlayspace()
AllPlayers: []player = Playspace.GetPlayers()
if (Player : player = AllPlayers[0]):
if (FortniteCharacter : fort_character = Player.GetFortCharacter[]):
MyCharacterHealth : float = FortniteCharacter.GetHealth()
DamageToDo : float = CalculateDamage(MyCharacterHealth, DamageAmount, 1.0)
Print("Наносимый урон: {DamageToDo}")
FortniteCharacter.Damage(DamageToDo)
CalculateDamage(PlayerHealth:float, DesiredDamageAmount:float, MinHealth:float):float =
# Если величина урона не приводит к устранению игрока, нанести урон такой величины
if (PlayerHealth > DesiredDamageAmount):
return DesiredDamageAmount
else if (PlayerHealth > MinHealth):
# Дать игроку ещё один шанс, если у него низкий запас здоровья
return PlayerHealth - MinHealth
else:
# Устранить игрока
return PlayerHealth
Что дальше
Вооружившись базовыми знаниями, вы сможете применить Verse для создания собственного устройства в Unreal Editor для Fortnite! Этому посвящен следующий урок.