[Гайд] Создаем карту с раундами и волнами мобов

Slavko

Продвинутый
22 Июн 2015
224
0
Цель гайда: Создать карту, на которой после начала матча(00:00 на игровых часах) через определенное время запустится система раундов.
В итоге мы получим:

• Определенное кол-во раундов с промежутками между друг другом.
• Нарастающая сложность мобов на разных раундах.
• Мобы движутся по заданной траектории(не прямая линия, а любые повороты и т.д.)
• Прекращение спавна мобов после указанного раунда.


Приступим. Шаг №1. Создаем траекторию пути мобов.
Для создания траектории пути мобов нам понадобится 4 или больше обычных блоков(Ctrl + B):

Далее кликаем на каждый из них и делаем из них Entity горячей клавишей Ctrl + T.
Теперь каждому блоку справа нужно вписать класс 'path_corner' и применить - нажать Enter.
Далее каждому блоку справа мы даем имя. Пусть это будет way1, way1.5, way2, и way3.
Настало время создавать траекторию. Указываем в каждом блоке имя последующего блока в поле 'Next stop target'. В way1 вписываем way1.5 и так далее.

Теперь если мы пошлем юнита на way1, он, дойдя туда, отправится на way.1.5, а оттуда - на way2 и т.д.
И расставим блоки в хаотичном порядке, но есть нюанс: на way1 мобы не побегут - они пойдут сразу к way1.5( возможно такой баг только у меня ):
http://i.imgur.com/JoRwNo8.jpg

Шаг №2. Создаем точку спавна мобов.
Создаем любой Entity. Пусть это будет 'info_target':

Размещаем его где душа пожелает и справа присваиваем ему произвольное имя, пусть это будет 'spawnerino':

Шаг №3. Создаем юнитов для разных волн.
Заходим в npc_units_custom.txt и создаем там 5 разных юнитов с именами, к примеру, example_unit_1, example_unit_2 - это, как Вы уже наверное догадались, юниты, которые будут идти на первой и второй волне соответственно. Я не углублялся в вопрос создания юнитов и пока просто создал одинаковых крипов, но на 2 и 5 волнах у них увеличенные модели.
// Units File
"DOTAUnits"
{
"Version" "1"

//=================================================================================
// Creature: Gnoll Assassin
//=================================================================================
"example_unit_1"
{
// General
//----------------------------------------------------------------
"Model" "models/creeps/neutral_creeps/n_creep_gnoll/n_creep_gnoll_frost.vmdl" // Model.
"BaseClass" "npc_dota_creature"
"SoundSet" "n_creep_Ranged"
"GameSoundsFile" "soundevents/game_sounds_creeps.vsndevts"
"Level" "1"
"ModelScale" ".9"

// Abilities
//----------------------------------------------------------------
"Ability1" "" // Ability 1
"Ability2" "" // Ability 2
"Ability3" "" // Ability 3
"Ability4" "" // Ability 4

// Armor
//----------------------------------------------------------------
"ArmorPhysical" "10" // Physical protection.

// Attack
//----------------------------------------------------------------
"AttackCapabilities" "DOTA_UNIT_CAP_RANGED_ATTACK"
"AttackDamageMin" "30" // Damage range min.
"AttackDamageMax" "36" // Damage range max.
"AttackRate" "1.6" // Speed of attack.
"AttackAnimationPoint" "0.4" // Normalized time in animation cycle to attack.
"AttackAcquisitionRange" "800" // Range within a target can be acquired.
"AttackRange" "500" // Range within a target can be attacked.
"ProjectileModel" "particles/neutral_fx/gnoll_base_attack.vpcf" // Particle system model for projectile.
"ProjectileSpeed" "1500" // Speed of projectile.

// Bounds
//----------------------------------------------------------------
"RingRadius" "40"
"HealthBarOffset" "170"

// Bounty
//----------------------------------------------------------------
"BountyXP" "24" // Experience earn.
"BountyGoldMin" "21" // Gold earned min.
"BountyGoldMax" "29" // Gold earned max.

// Movement
//----------------------------------------------------------------
"MovementCapabilities" "DOTA_UNIT_CAP_MOVE_GROUND"
"MovementSpeed" "270" // Speed.

// Status
//----------------------------------------------------------------
"StatusHealth" "75" // Base health.
"StatusHealthRegen" "0.5" // Health regeneration rate.
"StatusMana" "0" // Base mana.
"StatusManaRegen" "0.0" // Mana regeneration rate.

// Vision
//----------------------------------------------------------------
"VisionDaytimeRange" "400" // Range of vision during day light.
"VisionNighttimeRange" "400" // Range of vision at night time.

// Team
//----------------------------------------------------------------
"TeamName" "DOTA_TEAM_GOODGUYS" // Team name.
"CombatClassAttack" "DOTA_COMBAT_CLASS_ATTACK_PIERCE"
"CombatClassDefend" "DOTA_COMBAT_CLASS_DEFEND_BASIC"
"UnitRelationshipClass" "DOTA_NPC_UNIT_RELATIONSHIP_TYPE_DEFAULT"

// Creature Data
//----------------------------------------------------------------
"Creature"
{
//Level Up
"HPGain" "50"
"DamageGain" "2"
"ArmorGain" "0.25"
"MagicResistGain" "0.1"
"MoveSpeedGain" "1"
"BountyGain" "3"
"XPGain" "15"
}
}

"example_unit_2"
{
// General
//----------------------------------------------------------------
"Model" "models/creeps/neutral_creeps/n_creep_gnoll/n_creep_gnoll_frost.vmdl" // Model.
"BaseClass" "npc_dota_creature"
"SoundSet" "n_creep_Ranged"
"GameSoundsFile" "soundevents/game_sounds_creeps.vsndevts"
"Level" "1"
"ModelScale" "1.4"

// Abilities
//----------------------------------------------------------------
"Ability1" "" // Ability 1
"Ability2" "" // Ability 2
"Ability3" "" // Ability 3
"Ability4" "" // Ability 4

// Armor
//----------------------------------------------------------------
"ArmorPhysical" "10" // Physical protection.

// Attack
//----------------------------------------------------------------
"AttackCapabilities" "DOTA_UNIT_CAP_RANGED_ATTACK"
"AttackDamageMin" "30" // Damage range min.
"AttackDamageMax" "36" // Damage range max.
"AttackRate" "1.6" // Speed of attack.
"AttackAnimationPoint" "0.4" // Normalized time in animation cycle to attack.
"AttackAcquisitionRange" "800" // Range within a target can be acquired.
"AttackRange" "500" // Range within a target can be attacked.
"ProjectileModel" "particles/neutral_fx/gnoll_base_attack.vpcf" // Particle system model for projectile.
"ProjectileSpeed" "1500" // Speed of projectile.

// Bounds
//----------------------------------------------------------------
"RingRadius" "40"
"HealthBarOffset" "170"

// Bounty
//----------------------------------------------------------------
"BountyXP" "24" // Experience earn.
"BountyGoldMin" "21" // Gold earned min.
"BountyGoldMax" "29" // Gold earned max.

// Movement
//----------------------------------------------------------------
"MovementCapabilities" "DOTA_UNIT_CAP_MOVE_GROUND"
"MovementSpeed" "270" // Speed.

// Status
//----------------------------------------------------------------
"StatusHealth" "75" // Base health.
"StatusHealthRegen" "0.5" // Health regeneration rate.
"StatusMana" "0" // Base mana.
"StatusManaRegen" "0.0" // Mana regeneration rate.

// Vision
//----------------------------------------------------------------
"VisionDaytimeRange" "400" // Range of vision during day light.
"VisionNighttimeRange" "400" // Range of vision at night time.

// Team
//----------------------------------------------------------------
"TeamName" "DOTA_TEAM_GOODGUYS" // Team name.
"CombatClassAttack" "DOTA_COMBAT_CLASS_ATTACK_PIERCE"
"CombatClassDefend" "DOTA_COMBAT_CLASS_DEFEND_BASIC"
"UnitRelationshipClass" "DOTA_NPC_UNIT_RELATIONSHIP_TYPE_DEFAULT"

// Creature Data
//----------------------------------------------------------------
"Creature"
{
//Level Up
"HPGain" "50"
"DamageGain" "2"
"ArmorGain" "0.25"
"MagicResistGain" "0.1"
"MoveSpeedGain" "1"
"BountyGain" "3"
"XPGain" "15"
}
}
И так далее. Фулл npc_units_custom.tхt прикреплю в конце.

Шаг №4. Устанавливаем базовые скрипты BMD.
Для работы того, что мы задумали, требуется отслеживание момента начала матча и таймер. Получить такие возможности можно благодаря написанию мода на предоставленной базе скриптов: https://github.com/MNoya/barebones/tree/source2/game/dota_addons/barebones/scripts/vscripts. Вам следует заменить свой addon_game_mode.lua на предоставленный, а так же закинуть в vscripts скрипты timers.lua и barebones.lua. Timers.lua - здесь понятно, он позволяет использовать таймеры, о них подробнее тут: http://customgames.ru/forum/index.php?topic=43.0. Barebones.lua дает возможность изменять некоторые параметры Вашего мода, отслеживать события и еще много-много другого.

Шаг №5. Пишем скрипт.
Открываем addon_game_mode.lua и вверху, над встроенной в него функцией 'Precache', создаем глобальные переменные:
GAME_ROUND = 0 - номер текущего раунда
MAX_ROUNDS = 5 - номер конечного раунда
ROUND_UNITS = 2 - кол-во юнитов на 1 раунде
Переходим в самый низ нашего addon_game_mode.lua и пишем туда следующее:
function GameMode:OnGameInProgress() // Функция начнет выполняться, когда начнется матч( на часах будет 00:00 ).
local point = Entities:FindByName( nil, "spawnerino"):GetAbsOrigin() // Записываем в переменную 'point' координаты нашего спавнера 'spawnerino'
local waypoint = Entities:FindByName( nil, "way1") // Записываем в переменную 'waypoint' координаты первого бокса way1.
local return_time = 10 // Записываем в переменную значение '10'
Timers:CreateTimer(15, function() // Создаем таймер, который запустится через 15 секунд после начала матча и запустит следующую функцию.
GAME_ROUND = GAME_ROUND + 1 // Значение GAME_ROUND увеличивается на 1.
if GAME_ROUND == MAX_ROUNDS // Если GAME_ROUND равно MAX_ROUNDS, переменная return_time получит нулевое значение.
return_time = nil
end
Say(nil,"Wave №" .. GAME_ROUND, false) // Выводим в чат сообщение 'Wave №', в конце к которому добавится значение GAME_ROUND.
for i=1, ROUND_UNITS do // Произведет нижние действия столько раз, сколько указано в ROUND_UNITS. То есть в нашем случае создаст 2 юнита.
local unit = CreateUnitByName( "example_unit_" .. GAME_ROUND, point + RandomVector( RandomFloat( 0, 200 ) ), true, nil, nil, DOTA_TEAM_GOODGUYS ) // Создаем юнита 'example_unit_', в конце к названию добавится 1,2,3,4 или 5, в зависимости от раунда, и в итоге получатся наши example_unit_1, example_unit_2 и т.д.. Юнит появится в векторе point + RandomVector( RandomFloat( 0, 200 ) ) - point - наша переменная, а рандомный вектор добавляется для того, чтобы мобы не появлялись в одной точке и не застревали. Мобы будут за силы света.
unit:SetInitialGoalEntity( waypoint ) // Посылаем мобов на наш way1, координаты которого мы записали в переменную 'waypoint'
end
return return_time // Возвращаем таймеру время, через которое он должен снова сработать. Когда пройдет последний раунд таймер получит значение 'nil' и выключится.
end)
end

Шаг №6. Делаем предварительное кеширование юнитов.
Кэшируем только example_unit_1 - этого будет достаточно. В addon_game_mode.lua от ВMD вверху уже есть ф-ция 'Precache', просто вставляем в неё:
PrecacheUnitByNameSync("example_unit_1", context)

Советы:
• Советую для ознакомления два открытых на гитхабе популярных проекта:
Warchasers: https://github.com/MNoya/Warchasers
Жизнь на Арене: https://github.com/ZLOY5/LiA
Скачайте их, распакуйте и установите программу Far 3. И когда становится тяжело понять, как описать ту или иную команду или функцию - заходите через Far в корень скачанных проектов, жмите alt + F7. В первом поле вводите "*.*", во втором - то, что нужно найти, например "OnAttacked".
• На ГитХабе в поиске так же всегда можно поискать интересующие команды и функции. Также для поиска и вообще "почитать" советую https://moddota.com
• На сайте https://moddota.com создатель Warchasers - Noya, оформляет качественные гайды, несколько из них:
http://moddota.com/forums/discussion/14/datadriven-ability-breakdown-documentation
https://moddota.com/forums/discussion/4/datadriven-items
http://moddota.com/forums/discussion/93/point-channeling-aoe-ability-example
https://moddota.com/forums/discussion/69/particle-attachment
• Ну и конечно же - по возможности старайтесь создавать свои или переводить чужие гайды, так как то, что Вам кажется очевидным, кому-то придется понимать на забугорских сайтах 2 а то и больше дней, так как российское сообщество D2WT ушло не очень далеко от нулевого уровня.

Автор - Slavko.
На написание гайда натолкнуло: https://moddota.com/forums/discussion/comment/476/#Comment_476[
 
Последнее редактирование модератором:

Se7eN

Друзья CG
22 Ноя 2014
324
6
Скрины в jpg
и в тег заверни, чтобы авто показ был)
 

-ExotiC-

Администратор
Команда форума
11 Авг 2014
474
45
customgames.ru
Проект
Trolls vs Elves
Хороший гайд. Добавил на главную.
Исправил немного текст в некоторых местах, и на будущее - комментирование в lua начинается с двух дефисов --. Комментирование нескольких строк: --[[ Тут код ]]
 

Slavko

Продвинутый
22 Июн 2015
224
0
-ExotiC-, я в курсе, чего-то затупил, что это Lua :D
fiCeVitka, благодарю.
Se7eN, я спецом их не вставлял как картинку, чтоб место не занимали.
 

Captain_Pan

Пользователь
20 Авг 2015
21
0
1)Некоторые мобы в волнах почему-то двигаются медленно, хотя все остальные двигаются с нормальной скоростью. Если подойти к этим мобам, они агрятся и бегут с нормальной скоростью. Как это можно исправить?
2)Как убрать подчеркивания из имен юнитов?
 

Slavko

Продвинутый
22 Июн 2015
224
0
Captain_Pan,
1) Такое вроде встречается только при запуске из воркшопа. В лобби такого быть не должно.
2) backspace )
 

Captain_Pan

Пользователь
20 Авг 2015
21
0
1) В лобби проблема осталась.
2) Спрошу по-другому. Как заменить их на пробелы. Если я меняю их на пробелы в npc_units_custom.txt, то юниты не спавнятся.
 

Slavko

Продвинутый
22 Июн 2015
224
0
Captain_Pan, 2) Никак. Какая тебе разница, как в скриптах называется юнит ?
 

Engtch

Новичок
23 Авг 2015
3
0
[quote author=Slavko link=topic=155.msg639#msg639 date=1435588893]
Заходим в npc_units_custom.txt
[/quote]
В каком типе аддона надо делать свой мод чтобы появился этот файл?
В dota_pvp?
И ещё, мой вопрос многократно писался на форумах но ответа я так и не получил. У меня исчез из модов этот самый dota_pvp. Хотя может его и не было изначально, ибо не шарил совсем когда установил Reborn. Сейчас мало по малу вникаю и заметил что dota_pvp исчез. Как его вернуть или установить с нуля? Спасибо.
 

Engtch

Новичок
23 Авг 2015
3
0

Переустановил Доту. Вот какие аддоны есть по дефолту. Какой из них сейчас идет вместо dota_pvp? Или тут не все дефолтные аддоны?
И где почитать, какие аддоны для чего, и какие в итоге карты из них получатся если не накручивать своего?
Спасибо.
 

CryDeS

Друзья CG
14 Июл 2015
1,210
5
[quote author=Engtch link=topic=155.msg1401#msg1401 date=1440354860]

Переустановил Доту. Вот какие аддоны есть по дефолту. Какой из них сейчас идет вместо dota_pvp? Или тут не все дефолтные аддоны?
И где почитать, какие аддоны для чего, и какие в итоге карты из них получатся если не накручивать своего?
Спасибо.
[/quote]
dota_pvp нету по умолчанию.

adventure - режим приключения, убил босса, победил
holdout - отбиватся от волн мобов
lua_ability_example - пример абилки в lua
overthrow - тот режим из мастерской популярный
rpg_example - пример rpg
ui_example - пример интерфейса и его отрисовки в панораме.
 

Engtch

Новичок
23 Авг 2015
3
0
Спасибо за ответ. Значит ТС говорит здесь про аддон holdout? А можно ли сделать чтобы игрок отбивался не от толпы крипов, а чтобы вместо крипов был другой игрок? И так же по раундам. И еще, где все-таки взять dota_pvp или как его сделать самому (из какого аддона и по какому плану)? Спасибо.
 

CryDeS

Друзья CG
14 Июл 2015
1,210
5
Спасибо за ответ. Значит ТС говорит здесь про аддон holdout? А можно ли сделать чтобы игрок отбивался не от толпы крипов, а чтобы вместо крипов был другой игрок? И так же по раундам. И еще, где все-таки взять dota_pvp или как его сделать самому (из какого аддона и по какому плану)? Спасибо.
Да сделай ты чистый аддон и не парь себе мозги. Берешь таймеры от BDM, делаешь таймер на раунд, а потом тпшишь игроков команды тьмы туда куда надо.
 
Последнее редактирование модератором:

M@G

Пользователь
1 Авг 2015
63
0
Вместо кастомных юнитов попытался использовать уже имеющихся. Вместо GOODGUYS использую NEUTRALS. Если заспавнить обычных лайновых крипов, то они бегут по пути. Если заспавнить каких-нибудь нейтральных (например, кобольдов), то они появляются, но стоят на месте. В чем может быть причина? На нихSetInitialGoalEntity не работает?
 

M@G

Пользователь
1 Авг 2015
63
0
Действительно, не работает. Проблема решена: LINK
 

SanyaDuizFX

Пользователь
18 Окт 2015
37
0
[quote author=Slavko link=topic=155.msg639#msg639 date=1435588893]
Цель гайда: Создать карту, на которой после начала матча(00:00 на игровых часах) через определенное время запустится система раундов.
В итоге мы получим:

• Определенное кол-во раундов с промежутками между друг другом.
• Нарастающая сложность мобов на разных раундах.
• Мобы движутся по заданной траектории(не прямая линия, а любые повороты и т.д.)
• Прекращение спавна мобов после указанного раунда.


Приступим. Шаг №1. Создаем траекторию пути мобов.
Для создания траектории пути мобов нам понадобится 4 или больше обычных блоков(Ctrl + B):

Далее кликаем на каждый из них и делаем из них Entity горячей клавишей Ctrl + T.
Теперь каждому блоку справа нужно вписать класс 'path_corner' и применить - нажать Enter.
Далее каждому блоку справа мы даем имя. Пусть это будет way1, way1.5, way2, и way3.
Настало время создавать траекторию. Указываем в каждом блоке имя последующего блока в поле 'Next stop target'. В way1 вписываем way1.5 и так далее.

Теперь если мы пошлем юнита на way1, он, дойдя туда, отправится на way.1.5, а оттуда - на way2 и т.д.
И расставим блоки в хаотичном порядке, но есть нюанс: на way1 мобы не побегут - они пойдут сразу к way1.5( возможно такой баг только у меня ):
http://i.imgur.com/JoRwNo8.jpg

Шаг №2. Создаем точку спавна мобов.
Создаем любой Entity. Пусть это будет 'info_target':

Размещаем его где душа пожелает и справа присваиваем ему произвольное имя, пусть это будет 'spawnerino':

Шаг №3. Создаем юнитов для разных волн.
Заходим в npc_units_custom.txt и создаем там 5 разных юнитов с именами, к примеру, example_unit_1, example_unit_2 - это, как Вы уже наверное догадались, юниты, которые будут идти на первой и второй волне соответственно. Я не углублялся в вопрос создания юнитов и пока просто создал одинаковых крипов, но на 2 и 5 волнах у них увеличенные модели.
// Units File
"DOTAUnits"
{
"Version" "1"

//=================================================================================
// Creature: Gnoll Assassin
//=================================================================================
"example_unit_1"
{
// General
//----------------------------------------------------------------
"Model" "models/creeps/neutral_creeps/n_creep_gnoll/n_creep_gnoll_frost.vmdl" // Model.
"BaseClass" "npc_dota_creature"
"SoundSet" "n_creep_Ranged"
"GameSoundsFile" "soundevents/game_sounds_creeps.vsndevts"
"Level" "1"
"ModelScale" ".9"

// Abilities
//----------------------------------------------------------------
"Ability1" "" // Ability 1
"Ability2" "" // Ability 2
"Ability3" "" // Ability 3
"Ability4" "" // Ability 4

// Armor
//----------------------------------------------------------------
"ArmorPhysical" "10" // Physical protection.

// Attack
//----------------------------------------------------------------
"AttackCapabilities" "DOTA_UNIT_CAP_RANGED_ATTACK"
"AttackDamageMin" "30" // Damage range min.
"AttackDamageMax" "36" // Damage range max.
"AttackRate" "1.6" // Speed of attack.
"AttackAnimationPoint" "0.4" // Normalized time in animation cycle to attack.
"AttackAcquisitionRange" "800" // Range within a target can be acquired.
"AttackRange" "500" // Range within a target can be attacked.
"ProjectileModel" "particles/neutral_fx/gnoll_base_attack.vpcf" // Particle system model for projectile.
"ProjectileSpeed" "1500" // Speed of projectile.

// Bounds
//----------------------------------------------------------------
"RingRadius" "40"
"HealthBarOffset" "170"

// Bounty
//----------------------------------------------------------------
"BountyXP" "24" // Experience earn.
"BountyGoldMin" "21" // Gold earned min.
"BountyGoldMax" "29" // Gold earned max.

// Movement
//----------------------------------------------------------------
"MovementCapabilities" "DOTA_UNIT_CAP_MOVE_GROUND"
"MovementSpeed" "270" // Speed.

// Status
//----------------------------------------------------------------
"StatusHealth" "75" // Base health.
"StatusHealthRegen" "0.5" // Health regeneration rate.
"StatusMana" "0" // Base mana.
"StatusManaRegen" "0.0" // Mana regeneration rate.

// Vision
//----------------------------------------------------------------
"VisionDaytimeRange" "400" // Range of vision during day light.
"VisionNighttimeRange" "400" // Range of vision at night time.

// Team
//----------------------------------------------------------------
"TeamName" "DOTA_TEAM_GOODGUYS" // Team name.
"CombatClassAttack" "DOTA_COMBAT_CLASS_ATTACK_PIERCE"
"CombatClassDefend" "DOTA_COMBAT_CLASS_DEFEND_BASIC"
"UnitRelationshipClass" "DOTA_NPC_UNIT_RELATIONSHIP_TYPE_DEFAULT"

// Creature Data
//----------------------------------------------------------------
"Creature"
{
//Level Up
"HPGain" "50"
"DamageGain" "2"
"ArmorGain" "0.25"
"MagicResistGain" "0.1"
"MoveSpeedGain" "1"
"BountyGain" "3"
"XPGain" "15"
}
}

"example_unit_2"
{
// General
//----------------------------------------------------------------
"Model" "models/creeps/neutral_creeps/n_creep_gnoll/n_creep_gnoll_frost.vmdl" // Model.
"BaseClass" "npc_dota_creature"
"SoundSet" "n_creep_Ranged"
"GameSoundsFile" "soundevents/game_sounds_creeps.vsndevts"
"Level" "1"
"ModelScale" "1.4"

// Abilities
//----------------------------------------------------------------
"Ability1" "" // Ability 1
"Ability2" "" // Ability 2
"Ability3" "" // Ability 3
"Ability4" "" // Ability 4

// Armor
//----------------------------------------------------------------
"ArmorPhysical" "10" // Physical protection.

// Attack
//----------------------------------------------------------------
"AttackCapabilities" "DOTA_UNIT_CAP_RANGED_ATTACK"
"AttackDamageMin" "30" // Damage range min.
"AttackDamageMax" "36" // Damage range max.
"AttackRate" "1.6" // Speed of attack.
"AttackAnimationPoint" "0.4" // Normalized time in animation cycle to attack.
"AttackAcquisitionRange" "800" // Range within a target can be acquired.
"AttackRange" "500" // Range within a target can be attacked.
"ProjectileModel" "particles/neutral_fx/gnoll_base_attack.vpcf" // Particle system model for projectile.
"ProjectileSpeed" "1500" // Speed of projectile.

// Bounds
//----------------------------------------------------------------
"RingRadius" "40"
"HealthBarOffset" "170"

// Bounty
//----------------------------------------------------------------
"BountyXP" "24" // Experience earn.
"BountyGoldMin" "21" // Gold earned min.
"BountyGoldMax" "29" // Gold earned max.

// Movement
//----------------------------------------------------------------
"MovementCapabilities" "DOTA_UNIT_CAP_MOVE_GROUND"
"MovementSpeed" "270" // Speed.

// Status
//----------------------------------------------------------------
"StatusHealth" "75" // Base health.
"StatusHealthRegen" "0.5" // Health regeneration rate.
"StatusMana" "0" // Base mana.
"StatusManaRegen" "0.0" // Mana regeneration rate.

// Vision
//----------------------------------------------------------------
"VisionDaytimeRange" "400" // Range of vision during day light.
"VisionNighttimeRange" "400" // Range of vision at night time.

// Team
//----------------------------------------------------------------
"TeamName" "DOTA_TEAM_GOODGUYS" // Team name.
"CombatClassAttack" "DOTA_COMBAT_CLASS_ATTACK_PIERCE"
"CombatClassDefend" "DOTA_COMBAT_CLASS_DEFEND_BASIC"
"UnitRelationshipClass" "DOTA_NPC_UNIT_RELATIONSHIP_TYPE_DEFAULT"

// Creature Data
//----------------------------------------------------------------
"Creature"
{
//Level Up
"HPGain" "50"
"DamageGain" "2"
"ArmorGain" "0.25"
"MagicResistGain" "0.1"
"MoveSpeedGain" "1"
"BountyGain" "3"
"XPGain" "15"
}
}
И так далее. Фулл npc_units_custom.tхt прикреплю в конце.

Шаг №4. Устанавливаем базовые скрипты BMD.
Для работы того, что мы задумали, требуется отслеживание момента начала матча и таймер. Получить такие возможности можно благодаря написанию мода на предоставленной базе скриптов: https://github.com/MNoya/barebones/tree/source2/game/dota_addons/barebones/scripts/vscripts. Вам следует заменить свой addon_game_mode.lua на предоставленный, а так же закинуть в vscripts скрипты timers.lua и barebones.lua. Timers.lua - здесь понятно, он позволяет использовать таймеры, о них подробнее тут: http://customgames.ru/forum/index.php?topic=43.0. Barebones.lua дает возможность изменять некоторые параметры Вашего мода, отслеживать события и еще много-много другого.

Шаг №5. Пишем скрипт.
Открываем addon_game_mode.lua и вверху, над встроенной в него функцией 'Precache', создаем глобальные переменные:
GAME_ROUND = 0 - номер текущего раунда
MAX_ROUNDS = 5 - номер конечного раунда
ROUND_UNITS = 2 - кол-во юнитов на 1 раунде
Переходим в самый низ нашего addon_game_mode.lua и пишем туда следующее:
function GameMode:OnGameInProgress() // Функция начнет выполняться, когда начнется матч( на часах будет 00:00 ).
local point = Entities:FindByName( nil, "spawnerino"):GetAbsOrigin() // Записываем в переменную 'point' координаты нашего спавнера 'spawnerino'
local waypoint = Entities:FindByName( nil, "way1") // Записываем в переменную 'waypoint' координаты первого бокса way1.
local return_time = 10 // Записываем в переменную значение '10'
Timers:CreateTimer(15, function() // Создаем таймер, который запустится через 15 секунд после начала матча и запустит следующую функцию.
GAME_ROUND = GAME_ROUND + 1 // Значение GAME_ROUND увеличивается на 1.
if GAME_ROUND == MAX_ROUNDS // Если GAME_ROUND равно MAX_ROUNDS, переменная return_time получит нулевое значение.
return_time = nil
end
Say(nil,"Wave №" .. GAME_ROUND, false) // Выводим в чат сообщение 'Wave №', в конце к которому добавится значение GAME_ROUND.
for i=1, ROUND_UNITS do // Произведет нижние действия столько раз, сколько указано в ROUND_UNITS. То есть в нашем случае создаст 2 юнита.
local unit = CreateUnitByName( "example_unit_" .. GAME_ROUND, point + RandomVector( RandomFloat( 0, 200 ) ), true, nil, nil, DOTA_TEAM_GOODGUYS ) // Создаем юнита 'example_unit_', в конце к названию добавится 1,2,3,4 или 5, в зависимости от раунда, и в итоге получатся наши example_unit_1, example_unit_2 и т.д.. Юнит появится в векторе point + RandomVector( RandomFloat( 0, 200 ) ) - point - наша переменная, а рандомный вектор добавляется для того, чтобы мобы не появлялись в одной точке и не застревали. Мобы будут за силы света.
unit:SetInitialGoalEntity( waypoint ) // Посылаем мобов на наш way1, координаты которого мы записали в переменную 'waypoint'
end
return return_time // Возвращаем таймеру время, через которое он должен снова сработать. Когда пройдет последний раунд таймер получит значение 'nil' и выключится.
end)
end

Шаг №6. Делаем предварительное кеширование юнитов.
Кэшируем только example_unit_1 - этого будет достаточно. В addon_game_mode.lua от ВMD вверху уже есть ф-ция 'Precache', просто вставляем в неё:
PrecacheUnitByNameSync("example_unit_1", context)

Советы:
• Советую для ознакомления два открытых на гитхабе популярных проекта:
Warchasers: https://github.com/MNoya/Warchasers
Жизнь на Арене: https://github.com/ZLOY5/LiA
Скачайте их, распакуйте и установите программу Far 3. И когда становится тяжело понять, как описать ту или иную команду или функцию - заходите через Far в корень скачанных проектов, жмите alt + F7. В первом поле вводите "*.*", во втором - то, что нужно найти, например "OnAttacked".
• На ГитХабе в поиске так же всегда можно поискать интересующие команды и функции. Также для поиска и вообще "почитать" советую https://moddota.com
• На сайте https://moddota.com создатель Warchasers - Noya, оформляет качественные гайды, несколько из них:
http://moddota.com/forums/discussion/14/datadriven-ability-breakdown-documentation
https://moddota.com/forums/discussion/4/datadriven-items
http://moddota.com/forums/discussion/93/point-channeling-aoe-ability-example
https://moddota.com/forums/discussion/69/particle-attachment
• Ну и конечно же - по возможности старайтесь создавать свои или переводить чужие гайды, так как то, что Вам кажется очевидным, кому-то придется понимать на забугорских сайтах 2 а то и больше дней, так как российское сообщество D2WT ушло не очень далеко от нулевого уровня.

Автор - Slavko.
На написание гайда натолкнуло: https://moddota.com/forums/discussion/comment/476/#Comment_476[
[/quote]мм, как сделать чтоб новая волна спавнилась после убийства всей 1 волны? а не пока время определённое пройдёт. :-*
 
Последнее редактирование модератором:

CryDeS

Друзья CG
14 Июл 2015
1,210
5
мм, как сделать чтоб новая волна спавнилась после убийства всей 1 волны? а не пока время определённое пройдёт. :-*
При спавне волны записывать количество мобов в переменную, при смерти моба убавлять переменную. Когда равна нулю спавним новых.
 
Последнее редактирование модератором:

SanyaDuizFX

Пользователь
18 Окт 2015
37
0
При спавне волны записывать количество мобов в переменную, при смерти моба убавлять переменную. Когда равна нулю спавним новых.
Я не силён в lua шарю.. можно написать куда именно писать это.
 
Последнее редактирование модератором:
Реклама: