[4.5.9] Different Collisions for Different Game Modes

JamesNES

Well-known member
This is a pretty simple one I just had to write. I wanted to make a town but most of the collisions that you'd need in a dungeon just don't apply, so those are wasted. I figured if you swap out all your normal collision scripts for town-specific collisions, it'd be easier to make multiple warps on a single screen. Eg one goes to an inn, one goes to a house, etc. There are other ways to do that but this is by far the simplest. I've tested this in the adventure module, but I don't see why it wouldn't work for anything else (famous last words).

This uses a screen flag to tell when you're on a town screen, and then just redirects the tile collision script to use different scripts.

I'm using the third screen flag to tell the game to use the different collision set:

1685342330644.png

The only file we need to change in this is Bank18.asm.

By default, at line 52 (66 in adventure module) you'll see:

Code:
                    LDY temp
                    LDA TileTableLo,y
                    STA temp16
                    LDA TileTableHi,y
                    STA temp16+1

This gets changed to:

Code:
                    LDY temp
                    ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
                    ;;    Multiple Tile Script Starts Here  ;;
                    ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
                    LDA ScreenFlags00
                    AND #%00100000
                    BEQ +notTownTiles
                        LDA TownTileTableLo,y 
                        STA temp16 
                        LDA TownTileTableHi,y 
                        STA temp16+1
                        JMP +gotTileAddress
                    +notTownTiles 
                    
                    
                    ;;Use default tile types 
                    LDA TileTableLo,y 
                    STA temp16 
                    LDA TileTableHi,y 
                    STA temp16+1
                    
                    +gotTileAddress

                    ;;Ends here

Then at the very bottom of the file you can add the references to your new tile scripts:

Code:
TownTileTableLo:
    .db <TownTile_00, <TownTile_01, <TownTile_02, <TownTile_03, <TownTile_04, <TownTile_05, <TownTile_06, <TownTile_07
    .db <TownTile_08, <TownTile_09, <TownTile_10, <TownTile_11, <TownTile_12, <TownTile_13, <TownTile_14, <TownTile_15

TownTileTableHi:
    .db >TownTile_00, >TownTile_01, >TownTile_02, >TownTile_03, >TownTile_04, >TownTile_05, >TownTile_06, >TownTile_07
    .db >TownTile_08, >TownTile_09, >TownTile_10, >TownTile_11, >TownTile_12, >TownTile_13, >TownTile_14, >TownTile_15

TownTile_00:
    RTS 
    
TownTile_01: 
    .include ROOT\Game\TownTiles\TownTile01.asm 
    RTS 
    
TownTile_02: 
    .include ROOT\Game\TownTiles\TownTile02.asm 
    RTS 

TownTile_03: 
    .include ROOT\Game\TownTiles\TownTile03.asm 
    RTS 

TownTile_04: 
    .include ROOT\Game\TownTiles\TownTile04.asm 
    RTS 

TownTile_05: 
    .include ROOT\Game\TownTiles\TownTile05.asm 
    RTS 

TownTile_06: 
    .include ROOT\Game\TownTiles\TownTile06.asm 
    RTS 
    
TownTile_07: 
    .include ROOT\Game\TownTiles\TownTile07.asm 
    RTS 
    
TownTile_08: 
    .include ROOT\Game\TownTiles\TownTile08.asm 
    RTS 

TownTile_09: 
    .include ROOT\Game\TownTiles\TownTile09.asm 
    RTS 

TownTile_10: 
    .include ROOT\Game\TownTiles\TownTile10.asm 
    RTS 

TownTile_11: 
    .include ROOT\Game\TownTiles\TownTile11.asm 
    RTS 

TownTile_12: 
    .include ROOT\Game\TownTiles\TownTile12.asm 
    RTS
    
TownTile_13: 
    .include ROOT\Game\TownTiles\TownTile13.asm 
    RTS 
    
TownTile_14: 
    .include ROOT\Game\TownTiles\TownTile14.asm 
    RTS 
    
TownTile_15: 
    .include ROOT\Game\TownTiles\TownTile15.asm 
    RTS

Each include will have to point to where you've put your new scripts. If you don't need to use all 16 you can just delete the .include line.

You can also mix and match with your normal tile types, like:

Code:
TownTileTableLo:
    .db <TownTile_00, <Tile_01, <TownTile_02, <TownTile_03, <TownTile_04, <TownTile_05, <TownTile_06, <TownTile_07
    .db <TownTile_08, <TownTile_09, <TownTile_10, <TownTile_11, <TownTile_12, <TownTile_13, <TownTile_14, <TownTile_15

TownTileTableHi:
    .db >TownTile_00, >Tile_01, >TownTile_02, >TownTile_03, >TownTile_04, >TownTile_05, >TownTile_06, >TownTile_07
    .db >TownTile_08, >TownTile_09, >TownTile_10, >TownTile_11, >TownTile_12, >TownTile_13, >TownTile_14, >TownTile_15

To have #$01 still be the same solid tile script you'd normally use.


Downsides are that there's an extra LDA, AND and BEQ for every object on screen. I did do a workaround so it's only once per frame, but you'd need to use 4 zero page bytes that aren't affected by the object subroutine. So I went for simplicity.
 
Top Bottom