cHAm, NETRAT

WarCraft 3: Часть первая

Создаем загрузочный код

Предисловие. Зачем это надо

Ну, например, создал ты мапу для мультиплеера, где можно качать хира до 50 уровня. За один раз, ясен пень, до такого уровня докачаться сложно. Надо как-то сохранять героя, тем более, что если игрок может качаться очень долго, то у него появляется азарт, желание прокачаться до упора, и он может целыми днями играть в твою мапу. Так вот, для сохранения героя большинство мэпмейкеров используют зашифрованный пароль. Некоторые умники (не буду показывать пальцем, но я таких видел) используют кэш, но он в мультеплеере не работает. Вобщем, если ты хочешь создать онлайн-РПГ карту, то без умения создавать загрузочные коды тебе не обойтись.

Глава первая. «cHAm’s Crypt System» или «Шифруй по-нашему!»

сHAm’s Crypt System (далее CCS) - это jass-скрипт, позволяющий без особого труда шифровать числа и переводить их в строку. СCS работает на основе перевода числа в заданную систему исчисления по указанному словарю. Таким образом можно значительно сократить длину загрузочного кода.
Вообще, систему перевода из одной системы исчисления в другую при создании загрузочных кодов предлагал NETRAT еще до меня, однако он написал об этом так заумно, что его не понял почти никто =D. Я же не только создал готовый шифровальный скрипт, но и сейчас объясню, как им пользоваться. Итак, приступим…

Глава вторая. «Перенос CCS на карту» или «Вперед и с песней!»

Сейчас я научу тебя, как правильно сохранить обычного героя на обычной карте.
Прежде всего качаем из аттача файл CCS.rar и извлекаем его куда-нибудь. Сделано? Отлично! Теперь открываем World Editor и создаем новую карту. Размер, тайлсет и прочую фигню поставь на свое усмотрение. Потом сразу создай стартовую локацию для 1 игрока, убери стандартные триггеры и т.д. Едем дальше. Открываешь CCS.j любым текстовым или jass редактором и копируешь содержание в custom script карты. Потом создаешь переменную pvpcache типа буфер игры (game cache) и триггер InitPvP с событием “Map Initialization”. Кидаешь в него два действия:
Game сache – Create a game cache from PvP.w3v
Set pvpcache = (Last created game cache)
И сохраняешь карту. Все, CCS был успешно импортирован!

Глава третья. «Словари» или «Моя твоя не понимай!»

Систему CCS ты уже перекачал на карту, однако работать сейчас она не будет. Почему? Потому, что CCS для шифровки использует словарь символов, и если он не задан, то и шифровать не получится. Сейчас мы его зададим. В комплекте CCS уже имеется один готовый словарь. Его мы и будем пока юзать. Чтобы инициировать словарь, в CCS есть функция CreateGlossary. Единственным параметром этой функции является количество символов в словаре. Это число от 1 до 90. Причем, если ввести число 0, то словарь будет 61 символ, включая нуль. Еще в CCS имеется функция CustomGlossary(string s), которая создает нестандартный словарь, т.е. вместо словаря будет использоваться строка s. ВНИМАНИЕ! Первый символ строки s в нестандартном словаре будет считаться на нуль. Пока нам вполне хватит стандарта на 60 символов, поэтому в триггере InitPvP добавляем действие:
Custom script: call CreateGlossary(0)
Ок, словарь инициирован, осталось только создать на карте героя, которого мы будем сохранять. Кидаем на карту паладина, создаем переменную Hero типа юнит (unit) и в том же триггере добавляем действие Set Hero=Паладин 0001 <gen>. Итого должно получиться так:

Вот, мы все инициировали, и теперь можно начать шифровать.

Глава четвертая. «Триггер сохранения» или «Пароль «Рыба-Конь»»

Ну-с, приступим… Для начала создай два массива – массив строк str и массив целых чисел int. Потом создаешь новый триггер – Saving с событием
Игрок - Игрок 1 (красный) types a chat message containing -save as Точное совпадение
Все, полигон готов. Теперь кидай такие действия

Set int[1] = (Hero level of Hero)
Set int[2] = (Level of Благодать for Hero)
Set int[3] = (Level of Божественный щит for Hero)
Set int[4] = (Level of Доспехи веры for Hero)
Set int[5] = (Level of Воскрешение for Hero)
Set int[6] = (Игрок 1 (красный) Золото (текущ.))
Set int[7] = (Игрок 1 (красный) Древесина (текущ.))
Пока хватит. Как видишь, здесь записывается вся инфа о хире и ресурсах с массив int. Теперь это все надо зашифровать. Для шифровки в CCS есть две функции: GetCharCode(integer i) и GetCharCodeWithLength(integer i, integer length). Первая просто шифрует указанное число, а вторая возвращает шифровку с указанной длиной. Т.е., если код получится меньше указанного, то число выйдет с нулями впереди. ВНИМАНИЕ! Функции GetCharCode и GetCharCodeWithLength не работают с числами больше 1000000000 или меньше 0.
Ладно, хорош теории, создаем цикл:

For each (Integer A) from 1 to 5, do (Actions)
Цикл - Действия
Custom script: set udg_str[bj_forLoopAIndex]=GetCharCode(udg_int[bj_forLoopAIndex])
Присваиваю шифр первых пяти переменных массива int соответственным номерам массива str. Кстати, если кто не знает, bj_forLoopAIndex – это тот же (Integer A) цикла, только в jass. Теперь создаем еще два действия:

Custom script:   set udg_str[6]=GetCharCodeWithLength(udg_int[6],4)
Custom script:   set udg_str[7]=GetCharCodeWithLength(udg_int[7],4)
Здесь мы шифруем ресурсы, отводя по 4 символа на каждый. В четырех символах можно уместить число до 12960000, поэтому на этого хватит.
Ладно, теперь мы это все сбиваем в две строки:

Set str[100] = (str[1] + (str[2] + (str[3] + str[6])))
Set str[101] = (str[4] + (str[5] + str[7]))
И выводим пасс игроку:

Игра  - Display to (All players) the text: (str[100] + (- + str[101]))
Итого, должно получиться так:
Теперь запускаем карту и набираем –save. Работает! Базу сделали, теперь едем дальше…

Глава пятая. «О безопасности и айтемах» или «Будь продвинутым!»

Теперь ты уже познакомился с основами и пора приниматься за штучки «попродвинутее». А именно, за безопасность и сэйв айтемов. Начнем с безопасности. Как известно из курса зоологии, геймеры делятся на два класса – честные геймеры и читеры =). Первые будут честно качать хира и записывать пассы, а вторые попытаются твой пасс взломать. Что же делать? Бородануть их! Для этого используется контрольная сумма. Кидаем перед циклом еще одно действие:

Set int[8] = (Abs((int[5] + (int[5] - (int[3] - (int[2] + int[1]))))))
То есть прибавляем/вычитаем все числа, кроме дерева и золота, т.к. с ресурсами контрольная сумма будет очень большой… Прописываем после цикла действие

Custom script:   set udg_str[8]=GetCharCode(udg_int[8])
и добавляем к str[101] еще и str[8]. Также можно зашифровать, например, длину имени игрока и первые две буквы имени, и тогда пасс будет именным, но с этим ты будешь разбираться сам.
Перейдем к айтемам. Чтобы не криптовать их огромные id, в CCS есть три функции:
SetItemNumber(integer id, integer n) - присваивает типу айтемов id номер n
GetItemNumber(integer id) – возвращает номер для типа айтемов id
GetItemId(integer n) – возвращает тип айтема с номером n.
Например, чтобы присвоить кресту перерождения номер 1, надо в триггере InitPvP добавить действие:

Custom script:   call SetItemNumber('ankh',1)
Теперь можно в пароле добавить новый символ (например str[9]) со значением GetItemNumber(‘ankh’).
Но сейчас мы с тобой этого делать не будем. Сам потом разберешься… Итак, у нас есть вот такой триггер сохранения:
Такой в точности? Тогда приступим к загрузке…

Глава шестая. «Триггер загрузки» или «Грузчика вызывали?»

Наконец, мы закончили сохранение и перешли к загрузке. Создаем триггер Loading с событием

Игрок - Игрок 1 (красный) types a chat message containing -load as Подстрока
и условием

(Substring((Entered chat string), 1, 5)) равно –load
Кидаем в него следующие действия:

Set str[0] = (Substring((Entered chat string), 7, (Length of (Entered chat string))))
If ((Length of str[0]) не равно 10) then do 
     (Skip remaining actions) 
else do 
     (Do nothing)
Set str[1] = (Substring(str[0], 1, 1))
Set str[2] = (Substring(str[0], 2, 2))
Set str[3] = (Substring(str[0], 3, 3))
Set str[6] = (Substring(str[0], 4, 7))
Set str[4] = (Substring(str[0], 9, 9))
Set str[5] = (Substring(str[0], 10, 10))
Set str[7] = (Substring(str[0], 11, 14))
Set str[8] = (Substring(str[0], 15, 15))
Вот. Здесь мы извлекаем сам код, а потом из него значения параметров игрока. Теперь это все надо разкодировать. Для этого есть функция Decode(string s). Она превращает строку-код s в целое число. Создаем цикл разкодировки:

For each (Integer A) from 1 to 8, do (Actions)
  Цикл - Действия
    Custom script:   set udg_int[bj_forLoopAIndex]=Decode(udg_str[bj_forLoopAIndex])
Тоже самое, что и при кодировке, только наоборот. Теперь проверяем контрольную сумму и, если она правильная, восстанавливаем хира и ресурсы. Вот так:
Ну вот. Система сохранения/загрузки готова! Кричи «ура»!

Просмотров: 13 716

» Лучшие комментарии


SwissLarson #1 - 7 лет назад 1
Интересная система. Надо будет опробовать
Liebendig1993 #2 - 6 лет назад 0
АХах))) как-то по дурости сам использовал кэш...еще постоянно задавался вопросом, мол, почему все так мудрят xD какие-то пароли выдумывают...
djvirus0987 #3 - 6 лет назад 0
что то вообще не понятно
Witcher_2 #4 - 6 лет назад 0
Надо попробовать,позже
Zkay #5 - 6 лет назад 0
Set int[8] = (Abs((int[5] + (int[5] - (int[3] - (int[2] + int[1]))))))
Где искать Abs? *** Я уже незнаю чё делать.
*** Народ. Если ещё кто в этом месте споткнется Abs => это математика - модуль. Автор не написать. >(
_____________________________________________________
Чё означает Entered chat string ?
Автор в чём я ошибся. И вопрос: Этот сейф можно использовать для многопользовательской карты.
Автор. У тебя ошибка в условии на скрине 15, а написанный 10. Какой правильный?
эскалибур #6 - 5 лет назад -3
... Автор зачёт... Но у меня русские триггеры...
Player #7 - 5 лет назад 2
эскалибур:
... Автор зачёт... Но у меня русские триггеры...
русские триггеры зло
Exersist #8 - 4 года назад 0
Про лоад можно бы было побольше) но тест мап все решает))
Это сообщение удалено