Как написать аддон для wow

Обновлено: 17.05.2024

Для начала написания аддонов нам нужны:

  1. Установленный Wow. Теоретически существуют эмуляторы для тестирования и отладки аддонов, но на данный момент нет их аналогов, поддерживающих актуальную верисю API.
  2. Папка в нем: /Interface/Addons. Если ее нет, то создайте - это то место, где хранятся все модификации интерфейса.
  3. В ней должна быть папка с названием MYADDON (см. выше) - это папка, в которой вы и будете писать ваш аддон.
  4. Набор файлов кода вашего аддона, реализующего требуемый функционал.
  5. В этой папке должна быть папка Libs, содержащая используемые библиотеки. В нашем случае это WowAce3.0.
  6. В папке MYADDON должен быть файл MYADDON.toc - это корневой файл, описывающий весь ваш аддон. Его содержимое:
  7. В папке MYADDON должен быть файл embeds.toc - это файл, показывающий, какие сторонние библиотеки использует ваш аддон. Его содержимое:
  8. В папке MYADDON должен быть файл Core.lua - главный исполняемый файл аддона, может иметь другое название, но такое же, какое указано в MYADDON.toc. Его содержимое будет описано ниже в разделе написания кода аддона.

5. Написание кода

Далее будет описываться содержимое файла Core.lua, что в нем необходимо использовать и что может пригодиться при написании функциональности аддона.

5.1. Минимальный проект

Чтобы ваш аддон мог запуститься и работать (хоть и не выполнять никаких полезных действий) достаточно в Core.lua написать следующее:

5.3. Слеш-команды

5.4. Обработка событий

5.5. Графический интерфейс

Порою аддон нужно настраивать и настраивать не через слеш-команды, а с помощью удобного пользовательского интерфейса. WowAce также предоставляет возможность для его реализации.

4. Отладка аддонов

Создание несложного бота для WoW, программирование маршрутов

Я отлично понимаю, что использование ботов запрещено лицензионным соглашением Blizzard. Это может привести к перманентному бану аккаунта. Я бы расстроился, узнав, что кто-то, воспользовавшись материалами данного поста, стал наживаться, ухудшая экономику игры и вызывая неодобрение других игроков. И да, я понимаю, то, что делаю я, нечестно.

Цель поста — рассказать о моем опыте и описать сложности, с которыми я столкнулся, узнать у вас, что можно было сделать лучше.

Предыстория
Коллекционирование

Люди, далекие от индустрии игр, могут без ущерба пропустить этот раздел. В игре WoW есть такой аспект — коллекционирование. Как и в нумизматике/филателии, чем больше у вас, например, верховых животных, тем вам приятнее. Точно так же важен процесс получения. Какие-то драконы требуют для получения выполнения десятка задач («ачивок»), какие-то — войти в лучшие 2% игроков в мире по навыку управления персонажем (сражения на арене), что-то можно просто купить за игровую валюту, что-то — за реальные деньги в магазине. Подробности можно почитать в другом источнике, речь не об этом. Так вот, некоторые из коллекционируемых предметов падают в подземелье с шансом около 0,5%. Если шанс выпадения дается игроку лишь раз в день (иногда в неделю), вам потребуется время, соизмеримое с годом, для забегов. И все ради того мгновения получения заветного выстраданного предмета. Чем больше вы потратили времени и сил на "фарм" предмета, тем приятнее вам его в итоге получить. По моему опыту радость очень мимолетна.

Зависимость шанса выпадения от количества попыток

Небольшое отступление. Какова вероятность того, что за шесть бросков игральной кости выпадет «6»? Очевидно, что . То есть, наше событие является противоположным событием к невыпадению «6» за все шесть попыток.
Используя второй замечательный предел, нетрудно показать, что .

А вероятность получения коня с шансом «дропа» в 1% за 100 попыток примерно равна 63%.

Некоторые игроки, сделав триста попыток считают, что вот-вот повезет — ведь вероятность облома за такое большое число попыток мала. Их ждет разочарование, ведь за следующие 100 им повезет снова лишь на 63%. А старые труды не дают ничего.

Задача

Есть подземелье. Нужно пробежать по нему с виражами, выполнить пару несложных задач по пути. Убить финального босса и поднять добычу. Чтобы не бежать к выходу пешком, телепортироваться в ближайшую деревню и долететь ко входу. Повторить 5 раз.


Карта подземелья и маршрут:

Задача максимум. Запустил и ушел на пол часа. Процесс полностью автоматический.

Задача минимум. Запустить и сидеть рядом, читать или играть на гитаре, поглядывая на монитор. При необходимости изредка помогать персонажу выбраться из непредвиденной ситуации.

Важно иметь возможность при желании описать маршрут другого подземелья, не залезая в код.

Подход
Движение и позиционирование
  1. Вам требуется воспроизвести первоначальное положение персонажа и направление его взгляда. Если вы перед автоматическим забегом повернетесь слегка в другую сторону, вы побежите кривовато и рано или поздно упретесь в стенку
  2. Если вы записали точные координаты и угол, то поставить персонажа туда же вам также не удастся. Реагирует на кнопки он как бульдозер и поворачивается так же. А даже ошибка в 1 градус через 100 метров выльется в метра (ширина дверного проема)
  3. Время нажатия и отпускания кнопок тоже далеко от идеала. Это похоже на передвижение по квартире с закрытыми глазами. Вроде бы шесть шагов вперед и строго направо, но на деле вместо туалета мы оказываемся в ванной. Попробуйте также открыть дверь с закрытыми глазами, не щупая ручку


Это отрывок из списка команд робота по перемещению. Указаны координаты x, y и угол поворота в пространстве в радианах.

Клавиши и команды

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


Отдельно упомяну про «pitch» (наклон). Если персонаж смотрит в горизонт, он равен нулю. Если под ноги, наклон отрицателен. А в небо — положителен. Измеряется в радианах. Его пришлось добавить, как только персонажу захотелось летать.

Модули
  1. Мы напишем addon для интерфейса WoW, который будет определять позицию персонажа, азимут, наклон. Правилами игры аддоны ничуть не запрещены, указанная информация доступна через игровое API внутри аддона. Он будет рисовать это все на экране. Сам аддон пишется на языке Lua, потому что так решили разработчики игры.
  2. В аддоне можно определять кое-что, можно рисовать, но вот заставить персонажа двигаться нельзя. Еще в аддоне нельзя писать в файл, спрашивать у игры, где стены, где враги, да и много чего еще нельзя. Поэтому нам нужно написать внешнее управляющее приложение. Я не стал оригинальничать и использовал AutoIt. Это действительно быстро и удобно, хоть и немного дико для меня, привыкшего программировать на строго типизированных языках.
    • Приложение должно уметь записывать мои действия. Назовем этот функционал Recorder
    • Приложение должно уметь воспроизводить запись. Назовем Player
  3. Записанные действия и координаты мы будем хранить в текстовом файле построчно. Их можно и нужно редактировать вручную. Добавлять костыли, удалять мусор. Скажу сразу, это самое сложное.
Addon для WoW на Lua

Аддон для WoW это скрипт на языке Lua. Язык полноценный, гибкий, эффективный. Делать с системой ничего нельзя. Делать с игрой можно все, но только в рамках того API, которое предоставляет вам игра. Так как Blizzard не хочет, а точнее, запрещает игрокам и предпринимателям писать ботов, то и API кроме упомянутых выше координат почти ничего полезного и не предоставляет. Разумеется, полезного для наших нужд. Неплохой гайд по написанию аддонов сразу с описанием Lua можно найти здесь. Ну а я опишу свой вариант.

Манифест и GUI

Подробности и источник. В папке World of Warcraft\Interface\AddOns\ создаете папку HelloWorld. В нее кладете HelloWorld.toc с содержимым


Если бы я хотел понарисовать формочек и кнопочек (а для этого обычно и нужны аддоны), последней строчкой я бы вписал еще HelloWorld.xml с описанием этих кнопочек. В дизайне и написании такого GUI-аддона хорошо помогает AddOn Studio. Мощный инструмент на базе MS Visual Studio.

Но так как я минималист, рисовать мы в этот раз не будем. Кроме того, это даст мне возможность показать, что создавать формы можно динамически из самого скрипта без использования дизайнера. Рассмотрим же HelloWorld.lua. Редактировал я его в Notepad++. Чтобы игра подключила изменения в HelloWorld.toc, надо перезапустить ее целиком. А вот изменения в HelloWorld.lua можно подхватить, написав в консоли команду /reload. Поэтому процесс программирования и отладки не такой болезненный.

Слеш-команды

Кстати, об отладке. Советую сразу добавить обработчик слеш-команд:


Для этого определим переменную вида SLASH_ИМЯn. Где ИМЯ уникально для всех аддонов, а n либо пусто, либо порядковое число с 1. И добавим функцию с именем ИМЯ в некий объект. Может показаться странным для программиста на C++, что мы эту функцию-обработчик нигде явно не регистрируем. Да и со строковой переменной связываем чисто по имени переменной. Но вот такая она, мощь и магия Lua.

Теперь команда в WoW-консоли /helloworld выполнит требуемые вам действия: позволит вывести отладочную информацию, а для простейших аддонов, собственно, произведет все то, ради чего вы их писали.

Ну и тут же я показал WoW API, которое достает требуемую информацию.

Обработчик событий


Мы создаем фрейм типа "Frame" и подключаемся на действия "OnEvent" и "OnUpdate" командами


Обработчик OnUpdate будет вызываться после каждого кадра — то, что нам нужно для обновления координат. А OnEvent будет вызываться при других желаемых событиях. Из него будем дергать соответствующие функции:


Что еще удобнее в Lua, это то, что вот такой конструкцией можно вызвать уникальные обработчики вида


Здесь PLAYER_LOGIN — это событие, которое рассылается во все фреймы при входе в мир и перезапуске пользовательского интерфейса. Другие события: PLAYER_LEAVE_COMBAT, QUEST_FINISHED, PLAYER_EQUIPMENT_CHANGED, PLAYER_DEAD, — и еще очень много. С полным списком можно ознакомиться тут. Зарегистрируем то событие, которое мы хотим обрабатывать, командой

Передача информации

Так как в аддоне нельзя ничего делать с системой, информацию из WoW другой части бота мы будем передавать при помощи изменения цвета пикселей. Как это делал rednaxi в своем посте. Но только мы будем передавать цветом не один бит информации, а будем сериализовать данные и передавать их больше.

Рисование

Так как для рисования тоже нужны фреймы, создадим их


Думаю, тут все понятно и без комментариев. Подробности по каждому методу ищите сами.

Сериализация

У нас есть две координаты и два угла. Все — числа с плавающей запятой. Компоненты цветов пикселей в аддоне тоже числа с плавающей запятой, но от 0.0 до 1.0. Кроме того, известно, что сохранится компонента цвета в одном байте. Поначалу я каждую координату сохранял в одну компоненту цвета. В итоге точность позиционирования в локации составляла 1/255 от размера карты. Получалось как в GPS: вроде координаты есть, но вести машину на автомате (управление компьютером без человека) по дороге по навигатору не выйдет. Так что пришлось давать два байта. Как повыгоднее сохранить одно дробное число в два байта? Я сделал так


Функция modf возвращает целую и дробную часть числа через запятую. Здесь используется параллельное присваивание — еще одна полезная фишечка Lua.

При таком подходе я использую полную мощность каждого из двух байтов, в которые сохраняется координата. Ну а азимут и наклон не так требовательны к точности, лишь бы укладывались в отрезок 0.0-1.0. Получается вот так:


Теперь при перемещении по миру в левом верхнем углу два квадратика 10 на 10 будут хаотично менять свой цвет.

Как написать аддон для wow

пополнив наш счет на "яндекс деньги" :

Номер нашего счета -

Вот наш управляющий файл (test.toc)

Плугин ничего не делает, только демонстрирует себя в списке плугинов. В папке с плугином лежат два пустых файла
test.lua и test.xml для последующих экспериментов.
5. Файлы определений интерфейса.

Основная информация
Widget API

Вообще то можно поступить "правильно" (можно и без кавычек) и написать что-то типа :
Код:

<Ui xmlns="http://www.blizzard.com/wow/ui/" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://www.blizzard.com/wow/ui/C:\Projects\WoW\Bin\Interface\FrameXML\UI.xsd">
<Script file="test.lua"/>
<Frame name="test">
<Scripts>
<OnLoad>
Test_OnLoad();
</OnLoad>
<OnEvent>
Test_OnEvent(event);
</OnEvent>
</Scripts>
</Frame>
</Ui>

local print = function(msg) ChatFrame1:AddMessage(tostring(msg)) end
print "Hello, fucking world!"

Работает. Давайте сообразим что-то хоть на грамм пополезнее :

test_api.toc
Код:

local frame_x = 0
local frame_y = -300
local frame_w = 300
local frame_h = 20


frame = CreateFrame("Frame", "coord", UIParent)
frame:SetWidth(frame_w)
frame:SetHeight(frame_h)
frame.text=frame:CreateFontString(nil,"OVERLAY","GameFontNormal")
frame.text:SetAllPoints(frame)
frame:SetClampedToScreen(true)
frame:SetPoint("CENTER",UIParent,"CENTER",frame_x,frame_y)
frame:EnableMouse(true)
frame:SetMovable(true)
frame:RegisterForDrag("LeftButton")
frame:Show()
frame:SetScript("OnDragStart", function(this)
this:StartMoving()
end)
frame:SetScript("OnDragStop", function(this)
this:StopMovingOrSizing()
frame_x,frame_y = this:GetCenter()
frame_x = frame_x - GetScreenWidth() / 2
frame_y = frame_y - GetScreenHeight() / 2
this:ClearAllPoints()
this:SetPoint("CENTER",UIParent,"CENTER",frame_x,frame_y)
end)
frame:SetScript("OnUpdate", function(this)
local posx,posy=GetPlayerMapPosition("player")
this.text:SetText(floor(posx*100)..","..floor(posy*100).." [".. GetZoneText().."]")
end)


Привет, Гость сайта


Имя: Гость сайта
Ты здесь: -й день
Твой IP: 176.50.149.220
Ред. информацию
Профиль
Читать ЛС ( )

Как написать аддон для wow


Обстоятельства сложились так, что мне нужно написать аддон для нашей базы данных. Аддоны я никогда не писал, но хотел. И идеи были. Но не было времени. А теперь - нужно. Под это дело я начинаю цикл статей, который познакомит желающих с тем, как пишутся аддоны для World of Warcraft. Очень надеюсь на помощь и советы тех, кто аддоны уже писал или правил, вобщем - разбирается.

Скажу сразу, что данный цикл статей будет ориентирован на людей знакомых с программированием, или способных разобраться в программировании самостоятельно. Т.е. основ тут не будет. В идеале вам нужно иметь опыт работы с парой различных языков, javascript и представление о формате XML.

Данный цикл статей ориентирован на клиент версии 4.x, доступный сейчас на бета тесте и некоторые вещи могут не работать с младшими версиями. Это сделано из тех соображений, что когда мы доберемся до конца - как раз выйдет Катаклизм, или, по крайней мере - патч 4.0.1.

По первому впечатлению, разработка аддона во многом похожа на разработку Веб-приложения.

Начнем с начала.

Как оказалось, язык этот достаточно популярен, как среда для работы дополнений. Он используется во множестве игр и серьёзных приложений. Так что знать его может быть очень полезно.

Что нужно для начала

• Текстуры в ВоВ хранятся в проприетарном формате Близзард -.blp. В сети существует утилита, может даже не одна, позволяющая сконвертировать blp в png, чтобы было удобно просматривать файлы.

• Так же может быть полезно скачать Blizzard Addon Kit, который содержит документацию для начинающих, примеры и позволяет извлечь текстуры из клиента World of Warcraft. Документация на английском языке и во многом будет использоваться в моих статьях. Кит по умолчанию устанавливается в папку, где установлен World of Warcraft. Выбрать другую папку - нельзя.

• Документацию по самому языку LUA можно найти:

Аддон World of Warcraft состоит из трех основных типов файлов:

Формат файла toc

Описание аддона делается в следующем формате:

• Interface - это версия клиента, для которого написан ваш аддон. По всей видимости, это версия без точек. Т.е. в нашем случае 4.0.000 (хотя в бете 4.0.1. работает)
• Title - это название аддона, можно по-русски, но не забываем про UTF-8.
• Description - описание аддона.
• Dependencies - описание зависимостей, через запятую. Некоторые аддоны используют ресурсы других аддонов, функции, ресурсы. Так что здесь вы указываете то, без чего ваш аддон работать не будет. Яркий пример - DBM.

Читайте также: