IPB

Здравствуйте, гость ( Вход | Регистрация )

История благодарностей участнику Berserker. Спасибо сказали: 1151
Дата поста: В теме: За сообщение: Спасибо сказали:
16 Jun 2021, 01:43 ERA III


Вышло обновление для HoMM 3 ERA
Текущая версия: 3.8.1

Что нового ?

[+] Реализована поддержка композитных изображений png.
При загрузке любого изображения png для формирования окончательного композитного изображения может быть применен фон из другого изображения pcx8/pcx16 (или их замены png).
Это поведение контролируется с помощью конфигураций json. Например, можно сделать все кадры кнопки "Загрузить игру" составными изображениями:

Код
{
  "era": {
    "png_backs": {
      "data/defs/zmenulg.def/0_0.png": {
        "file": "zpic1005.pcx16",
        "x": "533",
        "y": "132",
      },

      "data/defs/zmenulg.def/0_1.png": {
        "file": "zpic1005.pcx16",
        "x": "533",
        "y": "132",
      },

      "data/defs/zmenulg.def/0_2.png": {
        "file": "zpic1005.pcx16",
        "x": "533",
        "y": "132",
      },

      "data/defs/zmenulg.def/0_3.png": {
        "file": "zpic1005.pcx16",
        "x": "533",
        "y": "132",
      },
    }
  }
}

Здесь "era.png_backs" - это раздел конфигурации. Укажите относительный путь к изображению png в нижнем регистре как подраздел и следующие параметры в значении:
- "file": имя файла pcx фона. Используйте расширение "*.pcx" для pcx8 (256 цветов с прозрачностью) и "*.pcx16" для pcx16 (65536 цветов без прозрачности).
Реальное используемое имя ресурса для "*. pcx16" — "*. pcx", но расширение указывает Era, какой формат изображения использовать. Если есть замена png для pcx изображения, то она будет использоваться вместо pcx.
- "x": начальная x-координата в фоновом изображении.
- "y": начальная y-координата в фоновом изображении.

Составные изображения позволяют применять полупрозрачность в игровых кнопках. Оригинальные кадры игровых кнопок были сделаны с предварительно нанесенным фоном, таким как фон главного меню (zpic1005.pcx). Таким образом, все разработчики интерфейсных модов должны были применять фиксированный фон к каждому кадру кнопки. Отныне мы можем выпускать скины, которые подойдут для любого фона. Мы также можем применять фиксированный фон для иконок, портретов монстров и навыков, предоставляя изображения переднего плана в формате png с прозрачными областями.

[+] Реализована реальная обрезка png в памяти. Потребление памяти было значительно снижено для изображений с большими прозрачными областями по периметру.

[+] Реализована поддержка стабильных многопользовательских сражений путем введения детерминированного генератора псевдослучайных чисел в PvP-сражениях. Спасибо ZVS за идею.
Детерминированный генератор влияет на все вызовы функции rand(), включая собственные способности существ, возможности опыта стека и команду VR:R.
Состояние генератора формируется следующими значениями: [Боевой раунд, Минимальное значение для генерации, Идентификатор боя, Максимальное значение для генерации, Идентификатор боевого действия], где Идентификатор боя — действительно случайное значение для каждого боя, Боевой раунд — счетчик раундов, а идентификатор боевого действия — счетчик действий.

[+] Добавлена опция "Debug.Rng" в heroes3.ini. Если установлено значение 1, команды rand/srand/VR:R будут генерировать отладочные сообщения.

[+] Положение анимации главного меню acredit.smk больше не зависит от переключателя Rus/Eng в zmess00.txt. Теперь координаты не жестко закодированы,а хранятся в конфигурационном файле json в ключах "era.acredit_pos.x" и "era.acredit_pos.y".

[+] Добавлена новая утилита на javascript для преобразования патчей UN:C в двоичные патчи. См. "Tools/UncToBin/index.html".
[+] Добавлен дополнительный бинарный патч "disable darkness dragons map shadowing.bin.off" в мод WoG.
[+] Добавлены недостающие константы в Era Erm Framework. Новые константы для классов героев: HERO_CLASS_XXX.
[+] Обновлен редактор Erm.
[*] Бинарный патч "no prisons on random maps.bin" включен по умолчанию.
[-] Исправлено поведение генератора случайных чисел в игре: установка состояния родного генератора больше не влияет на состояние генератора Вихря Мерсенна. VR:T не будет возвращать идентичные значения после боя.

Код
Version 3.8.1 (06/2021)
------------------------
[+] Implemented composite png images support.
    When any png image is loaded, a background from another pcx8/pcx16 (or their png replacement) image may be applied to form final composite image.
    This behavior is controlled via json configs. Example, making all "Load Game" button frames composite images:

    {
      "era": {
        "png_backs": {
          "data/defs/zmenulg.def/0_0.png": {
            "file": "zpic1005.pcx16",
            "x": "533",
            "y": "132",
          },

          "data/defs/zmenulg.def/0_1.png": {
            "file": "zpic1005.pcx16",
            "x": "533",
            "y": "132",
          },

          "data/defs/zmenulg.def/0_2.png": {
            "file": "zpic1005.pcx16",
            "x": "533",
            "y": "132",
          },

          "data/defs/zmenulg.def/0_3.png": {
            "file": "zpic1005.pcx16",
            "x": "533",
            "y": "132",
          },
        }
      }
    }

    Here "era.png_backs" is config section. Specify relative path to png image in a lower case as subkey and the following parameters in value:
    - "file": pcx file name of background. Use "*.pcx" extension for pcx8 (256 colors with transparency) and "*.pcx16" for pcx16 (65536 colors without transparency).
              The real resource name for "*.pcx16" extension is "*.pcx", but the extension tells Era, which image format to use. If there is png replacement for pcx
              image, it will be used instead.
    - "x":    x-coordinate in background image to start drawing from.
    - "y":    y-coordinate in background image to start drawing from.

    Composite images allow to have semi-transparency in game buttons. Original game buttons frames were made with pre-applied background like main menu background (zpic1005.pcx).
    Thus all skin makers had to apply fixed background to each button frame. From now we are able to release skins, which will suit any backgrounds. We are also able to apply
    fixed background for icons, monster portraits and skills, supplying foreground images in png format with transparent areas.

[+] Implemented real png cropping in memory. Memory consumption was highly reduced for images with large perimeter transparent areas.

[+] Implemented stable multiplayer battles support by introducing deterministic pseudo random number generator in PvP battles. Thanks to ZVS for idea.
    Deterministic generator influences all calls to rand() function, including native creature abilities, stack experience abilities and VR:R command.
    The state of generator is formed by the following values: [Combat round, Min value to generate, Combat ID, Max value to generate, Combat action ID], where Combat ID is truly random value for each combat, Combat round is round counter and Combat action ID is action counter.

[+] Added "DebugRng" option to heroes3.ini. If set to 1, rand/srand/VR:R commands will generate debug messages.

[+] acredit.smk main menu animation position does not depend on Rus/Eng switch in zmess00.txt. The coordinates are not hardcoded anymore and are stored in
    json config file in "era.acredit_pos.x" and "era.acredit_pos.y" keys.

[+] Added new javascript utility to convert UN:C patches into binary patches. See "Tools/UncToBin/index.html".
[+] Included optional binary patch "disable darkness dragons map shadowing.bin.off" in WoG mod.
[+] Added missing constants to Era Erm Framework. New constants for hero classes: HERO_CLASS_XXX.
[+] Updated Erm Editor.
[*] "no prisons on random maps.bin" binary patch is on by default.
[-] Fixed game random number generator behavior: reseeding does not influence Mersenne Twister generator state anymore. VR:T will not return the same values after battle.
Bes, hippocamus, magoth, Mefista, KypaToP_HM, Lokos, Grossmaster, Adrienne, Archer30
20 May 2021, 03:22 ERA III


Вышло обновление для HoMM 3 ERA
Текущая версия: 3.8.0

Что нового ?

[+] Улучшена поддержка png для кадров def. Исправлены известные ошибки и добавлена поддержка объектов карты приключений.

Для теней используйте 12,5%..75% прозрачного черного цвета. Наиболее часто используемая тень — черный 50% прозрачности.
Для объектов карты приключений с флагами используйте цвет $FFFF00 (желтый) в качестве заполнителя цвета флага.

Png-кадры могут иметь разные размеры, но рекомендуется сохранять их значения в пределах def. Для текстов EML кадры png могут иметь любые размеры.
F12 очищает кэш кадров png, позволяя немедленно протестировать изменения.

Png-изображения без прозрачности рисуются как минимум в 4 раза быстрее, чем изображения с хотя бы одним прозрачным пикселем.

[+] Добавлена поддержка замены pcx изображениями png. Замененные файлы pcx могут не существовать, если существует соответствующий файл png.
Чтобы заменить изображение pcx на изображение png, поместите файл png в следующее место:
"Mods/YourMod/Data/Pcx/[любые каталоги, возможно вложенные...]\[имя файла pcx без расширения].png".
Пример: "Heroes 3/Mods/Mixed Neutrals/Data/Pcx/Тест/zpic1005.png" для фона главного меню (zpic1005.pcx).

Многие изображения интерфейса pcx в игре раскрашены текущим цветом игрока с использованием 32-цветных палитр.
Например, фон интерфейса города (hd_towns.pcx в HD mod). Era поддерживает два способа раскрашивания изображений в формате png.
Первый использует одно изображение для всех цветов игрока, как это делается в оригинальных игровых ресурсах.
Используйте специальные 32 цвета из следующих файлов для рисования раскрашиваемых областей:

- Help/player interface palette.pal
- Help/player interface palette.png

Второй способ - предоставить уникальное изображение для определенного цвета игрока, например, для фиолетового (ID: 5).
В этом случае ваше изображение png должно иметь следующее имя:
"Mods/YourMod/Data/Pcx/[любые каталоги, возможно вложенные...]\[имя файла pcx без расширения]_p[идентификатор игрока].png".
Пример: "Heroes 3/Mods/Mixed Neutrals/Data/Pcx/Тест/HD_TownS_p5.png" для фиолетового игрока.

0 красный
1 синий
2 коричневый
3 зеленый
4 апельсина
5 фиолетовый
6 чирок
7 розовый

Оба метода могут быть объединены. Если Era не находит отдельного изображения для конкретного игрока, она пытается использовать общий png,
заменяя фиксированные 32 кода цвета цветами палитры активного игрока.

[+] Удвоена производительность ассоциативных массивов Era, что повлияло на большую часть кода Era и VFS. Обновлена библиотека vfs.dll.

Скачать: https://mods.hmm35.ru/Era%20Update.exe

Код
Version 3.8.0 (05/2021)
------------------------
[+] Improved png support for def frames. Fixed known bugs and added support for adventure map objects.

    For shadows use 12.5%..75% transparent black color. The most often used shadow is 50% transparent black.
    For adventure map objects with flags use $FFFF00 (yellow) color as flag color placeholder.

    Png frames may have different sizes, but it's recommended to keep their dimensions in def bounds. For EML texts png frames may have any sizes.
    F12 clears png frames cache, allowing to test changes immediately.

    Png images without transparency are drawn at least 4X faster than images with at least single transparent pixel.

[+] Added support for pcx replacement with png images. Replaced pcx files may not exist if corresponding png file exists.
    To replace pcx image with png image place png file in the following location:
    "Mods/YourMod/Data/Pcx/[any directories, possibly nested...]\[pcx file name without extension].png".
    Example: "Heroes 3/Mods/Mixed Neutrals/Data/Pcx/Test/zpic1005.png" for main menu background (zpic1005.pcx).

    Many interface pcx images in game are colorized with current player color using 32-color pal-palettes.
    For instance, town interface background (hd_towns.pcx in HD mod). Era supports two ways of png image colorization.
    The first one using single image for all player colors, like it's done in original game resources.
    Use special 32 colors from the following files to draw colorizable areas:

      - Help/player interface palette.pal
      - Help/player interface palette.png

    The second way it to provide unique image for specific player color, for instance for purple (ID: 5).
    In this case your png image should have the following name:
    "Mods/YourMod/Data/Pcx/[any directories, possibly nested...]\[pcx file name without extension]_p[player ID].png".
    Example: "Heroes 3/Mods/Mixed Neutrals/Data/Pcx/Test/HD_TownS_p5.png" for purple player.

      0 red
      1 blue
      2 tan
      3 green
      4 orange
      5 purple
      6 teal
      7 pink

    Both methods may be combined. If Era does not find a separate image for particular player, it tries to use common png,
    replacing fixed 32 color codes with player palette colors.

[+] Doubled Era associative arrays performance, affecting most Era and VFS code. Updated vfs.dll.
Bes, Iv, XEL, hippocamus, magoth, XEPOMAHT, Mefista, Lokos, Grossmaster
30 Apr 2021, 03:50 ERA III


Вышло обновление для HoMM 3 ERA
Текущая версия: 3.7.0

Что нового ?

[+] Добавлен новый синтаксис SN:H для работы с текстами заклинаний.

!!SN:H^spell^/#spell_id/#spell_text_type/$text

где #spell_text_type-одна из констант SPELL_TEXT_XXX.

Эта команда делает устаревшим использование SS для текстов.
Синтаксис удаления работает частично. Настройки сбрасываются, но текст будет восстановлен только при загрузке сохраненной игры.

Пример:

Код
!?FU(OnAfterErmInstructions);
; Список всех заклинаний с отображажением всех текстов
!!re i/(SPELL_FIRST)/(SPELL_LAST_WOG);
  !!SN:H^spell^/i/(SPELL_TEXT_NAME)/?(text0:z);
  !!SN:H^spell^/i/(SPELL_TEXT_SHORT_NAME)/?(text1:z);
  !!SN:H^spell^/i/(SPELL_TEXT_DESCR)/?(text2:z);
  !!SN:H^spell^/i/(SPELL_TEXT_DESCR_BASIC)/?(text3:z);
  !!SN:H^spell^/i/(SPELL_TEXT_DESCR_ADVANCED)/?(text4:z);
  !!SN:H^spell^/i/(SPELL_TEXT_DESCR_EXPERT)/?(text5:z);
  !!SN:H^spell^/i/(SPELL_TEXT_SOUND)/?(text6:z);
  !!IF:M^Заклинание %i:
  %(text0)
  %(text1)
  %(text2)
  %(text3)
  %(text4)
  %(text5)
  %(text6)^;
!!en;


[+] SN:Команда V#1/#2/#3 теперь применяет операцию "mod 32" к аргументу № 2, позволяя использовать команды на картах XXL без ошибок.

[+] Добавлены глобальные экспортируемые функции для работы с глобальными именованными переменными ERM (i^..^ и s^...^):

int (__stdcall) GetAssocVarIntValue (const char *VarName);
char* (__stdcall) GetAssocVarStrValue (const char *VarName);
void (__stdcall) SetAssocVarIntValue (const char *VarName, int newValue);
void (__stdcall) SetAssocVarStrValue (const char *VarName, const char *newValue);

Не забудьте вызвать (__stdcall) MemFree (void* Addr) для освобождения памяти, возвращаемой строковыми функциями.

[+] Добавлены глобальные экспортированные функции для работы с общим глобальным реестром в памяти ERA.
Реестр может использоваться плагинами для обмена значениями конфигурации и сигналами.

int (__stdcall) GetEraRegistryIntValue (const char *VarName);
char* (__stdcall) GetEraRegistryStrValue (const char *VarName);
void (__stdcall) SetEraRegistryIntValue (const char *VarName, int newValue);
void (__stdcall) SetEraRegistryStrValue (const char *VarName, const char *newValue);

Не забудьте вызвать (__stdcall) MemFree (void* Addr) для освобождения памяти, возвращаемой строковыми функциями.

[+] Добавлены отсутствующие файлы crtrait0.txt и crtraits.txt в hmm35wog.pac.
[*] Сообщение "Не удалось загрузить изображение %s" больше не будет отображаться для отсутствующих изображений в родных диалогах WoG.
[*] Обновлен редактор Erm и Era Erm Framework.

Скачать: https://mods.hmm35.ru/Era%203.X.exe

Код
Version 3.7.0 (04/2020)
------------------------
[+] Added new SN:H syntax to work with spell texts.

    !!SN:H^spell^/#spell_id/#spell_text_type/$text

    where #spell_text_type is one of SPELL_TEXT_XXX constants.

    This command deprecates SS usage for texts.
    Deletion syntax works partially. The settings are reset, but text will be restored on savegame load only.

    Example:

    !?FU(OnAfterErmInstructions);
   ; List all spell, displaying all texts
    !!re i/(SPELL_FIRST)/(SPELL_LAST_WOG);
      !!SN:H^spell^/i/(SPELL_TEXT_NAME)/?(text0:z);
      !!SN:H^spell^/i/(SPELL_TEXT_SHORT_NAME)/?(text1:z);
      !!SN:H^spell^/i/(SPELL_TEXT_DESCR)/?(text2:z);
      !!SN:H^spell^/i/(SPELL_TEXT_DESCR_BASIC)/?(text3:z);
      !!SN:H^spell^/i/(SPELL_TEXT_DESCR_ADVANCED)/?(text4:z);
      !!SN:H^spell^/i/(SPELL_TEXT_DESCR_EXPERT)/?(text5:z);
      !!SN:H^spell^/i/(SPELL_TEXT_SOUND)/?(text6:z);
      !!IF:M^Spell %i:
    %(text0)
    %(text1)
    %(text2)
    %(text3)
    %(text4)
    %(text5)
    %(text6)^;
    !!en;

[+] SN:V#1/#2/#3 command now applies "mod 32" operation to argument #2, allowing to use commands on XXL maps without errors.

[+] Added global exported functions to work with ERA global named ERM variables (i^..^ and s^...^):

  int (__stdcall) GetAssocVarIntValue (const char *VarName);
  char* (__stdcall) GetAssocVarStrValue (const char *VarName);
  void (__stdcall) SetAssocVarIntValue (const char *VarName, int NewValue);
  void (__stdcall) SetAssocVarStrValue (const char *VarName, const char *NewValue);

  Do not forget to call (__stdcall) MemFree (void* Addr) to release memory, returned by string functions.

[+] Added global exported functions to work with ERA shared global in-memory registry.
    The registry can be used by plugins to exchange config values and signals.

  int (__stdcall) GetEraRegistryIntValue (const char *VarName);
  char* (__stdcall) GetEraRegistryStrValue (const char *VarName);
  void (__stdcall) SetEraRegistryIntValue (const char *VarName, int NewValue);
  void (__stdcall) SetEraRegistryStrValue (const char *VarName, const char *NewValue);

  Do not forget to call (__stdcall) MemFree (void* Addr) to release memory, returned by string functions.

[+] Added missing crtrait0.txt and crtraits.txt to hmm35wog.pac.
[*] "Failed to load image at %s" message will not be displayed anymore for missing images in wog native dialogs.
[*] Updated Erm Editor and Era Erm Framework.
Bes, hippocamus, XEPOMAHT, KypaToP_HM, Iriniko, Grossmaster
28 Apr 2021, 04:38 ERA III


Вышло обновление для HoMM 3 ERA
Текущая версия: 3.4.1

Что нового ?

Константа (CURRENT_HERO) (-1) теперь может безопасно использоваться в триггерах. Ранее глобальное значение текущего героя могло быть перезаписано вложенными событиями.

Пример:

Код
!?HM0; нынешний герой-Оррин
!!HE(HERO_XERON):Ed100000; Повышение для Xeron, раньше текущий герой менялся на Xeron
!!HE(CURRENT_HERO):N?(hero:y); (hero) всегда (HERO_ORRIN), начиная с версии 3.4.1


Реализован высокоуровневый API для WoG радио-диалогов. Диалоговое окно настраивается перед показом. Опционально устанавливается значение и строковая метка для любого элемента. Опциональный пункт «Отмена». Возврат результата в виде индекса элемента, значения и строковой метки. Больше не нужно преобразовывать биты вручную.

Скачать: https://mods.hmm35.ru/Era%20Update.exe

Код
[+] (CURRENT_HERO) constant (-1) can be safely used in triggers from now. Previosly this global value could be overwritten by nested events.

  Example:
  !?HM0; current hero is Orrin
  !!HE(HERO_XERON):Ed100000;     Level up for Xeron, current hero used to become Xeron in previous Era versions
  !!HE(CURRENT_HERO):N?(hero:y); (hero) is always (HERO_ORRIN), starting from Era 3.4.1

[+] Implemented high level API for WoG radio dialogs. Configure dialog before showing. Optionally assign value and tag to each item.
    Optionally add special "cancel" item. The result is item index, value and tag. No need to convert bits anymore.

    Example 1:

    !?FU(OnAfterErmInstructions);
    !!FU(RadioDlg_Reset):P;
    !!FU(RadioDlg_SetTitle):P^What primary skill would you like to increase?^;
    !!FU(RadioDlg_AddCancelButton):P;

    !!FU(RadioDlg_AddItem):P^Attack^/(SKILL_ATTACK)/^attack^;
    !!FU(RadioDlg_AddItem):P^Defense^/(SKILL_DEFENSE)/^defense^;
    !!FU(RadioDlg_AddItem):P^Knowledge^/(SKILL_KNOWLEDGE)/^knowledge^;
    !!FU(RadioDlg_AddItem):P^Power^/(SKILL_POWER)/^power^;

    !!FU(RadioDlg_SelectItemByTag):P^knowledge^;
    !!FU(RadioDlg_Show):P?(item:y)/?(value:y)/?(tag:z);
    !!IF:M^Item: %(item). Value: %(value). Tag: %(tag)^;

    API:

    !?FU(RadioDlg_Reset);
  ; Resets all radio dialog settings to empty values.

    !?FU(RadioDlg_SetTitle);
  ; Changes radio dialog title.

    !?FU(RadioDlg_AddCancelButton);
  ; Adds cancel button to dialog. Decreases maximum number of items in dialog by one.

    !?FU(RadioDlg_SelectItem);
  ; Sets new selected item by its index.
    !#VA(itemInd:x);

    !?FU(RadioDlg_SelectItemByValue);
  ; Finds the first item with specified value and selects it.
    !#VA(itemValue:x);

    !?FU(RadioDlg_SelectItemByTag);
  ; Finds the first item with specified tag and selects it.
    !#VA(itemTagPtr:x); Tag string

    !?FU(RadioDlg_AddItem);
  ; Adds new item to radio dialog.
    !#VA(itemCaptionPtr:x); Optional. New item caption. Empty/spacy captions are valid. Default: icon6.gif.
    !#VA(itemValue:x);      Optional. Numeric value, associated with item. Default: 0.
    !#VA(itemTagPtr:x);     Optional. String tag, associated with item. Default: icon6.gif.
    !#VA(selectItem:x);     Optional. Boolean. If TRUE, item will be selected. Default: FALSE.

    !?FU(RadioDlg_AddItems);
  ; Adds up to 5 items to radio dialog. For detailed arguments description see (RadioDlg_AddItem).
    !#VA(firstItemCaptionPtr:x);
    !#VA(firstItemValue:x);
    !#VA(firstItemTagPtr:x);

    !?FU(RadioDlg_Show);
  ; Display previously configured radio dialog with single possible choice.
  ; Currently maximum RADIO_DLG_MAX_ITEMS (-1 for cancel button) items can be added to the dialog.
  ; Returns selected item index, value and tag. Item index is (NO_RADIO_DLG_ITEM) if no items are present for selection
  ; or Cancel button was pressed.
    !#VA(resultItem:x);   Default: (NO_RADIO_DLG_ITEM).
    !#VA(resultValue:x);  Default: -1.
    !#VA(resultTagPtr:x); Default: icon6.gif.




Вышло обновление для HoMM 3 ERA
Текущая версия: 3.4.2

Что нового ?

[+] Добавлены следующие функции в Era Erm Framework:

Код
!?FU(RadioDlg_GetNumItems);
; Возвращает количество элементов, добавленных в диалог
!#VA(result:x);

!?FU(RadioDlg_GetItemValue);
; Возвращает значение указанного элемента или выдает ошибку в случае недопустимого индекса.
!#VA(itemInd:x);
!#VA(result:x);

!?FU(RadioDlg_GetItemTag);
; Возвращает тег указанного элемента или выдает ошибку в случае недопустимого индекса.
!#VA(itemInd:x);
!#VA(result:x);


[+] Обновлен редактор ERM.
[-] Исправлен черный фон в меню «Авторы».

Скачать: https://mods.hmm35.ru/Era%20Update.exe

Код
[+] Added the following functions to Era Erm Framework:

  !?FU(RadioDlg_GetNumItems);
; Returns number of items, added to dialog
  !#VA(result:x);

  !?FU(RadioDlg_GetItemValue);
; Returns value of specified item or throws error in case of invalid index.
  !#VA(itemInd:x);
  !#VA(result:x);

  !?FU(RadioDlg_GetItemTag);
; Returns tag of specified item or throws error in case of invalid index.
  !#VA(itemInd:x);
  !#VA(result:x);

[+] Updated ERM Editor.
[-] Fixed black background in Credits menu.




Вышло обновление для HoMM 3 ERA
Текущая версия: 3.4.3

Что нового ?

[+] Добавлена новая команда ERM VR:B. Она преобразует любое число в логическое значение (1 или 0). Любое ненулевое значение становится 1.

Пример:

Код
!!OW:R(CURRENT_PLAYER)/(RES_GOLD)/?(goldAmount:y);
!!VR(hasGold:y):S(goldAmount) B; теперь hasGold = (TRUE) или (FALSE)

!!if&(hasGold)=(TRUE);
  !!IF:М^Я знаю, что у вас есть немного золота в карманах!^;
!!en;


Скачать: https://mods.hmm35.ru/Era%20Update.exe

Код
[+] Added new ERM command VR:B. It converts any number to boolean (1 or 0). Any non-zero value becomes 1.

  Example:

  !!OW:R(CURRENT_PLAYER)/(RES_GOLD)/?(goldAmount:y);
  !!VR(hasGold:y):S(goldAmount) B; now hasGold = (TRUE) or (FALSE)

  !!if&(hasGold)=(TRUE);
    !!IF:M^I know you have some gold in your pockets!^;
  !!en;




Вышло обновление для HoMM 3 ERA
Текущая версия: 3.5.0

Что нового ?

[+] Переписана часть старого ERM-движка, который отвечал за вычисление условий команд.

- Можно использовать пробелы и переводы строк для оформления сложных условий.

Пример:

Код
!!if|i^Master_Warrior_Hero%(hero)^         <> (prevWasMasterWarrior)/
     i^Master_Mage_Hero%(hero)^            <> (prevWasMasterMage)/
     i^Master_Adventurer_Hero%(hero)^      <> (prevWasMasterAdventurer)/
     i^Grandmaster_Warrior_Hero%(hero)^    <> (prevWasGrandmasterWarrior)/
     i^Grandmaster_Mage_Hero%(hero)^       <> (prevWasGrandmasterMage)/
     i^Grandmaster_Adventurer_Hero%(hero)^ <> (prevWasGrandmasterAdventurer);
; ...
!!en;


- Можно использовать числа в левой части сравнений. Раньше к ним относились как к флагам.

Пример 1:

Код
!!IF&1000>=(goldLeft):M^У вас достаточно золота, чтобы купить карту^;


Пример 2:

Код
!#DC(EDU_MOD_VERSION) = 317;

!!if & (EDU_MOD_VERSION) < 320;
  !!IF:M^Вы используете старую версию Edu мода. Пожалуйста, обновите его^;
!!en;


- Одиночные числовые или строковые значения теперь преобразуются в логические. Для чисел это то же самое, что <> 0. Для строк это то же самое, что <> icon6.gif (пустая строка).

Примеры:

Код
!!HE(CURRENT_HERO):W?(movePoints:y);
!!IF&(movePoints):M^Ладно, у вас есть несколько очков передвижения^; то же самое, что и &(movePoints)<>0
; Пожалуйста, используйте оператор >= в реальном коде для всего, что может стать отрицательным. Это просто пример

!!VR(inputText:z):S^test^;
!!IF&(inputText)/(inputText)<>^секретный пароль^:M^Вы ввели неправильный пароль!^; то же самое, что и &(inputText)<>^^/(inputText)<>^секретный пароль^


Скачать: https://mods.hmm35.ru/Era%20Update.exe

Код
[+] Rewritten part of old ERM engine, which was responsible for conditions evaluations.

  - It's now possible to use spaces and line feeds to decorate complex conditions.

  Example:

  !!if|i^Master_Warrior_Hero%(hero)^         <> (prevWasMasterWarrior)/
       i^Master_Mage_Hero%(hero)^            <> (prevWasMasterMage)/
       i^Master_Adventurer_Hero%(hero)^      <> (prevWasMasterAdventurer)/
       i^Grandmaster_Warrior_Hero%(hero)^    <> (prevWasGrandmasterWarrior)/
       i^Grandmaster_Mage_Hero%(hero)^       <> (prevWasGrandmasterMage)/
       i^Grandmaster_Adventurer_Hero%(hero)^ <> (prevWasGrandmasterAdventurer);
  ; ...
  !!en;

  - It's now possible to use numbers in the left side of comparisons. Previosly they were treated as flags.

  Example 1:

  !!IF&1000>=(goldLeft):M^You have enough gold to buy the map^;

  Example 2:

  !#DC(EDU_MOD_VERSION) = 317;

  !!if & (EDU_MOD_VERSION) < 320;
    !!IF:M^You use old version of Edu mod. Please, update it^;
  !!en;

  - Single numeric or string values are casted to boolean now. For numbers it's the same as <> 0. For strings it's the same as <> icon6.gif (empty string).

  Examples:

  !!HE(CURRENT_HERO):W?(movePoints:y);
  !!IF&(movePoints):M^Ok, you have some movement points^; same as &(movePoints)<>0
; Please, use >= operator in real code for anything, that can become negative. It's just an example

  !!VR(inputText:z):S^test^;
  !!IF&(inputText)/(inputText)<>^secret password^:M^You have entered wrong password!^; same as &(inputText)<>^^/(inputText)<>^secret password^




Вышло обновление для HoMM 3 ERA
Текущая версия: 3.5.1

Что нового ?

[-] Исправлена ошибка: пробелы после операторов сравнения (<, >, =, <>) все ещё не игнорировались.

Скачать: https://mods.hmm35.ru/Era%20Update.exe

Код
Version 3.5.1 (04/2020)
------------------------
[-] Fixed bug: spaces after comparison operators (<, >, =, <>) were still not ignored.




Вышло обновление для HoMM 3 ERA
Текущая версия: 3.6.0

Что нового ?

[+] Реализована замена кадров def на изображения png. Замена происходит на лету, когда игра просит нарисовать def-кадр. Реальный кадр def может отсутствовать, но сам файл def должен существовать. Он может иметь любые размеры, но предпочтительная высота должна быть больше или равна максимальной высоте всех кадров. Png-кадр может иметь любой размер, но всегда будет отображаться в координатах (0, 0) def.

Текущие поддерживаемые типы def: интерфейсные defs, интерфейсные defs с несколькими группами кадров.
Поддерживаемые функции: горизонтальное зеркальное отображение.

Шаблон пути к кадру png: "Data/Defs/[defname.def]/[group_index]_[frame_index].png".
Индексы групп и кадров отсчитываются от 0.
Пример: "Data/Defs/zmenulg.def/0_2.png". Это пункт меню "Загрузить игру", группа 0, кадр 2.

Поддерживаются все форматы png, включая все типы прозрачности.
Самая быстрая отрисовка выполняется для png без прозрачности и 32-битного режима HD.

Язык разметки Era (EML) полностью поддерживает defs с кадрами png. Таким образом, любое изображение png может отображаться практически в любом месте, где выводится текст.
Кадры автоматически обрезаются перед отображением.
Пример: "{~>cndrgn.def:12:2 block mirror}"

Примечание: движок Heroes 3 перерисовывает диалоговые кнопки при каждом движении мыши, поэтому кнопки с частичной прозрачностью рисуются много раз на одном и том же фоне.

[!] Единственным рекомендуемым способом распространения измененных значков артефактов/заклинаний/монстров в модах является использование кадров png.
Кадры png имеют приоритет над файлами def, даже если кадр находится в моде с более низким приоритетом.

[+] Добавлен глобальный менеджер ресурсов, который в настоящее время используется для кэширования png кадров def. Укажите максимальный размер кэша в файле heroes3.ini в ключе "ResourceCacheSize".

[*] ERA больше не поставляется с файлом "heroes3.ini". Вместо этого она поставляется с файлом "default heroes3.ini", который содержит значения по умолчанию для всех настроек, отсутствующих в "heroes3.ini". Таким образом, "heroes3.ini" никогда не будет перезаписан и сохранит настройки пользователя. "heroes 3.ini" будет автоматически создан при изменении любых настроек в игре.

Скачать: https://mods.hmm35.ru/Era%20Update.exe



Код
Version 3.6.0 (04/2020)
------------------------
[+] Implemented def frames replacement with png images. Replacement occurs on the fly when game asks to draw def frame.
    Real def frame may be missing, but a def file itself must exist. It may have any dimensions, but preferrable height should
    be greater or equal to maximum height of all frames. Png frame may have different size, but will be always drawn at (0, 0) def coordinates.

    Current supported def types: interface defs, interface defs with multiple frame groups.
    Supported features: horizontal mirroring.

    Png frame path template: "Data/Defs/[defname.def]/[group_index]_[frame_index].png".
    Group and frame indexes are counted from 0.
    Example: "Data/Defs/zmenulg.def/0_2.png". It's a "Load Game" menu item, group 0, frame 2.

    All png formats are supported, including all types of transparency.
    The fastest drawing is performed for png without transparency and 32 bit HD mode.

    Era Markup Language (EML) fully supports defs with png frames. Thus any png image can be displayed in almost any place, where text is output.
    Frames are automatically trimmed before displaying.
    Example: "{~>cndrgn.def:12:2 block mirror}"

    Note: Heroes 3 engine redraws dialog buttons on every mouse move, thus buttons with partial transparency are drawn many times on the same background.

[!] The only recommended way of providing changed artifacts/spells/monster icons in mods is png frames usage.
    Png frames have priority over def files even if frame is located in a mod with a lower priority.

[+] Added global resource manager, which is used currently for def frames png caching. Specify maximum cache size in heroes3.ini
    in the "ResourceCacheSize" key.

[*] ERA does not provide "heroes3.ini" anymore. Instead it comes with "default heroes3.ini" file, which is
    a fallback for any key, missing in "heroes3.ini". Thus "heroes3.ini" will never be overwritten and will
    preserve user settings. "heroes 3.ini" will be automatically created when any in-game setting is changed.
Bes, hippocamus, XEPOMAHT, Mefista, KypaToP_HM, Lokos, Iriniko, Grossmaster
09 Apr 2021, 02:09 ERA III


Вышло обновления для HoMM 3 ERA
Текущая версия: 3.4.0

Что нового ?

Поддержка анимации и выбора группы def-кадров в пользовательских диалогах;
Поддержка горизонтального выравнивания текста и встраиваемых блочных изображений;
Поддержка pcx-картинок с глубиной цвета 16 бит в пользовательских диалогах;
Поддержка обращения к ERM массивам по динамическим индексам;
Возможность обработки событий клавиатуры, колеса прокрутки и щелчков вне основной области для пользовательских диалогов;
Новые события победы, поражения, переноса героя между кампаниями, выбора навыков при повышении уровня. Локальные события карты.
Новые экспортируемые функции для работы с файлами и папками.
Исправленный перенос командиров в компаниях через транзитные зоны.
Поддержка 32-битных цветов в фонах пользовательских диалогв.
Поддержка комбинаций клавиш и щелчков с зажатой ALT.
Обновлённый редактор ЕРМ, исправление багов.

Скачать: https://mods.hmm35.ru/Era%203.X.exe

Код
Version 3.4.0 (04/2020)
------------------------
[+] Added possibility to use animated defs in DL-dialogs. Just append " animated" to dialog item name to make it animated. Example: "Def" => "Def animated".
    Up to 10 animated defs are supported for each dialog. Animation speed is 10 frames per second. One single DEF group of frames is used.

[+] Added possibility to specify frames group index for defs in DL-dialogs. Write frame index as GROUP_INDEX * 100000 + FRAME_INDEX. Group indexes are counted from 0.

[+] Implemented horizontal text alignment support in Era Markup Language (EML).

  To specify alignment use either regular color tags with new align=xxx attribute or new tag "text".
  Possible alignment values: "left", "center", "right".

  Examples:

  {~RosyBrown align=right}Some text with(out) images{~}
  {~text align=center}Some text with(out) images{~}
  {~RosyBrown align="left"}Some text with(out) images{~}
  {~text color="RosyBrown" align="left"}Some text with(out) images{~}

  Attribute values without spaces and special chars may be written without double quotes.

[+] Implemented block-style images support for Era Markup Language (EML).

  Use "block" attribute to mark image in text as block-style. New line before and after image will be forced automatically.
  Vertical space in text is also automatically reserved for block images. Moreover, they can be partially scrolled without vanishing effect, occuring for inline images.

  Examples:

  !!IF:M^{~text align=center}{~Orange}Fire camping{~}

  ----
  {~>CDEVIL.def:0:0 valign="middle" block}
  ----

  {~>cndrgn.def:12:2 block}{~}^;

[+] Added support for 65536-color pcx images (pcx16) in DL-dialogs. Default loading mode is 256 colors (pcx8). To load image as pcx16 change its name in dialogs editor to '****.pcx.pcx16'. Real file name in lod/pac archive should be left as is. The engine will recognise new extension, transform it into '.pcx' and load image as pcx16.

[+] Improved ERM 2 compiler. It became possible to use named local variables and quick variables (f..t) as arrays subscripts.
  Syntax: (array[index]) or (array[i]).
  Index value is evaluated BEFORE current receiver, thus do not change it in receiver itself like "!!MO998:G?i G(array[i])".

  A new magic constant 'SIZE' was added to return array size. Usage: (array[SIZE]). It's compiled into count of array items.
  Thus looping through all array items became easy:

  !!re i/0/(array[SIZE])/1/-1; Note the last -1, meaning loop from index 0 to SIZE - 1
    !!IF:M^%(array[i])^;
  !!en;

  Note, that regular constants are also supported:
  !!IF:M^%(array[PLAYER_TEAL])^;

[+] Implemented automatical static and dynamical index checking for ERM 2.0 arrays. Invalid indexes are reported and forced to valid range.

  Example:

  !#VA(msgType[7]:y) (msgColor[7]:y);

  !!re i/(PLAYER_FIRST)/(PLAYER_LAST);
    !!VR(msgType[i]):S(PIC_TYPE_FLAG); Here we get error. Array size is 7, while number of game players is 8. i = 7 is outside of valid 0..6 range
    !!VR(msgColor[i]):Si;              Here we get error. Array size is 7, while number of game players is 8. i = 7 is outside of valid 0..6 range
  !!en;

  Let's rewrite the example without bugs:

  !#VA(msgType[NUM_PLAYERS]:y) (msgColor[NUM_PLAYERS]:y);

  !!re i/(PLAYER_FIRST)/(PLAYER_LAST);
    !!VR(msgType[i]):S(PIC_TYPE_FLAG);
    !!VR(msgColor[i]):Si;
  !!en;

[+] Event DL/(OnCustomDialogEvent) now receive all mouse/keyboard parameters, accessible via !!CM and tracks clicks outside dialogs main area.
    Check CM:T or i^dlg_action^ value for:
      (DLG_ACTION_INDLG_CLICK)
      (DLG_ACTION_OUTDLG_CLICK)
      (DLG_ACTION_MOUSE_WHEEL)
      (DLG_ACTION_KEY_PRESSED)

    Example:

      !?DL&i^dlg_action^=(DLG_ACTION_OUTDLG_CLICK);
      !!IF:M^You clicked outside dialog!^;

    For (DLG_ACTION_MOUSE_WHEEL) action CM:S or i^mouse_action^ can be one of:
      (MOUSE_WHEEL_UP)
      (MOUSE_WHEEL_DOWN)

    Example:

      !?DL&i^dlg_action^=(DLG_ACTION_MOUSE_WHEEL);
      !!IF:M^Wheel: %i(mouse_action)^; display 1/-1 for wheel up/down

    Keyboard presses in dialog can be handled now using Era Erm Framework:

      !?DL&i^dlg_action^=(DLG_ACTION_KEY_PRESSED)/i^key^=(KEY_Q);
      !!IF:M^Good buy any dialog!^;
      !!DLi^dlg_id^:C(TRUE);

    Added two global variables to Era Erm Framework:
    - i^dlg_action^ with CM:T value (action type). Specially useful for DL-dialog events. See DLG_ACTION_XXX constants.
    - i^dlg_id^ with active DL-dialog ID.

[+] !!VR:F command can be called with 3 parameters now: !!VR(var):F(minValue)/(maxValue)/(showErrors);
    If the third parameter is specified and not (FALSE), values outside specified range are reported using regular ERM error reporting dialog.

[+] Added new ERM events:
  - "OnWinGame"  occurs when human player wins scenario.
  - "OnLoseGame" occurs when human player loses scenario.

  - "OnTransferHero" occurs when hero data from the previous campaign scenario is transferred to the next zone.
                     The events occurs after instructions but before PI (OnAfterErmInstructions).
                     The only argument is ID of hero, which is transferred from the previous scenario.

  - "OnAfterHeroGainLevel" occurs after AI/Human hero level-up. Dialog is already closed. Use (ERM_FLAG_IS_HUMAN) and (CURRENT_HERO) constants.
                           The only argument is Hero ID.

[+] Added extra parameter to "onKeyPressed" event. "onKeyPressed" occurs multiple times, when you hold the key, while it's sometimes necessary to catch only the first time, when key state changes to DOWN and ignore other events until key state changes to UP. The third event argument serves this purpose and is TRUE only when the key changes its state to DOWN.

!?FU(onKeyPressed);
!#VA(key:x) (preventDefault:x) (isDown:x);

[+] Implemented two universal events for handling human local events: "OnBeforeLocalEvent" and "OnAfterLocalEvent". They occur before any !?LE/!$LE trigger respecively
    and receive 3 parameters: x, y and z coordinates.

    Example:

    !?FU(OnBeforeLocalEvent);
    !#VA(x:x) (y:x) (z:x);
    !!IF:M^OnBeforeLocalEvent %(x) %(y) %(z)^;

    !?FU(OnAfterLocalEvent);
    !#VA(x:x) (y:x) (z:x);
    !!IF:M^OnAfterLocalEvent %(x) %(y) %(z)^;

[+] Added the following new functions to Era Erm Framework:

  !?FU(IsDllLoaded);
; Returns (TRUE) is specified DLL is loaded. The check is fast and does not lead to loading dll.
  !#VA(dllFileNamePtr:x); DLL file name with extension (*.dll, *.era, *.ani, etc).
  !#VA(result:x);         Boolean. (TRUE) if DLL is loaded.

  !?FU(FileExists);
; Returns true if file (not directory) exists.
  !#VA(filePathPtr:x); Absolute or relative path to file
  !#VA(result:x);      Boolean. (TRUE) if file exists and is not a directory

  !?FU(DirExists);
; Returns true if a directory (not a file) exists.
  !#VA(dirPathPtr:x); Absolute or relative path to directory
  !#VA(result:x);     Boolean. (TRUE) if directory exists and is not a directory

  !?FU(DeleteFile);
; Deletes specified file and returns success flag.
  !#VA(filePathPtr:x); Absolute or relative path to directory
  !#VA(result:x);      Boolean. (TRUE) if file existed and was deleted.

  !?FU(ClearIniCache);
; Erases all cached ini file data from memory. You can safely delete ini file afterwards.
  !#VA(filePathPtr:x); Absolute or relative path to ini file

  !?FU(CreateDir);
; Creates new directory if it does not exist.
  !#VA(dirPathPtr:x); Absolute or relative path to directory

[+] The following improvements were introduced in "Era Erm Framework" mod:

  - Added new globally saved parameters for "onKeyPressed" event:
  i^key_down^: boolean. TRUE only when the key changes its state from UP to DOWN the first time until being released.

[+] Added the following exported functions to era.dll:

  - function IsCampaign: TDwordBool;

  !!SN:F^IsCampaign^; v1 = (TRUE) or (FALSE)

  - procedure GetCampaignFileName (Buf: pchar);

  !!SN:F^GetCampaignFileName^/?(campaignFileName:z); will crash if it's not campaign

  - procedure GetMapFileName (Buf: pchar);

  !!SN:F^GetMapFileName^/?(mapFileName:z);

  - function GetCampaignMapInd: integer;
    Returns campaign map zone index (index in original zone maps list, starting from 0).

  !!SN:F^GetCampaignMapInd^;  will crash if it's not campaign
  !!IF:M^%v1^;

[+] Fixed transferring of WoG commanders with heroes in campaigns. Previously transferring didn't work if hero was inactive in transition zone.
    "OnTransferHero" is called for all transferred heroes, even for inactive ones, which will be used in other zones.

[+] Added support for 32-bit colors in backgrounds of text items (rewritten Pcx16_FillRect).
[+] Disabled ALT + KEY system menu triggering in windowed mode. ALT key combinations can be freely used by scripts.
[+] Updated ERM editor.

[*] Fixed non-working "OnBeforeBattleReplay" and "OnAfterBattleReplay events". Newest "BattleReplay" plugin by igrik is required.
    After battle end when user clicks "Cancel" button, "OnBeforeBattleReplay" is generated. Battle state is reset and "OnBattleReplay" event
    is generated, where you can revert global variables to pre-battle state, because OnBeforeBattleUniversal will not be called twice.

[*] Renamed "OnTownHallMouseClick" to more accurate "OnTownFortMouseClick".

[!] SN:Q is deprecated and shoudn't be used for new scripts because it may break any ERM library/mod/script functionality.
    ERM interpreter and Era Erm Framework were updated to support SN:Q in old scripts.
    If an event has at least single Lua/Erm/plugin handler, whenever it ends or SN:Q is called, an "OriginalEventName_Quit" trigger is called with the same x-arguments.
    In quit triggers SN:Q works as FU:E.

    Example:

    !?FU(OnAfterErmInstructions);
    !!FU(ex_OnSomeCustomEvent):P;

    !?FU(ex_OnSomeCustomEvent);
    !!IF:M^Trigger 1^;
    !!SN:Q; skip Trigger 2, trigger "ex_OnSomeCustomEvent_Quit" event

    !?FU(ex_OnSomeCustomEvent);
    !!IF:M^Trigger 2^;

    !?FU(ex_OnSomeCustomEvent_Quit);
    !!IF:M^Quit Trigger Handler^;
    !!SN:Q; works as FU:E here

    !?FU(ex_OnSomeCustomEvent_Quit);
    !!IF:M^Another Quit Trigger Handler^;

[-] Fixed bug with random input delay in text input controls.
[-] Fixed bug in Era Erm Framework: NewIntArray and NewStrArray function were ignoring (storageType) argument.
[-] Fixed bug in Era Erm Framework: mouse/keyboard event data was not restored on trigger end.
[-] Fixed invalid spells count for Thunder Lord in zcrtrait.txt. Credits: Archer30.
Bes, XEL, hippocamus, XEPOMAHT, Mefista, KypaToP_HM, Iriniko, Grossmaster
24 Jan 2021, 02:52 ERA III


Вышло обновления для HoMM 3 ERA
Текущая версия: 3.3.0

Кратко: цветные тексты с полупрозрачностью, корректным расчётом ширины, поддержкой азиатских языков и всех режимов HD-мода, а также возможностью ввода тегов в полях ввода; встраивание картинок и иконок в любые тексты, обновление игровых плагинов от igrik, новые наборы портретов монстров, множество новых функций, констант и событий для библиотеки ЕРМ, включая работу со временем, массивами, строками, каталогами, ini-файлами, монстрами и действиями в бою, загрузку настроек из json, работу с диалогами и подсказками; множественные исправления и улучшения в ЕРМ, включая исправления наиболее неприятных выявленных в процессе тестирования багов.

Реализована поддержка цветных текстов и языка разметки Эры в целом для всех режимов HD-мода.
Стал возможным ввод невидимых тегов в поля ввода с использованием символов "{" и "}". Реализация может измениться в будущем.
Реализована поддержка альфа-канала для цветных текстов с использованием синтаксиса {~RRGGBBAA}.
Значительно улучшена поддержки азиатских языков и текстов с несколькими языками, включая корректный перенос слов и расчёт ширины символов, слов и строк. Для китайского языка выбор файла шрифта происходит на основе размера оригинального игрового шрифта, а не имени файла в архиве.
Реализована возможность встраивать def-изображения в любые геройские тексты. Поддерживаются авто-обрезка, вертикальное выравнивание и возможность горизонтального отражения.
Обновлены плагины на исправление багов и родные диалоги от igrik.
В ресурсы включён файл "monprt44.def" с портретами монстров 44х44 от Bes. Кадры в def-файле отсортированы по идентификаторам монстров.
Добавлена поддержка обработки одиночных нажатий клавиши ALT.
Добавлено автосоздание каталогов "Runtime", "Games", "Random_Maps". Каталог "Runtime" предназначен для хранения настроек и данных, генерируемых скриптами и плагинами во время работы игры. Его очистка должна возвращать моды к чистому состоянию после установки.
Визуальное улучшение синтаксиса ЕРМ: нет нужды писать ":;", достаточно одной точки с запятой.
Добавлена команда для получения игрока-человека, сидящего за данным компьютером и команда для работы с адресами в оперативной памяти.
Новое событие "OnStartOrLoad" пригодится для выполнения действий при старте карты или загрузке сохранения.
Библиотека "Era Erm Framework" пополнилась сотнями новых констант для битовых масок, адресов игровых менеджеров, идентификаторов элементов диалогов и др.
Добавлены средства удобной обработки событий мыши и клавиатуры с сохранением в глобальных переменных всех необходимых для написания условий параметров.
Множество новых функций в библиотеке ЕРМ: упаковка и распаковка битовых флагов, перемешивание элементов в массивах, объединение массивов, получение срезов массивов, получение подстрок, получение списка файлов и папок в конкретных каталогах, чтение и запись ini-файлов, загрузка настроек из json-файлов прямо в глобальные переменные, получение лимитов монстров и героев, получение улучшенных и неулучшенных монстров, управление стрельбой отрядов в бою, сохранение игры, очистка экрана от сообщений чата, получение активных диалогов и отправка команд любому элементу диалога, перерисовка элементов диалога и управление подсказкой карты приключений.
События нажатия клавиши более не срабатывает при наличии фокуса в любом поле ввода. Ввод текстов в строке чата больше не мешает скриптам.
Ряд изменений и исправлений в ЕРМ командах.
Доработано событие установки подсказки для клетки или объекта при наведении курсора на карте приключений.
Исправлено порядка 10 ошибок в ресурсах игры, интерпретаторе и библиотеке ЕРМ.

Скачать: https://mods.hmm35.ru/Era%203.X.exe









Код
Version 3.3.0 (01/2021)
------------------------
[+] Implemented support for colored texts and Era Markup Language in general for all HD mod modes now.
[+] It became possible to enter invisible tags in edit fields using "{" and "}". This behavior may be changed in future.

[+] Implemented transparency support for colored texts using {~RRGGBBAA}...{~} tags, where AA stands for alpha channel, which determines text opaqueness. 0 means transparant, 255 is fully opaque, $80 is 50% transparent. Old-style tags in {~RRGGBB} format works as fully opaque.

Example: !!IF:L^{~FF0000}{~FF0000C0}{~FF000080}{~FF000040}You've{~} found{~} some{~} gold{~}^;

[+] Greatly improved European, Asian and mixed language colored texts support, including valid characters/words/lines width calculation and word-wrapping.
[+] Chinese font detection depends on H3 font size from now, not on H3 font file name.

[+] Added support for displaying inline def-images right in texts as a part of Era Markup Language (EML).

  To embed image in text use the following tags:
  {~>def_name.def}                          Will display the first frame from the first group of def_name.def image in place of text cursor.
  {~>def_name.def:frame_index}              Will display specified frame from the first group of def_name.def image or nothing if index is invalid.
  {~>def_name.def:group_index:frame_index}  Will display specified frame from specified group of def_name.def image or nothing if index is invalid.

  Frames and frame groups are counted from 0. Frames are automatically trimmed.
  By default images are rendered "inline". It means, that they are treated as non-wrapping sequence of white space characters. Images do not allocate
  vertical space except the height of current font. But they automatically allocate necessary width.

  Images can be aligned vertically using the following attribute: valign=top|middle|bottom.
  Examples:
    {~>ava0037.def valign=bottom}
    {~>smalres.def:5}

  Vertical alignment modes:
  - 'top'.    Image is drawn from the top left pixel of current character box.
  - 'middle'. Image is vertically centered relative to current text line height. This is the default mode for inline images.
  - 'bottom'. Image is drawn so, that it's bottom edge matches current text line bottom edge.

  It's possible to display image in a horizontally mirrored form. Just add "mirror" attribute.
  Example: {~>ava0037.def mirror}

[+] Updated "game bug fixes extended" plugin by igrik:
  - Removed screen redraw when AI visits teleports if "do not show enemy movement" option is on.
  - Stack experience marks are drawn in leave/join creature dialogs, but only for hero slots.
  - Fixed bugs caused by ALT usage during stack combining in leave/join creature dialogs.
  - Other fixes.

[+] Updated "wog native dialogs" by igrik:
  - Removed possibility to show settings window from main menu by F5 key. Removed automatical MAX selection in creature recruiting dialogs.
  - It's possible to select pictures in native H3 selection dialogs using keyboard arrow keys LEFT and RIGHT.
  - Leaving monsters/artefacts on map is trigged by CTRL + RMB instead of single RMB now.

[+] Included "monprt44.def" def with 44x44 monster portraits, sorted by monster ID. Credits: Bes.

[+] Event "onKeyPressed" now handles ALT key.

[+] Added "Runtime" directory to Heroes 3 directory. Mods should read/write data, created or modified at runtime there.
    If you need config, that player will be able to alter using GUI interface, read data from "Runtime\you mod.ini", fallbacking to json config values from "Lang" directory. Thus cleaning "Runtime" directory will have the same effect as reinstalling all mods from scratch.

[+] 'Runtime', 'Games' and 'Random_Maps' directories are recreated automatically on game start.

[+] ERM syntax can be safely beautified for all Era 3.X versions by skipping trailing ":" before ";".
  !!re 0/7/1;
    ...
  !!en;

  !!if&(heroId)=(HERO_XERON);
    ...
  !!en;

[+] Restored VR:S?$ syntax support from Era 2.

[+] Extended !!OW:C command with the following syntax: OW:C?(owner)/?(thisPcOwner).
    It became possible to get not only current player, who may play at remote PC, but also this PC human player, who possibly waits for his turn and triggers interface events.

[+] Added new ERM command SN:B to work with binary buffers on a low level. It allows to:
    - get address of local or static global ERM variable;
    - read/write integer/string from/to specific address.

    !!SN:B(intAddress) or ?(intVar) or (strVar) or ?(strVar)[/?(addressValue) or (dummy)/$valueAtAddress]

    The first argument determines variable address to work with. For strings it's always first string character address, regardless GET/SET syntax.
    For floats/ints SET syntax mean value of variable as address. GET syntax means address of specified variable.

    !!VR(test:y):S8943200;
    !!SN:B(test);  means use 8943200 as address
    !!SN:B?(test); means use address of (test) y-variable.

    !!VR(text:z):S^hello world^;
    !!SN:B(text);  means use address of (text) first character
    !!SN:B?(text); means use address of (text) first character too.

    Example:
    Let us declare integer y-variable and determine its address to use with external API function.
    !!VR(fileHandle:y):S(INVALID_HANDLE_VALUE);
    !!SN:B?(fileHandle)/?(fileHandleAddr:y); (fileHandlerAddr) is now address of (fileHandle) variable.

    Let us read last savegame name from H3 static buffer
    !!SN:B(ADDR_MARKED_SAVEGAME_NAME)/d/?(lastSavegameName:z);
    !!IF:M^You last savegame name was %(lastSavegameName)^;

[+] Added new events to "Era Erm Framework" mod:

  - "onStartOrLoad": occures after map start or savegame is loaded. Safe alternative to "OnGameStart", which is triggered before adventure map display.
  The event occurs after (OnAfterErmInstructions, OnAfterErmInited) and after (OnAfterLoadGame) event.
  The only argument is (isNewGame:x), which is (TRUE) for map start and (FALSE) for map loading.

[+] Added many new constants to "Era Erm Framework" mod for bits, bit masks, game managers addresses, dialog item ids, etc.

[+] The following improvements were introduced in "Era Erm Framework" mod:
  
  - "onKeyPressed" event and all mouse click events were improved, storing keyboard special keys in global variables.
  i^key^:            Pressed key virtual key code (not scan code) for "onKeyPressed" event only. Use KEY_XXX constants for it.
  i^key_leftAlt^:    TRUE if left ALT is pressed.
  i^key_rightAlt^:   TRUE if right alt is pressed.
  i^key_alt^:        TRUE if any alt is pressed.
  i^key_leftCtrl^:   TRUE if left control is pressed.
  i^key_rightCtrl^:  TRUE if right control is pressed.
  i^key_ctrl^:       TRUE if any control is pressed.
  i^key_leftShift^:  TRUE if left shift is pressed.
  i^key_rightShift^: TRUE if right shift is pressed.
  i^key_shift^:      TRUE if any shift is pressed.

  - All mouse click events were improved, storing event parameters in global variables.
  i^mouse_x^:         Cursor x-coordinate in game window.
  i^mouse_y^:         Cursor y-coordinate in game window.
  i^mouse_battleHex^: Battle hex ID for battle clicks.
  i^mouse_flags^:     Mouse flags mask: set of MOUSE_FLAG_XXX constants.
  i^mouse_hero_0^:    Hero screen hero ID or hero meeting screen left hero ID.
  i^mouse_hero_1^:    Hero meeting screen right hero ID.
  i^mouse_item^:      Clicked dialog item ID (CM:I). See ITEM_XXX constants.
  i^mouse_mapX^:      Map tile x-coordinate.
  i^mouse_mapY^:      Map tile y-coordinate.
  i^mouse_mapZ^:      Map tile z-coordinate.
  i^mouse_action^:    Action ID. One of MOUSE_XXX constants like MOUSE_LMB_RELEASED or MOUSE_RMB_PRESSED.

  Examples:
  !?FU(onKeyPressed_AdvMap)&i^key^=(KEY_F)/i^key_ctrl^=(TRUE);
  !!IF:M^CTRL+F on adventure map!^;

  !?FU(OnAdventureMapRightMouseClick)&i^mouse_item^=(ITEM_ADVMAP_HERO_LIST_MOVE_BAR_2)/i^mouse_action^=(MOUSE_RMB_PRESSED)/i^key_ctrl^=(TRUE);
  !!IF:N(NO_PIC_TYPE)/(NO_PIC_TYPE)/(NO_PIC_TYPE)/(NO_PIC_TYPE) N(MSG_TYPE_POPUP)/^ctrl + RMB on the second hero move bar!^;

[+] Added the following functions to "Era Erm Framework" mod:

  !?FU(GetTimeMsec);
; Returns current time in milliseconds (time from computer start, overflowing each 49.71 days)
  !#VA(result:x);

  !?FU(PackUnion);
; Safely packs union fields into single 32-bits integer, allowing to store multiple values in a single variable.
; Arguments are pairs of (field value, field size in bits). The first field is written at bit 0-th position.
; The last argument is result.
; Example: P(x)/8/ (y)/8/ (z)/8/ (heroId)/8/ ?(result:y);

  !?FU(UnpackUnion);
; Safely unpacks single 32-bits integer value into multiple field values.
; The first argument is packed value.
; Other arguments are pairs of (?field value, field size in bits). The first field is read at bit 0-th position.
; Example: P45683/ ?(x:y)/8/ ?(y:y)/8/ ?(z:y)/8/ ?(heroId:y)/8;

  !?FU(Array_Shuffle);
; Randomly shuffles all items in the list.
  !#VA(list:x); Array ID.

  !?FU(Array_Merge);
; Given destination array and arbitrary number of source arrays. Appends all items from all source arrays
; to the destination array.
; Example. Given listA = [100, 200, 300], listB = [500, 600]. P(listA)/(listB) => [100, 200, 300, 500, 600]
  !#VA(dstArray:x);          Destination array to append new items to.
  !#VA(firstArrayToMerge:x); ... Arrays to merge with the first one

  Examples:
  !!FU(NewStrArray):P?(listA:y);
  !!FU(Array_Push):P(listA)/^one^/^two^/^three^;
  !!FU(NewStrArray):P?(listB:y);
  !!FU(Array_Push):P(listB)/^wog^/^era^;
  !!FU(Array_Merge):P(listA)/(listB)/(listB);
  !!FU(Array_Join):P(listA)/?(text:z)/^ ^;
  !!IF:M^%(text)^; "one two three wog era wog era"

  !?FU(Array_Slice);
; Returns part of original array as new trigger-local array.
  !#VA(list:x);   Array to get slice of.
  !#VA(start:x);  Initial index, starting from zero. Negative offset means 'from the end'.
  !#VA(count:x);  Number of items to copy. Negative value means "skipping" that number of items from list end.
  !#VA(result:x); Result array.
  !#VA(arrayStorageType:x); OPT. Special storage type for result like M_STORED. Default: M_TRIGGER_LOCAL.

  Examples:
  !!FU(NewStrArray):P?(listA:y);
  !!FU(Array_Push):P(listA)/^one^/^two^/^three^/^four^/^five^;
  !!FU(Array_Slice):P(listA)/-4/-1/?(listB:y);
  !!FU(Array_Join):P(listB)/?(text:z)/^ ^;
  !!IF:M^%(text)^; "two three four"

  !?FU(Substr);
; Returns substring from existing string.
  !#VA(strPtr:x); Original string.
  !#VA(start:x);  Initial offset, starting from zero. Negative offset means 'from the end'.
  !#VA(count:x);  OPT. Number of characters to copy. Negative value means "skipping" that number of characters from string end.
  !#VA(result:x); Result substring.

  Examples:
  !!VRs^message^:S^Have a nice day dear Perry^;
  !!FU(Substr):Ps^message^/-5/(INT_MAX)/?s^submessage^; copy up to 5 characters from the end
  !!IF:M^%s(submessage)^; "Perry"

  !!VRs^message^:S^Have a nice day dear Perry^;
  !!FU(Substr):Ps^message^/5/(INT_MAX)/?s^submessage^; copy, skipping the first 5 characters
  !!IF:M^%s(submessage)^; "a nice day dear Perry"

  !!VRs^message^:S^Have a nice day dear Perry^;
  !!FU(Substr):Ps^message^/5/-6/?s^submessage^; copy from 6-th character to the end, not including the last 6 characters
  !!IF:M^%s(submessage)^; "a nice day dear"

  !?FU(ScanDir);
; Reads directory contents, filling specified list with file names.
; Example: P^Np3^/(fileList)/(SCAN_FILES_ONLY);
  !#VA(dirPathPtr:x); Absolute or relative path to directory to scan.
  !#VA(fileList:x);   ID of array to store file names in.
  !#VA(itemsType:x);  OPT. Type of items to collect: files, directories or both. One of SCAN_XXX constants. Default: SCAN_FILES_AND_DIRS.
  !#VA(fullPaths:x);  OPT boolean. If true, result items will be have dirPath predended. Default: false.

  !?FU(SaveIni);
; Saves ini file, if it was earlier cached in memory (any read/write operation was performed).
  !#VA(filePathPtr:x); Absolute or relative path to ini file
  
  !?FU(WriteIniInts);
; Writes multiple integer values to ini file in memory, but postpones saving data to disk. Call "SaveIni" to flush cached data.
; Example: P^Runtime/my mod.ini^/^hero levels^/(HERO_ORRIN)/13/(HERO_XERON)/41;
  !#VA(filePathPtr:x);    Absolute or relative path to ini file
  !#VA(sectionNamePtr:x); Section name in ini file.
  !#VA(firstKeyPtr:x);    ... Up to 7 key, value pairs to write.
  !#VA(firstValue:x);
  
  !?FU(WriteIniStrings);
; Writes multiple string values to ini file in memory, but postpones saving data to disk. Call "SaveIni" to flush cached data.
; Example: P^Runtime/my mod.ini^/^custom hero names^/^%(HERO_ORRIN)^/^Perrin R^/^%(HERO_XERON)^/^Berson^;
  !#VA(filePathPtr:x);    Absolute or relative path to ini file
  !#VA(sectionNamePtr:x); Section name in ini file.
  !#VA(firstKeyPtr:x);    ... Up to 7 key, value pairs to write.
  !#VA(firstValue:x);
  
  !?FU(ReadIniStrings);
; Reads multiple string values from ini file or from memory if ini file was read/written to earlier.
; Example: P(filePath)/(sectionName)/^%(HERO_ORRIN)^/?(orrinName:z)/^Orrin^/^%(HERO_XERON)^/?(xeronName:z)/^Xeron^;
  !#VA(filePathPtr:x);    Absolute or relative path to ini file
  !#VA(sectionNamePtr:x); Section name in ini file.
  !#VA(firstKeyPtr:x);    ... Up to 4 (key, ?value, defaultValue) tripples to read.
  !#VA(firstValue:x);
  !#VA(firstValueDefault:x);

  !?FU(ReadIniInts);
; Reads multiple integer values from ini file or from memory if ini file was read/written to earlier.
; Example: P(filePath)/^hero levels^/^%(HERO_ORRIN)^/?(orrinLevel:y)/1/^%(HERO_XERON)^/?(xeronLevel:y)/1;
  !#VA(filePathPtr:x);    Absolute or relative path to ini file
  !#VA(sectionNamePtr:x); Section name in ini file.
  !#VA(firstKeyPtr:x);    ... Up to 4 (key, ?value, defaultValue) tripples to read.
  !#VA(firstValue:x);
  !#VA(firstValueDefault:x);

  !?FU(GetMaxMonsterId);
; Returns ID of the last supported monster in game.
  !#VA(result:x);

  !?FU(GetUpgradedMonster);
; Returns ID of upgraded monster or NO_MON if no upgrade exists.
  !#VA(monId:x);  ID of monster to get upgrade for.
  !#VA(result:x); OUT. ID of upgraded monster or -1.

  !?FU(GetDegradedMonCandidates);
; Returns temporary list of all monsters, which can be upgraded to specified monster.
; There may exist multiple monster, upgrading to the same type. Function performance is low.
  !#VA(monId:x);        Upgraded monster ID.
  !#VA(degradesList:x); ID of temporary SN:M array with degraded monster candidates.

  !?FU(BattleStack_Shoot);
; Forces one stack to shoot at another one.
  !#VA(attackerStackId:x) (defenderStackId:x);
  !!BM(attackerStackId):Z?(attackerStackStruct:y);
  !!BM(defenderStackId):Z?(defenderStackStruct:y);
  !!SN:E4453920/(CALLCONV_THISCALL)/(attackerStackStruct)/(defenderStackStruct);

  !?FU(GetMaxHeroId);
; Returns ID of the last supported hero in game.
  !#VA(result:x);

  !?FU(LoadIntGlobalsFromJson);
; Loads global mod/script settings from json config right into prefixed named global variables.
; Supports usage of any constant name instead of numbers in JSON. For example, you want to load
; json values "umt.randomizationIntervalDays" and "umt.playAltThemesSequently" to global variables
; i^umt_randomizationIntervalDays^ and i^umt_playAltThemesSequently^ and want to be able to write in json:
; "umt.playAltThemesSequently": "TRUE".
;
; Example: P^umt.^/^umt_^/^randomizationIntervalDays^/^playAltThemesSequently^;
  !#VA(jsonKeysPrefixPtr:x);   Name of json keys prefix like ^mix.globals.^ for {"mix": {"globals": { ... }}}
  !#VA(globalVarsPrefixPtr:x); Name of global variables prefix. Usually mod prefix like "mix_" or "umt_".
  !#VA(firstKeyNamePtr:x);     ... Up to 14 json key names to read and convert into global variables

  !?FU(SaveGame);
  !#VA(fileNamePtr:x);     File name without extension to save game to.
  !#VA(appendExtension:x); OPT boolean. If true, automatical extension will be appended to file name. Default: TRUE.
  !#VA(compressFile:x);    OPT boolean. If true, saved file is gzipped. Otherwise the file is written without compression. Default: TRUE.
  !#VA(saveToData:x);      OPT boolean. If true, saving is performed to Data directory instead of "Games" directory. Default: FALSE.
  !#VA(markInList:x);      OPT boolean. If true, saved game will be marked in Save/Load dialogs as selected. Default: TRUE.

  !?FU(ClearScreenLog);
; Clears green screen log messages

  !?FU(H3Dlg_GetRootDlg);
; Returns root dialog object or NULL. Most of the time it's Adventure Map dialog.
  !#VA(result:x);

  !?FU(H3Dlg_GetCurrentDlg);
; Returns topmost dialog object or NULL. It may be message box, custom dialog or any in-game dialog.
  !#VA(result:x);

  !?FU(H3Dlg_SendCmdToItem);
; Sends command to h3 dialog item like DL:A.
  !#VA(h3Dlg:x);      H3 dialog object address.
  !#VA(itemId:x);     Dialog item ID.
  !#VA(cmdSubtype:x); Command subtype. See DLG_CMD_XXX constants.
  !#VA(param:x);      User-specified value. Some numeric parameter or string in case of DLG_CMD_SET_TEXT.
  !#VA(cmdType:x);    Optional. Type of command/action. Default: (DLG_CMD_TYPE_DEFAULT)

  !?FU(H3Dlg_DrawItemOnScreen);
; WoG function, drawing dialog item or the whole dialog on the screen.
  !#VA(h3Dlg:x);
  !#VA(itemId:x); Dialog item ID or (ALL_ITEMS).

  !?FU(H3Dlg_UpdateItemRange);
; Sends update command (0/0) to dialog items in specified range. Additionally forces dialog to update its internal state.
; Use the function after sending commands to native H3 dialogs and before trying to redraw them.
  !#VA(h3Dlg:x);     H3 dialog object address
  !#VA(minItemId:x); Minimal item ID to update
  !#VA(maxItemId:x); Maximal item ID to update

  !?FU(AdvMap_SetHint);
; Immediately shows adventure map hint with new text. Chat box text may become hidden until new character input.
  !#VA(newHint:x); New hint string.

[+] onKeyPressed event does not occur anymore in dialogs where an input element has focus. It became possible to handle keyboard safely without routine checks for chat enter/leave events.

[+] Added GetProcessGuid exported function, allowing to retrieve unique 32-character ID of game process run.
    Each game process start will generate different value. Modders can use this value to check, whether player restarted the game process or not.
    
    procedure GetProcessGuid (Buf: pchar); stdcall;

    Usage:
    !!SN:F^GetProcessGuid^/?(processGuid:z);
    !!IF:M^%(processGuid)^;

[!] Be sure not to use stack experience commands for battle stacks in OnBeforeBattle(Universal) triggers. Use them starting from "OnSetupBattlefield" event.
[!] Starting from version 5.2 RC 14 HD mod does not influence Era "OnGameEnter" and "OnGameLeave" events, which work reliably now.

[!] HE:L command was rewritten to support #/^...^ Era 3 syntax. Automatical adventure map redrawing was removed.
    From now command supports any ERM string. HE:L3 does not need the second argument.

[!] Improved "OnAdvMapTileHint" event. It will not occur on RMB popup anymore and will have extended arguments:

  !?FU(OnAdvMapTileHint);
  !#VA(x:x) (y:x) (z:x);             Object entrance coordinates
  !#VA(objType:x) (objSubtype:x);    Type and subtype of object. For active hero it's object under hero.
  !#VA(tileX:x) (tileY:x) (tileZ:x); Real tile coordinates.

[*] "OnAdvMapTileHint" event objSubtype argument is -1 for no object instead of previous 65535.
[*] Exported function WriteStrToIni creates empty ini in memory if no file exists on disk.

[-] Fixed FU/DO argument skipping handling. Previosly continuous slashes were ignored and Px1/x2/x3//////x9/x10 didn't work as it was expected.
[-] Fixed Era 2.0 bug: calling SN:E with floating point result used to leave garbage value in FPU stack.
[-] Fixed WoG 3.58 bug: CO:A used to automatically execute CO:N# due to missing final 'break' keyword in the source code.
[-] Fixed Era bug: %Dm and %Dd results were displayed in place of each other.
[-] Fixed bug in Array_CustomSort, causing invalid final list items ordering.

[-] Fixed EA:E, command, used to return on the first GET-parameter. From now E?(exp:y)/d/?(monType:y)/?(monNum:y) returns valid data.
    Use either SET syntax for all 4 commands to change data or GET/mixed syntax to get data.

[-] Removed ini option "Debug.TrackErm.IgnoreRealTimeTimers". ERA does no trace triggers without handlers anyway.
[-] Fixed missing "botcasw.pcx" file by redirecting it to existing "botcastw.pcx" resource.
[-] Fixed un44.def dragon specialty frame.
Bes, XEL, hippocamus, magoth, Mefista, igrik, KypaToP_HM, Lokos
23 Dec 2020, 04:15 Эра Плюс
бонусы для платформы ERA
Нужно ставить задачи и достигать их. А с оглядкой на молчаливые ворчания и шагу не сделаешь. С релизом!
hippocamus, XEPOMAHT, Ethereal, Lokos, Raistlin
29 Nov 2020, 06:17 ERA III
geglov2, Leency, Bes, XEL, hippocamus, magoth, XEPOMAHT, Mefista, igrik, Zabuza-san, KypaToP_HM, Barin, Lokos, Iriniko, Grossmaster
19 Nov 2020, 02:08 Мод «Безлимит на музыку»
Unlimited Music Themes mod
Вышла вторая версия мода «Безлимит на музыку»
Текущая версия: 2.0.0

Требует: ERA 3.3+, Erm Framework Mod

Особенности:

Автоматически ищет аудиофайлы для музыкальных тем Героев 3 в каталоге Mp3 и вложенных подкаталогах. Игнорирует числовые суффиксы в именах файлов. Так, "dirt.mp3", "dirt007.mp3" и "dirt1000.mp3" будут добавлены в один плейлист темы "dirt" (грязевая почва).
Гибкий json-файл с настройками.
Интеллектуальное управление переключением треков для обеспечения максимального разнообразия и комфорта.

Скачать

Как работает мод?

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

Например, будут найдены:

dirt.mp3
WoW_Music/dirt007.mp3
Music_Pack/dirt02.mp3

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

Боевые темы и темы ИИ принудительно меняются для каждого боя или хода ИИ.

Мод поддерживает следующие настройки:
Код
"umt": {
  "randomizationIntervalDays": "1",    // Интервал в игровых днях, после которых нужно при возможности выбрать другую дорожку для каждой музыкальной темы
  "minThemePlaybackTime":      "40",   // Минимальное время в секундах, которое должна проигрываться тема до того, как иметь возможность быть сменённой на другую
  "playAltThemesSequently":    "TRUE", // Если 1, то темы меняются не на случайную, а последовательно от первого альтернативного трека к последнему в перемешанном плейлисте
  "treatCombatThemeSpecially": "TRUE", // Если 1, то боевые дорожки будут сменяться для каждого боя.
  "treatAiThemeSpecially":     "TRUE", // Если 1, то дорожки ИИ темы будут сменяться каждый раз после хода игрока-человека.
}


Предлагаю смотреть композиции Героев 2-5 и ранее выпущенных модов. Подбирать альтернативы можно к любой игровой теме.

Вышло обновление мода «Безлимит на музыку»
Текущая версия: 2.1.0

Требует: ERA 3.3+, Erm Framework Mod

Изменения:

Исправлена обработка ИИ темы.
Исправлено неверное название файла иконки для менеджера модов.
Удалено отладочное сообщение с названием текущей музыкальной темы.
Добавлены две новые опции для контроля того, стоит ли обрабатывать боевые и ИИ темы особенным образом (принудительно переключать треки для каждого боя или хода ИИ) или нет.

Скачать
hippocamus, magoth, Mefista, SerAlexandr, Doctor Tea, KypaToP_HM, Iriniko
16 Nov 2020, 05:11 Мод «Смешанные Нейтралы II»
Mixed Neutrals II mod
Вышло обновление мода Смешанные Нейтралы
Текущая версия: 2.1.0

Требует: ERA 3.3+, Erm Framework Mod

Изменения:

Реализована совместимость с воговским скриптом на замену объектов.
Реализовано распределение остатка боевой силы, полученного из округления вещественных размеров отрядов в сторону нуля, среди существующих слотов. Таким образом, если очков боевой силы не хватило на высокоуровневых монстров, возрастёт число низкоуровневых, сохранив совокупную боевую мощь нейтралов.
Добавлен скрипт-пример использования API, в котором реализованы опции классического диалога просмотра нейтралов и просмотра точной численного каждого отряда нейтралов.

Скачать
hippocamus, magoth, Mefista, M.A.K.C., Iriniko
16 Nov 2020, 02:28 Погиб Docent Picolan
Всё это очень печально. Мои соболезнования друзьям, членам семьи и команде. Лучшее, что можно сделать, помимо информационной поддержки, это завершить проект. Мы живём в наших детях, в нашем влиянии на окружающих людей, в нашем труде и творчестве.
hippocamus, XEPOMAHT, lion-killer, Kastore, Mefista, XMenik, zeryss, KypaToP_HM, Striker X Fenix, Iriniko, arblade_official, redar2013, Slavic boy, DOC'a, Aeternus, Elendion
09 Nov 2020, 20:08 Мод «Смешанные Нейтралы II»
Mixed Neutrals II mod
Вышла вторая версия мода Смешанные Нейтралы
Текущая версия: 2.0.0
По просьбе: Gary K

Требует: ERA 3.2+, Erm Framework Mod

Особенности:

Вместо однотипных нейтралов на карте размещены группы смешанных монстров. Огромное поле для настроек генерации через json и ЕРМ.
Мод может быть базой для пользовательских мини-модов. Предусмотрена поддержка других дополнений.
Скрипты имеют возможность повлиять на работу мода через ЕРМ обработчики. Например, реализовать просмотр конкретного числа монстров в каждом отряде, запретить потери нейтралов при побеге героя или написать свой генератор монстров.
Мод полностью написан на ЕРМ 2.0 и может быть использован в образовательных целях.

Скачать














magoth, Mefista, KypaToP_HM, Iriniko
09 Nov 2020, 17:50 ERA III


Вышло обновления для HoMM 3 ERA
Текущая версия: 3.2.0

Кратко: рост библиотеки ЕРМ в два раза, исправление багов в движке и плагинах, новые и исправленные ЕРМ команды, исправление картинок специализаций монстров, функции для форматирования чисел, дальнейшее развитие системы диалогов игры и др.

Отдельное спасибо Andarium за поддержку проекта.

Обновлены плагины "wog native dialog" и "game bug fixes" от igrik. Возможность удобной настройки секций ВоГ-опций через ini-файлы, поддержка настройки, какие картинки будут выбираемы в диалогах, исправление багов с блоком урона и автоклонированием существ.
Добавлены средства форматирования чисел с учётом локализации и соответствующие json-настройки.
Переработан файл un44.def (картинки специализаций существ): исправление и оптимизация кадров, палитры. Автор: Bes.
ЕРМ редактор обновлён. Добавлена поддержка автодополнения новых констант и событий.
В универсальный диалог с выбором до 8 картинок добавлена возможность делать часть картинок невыбираемыми для декоративных целей.
ERM функции, наконец-то, получили возможность возвращать строки из функций.
Разрешено повторное объявлений ЕРМ констант с одними и теми же значениям, что позволит модам под более старые версии движка использовать новые файлы с константами. Сами константы теперь записываются в сохраняемые игры.
Добавлены ЕРМ команда для приведения числа к фиксированному диапазону и команда для получения значения константы по имени во время выполнения скриптов.
Добавлено событие, срабатывающее, когда основные настройки для боя уже установлены и можно анализировать отряды противников.
В ERM библиотеку добавлена встроенное получение большинство параметров боя в глобальные переменные.
В ERM библиотеку добавлены функции для создания динамических массивов, добавления в них элементов и вытягивания элементов с конца массива, остановки и старта игровых анимаций, открытия произвольных всплывающих DL диалогов, изменения координат DL диалогов, выравнивания положения DL диалогов, форматирования чисел.
Исправлено ряд багов в движке Эры: IF:Q, FU:S, HookCode.
И др.

Скачать: https://mods.hmm35.ru/Era%203.X.exe

Код
Version 3.2.0 (11/2020)
------------------------
[@] Special thanks to Andarium for project support.

[+] Updated "wog native dialogs" plugin. Added support to override any zsetup00.txt part using json config files.
    See example of full WoG Options tabs/pages replacement in Mods/WoG/Lang/wog options.json.example.
    Added support for controlling, which pictures may be selected in IF:N-like dialogs.
    Fixed possible crashes, related to usage freed language data buffers. Credits: igrik.

[+] Updated "game bug fixes extended.dll" plugin by igrik. Fixed stack block damage ability bug and WoG experience creature cloning bug.

[+] Updated events and constants autocompletion files in Sublime Text Erm Editor.

[+] Included reworked un44.def file by Bes.

[+] Added support for d- syntax in function parameters.
    !!FU(edu_Test):Pd-200; will pass -200, previously 200

[+] Added locale settings to Lang/era.json:

  "era.locale.decimal_separator"  - separator of fractional part in numbers (like dot in 3.14 for English)
  "era.locale.thousand_separator" - separator of each 3 digits group in decorated numbers. It's recommended to use universal space for that. Example: "19 841".
  "era.locale.non_breaking_space" - space character, that is treated as part of the word and is not word-wrapped.
  "era.locale.metric_suffixes.0"  - quantity metric suffix for thousands like "K". Example number: "15.3K" for "15 300".
  "era.locale.metric_suffixes.1"  - quantity metric suffix for millions like  "M". Example number: "1.2M" for "1 200 000".
  "era.locale.metric_suffixes.2"  - quantity metric suffix for billions like "G". Example number: "1.06G" for "1 060 000 000".

[+] Improved Heroes 3 complex dialogs support. Credits: Berserker, igrik.
    IF:N(msgType)/^text^[/?result/(textAlignment)/(preselectedPicId)/(selectablePicsMask)].
      selectablePicsMask - bit mask of pictures, allowed for selection. Default value is -1 (all pictures).
    
    To make the first and the forth pictures selectable only specify mask 1 ^ 0 + 1 ^ 3 = 1 + 8 = 9.
    This setting allows some pictures to act as decoration only and the others to act as selectable items.

    Example:
   ; Let's display selection of two army types in the center and two resource costs at the edges.
   ; Monster pictures will be selectable, resource pictures will not be selectable.
    !!FU(ConstructBitMask):P(DLG_RESULT_PIC_2)/(DLG_RESULT_PIC_3)/?(selectablePicsMask:y);
    !!IF:N(PIC_TYPE_RES_CRYSTAL)/100/(PIC_TYPE_MONSTER)/(MON_CYCLOPS)/(PIC_TYPE_MONSTER)/(MON_EFREETI)/(PIC_TYPE_RES_SULFUR)/100;
    !!IF:N(MSG_TYPE_CHOOSE_PIC)/^What army do you want to call?^/?(choice:y)/(TEXT_ALIGN_CENTER)/(DLG_NO_SELECTION)/(selectablePicsMask);

[+] Added new events "OnBeforeBattleReplay" and "OnAfterBattleReplay", depending on third-party plugins like "BattleReplay" by igrik.
    The engine now handles "OnBeforeBattleReplay" to fix issues with battlefield obstacles generation.

[+] Duplicate constant declarations with the same value are allowed from now.

  !#DC(TRUE) = 1;
  !#DC(TRUE) = 1; does not produce error
  !#DC(TRUE) = 3; error: constant TRUE is already defined with value 1

[+] Added new ERM command VR:F in the form of !!VR(numericVar):F(minValue)/(maxValue).
    It's used to force value to be in specific range and can be used instead of ToRange, Min and Max math functions.
    All arguments must be of the same type.
    
    (numericVar) - any integer or float variable.
    (minValue)   - minimum range value (integer or float).
    (maxValue)   - maximum range value (integer or float).

    If range is invalid (minValue) > (maxValue), the result is (minValue).

    Examples:
    !!VR(value:y):S77 F10/100; force 77 to be in 10..100 range
    !!IF:M^%(value)^;          displays 77

    !!VR(value:y):S444 F10/100; force 444 to be in 10..100 range
    !!IF:M^%(value)^;           displays "100" (maximum possible value)

    !!VR(value:y):S-7 F10/100; force -7 to be in 10..100 range
    !!IF:M^%(value)^;           displays "10" (minimum possible value)

    !!VR(value:y):S4 F6/2; force 4 to be in invalid 6..2 range
    !!IF:M^%(value)^;      displays "6" (range start value is used in case of invalid range)

    !!VR(value1:y):S93;
    !!VR(value2:y):S50;
    !!VR(value1):F(INT_MIN)/(value2); value1 = minimum of (value1, value2)
    !!IF:M^%(value)^;                 displays "50" (the smallest of 2 values)

    !!VR(value1:y):S93;
    !!VR(value2:y):S50;
    !!VR(value1):F(value2)/(INT_MAX); value1 = maximum of (value1, value2)
    !!IF:M^%(value)^;                 displays "93" (the biggest of 2 values)

[+] Added possibility to call functions, returning float values using SN:F. Simply prepend dot (".") before function name.

[+] Added possibility to return strings from functions using P?(someStr) syntax.
    If (someStr) is string variable, then an appropriate x-argument is set to 0 before function execution.
    It's expected, that function will assign z-string index of result to x-argument. It can be local string,
    global string, trigger local string, ERT string. The value of this string will be assigned to (someStr) variable
    on function exit.

    Example:

    !?FU(test_AppendHeroName);
    !#VA(introTextPtr:x); text to append hero name to
    !#VA(resultPtr:x);    result string
    !!VR(result:z):Sz(introTextPtr) +^Corwin^;
    !!VR(resultPtr):Z(result); create trigger local variable with result and assign its index to resultPtr argument

    !?FU(OnAfterErmInstructions);
    !!VR(greetingBeginning:z):S^Hello, ^;
    !!FU(test_AppendHeroName):P(greetingBeginning)/?(greeting:z);
    !!IF:M^%(greeting)^; display "Hello, Corwin"

[+] Implemented saving and loading global constants in savegames.

[+] Added new ERM command SN:C(constantName)/?(constantValue)[/?(constantExists)]
  It allows to get constant value by name in runtime. It's possible to use constants in json configs, for instance.

  Short example:
  !!SN:C^OBJ_MONSTER^/?(constValue:y)/?(constExists:y);
  !!IF:M^OBJ_MONSTER = %(constValue). Constant exists: %(constExists)^; OBJ_MONSTER = 54. Constant exists: 1

  Let's allow to use constants in json configuration file for key 'edu.banned_obj_type'.
  !!VR(key:z):S^edu.banned_obj_type^;            Prepare key to load from json
  !!SN:T(key)/?(valueStr:z);                     Load translation for given key as string
  !!SN:C(valueStr)/?(value:y)/?(constExists:y);  Try to find constant with the same name as value
  !!VR(value)&(constExists)=(FALSE):V(valueStr); If no constant is found, convert string value to integer
  !!IF:M^edu.banned_obj_type = %(value)^;        Display loaded config value

[+] Added new constants to "Era Erm Framework" mod:
  - ARG_SYNTAX_GET, ARG_SYNTAX_SET, ARG_SYNTAX_ADD for FU:S argument syntax types.
  - Numerous other new constants.

[+] Added new events to "Era Erm Framework" mod:

  - "OnAfterBattleSetup", occuring right after "OnBeforeBattle" and "OnBeforeBattleUniversal" events.
  New event allows to be sure, that basic battle parameters (heroes, quick battle, coordinates) are set up.

[+] The following improvements were introduced in "Era Erm Framework" mod:
  
  - "OnBeforeBattle" and "OnBeforeBattleUniversal" events were improved, storing most of prebattle parameters in global variables.
  i^battle_isQuick^:       (TRUE) if quick battle is enabled, (FALSE) otherwise
  i^battle_x^:             Battle x-coordinate
  i^battle_y^:             Battle y-coordinate
  i^battle_z^:             Battle z-coordinate
  i^battle_owner_0^:       Left side owner or (NO_OWNER)
  i^battle_owner_1^:       Right side owner or (NO_OWNER)
  i^battle_hero_0^:        Left side hero or (NO_HERO)
  i^battle_hero_1^:        Right side hero or (NO_HERO). Any negative value is normalized into (NO_HERO)
  i^battle_ai_0^:          (TRUE) if left side is controlled by AI, (FALSE) otherwise.
  i^battle_ai_1^:          (TRUE) if right side is controlled by AI, (FALSE) otherwise.
  i^battle_human_0^:       (TRUE) if left side is controlled by human, (FALSE) otherwise.
  i^battle_human_1^:       (TRUE) if right side is controlled by human, (FALSE) otherwise.
  i^battle_remote_0^:      (TRUE) if left side is controlled by remote human, (FALSE) otherwise.
  i^battle_remote_1^:      (TRUE) if right side is controlled by remote human, (FALSE) otherwise.
  i^battle_local_0^:       (TRUE) if left side is controlled by local human or AI, (FALSE) otherwise.
  i^battle_local_1^:       (TRUE) if right side is controlled by local human or AI, (FALSE) otherwise.
  i^battle_localHuman_0^:  (TRUE) if left side is controlled by local human, (FALSE) otherwise.
  i^battle_localHuman_1^:  (TRUE) if right side is controlled by local human, (FALSE) otherwise.
  i^battle_hasHuman^:      (TRUE) if least one side is controlled by human, (FALSE) otherwise.
  i^battle_humanOnly^:     (TRUE) if all sides are controlled by humans, (FALSE) otherwise.
  i^battle_aiOnly^:        (TRUE) if all sides are controlled by AI, (FALSE) otherwise.
  i^battle_isVisible^:     (TRUE) if at least one side is human and quick battle is off, (FALSE) otherwise.
  i^battle_isNetwork^:     (TRUE) if it's network human vs human battle, (FALSE) otherwise.
  i^battle_type^:          Battle type bit mask: a collection of BATTLE_TYPE_FLAG_XXX constants.
  i^battle_current_side^:  Current/active stack battle side (BATTLE_LEFT = 0 or BATTLE_RIGHT = 1). Changes in "OnBeforeBattleStackTurn" and "OnBattleStackObtainsTurn" events.
  i^battle_current_stack^: Current/active stack ID. Changes in "OnBeforeBattleStackTurn" and "OnBattleStackObtainsTurn" events.
  i^battle_acting_stack^:  ID of stack, performing action. It's set in "OnBeforeBattleAction" only.
  i^battle_acting_side^:   Side (BATTLE_LEFT = 0 or BATTLE_RIGHT = 1) of stack, performing action. It's set in "OnBeforeBattleAction" only.

  - i^battle_round^ keeps current valid round and can be used throughout battle triggers and in OnBattleRound condition
  like !?FU(OnBattleRound)&i^battle_round^=0 instead of v997.

[+] Added the following functions to "Era Erm Framework" mod:

  !?FU(NewIntArray);
; Creates and returns trigger local array of integers.
; Alternative function arguments:
;  (?result)                     The result array will have 0 items.
;  (size)/(?result)              The result array will have (size) items with 0 value.
;  (size)/(fillValue)/(?result)  The result array will have (size) items will (fillValue) value
;  You may optionally specify (storageType) parameter after (?result) argument with value like M_STORED or M_TEMP.
  
  !?FU(NewStrArray);
; Creates and returns trigger local array of strings.
; Alternative function arguments:
;  (?result)                     The result array will have 0 items.
;  (size)/(?result)              The result array will have (size) items with icon6.gif value.
;  (size)/(fillValue)/(?result)  The result array will have (size) items will (fillValue) value
;  You may optionally specify (storageType) parameter after (?result) argument with value like M_STORED or M_TEMP.

  !?FU(Array_Push);
; Adds new items to the end of the array, resizing it automatically.
  !#VA(list:x);      ID of array to push items to
  !#VA(firstItem:x); ... Up to 15 arguments to append to list

  !?FU(Array_Pop);
; Removes items from the end of the array one by one, returning their values and resizing array automatically.
; At least single item is removed from the array, if possible.
; Example: P{list}/?{lastItem}/?{beforeLastItem}.
  !#VA(list:x);      ID of array to pop items from.
  !#VA(firstItem:x); OUT parameters... Up to 15 arguments to pop from the list. If item cannot be popped, it will be assigned zero value or empty string.

  -------- EXAMPLES ---------

  !!FU(NewStrArray):P?(list:y);                                            create trigger-local string array
  !!FU(Array_Push):P(list)/^igrik^/^PerryR^/^Panda^;                       fill it with 3 values
  !#VA(items[4]:z);                                                        declare array of 4 local z-strings
  !!FU(Array_Pop):P(list)/?(items[0])/?(items[1])/?(items[2])/?(items[3]); pop items from array one by one
  !!IF:M^%(items[0]) %(items[1]) %(items[2]) %(items[3])^;                 displays "Panda PerryR igrik "
                                                        ;                 now (list) contains no items
  ------ END EXAMPLES -------

  !?FU(H3Dlg_StopAnimation);
; Stops current dialogs animation
  
  !?FU(H3Dlg_ResumeAnimation);
; Resumes stopped dialogs animation
  
  !?FU(H3Dlg_ShowPopup);
; Shows H3 dialog as RMB popup.
  !#VA(h3Dlg:x); H3 dialog object address

  !?FU(H3Dlg_Coords);
; Allows to access H3 dialog display coordinates. Automatically fixed invalid coordinates.
  !#VA(h3Dlg:x); H3 dialog object address.
  !#VA(x:x);     X-coordinate, supports GET/SET/ADD syntax
  !#VA(y:x);     Y-coordinate, supports GET/SET/ADD syntax
  
  !?FU(DL_FindById);
; Returns DL dialog object address by DL id or (NULL) .
  !#VA(dlgId:x);
  !#VA(result:x);
  
  !?FU(DL_Destroy);
; Destroys DL dialog object.
  !#VA(dlgObj:x);
  
  !?FU(DL_ShowPopup);
; Shows DL dialog as RMB popup.
; The dialog will be destroyed after showing. Call DL:N again to recreate it.
; © GrayFace
  !#VA(dlgId:x); DL dialog ID.

  Example:
  !?FU(OnAdventureMapRightMouseClick);
  !!CM:R(FALSE);           disable default reaction
  !!DL89:N^cmenu.txt^;     load custom DL dialog
  !!FU(DL_ShowPopup):P89;  display DL dialog while right mouse button is holded

  !?FU(DL_Coords);
; Allows to access DL-dialog display coordinates. Call DL:N before trying to access coordinates.
; © igrik
  !#VA(dlgId:x); DL dialog ID
  !#VA(x:x);     X-coordinate, supports GET/SET/ADD syntax
  !#VA(y:x);     Y-coordinate, supports GET/SET/ADD syntax

  !?FU(DL_GetSize);
; Returns DL-dialog width and height.
  !#VA(dlgId:x);  DL dialog ID
  !#VA(width:x);  OUT. Dialog width
  !#VA(height:x); OUT. Dialog height

  !?FU(DL_AlignDlg);
; Aligns dialog display position. Call DL:N before trying to use this function.
  !#VA(dlgId:x);     DL dialog ID
  !#VA(alignment:x); Bit-mask of TEXT_ALIGN_XXX constants.

  !?FU(DecorateInt);
; Converts integer to string, separating each three digit group by "era.locale.thousand_separator" characer.
; Example: P74276689 => "74 276 689"
  !#VA(value:x);              Number to decorate.
  !#VA(resultPtr:x);          OUT. Result string.
  !#VA(ignoreSmallNumbers:x); Optional boolean. If set to DONT_DECORATE_SMALL_INTS, values <= 9999 are not decorated. Default: false.

  !?FU(FormatQuantity);
; Formats given positive or negative quantity to human-readable string with desired constraints on length and maximal number of digits.
; Uses game locale settings and metric suffixes like "K", "M" and "G".
; Example: P-1234567890/6/4 => "-1.23G"
  !#VA(value:x);     Quantity to format.
  !#VA(resultPtr:x); OUT. Result string.
  !#VA(maxLen:x);    Optional. Maximum desired string length in logical characters. Default: 5.
  !#VA(maxDigits:x); Optional. Maximum number of digits to use in result (the more digits to display, the slower the number is read by humans). Default: 4.

[+] Changed the following functions in "Era Erm Framework" mod:

  !?FU(Array_Join);
; Concatenates array items into single string, using passed glue string. Works with both numeric and string arrays.
; Example: ['one', 'two', 'three'] with glue ' --- ' become 'one --- two --- three'.
  !#VA(list:x);      Array ID.
  !#VA(resultPtr:x); OUT. Result string
  !#VA(gluePtr:x);   Optional. Glue string. Default: ''.

  !?FU(GetStrAtAddr);
; Reads null terminated string at specified address into s^result^ variable.
; Null address (0) results in empty string.
  !#VA(strAddr:x);   Address of null-terminated string in memory or 0.
  !#VA(resultPtr:x); String variable, to copy string contents to.
  
  !?FU(StrToUpper);
; Converts given string to upper case.
  !#VA(strPtr:x);    Source string.
  !#VA(resultPtr:x); OUT. Result string.
  
  !?FU(StrToLower);
; Converts given string to lower case.
  !#VA(strPtr:x);    Source string.
  !#VA(resultPtr:x); OUT. Result string.

  !?FU(MonCountToFuzzyText);
; Converts monster quantity to stringish value range like "50-99" or "2K+" with maximum length restriction.
; Example P777/?{result}/(MON_FUZZY_COUNT_SHORT) => "500-999".
  !#VA(monNum:x);         Number of monsters to convert to text.
  !#VA(resultPtr:x);      OUT. Result string
  !#VA(maxTextLength:x);  Optional. Result length restriction in the form of MON_FUZZY_COUNT_XXX constant. Default: MON_FUZZY_COUNT_SHORT

[+] Added exported function "ToStaticStr" ({n} Str: pchar): {n} pchar;
    It accepts pointer to null-terminated string or null. Returns null on null argument. Otherwise returns permanent static string address for given string contents.
    The result is always the same for the same string contents. The result is read only and will never be deallocated.

    The function serves two purposes:
    - Convert string from temporary buffer into static buffer with endless lifetime without wasting memory for
      multiple calls for the same string contents.
    - The result can be treated as unique string hash/ID. Thus comparing two results of "ToStaticStr" can be
      performed using pointers only.

    For instance, you write plugin, where you need static string addresses for dialog items, hints, in-game structures.
    You get those string from json language file and want to support F12 reloading key.
    Simply use ToStaticStr(tr(...)). If translation is not changed during the game, ToStaticStr will return the same buffer
    addresses for the same string contents. Otherwise memory cunsumption will be growing, but F12 key will work well.
    No crashes, no dangling pointers.

[+] Added exported function "DecorateInt", which converts integer to string, separating each three digit group by "era.locale.thousand_separator" character.
    function DecorateInt (Value: integer; Buf: pchar; IgnoreSmallNumbers: integer): integer; stdcall;

    Returns final string length in bytes.
    Specify IgnoreSmallNumbers to leave values <= 9999 as is. Uses game locale settings.
    Example: 2138945 => "2 138 945"

[+] Added exported function "FormatQuantity", which formats given positive or negative quantity to human-readable string with desired constraints on length
    and maximal number of digits. Uses game locale settings and metric suffixes like "K", "M" and "G".

    function FormatQuantity (Value: integer; Buf: pchar; BufSize: integer; MaxLen, MaxDigits: integer): integer;

    Returns final string length in bytes;
    MaxLen    - maximum desired string length in logical characters.
    MaxDigits - maximum number of digits to use in result (the more digits to display, the slower the number is read by humans).
    Optimal settings, for damage or neutrals quantity, for instance, will be MaxLen = 5, MaxDigits = 4.

    Examples:
     FormatQuantity(1234567890, 10, 10) = '1234567890'
     FormatQuantity(-1234567890, 6, 4)  = '-1.23G'
     FormatQuantity(123, 2, 4)          = '0K'
     FormatQuantity(1234567890, 6, 2)   = '1G'
     FormatQuantity(1234567890, 1, 2)   = '9'
     FormatQuantity(1234567890, 1, 0)   = ''

[*] Restored old IF:Q functionality for message types MSG_TYPE_CHOOSE_PIC and MSG_TYPE_CHOOSE_PIC_OR_CANCEL: the third picture cannot be selected.
[*] Trigger-local strings and array lifetime was increased. Such items are disposed only after the whole chain of same trigger handlers is processed.
[*] Changed zcrtrait.txt: Santa Gremlin Fight Value and AI Value changed from 500 to 300. Removed "Can gift" from description.

[*] Totally disabled old buggy "OnBattleRound" event behavior. From now "OnBattleRound" is an alias of "OnCombatRound".
    v997 contains valid battle round throughout the whole battle. Do not use "OnCombatRound" in plugins, it's an alias for
    ERM only. Use "OnBattleRound" instead.

[*] (TRUE) and (FALSE) ERM constants are now predefined.

[-] Fixed re/FU/DO/OB/...dozens of commands... didn't support global named variables in receiver parameters.
    Examples:
    !!FUi^edu_someFunc^:P;
    !!OBi^edu_x^/i^edu_y^/i^edu_z^:T?(objType:y);

[-] Fixed bug: FU:S used to return corrupted values.
[-] Fixed bug in HookCode: hooking short jumps resulted in memory corruption.
[-] Fixed IF:Q with message type 7 (MSG_TYPE_CHOOSE_PIC): result is now valid 1/0 flag, not 1/2 value, as it was before.
[-] Fixed "Cornucopia" artefact name in artevent.txt. Credits: Valery (Salamandre).
Bes, magoth, Mefista, igrik, KypaToP_HM, Iriniko, arblade_official
22 Oct 2020, 02:37 ERA III


Вышло обновления для HoMM 3 ERA
Текущая версия: 3.1.1

Кратко: играбельные санта-гремлины, новейшие плагины от igrik, качественный генератор случайных чисел и обновление библиотеки ЕРМ.

Санта-гремлины стали играбельным монстром. Нормальный еженедельный прирост (16) вместо ежедневного, отмена подарков, урон ледяной стрелы = 10 * число сант. Итог: отличный третий апгрейд для мастер-гремлинов.
В установщик включена новейшая версия плагина исправления багов игры от igrik. Из последнего: исправлены вылеты из-за некорректной установки стены огня при атаке пожарами. Исправлены ошибки и в уже включённых плагинах.
Добавлены две новые опциональные заплатки: запрет генерации тюрем на случайных картах и однослотовые комбо-артефакты.
Генератор случайных чисел, порой изрядно раздражающий игроков, заменён на современный алгоритм «Вихрь Мерсена».
Библиотека ЕРМ дополнилась функциями для копирования и клонирования массивов, хэширования целых чисел, получения текстового описания размера нейтралов на карте и рядом других исправлений.

Скачать: https://mods.hmm35.ru/Era%203.X.exe

Код
Version 3.1.1 (10/2020)
------------------------
[+] Included updated "game bug fixes extended" plugin with many crash/overflow/bug fixes. Game stability increased. Credits: Ben, igrik, RoseKavalier and others.
    Old "game bug fixes" plugin by RoseKavalier was removed.

[+] Added "no prisons on random maps.bin.off" and "one slot combo arts.bin.off" patches by igrik.
    The first one disables prison generation on random maps. The second one makes combo artifacts to occupy one slot without possibility of further disassembling.

[+] Santa Gremlins now become a regular unit with normal weekly growth (16 per week), without gifts and with the following Ice Bold spell power:
    (Number of santas - 1) / 2 + Random(0, 1) if number of santas is even.

    Table of santa gremlin quantity and final damage:
    1 - 10
    2 - 10 or 30
    3 - 30
    4 - 30 or 50
    5 - 50
    6 - 50 or 70
    etc.

[+] Replaced Heroes 3 pseudo random number generator with high quality Mersenne Twister generator.
    Native generator is still used for battle obstacles generation and in multiplayer battles, excluding Hot Seat.

[+] Added new functions to "Era Erm Framework" mod:

  !?FU(Array_Copy);
; Resizes destination array to match source array size and copies all source items into destination array.
; Both arrays must have the same items type.
  !#VA(srcArray:x); ID of array to copy items from (source).
  !#VA(dstArray:x); ID of array to copy items to (destination).
  
  !?FU(Array_Clone);
; Creates trigger local copy of array.
  !#VA(srcArray:x); ID of array to clone.
  !#VA(result:x);   ID of result trigger local array.

  !?FU(Tm32Encode);
; Fast and reversable int32 hashing. Link: https://stackoverflow.com/questions/664014/what-integer-hash-function-are-good-that-accepts-an-integer-hash-key
  !#VA(value:x) (result:x);
  
  !?FU(Tm32Decode);
  !#VA(value:x) (result:x);

[+] Updated the following functions of "Era Erm Framework" mod:

  !?FU(MonCountToFuzzyText);
; Converts monster quantity to stringish value range like "50-99" or "2K+" of maximum 7 characters length.
; Returns result in s^result^
  !#VA(monNum:x);
  !#VA(withDescription:x); ?boolean. If true, the result will be native H3 text like "A pack (10-19) of". Default: false.

  !?FU(DeconstructBitMask);
; Deconstructs bit mask into list of bit/flag positions (each with 0..31 value).
; For example, P137/(list) will fill the list with [0, 3, 7] values, because
; 2 ^ 0 + 2 ^ 3 + 2 ^ 7 = 1 + 8 + 128 = 137. It means, that bits 0, 3 and 7 are set.
  !#VA(mask:x);   Bit mask.
  !#VA(result:x); Will contain new trigger local array ID with bit/flag positions.

[*] Removed type checking from SN:M(array)/(itemIndex)/(value), allowing to use integer addresses to set string item values.

[-] Fixed crash in "quest log" plugin by igrik.
Bes, hippocamus, magoth, Mefista, igrik, KypaToP_HM, Iriniko, arblade_official
20 Oct 2020, 02:58 ERA III


Вышло обновления для HoMM 3 ERA
Текущая версия: 3.1.0

Что нового ?



Обновлён плагин WoG-диалогов от igrik: добавлена поддержка диалога отображения текста с произвольной BMP/JPG картинкой (IF:B/P диалогов). Реализовано окно просмотра журнала боя по клавише "H" или ЛКМ на нижней панели в бою. Улучшена совместимость с плагинами от majaczek.
Обновлён плагин диалога просмотра заданий от igrik для совместимости с улучшенным движком игровых диалогов.
Реализована поддержка сложных диалогов с выбором до 8 картинок (здания, ресурсы, мана, монстры и т.д), возможностью предустановки выбранного элемента, управления выравниванием текста и типом диалога (сообщение, вопрос, всплывающая подсказка, выбор). Авторы: igrik, Berserker.
Существенно расширена библиотека ERM в виде поставляемого с Эрой мода: добавлено множество констант-идентификаторов (коды клавши, типы данных, опции WoG, игровые пределы, действия в бою, уровни магии, слоты артефактов и многое другое). Добавлено несколько удобных событий, таких как «после инициализации скриптов» и «нажатие клавиши в определённом игровом экране», а также более десятка вспомогательных функций.
Улучшен движок ЕРМ 2: использование констант в размерах локальных массивов, псевдонимы констант, приведение типов (целое - вещественное), возврат временных массивов из функций, передача локальных строк в функции, укороченные синтаксисы команд, удобный поиск объектов на карте и др.
Около десятка исправлений и изменений, включая защиту от переполнения опыта существ, корректный возврат клеток входа для объектов без сокрытия стоящих на них героев, возможность выбрать тип атаки монстра при игре в режиме Хот-Сит и др.

Скачать: https://mods.hmm35.ru/Era%203.X.exe

Код
Version 3.1.0 (10/2020)
------------------------
[+] Updated "wog native dialogs" plugin. Added support for IF:B/P dialogs and extended IF:Q/IF:N dialogs.
    Implemented advanced battle log dialog. To open it press "H" or click LMB on log bar in battle.
    Improved compatibility with majaczek's plugins. Credits: igrik.

[+] Updated "quest dialog" plugin. Provided compatibility with improved Heroes 3 dialogs. Credits: igrik.

[+] Implemented support for IF:Q with message type 7 (MSG_TYPE_CHOOSE_PIC) and 3-picture selection. The result is 1, 2, 3 or 0 for cancel.
    Prefer to use IF:N instead for better dialog control.

[+] Implemented extended complex dialogs support in ERM. Credits: igrik, Berserker.
    IF:N(msgType)/^text^[/?result/(textAlignment)/(preselectedPicId)].
    Display dialog with up to selectable 8 pictures.

    msgType           is one of MSG_TYPE_XXX constants (message, question, popup, picture selection with optional cancel button).
    textAlignment     is bit mask of TEXT_ALIGN_XXX flags. Both vertical and horisontal alignment are supported. -1 means "use default".
    preselectedPicId  is preselected picture index: 0-7 or -1 for none
    result            will contain -1 in most cases, (TRUE) or (FALSE) for questions, 0-7 (picture index) for picture selection and -1 for cancelled selection.

    Example:

    !?FU(OnAfterErmInstructions);
    !!IF:N(PIC_TYPE_SPELL)/(SPELL_TOWN_PORTAL)/(PIC_TYPE_RES_GOLD)/300/
          (PIC_TYPE_RES_WOOD)/5/(PIC_TYPE_RES_MERCURY)/10/(PIC_TYPE_RES_ORE)/15/
          (PIC_TYPE_RES_SULFUR)/20/(PIC_TYPE_RES_CRYSTAL)/25/(PIC_TYPE_MONEY)/5000;

    !!IF:N(MSG_TYPE_CHOOSE_PIC_OR_CANCEL)/^Take anything you need, bro!^/?(chosenItem:y)/(TEXT_ALIGN_LEFT);

    !!IF:M^%(chosenItem)^;

[+] IF:N and IF:Q dialogs with pictures now support special picture type flag: (PIC_TYPE_FLAG_DISPLAY_ZEROS).
    If it's set, zero quantities (resources, monsters, experience, etc) will be displayed like "0 Archangels" instead of "Archangels" or empty caption.

    Example:
    !!VR(picType:y):S(PIC_TYPE_EXPERIENCE) |(PIC_TYPE_FLAG_DISPLAY_ZEROS);
    !!VR(picSubtype:y):S0;
    !!IF:Q2/(picType)/(picSubtype)/(MSG_TYPE_QUESTION)/^Wanna nothing?^;

[+] Updated "Era Erm Framework" mod constants: data types, wog flags and options, town constants, game limits,
    magic levels, battle actions, hero artifact slots, dialog IDs, picture types, text alignment and many others.

[+] Added file "9999 era - key codes.erm" to "Era Erm Framework" with 150+ key codes constants.

[+] Added "OnAfterErmInited" event to "Era Erm Framework", occuring right in the end of !?PI / "OnAfterErmInstructions" event.
    The event allows to perform actions after most scripts initialized their variables and performed basic map/memory configuration.

[+] Added new events to "Era Erm Framework": "onKeyPressed_AdvMap", "onKeyPressed_Battle", "onKeyPressed_HeroScreen",
    "onKeyPressed_HeroMeetingScreen", "onKeyPressed_Town", occuring right after "onKeyPressed" events and taking two arguments:
    x1 - key code
    x2 - prevent default reaction (0 - no, 1 - yes).

    Example:
    !?FU(onKeyPressed_Battle)&x1=(KEY_F1):;
    !#VA(key:x) (preventDefault:x);
    !!VR(preventDefault):S(TRUE);
    !!IF:M^Pressed F1 in battle!^;

[+] SN:F now supports 'user32.dll' functions.

[+] Added new functions to "Era Erm Framework".
  !?FU(Array_SortedUnique);
; Leaves only unique sorted integer items in the array.
; Calling on [15, 4, 3, 3, 1, 20, 15] list will rearrange and truncate list to the following:
; [1, 3, 4, 15, 20]
  !#VA(list:x); Array ID

  !?FU(Array_EnsureMinSize);
; Checks, if array has at least specified minimal size and increasing the size if not, filling new items
; with optional default value.
  !#VA(list:x);      Array ID.
  !#VA(minSize:x);   Minimal desired array size.
  !#VA(fillValue:x); Optional. Fill value for new items. Default: icon6.gif or 0.

  !?FU(ConstructBitMask);
; Accepts up to 15 bit/flag positions (0..31). Returns mask with corresponding bit flags set.
; Actually, given Xi arguments, returns Sum(2 ^ xi).
; For example, P0/3/7/?(mask:y) will give 2 ^ 0 + 2 ^ 3 + 2 ^ 7 = 1 + 8 + 128 = 137.
  !#VA(args:x);   ... Up to 15 bit/flag positions.
  !#VA(result:x); The last argument will contain the result mask.

  !?FU(DeconstructBitMask);
; Deconstructs bit mask into list of bit/flag positions (each with 0..31 value).
; For example, P137/(list) will fill the list with [0, 3, 7] values, because
; 2 ^ 0 + 2 ^ 3 + 2 ^ 7 = 1 + 8 + 128 = 137. It means, that bits 0, 3 and 7 are set.
  !#VA(mask:x); Bit mask.
  !#VA(list:x); Array ID to fill with bit/flag positions.

  !?FU(MonCountToFuzzyText);
; Converts monster quantity to human readable value range like "50-99" or "2K+".
; Returns result in s^result^
  !#VA(monNum:x);

  !?FU(DisableErrors);
; Disables ERM error messages and resets error option.

  !?FU(EnableErrors);
; Enables ERM error messages and returns last error flag (TRUE or FALSE).
  !#VA(result:x);

  !?FU(StrToUpper);
; Converts given string to upper case. Result is returned in s^result^.
  !#VA(strPtr:x);
  
  !?FU(StrToLower);
; Converts given string to lower case. Result is returned in s^result^.
  !#VA(strPtr:x);

  !?FU(GetStrAtAddr);
; Reads null terminated string at specified address into s^result^ variable.
; Null address (0) results in empty string.
  !#VA(strAddr:x);

[+] Added Era exported function ShowErmError (Error: pchar); stdcall;
    The function shows regular ERM error dialog and can be used for ERM scripts error reporting and debugging.

    Example:

    !!if|(baseFaction)<(NO_TOWN)/(baseFaction)>(MIX_MAX_POSSIBLE_FACTION_ID):;
      !!SN:F^ShowErmError^/^Invalid "baseFaction" argument: %(baseFaction)^;
      !!FU:E;
    !!en;

[+] Added possibility to extend lifetime of trigger-local SN:M array to parent scope. It's now possible to return
    trigger-local arrays to caller function without necessity to free that array afterwards. Thus automatical memory
    management is preserved.

    Example:
   ; Deep level function returns trigger-local array of 3 strings to another function, which in its case returns the same array
   ; to "OnAfterErmInstructions" trigger. The array will be freed after "OnAfterErmInstructions" execution block ends.

    !?FU(FuncB);
    !#VA(result:x);
    !!SN:M(M_AUTO_ID)/3/(M_STR)/(M_TRIGGER_LOCAL)/?(result);
    !!SN:V(result)/0/^one^/^two^/^three^;
    !!SN:F^ExtendArrayLifetime^/(result);

    !?FU(FuncA);
    !#VA(result:x);
    !!FU(FuncB):P?(result);
    !!SN:F^ExtendArrayLifetime^/(result);

    !?(OnAfterErmInstructions);
    !!FU(FuncA):P?(arr:y);
    !!FU(Array_Join):P(arr)/^ ^;
    !!IF:M^%s(result)^; Display "one two three"

    !?(OnAfterErmInstructions);
   ; here the (arr) array is already deleted

[+] Added support for local z-strings as function parameters. They will be converted to temporary read-only z-variable indexes.
    
    Example:
    !!VR(str:z):S^haVe A nIce day!^;
    !!FU(StrToUpper):P(str); here z-1 will be converted into something like "10000002" which is z10000002 index
    !!IF:M^%s(result)^; Display "HAVE A NICE DAY!"

[+] Added possibility to define ERM 2 constant aliases.
    Example:

    !#DC(PIC_TYPE_RES_FIRST) = (PIC_TYPE_RES_WOOD);
    !#DC(PIC_TYPE_RES_LAST)  = (PIC_TYPE_RES_MITHRIL);

    Now (PIC_TYPE_RES_FIRST) will have the same value as (PIC_TYPE_RES_WOOD) constant.

[+] Added possiblity to use constants in local array declarations. Previously array size could be number only.
    Now it's possible to specify constant name instead of number without parenthesis.

    Example:
    !#DC(MAX_DWELLING_ALT_CREATURES) = 4;

    !#VA(dwellingMonTypes[MAX_DWELLING_ALT_CREATURES]:y); Define array of 4 items to hold dwelling monster types

[+] Added support for e-variables in VR:C. !!VR(floats[3]:e):C0/0/0;
    Do not forget, that no integer-float conversion is performed in VR:C, all values are copied as is. The only safe constant
    for e-variables is 0.

[+] Improved TR:T to allow any number of arguments.

[+] Improved UN:U command. It does not raise error if no more objects are found, but sets x-coordinate to -1 instead. Thus no premature
    objects counting is required. A new syntax with 6 parameters was added to allow using arbitrary integer variables instead of v-variables.
    !!UN:U(objectType)/(objectSubtype)/(direction like -1/-2 or object index)/(x)/(y)/(z).

    Example:
   ; Let's traverse through all map monsters, doubling their quantity

    !#VA(x:y) (y:y) (z:y); define variables to store object coordinates
    !!VR(x):S-1;           setting x-coordinate to -1 will force to start search from scratch
    
    !!re i; endless loop
      !!UN:U(OBJ_MONSTER)/(ANY_OBJ)/-1/(x)/(y)/(z); find next monster, (x) = -1 on failure
      !!br&(x)<0:;                                  exit loop if nothing found
      !!MO(x)/(y)/(z):Gd*2;                         double monsters quantity
    !!en:;

[+] Heroes 3 "DisplayComplexDialog" function (4F7D20) was improved. The last argument "closeTimeoutMsec" was overloaded to "Opts".
    Opts is:
    16 bits for closeTimeoutMsec,
    4 bits for msgType (1 - ok, 2 - question, 4 - popup, etc), // 0 is treated as 1.
    4 bits for text alignment bit mask (0..15),
    8 bits for internal H3 usage, usually 0

    Thus it's became possible to display dialogs with up to 8 images and of any type (message, question, popup, picture selection).

[+] Added exported function FindNextObject (ObjType, ObjSubtype: integer; var x, y, z: integer; Direction: integer): integer; stdcall;
    It works the same as UN:U with fast search syntax, but does not raise error on no more objects, returns success flag and allows
    to use non-v variables to store coordinates. You won't need to count objects before searching for them anymore.

    Direction is -1 for FORWARD and -2 for BACKWARD.

    Example:
   ; Let's traverse through all map monsters, doubling their quantity

    !#VA(x:y) (y:y) (z:y); define variables to store object coordinates
    !!VR(x):S-1;           setting x-coordinate to -1 will force to start search from scratch
    
    !!re i; endless loop
      !!SN:F^FindNextObject^/(OBJ_MONSTER)/(ANY_OBJ)/?(x)/?(y)/?(z)/-1; find next monster, v1 is (TRUE) on success
      !!br&v1=(FALSE):;                                                 exit loop if nothing found
      !!MO(x)/(y)/(z):Gd*2;                                             double monsters quantity
    !!en:;

[*] Local named e-variables are allocated from index 2 to preserve e1 for functions result.

[*] x16 can now be allocated as local named variable. Previosly the following code would lead to error:
    !!VA(args[16]:x);

[*] SN:G is DEPRECATED and may be removed in future versions.

[-] Fixed SN:O. No more boat/hero hiding.
[-] Fixed HE receiver to support any ERM variable like !!HEi^heroId^.
[-] Fixed VR:C indexes checking, allowing to override protected memory by commands like VRy-99:C1/2/3;

[-] Fixed ERM 2 compiler part, responsible for local z-arrays indexes allocation.
    Previosly !#VA(names[3]:z) used to allocate array of [z-3, z-4, z-5] (decreasing indexes).
    Now the appropriate array will be [z-5, z-4, z-3] (increasing indexes). Thus it's possible to use
    safely index arithmetics like:

    !#VA(names[3]:z);
    !!VR(names[2]):S^Have a nice day!^;
    !!VRi:S2;                     i is array item logical index
    !!VR(itemPtr:y):S(@array) +i; itemPtr holds real z-index of array item
    !!IF:M^%z(itemPtr)^;          display i-th item value

[-] Fixed UN:C. It didn't accept negative size argument, while -1, -2 and -4 are valid sizes.
    Prefer to use (UNC_XXX) constants to specify valid data type.

[-] Fixed creature experience overflow after battle. Credits: igrik.

[-] Fixed check for multiplayer in attack type selection dialog, causing wrong
    "This feature does not work in Human vs Human network baced battle" message.

[!] Note, that SN:O does not work with global named variables.

[!] Note, that v1 must not be used to store anything non-temporal, because from Era 2.X it's changed in every SN:E/SN:F call.
    It's a dirty variable for fast result return. Use v2/v3/v4 instead.
Bes, hippocamus, magoth, Mefista, igrik, KypaToP_HM, arblade_official
21 Sep 2020, 01:48 ERA III


Вышло обновления для HoMM 3 ERA
Текущая версия: 3.0.5

Что нового ?

Обновлён плагин WoG-диалогов от igrik: строки с переводом были вынесены в json, добавилась поддержка тонкой настройки шрифтов.
Исправлен патч для алтаря трансформации. Адские Гидры теперь преобразуются в костяных драконов, а для мумий возвращено оригинальное поведение.
Существенно доработан мод-основа на ЕРМ. Добавлена поддержка объединения, заполнения и сортировки массивов, расширено событие нового игрового дня и список игровых констант. Стал доступен ряд математических функций.
Исправлена 1 ошибка с отсутствующим портретом в редакторе карт, 2 ошибки модуля генерации отчётов по ЕРМ и 1 ошибка движка ЕРМ.
Обновлён ЕРМ редактор.

Скачать: https://mods.hmm35.ru/Era%203.X.exe

Код
Version 3.0.5 (09/2020)
------------------------
[+] Updated "wog native dialogs" plugin. All localized string were moved to json file.
    Added possibility to tune fonts, used in different dialogs. Credits: igrik.

[+] Updated "skeleton transformer fix.bin" patch. Hell Hydra is transformed into Bone Dragon.
    Returned original transformation for mummies. Credits: Bes.

[+] SN:V now supports negative indexes, meaning n-th from end, the same as SN:M.

[+] Added possibility to query SN:M arrays information.
    !!SN:M#1/(?)$2/(?)$3/?($4)[/?$5];
    #1 - array ID
    $2 - items count
    $3 - items type (0 - integers, 1 - strings)
    $4 - items storage type (-1 - trigger local, 0 - temporary, 1 - with savegame stored contents)
    $5 - unsafe temporary address of array first item in memory
    At least single #2..#4 parameter should use GET syntax. SET-syntax parameters are ignored in this case.

    Example:
    !!SN:M(array)/d/?(itemsType:y)/d; check if it's array of integers or strings
    !!if&(itemsType)=(M_INT):; ...

[+] Added new constants to "Era Erm Framework" mod:
  - TOWN_XXX constants for each town type in the game.
  - CALLCONV_XXX constants for possible SN:E calling conventions.
  - BATTLE_XXX constants for battle sides and stack limits.
  - FLOAT_INF and FLOAT_NEG_INF, representing infinity values for float numbers.
  Usage:
  !!VR(inf:e):C(FLOAT_INF);                   Assign positive infinity to (inf) variable without type conversion
  !!IF&(someValue)=(inf):M^Value is too big^; Check some e-var for positive infinity

[+] Extended OnEveryDay trigger in "Era Erm Framework" mod. The following global variables are automatically set:
    - i^timerDay^:        1..+inf
    - i^timerWeekDay^:    1..7
    - i^timerMonthDay^:   1..28
    - i^timerWeek^:       1..+inf
    - i^timerMonthWeek^:  1..4
    - i^timerMonth^:      1..+inf
    - i^timerOnce^:       0..1
    - i^timerOwner^:      0..7
    - i^timerIsAi^:       0..1
    - i^timerIsHuman^:    0..1

[+] Added mathemetical functions to "Era Erm Framework" mod.

  !?FU(Pow);
; Raises value to specified power. All arguments and result are floats.
; Example: 2^3 = 8, i.e. 2 * 2 * 2 = 8
  !#VA(base:x) (power:x) (result:x);

  !?FU(Sqrt);
; Returns value square root. All arguments and result are floats.
  !#VA(value:x) (result:x);

  !?FU(IntLog2);
; Returns Ceil(Log2(N)) or 0 for invalid values (<= 0).

  Examples:

  !!FU(IntLog2):P100/?(res:y);
  !!IF:M^%(res)^; displays 7, because 2^7 = 128 and 2^6 = 64
; It means that 7 bits are necessary to hold data with 100 possible values.
; It also means, that if one value is 100x greater than the other one, then
; it would take 7 multiplications by 2 before the second value will become >= the first one.

  
  !!VR(base:e):S123 :10; base = 12.3
  !!VR(power:e):S35 :10; power = 3.5
  !!FU(Pow):P(base)/(power)/?(float:e);
  !!IF:M^%(float)^; 12.3 ^ 3.5 = 6526.31287


  !!VR(value:e):S123 :10;
  !!FU(Sqrt):P(value)/?(float:e);
  !!IF:M^%(float)^; 12.3 ^ 0.5 = 3.507. I.e. 3.507 * 3.507 = 12.3

[+] Added functions for SN:M arrays handling to "Era Erm Framework" mod.

  !?FU(Array_Join);
; Concatenates array items into single string, using passed glue string. Works with both numeric and string arrays.
; Example: ['one', 'two', 'three'] with glue ' --- ' become 'one --- two --- three'.
; Returns s^result^
; Uses s^_^
  !#VA(list:x);    Array ID.
  !#VA(gluePtr:x); Optional. Glue string. Default: ''.

  Example:

; Create list with names of the first 10 heroes
  !!SN:M(M_AUTO_ID)/10/(M_STR)/(M_TRIGGER_LOCAL)/?(names:y);

  !!re i/0/10/1/-1:;
    !!HEi:B0/?(heroName:z);
    !!SN:V(names)/i/(heroName);
  !!en:;

; Display joined list items
  !!FU(Join):P(names)/^
  ^;
  !!VR(textPtr:y):Zs^result^;
  !!IF:M^%z(textPtr)^;


  !?FU(Array_Sort);
; Sorts array items in ascending order. Allows to sort specific array subrange.
  !#VA(list:x);     Array ID.
  !#VA(startInd:x); Optional Start index of array subrange to sort. Default: 0.
  !#VA(endInd:x);   Optional End index of array subrange to sort. Default: numItems - 1.

  Example:
; Let (names) variable hold SN:M array ID with heroes names (see example with Join function)
  !!FU(Array_Sort):P(names); will sort it


  !?FU(Array_CustomSort);
; Sorts array items in ascending order user custom comparator function. Allows to sort specific array subrange.
; It's possible to perform any complex sorting in any direction and by unlimited number of criteria, using this method.
; It's a stable sorting method, i.e. items, which we be reported as equal, will retain their relative position to each other.
; For example, if sorting 'Ann', 'David' and 'Ken' by name length, the result will be 'Ann', 'Ken', 'David' and not 'Ken', 'Ann', 'David'.
; When sorting string array, comparator function will receive z-indexes of strings as arguments.
  !#VA(list:x);        Array ID.

  !#VA(compareFunc:x); Comparison ERM function ID. It will be called multiple times with the following arguments:
                    ; (value1, value2, state), where 'state' is any custom value, you specify on call to Array_CustomSort.
                    ; Usually state is some array ID or external structure address, that client use to compare items.
                    ;
                    ; The function must return value:
                    ; < 0 if value1-item should be placed before value2-item
                    ; > 0 if value1-item should be placed after value2-item
                    ; 0 if the ordering between two items should be left as is.

  !#VA(state:x);    Optional. Custom value to be always passed to comparison function as the third argument. Default: 0.
  !#VA(startInd:x); Optional. Start index of array subrange to sort. Default: 0.
  !#VA(endInd:x);   Optional. End index of array subrange to sort. Default: numItems - 1.

  Example 1. Sorting monsters IDs array by HP of each monster

  !!SN:M(M_AUTO_ID)/10/(M_INT)/(M_TRIGGER_LOCAL)/?(mons:y);
  !!SN:V(mons)/0/39/12/20/92/78/17/13/43/6/32;
  !!FU(Array_CustomSort):P(mons)/(tst_CompareByMonHp);
  !!FU(Array_Join):P(mons)/^ ^;
  !!IF:M^Monster IDs: %s(result)^;

  !?FU(tst_CompareByMonHp);
  !#VA(mon1:x) (mon2:x) (state:x) (result:x);
  !!VR(result):S0;

  !!MA:P(mon1)/?(hp1:y);
  !!MA:P(mon2)/?(hp2:y);

  !!if&(hp1)>(hp2):;
    !!VR(result):S1;
  !!el&(hp1)<(hp2):;
    !!VR(result):S-1;
  !!en;

  Example 2. Sorting visitor names by name length

  !!SN:M(M_AUTO_ID)/4/(M_STR)/(M_TRIGGER_LOCAL)/?(visitors:y);
  !!SN:V(visitors)/0/^Laura^/^Den^/^Agriel^/^Ken^;
  !!FU(Array_CustomSort):P(visitors)/(tst_CompareByStrLen);
  !!FU(Array_Join):P(visitors)/^ ^;
  !!IF:M^Visitors: %s(result)^;

  !?FU(tst_CompareByStrLen);
  !#VA(str1Ptr:x) (str2Ptr:x) (state:x) (result:x);
  !!VRz(str1Ptr):M4/?(str1Len:y);
  !!VRz(str2Ptr):M4/?(str2Len:y);
  !!VR(result):S(str1Len) -(str2Len);


  !?FU(Array_Revert);
; Reverts order of itmes in the array. Allows to reverse the order of specific array subrange only.
  !#VA(list:x);     Array ID.
  !#VA(startInd:x); Optional Start index of array subrange. Default: 0.
  !#VA(endInd:x);   Optional End index of array subrange. Default: numItems - 1.

  Example:
; Let (names) variable hold SN:M array ID with heroes names (see example with Join function)
  !!FU(Array_Revert):P(names); will revert items order


  !?FU(Array_Fill);
; Fills array or arrays subrange with incrementing/decrementing values.
; Example: FU(Array_Fill):P(array)/100/2; Will fill items with 100, 102, 104, 106...
  !#VA(list:x);       Array ID.
  !#VA(startValue:x); Starting value to fill with.
  !#VA(step:x);       Value to add to increase filler on each step. Default: 0.
  !#VA(startInd:x);   Optional. Start index of array subrange. Default: 0.
  !#VA(endInd:x);     Optional. End index of array subrange. Default: numItems - 1.

  Example:
; Let (array) is some array of integer numbers. Let's fill it with 100, 98, 96...
  !!FU(Array_Fill):P(array)/100/-2;

[*] Creating array using SN:M with 5 parameters does not change v1 anymore.
[*] Extracted all Era supplied ERM scripts into "Era Erm Framework" mod.
[*] Extracted ERM testing code into separate mod "Era Erm Tests".
[*] Updated ERM editor snippets and autocompletion files. Added fast 'ifm', 'ifl' and 'snm' snippets.

[-] Applied fixes to ERM constants (Era Erm Framework mod):
  Fixed constant name: MON_SUPREMEARCHANGEL => MON_SUPREME_ARCHANGEL.
  Fixed constant MON_LAST_WOG => 196 instead of 197. Credits: igrik.
  Fixed primary skills constants. Credits: Algor.

[-] Fixed crash on !#VA(-varName) syntax usage.
[-] Fixed ERM memory dump generation: slots reporting use to contain information about reserved items.
[-] Fixed x-variables reporting in ERM tracking module. Previosly garbage x0 value was output as the first one.
[-] Fixed Nagash portrait name in game and map editor executables. No more "missing hpsz001.pcx" error.
Bes, magoth, Mefista, igrik, KypaToP_HM, arblade_official, NightLord
05 Sep 2020, 23:16 Мод «Смешанные Нейтралы II»
Mixed Neutrals II mod


Вышла первая версия мода Смешанные Нейтралы I
Текущая версия: 1.0.0
По просьбе: Gary K

Что нового ?

Вместо однотипных нейтралов на карте размещены группы смешанных монстров. Первый отряд совпадает с картинкой на карте. Остальные генерируются случайно.
В коде скрипта есть возможность настроить множитель силы отрядов для всех и дополнительный множитель силы отрядов для человека. По умолчанию 2 и 2 соответственно.
Скрипты имеют возможность повлиять на работу мода через ЕРМ обработчики. Например, реализовать просмотр конкретного числа монстров в каждом отряде, запретить потери нейтралов при побеге героя или написать свой генератор монстров.
Скрипт полностью написан на ЕРМ 2.0 и может быть использован в образовательных целях.

Скачать
Bes, magoth, lion-killer, Mefista, Haart of the Abyss, Арысь-Поле, Zabuza-san, Doctor Tea, Slavic boy
05 Sep 2020, 02:56 ERA III


Вышло обновления для HoMM 3 ERA
Текущая версия: 3.0.4

Что нового ?

Добавлено событие расчёта дохода города. Лимит дохода увеличен с 32767 до 2 млрд.+
Улучшена работа с ЕРМ циклами, повышена стабильность ЕРМ движка.
Для азиатских языков стало доступным переключение элемента ввода текста с игрового на системный.
Были возвращены оригинальные портреты, описания и специализации Нагаша и Джеддита. В WoG 3.58 эти герои получили Вуаль тьмы и Перестройку городов.
Исправлено более 7 ошибок, которые ранее могли приводить к вылетам или нестабильному поведению игры.

Скачать

Код
Version 3.0.4 (09/2020)
------------------------
[+] Extended town income limits from -32768..32767 to -2147483648..+2147483648 and added new event OnCalculateTownIncome
    with three parameters: Town ID, Income (gold amount), Account resource silo? (0 or 1).

[+] Introduced extended !!re syntax: !!re counter/start/stop/step/stop_modifier, where stop_modifier is any integer value,
    that will be added to stop value. New syntax allows to express such loops as FROM 0 to SOME_VAR - 1, for instance.

    Example:
    !!re i/0/(numStacks)/1/-1:;
      ...
    !!en:;

[+] !!re allows to use any variables now, including global named s/i variables.

[+] Improved ERM stability. Now all non-specified parameters are treated as 0 in X# syntax and ignored in X$ syntax.
    As a result, !!DL:A without the 4-th parameter will not randomly crash anymore and !!TR may be used with any number of parameters,
    while exactly 8 were required previously. Note, that many ERM commands still require exact number of obligatory parameters.

[+] !!DL:A was improved, accepting any string including string literal as the 3-d parameter.

[+] Included updated "wog native dialogs" plugin by igrik. From now plugins exports function __cdecl int UseWin32InputControl (int newState).
    The function allows to switch between Heroes 3 native input control and Windows input control. The latter allows to input Asian and '{', '}' characters.
    Mode can be switched any time even using ERM. UseWin32InputControl returns previous state.

[*] Fully restored Nagash and Jeddite original portraits, descriptions and specialties.

[*] Changed ERM error report generating: not only ERM memory dump is made, but the whole debug information is saved, like
    if you press F11 manually.

[-] Fixed WoG bug, disallowing to set dialog hints twice using DL:H command. Credits: gamecreator.
[-] Fixed bug in ERM caching engine: GET-syntax could produce garbage values on cache hit.
[-] Fixed bug in ERM engine, causing crashes in !!UR:S and a few other possible commands.
[-] Fixed bug: IF:N$ used to cause ERM errors and crashes. Credits: helgtla.
[-] Fixed bug: HE:P used to return unsigned 65535 instead of signed -1.
[-] Fixed bug: ERM compiler didn't process post-triggers.
[-] Fixed bug, causing many Era commands to return garbage after valid string contents. Credits: PerryR.
[-] Fixed map editor => WoG tools menu shortcuts to actual programs. Credits: Archer30.
Bes, hippocamus, magoth, Mefista, igrik, Zabuza-san, Odin, KypaToP_HM, Iriniko, arblade_official
30 Jul 2020, 02:20 ERA III


Вышло обновления для HoMM 3 ERA
Текущая версия: 3.0.3

Что нового ?

Добавлена долгожданная возможность безлимитной установки названий/описаний артефактов через ЕРМ без привязки к фиксированному набору строковых переменных.
ERS-файлы (файлы вог-опций) избавлены от ограничений геройского движка на имя в 12 символов, что позволило восстановить работу мода Era Scripts.
Добавлено новое событие на получение хода отрядом в бою до фазы регенерации. На необходимость такого события указал автор мода Z Усиленные Боевые Машины IV.
Множественные мелкие исправления.

Скачать: https://mods.hmm35.ru/Era%203.X.exe

Код
Version 3.0.3 (07/2020)
------------------------
[+] Added command SN:H^art^/art ID/0 (name) or 1 (description)/$text
    allowing to get/set any artifact name/description without z-variables dependency.

[+] ERS-files parser was rewritten. No more H3 bugs, caused by 12-character path length restriction.
    Any ers file name like "some loooooong script.ers" is supported.

[+] Added OnBeforeBattleStackTurn event. It occurs right before OnBattleRegenerationPhase event.
    Parameters: Stack ID (0..41). Change the first parameter to give turn to another stack.
    
    Note, that similar OnBattleStackObtainsTurn event occurs when stack becomes active and is not related to regeneration phase at all.
    Normally OnBattleStackObtainsTurn occurs after OnBattleRegenerationPhase but may also be triggered manually by calling
    464F10 (THISCALL, ecx = CombatManager, Side 0..1, StackInd 0..21).

[-] HE:P without 4-th parameter now works as in WoG 3.58f for compatibility reasons. If hero belongs to current player,
    teleport sound is played and screen redrawn. Otherwise teleportation is silent without visual update.

[-] Fixed bug: each reloading reduced ERT strings length by one. Credits: ArnoVanClaire.
[-] Included missing ztower1.def in hmm35wog.pac. Credits: ArnoVanClaire.
[-] Fixed invalid Sorceress fight value in zcrtraits.txt. Credits: Archer30.
[-] ztport01.def monolith will not be used on random maps anymore (removed from zaobjts.txt).
[*] IF:N fix was improved. Credits: igrik.
[*] Era exported functions with boolean results now return int32 0 or 1 (0 or -1 previously).
Bes, XEL, hippocamus, magoth, Mefista, igrik, Zabuza-san, KypaToP_HM, arblade_official
24 Jun 2020, 01:55 ERA III


Вышло обновления для HoMM 3 ERA
Текущая версия: 3.0.2 (альфа 2)

Что нового ?

Добавлено новое событие OnAdvMapObjectHint, позволяющее динамически управлять подсказкой при наведении на любую клетку карты, что активно используется, например, в моде на новые хранилища существ от PerryR.
Вернулась поддержка старого синтаксиса некоторых ЕРМ команд. Баг с улучшением существ до копейщика и ошибки в моде расширенных жилищ существ пропадут.
Исправлен баг в библиотеке тестов на ЕРМ и обновлена библиотека, отвечающая за виртуальную файловую систему.

Скачать: https://mods.hmm35.ru/Era%203.X.exe

Код
[+] Added new ERM event 'OnAdvMapObjectHint', allowing to get/set hint for any tile, mouse is currently over.
    Parameters: x, y, z, object type, object subtype.
    Example:

    !?FU(OnAdvMapTileHint); display tile coordinates and original hint
    !#VA(x:x) (y:x) (z:x) (objType:x) (objSubtype:x);
    !!MM:M?(existingHint:z);
    !!MM:M^%(x) %(y) %(z) %(objType) %(objSubtype): %(existingHint)^;

[+] Added support for %Vf..t syntax in interpolated strings, that was present in WoG 3.58.
[+] Restored short !!HE:X6 syntax support and fixed ERM HE:X7 bug: short syntax worked as X7/a/d/0/0/0/0 instead of X7/0/a/d/0/0/0.
[+] Updated VFS.dll to version 1.0.5.
[-] Fixed bug in "era - testlib.erm": !?FU(et_ExpectError) didn't restore error suppression option.
Bes, gamehuntera, XEL, hippocamus, magoth, Mefista, igrik, Odin, KypaToP_HM, Grossmaster
03 Jun 2020, 03:39 ERA III
ERA 3



Вышла новая мажорная версия HoMM 3 ERA
Текущая версия: 3.0.0 (альфа 0)

Что нового ?

Опциональный режим ERM 2.0: именованные константы, локальные переменные и функции на стадии прекомпиляции. На ЕРМ становится возможным писать понятный код с малым числом комментариев.
Переписан движок ЕРМ: множество исправлений наследия прошлого, универсальный синтаксис, удобная работа со строками, исправление багов, расширение и добавление команд и многое другое.
Добавлена стандартная библиотека ЭРЫ на ERM: 1 расширенное событие и тысячи предопределённых констант.
ЭРА становится полноценным ядром для мододелов всех мастей: больше нет навязанных модов, анимации, большинства графических изменений, нового интерфейса, заменённых кампаний и музыки и т.д. Установив ЭРУ вы получаете рабочий скелет со всеми инструментами для создания уникальной сборки под ваши вкусы и желания. Базовый комплект новых монстров/объектов из WoG 3.58 остаётся в качестве ресурсов и включаемых/выключаемых игровых механик.

Скачать: https://yadi.sk/d/Bhg4CGTf3PXi3k/Releases/Era%203.exe

Код
Version 3.0.0 (06/2020)
------------------------
[+] Introduced advanced ERM precompilation mode, called ERM 2.0 and activated via "ZVSE2" first line signature.
  Main features:
    - Named local variables to write human readable code instead of cryptic one.
      Example: !!HE-1:C0/0/?(monType:y)/?(monNum:y) instead of !!HE-1:C0/0/?y23/?y24;
    
    - Global named constants instead of magic numbers to write self-explaining code:
      Example: !?FU(onKeyPressed)&x1=(KEY_1) instead of !?FU(onKeyPressed)&x1=49; what is 49???
    
    - Strict distinguishing naming for functions, local variables and constants. No way to mix up.
      Example: thisIsVariable, THIS_IS_CONSTANT, ThisIsFunction and era_ThisIsFunctionAgain.

  ==== Named global constants ====
  Constant is named value, that is defined once and never changes. Like 13 (Archangel monster type).
  Constant can be used anywere, where numbers can be used. Era currently supports only integer numeric
  constants, written in all capitals: (MON_ARCHANGEL), (OBJ_MINE), (PLAYER_RED).
  Allowed characters are: [A-Z0-9_].
  To define a constant use the following instruction !#DC(CONSTANT_NAME) = 777; where 777 is arbitrary number.
  Examples:
  !#DC(PLAYER_BLUE)     = 1;
  !#DC(SKILL_FIRST_AID) = 27;

  To use a constant simply write its name in parentheses:
  !!OW:R(CURRENT_PLAYER)/(RES_GOLD)/d1000; give 1000 gold to current player

  will be compiled to

  !!OW:R-1/6/d1000; give 1000 gold to current player

  --- Naming ---
  Scripts writers must use unique prefix before constant names to prevent names collisions. Any constants without prefix
  may be added to ERA in the future and break your script.
  Example:
; for mod Battle Heroes let's use prefix "BH_"
  !#DC(BH_ART_RING_OF_POWER) = 160;
  
  !#DC(BH_CLASS_WARRIOR) = 1;
  !#DC(BH_CLASS_MAGE)    = 2;
  !#DC(BH_CLASS_RANGER)  = 3;

  --- Globality ---
  Constants are global. It means, that one script can use constants of another script. To ensure, that your constants
  are always loaded before other scripts, place them in the script with high priority (ex. "1000 - phoenix consts.erm").
  
  --- Standard constants ---
  ERA provides file "1000 - era consts.erm" with many predefined constants, covering most values, mentioned in ERM help.
  Look through it before defining your own constant for secondary skill, monster or player color.


  ==== Named local variables ====
  Each ERM trigger (!?XX before next !?XX) can now declare and use own named local variables, allocated from
  x1..x16, y1..y100, z-1..z-10, e1..e100 sets.
  Named variables are replaced with regular variables during scripts compilation and do not influence the performance at all.
  Example: (day) may be compiled to y5;

  --- Naming ---
  Names of variables must be in so called "camelCase" and contain only [a-zA-Z0-9] characters. They must be wrapped
  in parantheses the same way, as function names are wrapped.
  Example of valid variables: (hero), (monNum), (isAutocombatMode), (specialObject7).

  --- Declaration ---
  Variables must be declared on the first usage: i.e their type (x, y, z, e, v) and array length (for arrays) must be specified.
  If you write '[some number]' after variable name, variable will become an array (sequence of variables) with specified length.
  If you write ':e' after variable name or array length, it will mean, that variable type is "e" (floating point numbers).

  Examples:
  !!HE-1:N?(hero:y); give some y-variable name "hero" and write current hero ID to it
  !#VA(arts[4]:y);   allocate 4 y-variables with sequential indexes and name the array "arts"

  !#VA instruction is pseudo-command, that is dropped from final compiled code and that can be used to hold variables declarations.
  Example:
  !?FU(acm_Sum);
; The function calculates sum of two numbers
  !#VA(first:x) (second:x) (result:x); [bind "first" to x1, "second" to x2, "result" to x3]
  !!VR(result):S(first) +(second);     [calculate result]

  --- Usage ---
  It's allowed to specify the same type and array length for variables in every variable usage place, but it's not necessary.
  After you declared variable, there is no more any need to write its type/length.
  Example:
  !!HE-1:N?(hero:y);
  !!HE(hero):K1; kill hero with ID in (hero) variable.

  will be compiled to something like that:
  !!HE-1:N?y5;
  !!HEy5:K1;

  --- Arrays ---
  If you need not a single variable, but sequence of variables, for instance to hold [x, y, l] coordinates of objects,
  then you need an array. Specify array length in square brackets right after variable name during declaration.
  !#VA(coords[3]:y); allocate 3 y-variables named 'coords'

  Items or elements of arrays are zero-indexed and can be accessed by direct index.
  For 3-items array possible indexes are 0, 1, 2.
  Example:
  !!CM:P?(coords[0])/?(coords[1])/?(coords[2]);

  will be compiled to something like that:
  !!CM:P?y50/?y51/?y52;

  If you don't specify array index, the first array element will be used. It means that
  (test) and (test[0]) have the same sense. Regular variables are considered arrays of length 1.

  --- Negative array indexes ---
  Negative array index means n-th item from the end. -1 will point to the last item, -2 to the one before the last one and so on.
  Example:
; allocate array of 10 y-variables and assign the last one value 2000
  !#VA(array[10]:y);
  !!VR(array[-1]):S2000;

  will be compiled to something like that:
; allocate y1..y10
  !!VRy10:S2000;

  --- Releasing local variables ---
  If you don't need large variable array anymore, but want to declare another big array, then free the previous one.
  Syntax: !#VA(-variableName); will forget about specified variableName, allowing to reuse indexes, allocated for that variable.

  Example:
  !#VA(myArts[100]:y); allocate y1..y100 to hold artifact IDs
  ...;                 use them
  !#VA(-myArts);       release 'myArts' name and y1..y100 indexes.
  !#VA(coords[3]:y);   allocate y1..y3 as 'coords' variable

  --- Getting variable address (real index) ---
  It's often necessary to get real index of variable or even array element. When you want to output "2" instead of
  y2, use address operator '@'.
  
  Example:
; Initialize array with 3 artifacts
  !#VA(arts[3]:y);
  !!VR(arts):C(ART_SKULL_HELMET)/(ART_HELM_OF_CHAOS)/(ART_DEAD_MANS_BOOTS);

; Select one artifact randomly
; same as R0/0/2, generates random number in 0..2 range and assigns it to artPtr variable.
  !!VR(artPtr:y):R0/(@arts)/(@arts[-1]);
  
; Give artifact to hero
  !!HE-1:Ay(artPtr);

  will be compiled to something like that:
  
  !!VRy1:C20/21/56;
  !!VRy4:R0/0/2;
  !!HE-1:Ayy4;

  Address operator "@" compiles to real (final) variable index. For instance, for array "test[10]:y" mapped to y50..y59
  (@test[1]) will compile to "51".

  Example of declaring array of 10 y-variables and initializing all of them with -1.
  !#VA(monTypes[10]:y);

  !!re i/(@monTypes)/(@monTypes[-1]):; repeat from i = first array index to i = last array index
    !!VRyi:S-1; set -1 for current array item
  !!en:;

  In other programming languages variables, holding other variables addresses/indexes are usually called "pointers"
  and abbreviated as "ptr" or "Ptr". We will rewrite the previous example with named variable in place of quick "i" var
  just for learning purposes.

  !!re (monTypePtr:y)/(@monTypes)/(@monTypes[-1]):; repeat from (monTypePtr) = first array index to (monTypePtr) = last array index
    !!VRy(monTypePtr):S-1; set -1 for current array item
  !!en:;

  --- Naming function arguments ---
  Indexes for named local variables are allocated starting from the smallest possible value.
  It means, that we can name even function arguments if we declare them in the same order, as arguments will be passed.
  Example:

  !?FU(BH_GetHeroSecSkill);
  !#VA(hero:x) (skill:x) (result:x); now hero = x1, skill = x2, result = x3
  !!HE(hero):S(skill)/?(result);

  !?FU(...); some event
  !!FU(BH_GetHeroSecSkill)/(HERO_XERON)/(SKILL_FIRST_AID)/?(xeronFirstAidLevel:y); so what's the level of First Aid skill Xeron has? )

  --- Redeclaration ---
  If you need to declare variable in both branches of if-then block, specify type/length in both of them.

  !!if&(day)>90:;
    !!VR(price:y):S(day) *100;
    ...
  !!el:;
    !!VR(price:y):S(day) *(difficultyLevel) +300;
    ...
  !!en:;

  --- Reusing same name in other trigger ---
  Variable names are local to nearest trigger only. New trigger starts with no declared variables.
  Example:

  !?FU(OnHeroScreenMouseClick);
  !!CM:F?(flags:y); flags = y1

  !?FU(OnHeroScreenMouseClick);
  !#VA(flags[23]:e); flags is array, binded to e1..e23

  --- Interpolation ---
  To substitute local variables in string literals use %(varName) syntax. Example:
  !!VR(price:y):S600;
  !!VR(heroName:z):S^Robin Hood^;
  !!IF:Q2/^Would you like to hire %(heroName) for %(price) gold only?^;

  %y(varName) syntax is also supported and compiles to something like %yy5.


  ==== Named functions ====
  Function names must consist of [A-Za-z0-9_] characters only, start with letter and contain at least
  single lower case letter (a-z).
  There are two allowed naming methods:
  1) Start function with capital letter. (CalcHeroArmyPower), (ShowUpgradeDialog).
  ERA reserves right to declare prefixless functions, starting with "On" for events. This method is not
  recommended, due to possible names collisions in different mods. Two mods may declare functions
  will the same names and thus produce hard to debug bugs.

  2) Start function with any case unique prefix with '_' character. Prefix is usually mod abbreviation.
  For instance, for "Dwellings Extended" mod the following functions are used:
  !?FU(dex_SetDwellingSlotByTownType);
  !?FU(dex_DwellingPopulation);
  ...

  --- Generating new events ---
  You can call function, even if it has no handlers. For instance, in Upgrade All Creatures mod you
  want to allow other scripts to be able to notify, what monster can be upgraded to in particular town.
  Just call not existing function like !!FU(auc_OnDetermineMonsterUpgrade):P... in your script with all
  necessary parameters and other scripts will be able to write new event handlers like:

  !?FU(auc_OnDetermineMonsterUpgrade);
  ...

  --- Passing function as handlers or callbacks ---
  You can use function as ordinary constant, compiled to number. You can assign it to variable or pass to
  another function.
  !!VR(spellHandler:y):S(newmagic_DesintegrationSpellHandler);
  !!FU(spellHandler):P;

  will compile to something like that

  !!VRy20:S95003;
  !!FUy20:P;

[+] Added 1000 era - stdlib.erm script, which will contain safe for all extra ERM functionality.
    Currently !?FU(OnEvenyDay) event is enhanced. Its handlers will receive 5 parameters:

    !?FU(OnEveryDay);
    !#VA(day:x1) (weekDay:x) (once:x) (owner:x) (isAi:x);
    !!IF:M^%(day) %(weekDay) %(once) %(owner) %(isAi)^;

[+] Added 1000 era - consts.erm script with lots of constants to be used in ERM 2.0 scripts.
    ERM Editor, based on Sublime Text, supports constants autocompletion.
    Remember, that constants without mod name prefix are reserved for ERA.
    Prefer BH_GOLD_PER_VICTORY to GOLD_PER_VICTORY for Battle Heroes mod, for instance.

[+] Floating point variables (e-variables) are passed to ERM commands as raw 4 bytes value,
    treated by most commands as integer, which may cause many bugs, unless you know, what you are doing.
    The exception is !!VR:S command, allowing transparent conversion integer-float. To copy float value,
    stored in raw format in integer variable to e-variable and vice versa use !!VR:C command. It acts same
    as VR:S, but without data conversion.

[+] New command !!VR$1:S#2/#3. Convert float to integer using specific rounding mode.
    $1 - integer variable.
    #2 - float variable
    #3 - rounding mode:
      < 0 for floor operation (round towards negative infinity),
      0 for normal round (round half away from zero),
      > 0 for ceil operation (round towards positive infinity).

[+] !!VR: +/-/*/:/% convert both arguments to float if any is float before calculation and convert back
    to base var type on return.
    Thus
    !!VR(koef:e):S25 :10; koef = 2.5
    !!VR(gold:y):S2 *koef; gold = 5, not 4

[+] New command !!VR$1:~#2
    Unsets bits #2 in $1 integer variable.
    Example:
    !!VR(flags):~17; unset bits/flags 1 + 16 from (flags) variable.
  
[+] New command !!VR$1:Z#2. Creates trigger local temporary z-variable with given contents and assigns its index to integer variable.
    $1 - integer variable.
    #2 - any string.

    The command can be used to create temporal z-variables to change, for example, artifact description,
    show message and restore description.

[+] ^....^ literal in any ERM command is interpolated and replaced by temporal z-variable index before receiver
    execution. This z-variable is released right after receiver is executed.
    Don't use string literals in WoG 3.58 hint/description setting commands, because such descriptions have short life time.

    From now it's possible to pass strings to functions.

    !?FU(ES_Ask);
; Shows question dialog with caption. Returns boolean (1 on success and 0 on failure).
    !#VA(captionPtr:x) (questionPtr:x) (result:x);
    !!IF:Q1/^{%z(captionPtr)}

    %z(questionPtr)^;
    !!VR(result):S0;
    !!VR(result)&1:S1;

    !?OB(OBJ_TOWN)/(ANY_OBJ);
    !!FU(ES_Ask):P^Sphinx asks you:^/^Do you really want to die, fighting my guards?^/?(answer:y);
    !!HE(CURRENT_HERO)&(answer)=1:K1; let him die )))

[+] Only regular ERT variables are interpolated automatically.
    Regular z-variables and temporal ert variables are not interpolated in receivers.
    It means, that !!VRz2:S^%%y5^; z2 is now really "%y5"

    Previously interpolation would be performed again and again recursively, converting %y5 into y5 value like 0.
    and even later using z2 in any command would run interpolation again.

    !!IF:M1/z2; will display "%y5", not y5 value.

[+] New VR$1:R/T syntax: 0/min/max - generates random value in given range and assignes it to $1 integer variable.
[+] VR:R/T now both support syntaxes with 1/2/3 arguments.
[+] VR:T uses Mersenne Twister qualitive generator, but it's not synchronized in multiplayer.
[+] VR:M1. -1 as length means "till string end".

[+] VR:M2 does not store token index in global variable anymore. Token index, that was ignored earlier, works now as expected.
   Token delimiters are [#1..#31, ' ', ',', '.']. Don't use for huge text, because performance is O(n^2), where n is tokens number.

[+] VR:M3 Base/radix is enforced to be in 2..16 range.

[+] ERM interpolation (expanding variables starting with % in string literals ^...^ and ERT strings) was fully rewritten.
    Upper case registry for old ERM variables is supported, but deprecated.
    %X1 is good, but %x1 is better.

    All new s^...^, i^...^ and named local variables are supported.
    Indirect references is supported.

    %s(named global variable)
    %i(named global variable)
    %xy7
    %zi^named global variable^
    %z(namedLocalVar)
    %(namedLocalVar)

    Quick vars are supported:
    %i %g %k

    Interpolation of %Vf...t meaning is changed to real v-indexing
    %vi means v-var with i-index.
    %f means quick 'f' var.
    %i means quick 'i' var.

    %F5 means flag 5
    %Fx16 means flag with x16 index

    Function IDs and constants can be interpolated in the same way, as named local variables:
    %(CONST_NAME), %(era_FuncName), %(money), %y(moneyPtr)

[+] IF:M# now works with any string
[+] IF:N1/# now works with any string, not z1 only.
[+] IF:N# now works with any string.
[+] BA:B now can work with any string and integer.

[+] Call SN:F^GenerateDebugInfo^ to generate Debug directory contents, the same way as F11 does.

[+] Exported "NameTrigger" function (void NameTrigger(int TriggerId, const char* Name)), allowing plugins to
    give name to any ERM trigger, which can be used in ERM like !?FU(OnYourNewEvent).

[+] Updated "wog native dialogs" plugin by igrik. From now it's possible to select item in message dialogs
    using mouse double click.

[+] s^...^, ^...^, i^...^ can now be freely used in conditions.

[+] New d-modifiers (d~, d%, d|, d&, d<<, d>>) work with all receivers.

[+] Rewritten ert-strings storage implementation. Removed limit on 50000 strings. Increased add/delete operations
    performance (from linear search to binary tree search). Savegames format was changed.

[+] Added VR:C alternative for SN:M arrays. New command !!SN:U#1/#2/$3...up to $21 allows to set/check/get/modify
    many items of dynamical array.
    #1 - SN:M array ID.
    #2 - starting index
    $3... - items at starting index, starting index + 1, starting index + 2, etc.

[+] Added new command !!VR:R0/#min/#max, generating random value in specified range and assigning its to variable.
    Example: !!VRy1:R0/100/300; set y1 to random value in 100..300 range

[*] The following exported functions now return 4-bytes LONGBOOL value, 0 for false, -1 (0xFFFFFFFF) for true.
    "ReadStrFromIni", "WriteStrToIni", "SaveIni", "PatchExists", "PluginExists", "Ask".

[+] Added "1000 - era consts.erm" script to WoG mod with standard Era constants, including players,
    player bits, heroes, resources, objects, monsters, artifacts, spells. The file contents may be corrected
    and widened in the future. All constants were registered in Erm Editor, based on Sublime Text.

[+] Added "1000 - era stdlib.erm" script with universal ERM functions and events. Currently "OnEveryDay"
    event is enhanced with the following x-arguments: day, week day, once(0..1), owner (color), isAi (0..1).

[*] Fixed WoG bug with tactics detection on the very first round. Do not use BU:R in !?BR or !?FU(OnCombatRound) for zero round,
    because a few structures are not initialized at this moment and random crash may occur. First round code was moved after
    combat theme initialization and tactics popup message appearance.

[+] All *.ers files are loaded without name/quantity constraints. Previously only script00.ers..script99.ers were processed.

[+] HE:P command behavior was fixed. Teleport function with sound is called only if any coordinate
    was really changed. Advanced d-modifiers are supported for the first three parameters.

[+] HE:C0 command was rewritten.
    -1 and -2 values for creature type are not treated as "upgrade"/"degrade" anymore. Command supports any d-modifiers now.
    Exp. modifier parameter is now SET-only. Previosly !!HE:C0/0/?y1/?y2/d5000/2 would not increase slot experience.
    In fact, any GET syntax used to make ERM engine ignore stack experience at all. This bug was fixed.
    Creature Type < 0 or Number <= 0 will be normalized to Type -1, Number 0 automatically.
    Note, that in all cases the returned stack experience value is the one before applying any changes.

[+] Rewritten HE:X command to accept any number of parameters and understand any d-modifiers.
    Example: !!HE-1:X0/27 xD.gif1; become master of gold dragons

[+] Introduces many new d-modifiers for all ERM commands, except for GE:E/N, LE:E/N.
    d+# - integer addition
    d-# - integer substraction
    d*# - integer multiplication
    d:# - integer division
    d|# sets bits from # (bitwise OR operation)
    d& leaves only # bits, if any (bitwise AND operation)
    d& unsets bits, specified in #. d&17 unsets bits 1 and 16
    d%# calculates division modulo. 10%4 = 2, for instance.
    d<<# shifts original value bits to the left by # positions (bitwise logical shift left).
    d>># shifts original value bits to the right by # positions (bitwise logical shift right.

[+] Function parameters (FU:P, DO:P), which were passed using GET-syntax, are now initialized with
    original variable value. The behavior is similar to pass-by-reference in other programming languages.
    Example:
    !?FU(Add3):;
; (value:x)
    !!VR(value:x):+3;

    !?CM0;
    !!VR(numHeads:y):S10;
    !!FU(Add3):P?(numHeads:y); 10 is passed to function as the first argument, 13 is result

[+] Enhanced !!RD:I with new named parameters syntax.
    !!RD:I^parameter name^/?$parameter_value;
    ============================== Featured parameters: ==============================
    ^dlgId^        - Unique recruit dialog ID. Used to distinguish between nested dialogs (yep, it's possible). Reusable.
    ^townId^       - ID of town, for which dialog is opened or -1.
    ^dwellingId^   - ID of town dwelling, for which dialog is opened or -1. 0..6 non upgraded, 7..13 for upgraded.
                     Horde buildings (+X population) are treated as dwellings, they influence.
    ^slot^         - Active logical slot index.
    ^cost^         - Cost of single monster in current slot in gold.
    ^resource^     - Special resource for monster in current slot.
    ^resourceCost^ - Cost of single monster in current slot in special resource.
    ^quantity^     - Number of monsters, currently selected for recruitment.
    ^maxQuantity^  - Maximal number of monsters, the player can afford.

    Example:
    !?FU(OnRecruitDlgMouseClick);
    !!RD:I^dlgId^/?(dlgId:y) I^townId^/?(townId:y) I^dwellingId^/?(dwellingId:y) I^slot^/?(slot:y) I^cost^/?(cost:y);
    !!RD:I^resource^/?(resource:y) I^resourceCost^/?(resourceCost:y) I^quantity^/?(quantity:y) I^maxQuantity^/?(maxQuantity:y);
    !!IF:M^(dlgId:y) (townId:y) (dwellingId:y) (slot:y) (cost:y) (resource:y) (resourceCost:y) (quantity:y) (maxQuantity:y)^;

[+] Enhanced !!UN:C command. It supports all d-modifiers now. New syntax with offset from address is available:
    !!UN:C#addr/#offset/#size/$value;
    Era always calls GetRealAddr for #addr, thus !!UN:C supports all extended/relocated game structures.

[+] WoG interface and WoG campaigns were extracted to appropriate standalone mods. ERA is now mostly Vanilla game with
    enhanced ERM engine and other modding capabilities.

[+] Added !!BM:Z?$addr command to get battle stack structure address.
[+] Added !!HE:Z?$addr command to get hero structure address.
[+] Introduced ERM 2.0 support for scripts, beginning with 'ZVSE2'.
[+] Doubled stack size for h3era.exe executable to allow trigger depth level up to 150, but better avoid such depth.

[+] WoG Campaign editor loads resources from hmm35wog.pac and uses virtual file system. No more Campaign Fix required.
[+] Added extended resources redirection support with wav/bik/smk files, including missing resources redirection.

[+] Added new plugins events "OnAfterLoadLods", occured right after lods/pacs are loaded and "OnAfterLoadMedia", occured
    when lod/pacs/snd/vids are loaded.

[*] ERA is recommended to be installed over Heroes 3 Complete only. Removed resources, which are already present in Complete lods.

[-] Restored functionality of Data\Redirections\Missing\*.json files, which are used to setup redirections
    for missing resources only.

[+] ERM quick vars (f..t) are now local to triggers. Use them safely.

[+] Update ERM Editor.
[+] Rewritten core of ERM engine. Greatly improved old macro support ($macronam$). Just for perfection.

[+] Extracted WoG campaigns into standalone mod, which was removed from Era installer package.

[+] "remove exe protection.bin" was applied to h3era.exe and removed as patch.

[+] Many resources and features were extracted from WoG mod into separate mods: Animated Object Flags, Animated Trees,
    No Prebattle Music, Secondary Skills Scrolling, Quick Savings, Fast Battle Animation, Improved Battle Decorations,
    WoG Interface, WoG Campaigns, Yona.

[+] Added new event "OnDetermineMonInfoDlgUpgrade", occured, when game determines wether to show upgrade button
    in monster info dialog. Parameters: MonType, UpgradedType or -1, Town ID or -1, Hero ID or -1.
    -1 for UpgradedType means no upgrade button (because of wrong town type or appropriate building being not built, or monster having no upgrade).
    You can change this value to allow universal Jelu-like behavior or any upgrade system.
    Example:

    ZVSE2
    
    !?FU(OnDetermineMonInfoDlgUpgrade);
    !#VA(monType:x) (upgType:x) (town:x) (hero:x);
    !!VR(upgType):S(MON_GOLD_DRAGON); allow upgrade anything into Gold Dragons

[+] SN/RD/MP receivers now support indexed parameters like vy6 or zi^myIndex^.

[+] SN:D may be used now in battle, being equal to BU:R.

[+] Added support for trigger local dynamical arrays. !!SN:M-1/#/#/-1 will allocate new dynamical array
    with ID, that will be automatically released after current trigger is exited. Thus no
    corresponding !!SN:M# is necessary to release this temporary array. It can be used, for instance,
    for large calculations or to pass string arguments to function.

    Example:
    !?FU(OnAdventureMapRightMouseClick);
    !!SN:M-1/4/1/-1;        [allocate 4 strings array (-1 = auto ID, 4 = 4 items, 1 = of string type, -1 = local to current trigger)]
    !!VR(dlgStrings:y):Sv1; [save array ID]
    
; Setup strings
    !!SN:M(dlgStrings)/0/^Select commander bonus:^;
    !!SN:M(dlgStrings)/1/^1) Attack^;
    !!SN:M(dlgStrings)/2/^2) Speed^;
    !!SN:M(dlgStrings)/3/^3) Health^;
    
    !!FU(PM_ShowDialog):P(dlgStrings); [pass 4 string to dialog showing function]
; here array with (dlgStrings) ID will be automatically freed, same as SN:M(dlgStrings);

    !?FU(PM_ShowDialog);
; (dlgStrings:x) - dynamical array of 4 strings
; (items[3]:z)
    !!SN:M(dlgStrings)/0/?(caption:z);
    !!SN:M(dlgStrings)/1/?(items[0]);
    !!SN:M(dlgStrings)/2/?(items[1]);
    !!SN:M(dlgStrings)/3/?(items[2]);
    !!IF:M^{(caption)}
    (items[0])
    (items[1])
    (items[2])^;

[-] Fixed memory leakage in SN:M dynamical arrays deallocation and a few other places.




Вышло обновления для HoMM 3 ERA
Текущая версия: 3.0.1 (альфа 1)

Что нового ?

Работать с ЕРМ-функциями стало ещё приятнее: корректный подсчёт переданных параметров, значения параметров по умолчанию, автоинициализация параметров нулями.
Улучшенная поддержка отладки и тестирования: новые магические константы и первая версия библиотеки тестов Эры. Для обнаруженных багов написаны авто-тесты на ERM.
SN:M динамические массивы теперь отлично выполняют роль списков. Изменение размеров было оптимизировано. Появился доступ к концевым элементам по отрицательным индексам.
Исправлено несколько багов движка и недочётов предыдущего релиза.

Скачать: https://mods.hmm35.ru/Era%203.X.exe

Код
Version 3.0.1 (06/2020)
------------------------
[+] Added first ERA ERM tests. Tests library in "Tests/1000 era - testlib.erm" and tests, covering found
    bugs and part of new functionality in "Tests/era - tests.erm".

[+] Added new 3 magic constants. All are safe to use inside strings and as parameters:
    (FILE) expands into current script file name.
    (LINE) expands to current line number in script file.
    (CODE) expands to excerpt of escaped current line source code.
    These constants are specially useful for debugging, bug reporting and automated tests. See
    "Tests/era - tests.erm" for examples.

[+] Added new constants: TRUE, FALSE, SN_M_* (for SN:M parameters).

[+] Added new escape sequences for string literals (^...^):
    '%\:' expands into ';' (usually forbidden character for literals, marking receiver end).
    '%\"' expands into '^' (usually forbidden character for literals, marking end of literal).
    '%%'  expands into '%' (used to prevent possible variable interpolation, %%y5 => %y5, not y5 value).

[+] !!FU/DO receivers can now be really called without arguments.
    For all WoG 3.58 ERM receivers except SN/MP calling subcommand without parameters actually passes single
    parameter with 0 value.
    Example:
    !!CM:R; is the same as !!CM:R0;

    This is not suitable for functions, which could rely on arguments counting to implement default parameter values
    and optional parameters.
    From now !!FU:P; passes no parameters and !!FU:P6; passes single parameter.

[!] Old-style ERM macros ($...$) are deprecated, though improved and fully working.
    Note, that macro names are not cleared until game process is restarted, so prefer not to use them at all.

[*] !!SN:U was renamed to !!SN:V (Vector).

[+] !!SN:M was greatly improved. Negative indexes allow to access elements from the end of array.
    -1 - the last element
    -2 - the one before last, etc.
    It became easy to access list tail like !!SN:M(arrayId)/-1/^New value^;

    SN:M arrays resizing was improved so, that from now they can be used as lists without performance penalty.
    Memory is allocated by blocks, growing exponentially, so most of the time no allocation is really performed,
    just remembering new number of items.

    Examples:
; Create new list with 3 items, stored in saved games. Put its ID in i^heroNames^ global variable.
    !!SN:M(SN_M_AUTO_ID)/3/(SN_M_STR)/(SN_M_STORED)/?i^heroNames^;

; Set all items values at once
    !!SN:Vi^heroNames^/^Corwin^/^Deo^/^Bers^;

; Wait, forgot about 'Salamandre', add him too
    !!SN:Mi^heroNames^/d1;              increased list size by 1
    !!SN:Mi^heroNames^/-1/^Salamandre^; and written new item to the end

[+] Updated ERM Editor, based on Sublime Text.
[!] !!FU:C is deprecated and not supported anymore. It may be reused in future.

[*] ErmLegacySupport is set to 0 by default in heroes3.ini. It was introduced for old scripts, relying on
    negative y-vars automatical zeroing.

[+] All function x-parameters, which were not passed, are now initialised with zeroes. This behavior is suitable for
    optional arguments. Just don't pass odd arguments in !!FU:P/!!DO:P/etc, and they will have 0 value.

[+] Added new syntax to !!FU:A command. Set default values for parameters.
    !!FU:A#1/[#2.../#3...];
    #1 - default value for the first parameter (x1)
    #2 - default value for the second parameter...
    The command changes values only if the are not specified during function call.

    Example:
; Find object with given type and subtype
    !?FU(acl_FindObj);
; Declare two optional parameters
    !#VA / (objType:x) (objSubtype:x);
; Provide default -1 value for both parameters
    !!FU:A(NO_OBJ)/(NO_OBJ);
    ...

    Another example with string parameters.
    'Ptr' means 'pointer', index of z-variable.
    
    !?FU(acl_ShowMessage);
    !#VA / (messagePtr);
    
    !!FU:A?(numArgs:y);    get number of passed arguments
    !!VR(message:z):S^OK^; set up default message text
    !!VR(message)&(numArgs)>=(@messagePtr):Sz(messagePtr); override message text with provided value, if it's passed

    !!IF:M^%(message)^;    display message

    The last line works, because @messagePtr for the first argument (x1) will return 1.
    This is handy way to check if particular parameter was passed.

[+] It's proposed to decorate functions declarations in the following variants:

; Bried function description like:
; Hides rectangular area on the map.
  !?FU(es_HideMapSquare);
  !#VA(x1:x) (y1:x) (x2:x) (y2:x) (level:x); fast declare all parameters without description

; Alternative declaration with arguments explained:
  !?FU(es_HideMapSquare);
  !#VA(x1:x); top-left x-coordinate
  !#VA(y1:x); top-left y-coordinate
  !#VA(x2:x); bottom-right x-coordinate
  !#VA(y2:x); bottom-right y-coordinate

  Remember, that everything in !#VA before closing ';' and except of (variableName) is simply deleted
  from compiled code.

  For functions with optional arguments it's proposed to separate optional arguments from required ones by '/'.

; Adds monsters stack to hero army. Default quantity is 1.
  !?FU(es_AddMonster);
  !#VA(hero:x) (monType:x) / (monNum:x);
  !!FU:A0/0/1; specify default argument values
  !!HE(hero):C2/(monType)/(monNum)/1;

  Alternatively argument optionality may be specified in its description.
  !?FU(es_AddMonster);
  !#VA(hero:x);    hero ID
  !#VA(monType:x); monster type
  !#VA(monNum:x);  optional. Default: 1

[-] Added missing 1000 era - const.erm and 1000 era - stdlib.erm files to WoG mod.
[-] Fixed bug: z-variables with invalid negative indexes were considered mutable. Credits: gamemaster.
[-] Unknown macro names $...$ are now reported as errors, same as it was in ERA 2.x.
[-] Fixed bug: ERM must stop evaluating cached receiver parameters after first error.
Bes, gamehuntera, ZahaR, XEL, hippocamus, IQUARE, magoth, Ben, feanor, Mefista, Haart of the Abyss, Chainsaw_Charlie, Axolotl, Эроласт, igrik, Zabuza-san, KypaToP_HM, Barin, Lokos, arblade_official, Grossmaster
27 Feb 2020, 03:32 Era II Рус
Вышло обновление HoMM 3 ERA
Текущая версия: 2.9.11

Кратко: небольшое обновление, восстанавливающее работоспособность старых карт и модов, а также включающее несколько новых фишек для разработчиков и игроков.

Добавлен плагин «Журнал Заданий» от igrik. Позволяет удобно просматривать содержание заданий и перемещать экран к требуемой хижине провидца.
Стало проще использовать локализуемые строки на ЕРМ (синтаксис %T() в литералах).
Восстановлена работа оригинального генератора псевдослучайных чисел. Препятствия в бою более не меняются при перезагрузке. Качественный ГСЧ «Вихрь Мерсена» перенесён на ЕРМ команду VR:T.
И другие мелкие исправления (h3 structures and constants.txt, макросы для ЕРМ редактора от Algor, исправление названий событий).

Скачать
Скачать мод WoG Scripts

Код
Version 2.9.11
------------------------
[+] Added Quest Dialog plugin by igrik. It allows to easily view quests contents and move view to seer huts.

[+] Added %T(translatable_key_from_json) interpolation in ^...^ strings. Thus json texts without parameters may be inserted directly.
    Example: !!IF:M^Welcome to {%T(mymod.woody_castle_object)}!^;

[+] Heroes 3 PRNG was restored. VR:R uses it, as in old times. Mersenne Twister PRNG was moved to VR:T command.
    Mersenne Twister generator state is NOT synchronized between remote PCs automatically. Do not use it in
    battles for you mod to be compatible with multiplayer.

[+] Included macros for Erm Editor, enabling automatical indentation and comment insertion via ALT + END. Credits: Algor.
[+] Added "h3 structures and constants.txt" by BTB/RoseCavalier to Help directory.
[*] Reallowed SN:K#1/#2/#3/#4 to work with strings.
[-] Fixed OnUnequipArt and OnEquipArt named events. They were called instead of each other.
Bes, Mefista, igrik, Odin, Ethereal
13 Feb 2020, 04:11 Brave New World
переделка старой карты из Клинка Армагеддона
Хантера, дружище, ты жив? )) С днём рождения!
Пост по карте в ВК: https://vk.com/wall-936488_76832
gamehuntera, XEL
12 Feb 2020, 04:20 Era II Рус
Вышло обновление HoMM 3 ERA
Текущая версия: 2.9.10

Что нового ?

Мод «WoG Scripts» получил несколько исправлений и был благополучно отправлен на пенсию. Теперь он не является частью установщика Эры, но его можно скачать и установить отдельно.
ERM движок научился игнорировать пробельные символы и переводы строк между командами, а также не трактовать точку с запятой как команду.
Улучшен вывод ошибок ЕРМ: чаще правильно показывается точное местоположение проблемного места.
Обновлена утилита MMArchive до свежей версии 1.3.1

Скачать
Скачать мод WoG Scripts
Bes, hippocamus, magoth, Mefista, igrik, Ethereal
06 Feb 2020, 03:02 Era II Рус
Вышло обновление HoMM 3 ERA
Текущая версия: 2.9.9

Что нового ?

Появилась возможность прерывать/продолжать циклы верхних уровней с использованием команд !!br и !!co.
Рудиментарная универсальная команда отключения ресиверов XX:Z была удалена.
Исправлен ЕРМ интерпретатор: теперь любое число пробелов перед командами воспринимается корректно. Меньше багов, чище код.
Досадная ошибка, запарывающая сохранённые игры, исправлена.
Данная версия идеально подходит для нового мода «Расширенные Жилища»

Скачать: https://mods.hmm35.ru/Era%20Latest.exe
Bes, hippocamus, magoth, igrik, Ethereal

22 страниц V   1 2 3 > » 
Текстовая версия Сейчас: 29 March 2024 - 01:13
Copyright by Алексей Крючков
Strategy Gamez by GrayMage
Programming by Degtyarev Dmitry
  Яндекс.Метрика