Auto-attack: bow shots chain at full speed, arts start by their cooldown; hang watchdog

- The shot end's button check (0x4def52) answers "held" for the auto-attack
  target, like the melee swing end.
- An art order counts as started when the art's cooldown rises, so bow arts
  and arts ordered mid-swing hand over to auto-attack.
- re/crash.cpp: a watchdog writes sacred_re_hang.dmp when the engine tick
  stops for 10 s while the game is in front.

Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
This commit is contained in:
khallaandClaude Opus 5.5 committed 2026-10-18 01:29:29 +02:00
1 parent 432cac2ccf
commit 184c7058fd
6 files changed
+125 -13

No files matched your search

+3
View File
@@ -2,6 +2,7 @@
#include <vector>
#include "re/crash.h"
#include "re/hook.h"
namespace game {
@@ -57,6 +58,7 @@ void __fastcall Engine_Tick(void* self, void* edx, void* event);
RE_HOOK(0x0060f1d0, Engine_Tick);
void __fastcall Engine_Tick(void* self, void* edx, void* event) {
Engine_Tick_original(self, edx, event);
re::EngineHeartbeat(true);
if (self) {
for (EngineTickFn callback : TickCallbacks()) {
callback(static_cast<uint8_t*>(self));
@@ -80,6 +82,7 @@ void* __fastcall Engine_Construct(void* self, void* edx, uint32_t arg) {
void __fastcall Engine_Destruct(void* self, void* edx);
RE_HOOK(0x0060d5e0, Engine_Destruct);
void __fastcall Engine_Destruct(void* self, void* edx) {
re::EngineHeartbeat(false);
for (GameEndFn callback : GameEndCallbacks()) {
callback();
}
+3 -1
View File
@@ -70,13 +70,15 @@ constexpr size_t kCreatureY = 0x20;
// +0x150: low word the current action, high word its phase; 0x10000 when
// standing idle. Measured on the hero: 1 walking (also up to a target),
// 3 weapon attack, 4 casting a spell (2026-10-16), 6 dying, 8 an art seen
// after walking up (2026-10-15, presumably a combat move).
// after walking up (2026-10-15, presumably a combat move), 5 a shot with a
// projectile weapon (bow, 2026-10-18).
constexpr size_t kCreatureAction = 0x150;
enum CreatureAction : int32_t {
kActionIdle = 0,
kActionWalk = 1,
kActionAttack = 3,
kActionCastSpell = 4,
kActionShoot = 5,
kActionDying = 6,
kActionCombatMove = 8,
};