Decomped AvoidEnemies()

This commit is contained in:
AnonymousRandomPerson 2022-03-12 23:03:48 -05:00
parent 905723858c
commit e040eafca8
12 changed files with 642 additions and 834 deletions

View File

@ -4,7 +4,7 @@
.syntax unified
.text
thumb_func_start CanTakeItem
CanTakeItem:
push {r4-r6,lr}
@ -236,7 +236,7 @@ _0807B082:
adds r1, r4, 0x4
mov r0, r8
adds r0, 0x4
bl GetMaxPositionDifference
bl GetDistance
cmp r9, r0
ble _0807B098
mov r9, r0
@ -595,7 +595,7 @@ DecideMovement:
beq _0807B37C
adds r0, r6, 0
adds r1, r4, 0
bl GetMaxPositionDifference
bl GetDistance
cmp r0, 0x2
bne _0807B354
_0807B348:
@ -944,752 +944,4 @@ _0807B5CE:
bx r0
thumb_func_end DecideMovement
thumb_func_start AvoidEnemies
AvoidEnemies:
push {r4-r7,lr}
mov r7, r10
mov r6, r9
mov r5, r8
push {r5-r7}
sub sp, 0x30
adds r7, r0, 0
ldr r0, _0807B61C
str r0, [sp, 0x8]
ldr r1, [r7, 0x70]
str r1, [sp, 0x10]
adds r0, r7, 0
bl GetEntityRoomIndex
lsls r0, 24
lsrs r0, 24
mov r10, r0
ldr r0, _0807B620
ldr r1, [r0]
ldr r2, _0807B624
adds r0, r1, r2
ldrb r0, [r0]
cmp r0, 0
beq _0807B62C
ldr r3, _0807B628
adds r0, r1, r3
movs r4, 0x14
mov r9, r4
b _0807B64C
.align 2, 0
_0807B61C: .4byte 0x000f423f
_0807B620: .4byte gDungeonGlobalData
_0807B624: .4byte 0x000037fc
_0807B628: .4byte 0x000135cc
_0807B62C:
ldr r2, [sp, 0x10]
ldrb r0, [r2, 0x6]
cmp r0, 0
beq _0807B644
ldr r3, _0807B640
adds r0, r1, r3
movs r4, 0x4
mov r9, r4
b _0807B64C
.align 2, 0
_0807B640: .4byte 0x0001357c
_0807B644:
ldr r2, _0807B790
adds r0, r1, r2
movs r3, 0x10
mov r9, r3
_0807B64C:
movs r4, 0
str r4, [sp, 0xC]
movs r1, 0xFF
str r1, [sp, 0x4]
mov r8, r4
cmp r4, r9
bge _0807B6D8
adds r6, r0, 0
_0807B65C:
ldr r4, [r6]
adds r0, r4, 0
bl EntityExists
lsls r0, 24
cmp r0, 0
beq _0807B6CE
adds r0, r7, 0
adds r1, r4, 0
bl CanSee
lsls r0, 24
cmp r0, 0
beq _0807B6CE
ldr r0, _0807B794
ldr r0, [r0]
ldr r2, _0807B798
adds r0, r2
ldrb r0, [r0]
cmp r0, 0
beq _0807B69A
adds r0, r7, 0
adds r1, r4, 0
movs r2, 0
movs r3, 0x1
bl CanTarget
lsls r0, 24
lsrs r0, 24
cmp r0, 0x1
bne _0807B6CE
_0807B69A:
adds r1, r4, 0x4
adds r0, r7, 0x4
bl GetMaxPositionDifference
ldr r3, [sp, 0x8]
cmp r3, r0
ble _0807B6CE
str r0, [sp, 0x8]
str r4, [sp, 0xC]
adds r0, r4, 0
bl GetEntityRoomIndex
lsls r0, 24
lsrs r0, 24
str r0, [sp, 0x4]
ldr r1, [sp, 0x10]
adds r1, 0x88
ldr r4, [sp, 0xC]
ldr r0, [r4, 0x4]
str r0, [r1]
ldr r0, [sp, 0x10]
movs r2, 0xB6
lsls r2, 1
adds r1, r0, r2
ldr r0, [r4, 0x4]
str r0, [r1]
_0807B6CE:
adds r6, 0x4
movs r3, 0x1
add r8, r3
cmp r8, r9
blt _0807B65C
_0807B6D8:
ldr r0, _0807B79C
ldr r4, [sp, 0x8]
cmp r4, r0
bne _0807B6E2
b _0807B906
_0807B6E2:
ldr r0, [sp, 0x10]
adds r0, 0x88
str r0, [sp, 0x28]
ldr r1, [sp, 0x10]
adds r1, 0x78
str r1, [sp, 0x24]
ldr r2, [sp, 0x4]
cmp r10, r2
beq _0807B6F6
b _0807B8E0
_0807B6F6:
mov r3, r10
cmp r3, 0xFF
bne _0807B6FE
b _0807B8E0
_0807B6FE:
movs r4, 0x4
ldrsh r0, [r7, r4]
movs r2, 0x6
ldrsh r1, [r7, r2]
bl GetMapTile_1
ldrh r1, [r0]
movs r0, 0x8
ands r0, r1
cmp r0, 0
beq _0807B7B2
ldrh r0, [r7, 0x6]
lsls r0, 16
ldrh r5, [r7, 0x4]
orrs r5, r0
movs r4, 0
_0807B71E:
ldr r1, _0807B7A0
lsls r0, r4, 2
adds r0, r1
ldrh r1, [r0]
ldrh r3, [r7, 0x4]
adds r1, r3
lsls r1, 16
ldrh r0, [r0, 0x2]
ldrh r2, [r7, 0x6]
adds r0, r2
lsls r0, 16
lsrs r5, r1, 16
orrs r5, r0
lsls r0, r5, 16
asrs r0, 16
asrs r1, r5, 16
bl GetMapTile_1
ldrb r0, [r0, 0x9]
cmp r0, r10
beq _0807B758
adds r0, r7, 0
adds r1, r4, 0
mov r2, sp
bl CanMoveForward
lsls r0, 24
cmp r0, 0
bne _0807B75E
_0807B758:
adds r4, 0x1
cmp r4, 0x7
ble _0807B71E
_0807B75E:
cmp r4, 0x8
bne _0807B7A4
movs r0, 0x8
bl DungeonRandomCapped
adds r4, r0, 0
movs r0, 0x6
ldr r3, [sp, 0x24]
strb r0, [r3]
ldr r0, _0807B7A0
lsls r1, r4, 2
adds r1, r0
ldrh r0, [r1]
ldrh r4, [r7, 0x4]
adds r0, r4
ldr r2, [sp, 0x28]
strh r0, [r2]
ldrh r0, [r1, 0x2]
ldrh r7, [r7, 0x6]
adds r0, r7
ldr r1, [sp, 0x10]
adds r1, 0x8A
strh r0, [r1]
movs r0, 0x1
b _0807B910
.align 2, 0
_0807B790: .4byte 0x0001358c
_0807B794: .4byte gDungeonGlobalData
_0807B798: .4byte 0x000037fc
_0807B79C: .4byte 0x000f423f
_0807B7A0: .4byte gAdjacentTileOffsets
_0807B7A4:
movs r0, 0x5
ldr r3, [sp, 0x24]
strb r0, [r3]
ldr r4, [sp, 0x28]
str r5, [r4]
movs r0, 0x1
b _0807B910
_0807B7B2:
ldr r0, _0807B8D0
mov r2, r10
lsls r1, r2, 7
ldr r3, _0807B8D4
adds r1, r3
ldr r0, [r0]
adds r1, r0, r1
str r1, [sp, 0x18]
lsls r1, r2, 1
ldr r4, _0807B8D8
adds r0, r4
adds r0, r1
movs r2, 0
ldrsh r1, [r0, r2]
str r1, [sp, 0x14]
ldr r3, _0807B8DC
str r3, [sp, 0x20]
movs r4, 0
str r4, [sp, 0x1C]
ldr r0, [sp, 0xC]
movs r1, 0x4
ldrsh r3, [r0, r1]
movs r2, 0x4
ldrsh r0, [r7, r2]
subs r2, r3, r0
cmp r2, 0
bge _0807B7EA
negs r2, r2
_0807B7EA:
ldr r4, [sp, 0xC]
movs r0, 0x6
ldrsh r1, [r4, r0]
movs r4, 0x6
ldrsh r0, [r7, r4]
subs r1, r0
mov r8, r1
cmp r1, 0
bge _0807B802
mov r0, r8
negs r0, r0
mov r8, r0
_0807B802:
cmp r8, r2
bge _0807B808
mov r8, r2
_0807B808:
movs r1, 0
mov r9, r1
ldr r2, [sp, 0x10]
adds r2, 0x8A
str r2, [sp, 0x2C]
ldr r4, [sp, 0x1C]
ldr r0, [sp, 0x14]
cmp r4, r0
bge _0807B8AA
mov r10, r3
ldr r6, [sp, 0x18]
_0807B81E:
movs r1, 0
ldrsh r3, [r6, r1]
mov r2, r10
subs r0, r2, r3
cmp r0, 0
bge _0807B82C
negs r0, r0
_0807B82C:
ldr r4, [sp, 0xC]
movs r1, 0x6
ldrsh r4, [r4, r1]
mov r12, r4
movs r4, 0x2
ldrsh r2, [r6, r4]
mov r4, r12
subs r1, r4, r2
cmp r1, 0
bge _0807B842
negs r1, r1
_0807B842:
cmp r1, r0
bge _0807B848
adds r1, r0, 0
_0807B848:
movs r0, 0x4
ldrsh r4, [r7, r0]
subs r0, r3, r4
movs r3, 0x6
ldrsh r5, [r7, r3]
subs r3, r2, r5
movs r2, 0x1
negs r2, r2
cmp r0, r2
bge _0807B85E
adds r0, r2, 0
_0807B85E:
cmp r3, r2
bge _0807B864
adds r3, r2, 0
_0807B864:
cmp r0, 0x1
ble _0807B86A
movs r0, 0x1
_0807B86A:
cmp r3, 0x1
ble _0807B870
movs r3, 0x1
_0807B870:
adds r0, r4, r0
mov r4, r10
subs r2, r4, r0
cmp r2, 0
bge _0807B87C
negs r2, r2
_0807B87C:
adds r0, r5, r3
mov r3, r12
subs r0, r3, r0
cmp r0, 0
bge _0807B888
negs r0, r0
_0807B888:
cmp r0, r2
bge _0807B88E
adds r0, r2, 0
_0807B88E:
cmp r0, r8
blt _0807B89E
ldr r4, [sp, 0x20]
cmp r4, r1
bge _0807B89E
mov r0, r9
str r0, [sp, 0x1C]
str r1, [sp, 0x20]
_0807B89E:
adds r6, 0x4
movs r1, 0x1
add r9, r1
ldr r2, [sp, 0x14]
cmp r9, r2
blt _0807B81E
_0807B8AA:
ldr r3, [sp, 0x20]
cmp r3, 0
blt _0807B8E0
movs r0, 0x5
ldr r4, [sp, 0x24]
strb r0, [r4]
ldr r1, [sp, 0x1C]
lsls r0, r1, 2
ldr r2, [sp, 0x18]
adds r0, r2
ldrh r1, [r0]
ldr r3, [sp, 0x28]
strh r1, [r3]
ldrh r0, [r0, 0x2]
ldr r4, [sp, 0x2C]
strh r0, [r4]
movs r0, 0x1
b _0807B910
.align 2, 0
_0807B8D0: .4byte gDungeonGlobalData
_0807B8D4: .4byte 0x00010884
_0807B8D8: .4byte 0x00010844
_0807B8DC: .4byte 0xfff0bdc1
_0807B8E0:
movs r0, 0x5
ldr r1, [sp, 0x24]
strb r0, [r1]
ldr r2, [sp, 0xC]
ldrh r1, [r2, 0x4]
ldrh r0, [r7, 0x4]
subs r1, r0
subs r0, r1
ldr r3, [sp, 0x28]
strh r0, [r3]
ldrh r0, [r2, 0x6]
ldrh r1, [r7, 0x6]
subs r0, r1
subs r1, r0
ldr r0, [sp, 0x10]
adds r0, 0x8A
strh r1, [r0]
movs r0, 0x1
b _0807B910
_0807B906:
adds r0, r7, 0
bl Explore
lsls r0, 24
lsrs r0, 24
_0807B910:
add sp, 0x30
pop {r3-r5}
mov r8, r3
mov r9, r4
mov r10, r5
pop {r4-r7}
pop {r1}
bx r1
thumb_func_end AvoidEnemies
thumb_func_start Explore
Explore:
push {r4-r7,lr}
mov r7, r10
mov r6, r9
mov r5, r8
push {r5-r7}
sub sp, 0x10
adds r6, r0, 0
ldr r7, [r6, 0x70]
bl GetEntityRoomIndex
lsls r0, 24
lsrs r3, r0, 24
cmp r3, 0xFF
bne _0807B9DC
movs r0, 0
str r0, [sp, 0x4]
adds r4, r7, 0
adds r4, 0x46
ldrb r0, [r4]
adds r0, 0x4
mov r8, r0
movs r0, 0x7
mov r1, r8
ands r1, r0
mov r8, r1
adds r0, r6, 0
bl IsAtJunction
lsls r0, 24
mov r9, r4
cmp r0, 0
beq _0807B96C
movs r0, 0x8
bl DungeonRandomCapped
strb r0, [r4]
movs r2, 0x1
str r2, [sp, 0x4]
_0807B96C:
movs r3, 0
movs r4, 0x78
adds r4, r7
mov r10, r4
adds r0, r7, 0
adds r0, 0x88
str r0, [sp, 0x8]
adds r7, 0x8A
ldr r5, _0807B9D4
_0807B97E:
mov r1, r9
ldrb r0, [r1]
ldr r1, [r5]
adds r4, r0, r1
movs r0, 0x7
ands r4, r0
ldr r2, [sp, 0x4]
cmp r2, 0
beq _0807B994
cmp r4, r8
beq _0807B9AA
_0807B994:
adds r0, r6, 0
adds r1, r4, 0
mov r2, sp
str r3, [sp, 0xC]
bl CanMoveForward
lsls r0, 24
ldr r3, [sp, 0xC]
cmp r0, 0
beq _0807B9AA
b _0807BB42
_0807B9AA:
adds r5, 0x4
adds r3, 0x1
cmp r3, 0x7
ble _0807B97E
movs r0, 0x8
bl DungeonRandomCapped
movs r1, 0x6
mov r3, r10
strb r1, [r3]
ldr r1, _0807B9D8
lsls r0, 2
adds r0, r1
ldrh r1, [r0]
ldrh r4, [r6, 0x4]
adds r1, r4
ldr r2, [sp, 0x8]
strh r1, [r2]
ldrh r0, [r0, 0x2]
b _0807BB5A
.align 2, 0
_0807B9D4: .4byte gFaceDirectionIncrements
_0807B9D8: .4byte gAdjacentTileOffsets
_0807B9DC:
ldr r0, _0807BA30
ldr r2, [r0]
lsls r1, r3, 1
ldr r4, _0807BA34
adds r0, r2, r4
adds r0, r1
movs r4, 0
ldrsh r1, [r0, r4]
mov r8, r1
lsls r0, r3, 7
ldr r1, _0807BA38
adds r0, r1
adds r2, r0
mov r9, r2
movs r2, 0x8A
lsls r2, 1
adds r0, r7, r2
ldr r0, [r0]
cmp r0, 0
beq _0807BA40
movs r0, 0x8
bl DungeonRandomCapped
adds r2, r7, 0
adds r2, 0x78
movs r1, 0x6
strb r1, [r2]
ldr r1, _0807BA3C
lsls r0, 2
adds r0, r1
ldrh r1, [r0]
ldrh r3, [r6, 0x4]
adds r1, r3
adds r2, 0x10
strh r1, [r2]
ldrh r0, [r0, 0x2]
ldrh r6, [r6, 0x6]
adds r0, r6
adds r1, r7, 0
adds r1, 0x8A
strh r0, [r1]
b _0807BB60
.align 2, 0
_0807BA30: .4byte gDungeonGlobalData
_0807BA34: .4byte 0x00010844
_0807BA38: .4byte 0x00010884
_0807BA3C: .4byte gAdjacentTileOffsets
_0807BA40:
adds r0, r7, 0
adds r0, 0x78
ldrb r1, [r0]
mov r10, r0
cmp r1, 0x4
beq _0807BAA2
mov r4, r8
cmp r4, 0
bne _0807BA84
movs r0, 0x8
bl DungeonRandomCapped
adds r4, r0, 0
movs r0, 0x6
mov r1, r10
strb r0, [r1]
ldr r0, _0807BA80
lsls r2, r4, 2
adds r2, r0
ldrh r0, [r2]
ldrh r3, [r6, 0x4]
adds r0, r3
adds r1, r7, 0
adds r1, 0x88
strh r0, [r1]
ldrh r0, [r2, 0x2]
ldrh r6, [r6, 0x6]
adds r0, r6
adds r1, 0x2
strh r0, [r1]
b _0807BB60
.align 2, 0
_0807BA80: .4byte gAdjacentTileOffsets
_0807BA84:
movs r5, 0
_0807BA86:
mov r0, r8
bl DungeonRandomCapped
adds r4, r0, 0
ldr r0, [r6, 0x4]
lsls r1, r4, 2
mov r4, r9
adds r2, r1, r4
ldr r1, [r2]
cmp r0, r1
bne _0807BB18
adds r5, 0x1
cmp r5, 0x9
ble _0807BA86
_0807BAA2:
movs r1, 0x4
ldrsh r0, [r6, r1]
movs r2, 0x6
ldrsh r1, [r6, r2]
bl GetMapTile_1
ldrh r1, [r0]
movs r0, 0x8
ands r0, r1
cmp r0, 0
beq _0807BB60
movs r0, 0x8
bl DungeonRandomCapped
adds r4, r0, 0
movs r3, 0
mov r9, r3
_0807BAC4:
movs r0, 0x7
ands r4, r0
movs r0, 0x4
ldrsh r2, [r6, r0]
ldr r0, _0807BB14
lsls r1, r4, 2
adds r1, r0
movs r3, 0
ldrsh r0, [r1, r3]
adds r2, r0
mov r8, r2
movs r0, 0x6
ldrsh r2, [r6, r0]
movs r3, 0x2
ldrsh r0, [r1, r3]
adds r5, r2, r0
mov r0, r8
adds r1, r5, 0
bl GetMapTile_1
ldrb r0, [r0, 0x9]
cmp r0, 0xFF
bne _0807BB04
adds r0, r6, 0
adds r1, r4, 0
mov r2, sp
adds r2, 0x1
bl CanMoveForward
lsls r0, 24
cmp r0, 0
bne _0807BB2E
_0807BB04:
movs r0, 0x1
add r9, r0
adds r4, 0x1
mov r1, r9
cmp r1, 0x7
ble _0807BAC4
b _0807BB60
.align 2, 0
_0807BB14: .4byte gAdjacentTileOffsets
_0807BB18:
movs r0, 0x4
mov r3, r10
strb r0, [r3]
ldrh r1, [r2]
adds r0, r7, 0
adds r0, 0x88
strh r1, [r0]
ldrh r1, [r2, 0x2]
adds r0, 0x2
strh r1, [r0]
b _0807BB60
_0807BB2E:
movs r0, 0x3
mov r4, r10
strb r0, [r4]
adds r0, r7, 0
adds r0, 0x88
mov r1, r8
strh r1, [r0]
adds r0, 0x2
strh r5, [r0]
b _0807BB60
_0807BB42:
movs r0, 0x3
mov r2, r10
strb r0, [r2]
ldr r0, _0807BB74
lsls r1, r4, 2
adds r1, r0
ldrh r0, [r1]
ldrh r3, [r6, 0x4]
adds r0, r3
ldr r4, [sp, 0x8]
strh r0, [r4]
ldrh r0, [r1, 0x2]
_0807BB5A:
ldrh r6, [r6, 0x6]
adds r0, r6
strh r0, [r7]
_0807BB60:
movs r0, 0x1
add sp, 0x10
pop {r3-r5}
mov r8, r3
mov r9, r4
mov r10, r5
pop {r4-r7}
pop {r1}
bx r1
.align 2, 0
_0807BB74: .4byte gAdjacentTileOffsets
thumb_func_end Explore
thumb_func_start sub_807BB78
sub_807BB78:
ldr r3, [r0, 0x70]
adds r1, r3, 0
adds r1, 0x78
movs r2, 0
strb r2, [r1]
adds r1, 0x10
ldr r0, [r0, 0x4]
str r0, [r1]
adds r0, r3, 0
adds r0, 0x80
str r2, [r0]
subs r0, 0x4
strh r2, [r0]
bx lr
thumb_func_end sub_807BB78
.align 2, 0

326
asm/code_807B920.s Normal file
View File

@ -0,0 +1,326 @@
#include "asm/constants/gba_constants.inc"
#include "asm/macros.inc"
.syntax unified
.text
thumb_func_start Explore
Explore:
push {r4-r7,lr}
mov r7, r10
mov r6, r9
mov r5, r8
push {r5-r7}
sub sp, 0x10
adds r6, r0, 0
ldr r7, [r6, 0x70]
bl GetEntityRoomIndex
lsls r0, 24
lsrs r3, r0, 24
cmp r3, 0xFF
bne _0807B9DC
movs r0, 0
str r0, [sp, 0x4]
adds r4, r7, 0
adds r4, 0x46
ldrb r0, [r4]
adds r0, 0x4
mov r8, r0
movs r0, 0x7
mov r1, r8
ands r1, r0
mov r8, r1
adds r0, r6, 0
bl IsAtJunction
lsls r0, 24
mov r9, r4
cmp r0, 0
beq _0807B96C
movs r0, 0x8
bl DungeonRandomCapped
strb r0, [r4]
movs r2, 0x1
str r2, [sp, 0x4]
_0807B96C:
movs r3, 0
movs r4, 0x78
adds r4, r7
mov r10, r4
adds r0, r7, 0
adds r0, 0x88
str r0, [sp, 0x8]
adds r7, 0x8A
ldr r5, _0807B9D4
_0807B97E:
mov r1, r9
ldrb r0, [r1]
ldr r1, [r5]
adds r4, r0, r1
movs r0, 0x7
ands r4, r0
ldr r2, [sp, 0x4]
cmp r2, 0
beq _0807B994
cmp r4, r8
beq _0807B9AA
_0807B994:
adds r0, r6, 0
adds r1, r4, 0
mov r2, sp
str r3, [sp, 0xC]
bl CanMoveForward
lsls r0, 24
ldr r3, [sp, 0xC]
cmp r0, 0
beq _0807B9AA
b _0807BB42
_0807B9AA:
adds r5, 0x4
adds r3, 0x1
cmp r3, 0x7
ble _0807B97E
movs r0, 0x8
bl DungeonRandomCapped
movs r1, 0x6
mov r3, r10
strb r1, [r3]
ldr r1, _0807B9D8
lsls r0, 2
adds r0, r1
ldrh r1, [r0]
ldrh r4, [r6, 0x4]
adds r1, r4
ldr r2, [sp, 0x8]
strh r1, [r2]
ldrh r0, [r0, 0x2]
b _0807BB5A
.align 2, 0
_0807B9D4: .4byte gFaceDirectionIncrements
_0807B9D8: .4byte gAdjacentTileOffsets
_0807B9DC:
ldr r0, _0807BA30
ldr r2, [r0]
lsls r1, r3, 1
ldr r4, _0807BA34
adds r0, r2, r4
adds r0, r1
movs r4, 0
ldrsh r1, [r0, r4]
mov r8, r1
lsls r0, r3, 7
ldr r1, _0807BA38
adds r0, r1
adds r2, r0
mov r9, r2
movs r2, 0x8A
lsls r2, 1
adds r0, r7, r2
ldr r0, [r0]
cmp r0, 0
beq _0807BA40
movs r0, 0x8
bl DungeonRandomCapped
adds r2, r7, 0
adds r2, 0x78
movs r1, 0x6
strb r1, [r2]
ldr r1, _0807BA3C
lsls r0, 2
adds r0, r1
ldrh r1, [r0]
ldrh r3, [r6, 0x4]
adds r1, r3
adds r2, 0x10
strh r1, [r2]
ldrh r0, [r0, 0x2]
ldrh r6, [r6, 0x6]
adds r0, r6
adds r1, r7, 0
adds r1, 0x8A
strh r0, [r1]
b _0807BB60
.align 2, 0
_0807BA30: .4byte gDungeonGlobalData
_0807BA34: .4byte 0x00010844
_0807BA38: .4byte 0x00010884
_0807BA3C: .4byte gAdjacentTileOffsets
_0807BA40:
adds r0, r7, 0
adds r0, 0x78
ldrb r1, [r0]
mov r10, r0
cmp r1, 0x4
beq _0807BAA2
mov r4, r8
cmp r4, 0
bne _0807BA84
movs r0, 0x8
bl DungeonRandomCapped
adds r4, r0, 0
movs r0, 0x6
mov r1, r10
strb r0, [r1]
ldr r0, _0807BA80
lsls r2, r4, 2
adds r2, r0
ldrh r0, [r2]
ldrh r3, [r6, 0x4]
adds r0, r3
adds r1, r7, 0
adds r1, 0x88
strh r0, [r1]
ldrh r0, [r2, 0x2]
ldrh r6, [r6, 0x6]
adds r0, r6
adds r1, 0x2
strh r0, [r1]
b _0807BB60
.align 2, 0
_0807BA80: .4byte gAdjacentTileOffsets
_0807BA84:
movs r5, 0
_0807BA86:
mov r0, r8
bl DungeonRandomCapped
adds r4, r0, 0
ldr r0, [r6, 0x4]
lsls r1, r4, 2
mov r4, r9
adds r2, r1, r4
ldr r1, [r2]
cmp r0, r1
bne _0807BB18
adds r5, 0x1
cmp r5, 0x9
ble _0807BA86
_0807BAA2:
movs r1, 0x4
ldrsh r0, [r6, r1]
movs r2, 0x6
ldrsh r1, [r6, r2]
bl GetMapTile_1
ldrh r1, [r0]
movs r0, 0x8
ands r0, r1
cmp r0, 0
beq _0807BB60
movs r0, 0x8
bl DungeonRandomCapped
adds r4, r0, 0
movs r3, 0
mov r9, r3
_0807BAC4:
movs r0, 0x7
ands r4, r0
movs r0, 0x4
ldrsh r2, [r6, r0]
ldr r0, _0807BB14
lsls r1, r4, 2
adds r1, r0
movs r3, 0
ldrsh r0, [r1, r3]
adds r2, r0
mov r8, r2
movs r0, 0x6
ldrsh r2, [r6, r0]
movs r3, 0x2
ldrsh r0, [r1, r3]
adds r5, r2, r0
mov r0, r8
adds r1, r5, 0
bl GetMapTile_1
ldrb r0, [r0, 0x9]
cmp r0, 0xFF
bne _0807BB04
adds r0, r6, 0
adds r1, r4, 0
mov r2, sp
adds r2, 0x1
bl CanMoveForward
lsls r0, 24
cmp r0, 0
bne _0807BB2E
_0807BB04:
movs r0, 0x1
add r9, r0
adds r4, 0x1
mov r1, r9
cmp r1, 0x7
ble _0807BAC4
b _0807BB60
.align 2, 0
_0807BB14: .4byte gAdjacentTileOffsets
_0807BB18:
movs r0, 0x4
mov r3, r10
strb r0, [r3]
ldrh r1, [r2]
adds r0, r7, 0
adds r0, 0x88
strh r1, [r0]
ldrh r1, [r2, 0x2]
adds r0, 0x2
strh r1, [r0]
b _0807BB60
_0807BB2E:
movs r0, 0x3
mov r4, r10
strb r0, [r4]
adds r0, r7, 0
adds r0, 0x88
mov r1, r8
strh r1, [r0]
adds r0, 0x2
strh r5, [r0]
b _0807BB60
_0807BB42:
movs r0, 0x3
mov r2, r10
strb r0, [r2]
ldr r0, _0807BB74
lsls r1, r4, 2
adds r1, r0
ldrh r0, [r1]
ldrh r3, [r6, 0x4]
adds r0, r3
ldr r4, [sp, 0x8]
strh r0, [r4]
ldrh r0, [r1, 0x2]
_0807BB5A:
ldrh r6, [r6, 0x6]
adds r0, r6
strh r0, [r7]
_0807BB60:
movs r0, 0x1
add sp, 0x10
pop {r3-r5}
mov r8, r3
mov r9, r4
mov r10, r5
pop {r4-r7}
pop {r1}
bx r1
.align 2, 0
_0807BB74: .4byte gAdjacentTileOffsets
thumb_func_end Explore
thumb_func_start sub_807BB78
sub_807BB78:
ldr r3, [r0, 0x70]
adds r1, r3, 0
adds r1, 0x78
movs r2, 0
strb r2, [r1]
adds r1, 0x10
ldr r0, [r0, 0x4]
str r0, [r1]
adds r0, r3, 0
adds r0, 0x80
str r2, [r0]
subs r0, 0x4
strh r2, [r0]
bx lr
thumb_func_end sub_807BB78
.align 2, 0

View File

@ -0,0 +1,8 @@
#ifndef GUARD_DUNGEON_AI_MOVEMENT_1_H
#define GUARD_DUNGEON_AI_MOVEMENT_1_H
#include "dungeon_entity.h"
bool8 AvoidEnemies(struct DungeonEntity *pokemon);
#endif

View File

@ -74,7 +74,7 @@ struct DungeonGlobalData
u8 fill104C0[0x104C4 - 0x104C0];
/* 0x104C4 */ struct MapRoom roomData[MAX_ROOM_COUNT];
u8 fill10764[0x10844 - 0x10764];
/* 0x10844 */ u16 numRoomExits[MAX_ROOM_COUNT];
/* 0x10844 */ s16 numRoomExits[MAX_ROOM_COUNT];
u8 fill10874[0x10884 - 0x10874];
/* 0x10884 */ struct Position roomExits[MAX_ROOM_COUNT][32]; // Arrays of room exits for each room.
u8 fill11444[0x1356C - 0x11484];

View File

@ -9,6 +9,7 @@ extern const struct Position gAdjacentTileOffsets[NUM_DIRECTIONS];
bool8 EntityExists(struct DungeonEntity *pokemon);
u32 GetEntityType(struct DungeonEntity *entity);
u8 GetEntityRoomIndex(struct DungeonEntity *entity);
struct DungeonEntityData *GetTrapData(struct DungeonEntity *entity);
struct ItemSlot *GetItemData(struct DungeonEntity *entity);
struct MapTile *GetMapTileForDungeonEntity_2(struct DungeonEntity *entity);

View File

@ -4,5 +4,6 @@
#include "position.h"
s32 CalculateFacingDir(struct Position *originPos, struct Position *targetPos);
s32 GetDistance(struct Position *pos1, struct Position *pos2);
#endif

View File

@ -246,6 +246,8 @@ SECTIONS {
asm/code_8077274.o(.text);
src/dungeon_ai_movement.o(.text);
asm/code_807AEBC.o(.text);
src/dungeon_ai_movement_1.o(.text);
asm/code_807B920.o(.text);
src/dungeon_ai_attack.o(.text);
asm/code_807CABC.o(.text);
src/targeting_flags.o(.text);

View File

@ -252,6 +252,8 @@ void DecideAttack(struct DungeonEntity *pokemon)
{
if (maxWeight != moveTargetResults[i].moveWeight)
{
// Only the move(s) with the highest weight can be used, instead of a weighted random.
// This has the side effect of making the AI use a STAB ranged move consistently when at a distance.
moveTargetResults[i].moveWeight = 0;
}
total += moveTargetResults[i].moveWeight;
@ -524,29 +526,29 @@ s32 FindMoveTarget(struct MoveTargetResults *moveTargetResults, struct DungeonEn
bool8 IsTargetInLineRange(struct DungeonEntity *user, struct DungeonEntity *target, s32 range)
{
s32 posDiffX = user->posWorld.x - target->posWorld.x;
s32 posDiffY, maxPosDiff;
s32 distanceX = user->posWorld.x - target->posWorld.x;
s32 distanceY, distance;
s32 direction;
if (posDiffX < 0)
if (distanceX < 0)
{
posDiffX = -posDiffX;
distanceX = -distanceX;
}
posDiffY = user->posWorld.y - target->posWorld.y;
if (posDiffY < 0)
distanceY = user->posWorld.y - target->posWorld.y;
if (distanceY < 0)
{
posDiffY = -posDiffY;
distanceY = -distanceY;
}
maxPosDiff = posDiffY;
if (posDiffY < posDiffX)
distance = distanceY;
if (distanceY < distanceX)
{
maxPosDiff = posDiffX;
distance = distanceX;
}
if (maxPosDiff > RANGED_ATTACK_RANGE || maxPosDiff > range)
if (distance > RANGED_ATTACK_RANGE || distance > range)
{
return FALSE;
}
direction = -1;
if (posDiffX == posDiffY)
if (distanceX == distanceY)
{
if (user->posWorld.x < target->posWorld.x &&
(user->posWorld.y < target->posWorld.y || user->posWorld.y > target->posWorld.y))
@ -857,20 +859,20 @@ bool8 TargetRegularAttack(struct DungeonEntity *pokemon, u32 *targetDir, bool8 c
bool8 IsTargetStraightAhead(struct DungeonEntity *pokemon, struct DungeonEntity *targetPokemon, s32 facingDir, s32 maxRange)
{
s32 posDiffX = pokemon->posWorld.x - targetPokemon->posWorld.x;
s32 distanceX = pokemon->posWorld.x - targetPokemon->posWorld.x;
s32 effectiveMaxRange;
if (posDiffX < 0)
if (distanceX < 0)
{
posDiffX = -posDiffX;
distanceX = -distanceX;
}
effectiveMaxRange = pokemon->posWorld.y - targetPokemon->posWorld.y;
if (effectiveMaxRange < 0)
{
effectiveMaxRange = -effectiveMaxRange;
}
if (effectiveMaxRange < posDiffX)
if (effectiveMaxRange < distanceX)
{
effectiveMaxRange = posDiffX;
effectiveMaxRange = distanceX;
}
if (effectiveMaxRange > maxRange)
{

View File

@ -323,23 +323,23 @@ void FindRockItemTargets(struct DungeonEntity *pokemon, struct ItemSlot *item, s
if (EntityExists(targetPokemon) && pokemon != targetPokemon &&
CanSee(pokemon, targetPokemon) && CanTarget(pokemon, targetPokemon, FALSE, TRUE) == TARGET_CAPABILITY_CAN_TARGET)
{
s32 posDiffX;
s32 maxPosDiff;
posDiffX = targetPokemon->posWorld.x - pokemon->posWorld.x;
if (posDiffX < 0)
s32 distanceX;
s32 distance;
distanceX = targetPokemon->posWorld.x - pokemon->posWorld.x;
if (distanceX < 0)
{
posDiffX = -posDiffX;
distanceX = -distanceX;
}
maxPosDiff = targetPokemon->posWorld.y - pokemon->posWorld.y;
if (maxPosDiff < 0)
distance = targetPokemon->posWorld.y - pokemon->posWorld.y;
if (distance < 0)
{
maxPosDiff = -maxPosDiff;
distance = -distance;
}
if (maxPosDiff < posDiffX)
if (distance < distanceX)
{
maxPosDiff = posDiffX;
distance = distanceX;
}
if (maxPosDiff <= 10)
if (distance <= 10)
{
struct Position *newPotentialTarget;
if (!ignoreRollChance)
@ -361,22 +361,22 @@ void FindRockItemTargets(struct DungeonEntity *pokemon, struct ItemSlot *item, s
void TargetThrownItem(struct DungeonEntity *pokemon, struct DungeonEntity *targetPokemon, struct ItemSlot *item, s32 targetingFlags, bool8 ignoreRollChance)
{
s32 posDiffX = pokemon->posWorld.x - targetPokemon->posWorld.x;
s32 posDiffY;
s32 distanceX = pokemon->posWorld.x - targetPokemon->posWorld.x;
s32 distanceY;
s32 targetDirection;
posDiffX = posDiffX < 0 ? -posDiffX : posDiffX;
posDiffY = pokemon->posWorld.y - targetPokemon->posWorld.y;
posDiffY = posDiffY < 0 ? -posDiffY : posDiffY;
distanceX = distanceX < 0 ? -distanceX : distanceX;
distanceY = pokemon->posWorld.y - targetPokemon->posWorld.y;
distanceY = distanceY < 0 ? -distanceY : distanceY;
if (pokemon->entityData->itemStatus == ITEM_STATUS_NONE)
{
s32 maxPosDiff = posDiffY < posDiffX ? posDiffX : posDiffY;
if (maxPosDiff > RANGED_ATTACK_RANGE)
s32 distance = distanceY < distanceX ? distanceX : distanceY;
if (distance > RANGED_ATTACK_RANGE)
{
return;
}
}
targetDirection = -1;
if (posDiffX == posDiffY)
if (distanceX == distanceY)
{
if (pokemon->posWorld.x < targetPokemon->posWorld.x && pokemon->posWorld.y < targetPokemon->posWorld.y)
{

View File

@ -7,10 +7,10 @@
#include "dungeon_action.h"
#include "dungeon_pokemon_attributes.h"
#include "dungeon_random.h"
#include "dungeon_ai_movement_1.h"
#include "dungeon_ai_targeting_1.h"
#include "number_util.h"
extern bool8 AvoidEnemies(struct DungeonEntity *pokemon);
extern bool8 CanTakeItem(struct DungeonEntity *pokemon);
extern bool8 ChooseTargetPosition(struct DungeonEntity *pokemon);
extern void DecideMovement(struct DungeonEntity *pokemon, bool8 showRunAwayEffect);

215
src/dungeon_ai_movement_1.c Normal file
View File

@ -0,0 +1,215 @@
#include "global.h"
#include "dungeon_ai_movement_1.h"
#include "constants/targeting.h"
#include "dungeon_ai_targeting_2.h"
#include "dungeon_global_data.h"
#include "dungeon_map_access.h"
#include "dungeon_random.h"
#include "dungeon_util.h"
#include "dungeon_visibility.h"
#include "position_util.h"
#define INFINITY 999999
extern bool8 CanMoveForward(struct DungeonEntity *pokemon, s32 facingDir, bool8 *pokemonInFront);
extern bool8 Explore(struct DungeonEntity *pokemon);
bool8 AvoidEnemies(struct DungeonEntity *pokemon)
{
bool8 pokemonInFront;
u8 closestTargetRoomIndex;
s32 closestTargetDistance = INFINITY;
struct DungeonEntity *closestTarget;
struct DungeonEntityData *pokemonData = pokemon->entityData;
u8 roomIndex = GetEntityRoomIndex(pokemon);
struct DungeonEntity **possibleTargets;
s32 numPossibleTargets;
s32 i;
if (gDungeonGlobalData->decoyActive)
{
possibleTargets = gDungeonGlobalData->allPokemon;
numPossibleTargets = DUNGEON_MAX_POKEMON;
}
else if (pokemonData->isEnemy)
{
possibleTargets = gDungeonGlobalData->teamPokemon;
numPossibleTargets = MAX_TEAM_MEMBERS;
}
else
{
possibleTargets = gDungeonGlobalData->wildPokemon;
numPossibleTargets = DUNGEON_MAX_WILD_POKEMON;
}
closestTarget = NULL;
closestTargetRoomIndex = CORRIDOR_ROOM_INDEX;
for (i = 0; i < numPossibleTargets; i++)
{
struct DungeonEntity *target = possibleTargets[i];
if (EntityExists(target) && CanSee(pokemon, target))
{
s32 distance;
if (gDungeonGlobalData->decoyActive && CanTarget(pokemon, target, FALSE, TRUE) != TARGET_CAPABILITY_CAN_TARGET)
{
continue;
}
distance = GetDistance(&pokemon->posWorld, &target->posWorld);
if (closestTargetDistance > distance)
{
closestTargetDistance = distance;
closestTarget = target;
closestTargetRoomIndex = GetEntityRoomIndex(target);
pokemonData->targetMovePosition = closestTarget->posWorld;
pokemonData->targetPosition = closestTarget->posWorld;
}
}
}
if (closestTargetDistance != INFINITY)
{
if (roomIndex == closestTargetRoomIndex && roomIndex != CORRIDOR_ROOM_INDEX)
{
struct MapTile *tile = GetMapTile_1(pokemon->posWorld.x, pokemon->posWorld.y);
if (tile->tileType & TILE_TYPE_ROOM_EXIT)
{
struct Position targetMovePosition;
s32 targetDir;
targetMovePosition.x = pokemon->posWorld.x;
targetMovePosition.y = pokemon->posWorld.y;
// Scan for a direction leading outside the room.
for (targetDir = 0; targetDir < NUM_DIRECTIONS; targetDir++)
{
struct MapTile *adjacentTile;
targetMovePosition.x = pokemon->posWorld.x + gAdjacentTileOffsets[targetDir].x;
targetMovePosition.y = pokemon->posWorld.y + gAdjacentTileOffsets[targetDir].y;
adjacentTile = GetMapTile_1(targetMovePosition.x, targetMovePosition.y);
if (adjacentTile->roomIndex != roomIndex && CanMoveForward(pokemon, targetDir, &pokemonInFront))
{
break;
}
}
if (targetDir == NUM_DIRECTIONS)
{
targetDir = DungeonRandomCapped(NUM_DIRECTIONS);
pokemonData->movementAction = MOVEMENT_ACTION_FACE_RANDOM_DIRECTION;
pokemonData->targetMovePosition.x = pokemon->posWorld.x + gAdjacentTileOffsets[targetDir].x;
pokemonData->targetMovePosition.y = pokemon->posWorld.y + gAdjacentTileOffsets[targetDir].y;
return TRUE;
}
else
{
pokemonData->movementAction = MOVEMENT_ACTION_RUN_AWAY_FROM_ENEMY;
pokemonData->targetMovePosition = targetMovePosition;
return TRUE;
}
}
else
{
// At this point, the Pokémon is running directly away from the target.
// If there are any room exits that the Pokémon can head towards without moving
// closer to the target, head towards the furthest eligible exit.
s32 numRoomExits;
struct Position *roomExits = gDungeonGlobalData->roomExits[roomIndex];
s32 furthestTargetExitIndex;
s32 furthestTargetToExitDistance;
s32 distanceX;
s32 pokemonToTargetDistance;
s32 i;
numRoomExits = gDungeonGlobalData->numRoomExits[roomIndex];
furthestTargetToExitDistance = -INFINITY;
furthestTargetExitIndex = 0;
distanceX = closestTarget->posWorld.x - pokemon->posWorld.x;
if (distanceX < 0)
{
distanceX = -distanceX;
}
pokemonToTargetDistance = closestTarget->posWorld.y - pokemon->posWorld.y;
if (pokemonToTargetDistance < 0)
{
pokemonToTargetDistance = -pokemonToTargetDistance;
}
if (pokemonToTargetDistance < distanceX)
{
pokemonToTargetDistance = distanceX;
}
for (i = 0; i < numRoomExits; i++)
{
s32 targetToExitDistance;
s32 pokemonToExitSignX, pokemonToExitSignY;
s32 adjacentToTargetDistanceX, adjacentToTargetDistance;
s32 distanceX = closestTarget->posWorld.x - roomExits[i].x;
if (distanceX < 0)
{
distanceX = -distanceX;
}
targetToExitDistance = closestTarget->posWorld.y - roomExits[i].y;
if (targetToExitDistance < 0)
{
targetToExitDistance = -targetToExitDistance;
}
if (targetToExitDistance < distanceX)
{
targetToExitDistance = distanceX;
}
pokemonToExitSignX = roomExits[i].x - pokemon->posWorld.x;
pokemonToExitSignY = roomExits[i].y - pokemon->posWorld.y;
if (pokemonToExitSignX < -1)
{
pokemonToExitSignX = -1;
}
if (pokemonToExitSignY < -1)
{
pokemonToExitSignY = -1;
}
if (pokemonToExitSignX > 1)
{
pokemonToExitSignX = 1;
}
if (pokemonToExitSignY > 1)
{
pokemonToExitSignY = 1;
}
adjacentToTargetDistanceX = closestTarget->posWorld.x - (pokemon->posWorld.x + pokemonToExitSignX);
if (adjacentToTargetDistanceX < 0)
{
adjacentToTargetDistanceX = -adjacentToTargetDistanceX;
}
adjacentToTargetDistance = closestTarget->posWorld.y - (pokemon->posWorld.y + pokemonToExitSignY);
if (adjacentToTargetDistance < 0)
{
adjacentToTargetDistance = -adjacentToTargetDistance;
}
if (adjacentToTargetDistance < adjacentToTargetDistanceX)
{
adjacentToTargetDistance = adjacentToTargetDistanceX;
}
// BUG: The Pokémon is allowed to move towards the exit and remain the same
// distance away from the target.
// This leads to odd behavior like turning around when near an exit.
// Using a > instead of a >= would avoid this issue.
// For an example of this behavior, see https://youtu.be/plke4eU_PU8?t=435.
if (adjacentToTargetDistance >= pokemonToTargetDistance &&
furthestTargetToExitDistance < targetToExitDistance)
{
furthestTargetExitIndex = i;
furthestTargetToExitDistance = targetToExitDistance;
}
}
if (furthestTargetToExitDistance >= 0)
{
pokemonData->movementAction = MOVEMENT_ACTION_RUN_AWAY_FROM_ENEMY;
pokemonData->targetMovePosition.x = roomExits[furthestTargetExitIndex].x;
pokemonData->targetMovePosition.y = roomExits[furthestTargetExitIndex].y;
return TRUE;
}
}
}
pokemonData->movementAction = MOVEMENT_ACTION_RUN_AWAY_FROM_ENEMY;
pokemonData->targetMovePosition.x = pokemon->posWorld.x - (closestTarget->posWorld.x - pokemon->posWorld.x);
pokemonData->targetMovePosition.y = pokemon->posWorld.y - (closestTarget->posWorld.y - pokemon->posWorld.y);
return TRUE;
}
else
{
return Explore(pokemon);
}
}

View File

@ -4,62 +4,63 @@
#include "constants/direction.h"
const s32 gFacingDirMapping[3][3] = {
{DIRECTION_NORTHWEST, DIRECTION_NORTH, DIRECTION_NORTHEAST},
{DIRECTION_WEST, DIRECTION_SOUTH, DIRECTION_EAST},
{DIRECTION_SOUTHWEST, DIRECTION_SOUTH, DIRECTION_SOUTHEAST}
{DIRECTION_NORTHWEST, DIRECTION_NORTH, DIRECTION_NORTHEAST},
{DIRECTION_WEST, DIRECTION_SOUTH, DIRECTION_EAST},
{DIRECTION_SOUTHWEST, DIRECTION_SOUTH, DIRECTION_SOUTHEAST}
};
s32 CalculateFacingDir(struct Position *originPos, struct Position *targetPos)
{
s32 facingDir;
s32 yDiff;
s32 xDiff;
s32 facingDir;
s32 yDiff;
s32 xDiff;
xDiff = targetPos->x - originPos->x;
yDiff = targetPos->y - originPos->y;
if (xDiff == 0 && yDiff == 0)
{
facingDir = DIRECTION_SOUTH;
}
else
{
if (xDiff > 0)
xDiff = targetPos->x - originPos->x;
yDiff = targetPos->y - originPos->y;
if (xDiff == 0 && yDiff == 0)
{
xDiff = 1;
facingDir = DIRECTION_SOUTH;
}
if (yDiff > 0)
else
{
yDiff = 1;
if (xDiff > 0)
{
xDiff = 1;
}
if (yDiff > 0)
{
yDiff = 1;
}
if (xDiff <= -1)
{
xDiff = -1;
}
if (yDiff <= -1)
{
yDiff = -1;
}
facingDir = gFacingDirMapping[yDiff + 1][xDiff + 1];
}
if (xDiff <= -1)
{
xDiff = -1;
}
if (yDiff <= -1)
{
yDiff = -1;
}
facingDir = gFacingDirMapping[yDiff + 1][xDiff + 1];
}
return facingDir;
return facingDir;
}
s32 GetMaxPositionDifference(short param_1[],short param_2[])
s32 GetDistance(struct Position *pos1, struct Position *pos2)
{
s32 diff_index1;
s32 diff_index0;
diff_index0 = param_1[0] - param_2[0];
if (diff_index0 < 0) {
diff_index0 = -diff_index0;
}
diff_index1 = param_1[1] - param_2[1];
if (diff_index1 < 0) {
diff_index1 = -diff_index1;
}
if (diff_index1 < diff_index0) {
diff_index1 = diff_index0;
}
return diff_index1;
s32 distanceX = pos1->x - pos2->x;
s32 distance;
if (distanceX < 0)
{
distanceX = -distanceX;
}
distance = pos1->y - pos2->y;
if (distance < 0)
{
distance = -distance;
}
if (distance < distanceX)
{
distance = distanceX;
}
return distance;
}