Current time: 21.04.2024, 15:36 Hello There, Guest! (LoginRegister)
Language: english | russian  

Post Reply 
Threaded Mode | Linear Mode
Ваши вопросы по ERM-скриптам
Author Message
Berserker Offline
Administrators

Posts: 16488
Post: #8716

Этот код нужно в тему готовых решений. С головы его не выдумать быстро, рабочий вариант.


Скачать Герои 3 Эра и всё, что с ней связано / ERA 2.46f для старых модов
Поддержать проект
10.03.2022 21:40
Find all posts by this user Quote this message in a reply
major Offline

Posts: 132
Post: #8717

igrik, просто супер! Работает идеально.

По ходу дела возник еще один вопрос. Эра позволяет блокировать регенерацию существ, но вот элексир продолжает работать. Как его можно отключить?
11.03.2022 18:19
Find all posts by this user Quote this message in a reply
Archer30 Offline
Moderators

Posts: 1117
Post: #8718

igrik, awesome!

I wonder if customising Necromancy is still a thing? I wish the code can help someone if it has not yet been revealed.

GitHub

Edit: Fixed a typo thanks to daemon_n


Latest ERA mods and scripts in development - My GitHub
(This post was last modified: 12.03.2022 04:17 by Archer30.)
11.03.2022 19:27
Find all posts by this user Quote this message in a reply
daemon_n Offline
Administrators

Posts: 4338
Post: #8719

Archer30,
!!FU|(side)=-1/i^battle_hero_%(side)^=(NO_HERO):E


Image: widget.png?style=banner2

Новейший Heroes 3 Launcher
12.03.2022 01:15
Visit this user's website Find all posts by this user Quote this message in a reply
Archer30 Offline
Moderators

Posts: 1117
Post: #8720

Looking for help with a function for getting a random position for summoning with BU:S

Input: Side for summoning, is Double Wide (monster Flag)
Output: random available position for BU:S summoning (both hex must not be unoccupied if doubled wide)

It looks like I have achieved undesirable outcome with it...I would like to know what could possibly be wrong.
I understand that the code must be optimised a lot more



Latest ERA mods and scripts in development - My GitHub
(This post was last modified: 13.03.2022 18:27 by Archer30.)
13.03.2022 18:05
Find all posts by this user Quote this message in a reply
Berserker Offline
Administrators

Posts: 16488
Post: #8721

Seems like code is valid.

But I would generate single array of valid positions first and then generate single random value in 0..array_size - 1 range. Value under generated index will be the result.
---------------------------------
Another variant is to fill "positions" array of 186 items with 0..185 values correspondingly.
Also define variable numCandidates = 186 (array size).

Repeat until free position is found or numCandidates = 0.
Generate random value in 0..numCandidates - 1 range.

Battle pos = positions[generated random index]
If position is not free or invalid, then

positions[generated random index] = numCandidates - 1; we make array index to actually point to another position, thus virtually removing tested hex from further check attempts
numCandidates = numCandidates - 1; decrease positions array size, because the last position is not referrered by "generated random index".

------------------------

For instance, imagine there are max 8 positions on battle: 0..7.

Define positions array = (0, 1, 2, 3, 4, 5, 6, 7).
numCandidates = 8

generated random value 0..(8 - 1) = 3
Look at positions array at index 3. positions[3] = 3.
Check battle hex #3, it's occupied.

positions[3] = numCandidates - 1 = 7
numCandidates = numCandidates - 1 = 7
Thus we have updated positions array: (0, 1, 2, 7, 4, 5, 6)

As you see, new array does not have hex #3 anymore.

Both approaches guarantee to find free positions. Your variant with 100 generations may fail for unlucky generated sequences.


Скачать Герои 3 Эра и всё, что с ней связано / ERA 2.46f для старых модов
Поддержать проект
13.03.2022 22:30
Find all posts by this user Quote this message in a reply
Archer30 Offline
Moderators

Posts: 1117
Post: #8722

Berserker, great approaches! Well, I had a hard time using the function I wrote. For some reason, I can't get the second IF:M shown on my screen from time to time. This is so weird as there is no FU:E in the function, it is technically not possible...

At the moment I need some advice on writing. Is there a convenient way to bypass invalid positions (0, 17, 34, those hex out of the battlefield)? Both BU:E/BU:D returns -1, making it not possible to
distinguish them with empty hex.

Alternatively, is there a way to remove mutual elements from both arrays? You know what I am thinking about Rolleyes


Latest ERA mods and scripts in development - My GitHub
(This post was last modified: 15.03.2022 04:55 by Archer30.)
14.03.2022 19:58
Find all posts by this user Quote this message in a reply
wessonsm Offline

Posts: 779
Post: #8723

(14.03.2022 19:58)Archer30 Wrote:  Is there a convenient way to filter invalid positions (0, 17, 34, those hex out of the battlefield)?
I think something like this:
14.03.2022 21:12
Find all posts by this user Quote this message in a reply
wessonsm Offline

Posts: 779
Post: #8724

Archer30, here is the complete function. It has not yet been fully tested, but at first glance it works.

15.03.2022 13:55
Find all posts by this user Quote this message in a reply
Archer30 Offline
Moderators

Posts: 1117
Post: #8725

wessonsm, thanks. I forgot that it can be solved by math lol.

Umm. Usually, I would use &(variable) for booleans. My (isDoubleWide) and (isAvailPos) are either 0 or 1. I believe we were introduced &(variable) some versions around ERA 3.5, it equals to &(variable)>(FALSE). Is that a bad practice though?


Latest ERA mods and scripts in development - My GitHub
15.03.2022 13:59
Find all posts by this user Quote this message in a reply
Berserker Offline
Administrators

Posts: 16488
Post: #8726

Quote:Umm. Usually, I would use &(variable) for booleans. My (isDoubleWide) and (isAvailPos) are either 0 or 1. I believe we were introduced &(variable) some versions around ERA 3.5, it equals to &(variable)>(FALSE). Is that a bad practice though?
No, it's a good practice. wessonsm just was not aware of this improvement.

P.S. Чуток дооформил код выше.


Скачать Герои 3 Эра и всё, что с ней связано / ERA 2.46f для старых модов
Поддержать проект
15.03.2022 14:16
Find all posts by this user Quote this message in a reply
wessonsm Offline

Posts: 779
Post: #8727

Archer30, Berserker. I really missed this moment in the changelog, apparently I didn’t read well.
Sorry for the misinformation and thanks for the clarification.
I'll edit my post to avoid misleading others.
15.03.2022 14:30
Find all posts by this user Quote this message in a reply
Archer30 Offline
Moderators

Posts: 1117
Post: #8728

wessonsm, no need to worry about it Sm

Well, I come up with another question with BU:S summoning, I want to write a function with the following requirements, and I'd like to know the best approach to it.

The task of the function: Find a random but closest position to the given position for BU:S summoning. The monster for summoning is known for whether it is double wide, and the side for summoning.
Input: a known Position, Is Double Wide, Side.
Output: Closest position to the known position for BU:S


I have two approaches in mind, first one:
- loop through all the hex on the battlefield
- Check the distance between the looped hex and the known hex
- Collect the hex with the smallest distance and put to the array
- Get a random position from this array

Second one:
- Check for the closet positions around the given position. The first batch would be the six hex around the target
- If none is available, check for a larger hex around the target, repeat this if nothing is found again

Basically, the first approach is easier to code, but I am worried about its efficiency. The second approach should be faster, but it is a bit tricky to code. If I can't combine the steps, I might end up checking for every single position manually.

Any thoughts?


Latest ERA mods and scripts in development - My GitHub
(This post was last modified: 15.03.2022 17:42 by Archer30.)
15.03.2022 14:48
Find all posts by this user Quote this message in a reply
wessonsm Offline

Posts: 779
Post: #8729

Archer30,
It seems that the first method will be quite effective if we have a simple and fast function for calculating the distance between two hexes.
The second way can be implemented if you come up with a fairly simple algorithm for bypassing hexes along a spiral path.
I think this can be done by converting the hex numbers to pairs of coordinates (row, column).
The second way seems more interesting to me, and I will think about it.
15.03.2022 16:37
Find all posts by this user Quote this message in a reply
Berserker Offline
Administrators

Posts: 16488
Post: #8730

We already had distance calculating function (based on row and column) on this forum in ERM 1, probably. I have old code in Pascal.

BATTLEFIELD_LINE_SIZE = 17;

Code:
FUNCTION CalculateDistance (SrcPos, DstPos: INTEGER): INTEGER;
VAR
  DistanceX:  INTEGER;
  DistanceY:  INTEGER;
  x1, x2:     INTEGER;
  y1, y2:     INTEGER;

BEGIN
  x1  :=  SrcPos MOD BATTLEFIELD_LINE_SIZE;
  y1  :=  SrcPos DIV BATTLEFIELD_LINE_SIZE;
  x2  :=  DstPos MOD BATTLEFIELD_LINE_SIZE;
  y2  :=  DstPos DIV BATTLEFIELD_LINE_SIZE;

  DistanceY :=  ABS(y1 - y2);
  DistanceX :=  ABS(x1 * 2 - (y1 AND 1) - x2 * 2 + (y2 AND 1)) - DistanceY;
  
  RESULT  :=  (DistanceY * 2 + Math.Max(DistanceX, 0)) DIV 2;
END; // .FUNCTION CalculateDistance


Скачать Герои 3 Эра и всё, что с ней связано / ERA 2.46f для старых модов
Поддержать проект
15.03.2022 17:37
Find all posts by this user Quote this message in a reply
« Next Oldest | Next Newest »
Post Reply 


Forum Jump:

Powered by MyBB Copyright © 2002-2024 MyBB Group