Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Simplify and improve the logic for passability calculations #9404

Draft
wants to merge 10 commits into
base: master
Choose a base branch
from

Conversation

ihhub
Copy link
Owner

@ihhub ihhub commented Jan 2, 2025

This pull request fixes multiple places with object passabilities:

  • single tile Mandrake objects made by an original Editor have invalid layers

This is how single tile Mandrake's passability look like in the original Editor (highlighted by a yellow color):
image

Notice that dark red tiles are for object parts while grey color is used for shadows. All other objects have the correct layer type.

A tile with top part of Oasis object was not being updated properly.

  • somehow Oasis object is considered as a short object. This pull request fixes a bug in our code but keep the passability logic the same as in the original game.

This is how Oasis's passability is shown in the original Editor (highlighted by a yellow color):
image

Somehow, in the original game the top tiles of Oasis are passable o_O

  • one variant of Rock object has a shadow part being marked as object layer in the original Editor (highlighted by a yellow color):
    image

  • tiles with no objects or objects that do not affect passability must not be affected by a tile below. This isn't true in the original game but it led to broken gameplay, like Colossal Cavern map.

This is how it looks on master branch and in the original game:
image

and this is how it looks in this branch:
image

The tile which is pointed by cursor has no objects except shadows but somehow it was marked as impassible.

Map master branch wrong tiles this branch wrong tiles
Alteris 9728, 9729 (Oasis top part)
Alteris2 - -
Arrax the Jerk - -
Beltway - -
Black Forest 8376 (unverifable) 8376 (unverifable)
Broken Alliance - -
Clouds of Xeen 8105 (Oasis top part)
Colossal Cavern
Decisions - -
Enroth - -
Fortress Isle
Good vs. Evil - -
Great War II - -
Heroes
Leopoldville - -
Lost Continent - -
Might vs. Magic
Revolution
Seven Lakes
Teleporters - -
Terrain Wars - -
The Road Home - -
THUNK - -
Warrior Knight
Winterlands - -
Witch Hunt - -

(*) only tiles which have different passability were being tested on the OG

How differences in passabilities were detected:

  1. Comment out lines 587-741 in interface_gamearea.cpp file.
  2. Uncomment line 59 in view_world.cpp file.
  3. Set debug values in fheroes2.cfg file to 65535.
  4. Check out master branch
  5. Compile and run the engine.
  6. New Game --> Standard --> select a map --> set only Knight as a starting race --> Start the game --> open View World for each map.
  7. Repeat step 6 for desired maps.
  8. Check out this branch.
  9. Change line 67 in interface_gamearea.cpp file. to const std::string saveFilePrefix = "_new";
  10. Run steps 5-7.
  11. Modify fheroes2.cpp file with the following code:
bool substract( const fheroes2::Sprite & image1, const fheroes2::Sprite & image2, fheroes2::Sprite & output )
{
    assert( image1.width() == image2.width() && image1.height() == image2.height() );

    output.resize( image1.width(), image1.height() );
    output.reset();

    const uint8_t * in1 = image1.image();
    const uint8_t * in1End = in1 + image1.width() * image1.height();
    const uint8_t * in2 = image2.image();
    uint8_t * out = output.image();

    bool isDiff = false;

    for ( ; in1 != in1End; ++in1, ++in2, ++out ) {
        *out = *in1 - *in2;

        isDiff = isDiff || ( *in1 != *in2 );
    }

    return isDiff;
}

...
        const std::vector<std::string> mapNames = { "Alteris", "Alteris2", "Arrax the Jerk", "Beltway", "Black Forest", "Broken Alliance", "Clouds of Xeen",
                                                    "Colossal Cavern", "Decisions", "Enroth", "Fortress Isle", "Good vs. Evil", "Great War II", "Heroes",
                                                    "Leopoldville", "Lost Continent", "Might vs. Magic", "Revolution", "Seven Lakes", "Teleporters", "Terrain Wars",
                                                    "The Road Home", "THUNK", "Warrior Knight", "Winterlands", "Witch Hunt" };

        for ( const std::string & name : mapNames ) {
            fheroes2::Sprite masterBranch;
            fheroes2::Sprite thisBranch;
            fheroes2::Sprite diff;

            fheroes2::Load( name + "_old.bmp", masterBranch );
            fheroes2::Load( name + "_new.bmp", thisBranch );
            if ( substract( masterBranch, thisBranch, diff ) ) {
                fheroes2::Save( diff, name + "_diff.bmp" );
            }
            else {
                fheroes2::Save( diff, name + "_no_diff.bmp" );
            }
        }
  1. Observe the results.

@ihhub ihhub added improvement New feature, request or improvement logic Things related to game logic labels Jan 2, 2025
@ihhub ihhub added this to the 1.1.6 milestone Jan 2, 2025
@ihhub ihhub self-assigned this Jan 2, 2025
@ihhub ihhub marked this pull request as draft January 2, 2025 15:33
Copy link

sonarqubecloud bot commented Jan 5, 2025

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
improvement New feature, request or improvement logic Things related to game logic
Projects
None yet
Development

Successfully merging this pull request may close these issues.

1 participant