Аллоды 2: алгоритм создания вещей в магазине

Автор: ZZYZX

Добыто из sub_54D423 в сервере и связанных функций:

1. Количество созданных шмоток и выбор
Шмотки выбираются тупо из списка шмоток доступных исходя из выбранных материалов.
Если какая-то шмотка не подходит по цене, она всё равно выбирается, но потом «отбрасывается».
В магазине захардкожено 10 * MaxItems циклов для попыток добавления итемов.
(проще говоря если на полке указана маленькая максимальная цена и при этом все возможные классы и материалы, шмоток на полке скорее всего будет мало)
Количество в каждой созданной немагической шмотке выбирается от 1 до (MaxSingleType + 1)
В магической всегда 1.

2. Шанс создания магической шмотки
Если на полке магазина прописано Magic+Common, шанс создания магической шмотки — 50%
Если прописано только Magic, то шанс создания магической шмотки 100%
Во всех остальных случаях шанс 0%

3. Количество параметров на магической шмотке
Количество параметров всегда захардкожено — от 1 до 3.
Шанс одного параметра — 100%
Шанс двух параметров — 50%
Шанс трёх параметров — 12.5%

4. Выбор параметра для добавления в шмотку
Если шмотка — посох мага, в ней может быть только один параметр — 41, т.е. castSpell
Если шмотка любая другая, то логика следующая:
Берётся значение in_Warrior# или in_Mage# от последнего параметра (damageBonus)
Высчитывается рандомное значение от 0 до значения этой переменной в damageBonus.
Ищется первый параметр, подходящий по принципу:
значение_в_предыдущем_параметре < рандомное_значение <= значение_в_текущем_параметре
т.е. здесь ожидается что значения in_Warrior#, in_Mage# отсортированы по возрастанию.

В любой момент может внезапно выпасть параметр 41 castSpell.
Если этот параметр выпадает вторым или третьим, то он не добавляется, и больше параметров в шмотку добавлено не будет вообще.
Если же он выпадает первым, то добавляется только он и больше параметров добавлено не будет.

5. Выбор заклинания для параметра 41 castSpell
Захардкоженный список заклинаний.
Для посохов: Огненная стрела, Молния, Радужная молния, Каменное проклятие, Вампиризм, Ледяная стрела, Каменная стрела
Для воинов: Каменное проклятие, Вампиризм

6. Расчёт максимальной силы параметров

Несколько переменных:
priceMax = максимальная цена для итема, указанная в полке для магазина
itemPrice = реальная цена для итема без учёта статов на нём, т.е. например «9600» для эльфийской накидки
itemPriceMax = 2 * priceMax — itemPrice
manaMax = магическая вместимость шмотки, считается из магической вместимости материала и класса (Elven None для эльфийской накидки) минус уже существующие параметры на шмотке
manaCost = стоимость параметра прописанная в датабине
absoluteMax = manaMax / manaCost
affectMin = значение из датабина
affectMax = значение из датабина

Если параметр 41 и оружие для воина, то priceMax умножается на 10
Если параметр 41 и оружие для мага, то priceMax умножается на 100

Если параметр 41, навык считается так:
v9 = log(itemPriceMax / (scrollCost * 10)) / log(2) // ЗДЕСЬ НЕТОЧНО, scrollCost взял по сути с потолка
if (v9 > 0) v9 = ((pow(1.2, v9) — 1) * 30)
else v9 = -1
v9 = min(v9, absoluteMax)
v9 = min(v9, 100)

Если параметр не 41, то сила параметра считается так:
v9 = log(itemPriceMax / (manaMax * 50) — 1) / log(1.5) * 70 / manaCost
v9 = min(v9, absoluteMax)
v9 = min(v9, affectMax)

В случае если на любом этапе v9 становится отрицательным или NaN, параметр не добавляется.
Также если параметр не 41 и значение меньше affectMin, то параметр не добавляется.

7. Расчёт стоимости по мане уже добавленного параметра
Для параметра 41: manaCost * skill
Для параметров 44, 45, 46, 47, 48: manaCost * damageMax
Для всех остальных параметров: manaCost * value

8. Расчёт фактического параметра на шмотке (рандомного):
Для параметра 41: рандомное значение от 1 до максимального
Для параметров 44, 45, 46, 47, 48:
Минимальный урон = рандомное значение от 1 до максимального
Максимальный урон = рандомное значение до х1.5 от минимального (приблизительно, на самом деле чуть сложнее)
Для всех остальных параметров: от рандомного значения до максимального. Но если меньше минималки, ставится минималка (affectMin)